SAE J1939 Explained - A Simple Intro

SAE J1939 is a key protocol in CAN bus data logging, yet it is difficult to find a really simple and understandable intro to J1939.

But we've added the secret sauce: We asked one of our non-engineers to write this article - and if he gets it, you'll get it!
[don't worry, an engineer reviewed it]

In this article, we cover:

  • J1939 basics & applications
  • J1939 message interpretation (PGNs, SPNs)
  • Five practical considerations for logging J1939 data

After this, you should be ready to log and convert J1939 raw frames into human-readable data. Let's dive in!

Note: You can also check out our video above with a smooth voice over by Samuel Fleming!


As evident from our intro to CAN bus, practically all vehicles today use the Controller Area Network (CAN bus) protocol as basis for communication between ECUs. 

However, CAN bus merely provides a tool for communication (i.e. like a telephone), not a “language” to allow more complex operations. In most commercial vehicles, this language is the SAE J1939 standard defined by the Society of Automotive Engineers (SAE). In short, J1939 provides a higher layer protocol (HLP) using CAN as the physical layer basis.

SAE J1939 Commercial Vehicle Application Examples
Fleet Management J1939 Optimization Bus WiFi IoT

In simple terms, this means that J1939 offers a standardized method for communication across ECUs, i.e. one language across manufacturers. In contrast, passenger cars typically rely on manufacturer specific protocols.

Heavy-duty vehicles (e.g. trucks and buses) is one of the most well-known applications. However, several other key industries leverage SAE J1939 today either directly or via derived standards (e.g. ISO 11783, MilCAN, NMEA 2000, FMS):

  • Foresting machinery (e.g. delimbers, forwarders, skidders, ...)
  • Mining vehicles (e.g. bulldozers, draglines, excavators, …)
  • Military vehicles (e.g. tanks, transport vehicles, …)
  • Agriculture (e.g. tractors, harvesters, …)
  • Construction (e.g. mobile hydraulics, cranes, …)
  • Fire & Rescue (e.g. ambulances, fire trucks, …)
  • Many other (e.g. ships, pumping, power generation, ...)

From a data logging perspective, SAE J1939 provides an overlay to CAN including a set of standardized messages and conversion rules that apply across a wide array of vehicles within the above areas. For this reason, a good understanding of J1939 is core in e.g. building fleet management systems.

In terms of the J1939 history, the original top level SAE J1939 document was published in 2000, though some of the underlying documents were already released back in 1994 (J1939-11, J1939-21, J1939-31). The SAE J1939 standard has replaced former standards SAE J1708 and SAE J1587.

Today, we see massive growth in IoT (Internet of Things) and transportation will be a key area of application. This is likely to be enabled through scalable fleet solutions using affordable WiFi data loggers, but the heart of such applications will be the SAE J1939 protocol. In other words, the standard will only grow in importance going forward.


Let’s get a bit more technical: 

To understand a higher layer protocol like J1939, think of the CAN standard as providing only the basic physical layer and the data link layer, i.e. the lowest two layers in the seven layered OSI model. Together, they offer the basic means of communicating small packets on the CAN bus - but not a lot more than that.

So what's a higher layer protocol?

A higher layer protocol is required to enable the communication across the large complex networks of e.g. vehicle manufacturers. 

Let's take an example:

SAE J1939 specifies how to handle “multi-packet messages”, i.e. when data larger than 8 bytes needs to be transferred. Similarly, it specifies how data is to be converted into human-readable data. It does so by providing a family of standards. For example, J1939-71 is a document detailing the information required to convert a large set of cross-manufacturer standardized J1939 messages into human-readable data (more on this below).

Several other examples of CAN based higher layer protocols exist, incl. CANopen, DeviceNet, Unified Diagnostic Services and more. These typically offer some level of standardization within their respective industries - though all of them can be extended by manufacturers. In comparison, the aforementioned passenger cars have unique standards per manufacturer.

In other words, you can use the same J1939 database file to convert e.g. engine speed across two trucks from different manufacturers - but you cannot e.g. read the data from an Audi A4 using the same IDs & scaling parameters as for a Peugeot 207.

J1939 OSI Layer Model Standards Family

Before we move on, it is worth noting some key characteristics of SAE J1939:

  • The speed is typically 250 kbit/s, though recently with support for 500 kbit/s
  • J1939 uses CAN 2.0B, i.e. an extended 29 bit identifier
  • Messages are identified by PGNs (Parameter Group Numbers), which comprise 18 of the 29 bit identifier
  • A PGN will thus contain a number of SPNs (Suspect Parameter Numbers) in the 8 data bytes reflecting parameters (e.g. RPM)
  • Messages can be broadcast, sent peer-to-peer or be requested
  • J1939 includes a large range of standard PGNs, though PGNs 00FF00 through 00FFFF are reserved for proprietary use
  • A data byte of 0xFF (255) reflects N/A data, while 0xFE (254) reflects an error
  • Multibyte variables are sent least significant byte first (Intel byte order) 
  • J1939 supports PGNs with up to 1785 bytes using a transport protocol 

We will go more in-depth on some of the above characteristics in the sections below.



If you’re reading this article, your end goal is likely to analyse converted SAE J1939 data in human-readable form

To do so, an understanding of how to interpret the raw SAE J1939 packets is key - here we provide the basics incl. PGNs and SPNs.

Let's try to explain the concept of PGNs and SPNs at the basic level: A J1939 message is "identified" via the PGN. Further, each message contains 8 data bytes. This leaves enough space to contain multiple data parameters per PGN. These individual parameters are called SPNs.

Below we go into detail on these concepts.


Let’s start with the SAE J1939 identifier, the PGN:

A PGN acts as a unique ID for looking up the function of a J1939 message and the associated data parameters (i.e. the SPNs). 

You can find this information in the SAE J1939-71 document, which provides lists of PGNs and SPNs, as well as information on how to interpret and convert the data. For an illustration of what the various PGN names may look like, cf. our J1939 PGN list.

A word of caution:

You cannot match PGNs vs the full 29 bit CAN identifier. Instead, you need to separate out the 18 bit PGN as below.

SAE J1939 PGN SPN Message Structure Example

Tip: If in doubt, use our online J1939 PGN converter to parse a full 29 bit J1939 message ID and get the PGN in decimal form.

PGN J1939 SPN Example Engine Speed

Example: Let’s assume we log a J1939 message with the extended identifier 0x0CF00401. To get the PGN, we carve out the ID starting at bit 9 with length 18 (indexed from 1) - or we apply the HEX mask 0x03FFFF00 (and a bit shift of 8 bit), which leads to the same result. The outcome is the PGN 0x0F004 or in decimal 61444. Looking this up in the SAE J1939-71 documentation we see that it’s the “Electronic Engine Controller 1 - EEC1”. 

Further, the document will have details on the PGN including priority, transmission rate and a list of the associated SPNs - cf. the example below. For this PGN, there are seven SPNs (e.g. Engine Speed, RPM), each of which can be looked up in the J1939-71 documentation for further details.

That seems simple enough, right?

Note, however, that the above is a bit simplified as the J1939 29-bit identifier can be broken further down into sub components. Specifically, the ID comprises the Priority (3 bits), PGN (18 bits) and Source Address (8 bits). Further, the PGN can be broken into four parts: Reserved (1 bit), Data Page (1 bit), PDU Format (8 bits) and PDU Specific (8 bits). However, this level of detail is less critical from a data logging perspective and will not be covered here to avoid confusion.


You may be wondering: "Are the PGNs the data parameters I'm looking for?" 

Not exactly. That's where SPNs come in:

Let’s assume we’ve identified a PGN (e.g. 61444) based on a raw 29 bit message ID (e.g. 0x0CF00401). 

For a given entry of this message ID, we also logged 8 bytes of raw data - now, how do we interpret and convert this?

J1939 Data Message Example Engine Speed RPM

Here we need to look at the SPN, which reflects the ID of a specific parameter contained within the data bytes of a given PGN.

For example consider SPN 190, Engine Speed, mentioned in the previous example (cf. below).

For simplicity, let’s assume we’re only interested in converting and analysing this particular parameter.

In that case we see from the PGN info that relevant data is in byte 4 and 5, i.e. 0x68 and 0x13. Taking the decimal form of 0x1368 (Intel byte order), we get 4968 decimal. To arrive at the RPM, we conduct a scaling of this value using the offset 0 and the scale 0.125 RPM/bit. 

The result is 621 RPM. 

Note how some data bytes in the above are FF or 255 decimal, i.e. not available. While the PGN may support SPNs in this range, this specific application does not support these parameters.

In practice, one will of course not do manual lookups in the J1939-71 documentation! 

Rather, most use software that can load J1939 DBC files for converting logged or streamed data. In a DBC context, PGNs are called “Messages” and SPNs are called “Signals”. For more on this, check out our DBC conversion article which uses SAE J1939 as a case example.


The SAE J1939 protocol supports a number of more advanced operations. These include requests, multi-packet messages, multiplexing and more. Below we cover some of these.


Most J1939 messages are broadcast to the CAN bus, but some need to be requested. This is achieved using the ‘request message’ (PGN 59904), which is the only J1939 message with only 3 bytes of data. It has priority 6, a variable transmit rate and can either be sent as a global or specific address request. The data bytes 1-3 should contain the requested PGN (Intel byte order). Examples of requested J1939 messages include the diagnostic messages (DM). As for OBD2, you can use our Transmit feature to set up SAE J1939 request messages.


The PGN and SPN examples from before are based on a J1939 message size of 8 data bytes, which will be the case for the majority of messages. However, two other possible sizes exist: The 3 bytes request message above - and variable size messages.

The latter is used in the J1939 standard to allow communication of data packets beyond the usual 8 bytes limit of the CAN bus format. These are referred to as J1939 multi-frame or multi-packet messages. J1939 specifies how to deconstruct, transfer and reassemble the packets - a process referred to as the Transport Protocol (cf. J1939-21). Two types exist: The Connection Mode (intended for a specific device) and the BAM (Broadcast Announce Message) which is intended for the entire network.

In simple terms, the BAM works by the transmitting ECU sending an initial BAM packet to set up the transfer. The BAM specifies the multi-packet PGN identifier as well as the number of data bytes and packets to be sent. It is then followed by up to 255 packets of data. Each of these 255 packets use the first data byte to specify the sequence number (1 up to 255), followed by 7 bytes of data. The max number of bytes per multi-packet message is therefore 7 bytes x 255 = 1785 bytes. The final packet will contain at least one byte of data, followed by unused bytes set to FF. In the BAM type scenario, the time between messages is 50-200 ms. Finally, a conversion software can reassemble the multiple entries of 7 data bytes into a single string and handle it according to the multi-packet PGN and SPN specifications. 


To round things off, this section provides five considerations for choosing a J1939 data logger solution for your J1939 application.

Logger vs. Interface: First, consider if you need a logger or interface. Standalone CAN bus based J1939 data loggers allow you to gather data over e.g. weeks or months of driving, depending on the size of the SD card. A J1939 interface, in contrast, requires a PC to stream or trace the data from the CAN bus in real-time. The interface is e.g. useful for diagnostic purposes or event based analysis. Some J1939 data loggers like the CANLoggerX000 double as interfaces to provide a two-in-one solution.

Adaptor Cable: To connect your CAN bus analyzer to a SAE J1939 application (e.g. a truck), you will need the right adaptor cable. For the CANLoggerX000, we offer a D-SUB 9 to J1939 connector (Deutsch Connector, 9-Pin).

WiFi: For vehicle fleet management at scale, WiFi may be a useful upgrade to allow remote access to the logged data and/or pushing the data to an ftp/cloud server for post processing. If the aim is to analyse J1939 data from e.g. a big fleet of trucks on a daily or weekly basis, a WiFi solution is ideal (e.g. the CANLogger3000). However, in cases where the J1939 logger acts like e.g. a black box and data only needs to be retrieved rarely, a more affordable solution can work (e.g. the CANLogger2000).

Software: When logging or streaming J1939 data, software for post processing is key. In particular, the software should support DBC-based data conversion to allow quick access to human-readable data. Our free CANvas software allows DBC conversion of e.g. J1939 data, while the free Wireshark plugin allows DBC conversion of live-streamed data.

Advanced Features: To optimize your logging of J1939 data a number of features can be useful. For example, cyclical logging allows you to automatically overwrite old log files. This is practical for e.g. black box logger purposes where the J1939 data logger may need to continue logging for months or years until an issue occurs. Another useful feature is message filtering, allowing you to avoid logging specific parameters to conserve space. Finally, to access request-dependent J1939 messages, the J1939 logger needs to be able to transmit message requests. The CANLoggerX000 supports these features along with e.g. heartbeat signal, run-time logging control and more.

At the end of the day, J1939 is often related to logging data from major fleets of commercial vehicles. 

What does this imply?

This makes price a core factor. 

The CANLoggerX000 series is a powerful solution for J1939 applications, yet also one of the most affordable options. Pricing starts at 169 EUR with free shipping and free software. 

If you’re interested, check out our products page for more info! 

In case you’re looking for more articles on CAN bus, OBD2, J1939, DBC and more check out our GUIDES page.

If you have any questions, please contact us - we aim to respond within 24 hours!


This site uses cookies to enhance your experience

Got it!