LT Programming Hex File Format Documentation -- In Circuit Programming

LT Programming Hex File Format Documentation -- In Circuit Programming

作者联系方式

Purpose of Document

The purpose of this document is to clearly articulate the structure of the LT Programming Hex file in such a way that test engineers can build infrastructure to parse these files and execute programming logic to successfully program one or more LT Digital Power Product devices in cicruit, during test, or during prototype phases.

This document is in a draft stage. Information herein is subject to change. Further detail may be added or changed at a later date without notice.

Document Structure

This document starts by describing the general structure of the LT Programming Hex file as it relates to an Intel Hex file. A brief description of the overall programming flow is discussed next, followed by showing the necessary steps for each part of the translation process needed to decode data in the LT Programming Hex file at the various levels of abstraction. The final section walks through a single concrete example, including all the necessary steps to decode a very simple hex file with one programming command into the exact programming recipe specified by that file.

You can use the navigation table located below to navigate to various sections on this same page if you know what content you are targetting.

General File Structure Translating Hex to Raw Bytes Example Intel HEX File
Overall Task Flow Translate Bytes to LT Records Putting It All Together
Summary of LT Records Record Payload Definitions Record Type Definitions
Basic Definitions
0×01:
PMBUS_WRITE_BYTE
0×02:
PMBUS_WRITE_WORD
0×03:
PPMBUS_WRITE_BLOCK
0×04:
PMBUS_READ_BYTE_EXPECT
0×05:
PMBUS_READ_WORD_EXPECT
0×06:
PMBUS_READ_BLOCK_EXPECT
0×07:
DEVICE_ADDRESS
0×08:
PACKING_CODE
0×09:
NVM_DATA
0×0A:
PMBUS_READ_BYTE_LOOP_MASK
0×0B:
PMBUS_READ_WORD_LOOP_MASK
0×0C:
PMBUS_POLL_UNTIL_ACK_NOPEC
0×0D:
DELAY_MS
0×0E:
PMBUS_SEND_BYTE
0×0F:
PMBUS_WRITE_BYTE_NOPEC
0×10:
PMBUS_WRITE_WORD_NOPEC
0×11:
PMBUS_WRITE_BLOCK_NOPEC
0×12:
PMBUS_READ_BYTE_EXPECT_NOPEC
0×13:
PMBUS_READ_WORD_EXPECT_NOPEC
0×14:
PMBUS_READ_BLOCK_EXPECT_NOPEC
0×15:
PMBUS_READ_BYTE_LOOP_MASK_NOPEC
0×16:
PMBUS_READ_WORD_LOOP_MASK_NOPEC
0×17:
PMBUS_SEND_BYTE_NOPEC
0×18:
EVENT
0×19:
PMBUS_READ_BYTE_EXPECT_MASK_NOPEC
0×1A:
PMBUS_READ_WORD_EXPECT_MASK_NOPEC
0×1B:
VARIABLE_META_DATA
0×1C:
MODIFY_WORD_NOPEC
0×1D:
MODIFY_BYTE_NOPEC
0×1E:
PMBUS_WRITE_EE_DATA
0×1F:
PMBUS_READ_AND_VERIFY_EE_DATA
0×20:
PMBUS_MODIFY_BYTE
0×21:
PMBUS_MODIFY_WORD
Full Sample Source Code

General File Structure

The LT Programming Hex File is a standard Intel 386 hex file, also known as I32HEX or INTEL 32 Hex file Format. For detailed information on the Intel hex format, please reference this Wikipedia article: http://en.wikipedia.org/wiki/Intel_HEX.

At the lowest level of interpretation, the LT Programming Hex file represents a simple linear sequence (or ‘array’) of raw bytes. Higher level structures are imposed on this sequence of bytes to define a set of what we call “LT Programming Records”.

Each of these LT Programming Records instructs the In-System Programming software to perform a particular operation. As an example, one LT Programming Record type, PMBUS_WRITE_BYTE_NOPEC instructs the In-System Programming software to execute a PMBus/SMBus write byte operation to a specified address with a specified command code and data byte.

Generally LT Programming Record ‘instructions’ are somewhat low level – that is, they do not burden the In-System Programming software with understanding the algorithm necessary to program a device—the In-System Programming software simply executes a series of simple instructions, and in the order they are defined in the LT Programming Hex File.

Once the In-System Programming software has successfully processed all the LT Programming Record ‘instructions’ it will have successfully programmed and verified the NVM for all chips for a particular system as defined in the file.

LTProgrammingFileHeirarchy

Overall Task Flow

The LTpowerPlay GUI is responsible for managing all the desired register settings for a particular system. The normal convention in LTpowerPlay is to use a single ‘project’ (.proj) file to define one or more “chips” that will ultimately be populated on a customer board. LTpowerPlay stores into this project file all the desired register settings for each chip in defined in the project.

LTpowerPlay provides a “File, Export…” feature that generates a single LT Programming Hex File that can be used to program all devices defined in the project file on the target board in cicruit, during test, or during prototype phases. This single Intel hex file will contain for each chip in the project a complete set of LT Programming Record ‘instructions’ required to program and verify the NVM for that particular chip. We commonly refer to this complete set of instructions as the ‘recipe’ to program a device.

The In-Circuit Programming software will simply process each LT Programming Record ‘instruction’ in the order they are defined in the ‘recipe’ file. Once the In-Circuit Programming software has successfully processed all the LT Programming Record ‘instructions’ it will have successfully programmed and verified the NVM for all chips for a particular system as defined in the file.

Translating LTC HEX to Raw Bytes

As mentioned above, the LT Programming Hex File at its lowest level of interpretation is simply a linear sequence of bytes. The first task in processing the hex file is to parse the hex file and build a “buffer” of raw data bytes. The hex file itself contains start codes, memory addresses, line byte counts, Intel Hex File record types (note that these are different than our LT Record Types), line-by-line checksums, and of course the data itself. The data that you parse out of this Intel hex file is the recipe that itself contains many instructions.

Example Intel Hex File

The listing below shows an example Intel Hex file. The color coding below the listing defines the various fields of the Intel hex file:

:10010000214601360121470136007EFE09D2190140
:100110002146017EB7C20001FF5F16002148011988
:10012000194E79234623965778239EDA3F01B2CAA7
:100130003F0156702B5E712B722B732146013421C7
:00000001FF


 Start code
 Byte count
 Address
 Record type
 Data
 Checksum

As you can see, each line of the hex file starts with a “:” character, followed by a byte count, address, record type, some number of data bytes, and ends with a checksum for that line. Each line of the file in this case is an ‘Intel Hex File Data Record’ (record type 0×00), with the exception of the last line, which is a standard Intel Hex File ‘end of file’ (EOF) indicator.

A Note on the need for a 32-bit format:
Note that record type 0×00 will normally be used for the data records, although if the project files contain so many chips that the hex file contains more the 65535 bytes, record types 0×04 and 0×05 will be required. According to the current benchmarks, you would have to have a project with > 13 chips to reach this limit. Again, for further detail on Intel Hex record types, see the Wikipedia article. The remainder of this article assumes that data records of type 0×00 (16-bit byte address).

The ‘address’ field for each line refers to the starting byte address of the first byte of the line. As you can see in the example, the first 16 data bytes are intended to be located starting at byte-address 0×0100. The next 16 data bytes (on the second row) are located starting at address 0×0110. So this file defines what we would call a linear sequence of bytes.

