Custom implementation of the GUID generation



{*****************************************************************************
Name : GuidGen
Author : Perevoznyk Serhiy
Description : Custom implementation of the GUID generation
History :

Date By Description
---- -- -----------
5/13/05 Perevoznyk Serhiy Initial creation of the Unit.
*****************************************************************************}

unit GuidGen;

interface

uses
Windows, SysUtils;

const
PROV_RSA_FULL = 1;
CRYPT_VERIFYCONTEXT = $f0000000;
ReservedNCS = $00;
Standard = $02;
ReservedMicrosoft = $06;
ReservedFuture = $07;
TimeBased = $01;
Reserved = $02;
NameBased = $03;
VRandom = $04;
VariantByte = 8;
VariantByteMask = $3f;
VariantByteShift = 6;
VersionByte = 7;
VersionByteMask = $0f;
VersionByteShift = 4;


{:-----------------------------------------------------------------------------
The CryptAcquireContext function is used to acquire a handle to a particular
key container within a particular cryptographic service provider (CSP). This
returned handle is used in calls to CryptoAPI functions that use the selected CSP.
-----------------------------------------------------------------------------}
function CryptAcquireContextA(phProv : pointer; pszContainer : LPCTSTR;
pszProvider : LPCTSTR; dwprovType : DWORD; dwFlags : DWORD) : boolean; stdcall; external 'Advapi32.dll';

{:-----------------------------------------------------------------------------
The CryptReleaseContext function releases the handle of a cryptographic service
provider (CSP) and a key container. At each call to this function, the reference
count on the CSP is reduced by one. When the reference count reaches zero, the
context is fully released and it can no longer be used by any function in
the application.
-----------------------------------------------------------------------------}
function CryptReleaseContext(hProv : pointer; dwFlags : DWORD) : boolean; stdcall; external 'Advapi32.dll';

{:-----------------------------------------------------------------------------
The CryptGenRandom function fills a buffer with cryptographically random bytes.
-----------------------------------------------------------------------------}
function CryptGenRandom(hProv : pointer; dwLen : DWORD; pbBuffer : pointer) : boolean; stdcall; external 'Advapi32.dll';

{:-----------------------------------------------------------------------------
Custom method to generate GUIDs
-----------------------------------------------------------------------------}
function NewGUID : TGUID;

implementation

function NewGUID : TGUID;
var
hCryptProv : pointer;
bits : array[0..15] of byte;
begin
FillChar(Result, 16, 0);
hCryptProv := nil;
try
if not CryptAcquireContextA(@hCryptProv, nil, nil, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT) then
raise Exception.Create('Failed to acquire cryptography handle');
if not CryptGenRandom(hCryptProv, 16, @bits) then
raise Exception.Create('Failed to generate cryptography random bytes');
bits[VariantByte] := bits[VariantByte] AND VariantByteMask;
bits[VariantByte] := bits[VariantByte] Or (Standard shl VariantByteShift);
bits[VersionByte] := bits[VersionByte] And VersionByteMask;
bits[VersionByte] := bits[VersionByte] Or (VRandom shl VersionByteShift);
Move(bits, Result, 16);
finally
if hCryptProv <> nil then
CryptReleaseContext(hCryptProv, 0);
end;
end;

end.

Comments

Post a Comment

Popular posts from this blog

Quricol - QR code generator library

Quricol 2.0 - QR Code generator

EIDNative Library 2.0 released