Undocumented Windows cryptography

2006 December 18
by Ilya

The last time we described semi- and undocumented functions in Windows, these were . Today’s subject is cryptographic functions. There are such functions in Windows core that allows you to use few cryptographic primitives easier, without whole CAPI overhead and hassle. Here is an example of how to generate secure random numbers and calculate SHA-1 hash.

First, a C header file capix.h which you may use in your own programs right away:

/* =======================================================================
   CAPIx
   Few cryptographic primitives for direct usage without CAPI overhead.
   Based on un(semi)documented Windows XP+ interface
========================================================================= */

#pragma warning (push, 1)
#define WINDOWS_MEAN_AND_LEAN
#include <windows.h>
#pragma warning(pop)

typedef struct {
   ULONG SomeJunk[6];
   ULONG State[5];
   ULONG Count[2];
   UCHAR Buffer[64];
} SHA_CONTEXT, *PSHA_CONTEXT;

typedef BOOL  (__stdcall *RtlGenRandom_Fn)(OUT PVOID, IN ULONG);
typedef PVOID (__stdcall *SHA_Init_Fn)(IN OUT PSHA_CONTEXT);
typedef PVOID (__stdcall *SHA_Update_Fn)(IN OUT PSHA_CONTEXT, IN PCHAR, IN UINT);
typedef PVOID (__stdcall *SHA_Final_Fn)(IN OUT PSHA_CONTEXT, OUT PVOID); 

static HANDLE          hAA32DLL      = NULL;
static RtlGenRandom_Fn pf_rand       = NULL;
static SHA_Init_Fn     pf_sha_init   = NULL;
static SHA_Update_Fn   pf_sha_update = NULL;
static SHA_Final_Fn    pf_sha_final  = NULL;

BOOL InitCAPIX (void)
{
  hAA32DLL = LoadLibrary ("advapi32.dll");
  if ( hAA32DLL != NULL )
  {
    pf_rand = (RtlGenRandom_Fn) GetProcAddress(hAA32DLL, "SystemFunction036");
    pf_sha_init = (SHA_Init_Fn) GetProcAddress(hAA32DLL, "A_SHAInit");
    pf_sha_update = (SHA_Update_Fn) GetProcAddress(hAA32DLL, "A_SHAUpdate");
    pf_sha_final = (SHA_Final_Fn) GetProcAddress(hAA32DLL, "A_SHAFinal");
  }
  return ( hAA32DLL != NULL );
} /* initcapix */

void _inline ReleaseCAPIX (void)
{
   pf_rand = NULL;
   pf_sha_init = NULL;
   pf_sha_update = NULL;
   pf_sha_final = NULL;
   while (!FreeLibrary (hAA32DLL) );
   hAA32DLL = NULL;
} /* donecapix */

#define random_s(x,y)      ((pf_rand != NULL)?(*pf_rand)(x,y):FALSE)
#define sha1_init(x)       ((pf_sha_init != NULL)?(*pf_sha_init)(x):NULL)
#define sha1_update(x,y,z) ((pf_sha_update != NULL)?(*pf_sha_update)(x,(PCHAR)y,z):NULL)
#define sha1_final(x,y)    ((pf_sha_final != NULL)?(*pf_sha_final)(x,y):NULL)

Next is a C demo program that uses capix.h:

#pragma warning (push, 1)
#include "capix.h"
#include <stdlib.h>
#include <stdio.h>
#pragma warning(pop)

int main (void)
{
   BYTE hash[20] = {0}, buf[12] = {0};
   SHA_CONTEXT ctx;
   PVOID dw;
   register BYTE i;

   InitCAPIX();

   if ( !random_s(buf, sizeof(buf)) ) printf("Failed at generate random\n");
   printf("data: ");
   for (i = 0; i< sizeof(buf); i++) printf("%02x", buf[i]);
   printf("\n");

   dw = sha1_init(&ctx);
   if ( dw ) dw = sha1_update(&ctx, buf, sizeof(buf));
   if ( dw ) dw = sha1_final(&ctx, hash);
   if ( dw )
   {
      printf("hash: ");
      for (i = 0; i< sizeof(hash); i++) printf("%02x", hash[i]);
      printf("\n");
   }
   else printf("SHA1 functions failed\n");

   ReleaseCAPIX();

   return 0;
}
Reddit this / Add to del.icio.us / Digg this!
13 Comments leave one →
2006 December 20

Do you know why they’re undocumented? Because they are implementation details subject to change in future versions of Windows. Anyone using this is likely to wind up with a broken application. You are performing a public disservice.

2006 December 20

Dan,
I’m very well aware about that, thank you very much. As anyone else, who would understand this without an explicit disclaimer. You’ve missed two points:
- tag ‘zanymatics’
- this is not a tech course

2006 December 20

Oh, sorry, I missed the obscure, if not invented term in your tiny tag cloud tucked away on the right. However, I did notice: “First, a C header file capix.h which you may use in your own programs right away.” Retard.

2006 December 20

How lovely!
Is it just Wednesday, or you are like this 24/7/365?

2006 December 30
Jeff permalink

Microsoft is using Crypto++ code. The are aiding in the Library’s FIPS certification.

See http://www.crytpopp.com

2006 December 30
Jeff permalink

Whoops… http://www.cryptopp.com

2007 January 4

@Jeff:

Why do you think so? Is it because of SHA_CONTEXT structure of what? From what I see there is nothing firm enough to support such conclusion.

2007 July 3
student permalink

hey can sum1 help me…i hv this huge asssignment due 2mrw .. im doin my IT degree…i need information on the UNIX and Windows encryption in terms of passwords and the use of hashing and block ciphers in both…. thanks alot…

2007 July 3
student permalink

this is the question:
compare the way UNIX passwords and Windows Lan Manager passwords are encrypted with a block cipher. Explain why seemingly similar algorithms have such different properties.

2007 July 3
student permalink

thanx 4 the other links but i already had that i need more help… another question:
what are the objectives of an attacker performing reconnaissance?

2007 July 3
student permalink

and 3 good sources of information for this purpose- reconnaissance

2007 July 3

@student

The purpose of reconnaissance (”information gathering”) is to learn the target and identify the attack points.
http://en.wikipedia.org/wiki/Reconnaissance

You may google for the rest :)

Leave A Comment

Note: You can use basic XHTML in your comments. Your email address will never be published.

Subscribe to this comment feed via RSS