LT Programming Hex Files will always represent a linear/contiguous sequence of raw bytes starting at byte address 0×0000 and going upward.

The In-System Programming software has completed the first step of processing this file when it has built a raw byte buffer by reading the raw bytes of the hex file. A concrete example is shown in a later section.

Translating the Raw Byte Buffer into LT Programming Records

You can think of LT Programming Records as higher level data on top of a raw byte stream. These Records will typically be used to represent higher level meta-data or procedural instructions.

As an example, one LT Programming Record type is the PMBUS_READ_BYTE_EXPECT_NOPEC record type (see appendix). This record type contains payload data that includes an I2C address, a command code, and an expected byte value. If this instruction is received, you perform a PMBus/SMBus Read Byte command without the use of Packet Error Checking (PEC) to the address specified with the specified command code. You then compare the returned value with the expected byte value in the record. You can see that the system programmer does not need to worry about the actual values of the check, just that the record type is parsed correctly which then presents the correct data and method to execute.

The file format is designed to be generic and extensible to any expanding number of record types required for future use. The presently defined record types are shown below with more details. There may be additional LT Record Types added in the future. The In-System Programming software needs to be able to decode and process each of these record types. If the In-System Programming software encounters other record types not defined in this document, you need to fail with an error code that indicates the firmware needs to be updated, and ask for the latest version of this document.

All LT Programming records follow a consistent packet structure. The packets have a header and a payload as shown in the diagram above. The header is always 4 bytes, and the payload varies depending on the record type. The breakdown of the packet and its header is shown below:

Header (4 bytes) Payload bytes (depends on record type)
Field Record Length Record Type Fields defined by record type
Low Byte High Byte Low Byte High Byte
#bytes 1 1 1 1 (defined by record type)

Note that the header contains two 16-bit values—a Record length (including the 4 byte header) and a Record Type. LT Programming files will always represent multi-byte values as little-Indian. That is, the low byte always precedes the high byte.

For example, consider the LT Programming record type PMBUS_WRITE_BYTE_NOPEC (record type 0×0F – see later section), which has 4 bytes in its payload. The 4-byte header would be 0×08,0×00,0×0F,0×00 indicating a total record length 8 bytes (4bytes of header and 4 bytes of payload) with a record type of 0×0F. A diagrammatic view of the just the header fields may help you see the decoding process more clearly:

PMBUS_WRITE_BYTE_NOPEC [Header Only] (4 bytes)
Field Record Length Record Type
Low Byte High Byte Low Byte High Byte
#bytes 1 1 1 1
Value 0×08 0×00 0×0F 0×00

A diagrammatic view of the the header fields and non-decoded payload fields for the LT Programming Record Type PMBUS_WRITE_BYTE_NOPEC is shown below to complete the visualization:

PMBUS_WRITE_BYTE_NOPEC [Full Non-Decoded LT Programming Record Type] (8 bytes)
Field Record Length Record Type Payload
Low Byte High Byte Low Byte High Byte
#bytes 2 2 4
Value 0×08 0×00 0×0F 0×00 4 bytes of payload data

Because all LT Programming Records follow this consistent structure of header/payload, this makes it a simple task to build a list of Programming Records from raw bytes.

The next step in processing the file after building a sequential list of LT Programming Record instructions is to process the individual records in order to satisfy the recipe. Remember that the length and meaning of the bytes in the payload is dependent on record type. Each record type will group the payload bytes into specific fields that have meaning for that particular record type and only that particular record type.

Let's continue our example using the same LT Programming Record of PMBUS_WRITE_BYTE_NOPEC record type. If the hex file ("recipe") was instructing the In-System Programming software to issue a PMBus/SMBus Write Byte to the 7-bit I2C address of 7’h5C, with command code 0×01, and data byte 0×80, the payload would look as follows:

PMBUS_WRITE_BYTE_NOPEC [Payload Only] (4 bytes)
Field Device Address Command Code Data byte
Low Byte High Byte
#bytes 1 1 1 1
Value 0×5C 0×00 0×01 0×80

So if we put this entire PMBUS_WRITE_BYTE_NOPEC LT Programming Record together, it would like:

PMBUS_WRITE_BYTE_NOPEC [Full Example] (8 bytes)
Field Record Header Payload
Record Length Record Type Device Address Command Code Data Byte
Low byte High byte Low byte High byte Low byte High byte
#bytes 2 2 2 1 1
Value 0×08 0×00 0×0F 0×00 0×5C 0×00 0×80 0×01

This fully illustrates the PMBUS_WRITE_BYTE_NOPEC LT Programming Record type. This record type, as with all record types, contains the 4 byte Record Header. This Record Header details the Record Length in bytes (including the header itself) as well as the Record Type. The length of the Payload is the size of the Record Header (always 4 bytes) subtracted from the total Record Length (8 bytes in this case). When we lookup the Record Type of 0×0F we discover it is a PMBUS_WRITE_BYTE_NOPEC LT Programming Record Type. We therefore use that record type's decoder table, and we see 3 more details: I2C Device Address, I2C Command Code, I2C Data Byte. Now that we have decoded what the record means, we must actually do it. So in this case, we would write the I2C Command Code (0×01) to I2C Device Address (0×5C) with the I2C Data Byte of (0×80) without using Packet Error Checking (PEC). If the device ACKnowledges the command, then we move on to the next instruction. Otherwise we fail.

Putting It All Together

Let’s take one simple but concrete example all the way from hex file to the actions that the In-System Programming software will take. Let’s say we had a hex file with just the following raw data bytes defined:

:0800000008000F005C00000283
:00000001FF


 Start code
 Byte count
 Address
 Record type
 Data
 Checksum

For the first line

  • The byte count of the first line is 8, indicating 8 data bytes in this line of the hex file
  • The starting address is 0×0000
  • The record type is 00 (data record)
  • The 8 raw data bytes are 0×08, 0×00, 0×0F, 0×00, 0×5C, 0×00, 0×00, 0×02
  • We validate the checksum by summing all the bytes in the row (including checksum)
  • 0×08+0×00+0×00+0×00+0×08+0×00+0×0F+0×00+0×5c+0×00+0×00+0×02+0×83 == 0×00 (8-bit)
Note:
The checksum is valid if all the bytes including the checksum add to 0×00.

For the second line

  • This is the standard end of file record type indicating the end of the hex file

So we have 8 raw data bytes: 0×08, 0×00, 0×0F, 0×00, 0×5C, 0×00, 0×00, 0×02

 0×08 0×00 0×0F 0×00  0×5C 0×00 0×00 0×02 

 LT Record Header
 Payload Data
Unknown LT Programming Record Type [ 0×08 0×00 0×0F 0×00  0×5C 0×00 0×00 0×02] (8 bytes)
Field Record Length Record Type Payload
Low byte High byte Low byte High byte
#bytes 2 2 1 1 1 1
Value 0×08 0×00 0×0F 0×00 0×5C 0×00 0×00 0×02

The first 4 bytes comprise the LT Programming Record header for the first and only record. When we decode the header, we see that the record length is 8 bytes, and the record type is 0×F (PMBUS_WRITE_BYTE_NOPEC). The remaining 4 of 8 bytes is the payload for the PMBUS_WRITE_BYTE_NOPEC record type. We decoded the PMBUS_WRITE_BYTE_NOPEC payload fields above in the previous example. When we put it all together we get:

