| Platform SDK: Cryptography | 
The following is typical Diffie-Hellman/Schannel client-side code for creating a master key:
//--------------------------------------------------------------------
//   Define and initialize local variables.
HCRYPTPROV hProv      = <protocol engine's key container>;
HCRYPTKEY  hClientDHKey;  // handle to the client's DH key
HCRYPTKEY  hMasterKey;
ALG_ID     Algid;
PBYTE      pbServerPub = <pointer to Server Public Key>;
DWORD      cbServerPub = <size of Server Public Key>;
BYTE       rgbServerBlob[<max BLOB size>];
DWORD      cbServerBlob;
PBYTE      pbG = <pointer to generator G from Server>;
DWORD      cbG = <size of generator G from Server>;
PBYTE      pbP = <pointer to prime P from Server>;
DWORD      cbP = <size of prime P from Server>;
CRYPT_DATA_BLOB Data;
BYTE       rgbClientPubBlob[size of the client public key BLOB];
DWORD      cbClientPubBlob;
//--------------------------------------------------------------------
// Generate and set the parameters on the client DH key
// Schannel specifies the key size and [regen flag when generating
// a client DH key.
CryptGenKey(
      hProv, 
      CALG_DH_EPHEM, 
      ((cbP * 8) << 16)|CRYPT_PREGEN, 
      &hClientDHKey);
Data.pbData = pbP;
Data.cbData = cbP;
CryptSetKeyParam(
         hClientDHKey, 
         KP_P, 
         (BYTE*)&Data, 
         0);
Data.pbData = pbG;
Data.cbData = cbG;
CryptSetKeyParam(
          hClientDHKey, 
          KP_G, 
          (BYTE*)&Data, 
          0);
//--------------------------------------------------------------------
// Create the client private DH key
CryptSetKeyParam(
     hClientDHKey, 
     KP_X, 
     NULL, 
     0);
//--------------------------------------------------------------------
// Build PUBLICKEYBLOB around the server's public key
{
     BLOBHEADER *pBlobHeader = (BLOBHEADER *)rgbServerBlob;
     DHPUBKEY   *pDHPubKey   = (DHPUBKEY *)(pBlobHeader + 1);
     BYTE       *pData       = (BYTE *)(pDHPubKey + 1);
     pBlobHeader->bType    = PUBLICKEYBLOB;
     pBlobHeader->bVersion = CUR_BLOB_VERSION;
     pBlobHeader->reserved = 0;
     pBlobHeader->aiKeyAlg = CALG_DH_EPHEM;
     pDHPubKey->magic = 0x31484400;
     pDHPubKey->bitlen = dwServerPub * 8;
     ReverseMemCopy(pData, pbServerPub, cbServerPub);
     cbServerBlob = sizeof(BLOBHEADER) + sizeof(DHPUBKEY) + 
       cbServerPub;
}
//--------------------------------------------------------------------
// Import the server's public key and get an agreed key
CryptImportKey(
        hProv, 
        rgbServerBlob, 
        cbServerBlob, 
        hClientDHKey, 
        0, 
        &hMasterKey);
//--------------------------------------------------------------------
// Select the master key type.
switch(<protocol being used>)
{
    case <SSL 3.0>:
        Algid = CALG_SSL3_MASTER;
        break;
    case <TLS 1.0>:
        Algid = CALG_TLS1_MASTER;
        break;
}
//--------------------------------------------------------------------
// Convert the agreed key to the appropriate master key
CryptSetKeyParam(
        hMasterKey, 
        KP_ALGID, 
        (BYTE*)&Algid, 
        0);
//--------------------------------------------------------------------
// Export the client Diffie-Hellman public key.
cbClientPubBlob = sizeof(rgbClientPubBlob);
CryptExportKey(
           hClientDHKey, 
           0, 
           PUBLICKEYBLOB,
           0, 
           rgbClientPubBlob, 
           & cbClientPubBlob);
CryptDestroyKey(hClientDHKey);