Platform SDK: Cryptography

Simple Key BLOBs

Simple key BLOBs (type SIMPLEBLOB) are used to store and transport session keys. These are always encrypted with a key exchange public key. They have the following format:

BLOBHEADER blobheader;
ALG_ID algid;
BYTE encryptedkey[rsapubkey.bitlen/8];

The algorithm identifier that immediately follows the BLOBHEADER structure specifies the encryption algorithm that was used to encrypt the session key data. This typically has a value of CALG_RSA_KEYX, indicating that the session key data was encrypted with a key exchange public key, using the RSA Public-Key algorithm.

The encrypted session key data is in the form of a PKCS #1, type 2 encryption block. For details on this data format, see The Public-Key Cryptography Standards (PKCS), published by RSA Data Security, Inc.

This data is always the same size as the public key's modulus. For example, public keys generated by the Microsoft Base Cryptographic Provider are always 512 bits (64 bytes) in length, so the encrypted session key data is also always 64 bytes.

Sample Simple Key BLOB

Two data items are required before a SIMPLEBLOB structure can be built: the session key to be transported and the public key used to encrypt the session key. This example shows a typical 40-bit RC4 session key and a public key used to encrypt it. In this example, the hexadecimal value of the session key material is:

74 4f 06 35 3f

The first step is building the PKCS #1, type 2 encryption block. This is always the same size as the public key's modulus (64 bytes) and contains the following fields.

Field Bytes Description
Key material 1 to 5 Session key material. The size of this field varies depending on the size of the session key.

The bytes in the session key data are reversed before they are placed in the encryption block because the operating system formats data in little-endian format, and the encryption block must be built in big-endian format.

Reserved 6 Zero value.
Padding 7 to 56 Random padding data. The size of this field is adjusted as necessary so that the encryption block's overall length is correct. It can be longer than the 50 bytes indicated here if a longer RSA key is used. None of these bytes are allowed to be zero.
Block type 57 The PKCS block type (0x02).
Reserved 58 Zero value.

The order of this table is reversed from the diagram found in the PKCS documentation because the encryption block is built in big-endian format on a little-endian computer.

After the encryption block has been built, its sixty-four byte hexadecimal value could look something like this:

3f 35 06 4f 74 00 c9 db
b1 74 b0 de 8e d4 aa c5
99 8a 4d 19 4f 0f ed 24
b0 2e 93 fe e9 f4 d4 93
dc ac 9e 9f 3a 62 be f1
e4 1d 44 5c 33 e5 2f 4f
58 01 95 16 36 f7 86 65
68 6c 2a 28 79 55 02 00

Next, the block is encrypted with the appropriate public key. After this is done, the encrypted block might look like this:

e3 c1 78 62 c4 1f 51 4f
e9 50 89 fd 0d 58 bd 9d
74 c7 54 19 bd 97 3b a0
f0 6c ee 86 05 74 16 62
27 a5 99 63 c4 6f 95 ed
3e 93 ba 9a ea 36 cc 96
92 e8 aa 15 2c 50 a1 3c
38 d3 1f 08 e2 82 cd 90

Finally, the BLOBHEADER structure and the algorithm identifier are tacked onto the front of the encryption block, resulting in a complete SIMPLEBLOB data structure:

01 02 00 00 01 68 00 00
00 a4 00 00 e3 c1 78 62
c4 1f 51 4f e9 50 89 fd
0d 58 bd 9d 74 c7 54 19
bd 97 3b a0 f0 6c ee 86
05 74 16 62 27 a5 99 63
c4 6f 95 ed 3e 93 ba 9a
ea 36 cc 96 92 e8 aa 15
2c 50 a1 3c d3 1f 08 e2
82 cd 90 2b            

Note  The encrypted block begins at byte 13.

The BLOBHEADER structure and the algorithm identifier have been assigned the following values:

blobheader.bType    = SIMPLEBLOB;         // 0x01     in byte number 1
blobheader.bVersion = CUR_BLOB_VERSION;   // 0x02     in byte number 2
blobheader.Reserved = 0;                  // 0x0000   in bytes 3 and 4
blobheader.aiKeyAlg = CALG_RC4;           // 0x00006801 in reverse 
                                          // order in bytes 5, 6, 7,
                                          // and 8
algid               = CALG_RSA_KEYX;      // 0x0000a400  in reverse
                                          // order in bytes 9, 10, 11,
                                          // and 12

When filling in the BLOBHEADER structure, the two Reserved field bytes are set to zero.