PMBUS_WRITE_BYTE_NOPEC [0×08 0×00 0×0F 0×00  0×5C 0×00 0×00 0×02] (8 bytes)
Field Record Header Payload
Record Length Record Type Device Address Command Code Data Byte
Low byte High byte Low byte High byte
# bytes 2 2 2 1 1
Value 0×08 0×00 0×0F 0×00 0×5C 0×00 0×00 0×02

So this one LT Programming Record has instructed our In-System Programming software to execute a PMBus/SMBus write byte operation to the 7-bit address 7’h5C, with command code 0×00, and data byte 0×02. In PMBus, this is equivalent to setting the PAGE register to 2.

In terms of raw I2C protocol, the specific write byte operation would look like the following sequence of I2C primitives on the wire:

  • <Start Condition>
  • 0×B8 -- 7-bit address 7’h5C with read bit set to 0
  • 0×00 -- Command Code
  • 0×02 -- Data Byte
  • <Start Condition>

We have taken a hex file that contained a single LT Programming Record ‘instruction’ from the hex file to the actual steps that would be performed by In-System Programming software. In reality, a LT Programming hex file will contain many such instructions, but this gives you an idea of what is necessary to parse the file and execute a particular programming process.

Summary of LT Programming Records

LTpowerPlay is responsible for generating a LT Programming hex file that contains a sequence of LT Programming Record ‘instructions’ required to program one or more LTC2978’s on a customer board at In-System Programming. The user can easily generate this file using LTpowerPlay.

The customer’s In-System Programming software or firmware is then responsible for reading in this file and carrying out a sequence LT Programming Record (instructions) as defined in the LT Programming hex file.

The above sections illustrate how to parse the Intel hex file and decode the raw bytes into a set of these LT Programming Records. The appendix shows the payload definitions for the presently defined set of LT Programming Record types.

Record Type Definitions

LT Programming File Record Types
Hex Value Record Type Name Record Type Notes
0×01 RECORD_TYPE_PMBUS_WRITE_BYTE
0×02 RECORD_TYPE_PMBUS_WRITE_WORD
0×03 RECORD_TYPE_PMBUS_WRITE_BLOCK
0×04 RECORD_TYPE_PMBUS_READ_BYTE_EXPECT
0×05 RECORD_TYPE_PMBUS_READ_WORD_EXPECT
0×06 RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT
0×07 RECORD_TYPE_DEVICE_ADDRESS OBSOLETED
0×08 RECORD_TYPE_PACKING_CODE OBSOLETED
0×09 RECORD_TYPE_NVM_DATA
0×0A RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK
0×0B RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK
0×0C RECORD_TYPE_PMBUS_POLL_UNTIL_ACK_NOPEC
0×0D RECORD_TYPE_DELAY_MS
0×0E RECORD_TYPE_PMBUS_SEND_BYTE
0×0F RECORD_TYPE_PMBUS_WRITE_BYTE_NOPEC
0×10 RECORD_TYPE_PMBUS_WRITE_WORD_NOPEC
0×11 RECORD_TYPE_PMBUS_WRITE_BLOCK_NOPEC
0×12 RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_NOPEC
0×13 RECORD_TYPE_PMBUS_READ_WORD_EXPECT_NOPEC
0×14 RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT_NOPEC
0×15 RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK_NOPEC
0×16 RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK_NOPEC
0×17 RECORD_TYPE_PMBUS_SEND_BYTE_NOPEC
0×18 RECORD_TYPE_EVENT
0×19 RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC
0×1A RECORD_TYPE_PMBUS_READ_WORD_EXPECT_MASK_NOPEC
0×1B RECORD_TYPE_VARIABLE_META_DATA
0×1C RECORD_TYPE_MODIFY_WORD_NOPEC
0×1D RECORD_TYPE_MODIFY_BYTE_NOPEC
0×1E RECORD_TYPE_PMBUS_WRITE_EE_DATA
0×1F RECORD_TYPE_PMBUS_READ_AND_VERIFY_EE_DATA
0×20 RECORD_TYPE_PMBUS_MODIFY_BYTE
0×21 RECORD_TYPE_PMBUS_MODIFY_WORD

LT Programming Record Payload Definitions

Basic Record Type Definitions

These records form a basic building block for the other records.

There is the tRecordHeaderLengthAndType which is always the first 4 bytes of the record. This defines how long the record is (remember to subtract 4 bytes since the length includes this header!) and what type the record is. You can then lookup the type and parse its payload accordingly. The specific ways of parsing each supported type's payload is defined in the sections following this.

The other two basic types are used in many of the payloads because they both define an I2C Address (which address the instruction is directed towards) as well as an I2C Command Code. The difference between the two structures is with Packet Error Checking (PEC).

The tRecordHeaderAddressAndCommandWithOptionalPEC struct includes a UINT8 that when it is equal to 1, you must send the command (writes or reads) with PEC enabled.

The tRecordHeaderAddressAndCommandWithoutPEC struct does not include this UINT8 value because it is always sent without using PEC.

tRecordHeaderLengthAndType (4 bytes)
Field Record Header Structure
Record Length Record Type
Low byte High byte Low byte High byte
# bytes 2 2
tRecordHeaderAddressAndCommandWithOptionalPEC (4 bytes)
Field Payload Header Structure with PEC
Device Address Command Code Use PEC
Low byte High byte
# bytes 2 1 1
tRecordHeaderAddressAndCommandWithoutPEC (3 bytes)
Field Payload Header Structure without PEC
Device Address Command Code
Low byte High byte
# bytes 2 1
/** Basic Record Type Definitions **********************************/

typedef struct tRecordHeader
{
UINT16 Length;
UINT16 RecordType;
}tRecordHeaderLengthAndType, *pRecordHeaderLengthAndType;

typedef struct
{
UINT16 DeviceAddress;
UINT8 CommandCode;
UINT8 UsePec;
} tRecordHeaderAddressAndCommandWithOptionalPEC;

typedef struct
{
UINT16 DeviceAddress;
UINT8 CommandCode;  
} tRecordHeaderAddressAndCommandWithoutPEC;

0×01 - RECORD_TYPE_PMBUS_WRITE_BYTE

This record is a standard PMBus communication record. The host should process this record by writing a single byte to the specified address with the specified command code, optionally with PEC.

