Sample code for 30+ languages & platforms
Pascal (Lazarus/Delphi)

PKCS11 Discover Readers and Smart Cards / Tokens

See more PKCS11 Examples

Example showing how to discover the readers (slots) and smart cards and tokens available through a vendor's PKCS11 Cryptoki module.

Note: This example requires Chilkat v9.5.0.88 or later.

Chilkat Pascal (Lazarus/Delphi) Downloads

Pascal (Lazarus/Delphi)
program ChilkatDemo;

// Demonstrates using the Chilkat Pascal wrapper via the C bridge DLL.
// Builds as a console application under Lazarus (FPC) or Delphi.

{$IFDEF FPC}
  {$MODE DELPHI}
{$ENDIF}
{$APPTYPE CONSOLE}

uses
  {$IFDEF UNIX}
  cthreads,
  {$ENDIF}
  SysUtils,
  CkDllLoader,
  Chilkat.Pkcs11,
  Chilkat.JsonObject;

// ---------------------------------------------------------------------------

procedure RunDemo;
var
  success: Boolean;
  pkcs11: TPkcs11;
  onlyTokensPresent: Boolean;
  json: TJsonObject;
  id: Integer;
  slotDescription: string;
  tokenPresent: Boolean;
  removableDevice: Boolean;
  hardwareSlot: Boolean;
  hardwareVersionMajor: Integer;
  hardwareVersionMinor: Integer;
  firmwareVersionMajor: Integer;
  firmwareVersionMinor: Integer;
  tokenLabel: string;
  tokenManufacturerID: string;
  tokenModel: string;
  tokenSerialNumber: string;
  tokenMaxSessionCount: Integer;
  tokenSessionCount: Integer;
  tokenMaxRwSessionCount: Integer;
  tokenRwSessionCount: Integer;
  tokenMaxPinLen: Integer;
  tokenMinPinLen: Integer;
  tokenTotalPublicMemory: Integer;
  tokenFreePublicMemory: Integer;
  tokenTotalPrivateMemory: Integer;
  tokenFreePrivateMemory: Integer;
  tokenHardwareVersionMajor: Integer;
  tokenHardwareVersionMinor: Integer;
  tokenFirmwareVersionMajor: Integer;
  tokenFirmwareVersionMinor: Integer;
  tokenUtcTime: string;
  tokenRsaMinKeySize: Integer;
  tokenRsaMaxKeySize: Integer;
  j: Integer;
  count_j: Integer;
  strVal: string;
  cryptokiVersionMajor: Integer;
  cryptokiVersionMinor: Integer;
  manufacturerID: string;
  libraryDescription: string;
  libraryVersionMajor: Integer;
  libraryVersionMinor: Integer;
  i: Integer;
  count_i: Integer;