RECORD_TYPE_PMBUS_WRITE_BYTE [0×01] (9 bytes)
Field Record Header Payload Header with PEC Payload
Data
Record Length Record Type Device Address Command
Code
Use
PEC
Data Byte
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1 1
Value 0×09 0×00 0×01 0×00          
/********************************************************************
* Struct:          t_RECORD_PMBUS_WRITE_BYTE
*
* Overview:        PMBus write byte with optional PEC
* Note:            RECORD_TYPE_PMBUS_WRITE_BYTE with value of 0×01 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_BYTE  (1)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;
UINT8 dataByte;
}t_RECORD_PMBUS_WRITE_BYTE;

0×02 - RECORD_TYPE_PMBUS_WRITE_WORD

This record is a standard PMBus communication record. The host should process this record by writing a single word to the specified address with the specified command code, optionally with PEC.

RECORD_TYPE_PMBUS_WRITE_WORD [0×02] (10 BYTES)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command Code Use
PEC
Data Word
  Low
byte
High
byte
Low
byte
High
byte
Low
byte
High
byte
    Low
byte
High
byte
#
bytes
2 2 2 1 1 2
Value 0×0A
[10]
0×00 0×02 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_WRITE_WORD
*
* Overview:        PMBus write word with optional PEC
* Note:            RECORD_TYPE_PMBUS_WRITE_WORD with value of 0×02 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_WORD (2)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;
UINT16 dataWord;
}t_RECORD_PMBUS_WRITE_WORD;

0×03 - RECORD_TYPE_PMBUS_WRITE_BLOCK

Note:
This record is not defined or currently used.
/********************************************************************
* Struct:          NOT DEFINED
*
* Overview:        PMBus Write Block with optional PEC
* Note:            RECORD_TYPE_PMBUS_WRITE_BLOCK with value of 0×03 would use this struct
*                  RECORD TYPE NOT USED AND NOT DEFINED
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_BLOCK (3)

0×04 - RECORD_TYPE_PMBUS_READ_BYTE_EXPECT

This record is a standard PMBus communication record combined with a verification step. The host should process this record by reading a single byte from the specified address with the specified command code, optionally with PEC. The byte value that is returned should then be compared against the expected data byte found in the payload. If the values do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_BYTE_EXPECT [0×04] (9 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Use
PEC
Expected Data
Byte
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1 1
Value 0×09 0×00 0×04 0×00
/********************************************************************
* Struct:	        t_RECORD_PMBUS_READ_BYTE_EXPECT
*
* Overview:        PMBus Read Byte with optional PEC, and expect a specified value (fail if different)
* Note:            RECORD_TYPE_PMBUS_READ_BYTE_EXPECT with value of 0×04 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BYTE_EXPECT (4)
typedef struct 
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;
UINT8 expectedDataByte;
}t_RECORD_PMBUS_READ_BYTE_EXPECT;

0×05 - RECORD_TYPE_PMBUS_READ_WORD_EXPECT

This record is a standard PMBus communication record combined with a verification step. The host should process this record by reading a single word from the specified address with the specified command code, optionally with PEC. The word value that is returned should then be compared against the expected data word found in the payload. If the values do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_WORD_EXPECT [0×05] (10 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Use
PEC
Expected Data
Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1 2
Value 0×0A
[10]
0×00 0×05 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_WORD_EXPECT
*
* Overview:        PMBus Read Word with optional PEC, and expect a specified value (fail if different)
* Note:            t_RECORD_PMBUS_READ_WORD_EXPECT with value of 0×05 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_WORD_EXPECT (5)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;
UINT16 expectedDataWord;
}t_RECORD_PMBUS_READ_WORD_EXPECT;

0×06 - RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT

Note:
This record is not defined or currently used.
/********************************************************************
* Struct:          NOT DEFINED
*
* Overview:        PMBus Read Block with optional PEC, and expect a specified value (fail if different)
* Note:            RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT with value of 0×06 would use this struct
*                  RECORD TYPE NOT USED AND NOT DEFINED
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT (6)

0×07 - RECORD_TYPE_DEVICE_ADDRESS

Note:
This record is not defined or currently used. It has been obsoleted.
/********************************************************************
* Struct:          NOT DEFINED
*
* Overview:        Not Available
* Note:            RECORD_TYPE_DEVICE_ADDRESS with value of 0×07 would use this struct
*                  RECORD TYPE NOT USED AND NOT DEFINED
*******************************************************************/
#define RECORD_TYPE_DEVICE_ADDRESS (7)

0×08 - RECORD_TYPE_PACKING_CODE

Note:
This record is not defined or currently used. It has been obsoleted.
/********************************************************************
* Struct:          t_RECORD_PACKING_CODE
*
* Overview:        Not Available
* Note:            RECORD_TYPE_PACKING_CODE with value of 0×08 would use this struct
*                  RECORD TYPE NOT USED BUT IS DEFINED
*******************************************************************/
#define RECORD_TYPE_PACKING_CODE (8)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
UINT16 packingCode;
}t_RECORD_PACKING_CODE;

0×09 - RECORD_TYPE_NVM_DATA

Note:
The functionality of this record changed 25/01/2011. The previous implementation has been obsoleted. You are now required to support a variable length block of data and the ability to buffer it for programming and verification at a later time within the recipe.

This record is non-standard record. The host should process this record by reading the entire payload as raw bytes and storing them in a variable buffer for later use. The implementation we provide stores the bytes in a linked list. This particular list structure is somewhat wasteful in resources in that it duplicates much data but it is done for the sake of code simplicity and to provide an easier to read and understand example.

Like all other records, it contains the standard 4-byte header identifying its record type and the length of the record. The length in this case will be variable. As before, the length of your payload is this length minus 4 bytes long. Each of these bytes should be stored sequentially somehwere that is accessible by other areas of your programming software or (if your language supports it) in an object that can be passed back to the programming area of your software. Other record types such as 0×1E - RECORD_TYPE_PMBUS_WRITE_EE_DATA and 0×1F - RECORD_TYPE_PMBUS_READ_AND_VERIFY_EE_DATA use this data to perform the actual writes, reads, and verification. Care and thought should be taken how to best implement this for your system. Many trade-offs between code size, processor usage, heap/stack size, and other things must be made to accomodate such a list. In smaller and less resourceful systems, this matters more. The implementation provided in the source code runs well for an above averaged sized system on an embedded MIPS core taking only a few KB's of flash and a few KB's of data memory with a shared stack/heap size of 1KB. Note that these size values are for the entire code space and are only given to help estimate resource usage on your system.

Note:
This record DOES NOT actually perform a write to the Non-Volatile Memory (NVM)! It buffers the contents for use later and this is important.
RECORD_TYPE_NVM_DATA [0×09] (4 byte header + variable payload length)
Field Record Header Payload Data
Record Length Record Type Block of NVM Data
Low byte High byte Low byte High byte
# bytes 2 2 VARIABLE LENGTH
Value 0×09 0×00
/********************************************************************
* Struct:          t_RECORD_NVM_DATA
*
* Overview:        A block of NVM Data to be written as a block of bytes
* Note:            t_RECORD_NVM_DATA with value of 0×09 uses this struct
*                  The actual NVM Data to be written is not absolutely
*                  defined in this struct because the length of the
*                  NVM data is variable
*******************************************************************/
#define RECORD_TYPE_NVM_DATA (9)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;  
}t_RECORD_NVM_DATA;

/********************************************************************
* Struct:          _NVRAM_ListItem, nvramNode_t, *nvramNode_p
*
* Overview:        A struct used to build a linked list that contains
*                  NVM data
* Note:            The actual contents of the NVM write from a
*                  RECORD_TYPE_NVM_DATA are stored in a linked list
*                  built using this struct
*******************************************************************/
typedef struct _NVRAM_ListItem
{
UINT16 data_store;
UINT8  nvram_usePEC;
UINT8  nvram_pmbusAddress;
UINT8  nvram_pmbusCommand;
struct _NVRAM_ListItem* next;
} nvramNode_t, *nvramNode_p;

0×0A - RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK

This record is a standard PMBus communication record combined with a verification step that is potentially repeated in a loop until the condition is satisfied. The host should process this record by continuously reading a single byte from the specified address with the specified command code, optionally with PEC. The byte value that is returned should be bit- wise ANDed with the Data Byte Mask and then be compared against the expected data byte found in the payload. If the values do not match, it should re-read the device and only continue if the values match. It is suggested to put a timeout feature in this loop for many seconds, and if after this timeout the values still do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK [0×0A] (10 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Use
PEC
Data
Byte
Mask
Expected
Data Byte
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1 1 1
Value 0×0A
[10]
0×00 0×0A 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_BYTE_LOOP_MASK
*
* Overview:        PMBus Read Byte with optional PEC in a loop until
*                  the device returns a specified value
* Note:            RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK with value
*                  of 0×0A uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK (0×A)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;   
UINT8 byteMask;
UINT8 expectedDataByte;
}t_RECORD_PMBUS_READ_BYTE_LOOP_MASK;

0×0B - RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK

This record is a standard PMBus communication record combined with a verification step that is potentially repeated in a loop until the condition is satisfied. The host should process this record by continuously reading a single word from the specified address with the specified command code, optionally with PEC. The word value that is returned should be bit- wise ANDed with the Data Word Mask and then be compared against the expected data word found in the payload. If the values do not match, it should re-read the device and only continue if the values match. It is suggested to put a timeout feature in this loop for many seconds, and if after this timeout the values still do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK [0×0B] (12 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Use
PEC
Data Word
Mask
Expected Data
Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1 2 2
Value 0×0C
[12]
0×00 0×0B 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_WORD_LOOP_MASK
*
* Overview:        PMBus Read Word with optional PEC in a loop until
*                  the device returns a specified value
* Note:            RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK with value of
0×0B uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK (0×B)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;   
UINT16 wordMask;
UINT16 expectedDataWord;
}t_RECORD_PMBUS_READ_WORD_LOOP_MASK;

0×0C - RECORD_TYPE_PMBUS_POLL_UNTIL_ACK_NOPEC

This record is a standard PMBus communication record that is potentially repeated in a loop until the condition is satisfied. The host should process this record by continuously reading a single byte from the specified address with the specified command code, without PEC. The byte value that is returned is not as important as whether or not the device ACKnowledges the read. If the host does not ACK, the programming software should re-read the device and only continue when the device is ACKing or if the timeout value in milliseconds has ellapsed. If after this timeout the device is still not ACKing, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

Note:
A timeout value of 0×0000 (0 milliseconds) means wait forever with no timeout. This is an important feature and must be implemented for times that long operations are required or during system bring up when there is an uncertainty on when the devices will be ready for communication. If you want to be clever and have a way of sending messages back to the engineer during programming, you may want to have a global timeout value and if while waiting in this infinite loop it is taking longer than many seconds, notify the engineer of a possible failure, where you are in the code, and the record you were parsing.
RECORD_TYPE_PMBUS_POLL_UNTIL_ACK_NOPEC [0×0C] (9 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Timeout in mS
Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 2
Value 0×09 0×00 0×0C 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_POLL_READ_BYTE_UNTIL_ACK
*
* Overview:        Poll a device at an address until it Acknowledges (ACKs)
* Note:            t_RECORD_PMBUS_POLL_READ_BYTE_UNTIL_ACK with value
*                  of 0×0C uses this struct. This record type indicates
*                  that the software should continually attempt to
*                  execute a PMBus read byte operation until the
*                  slave devices acknowledges the command code or until
*                  the timeout value in milliseconds is reached. This
*                  is typically used to wait until the device is
*                  non-busy. This never uses PEC
*******************************************************************/
#define RECORD_TYPE_PMBUS_POLL_UNTIL_ACK_NOPEC (0×C)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;
UINT16 timeout_in_ms; 
}t_RECORD_PMBUS_POLL_READ_BYTE_UNTIL_ACK;

0×0D - RECORD_TYPE_DELAY_MS

This record is not standard PMBus communication record. The host should process this record by delaying for the time specified (in milliseconds). After this time, return. There is no error checking or validation of any kind performed in this record. It is a standard simple wait/sleep routine.

Note:
This function's implementation is the example code will more than likely vary substantially from your implementation. Some cores provide a built in library function for this. In our example's case, there are 4 instructions per loop, and it is a single-cycle processor running at 80MHz. Using some math we determined the magic integer numbers in the function. We disregarded the (in our case) 12 instructions to enter and exit the subroutine.
RECORD_TYPE_DELAY_MS [0×0D] (6 bytes)
Field Record Header Payload Data
Record Length Record Type Timeout to Delay in mS
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2
Value 0×06 0×00 0×0D 0×00
/********************************************************************
* Struct:          t_RECORD_DELAY_MS
*
* Overview:        Simple delay function. Idle the bus for a specified
*                  amount of time
* Note:            RECORD_TYPE_DELAY_MS with value of 0×0D uses this
*                  struct. This record type indicates that the software
*                  should delay execution for a specified number of
*                  milliseconds before proceeding.
*******************************************************************/
#define RECORD_TYPE_DELAY_MS (0×D)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;  
UINT16 numMs;
}t_RECORD_DELAY_MS;

0×0E - RECORD_TYPE_PMBUS_SEND_BYTE

This record is a standard PMBus communication record. The host should process this record by writing the specified command code to the specified address, optionally with PEC.

RECORD_TYPE_PMBUS_SEND_BYTE [0×0E] (8 bytes)
Field Record Header Payload Header with PEC
Record Length Record Type Device Address Command Code Use PEC
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1
Value 0×08 0×00 0×0E 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_SEND_BYTE
*
* Overview:        This record type indicates that the software
*                  should execute a PMBus send byte operation
* Note:            RECORD_TYPE_PMBUS_SEND_BYTE with value of 0×0E
*                  uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_SEND_BYTE (0×E)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader;  
}t_RECORD_PMBUS_SEND_BYTE;

0×0F - RECORD_TYPE_PMBUS_WRITE_BYTE_NOPEC

This record is a standard PMBus communication record. The host should process this record by writing a single byte to the specified address with the specified command code, without PEC.

RECORD_TYPE_PMBUS_WRITE_BYTE_NOPEC [0×0F] (8 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command Code Data Byte
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1
Value 0×08 0×00 0×0F 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_WRITE_BYTE_NOPEC
*
* Overview:        PMBus write byte WITHOUT optional PEC. PEC is *never* used
* Note:            RECORD_TYPE_PMBUS_WRITE_BYTE_NOPEC with value of 0×0F uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_BYTE_NOPEC (0×F)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;;
UINT8 dataByte;
}t_RECORD_PMBUS_WRITE_BYTE_NOPEC;

0×10 - RECORD_TYPE_PMBUS_WRITE_WORD_NOPEC

This record is a standard PMBus communication record. The host should process this record by writing a single word to the specified address with the specified command code, without PEC.

RECORD_TYPE_PMBUS_WRITE_WORD_NOPEC [0×10] (9 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Data Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 2
Value 0×09 0×00 0×10 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_WRITE_WORD_NOPEC
*
* Overview:        PMBus write word WITHOUT optional PEC. PEC is *never* used
* Note:            RECORD_TYPE_PMBUS_WRITE_WORD_NOPEC with value of 0×10 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_WORD_NOPEC (0×10)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;;
UINT16 dataWord;
}t_RECORD_PMBUS_WRITE_WORD_NOPEC;

0×11 - RECORD_TYPE_PMBUS_WRITE_BLOCK_NOPEC

Note:
This record is not defined or used currently.
/********************************************************************
* Struct:          NOT DEFINED
*
* Overview:        Same as RECORD_TYPE_PMBUS_WRITE_BLOCK except PEC is never used
* Note:            RECORD_TYPE_PMBUS_WRITE_BLOCK_NOPEC with value of 0×11 would use this struct
*                  RECORD TYPE NOT USED AND NOT DEFINED
*******************************************************************/
/* RECORD TYPE NOT USED AND NOT DEFINED */
#define RECORD_TYPE_PMBUS_WRITE_BLOCK_NOPEC (0×11)

0×12 - RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_NOPEC