begin
  success := False;

  //  This example requires the Chilkat API to have been previously unlocked.
  //  See Global Unlock Sample for sample code.

  //  Note: Chilkat's PKCS11 implementation runs on Windows, Linux, Mac OS X, and other supported operating systems.

  pkcs11 := TPkcs11.Create;

  //  Specify the vendor's Cryptoki module DLL / shared lib.
  pkcs11.SharedLibPath := 'aetpkss1.dll';

  success := pkcs11.Initialize();
  if (success = False) then
    begin
      WriteLn(pkcs11.LastErrorText);
      Exit;
    end;

  //  Call Discover to discover what's available.
  //  Indicate that we only want to return slots (readers) where tokens (smart cards) are present.
  //  (If the device is a USB token, such as an ePass300Auto, then by definition it has a "token" present.)
  onlyTokensPresent := True;
  json := TJsonObject.Create;
  success := pkcs11.Discover(onlyTokensPresent,json);
  if (success = False) then
    begin
      WriteLn(pkcs11.LastErrorText);
      Exit;
    end;

  json.EmitCompact := False;
  WriteLn(json.Emit());

  //  Sample JSON output.
  //  Code for parsing this JSON is shown below..

  //  {
  //    "cryptokiVersion": {
  //      "major": 2,
  //      "minor": 20
  //    },
  //    "manufacturerID": "A.E.T. Europe B.V.",
  //    "libraryDescription": "Cryptographic Token Interface",
  //    "libraryVersion": {
  //      "major": 3,
  //      "minor": 0
  //    },
  //    "slot": [
  //      {
  //        "id": 52482,
  //        "slotDescription": "SCM Microsystems Inc. SCR33x USB Smart Card Reader 0",
  //        "manufacturerID": "SCM Microsystems Inc. SCR33x USB",
  //        "tokenPresent": true,
  //        "removableDevice": true,
  //        "hardwareSlot": true,
  //        "hardwareVersion": {
  //          "major": 0,
  //          "minor": 0
  //        },
  //        "firmwareVersion": {
  //          "major": 0,
  //          "minor": 0
  //        },
  //        "token": {
  //          "label": "chilkat",
  //          "manufacturerID": "A.E.T. Europe B.V.",
  //          "model": "19C40406010D00C0",
  //          "serialNumber": "21619600583C4505",
  //          "flags": [
  //            "CKF_RNG",
  //            "CKF_LOGIN_REQUIRED",
  //            "CKF_USER_PIN_INITIALIZED",
  //            "CKF_TOKEN_INITIALIZED"
  //          ],
  //          "maxSessionCount": 126,
  //          "sessionCount": 0,
  //          "maxRwSessionCount": 126,
  //          "rwSessionCount": 0,
  //          "maxPinLen": 15,
  //          "minPinLen": 4,
  //          "totalPublicMemory": 32767,
  //          "freePublicMemory": 32767,
  //          "totalPrivateMemory": 32767,
  //          "freePrivateMemory": 32767,
  //          "hardwareVersion": {
  //            "major": 0,
  //            "minor": 0
  //          },
  //          "firmwareVersion": {
  //            "major": 0,
  //            "minor": 0
  //          },
  //          "utcTime": "",
  //          "rsa": {
  //            "minKeySize": 768,
  //            "maxKeySize": 2048
  //          },
  //          "mechanism": [
  //            "CKM_RSA_PKCS",
  //            "CKM_RSA_X_509",
  //            "CKM_RSA_PKCS_OAEP",
  //            "CKM_MD5_RSA_PKCS",
  //            "CKM_SHA1_RSA_PKCS",
  //            "CKM_SHA224_RSA_PKCS",
  //            "CKM_SHA256_RSA_PKCS",
  //            "CKM_SHA384_RSA_PKCS",
  //            "CKM_SHA512_RSA_PKCS",
  //            "CKM_RIPEMD160_RSA_PKCS",
  //            "CKM_CPK_ECDSA",
  //            "CKM_CPK_ECDSA_SHA1",
  //            "CKM_CPK_ECIES",
  //            "CKM_CPK_ECIES_STDDH_SHA1KDF_DES3CBC_PAD_SHA1HMAC",
  //            "CKM_CPK_ECIES_STDDH_SHA1KDF_AES128CBC_PAD_SHA1HMAC",
  //            "CKM_CPK_PKCS7_SIGNED",
  //            "CKM_CPK_PKCS7_ENVELOPE_DES3CBC_PAD",
  //            "CKM_RSA_PKCS_PSS",
  //            "CKM_RSA_PKCS_KEY_PAIR_GEN",
  //            "CKM_RC2_KEY_GEN",
  //            "CKM_RC2_ECB",
  //            "CKM_RC2_CBC",
  //            "CKM_RC2_CBC_PAD",
  //            "CKM_RC4_KEY_GEN",
  //            "CKM_RC4",
  //            "CKM_DES_KEY_GEN",
  //            "CKM_DES2_KEY_GEN",
  //            "CKM_DES3_KEY_GEN",
  //            "CKM_DES_ECB",
  //            "CKM_DES_CBC",
  //            "CKM_DES3_ECB",
  //            "CKM_DES3_CBC",
  //            "CKM_DES_CBC_PAD",
  //            "CKM_DES3_CBC_PAD",
  //            "CKM_MD5",
  //            "CKM_SHA_1",
  //            "CKM_SHA224",
  //            "CKM_SHA256",
  //            "CKM_SHA384",
  //            "CKM_SHA512",
  //            "CKM_RIPEMD160"
  //          ]
  //        }
  //      }
  //    ]
  //  }

  //  Use this online tool to generate parsing code from sample JSON: 
  //  Generate Parsing Code from JSON

  //  Use this online tool to generate parsing code from sample JSON: 
  //  Generate Parsing Code from JSON

  cryptokiVersionMajor := json.IntOf('cryptokiVersion.major');
  cryptokiVersionMinor := json.IntOf('cryptokiVersion.minor');
  manufacturerID := json.StringOf('manufacturerID');
  libraryDescription := json.StringOf('libraryDescription');
  libraryVersionMajor := json.IntOf('libraryVersion.major');
  libraryVersionMinor := json.IntOf('libraryVersion.minor');
  i := 0;
  count_i := json.SizeOfArray('slot');
  while i < count_i do
    begin
      json.I := i;
      id := json.IntOf('slot[i].id');
      slotDescription := json.StringOf('slot[i].slotDescription');
      manufacturerID := json.StringOf('slot[i].manufacturerID');
      tokenPresent := json.BoolOf('slot[i].tokenPresent');
      removableDevice := json.BoolOf('slot[i].removableDevice');
      hardwareSlot := json.BoolOf('slot[i].hardwareSlot');
      hardwareVersionMajor := json.IntOf('slot[i].hardwareVersion.major');
      hardwareVersionMinor := json.IntOf('slot[i].hardwareVersion.minor');
      firmwareVersionMajor := json.IntOf('slot[i].firmwareVersion.major');
      firmwareVersionMinor := json.IntOf('slot[i].firmwareVersion.minor');
      tokenLabel := json.StringOf('slot[i].token.label');
      tokenManufacturerID := json.StringOf('slot[i].token.manufacturerID');
      tokenModel := json.StringOf('slot[i].token.model');
      tokenSerialNumber := json.StringOf('slot[i].token.serialNumber');
      tokenMaxSessionCount := json.IntOf('slot[i].token.maxSessionCount');
      tokenSessionCount := json.IntOf('slot[i].token.sessionCount');
      tokenMaxRwSessionCount := json.IntOf('slot[i].token.maxRwSessionCount');
      tokenRwSessionCount := json.IntOf('slot[i].token.rwSessionCount');
      tokenMaxPinLen := json.IntOf('slot[i].token.maxPinLen');
      tokenMinPinLen := json.IntOf('slot[i].token.minPinLen');
      tokenTotalPublicMemory := json.IntOf('slot[i].token.totalPublicMemory');
      tokenFreePublicMemory := json.IntOf('slot[i].token.freePublicMemory');
      tokenTotalPrivateMemory := json.IntOf('slot[i].token.totalPrivateMemory');
      tokenFreePrivateMemory := json.IntOf('slot[i].token.freePrivateMemory');
      tokenHardwareVersionMajor := json.IntOf('slot[i].token.hardwareVersion.major');
      tokenHardwareVersionMinor := json.IntOf('slot[i].token.hardwareVersion.minor');
      tokenFirmwareVersionMajor := json.IntOf('slot[i].token.firmwareVersion.major');
      tokenFirmwareVersionMinor := json.IntOf('slot[i].token.firmwareVersion.minor');
      tokenUtcTime := json.StringOf('slot[i].token.utcTime');
      tokenRsaMinKeySize := json.IntOf('slot[i].token.rsa.minKeySize');
      tokenRsaMaxKeySize := json.IntOf('slot[i].token.rsa.maxKeySize');
      j := 0;
      count_j := json.SizeOfArray('slot[i].token.flags');
      while j < count_j do
        begin
          json.J := j;
          strVal := json.StringOf('slot[i].token.flags[j]');
          j := j + 1;
        end;

      j := 0;
      count_j := json.SizeOfArray('slot[i].token.mechanism');
      while j < count_j do
        begin
          json.J := j;
          strVal := json.StringOf('slot[i].token.mechanism[j]');
          j := j + 1;
        end;

      i := i + 1;
    end;



  pkcs11.Free;
  json.Free;

end;

// ---------------------------------------------------------------------------

begin

  try
    RunDemo;
  except
    on E: Exception do
      WriteLn('Unhandled exception: ', E.ClassName, ': ', E.Message);
  end;

  WriteLn;
  {$IFDEF MSWINDOWS}
  WriteLn('Press Enter to exit...');
  ReadLn;
  {$ENDIF}
end.