This record is a standard PMBus communication record combined with a verification step. The host should process this record by reading a single byte from the specified address with the specified command code, without PEC. The byte value that is returned should then be compared against the expected data byte found in the payload. If the values do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_NOPEC [0×12] (8 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Expected Data Byte
Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1
Value 0×08 0×00 0×12 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_BYTE_EXPECT_NOPEC
*
* Overview:        PMBus Read Byte without PEC, and expect a specified value (fail if different)
* Note:            RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_NOPEC with value of 0×12 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_NOPEC (0×12)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;;
UINT8 expectedDataByte;
}t_RECORD_PMBUS_READ_BYTE_EXPECT_NOPEC;

0×13 - RECORD_TYPE_PMBUS_READ_WORD_EXPECT_NOPEC

This record is a standard PMBus communication record combined with a verification step. The host should process this record by reading a single word from the specified address with the specified command code, without PEC. The word value that is returned should then be compared against the expected data word found in the payload. If the values do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_WORD_EXPECT_NOPEC [0×13] (9 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Expected Data Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 2
Value 0×09 0×00 0×13 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_WORD_EXPECT_NOPEC
*
* Overview:        PMBus Read Word without PEC, and expect a specified value (fail if different)
* Note:            RECORD_TYPE_PMBUS_READ_WORD_EXPECT_NOPEC with value of 0×13 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_WORD_EXPECT_NOPEC (0×13)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;;
UINT16 expectedDataWord;
}t_RECORD_PMBUS_READ_WORD_EXPECT_NOPEC;

0×14 - RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT_NOPEC

Note:
This record is not defined or used currently.
/********************************************************************
* Struct:          NOT DEFINED
*
* Overview:        Same as RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT except PEC is never used
* Note:            RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT_NOPEC with value of 0×14 would use this struct
*                  RECORD TYPE NOT USED AND NOT DEFINED
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BLOCK_EXPECT_NOPEC (0×14)

0×15 - RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK_NOPEC

This record is a standard PMBus communication record combined with a verification step that is potentially repeated in a loop until the condition is satisfied. The host should process this record by continuously reading a single byte from the specified address with the specified command code, without PEC. The byte value that is returned should be bit-wise ANDed with the Data Byte Mask and then be compared against the expected data byte found in the payload. If the values do not match, it should re-read the device and only continue if the values match. It is suggested to put a timeout feature in this loop for many seconds, and if after this timeout the values still do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK_NOPEC [0×15] (9 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Data Byte
Mask
Expected Data
Byte
Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1 1
Value 0×09 0×00 0×15 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_BYTE_LOOP_MASK_NOPEC
*
* Overview:        PMBus Read Byte without PEC in a loop until the
*                  device returns a specified value
* Note:            RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK_NOPEC with
*                  value of 0×15 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BYTE_LOOP_MASK_NOPEC (0×15)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;; 
UINT8 byteMask;
UINT8 expectedDataByte;  
}t_RECORD_PMBUS_READ_BYTE_LOOP_MASK_NOPEC;

0×16 - RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK_NOPEC

This record is a standard PMBus communication record combined with a verification step that is potentially repeated in a loop until the condition is satisfied. The host should process this record by continuously reading a single word from the specified address with the specified command code, without PEC. The word value that is returned should be bit-wise ANDed with the Data Word Mask and then be compared against the expected data word found in the payload. If the values do not match, it should re-read the device and only continue if the values match. It is suggested to put a timeout feature in this loop for many seconds, and if after this timeout the values still do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK_NOPEC [0×16] (11 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Data Word
Mask
Expected Data
Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 2 2
Value 0×0B 0×00 0×16 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_WORD_LOOP_MASK_NOPEC
*
* Overview:        PMBus Read Word without PEC in a loop until the
*                  device returns a specified value
* Note:            RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK_NOPEC with
*                  value of 0×16 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK_NOPEC (0×16)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;; 
UINT16 wordMask;
UINT16 expectedDataWord; 
}t_RECORD_PMBUS_READ_WORD_LOOP_MASK_NOPEC;

0×17 - RECORD_TYPE_PMBUS_SEND_BYTE_NOPEC

This record is a standard PMBus communication record. The host should process this record by writing the specified command code to the specified address, without PEC.

RECORD_TYPE_PMBUS_SEND_BYTE_NOPEC [0×17] (7 bytes)
Field Record Header Payload Header without PEC
Record Length Record Type Device Address Command Code
Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1
Value 0×07 0×00 0×17 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_SEND_BYTE_NOPEC
*
* Overview:        This record type indicates that the software
*                  should execute a PMBus send byte operation and never
*                  using PEC
* Note:            RECORD_TYPE_PMBUS_SEND_BYTE_NOPEC with value of
*                  0×17 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_SEND_BYTE_NOPEC (0×17)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;;  
}t_RECORD_PMBUS_SEND_BYTE_NOPEC;

0×18 - RECORD_TYPE_EVENT

This record is not standard PMBus communication record. The host should process this record by setting event flags in the code if wanted. For instance, if you want to let the user know that you are about to program the part, or provide prompting, this is the interface in which to do so. These events do not interact with the device itself in any way, they only let the programming software know where in the file you are. The event types are defined in the code sample below.

RECORD_TYPE_EVENT [0×18] (6 bytes)
Field Record Header Payload Data
Record Length Record Type Event Type ID
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2
Value 0×06 0×00 0×18 0×00
/********************************************************************
* Struct:          t_RECORD_EVENT
*
* Overview:        Indicates that we are at a particular place in
*                  the In-Circuit Programming file [recipe file]
* Note:            RECORD_TYPE_EVENT with value of 0×18 uses this
*                  struct. This can be used for custom user
*                  interactions or at a basic level debug prompts/actions
*******************************************************************/
#define RECORD_TYPE_EVENT (0×18)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
UINT16 eventId;
}t_RECORD_EVENT;

/********************************************************************************************
* Definitions: NAME (VALUE) NOTE
*      BEFORE_BEGIN                        (0)     This event is fired before any 
*                                                  commands are issued to communicate
*                                                  with the system
*      BEFORE_INSYSTEM_PROGRAMMING_BEGIN   (0×10)  This event is fired before
*                                                  any commands are issued to communicate
*                                                  with a multi-chip system
*      SYSTEM_BEFORE_PROGRAM               (1)     This event is fired before any
*                                                  commands are issued to program
*                                                  the NVM
*      INSYSTEM_CHIP_BEFORE_PROGRAM        (0×11)  This event is fired before any
*                                                  commands are issued to program
*                                                  the NVM of bulk programmed devices
*      SYSTEM_BEFORE_VERIFY                (2)     This event is fired after programming
*                                                  the system before any commands are
*                                                  issued to verify the NVM
*      INSYSTEM_CHIP_BEFORE_VERIFY         (0×12)  This event is fired after programming
*                                                  the system before any commands are
*                                                  issued to verify the NVM of bulk
*                                                  programmed devices
*      INSYSTEM_CHIP_AFTER_VERIFY          (0×13)  This event is fired after programming
*                                                  the system and after any commands are
*                                                  issued to verify the NVM of bulk 
*                                                  programmed devices
*      SYSTEM_AFTER_VERIFY                 (4)     This event is fired after programming
*                                                  the system and after all commands are
*                                                  issued to verify the NVM. This had to be
*                                                  out of order because of compatibility
*                                                  issues (it was defined after #3).
*      AFTER_DONE                          (3)     This event is fired after the end
*                                                  of the entire programming and
*                                                  verification sequence is complete
********************************************************************************************/
#define BEFORE_BEGIN (0×00)
#define BEFORE_INSYSTEM_PROGRAMMING_BEGIN (0×10)
#define SYSTEM_BEFORE_PROGRAM (0×01)
#define INSYSTEM_CHIP_BEFORE_PROGRAM (0×11)
#define SYSTEM_BEFORE_VERIFY (0×02)
#define INSYSTEM_CHIP_BEFORE_VERIFY (0×12),
#define INSYSTEM_CHIP_AFTER_VERIFY (0×13)
#define SYSTEM_AFTER_VERIFY (0×04)
#define AFTER_DONE (0×03) 

0×19 - RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC

This record is a standard PMBus communication record combined with a verification step. The host should process this record by reading a single byte from the specified address with the specified command code, without PEC. The byte value that is returned should be bit-wise ANDed with the Data Byte Mask and then be compared against the expected data byte found in the payload. If the values do not match it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC [0×19] (9 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Data Byte
Mask
Expected Data
Byte
Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1 1
Value 0×09 0×00 0×19 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC
*
* Overview:        PMBus Read Byte without PEC, and expect a specified
*                  value bitwise ANDed with the Mask (fail if different)
* Note:            RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC with
*                  value of 0×19 uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC (0×19)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;; 
UINT8 expectedDataByte;
UINT8 byteMask;
}t_RECORD_PMBUS_READ_BYTE_EXPECT_MASK_NOPEC; 

0×1A - RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK

This record is a standard PMBus communication record combined with a verification step that is potentially repeated in a loop until the condition is satisfied. The host should process this record by continuously reading a single word from the specified address with the specified command code, optionally with PEC. The word value that is returned should be bit- wise ANDed with the Data Word Mask and then be compared against the expected data word found in the payload. If the values do not match, it should re-read the device and only continue if the values match. It is suggested to put a timeout feature in this loop for many seconds, and if after this timeout the values still do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_WORD_LOOP_MASK [0×1A] (11 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Expected Data
Word
Data Word
Mask
Low byte High byte Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 2 2
Value 0×0B

0×00 0×1A 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_READ_WORD_EXPECT_MASK_NOPEC
*
* Overview:        PMBus Read Word without PEC, and expect a specified
*                  value bitwise ANDed with the Mask (fail if different)
* Note:            RECORD_TYPE_PMBUS_READ_WORD_EXPECT_MASK_NOPEC with
*                  value of 0×1A uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_READ_WORD_EXPECT_MASK_NOPEC (0×1A)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithoutPEC detailedRecordHeader;
UINT16 expectedDataWord;
UINT16 wordMask;
}t_RECORD_PMBUS_READ_WORD_EXPECT_MASK_NOPEC;

0×1B - RECORD_TYPE_VARIABLE_META_DATA

This record is non-standard record. The host should process this record differently depending on what the meta data type is. The type definitions are shown in the code sample below. Currently you can change the global base address or perform serialization (only supported on the LTC2978).

Like all other records, it contains the standard 4-byte header identifying its record type and the length of the record. The length in this case will be variable. As before, the length of your payload is this length minus 4 bytes long. The length will depend on what type of meta data you have.

In the case of setting the global base address, the programmer should first poll using the current global base address (0×5B by default) until it receives an ACKnowledgment. The next step is to unprotect chip. If the chip cannot be unlocked for writing, then the code should return a failure. If it succeeds, you should then write a new 16bit global base address value as defined in the meta data payload.

In the case of setting an individual chip’s serial number, you must be sure that the receiving device is an LTC2978. No other chip currently supports this feature. It is your choice as to how to get the serial number into the byte stream. The serial number is a 16bit value, with its lower 8bits stored in memory location 0×C, and its higher 8bits stored in memory location 0×D. This memory location is reserved just for the serial number, and is considered static. You may alter this memory directly to inject the serial number into the stream. To actually write the serial number, you must first poll the device until it acknowledges and then un-write protect the chip similar to above. Again, fail if you are unable to disable the write protection. Then by using command code 0×F8, write the word to the bus. You must write this word using PEC. It is then recommended to read back the written value to confirm it matches, and fail on a mismatch condition.

Note:
Serialization is only supported on the LTC2978 and attempts to serialize other devices will fail. We recommend alerting the engineer if the recipe attempts to serialize a non-LTC2978 device.
RECORD_TYPE_VARIABLE_META_DATA [0×1B] (4 byte header + variable payload length)
Field Record Header Payload Data
Record Length Record Type Meta Data Payload
Low byte High byte Low byte High byte
# bytes 2 2 VARIABLE LENGTH
Value 0×1B 0×00
/********************************************************************
* Struct:          t_RECORD_VARIABLE_META_DATA
*
* Overview:        Generic instruction used to communicate meta data
*                  to the host processor
* Note:            RECORD_TYPE_VARIABLE_META_DATA with value of 0×1B
*                  uses this struct. Currently setting the global
*                  base address and serialization are supported
*******************************************************************/
#define RECORD_TYPE_VARIABLE_META_DATA (0×1B)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
UINT16 metaDataType;
}t_RECORD_VARIABLE_META_DATA;

/********************************************************************
* Struct:          t_RECORD_META_SET_GLOBAL_BASE_ADDRESS
* Overview:        A META DATA struct containing the new global
*                  base address
*******************************************************************/
#define META_SET_GLOBAL_BASE_ADDRESS (0)
typedef struct
{
t_RECORD_VARIABLE_META_DATA metaHeader;
UINT16 globalBaseAddressInWordFormat;
}t_RECORD_META_SET_GLOBAL_BASE_ADDRESS;


/********************************************************************
* Struct:          t_RECORD_META_OEM_SERIAL_NUMBER
* Overview:        A META DATA struct containing the serial number
*                  of the device to program
*******************************************************************/
#define META_OEM_SERIAL_NUMBER (1)
typedef struct
{
t_RECORD_VARIABLE_META_DATA metaHeader;
UINT16 serialNumber;    
}t_RECORD_META_OEM_SERIAL_NUMBER;

0×1C - RECORD_TYPE_MODIFY_WORD_NOPEC

This record is multiple standard PMBus communication records. The host should process this record by reading a single word from the specified address with the specified command code, without PEC. The word value that is returned should be modified so that the bit-wise ANDed Data Word Mask bits equal the same Data Word Mask bits of the Desired Data Word. This is a read-modify-write instruction where the read is into local storage, processed upon locally by the host, and then written back to the device modified. Only the bits that are 1's in the mask should be touched.

RECORD_TYPE_MODIFY_WORD_NOPEC [0×1C] (11 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Data Word
Mask
Desired Data
Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 2 2
Value 0×0B
[11]
0×00 0×1C 0×00
/********************************************************************
* Struct:          t_RECORD_TYPE__MODIFY_WORD_NOPEC
*
* Overview:        This record type indicates that the software should
*                  read a word, apply a mask with new data to it, and
*                  then write it back to the device never using PEC
* Note:            RECORD_TYPE_MODIFY_WORD_NOPEC with value of 0×1C
*                  uses this struct. Modify only the specified bits
*                  (set to 1 in wordMask) to be desiredDataWord,
*                  never use PEC
*******************************************************************/
#define RECORD_TYPE_MODIFY_WORD_NOPEC (0×1C)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader; 
UINT16 wordMask;
UINT16 desiredDataWord;
} t_RECORD_PMBUS_MODIFY_WORD_NO_PEC;

0×1D - RECORD_TYPE_MODIFY_BYTE_NOPEC

This record is multiple standard PMBus communication records. The host should process this record by reading a single byte from the specified address with the specified command code, without PEC. The byte value that is returned should be modified so that the bit-wise ANDed Data Byte Mask bits equal the same Data Byte Mask bits of the Desired Data Byte. This is a read-modify-write instruction where the read is into local storage, processed upon locally by the host, and then written back to the device modified. Only the bits that are 1's in the mask should be touched.

RECORD_TYPE_MODIFY_BYTE_NOPEC [0×1D] (9 bytes)
Field Record Header Payload Header without PEC Payload Data
Record Length Record Type Device Address Command
Code
Data Byte
Mask
Desired Data
Byte
Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1 1
Value 0×09 0×00 0×1D 0×00
/********************************************************************
* Struct:          t_RECORD_TYPE__MODIFY_BYTE_NOPEC
*
* Overview:        This record type indicates that the software should
*                  read a byte, apply a mask with new data to it, and
*                  then write it back to the device never using PEC
* Note:            RECORD_TYPE_MODIFY_BYTE_NOPEC with value of 0×1D
*                  uses this struct. Modify only the specified bits
*                  (set to 1 in byteMask) to be desiredDataByte,
*                  never use PEC
*******************************************************************/
#define RECORD_TYPE_MODIFY_BYTE_NOPEC (0×1D)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader; 
UINT8 byteMask;
UINT8 desiredDataByte;
} t_RECORD_PMBUS_MODIFY_BYTE_NO_PEC;

0×1E - RECORD_TYPE_PMBUS_WRITE_EE_DATA

This record is not a standard PMBus communication record. The host should process this record by taking the data previously stored by 0×09 - RECORD_TYPE_NVM_DATA and actually write it to the device. It should be written to the specified address, using the specified command and optionally with PEC.

RECORD_TYPE_PMBUS_WRITE_EE_DATA [0×1E] (8 bytes)
Field Record Header Payload Header with PEC
Record Length Record Type Device Address Command Code Use PEC
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1
Value 0×08 0×00 0×1E 0×00
/********************************************************************
* Struct:          t_RECORD_TYPE_PMBUS_WRITE_EE_DATA
*
* Overview:        Write data that was previously specified in the
*                  NVM_DATA record and stored in the global linked
*                  list to the slave
* Note:            RECORD_TYPE_PMBUS_WRITE_EE_DATA with value of 0×1E
*                  uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_EE_DATA (0×1E)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader; 

}t_RECORD_TYPE_PMBUS_WRITE_EE_DATA;

0×1F - RECORD_TYPE_PMBUS_READ_AND_VERIFY_EE_DATA

This record is not a standard PMBus communication record. The host should process this record by reading a block of data from the specified address, using the specified command, optionally using PEC. Then this block of data should be compared byte-by-byte to the data previously stored by 0×09 - RECORD_TYPE_NVM_DATA. If the values do not match, it should be treated as a failure, the programming should not continue and the software should error out to the top and notify the engineer.

RECORD_TYPE_PMBUS_READ_AND_VERIFY_EE_DATA [0×1F] (8 bytes)
Field Record Header Payload Header with PEC
Record Length Record Type Device Address Command Code Use PEC
Low byte High byte Low byte High byte Low byte High byte
# bytes 2 2 2 1 1
Value 0×08 0×00 0×1F 0×00
/********************************************************************
* Struct:          t_RECORD_TYPE_PMBUS_WRITE_EE_DATA
*
* Overview:        Write data that was previously specified in the
*                  NVM_DATA record and stored in the global linked
*                  list to the slave
* Note:            RECORD_TYPE_PMBUS_WRITE_EE_DATA with value of 0×1E
*                  uses this struct
*******************************************************************/
#define RECORD_TYPE_PMBUS_WRITE_EE_DATA (0×1E)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader; 

}t_RECORD_TYPE_PMBUS_WRITE_EE_DATA;

0×20 - RECORD_TYPE_MODIFY_BYTE

This record is multiple standard PMBus communication records. The host should process this record by reading a single byte from the specified address with the specified command code, optionally with PEC. The byte value that is returned should be modified so that the bit- wise ANDed Data Byte Mask bits equal the same Data Byte Mask bits of the Desired Data Byte. This is a read-modify-write instruction where the read is into local storage, processed upon locally by the host, and then written back to the device modified. Only the bits that are 1's in the mask should be touched.

RECORD_TYPE_MODIFY_BYTE [0×20] (10 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device Address Command
Code
Use PEC Data
Byte
Mask
Desired
Data Byte
Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1 1 1
Value 0×0A
[10]
0×00 0×20 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_MODIFY_BYTE
*
* Overview:        This record type indicates that the software should
*                  read a byte, apply a mask with new data to it, and
*                  then write it back to the device optionally using PEC
* Note:            RECORD_TYPE_PMBUS_MODIFY_BYTE with value of 0×20
*                  uses this struct. Modify only the specified bits
*                  (set to 1 in byteMask) to be desiredDataByte,
*                  optionally using PEC
*******************************************************************/
// Modify only the specified word bits (set to 1 in MaskData) to be DesiredData, optional PEC
#define RECORD_TYPE_PMBUS_MODIFY_BYTE (0×20)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader; 
UINT8 byteMask;
UINT8 desiredDataByte; 
}t_RECORD_PMBUS_MODIFY_BYTE;

0×21 - RECORD_TYPE_PMBUS_MODIFY_WORD

This record is multiple standard PMBus communication records. The host should process this record by reading a single word from the specified address with the specified command code, optionally with PEC. The word value that is returned should be modified so that the bit- wise ANDed Data Word Mask bits equal the same Data Word Mask bits of the Desired Data Word. This is a read-modify-write instruction where the read is into local storage, processed upon locally by the host, and then written back to the device modified. Only the bits that are 1's in the mask should be touched.

RECORD_TYPE_PMBUS_MODIFY_WORD [0×21] (12 bytes)
Field Record Header Payload Header with PEC Payload Data
Record Length Record Type Device
Address
Command
Code
Use PEC Data Word
Mask
Desired Data
Word
Low byte High byte Low byte High byte Low byte High byte Low byte High byte Low byte High byte
#
bytes
2 2 2 1 1 2 2
Value 0×0C
[12]
0×00 0×21 0×00
/********************************************************************
* Struct:          t_RECORD_PMBUS_MODIFY_WORD
*
* Overview:        This record type indicates that the software should
*                  read a word, apply a mask with new data to it, and
*                  then write it back to the device optionally using PEC
* Note:            RECORD_TYPE_PMBUS_MODIFY_WORD with value of 0×21
*                  uses this struct. Modify only the specified bits
*                  (set to 1 in wordMask) to be desiredDataWord,
*                  optionally using PEC
*******************************************************************/
#define RECORD_TYPE_PMBUS_MODIFY_WORD (0×21)
typedef struct
{
tRecordHeaderLengthAndType baseRecordHeader;
tRecordHeaderAddressAndCommandWithOptionalPEC detailedRecordHeader; 
UINT16 wordMask;
UINT16 desiredDataWord; 
}t_RECORD_PMBUS_MODIFY_WORD;

Full Sample Source Code

You can find a full working library of the code in the LTSketchbook

This code is fully compilable with a DC2026B. Look in directory LTSketchbook/libraries/LTPSM_InFlightUpdate for the code. Some changes may be neccessary for your compiler and system. Use this code as a guide that shows a fully operational implementation in C.