Replaced stdio logging with WLog

This commit is contained in:
Armin Novak 2014-08-18 17:22:22 +02:00
parent 3e21e570b8
commit 28ece6bb46
40 changed files with 2509 additions and 3166 deletions

View File

@ -42,34 +42,37 @@
#include <malloc.h>
#endif
#include "../log.h"
#define TAG "crt"
struct winpr_aligned_mem
{
UINT32 sig;
size_t size;
void* base_addr;
void *base_addr;
};
typedef struct winpr_aligned_mem WINPR_ALIGNED_MEM;
void* _aligned_malloc(size_t size, size_t alignment)
void *_aligned_malloc(size_t size, size_t alignment)
{
return _aligned_offset_malloc(size, alignment, 0);
}
void* _aligned_realloc(void* memblock, size_t size, size_t alignment)
void *_aligned_realloc(void *memblock, size_t size, size_t alignment)
{
return _aligned_offset_realloc(memblock, size, alignment, 0);
}
void* _aligned_recalloc(void* memblock, size_t num, size_t size, size_t alignment)
void *_aligned_recalloc(void *memblock, size_t num, size_t size, size_t alignment)
{
return _aligned_offset_recalloc(memblock, num, size, alignment, 0);
}
void* _aligned_offset_malloc(size_t size, size_t alignment, size_t offset)
void *_aligned_offset_malloc(size_t size, size_t alignment, size_t offset)
{
void* base;
void* memblock;
WINPR_ALIGNED_MEM* pMem;
void *base;
void *memblock;
WINPR_ALIGNED_MEM *pMem;
/* alignment must be a power of 2 */
if (alignment % 2 == 1)
@ -80,8 +83,8 @@ void* _aligned_offset_malloc(size_t size, size_t alignment, size_t offset)
return NULL;
/* minimum alignment is pointer size */
if (alignment < sizeof(void*))
alignment = sizeof(void*);
if (alignment < sizeof(void *))
alignment = sizeof(void *);
/* malloc size + alignment to make sure we can align afterwards */
base = malloc(size + alignment + sizeof(WINPR_ALIGNED_MEM));
@ -89,22 +92,20 @@ void* _aligned_offset_malloc(size_t size, size_t alignment, size_t offset)
if (!base)
return NULL;
memblock = (void*)((((size_t)(((BYTE*) base) + alignment + offset + sizeof(WINPR_ALIGNED_MEM)) & ~(alignment - 1)) - offset));
memblock = (void *)((((size_t)(((BYTE *) base) + alignment + offset + sizeof(WINPR_ALIGNED_MEM)) & ~(alignment - 1)) - offset));
pMem = WINPR_ALIGNED_MEM_STRUCT_FROM_PTR(memblock);
pMem->sig = WINPR_ALIGNED_MEM_SIGNATURE;
pMem->base_addr = base;
pMem->size = size;
return memblock;
}
void* _aligned_offset_realloc(void* memblock, size_t size, size_t alignment, size_t offset)
void *_aligned_offset_realloc(void *memblock, size_t size, size_t alignment, size_t offset)
{
size_t copySize;
void* newMemblock;
WINPR_ALIGNED_MEM* pMem;
WINPR_ALIGNED_MEM* pNewMem;
void *newMemblock;
WINPR_ALIGNED_MEM *pMem;
WINPR_ALIGNED_MEM *pNewMem;
if (!memblock)
return _aligned_offset_malloc(size, alignment, offset);
@ -125,23 +126,21 @@ void* _aligned_offset_realloc(void* memblock, size_t size, size_t alignment, siz
if (pMem->sig != WINPR_ALIGNED_MEM_SIGNATURE)
{
fprintf(stderr, "_aligned_offset_realloc: memory block was not allocated by _aligned_malloc!\n");
WLog_ERR(TAG, "_aligned_offset_realloc: memory block was not allocated by _aligned_malloc!\n");
return NULL;
}
copySize = (pNewMem->size < pMem->size) ? pNewMem->size : pMem->size;
CopyMemory(newMemblock, memblock, copySize);
_aligned_free(memblock);
return newMemblock;
}
void* _aligned_offset_recalloc(void* memblock, size_t num, size_t size, size_t alignment, size_t offset)
void *_aligned_offset_recalloc(void *memblock, size_t num, size_t size, size_t alignment, size_t offset)
{
void* newMemblock;
WINPR_ALIGNED_MEM* pMem;
WINPR_ALIGNED_MEM* pNewMem;
void *newMemblock;
WINPR_ALIGNED_MEM *pMem;
WINPR_ALIGNED_MEM *pNewMem;
if (!memblock)
return _aligned_offset_malloc(size, alignment, offset);
@ -162,19 +161,18 @@ void* _aligned_offset_recalloc(void* memblock, size_t num, size_t size, size_t a
if (pMem->sig != WINPR_ALIGNED_MEM_SIGNATURE)
{
fprintf(stderr, "_aligned_offset_recalloc: memory block was not allocated by _aligned_malloc!\n");
WLog_ERR(TAG, "_aligned_offset_recalloc: memory block was not allocated by _aligned_malloc!\n");
return NULL;
}
ZeroMemory(newMemblock, pNewMem->size);
_aligned_free(memblock);
return newMemblock;
}
size_t _aligned_msize(void* memblock, size_t alignment, size_t offset)
size_t _aligned_msize(void *memblock, size_t alignment, size_t offset)
{
WINPR_ALIGNED_MEM* pMem;
WINPR_ALIGNED_MEM *pMem;
if (!memblock)
return 0;
@ -183,16 +181,16 @@ size_t _aligned_msize(void* memblock, size_t alignment, size_t offset)
if (pMem->sig != WINPR_ALIGNED_MEM_SIGNATURE)
{
fprintf(stderr, "_aligned_msize: memory block was not allocated by _aligned_malloc!\n");
WLog_ERR(TAG, "_aligned_msize: memory block was not allocated by _aligned_malloc!\n");
return 0;
}
return pMem->size;
}
void _aligned_free(void* memblock)
void _aligned_free(void *memblock)
{
WINPR_ALIGNED_MEM* pMem;
WINPR_ALIGNED_MEM *pMem;
if (!memblock)
return;
@ -201,7 +199,7 @@ void _aligned_free(void* memblock)
if (pMem->sig != WINPR_ALIGNED_MEM_SIGNATURE)
{
fprintf(stderr, "_aligned_free: memory block was not allocated by _aligned_malloc!\n");
WLog_ERR(TAG, "_aligned_free: memory block was not allocated by _aligned_malloc!\n");
return;
}

View File

@ -32,9 +32,12 @@
#include "casing.c"
char* _strdup(const char* strSource)
#include "../log.h"
#define TAG "crt"
char *_strdup(const char *strSource)
{
char* strDestination;
char *strDestination;
if (strSource == NULL)
return NULL;
@ -42,14 +45,14 @@ char* _strdup(const char* strSource)
strDestination = strdup(strSource);
if (strDestination == NULL)
perror("strdup");
WLog_ERR(TAG,"strdup");
return strDestination;
}
WCHAR* _wcsdup(const WCHAR* strSource)
WCHAR *_wcsdup(const WCHAR *strSource)
{
WCHAR* strDestination;
WCHAR *strDestination;
if (strSource == NULL)
return NULL;
@ -57,33 +60,34 @@ WCHAR* _wcsdup(const WCHAR* strSource)
#if defined(sun) && sun
strDestination = wsdup(strSource);
#elif defined(__APPLE__) && defined(__MACH__) || defined(ANDROID)
strDestination = malloc(wcslen((wchar_t*)strSource));
strDestination = malloc(wcslen((wchar_t *)strSource));
if (strDestination != NULL)
wcscpy((wchar_t*)strDestination, (const wchar_t*)strSource);
wcscpy((wchar_t *)strDestination, (const wchar_t *)strSource);
#else
strDestination = (WCHAR*) wcsdup((wchar_t*) strSource);
strDestination = (WCHAR *) wcsdup((wchar_t *) strSource);
#endif
if (strDestination == NULL)
perror("wcsdup");
WLog_ERR(TAG,"wcsdup");
return strDestination;
}
int _stricmp(const char* string1, const char* string2)
int _stricmp(const char *string1, const char *string2)
{
return strcasecmp(string1, string2);
}
int _strnicmp(const char* string1, const char* string2, size_t count)
int _strnicmp(const char *string1, const char *string2, size_t count)
{
return strncasecmp(string1, string2, count);
}
/* _wcscmp -> wcscmp */
int _wcscmp(const WCHAR* string1, const WCHAR* string2)
int _wcscmp(const WCHAR *string1, const WCHAR *string2)
{
while (*string1 && (*string1 == *string2))
{
@ -96,9 +100,9 @@ int _wcscmp(const WCHAR* string1, const WCHAR* string2)
/* _wcslen -> wcslen */
size_t _wcslen(const WCHAR* str)
size_t _wcslen(const WCHAR *str)
{
WCHAR* p = (WCHAR*) str;
WCHAR *p = (WCHAR *) str;
if (!p)
return 0;
@ -111,9 +115,9 @@ size_t _wcslen(const WCHAR* str)
/* _wcschr -> wcschr */
WCHAR* _wcschr(const WCHAR* str, WCHAR c)
WCHAR *_wcschr(const WCHAR *str, WCHAR c)
{
WCHAR* p = (WCHAR*) str;
WCHAR *p = (WCHAR *) str;
while (*p && (*p != c))
p++;
@ -121,14 +125,14 @@ WCHAR* _wcschr(const WCHAR* str, WCHAR c)
return ((*p == c) ? p : NULL);
}
char* strtok_s(char* strToken, const char* strDelimit, char** context)
char *strtok_s(char *strToken, const char *strDelimit, char **context)
{
return strtok_r(strToken, strDelimit, context);
}
WCHAR* wcstok_s(WCHAR* strToken, const WCHAR* strDelimit, WCHAR** context)
WCHAR *wcstok_s(WCHAR *strToken, const WCHAR *strDelimit, WCHAR **context)
{
WCHAR* nextToken;
WCHAR *nextToken;
if (!strToken)
strToken = *context;
@ -148,7 +152,6 @@ WCHAR* wcstok_s(WCHAR* strToken, const WCHAR* strDelimit, WCHAR** context)
*strToken++ = 0;
*context = strToken;
return nextToken;
}
@ -165,6 +168,7 @@ LPSTR CharUpperA(LPSTR lpsz)
return NULL;
length = strlen(lpsz);
if (length < 1)
return (LPSTR) NULL;
@ -176,7 +180,6 @@ LPSTR CharUpperA(LPSTR lpsz)
c = c - 32;
*lpsz = c;
return lpsz;
}
@ -191,8 +194,7 @@ LPSTR CharUpperA(LPSTR lpsz)
LPWSTR CharUpperW(LPWSTR lpsz)
{
fprintf(stderr, "CharUpperW unimplemented!\n");
WLog_ERR(TAG, "CharUpperW unimplemented!\n");
return (LPWSTR) NULL;
}
@ -245,7 +247,6 @@ LPSTR CharLowerA(LPSTR lpsz)
c = c + 32;
*lpsz = c;
return lpsz;
}
@ -260,8 +261,7 @@ LPSTR CharLowerA(LPSTR lpsz)
LPWSTR CharLowerW(LPWSTR lpsz)
{
fprintf(stderr, "CharLowerW unimplemented!\n");
WLog_ERR(TAG, "CharLowerW unimplemented!\n");
return (LPWSTR) NULL;
}
@ -303,7 +303,7 @@ BOOL IsCharAlphaA(CHAR ch)
BOOL IsCharAlphaW(WCHAR ch)
{
fprintf(stderr, "IsCharAlphaW unimplemented!\n");
WLog_ERR(TAG, "IsCharAlphaW unimplemented!\n");
return 0;
}
@ -318,7 +318,7 @@ BOOL IsCharAlphaNumericA(CHAR ch)
BOOL IsCharAlphaNumericW(WCHAR ch)
{
fprintf(stderr, "IsCharAlphaNumericW unimplemented!\n");
WLog_ERR(TAG, "IsCharAlphaNumericW unimplemented!\n");
return 0;
}
@ -332,7 +332,7 @@ BOOL IsCharUpperA(CHAR ch)
BOOL IsCharUpperW(WCHAR ch)
{
fprintf(stderr, "IsCharUpperW unimplemented!\n");
WLog_ERR(TAG, "IsCharUpperW unimplemented!\n");
return 0;
}
@ -346,7 +346,7 @@ BOOL IsCharLowerA(CHAR ch)
BOOL IsCharLowerW(WCHAR ch)
{
fprintf(stderr, "IsCharLowerW unimplemented!\n");
WLog_ERR(TAG, "IsCharLowerW unimplemented!\n");
return 0;
}

View File

@ -1,8 +1,8 @@
/*
* Copyright 2001-2004 Unicode, Inc.
*
*
* Disclaimer
*
*
* This source code is provided as is by Unicode, Inc. No claims are
* made as to fitness for any particular purpose. No warranties of any
* kind are expressed or implied. The recipient agrees to determine
@ -10,9 +10,9 @@
* purchased on magnetic or optical media from Unicode, Inc., the
* sole remedy for any claim will be exchange of defective media
* within 90 days of receipt.
*
*
* Limitations on Rights to Redistribute This Code
*
*
* Unicode, Inc. hereby grants the right to freely use the information
* supplied in this file in the creation of products supporting the
* Unicode Standard, and to make copies of this file in any form
@ -52,108 +52,156 @@ static const DWORD halfMask = 0x3FFUL;
/* --------------------------------------------------------------------- */
ConversionResult ConvertUTF32toUTF16 (
const DWORD** sourceStart, const DWORD* sourceEnd,
WCHAR** targetStart, WCHAR* targetEnd, ConversionFlags flags) {
ConversionResult result = conversionOK;
const DWORD* source = *sourceStart;
WCHAR* target = *targetStart;
while (source < sourceEnd) {
DWORD ch;
if (target >= targetEnd) {
result = targetExhausted; break;
}
ch = *source++;
if (ch <= UNI_MAX_BMP) { /* Target is a character <= 0xFFFF */
/* UTF-16 surrogate values are illegal in UTF-32; 0xffff or 0xfffe are both reserved values */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END) {
if (flags == strictConversion) {
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
} else {
*target++ = UNI_REPLACEMENT_CHAR;
}
} else {
*target++ = (WCHAR)ch; /* normal case */
}
} else if (ch > UNI_MAX_LEGAL_UTF32) {
if (flags == strictConversion) {
result = sourceIllegal;
} else {
*target++ = UNI_REPLACEMENT_CHAR;
}
} else {
/* target is a character in range 0xFFFF - 0x10FFFF. */
if (target + 1 >= targetEnd) {
--source; /* Back up source pointer! */
result = targetExhausted; break;
}
ch -= halfBase;
*target++ = (WCHAR)((ch >> halfShift) + UNI_SUR_HIGH_START);
*target++ = (WCHAR)((ch & halfMask) + UNI_SUR_LOW_START);
}
}
*sourceStart = source;
*targetStart = target;
return result;
ConversionResult ConvertUTF32toUTF16(
const DWORD **sourceStart, const DWORD *sourceEnd,
WCHAR **targetStart, WCHAR *targetEnd, ConversionFlags flags)
{
ConversionResult result = conversionOK;
const DWORD *source = *sourceStart;
WCHAR *target = *targetStart;
while (source < sourceEnd)
{
DWORD ch;
if (target >= targetEnd)
{
result = targetExhausted;
break;
}
ch = *source++;
if (ch <= UNI_MAX_BMP) /* Target is a character <= 0xFFFF */
{
/* UTF-16 surrogate values are illegal in UTF-32; 0xffff or 0xfffe are both reserved values */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END)
{
if (flags == strictConversion)
{
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
else
{
*target++ = UNI_REPLACEMENT_CHAR;
}
}
else
{
*target++ = (WCHAR)ch; /* normal case */
}
}
else if (ch > UNI_MAX_LEGAL_UTF32)
{
if (flags == strictConversion)
{
result = sourceIllegal;
}
else
{
*target++ = UNI_REPLACEMENT_CHAR;
}
}
else
{
/* target is a character in range 0xFFFF - 0x10FFFF. */
if (target + 1 >= targetEnd)
{
--source; /* Back up source pointer! */
result = targetExhausted;
break;
}
ch -= halfBase;
*target++ = (WCHAR)((ch >> halfShift) + UNI_SUR_HIGH_START);
*target++ = (WCHAR)((ch & halfMask) + UNI_SUR_LOW_START);
}
}
*sourceStart = source;
*targetStart = target;
return result;
}
/* --------------------------------------------------------------------- */
ConversionResult ConvertUTF16toUTF32 (
const WCHAR** sourceStart, const WCHAR* sourceEnd,
DWORD** targetStart, DWORD* targetEnd, ConversionFlags flags) {
ConversionResult result = conversionOK;
const WCHAR* source = *sourceStart;
DWORD* target = *targetStart;
DWORD ch, ch2;
while (source < sourceEnd) {
const WCHAR* oldSource = source; /* In case we have to back up because of target overflow. */
ch = *source++;
/* If we have a surrogate pair, convert to UTF32 first. */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_HIGH_END) {
/* If the 16 bits following the high surrogate are in the source buffer... */
if (source < sourceEnd) {
ch2 = *source;
/* If it's a low surrogate, convert to UTF32. */
if (ch2 >= UNI_SUR_LOW_START && ch2 <= UNI_SUR_LOW_END) {
ch = ((ch - UNI_SUR_HIGH_START) << halfShift)
+ (ch2 - UNI_SUR_LOW_START) + halfBase;
++source;
} else if (flags == strictConversion) { /* it's an unpaired high surrogate */
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
} else { /* We don't have the 16 bits following the high surrogate. */
--source; /* return to the high surrogate */
result = sourceExhausted;
break;
}
} else if (flags == strictConversion) {
/* UTF-16 surrogate values are illegal in UTF-32 */
if (ch >= UNI_SUR_LOW_START && ch <= UNI_SUR_LOW_END) {
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
}
if (target >= targetEnd) {
source = oldSource; /* Back up source pointer! */
result = targetExhausted; break;
}
*target++ = ch;
}
*sourceStart = source;
*targetStart = target;
ConversionResult ConvertUTF16toUTF32(
const WCHAR **sourceStart, const WCHAR *sourceEnd,
DWORD **targetStart, DWORD *targetEnd, ConversionFlags flags)
{
ConversionResult result = conversionOK;
const WCHAR *source = *sourceStart;
DWORD *target = *targetStart;
DWORD ch, ch2;
while (source < sourceEnd)
{
const WCHAR *oldSource = source; /* In case we have to back up because of target overflow. */
ch = *source++;
/* If we have a surrogate pair, convert to UTF32 first. */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_HIGH_END)
{
/* If the 16 bits following the high surrogate are in the source buffer... */
if (source < sourceEnd)
{
ch2 = *source;
/* If it's a low surrogate, convert to UTF32. */
if (ch2 >= UNI_SUR_LOW_START && ch2 <= UNI_SUR_LOW_END)
{
ch = ((ch - UNI_SUR_HIGH_START) << halfShift)
+ (ch2 - UNI_SUR_LOW_START) + halfBase;
++source;
}
else if (flags == strictConversion) /* it's an unpaired high surrogate */
{
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
}
else /* We don't have the 16 bits following the high surrogate. */
{
--source; /* return to the high surrogate */
result = sourceExhausted;
break;
}
}
else if (flags == strictConversion)
{
/* UTF-16 surrogate values are illegal in UTF-32 */
if (ch >= UNI_SUR_LOW_START && ch <= UNI_SUR_LOW_END)
{
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
}
if (target >= targetEnd)
{
source = oldSource; /* Back up source pointer! */
result = targetExhausted;
break;
}
*target++ = ch;
}
*sourceStart = source;
*targetStart = target;
#ifdef CVTUTF_DEBUG
if (result == sourceIllegal) {
fprintf(stderr, "ConvertUTF16toUTF32 illegal seq 0x%04x,%04x\n", ch, ch2);
fflush(stderr);
}
if (result == sourceIllegal)
{
WLOG_WARN(TAG, "ConvertUTF16toUTF32 illegal seq 0x%04x,%04x\n", ch, ch2);
}
#endif
return result;
return result;
}
/* --------------------------------------------------------------------- */
@ -165,15 +213,16 @@ if (result == sourceIllegal) {
* left as-is for anyone who may want to do such conversion, which was
* allowed in earlier algorithms.
*/
static const char trailingBytesForUTF8[256] = {
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2, 3,3,3,3,3,3,3,3,4,4,4,4,5,5,5,5
static const char trailingBytesForUTF8[256] =
{
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1, 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2, 3,3,3,3,3,3,3,3,4,4,4,4,5,5,5,5
};
/*
@ -181,8 +230,9 @@ static const char trailingBytesForUTF8[256] = {
* This table contains as many values as there might be trailing bytes
* in a UTF-8 sequence.
*/
static const DWORD offsetsFromUTF8[6] = { 0x00000000UL, 0x00003080UL, 0x000E2080UL,
0x03C82080UL, 0xFA082080UL, 0x82082080UL };
static const DWORD offsetsFromUTF8[6] = { 0x00000000UL, 0x00003080UL, 0x000E2080UL,
0x03C82080UL, 0xFA082080UL, 0x82082080UL
};
/*
* Once the bits are split out into bytes of UTF-8, this is a mask OR-ed
@ -206,16 +256,14 @@ static const BYTE firstByteMark[7] = { 0x00, 0x00, 0xC0, 0xE0, 0xF0, 0xF8, 0xFC
/* --------------------------------------------------------------------- */
ConversionResult ConvertUTF16toUTF8(
const WCHAR** sourceStart, const WCHAR* sourceEnd,
BYTE** targetStart, BYTE* targetEnd, ConversionFlags flags)
const WCHAR **sourceStart, const WCHAR *sourceEnd,
BYTE **targetStart, BYTE *targetEnd, ConversionFlags flags)
{
BYTE* target;
const WCHAR* source;
BYTE *target;
const WCHAR *source;
BOOL computeLength;
ConversionResult result;
computeLength = (!targetEnd) ? TRUE : FALSE;
source = *sourceStart;
target = *targetStart;
result = conversionOK;
@ -226,23 +274,22 @@ ConversionResult ConvertUTF16toUTF8(
unsigned short bytesToWrite = 0;
const DWORD byteMask = 0xBF;
const DWORD byteMark = 0x80;
const WCHAR* oldSource = source; /* In case we have to back up because of target overflow. */
const WCHAR *oldSource = source; /* In case we have to back up because of target overflow. */
ch = *source++;
/* If we have a surrogate pair, convert to UTF32 first. */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_HIGH_END)
{
/* If the 16 bits following the high surrogate are in the source buffer... */
if (source < sourceEnd)
{
DWORD ch2 = *source;
/* If it's a low surrogate, convert to UTF32. */
if (ch2 >= UNI_SUR_LOW_START && ch2 <= UNI_SUR_LOW_END)
{
ch = ((ch - UNI_SUR_HIGH_START) << halfShift)
+ (ch2 - UNI_SUR_LOW_START) + halfBase;
+ (ch2 - UNI_SUR_LOW_START) + halfBase;
++source;
}
else if (flags == strictConversion)
@ -309,8 +356,7 @@ ConversionResult ConvertUTF16toUTF8(
{
switch (bytesToWrite)
{
/* note: everything falls through. */
/* note: everything falls through. */
case 4:
*--target = (BYTE)((ch | byteMark) & byteMask);
ch >>= 6;
@ -328,20 +374,16 @@ ConversionResult ConvertUTF16toUTF8(
{
switch (bytesToWrite)
{
/* note: everything falls through. */
/* note: everything falls through. */
case 4:
--target;
ch >>= 6;
case 3:
--target;
ch >>= 6;
case 2:
--target;
ch >>= 6;
case 1:
--target;
}
@ -352,7 +394,6 @@ ConversionResult ConvertUTF16toUTF8(
*sourceStart = source;
*targetStart = target;
return result;
}
@ -378,23 +419,50 @@ static BOOL isLegalUTF8(const BYTE *source, int length)
{
default:
return FALSE;
/* Everything else falls through when "TRUE"... */
case 4:
/* Everything else falls through when "TRUE"... */
case 4: if ((a = (*--srcptr)) < 0x80 || a > 0xBF) return FALSE;
case 3: if ((a = (*--srcptr)) < 0x80 || a > 0xBF) return FALSE;
case 2: if ((a = (*--srcptr)) > 0xBF) return FALSE;
if ((a = (*--srcptr)) < 0x80 || a > 0xBF) return FALSE;
case 3:
if ((a = (*--srcptr)) < 0x80 || a > 0xBF) return FALSE;
case 2:
if ((a = (*--srcptr)) > 0xBF) return FALSE;
switch (*source)
{
/* no fall-through in this inner switch */
case 0xE0: if (a < 0xA0) return FALSE; break;
case 0xED: if (a > 0x9F) return FALSE; break;
case 0xF0: if (a < 0x90) return FALSE; break;
case 0xF4: if (a > 0x8F) return FALSE; break;
default: if (a < 0x80) return FALSE;
/* no fall-through in this inner switch */
case 0xE0:
if (a < 0xA0) return FALSE;
break;
case 0xED:
if (a > 0x9F) return FALSE;
break;
case 0xF0:
if (a < 0x90) return FALSE;
break;
case 0xF4:
if (a > 0x8F) return FALSE;
break;
default:
if (a < 0x80) return FALSE;
}
case 1: if (*source >= 0x80 && *source < 0xC2) return FALSE;
case 1:
if (*source >= 0x80 && *source < 0xC2) return FALSE;
}
if (*source > 0xF4)
@ -422,16 +490,14 @@ BOOL isLegalUTF8Sequence(const BYTE *source, const BYTE *sourceEnd)
/* --------------------------------------------------------------------- */
ConversionResult ConvertUTF8toUTF16(
const BYTE** sourceStart, const BYTE* sourceEnd,
WCHAR** targetStart, WCHAR* targetEnd, ConversionFlags flags)
const BYTE **sourceStart, const BYTE *sourceEnd,
WCHAR **targetStart, WCHAR *targetEnd, ConversionFlags flags)
{
WCHAR* target;
const BYTE* source;
WCHAR *target;
const BYTE *source;
BOOL computeLength;
ConversionResult result;
computeLength = (!targetEnd) ? TRUE : FALSE;
result = conversionOK;
source = *sourceStart;
target = *targetStart;
@ -459,12 +525,23 @@ ConversionResult ConvertUTF8toUTF16(
*/
switch (extraBytesToRead)
{
case 5: ch += *source++; ch <<= 6; /* remember, illegal UTF-8 */
case 4: ch += *source++; ch <<= 6; /* remember, illegal UTF-8 */
case 3: ch += *source++; ch <<= 6;
case 2: ch += *source++; ch <<= 6;
case 1: ch += *source++; ch <<= 6;
case 0: ch += *source++;
case 5:
ch += *source++;
ch <<= 6; /* remember, illegal UTF-8 */
case 4:
ch += *source++;
ch <<= 6; /* remember, illegal UTF-8 */
case 3:
ch += *source++;
ch <<= 6;
case 2:
ch += *source++;
ch <<= 6;
case 1:
ch += *source++;
ch <<= 6;
case 0:
ch += *source++;
}
ch -= offsetsFromUTF8[extraBytesToRead];
@ -480,7 +557,6 @@ ConversionResult ConvertUTF8toUTF16(
{
/* Target is a character <= 0xFFFF */
/* UTF-16 surrogate values are illegal in UTF-32 */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END)
{
if (flags == strictConversion)
@ -524,7 +600,6 @@ ConversionResult ConvertUTF8toUTF16(
else
{
/* target is a character in range 0xFFFF - 0x10FFFF. */
if ((target + 1 >= targetEnd) && (!computeLength))
{
source -= (extraBytesToRead + 1); /* Back up source pointer! */
@ -549,123 +624,193 @@ ConversionResult ConvertUTF8toUTF16(
*sourceStart = source;
*targetStart = target;
return result;
}
/* --------------------------------------------------------------------- */
ConversionResult ConvertUTF32toUTF8 (
const DWORD** sourceStart, const DWORD* sourceEnd,
BYTE** targetStart, BYTE* targetEnd, ConversionFlags flags) {
ConversionResult result = conversionOK;
const DWORD* source = *sourceStart;
BYTE* target = *targetStart;
while (source < sourceEnd) {
DWORD ch;
unsigned short bytesToWrite = 0;
const DWORD byteMask = 0xBF;
const DWORD byteMark = 0x80;
ch = *source++;
if (flags == strictConversion ) {
/* UTF-16 surrogate values are illegal in UTF-32 */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END) {
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
}
/*
* Figure out how many bytes the result will require. Turn any
* illegally large UTF32 things (> Plane 17) into replacement chars.
*/
if (ch < (DWORD)0x80) { bytesToWrite = 1;
} else if (ch < (DWORD)0x800) { bytesToWrite = 2;
} else if (ch < (DWORD)0x10000) { bytesToWrite = 3;
} else if (ch <= UNI_MAX_LEGAL_UTF32) { bytesToWrite = 4;
} else { bytesToWrite = 3;
ch = UNI_REPLACEMENT_CHAR;
result = sourceIllegal;
}
ConversionResult ConvertUTF32toUTF8(
const DWORD **sourceStart, const DWORD *sourceEnd,
BYTE **targetStart, BYTE *targetEnd, ConversionFlags flags)
{
ConversionResult result = conversionOK;
const DWORD *source = *sourceStart;
BYTE *target = *targetStart;
target += bytesToWrite;
if (target > targetEnd) {
--source; /* Back up source pointer! */
target -= bytesToWrite; result = targetExhausted; break;
}
switch (bytesToWrite) { /* note: everything falls through. */
case 4: *--target = (BYTE)((ch | byteMark) & byteMask); ch >>= 6;
case 3: *--target = (BYTE)((ch | byteMark) & byteMask); ch >>= 6;
case 2: *--target = (BYTE)((ch | byteMark) & byteMask); ch >>= 6;
case 1: *--target = (BYTE) (ch | firstByteMark[bytesToWrite]);
}
target += bytesToWrite;
}
*sourceStart = source;
*targetStart = target;
return result;
while (source < sourceEnd)
{
DWORD ch;
unsigned short bytesToWrite = 0;
const DWORD byteMask = 0xBF;
const DWORD byteMark = 0x80;
ch = *source++;
if (flags == strictConversion)
{
/* UTF-16 surrogate values are illegal in UTF-32 */
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END)
{
--source; /* return to the illegal value itself */
result = sourceIllegal;
break;
}
}
/*
* Figure out how many bytes the result will require. Turn any
* illegally large UTF32 things (> Plane 17) into replacement chars.
*/
if (ch < (DWORD)0x80)
{
bytesToWrite = 1;
}
else if (ch < (DWORD)0x800)
{
bytesToWrite = 2;
}
else if (ch < (DWORD)0x10000)
{
bytesToWrite = 3;
}
else if (ch <= UNI_MAX_LEGAL_UTF32)
{
bytesToWrite = 4;
}
else
{
bytesToWrite = 3;
ch = UNI_REPLACEMENT_CHAR;
result = sourceIllegal;
}
target += bytesToWrite;
if (target > targetEnd)
{
--source; /* Back up source pointer! */
target -= bytesToWrite;
result = targetExhausted;
break;
}
switch (bytesToWrite) /* note: everything falls through. */
{
case 4:
*--target = (BYTE)((ch | byteMark) & byteMask);
ch >>= 6;
case 3:
*--target = (BYTE)((ch | byteMark) & byteMask);
ch >>= 6;
case 2:
*--target = (BYTE)((ch | byteMark) & byteMask);
ch >>= 6;
case 1:
*--target = (BYTE)(ch | firstByteMark[bytesToWrite]);
}
target += bytesToWrite;
}
*sourceStart = source;
*targetStart = target;
return result;
}
/* --------------------------------------------------------------------- */
ConversionResult ConvertUTF8toUTF32 (
const BYTE** sourceStart, const BYTE* sourceEnd,
DWORD** targetStart, DWORD* targetEnd, ConversionFlags flags) {
ConversionResult result = conversionOK;
const BYTE* source = *sourceStart;
DWORD* target = *targetStart;
while (source < sourceEnd) {
DWORD ch = 0;
unsigned short extraBytesToRead = trailingBytesForUTF8[*source];
if (source + extraBytesToRead >= sourceEnd) {
result = sourceExhausted; break;
}
/* Do this check whether lenient or strict */
if (! isLegalUTF8(source, extraBytesToRead+1)) {
result = sourceIllegal;
break;
}
/*
* The cases all fall through. See "Note A" below.
*/
switch (extraBytesToRead) {
case 5: ch += *source++; ch <<= 6;
case 4: ch += *source++; ch <<= 6;
case 3: ch += *source++; ch <<= 6;
case 2: ch += *source++; ch <<= 6;
case 1: ch += *source++; ch <<= 6;
case 0: ch += *source++;
}
ch -= offsetsFromUTF8[extraBytesToRead];
ConversionResult ConvertUTF8toUTF32(
const BYTE **sourceStart, const BYTE *sourceEnd,
DWORD **targetStart, DWORD *targetEnd, ConversionFlags flags)
{
ConversionResult result = conversionOK;
const BYTE *source = *sourceStart;
DWORD *target = *targetStart;
if (target >= targetEnd) {
source -= (extraBytesToRead+1); /* Back up the source pointer! */
result = targetExhausted; break;
}
if (ch <= UNI_MAX_LEGAL_UTF32) {
/*
* UTF-16 surrogate values are illegal in UTF-32, and anything
* over Plane 17 (> 0x10FFFF) is illegal.
*/
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END) {
if (flags == strictConversion) {
source -= (extraBytesToRead+1); /* return to the illegal value itself */
result = sourceIllegal;
break;
} else {
*target++ = UNI_REPLACEMENT_CHAR;
}
} else {
*target++ = ch;
}
} else { /* i.e., ch > UNI_MAX_LEGAL_UTF32 */
result = sourceIllegal;
*target++ = UNI_REPLACEMENT_CHAR;
}
}
*sourceStart = source;
*targetStart = target;
return result;
while (source < sourceEnd)
{
DWORD ch = 0;
unsigned short extraBytesToRead = trailingBytesForUTF8[*source];
if (source + extraBytesToRead >= sourceEnd)
{
result = sourceExhausted;
break;
}
/* Do this check whether lenient or strict */
if (! isLegalUTF8(source, extraBytesToRead+1))
{
result = sourceIllegal;
break;
}
/*
* The cases all fall through. See "Note A" below.
*/
switch (extraBytesToRead)
{
case 5:
ch += *source++;
ch <<= 6;
case 4:
ch += *source++;
ch <<= 6;
case 3:
ch += *source++;
ch <<= 6;
case 2:
ch += *source++;
ch <<= 6;
case 1:
ch += *source++;
ch <<= 6;
case 0:
ch += *source++;
}
ch -= offsetsFromUTF8[extraBytesToRead];
if (target >= targetEnd)
{
source -= (extraBytesToRead+1); /* Back up the source pointer! */
result = targetExhausted;
break;
}
if (ch <= UNI_MAX_LEGAL_UTF32)
{
/*
* UTF-16 surrogate values are illegal in UTF-32, and anything
* over Plane 17 (> 0x10FFFF) is illegal.
*/
if (ch >= UNI_SUR_HIGH_START && ch <= UNI_SUR_LOW_END)
{
if (flags == strictConversion)
{
source -= (extraBytesToRead+1); /* return to the illegal value itself */
result = sourceIllegal;
break;
}
else
{
*target++ = UNI_REPLACEMENT_CHAR;
}
}
else
{
*target++ = ch;
}
}
else /* i.e., ch > UNI_MAX_LEGAL_UTF32 */
{
result = sourceIllegal;
*target++ = UNI_REPLACEMENT_CHAR;
}
}
*sourceStart = source;
*targetStart = target;
return result;
}
/* ---------------------------------------------------------------------

View File

@ -2,23 +2,21 @@
#include <winpr/crt.h>
#include <winpr/print.h>
#include <winpr/crypto.h>
#include <winpr/wlog.h>
static const char* SECRET_PASSWORD_TEST = "MySecretPassword123!";
static const char *SECRET_PASSWORD_TEST = "MySecretPassword123!";
int TestCryptoProtectMemory(int argc, char* argv[])
int TestCryptoProtectMemory(int argc, char *argv[])
{
int cbPlainText;
int cbCipherText;
char* pPlainText;
BYTE* pCipherText;
pPlainText = (char*) SECRET_PASSWORD_TEST;
char *pPlainText;
BYTE *pCipherText;
pPlainText = (char *) SECRET_PASSWORD_TEST;
cbPlainText = strlen(pPlainText) + 1;
cbCipherText = cbPlainText + (CRYPTPROTECTMEMORY_BLOCK_SIZE - (cbPlainText % CRYPTPROTECTMEMORY_BLOCK_SIZE));
printf("cbPlainText: %d cbCipherText: %d\n", cbPlainText, cbCipherText);
pCipherText = (BYTE*) malloc(cbCipherText);
pCipherText = (BYTE *) malloc(cbCipherText);
CopyMemory(pCipherText, pPlainText, cbPlainText);
ZeroMemory(&pCipherText[cbPlainText], (cbCipherText - cbPlainText));
@ -29,8 +27,7 @@ int TestCryptoProtectMemory(int argc, char* argv[])
}
printf("PlainText: %s (cbPlainText = %d, cbCipherText = %d)\n", pPlainText, cbPlainText, cbCipherText);
winpr_HexDump(pCipherText, cbCipherText);
winpr_HexDump("crypto.test", WLOG_DEBUG, pCipherText, cbCipherText);
if (!CryptUnprotectMemory(pCipherText, cbCipherText, CRYPTPROTECTMEMORY_SAME_PROCESS))
{
@ -39,9 +36,7 @@ int TestCryptoProtectMemory(int argc, char* argv[])
}
printf("Decrypted CipherText: %s\n", pCipherText);
SecureZeroMemory(pCipherText, cbCipherText);
free(pCipherText);
return 0;
}

View File

@ -40,6 +40,9 @@
#include <fcntl.h>
#endif
#include "../log.h"
#define TAG "file"
/**
* api-ms-win-core-file-l1-2-0.dll:
*
@ -262,7 +265,7 @@ static BOOL g_AioSignalHandlerInstalled = FALSE;
void AioSignalHandler(int signum, siginfo_t* siginfo, void* arg)
{
printf("AioSignalHandler\n");
WLog_INFO("%d", signum);
}
int InstallAioSignalHandler()
@ -534,7 +537,7 @@ BOOL ReadFile(HANDLE hFile, LPVOID lpBuffer, DWORD nNumberOfBytesToRead,
aio_status = aio_read(&cb);
printf("aio_read status: %d\n", aio_status);
WLog_DBG(TAG, "aio_read status: %d", aio_status);
if (aio_status < 0)
status = FALSE;
@ -674,7 +677,7 @@ BOOL WriteFile(HANDLE hFile, LPCVOID lpBuffer, DWORD nNumberOfBytesToWrite,
io_status = aio_write(&cb);
printf("aio_write status: %d\n", io_status);
WLog_DBG("aio_write status: %d", io_status);
if (io_status < 0)
status = FALSE;

View File

@ -34,15 +34,17 @@
#include <fcntl.h>
#endif
#include "../log.h"
#define TAG "file"
/**
* File System Behavior in the Microsoft Windows Environment:
* http://download.microsoft.com/download/4/3/8/43889780-8d45-4b2e-9d3a-c696a890309f/File%20System%20Behavior%20Overview.pdf
*/
LPSTR FilePatternFindNextWildcardA(LPCSTR lpPattern, DWORD* pFlags)
LPSTR FilePatternFindNextWildcardA(LPCSTR lpPattern, DWORD *pFlags)
{
LPSTR lpWildcard;
*pFlags = 0;
lpWildcard = strpbrk(lpPattern, "*?~");
@ -82,7 +84,7 @@ LPSTR FilePatternFindNextWildcardA(LPCSTR lpPattern, DWORD* pFlags)
}
BOOL FilePatternMatchSubExpressionA(LPCSTR lpFileName, size_t cchFileName,
LPCSTR lpX, size_t cchX, LPCSTR lpY, size_t cchY, LPCSTR lpWildcard, LPSTR* ppMatchEnd)
LPCSTR lpX, size_t cchX, LPCSTR lpY, size_t cchY, LPCSTR lpWildcard, LPSTR *ppMatchEnd)
{
LPSTR lpMatch;
@ -101,7 +103,6 @@ BOOL FilePatternMatchSubExpressionA(LPCSTR lpFileName, size_t cchFileName,
/*
* State 0: match 'X'
*/
if (_strnicmp(lpFileName, lpX, cchX) != 0)
return FALSE;
@ -134,9 +135,7 @@ BOOL FilePatternMatchSubExpressionA(LPCSTR lpFileName, size_t cchFileName,
/**
* State 3: final state
*/
*ppMatchEnd = (LPSTR) &lpMatch[cchY];
return TRUE;
}
else if (*lpWildcard == '?')
@ -149,7 +148,6 @@ BOOL FilePatternMatchSubExpressionA(LPCSTR lpFileName, size_t cchFileName,
/*
* State 0: match 'X'
*/
if (cchFileName < cchX)
return FALSE;
@ -174,7 +172,7 @@ BOOL FilePatternMatchSubExpressionA(LPCSTR lpFileName, size_t cchFileName,
if (_strnicmp(lpMatch, lpY, cchY) != 0)
return FALSE;
}
}
else
{
if ((cchX + 1) > cchFileName)
@ -186,15 +184,12 @@ BOOL FilePatternMatchSubExpressionA(LPCSTR lpFileName, size_t cchFileName,
/**
* State 3: final state
*/
*ppMatchEnd = (LPSTR) &lpMatch[cchY];
return TRUE;
}
else if (*lpWildcard == '~')
{
fprintf(stderr, "warning: unimplemented '~' pattern match\n");
WLog_ERR(TAG, "warning: unimplemented '~' pattern match\n");
return TRUE;
}
@ -264,7 +259,6 @@ BOOL FilePatternMatchA(LPCSTR lpFileName, LPCSTR lpPattern)
if (!FilePatternFindNextWildcardA(lpTail, &dwFlags))
{
/* tail contains no wildcards */
if (cchFileName < cchTail)
return FALSE;
@ -308,7 +302,6 @@ BOOL FilePatternMatchA(LPCSTR lpFileName, LPCSTR lpPattern)
* ^EOF of .^
*
*/
lpWildcard = FilePatternFindNextWildcardA(lpPattern, &dwFlags);
if (lpWildcard)
@ -324,13 +317,10 @@ BOOL FilePatternMatchA(LPCSTR lpFileName, LPCSTR lpPattern)
size_t cchSubFileName;
size_t cchWildcard;
size_t cchNextWildcard;
cchSubPattern = cchPattern;
lpSubPattern = (LPSTR) lpPattern;
cchSubFileName = cchFileName;
lpSubFileName = (LPSTR) lpFileName;
cchWildcard = ((dwFlags & WILDCARD_DOS) ? 2 : 1);
lpNextWildcard = FilePatternFindNextWildcardA(&lpWildcard[cchWildcard], &dwNextFlags);
@ -338,13 +328,10 @@ BOOL FilePatternMatchA(LPCSTR lpFileName, LPCSTR lpPattern)
{
lpX = (LPSTR) lpSubPattern;
cchX = (lpWildcard - lpSubPattern);
lpY = (LPSTR) &lpSubPattern[cchX + cchWildcard];
cchY = (cchSubPattern - (lpY - lpSubPattern));
match = FilePatternMatchSubExpressionA(lpSubFileName, cchSubFileName,
lpX, cchX, lpY, cchY, lpWildcard, &lpMatchEnd);
lpX, cchX, lpY, cchY, lpWildcard, &lpMatchEnd);
return match;
}
else
@ -353,25 +340,20 @@ BOOL FilePatternMatchA(LPCSTR lpFileName, LPCSTR lpPattern)
{
cchSubFileName = cchFileName - (lpSubFileName - lpFileName);
cchNextWildcard = ((dwNextFlags & WILDCARD_DOS) ? 2 : 1);
lpX = (LPSTR) lpSubPattern;
cchX = (lpWildcard - lpSubPattern);
lpY = (LPSTR) &lpSubPattern[cchX + cchWildcard];
cchY = (lpNextWildcard - lpWildcard) - cchWildcard;
match = FilePatternMatchSubExpressionA(lpSubFileName, cchSubFileName,
lpX, cchX, lpY, cchY, lpWildcard, &lpMatchEnd);
lpX, cchX, lpY, cchY, lpWildcard, &lpMatchEnd);
if (!match)
return FALSE;
lpSubFileName = lpMatchEnd;
cchWildcard = cchNextWildcard;
lpWildcard = lpNextWildcard;
dwFlags = dwNextFlags;
lpNextWildcard = FilePatternFindNextWildcardA(&lpWildcard[cchWildcard], &dwNextFlags);
}
@ -381,7 +363,6 @@ BOOL FilePatternMatchA(LPCSTR lpFileName, LPCSTR lpPattern)
else
{
/* no wildcard characters */
if (_stricmp(lpFileName, lpPattern) == 0)
return TRUE;
}

View File

@ -51,13 +51,9 @@ static pthread_once_t _HandleCloseCbsInitialized = PTHREAD_ONCE_INIT;
static void _HandleCloseCbsInit()
{
/* NB: error management to be done outside of this function */
assert(_HandleCloseCbs == NULL);
_HandleCloseCbs = (HANDLE_CLOSE_CB**)calloc(HANDLE_CLOSE_CB_MAX+1, sizeof(HANDLE_CLOSE_CB*));
_HandleCloseCbs = (HANDLE_CLOSE_CB **)calloc(HANDLE_CLOSE_CB_MAX+1, sizeof(HANDLE_CLOSE_CB *));
InitializeCriticalSection(&_HandleCloseCbsLock);
assert(_HandleCloseCbs != NULL);
}
@ -85,7 +81,6 @@ BOOL RegisterHandleCloseCb(HANDLE_CLOSE_CB *pHandleCloseCb)
if (_HandleCloseCbs[i] == NULL)
{
_HandleCloseCbs[i] = pHandleCloseCb;
LeaveCriticalSection(&_HandleCloseCbsLock);
return TRUE;
}
@ -116,16 +111,15 @@ BOOL CloseHandle(HANDLE hObject)
return FALSE;
}
EnterCriticalSection(&_HandleCloseCbsLock);
for (i=0; _HandleCloseCbs[i] != NULL; i++)
{
HANDLE_CLOSE_CB *close_cb = (HANDLE_CLOSE_CB*)_HandleCloseCbs[i];
HANDLE_CLOSE_CB *close_cb = (HANDLE_CLOSE_CB *)_HandleCloseCbs[i];
if (close_cb && close_cb->IsHandled(hObject))
{
BOOL result = close_cb->CloseHandle(hObject);
LeaveCriticalSection(&_HandleCloseCbsLock);
return result;
}
@ -133,45 +127,38 @@ BOOL CloseHandle(HANDLE hObject)
LeaveCriticalSection(&_HandleCloseCbsLock);
if (Type == HANDLE_TYPE_THREAD)
{
WINPR_THREAD* thread;
WINPR_THREAD *thread;
thread = (WINPR_THREAD *) Object;
thread = (WINPR_THREAD*) Object;
if (thread->started) {
if (thread->started)
{
pthread_detach(thread->thread);
}
free(thread);
free(thread);
return TRUE;
}
else if (Type == HANDLE_TYPE_PROCESS)
{
WINPR_PROCESS* process;
process = (WINPR_PROCESS*) Object;
WINPR_PROCESS *process;
process = (WINPR_PROCESS *) Object;
free(process);
return TRUE;
}
else if (Type == HANDLE_TYPE_MUTEX)
{
WINPR_MUTEX* mutex;
mutex = (WINPR_MUTEX*) Object;
WINPR_MUTEX *mutex;
mutex = (WINPR_MUTEX *) Object;
pthread_mutex_destroy(&mutex->mutex);
free(Object);
return TRUE;
}
else if (Type == HANDLE_TYPE_EVENT)
{
WINPR_EVENT* event;
event = (WINPR_EVENT*) Object;
WINPR_EVENT *event;
event = (WINPR_EVENT *) Object;
if (!event->bAttached)
{
@ -180,6 +167,7 @@ BOOL CloseHandle(HANDLE hObject)
close(event->pipe_fd[0]);
event->pipe_fd[0] = -1;
}
if (event->pipe_fd[1] != -1)
{
close(event->pipe_fd[1]);
@ -188,15 +176,12 @@ BOOL CloseHandle(HANDLE hObject)
}
free(Object);
return TRUE;
}
else if (Type == HANDLE_TYPE_SEMAPHORE)
{
WINPR_SEMAPHORE* semaphore;
semaphore = (WINPR_SEMAPHORE*) Object;
WINPR_SEMAPHORE *semaphore;
semaphore = (WINPR_SEMAPHORE *) Object;
#ifdef WINPR_PIPE_SEMAPHORE
if (semaphore->pipe_fd[0] != -1)
@ -212,38 +197,32 @@ BOOL CloseHandle(HANDLE hObject)
}
#else
#if defined __APPLE__
semaphore_destroy(mach_task_self(), *((winpr_sem_t*) semaphore->sem));
semaphore_destroy(mach_task_self(), *((winpr_sem_t *) semaphore->sem));
#else
sem_destroy((winpr_sem_t*) semaphore->sem);
sem_destroy((winpr_sem_t *) semaphore->sem);
#endif
#endif
free(Object);
return TRUE;
}
else if (Type == HANDLE_TYPE_TIMER)
{
WINPR_TIMER* timer;
timer = (WINPR_TIMER*) Object;
WINPR_TIMER *timer;
timer = (WINPR_TIMER *) Object;
#ifdef __linux__
if (timer->fd != -1)
close(timer->fd);
#endif
free(Object);
return TRUE;
}
else if (Type == HANDLE_TYPE_ANONYMOUS_PIPE)
{
WINPR_PIPE* pipe;
pipe = (WINPR_PIPE*) Object;
WINPR_PIPE *pipe;
pipe = (WINPR_PIPE *) Object;
if (pipe->fd != -1)
{
@ -251,37 +230,37 @@ BOOL CloseHandle(HANDLE hObject)
}
free(Object);
return TRUE;
}
else if (Type == HANDLE_TYPE_NAMED_PIPE)
{
WINPR_NAMED_PIPE* pNamedPipe = (WINPR_NAMED_PIPE*) Object;
WINPR_NAMED_PIPE *pNamedPipe = (WINPR_NAMED_PIPE *) Object;
if (pNamedPipe->clientfd != -1) {
//fprintf(stderr, "%s: closing clientfd %d\n", __FUNCTION__, pNamedPipe->clientfd);
if (pNamedPipe->clientfd != -1)
{
//WLOG_DBG(TAG, "%s: closing clientfd %d\n", __FUNCTION__, pNamedPipe->clientfd);
close(pNamedPipe->clientfd);
}
if (pNamedPipe->serverfd != -1) {
//fprintf(stderr, "%s: closing serverfd %d\n", __FUNCTION__, pNamedPipe->serverfd);
if (pNamedPipe->serverfd != -1)
{
//WLOG_DBG(TAG, "%s: closing serverfd %d\n", __FUNCTION__, pNamedPipe->serverfd);
close(pNamedPipe->serverfd);
}
if (pNamedPipe->pfnUnrefNamedPipe)
pNamedPipe->pfnUnrefNamedPipe(pNamedPipe);
free((void*)pNamedPipe->lpFileName);
free((void*)pNamedPipe->lpFilePath);
free((void*)pNamedPipe->name);
free((void *)pNamedPipe->lpFileName);
free((void *)pNamedPipe->lpFilePath);
free((void *)pNamedPipe->name);
free(pNamedPipe);
return TRUE;
}
else if (Type == HANDLE_TYPE_ACCESS_TOKEN)
{
WINPR_ACCESS_TOKEN* token;
token = (WINPR_ACCESS_TOKEN*) Object;
WINPR_ACCESS_TOKEN *token;
token = (WINPR_ACCESS_TOKEN *) Object;
if (token->Username)
free(token->Username);
@ -290,7 +269,6 @@ BOOL CloseHandle(HANDLE hObject)
free(token->Domain);
free(token);
return TRUE;
}
@ -298,7 +276,7 @@ BOOL CloseHandle(HANDLE hObject)
}
BOOL DuplicateHandle(HANDLE hSourceProcessHandle, HANDLE hSourceHandle, HANDLE hTargetProcessHandle,
LPHANDLE lpTargetHandle, DWORD dwDesiredAccess, BOOL bInheritHandle, DWORD dwOptions)
LPHANDLE lpTargetHandle, DWORD dwDesiredAccess, BOOL bInheritHandle, DWORD dwOptions)
{
return TRUE;
}

View File

@ -26,6 +26,9 @@
#include <winpr/library.h>
#include "../log.h"
#define TAG "com.winpr.library"
/**
* api-ms-win-core-libraryloader-l1-1-1.dll:
*
@ -92,12 +95,11 @@ BOOL SetDefaultDllDirectories(DWORD DirectoryFlags)
HMODULE LoadLibraryA(LPCSTR lpLibFileName)
{
HMODULE library;
library = dlopen(lpLibFileName, RTLD_LOCAL | RTLD_LAZY);
if (!library)
{
fprintf(stderr, "LoadLibraryA: %s\n", dlerror());
WLog_ERR(TAG, "LoadLibraryA: %s\n", dlerror());
return NULL;
}
@ -112,12 +114,11 @@ HMODULE LoadLibraryW(LPCWSTR lpLibFileName)
HMODULE LoadLibraryExA(LPCSTR lpLibFileName, HANDLE hFile, DWORD dwFlags)
{
HMODULE library;
library = dlopen(lpLibFileName, RTLD_LOCAL | RTLD_LAZY);
if (!library)
{
fprintf(stderr, "LoadLibraryExA: failed to open %s: %s\n", lpLibFileName, dlerror());
WLog_ERR(TAG, "LoadLibraryExA: failed to open %s: %s\n", lpLibFileName, dlerror());
return NULL;
}
@ -132,12 +133,11 @@ HMODULE LoadLibraryExW(LPCWSTR lpLibFileName, HANDLE hFile, DWORD dwFlags)
FARPROC GetProcAddress(HMODULE hModule, LPCSTR lpProcName)
{
FARPROC proc;
proc = dlsym(hModule, lpProcName);
if (proc == NULL)
{
fprintf(stderr, "GetProcAddress: could not find procedure %s: %s\n", lpProcName, dlerror());
WLog_ERR(TAG, "GetProcAddress: could not find procedure %s: %s\n", lpProcName, dlerror());
return (FARPROC) NULL;
}
@ -147,7 +147,6 @@ FARPROC GetProcAddress(HMODULE hModule, LPCSTR lpProcName)
BOOL FreeLibrary(HMODULE hLibModule)
{
int status;
status = dlclose(hLibModule);
if (status != 0)
@ -180,7 +179,7 @@ DWORD GetModuleFileNameW(HMODULE hModule, LPWSTR lpFilename, DWORD nSize)
}
DWORD GetModuleFileNameA(HMODULE hModule, LPSTR lpFilename, DWORD nSize)
{
{
#if defined(__linux__)
int status;
int length;
@ -189,16 +188,13 @@ DWORD GetModuleFileNameA(HMODULE hModule, LPSTR lpFilename, DWORD nSize)
if (!hModule)
{
char buffer[4096];
sprintf(path, "/proc/%d/exe", getpid());
status = readlink(path, buffer, sizeof(buffer));
if (status < 0)
return 0;
buffer[status] = '\0';
length = strlen(buffer);
if (length < nSize)
@ -214,33 +210,31 @@ DWORD GetModuleFileNameA(HMODULE hModule, LPSTR lpFilename, DWORD nSize)
return 0;
}
#elif defined(__MACOSX__)
int status;
int length;
if (!hModule)
{
char path[4096];
char buffer[4096];
uint32_t size = sizeof(path);
status = _NSGetExecutablePath(path, &size);
if (status != 0)
{
/* path too small */
return 0;
}
/*
* _NSGetExecutablePath may not return the canonical path,
* so use realpath to find the absolute, canonical path.
*/
realpath(path, buffer);
length = strlen(buffer);
if (length < nSize)
{
CopyMemory(lpFilename, buffer, length);
@ -251,11 +245,11 @@ DWORD GetModuleFileNameA(HMODULE hModule, LPSTR lpFilename, DWORD nSize)
CopyMemory(lpFilename, buffer, nSize - 1);
lpFilename[nSize - 1] = '\0';
}
return 0;
}
#endif
#endif
return 0;
}

60
winpr/libwinpr/log.h Normal file
View File

@ -0,0 +1,60 @@
/**
* FreeRDP: A Remote Desktop Protocol Implementation
* Winpr log defines
*
* Copyright 2014 Armin Novak <armin.novak@gmail.com>
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifndef WINPR_LOG_PRIV_H
#define WINPR_LOG_PRIV_H
#include <winpr/wlog.h>
#define WLOG_PRINT(level, file, fkt, line, dbg_str, fmt, ...) \
do { \
const char *hdr = "com.winpr."; \
char tag[1024] = { 0 }; \
wLogMessage msg; \
wLog *log; \
\
strncat(tag, hdr, sizeof(tag)); \
strncat(tag, dbg_str, sizeof(tag) - sizeof(hdr)); \
log = WLog_Get(tag); \
\
msg.Type = WLOG_MESSAGE_TEXT; \
msg.Level = level; \
msg.FormatString = fmt; \
msg.LineNumber = line; \
msg.FileName = file; \
msg.FunctionName = fkt; \
WLog_PrintMessage(log, &msg, ##__VA_ARGS__); \
} while (0 )
#define WLog_LVL(tag, lvl, fmt, ...) WLOG_PRINT(lvl, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#define WLog_VRB(tag, fmt, ...) WLOG_PRINT(WLOG_TRACE, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#define WLog_DBG(tag, fmt, ...) WLOG_PRINT(WLOG_DEBUG, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#define WLog_INFO(tag, fmt, ...) WLOG_PRINT(WLOG_INFO, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#define WLog_WARN(tag, fmt, ...) WLOG_PRINT(WLOG_WARN, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#define WLog_ERR(tag, fmt, ...) WLOG_PRINT(WLOG_ERROR, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#define WLog_FATAL(tag, fmt, ...) WLOG_PRINT(WLOG_FATAL, __FILE__, __FUNCTION__, \
__LINE__, tag, fmt, ## __VA_ARGS__)
#endif /* FREERDP_UTILS_DEBUG_H */

View File

@ -45,6 +45,9 @@
#include "pipe.h"
#include "../log.h"
#define TAG "pipe"
/*
* Since the WinPR implementation of named pipes makes use of UNIX domain
* sockets, it is not possible to bind the same name more than once (i.e.,
@ -58,11 +61,11 @@
* descriptor gets closed and the entry is removed from the list.
*/
static wArrayList* g_NamedPipeServerSockets = NULL;
static wArrayList *g_NamedPipeServerSockets = NULL;
typedef struct _NamedPipeServerSocketEntry
{
char* name;
char *name;
int serverfd;
int references;
} NamedPipeServerSocketEntry;
@ -83,20 +86,19 @@ static void InitWinPRPipeModule()
BOOL CreatePipe(PHANDLE hReadPipe, PHANDLE hWritePipe, LPSECURITY_ATTRIBUTES lpPipeAttributes, DWORD nSize)
{
int pipe_fd[2];
WINPR_PIPE* pReadPipe;
WINPR_PIPE* pWritePipe;
WINPR_PIPE *pReadPipe;
WINPR_PIPE *pWritePipe;
pipe_fd[0] = -1;
pipe_fd[1] = -1;
if (pipe(pipe_fd) < 0)
{
printf("CreatePipe: failed to create pipe\n");
WLog_ERR(TAG, "failed to create pipe");
return FALSE;
}
pReadPipe = (WINPR_PIPE*) malloc(sizeof(WINPR_PIPE));
pWritePipe = (WINPR_PIPE*) malloc(sizeof(WINPR_PIPE));
pReadPipe = (WINPR_PIPE *) malloc(sizeof(WINPR_PIPE));
pWritePipe = (WINPR_PIPE *) malloc(sizeof(WINPR_PIPE));
if (!pReadPipe || !pWritePipe)
{
@ -111,13 +113,10 @@ BOOL CreatePipe(PHANDLE hReadPipe, PHANDLE hWritePipe, LPSECURITY_ATTRIBUTES lpP
pReadPipe->fd = pipe_fd[0];
pWritePipe->fd = pipe_fd[1];
WINPR_HANDLE_SET_TYPE(pReadPipe, HANDLE_TYPE_ANONYMOUS_PIPE);
*((ULONG_PTR*) hReadPipe) = (ULONG_PTR) pReadPipe;
*((ULONG_PTR *) hReadPipe) = (ULONG_PTR) pReadPipe;
WINPR_HANDLE_SET_TYPE(pWritePipe, HANDLE_TYPE_ANONYMOUS_PIPE);
*((ULONG_PTR*) hWritePipe) = (ULONG_PTR) pWritePipe;
*((ULONG_PTR *) hWritePipe) = (ULONG_PTR) pWritePipe;
return TRUE;
}
@ -125,7 +124,7 @@ BOOL CreatePipe(PHANDLE hReadPipe, PHANDLE hWritePipe, LPSECURITY_ATTRIBUTES lpP
* Named pipe
*/
static void winpr_unref_named_pipe(WINPR_NAMED_PIPE* pNamedPipe)
static void winpr_unref_named_pipe(WINPR_NAMED_PIPE *pNamedPipe)
{
int index;
NamedPipeServerSocketEntry *baseSocket;
@ -135,42 +134,45 @@ static void winpr_unref_named_pipe(WINPR_NAMED_PIPE* pNamedPipe)
assert(pNamedPipe->name);
assert(g_NamedPipeServerSockets);
//fprintf(stderr, "%s: %p (%s)\n", __FUNCTION__, pNamedPipe, pNamedPipe->name);
//WLog_VRB(TAG, "%s: %p (%s)\n", __FUNCTION__, pNamedPipe, pNamedPipe->name);
ArrayList_Lock(g_NamedPipeServerSockets);
for (index = 0; index < ArrayList_Count(g_NamedPipeServerSockets); index++)
{
baseSocket = (NamedPipeServerSocketEntry*) ArrayList_GetItem(
g_NamedPipeServerSockets, index);
baseSocket = (NamedPipeServerSocketEntry *) ArrayList_GetItem(
g_NamedPipeServerSockets, index);
assert(baseSocket->name);
if (!strcmp(baseSocket->name, pNamedPipe->name))
{
assert(baseSocket->references > 0);
assert(baseSocket->serverfd != -1);
if (--baseSocket->references == 0)
{
//fprintf(stderr, "%s: removing shared server socked resource\n", __FUNCTION__);
//fprintf(stderr, "%s: closing shared serverfd %d\n", __FUNCTION__, baseSocket->serverfd);
//WLog_DBG(TAG, "%s: removing shared server socked resource\n", __FUNCTION__);
//WLog_DBG(TAG, "%s: closing shared serverfd %d\n", __FUNCTION__, baseSocket->serverfd);
ArrayList_Remove(g_NamedPipeServerSockets, baseSocket);
close(baseSocket->serverfd);
free(baseSocket->name);
free(baseSocket);
}
break;
}
}
ArrayList_Unlock(g_NamedPipeServerSockets);
}
HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD nMaxInstances,
DWORD nOutBufferSize, DWORD nInBufferSize, DWORD nDefaultTimeOut, LPSECURITY_ATTRIBUTES lpSecurityAttributes)
DWORD nOutBufferSize, DWORD nInBufferSize, DWORD nDefaultTimeOut, LPSECURITY_ATTRIBUTES lpSecurityAttributes)
{
int index;
HANDLE hNamedPipe = INVALID_HANDLE_VALUE;
char* lpPipePath;
char *lpPipePath;
struct sockaddr_un s;
WINPR_NAMED_PIPE* pNamedPipe = NULL;
WINPR_NAMED_PIPE *pNamedPipe = NULL;
int serverfd = -1;
NamedPipeServerSocketEntry *baseSocket = NULL;
@ -178,17 +180,18 @@ HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD
return INVALID_HANDLE_VALUE;
InitWinPRPipeModule();
pNamedPipe = (WINPR_NAMED_PIPE*) calloc(1, sizeof(WINPR_NAMED_PIPE));
pNamedPipe = (WINPR_NAMED_PIPE *) calloc(1, sizeof(WINPR_NAMED_PIPE));
WINPR_HANDLE_SET_TYPE(pNamedPipe, HANDLE_TYPE_NAMED_PIPE);
if (!(pNamedPipe->name = _strdup(lpName)))
goto out;
if (!(pNamedPipe->lpFileName = GetNamedPipeNameWithoutPrefixA(lpName)))
goto out;
if (!(pNamedPipe->lpFilePath = GetNamedPipeUnixDomainSocketFilePathA(lpName)))
goto out;
pNamedPipe->dwOpenMode = dwOpenMode;
pNamedPipe->dwPipeMode = dwPipeMode;
pNamedPipe->nMaxInstances = nMaxInstances;
@ -196,20 +199,19 @@ HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD
pNamedPipe->nInBufferSize = nInBufferSize;
pNamedPipe->nDefaultTimeOut = nDefaultTimeOut;
pNamedPipe->dwFlagsAndAttributes = dwOpenMode;
pNamedPipe->clientfd = -1;
pNamedPipe->ServerMode = TRUE;
ArrayList_Lock(g_NamedPipeServerSockets);
for (index = 0; index < ArrayList_Count(g_NamedPipeServerSockets); index++)
{
baseSocket = (NamedPipeServerSocketEntry*) ArrayList_GetItem(
g_NamedPipeServerSockets, index);
baseSocket = (NamedPipeServerSocketEntry *) ArrayList_GetItem(
g_NamedPipeServerSockets, index);
if (!strcmp(baseSocket->name, lpName))
{
serverfd = baseSocket->serverfd;
//fprintf(stderr, "using shared socked resource for pipe %p (%s)\n", pNamedPipe, lpName);
//WLog_DBG(TAG, "using shared socked resource for pipe %p (%s)\n", pNamedPipe, lpName);
break;
}
}
@ -236,7 +238,7 @@ HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD
if ((serverfd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1)
{
fprintf(stderr, "CreateNamedPipeA: socket error, %s\n", strerror(errno));
WLog_ERR(TAG, "CreateNamedPipeA: socket error, %s\n", strerror(errno));
goto out;
}
@ -244,15 +246,15 @@ HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD
s.sun_family = AF_UNIX;
strcpy(s.sun_path, pNamedPipe->lpFilePath);
if (bind(serverfd, (struct sockaddr*) &s, sizeof(struct sockaddr_un)) == -1)
if (bind(serverfd, (struct sockaddr *) &s, sizeof(struct sockaddr_un)) == -1)
{
fprintf(stderr, "CreateNamedPipeA: bind error, %s\n", strerror(errno));
WLog_ERR(TAG, "CreateNamedPipeA: bind error, %s\n", strerror(errno));
goto out;
}
if (listen(serverfd, 2) == -1)
{
fprintf(stderr, "CreateNamedPipeA: listen error, %s\n", strerror(errno));
WLog_ERR(TAG, "CreateNamedPipeA: listen error, %s\n", strerror(errno));
goto out;
}
@ -260,20 +262,21 @@ HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD
if (!(baseSocket = (NamedPipeServerSocketEntry *) malloc(sizeof(NamedPipeServerSocketEntry))))
goto out;
if (!(baseSocket->name = _strdup(lpName)))
{
free(baseSocket);
goto out;
}
baseSocket->serverfd = serverfd;
baseSocket->references = 0;
ArrayList_Add(g_NamedPipeServerSockets, baseSocket);
//fprintf(stderr, "created shared socked resource for pipe %p (%s). base serverfd = %d\n", pNamedPipe, lpName, serverfd);
//WLog_DBG(TAG, "created shared socked resource for pipe %p (%s). base serverfd = %d\n", pNamedPipe, lpName, serverfd);
}
pNamedPipe->serverfd = dup(baseSocket->serverfd);
//fprintf(stderr, "using serverfd %d (duplicated from %d)\n", pNamedPipe->serverfd, baseSocket->serverfd);
//WLog_DBG(TAG, "using serverfd %d (duplicated from %d)\n", pNamedPipe->serverfd, baseSocket->serverfd);
pNamedPipe->pfnUnrefNamedPipe = winpr_unref_named_pipe;
baseSocket->references++;
@ -284,30 +287,33 @@ HANDLE CreateNamedPipeA(LPCSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD
if (flags != -1)
fcntl(pNamedPipe->serverfd, F_SETFL, flags | O_NONBLOCK);
#endif
}
hNamedPipe = (HANDLE) pNamedPipe;
out:
if (hNamedPipe == INVALID_HANDLE_VALUE)
{
if (pNamedPipe)
{
free((void*)pNamedPipe->name);
free((void*)pNamedPipe->lpFileName);
free((void*)pNamedPipe->lpFilePath);
free((void *)pNamedPipe->name);
free((void *)pNamedPipe->lpFileName);
free((void *)pNamedPipe->lpFilePath);
free(pNamedPipe);
}
if (serverfd != -1)
close(serverfd);
}
ArrayList_Unlock(g_NamedPipeServerSockets);
return hNamedPipe;
}
HANDLE CreateNamedPipeW(LPCWSTR lpName, DWORD dwOpenMode, DWORD dwPipeMode, DWORD nMaxInstances,
DWORD nOutBufferSize, DWORD nInBufferSize, DWORD nDefaultTimeOut, LPSECURITY_ATTRIBUTES lpSecurityAttributes)
DWORD nOutBufferSize, DWORD nInBufferSize, DWORD nDefaultTimeOut, LPSECURITY_ATTRIBUTES lpSecurityAttributes)
{
return NULL;
}
@ -317,23 +323,22 @@ BOOL ConnectNamedPipe(HANDLE hNamedPipe, LPOVERLAPPED lpOverlapped)
int status;
socklen_t length;
struct sockaddr_un s;
WINPR_NAMED_PIPE* pNamedPipe;
WINPR_NAMED_PIPE *pNamedPipe;
if (!hNamedPipe)
return FALSE;
pNamedPipe = (WINPR_NAMED_PIPE*) hNamedPipe;
pNamedPipe = (WINPR_NAMED_PIPE *) hNamedPipe;
if (!(pNamedPipe->dwFlagsAndAttributes & FILE_FLAG_OVERLAPPED))
{
length = sizeof(struct sockaddr_un);
ZeroMemory(&s, sizeof(struct sockaddr_un));
status = accept(pNamedPipe->serverfd, (struct sockaddr*) &s, &length);
status = accept(pNamedPipe->serverfd, (struct sockaddr *) &s, &length);
if (status < 0)
{
fprintf(stderr, "ConnectNamedPipe: accept error\n");
WLog_ERR(TAG, "ConnectNamedPipe: accept error\n");
return FALSE;
}
@ -349,13 +354,10 @@ BOOL ConnectNamedPipe(HANDLE hNamedPipe, LPOVERLAPPED lpOverlapped)
return FALSE;
pNamedPipe->lpOverlapped = lpOverlapped;
/* synchronous behavior */
lpOverlapped->Internal = 2;
lpOverlapped->InternalHigh = (ULONG_PTR) 0;
lpOverlapped->Pointer = (PVOID) NULL;
SetEvent(lpOverlapped->hEvent);
}
@ -364,9 +366,8 @@ BOOL ConnectNamedPipe(HANDLE hNamedPipe, LPOVERLAPPED lpOverlapped)
BOOL DisconnectNamedPipe(HANDLE hNamedPipe)
{
WINPR_NAMED_PIPE* pNamedPipe;
pNamedPipe = (WINPR_NAMED_PIPE*) hNamedPipe;
WINPR_NAMED_PIPE *pNamedPipe;
pNamedPipe = (WINPR_NAMED_PIPE *) hNamedPipe;
if (pNamedPipe->clientfd != -1)
{
@ -378,13 +379,13 @@ BOOL DisconnectNamedPipe(HANDLE hNamedPipe)
}
BOOL PeekNamedPipe(HANDLE hNamedPipe, LPVOID lpBuffer, DWORD nBufferSize,
LPDWORD lpBytesRead, LPDWORD lpTotalBytesAvail, LPDWORD lpBytesLeftThisMessage)
LPDWORD lpBytesRead, LPDWORD lpTotalBytesAvail, LPDWORD lpBytesLeftThisMessage)
{
return TRUE;
}
BOOL TransactNamedPipe(HANDLE hNamedPipe, LPVOID lpInBuffer, DWORD nInBufferSize, LPVOID lpOutBuffer,
DWORD nOutBufferSize, LPDWORD lpBytesRead, LPOVERLAPPED lpOverlapped)
DWORD nOutBufferSize, LPDWORD lpBytesRead, LPOVERLAPPED lpOverlapped)
{
return TRUE;
}
@ -393,7 +394,7 @@ BOOL WaitNamedPipeA(LPCSTR lpNamedPipeName, DWORD nTimeOut)
{
BOOL status;
DWORD nWaitTime;
char* lpFilePath;
char *lpFilePath;
DWORD dwSleepInterval;
if (!lpNamedPipeName)
@ -419,6 +420,7 @@ BOOL WaitNamedPipeA(LPCSTR lpNamedPipeName, DWORD nTimeOut)
break;
}
}
free(lpFilePath);
return status;
}
@ -432,14 +434,12 @@ BOOL SetNamedPipeHandleState(HANDLE hNamedPipe, LPDWORD lpMode, LPDWORD lpMaxCol
{
int fd;
int flags;
WINPR_NAMED_PIPE* pNamedPipe;
pNamedPipe = (WINPR_NAMED_PIPE*) hNamedPipe;
WINPR_NAMED_PIPE *pNamedPipe;
pNamedPipe = (WINPR_NAMED_PIPE *) hNamedPipe;
if (lpMode)
{
pNamedPipe->dwPipeMode = *lpMode;
fd = (pNamedPipe->ServerMode) ? pNamedPipe->serverfd : pNamedPipe->clientfd;
if (fd == -1)
@ -457,12 +457,10 @@ BOOL SetNamedPipeHandleState(HANDLE hNamedPipe, LPDWORD lpMode, LPDWORD lpMaxCol
if (lpMaxCollectionCount)
{
}
if (lpCollectDataTimeout)
{
}
return TRUE;

View File

@ -7,6 +7,7 @@
#include <winpr/winpr.h>
#include <winpr/print.h>
#include <winpr/synch.h>
#include <winpr/wlog.h>
#include <winpr/thread.h>
#ifndef _WIN32
#include <signal.h>
@ -22,19 +23,17 @@ static LPTSTR lpszPipeNameSt = _T("\\\\.\\pipe\\winpr_test_pipe_st");
BOOL testFailed = FALSE;
static void* named_pipe_client_thread(void* arg)
static void *named_pipe_client_thread(void *arg)
{
HANDLE hNamedPipe = NULL;
BYTE* lpReadBuffer = NULL;
BYTE* lpWriteBuffer = NULL;
BYTE *lpReadBuffer = NULL;
BYTE *lpWriteBuffer = NULL;
BOOL fSuccess = FALSE;
DWORD nNumberOfBytesToRead;
DWORD nNumberOfBytesToWrite;
DWORD lpNumberOfBytesRead;
DWORD lpNumberOfBytesWritten;
WaitForSingleObject(ReadyEvent, INFINITE);
hNamedPipe = CreateFile(lpszPipeNameMt, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL);
if (!hNamedPipe)
@ -49,13 +48,13 @@ static void* named_pipe_client_thread(void* arg)
goto out;
}
if (!(lpReadBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE)))
if (!(lpReadBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE)))
{
printf("%s: Error allocating read buffer\n", __FUNCTION__);
goto out;
}
if (!(lpWriteBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE)))
if (!(lpWriteBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE)))
{
printf("%s: Error allocating write buffer\n", __FUNCTION__);
goto out;
@ -63,11 +62,10 @@ static void* named_pipe_client_thread(void* arg)
lpNumberOfBytesWritten = 0;
nNumberOfBytesToWrite = PIPE_BUFFER_SIZE;
FillMemory(lpWriteBuffer, PIPE_BUFFER_SIZE, 0x59);
if (!WriteFile(hNamedPipe, lpWriteBuffer, nNumberOfBytesToWrite, &lpNumberOfBytesWritten, NULL) ||
lpNumberOfBytesWritten != nNumberOfBytesToWrite)
lpNumberOfBytesWritten != nNumberOfBytesToWrite)
{
printf("%s: Client NamedPipe WriteFile failure\n", __FUNCTION__);
goto out;
@ -75,44 +73,43 @@ static void* named_pipe_client_thread(void* arg)
lpNumberOfBytesRead = 0;
nNumberOfBytesToRead = PIPE_BUFFER_SIZE;
ZeroMemory(lpReadBuffer, PIPE_BUFFER_SIZE);
if (!ReadFile(hNamedPipe, lpReadBuffer, nNumberOfBytesToRead, &lpNumberOfBytesRead, NULL) ||
lpNumberOfBytesRead != nNumberOfBytesToRead)
lpNumberOfBytesRead != nNumberOfBytesToRead)
{
printf("%s: Client NamedPipe ReadFile failure\n", __FUNCTION__);
goto out;
}
printf("Client ReadFile (%d):\n", lpNumberOfBytesRead);
winpr_HexDump(lpReadBuffer, lpNumberOfBytesRead);
winpr_HexDump("pipe.test", WLOG_DEBUG, lpReadBuffer, lpNumberOfBytesRead);
fSuccess = TRUE;
out:
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
if (!fSuccess)
testFailed = TRUE;
testFailed = TRUE;
return NULL;
}
static void* named_pipe_server_thread(void* arg)
static void *named_pipe_server_thread(void *arg)
{
HANDLE hNamedPipe = NULL;
BYTE* lpReadBuffer = NULL;
BYTE* lpWriteBuffer = NULL;
BYTE *lpReadBuffer = NULL;
BYTE *lpWriteBuffer = NULL;
BOOL fSuccess = FALSE;
BOOL fConnected = FALSE;
DWORD nNumberOfBytesToRead;
DWORD nNumberOfBytesToWrite;
DWORD lpNumberOfBytesRead;
DWORD lpNumberOfBytesWritten;
hNamedPipe = CreateNamedPipe(lpszPipeNameMt,
PIPE_ACCESS_DUPLEX, PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES, PIPE_BUFFER_SIZE, PIPE_BUFFER_SIZE, 0, NULL);
PIPE_ACCESS_DUPLEX, PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES, PIPE_BUFFER_SIZE, PIPE_BUFFER_SIZE, 0, NULL);
if (!hNamedPipe)
{
@ -127,7 +124,6 @@ static void* named_pipe_server_thread(void* arg)
}
SetEvent(ReadyEvent);
fConnected = ConnectNamedPipe(hNamedPipe, NULL);
if (!fConnected)
@ -139,13 +135,13 @@ static void* named_pipe_server_thread(void* arg)
goto out;
}
if (!(lpReadBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE)))
if (!(lpReadBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE)))
{
printf("%s: Error allocating read buffer\n", __FUNCTION__);
goto out;
}
if (!(lpWriteBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE)))
if (!(lpWriteBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE)))
{
printf("%s: Error allocating write buffer\n", __FUNCTION__);
goto out;
@ -153,43 +149,42 @@ static void* named_pipe_server_thread(void* arg)
lpNumberOfBytesRead = 0;
nNumberOfBytesToRead = PIPE_BUFFER_SIZE;
ZeroMemory(lpReadBuffer, PIPE_BUFFER_SIZE);
if (!ReadFile(hNamedPipe, lpReadBuffer, nNumberOfBytesToRead, &lpNumberOfBytesRead, NULL) ||
lpNumberOfBytesRead != nNumberOfBytesToRead)
lpNumberOfBytesRead != nNumberOfBytesToRead)
{
printf("%s: Server NamedPipe ReadFile failure\n", __FUNCTION__);
goto out;
}
printf("Server ReadFile (%d):\n", lpNumberOfBytesRead);
winpr_HexDump(lpReadBuffer, lpNumberOfBytesRead);
winpr_HexDump("pipe.test", WLOG_DEBUG, lpReadBuffer, lpNumberOfBytesRead);
lpNumberOfBytesWritten = 0;
nNumberOfBytesToWrite = PIPE_BUFFER_SIZE;
FillMemory(lpWriteBuffer, PIPE_BUFFER_SIZE, 0x45);
if (!WriteFile(hNamedPipe, lpWriteBuffer, nNumberOfBytesToWrite, &lpNumberOfBytesWritten, NULL) ||
lpNumberOfBytesWritten != nNumberOfBytesToWrite)
lpNumberOfBytesWritten != nNumberOfBytesToWrite)
{
printf("%s: Server NamedPipe WriteFile failure\n", __FUNCTION__);
goto out;
}
fSuccess = TRUE;
fSuccess = TRUE;
out:
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
if (!fSuccess)
testFailed = TRUE;
testFailed = TRUE;
return NULL;
}
#define TESTNUMPIPESST 16
static void* named_pipe_single_thread(void* arg)
static void *named_pipe_single_thread(void *arg)
{
HANDLE servers[TESTNUMPIPESST];
HANDLE clients[TESTNUMPIPESST];
@ -201,21 +196,18 @@ static void* named_pipe_single_thread(void* arg)
int numPipes;
BOOL bSuccess = FALSE;
#ifndef _WIN32
WINPR_NAMED_PIPE* p;
WINPR_NAMED_PIPE *p;
#endif
numPipes = TESTNUMPIPESST;
memset(servers, 0, sizeof(servers));
memset(clients, 0, sizeof(clients));
WaitForSingleObject(ReadyEvent, INFINITE);
for (i = 0; i < numPipes; i++)
{
if (!(servers[i] = CreateNamedPipe(lpszPipeNameSt,
PIPE_ACCESS_DUPLEX, PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES, PIPE_BUFFER_SIZE, PIPE_BUFFER_SIZE, 0, NULL)))
PIPE_ACCESS_DUPLEX, PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES, PIPE_BUFFER_SIZE, PIPE_BUFFER_SIZE, 0, NULL)))
{
printf("%s: CreateNamedPipe #%d failed\n", __FUNCTION__, i);
goto out;
@ -223,44 +215,46 @@ static void* named_pipe_single_thread(void* arg)
}
#ifndef _WIN32
for (i = 0; i < numPipes; i++)
{
p = (WINPR_NAMED_PIPE*)servers[i];
p = (WINPR_NAMED_PIPE *)servers[i];
if (strcmp(lpszPipeNameSt, p->name))
{
printf("%s: Pipe name mismatch for pipe #%d ([%s] instead of [%s])\n",
__FUNCTION__, i, p->name, lpszPipeNameSt);
__FUNCTION__, i, p->name, lpszPipeNameSt);
goto out;
}
if (p->clientfd != -1)
{
printf("%s: Unexpected client fd value for pipe #%d (%d instead of -1)\n",
__FUNCTION__, i, p->clientfd);
__FUNCTION__, i, p->clientfd);
goto out;
}
if (p->serverfd < 1)
{
printf("%s: Unexpected server fd value for pipe #%d (%d is not > 0)\n",
__FUNCTION__, i, p->serverfd);
__FUNCTION__, i, p->serverfd);
goto out;
}
if (p->ServerMode == FALSE)
{
printf("%s: Unexpected ServerMode value for pipe #%d (0 instead of 1)\n",
__FUNCTION__, i);
__FUNCTION__, i);
goto out;
}
}
#endif
for (i = 0; i < numPipes; i++)
{
if (!(clients[i] = CreateFile(lpszPipeNameSt, GENERIC_READ | GENERIC_WRITE,
0, NULL, OPEN_EXISTING, 0, NULL)))
0, NULL, OPEN_EXISTING, 0, NULL)))
{
printf("%s: CreateFile #%d failed\n", __FUNCTION__, i);
goto out;
@ -274,6 +268,7 @@ static void* named_pipe_single_thread(void* arg)
}
#ifndef _WIN32
for (i = 0; i < numPipes; i++)
{
p = servers[i];
@ -281,14 +276,14 @@ static void* named_pipe_single_thread(void* arg)
if (p->clientfd < 1)
{
printf("%s: Unexpected client fd value for pipe #%d (%d is not > 0)\n",
__FUNCTION__, i, p->clientfd);
__FUNCTION__, i, p->clientfd);
goto out;
}
if (p->ServerMode)
{
printf("%s: Unexpected ServerMode value for pipe #%d (1 instead of 0)\n",
__FUNCTION__, i);
__FUNCTION__, i);
goto out;
}
}
@ -296,22 +291,20 @@ static void* named_pipe_single_thread(void* arg)
for (i = 0; i < numPipes; i++)
{
/* Test writing from clients to servers */
ZeroMemory(sndbuf, sizeof(sndbuf));
ZeroMemory(rcvbuf, sizeof(rcvbuf));
sprintf_s(sndbuf, sizeof(sndbuf), "CLIENT->SERVER ON PIPE #%05d", i);
p = servers[i];
if (!WriteFile(clients[i], sndbuf, sizeof(sndbuf), &dwWritten, NULL) ||
dwWritten != sizeof(sndbuf))
dwWritten != sizeof(sndbuf))
{
printf("%s: Error writing to client end of pipe #%d\n", __FUNCTION__, i);
goto out;
}
if (!ReadFile(servers[i], rcvbuf, dwWritten, &dwRead, NULL) ||
dwRead != dwWritten)
dwRead != dwWritten)
{
printf("%s: Error reading on server end of pipe #%d\n", __FUNCTION__, i);
goto out;
@ -320,26 +313,25 @@ static void* named_pipe_single_thread(void* arg)
if (memcmp(sndbuf, rcvbuf, sizeof(sndbuf)))
{
printf("%s: Error data read on server end of pipe #%d is corrupted\n",
__FUNCTION__, i);
__FUNCTION__, i);
goto out;
}
/* Test writing from servers to clients */
ZeroMemory(sndbuf, sizeof(sndbuf));
ZeroMemory(rcvbuf, sizeof(rcvbuf));
sprintf_s(sndbuf, sizeof(sndbuf), "SERVER->CLIENT ON PIPE #%05d", i);
p = servers[i];
if (!WriteFile(servers[i], sndbuf, sizeof(sndbuf), &dwWritten, NULL) ||
dwWritten != sizeof(sndbuf))
dwWritten != sizeof(sndbuf))
{
printf("%s: Error writing to server end of pipe #%d\n", __FUNCTION__, i);
goto out;
}
if (!ReadFile(clients[i], rcvbuf, dwWritten, &dwRead, NULL) ||
dwRead != dwWritten)
dwRead != dwWritten)
{
printf("%s: Error reading on client end of pipe #%d\n", __FUNCTION__, i);
goto out;
@ -348,18 +340,17 @@ static void* named_pipe_single_thread(void* arg)
if (memcmp(sndbuf, rcvbuf, sizeof(sndbuf)))
{
printf("%s: Error data read on client end of pipe #%d is corrupted\n",
__FUNCTION__, i);
__FUNCTION__, i);
goto out;
}
}
#endif
#endif
/**
* After DisconnectNamedPipe on server end
* ReadFile/WriteFile must fail on client end
*/
i = numPipes - 1;
DisconnectNamedPipe(servers[i]);
if (ReadFile(clients[i], rcvbuf, sizeof(rcvbuf), &dwRead, NULL))
@ -376,16 +367,12 @@ static void* named_pipe_single_thread(void* arg)
CloseHandle(servers[i]);
CloseHandle(clients[i]);
numPipes--;
/**
* After CloseHandle (without calling DisconnectNamedPipe first) on server end
* ReadFile/WriteFile must fail on client end
*/
i = numPipes - 1;
CloseHandle(servers[i]);
if (ReadFile(clients[i], rcvbuf, sizeof(rcvbuf), &dwRead, NULL))
@ -401,16 +388,12 @@ static void* named_pipe_single_thread(void* arg)
}
CloseHandle(clients[i]);
numPipes--;
/**
* After CloseHandle on client end
* ReadFile/WriteFile must fail on server end
*/
i = numPipes - 1;
CloseHandle(clients[i]);
if (ReadFile(servers[i], rcvbuf, sizeof(rcvbuf), &dwRead, NULL))
@ -427,7 +410,6 @@ static void* named_pipe_single_thread(void* arg)
DisconnectNamedPipe(servers[i]);
CloseHandle(servers[i]);
numPipes--;
/* Close all remaining pipes */
@ -437,41 +419,36 @@ static void* named_pipe_single_thread(void* arg)
CloseHandle(servers[i]);
CloseHandle(clients[i]);
}
numPipes = 0;
bSuccess = TRUE;
out:
if (!bSuccess)
testFailed = TRUE;
return NULL;
}
int TestPipeCreateNamedPipe(int argc, char* argv[])
int TestPipeCreateNamedPipe(int argc, char *argv[])
{
HANDLE SingleThread;
HANDLE ClientThread;
HANDLE ServerThread;
#ifndef _WIN32
signal(SIGPIPE, SIG_IGN);
signal(SIGPIPE, SIG_IGN);
#endif
ReadyEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
SingleThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) named_pipe_single_thread, NULL, 0, NULL);
ClientThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) named_pipe_client_thread, NULL, 0, NULL);
ServerThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) named_pipe_server_thread, NULL, 0, NULL);
WaitForSingleObject(SingleThread, INFINITE);
WaitForSingleObject(ClientThread, INFINITE);
WaitForSingleObject(ServerThread, INFINITE);
CloseHandle(SingleThread);
CloseHandle(ClientThread);
CloseHandle(ServerThread);
return testFailed;
}

View File

@ -5,6 +5,7 @@
#include <winpr/file.h>
#include <winpr/tchar.h>
#include <winpr/winpr.h>
#include <winpr/wlog.h>
#include <winpr/print.h>
#include <winpr/synch.h>
#include <winpr/thread.h>
@ -15,21 +16,19 @@ static HANDLE ReadyEvent;
static LPTSTR lpszPipeName = _T("\\\\.\\pipe\\winpr_test_pipe_overlapped");
static void* named_pipe_client_thread(void* arg)
static void *named_pipe_client_thread(void *arg)
{
DWORD status;
HANDLE hEvent;
HANDLE hNamedPipe;
BYTE* lpReadBuffer;
BYTE* lpWriteBuffer;
BYTE *lpReadBuffer;
BYTE *lpWriteBuffer;
BOOL fSuccess = FALSE;
OVERLAPPED overlapped;
DWORD nNumberOfBytesToRead;
DWORD nNumberOfBytesToWrite;
DWORD NumberOfBytesTransferred;
WaitForSingleObject(ReadyEvent, INFINITE);
hNamedPipe = CreateFile(lpszPipeName, GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_FLAG_OVERLAPPED, NULL);
if (!hNamedPipe)
@ -44,17 +43,13 @@ static void* named_pipe_client_thread(void* arg)
return NULL;
}
lpReadBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE);
lpWriteBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE);
lpReadBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE);
lpWriteBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE);
ZeroMemory(&overlapped, sizeof(OVERLAPPED));
hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
overlapped.hEvent = hEvent;
nNumberOfBytesToWrite = PIPE_BUFFER_SIZE;
FillMemory(lpWriteBuffer, PIPE_BUFFER_SIZE, 0x59);
fSuccess = WriteFile(hNamedPipe, lpWriteBuffer, nNumberOfBytesToWrite, NULL, &overlapped);
if (!fSuccess)
@ -65,23 +60,17 @@ static void* named_pipe_client_thread(void* arg)
printf("Client NamedPipe WriteFile failure: %d\n", GetLastError());
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
status = WaitForMultipleObjects(1, &hEvent, FALSE, INFINITE);
NumberOfBytesTransferred = 0;
fSuccess = GetOverlappedResult(hNamedPipe, &overlapped, &NumberOfBytesTransferred, TRUE);
printf("Client GetOverlappedResult: fSuccess: %d NumberOfBytesTransferred: %d\n", fSuccess, NumberOfBytesTransferred);
nNumberOfBytesToRead = PIPE_BUFFER_SIZE;
ZeroMemory(lpReadBuffer, PIPE_BUFFER_SIZE);
fSuccess = ReadFile(hNamedPipe, lpReadBuffer, nNumberOfBytesToRead, NULL, &overlapped);
if (!fSuccess)
@ -92,48 +81,40 @@ static void* named_pipe_client_thread(void* arg)
printf("Client NamedPipe ReadFile failure: %d\n", GetLastError());
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
status = WaitForMultipleObjects(1, &hEvent, FALSE, INFINITE);
NumberOfBytesTransferred = 0;
fSuccess = GetOverlappedResult(hNamedPipe, &overlapped, &NumberOfBytesTransferred, TRUE);
printf("Client GetOverlappedResult: fSuccess: %d NumberOfBytesTransferred: %d\n", fSuccess, NumberOfBytesTransferred);
printf("Client ReadFile (%d):\n", NumberOfBytesTransferred);
winpr_HexDump(lpReadBuffer, NumberOfBytesTransferred);
winpr_HexDump("pipe.test", WLOG_DEBUG, lpReadBuffer, NumberOfBytesTransferred);
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
static void* named_pipe_server_thread(void* arg)
static void *named_pipe_server_thread(void *arg)
{
DWORD status;
HANDLE hEvent;
HANDLE hNamedPipe;
BYTE* lpReadBuffer;
BYTE* lpWriteBuffer;
BYTE *lpReadBuffer;
BYTE *lpWriteBuffer;
OVERLAPPED overlapped;
BOOL fSuccess = FALSE;
BOOL fConnected = FALSE;
DWORD nNumberOfBytesToRead;
DWORD nNumberOfBytesToWrite;
DWORD NumberOfBytesTransferred;
hNamedPipe = CreateNamedPipe(lpszPipeName,
PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED, PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES, PIPE_BUFFER_SIZE, PIPE_BUFFER_SIZE, 0, NULL);
PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED, PIPE_TYPE_BYTE | PIPE_READMODE_BYTE | PIPE_WAIT,
PIPE_UNLIMITED_INSTANCES, PIPE_BUFFER_SIZE, PIPE_BUFFER_SIZE, 0, NULL);
if (!hNamedPipe)
{
@ -148,42 +129,32 @@ static void* named_pipe_server_thread(void* arg)
}
SetEvent(ReadyEvent);
ZeroMemory(&overlapped, sizeof(OVERLAPPED));
hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
overlapped.hEvent = hEvent;
fConnected = ConnectNamedPipe(hNamedPipe, &overlapped);
printf("ConnectNamedPipe status: %d\n", GetLastError());
if (!fConnected)
fConnected = (GetLastError() == ERROR_IO_PENDING);
status = WaitForMultipleObjects(1, &hEvent, FALSE, INFINITE);
NumberOfBytesTransferred = 0;
fSuccess = GetOverlappedResult(hNamedPipe, &overlapped, &NumberOfBytesTransferred, TRUE);
printf("Server GetOverlappedResult: fSuccess: %d NumberOfBytesTransferred: %d\n", fSuccess, NumberOfBytesTransferred);
if (!fConnected)
{
printf("ConnectNamedPipe failure: %d\n", GetLastError());
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
lpReadBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE);
lpWriteBuffer = (BYTE*) malloc(PIPE_BUFFER_SIZE);
lpReadBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE);
lpWriteBuffer = (BYTE *) malloc(PIPE_BUFFER_SIZE);
nNumberOfBytesToRead = PIPE_BUFFER_SIZE;
ZeroMemory(lpReadBuffer, PIPE_BUFFER_SIZE);
fSuccess = ReadFile(hNamedPipe, lpReadBuffer, nNumberOfBytesToRead, NULL, &overlapped);
if (!fSuccess)
@ -194,27 +165,19 @@ static void* named_pipe_server_thread(void* arg)
printf("Server NamedPipe ReadFile failure: %d\n", GetLastError());
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
status = WaitForMultipleObjects(1, &hEvent, FALSE, INFINITE);
NumberOfBytesTransferred = 0;
fSuccess = GetOverlappedResult(hNamedPipe, &overlapped, &NumberOfBytesTransferred, TRUE);
printf("Server GetOverlappedResult: fSuccess: %d NumberOfBytesTransferred: %d\n", fSuccess, NumberOfBytesTransferred);
printf("Server ReadFile (%d):\n", NumberOfBytesTransferred);
winpr_HexDump(lpReadBuffer, NumberOfBytesTransferred);
winpr_HexDump("pipe.test", WLOG_DEBUG, lpReadBuffer, NumberOfBytesTransferred);
nNumberOfBytesToWrite = PIPE_BUFFER_SIZE;
FillMemory(lpWriteBuffer, PIPE_BUFFER_SIZE, 0x45);
fSuccess = WriteFile(hNamedPipe, lpWriteBuffer, nNumberOfBytesToWrite, NULL, &overlapped);
if (!fSuccess)
@ -223,45 +186,33 @@ static void* named_pipe_server_thread(void* arg)
if (!fSuccess)
{
printf("Server NamedPipe WriteFile failure: %d\n", GetLastError());
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
status = WaitForMultipleObjects(1, &hEvent, FALSE, INFINITE);
NumberOfBytesTransferred = 0;
fSuccess = GetOverlappedResult(hNamedPipe, &overlapped, &NumberOfBytesTransferred, TRUE);
printf("Server GetOverlappedResult: fSuccess: %d NumberOfBytesTransferred: %d\n", fSuccess, NumberOfBytesTransferred);
free(lpReadBuffer);
free(lpWriteBuffer);
CloseHandle(hNamedPipe);
CloseHandle(hEvent);
return NULL;
}
int TestPipeCreateNamedPipeOverlapped(int argc, char* argv[])
int TestPipeCreateNamedPipeOverlapped(int argc, char *argv[])
{
HANDLE ClientThread;
HANDLE ServerThread;
ReadyEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
ClientThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) named_pipe_client_thread, NULL, 0, NULL);
ServerThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) named_pipe_server_thread, NULL, 0, NULL);
WaitForSingleObject(ClientThread, INFINITE);
WaitForSingleObject(ServerThread, INFINITE);
return 0;
}

View File

@ -25,6 +25,8 @@
#include <winpr/pool.h>
#include "pool.h"
#include "../log.h"
#define TAG "pool"
#ifdef _WIN32
@ -152,7 +154,7 @@ VOID WaitForThreadpoolWorkCallbacks(PTP_WORK pwk, BOOL fCancelPendingCallbacks)
event = CountdownEvent_WaitHandle(pool->WorkComplete);
if (WaitForSingleObject(event, INFINITE) != WAIT_OBJECT_0)
printf("WaitForThreadpoolWorkCallbacks: error waiting on work completion\n");
WLog_ERR(TAG, "error waiting on work completion");
#endif
}

View File

@ -29,14 +29,17 @@
#include "registry_reg.h"
#include "../log.h"
#define TAG "registry"
#define WINPR_HKLM_HIVE "/etc/winpr/HKLM.reg"
static void reg_print_key(Reg* reg, RegKey* key);
static void reg_print_value(Reg* reg, RegVal* value);
static void reg_print_key(Reg *reg, RegKey *key);
static void reg_print_value(Reg *reg, RegVal *value);
struct reg_data_type
{
char* tag;
char *tag;
int length;
DWORD type;
};
@ -55,7 +58,7 @@ static struct reg_data_type REG_DATA_TYPE_TABLE[] =
{ NULL, 0, 0 }
};
static char* REG_DATA_TYPE_STRINGS[] =
static char *REG_DATA_TYPE_STRINGS[] =
{
"REG_NONE",
"REG_SZ",
@ -71,14 +74,12 @@ static char* REG_DATA_TYPE_STRINGS[] =
"REG_QWORD"
};
static void reg_load_start(Reg* reg)
static void reg_load_start(Reg *reg)
{
long int file_size;
fseek(reg->fp, 0, SEEK_END);
file_size = ftell(reg->fp);
fseek(reg->fp, 0, SEEK_SET);
reg->line = NULL;
reg->next_line = NULL;
reg->buffer = NULL;
@ -86,7 +87,7 @@ static void reg_load_start(Reg* reg)
if (file_size < 1)
return;
reg->buffer = (char*) malloc(file_size + 2);
reg->buffer = (char *) malloc(file_size + 2);
if (fread(reg->buffer, file_size, 1, reg->fp) != 1)
{
@ -97,11 +98,10 @@ static void reg_load_start(Reg* reg)
reg->buffer[file_size] = '\n';
reg->buffer[file_size + 1] = '\0';
reg->next_line = strtok(reg->buffer, "\n");
}
static void reg_load_finish(Reg* reg)
static void reg_load_finish(Reg *reg)
{
if (!reg)
return;
@ -113,16 +113,15 @@ static void reg_load_finish(Reg* reg)
}
}
static RegVal* reg_load_value(Reg* reg, RegKey* key)
static RegVal *reg_load_value(Reg *reg, RegKey *key)
{
int index;
char* p[5];
char *p[5];
int length;
char* name;
char* type;
char* data;
RegVal* value;
char *name;
char *type;
char *data;
RegVal *value;
p[0] = reg->line + 1;
p[1] = strstr(p[0], "\"=");
p[2] = p[1] + 2;
@ -134,14 +133,11 @@ static RegVal* reg_load_value(Reg* reg, RegKey* key)
p[3] = strchr(p[2], ':');
data = p[3] + 1;
length = p[1] - p[0];
name = (char*) malloc(length + 1);
name = (char *) malloc(length + 1);
memcpy(name, p[0], length);
name[length] = '\0';
value = (RegVal*) malloc(sizeof(RegVal));
value = (RegVal *) malloc(sizeof(RegVal));
value->name = name;
value->type = REG_NONE;
value->next = value->prev = NULL;
@ -167,7 +163,7 @@ static RegVal* reg_load_value(Reg* reg, RegKey* key)
}
else
{
fprintf(stderr, "unimplemented format: %s\n", REG_DATA_TYPE_STRINGS[value->type]);
WLog_ERR(TAG, "unimplemented format: %s\n", REG_DATA_TYPE_STRINGS[value->type]);
}
if (!key->values)
@ -176,7 +172,7 @@ static RegVal* reg_load_value(Reg* reg, RegKey* key)
}
else
{
RegVal* pValue = key->values;
RegVal *pValue = key->values;
while (pValue->next != NULL)
{
@ -190,7 +186,7 @@ static RegVal* reg_load_value(Reg* reg, RegKey* key)
return value;
}
static BOOL reg_load_has_next_line(Reg* reg)
static BOOL reg_load_has_next_line(Reg *reg)
{
if (!reg)
return 0;
@ -198,7 +194,7 @@ static BOOL reg_load_has_next_line(Reg* reg)
return (reg->next_line != NULL) ? 1 : 0;
}
static char* reg_load_get_next_line(Reg* reg)
static char *reg_load_get_next_line(Reg *reg)
{
if (!reg)
return NULL;
@ -206,24 +202,21 @@ static char* reg_load_get_next_line(Reg* reg)
reg->line = reg->next_line;
reg->next_line = strtok(NULL, "\n");
reg->line_length = strlen(reg->line);
return reg->line;
}
static char* reg_load_peek_next_line(Reg* reg)
static char *reg_load_peek_next_line(Reg *reg)
{
return reg->next_line;
}
static void reg_insert_key(Reg* reg, RegKey* key, RegKey* subkey)
static void reg_insert_key(Reg *reg, RegKey *key, RegKey *subkey)
{
char* name;
char* path;
char* save;
char *name;
char *path;
char *save;
int length;
path = _strdup(subkey->name);
name = strtok_s(path, "\\", &save);
while (name != NULL)
@ -241,23 +234,19 @@ static void reg_insert_key(Reg* reg, RegKey* key, RegKey* subkey)
free(path);
}
static RegKey* reg_load_key(Reg* reg, RegKey* key)
static RegKey *reg_load_key(Reg *reg, RegKey *key)
{
char* p[2];
char *p[2];
int length;
char* line;
RegKey* subkey;
char *line;
RegKey *subkey;
p[0] = reg->line + 1;
p[1] = strrchr(p[0], ']');
subkey = (RegKey*) malloc(sizeof(RegKey));
subkey = (RegKey *) malloc(sizeof(RegKey));
subkey->values = NULL;
subkey->prev = subkey->next = NULL;
length = p[1] - p[0];
subkey->name = (char*) malloc(length + 1);
subkey->name = (char *) malloc(length + 1);
memcpy(subkey->name, p[0], length);
subkey->name[length] = '\0';
@ -284,7 +273,7 @@ static RegKey* reg_load_key(Reg* reg, RegKey* key)
}
else
{
RegKey* pKey = key->subkeys;
RegKey *pKey = key->subkeys;
while (pKey->next != NULL)
{
@ -298,7 +287,7 @@ static RegKey* reg_load_key(Reg* reg, RegKey* key)
return subkey;
}
void reg_load(Reg* reg)
void reg_load(Reg *reg)
{
reg_load_start(reg);
@ -315,11 +304,10 @@ void reg_load(Reg* reg)
reg_load_finish(reg);
}
static void reg_unload_value(Reg* reg, RegVal* value)
static void reg_unload_value(Reg *reg, RegVal *value)
{
if (value->type == REG_DWORD)
{
}
else if (value->type == REG_SZ)
{
@ -327,17 +315,16 @@ static void reg_unload_value(Reg* reg, RegVal* value)
}
else
{
fprintf(stderr, "unimplemented format: %s\n", REG_DATA_TYPE_STRINGS[value->type]);
WLog_ERR(TAG, "unimplemented format: %s\n", REG_DATA_TYPE_STRINGS[value->type]);
}
free(value);
}
static void reg_unload_key(Reg* reg, RegKey* key)
static void reg_unload_key(Reg *reg, RegKey *key)
{
RegVal* pValue;
RegVal* pValueNext;
RegVal *pValue;
RegVal *pValueNext;
pValue = key->values;
while (pValue != NULL)
@ -351,11 +338,10 @@ static void reg_unload_key(Reg* reg, RegKey* key)
free(key);
}
void reg_unload(Reg* reg)
void reg_unload(Reg *reg)
{
RegKey* pKey;
RegKey* pKeyNext;
RegKey *pKey;
RegKey *pKeyNext;
pKey = reg->root_key->subkeys;
while (pKey != NULL)
@ -368,11 +354,10 @@ void reg_unload(Reg* reg)
free(reg->root_key);
}
Reg* reg_open(BOOL read_only)
Reg *reg_open(BOOL read_only)
{
Reg* reg;
reg = (Reg*) malloc(sizeof(Reg));
Reg *reg;
reg = (Reg *) malloc(sizeof(Reg));
if (reg)
{
@ -397,19 +382,17 @@ Reg* reg_open(BOOL read_only)
return NULL;
}
reg->root_key = (RegKey*) malloc(sizeof(RegKey));
reg->root_key = (RegKey *) malloc(sizeof(RegKey));
reg->root_key->values = NULL;
reg->root_key->subkeys = NULL;
reg->root_key->name = "HKEY_LOCAL_MACHINE";
reg_load(reg);
}
return reg;
}
void reg_close(Reg* reg)
void reg_close(Reg *reg)
{
if (reg)
{
@ -419,31 +402,29 @@ void reg_close(Reg* reg)
}
}
void reg_print_value(Reg* reg, RegVal* value)
void reg_print_value(Reg *reg, RegVal *value)
{
fprintf(stderr, "\"%s\"=", value->name);
WLog_INFO(TAG, "\"%s\"=", value->name);
if (value->type == REG_DWORD)
{
fprintf(stderr, "dword:%08X\n", (int) value->data.dword);
WLog_INFO(TAG, "dword:%08X\n", (int) value->data.dword);
}
else if (value->type == REG_SZ)
{
fprintf(stderr, "%s\"\n", value->data.string);
WLog_INFO(TAG, "%s\"\n", value->data.string);
}
else
{
fprintf(stderr, "unimplemented format: %s\n", REG_DATA_TYPE_STRINGS[value->type]);
WLog_ERR(TAG, "unimplemented format: %s\n", REG_DATA_TYPE_STRINGS[value->type]);
}
}
void reg_print_key(Reg* reg, RegKey* key)
void reg_print_key(Reg *reg, RegKey *key)
{
RegVal* pValue;
RegVal *pValue;
pValue = key->values;
fprintf(stderr, "[%s]\n", key->name);
WLog_INFO(TAG, "[%s]\n", key->name);
while (pValue != NULL)
{
@ -452,10 +433,9 @@ void reg_print_key(Reg* reg, RegKey* key)
}
}
void reg_print(Reg* reg)
void reg_print(Reg *reg)
{
RegKey* pKey;
RegKey *pKey;
pKey = reg->root_key->subkeys;
while (pKey != NULL)

View File

@ -39,6 +39,9 @@
#include "ndr_private.h"
#include "../log.h"
#define TAG "rpc"
/**
* MSRPC NDR Types Technical Overview:
* http://dvlabs.tippingpoint.com/blog/2007/11/24/msrpc-ndr-types/
@ -47,32 +50,43 @@
void NdrPrintParamAttributes(PARAM_ATTRIBUTES attributes)
{
if (attributes.ServerAllocSize)
fprintf(stderr, "ServerAllocSize, ");
WLog_INFO(TAG, "ServerAllocSize, ");
if (attributes.SaveForAsyncFinish)
fprintf(stderr, "SaveForAsyncFinish, ");
WLog_INFO(TAG, "SaveForAsyncFinish, ");
if (attributes.IsDontCallFreeInst)
fprintf(stderr, "IsDontCallFreeInst, ");
WLog_INFO(TAG, "IsDontCallFreeInst, ");
if (attributes.IsSimpleRef)
fprintf(stderr, "IsSimpleRef, ");
WLog_INFO(TAG, "IsSimpleRef, ");
if (attributes.IsByValue)
fprintf(stderr, "IsByValue, ");
WLog_INFO(TAG, "IsByValue, ");
if (attributes.IsBasetype)
fprintf(stderr, "IsBaseType, ");
WLog_INFO(TAG, "IsBaseType, ");
if (attributes.IsReturn)
fprintf(stderr, "IsReturn, ");
WLog_INFO(TAG, "IsReturn, ");
if (attributes.IsOut)
fprintf(stderr, "IsOut, ");
WLog_INFO(TAG, "IsOut, ");
if (attributes.IsIn)
fprintf(stderr, "IsIn, ");
WLog_INFO(TAG, "IsIn, ");
if (attributes.IsPipe)
fprintf(stderr, "IsPipe, ");
WLog_INFO(TAG, "IsPipe, ");
if (attributes.MustFree)
fprintf(stderr, "MustFree, ");
WLog_INFO(TAG, "MustFree, ");
if (attributes.MustSize)
fprintf(stderr, "MustSize, ");
WLog_INFO(TAG, "MustSize, ");
}
void NdrProcessParam(PMIDL_STUB_MESSAGE pStubMsg, NDR_PHASE phase, unsigned char* pMemory, NDR_PARAM* param)
void NdrProcessParam(PMIDL_STUB_MESSAGE pStubMsg, NDR_PHASE phase, unsigned char *pMemory, NDR_PARAM *param)
{
unsigned char type;
PFORMAT_STRING pFormat;
@ -84,14 +98,14 @@ void NdrProcessParam(PMIDL_STUB_MESSAGE pStubMsg, NDR_PHASE phase, unsigned char
pFormat = &param->Type.FormatChar;
if (param->Attributes.IsSimpleRef)
pMemory = *(unsigned char**) pMemory;
pMemory = *(unsigned char **) pMemory;
}
else
{
pFormat = &pStubMsg->StubDesc->pFormatTypes[param->Type.Offset];
if (!(param->Attributes.IsByValue))
pMemory = *(unsigned char**) pMemory;
pMemory = *(unsigned char **) pMemory;
}
type = (pFormat[0] & 0x7F);
@ -129,58 +143,47 @@ void NdrProcessParam(PMIDL_STUB_MESSAGE pStubMsg, NDR_PHASE phase, unsigned char
}
}
void NdrProcessParams(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat, NDR_PHASE phase, void** fpuArgs, unsigned short numberParams)
void NdrProcessParams(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat, NDR_PHASE phase, void **fpuArgs, unsigned short numberParams)
{
unsigned int i;
NDR_PARAM* params;
NDR_PARAM *params;
PFORMAT_STRING fmt;
unsigned char* arg;
unsigned char *arg;
unsigned char type;
params = (NDR_PARAM*) pFormat;
fprintf(stderr, "Params = \n{\n");
params = (NDR_PARAM *) pFormat;
WLog_INFO(TAG, "Params = ");
for (i = 0; i < numberParams; i++)
{
#ifdef __x86_64__
float tmp;
#endif
arg = pStubMsg->StackTop + params[i].StackOffset;
fmt = (PFORMAT_STRING) &pStubMsg->StubDesc->pFormatTypes[params[i].Type.Offset];
#ifdef __x86_64__
if ((params[i].Attributes.IsBasetype) &&
!(params[i].Attributes.IsSimpleRef) &&
((params[i].Type.FormatChar) == FC_FLOAT) && !fpuArgs)
{
tmp = *(double*) arg;
arg = (unsigned char*) &tmp;
tmp = *(double *) arg;
arg = (unsigned char *) &tmp;
}
#endif
fprintf(stderr, "\t#%d\t", i);
type = (params[i].Attributes.IsBasetype) ? params[i].Type.FormatChar : *fmt;
fprintf(stderr, " type %s (0x%02X) ", FC_TYPE_STRINGS[type], type);
WLog_INFO(TAG, "'\t#%d\ttype %s (0x%02X) ", i, FC_TYPE_STRINGS[type], type);
NdrPrintParamAttributes(params[i].Attributes);
if (params[i].Attributes.IsIn)
{
NdrProcessParam(pStubMsg, phase, arg, &params[i]);
}
fprintf(stderr, "\n");
}
fprintf(stderr, "}\n");
}
void NdrClientInitializeNew(PRPC_MESSAGE pRpcMessage, PMIDL_STUB_MESSAGE pStubMsg,
PMIDL_STUB_DESC pStubDesc, unsigned int ProcNum)
PMIDL_STUB_DESC pStubDesc, unsigned int ProcNum)
{
pRpcMessage->Handle = NULL;
pRpcMessage->RpcFlags = 0;
@ -188,7 +191,6 @@ void NdrClientInitializeNew(PRPC_MESSAGE pRpcMessage, PMIDL_STUB_MESSAGE pStubMs
pRpcMessage->DataRepresentation = 0;
pRpcMessage->ReservedForRuntime = NULL;
pRpcMessage->RpcInterfaceInformation = pStubDesc->RpcInterfaceInformation;
pStubMsg->RpcMsg = pRpcMessage;
pStubMsg->BufferStart = NULL;
pStubMsg->BufferEnd = NULL;
@ -202,36 +204,46 @@ void NdrClientInitializeNew(PRPC_MESSAGE pRpcMessage, PMIDL_STUB_MESSAGE pStubMs
void NdrPrintOptFlags(INTERPRETER_OPT_FLAGS optFlags)
{
if (optFlags.ClientMustSize)
fprintf(stderr, "ClientMustSize, ");
WLog_INFO(TAG, "ClientMustSize, ");
if (optFlags.ServerMustSize)
fprintf(stderr, "ServerMustSize, ");
WLog_INFO(TAG, "ServerMustSize, ");
if (optFlags.HasAsyncUuid)
fprintf(stderr, "HasAsyncUiid, ");
WLog_INFO(TAG, "HasAsyncUiid, ");
if (optFlags.HasAsyncHandle)
fprintf(stderr, "HasAsyncHandle, ");
WLog_INFO(TAG, "HasAsyncHandle, ");
if (optFlags.HasReturn)
fprintf(stderr, "HasReturn, ");
WLog_INFO(TAG, "HasReturn, ");
if (optFlags.HasPipes)
fprintf(stderr, "HasPipes, ");
WLog_INFO(TAG, "HasPipes, ");
if (optFlags.HasExtensions)
fprintf(stderr, "HasExtensions, ");
WLog_INFO(TAG, "HasExtensions, ");
}
void NdrPrintExtFlags(INTERPRETER_OPT_FLAGS2 extFlags)
{
if (extFlags.HasNewCorrDesc)
fprintf(stderr, "HasNewCorrDesc, ");
WLog_INFO(TAG, "HasNewCorrDesc, ");
if (extFlags.ClientCorrCheck)
fprintf(stderr, "ClientCorrCheck, ");
WLog_INFO(TAG, "ClientCorrCheck, ");
if (extFlags.ServerCorrCheck)
fprintf(stderr, "ServerCorrCheck, ");
WLog_INFO(TAG, "ServerCorrCheck, ");
if (extFlags.HasNotify)
fprintf(stderr, "HasNotify, ");
WLog_INFO(TAG, "HasNotify, ");
if (extFlags.HasNotify2)
fprintf(stderr, "HasNotify2, ");
WLog_INFO(TAG, "HasNotify2, ");
}
CLIENT_CALL_RETURN NdrClientCall(PMIDL_STUB_DESC pStubDescriptor, PFORMAT_STRING pFormat, void** stackTop, void** fpuStack)
CLIENT_CALL_RETURN NdrClientCall(PMIDL_STUB_DESC pStubDescriptor, PFORMAT_STRING pFormat, void **stackTop, void **fpuStack)
{
RPC_MESSAGE rpcMsg;
unsigned short procNum;
@ -241,100 +253,87 @@ CLIENT_CALL_RETURN NdrClientCall(PMIDL_STUB_DESC pStubDescriptor, PFORMAT_STRING
MIDL_STUB_MESSAGE stubMsg;
INTERPRETER_FLAGS flags;
INTERPRETER_OPT_FLAGS optFlags;
NDR_PROC_HEADER* procHeader;
NDR_OI2_PROC_HEADER* oi2ProcHeader;
NDR_PROC_HEADER *procHeader;
NDR_OI2_PROC_HEADER *oi2ProcHeader;
CLIENT_CALL_RETURN client_call_return;
procNum = stackSize = numberParams = 0;
procHeader = (NDR_PROC_HEADER*) &pFormat[0];
procHeader = (NDR_PROC_HEADER *) &pFormat[0];
client_call_return.Pointer = NULL;
handleType = procHeader->HandleType;
flags = procHeader->OldOiFlags;
procNum = procHeader->ProcNum;
stackSize = procHeader->StackSize;
pFormat += sizeof(NDR_PROC_HEADER);
/* The Header: http://msdn.microsoft.com/en-us/library/windows/desktop/aa378707/ */
/* Procedure Header Descriptor: http://msdn.microsoft.com/en-us/library/windows/desktop/aa374387/ */
/* Handles: http://msdn.microsoft.com/en-us/library/windows/desktop/aa373932/ */
fprintf(stderr, "Oi Header: HandleType: 0x%02X OiFlags: 0x%02X ProcNum: %d StackSize: 0x%04X\n",
handleType, *((unsigned char*) &flags),
(unsigned short) procNum, (unsigned short) stackSize);
WLog_DBG(TAG, "Oi Header: HandleType: 0x%02X OiFlags: 0x%02X ProcNum: %d StackSize: 0x%04X",
handleType, *((unsigned char *) &flags),
(unsigned short) procNum, (unsigned short) stackSize);
if (handleType > 0)
{
/* implicit handle */
fprintf(stderr, "Implicit Handle\n");
oi2ProcHeader = (NDR_OI2_PROC_HEADER*) &pFormat[0];
WLog_INFO(TAG, "Implicit Handle");
oi2ProcHeader = (NDR_OI2_PROC_HEADER *) &pFormat[0];
pFormat += sizeof(NDR_OI2_PROC_HEADER);
}
else
{
/* explicit handle */
fprintf(stderr, "Explicit Handle\n");
oi2ProcHeader = (NDR_OI2_PROC_HEADER*) &pFormat[6];
WLog_INFO(TAG, "Explicit Handle");
oi2ProcHeader = (NDR_OI2_PROC_HEADER *) &pFormat[6];
pFormat += sizeof(NDR_OI2_PROC_HEADER) + 6;
}
optFlags = oi2ProcHeader->Oi2Flags;
numberParams = oi2ProcHeader->NumberParams;
fprintf(stderr, "Oi2 Header: Oi2Flags: 0x%02X, NumberParams: %d ClientBufferSize: %d ServerBufferSize: %d\n",
*((unsigned char*) &optFlags),
(unsigned char) numberParams,
oi2ProcHeader->ClientBufferSize,
oi2ProcHeader->ServerBufferSize);
fprintf(stderr, "Oi2Flags: ");
WLog_DBG(TAG, "Oi2 Header: Oi2Flags: 0x%02X, NumberParams: %d ClientBufferSize: %d ServerBufferSize: %d",
*((unsigned char *) &optFlags),
(unsigned char) numberParams,
oi2ProcHeader->ClientBufferSize,
oi2ProcHeader->ServerBufferSize);
WLog_INFO(TAG, "Oi2Flags: ");
NdrPrintOptFlags(optFlags);
fprintf(stderr, "\n");
NdrClientInitializeNew(&rpcMsg, &stubMsg, pStubDescriptor, procNum);
if (optFlags.HasExtensions)
{
INTERPRETER_OPT_FLAGS2 extFlags;
NDR_PROC_HEADER_EXTS* extensions = (NDR_PROC_HEADER_EXTS*) pFormat;
NDR_PROC_HEADER_EXTS *extensions = (NDR_PROC_HEADER_EXTS *) pFormat;
pFormat += extensions->Size;
extFlags = extensions->Flags2;
fprintf(stderr, "Extensions: Size: %d, flags2: 0x%02X\n",
extensions->Size, *((unsigned char*) &extensions->Flags2));
WLog_DBG(TAG, "Extensions: Size: %d, flags2: 0x%02X",
extensions->Size, *((unsigned char *) &extensions->Flags2));
#ifdef __x86_64__
if (extensions->Size > sizeof(*extensions) && fpuStack)
{
int i;
unsigned short fpuMask = *(unsigned short*) (extensions + 1);
unsigned short fpuMask = *(unsigned short *)(extensions + 1);
for (i = 0; i < 4; i++, fpuMask >>= 2)
{
switch (fpuMask & 3)
{
case 1: *(float*) &stackTop[i] = *(float*) &fpuStack[i];
case 1:
*(float *) &stackTop[i] = *(float *) &fpuStack[i];
break;
case 2: *(double*) &stackTop[i] = *(double*) &fpuStack[i];
case 2:
*(double *) &stackTop[i] = *(double *) &fpuStack[i];
break;
}
}
}
#endif
fprintf(stderr, "ExtFlags: ");
WLog_INFO(TAG, "ExtFlags: ");
NdrPrintExtFlags(extFlags);
fprintf(stderr, "\n");
}
stubMsg.StackTop = (unsigned char*) stackTop;
stubMsg.StackTop = (unsigned char *) stackTop;
NdrProcessParams(&stubMsg, pFormat, NDR_PHASE_SIZE, fpuStack, numberParams);
fprintf(stderr, "stubMsg BufferLength: %d\n", (int) stubMsg.BufferLength);
WLog_DBG(TAG, "stubMsg BufferLength: %d", (int) stubMsg.BufferLength);
return client_call_return;
}
@ -342,11 +341,9 @@ CLIENT_CALL_RETURN NdrClientCall2(PMIDL_STUB_DESC pStubDescriptor, PFORMAT_STRIN
{
va_list args;
CLIENT_CALL_RETURN client_call_return;
va_start(args, pFormat);
client_call_return = NdrClientCall(pStubDescriptor, pFormat, va_arg(args, void**), NULL);
client_call_return = NdrClientCall(pStubDescriptor, pFormat, va_arg(args, void **), NULL);
va_end(args);
return client_call_return;
}

View File

@ -30,7 +30,10 @@
#ifndef _WIN32
void NdrConformantArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
#include "../log.h"
#define TAG "rpc"
void NdrConformantArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_CARRAY
@ -41,25 +44,23 @@ void NdrConformantArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pM
* element_description<>
* FC_END
*/
unsigned char type;
unsigned char alignment;
unsigned short element_size;
type = pFormat[0];
alignment = pFormat[1] + 1;
element_size = *(unsigned short*) &pFormat[2];
element_size = *(unsigned short *) &pFormat[2];
if (type != FC_CARRAY)
{
fprintf(stderr, "error: expected FC_CARRAY, got 0x%02X\n", type);
WLog_ERR(TAG, "error: expected FC_CARRAY, got 0x%02X", type);
return;
}
fprintf(stderr, "warning: NdrConformantArrayBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrConformantArrayBufferSize unimplemented");
}
void NdrConformantVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrConformantVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_CVARRAY
@ -71,11 +72,10 @@ void NdrConformantVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned c
* element_description<>
* FC_END
*/
fprintf(stderr, "warning: NdrConformantVaryingArrayBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrConformantVaryingArrayBufferSize unimplemented");
}
void NdrFixedArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrFixedArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_SMFARRAY
@ -85,7 +85,6 @@ void NdrFixedArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory
* element_description<>
* FC_END
*/
/**
* FC_LGFARRAY
* alignment<1>
@ -94,11 +93,10 @@ void NdrFixedArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory
* element_description<>
* FC_END
*/
fprintf(stderr, "warning: NdrFixedArrayBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrFixedArrayBufferSize unimplemented");
}
void NdrVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_SMVARRAY
@ -111,7 +109,6 @@ void NdrVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemo
* element_description<>
* FC_END
*/
/**
* FC_LGVARRAY
* alignment<1>
@ -123,11 +120,10 @@ void NdrVaryingArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemo
* element_description<>
* FC_END
*/
fprintf(stderr, "warning: NdrVaryingArrayBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrVaryingArrayBufferSize unimplemented");
}
void NdrComplexArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrComplexArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_BOGUS_ARRAY
@ -138,8 +134,7 @@ void NdrComplexArrayBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemo
* element_description<>
* FC_END
*/
fprintf(stderr, "warning: NdrComplexArrayBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrComplexArrayBufferSize unimplemented");
}
#endif

View File

@ -31,7 +31,10 @@
#include "ndr_context.h"
#include "ndr_private.h"
void NdrContextHandleBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
#include "../log.h"
#define TAG "rpc"
void NdrContextHandleBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
unsigned char type = *pFormat;
@ -42,8 +45,7 @@ void NdrContextHandleBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
* flag<1>
* offset<2>
*/
fprintf(stderr, "warning: NdrContextHandleBufferSize FC_BIND_PRIMITIVE unimplemented\n");
WLog_ERR(TAG, "warning: NdrContextHandleBufferSize FC_BIND_PRIMITIVE unimplemented");
}
else if (type == FC_BIND_GENERIC)
{
@ -54,8 +56,7 @@ void NdrContextHandleBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
* binding_routine_pair_index<1>
* FC_PAD
*/
fprintf(stderr, "warning: NdrContextHandleBufferSize FC_BIND_GENERIC unimplemented\n");
WLog_ERR(TAG, "warning: NdrContextHandleBufferSize FC_BIND_GENERIC unimplemented");
}
else if (type == FC_BIND_CONTEXT)
{
@ -66,7 +67,6 @@ void NdrContextHandleBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
* context_rundown_routine_index<1>
* param_num<1>
*/
NdrpAlignLength(&(pStubMsg->BufferLength), 4);
NdrpIncrementLength(&(pStubMsg->BufferLength), 20);
}

View File

@ -31,6 +31,9 @@
#include "ndr_correlation.h"
#include "ndr_private.h"
#include "../log.h"
#define TAG "rpc"
/*
* Correlation Descriptors: http://msdn.microsoft.com/en-us/library/windows/desktop/aa373607/
*
@ -41,7 +44,7 @@
*
*/
PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat, ULONG_PTR* pCount)
PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat, ULONG_PTR *pCount)
{
LPVOID ptr = NULL;
ULONG_PTR data = 0;
@ -50,13 +53,11 @@ PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
unsigned char conformance;
unsigned char correlation_type;
unsigned char correlation_operator;
correlation_type = pFormat[0];
type = correlation_type & 0x0F;
conformance = correlation_type & 0xF0;
correlation_operator = pFormat[1];
offset = *(unsigned short*) & pFormat[2];
offset = *(unsigned short *) & pFormat[2];
if (conformance == FC_NORMAL_CONFORMANCE)
{
@ -70,7 +71,7 @@ PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
{
ptr = pStubMsg->StackTop;
}
else if (conformance == FC_CONSTANT_CONFORMANCE )
else if (conformance == FC_CONSTANT_CONFORMANCE)
{
data = offset | ((DWORD) pFormat[1] << 16);
*pCount = data;
@ -86,28 +87,23 @@ PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
switch (correlation_operator)
{
case FC_DEREFERENCE:
ptr = *(LPVOID*)((char*) ptr + offset);
ptr = *(LPVOID *)((char *) ptr + offset);
break;
case FC_DIV_2:
ptr = (char*) ptr + offset;
ptr = (char *) ptr + offset;
break;
case FC_MULT_2:
ptr = (char*) ptr + offset;
ptr = (char *) ptr + offset;
break;
case FC_SUB_1:
ptr = (char*) ptr + offset;
ptr = (char *) ptr + offset;
break;
case FC_ADD_1:
ptr = (char*) ptr + offset;
ptr = (char *) ptr + offset;
break;
case FC_CALLBACK:
{
fprintf(stderr, "warning: NdrpComputeConformance FC_CALLBACK unimplemented\n");
WLog_ERR(TAG, "warning: NdrpComputeConformance FC_CALLBACK unimplemented\n");
}
break;
}
@ -118,33 +114,27 @@ PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
switch (type)
{
case FC_LONG:
data = *(LONG*) ptr;
data = *(LONG *) ptr;
break;
case FC_ULONG:
data = *(ULONG*) ptr;
data = *(ULONG *) ptr;
break;
case FC_SHORT:
data = *(SHORT*) ptr;
data = *(SHORT *) ptr;
break;
case FC_USHORT:
data = *(USHORT*) ptr;
data = *(USHORT *) ptr;
break;
case FC_CHAR:
case FC_SMALL:
data = *(CHAR*) ptr;
data = *(CHAR *) ptr;
break;
case FC_BYTE:
case FC_USMALL:
data = *(BYTE*) ptr;
data = *(BYTE *) ptr;
break;
case FC_HYPER:
data = (ULONG_PTR) *(ULONGLONG*) ptr;
data = (ULONG_PTR) *(ULONGLONG *) ptr;
break;
}
@ -154,23 +144,18 @@ PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
case FC_DEREFERENCE:
*pCount = data;
break;
case FC_DIV_2:
*pCount = data / 1;
break;
case FC_MULT_2:
*pCount = data * 1;
break;
case FC_SUB_1:
*pCount = data - 1;
break;
case FC_ADD_1:
*pCount = data + 1;
break;
case FC_CALLBACK:
break;
}
@ -183,18 +168,16 @@ PFORMAT_STRING NdrpComputeCount(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
return pFormat;
}
PFORMAT_STRING NdrpComputeConformance(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
PFORMAT_STRING NdrpComputeConformance(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
return NdrpComputeCount(pStubMsg, pMemory, pFormat, &pStubMsg->MaxCount);
}
PFORMAT_STRING NdrpComputeVariance(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
PFORMAT_STRING NdrpComputeVariance(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
ULONG_PTR ActualCount = pStubMsg->ActualCount;
pFormat = NdrpComputeCount(pStubMsg, pMemory, pFormat, &ActualCount);
pStubMsg->ActualCount = (ULONG) ActualCount;
return pFormat;
}

View File

@ -31,6 +31,9 @@
#include "ndr_pointer.h"
#include "ndr_private.h"
#include "../log.h"
#define TAG "rpc"
/**
* Pointer Layout: http://msdn.microsoft.com/en-us/library/windows/desktop/aa374376/
*
@ -62,13 +65,11 @@ PFORMAT_STRING NdrpSkipPointerLayout(PFORMAT_STRING pFormat)
* FC_PAD
* pointer_instance<8>
*/
pFormat += 10;
}
else if (*pFormat == FC_FIXED_REPEAT)
{
unsigned short number_of_pointers;
/**
* FC_FIXED_REPEAT
* FC_PAD
@ -78,15 +79,13 @@ PFORMAT_STRING NdrpSkipPointerLayout(PFORMAT_STRING pFormat)
* number_of_pointers<2>
* { pointer_instance<8> }*
*/
pFormat += 8;
number_of_pointers = *(unsigned short*) pFormat;
number_of_pointers = *(unsigned short *) pFormat;
pFormat += 2 + (number_of_pointers * 8);
}
else if (*pFormat == FC_VARIABLE_REPEAT)
{
unsigned short number_of_pointers;
/**
* FC_VARIABLE_REPEAT (FC_FIXED_OFFSET | FC_VARIABLE_OFFSET)
* FC_PAD ?!
@ -95,14 +94,13 @@ PFORMAT_STRING NdrpSkipPointerLayout(PFORMAT_STRING pFormat)
* number_of_pointers<2>
* { pointer_instance<8> }*
*/
pFormat += 6;
number_of_pointers = *(unsigned short*) pFormat;
number_of_pointers = *(unsigned short *) pFormat;
pFormat += 2 + (number_of_pointers * 8);
}
else
{
fprintf(stderr, "error: NdrpSkipPointerLayout unexpected 0x%02X\n", *pFormat);
WLog_ERR(TAG, "error: NdrpSkipPointerLayout unexpected 0x%02X", *pFormat);
break;
}
}
@ -125,13 +123,12 @@ PFORMAT_STRING NdrpSkipPointerLayout(PFORMAT_STRING pFormat)
* offset_to_complex_description<2>
*/
void NdrpPointerBufferSize(unsigned char* pMemory, PFORMAT_STRING pFormat, PMIDL_STUB_MESSAGE pStubMsg)
void NdrpPointerBufferSize(unsigned char *pMemory, PFORMAT_STRING pFormat, PMIDL_STUB_MESSAGE pStubMsg)
{
unsigned char type;
unsigned char attributes;
PFORMAT_STRING pNextFormat;
NDR_TYPE_SIZE_ROUTINE pfnSizeRoutine;
type = pFormat[0];
attributes = pFormat[1];
pFormat += 2;
@ -139,13 +136,12 @@ void NdrpPointerBufferSize(unsigned char* pMemory, PFORMAT_STRING pFormat, PMIDL
if (attributes & FC_SIMPLE_POINTER)
pNextFormat = pFormat;
else
pNextFormat = pFormat + *(SHORT*) pFormat;
pNextFormat = pFormat + *(SHORT *) pFormat;
switch (type)
{
case FC_RP: /* Reference Pointer */
break;
case FC_UP: /* Unique Pointer */
case FC_OP: /* Unique Pointer in an object interface */
@ -153,14 +149,13 @@ void NdrpPointerBufferSize(unsigned char* pMemory, PFORMAT_STRING pFormat, PMIDL
return;
break;
case FC_FP: /* Full Pointer */
fprintf(stderr, "warning: FC_FP unimplemented\n");
WLog_ERR(TAG, "warning: FC_FP unimplemented");
break;
}
if (attributes & FC_POINTER_DEREF)
pMemory = *(unsigned char**) pMemory;
pMemory = *(unsigned char **) pMemory;
pfnSizeRoutine = pfnSizeRoutines[*pNextFormat];
@ -168,26 +163,25 @@ void NdrpPointerBufferSize(unsigned char* pMemory, PFORMAT_STRING pFormat, PMIDL
pfnSizeRoutine(pStubMsg, pMemory, pNextFormat);
}
PFORMAT_STRING NdrpEmbeddedRepeatPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat, unsigned char** ppMemory)
PFORMAT_STRING NdrpEmbeddedRepeatPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat, unsigned char **ppMemory)
{
ULONG_PTR MaxCount;
unsigned char* Memory;
unsigned char* MemoryCopy;
unsigned char* MemoryPointer;
unsigned char *Memory;
unsigned char *MemoryCopy;
unsigned char *MemoryPointer;
PFORMAT_STRING pFormatNext;
PFORMAT_STRING pFormatPointers;
unsigned short increment;
unsigned short pointer_count;
unsigned short offset_to_array;
unsigned short number_of_pointers;
Memory = pStubMsg->Memory;
MemoryCopy = pStubMsg->Memory;
if (*pFormat == FC_FIXED_REPEAT)
{
pFormat += 2;
MaxCount = *(unsigned short*) pFormat;
MaxCount = *(unsigned short *) pFormat;
}
else
{
@ -201,22 +195,18 @@ PFORMAT_STRING NdrpEmbeddedRepeatPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg,
if (pFormat[1] == FC_VARIABLE_OFFSET)
{
pMemory += pStubMsg->Offset * *((unsigned short*) &pFormat[1]);
pMemory += pStubMsg->Offset * *((unsigned short *) &pFormat[1]);
}
}
pFormat += 2;
increment = *(unsigned short*) pFormat;
increment = *(unsigned short *) pFormat;
pFormat += 2;
offset_to_array = *(unsigned short*) pFormat;
offset_to_array = *(unsigned short *) pFormat;
pStubMsg->Memory = Memory + offset_to_array;
pFormat += 2;
number_of_pointers = *(unsigned short*) pFormat;
number_of_pointers = *(unsigned short *) pFormat;
pFormat += 2;
pFormatPointers = pFormat;
if (MaxCount)
@ -232,7 +222,7 @@ PFORMAT_STRING NdrpEmbeddedRepeatPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg,
do
{
pointer_count--;
MemoryPointer = &pMemory[*(unsigned short*) pFormatNext];
MemoryPointer = &pMemory[*(unsigned short *) pFormatNext];
NdrpPointerBufferSize(MemoryPointer, pFormatNext + 4, pStubMsg);
pFormatNext += 8;
}
@ -249,22 +239,20 @@ PFORMAT_STRING NdrpEmbeddedRepeatPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg,
pFormat = pFormatPointers + (number_of_pointers * 8);
pStubMsg->Memory = Memory;
return pFormat;
}
PFORMAT_STRING NdrpEmbeddedPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
PFORMAT_STRING NdrpEmbeddedPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
ULONG_PTR MaxCount;
unsigned long Offset;
unsigned char* Memory;
unsigned char *Memory;
char PointerLengthSet;
PFORMAT_STRING pFormatCopy;
unsigned long BufferLength;
unsigned long BufferLengthCopy = 0;
unsigned long PointerLength;
unsigned char* pMemoryPtr = NULL;
unsigned char *pMemoryPtr = NULL;
pFormatCopy = pFormat;
if (!pStubMsg->IgnoreEmbeddedPointers)
@ -296,7 +284,6 @@ PFORMAT_STRING NdrpEmbeddedPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsign
pStubMsg->Offset = Offset;
pStubMsg->MaxCount = MaxCount;
NdrpEmbeddedRepeatPointerBufferSize(pStubMsg, pMemory, pFormat, &pMemoryPtr);
}
@ -312,7 +299,7 @@ PFORMAT_STRING NdrpEmbeddedPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsign
return pFormat;
}
void NdrPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
if (*pFormat != FC_RP)
{
@ -323,9 +310,9 @@ void NdrPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, P
NdrpPointerBufferSize(pMemory, pFormat, pStubMsg);
}
void NdrByteCountPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrByteCountPointerBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
fprintf(stderr, "warning: NdrByteCountPointerBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrByteCountPointerBufferSize unimplemented");
}
#endif

View File

@ -30,14 +30,17 @@
#include "ndr_string.h"
void NdrConformantStringBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
#include "../log.h"
#define TAG "rpc"
void NdrConformantStringBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
fprintf(stderr, "warning: NdrConformantStringBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrConformantStringBufferSize unimplemented");
}
void NdrNonConformantStringBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrNonConformantStringBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
fprintf(stderr, "warning: NdrNonConformantStringBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrNonConformantStringBufferSize unimplemented");
}
#endif

View File

@ -32,9 +32,12 @@
#include "ndr_pointer.h"
#include "ndr_structure.h"
#include "../log.h"
#define TAG "rpc"
/* Structures: http://msdn.microsoft.com/en-us/library/windows/desktop/aa378695/ */
void NdrSimpleStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrSimpleStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_STRUCT
@ -43,7 +46,6 @@ void NdrSimpleStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemo
* member_layout<>
* FC_END
*/
/**
* FC_PSTRUCT
* alignment<1>
@ -52,27 +54,23 @@ void NdrSimpleStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemo
* member_layout<>
* FC_END
*/
unsigned char type;
unsigned char alignment;
unsigned short memory_size;
type = pFormat[0];
alignment = pFormat[1] + 1;
memory_size = *(unsigned short*) &pFormat[2];
memory_size = *(unsigned short *) &pFormat[2];
NdrpAlignLength(&(pStubMsg->BufferLength), alignment);
NdrpIncrementLength(&(pStubMsg->BufferLength), memory_size);
pFormat += 4;
if (*pFormat == FC_PSTRUCT)
NdrpEmbeddedPointerBufferSize(pStubMsg, pMemory, pFormat);
fprintf(stderr, "warning: NdrSimpleStructBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrSimpleStructBufferSize unimplemented");
}
void NdrConformantStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrConformantStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_CSTRUCT alignment<1>
@ -81,7 +79,6 @@ void NdrConformantStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* p
* member_layout<>
* FC_END
*/
/**
* FC_CPSTRUCT alignment<1>
* memory_size<2>
@ -89,11 +86,10 @@ void NdrConformantStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* p
* pointer_layout<>
* member_layout<> FC_END
*/
fprintf(stderr, "warning: NdrConformantStructBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrConformantStructBufferSize unimplemented");
}
void NdrConformantVaryingStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrConformantVaryingStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_CVSTRUCT alignment<1>
@ -103,8 +99,7 @@ void NdrConformantVaryingStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned
* layout<>
* FC_END
*/
fprintf(stderr, "warning: NdrConformantVaryingStructBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrConformantVaryingStructBufferSize unimplemented");
}
ULONG NdrComplexStructMemberSize(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFormat)
@ -121,66 +116,55 @@ ULONG NdrComplexStructMemberSize(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFo
case FC_USMALL:
size += sizeof(BYTE);
break;
case FC_WCHAR:
case FC_SHORT:
case FC_USHORT:
case FC_ENUM16:
size += sizeof(USHORT);
break;
case FC_LONG:
case FC_ULONG:
case FC_ENUM32:
size += sizeof(ULONG);
break;
case FC_INT3264:
case FC_UINT3264:
size += sizeof(INT_PTR);
break;
case FC_FLOAT:
size += sizeof(FLOAT);
break;
case FC_DOUBLE:
size += sizeof(DOUBLE);
break;
case FC_HYPER:
size += sizeof(ULONGLONG);
break;
case FC_ERROR_STATUS_T:
size += sizeof(error_status_t);
break;
case FC_IGNORE:
break;
case FC_RP:
case FC_UP:
case FC_OP:
case FC_FP:
case FC_POINTER:
size += sizeof(void*);
size += sizeof(void *);
if (*pFormat != FC_POINTER)
pFormat += 4;
break;
break;
case FC_ALIGNM2:
NdrpAlignLength(&size, 2);
break;
case FC_ALIGNM4:
NdrpAlignLength(&size, 4);
break;
case FC_ALIGNM8:
NdrpAlignLength(&size, 8);
break;
case FC_STRUCTPAD1:
case FC_STRUCTPAD2:
case FC_STRUCTPAD3:
@ -190,16 +174,13 @@ ULONG NdrComplexStructMemberSize(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFo
case FC_STRUCTPAD7:
size += *pFormat - FC_STRUCTPAD1 + 1;
break;
case FC_PAD:
break;
case FC_EMBEDDED_COMPLEX:
fprintf(stderr, "warning: NdrComplexStructMemberSize FC_EMBEDDED_COMPLEX unimplemented\n");
WLog_ERR(TAG, "warning: NdrComplexStructMemberSize FC_EMBEDDED_COMPLEX unimplemented");
break;
default:
fprintf(stderr, "warning: NdrComplexStructMemberSize 0x%02X unimplemented\n", *pFormat);
WLog_ERR(TAG, "warning: NdrComplexStructMemberSize 0x%02X unimplemented", *pFormat);
break;
}
@ -209,7 +190,7 @@ ULONG NdrComplexStructMemberSize(PMIDL_STUB_MESSAGE pStubMsg, PFORMAT_STRING pFo
return size;
}
void NdrComplexStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrComplexStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
/**
* FC_BOGUS_STRUCT
@ -221,77 +202,66 @@ void NdrComplexStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
* FC_END
* [pointer_layout<>]
*/
ULONG_PTR MaxCount;
unsigned long Offset;
unsigned long ActualCount;
unsigned char* pMemoryCopy;
unsigned char *pMemoryCopy;
unsigned char type;
unsigned char alignment;
unsigned short memory_size;
unsigned char* pointer_layout;
unsigned char* conformant_array_description;
unsigned char *pointer_layout;
unsigned char *conformant_array_description;
unsigned short offset_to_pointer_layout;
unsigned short offset_to_conformant_array_description;
type = pFormat[0];
pMemoryCopy = pMemory;
pointer_layout = conformant_array_description = NULL;
if (type != FC_BOGUS_STRUCT)
{
fprintf(stderr, "error: expected FC_BOGUS_STRUCT, got 0x%02X\n", type);
WLog_ERR(TAG, "error: expected FC_BOGUS_STRUCT, got 0x%02X", type);
return;
}
alignment = pFormat[1] + 1;
memory_size = *(unsigned short*) &pFormat[2];
memory_size = *(unsigned short *) &pFormat[2];
NdrpAlignLength(&(pStubMsg->BufferLength), alignment);
if (!pStubMsg->IgnoreEmbeddedPointers && !pStubMsg->PointerLength)
{
unsigned long BufferLengthCopy = pStubMsg->BufferLength;
int IgnoreEmbeddedPointersCopy = pStubMsg->IgnoreEmbeddedPointers;
pStubMsg->IgnoreEmbeddedPointers = 1;
NdrComplexStructBufferSize(pStubMsg, pMemory, pFormat);
pStubMsg->IgnoreEmbeddedPointers = IgnoreEmbeddedPointersCopy;
pStubMsg->PointerLength = pStubMsg->BufferLength;
pStubMsg->BufferLength = BufferLengthCopy;
}
pFormat += 4;
offset_to_conformant_array_description = *(unsigned short*) &pFormat[0];
offset_to_conformant_array_description = *(unsigned short *) &pFormat[0];
if (offset_to_conformant_array_description)
conformant_array_description = (unsigned char*) pFormat + offset_to_conformant_array_description;
pFormat += 2;
conformant_array_description = (unsigned char *) pFormat + offset_to_conformant_array_description;
offset_to_pointer_layout = *(unsigned short*) &pFormat[0];
pFormat += 2;
offset_to_pointer_layout = *(unsigned short *) &pFormat[0];
if (offset_to_pointer_layout)
pointer_layout = (unsigned char*) pFormat + offset_to_pointer_layout;
pFormat += 2;
pointer_layout = (unsigned char *) pFormat + offset_to_pointer_layout;
pFormat += 2;
pStubMsg->Memory = pMemory;
if (conformant_array_description)
{
ULONG size;
unsigned char array_type;
array_type = conformant_array_description[0];
size = NdrComplexStructMemberSize(pStubMsg, pFormat);
fprintf(stderr, "warning: NdrComplexStructBufferSize array_type: 0x%02X unimplemented\n", array_type);
WLog_ERR(TAG, "warning: NdrComplexStructBufferSize array_type: 0x%02X unimplemented", array_type);
NdrpComputeConformance(pStubMsg, pMemory + size, conformant_array_description);
NdrpComputeVariance(pStubMsg, pMemory + size, conformant_array_description);
MaxCount = pStubMsg->MaxCount;
ActualCount = pStubMsg->ActualCount;
Offset = pStubMsg->Offset;
@ -300,14 +270,11 @@ void NdrComplexStructBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMem
if (conformant_array_description)
{
unsigned char array_type;
array_type = conformant_array_description[0];
pStubMsg->MaxCount = MaxCount;
pStubMsg->ActualCount = ActualCount;
pStubMsg->Offset = Offset;
fprintf(stderr, "warning: NdrComplexStructBufferSize array_type: 0x%02X unimplemented\n", array_type);
WLog_ERR(TAG, "warning: NdrComplexStructBufferSize array_type: 0x%02X unimplemented", array_type);
}
pStubMsg->Memory = pMemoryCopy;

View File

@ -30,14 +30,17 @@
#include "ndr_union.h"
void NdrEncapsulatedUnionBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
#include "../log.h"
#define TAG "rpc"
void NdrEncapsulatedUnionBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
fprintf(stderr, "warning: NdrEncapsulatedUnionBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrEncapsulatedUnionBufferSize unimplemented");
}
void NdrNonEncapsulatedUnionBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char* pMemory, PFORMAT_STRING pFormat)
void NdrNonEncapsulatedUnionBufferSize(PMIDL_STUB_MESSAGE pStubMsg, unsigned char *pMemory, PFORMAT_STRING pFormat)
{
fprintf(stderr, "warning: NdrNonEncapsulatedUnionBufferSize unimplemented\n");
WLog_ERR(TAG, "warning: NdrNonEncapsulatedUnionBufferSize unimplemented");
}
#endif

View File

@ -30,12 +30,15 @@
#include <openssl/rand.h>
RPC_STATUS RpcBindingCopy(RPC_BINDING_HANDLE SourceBinding, RPC_BINDING_HANDLE* DestinationBinding)
#include "../log.h"
#define TAG "rpc"
RPC_STATUS RpcBindingCopy(RPC_BINDING_HANDLE SourceBinding, RPC_BINDING_HANDLE *DestinationBinding)
{
return 0;
}
RPC_STATUS RpcBindingFree(RPC_BINDING_HANDLE* Binding)
RPC_STATUS RpcBindingFree(RPC_BINDING_HANDLE *Binding)
{
return 0;
}
@ -50,22 +53,22 @@ RPC_STATUS RpcBindingInqOption(RPC_BINDING_HANDLE hBinding, unsigned long option
return 0;
}
RPC_STATUS RpcBindingFromStringBindingA(RPC_CSTR StringBinding, RPC_BINDING_HANDLE* Binding)
RPC_STATUS RpcBindingFromStringBindingA(RPC_CSTR StringBinding, RPC_BINDING_HANDLE *Binding)
{
return 0;
}
RPC_STATUS RpcBindingFromStringBindingW(RPC_WSTR StringBinding, RPC_BINDING_HANDLE* Binding)
RPC_STATUS RpcBindingFromStringBindingW(RPC_WSTR StringBinding, RPC_BINDING_HANDLE *Binding)
{
return 0;
}
RPC_STATUS RpcSsGetContextBinding(void* ContextHandle, RPC_BINDING_HANDLE* Binding)
RPC_STATUS RpcSsGetContextBinding(void *ContextHandle, RPC_BINDING_HANDLE *Binding)
{
return 0;
}
RPC_STATUS RpcBindingInqObject(RPC_BINDING_HANDLE Binding, UUID* ObjectUuid)
RPC_STATUS RpcBindingInqObject(RPC_BINDING_HANDLE Binding, UUID *ObjectUuid)
{
return 0;
}
@ -75,68 +78,68 @@ RPC_STATUS RpcBindingReset(RPC_BINDING_HANDLE Binding)
return 0;
}
RPC_STATUS RpcBindingSetObject(RPC_BINDING_HANDLE Binding, UUID* ObjectUuid)
RPC_STATUS RpcBindingSetObject(RPC_BINDING_HANDLE Binding, UUID *ObjectUuid)
{
return 0;
}
RPC_STATUS RpcMgmtInqDefaultProtectLevel(unsigned long AuthnSvc, unsigned long* AuthnLevel)
RPC_STATUS RpcMgmtInqDefaultProtectLevel(unsigned long AuthnSvc, unsigned long *AuthnLevel)
{
return 0;
}
RPC_STATUS RpcBindingToStringBindingA(RPC_BINDING_HANDLE Binding, RPC_CSTR* StringBinding)
RPC_STATUS RpcBindingToStringBindingA(RPC_BINDING_HANDLE Binding, RPC_CSTR *StringBinding)
{
return 0;
}
RPC_STATUS RpcBindingToStringBindingW(RPC_BINDING_HANDLE Binding, RPC_WSTR* StringBinding)
RPC_STATUS RpcBindingToStringBindingW(RPC_BINDING_HANDLE Binding, RPC_WSTR *StringBinding)
{
return 0;
}
RPC_STATUS RpcBindingVectorFree(RPC_BINDING_VECTOR** BindingVector)
RPC_STATUS RpcBindingVectorFree(RPC_BINDING_VECTOR **BindingVector)
{
return 0;
}
RPC_STATUS RpcStringBindingComposeA(RPC_CSTR ObjUuid, RPC_CSTR Protseq, RPC_CSTR NetworkAddr,
RPC_CSTR Endpoint, RPC_CSTR Options, RPC_CSTR* StringBinding)
RPC_CSTR Endpoint, RPC_CSTR Options, RPC_CSTR *StringBinding)
{
return 0;
}
RPC_STATUS RpcStringBindingComposeW(RPC_WSTR ObjUuid, RPC_WSTR Protseq, RPC_WSTR NetworkAddr,
RPC_WSTR Endpoint, RPC_WSTR Options, RPC_WSTR* StringBinding)
RPC_WSTR Endpoint, RPC_WSTR Options, RPC_WSTR *StringBinding)
{
return 0;
}
RPC_STATUS RpcStringBindingParseA(RPC_CSTR StringBinding, RPC_CSTR* ObjUuid, RPC_CSTR* Protseq,
RPC_CSTR* NetworkAddr, RPC_CSTR *Endpoint, RPC_CSTR* NetworkOptions)
RPC_STATUS RpcStringBindingParseA(RPC_CSTR StringBinding, RPC_CSTR *ObjUuid, RPC_CSTR *Protseq,
RPC_CSTR *NetworkAddr, RPC_CSTR *Endpoint, RPC_CSTR *NetworkOptions)
{
return 0;
}
RPC_STATUS RpcStringBindingParseW(RPC_WSTR StringBinding, RPC_WSTR* ObjUuid, RPC_WSTR* Protseq,
RPC_WSTR* NetworkAddr, RPC_WSTR *Endpoint, RPC_WSTR* NetworkOptions)
RPC_STATUS RpcStringBindingParseW(RPC_WSTR StringBinding, RPC_WSTR *ObjUuid, RPC_WSTR *Protseq,
RPC_WSTR *NetworkAddr, RPC_WSTR *Endpoint, RPC_WSTR *NetworkOptions)
{
return 0;
}
RPC_STATUS RpcStringFreeA(RPC_CSTR* String)
RPC_STATUS RpcStringFreeA(RPC_CSTR *String)
{
free(String);
return RPC_S_OK;
}
RPC_STATUS RpcStringFreeW(RPC_WSTR* String)
RPC_STATUS RpcStringFreeW(RPC_WSTR *String)
{
free(String);
return RPC_S_OK;
}
RPC_STATUS RpcIfInqId(RPC_IF_HANDLE RpcIfHandle, RPC_IF_ID* RpcIfId)
RPC_STATUS RpcIfInqId(RPC_IF_HANDLE RpcIfHandle, RPC_IF_ID *RpcIfId)
{
return 0;
}
@ -151,7 +154,7 @@ RPC_STATUS RpcNetworkIsProtseqValidW(RPC_WSTR Protseq)
return 0;
}
RPC_STATUS RpcMgmtInqComTimeout(RPC_BINDING_HANDLE Binding, unsigned int* Timeout)
RPC_STATUS RpcMgmtInqComTimeout(RPC_BINDING_HANDLE Binding, unsigned int *Timeout)
{
return 0;
}
@ -166,47 +169,47 @@ RPC_STATUS RpcMgmtSetCancelTimeout(long Timeout)
return 0;
}
RPC_STATUS RpcNetworkInqProtseqsA(RPC_PROTSEQ_VECTORA** ProtseqVector)
RPC_STATUS RpcNetworkInqProtseqsA(RPC_PROTSEQ_VECTORA **ProtseqVector)
{
return 0;
}
RPC_STATUS RpcNetworkInqProtseqsW(RPC_PROTSEQ_VECTORW** ProtseqVector)
RPC_STATUS RpcNetworkInqProtseqsW(RPC_PROTSEQ_VECTORW **ProtseqVector)
{
return 0;
}
RPC_STATUS RpcObjectInqType(UUID* ObjUuid, UUID* TypeUuid)
RPC_STATUS RpcObjectInqType(UUID *ObjUuid, UUID *TypeUuid)
{
return 0;
}
RPC_STATUS RpcObjectSetInqFn(RPC_OBJECT_INQ_FN* InquiryFn)
RPC_STATUS RpcObjectSetInqFn(RPC_OBJECT_INQ_FN *InquiryFn)
{
return 0;
}
RPC_STATUS RpcObjectSetType(UUID* ObjUuid, UUID* TypeUuid)
RPC_STATUS RpcObjectSetType(UUID *ObjUuid, UUID *TypeUuid)
{
return 0;
}
RPC_STATUS RpcProtseqVectorFreeA(RPC_PROTSEQ_VECTORA** ProtseqVector)
RPC_STATUS RpcProtseqVectorFreeA(RPC_PROTSEQ_VECTORA **ProtseqVector)
{
return 0;
}
RPC_STATUS RpcProtseqVectorFreeW(RPC_PROTSEQ_VECTORW** ProtseqVector)
RPC_STATUS RpcProtseqVectorFreeW(RPC_PROTSEQ_VECTORW **ProtseqVector)
{
return 0;
}
RPC_STATUS RpcServerInqBindings (RPC_BINDING_VECTOR** BindingVector)
RPC_STATUS RpcServerInqBindings(RPC_BINDING_VECTOR **BindingVector)
{
return 0;
}
RPC_STATUS RpcServerInqIf(RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, RPC_MGR_EPV** MgrEpv)
RPC_STATUS RpcServerInqIf(RPC_IF_HANDLE IfSpec, UUID *MgrTypeUuid, RPC_MGR_EPV **MgrEpv)
{
return 0;
}
@ -216,124 +219,123 @@ RPC_STATUS RpcServerListen(unsigned int MinimumCallThreads, unsigned int MaxCall
return 0;
}
RPC_STATUS RpcServerRegisterIf(RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, RPC_MGR_EPV* MgrEpv)
RPC_STATUS RpcServerRegisterIf(RPC_IF_HANDLE IfSpec, UUID *MgrTypeUuid, RPC_MGR_EPV *MgrEpv)
{
return 0;
}
RPC_STATUS RpcServerRegisterIfEx(RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, RPC_MGR_EPV* MgrEpv,
unsigned int Flags, unsigned int MaxCalls, RPC_IF_CALLBACK_FN* IfCallback)
RPC_STATUS RpcServerRegisterIfEx(RPC_IF_HANDLE IfSpec, UUID *MgrTypeUuid, RPC_MGR_EPV *MgrEpv,
unsigned int Flags, unsigned int MaxCalls, RPC_IF_CALLBACK_FN *IfCallback)
{
return 0;
}
RPC_STATUS RpcServerRegisterIf2(RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, RPC_MGR_EPV* MgrEpv,
unsigned int Flags, unsigned int MaxCalls, unsigned int MaxRpcSize, RPC_IF_CALLBACK_FN* IfCallbackFn)
RPC_STATUS RpcServerRegisterIf2(RPC_IF_HANDLE IfSpec, UUID *MgrTypeUuid, RPC_MGR_EPV *MgrEpv,
unsigned int Flags, unsigned int MaxCalls, unsigned int MaxRpcSize, RPC_IF_CALLBACK_FN *IfCallbackFn)
{
return 0;
}
RPC_STATUS RpcServerUnregisterIf(RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, unsigned int WaitForCallsToComplete)
RPC_STATUS RpcServerUnregisterIf(RPC_IF_HANDLE IfSpec, UUID *MgrTypeUuid, unsigned int WaitForCallsToComplete)
{
return 0;
}
RPC_STATUS RpcServerUnregisterIfEx(RPC_IF_HANDLE IfSpec, UUID* MgrTypeUuid, int RundownContextHandles)
RPC_STATUS RpcServerUnregisterIfEx(RPC_IF_HANDLE IfSpec, UUID *MgrTypeUuid, int RundownContextHandles)
{
return 0;
}
RPC_STATUS RpcServerUseAllProtseqs(unsigned int MaxCalls, void* SecurityDescriptor)
RPC_STATUS RpcServerUseAllProtseqs(unsigned int MaxCalls, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseAllProtseqsEx(unsigned int MaxCalls, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseAllProtseqsEx(unsigned int MaxCalls, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseAllProtseqsIf(unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void* SecurityDescriptor)
RPC_STATUS RpcServerUseAllProtseqsIf(unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseAllProtseqsIfEx(unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseAllProtseqsIfEx(unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqA(RPC_CSTR Protseq, unsigned int MaxCalls, void* SecurityDescriptor)
RPC_STATUS RpcServerUseProtseqA(RPC_CSTR Protseq, unsigned int MaxCalls, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqExA(RPC_CSTR Protseq, unsigned int MaxCalls, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseProtseqExA(RPC_CSTR Protseq, unsigned int MaxCalls, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqW(RPC_WSTR Protseq, unsigned int MaxCalls, void* SecurityDescriptor)
RPC_STATUS RpcServerUseProtseqW(RPC_WSTR Protseq, unsigned int MaxCalls, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqExW(RPC_WSTR Protseq, unsigned int MaxCalls, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseProtseqExW(RPC_WSTR Protseq, unsigned int MaxCalls, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqEpA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_CSTR Endpoint, void* SecurityDescriptor)
RPC_STATUS RpcServerUseProtseqEpA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_CSTR Endpoint, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqEpExA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_CSTR Endpoint, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseProtseqEpExA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_CSTR Endpoint, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqEpW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_WSTR Endpoint, void* SecurityDescriptor)
RPC_STATUS RpcServerUseProtseqEpW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_WSTR Endpoint, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqEpExW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_WSTR Endpoint, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseProtseqEpExW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_WSTR Endpoint, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqIfA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void* SecurityDescriptor)
RPC_STATUS RpcServerUseProtseqIfA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqIfExA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseProtseqIfExA(RPC_CSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqIfW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void* SecurityDescriptor)
RPC_STATUS RpcServerUseProtseqIfW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void *SecurityDescriptor)
{
return 0;
}
RPC_STATUS RpcServerUseProtseqIfExW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void* SecurityDescriptor, PRPC_POLICY Policy)
RPC_STATUS RpcServerUseProtseqIfExW(RPC_WSTR Protseq, unsigned int MaxCalls, RPC_IF_HANDLE IfSpec, void *SecurityDescriptor, PRPC_POLICY Policy)
{
return 0;
}
void RpcServerYield()
{
}
RPC_STATUS RpcMgmtStatsVectorFree(RPC_STATS_VECTOR** StatsVector)
RPC_STATUS RpcMgmtStatsVectorFree(RPC_STATS_VECTOR **StatsVector)
{
return 0;
}
RPC_STATUS RpcMgmtInqStats(RPC_BINDING_HANDLE Binding, RPC_STATS_VECTOR** Statistics)
RPC_STATUS RpcMgmtInqStats(RPC_BINDING_HANDLE Binding, RPC_STATS_VECTOR **Statistics)
{
return 0;
}
@ -360,7 +362,6 @@ RPC_STATUS RpcMgmtSetServerStackSize(unsigned long ThreadStackSize)
void RpcSsDontSerializeContext(void)
{
}
RPC_STATUS RpcMgmtEnableIdleCleanup(void)
@ -368,32 +369,32 @@ RPC_STATUS RpcMgmtEnableIdleCleanup(void)
return 0;
}
RPC_STATUS RpcMgmtInqIfIds(RPC_BINDING_HANDLE Binding, RPC_IF_ID_VECTOR** IfIdVector)
RPC_STATUS RpcMgmtInqIfIds(RPC_BINDING_HANDLE Binding, RPC_IF_ID_VECTOR **IfIdVector)
{
return 0;
}
RPC_STATUS RpcIfIdVectorFree(RPC_IF_ID_VECTOR** IfIdVector)
RPC_STATUS RpcIfIdVectorFree(RPC_IF_ID_VECTOR **IfIdVector)
{
return 0;
}
RPC_STATUS RpcMgmtInqServerPrincNameA(RPC_BINDING_HANDLE Binding, unsigned long AuthnSvc, RPC_CSTR* ServerPrincName)
RPC_STATUS RpcMgmtInqServerPrincNameA(RPC_BINDING_HANDLE Binding, unsigned long AuthnSvc, RPC_CSTR *ServerPrincName)
{
return 0;
}
RPC_STATUS RpcMgmtInqServerPrincNameW(RPC_BINDING_HANDLE Binding, unsigned long AuthnSvc, RPC_WSTR* ServerPrincName)
RPC_STATUS RpcMgmtInqServerPrincNameW(RPC_BINDING_HANDLE Binding, unsigned long AuthnSvc, RPC_WSTR *ServerPrincName)
{
return 0;
}
RPC_STATUS RpcServerInqDefaultPrincNameA(unsigned long AuthnSvc, RPC_CSTR* PrincName)
RPC_STATUS RpcServerInqDefaultPrincNameA(unsigned long AuthnSvc, RPC_CSTR *PrincName)
{
return 0;
}
RPC_STATUS RpcServerInqDefaultPrincNameW(unsigned long AuthnSvc, RPC_WSTR* PrincName)
RPC_STATUS RpcServerInqDefaultPrincNameW(unsigned long AuthnSvc, RPC_WSTR *PrincName)
{
return 0;
}
@ -403,12 +404,12 @@ RPC_STATUS RpcEpResolveBinding(RPC_BINDING_HANDLE Binding, RPC_IF_HANDLE IfSpec)
return 0;
}
RPC_STATUS RpcNsBindingInqEntryNameA(RPC_BINDING_HANDLE Binding, unsigned long EntryNameSyntax, RPC_CSTR* EntryName)
RPC_STATUS RpcNsBindingInqEntryNameA(RPC_BINDING_HANDLE Binding, unsigned long EntryNameSyntax, RPC_CSTR *EntryName)
{
return 0;
}
RPC_STATUS RpcNsBindingInqEntryNameW(RPC_BINDING_HANDLE Binding, unsigned long EntryNameSyntax, RPC_WSTR* EntryName)
RPC_STATUS RpcNsBindingInqEntryNameW(RPC_BINDING_HANDLE Binding, unsigned long EntryNameSyntax, RPC_WSTR *EntryName)
{
return 0;
}
@ -429,100 +430,100 @@ RPC_STATUS RpcRevertToSelf()
return 0;
}
RPC_STATUS RpcBindingInqAuthClientA(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE* Privs,
RPC_CSTR* ServerPrincName, unsigned long* AuthnLevel, unsigned long* AuthnSvc, unsigned long* AuthzSvc)
RPC_STATUS RpcBindingInqAuthClientA(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE *Privs,
RPC_CSTR *ServerPrincName, unsigned long *AuthnLevel, unsigned long *AuthnSvc, unsigned long *AuthzSvc)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthClientW(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE* Privs,
RPC_WSTR* ServerPrincName, unsigned long* AuthnLevel, unsigned long* AuthnSvc, unsigned long* AuthzSvc)
RPC_STATUS RpcBindingInqAuthClientW(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE *Privs,
RPC_WSTR *ServerPrincName, unsigned long *AuthnLevel, unsigned long *AuthnSvc, unsigned long *AuthzSvc)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthClientExA(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE* Privs,
RPC_CSTR* ServerPrincName, unsigned long* AuthnLevel, unsigned long* AuthnSvc, unsigned long* AuthzSvc, unsigned long Flags)
RPC_STATUS RpcBindingInqAuthClientExA(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE *Privs,
RPC_CSTR *ServerPrincName, unsigned long *AuthnLevel, unsigned long *AuthnSvc, unsigned long *AuthzSvc, unsigned long Flags)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthClientExW(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE* Privs,
RPC_WSTR* ServerPrincName, unsigned long* AuthnLevel, unsigned long* AuthnSvc, unsigned long* AuthzSvc, unsigned long Flags)
RPC_STATUS RpcBindingInqAuthClientExW(RPC_BINDING_HANDLE ClientBinding, RPC_AUTHZ_HANDLE *Privs,
RPC_WSTR *ServerPrincName, unsigned long *AuthnLevel, unsigned long *AuthnSvc, unsigned long *AuthzSvc, unsigned long Flags)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthInfoA(RPC_BINDING_HANDLE Binding, RPC_CSTR* ServerPrincName, unsigned long* AuthnLevel,
unsigned long* AuthnSvc, RPC_AUTH_IDENTITY_HANDLE* AuthIdentity, unsigned long* AuthzSvc)
RPC_STATUS RpcBindingInqAuthInfoA(RPC_BINDING_HANDLE Binding, RPC_CSTR *ServerPrincName, unsigned long *AuthnLevel,
unsigned long *AuthnSvc, RPC_AUTH_IDENTITY_HANDLE *AuthIdentity, unsigned long *AuthzSvc)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthInfoW(RPC_BINDING_HANDLE Binding, RPC_WSTR* ServerPrincName, unsigned long* AuthnLevel,
unsigned long* AuthnSvc, RPC_AUTH_IDENTITY_HANDLE* AuthIdentity, unsigned long* AuthzSvc)
RPC_STATUS RpcBindingInqAuthInfoW(RPC_BINDING_HANDLE Binding, RPC_WSTR *ServerPrincName, unsigned long *AuthnLevel,
unsigned long *AuthnSvc, RPC_AUTH_IDENTITY_HANDLE *AuthIdentity, unsigned long *AuthzSvc)
{
return 0;
}
RPC_STATUS RpcBindingSetAuthInfoA(RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName, unsigned long AuthnLevel,
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc)
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc)
{
return 0;
}
RPC_STATUS RpcBindingSetAuthInfoExA(RPC_BINDING_HANDLE Binding, RPC_CSTR ServerPrincName, unsigned long AuthnLevel,
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc, RPC_SECURITY_QOS* SecurityQos)
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc, RPC_SECURITY_QOS *SecurityQos)
{
return 0;
}
RPC_STATUS RpcBindingSetAuthInfoW(RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName, unsigned long AuthnLevel,
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc)
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc)
{
return 0;
}
RPC_STATUS RpcBindingSetAuthInfoExW(RPC_BINDING_HANDLE Binding, RPC_WSTR ServerPrincName, unsigned long AuthnLevel,
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc, RPC_SECURITY_QOS* SecurityQOS)
unsigned long AuthnSvc, RPC_AUTH_IDENTITY_HANDLE AuthIdentity, unsigned long AuthzSvc, RPC_SECURITY_QOS *SecurityQOS)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthInfoExA(RPC_BINDING_HANDLE Binding, RPC_CSTR* ServerPrincName, unsigned long* AuthnLevel,
unsigned long* AuthnSvc, RPC_AUTH_IDENTITY_HANDLE* AuthIdentity, unsigned long* AuthzSvc,
unsigned long RpcQosVersion, RPC_SECURITY_QOS* SecurityQOS)
RPC_STATUS RpcBindingInqAuthInfoExA(RPC_BINDING_HANDLE Binding, RPC_CSTR *ServerPrincName, unsigned long *AuthnLevel,
unsigned long *AuthnSvc, RPC_AUTH_IDENTITY_HANDLE *AuthIdentity, unsigned long *AuthzSvc,
unsigned long RpcQosVersion, RPC_SECURITY_QOS *SecurityQOS)
{
return 0;
}
RPC_STATUS RpcBindingInqAuthInfoExW(RPC_BINDING_HANDLE Binding, RPC_WSTR* ServerPrincName, unsigned long* AuthnLevel,
unsigned long* AuthnSvc, RPC_AUTH_IDENTITY_HANDLE* AuthIdentity, unsigned long* AuthzSvc,
unsigned long RpcQosVersion, RPC_SECURITY_QOS* SecurityQOS)
RPC_STATUS RpcBindingInqAuthInfoExW(RPC_BINDING_HANDLE Binding, RPC_WSTR *ServerPrincName, unsigned long *AuthnLevel,
unsigned long *AuthnSvc, RPC_AUTH_IDENTITY_HANDLE *AuthIdentity, unsigned long *AuthzSvc,
unsigned long RpcQosVersion, RPC_SECURITY_QOS *SecurityQOS)
{
return 0;
}
RPC_STATUS RpcServerRegisterAuthInfoA(RPC_CSTR ServerPrincName, unsigned long AuthnSvc, RPC_AUTH_KEY_RETRIEVAL_FN GetKeyFn, void* Arg)
RPC_STATUS RpcServerRegisterAuthInfoA(RPC_CSTR ServerPrincName, unsigned long AuthnSvc, RPC_AUTH_KEY_RETRIEVAL_FN GetKeyFn, void *Arg)
{
return 0;
}
RPC_STATUS RpcServerRegisterAuthInfoW(RPC_WSTR ServerPrincName, unsigned long AuthnSvc, RPC_AUTH_KEY_RETRIEVAL_FN GetKeyFn, void* Arg)
RPC_STATUS RpcServerRegisterAuthInfoW(RPC_WSTR ServerPrincName, unsigned long AuthnSvc, RPC_AUTH_KEY_RETRIEVAL_FN GetKeyFn, void *Arg)
{
return 0;
}
RPC_STATUS RpcBindingServerFromClient(RPC_BINDING_HANDLE ClientBinding, RPC_BINDING_HANDLE* ServerBinding)
RPC_STATUS RpcBindingServerFromClient(RPC_BINDING_HANDLE ClientBinding, RPC_BINDING_HANDLE *ServerBinding)
{
return 0;
}
void RpcRaiseException(RPC_STATUS exception)
{
fprintf(stderr, "RpcRaiseException: 0x%08luX\n", exception);
WLog_ERR(TAG, "RpcRaiseException: 0x%08luX", exception);
exit((int) exception);
}
@ -536,12 +537,12 @@ RPC_STATUS RpcServerTestCancel(RPC_BINDING_HANDLE BindingHandle)
return 0;
}
RPC_STATUS RpcCancelThread(void* Thread)
RPC_STATUS RpcCancelThread(void *Thread)
{
return 0;
}
RPC_STATUS RpcCancelThreadEx(void* Thread, long Timeout)
RPC_STATUS RpcCancelThreadEx(void *Thread, long Timeout)
{
return 0;
}
@ -556,19 +557,19 @@ static UUID UUID_NIL =
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
};
RPC_STATUS UuidCreate(UUID* Uuid)
RPC_STATUS UuidCreate(UUID *Uuid)
{
RAND_pseudo_bytes((void*) Uuid, 16);
RAND_pseudo_bytes((void *) Uuid, 16);
return RPC_S_OK;
}
RPC_STATUS UuidCreateSequential(UUID* Uuid)
RPC_STATUS UuidCreateSequential(UUID *Uuid)
{
RAND_pseudo_bytes((void*) Uuid, 16);
RAND_pseudo_bytes((void *) Uuid, 16);
return RPC_S_OK;
}
RPC_STATUS UuidToStringA(UUID* Uuid, RPC_CSTR* StringUuid)
RPC_STATUS UuidToStringA(UUID *Uuid, RPC_CSTR *StringUuid)
{
*StringUuid = (RPC_CSTR) malloc(36 + 1);
@ -582,22 +583,20 @@ RPC_STATUS UuidToStringA(UUID* Uuid, RPC_CSTR* StringUuid)
* Format is 32 hex digits partitioned in 5 groups:
* xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx
*/
sprintf_s((char*) *StringUuid, 36 + 1, "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x",
Uuid->Data1, Uuid->Data2, Uuid->Data3,
Uuid->Data4[0], Uuid->Data4[1],
Uuid->Data4[2], Uuid->Data4[3], Uuid->Data4[4],
Uuid->Data4[5], Uuid->Data4[6], Uuid->Data4[7]);
sprintf_s((char *) *StringUuid, 36 + 1, "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x",
Uuid->Data1, Uuid->Data2, Uuid->Data3,
Uuid->Data4[0], Uuid->Data4[1],
Uuid->Data4[2], Uuid->Data4[3], Uuid->Data4[4],
Uuid->Data4[5], Uuid->Data4[6], Uuid->Data4[7]);
return RPC_S_OK;
}
RPC_STATUS UuidToStringW(UUID* Uuid, RPC_WSTR* StringUuid)
RPC_STATUS UuidToStringW(UUID *Uuid, RPC_WSTR *StringUuid)
{
return 0;
}
RPC_STATUS UuidFromStringA(RPC_CSTR StringUuid, UUID* Uuid)
RPC_STATUS UuidFromStringA(RPC_CSTR StringUuid, UUID *Uuid)
{
int index;
BYTE bin[36];
@ -605,7 +604,7 @@ RPC_STATUS UuidFromStringA(RPC_CSTR StringUuid, UUID* Uuid)
if (!StringUuid)
return UuidCreateNil(Uuid);
if (strlen((char*) StringUuid) != 36)
if (strlen((char *) StringUuid) != 36)
return RPC_S_INVALID_STRING_UUID;
if ((StringUuid[8] != '-') || (StringUuid[13] != '-') ||
@ -630,11 +629,9 @@ RPC_STATUS UuidFromStringA(RPC_CSTR StringUuid, UUID* Uuid)
}
Uuid->Data1 = ((bin[0] << 28) | (bin[1] << 24) | (bin[2] << 20) | (bin[3] << 16) |
(bin[4] << 12) | (bin[5] << 8) | (bin[6] << 4) | bin[7]);
(bin[4] << 12) | (bin[5] << 8) | (bin[6] << 4) | bin[7]);
Uuid->Data2 = ((bin[9] << 12) | (bin[10] << 8) | (bin[11] << 4) | bin[12]);
Uuid->Data3 = ((bin[14] << 12) | (bin[15] << 8) | (bin[16] << 4) | bin[17]);
Uuid->Data4[0] = ((bin[19] << 4) | bin[20]);
Uuid->Data4[1] = ((bin[21] << 4) | bin[22]);
Uuid->Data4[2] = ((bin[24] << 4) | bin[25]);
@ -643,19 +640,17 @@ RPC_STATUS UuidFromStringA(RPC_CSTR StringUuid, UUID* Uuid)
Uuid->Data4[5] = ((bin[30] << 4) | bin[31]);
Uuid->Data4[6] = ((bin[32] << 4) | bin[33]);
Uuid->Data4[7] = ((bin[34] << 4) | bin[35]);
return RPC_S_OK;
}
RPC_STATUS UuidFromStringW(RPC_WSTR StringUuid, UUID* Uuid)
RPC_STATUS UuidFromStringW(RPC_WSTR StringUuid, UUID *Uuid)
{
return 0;
}
signed int UuidCompare(UUID* Uuid1, UUID* Uuid2, RPC_STATUS* Status)
signed int UuidCompare(UUID *Uuid1, UUID *Uuid2, RPC_STATUS *Status)
{
int index;
*Status = RPC_S_OK;
if (!Uuid1)
@ -682,48 +677,48 @@ signed int UuidCompare(UUID* Uuid1, UUID* Uuid2, RPC_STATUS* Status)
return 0;
}
RPC_STATUS UuidCreateNil(UUID* NilUuid)
RPC_STATUS UuidCreateNil(UUID *NilUuid)
{
CopyMemory((void*) NilUuid, (void*) &UUID_NIL, 16);
CopyMemory((void *) NilUuid, (void *) &UUID_NIL, 16);
return RPC_S_OK;
}
int UuidEqual(UUID* Uuid1, UUID* Uuid2, RPC_STATUS* Status)
int UuidEqual(UUID *Uuid1, UUID *Uuid2, RPC_STATUS *Status)
{
return ((UuidCompare(Uuid1, Uuid2, Status) == 0) ? TRUE : FALSE);
}
unsigned short UuidHash(UUID* Uuid, RPC_STATUS* Status)
unsigned short UuidHash(UUID *Uuid, RPC_STATUS *Status)
{
return 0;
}
int UuidIsNil(UUID* Uuid, RPC_STATUS* Status)
int UuidIsNil(UUID *Uuid, RPC_STATUS *Status)
{
return UuidEqual(Uuid, &UUID_NIL, Status);
}
RPC_STATUS RpcEpRegisterNoReplaceA(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR* BindingVector, UUID_VECTOR* UuidVector, RPC_CSTR Annotation)
RPC_STATUS RpcEpRegisterNoReplaceA(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR *BindingVector, UUID_VECTOR *UuidVector, RPC_CSTR Annotation)
{
return 0;
}
RPC_STATUS RpcEpRegisterNoReplaceW(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR* BindingVector, UUID_VECTOR* UuidVector, RPC_WSTR Annotation)
RPC_STATUS RpcEpRegisterNoReplaceW(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR *BindingVector, UUID_VECTOR *UuidVector, RPC_WSTR Annotation)
{
return 0;
}
RPC_STATUS RpcEpRegisterA(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR* BindingVector, UUID_VECTOR* UuidVector, RPC_CSTR Annotation)
RPC_STATUS RpcEpRegisterA(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR *BindingVector, UUID_VECTOR *UuidVector, RPC_CSTR Annotation)
{
return 0;
}
RPC_STATUS RpcEpRegisterW(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR* BindingVector, UUID_VECTOR* UuidVector, RPC_WSTR Annotation)
RPC_STATUS RpcEpRegisterW(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR *BindingVector, UUID_VECTOR *UuidVector, RPC_WSTR Annotation)
{
return 0;
}
RPC_STATUS RpcEpUnregister(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR* BindingVector, UUID_VECTOR* UuidVector)
RPC_STATUS RpcEpUnregister(RPC_IF_HANDLE IfSpec, RPC_BINDING_VECTOR *BindingVector, UUID_VECTOR *UuidVector)
{
return 0;
}
@ -740,31 +735,31 @@ RPC_STATUS DceErrorInqTextW(RPC_STATUS RpcStatus, RPC_WSTR ErrorText)
}
RPC_STATUS RpcMgmtEpEltInqBegin(RPC_BINDING_HANDLE EpBinding, unsigned long InquiryType, RPC_IF_ID* IfId,
unsigned long VersOption, UUID* ObjectUuid, RPC_EP_INQ_HANDLE* InquiryContext)
RPC_STATUS RpcMgmtEpEltInqBegin(RPC_BINDING_HANDLE EpBinding, unsigned long InquiryType, RPC_IF_ID *IfId,
unsigned long VersOption, UUID *ObjectUuid, RPC_EP_INQ_HANDLE *InquiryContext)
{
return 0;
}
RPC_STATUS RpcMgmtEpEltInqDone(RPC_EP_INQ_HANDLE* InquiryContext)
RPC_STATUS RpcMgmtEpEltInqDone(RPC_EP_INQ_HANDLE *InquiryContext)
{
return 0;
}
RPC_STATUS RpcMgmtEpEltInqNextA(RPC_EP_INQ_HANDLE InquiryContext, RPC_IF_ID* IfId,
RPC_BINDING_HANDLE* Binding, UUID* ObjectUuid, RPC_CSTR* Annotation)
RPC_STATUS RpcMgmtEpEltInqNextA(RPC_EP_INQ_HANDLE InquiryContext, RPC_IF_ID *IfId,
RPC_BINDING_HANDLE *Binding, UUID *ObjectUuid, RPC_CSTR *Annotation)
{
return 0;
}
RPC_STATUS RpcMgmtEpEltInqNextW(RPC_EP_INQ_HANDLE InquiryContext, RPC_IF_ID* IfId,
RPC_BINDING_HANDLE* Binding, UUID* ObjectUuid, RPC_WSTR* Annotation)
RPC_STATUS RpcMgmtEpEltInqNextW(RPC_EP_INQ_HANDLE InquiryContext, RPC_IF_ID *IfId,
RPC_BINDING_HANDLE *Binding, UUID *ObjectUuid, RPC_WSTR *Annotation)
{
return 0;
}
RPC_STATUS RpcMgmtEpUnregister(RPC_BINDING_HANDLE EpBinding, RPC_IF_ID* IfId,
RPC_BINDING_HANDLE Binding, UUID* ObjectUuid)
RPC_STATUS RpcMgmtEpUnregister(RPC_BINDING_HANDLE EpBinding, RPC_IF_ID *IfId,
RPC_BINDING_HANDLE Binding, UUID *ObjectUuid)
{
return 0;
}
@ -775,7 +770,7 @@ RPC_STATUS RpcMgmtSetAuthorizationFn(RPC_MGMT_AUTHORIZATION_FN AuthorizationFn)
}
RPC_STATUS RpcServerInqBindingHandle(RPC_BINDING_HANDLE* Binding)
RPC_STATUS RpcServerInqBindingHandle(RPC_BINDING_HANDLE *Binding)
{
return 0;
}

File diff suppressed because it is too large Load Diff

View File

@ -39,19 +39,21 @@
#include "ntlm_message.h"
char* NTLM_PACKAGE_NAME = "NTLM";
#include "../../log.h"
#define TAG "sspi.NTLM"
int ntlm_SetContextWorkstation(NTLM_CONTEXT* context, char* Workstation)
char *NTLM_PACKAGE_NAME = "NTLM";
int ntlm_SetContextWorkstation(NTLM_CONTEXT *context, char *Workstation)
{
int status;
DWORD nSize = 0;
char* ws = Workstation;
char *ws = Workstation;
if (!Workstation)
{
GetComputerNameExA(ComputerNameNetBIOS, NULL, &nSize);
ws = (char*) malloc(nSize);
ws = (char *) malloc(nSize);
if (!ws)
return -1;
@ -67,7 +69,7 @@ int ntlm_SetContextWorkstation(NTLM_CONTEXT* context, char* Workstation)
if (status <= 0)
return -1;
context->Workstation.Length = (USHORT) (status - 1);
context->Workstation.Length = (USHORT)(status - 1);
context->Workstation.Length *= 2;
if (!Workstation)
@ -76,7 +78,7 @@ int ntlm_SetContextWorkstation(NTLM_CONTEXT* context, char* Workstation)
return 1;
}
int ntlm_SetContextServicePrincipalNameW(NTLM_CONTEXT* context, LPWSTR ServicePrincipalName)
int ntlm_SetContextServicePrincipalNameW(NTLM_CONTEXT *context, LPWSTR ServicePrincipalName)
{
if (!ServicePrincipalName)
{
@ -92,38 +94,34 @@ int ntlm_SetContextServicePrincipalNameW(NTLM_CONTEXT* context, LPWSTR ServicePr
return -1;
CopyMemory(context->ServicePrincipalName.Buffer, ServicePrincipalName, context->ServicePrincipalName.Length + 2);
return 1;
}
int ntlm_SetContextServicePrincipalNameA(NTLM_CONTEXT* context, char* ServicePrincipalName)
int ntlm_SetContextServicePrincipalNameA(NTLM_CONTEXT *context, char *ServicePrincipalName)
{
int status;
context->ServicePrincipalName.Buffer = NULL;
status = ConvertToUnicode(CP_UTF8, 0, ServicePrincipalName, -1, &context->ServicePrincipalName.Buffer, 0);
if (status <= 0)
return -1;
context->ServicePrincipalName.Length = (USHORT) ((status - 1) * 2);
context->ServicePrincipalName.Length = (USHORT)((status - 1) * 2);
return 1;
}
int ntlm_SetContextTargetName(NTLM_CONTEXT* context, char* TargetName)
int ntlm_SetContextTargetName(NTLM_CONTEXT *context, char *TargetName)
{
int status;
DWORD nSize = 0;
char* name = TargetName;
char *name = TargetName;
if (!TargetName)
{
if (!GetComputerNameExA(ComputerNameDnsHostname, NULL, &nSize))
return -1;
name = (char*) malloc(nSize);
name = (char *) malloc(nSize);
if (!name)
return -1;
@ -135,12 +133,12 @@ int ntlm_SetContextTargetName(NTLM_CONTEXT* context, char* TargetName)
}
context->TargetName.pvBuffer = NULL;
status = ConvertToUnicode(CP_UTF8, 0, name, -1, (LPWSTR*) &context->TargetName.pvBuffer, 0);
status = ConvertToUnicode(CP_UTF8, 0, name, -1, (LPWSTR *) &context->TargetName.pvBuffer, 0);
if (status <= 0)
return -1;
context->TargetName.cbBuffer = (USHORT) ((status - 1) * 2);
context->TargetName.cbBuffer = (USHORT)((status - 1) * 2);
if (!TargetName)
free(name);
@ -148,16 +146,15 @@ int ntlm_SetContextTargetName(NTLM_CONTEXT* context, char* TargetName)
return 1;
}
NTLM_CONTEXT* ntlm_ContextNew()
NTLM_CONTEXT *ntlm_ContextNew()
{
HKEY hKey;
LONG status;
DWORD dwType;
DWORD dwSize;
DWORD dwValue;
NTLM_CONTEXT* context;
context = (NTLM_CONTEXT*) calloc(1, sizeof(NTLM_CONTEXT));
NTLM_CONTEXT *context;
context = (NTLM_CONTEXT *) calloc(1, sizeof(NTLM_CONTEXT));
if (!context)
return NULL;
@ -169,34 +166,33 @@ NTLM_CONTEXT* ntlm_ContextNew()
context->SendWorkstationName = TRUE;
context->NegotiateKeyExchange = TRUE;
context->UseSamFileDatabase = TRUE;
status = RegOpenKeyEx(HKEY_LOCAL_MACHINE, _T("Software\\WinPR\\NTLM"), 0, KEY_READ | KEY_WOW64_64KEY, &hKey);
if (status == ERROR_SUCCESS)
{
if (RegQueryValueEx(hKey, _T("NTLMv2"), NULL, &dwType, (BYTE*) &dwValue, &dwSize) == ERROR_SUCCESS)
if (RegQueryValueEx(hKey, _T("NTLMv2"), NULL, &dwType, (BYTE *) &dwValue, &dwSize) == ERROR_SUCCESS)
context->NTLMv2 = dwValue ? 1 : 0;
if (RegQueryValueEx(hKey, _T("UseMIC"), NULL, &dwType, (BYTE*) &dwValue, &dwSize) == ERROR_SUCCESS)
if (RegQueryValueEx(hKey, _T("UseMIC"), NULL, &dwType, (BYTE *) &dwValue, &dwSize) == ERROR_SUCCESS)
context->UseMIC = dwValue ? 1 : 0;
if (RegQueryValueEx(hKey, _T("SendVersionInfo"), NULL, &dwType, (BYTE*) &dwValue, &dwSize) == ERROR_SUCCESS)
if (RegQueryValueEx(hKey, _T("SendVersionInfo"), NULL, &dwType, (BYTE *) &dwValue, &dwSize) == ERROR_SUCCESS)
context->SendVersionInfo = dwValue ? 1 : 0;
if (RegQueryValueEx(hKey, _T("SendSingleHostData"), NULL, &dwType, (BYTE*) &dwValue, &dwSize) == ERROR_SUCCESS)
if (RegQueryValueEx(hKey, _T("SendSingleHostData"), NULL, &dwType, (BYTE *) &dwValue, &dwSize) == ERROR_SUCCESS)
context->SendSingleHostData = dwValue ? 1 : 0;
if (RegQueryValueEx(hKey, _T("SendWorkstationName"), NULL, &dwType, (BYTE*) &dwValue, &dwSize) == ERROR_SUCCESS)
if (RegQueryValueEx(hKey, _T("SendWorkstationName"), NULL, &dwType, (BYTE *) &dwValue, &dwSize) == ERROR_SUCCESS)
context->SendWorkstationName = dwValue ? 1 : 0;
if (RegQueryValueEx(hKey, _T("WorkstationName"), NULL, &dwType, NULL, &dwSize) == ERROR_SUCCESS)
{
char* workstation = (char*) malloc(dwSize + 1);
char *workstation = (char *) malloc(dwSize + 1);
if (!workstation)
return NULL;
status = RegQueryValueExA(hKey, "WorkstationName", NULL, &dwType, (BYTE*) workstation, &dwSize);
status = RegQueryValueExA(hKey, "WorkstationName", NULL, &dwType, (BYTE *) workstation, &dwSize);
workstation[dwSize] = '\0';
if (ntlm_SetContextWorkstation(context, workstation) < 0)
@ -213,12 +209,11 @@ NTLM_CONTEXT* ntlm_ContextNew()
* but enabling it in WinPR breaks TS Gateway at this point
*/
context->SuppressExtendedProtection = FALSE;
status = RegOpenKeyEx(HKEY_LOCAL_MACHINE, _T("System\\CurrentControlSet\\Control\\LSA"), 0, KEY_READ | KEY_WOW64_64KEY, &hKey);
if (status == ERROR_SUCCESS)
{
if (RegQueryValueEx(hKey, _T("SuppressExtendedProtection"), NULL, &dwType, (BYTE*) &dwValue, &dwSize) == ERROR_SUCCESS)
if (RegQueryValueEx(hKey, _T("SuppressExtendedProtection"), NULL, &dwType, (BYTE *) &dwValue, &dwSize) == ERROR_SUCCESS)
context->SuppressExtendedProtection = dwValue ? 1 : 0;
RegCloseKey(hKey);
@ -235,7 +230,7 @@ NTLM_CONTEXT* ntlm_ContextNew()
return context;
}
void ntlm_ContextFree(NTLM_CONTEXT* context)
void ntlm_ContextFree(NTLM_CONTEXT *context)
{
if (!context)
return;
@ -247,22 +242,21 @@ void ntlm_ContextFree(NTLM_CONTEXT* context)
sspi_SecBufferFree(&context->TargetName);
sspi_SecBufferFree(&context->NtChallengeResponse);
sspi_SecBufferFree(&context->LmChallengeResponse);
free(context->ServicePrincipalName.Buffer);
free(context->Workstation.Buffer);
free(context);
}
SECURITY_STATUS SEC_ENTRY ntlm_AcquireCredentialsHandleW(SEC_WCHAR* pszPrincipal, SEC_WCHAR* pszPackage,
ULONG fCredentialUse, void* pvLogonID, void* pAuthData, SEC_GET_KEY_FN pGetKeyFn,
void* pvGetKeyArgument, PCredHandle phCredential, PTimeStamp ptsExpiry)
SECURITY_STATUS SEC_ENTRY ntlm_AcquireCredentialsHandleW(SEC_WCHAR *pszPrincipal, SEC_WCHAR *pszPackage,
ULONG fCredentialUse, void *pvLogonID, void *pAuthData, SEC_GET_KEY_FN pGetKeyFn,
void *pvGetKeyArgument, PCredHandle phCredential, PTimeStamp ptsExpiry)
{
SSPI_CREDENTIALS* credentials;
SEC_WINNT_AUTH_IDENTITY* identity;
SSPI_CREDENTIALS *credentials;
SEC_WINNT_AUTH_IDENTITY *identity;
if ((fCredentialUse != SECPKG_CRED_OUTBOUND) &&
(fCredentialUse != SECPKG_CRED_INBOUND) &&
(fCredentialUse != SECPKG_CRED_BOTH))
(fCredentialUse != SECPKG_CRED_INBOUND) &&
(fCredentialUse != SECPKG_CRED_BOTH))
{
return SEC_E_INVALID_PARAMETER;
}
@ -275,28 +269,26 @@ SECURITY_STATUS SEC_ENTRY ntlm_AcquireCredentialsHandleW(SEC_WCHAR* pszPrincipal
credentials->fCredentialUse = fCredentialUse;
credentials->pGetKeyFn = pGetKeyFn;
credentials->pvGetKeyArgument = pvGetKeyArgument;
identity = (SEC_WINNT_AUTH_IDENTITY*) pAuthData;
identity = (SEC_WINNT_AUTH_IDENTITY *) pAuthData;
if (identity)
sspi_CopyAuthIdentity(&(credentials->identity), identity);
sspi_SecureHandleSetLowerPointer(phCredential, (void*) credentials);
sspi_SecureHandleSetUpperPointer(phCredential, (void*) NTLM_PACKAGE_NAME);
sspi_SecureHandleSetLowerPointer(phCredential, (void *) credentials);
sspi_SecureHandleSetUpperPointer(phCredential, (void *) NTLM_PACKAGE_NAME);
return SEC_E_OK;
}
SECURITY_STATUS SEC_ENTRY ntlm_AcquireCredentialsHandleA(SEC_CHAR* pszPrincipal, SEC_CHAR* pszPackage,
ULONG fCredentialUse, void* pvLogonID, void* pAuthData, SEC_GET_KEY_FN pGetKeyFn,
void* pvGetKeyArgument, PCredHandle phCredential, PTimeStamp ptsExpiry)
SECURITY_STATUS SEC_ENTRY ntlm_AcquireCredentialsHandleA(SEC_CHAR *pszPrincipal, SEC_CHAR *pszPackage,
ULONG fCredentialUse, void *pvLogonID, void *pAuthData, SEC_GET_KEY_FN pGetKeyFn,
void *pvGetKeyArgument, PCredHandle phCredential, PTimeStamp ptsExpiry)
{
SSPI_CREDENTIALS* credentials;
SEC_WINNT_AUTH_IDENTITY* identity;
SSPI_CREDENTIALS *credentials;
SEC_WINNT_AUTH_IDENTITY *identity;
if ((fCredentialUse != SECPKG_CRED_OUTBOUND) &&
(fCredentialUse != SECPKG_CRED_INBOUND) &&
(fCredentialUse != SECPKG_CRED_BOTH))
(fCredentialUse != SECPKG_CRED_INBOUND) &&
(fCredentialUse != SECPKG_CRED_BOTH))
{
return SEC_E_INVALID_PARAMETER;
}
@ -309,36 +301,33 @@ SECURITY_STATUS SEC_ENTRY ntlm_AcquireCredentialsHandleA(SEC_CHAR* pszPrincipal,
credentials->fCredentialUse = fCredentialUse;
credentials->pGetKeyFn = pGetKeyFn;
credentials->pvGetKeyArgument = pvGetKeyArgument;
identity = (SEC_WINNT_AUTH_IDENTITY*) pAuthData;
identity = (SEC_WINNT_AUTH_IDENTITY *) pAuthData;
if (identity)
sspi_CopyAuthIdentity(&(credentials->identity), identity);
sspi_SecureHandleSetLowerPointer(phCredential, (void*) credentials);
sspi_SecureHandleSetUpperPointer(phCredential, (void*) NTLM_PACKAGE_NAME);
sspi_SecureHandleSetLowerPointer(phCredential, (void *) credentials);
sspi_SecureHandleSetUpperPointer(phCredential, (void *) NTLM_PACKAGE_NAME);
return SEC_E_OK;
}
SECURITY_STATUS SEC_ENTRY ntlm_FreeCredentialsHandle(PCredHandle phCredential)
{
SSPI_CREDENTIALS* credentials;
SSPI_CREDENTIALS *credentials;
if (!phCredential)
return SEC_E_INVALID_HANDLE;
credentials = (SSPI_CREDENTIALS*) sspi_SecureHandleGetLowerPointer(phCredential);
credentials = (SSPI_CREDENTIALS *) sspi_SecureHandleGetLowerPointer(phCredential);
if (!credentials)
return SEC_E_INVALID_HANDLE;
sspi_CredentialsFree(credentials);
return SEC_E_OK;
}
SECURITY_STATUS SEC_ENTRY ntlm_QueryCredentialsAttributesW(PCredHandle phCredential, ULONG ulAttribute, void* pBuffer)
SECURITY_STATUS SEC_ENTRY ntlm_QueryCredentialsAttributesW(PCredHandle phCredential, ULONG ulAttribute, void *pBuffer)
{
if (ulAttribute == SECPKG_CRED_ATTR_NAMES)
{
@ -348,7 +337,7 @@ SECURITY_STATUS SEC_ENTRY ntlm_QueryCredentialsAttributesW(PCredHandle phCredent
return SEC_E_UNSUPPORTED_FUNCTION;
}
SECURITY_STATUS SEC_ENTRY ntlm_QueryCredentialsAttributesA(PCredHandle phCredential, ULONG ulAttribute, void* pBuffer)
SECURITY_STATUS SEC_ENTRY ntlm_QueryCredentialsAttributesA(PCredHandle phCredential, ULONG ulAttribute, void *pBuffer)
{
return ntlm_QueryCredentialsAttributesW(phCredential, ulAttribute, pBuffer);
}
@ -360,13 +349,12 @@ SECURITY_STATUS SEC_ENTRY ntlm_AcceptSecurityContext(PCredHandle phCredential, P
PSecBufferDesc pInput, ULONG fContextReq, ULONG TargetDataRep, PCtxtHandle phNewContext,
PSecBufferDesc pOutput, PULONG pfContextAttr, PTimeStamp ptsTimeStamp)
{
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
SECURITY_STATUS status;
SSPI_CREDENTIALS* credentials;
SSPI_CREDENTIALS *credentials;
PSecBuffer input_buffer;
PSecBuffer output_buffer;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
if (!context)
{
@ -380,13 +368,11 @@ SECURITY_STATUS SEC_ENTRY ntlm_AcceptSecurityContext(PCredHandle phCredential, P
if (fContextReq & ASC_REQ_CONFIDENTIALITY)
context->confidentiality = TRUE;
credentials = (SSPI_CREDENTIALS*) sspi_SecureHandleGetLowerPointer(phCredential);
credentials = (SSPI_CREDENTIALS *) sspi_SecureHandleGetLowerPointer(phCredential);
context->credentials = credentials;
ntlm_SetContextTargetName(context, NULL);
sspi_SecureHandleSetLowerPointer(phNewContext, context);
sspi_SecureHandleSetUpperPointer(phNewContext, (void*) NTLM_PACKAGE_NAME);
sspi_SecureHandleSetUpperPointer(phNewContext, (void *) NTLM_PACKAGE_NAME);
}
if (context->state == NTLM_STATE_INITIAL)
@ -471,18 +457,17 @@ SECURITY_STATUS SEC_ENTRY ntlm_ImpersonateSecurityContext(PCtxtHandle phContext)
}
SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextW(PCredHandle phCredential, PCtxtHandle phContext,
SEC_WCHAR* pszTargetName, ULONG fContextReq, ULONG Reserved1, ULONG TargetDataRep,
SEC_WCHAR *pszTargetName, ULONG fContextReq, ULONG Reserved1, ULONG TargetDataRep,
PSecBufferDesc pInput, ULONG Reserved2, PCtxtHandle phNewContext,
PSecBufferDesc pOutput, PULONG pfContextAttr, PTimeStamp ptsExpiry)
{
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
SECURITY_STATUS status;
SSPI_CREDENTIALS* credentials;
SSPI_CREDENTIALS *credentials;
PSecBuffer input_buffer = NULL;
PSecBuffer output_buffer = NULL;
PSecBuffer channel_bindings = NULL;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
if (!context)
{
@ -494,7 +479,7 @@ SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextW(PCredHandle phCredenti
if (fContextReq & ISC_REQ_CONFIDENTIALITY)
context->confidentiality = TRUE;
credentials = (SSPI_CREDENTIALS*) sspi_SecureHandleGetLowerPointer(phCredential);
credentials = (SSPI_CREDENTIALS *) sspi_SecureHandleGetLowerPointer(phCredential);
context->credentials = credentials;
if (context->Workstation.Length < 1)
@ -507,7 +492,7 @@ SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextW(PCredHandle phCredenti
return SEC_E_INTERNAL_ERROR;
sspi_SecureHandleSetLowerPointer(phNewContext, context);
sspi_SecureHandleSetUpperPointer(phNewContext, (void*) NTLM_PACKAGE_NAME);
sspi_SecureHandleSetUpperPointer(phNewContext, (void *) NTLM_PACKAGE_NAME);
}
if ((!pInput) || (context->state == NTLM_STATE_AUTHENTICATE))
@ -552,7 +537,7 @@ SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextW(PCredHandle phCredenti
if (channel_bindings)
{
context->Bindings.BindingsLength = channel_bindings->cbBuffer;
context->Bindings.Bindings = (SEC_CHANNEL_BINDINGS*) channel_bindings->pvBuffer;
context->Bindings.Bindings = (SEC_CHANNEL_BINDINGS *) channel_bindings->pvBuffer;
}
if (context->state == NTLM_STATE_CHALLENGE)
@ -587,12 +572,12 @@ SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextW(PCredHandle phCredenti
* @see http://msdn.microsoft.com/en-us/library/windows/desktop/aa375512%28v=vs.85%29.aspx
*/
SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextA(PCredHandle phCredential, PCtxtHandle phContext,
SEC_CHAR* pszTargetName, ULONG fContextReq, ULONG Reserved1, ULONG TargetDataRep,
SEC_CHAR *pszTargetName, ULONG fContextReq, ULONG Reserved1, ULONG TargetDataRep,
PSecBufferDesc pInput, ULONG Reserved2, PCtxtHandle phNewContext,
PSecBufferDesc pOutput, PULONG pfContextAttr, PTimeStamp ptsExpiry)
{
SECURITY_STATUS status;
SEC_WCHAR* pszTargetNameW = NULL;
SEC_WCHAR *pszTargetNameW = NULL;
if (pszTargetName)
{
@ -601,20 +586,19 @@ SECURITY_STATUS SEC_ENTRY ntlm_InitializeSecurityContextA(PCredHandle phCredenti
}
status = ntlm_InitializeSecurityContextW(phCredential, phContext, pszTargetNameW, fContextReq,
Reserved1, TargetDataRep, pInput, Reserved2, phNewContext, pOutput, pfContextAttr, ptsExpiry);
Reserved1, TargetDataRep, pInput, Reserved2, phNewContext, pOutput, pfContextAttr, ptsExpiry);
if (pszTargetNameW)
free(pszTargetNameW);
return status;
}
SECURITY_STATUS SEC_ENTRY ntlm_CompleteAuthToken(PCtxtHandle phContext, PSecBufferDesc pToken)
{
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
SECURITY_STATUS status = SEC_E_OK;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
if (!context)
return SEC_E_INVALID_HANDLE;
@ -631,23 +615,21 @@ SECURITY_STATUS SEC_ENTRY ntlm_CompleteAuthToken(PCtxtHandle phContext, PSecBuff
SECURITY_STATUS SEC_ENTRY ntlm_DeleteSecurityContext(PCtxtHandle phContext)
{
NTLM_CONTEXT* context;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
NTLM_CONTEXT *context;
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
if (!context)
return SEC_E_INVALID_HANDLE;
ntlm_ContextFree(context);
return SEC_E_OK;
}
/* http://msdn.microsoft.com/en-us/library/windows/desktop/aa379337/ */
SECURITY_STATUS SEC_ENTRY ntlm_QueryContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void* pBuffer)
SECURITY_STATUS SEC_ENTRY ntlm_QueryContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer)
{
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
if (!phContext)
return SEC_E_INVALID_HANDLE;
@ -655,44 +637,39 @@ SECURITY_STATUS SEC_ENTRY ntlm_QueryContextAttributesW(PCtxtHandle phContext, UL
if (!pBuffer)
return SEC_E_INSUFFICIENT_MEMORY;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
if (ulAttribute == SECPKG_ATTR_SIZES)
{
SecPkgContext_Sizes* ContextSizes = (SecPkgContext_Sizes*) pBuffer;
SecPkgContext_Sizes *ContextSizes = (SecPkgContext_Sizes *) pBuffer;
ContextSizes->cbMaxToken = 2010;
ContextSizes->cbMaxSignature = 16;
ContextSizes->cbBlockSize = 0;
ContextSizes->cbSecurityTrailer = 16;
return SEC_E_OK;
}
else if (ulAttribute == SECPKG_ATTR_AUTH_IDENTITY)
{
int status;
char* UserA = NULL;
char* DomainA = NULL;
SSPI_CREDENTIALS* credentials;
SecPkgContext_AuthIdentity* AuthIdentity = (SecPkgContext_AuthIdentity*) pBuffer;
char *UserA = NULL;
char *DomainA = NULL;
SSPI_CREDENTIALS *credentials;
SecPkgContext_AuthIdentity *AuthIdentity = (SecPkgContext_AuthIdentity *) pBuffer;
context->UseSamFileDatabase = FALSE;
credentials = context->credentials;
ZeroMemory(AuthIdentity, sizeof(SecPkgContext_AuthIdentity));
UserA = AuthIdentity->User;
status = ConvertFromUnicode(CP_UTF8, 0, (WCHAR*) credentials->identity.User,
credentials->identity.UserLength,
&UserA, 256, NULL, NULL);
status = ConvertFromUnicode(CP_UTF8, 0, (WCHAR *) credentials->identity.User,
credentials->identity.UserLength,
&UserA, 256, NULL, NULL);
if (status <= 0)
return SEC_E_INTERNAL_ERROR;
DomainA = AuthIdentity->Domain;
status = ConvertFromUnicode(CP_UTF8, 0, (WCHAR*) credentials->identity.Domain,
credentials->identity.DomainLength,
&DomainA, 256, NULL, NULL);
status = ConvertFromUnicode(CP_UTF8, 0, (WCHAR *) credentials->identity.Domain,
credentials->identity.DomainLength,
&DomainA, 256, NULL, NULL);
if (status <= 0)
return SEC_E_INTERNAL_ERROR;
@ -703,14 +680,14 @@ SECURITY_STATUS SEC_ENTRY ntlm_QueryContextAttributesW(PCtxtHandle phContext, UL
return SEC_E_UNSUPPORTED_FUNCTION;
}
SECURITY_STATUS SEC_ENTRY ntlm_QueryContextAttributesA(PCtxtHandle phContext, ULONG ulAttribute, void* pBuffer)
SECURITY_STATUS SEC_ENTRY ntlm_QueryContextAttributesA(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer)
{
return ntlm_QueryContextAttributesW(phContext, ulAttribute, pBuffer);
}
SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void* pBuffer, ULONG cbBuffer)
SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesW(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer, ULONG cbBuffer)
{
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
if (!phContext)
return SEC_E_INVALID_HANDLE;
@ -718,11 +695,11 @@ SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesW(PCtxtHandle phContext, ULON
if (!pBuffer)
return SEC_E_INVALID_PARAMETER;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
if (ulAttribute == SECPKG_ATTR_AUTH_NTLM_HASH)
{
SecPkgContext_AuthNtlmHash* AuthNtlmHash = (SecPkgContext_AuthNtlmHash*) pBuffer;
SecPkgContext_AuthNtlmHash *AuthNtlmHash = (SecPkgContext_AuthNtlmHash *) pBuffer;
if (cbBuffer < sizeof(SecPkgContext_AuthNtlmHash))
return SEC_E_INVALID_PARAMETER;
@ -736,7 +713,7 @@ SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesW(PCtxtHandle phContext, ULON
}
else if (ulAttribute == SECPKG_ATTR_AUTH_NTLM_MESSAGE)
{
SecPkgContext_AuthNtlmMessage* AuthNtlmMessage = (SecPkgContext_AuthNtlmMessage*) pBuffer;
SecPkgContext_AuthNtlmMessage *AuthNtlmMessage = (SecPkgContext_AuthNtlmMessage *) pBuffer;
if (cbBuffer < sizeof(SecPkgContext_AuthNtlmMessage))
return SEC_E_INVALID_PARAMETER;
@ -764,7 +741,7 @@ SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesW(PCtxtHandle phContext, ULON
}
else if (ulAttribute == SECPKG_ATTR_AUTH_NTLM_TIMESTAMP)
{
SecPkgContext_AuthNtlmTimestamp* AuthNtlmTimestamp = (SecPkgContext_AuthNtlmTimestamp*) pBuffer;
SecPkgContext_AuthNtlmTimestamp *AuthNtlmTimestamp = (SecPkgContext_AuthNtlmTimestamp *) pBuffer;
if (cbBuffer < sizeof(SecPkgContext_AuthNtlmTimestamp))
return SEC_E_INVALID_PARAMETER;
@ -778,31 +755,29 @@ SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesW(PCtxtHandle phContext, ULON
}
else if (ulAttribute == SECPKG_ATTR_AUTH_NTLM_CLIENT_CHALLENGE)
{
SecPkgContext_AuthNtlmClientChallenge* AuthNtlmClientChallenge = (SecPkgContext_AuthNtlmClientChallenge*) pBuffer;
SecPkgContext_AuthNtlmClientChallenge *AuthNtlmClientChallenge = (SecPkgContext_AuthNtlmClientChallenge *) pBuffer;
if (cbBuffer < sizeof(SecPkgContext_AuthNtlmClientChallenge))
return SEC_E_INVALID_PARAMETER;
CopyMemory(context->ClientChallenge, AuthNtlmClientChallenge->ClientChallenge, 8);
return SEC_E_OK;
}
else if (ulAttribute == SECPKG_ATTR_AUTH_NTLM_SERVER_CHALLENGE)
{
SecPkgContext_AuthNtlmServerChallenge* AuthNtlmServerChallenge = (SecPkgContext_AuthNtlmServerChallenge*) pBuffer;
SecPkgContext_AuthNtlmServerChallenge *AuthNtlmServerChallenge = (SecPkgContext_AuthNtlmServerChallenge *) pBuffer;
if (cbBuffer < sizeof(SecPkgContext_AuthNtlmServerChallenge))
return SEC_E_INVALID_PARAMETER;
CopyMemory(context->ServerChallenge, AuthNtlmServerChallenge->ServerChallenge, 8);
return SEC_E_OK;
}
return SEC_E_UNSUPPORTED_FUNCTION;
}
SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesA(PCtxtHandle phContext, ULONG ulAttribute, void* pBuffer, ULONG cbBuffer)
SECURITY_STATUS SEC_ENTRY ntlm_SetContextAttributesA(PCtxtHandle phContext, ULONG ulAttribute, void *pBuffer, ULONG cbBuffer)
{
return ntlm_SetContextAttributesW(phContext, ulAttribute, pBuffer, cbBuffer);
}
@ -816,19 +791,18 @@ SECURITY_STATUS SEC_ENTRY ntlm_EncryptMessage(PCtxtHandle phContext, ULONG fQOP,
{
int index;
int length;
void* data;
void *data;
UINT32 SeqNo;
HMAC_CTX hmac;
BYTE digest[16];
BYTE checksum[8];
BYTE* signature;
BYTE *signature;
ULONG version = 1;
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
PSecBuffer data_buffer = NULL;
PSecBuffer signature_buffer = NULL;
SeqNo = MessageSeqNo;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
for (index = 0; index < (int) pMessage->cBuffers; index++)
{
@ -852,51 +826,40 @@ SECURITY_STATUS SEC_ENTRY ntlm_EncryptMessage(PCtxtHandle phContext, ULONG fQOP,
return SEC_E_INSUFFICIENT_MEMORY;
CopyMemory(data, data_buffer->pvBuffer, length);
/* Compute the HMAC-MD5 hash of ConcatenationOf(seq_num,data) using the client signing key */
HMAC_CTX_init(&hmac);
HMAC_Init_ex(&hmac, context->SendSigningKey, 16, EVP_md5(), NULL);
HMAC_Update(&hmac, (void*) &(SeqNo), 4);
HMAC_Update(&hmac, (void*) data, length);
HMAC_Update(&hmac, (void *) &(SeqNo), 4);
HMAC_Update(&hmac, (void *) data, length);
HMAC_Final(&hmac, digest, NULL);
HMAC_CTX_cleanup(&hmac);
/* Encrypt message using with RC4, result overwrites original buffer */
if (context->confidentiality)
RC4(&context->SendRc4Seal, length, (BYTE*) data, (BYTE*) data_buffer->pvBuffer);
RC4(&context->SendRc4Seal, length, (BYTE *) data, (BYTE *) data_buffer->pvBuffer);
else
CopyMemory(data_buffer->pvBuffer, data, length);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "Data Buffer (length = %d)\n", length);
WLog_DBG(TAG, "Data Buffer (length = %d)", length);
winpr_HexDump(data, length);
fprintf(stderr, "\n");
fprintf(stderr, "Encrypted Data Buffer (length = %d)\n", (int) data_buffer->cbBuffer);
WLog_DBG(TAG, "Encrypted Data Buffer (length = %d)", (int) data_buffer->cbBuffer);
winpr_HexDump(data_buffer->pvBuffer, data_buffer->cbBuffer);
fprintf(stderr, "\n");
#endif
free(data);
/* RC4-encrypt first 8 bytes of digest */
RC4(&context->SendRc4Seal, 8, digest, checksum);
signature = (BYTE*) signature_buffer->pvBuffer;
signature = (BYTE *) signature_buffer->pvBuffer;
/* Concatenate version, ciphertext and sequence number to build signature */
CopyMemory(signature, (void*) &version, 4);
CopyMemory(&signature[4], (void*) checksum, 8);
CopyMemory(&signature[12], (void*) &(SeqNo), 4);
CopyMemory(signature, (void *) &version, 4);
CopyMemory(&signature[4], (void *) checksum, 8);
CopyMemory(&signature[12], (void *) &(SeqNo), 4);
context->SendSeqNum++;
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "Signature (length = %d)\n", (int) signature_buffer->cbBuffer);
WLog_DBG(TAG, "Signature (length = %d)", (int) signature_buffer->cbBuffer);
winpr_HexDump(signature_buffer->pvBuffer, signature_buffer->cbBuffer);
fprintf(stderr, "\n");
#endif
return SEC_E_OK;
}
@ -904,19 +867,18 @@ SECURITY_STATUS SEC_ENTRY ntlm_DecryptMessage(PCtxtHandle phContext, PSecBufferD
{
int index;
int length;
void* data;
void *data;
UINT32 SeqNo;
HMAC_CTX hmac;
BYTE digest[16];
BYTE checksum[8];
UINT32 version = 1;
NTLM_CONTEXT* context;
NTLM_CONTEXT *context;
BYTE expected_signature[16];
PSecBuffer data_buffer = NULL;
PSecBuffer signature_buffer = NULL;
SeqNo = (UINT32) MessageSeqNo;
context = (NTLM_CONTEXT*) sspi_SecureHandleGetLowerPointer(phContext);
context = (NTLM_CONTEXT *) sspi_SecureHandleGetLowerPointer(phContext);
for (index = 0; index < (int) pMessage->cBuffers; index++)
{
@ -944,49 +906,40 @@ SECURITY_STATUS SEC_ENTRY ntlm_DecryptMessage(PCtxtHandle phContext, PSecBufferD
/* Decrypt message using with RC4, result overwrites original buffer */
if (context->confidentiality)
RC4(&context->RecvRc4Seal, length, (BYTE*) data, (BYTE*) data_buffer->pvBuffer);
RC4(&context->RecvRc4Seal, length, (BYTE *) data, (BYTE *) data_buffer->pvBuffer);
else
CopyMemory(data_buffer->pvBuffer, data, length);
/* Compute the HMAC-MD5 hash of ConcatenationOf(seq_num,data) using the client signing key */
HMAC_CTX_init(&hmac);
HMAC_Init_ex(&hmac, context->RecvSigningKey, 16, EVP_md5(), NULL);
HMAC_Update(&hmac, (void*) &(SeqNo), 4);
HMAC_Update(&hmac, (void*) data_buffer->pvBuffer, data_buffer->cbBuffer);
HMAC_Update(&hmac, (void *) &(SeqNo), 4);
HMAC_Update(&hmac, (void *) data_buffer->pvBuffer, data_buffer->cbBuffer);
HMAC_Final(&hmac, digest, NULL);
HMAC_CTX_cleanup(&hmac);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "Encrypted Data Buffer (length = %d)\n", length);
WLog_DBG(TAG, "Encrypted Data Buffer (length = %d)", length);
winpr_HexDump(data, length);
fprintf(stderr, "\n");
fprintf(stderr, "Data Buffer (length = %d)\n", (int) data_buffer->cbBuffer);
WLog_DBG(TAG, "Data Buffer (length = %d)", (int) data_buffer->cbBuffer);
winpr_HexDump(data_buffer->pvBuffer, data_buffer->cbBuffer);
fprintf(stderr, "\n");
#endif
free(data);
/* RC4-encrypt first 8 bytes of digest */
RC4(&context->RecvRc4Seal, 8, digest, checksum);
/* Concatenate version, ciphertext and sequence number to build signature */
CopyMemory(expected_signature, (void*) &version, 4);
CopyMemory(&expected_signature[4], (void*) checksum, 8);
CopyMemory(&expected_signature[12], (void*) &(SeqNo), 4);
CopyMemory(expected_signature, (void *) &version, 4);
CopyMemory(&expected_signature[4], (void *) checksum, 8);
CopyMemory(&expected_signature[12], (void *) &(SeqNo), 4);
context->RecvSeqNum++;
if (memcmp(signature_buffer->pvBuffer, expected_signature, 16) != 0)
{
/* signature verification failed! */
fprintf(stderr, "signature verification failed, something nasty is going on!\n");
fprintf(stderr, "Expected Signature:\n");
winpr_HexDump(expected_signature, 16);
fprintf(stderr, "Actual Signature:\n");
winpr_HexDump((BYTE*) signature_buffer->pvBuffer, 16);
WLog_ERR(TAG, "signature verification failed, something nasty is going on!\n");
WLog_ERR(TAG, "Expected Signature:");
winpr_HexDump(TAG, WLOG_ERROR, expected_signature, 16);
WLog_ERR(TAG, "Actual Signature:");
winpr_HexDump(TAG, WLOG_ERROR, (BYTE *) signature_buffer->pvBuffer, 16);
return SEC_E_MESSAGE_ALTERED;
}

View File

@ -32,7 +32,10 @@
#include "ntlm_av_pairs.h"
const char* const AV_PAIR_STRINGS[] =
#include "../../log.h"
#define TAG "sspi.NTLM"
const char *const AV_PAIR_STRINGS[] =
{
"MsvAvEOL",
"MsvAvNbComputerName",
@ -47,18 +50,17 @@ const char* const AV_PAIR_STRINGS[] =
"MsvChannelBindings"
};
void ntlm_av_pair_list_init(NTLM_AV_PAIR* pAvPairList)
void ntlm_av_pair_list_init(NTLM_AV_PAIR *pAvPairList)
{
NTLM_AV_PAIR* pAvPair = pAvPairList;
NTLM_AV_PAIR *pAvPair = pAvPairList;
pAvPair->AvId = MsvAvEOL;
pAvPair->AvLen = 0;
}
ULONG ntlm_av_pair_list_length(NTLM_AV_PAIR* pAvPairList)
ULONG ntlm_av_pair_list_length(NTLM_AV_PAIR *pAvPairList)
{
ULONG length;
NTLM_AV_PAIR* pAvPair = pAvPairList;
NTLM_AV_PAIR *pAvPair = pAvPairList;
if (!pAvPair)
return 0;
@ -69,31 +71,26 @@ ULONG ntlm_av_pair_list_length(NTLM_AV_PAIR* pAvPairList)
}
length = (pAvPair - pAvPairList) + sizeof(NTLM_AV_PAIR);
return length;
}
void ntlm_print_av_pair_list(NTLM_AV_PAIR* pAvPairList)
void ntlm_print_av_pair_list(NTLM_AV_PAIR *pAvPairList)
{
NTLM_AV_PAIR* pAvPair = pAvPairList;
NTLM_AV_PAIR *pAvPair = pAvPairList;
if (!pAvPair)
return;
fprintf(stderr, "AV_PAIRs =\n{\n");
WLog_INFO(TAG, "AV_PAIRs =");
while (pAvPair->AvId != MsvAvEOL)
{
fprintf(stderr, "\t%s AvId: %d AvLen: %d\n",
AV_PAIR_STRINGS[pAvPair->AvId],
pAvPair->AvId, pAvPair->AvLen);
winpr_HexDump(ntlm_av_pair_get_value_pointer(pAvPair), pAvPair->AvLen);
WLog_INFO(TAG, "\t%s AvId: %d AvLen: %d",
AV_PAIR_STRINGS[pAvPair->AvId],
pAvPair->AvId, pAvPair->AvLen);
winpr_HexDump(TAG, WLOG_INFO, ntlm_av_pair_get_value_pointer(pAvPair), pAvPair->AvLen);
pAvPair = ntlm_av_pair_get_next_pointer(pAvPair);
}
fprintf(stderr, "}\n");
}
ULONG ntlm_av_pair_list_size(ULONG AvPairsCount, ULONG AvPairsValueLength)
@ -102,24 +99,24 @@ ULONG ntlm_av_pair_list_size(ULONG AvPairsCount, ULONG AvPairsValueLength)
return ((AvPairsCount + 1) * 4) + AvPairsValueLength;
}
PBYTE ntlm_av_pair_get_value_pointer(NTLM_AV_PAIR* pAvPair)
PBYTE ntlm_av_pair_get_value_pointer(NTLM_AV_PAIR *pAvPair)
{
return &((PBYTE) pAvPair)[sizeof(NTLM_AV_PAIR)];
}
int ntlm_av_pair_get_next_offset(NTLM_AV_PAIR* pAvPair)
int ntlm_av_pair_get_next_offset(NTLM_AV_PAIR *pAvPair)
{
return pAvPair->AvLen + sizeof(NTLM_AV_PAIR);
}
NTLM_AV_PAIR* ntlm_av_pair_get_next_pointer(NTLM_AV_PAIR* pAvPair)
NTLM_AV_PAIR *ntlm_av_pair_get_next_pointer(NTLM_AV_PAIR *pAvPair)
{
return (NTLM_AV_PAIR*) ((PBYTE) pAvPair + ntlm_av_pair_get_next_offset(pAvPair));
return (NTLM_AV_PAIR *)((PBYTE) pAvPair + ntlm_av_pair_get_next_offset(pAvPair));
}
NTLM_AV_PAIR* ntlm_av_pair_get(NTLM_AV_PAIR* pAvPairList, NTLM_AV_ID AvId)
NTLM_AV_PAIR *ntlm_av_pair_get(NTLM_AV_PAIR *pAvPairList, NTLM_AV_ID AvId)
{
NTLM_AV_PAIR* pAvPair = pAvPairList;
NTLM_AV_PAIR *pAvPair = pAvPairList;
if (!pAvPair)
return NULL;
@ -138,10 +135,9 @@ NTLM_AV_PAIR* ntlm_av_pair_get(NTLM_AV_PAIR* pAvPairList, NTLM_AV_ID AvId)
return NULL;
}
NTLM_AV_PAIR* ntlm_av_pair_add(NTLM_AV_PAIR* pAvPairList, NTLM_AV_ID AvId, PBYTE Value, UINT16 AvLen)
NTLM_AV_PAIR *ntlm_av_pair_add(NTLM_AV_PAIR *pAvPairList, NTLM_AV_ID AvId, PBYTE Value, UINT16 AvLen)
{
NTLM_AV_PAIR* pAvPair;
NTLM_AV_PAIR *pAvPair;
pAvPair = ntlm_av_pair_get(pAvPairList, MsvAvEOL);
if (!pAvPair)
@ -149,16 +145,13 @@ NTLM_AV_PAIR* ntlm_av_pair_add(NTLM_AV_PAIR* pAvPairList, NTLM_AV_ID AvId, PBYTE
pAvPair->AvId = AvId;
pAvPair->AvLen = AvLen;
CopyMemory(ntlm_av_pair_get_value_pointer(pAvPair), Value, AvLen);
return pAvPair;
}
NTLM_AV_PAIR* ntlm_av_pair_add_copy(NTLM_AV_PAIR* pAvPairList, NTLM_AV_PAIR* pAvPair)
NTLM_AV_PAIR *ntlm_av_pair_add_copy(NTLM_AV_PAIR *pAvPairList, NTLM_AV_PAIR *pAvPair)
{
NTLM_AV_PAIR* pAvPairCopy;
NTLM_AV_PAIR *pAvPairCopy;
pAvPairCopy = ntlm_av_pair_get(pAvPairList, MsvAvEOL);
if (!pAvPairCopy)
@ -166,26 +159,22 @@ NTLM_AV_PAIR* ntlm_av_pair_add_copy(NTLM_AV_PAIR* pAvPairList, NTLM_AV_PAIR* pAv
pAvPairCopy->AvId = pAvPair->AvId;
pAvPairCopy->AvLen = pAvPair->AvLen;
CopyMemory(ntlm_av_pair_get_value_pointer(pAvPairCopy),
ntlm_av_pair_get_value_pointer(pAvPair), pAvPair->AvLen);
ntlm_av_pair_get_value_pointer(pAvPair), pAvPair->AvLen);
return pAvPairCopy;
}
int ntlm_get_target_computer_name(PUNICODE_STRING pName, COMPUTER_NAME_FORMAT type)
{
char* name;
char *name;
int status;
DWORD nSize = 0;
GetComputerNameExA(type, NULL, &nSize);
name = (char *) malloc(nSize);
name = (char*) malloc(nSize);
if (!name)
return -1;
if (!GetComputerNameExA(type, name, &nSize))
return -1;
@ -197,11 +186,9 @@ int ntlm_get_target_computer_name(PUNICODE_STRING pName, COMPUTER_NAME_FORMAT ty
if (status <= 0)
return status;
pName->Length = (USHORT) ((status - 1) * 2);
pName->Length = (USHORT)((status - 1) * 2);
pName->MaximumLength = pName->Length;
free(name);
return 1;
}
@ -249,25 +236,22 @@ typedef struct gss_channel_bindings_struct {
} *gss_channel_bindings_t;
*/
static void ntlm_md5_update_uint32_be(MD5_CTX* md5, UINT32 num)
static void ntlm_md5_update_uint32_be(MD5_CTX *md5, UINT32 num)
{
BYTE be32[4];
be32[0] = (num >> 0) & 0xFF;
be32[1] = (num >> 8) & 0xFF;
be32[2] = (num >> 16) & 0xFF;
be32[3] = (num >> 24) & 0xFF;
MD5_Update(md5, be32, 4);
}
void ntlm_compute_channel_bindings(NTLM_CONTEXT* context)
void ntlm_compute_channel_bindings(NTLM_CONTEXT *context)
{
MD5_CTX md5;
BYTE* ChannelBindingToken;
BYTE *ChannelBindingToken;
UINT32 ChannelBindingTokenLength;
SEC_CHANNEL_BINDINGS* ChannelBindings;
SEC_CHANNEL_BINDINGS *ChannelBindings;
ZeroMemory(context->ChannelBindingsHash, 16);
ChannelBindings = context->Bindings.Bindings;
@ -275,22 +259,18 @@ void ntlm_compute_channel_bindings(NTLM_CONTEXT* context)
return;
ChannelBindingTokenLength = context->Bindings.BindingsLength - sizeof(SEC_CHANNEL_BINDINGS);
ChannelBindingToken = &((BYTE*) ChannelBindings)[ChannelBindings->dwApplicationDataOffset];
ChannelBindingToken = &((BYTE *) ChannelBindings)[ChannelBindings->dwApplicationDataOffset];
MD5_Init(&md5);
ntlm_md5_update_uint32_be(&md5, ChannelBindings->dwInitiatorAddrType);
ntlm_md5_update_uint32_be(&md5, ChannelBindings->cbInitiatorLength);
ntlm_md5_update_uint32_be(&md5, ChannelBindings->dwAcceptorAddrType);
ntlm_md5_update_uint32_be(&md5, ChannelBindings->cbAcceptorLength);
ntlm_md5_update_uint32_be(&md5, ChannelBindings->cbApplicationDataLength);
MD5_Update(&md5, (void*) ChannelBindingToken, ChannelBindingTokenLength);
MD5_Update(&md5, (void *) ChannelBindingToken, ChannelBindingTokenLength);
MD5_Final(context->ChannelBindingsHash, &md5);
}
void ntlm_compute_single_host_data(NTLM_CONTEXT* context)
void ntlm_compute_single_host_data(NTLM_CONTEXT *context)
{
/**
* The Single_Host_Data structure allows a client to send machine-specific information
@ -300,7 +280,6 @@ void ntlm_compute_single_host_data(NTLM_CONTEXT* context)
* different or if they are on different hosts, then the information MUST be ignored.
* Any fields after the MachineID field MUST be ignored on receipt.
*/
context->SingleHostData.Size = 48;
context->SingleHostData.Z4 = 0;
context->SingleHostData.DataPresent = 1;
@ -308,18 +287,17 @@ void ntlm_compute_single_host_data(NTLM_CONTEXT* context)
FillMemory(context->SingleHostData.MachineID, 32, 0xAA);
}
int ntlm_construct_challenge_target_info(NTLM_CONTEXT* context)
int ntlm_construct_challenge_target_info(NTLM_CONTEXT *context)
{
int length;
ULONG AvPairsCount;
ULONG AvPairsLength;
LONG AvPairListSize;
NTLM_AV_PAIR* pAvPairList;
NTLM_AV_PAIR *pAvPairList;
UNICODE_STRING NbDomainName;
UNICODE_STRING NbComputerName;
UNICODE_STRING DnsDomainName;
UNICODE_STRING DnsComputerName;
NbDomainName.Buffer = NULL;
if (ntlm_get_target_computer_name(&NbDomainName, ComputerNameNetBIOS) < 0)
@ -342,49 +320,43 @@ int ntlm_construct_challenge_target_info(NTLM_CONTEXT* context)
AvPairsCount = 5;
AvPairsLength = NbDomainName.Length + NbComputerName.Length +
DnsDomainName.Length + DnsComputerName.Length + 8;
DnsDomainName.Length + DnsComputerName.Length + 8;
length = ntlm_av_pair_list_size(AvPairsCount, AvPairsLength);
if (!sspi_SecBufferAlloc(&context->ChallengeTargetInfo, length))
return -1;
pAvPairList = (NTLM_AV_PAIR*) context->ChallengeTargetInfo.pvBuffer;
pAvPairList = (NTLM_AV_PAIR *) context->ChallengeTargetInfo.pvBuffer;
AvPairListSize = (ULONG) context->ChallengeTargetInfo.cbBuffer;
ntlm_av_pair_list_init(pAvPairList);
ntlm_av_pair_add(pAvPairList, MsvAvNbDomainName, (PBYTE) NbDomainName.Buffer, NbDomainName.Length);
ntlm_av_pair_add(pAvPairList, MsvAvNbComputerName, (PBYTE) NbComputerName.Buffer, NbComputerName.Length);
ntlm_av_pair_add(pAvPairList, MsvAvDnsDomainName, (PBYTE) DnsDomainName.Buffer, DnsDomainName.Length);
ntlm_av_pair_add(pAvPairList, MsvAvDnsComputerName, (PBYTE) DnsComputerName.Buffer, DnsComputerName.Length);
ntlm_av_pair_add(pAvPairList, MsvAvTimestamp, context->Timestamp, sizeof(context->Timestamp));
ntlm_free_unicode_string(&NbDomainName);
ntlm_free_unicode_string(&NbComputerName);
ntlm_free_unicode_string(&DnsDomainName);
ntlm_free_unicode_string(&DnsComputerName);
return 1;
}
int ntlm_construct_authenticate_target_info(NTLM_CONTEXT* context)
int ntlm_construct_authenticate_target_info(NTLM_CONTEXT *context)
{
ULONG size;
ULONG AvPairsCount;
ULONG AvPairsValueLength;
NTLM_AV_PAIR* AvTimestamp;
NTLM_AV_PAIR* AvNbDomainName;
NTLM_AV_PAIR* AvNbComputerName;
NTLM_AV_PAIR* AvDnsDomainName;
NTLM_AV_PAIR* AvDnsComputerName;
NTLM_AV_PAIR* AvDnsTreeName;
NTLM_AV_PAIR* ChallengeTargetInfo;
NTLM_AV_PAIR* AuthenticateTargetInfo;
NTLM_AV_PAIR *AvTimestamp;
NTLM_AV_PAIR *AvNbDomainName;
NTLM_AV_PAIR *AvNbComputerName;
NTLM_AV_PAIR *AvDnsDomainName;
NTLM_AV_PAIR *AvDnsComputerName;
NTLM_AV_PAIR *AvDnsTreeName;
NTLM_AV_PAIR *ChallengeTargetInfo;
NTLM_AV_PAIR *AuthenticateTargetInfo;
AvPairsCount = 1;
AvPairsValueLength = 0;
ChallengeTargetInfo = (NTLM_AV_PAIR*) context->ChallengeTargetInfo.pvBuffer;
ChallengeTargetInfo = (NTLM_AV_PAIR *) context->ChallengeTargetInfo.pvBuffer;
AvNbDomainName = ntlm_av_pair_get(ChallengeTargetInfo, MsvAvNbDomainName);
AvNbComputerName = ntlm_av_pair_get(ChallengeTargetInfo, MsvAvNbComputerName);
AvDnsDomainName = ntlm_av_pair_get(ChallengeTargetInfo, MsvAvDnsDomainName);
@ -449,7 +421,6 @@ int ntlm_construct_authenticate_target_info(NTLM_CONTEXT* context)
* SEC_CHANNEL_BINDINGS structure
* http://msdn.microsoft.com/en-us/library/windows/desktop/dd919963/
*/
AvPairsCount++; /* MsvChannelBindings */
AvPairsValueLength += 16;
ntlm_compute_channel_bindings(context);
@ -467,8 +438,7 @@ int ntlm_construct_authenticate_target_info(NTLM_CONTEXT* context)
size += 8; /* unknown 8-byte padding */
sspi_SecBufferAlloc(&context->AuthenticateTargetInfo, size);
AuthenticateTargetInfo = (NTLM_AV_PAIR*) context->AuthenticateTargetInfo.pvBuffer;
AuthenticateTargetInfo = (NTLM_AV_PAIR *) context->AuthenticateTargetInfo.pvBuffer;
ntlm_av_pair_list_init(AuthenticateTargetInfo);
if (AvNbDomainName)
@ -498,7 +468,7 @@ int ntlm_construct_authenticate_target_info(NTLM_CONTEXT* context)
if (context->SendSingleHostData)
{
ntlm_av_pair_add(AuthenticateTargetInfo, MsvAvSingleHost,
(PBYTE) &context->SingleHostData, context->SingleHostData.Size);
(PBYTE) &context->SingleHostData, context->SingleHostData.Size);
}
if (!context->SuppressExtendedProtection)
@ -508,17 +478,16 @@ int ntlm_construct_authenticate_target_info(NTLM_CONTEXT* context)
if (context->ServicePrincipalName.Length > 0)
{
ntlm_av_pair_add(AuthenticateTargetInfo, MsvAvTargetName,
(PBYTE) context->ServicePrincipalName.Buffer,
context->ServicePrincipalName.Length);
(PBYTE) context->ServicePrincipalName.Buffer,
context->ServicePrincipalName.Length);
}
}
if (context->NTLMv2)
{
NTLM_AV_PAIR* AvEOL;
NTLM_AV_PAIR *AvEOL;
AvEOL = ntlm_av_pair_get(ChallengeTargetInfo, MsvAvEOL);
ZeroMemory((void*) AvEOL, 4);
ZeroMemory((void *) AvEOL, 4);
}
return 1;

View File

@ -32,6 +32,9 @@
#include "ntlm_compute.h"
#include "../../log.h"
#define TAG "sspi.NTLM"
const char LM_MAGIC[] = "KGS!@#$%";
static const char NTLM_CLIENT_SIGN_MAGIC[] = "session key to client-to-server signing key magic constant";
@ -40,22 +43,19 @@ static const char NTLM_CLIENT_SEAL_MAGIC[] = "session key to client-to-server se
static const char NTLM_SERVER_SEAL_MAGIC[] = "session key to server-to-client sealing key magic constant";
static const BYTE NTLM_NULL_BUFFER[16] =
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
{ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
/**
* Populate VERSION structure.\n
* Populate VERSION structure.
* VERSION @msdn{cc236654}
* @param s
*/
void ntlm_get_version_info(NTLM_VERSION_INFO* versionInfo)
void ntlm_get_version_info(NTLM_VERSION_INFO *versionInfo)
{
OSVERSIONINFOA osVersionInfo;
osVersionInfo.dwOSVersionInfoSize = sizeof(OSVERSIONINFOA);
GetVersionExA(&osVersionInfo);
versionInfo->ProductMajorVersion = (UINT8) osVersionInfo.dwMajorVersion;
versionInfo->ProductMinorVersion = (UINT8) osVersionInfo.dwMinorVersion;
versionInfo->ProductBuild = (UINT16) osVersionInfo.dwBuildNumber;
@ -64,12 +64,12 @@ void ntlm_get_version_info(NTLM_VERSION_INFO* versionInfo)
}
/**
* Read VERSION structure.\n
* Read VERSION structure.
* VERSION @msdn{cc236654}
* @param s
*/
int ntlm_read_version_info(wStream* s, NTLM_VERSION_INFO* versionInfo)
int ntlm_read_version_info(wStream *s, NTLM_VERSION_INFO *versionInfo)
{
if (Stream_GetRemainingLength(s) < 8)
return -1;
@ -79,17 +79,16 @@ int ntlm_read_version_info(wStream* s, NTLM_VERSION_INFO* versionInfo)
Stream_Read_UINT16(s, versionInfo->ProductBuild); /* ProductBuild (2 bytes) */
Stream_Read(s, versionInfo->Reserved, sizeof(versionInfo->Reserved)); /* Reserved (3 bytes) */
Stream_Read_UINT8(s, versionInfo->NTLMRevisionCurrent); /* NTLMRevisionCurrent (1 byte) */
return 1;
}
/**
* Write VERSION structure.\n
* Write VERSION structure.
* VERSION @msdn{cc236654}
* @param s
*/
void ntlm_write_version_info(wStream* s, NTLM_VERSION_INFO* versionInfo)
void ntlm_write_version_info(wStream *s, NTLM_VERSION_INFO *versionInfo)
{
Stream_Write_UINT8(s, versionInfo->ProductMajorVersion); /* ProductMajorVersion (1 byte) */
Stream_Write_UINT8(s, versionInfo->ProductMinorVersion); /* ProductMinorVersion (1 byte) */
@ -99,26 +98,25 @@ void ntlm_write_version_info(wStream* s, NTLM_VERSION_INFO* versionInfo)
}
/**
* Print VERSION structure.\n
* Print VERSION structure.
* VERSION @msdn{cc236654}
* @param s
*/
void ntlm_print_version_info(NTLM_VERSION_INFO* versionInfo)
void ntlm_print_version_info(NTLM_VERSION_INFO *versionInfo)
{
fprintf(stderr, "VERSION =\n{\n");
fprintf(stderr, "\tProductMajorVersion: %d\n", versionInfo->ProductMajorVersion);
fprintf(stderr, "\tProductMinorVersion: %d\n", versionInfo->ProductMinorVersion);
fprintf(stderr, "\tProductBuild: %d\n", versionInfo->ProductBuild);
fprintf(stderr, "\tReserved: 0x%02X%02X%02X\n", versionInfo->Reserved[0],
versionInfo->Reserved[1], versionInfo->Reserved[2]);
fprintf(stderr, "\tNTLMRevisionCurrent: 0x%02X\n", versionInfo->NTLMRevisionCurrent);
WLog_INFO(TAG, "VERSION ={");
WLog_INFO(TAG, "\tProductMajorVersion: %d", versionInfo->ProductMajorVersion);
WLog_INFO(TAG, "\tProductMinorVersion: %d", versionInfo->ProductMinorVersion);
WLog_INFO(TAG, "\tProductBuild: %d", versionInfo->ProductBuild);
WLog_INFO(TAG, "\tReserved: 0x%02X%02X%02X", versionInfo->Reserved[0],
versionInfo->Reserved[1], versionInfo->Reserved[2]);
WLog_INFO(TAG, "\tNTLMRevisionCurrent: 0x%02X", versionInfo->NTLMRevisionCurrent);
}
int ntlm_read_ntlm_v2_client_challenge(wStream* s, NTLMv2_CLIENT_CHALLENGE* challenge)
int ntlm_read_ntlm_v2_client_challenge(wStream *s, NTLMv2_CLIENT_CHALLENGE *challenge)
{
size_t size;
Stream_Read_UINT8(s, challenge->RespType);
Stream_Read_UINT8(s, challenge->HiRespType);
Stream_Read_UINT16(s, challenge->Reserved1);
@ -126,22 +124,19 @@ int ntlm_read_ntlm_v2_client_challenge(wStream* s, NTLMv2_CLIENT_CHALLENGE* chal
Stream_Read(s, challenge->Timestamp, 8);
Stream_Read(s, challenge->ClientChallenge, 8);
Stream_Read_UINT32(s, challenge->Reserved3);
size = Stream_Length(s) - Stream_GetPosition(s);
challenge->AvPairs = (NTLM_AV_PAIR*) malloc(size);
challenge->AvPairs = (NTLM_AV_PAIR *) malloc(size);
if (!challenge->AvPairs)
return -1;
Stream_Read(s, challenge->AvPairs, size);
return 1;
}
int ntlm_write_ntlm_v2_client_challenge(wStream* s, NTLMv2_CLIENT_CHALLENGE* challenge)
int ntlm_write_ntlm_v2_client_challenge(wStream *s, NTLMv2_CLIENT_CHALLENGE *challenge)
{
ULONG length;
Stream_Write_UINT8(s, challenge->RespType);
Stream_Write_UINT8(s, challenge->HiRespType);
Stream_Write_UINT16(s, challenge->Reserved1);
@ -149,20 +144,18 @@ int ntlm_write_ntlm_v2_client_challenge(wStream* s, NTLMv2_CLIENT_CHALLENGE* cha
Stream_Write(s, challenge->Timestamp, 8);
Stream_Write(s, challenge->ClientChallenge, 8);
Stream_Write_UINT32(s, challenge->Reserved3);
length = ntlm_av_pair_list_length(challenge->AvPairs);
Stream_Write(s, challenge->AvPairs, length);
return 1;
}
int ntlm_read_ntlm_v2_response(wStream* s, NTLMv2_RESPONSE* response)
int ntlm_read_ntlm_v2_response(wStream *s, NTLMv2_RESPONSE *response)
{
Stream_Read(s, response->Response, 16);
return ntlm_read_ntlm_v2_client_challenge(s, &(response->Challenge));
}
int ntlm_write_ntlm_v2_response(wStream* s, NTLMv2_RESPONSE* response)
int ntlm_write_ntlm_v2_response(wStream *s, NTLMv2_RESPONSE *response)
{
Stream_Write(s, response->Response, 16);
return ntlm_write_ntlm_v2_client_challenge(s, &(response->Challenge));
@ -173,16 +166,13 @@ int ntlm_write_ntlm_v2_response(wStream* s, NTLMv2_RESPONSE* response)
* @param[out] timestamp 64-bit little-endian timestamp
*/
void ntlm_current_time(BYTE* timestamp)
void ntlm_current_time(BYTE *timestamp)
{
FILETIME filetime;
ULARGE_INTEGER time64;
GetSystemTimeAsFileTime(&filetime);
time64.LowPart = filetime.dwLowDateTime;
time64.HighPart = filetime.dwHighDateTime;
CopyMemory(timestamp, &(time64.QuadPart), 8);
}
@ -191,7 +181,7 @@ void ntlm_current_time(BYTE* timestamp)
* @param NTLM context
*/
void ntlm_generate_timestamp(NTLM_CONTEXT* context)
void ntlm_generate_timestamp(NTLM_CONTEXT *context)
{
if (memcmp(context->ChallengeTimestamp, NTLM_NULL_BUFFER, 8) != 0)
CopyMemory(context->Timestamp, context->ChallengeTimestamp, 8);
@ -199,84 +189,73 @@ void ntlm_generate_timestamp(NTLM_CONTEXT* context)
ntlm_current_time(context->Timestamp);
}
int ntlm_fetch_ntlm_v2_hash(NTLM_CONTEXT* context, BYTE* hash)
int ntlm_fetch_ntlm_v2_hash(NTLM_CONTEXT *context, BYTE *hash)
{
WINPR_SAM* sam;
WINPR_SAM_ENTRY* entry;
SSPI_CREDENTIALS* credentials = context->credentials;
WINPR_SAM *sam;
WINPR_SAM_ENTRY *entry;
SSPI_CREDENTIALS *credentials = context->credentials;
sam = SamOpen(TRUE);
if (!sam)
return -1;
entry = SamLookupUserW(sam,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2);
if (entry)
{
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "NTLM Hash:\n");
WLog_DBG(TAG, "NTLM Hash:");
winpr_HexDump(entry->NtHash, 16);
#endif
NTOWFv2FromHashW(entry->NtHash,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE*) hash);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE *) hash);
SamFreeEntry(sam, entry);
SamClose(sam);
return 1;
}
entry = SamLookupUserW(sam,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2, NULL, 0);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2, NULL, 0);
if (entry)
{
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "NTLM Hash:\n");
WLog_DBG(TAG, "NTLM Hash:");
winpr_HexDump(entry->NtHash, 16);
#endif
NTOWFv2FromHashW(entry->NtHash,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE*) hash);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE *) hash);
SamFreeEntry(sam, entry);
SamClose(sam);
return 1;
}
else
{
fprintf(stderr, "Error: Could not find user in SAM database\n");
WLog_ERR(TAG, "Error: Could not find user in SAM database");
return 0;
}
SamClose(sam);
return 1;
}
int ntlm_convert_password_hash(NTLM_CONTEXT* context, BYTE* hash)
int ntlm_convert_password_hash(NTLM_CONTEXT *context, BYTE *hash)
{
int status;
int i, hn, ln;
char* PasswordHash = NULL;
char *PasswordHash = NULL;
UINT32 PasswordHashLength = 0;
SSPI_CREDENTIALS* credentials = context->credentials;
SSPI_CREDENTIALS *credentials = context->credentials;
/* Password contains a password hash of length (PasswordLength / SSPI_CREDENTIALS_HASH_LENGTH_FACTOR) */
PasswordHashLength = credentials->identity.PasswordLength / SSPI_CREDENTIALS_HASH_LENGTH_FACTOR;
status = ConvertFromUnicode(CP_UTF8, 0, (LPCWSTR) credentials->identity.Password,
PasswordHashLength, &PasswordHash, 0, NULL, NULL);
PasswordHashLength, &PasswordHash, 0, NULL, NULL);
if (status <= 0)
return -1;
@ -291,13 +270,12 @@ int ntlm_convert_password_hash(NTLM_CONTEXT* context, BYTE* hash)
}
free(PasswordHash);
return 1;
}
int ntlm_compute_ntlm_v2_hash(NTLM_CONTEXT* context, BYTE* hash)
int ntlm_compute_ntlm_v2_hash(NTLM_CONTEXT *context, BYTE *hash)
{
SSPI_CREDENTIALS* credentials = context->credentials;
SSPI_CREDENTIALS *credentials = context->credentials;
if (memcmp(context->NtlmV2Hash, NTLM_NULL_BUFFER, 16) != 0)
return 1;
@ -305,27 +283,26 @@ int ntlm_compute_ntlm_v2_hash(NTLM_CONTEXT* context, BYTE* hash)
if (memcmp(context->NtlmHash, NTLM_NULL_BUFFER, 16) != 0)
{
NTOWFv2FromHashW(context->NtlmHash,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE*) hash);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE *) hash);
}
else if (credentials->identity.PasswordLength > 256)
{
/* Special case for WinPR: password hash */
if (ntlm_convert_password_hash(context, context->NtlmHash) < 0)
return -1;
NTOWFv2FromHashW(context->NtlmHash,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE*) hash);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2,
(BYTE *) hash);
}
else if (credentials->identity.PasswordLength > 0)
{
NTOWFv2W((LPWSTR) credentials->identity.Password, credentials->identity.PasswordLength * 2,
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2, (BYTE*) hash);
(LPWSTR) credentials->identity.User, credentials->identity.UserLength * 2,
(LPWSTR) credentials->identity.Domain, credentials->identity.DomainLength * 2, (BYTE *) hash);
}
else if (context->UseSamFileDatabase)
{
@ -335,9 +312,9 @@ int ntlm_compute_ntlm_v2_hash(NTLM_CONTEXT* context, BYTE* hash)
return 1;
}
int ntlm_compute_lm_v2_response(NTLM_CONTEXT* context)
int ntlm_compute_lm_v2_response(NTLM_CONTEXT *context)
{
BYTE* response;
BYTE *response;
BYTE value[16];
if (context->LmCompatibilityLevel < 2)
@ -346,7 +323,6 @@ int ntlm_compute_lm_v2_response(NTLM_CONTEXT* context)
return -1;
ZeroMemory(context->LmChallengeResponse.pvBuffer, 24);
return 1;
}
@ -362,33 +338,29 @@ int ntlm_compute_lm_v2_response(NTLM_CONTEXT* context)
if (!sspi_SecBufferAlloc(&context->LmChallengeResponse, 24))
return -1;
response = (BYTE*) context->LmChallengeResponse.pvBuffer;
response = (BYTE *) context->LmChallengeResponse.pvBuffer;
/* Compute the HMAC-MD5 hash of the resulting value using the NTLMv2 hash as the key */
HMAC(EVP_md5(), (void*) context->NtlmV2Hash, 16, (BYTE*) value, 16, (BYTE*) response, NULL);
HMAC(EVP_md5(), (void *) context->NtlmV2Hash, 16, (BYTE *) value, 16, (BYTE *) response, NULL);
/* Concatenate the resulting HMAC-MD5 hash and the client challenge, giving us the LMv2 response (24 bytes) */
CopyMemory(&response[16], context->ClientChallenge, 8);
return 1;
}
/**
* Compute NTLMv2 Response.\n
* NTLMv2_RESPONSE @msdn{cc236653}\n
* Compute NTLMv2 Response.
* NTLMv2_RESPONSE @msdn{cc236653}
* NTLMv2 Authentication @msdn{cc236700}
* @param NTLM context
*/
int ntlm_compute_ntlm_v2_response(NTLM_CONTEXT* context)
int ntlm_compute_ntlm_v2_response(NTLM_CONTEXT *context)
{
BYTE* blob;
BYTE *blob;
BYTE nt_proof_str[16];
SecBuffer ntlm_v2_temp;
SecBuffer ntlm_v2_temp_chal;
PSecBuffer TargetInfo;
SSPI_CREDENTIALS* credentials;
SSPI_CREDENTIALS *credentials;
credentials = context->credentials;
TargetInfo = &context->ChallengeTargetInfo;
@ -396,35 +368,25 @@ int ntlm_compute_ntlm_v2_response(NTLM_CONTEXT* context)
return -1;
ZeroMemory(ntlm_v2_temp.pvBuffer, ntlm_v2_temp.cbBuffer);
blob = (BYTE*) ntlm_v2_temp.pvBuffer;
blob = (BYTE *) ntlm_v2_temp.pvBuffer;
/* Compute the NTLMv2 hash */
if (ntlm_compute_ntlm_v2_hash(context, (BYTE*) context->NtlmV2Hash) < 0)
if (ntlm_compute_ntlm_v2_hash(context, (BYTE *) context->NtlmV2Hash) < 0)
return -1;
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "Password (length = %d)\n", credentials->identity.PasswordLength * 2);
winpr_HexDump((BYTE*) credentials->identity.Password, credentials->identity.PasswordLength * 2);
fprintf(stderr, "\n");
fprintf(stderr, "Username (length = %d)\n", credentials->identity.UserLength * 2);
winpr_HexDump((BYTE*) credentials->identity.User, credentials->identity.UserLength * 2);
fprintf(stderr, "\n");
fprintf(stderr, "Domain (length = %d)\n", credentials->identity.DomainLength * 2);
winpr_HexDump((BYTE*) credentials->identity.Domain, credentials->identity.DomainLength * 2);
fprintf(stderr, "\n");
fprintf(stderr, "Workstation (length = %d)\n", context->Workstation.Length);
winpr_HexDump((BYTE*) context->Workstation.Buffer, context->Workstation.Length);
fprintf(stderr, "\n");
fprintf(stderr, "NTOWFv2, NTLMv2 Hash\n");
WLog_DBG(TAG, "Password (length = %d)", credentials->identity.PasswordLength * 2);
winpr_HexDump((BYTE *) credentials->identity.Password, credentials->identity.PasswordLength * 2);
WLog_DBG(TAG, "Username (length = %d)", credentials->identity.UserLength * 2);
winpr_HexDump((BYTE *) credentials->identity.User, credentials->identity.UserLength * 2);
WLog_DBG(TAG, "Domain (length = %d)", credentials->identity.DomainLength * 2);
winpr_HexDump((BYTE *) credentials->identity.Domain, credentials->identity.DomainLength * 2);
WLog_DBG(TAG, "Workstation (length = %d)", context->Workstation.Length);
winpr_HexDump((BYTE *) context->Workstation.Buffer, context->Workstation.Length);
WLog_DBG(TAG, "NTOWFv2, NTLMv2 Hash");
winpr_HexDump(context->NtlmV2Hash, 16);
fprintf(stderr, "\n");
#endif
/* Construct temp */
blob[0] = 1; /* RespType (1 byte) */
blob[1] = 1; /* HighRespType (1 byte) */
@ -434,11 +396,9 @@ int ntlm_compute_ntlm_v2_response(NTLM_CONTEXT* context)
CopyMemory(&blob[16], context->ClientChallenge, 8); /* ClientChallenge (8 bytes) */
/* Reserved3 (4 bytes) */
CopyMemory(&blob[28], TargetInfo->pvBuffer, TargetInfo->cbBuffer);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "NTLMv2 Response Temp Blob\n");
WLog_DBG(TAG, "NTLMv2 Response Temp Blob");
winpr_HexDump(ntlm_v2_temp.pvBuffer, ntlm_v2_temp.cbBuffer);
fprintf(stderr, "\n");
#endif
/* Concatenate server challenge with temp */
@ -446,28 +406,24 @@ int ntlm_compute_ntlm_v2_response(NTLM_CONTEXT* context)
if (!sspi_SecBufferAlloc(&ntlm_v2_temp_chal, ntlm_v2_temp.cbBuffer + 8))
return -1;
blob = (BYTE*) ntlm_v2_temp_chal.pvBuffer;
blob = (BYTE *) ntlm_v2_temp_chal.pvBuffer;
CopyMemory(blob, context->ServerChallenge, 8);
CopyMemory(&blob[8], ntlm_v2_temp.pvBuffer, ntlm_v2_temp.cbBuffer);
HMAC(EVP_md5(), (BYTE*) context->NtlmV2Hash, 16, (BYTE*) ntlm_v2_temp_chal.pvBuffer,
ntlm_v2_temp_chal.cbBuffer, (BYTE*) nt_proof_str, NULL);
HMAC(EVP_md5(), (BYTE *) context->NtlmV2Hash, 16, (BYTE *) ntlm_v2_temp_chal.pvBuffer,
ntlm_v2_temp_chal.cbBuffer, (BYTE *) nt_proof_str, NULL);
/* NtChallengeResponse, Concatenate NTProofStr with temp */
if (!sspi_SecBufferAlloc(&context->NtChallengeResponse, ntlm_v2_temp.cbBuffer + 16))
return -1;
blob = (BYTE*) context->NtChallengeResponse.pvBuffer;
blob = (BYTE *) context->NtChallengeResponse.pvBuffer;
CopyMemory(blob, nt_proof_str, 16);
CopyMemory(&blob[16], ntlm_v2_temp.pvBuffer, ntlm_v2_temp.cbBuffer);
/* Compute SessionBaseKey, the HMAC-MD5 hash of NTProofStr using the NTLMv2 hash as the key */
HMAC(EVP_md5(), (BYTE*) context->NtlmV2Hash, 16, (BYTE*) nt_proof_str, 16, (BYTE*) context->SessionBaseKey, NULL);
HMAC(EVP_md5(), (BYTE *) context->NtlmV2Hash, 16, (BYTE *) nt_proof_str, 16, (BYTE *) context->SessionBaseKey, NULL);
sspi_SecBufferFree(&ntlm_v2_temp);
sspi_SecBufferFree(&ntlm_v2_temp_chal);
return 1;
}
@ -479,15 +435,13 @@ int ntlm_compute_ntlm_v2_response(NTLM_CONTEXT* context)
* @param ciphertext cipher text
*/
void ntlm_rc4k(BYTE* key, int length, BYTE* plaintext, BYTE* ciphertext)
void ntlm_rc4k(BYTE *key, int length, BYTE *plaintext, BYTE *ciphertext)
{
RC4_KEY rc4;
/* Initialize RC4 cipher with key */
RC4_set_key(&rc4, 16, (void*) key);
RC4_set_key(&rc4, 16, (void *) key);
/* Encrypt plaintext with key */
RC4(&rc4, length, (void*) plaintext, (void*) ciphertext);
RC4(&rc4, length, (void *) plaintext, (void *) ciphertext);
}
/**
@ -495,10 +449,9 @@ void ntlm_rc4k(BYTE* key, int length, BYTE* plaintext, BYTE* ciphertext)
* @param NTLM context
*/
void ntlm_generate_client_challenge(NTLM_CONTEXT* context)
void ntlm_generate_client_challenge(NTLM_CONTEXT *context)
{
/* ClientChallenge is used in computation of LMv2 and NTLMv2 responses */
if (memcmp(context->ClientChallenge, NTLM_NULL_BUFFER, 8) == 0)
RAND_bytes(context->ClientChallenge, 8);
}
@ -508,19 +461,19 @@ void ntlm_generate_client_challenge(NTLM_CONTEXT* context)
* @param NTLM context
*/
void ntlm_generate_server_challenge(NTLM_CONTEXT* context)
void ntlm_generate_server_challenge(NTLM_CONTEXT *context)
{
if (memcmp(context->ServerChallenge, NTLM_NULL_BUFFER, 8) == 0)
RAND_bytes(context->ServerChallenge, 8);
}
/**
* Generate KeyExchangeKey (the 128-bit SessionBaseKey).\n
* Generate KeyExchangeKey (the 128-bit SessionBaseKey).
* @msdn{cc236710}
* @param NTLM context
*/
void ntlm_generate_key_exchange_key(NTLM_CONTEXT* context)
void ntlm_generate_key_exchange_key(NTLM_CONTEXT *context)
{
/* In NTLMv2, KeyExchangeKey is the 128-bit SessionBaseKey */
CopyMemory(context->KeyExchangeKey, context->SessionBaseKey, 16);
@ -531,7 +484,7 @@ void ntlm_generate_key_exchange_key(NTLM_CONTEXT* context)
* @param NTLM context
*/
void ntlm_generate_random_session_key(NTLM_CONTEXT* context)
void ntlm_generate_random_session_key(NTLM_CONTEXT *context)
{
RAND_bytes(context->RandomSessionKey, 16);
}
@ -541,7 +494,7 @@ void ntlm_generate_random_session_key(NTLM_CONTEXT* context)
* @param NTLM context
*/
void ntlm_generate_exported_session_key(NTLM_CONTEXT* context)
void ntlm_generate_exported_session_key(NTLM_CONTEXT *context)
{
CopyMemory(context->ExportedSessionKey, context->RandomSessionKey, 16);
}
@ -551,7 +504,7 @@ void ntlm_generate_exported_session_key(NTLM_CONTEXT* context)
* @param NTLM context
*/
void ntlm_encrypt_random_session_key(NTLM_CONTEXT* context)
void ntlm_encrypt_random_session_key(NTLM_CONTEXT *context)
{
/* In NTLMv2, EncryptedRandomSessionKey is the ExportedSessionKey RC4-encrypted with the KeyExchangeKey */
ntlm_rc4k(context->KeyExchangeKey, 16, context->RandomSessionKey, context->EncryptedRandomSessionKey);
@ -562,7 +515,7 @@ void ntlm_encrypt_random_session_key(NTLM_CONTEXT* context)
* @param NTLM context
*/
void ntlm_decrypt_random_session_key(NTLM_CONTEXT* context)
void ntlm_decrypt_random_session_key(NTLM_CONTEXT *context)
{
/* In NTLMv2, EncryptedRandomSessionKey is the ExportedSessionKey RC4-encrypted with the KeyExchangeKey */
@ -572,7 +525,6 @@ void ntlm_decrypt_random_session_key(NTLM_CONTEXT* context)
* else
* Set RandomSessionKey to KeyExchangeKey
*/
if (context->NegotiateKeyExchange)
ntlm_rc4k(context->KeyExchangeKey, 16, context->EncryptedRandomSessionKey, context->RandomSessionKey);
else
@ -580,21 +532,20 @@ void ntlm_decrypt_random_session_key(NTLM_CONTEXT* context)
}
/**
* Generate signing key.\n
* Generate signing key.
* @msdn{cc236711}
* @param exported_session_key ExportedSessionKey
* @param sign_magic Sign magic string
* @param signing_key Destination signing key
*/
int ntlm_generate_signing_key(BYTE* exported_session_key, PSecBuffer sign_magic, BYTE* signing_key)
int ntlm_generate_signing_key(BYTE *exported_session_key, PSecBuffer sign_magic, BYTE *signing_key)
{
int length;
BYTE* value;
BYTE *value;
MD5_CTX md5;
length = 16 + sign_magic->cbBuffer;
value = (BYTE*) malloc(length);
value = (BYTE *) malloc(length);
if (!value)
return -1;
@ -602,109 +553,94 @@ int ntlm_generate_signing_key(BYTE* exported_session_key, PSecBuffer sign_magic,
/* Concatenate ExportedSessionKey with sign magic */
CopyMemory(value, exported_session_key, 16);
CopyMemory(&value[16], sign_magic->pvBuffer, sign_magic->cbBuffer);
MD5_Init(&md5);
MD5_Update(&md5, value, length);
MD5_Final(signing_key, &md5);
free(value);
return 1;
}
/**
* Generate client signing key (ClientSigningKey).\n
* Generate client signing key (ClientSigningKey).
* @msdn{cc236711}
* @param NTLM context
*/
void ntlm_generate_client_signing_key(NTLM_CONTEXT* context)
void ntlm_generate_client_signing_key(NTLM_CONTEXT *context)
{
SecBuffer signMagic;
signMagic.pvBuffer = (void*) NTLM_CLIENT_SIGN_MAGIC;
signMagic.pvBuffer = (void *) NTLM_CLIENT_SIGN_MAGIC;
signMagic.cbBuffer = sizeof(NTLM_CLIENT_SIGN_MAGIC);
ntlm_generate_signing_key(context->ExportedSessionKey, &signMagic, context->ClientSigningKey);
}
/**
* Generate server signing key (ServerSigningKey).\n
* Generate server signing key (ServerSigningKey).
* @msdn{cc236711}
* @param NTLM context
*/
void ntlm_generate_server_signing_key(NTLM_CONTEXT* context)
void ntlm_generate_server_signing_key(NTLM_CONTEXT *context)
{
SecBuffer signMagic;
signMagic.pvBuffer = (void*) NTLM_SERVER_SIGN_MAGIC;
signMagic.pvBuffer = (void *) NTLM_SERVER_SIGN_MAGIC;
signMagic.cbBuffer = sizeof(NTLM_SERVER_SIGN_MAGIC);
ntlm_generate_signing_key(context->ExportedSessionKey, &signMagic, context->ServerSigningKey);
}
/**
* Generate sealing key.\n
* Generate sealing key.
* @msdn{cc236712}
* @param exported_session_key ExportedSessionKey
* @param seal_magic Seal magic string
* @param sealing_key Destination sealing key
*/
int ntlm_generate_sealing_key(BYTE* exported_session_key, PSecBuffer seal_magic, BYTE* sealing_key)
int ntlm_generate_sealing_key(BYTE *exported_session_key, PSecBuffer seal_magic, BYTE *sealing_key)
{
BYTE* p;
BYTE *p;
MD5_CTX md5;
SecBuffer buffer;
if (!sspi_SecBufferAlloc(&buffer, 16 + seal_magic->cbBuffer))
return -1;
p = (BYTE*) buffer.pvBuffer;
p = (BYTE *) buffer.pvBuffer;
/* Concatenate ExportedSessionKey with seal magic */
CopyMemory(p, exported_session_key, 16);
CopyMemory(&p[16], seal_magic->pvBuffer, seal_magic->cbBuffer);
MD5_Init(&md5);
MD5_Update(&md5, buffer.pvBuffer, buffer.cbBuffer);
MD5_Final(sealing_key, &md5);
sspi_SecBufferFree(&buffer);
return 1;
}
/**
* Generate client sealing key (ClientSealingKey).\n
* Generate client sealing key (ClientSealingKey).
* @msdn{cc236712}
* @param NTLM context
*/
void ntlm_generate_client_sealing_key(NTLM_CONTEXT* context)
void ntlm_generate_client_sealing_key(NTLM_CONTEXT *context)
{
SecBuffer sealMagic;
sealMagic.pvBuffer = (void*) NTLM_CLIENT_SEAL_MAGIC;
sealMagic.pvBuffer = (void *) NTLM_CLIENT_SEAL_MAGIC;
sealMagic.cbBuffer = sizeof(NTLM_CLIENT_SEAL_MAGIC);
ntlm_generate_signing_key(context->ExportedSessionKey, &sealMagic, context->ClientSealingKey);
}
/**
* Generate server sealing key (ServerSealingKey).\n
* Generate server sealing key (ServerSealingKey).
* @msdn{cc236712}
* @param NTLM context
*/
void ntlm_generate_server_sealing_key(NTLM_CONTEXT* context)
void ntlm_generate_server_sealing_key(NTLM_CONTEXT *context)
{
SecBuffer sealMagic;
sealMagic.pvBuffer = (void*) NTLM_SERVER_SEAL_MAGIC;
sealMagic.pvBuffer = (void *) NTLM_SERVER_SEAL_MAGIC;
sealMagic.cbBuffer = sizeof(NTLM_SERVER_SEAL_MAGIC);
ntlm_generate_signing_key(context->ExportedSessionKey, &sealMagic, context->ServerSealingKey);
}
@ -713,7 +649,7 @@ void ntlm_generate_server_sealing_key(NTLM_CONTEXT* context)
* @param NTLM context
*/
void ntlm_init_rc4_seal_states(NTLM_CONTEXT* context)
void ntlm_init_rc4_seal_states(NTLM_CONTEXT *context)
{
if (context->server)
{
@ -735,20 +671,18 @@ void ntlm_init_rc4_seal_states(NTLM_CONTEXT* context)
}
}
void ntlm_compute_message_integrity_check(NTLM_CONTEXT* context)
void ntlm_compute_message_integrity_check(NTLM_CONTEXT *context)
{
HMAC_CTX hmac_ctx;
/*
* Compute the HMAC-MD5 hash of ConcatenationOf(NEGOTIATE_MESSAGE,
* CHALLENGE_MESSAGE, AUTHENTICATE_MESSAGE) using the ExportedSessionKey
*/
HMAC_CTX_init(&hmac_ctx);
HMAC_Init_ex(&hmac_ctx, context->ExportedSessionKey, 16, EVP_md5(), NULL);
HMAC_Update(&hmac_ctx, (BYTE*) context->NegotiateMessage.pvBuffer, context->NegotiateMessage.cbBuffer);
HMAC_Update(&hmac_ctx, (BYTE*) context->ChallengeMessage.pvBuffer, context->ChallengeMessage.cbBuffer);
HMAC_Update(&hmac_ctx, (BYTE*) context->AuthenticateMessage.pvBuffer, context->AuthenticateMessage.cbBuffer);
HMAC_Update(&hmac_ctx, (BYTE *) context->NegotiateMessage.pvBuffer, context->NegotiateMessage.cbBuffer);
HMAC_Update(&hmac_ctx, (BYTE *) context->ChallengeMessage.pvBuffer, context->ChallengeMessage.cbBuffer);
HMAC_Update(&hmac_ctx, (BYTE *) context->AuthenticateMessage.pvBuffer, context->AuthenticateMessage.cbBuffer);
HMAC_Final(&hmac_ctx, context->MessageIntegrityCheck, NULL);
HMAC_CTX_cleanup(&hmac_ctx);
}

View File

@ -33,9 +33,12 @@
#include "ntlm_message.h"
#include "../log.h"
#define TAG "sspi.NTLM"
static const char NTLM_SIGNATURE[8] = { 'N', 'T', 'L', 'M', 'S', 'S', 'P', '\0' };
static const char* const NTLM_NEGOTIATE_STRINGS[] =
static const char *const NTLM_NEGOTIATE_STRINGS[] =
{
"NTLMSSP_NEGOTIATE_56",
"NTLMSSP_NEGOTIATE_KEY_EXCH",
@ -74,23 +77,20 @@ static const char* const NTLM_NEGOTIATE_STRINGS[] =
void ntlm_print_negotiate_flags(UINT32 flags)
{
int i;
const char* str;
fprintf(stderr, "negotiateFlags \"0x%08X\"{\n", flags);
const char *str;
WLog_INFO(TAG, "negotiateFlags \"0x%08X\"", flags);
for (i = 31; i >= 0; i--)
{
if ((flags >> i) & 1)
{
str = NTLM_NEGOTIATE_STRINGS[(31 - i)];
fprintf(stderr, "\t%s (%d),\n", str, (31 - i));
WLog_INFO(TAG, "\t%s (%d),", str, (31 - i));
}
}
fprintf(stderr, "}\n");
}
int ntlm_read_message_header(wStream* s, NTLM_MESSAGE_HEADER* header)
int ntlm_read_message_header(wStream *s, NTLM_MESSAGE_HEADER *header)
{
if (Stream_GetRemainingLength(s) < 12)
return -1;
@ -98,25 +98,25 @@ int ntlm_read_message_header(wStream* s, NTLM_MESSAGE_HEADER* header)
Stream_Read(s, header->Signature, 8);
Stream_Read_UINT32(s, header->MessageType);
if (strncmp((char*) header->Signature, NTLM_SIGNATURE, 8) != 0)
if (strncmp((char *) header->Signature, NTLM_SIGNATURE, 8) != 0)
return -1;
return 1;
}
void ntlm_write_message_header(wStream* s, NTLM_MESSAGE_HEADER* header)
void ntlm_write_message_header(wStream *s, NTLM_MESSAGE_HEADER *header)
{
Stream_Write(s, header->Signature, sizeof(NTLM_SIGNATURE));
Stream_Write_UINT32(s, header->MessageType);
}
void ntlm_populate_message_header(NTLM_MESSAGE_HEADER* header, UINT32 MessageType)
void ntlm_populate_message_header(NTLM_MESSAGE_HEADER *header, UINT32 MessageType)
{
CopyMemory(header->Signature, NTLM_SIGNATURE, sizeof(NTLM_SIGNATURE));
header->MessageType = MessageType;
}
int ntlm_read_message_fields(wStream* s, NTLM_MESSAGE_FIELDS* fields)
int ntlm_read_message_fields(wStream *s, NTLM_MESSAGE_FIELDS *fields)
{
if (Stream_GetRemainingLength(s) < 8)
return -1;
@ -124,11 +124,10 @@ int ntlm_read_message_fields(wStream* s, NTLM_MESSAGE_FIELDS* fields)
Stream_Read_UINT16(s, fields->Len); /* Len (2 bytes) */
Stream_Read_UINT16(s, fields->MaxLen); /* MaxLen (2 bytes) */
Stream_Read_UINT32(s, fields->BufferOffset); /* BufferOffset (4 bytes) */
return 1;
}
void ntlm_write_message_fields(wStream* s, NTLM_MESSAGE_FIELDS* fields)
void ntlm_write_message_fields(wStream *s, NTLM_MESSAGE_FIELDS *fields)
{
if (fields->MaxLen < 1)
fields->MaxLen = fields->Len;
@ -138,7 +137,7 @@ void ntlm_write_message_fields(wStream* s, NTLM_MESSAGE_FIELDS* fields)
Stream_Write_UINT32(s, fields->BufferOffset); /* BufferOffset (4 bytes) */
}
int ntlm_read_message_fields_buffer(wStream* s, NTLM_MESSAGE_FIELDS* fields)
int ntlm_read_message_fields_buffer(wStream *s, NTLM_MESSAGE_FIELDS *fields)
{
if (fields->Len > 0)
{
@ -157,7 +156,7 @@ int ntlm_read_message_fields_buffer(wStream* s, NTLM_MESSAGE_FIELDS* fields)
return 1;
}
void ntlm_write_message_fields_buffer(wStream* s, NTLM_MESSAGE_FIELDS* fields)
void ntlm_write_message_fields_buffer(wStream *s, NTLM_MESSAGE_FIELDS *fields)
{
if (fields->Len > 0)
{
@ -166,14 +165,13 @@ void ntlm_write_message_fields_buffer(wStream* s, NTLM_MESSAGE_FIELDS* fields)
}
}
void ntlm_free_message_fields_buffer(NTLM_MESSAGE_FIELDS* fields)
void ntlm_free_message_fields_buffer(NTLM_MESSAGE_FIELDS *fields)
{
if (fields)
{
if (fields->Buffer)
{
free(fields->Buffer);
fields->Len = 0;
fields->MaxLen = 0;
fields->Buffer = NULL;
@ -182,32 +180,28 @@ void ntlm_free_message_fields_buffer(NTLM_MESSAGE_FIELDS* fields)
}
}
void ntlm_print_message_fields(NTLM_MESSAGE_FIELDS* fields, const char* name)
void ntlm_print_message_fields(NTLM_MESSAGE_FIELDS *fields, const char *name)
{
fprintf(stderr, "%s (Len: %d MaxLen: %d BufferOffset: %d)\n",
name, fields->Len, fields->MaxLen, fields->BufferOffset);
WLog_DBG(TAG, "%s (Len: %d MaxLen: %d BufferOffset: %d)",
name, fields->Len, fields->MaxLen, fields->BufferOffset);
if (fields->Len > 0)
winpr_HexDump(fields->Buffer, fields->Len);
fprintf(stderr, "\n");
winpr_HexDump(TAG, WLOG_DEBUG, fields->Buffer, fields->Len);
}
SECURITY_STATUS ntlm_read_NegotiateMessage(NTLM_CONTEXT* context, PSecBuffer buffer)
SECURITY_STATUS ntlm_read_NegotiateMessage(NTLM_CONTEXT *context, PSecBuffer buffer)
{
wStream* s;
wStream *s;
int length;
NTLM_NEGOTIATE_MESSAGE* message;
NTLM_NEGOTIATE_MESSAGE *message;
message = &context->NEGOTIATE_MESSAGE;
ZeroMemory(message, sizeof(NTLM_NEGOTIATE_MESSAGE));
s = Stream_New((BYTE*) buffer->pvBuffer, buffer->cbBuffer);
s = Stream_New((BYTE *) buffer->pvBuffer, buffer->cbBuffer);
if (!s)
return SEC_E_INTERNAL_ERROR;
if (ntlm_read_message_header(s, (NTLM_MESSAGE_HEADER*) message) < 0)
if (ntlm_read_message_header(s, (NTLM_MESSAGE_HEADER *) message) < 0)
return SEC_E_INVALID_TOKEN;
if (message->MessageType != MESSAGE_TYPE_NEGOTIATE)
@ -250,40 +244,33 @@ SECURITY_STATUS ntlm_read_NegotiateMessage(NTLM_CONTEXT* context, PSecBuffer buf
CopyMemory(context->NegotiateMessage.pvBuffer, buffer->pvBuffer, buffer->cbBuffer);
context->NegotiateMessage.BufferType = buffer->BufferType;
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "NEGOTIATE_MESSAGE (length = %d)\n", (int) context->NegotiateMessage.cbBuffer);
WLog_DBG(TAG, "NEGOTIATE_MESSAGE (length = %d)", (int) context->NegotiateMessage.cbBuffer);
winpr_HexDump(context->NegotiateMessage.pvBuffer, context->NegotiateMessage.cbBuffer);
fprintf(stderr, "\n");
ntlm_print_negotiate_flags(message->NegotiateFlags);
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
ntlm_print_version_info(&(message->Version));
#endif
context->state = NTLM_STATE_CHALLENGE;
Stream_Free(s, FALSE);
return SEC_I_CONTINUE_NEEDED;
}
SECURITY_STATUS ntlm_write_NegotiateMessage(NTLM_CONTEXT* context, PSecBuffer buffer)
SECURITY_STATUS ntlm_write_NegotiateMessage(NTLM_CONTEXT *context, PSecBuffer buffer)
{
wStream* s;
wStream *s;
int length;
NTLM_NEGOTIATE_MESSAGE* message;
NTLM_NEGOTIATE_MESSAGE *message;
message = &context->NEGOTIATE_MESSAGE;
ZeroMemory(message, sizeof(NTLM_NEGOTIATE_MESSAGE));
s = Stream_New((BYTE*) buffer->pvBuffer, buffer->cbBuffer);
s = Stream_New((BYTE *) buffer->pvBuffer, buffer->cbBuffer);
if (!s)
return SEC_E_INTERNAL_ERROR;
ntlm_populate_message_header((NTLM_MESSAGE_HEADER*) message, MESSAGE_TYPE_NEGOTIATE);
ntlm_populate_message_header((NTLM_MESSAGE_HEADER *) message, MESSAGE_TYPE_NEGOTIATE);
if (context->NTLMv2)
{
@ -312,19 +299,13 @@ SECURITY_STATUS ntlm_write_NegotiateMessage(NTLM_CONTEXT* context, PSecBuffer bu
ntlm_get_version_info(&(message->Version));
context->NegotiateFlags = message->NegotiateFlags;
/* Message Header (12 bytes) */
ntlm_write_message_header(s, (NTLM_MESSAGE_HEADER*) message);
ntlm_write_message_header(s, (NTLM_MESSAGE_HEADER *) message);
Stream_Write_UINT32(s, message->NegotiateFlags); /* NegotiateFlags (4 bytes) */
/* only set if NTLMSSP_NEGOTIATE_DOMAIN_SUPPLIED is set */
/* DomainNameFields (8 bytes) */
ntlm_write_message_fields(s, &(message->DomainName));
/* only set if NTLMSSP_NEGOTIATE_WORKSTATION_SUPPLIED is set */
/* WorkstationFields (8 bytes) */
ntlm_write_message_fields(s, &(message->Workstation));
@ -339,45 +320,38 @@ SECURITY_STATUS ntlm_write_NegotiateMessage(NTLM_CONTEXT* context, PSecBuffer bu
CopyMemory(context->NegotiateMessage.pvBuffer, buffer->pvBuffer, buffer->cbBuffer);
context->NegotiateMessage.BufferType = buffer->BufferType;
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "NEGOTIATE_MESSAGE (length = %d)\n", length);
WLog_DBG(TAG, "NEGOTIATE_MESSAGE (length = %d)", length);
winpr_HexDump(Stream_Buffer(s), length);
fprintf(stderr, "\n");
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
ntlm_print_version_info(&(message->Version));
#endif
context->state = NTLM_STATE_CHALLENGE;
Stream_Free(s, FALSE);
return SEC_I_CONTINUE_NEEDED;
}
SECURITY_STATUS ntlm_read_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer buffer)
SECURITY_STATUS ntlm_read_ChallengeMessage(NTLM_CONTEXT *context, PSecBuffer buffer)
{
wStream* s;
wStream *s;
int length;
PBYTE StartOffset;
PBYTE PayloadOffset;
NTLM_AV_PAIR* AvTimestamp;
NTLM_CHALLENGE_MESSAGE* message;
NTLM_AV_PAIR *AvTimestamp;
NTLM_CHALLENGE_MESSAGE *message;
ntlm_generate_client_challenge(context);
message = &context->CHALLENGE_MESSAGE;
ZeroMemory(message, sizeof(NTLM_CHALLENGE_MESSAGE));
s = Stream_New((BYTE*) buffer->pvBuffer, buffer->cbBuffer);
s = Stream_New((BYTE *) buffer->pvBuffer, buffer->cbBuffer);
if (!s)
return SEC_E_INTERNAL_ERROR;
StartOffset = Stream_Pointer(s);
if (ntlm_read_message_header(s, (NTLM_MESSAGE_HEADER*) message) < 0)
if (ntlm_read_message_header(s, (NTLM_MESSAGE_HEADER *) message) < 0)
return SEC_E_INVALID_TOKEN;
if (message->MessageType != MESSAGE_TYPE_CHALLENGE)
@ -428,8 +402,7 @@ SECURITY_STATUS ntlm_read_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer buf
context->ChallengeTargetInfo.pvBuffer = message->TargetInfo.Buffer;
context->ChallengeTargetInfo.cbBuffer = message->TargetInfo.Len;
AvTimestamp = ntlm_av_pair_get((NTLM_AV_PAIR*) message->TargetInfo.Buffer, MsvAvTimestamp);
AvTimestamp = ntlm_av_pair_get((NTLM_AV_PAIR *) message->TargetInfo.Buffer, MsvAvTimestamp);
if (AvTimestamp)
{
@ -446,12 +419,9 @@ SECURITY_STATUS ntlm_read_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer buf
return SEC_E_INTERNAL_ERROR;
CopyMemory(context->ChallengeMessage.pvBuffer, StartOffset, length);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "CHALLENGE_MESSAGE (length = %d)\n", length);
WLog_DBG(TAG, "CHALLENGE_MESSAGE (length = %d)", length);
winpr_HexDump(context->ChallengeMessage.pvBuffer, context->ChallengeMessage.cbBuffer);
fprintf(stderr, "\n");
ntlm_print_negotiate_flags(context->NegotiateFlags);
if (context->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
@ -462,9 +432,10 @@ SECURITY_STATUS ntlm_read_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer buf
if (context->ChallengeTargetInfo.cbBuffer > 0)
{
fprintf(stderr, "ChallengeTargetInfo (%d):\n", (int) context->ChallengeTargetInfo.cbBuffer);
WLog_ERR(TAG, "ChallengeTargetInfo (%d):", (int) context->ChallengeTargetInfo.cbBuffer);
ntlm_print_av_pair_list(context->ChallengeTargetInfo.pvBuffer);
}
#endif
/* AV_PAIRs */
@ -487,111 +458,72 @@ SECURITY_STATUS ntlm_read_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer buf
return SEC_E_INTERNAL_ERROR;
ntlm_generate_key_exchange_key(context); /* KeyExchangeKey */
ntlm_generate_random_session_key(context); /* RandomSessionKey */
ntlm_generate_exported_session_key(context); /* ExportedSessionKey */
ntlm_encrypt_random_session_key(context); /* EncryptedRandomSessionKey */
/* Generate signing keys */
ntlm_generate_client_signing_key(context);
ntlm_generate_server_signing_key(context);
/* Generate sealing keys */
ntlm_generate_client_sealing_key(context);
ntlm_generate_server_sealing_key(context);
/* Initialize RC4 seal state using client sealing key */
ntlm_init_rc4_seal_states(context);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "ClientChallenge\n");
WLog_DBG(TAG, "ClientChallenge");
winpr_HexDump(context->ClientChallenge, 8);
fprintf(stderr, "\n");
fprintf(stderr, "ServerChallenge\n");
WLog_DBG(TAG, "ServerChallenge");
winpr_HexDump(context->ServerChallenge, 8);
fprintf(stderr, "\n");
fprintf(stderr, "SessionBaseKey\n");
WLog_DBG(TAG, "SessionBaseKey");
winpr_HexDump(context->SessionBaseKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "KeyExchangeKey\n");
WLog_DBG(TAG, "KeyExchangeKey");
winpr_HexDump(context->KeyExchangeKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ExportedSessionKey\n");
WLog_DBG(TAG, "ExportedSessionKey");
winpr_HexDump(context->ExportedSessionKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "RandomSessionKey\n");
WLog_DBG(TAG, "RandomSessionKey");
winpr_HexDump(context->RandomSessionKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ClientSigningKey\n");
WLog_DBG(TAG, "ClientSigningKey");
winpr_HexDump(context->ClientSigningKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ClientSealingKey\n");
WLog_DBG(TAG, "ClientSealingKey");
winpr_HexDump(context->ClientSealingKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ServerSigningKey\n");
WLog_DBG(TAG, "ServerSigningKey");
winpr_HexDump(context->ServerSigningKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ServerSealingKey\n");
WLog_DBG(TAG, "ServerSealingKey");
winpr_HexDump(context->ServerSealingKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "Timestamp\n");
WLog_DBG(TAG, "Timestamp");
winpr_HexDump(context->Timestamp, 8);
fprintf(stderr, "\n");
#endif
context->state = NTLM_STATE_AUTHENTICATE;
ntlm_free_message_fields_buffer(&(message->TargetName));
Stream_Free(s, FALSE);
return SEC_I_CONTINUE_NEEDED;
}
SECURITY_STATUS ntlm_write_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer buffer)
SECURITY_STATUS ntlm_write_ChallengeMessage(NTLM_CONTEXT *context, PSecBuffer buffer)
{
wStream* s;
wStream *s;
int length;
UINT32 PayloadOffset;
NTLM_CHALLENGE_MESSAGE* message;
NTLM_CHALLENGE_MESSAGE *message;
message = &context->CHALLENGE_MESSAGE;
ZeroMemory(message, sizeof(NTLM_CHALLENGE_MESSAGE));
s = Stream_New((BYTE*) buffer->pvBuffer, buffer->cbBuffer);
s = Stream_New((BYTE *) buffer->pvBuffer, buffer->cbBuffer);
if (!s)
return SEC_E_INTERNAL_ERROR;
ntlm_get_version_info(&(message->Version)); /* Version */
ntlm_generate_server_challenge(context); /* Server Challenge */
ntlm_generate_timestamp(context); /* Timestamp */
if (ntlm_construct_challenge_target_info(context) < 0) /* TargetInfo */
return SEC_E_INTERNAL_ERROR;
CopyMemory(message->ServerChallenge, context->ServerChallenge, 8); /* ServerChallenge */
message->NegotiateFlags = context->NegotiateFlags;
ntlm_populate_message_header((NTLM_MESSAGE_HEADER*) message, MESSAGE_TYPE_CHALLENGE);
ntlm_populate_message_header((NTLM_MESSAGE_HEADER *) message, MESSAGE_TYPE_CHALLENGE);
/* Message Header (12 bytes) */
ntlm_write_message_header(s, (NTLM_MESSAGE_HEADER*) message);
ntlm_write_message_header(s, (NTLM_MESSAGE_HEADER *) message);
if (message->NegotiateFlags & NTLMSSP_REQUEST_TARGET)
{
@ -614,15 +546,11 @@ SECURITY_STATUS ntlm_write_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer bu
message->TargetName.BufferOffset = PayloadOffset;
message->TargetInfo.BufferOffset = message->TargetName.BufferOffset + message->TargetName.Len;
/* TargetNameFields (8 bytes) */
ntlm_write_message_fields(s, &(message->TargetName));
Stream_Write_UINT32(s, message->NegotiateFlags); /* NegotiateFlags (4 bytes) */
Stream_Write(s, message->ServerChallenge, 8); /* ServerChallenge (8 bytes) */
Stream_Write(s, message->Reserved, 8); /* Reserved (8 bytes), should be ignored */
/* TargetInfoFields (8 bytes) */
ntlm_write_message_fields(s, &(message->TargetInfo));
@ -644,12 +572,9 @@ SECURITY_STATUS ntlm_write_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer bu
return SEC_E_INTERNAL_ERROR;
CopyMemory(context->ChallengeMessage.pvBuffer, Stream_Buffer(s), length);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "CHALLENGE_MESSAGE (length = %d)\n", length);
WLog_DBG(TAG, "CHALLENGE_MESSAGE (length = %d)", length);
winpr_HexDump(context->ChallengeMessage.pvBuffer, context->ChallengeMessage.cbBuffer);
fprintf(stderr, "\n");
ntlm_print_negotiate_flags(message->NegotiateFlags);
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
@ -658,36 +583,30 @@ SECURITY_STATUS ntlm_write_ChallengeMessage(NTLM_CONTEXT* context, PSecBuffer bu
ntlm_print_message_fields(&(message->TargetName), "TargetName");
ntlm_print_message_fields(&(message->TargetInfo), "TargetInfo");
#endif
context->state = NTLM_STATE_AUTHENTICATE;
Stream_Free(s, FALSE);
return SEC_I_CONTINUE_NEEDED;
}
SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer buffer)
SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT *context, PSecBuffer buffer)
{
wStream* s;
wStream *s;
int length;
UINT32 flags;
NTLM_AV_PAIR* AvFlags;
NTLM_AV_PAIR *AvFlags;
UINT32 PayloadBufferOffset;
NTLM_AUTHENTICATE_MESSAGE* message;
SSPI_CREDENTIALS* credentials = context->credentials;
NTLM_AUTHENTICATE_MESSAGE *message;
SSPI_CREDENTIALS *credentials = context->credentials;
flags = 0;
AvFlags = NULL;
message = &context->AUTHENTICATE_MESSAGE;
ZeroMemory(message, sizeof(NTLM_AUTHENTICATE_MESSAGE));
s = Stream_New((BYTE*) buffer->pvBuffer, buffer->cbBuffer);
s = Stream_New((BYTE *) buffer->pvBuffer, buffer->cbBuffer);
if (!s)
return SEC_E_INTERNAL_ERROR;
if (ntlm_read_message_header(s, (NTLM_MESSAGE_HEADER*) message) < 0)
if (ntlm_read_message_header(s, (NTLM_MESSAGE_HEADER *) message) < 0)
return SEC_E_INVALID_TOKEN;
if (message->MessageType != MESSAGE_TYPE_AUTHENTICATE)
@ -712,11 +631,10 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
return SEC_E_INVALID_TOKEN;
Stream_Read_UINT32(s, message->NegotiateFlags); /* NegotiateFlags (4 bytes) */
context->NegotiateKeyExchange = (message->NegotiateFlags & NTLMSSP_NEGOTIATE_KEY_EXCH) ? TRUE : FALSE;
if ((context->NegotiateKeyExchange && !message->EncryptedRandomSessionKey.Len) ||
(!context->NegotiateKeyExchange && message->EncryptedRandomSessionKey.Len))
(!context->NegotiateKeyExchange && message->EncryptedRandomSessionKey.Len))
return SEC_E_INVALID_TOKEN;
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
@ -744,7 +662,7 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
if (message->NtChallengeResponse.Len > 0)
{
wStream* snt = Stream_New(message->NtChallengeResponse.Buffer, message->NtChallengeResponse.Len);
wStream *snt = Stream_New(message->NtChallengeResponse.Buffer, message->NtChallengeResponse.Len);
if (!snt)
return SEC_E_INTERNAL_ERROR;
@ -753,20 +671,16 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
return SEC_E_INVALID_TOKEN;
Stream_Free(snt, FALSE);
context->NtChallengeResponse.pvBuffer = message->NtChallengeResponse.Buffer;
context->NtChallengeResponse.cbBuffer = message->NtChallengeResponse.Len;
sspi_SecBufferFree(&(context->ChallengeTargetInfo));
context->ChallengeTargetInfo.pvBuffer = (void*) context->NTLMv2Response.Challenge.AvPairs;
context->ChallengeTargetInfo.pvBuffer = (void *) context->NTLMv2Response.Challenge.AvPairs;
context->ChallengeTargetInfo.cbBuffer = message->NtChallengeResponse.Len - (28 + 16);
CopyMemory(context->ClientChallenge, context->NTLMv2Response.Challenge.ClientChallenge, 8);
AvFlags = ntlm_av_pair_get(context->NTLMv2Response.Challenge.AvPairs, MsvAvFlags);
if (AvFlags)
flags = *((UINT32*) ntlm_av_pair_get_value_pointer(AvFlags));
flags = *((UINT32 *) ntlm_av_pair_get_value_pointer(AvFlags));
}
if (ntlm_read_message_fields_buffer(s, &(message->EncryptedRandomSessionKey)) < 0) /* EncryptedRandomSessionKey */
@ -784,10 +698,9 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
if (!sspi_SecBufferAlloc(&context->AuthenticateMessage, length))
return SEC_E_INTERNAL_ERROR;
CopyMemory(context->AuthenticateMessage.pvBuffer, Stream_Buffer(s), length);
buffer->cbBuffer = length;
Stream_SetPosition(s, PayloadBufferOffset);
if (flags & MSV_AV_FLAGS_MESSAGE_INTEGRITY_CHECK)
@ -802,9 +715,8 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
}
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "AUTHENTICATE_MESSAGE (length = %d)\n", (int) context->AuthenticateMessage.cbBuffer);
WLog_DBG(TAG, "AUTHENTICATE_MESSAGE (length = %d)", (int) context->AuthenticateMessage.cbBuffer);
winpr_HexDump(context->AuthenticateMessage.pvBuffer, context->AuthenticateMessage.cbBuffer);
fprintf(stderr, "\n");
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
ntlm_print_version_info(&(message->Version));
@ -815,19 +727,19 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
ntlm_print_message_fields(&(message->LmChallengeResponse), "LmChallengeResponse");
ntlm_print_message_fields(&(message->NtChallengeResponse), "NtChallengeResponse");
ntlm_print_message_fields(&(message->EncryptedRandomSessionKey), "EncryptedRandomSessionKey");
ntlm_print_av_pair_list(context->NTLMv2Response.Challenge.AvPairs);
if (flags & MSV_AV_FLAGS_MESSAGE_INTEGRITY_CHECK)
{
fprintf(stderr, "MessageIntegrityCheck:\n");
WLog_DBG(TAG, "MessageIntegrityCheck:");
winpr_HexDump(message->MessageIntegrityCheck, 16);
}
#endif
if (message->UserName.Len > 0)
{
credentials->identity.User = (UINT16*) malloc(message->UserName.Len);
credentials->identity.User = (UINT16 *) malloc(message->UserName.Len);
if (!credentials->identity.User)
return SEC_E_INTERNAL_ERROR;
@ -838,7 +750,7 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
if (message->DomainName.Len > 0)
{
credentials->identity.Domain = (UINT16*) malloc(message->DomainName.Len);
credentials->identity.Domain = (UINT16 *) malloc(message->DomainName.Len);
if (!credentials->identity.Domain)
return SEC_E_INTERNAL_ERROR;
@ -848,11 +760,8 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
}
Stream_Free(s, FALSE);
/* Computations beyond this point require the NTLM hash of the password */
context->state = NTLM_STATE_COMPLETION;
return SEC_I_COMPLETE_NEEDED;
}
@ -863,18 +772,16 @@ SECURITY_STATUS ntlm_read_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
* @param buffer
*/
SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer buffer)
SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT *context, PSecBuffer buffer)
{
wStream* s;
wStream *s;
int length;
UINT32 PayloadBufferOffset;
NTLM_AUTHENTICATE_MESSAGE* message;
SSPI_CREDENTIALS* credentials = context->credentials;
NTLM_AUTHENTICATE_MESSAGE *message;
SSPI_CREDENTIALS *credentials = context->credentials;
message = &context->AUTHENTICATE_MESSAGE;
ZeroMemory(message, sizeof(NTLM_AUTHENTICATE_MESSAGE));
s = Stream_New((BYTE*) buffer->pvBuffer, buffer->cbBuffer);
s = Stream_New((BYTE *) buffer->pvBuffer, buffer->cbBuffer);
if (!s)
return SEC_E_INTERNAL_ERROR;
@ -913,24 +820,22 @@ SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_WORKSTATION_SUPPLIED)
{
message->Workstation.Len = context->Workstation.Length;
message->Workstation.Buffer = (BYTE*) context->Workstation.Buffer;
message->Workstation.Buffer = (BYTE *) context->Workstation.Buffer;
}
if (credentials->identity.DomainLength > 0)
{
message->NegotiateFlags |= NTLMSSP_NEGOTIATE_DOMAIN_SUPPLIED;
message->DomainName.Len = (UINT16) credentials->identity.DomainLength * 2;
message->DomainName.Buffer = (BYTE*) credentials->identity.Domain;
message->DomainName.Buffer = (BYTE *) credentials->identity.Domain;
}
message->UserName.Len = (UINT16) credentials->identity.UserLength * 2;
message->UserName.Buffer = (BYTE*) credentials->identity.User;
message->UserName.Buffer = (BYTE *) credentials->identity.User;
message->LmChallengeResponse.Len = (UINT16) context->LmChallengeResponse.cbBuffer;
message->LmChallengeResponse.Buffer = (BYTE*) context->LmChallengeResponse.pvBuffer;
message->LmChallengeResponse.Buffer = (BYTE *) context->LmChallengeResponse.pvBuffer;
message->NtChallengeResponse.Len = (UINT16) context->NtChallengeResponse.cbBuffer;
message->NtChallengeResponse.Buffer = (BYTE*) context->NtChallengeResponse.pvBuffer;
message->NtChallengeResponse.Buffer = (BYTE *) context->NtChallengeResponse.pvBuffer;
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_KEY_EXCH)
{
@ -952,23 +857,14 @@ SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
message->LmChallengeResponse.BufferOffset = message->Workstation.BufferOffset + message->Workstation.Len;
message->NtChallengeResponse.BufferOffset = message->LmChallengeResponse.BufferOffset + message->LmChallengeResponse.Len;
message->EncryptedRandomSessionKey.BufferOffset = message->NtChallengeResponse.BufferOffset + message->NtChallengeResponse.Len;
ntlm_populate_message_header((NTLM_MESSAGE_HEADER*) message, MESSAGE_TYPE_AUTHENTICATE);
ntlm_write_message_header(s, (NTLM_MESSAGE_HEADER*) message); /* Message Header (12 bytes) */
ntlm_populate_message_header((NTLM_MESSAGE_HEADER *) message, MESSAGE_TYPE_AUTHENTICATE);
ntlm_write_message_header(s, (NTLM_MESSAGE_HEADER *) message); /* Message Header (12 bytes) */
ntlm_write_message_fields(s, &(message->LmChallengeResponse)); /* LmChallengeResponseFields (8 bytes) */
ntlm_write_message_fields(s, &(message->NtChallengeResponse)); /* NtChallengeResponseFields (8 bytes) */
ntlm_write_message_fields(s, &(message->DomainName)); /* DomainNameFields (8 bytes) */
ntlm_write_message_fields(s, &(message->UserName)); /* UserNameFields (8 bytes) */
ntlm_write_message_fields(s, &(message->Workstation)); /* WorkstationFields (8 bytes) */
ntlm_write_message_fields(s, &(message->EncryptedRandomSessionKey)); /* EncryptedRandomSessionKeyFields (8 bytes) */
Stream_Write_UINT32(s, message->NegotiateFlags); /* NegotiateFlags (4 bytes) */
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
@ -989,14 +885,13 @@ SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
ntlm_write_message_fields_buffer(s, &(message->Workstation)); /* Workstation */
ntlm_write_message_fields_buffer(s, &(message->LmChallengeResponse)); /* LmChallengeResponse */
ntlm_write_message_fields_buffer(s, &(message->NtChallengeResponse)); /* NtChallengeResponse */
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_KEY_EXCH)
ntlm_write_message_fields_buffer(s, &(message->EncryptedRandomSessionKey)); /* EncryptedRandomSessionKey */
length = Stream_GetPosition(s);
if (!sspi_SecBufferAlloc(&context->AuthenticateMessage, length))
return SEC_E_INTERNAL_ERROR;
@ -1007,17 +902,14 @@ SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
{
/* Message Integrity Check */
ntlm_compute_message_integrity_check(context);
Stream_SetPosition(s, context->MessageIntegrityCheckOffset);
Stream_Write(s, context->MessageIntegrityCheck, 16);
Stream_SetPosition(s, length);
}
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "AUTHENTICATE_MESSAGE (length = %d)\n", length);
WLog_DBG(TAG, "AUTHENTICATE_MESSAGE (length = %d)", length);
winpr_HexDump(Stream_Buffer(s), length);
fprintf(stderr, "\n");
ntlm_print_negotiate_flags(message->NegotiateFlags);
if (message->NegotiateFlags & NTLMSSP_NEGOTIATE_VERSION)
@ -1025,7 +917,7 @@ SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
if (context->AuthenticateTargetInfo.cbBuffer > 0)
{
fprintf(stderr, "AuthenticateTargetInfo (%d):\n", (int) context->AuthenticateTargetInfo.cbBuffer);
WLog_ERR(TAG, "AuthenticateTargetInfo (%d):", (int) context->AuthenticateTargetInfo.cbBuffer);
ntlm_print_av_pair_list(context->AuthenticateTargetInfo.pvBuffer);
}
@ -1038,34 +930,30 @@ SECURITY_STATUS ntlm_write_AuthenticateMessage(NTLM_CONTEXT* context, PSecBuffer
if (context->UseMIC)
{
fprintf(stderr, "MessageIntegrityCheck (length = 16)\n");
WLog_DBG(TAG, "MessageIntegrityCheck (length = 16)");
winpr_HexDump(context->MessageIntegrityCheck, 16);
fprintf(stderr, "\n");
}
#endif
context->state = NTLM_STATE_FINAL;
Stream_Free(s, FALSE);
return SEC_I_COMPLETE_NEEDED;
}
SECURITY_STATUS ntlm_server_AuthenticateComplete(NTLM_CONTEXT* context)
SECURITY_STATUS ntlm_server_AuthenticateComplete(NTLM_CONTEXT *context)
{
UINT32 flags = 0;
NTLM_AV_PAIR* AvFlags = NULL;
NTLM_AUTHENTICATE_MESSAGE* message;
NTLM_AV_PAIR *AvFlags = NULL;
NTLM_AUTHENTICATE_MESSAGE *message;
if (context->state != NTLM_STATE_COMPLETION)
return SEC_E_OUT_OF_SEQUENCE;
message = &context->AUTHENTICATE_MESSAGE;
AvFlags = ntlm_av_pair_get(context->NTLMv2Response.Challenge.AvPairs, MsvAvFlags);
if (AvFlags)
flags = *((UINT32*) ntlm_av_pair_get_value_pointer(AvFlags));
flags = *((UINT32 *) ntlm_av_pair_get_value_pointer(AvFlags));
if (ntlm_compute_lm_v2_response(context) < 0) /* LmChallengeResponse */
return SEC_E_INTERNAL_ERROR;
@ -1075,31 +963,25 @@ SECURITY_STATUS ntlm_server_AuthenticateComplete(NTLM_CONTEXT* context)
/* KeyExchangeKey */
ntlm_generate_key_exchange_key(context);
/* EncryptedRandomSessionKey */
ntlm_decrypt_random_session_key(context);
/* ExportedSessionKey */
ntlm_generate_exported_session_key(context);
if (flags & MSV_AV_FLAGS_MESSAGE_INTEGRITY_CHECK)
{
ZeroMemory(&((PBYTE) context->AuthenticateMessage.pvBuffer)[context->MessageIntegrityCheckOffset], 16);
ntlm_compute_message_integrity_check(context);
CopyMemory(&((PBYTE) context->AuthenticateMessage.pvBuffer)[context->MessageIntegrityCheckOffset],
message->MessageIntegrityCheck, 16);
message->MessageIntegrityCheck, 16);
if (memcmp(context->MessageIntegrityCheck, message->MessageIntegrityCheck, 16) != 0)
{
fprintf(stderr, "Message Integrity Check (MIC) verification failed!\n");
fprintf(stderr, "Expected MIC:\n");
winpr_HexDump(context->MessageIntegrityCheck, 16);
fprintf(stderr, "Actual MIC:\n");
winpr_HexDump(message->MessageIntegrityCheck, 16);
WLog_ERR(TAG, "Message Integrity Check (MIC) verification failed!");
WLog_ERR(TAG, "Expected MIC:");
winpr_HexDump(TAG, WLOG_ERROR, context->MessageIntegrityCheck, 16);
WLog_ERR(TAG, "Actual MIC:");
winpr_HexDump(TAG, WLOG_ERROR, message->MessageIntegrityCheck, 16);
return SEC_E_MESSAGE_ALTERED;
}
}
@ -1107,68 +989,41 @@ SECURITY_STATUS ntlm_server_AuthenticateComplete(NTLM_CONTEXT* context)
/* Generate signing keys */
ntlm_generate_client_signing_key(context);
ntlm_generate_server_signing_key(context);
/* Generate sealing keys */
ntlm_generate_client_sealing_key(context);
ntlm_generate_server_sealing_key(context);
/* Initialize RC4 seal state */
ntlm_init_rc4_seal_states(context);
#ifdef WITH_DEBUG_NTLM
fprintf(stderr, "ClientChallenge\n");
WLog_DBG(TAG, "ClientChallenge");
winpr_HexDump(context->ClientChallenge, 8);
fprintf(stderr, "\n");
fprintf(stderr, "ServerChallenge\n");
WLog_DBG(TAG, "ServerChallenge");
winpr_HexDump(context->ServerChallenge, 8);
fprintf(stderr, "\n");
fprintf(stderr, "SessionBaseKey\n");
WLog_DBG(TAG, "SessionBaseKey");
winpr_HexDump(context->SessionBaseKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "KeyExchangeKey\n");
WLog_DBG(TAG, "KeyExchangeKey");
winpr_HexDump(context->KeyExchangeKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ExportedSessionKey\n");
WLog_DBG(TAG, "ExportedSessionKey");
winpr_HexDump(context->ExportedSessionKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "RandomSessionKey\n");
WLog_DBG(TAG, "RandomSessionKey");
winpr_HexDump(context->RandomSessionKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ClientSigningKey\n");
WLog_DBG(TAG, "ClientSigningKey");
winpr_HexDump(context->ClientSigningKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ClientSealingKey\n");
WLog_DBG(TAG, "ClientSealingKey");
winpr_HexDump(context->ClientSealingKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ServerSigningKey\n");
WLog_DBG(TAG, "ServerSigningKey");
winpr_HexDump(context->ServerSigningKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "ServerSealingKey\n");
WLog_DBG(TAG, "ServerSealingKey");
winpr_HexDump(context->ServerSealingKey, 16);
fprintf(stderr, "\n");
fprintf(stderr, "Timestamp\n");
WLog_DBG(TAG, "Timestamp");
winpr_HexDump(context->Timestamp, 8);
fprintf(stderr, "\n");
#endif
context->state = NTLM_STATE_FINAL;
ntlm_free_message_fields_buffer(&(message->DomainName));
ntlm_free_message_fields_buffer(&(message->UserName));
ntlm_free_message_fields_buffer(&(message->Workstation));
ntlm_free_message_fields_buffer(&(message->LmChallengeResponse));
ntlm_free_message_fields_buffer(&(message->NtChallengeResponse));
ntlm_free_message_fields_buffer(&(message->EncryptedRandomSessionKey));
return SEC_E_OK;
}

View File

@ -3,7 +3,7 @@
* Schannel Security Package (OpenSSL)
*
* Copyright 2012-2014 Marc-Andre Moreau <marcandre.moreau@gmail.com>
*
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
@ -28,22 +28,21 @@
#include "schannel_openssl.h"
char* openssl_get_ssl_error_string(int ssl_error)
#include "../../log.h"
#define TAG "sspi.schannel"
char *openssl_get_ssl_error_string(int ssl_error)
{
switch (ssl_error)
{
case SSL_ERROR_ZERO_RETURN:
return "SSL_ERROR_ZERO_RETURN";
case SSL_ERROR_WANT_READ:
return "SSL_ERROR_WANT_READ";
case SSL_ERROR_WANT_WRITE:
return "SSL_ERROR_WANT_WRITE";
case SSL_ERROR_SYSCALL:
return "SSL_ERROR_SYSCALL";
case SSL_ERROR_SSL:
ERR_print_errors_fp(stdout);
return "SSL_ERROR_SSL";
@ -52,16 +51,15 @@ char* openssl_get_ssl_error_string(int ssl_error)
return "SSL_ERROR_UNKNOWN";
}
int schannel_openssl_client_init(SCHANNEL_OPENSSL* context)
int schannel_openssl_client_init(SCHANNEL_OPENSSL *context)
{
int status;
long options = 0;
context->ctx = SSL_CTX_new(TLSv1_client_method());
if (!context->ctx)
{
fprintf(stderr, "SSL_CTX_new failed\n");
WLog_ERR(TAG, "SSL_CTX_new failed\n");
return -1;
}
@ -77,7 +75,6 @@ int schannel_openssl_client_init(SCHANNEL_OPENSSL* context)
#ifdef SSL_OP_NO_COMPRESSION
options |= SSL_OP_NO_COMPRESSION;
#endif
/**
* SSL_OP_TLS_BLOCK_PADDING_BUG:
*
@ -85,7 +82,6 @@ int schannel_openssl_client_init(SCHANNEL_OPENSSL* context)
* It absolutely needs to be disabled otherwise it won't work.
*/
options |= SSL_OP_TLS_BLOCK_PADDING_BUG;
/**
* SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS:
*
@ -93,14 +89,12 @@ int schannel_openssl_client_init(SCHANNEL_OPENSSL* context)
* support empty fragments. This needs to be disabled.
*/
options |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS;
SSL_CTX_set_options(context->ctx, options);
context->ssl = SSL_new(context->ctx);
if (!context->ssl)
{
fprintf(stderr, "SSL_new failed\n");
WLog_ERR(TAG, "SSL_new failed\n");
return -1;
}
@ -108,43 +102,37 @@ int schannel_openssl_client_init(SCHANNEL_OPENSSL* context)
if (!context->bioRead)
{
fprintf(stderr, "BIO_new failed\n");
WLog_ERR(TAG, "BIO_new failed\n");
return -1;
}
status = BIO_set_write_buf_size(context->bioRead, SCHANNEL_CB_MAX_TOKEN);
context->bioWrite = BIO_new(BIO_s_mem());
if (!context->bioWrite)
{
fprintf(stderr, "BIO_new failed\n");
WLog_ERR(TAG, "BIO_new failed\n");
return -1;
}
status = BIO_set_write_buf_size(context->bioWrite, SCHANNEL_CB_MAX_TOKEN);
status = BIO_make_bio_pair(context->bioRead, context->bioWrite);
SSL_set_bio(context->ssl, context->bioRead, context->bioWrite);
context->ReadBuffer = (BYTE*) malloc(SCHANNEL_CB_MAX_TOKEN);
context->WriteBuffer = (BYTE*) malloc(SCHANNEL_CB_MAX_TOKEN);
context->ReadBuffer = (BYTE *) malloc(SCHANNEL_CB_MAX_TOKEN);
context->WriteBuffer = (BYTE *) malloc(SCHANNEL_CB_MAX_TOKEN);
return 0;
}
int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
int schannel_openssl_server_init(SCHANNEL_OPENSSL *context)
{
int status;
long options = 0;
//context->ctx = SSL_CTX_new(SSLv23_server_method());
context->ctx = SSL_CTX_new(TLSv1_server_method());
if (!context->ctx)
{
fprintf(stderr, "SSL_CTX_new failed\n");
WLog_ERR(TAG, "SSL_CTX_new failed\n");
return -1;
}
@ -155,7 +143,6 @@ int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
* SSLv3 is used by, eg. Microsoft RDC for Mac OS X.
*/
options |= SSL_OP_NO_SSLv2;
/**
* SSL_OP_NO_COMPRESSION:
*
@ -168,7 +155,6 @@ int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
#ifdef SSL_OP_NO_COMPRESSION
options |= SSL_OP_NO_COMPRESSION;
#endif
/**
* SSL_OP_TLS_BLOCK_PADDING_BUG:
*
@ -176,7 +162,6 @@ int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
* It absolutely needs to be disabled otherwise it won't work.
*/
options |= SSL_OP_TLS_BLOCK_PADDING_BUG;
/**
* SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS:
*
@ -184,12 +169,11 @@ int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
* support empty fragments. This needs to be disabled.
*/
options |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS;
SSL_CTX_set_options(context->ctx, options);
if (SSL_CTX_use_RSAPrivateKey_file(context->ctx, "/tmp/localhost.key", SSL_FILETYPE_PEM) <= 0)
{
fprintf(stderr, "SSL_CTX_use_RSAPrivateKey_file failed\n");
WLog_ERR(TAG, "SSL_CTX_use_RSAPrivateKey_file failed\n");
return -1;
}
@ -197,13 +181,13 @@ int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
if (!context->ssl)
{
fprintf(stderr, "SSL_new failed\n");
WLog_ERR(TAG, "SSL_new failed\n");
return -1;
}
if (SSL_use_certificate_file(context->ssl, "/tmp/localhost.crt", SSL_FILETYPE_PEM) <= 0)
{
fprintf(stderr, "SSL_use_certificate_file failed\n");
WLog_ERR(TAG, "SSL_use_certificate_file failed\n");
return -1;
}
@ -211,33 +195,28 @@ int schannel_openssl_server_init(SCHANNEL_OPENSSL* context)
if (!context->bioRead)
{
fprintf(stderr, "BIO_new failed\n");
WLog_ERR(TAG, "BIO_new failed\n");
return -1;
}
status = BIO_set_write_buf_size(context->bioRead, SCHANNEL_CB_MAX_TOKEN);
context->bioWrite = BIO_new(BIO_s_mem());
if (!context->bioWrite)
{
fprintf(stderr, "BIO_new failed\n");
WLog_ERR(TAG, "BIO_new failed\n");
return -1;
}
status = BIO_set_write_buf_size(context->bioWrite, SCHANNEL_CB_MAX_TOKEN);
status = BIO_make_bio_pair(context->bioRead, context->bioWrite);
SSL_set_bio(context->ssl, context->bioRead, context->bioWrite);
context->ReadBuffer = (BYTE*) malloc(SCHANNEL_CB_MAX_TOKEN);
context->WriteBuffer = (BYTE*) malloc(SCHANNEL_CB_MAX_TOKEN);
context->ReadBuffer = (BYTE *) malloc(SCHANNEL_CB_MAX_TOKEN);
context->WriteBuffer = (BYTE *) malloc(SCHANNEL_CB_MAX_TOKEN);
return 0;
}
SECURITY_STATUS schannel_openssl_client_process_tokens(SCHANNEL_OPENSSL* context, PSecBufferDesc pInput, PSecBufferDesc pOutput)
SECURITY_STATUS schannel_openssl_client_process_tokens(SCHANNEL_OPENSSL *context, PSecBufferDesc pInput, PSecBufferDesc pOutput)
{
int status;
int ssl_error;
@ -263,7 +242,7 @@ SECURITY_STATUS schannel_openssl_client_process_tokens(SCHANNEL_OPENSSL* context
if (status < 0)
{
ssl_error = SSL_get_error(context->ssl, status);
fprintf(stderr, "SSL_connect error: %s\n", openssl_get_ssl_error_string(ssl_error));
WLog_ERR(TAG, "SSL_connect error: %s\n", openssl_get_ssl_error_string(ssl_error));
}
if (status == 1)
@ -286,7 +265,6 @@ SECURITY_STATUS schannel_openssl_client_process_tokens(SCHANNEL_OPENSSL* context
CopyMemory(pBuffer->pvBuffer, context->ReadBuffer, status);
pBuffer->cbBuffer = status;
return (context->connected) ? SEC_E_OK : SEC_I_CONTINUE_NEEDED;
}
else
@ -299,7 +277,7 @@ SECURITY_STATUS schannel_openssl_client_process_tokens(SCHANNEL_OPENSSL* context
return SEC_E_OK;
}
SECURITY_STATUS schannel_openssl_server_process_tokens(SCHANNEL_OPENSSL* context, PSecBufferDesc pInput, PSecBufferDesc pOutput)
SECURITY_STATUS schannel_openssl_server_process_tokens(SCHANNEL_OPENSSL *context, PSecBufferDesc pInput, PSecBufferDesc pOutput)
{
int status;
int ssl_error;
@ -316,13 +294,12 @@ SECURITY_STATUS schannel_openssl_server_process_tokens(SCHANNEL_OPENSSL* context
return SEC_E_INVALID_TOKEN;
status = BIO_write(context->bioRead, pBuffer->pvBuffer, pBuffer->cbBuffer);
status = SSL_accept(context->ssl);
if (status < 0)
{
ssl_error = SSL_get_error(context->ssl, status);
fprintf(stderr, "SSL_accept error: %s\n", openssl_get_ssl_error_string(ssl_error));
WLog_ERR(TAG, "SSL_accept error: %s\n", openssl_get_ssl_error_string(ssl_error));
}
if (status == 1)
@ -345,7 +322,6 @@ SECURITY_STATUS schannel_openssl_server_process_tokens(SCHANNEL_OPENSSL* context
CopyMemory(pBuffer->pvBuffer, context->ReadBuffer, status);
pBuffer->cbBuffer = status;
return (context->connected) ? SEC_E_OK : SEC_I_CONTINUE_NEEDED;
}
else
@ -358,7 +334,7 @@ SECURITY_STATUS schannel_openssl_server_process_tokens(SCHANNEL_OPENSSL* context
return SEC_E_OK;
}
SECURITY_STATUS schannel_openssl_encrypt_message(SCHANNEL_OPENSSL* context, PSecBufferDesc pMessage)
SECURITY_STATUS schannel_openssl_encrypt_message(SCHANNEL_OPENSSL *context, PSecBufferDesc pMessage)
{
int status;
int length;
@ -367,7 +343,6 @@ SECURITY_STATUS schannel_openssl_encrypt_message(SCHANNEL_OPENSSL* context, PSec
PSecBuffer pStreamBodyBuffer;
PSecBuffer pStreamHeaderBuffer;
PSecBuffer pStreamTrailerBuffer;
pStreamHeaderBuffer = sspi_FindSecBuffer(pMessage, SECBUFFER_STREAM_HEADER);
pStreamBodyBuffer = sspi_FindSecBuffer(pMessage, SECBUFFER_DATA);
pStreamTrailerBuffer = sspi_FindSecBuffer(pMessage, SECBUFFER_STREAM_TRAILER);
@ -380,7 +355,7 @@ SECURITY_STATUS schannel_openssl_encrypt_message(SCHANNEL_OPENSSL* context, PSec
if (status < 0)
{
ssl_error = SSL_get_error(context->ssl, status);
fprintf(stderr, "SSL_write: %s\n", openssl_get_ssl_error_string(ssl_error));
WLog_ERR(TAG, "SSL_write: %s\n", openssl_get_ssl_error_string(ssl_error));
}
status = BIO_read(context->bioWrite, context->ReadBuffer, SCHANNEL_CB_MAX_TOKEN);
@ -391,12 +366,10 @@ SECURITY_STATUS schannel_openssl_encrypt_message(SCHANNEL_OPENSSL* context, PSec
length = (pStreamHeaderBuffer->cbBuffer > (unsigned long) status) ? status : pStreamHeaderBuffer->cbBuffer;
CopyMemory(pStreamHeaderBuffer->pvBuffer, &context->ReadBuffer[offset], length);
status -= length;
offset += length;
length = (pStreamBodyBuffer->cbBuffer > (unsigned long) status) ? status : pStreamBodyBuffer->cbBuffer;
CopyMemory(pStreamBodyBuffer->pvBuffer, &context->ReadBuffer[offset], length);
status -= length;
offset += length;
length = (pStreamTrailerBuffer->cbBuffer > (unsigned long) status) ? status : pStreamTrailerBuffer->cbBuffer;
CopyMemory(pStreamTrailerBuffer->pvBuffer, &context->ReadBuffer[offset], length);
@ -406,53 +379,45 @@ SECURITY_STATUS schannel_openssl_encrypt_message(SCHANNEL_OPENSSL* context, PSec
return SEC_E_OK;
}
SECURITY_STATUS schannel_openssl_decrypt_message(SCHANNEL_OPENSSL* context, PSecBufferDesc pMessage)
SECURITY_STATUS schannel_openssl_decrypt_message(SCHANNEL_OPENSSL *context, PSecBufferDesc pMessage)
{
int status;
int length;
BYTE* buffer;
BYTE *buffer;
int ssl_error;
PSecBuffer pBuffer;
pBuffer = sspi_FindSecBuffer(pMessage, SECBUFFER_DATA);
if (!pBuffer)
return SEC_E_INVALID_TOKEN;
status = BIO_write(context->bioRead, pBuffer->pvBuffer, pBuffer->cbBuffer);
status = SSL_read(context->ssl, pBuffer->pvBuffer, pBuffer->cbBuffer);
if (status < 0)
{
ssl_error = SSL_get_error(context->ssl, status);
fprintf(stderr, "SSL_read: %s\n", openssl_get_ssl_error_string(ssl_error));
WLog_ERR(TAG, "SSL_read: %s\n", openssl_get_ssl_error_string(ssl_error));
}
length = status;
buffer = pBuffer->pvBuffer;
pMessage->pBuffers[0].BufferType = SECBUFFER_STREAM_HEADER;
pMessage->pBuffers[0].cbBuffer = 5;
pMessage->pBuffers[1].BufferType = SECBUFFER_DATA;
pMessage->pBuffers[1].pvBuffer = buffer;
pMessage->pBuffers[1].cbBuffer = length;
pMessage->pBuffers[2].BufferType = SECBUFFER_STREAM_TRAILER;
pMessage->pBuffers[2].cbBuffer = 36;
pMessage->pBuffers[3].BufferType = SECBUFFER_EMPTY;
pMessage->pBuffers[3].cbBuffer = 0;
return SEC_E_OK;
}
SCHANNEL_OPENSSL* schannel_openssl_new()
SCHANNEL_OPENSSL *schannel_openssl_new()
{
SCHANNEL_OPENSSL* context;
context = (SCHANNEL_OPENSSL*) malloc(sizeof(SCHANNEL_OPENSSL));
SCHANNEL_OPENSSL *context;
context = (SCHANNEL_OPENSSL *) malloc(sizeof(SCHANNEL_OPENSSL));
if (context != NULL)
{
@ -464,13 +429,12 @@ SCHANNEL_OPENSSL* schannel_openssl_new()
return context;
}
void schannel_openssl_free(SCHANNEL_OPENSSL* context)
void schannel_openssl_free(SCHANNEL_OPENSSL *context)
{
if (context)
{
free(context->ReadBuffer);
free(context->WriteBuffer);
free(context);
}
}

View File

@ -2,6 +2,7 @@
#include <winpr/crt.h>
#include <winpr/sspi.h>
#include <winpr/print.h>
#include <winpr/wlog.h>
static BYTE TEST_NTLM_TIMESTAMP[8] = { 0x33, 0x57, 0xbd, 0xb1, 0x07, 0x8b, 0xcf, 0x01 };
@ -57,19 +58,19 @@ static BYTE TEST_NTLM_AUTHENTICATE[] =
#define TEST_SSPI_INTERFACE SSPI_INTERFACE_WINPR
static const char* TEST_NTLM_USER = "Username";
static const char* TEST_NTLM_DOMAIN = "Domain";
static const char* TEST_NTLM_PASSWORD = "P4ss123!";
static const char *TEST_NTLM_USER = "Username";
static const char *TEST_NTLM_DOMAIN = "Domain";
static const char *TEST_NTLM_PASSWORD = "P4ss123!";
//static const char* TEST_NTLM_HASH_STRING = "d5922a65c4d5c082ca444af1be0001db";
static const BYTE TEST_NTLM_HASH[16] =
{ 0xd5, 0x92, 0x2a, 0x65, 0xc4, 0xd5, 0xc0, 0x82, 0xca, 0x44, 0x4a, 0xf1, 0xbe, 0x00, 0x01, 0xdb };
{ 0xd5, 0x92, 0x2a, 0x65, 0xc4, 0xd5, 0xc0, 0x82, 0xca, 0x44, 0x4a, 0xf1, 0xbe, 0x00, 0x01, 0xdb };
//static const char* TEST_NTLM_HASH_V2_STRING = "4c7f706f7dde05a9d1a0f4e7ffe3bfb8";
static const BYTE TEST_NTLM_V2_HASH[16] =
{ 0x4c, 0x7f, 0x70, 0x6f, 0x7d, 0xde, 0x05, 0xa9, 0xd1, 0xa0, 0xf4, 0xe7, 0xff, 0xe3, 0xbf, 0xb8 };
{ 0x4c, 0x7f, 0x70, 0x6f, 0x7d, 0xde, 0x05, 0xa9, 0xd1, 0xa0, 0xf4, 0xe7, 0xff, 0xe3, 0xbf, 0xb8 };
//#define NTLM_PACKAGE_NAME NEGOSSP_NAME
#define NTLM_PACKAGE_NAME NTLMSP_NAME
@ -91,22 +92,18 @@ struct _TEST_NTLM_CLIENT
SecBufferDesc outputBufferDesc;
CredHandle credentials;
BOOL confidentiality;
SecPkgInfo* pPackageInfo;
SecurityFunctionTable* table;
SecPkgInfo *pPackageInfo;
SecurityFunctionTable *table;
SEC_WINNT_AUTH_IDENTITY identity;
};
typedef struct _TEST_NTLM_CLIENT TEST_NTLM_CLIENT;
int test_ntlm_client_init(TEST_NTLM_CLIENT* ntlm, const char* user, const char* domain, const char* password)
int test_ntlm_client_init(TEST_NTLM_CLIENT *ntlm, const char *user, const char *domain, const char *password)
{
SECURITY_STATUS status;
SecInvalidateHandle(&(ntlm->context));
ntlm->table = InitSecurityInterfaceEx(TEST_SSPI_INTERFACE);
sspi_SetAuthIdentity(&(ntlm->identity), user, domain, password);
status = ntlm->table->QuerySecurityPackageInfo(NTLM_PACKAGE_NAME, &ntlm->pPackageInfo);
if (status != SEC_E_OK)
@ -117,9 +114,8 @@ int test_ntlm_client_init(TEST_NTLM_CLIENT* ntlm, const char* user, const char*
}
ntlm->cbMaxToken = ntlm->pPackageInfo->cbMaxToken;
status = ntlm->table->AcquireCredentialsHandle(NULL, NTLM_PACKAGE_NAME,
SECPKG_CRED_OUTBOUND, NULL, &ntlm->identity, NULL, NULL, &ntlm->credentials, &ntlm->expiration);
SECPKG_CRED_OUTBOUND, NULL, &ntlm->identity, NULL, NULL, &ntlm->credentials, &ntlm->expiration);
if (status != SEC_E_OK)
{
@ -132,23 +128,19 @@ int test_ntlm_client_init(TEST_NTLM_CLIENT* ntlm, const char* user, const char*
ntlm->haveInputBuffer = FALSE;
ZeroMemory(&ntlm->inputBuffer, sizeof(SecBuffer));
ZeroMemory(&ntlm->outputBuffer, sizeof(SecBuffer));
ntlm->fContextReq = 0;
#if 0
/* HTTP authentication flags */
ntlm->fContextReq |= ISC_REQ_CONFIDENTIALITY;
#endif
/* NLA authentication flags */
ntlm->fContextReq |= ISC_REQ_MUTUAL_AUTH;
ntlm->fContextReq |= ISC_REQ_CONFIDENTIALITY;
ntlm->fContextReq |= ISC_REQ_USE_SESSION_KEY;
return 1;
}
void test_ntlm_client_uninit(TEST_NTLM_CLIENT* ntlm)
void test_ntlm_client_uninit(TEST_NTLM_CLIENT *ntlm)
{
if (!ntlm)
return;
@ -210,7 +202,7 @@ void test_ntlm_client_uninit(TEST_NTLM_CLIENT* ntlm)
* --------------
*/
int test_ntlm_client_authenticate(TEST_NTLM_CLIENT* ntlm)
int test_ntlm_client_authenticate(TEST_NTLM_CLIENT *ntlm)
{
SECURITY_STATUS status;
@ -245,12 +237,12 @@ int test_ntlm_client_authenticate(TEST_NTLM_CLIENT* ntlm)
}
status = ntlm->table->InitializeSecurityContext(&ntlm->credentials,
(ntlm->haveContext) ? &ntlm->context : NULL,
(ntlm->ServicePrincipalName) ? ntlm->ServicePrincipalName : NULL,
ntlm->fContextReq, 0, SECURITY_NATIVE_DREP,
(ntlm->haveInputBuffer) ? &ntlm->inputBufferDesc : NULL,
0, &ntlm->context, &ntlm->outputBufferDesc,
&ntlm->pfContextAttr, &ntlm->expiration);
(ntlm->haveContext) ? &ntlm->context : NULL,
(ntlm->ServicePrincipalName) ? ntlm->ServicePrincipalName : NULL,
ntlm->fContextReq, 0, SECURITY_NATIVE_DREP,
(ntlm->haveInputBuffer) ? &ntlm->inputBufferDesc : NULL,
0, &ntlm->context, &ntlm->outputBufferDesc,
&ntlm->pfContextAttr, &ntlm->expiration);
if ((status == SEC_I_COMPLETE_AND_CONTINUE) || (status == SEC_I_COMPLETE_NEEDED))
{
@ -270,15 +262,13 @@ int test_ntlm_client_authenticate(TEST_NTLM_CLIENT* ntlm)
ntlm->haveInputBuffer = TRUE;
ntlm->haveContext = TRUE;
return (status == SEC_I_CONTINUE_NEEDED) ? 1 : 0;
}
TEST_NTLM_CLIENT* test_ntlm_client_new()
TEST_NTLM_CLIENT *test_ntlm_client_new()
{
TEST_NTLM_CLIENT* ntlm;
ntlm = (TEST_NTLM_CLIENT*) calloc(1, sizeof(TEST_NTLM_CLIENT));
TEST_NTLM_CLIENT *ntlm;
ntlm = (TEST_NTLM_CLIENT *) calloc(1, sizeof(TEST_NTLM_CLIENT));
if (!ntlm)
return NULL;
@ -286,13 +276,12 @@ TEST_NTLM_CLIENT* test_ntlm_client_new()
return ntlm;
}
void test_ntlm_client_free(TEST_NTLM_CLIENT* ntlm)
void test_ntlm_client_free(TEST_NTLM_CLIENT *ntlm)
{
if (!ntlm)
return;
test_ntlm_client_uninit(ntlm);
free(ntlm);
}
@ -314,22 +303,18 @@ struct _TEST_NTLM_SERVER
SecBufferDesc outputBufferDesc;
CredHandle credentials;
BOOL confidentiality;
SecPkgInfo* pPackageInfo;
SecurityFunctionTable* table;
SecPkgInfo *pPackageInfo;
SecurityFunctionTable *table;
SEC_WINNT_AUTH_IDENTITY identity;
};
typedef struct _TEST_NTLM_SERVER TEST_NTLM_SERVER;
int test_ntlm_server_init(TEST_NTLM_SERVER* ntlm)
int test_ntlm_server_init(TEST_NTLM_SERVER *ntlm)
{
SECURITY_STATUS status;
ntlm->UseNtlmV2Hash = TRUE;
SecInvalidateHandle(&(ntlm->context));
ntlm->table = InitSecurityInterfaceEx(TEST_SSPI_INTERFACE);
status = ntlm->table->QuerySecurityPackageInfo(NTLM_PACKAGE_NAME, &ntlm->pPackageInfo);
if (status != SEC_E_OK)
@ -340,10 +325,9 @@ int test_ntlm_server_init(TEST_NTLM_SERVER* ntlm)
}
ntlm->cbMaxToken = ntlm->pPackageInfo->cbMaxToken;
status = ntlm->table->AcquireCredentialsHandle(NULL, NTLM_PACKAGE_NAME,
SECPKG_CRED_INBOUND, NULL, NULL, NULL, NULL,
&ntlm->credentials, &ntlm->expiration);
SECPKG_CRED_INBOUND, NULL, NULL, NULL, NULL,
&ntlm->credentials, &ntlm->expiration);
if (status != SEC_E_OK)
{
@ -356,9 +340,7 @@ int test_ntlm_server_init(TEST_NTLM_SERVER* ntlm)
ntlm->haveInputBuffer = FALSE;
ZeroMemory(&ntlm->inputBuffer, sizeof(SecBuffer));
ZeroMemory(&ntlm->outputBuffer, sizeof(SecBuffer));
ntlm->fContextReq = 0;
/* NLA authentication flags */
ntlm->fContextReq |= ASC_REQ_MUTUAL_AUTH;
ntlm->fContextReq |= ASC_REQ_CONFIDENTIALITY;
@ -367,11 +349,10 @@ int test_ntlm_server_init(TEST_NTLM_SERVER* ntlm)
ntlm->fContextReq |= ASC_REQ_REPLAY_DETECT;
ntlm->fContextReq |= ASC_REQ_SEQUENCE_DETECT;
ntlm->fContextReq |= ASC_REQ_EXTENDED_ERROR;
return 1;
}
void test_ntlm_server_uninit(TEST_NTLM_SERVER* ntlm)
void test_ntlm_server_uninit(TEST_NTLM_SERVER *ntlm)
{
if (!ntlm)
return;
@ -395,35 +376,30 @@ void test_ntlm_server_uninit(TEST_NTLM_SERVER* ntlm)
}
}
int test_ntlm_server_authenticate(TEST_NTLM_SERVER* ntlm)
int test_ntlm_server_authenticate(TEST_NTLM_SERVER *ntlm)
{
SECURITY_STATUS status;
ntlm->inputBufferDesc.ulVersion = SECBUFFER_VERSION;
ntlm->inputBufferDesc.cBuffers = 1;
ntlm->inputBufferDesc.pBuffers = ntlm->inputBuffer;
ntlm->inputBuffer[0].BufferType = SECBUFFER_TOKEN;
ntlm->outputBufferDesc.ulVersion = SECBUFFER_VERSION;
ntlm->outputBufferDesc.cBuffers = 1;
ntlm->outputBufferDesc.pBuffers = &ntlm->outputBuffer[0];
ntlm->outputBuffer[0].BufferType = SECBUFFER_TOKEN;
ntlm->outputBuffer[0].cbBuffer = ntlm->cbMaxToken;
ntlm->outputBuffer[0].pvBuffer = malloc(ntlm->outputBuffer[0].cbBuffer);
status = ntlm->table->AcceptSecurityContext(&ntlm->credentials,
ntlm->haveContext? &ntlm->context: NULL,
&ntlm->inputBufferDesc, ntlm->fContextReq, SECURITY_NATIVE_DREP, &ntlm->context,
&ntlm->outputBufferDesc, &ntlm->pfContextAttr, &ntlm->expiration);
ntlm->haveContext? &ntlm->context: NULL,
&ntlm->inputBufferDesc, ntlm->fContextReq, SECURITY_NATIVE_DREP, &ntlm->context,
&ntlm->outputBufferDesc, &ntlm->pfContextAttr, &ntlm->expiration);
if ((status == SEC_I_COMPLETE_AND_CONTINUE) || (status == SEC_I_COMPLETE_NEEDED))
{
SecPkgContext_AuthIdentity AuthIdentity;
SecPkgContext_AuthNtlmHash AuthNtlmHash;
ZeroMemory(&AuthIdentity, sizeof(SecPkgContext_AuthIdentity));
ZeroMemory(&AuthNtlmHash, sizeof(SecPkgContext_AuthNtlmHash));
status = ntlm->table->QueryContextAttributes(&ntlm->context, SECPKG_ATTR_AUTH_IDENTITY, &AuthIdentity);
if (status == SEC_E_OK)
@ -442,7 +418,7 @@ int test_ntlm_server_authenticate(TEST_NTLM_SERVER* ntlm)
}
status = ntlm->table->SetContextAttributes(&ntlm->context,
SECPKG_ATTR_AUTH_NTLM_HASH, &AuthNtlmHash, sizeof(SecPkgContext_AuthNtlmHash));
SECPKG_ATTR_AUTH_NTLM_HASH, &AuthNtlmHash, sizeof(SecPkgContext_AuthNtlmHash));
}
}
@ -463,15 +439,13 @@ int test_ntlm_server_authenticate(TEST_NTLM_SERVER* ntlm)
}
ntlm->haveContext = TRUE;
return (status == SEC_I_CONTINUE_NEEDED) ? 1 : 0;
}
TEST_NTLM_SERVER* test_ntlm_server_new()
TEST_NTLM_SERVER *test_ntlm_server_new()
{
TEST_NTLM_SERVER* ntlm;
ntlm = (TEST_NTLM_SERVER*) calloc(1, sizeof(TEST_NTLM_SERVER));
TEST_NTLM_SERVER *ntlm;
ntlm = (TEST_NTLM_SERVER *) calloc(1, sizeof(TEST_NTLM_SERVER));
if (!ntlm)
return NULL;
@ -479,30 +453,26 @@ TEST_NTLM_SERVER* test_ntlm_server_new()
return ntlm;
}
void test_ntlm_server_free(TEST_NTLM_SERVER* ntlm)
void test_ntlm_server_free(TEST_NTLM_SERVER *ntlm)
{
if (!ntlm)
return;
test_ntlm_server_uninit(ntlm);
free(ntlm);
}
int TestNTLM(int argc, char* argv[])
int TestNTLM(int argc, char *argv[])
{
int status;
PSecBuffer pSecBuffer;
TEST_NTLM_CLIENT* client;
TEST_NTLM_SERVER* server;
TEST_NTLM_CLIENT *client;
TEST_NTLM_SERVER *server;
BOOL DynamicTest = TRUE;
/**
* Client Initialization
*/
client = test_ntlm_client_new();
status = test_ntlm_client_init(client, TEST_NTLM_USER, TEST_NTLM_DOMAIN, TEST_NTLM_PASSWORD);
if (status < 0)
@ -514,9 +484,7 @@ int TestNTLM(int argc, char* argv[])
/**
* Server Initialization
*/
server = test_ntlm_server_new();
status = test_ntlm_server_init(server);
if (status < 0)
@ -528,7 +496,6 @@ int TestNTLM(int argc, char* argv[])
/**
* Client -> Negotiate Message
*/
status = test_ntlm_client_authenticate(client);
if (status < 0)
@ -542,24 +509,19 @@ int TestNTLM(int argc, char* argv[])
SecPkgContext_AuthNtlmTimestamp AuthNtlmTimestamp;
SecPkgContext_AuthNtlmClientChallenge AuthNtlmClientChallenge;
SecPkgContext_AuthNtlmServerChallenge AuthNtlmServerChallenge;
CopyMemory(AuthNtlmTimestamp.Timestamp, TEST_NTLM_TIMESTAMP, 8);
AuthNtlmTimestamp.ChallengeOrResponse = TRUE;
client->table->SetContextAttributes(&client->context, SECPKG_ATTR_AUTH_NTLM_TIMESTAMP,
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
AuthNtlmTimestamp.ChallengeOrResponse = FALSE;
client->table->SetContextAttributes(&client->context, SECPKG_ATTR_AUTH_NTLM_TIMESTAMP,
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
CopyMemory(AuthNtlmClientChallenge.ClientChallenge, TEST_NTLM_CLIENT_CHALLENGE, 8);
CopyMemory(AuthNtlmServerChallenge.ServerChallenge, TEST_NTLM_SERVER_CHALLENGE, 8);
client->table->SetContextAttributes(&client->context, SECPKG_ATTR_AUTH_NTLM_CLIENT_CHALLENGE,
&AuthNtlmClientChallenge, sizeof(SecPkgContext_AuthNtlmClientChallenge));
&AuthNtlmClientChallenge, sizeof(SecPkgContext_AuthNtlmClientChallenge));
client->table->SetContextAttributes(&client->context, SECPKG_ATTR_AUTH_NTLM_SERVER_CHALLENGE,
&AuthNtlmServerChallenge, sizeof(SecPkgContext_AuthNtlmServerChallenge));
&AuthNtlmServerChallenge, sizeof(SecPkgContext_AuthNtlmServerChallenge));
}
pSecBuffer = &(client->outputBuffer[0]);
@ -567,23 +529,20 @@ int TestNTLM(int argc, char* argv[])
if (!DynamicTest)
{
pSecBuffer->cbBuffer = sizeof(TEST_NTLM_NEGOTIATE) -1;
pSecBuffer->pvBuffer = (void*) malloc(pSecBuffer->cbBuffer);
pSecBuffer->pvBuffer = (void *) malloc(pSecBuffer->cbBuffer);
CopyMemory(pSecBuffer->pvBuffer, TEST_NTLM_NEGOTIATE, pSecBuffer->cbBuffer);
}
fprintf(stderr, "NTLM_NEGOTIATE (length = %d):\n", pSecBuffer->cbBuffer);
winpr_HexDump((BYTE*) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
winpr_HexDump("sspi.test", WLOG_DEBUG, (BYTE *) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
/**
* Server <- Negotiate Message
* Server -> Challenge Message
*/
server->haveInputBuffer = TRUE;
server->inputBuffer[0].BufferType = SECBUFFER_TOKEN;
server->inputBuffer[0].pvBuffer = pSecBuffer->pvBuffer;
server->inputBuffer[0].cbBuffer = pSecBuffer->cbBuffer;
status = test_ntlm_server_authenticate(server);
if (status < 0)
@ -597,24 +556,19 @@ int TestNTLM(int argc, char* argv[])
SecPkgContext_AuthNtlmTimestamp AuthNtlmTimestamp;
SecPkgContext_AuthNtlmClientChallenge AuthNtlmClientChallenge;
SecPkgContext_AuthNtlmServerChallenge AuthNtlmServerChallenge;
CopyMemory(AuthNtlmTimestamp.Timestamp, TEST_NTLM_TIMESTAMP, 8);
AuthNtlmTimestamp.ChallengeOrResponse = TRUE;
client->table->SetContextAttributes(&server->context, SECPKG_ATTR_AUTH_NTLM_TIMESTAMP,
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
AuthNtlmTimestamp.ChallengeOrResponse = FALSE;
client->table->SetContextAttributes(&server->context, SECPKG_ATTR_AUTH_NTLM_TIMESTAMP,
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
&AuthNtlmTimestamp, sizeof(SecPkgContext_AuthNtlmTimestamp));
CopyMemory(AuthNtlmClientChallenge.ClientChallenge, TEST_NTLM_CLIENT_CHALLENGE, 8);
CopyMemory(AuthNtlmServerChallenge.ServerChallenge, TEST_NTLM_SERVER_CHALLENGE, 8);
server->table->SetContextAttributes(&server->context, SECPKG_ATTR_AUTH_NTLM_CLIENT_CHALLENGE,
&AuthNtlmClientChallenge, sizeof(SecPkgContext_AuthNtlmClientChallenge));
&AuthNtlmClientChallenge, sizeof(SecPkgContext_AuthNtlmClientChallenge));
server->table->SetContextAttributes(&server->context, SECPKG_ATTR_AUTH_NTLM_SERVER_CHALLENGE,
&AuthNtlmServerChallenge, sizeof(SecPkgContext_AuthNtlmServerChallenge));
&AuthNtlmServerChallenge, sizeof(SecPkgContext_AuthNtlmServerChallenge));
}
pSecBuffer = &(server->outputBuffer[0]);
@ -622,32 +576,26 @@ int TestNTLM(int argc, char* argv[])
if (!DynamicTest)
{
SecPkgContext_AuthNtlmMessage AuthNtlmMessage;
pSecBuffer->cbBuffer = sizeof(TEST_NTLM_CHALLENGE) -1;
pSecBuffer->pvBuffer = (void*) malloc(pSecBuffer->cbBuffer);
pSecBuffer->pvBuffer = (void *) malloc(pSecBuffer->cbBuffer);
CopyMemory(pSecBuffer->pvBuffer, TEST_NTLM_CHALLENGE, pSecBuffer->cbBuffer);
AuthNtlmMessage.type = 2;
AuthNtlmMessage.length = pSecBuffer->cbBuffer;
AuthNtlmMessage.buffer = (BYTE*) pSecBuffer->pvBuffer;
AuthNtlmMessage.buffer = (BYTE *) pSecBuffer->pvBuffer;
server->table->SetContextAttributes(&server->context, SECPKG_ATTR_AUTH_NTLM_MESSAGE,
&AuthNtlmMessage, sizeof(SecPkgContext_AuthNtlmMessage));
&AuthNtlmMessage, sizeof(SecPkgContext_AuthNtlmMessage));
}
fprintf(stderr, "NTLM_CHALLENGE (length = %d):\n", pSecBuffer->cbBuffer);
winpr_HexDump((BYTE*) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
winpr_HexDump("sspi.test", WLOG_DEBUG, (BYTE *) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
/**
* Client <- Challenge Message
* Client -> Authenticate Message
*/
client->haveInputBuffer = TRUE;
client->inputBuffer[0].BufferType = SECBUFFER_TOKEN;
client->inputBuffer[0].pvBuffer = pSecBuffer->pvBuffer;
client->inputBuffer[0].cbBuffer = pSecBuffer->cbBuffer;
status = test_ntlm_client_authenticate(client);
if (status < 0)
@ -657,25 +605,23 @@ int TestNTLM(int argc, char* argv[])
}
pSecBuffer = &(client->outputBuffer[0]);
if (!DynamicTest)
{
pSecBuffer->cbBuffer = sizeof(TEST_NTLM_AUTHENTICATE) -1;
pSecBuffer->pvBuffer = (void*) malloc(pSecBuffer->cbBuffer);
pSecBuffer->pvBuffer = (void *) malloc(pSecBuffer->cbBuffer);
CopyMemory(pSecBuffer->pvBuffer, TEST_NTLM_AUTHENTICATE, pSecBuffer->cbBuffer);
}
fprintf(stderr, "NTLM_AUTHENTICATE (length = %d):\n", pSecBuffer->cbBuffer);
winpr_HexDump((BYTE*) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
winpr_HexDump("sspi.test", WLOG_DEBUG, (BYTE *) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
/**
* Server <- Authenticate Message
*/
server->haveInputBuffer = TRUE;
server->inputBuffer[0].BufferType = SECBUFFER_TOKEN;
server->inputBuffer[0].pvBuffer = pSecBuffer->pvBuffer;
server->inputBuffer[0].cbBuffer = pSecBuffer->cbBuffer;
status = test_ntlm_server_authenticate(server);
if (status < 0)
@ -687,9 +633,7 @@ int TestNTLM(int argc, char* argv[])
/**
* Cleanup & Termination
*/
test_ntlm_client_free(client);
test_ntlm_server_free(server);
return 0;
}

View File

@ -9,6 +9,7 @@
#include <winpr/synch.h>
#include <winpr/thread.h>
#include <winpr/crypto.h>
#include <winpr/wlog.h>
#include <winpr/schannel.h>
BOOL g_ClientWait = FALSE;
@ -21,193 +22,193 @@ HANDLE g_ServerWritePipe = NULL;
BYTE test_localhost_crt[1029] =
{
0x2D,0x2D,0x2D,0x2D,0x2D,0x42,0x45,0x47,0x49,0x4E,0x20,0x43,0x45,0x52,0x54,
0x49,0x46,0x49,0x43,0x41,0x54,0x45,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A,0x4D,0x49,
0x49,0x43,0x79,0x6A,0x43,0x43,0x41,0x62,0x4B,0x67,0x41,0x77,0x49,0x42,0x41,
0x67,0x49,0x45,0x63,0x61,0x64,0x63,0x72,0x7A,0x41,0x4E,0x42,0x67,0x6B,0x71,
0x68,0x6B,0x69,0x47,0x39,0x77,0x30,0x42,0x41,0x51,0x55,0x46,0x41,0x44,0x41,
0x55,0x4D,0x52,0x49,0x77,0x45,0x41,0x59,0x44,0x56,0x51,0x51,0x44,0x45,0x77,
0x6C,0x73,0x0A,0x62,0x32,0x4E,0x68,0x62,0x47,0x68,0x76,0x63,0x33,0x51,0x77,
0x48,0x68,0x63,0x4E,0x4D,0x54,0x4D,0x78,0x4D,0x44,0x45,0x78,0x4D,0x44,0x59,
0x78,0x4E,0x7A,0x55,0x31,0x57,0x68,0x63,0x4E,0x4D,0x54,0x51,0x78,0x4D,0x44,
0x45,0x78,0x4D,0x44,0x59,0x78,0x4E,0x7A,0x55,0x31,0x57,0x6A,0x41,0x55,0x4D,
0x52,0x49,0x77,0x45,0x41,0x59,0x44,0x0A,0x56,0x51,0x51,0x44,0x45,0x77,0x6C,
0x73,0x62,0x32,0x4E,0x68,0x62,0x47,0x68,0x76,0x63,0x33,0x51,0x77,0x67,0x67,
0x45,0x69,0x4D,0x41,0x30,0x47,0x43,0x53,0x71,0x47,0x53,0x49,0x62,0x33,0x44,
0x51,0x45,0x42,0x41,0x51,0x55,0x41,0x41,0x34,0x49,0x42,0x44,0x77,0x41,0x77,
0x67,0x67,0x45,0x4B,0x41,0x6F,0x49,0x42,0x41,0x51,0x43,0x33,0x0A,0x65,0x6E,
0x33,0x68,0x5A,0x4F,0x53,0x33,0x6B,0x51,0x2F,0x55,0x54,0x30,0x53,0x45,0x6C,
0x30,0x48,0x6E,0x50,0x79,0x64,0x48,0x75,0x35,0x39,0x61,0x69,0x71,0x64,0x73,
0x64,0x53,0x55,0x74,0x6E,0x43,0x41,0x37,0x46,0x66,0x74,0x30,0x4F,0x36,0x51,
0x79,0x68,0x49,0x71,0x58,0x7A,0x30,0x47,0x32,0x53,0x76,0x77,0x4C,0x54,0x62,
0x79,0x68,0x0A,0x59,0x54,0x68,0x31,0x36,0x78,0x31,0x72,0x45,0x48,0x68,0x31,
0x57,0x47,0x5A,0x6D,0x36,0x77,0x64,0x2B,0x4B,0x76,0x38,0x6B,0x31,0x6B,0x2F,
0x36,0x6F,0x41,0x2F,0x4F,0x51,0x76,0x65,0x61,0x38,0x6B,0x63,0x45,0x64,0x53,
0x72,0x54,0x64,0x75,0x71,0x4A,0x33,0x65,0x66,0x74,0x48,0x4A,0x4A,0x6E,0x43,
0x4B,0x30,0x41,0x62,0x68,0x34,0x39,0x0A,0x41,0x47,0x41,0x50,0x39,0x79,0x58,
0x77,0x77,0x59,0x41,0x6A,0x51,0x49,0x52,0x6E,0x38,0x2B,0x4F,0x63,0x63,0x48,
0x74,0x6F,0x4E,0x75,0x75,0x79,0x52,0x63,0x6B,0x49,0x50,0x71,0x75,0x70,0x78,
0x79,0x31,0x4A,0x5A,0x4B,0x39,0x64,0x76,0x76,0x62,0x34,0x79,0x53,0x6B,0x49,
0x75,0x7A,0x62,0x79,0x50,0x6F,0x54,0x41,0x79,0x61,0x55,0x2B,0x0A,0x51,0x72,
0x70,0x34,0x78,0x67,0x64,0x4B,0x46,0x54,0x70,0x6B,0x50,0x46,0x34,0x33,0x6A,
0x32,0x4D,0x6D,0x5A,0x72,0x46,0x63,0x42,0x76,0x79,0x6A,0x69,0x35,0x6A,0x4F,
0x37,0x74,0x66,0x6F,0x56,0x61,0x6B,0x59,0x47,0x53,0x2F,0x4C,0x63,0x78,0x77,
0x47,0x2B,0x77,0x51,0x77,0x63,0x4F,0x43,0x54,0x42,0x45,0x78,0x2F,0x7A,0x31,
0x53,0x30,0x0A,0x37,0x49,0x2F,0x6A,0x62,0x44,0x79,0x53,0x4E,0x68,0x44,0x35,
0x63,0x61,0x63,0x54,0x75,0x4E,0x36,0x50,0x68,0x33,0x58,0x30,0x71,0x70,0x47,
0x73,0x37,0x79,0x50,0x6B,0x4E,0x79,0x69,0x4A,0x33,0x57,0x52,0x69,0x6C,0x35,
0x75,0x57,0x73,0x4B,0x65,0x79,0x63,0x64,0x71,0x42,0x4E,0x72,0x34,0x75,0x32,
0x62,0x49,0x52,0x6E,0x63,0x54,0x51,0x0A,0x46,0x72,0x68,0x73,0x58,0x39,0x69,
0x77,0x37,0x35,0x76,0x75,0x53,0x64,0x35,0x46,0x39,0x37,0x56,0x70,0x41,0x67,
0x4D,0x42,0x41,0x41,0x47,0x6A,0x4A,0x44,0x41,0x69,0x4D,0x42,0x4D,0x47,0x41,
0x31,0x55,0x64,0x4A,0x51,0x51,0x4D,0x4D,0x41,0x6F,0x47,0x43,0x43,0x73,0x47,
0x41,0x51,0x55,0x46,0x42,0x77,0x4D,0x42,0x4D,0x41,0x73,0x47,0x0A,0x41,0x31,
0x55,0x64,0x44,0x77,0x51,0x45,0x41,0x77,0x49,0x45,0x4D,0x44,0x41,0x4E,0x42,
0x67,0x6B,0x71,0x68,0x6B,0x69,0x47,0x39,0x77,0x30,0x42,0x41,0x51,0x55,0x46,
0x41,0x41,0x4F,0x43,0x41,0x51,0x45,0x41,0x49,0x51,0x66,0x75,0x2F,0x77,0x39,
0x45,0x34,0x4C,0x6F,0x67,0x30,0x71,0x35,0x4B,0x53,0x38,0x71,0x46,0x78,0x62,
0x36,0x6F,0x0A,0x36,0x31,0x62,0x35,0x37,0x6F,0x6D,0x6E,0x46,0x59,0x52,0x34,
0x47,0x43,0x67,0x33,0x6F,0x6A,0x4F,0x4C,0x54,0x66,0x38,0x7A,0x6A,0x4D,0x43,
0x52,0x6D,0x75,0x59,0x32,0x76,0x30,0x4E,0x34,0x78,0x66,0x68,0x69,0x35,0x4B,
0x69,0x59,0x67,0x64,0x76,0x4E,0x4C,0x4F,0x33,0x52,0x42,0x6D,0x4E,0x50,0x76,
0x59,0x58,0x50,0x52,0x46,0x41,0x76,0x0A,0x66,0x61,0x76,0x66,0x57,0x75,0x6C,
0x44,0x31,0x64,0x50,0x36,0x31,0x69,0x35,0x62,0x36,0x59,0x66,0x56,0x6C,0x78,
0x62,0x31,0x61,0x57,0x46,0x37,0x4C,0x5A,0x44,0x32,0x55,0x6E,0x63,0x41,0x6A,
0x37,0x4E,0x38,0x78,0x38,0x2B,0x36,0x58,0x6B,0x30,0x6B,0x63,0x70,0x58,0x46,
0x38,0x6C,0x77,0x58,0x48,0x55,0x57,0x57,0x55,0x6D,0x73,0x2B,0x0A,0x4B,0x56,
0x44,0x34,0x34,0x39,0x68,0x6F,0x4D,0x2B,0x77,0x4E,0x4A,0x49,0x61,0x4F,0x52,
0x39,0x4C,0x46,0x2B,0x6B,0x6F,0x32,0x32,0x37,0x7A,0x74,0x37,0x54,0x41,0x47,
0x64,0x56,0x35,0x4A,0x75,0x7A,0x71,0x38,0x32,0x2F,0x6B,0x75,0x73,0x6F,0x65,
0x32,0x69,0x75,0x57,0x77,0x54,0x65,0x42,0x6C,0x53,0x5A,0x6E,0x6B,0x42,0x38,
0x63,0x64,0x0A,0x77,0x4D,0x30,0x5A,0x42,0x58,0x6D,0x34,0x35,0x48,0x38,0x6F,
0x79,0x75,0x36,0x4A,0x71,0x59,0x71,0x45,0x6D,0x75,0x4A,0x51,0x64,0x67,0x79,
0x52,0x2B,0x63,0x53,0x53,0x41,0x7A,0x2B,0x4F,0x32,0x6D,0x61,0x62,0x68,0x50,
0x5A,0x65,0x49,0x76,0x78,0x65,0x67,0x6A,0x6A,0x61,0x5A,0x61,0x46,0x4F,0x71,
0x74,0x73,0x2B,0x64,0x33,0x72,0x39,0x0A,0x79,0x71,0x4A,0x78,0x67,0x75,0x39,
0x43,0x38,0x39,0x5A,0x69,0x33,0x39,0x57,0x34,0x38,0x46,0x66,0x46,0x63,0x49,
0x58,0x4A,0x4F,0x6B,0x39,0x43,0x4E,0x46,0x41,0x2F,0x69,0x70,0x54,0x57,0x6A,
0x74,0x74,0x4E,0x2F,0x6B,0x4F,0x6B,0x5A,0x42,0x70,0x6F,0x6A,0x2F,0x32,0x6A,
0x4E,0x45,0x62,0x4F,0x59,0x7A,0x7A,0x6E,0x4B,0x77,0x3D,0x3D,0x0A,0x2D,0x2D,
0x2D,0x2D,0x2D,0x45,0x4E,0x44,0x20,0x43,0x45,0x52,0x54,0x49,0x46,0x49,0x43,
0x41,0x54,0x45,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A
0x2D,0x2D,0x2D,0x2D,0x2D,0x42,0x45,0x47,0x49,0x4E,0x20,0x43,0x45,0x52,0x54,
0x49,0x46,0x49,0x43,0x41,0x54,0x45,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A,0x4D,0x49,
0x49,0x43,0x79,0x6A,0x43,0x43,0x41,0x62,0x4B,0x67,0x41,0x77,0x49,0x42,0x41,
0x67,0x49,0x45,0x63,0x61,0x64,0x63,0x72,0x7A,0x41,0x4E,0x42,0x67,0x6B,0x71,
0x68,0x6B,0x69,0x47,0x39,0x77,0x30,0x42,0x41,0x51,0x55,0x46,0x41,0x44,0x41,
0x55,0x4D,0x52,0x49,0x77,0x45,0x41,0x59,0x44,0x56,0x51,0x51,0x44,0x45,0x77,
0x6C,0x73,0x0A,0x62,0x32,0x4E,0x68,0x62,0x47,0x68,0x76,0x63,0x33,0x51,0x77,
0x48,0x68,0x63,0x4E,0x4D,0x54,0x4D,0x78,0x4D,0x44,0x45,0x78,0x4D,0x44,0x59,
0x78,0x4E,0x7A,0x55,0x31,0x57,0x68,0x63,0x4E,0x4D,0x54,0x51,0x78,0x4D,0x44,
0x45,0x78,0x4D,0x44,0x59,0x78,0x4E,0x7A,0x55,0x31,0x57,0x6A,0x41,0x55,0x4D,
0x52,0x49,0x77,0x45,0x41,0x59,0x44,0x0A,0x56,0x51,0x51,0x44,0x45,0x77,0x6C,
0x73,0x62,0x32,0x4E,0x68,0x62,0x47,0x68,0x76,0x63,0x33,0x51,0x77,0x67,0x67,
0x45,0x69,0x4D,0x41,0x30,0x47,0x43,0x53,0x71,0x47,0x53,0x49,0x62,0x33,0x44,
0x51,0x45,0x42,0x41,0x51,0x55,0x41,0x41,0x34,0x49,0x42,0x44,0x77,0x41,0x77,
0x67,0x67,0x45,0x4B,0x41,0x6F,0x49,0x42,0x41,0x51,0x43,0x33,0x0A,0x65,0x6E,
0x33,0x68,0x5A,0x4F,0x53,0x33,0x6B,0x51,0x2F,0x55,0x54,0x30,0x53,0x45,0x6C,
0x30,0x48,0x6E,0x50,0x79,0x64,0x48,0x75,0x35,0x39,0x61,0x69,0x71,0x64,0x73,
0x64,0x53,0x55,0x74,0x6E,0x43,0x41,0x37,0x46,0x66,0x74,0x30,0x4F,0x36,0x51,
0x79,0x68,0x49,0x71,0x58,0x7A,0x30,0x47,0x32,0x53,0x76,0x77,0x4C,0x54,0x62,
0x79,0x68,0x0A,0x59,0x54,0x68,0x31,0x36,0x78,0x31,0x72,0x45,0x48,0x68,0x31,
0x57,0x47,0x5A,0x6D,0x36,0x77,0x64,0x2B,0x4B,0x76,0x38,0x6B,0x31,0x6B,0x2F,
0x36,0x6F,0x41,0x2F,0x4F,0x51,0x76,0x65,0x61,0x38,0x6B,0x63,0x45,0x64,0x53,
0x72,0x54,0x64,0x75,0x71,0x4A,0x33,0x65,0x66,0x74,0x48,0x4A,0x4A,0x6E,0x43,
0x4B,0x30,0x41,0x62,0x68,0x34,0x39,0x0A,0x41,0x47,0x41,0x50,0x39,0x79,0x58,
0x77,0x77,0x59,0x41,0x6A,0x51,0x49,0x52,0x6E,0x38,0x2B,0x4F,0x63,0x63,0x48,
0x74,0x6F,0x4E,0x75,0x75,0x79,0x52,0x63,0x6B,0x49,0x50,0x71,0x75,0x70,0x78,
0x79,0x31,0x4A,0x5A,0x4B,0x39,0x64,0x76,0x76,0x62,0x34,0x79,0x53,0x6B,0x49,
0x75,0x7A,0x62,0x79,0x50,0x6F,0x54,0x41,0x79,0x61,0x55,0x2B,0x0A,0x51,0x72,
0x70,0x34,0x78,0x67,0x64,0x4B,0x46,0x54,0x70,0x6B,0x50,0x46,0x34,0x33,0x6A,
0x32,0x4D,0x6D,0x5A,0x72,0x46,0x63,0x42,0x76,0x79,0x6A,0x69,0x35,0x6A,0x4F,
0x37,0x74,0x66,0x6F,0x56,0x61,0x6B,0x59,0x47,0x53,0x2F,0x4C,0x63,0x78,0x77,
0x47,0x2B,0x77,0x51,0x77,0x63,0x4F,0x43,0x54,0x42,0x45,0x78,0x2F,0x7A,0x31,
0x53,0x30,0x0A,0x37,0x49,0x2F,0x6A,0x62,0x44,0x79,0x53,0x4E,0x68,0x44,0x35,
0x63,0x61,0x63,0x54,0x75,0x4E,0x36,0x50,0x68,0x33,0x58,0x30,0x71,0x70,0x47,
0x73,0x37,0x79,0x50,0x6B,0x4E,0x79,0x69,0x4A,0x33,0x57,0x52,0x69,0x6C,0x35,
0x75,0x57,0x73,0x4B,0x65,0x79,0x63,0x64,0x71,0x42,0x4E,0x72,0x34,0x75,0x32,
0x62,0x49,0x52,0x6E,0x63,0x54,0x51,0x0A,0x46,0x72,0x68,0x73,0x58,0x39,0x69,
0x77,0x37,0x35,0x76,0x75,0x53,0x64,0x35,0x46,0x39,0x37,0x56,0x70,0x41,0x67,
0x4D,0x42,0x41,0x41,0x47,0x6A,0x4A,0x44,0x41,0x69,0x4D,0x42,0x4D,0x47,0x41,
0x31,0x55,0x64,0x4A,0x51,0x51,0x4D,0x4D,0x41,0x6F,0x47,0x43,0x43,0x73,0x47,
0x41,0x51,0x55,0x46,0x42,0x77,0x4D,0x42,0x4D,0x41,0x73,0x47,0x0A,0x41,0x31,
0x55,0x64,0x44,0x77,0x51,0x45,0x41,0x77,0x49,0x45,0x4D,0x44,0x41,0x4E,0x42,
0x67,0x6B,0x71,0x68,0x6B,0x69,0x47,0x39,0x77,0x30,0x42,0x41,0x51,0x55,0x46,
0x41,0x41,0x4F,0x43,0x41,0x51,0x45,0x41,0x49,0x51,0x66,0x75,0x2F,0x77,0x39,
0x45,0x34,0x4C,0x6F,0x67,0x30,0x71,0x35,0x4B,0x53,0x38,0x71,0x46,0x78,0x62,
0x36,0x6F,0x0A,0x36,0x31,0x62,0x35,0x37,0x6F,0x6D,0x6E,0x46,0x59,0x52,0x34,
0x47,0x43,0x67,0x33,0x6F,0x6A,0x4F,0x4C,0x54,0x66,0x38,0x7A,0x6A,0x4D,0x43,
0x52,0x6D,0x75,0x59,0x32,0x76,0x30,0x4E,0x34,0x78,0x66,0x68,0x69,0x35,0x4B,
0x69,0x59,0x67,0x64,0x76,0x4E,0x4C,0x4F,0x33,0x52,0x42,0x6D,0x4E,0x50,0x76,
0x59,0x58,0x50,0x52,0x46,0x41,0x76,0x0A,0x66,0x61,0x76,0x66,0x57,0x75,0x6C,
0x44,0x31,0x64,0x50,0x36,0x31,0x69,0x35,0x62,0x36,0x59,0x66,0x56,0x6C,0x78,
0x62,0x31,0x61,0x57,0x46,0x37,0x4C,0x5A,0x44,0x32,0x55,0x6E,0x63,0x41,0x6A,
0x37,0x4E,0x38,0x78,0x38,0x2B,0x36,0x58,0x6B,0x30,0x6B,0x63,0x70,0x58,0x46,
0x38,0x6C,0x77,0x58,0x48,0x55,0x57,0x57,0x55,0x6D,0x73,0x2B,0x0A,0x4B,0x56,
0x44,0x34,0x34,0x39,0x68,0x6F,0x4D,0x2B,0x77,0x4E,0x4A,0x49,0x61,0x4F,0x52,
0x39,0x4C,0x46,0x2B,0x6B,0x6F,0x32,0x32,0x37,0x7A,0x74,0x37,0x54,0x41,0x47,
0x64,0x56,0x35,0x4A,0x75,0x7A,0x71,0x38,0x32,0x2F,0x6B,0x75,0x73,0x6F,0x65,
0x32,0x69,0x75,0x57,0x77,0x54,0x65,0x42,0x6C,0x53,0x5A,0x6E,0x6B,0x42,0x38,
0x63,0x64,0x0A,0x77,0x4D,0x30,0x5A,0x42,0x58,0x6D,0x34,0x35,0x48,0x38,0x6F,
0x79,0x75,0x36,0x4A,0x71,0x59,0x71,0x45,0x6D,0x75,0x4A,0x51,0x64,0x67,0x79,
0x52,0x2B,0x63,0x53,0x53,0x41,0x7A,0x2B,0x4F,0x32,0x6D,0x61,0x62,0x68,0x50,
0x5A,0x65,0x49,0x76,0x78,0x65,0x67,0x6A,0x6A,0x61,0x5A,0x61,0x46,0x4F,0x71,
0x74,0x73,0x2B,0x64,0x33,0x72,0x39,0x0A,0x79,0x71,0x4A,0x78,0x67,0x75,0x39,
0x43,0x38,0x39,0x5A,0x69,0x33,0x39,0x57,0x34,0x38,0x46,0x66,0x46,0x63,0x49,
0x58,0x4A,0x4F,0x6B,0x39,0x43,0x4E,0x46,0x41,0x2F,0x69,0x70,0x54,0x57,0x6A,
0x74,0x74,0x4E,0x2F,0x6B,0x4F,0x6B,0x5A,0x42,0x70,0x6F,0x6A,0x2F,0x32,0x6A,
0x4E,0x45,0x62,0x4F,0x59,0x7A,0x7A,0x6E,0x4B,0x77,0x3D,0x3D,0x0A,0x2D,0x2D,
0x2D,0x2D,0x2D,0x45,0x4E,0x44,0x20,0x43,0x45,0x52,0x54,0x49,0x46,0x49,0x43,
0x41,0x54,0x45,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A
};
BYTE test_localhost_key[1704] =
{
0x2D,0x2D,0x2D,0x2D,0x2D,0x42,0x45,0x47,0x49,0x4E,0x20,0x50,0x52,0x49,0x56,
0x41,0x54,0x45,0x20,0x4B,0x45,0x59,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A,0x4D,0x49,
0x49,0x45,0x76,0x51,0x49,0x42,0x41,0x44,0x41,0x4E,0x42,0x67,0x6B,0x71,0x68,
0x6B,0x69,0x47,0x39,0x77,0x30,0x42,0x41,0x51,0x45,0x46,0x41,0x41,0x53,0x43,
0x42,0x4B,0x63,0x77,0x67,0x67,0x53,0x6A,0x41,0x67,0x45,0x41,0x41,0x6F,0x49,
0x42,0x41,0x51,0x43,0x33,0x65,0x6E,0x33,0x68,0x5A,0x4F,0x53,0x33,0x6B,0x51,
0x2F,0x55,0x0A,0x54,0x30,0x53,0x45,0x6C,0x30,0x48,0x6E,0x50,0x79,0x64,0x48,
0x75,0x35,0x39,0x61,0x69,0x71,0x64,0x73,0x64,0x53,0x55,0x74,0x6E,0x43,0x41,
0x37,0x46,0x66,0x74,0x30,0x4F,0x36,0x51,0x79,0x68,0x49,0x71,0x58,0x7A,0x30,
0x47,0x32,0x53,0x76,0x77,0x4C,0x54,0x62,0x79,0x68,0x59,0x54,0x68,0x31,0x36,
0x78,0x31,0x72,0x45,0x48,0x68,0x31,0x0A,0x57,0x47,0x5A,0x6D,0x36,0x77,0x64,
0x2B,0x4B,0x76,0x38,0x6B,0x31,0x6B,0x2F,0x36,0x6F,0x41,0x2F,0x4F,0x51,0x76,
0x65,0x61,0x38,0x6B,0x63,0x45,0x64,0x53,0x72,0x54,0x64,0x75,0x71,0x4A,0x33,
0x65,0x66,0x74,0x48,0x4A,0x4A,0x6E,0x43,0x4B,0x30,0x41,0x62,0x68,0x34,0x39,
0x41,0x47,0x41,0x50,0x39,0x79,0x58,0x77,0x77,0x59,0x41,0x6A,0x0A,0x51,0x49,
0x52,0x6E,0x38,0x2B,0x4F,0x63,0x63,0x48,0x74,0x6F,0x4E,0x75,0x75,0x79,0x52,
0x63,0x6B,0x49,0x50,0x71,0x75,0x70,0x78,0x79,0x31,0x4A,0x5A,0x4B,0x39,0x64,
0x76,0x76,0x62,0x34,0x79,0x53,0x6B,0x49,0x75,0x7A,0x62,0x79,0x50,0x6F,0x54,
0x41,0x79,0x61,0x55,0x2B,0x51,0x72,0x70,0x34,0x78,0x67,0x64,0x4B,0x46,0x54,
0x70,0x6B,0x0A,0x50,0x46,0x34,0x33,0x6A,0x32,0x4D,0x6D,0x5A,0x72,0x46,0x63,
0x42,0x76,0x79,0x6A,0x69,0x35,0x6A,0x4F,0x37,0x74,0x66,0x6F,0x56,0x61,0x6B,
0x59,0x47,0x53,0x2F,0x4C,0x63,0x78,0x77,0x47,0x2B,0x77,0x51,0x77,0x63,0x4F,
0x43,0x54,0x42,0x45,0x78,0x2F,0x7A,0x31,0x53,0x30,0x37,0x49,0x2F,0x6A,0x62,
0x44,0x79,0x53,0x4E,0x68,0x44,0x35,0x0A,0x63,0x61,0x63,0x54,0x75,0x4E,0x36,
0x50,0x68,0x33,0x58,0x30,0x71,0x70,0x47,0x73,0x37,0x79,0x50,0x6B,0x4E,0x79,
0x69,0x4A,0x33,0x57,0x52,0x69,0x6C,0x35,0x75,0x57,0x73,0x4B,0x65,0x79,0x63,
0x64,0x71,0x42,0x4E,0x72,0x34,0x75,0x32,0x62,0x49,0x52,0x6E,0x63,0x54,0x51,
0x46,0x72,0x68,0x73,0x58,0x39,0x69,0x77,0x37,0x35,0x76,0x75,0x0A,0x53,0x64,
0x35,0x46,0x39,0x37,0x56,0x70,0x41,0x67,0x4D,0x42,0x41,0x41,0x45,0x43,0x67,
0x67,0x45,0x41,0x42,0x36,0x6A,0x6C,0x65,0x48,0x4E,0x74,0x32,0x50,0x77,0x46,
0x58,0x53,0x65,0x79,0x42,0x4A,0x63,0x4C,0x2B,0x55,0x74,0x35,0x71,0x46,0x54,
0x38,0x34,0x68,0x72,0x48,0x77,0x6F,0x39,0x68,0x62,0x66,0x59,0x47,0x6F,0x6E,
0x44,0x59,0x0A,0x66,0x70,0x47,0x2B,0x32,0x52,0x30,0x50,0x62,0x43,0x63,0x4B,
0x35,0x30,0x46,0x61,0x4A,0x46,0x36,0x71,0x63,0x56,0x4A,0x4E,0x75,0x52,0x36,
0x48,0x71,0x2B,0x43,0x55,0x4A,0x74,0x48,0x35,0x39,0x48,0x48,0x37,0x62,0x68,
0x6A,0x39,0x62,0x64,0x78,0x45,0x6D,0x6F,0x48,0x30,0x4A,0x76,0x68,0x45,0x76,
0x67,0x4D,0x2F,0x55,0x38,0x42,0x51,0x0A,0x65,0x57,0x4F,0x4E,0x68,0x78,0x50,
0x73,0x69,0x73,0x6D,0x57,0x6B,0x78,0x61,0x5A,0x6F,0x6C,0x72,0x32,0x69,0x44,
0x56,0x72,0x7A,0x54,0x37,0x55,0x4A,0x71,0x6A,0x74,0x59,0x49,0x74,0x67,0x2B,
0x37,0x59,0x43,0x32,0x70,0x55,0x58,0x6B,0x64,0x49,0x35,0x4A,0x4D,0x67,0x6C,
0x44,0x47,0x4D,0x52,0x5A,0x35,0x55,0x5A,0x48,0x75,0x63,0x7A,0x0A,0x41,0x56,
0x2B,0x71,0x77,0x77,0x33,0x65,0x45,0x52,0x74,0x78,0x44,0x50,0x61,0x61,0x61,
0x34,0x54,0x39,0x50,0x64,0x33,0x44,0x31,0x6D,0x62,0x71,0x58,0x66,0x75,0x45,
0x68,0x42,0x6D,0x33,0x51,0x6F,0x2B,0x75,0x7A,0x51,0x32,0x36,0x76,0x73,0x66,
0x48,0x75,0x56,0x76,0x61,0x39,0x38,0x32,0x4F,0x6A,0x41,0x55,0x6A,0x6E,0x64,
0x30,0x70,0x0A,0x77,0x43,0x53,0x6E,0x42,0x49,0x48,0x67,0x70,0x73,0x30,0x79,
0x61,0x45,0x50,0x63,0x37,0x46,0x78,0x39,0x71,0x45,0x63,0x6D,0x33,0x70,0x7A,
0x41,0x56,0x31,0x69,0x72,0x31,0x4E,0x4E,0x63,0x51,0x47,0x55,0x45,0x75,0x45,
0x6C,0x4A,0x78,0x76,0x2B,0x69,0x57,0x34,0x6D,0x35,0x70,0x7A,0x4C,0x6A,0x64,
0x53,0x63,0x49,0x30,0x59,0x45,0x73,0x0A,0x4D,0x61,0x33,0x78,0x32,0x79,0x48,
0x74,0x6E,0x77,0x79,0x65,0x4C,0x4D,0x54,0x4B,0x6C,0x72,0x46,0x4B,0x70,0x55,
0x4E,0x4A,0x62,0x78,0x73,0x35,0x32,0x62,0x5A,0x4B,0x71,0x49,0x56,0x33,0x33,
0x4A,0x53,0x34,0x41,0x51,0x4B,0x42,0x67,0x51,0x44,0x73,0x4C,0x54,0x49,0x68,
0x35,0x59,0x38,0x4C,0x2F,0x48,0x33,0x64,0x74,0x68,0x63,0x62,0x0A,0x53,0x43,
0x45,0x77,0x32,0x64,0x42,0x49,0x76,0x49,0x79,0x54,0x7A,0x39,0x53,0x72,0x62,
0x33,0x58,0x37,0x37,0x41,0x77,0x57,0x45,0x4C,0x53,0x4D,0x49,0x57,0x53,0x50,
0x55,0x43,0x4B,0x54,0x49,0x70,0x6A,0x4D,0x73,0x6E,0x7A,0x6B,0x46,0x67,0x32,
0x32,0x59,0x32,0x53,0x75,0x47,0x38,0x4C,0x72,0x50,0x6D,0x76,0x73,0x46,0x4A,
0x34,0x30,0x0A,0x32,0x67,0x35,0x44,0x55,0x6C,0x59,0x33,0x59,0x6D,0x53,0x4F,
0x46,0x61,0x45,0x4A,0x54,0x70,0x55,0x47,0x44,0x4D,0x79,0x65,0x33,0x74,0x36,
0x4F,0x30,0x6C,0x63,0x51,0x41,0x66,0x79,0x6D,0x58,0x66,0x41,0x38,0x74,0x50,
0x42,0x48,0x6A,0x5A,0x78,0x56,0x61,0x38,0x78,0x78,0x52,0x5A,0x6E,0x56,0x43,
0x31,0x41,0x62,0x75,0x49,0x49,0x52,0x0A,0x6E,0x77,0x72,0x4E,0x46,0x2B,0x42,
0x6F,0x53,0x4B,0x55,0x41,0x73,0x78,0x2B,0x46,0x75,0x35,0x5A,0x4A,0x4B,0x4F,
0x66,0x79,0x4D,0x51,0x4B,0x42,0x67,0x51,0x44,0x47,0x34,0x50,0x52,0x39,0x2F,
0x58,0x58,0x6B,0x51,0x54,0x36,0x6B,0x7A,0x4B,0x64,0x34,0x50,0x6C,0x50,0x4D,
0x63,0x2B,0x4B,0x51,0x79,0x4C,0x45,0x6C,0x4B,0x39,0x71,0x47,0x0A,0x41,0x6D,
0x6E,0x2F,0x31,0x68,0x64,0x69,0x57,0x57,0x4F,0x52,0x57,0x46,0x62,0x32,0x38,
0x30,0x4D,0x77,0x76,0x77,0x41,0x64,0x78,0x72,0x66,0x65,0x4C,0x57,0x4D,0x57,
0x32,0x66,0x76,0x4C,0x59,0x4B,0x66,0x6C,0x4F,0x35,0x50,0x51,0x44,0x59,0x67,
0x4B,0x4A,0x78,0x35,0x79,0x50,0x37,0x52,0x64,0x38,0x2F,0x64,0x50,0x79,0x5A,
0x59,0x36,0x0A,0x7A,0x56,0x37,0x47,0x47,0x6B,0x51,0x5A,0x42,0x4B,0x36,0x79,
0x74,0x61,0x66,0x32,0x35,0x44,0x50,0x67,0x50,0x72,0x32,0x77,0x73,0x59,0x4D,
0x43,0x6C,0x53,0x74,0x6C,0x56,0x74,0x72,0x6D,0x4F,0x78,0x59,0x55,0x56,0x77,
0x42,0x59,0x4F,0x69,0x36,0x45,0x62,0x50,0x69,0x6B,0x78,0x47,0x48,0x5A,0x70,
0x59,0x6F,0x5A,0x5A,0x70,0x68,0x4A,0x0A,0x4E,0x61,0x38,0x4F,0x4C,0x31,0x69,
0x77,0x75,0x51,0x4B,0x42,0x67,0x51,0x44,0x42,0x55,0x55,0x31,0x54,0x79,0x5A,
0x2B,0x4A,0x5A,0x43,0x64,0x79,0x72,0x33,0x58,0x43,0x63,0x77,0x77,0x58,0x2F,
0x48,0x49,0x73,0x31,0x34,0x6B,0x4B,0x42,0x48,0x68,0x44,0x79,0x33,0x78,0x37,
0x74,0x50,0x38,0x2F,0x6F,0x48,0x54,0x6F,0x72,0x76,0x79,0x74,0x0A,0x41,0x68,
0x38,0x4B,0x36,0x4B,0x72,0x43,0x41,0x75,0x65,0x50,0x6D,0x79,0x32,0x6D,0x4F,
0x54,0x31,0x54,0x39,0x6F,0x31,0x61,0x47,0x55,0x49,0x6C,0x66,0x38,0x72,0x76,
0x33,0x2F,0x30,0x45,0x78,0x67,0x53,0x6B,0x57,0x50,0x6D,0x4F,0x41,0x38,0x35,
0x49,0x32,0x2F,0x58,0x48,0x65,0x66,0x71,0x54,0x6F,0x45,0x48,0x30,0x44,0x65,
0x41,0x4E,0x0A,0x7A,0x6C,0x4B,0x4C,0x71,0x79,0x44,0x56,0x30,0x42,0x56,0x4E,
0x76,0x48,0x42,0x57,0x79,0x32,0x49,0x51,0x35,0x62,0x50,0x42,0x57,0x76,0x30,
0x37,0x63,0x34,0x2B,0x6A,0x39,0x4E,0x62,0x57,0x67,0x64,0x44,0x43,0x43,0x35,
0x52,0x6B,0x4F,0x6A,0x70,0x33,0x4D,0x4E,0x45,0x58,0x47,0x56,0x43,0x69,0x51,
0x51,0x4B,0x42,0x67,0x43,0x7A,0x4D,0x0A,0x77,0x65,0x61,0x62,0x73,0x50,0x48,
0x68,0x44,0x4B,0x5A,0x38,0x2F,0x34,0x43,0x6A,0x73,0x61,0x62,0x4E,0x75,0x41,
0x7A,0x62,0x57,0x4B,0x52,0x42,0x38,0x37,0x44,0x61,0x58,0x46,0x78,0x6F,0x4D,
0x73,0x35,0x52,0x79,0x6F,0x38,0x55,0x4D,0x6B,0x72,0x67,0x30,0x35,0x4C,0x6F,
0x67,0x37,0x4D,0x78,0x62,0x33,0x76,0x61,0x42,0x34,0x63,0x2F,0x0A,0x52,0x57,
0x77,0x7A,0x38,0x72,0x34,0x39,0x70,0x48,0x64,0x71,0x68,0x4F,0x6D,0x63,0x6C,
0x45,0x77,0x79,0x4D,0x34,0x51,0x79,0x6A,0x39,0x52,0x6D,0x57,0x62,0x51,0x58,
0x54,0x54,0x45,0x63,0x2B,0x35,0x67,0x54,0x4B,0x50,0x4E,0x53,0x33,0x6D,0x70,
0x4D,0x54,0x36,0x39,0x46,0x45,0x74,0x2F,0x35,0x72,0x4D,0x52,0x70,0x4B,0x2B,
0x52,0x68,0x0A,0x49,0x32,0x42,0x58,0x6B,0x51,0x71,0x31,0x36,0x6E,0x72,0x31,
0x61,0x45,0x4D,0x6D,0x64,0x51,0x42,0x51,0x79,0x4B,0x59,0x4A,0x6C,0x30,0x6C,
0x50,0x68,0x69,0x42,0x2F,0x75,0x6C,0x5A,0x63,0x72,0x67,0x4C,0x70,0x41,0x6F,
0x47,0x41,0x65,0x30,0x65,0x74,0x50,0x4A,0x77,0x6D,0x51,0x46,0x6B,0x6A,0x4D,
0x70,0x66,0x4D,0x44,0x61,0x4E,0x34,0x0A,0x70,0x7A,0x71,0x45,0x51,0x72,0x52,
0x35,0x4B,0x35,0x4D,0x6E,0x54,0x48,0x76,0x47,0x67,0x2F,0x70,0x6A,0x57,0x6A,
0x43,0x57,0x58,0x56,0x48,0x67,0x35,0x76,0x36,0x46,0x6F,0x5A,0x48,0x35,0x6E,
0x59,0x2B,0x56,0x2F,0x57,0x75,0x57,0x38,0x38,0x6A,0x6C,0x4B,0x53,0x50,0x6C,
0x77,0x6A,0x50,0x7A,0x41,0x67,0x7A,0x47,0x33,0x45,0x41,0x55,0x0A,0x71,0x57,
0x6B,0x42,0x67,0x30,0x71,0x75,0x50,0x4D,0x72,0x54,0x6B,0x73,0x69,0x6E,0x58,
0x50,0x2B,0x58,0x6B,0x51,0x65,0x46,0x66,0x58,0x61,0x33,0x38,0x6A,0x72,0x70,
0x62,0x4B,0x46,0x4F,0x72,0x7A,0x49,0x6F,0x6A,0x69,0x65,0x6C,0x4B,0x55,0x4D,
0x50,0x4D,0x78,0x2F,0x78,0x70,0x53,0x6A,0x63,0x55,0x42,0x68,0x62,0x4E,0x34,
0x45,0x54,0x0A,0x4F,0x30,0x66,0x63,0x57,0x47,0x6F,0x61,0x56,0x50,0x72,0x63,
0x6E,0x38,0x62,0x58,0x4D,0x54,0x45,0x4E,0x53,0x31,0x41,0x3D,0x0A,0x2D,0x2D,
0x2D,0x2D,0x2D,0x45,0x4E,0x44,0x20,0x50,0x52,0x49,0x56,0x41,0x54,0x45,0x20,
0x4B,0x45,0x59,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A
0x2D,0x2D,0x2D,0x2D,0x2D,0x42,0x45,0x47,0x49,0x4E,0x20,0x50,0x52,0x49,0x56,
0x41,0x54,0x45,0x20,0x4B,0x45,0x59,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A,0x4D,0x49,
0x49,0x45,0x76,0x51,0x49,0x42,0x41,0x44,0x41,0x4E,0x42,0x67,0x6B,0x71,0x68,
0x6B,0x69,0x47,0x39,0x77,0x30,0x42,0x41,0x51,0x45,0x46,0x41,0x41,0x53,0x43,
0x42,0x4B,0x63,0x77,0x67,0x67,0x53,0x6A,0x41,0x67,0x45,0x41,0x41,0x6F,0x49,
0x42,0x41,0x51,0x43,0x33,0x65,0x6E,0x33,0x68,0x5A,0x4F,0x53,0x33,0x6B,0x51,
0x2F,0x55,0x0A,0x54,0x30,0x53,0x45,0x6C,0x30,0x48,0x6E,0x50,0x79,0x64,0x48,
0x75,0x35,0x39,0x61,0x69,0x71,0x64,0x73,0x64,0x53,0x55,0x74,0x6E,0x43,0x41,
0x37,0x46,0x66,0x74,0x30,0x4F,0x36,0x51,0x79,0x68,0x49,0x71,0x58,0x7A,0x30,
0x47,0x32,0x53,0x76,0x77,0x4C,0x54,0x62,0x79,0x68,0x59,0x54,0x68,0x31,0x36,
0x78,0x31,0x72,0x45,0x48,0x68,0x31,0x0A,0x57,0x47,0x5A,0x6D,0x36,0x77,0x64,
0x2B,0x4B,0x76,0x38,0x6B,0x31,0x6B,0x2F,0x36,0x6F,0x41,0x2F,0x4F,0x51,0x76,
0x65,0x61,0x38,0x6B,0x63,0x45,0x64,0x53,0x72,0x54,0x64,0x75,0x71,0x4A,0x33,
0x65,0x66,0x74,0x48,0x4A,0x4A,0x6E,0x43,0x4B,0x30,0x41,0x62,0x68,0x34,0x39,
0x41,0x47,0x41,0x50,0x39,0x79,0x58,0x77,0x77,0x59,0x41,0x6A,0x0A,0x51,0x49,
0x52,0x6E,0x38,0x2B,0x4F,0x63,0x63,0x48,0x74,0x6F,0x4E,0x75,0x75,0x79,0x52,
0x63,0x6B,0x49,0x50,0x71,0x75,0x70,0x78,0x79,0x31,0x4A,0x5A,0x4B,0x39,0x64,
0x76,0x76,0x62,0x34,0x79,0x53,0x6B,0x49,0x75,0x7A,0x62,0x79,0x50,0x6F,0x54,
0x41,0x79,0x61,0x55,0x2B,0x51,0x72,0x70,0x34,0x78,0x67,0x64,0x4B,0x46,0x54,
0x70,0x6B,0x0A,0x50,0x46,0x34,0x33,0x6A,0x32,0x4D,0x6D,0x5A,0x72,0x46,0x63,
0x42,0x76,0x79,0x6A,0x69,0x35,0x6A,0x4F,0x37,0x74,0x66,0x6F,0x56,0x61,0x6B,
0x59,0x47,0x53,0x2F,0x4C,0x63,0x78,0x77,0x47,0x2B,0x77,0x51,0x77,0x63,0x4F,
0x43,0x54,0x42,0x45,0x78,0x2F,0x7A,0x31,0x53,0x30,0x37,0x49,0x2F,0x6A,0x62,
0x44,0x79,0x53,0x4E,0x68,0x44,0x35,0x0A,0x63,0x61,0x63,0x54,0x75,0x4E,0x36,
0x50,0x68,0x33,0x58,0x30,0x71,0x70,0x47,0x73,0x37,0x79,0x50,0x6B,0x4E,0x79,
0x69,0x4A,0x33,0x57,0x52,0x69,0x6C,0x35,0x75,0x57,0x73,0x4B,0x65,0x79,0x63,
0x64,0x71,0x42,0x4E,0x72,0x34,0x75,0x32,0x62,0x49,0x52,0x6E,0x63,0x54,0x51,
0x46,0x72,0x68,0x73,0x58,0x39,0x69,0x77,0x37,0x35,0x76,0x75,0x0A,0x53,0x64,
0x35,0x46,0x39,0x37,0x56,0x70,0x41,0x67,0x4D,0x42,0x41,0x41,0x45,0x43,0x67,
0x67,0x45,0x41,0x42,0x36,0x6A,0x6C,0x65,0x48,0x4E,0x74,0x32,0x50,0x77,0x46,
0x58,0x53,0x65,0x79,0x42,0x4A,0x63,0x4C,0x2B,0x55,0x74,0x35,0x71,0x46,0x54,
0x38,0x34,0x68,0x72,0x48,0x77,0x6F,0x39,0x68,0x62,0x66,0x59,0x47,0x6F,0x6E,
0x44,0x59,0x0A,0x66,0x70,0x47,0x2B,0x32,0x52,0x30,0x50,0x62,0x43,0x63,0x4B,
0x35,0x30,0x46,0x61,0x4A,0x46,0x36,0x71,0x63,0x56,0x4A,0x4E,0x75,0x52,0x36,
0x48,0x71,0x2B,0x43,0x55,0x4A,0x74,0x48,0x35,0x39,0x48,0x48,0x37,0x62,0x68,
0x6A,0x39,0x62,0x64,0x78,0x45,0x6D,0x6F,0x48,0x30,0x4A,0x76,0x68,0x45,0x76,
0x67,0x4D,0x2F,0x55,0x38,0x42,0x51,0x0A,0x65,0x57,0x4F,0x4E,0x68,0x78,0x50,
0x73,0x69,0x73,0x6D,0x57,0x6B,0x78,0x61,0x5A,0x6F,0x6C,0x72,0x32,0x69,0x44,
0x56,0x72,0x7A,0x54,0x37,0x55,0x4A,0x71,0x6A,0x74,0x59,0x49,0x74,0x67,0x2B,
0x37,0x59,0x43,0x32,0x70,0x55,0x58,0x6B,0x64,0x49,0x35,0x4A,0x4D,0x67,0x6C,
0x44,0x47,0x4D,0x52,0x5A,0x35,0x55,0x5A,0x48,0x75,0x63,0x7A,0x0A,0x41,0x56,
0x2B,0x71,0x77,0x77,0x33,0x65,0x45,0x52,0x74,0x78,0x44,0x50,0x61,0x61,0x61,
0x34,0x54,0x39,0x50,0x64,0x33,0x44,0x31,0x6D,0x62,0x71,0x58,0x66,0x75,0x45,
0x68,0x42,0x6D,0x33,0x51,0x6F,0x2B,0x75,0x7A,0x51,0x32,0x36,0x76,0x73,0x66,
0x48,0x75,0x56,0x76,0x61,0x39,0x38,0x32,0x4F,0x6A,0x41,0x55,0x6A,0x6E,0x64,
0x30,0x70,0x0A,0x77,0x43,0x53,0x6E,0x42,0x49,0x48,0x67,0x70,0x73,0x30,0x79,
0x61,0x45,0x50,0x63,0x37,0x46,0x78,0x39,0x71,0x45,0x63,0x6D,0x33,0x70,0x7A,
0x41,0x56,0x31,0x69,0x72,0x31,0x4E,0x4E,0x63,0x51,0x47,0x55,0x45,0x75,0x45,
0x6C,0x4A,0x78,0x76,0x2B,0x69,0x57,0x34,0x6D,0x35,0x70,0x7A,0x4C,0x6A,0x64,
0x53,0x63,0x49,0x30,0x59,0x45,0x73,0x0A,0x4D,0x61,0x33,0x78,0x32,0x79,0x48,
0x74,0x6E,0x77,0x79,0x65,0x4C,0x4D,0x54,0x4B,0x6C,0x72,0x46,0x4B,0x70,0x55,
0x4E,0x4A,0x62,0x78,0x73,0x35,0x32,0x62,0x5A,0x4B,0x71,0x49,0x56,0x33,0x33,
0x4A,0x53,0x34,0x41,0x51,0x4B,0x42,0x67,0x51,0x44,0x73,0x4C,0x54,0x49,0x68,
0x35,0x59,0x38,0x4C,0x2F,0x48,0x33,0x64,0x74,0x68,0x63,0x62,0x0A,0x53,0x43,
0x45,0x77,0x32,0x64,0x42,0x49,0x76,0x49,0x79,0x54,0x7A,0x39,0x53,0x72,0x62,
0x33,0x58,0x37,0x37,0x41,0x77,0x57,0x45,0x4C,0x53,0x4D,0x49,0x57,0x53,0x50,
0x55,0x43,0x4B,0x54,0x49,0x70,0x6A,0x4D,0x73,0x6E,0x7A,0x6B,0x46,0x67,0x32,
0x32,0x59,0x32,0x53,0x75,0x47,0x38,0x4C,0x72,0x50,0x6D,0x76,0x73,0x46,0x4A,
0x34,0x30,0x0A,0x32,0x67,0x35,0x44,0x55,0x6C,0x59,0x33,0x59,0x6D,0x53,0x4F,
0x46,0x61,0x45,0x4A,0x54,0x70,0x55,0x47,0x44,0x4D,0x79,0x65,0x33,0x74,0x36,
0x4F,0x30,0x6C,0x63,0x51,0x41,0x66,0x79,0x6D,0x58,0x66,0x41,0x38,0x74,0x50,
0x42,0x48,0x6A,0x5A,0x78,0x56,0x61,0x38,0x78,0x78,0x52,0x5A,0x6E,0x56,0x43,
0x31,0x41,0x62,0x75,0x49,0x49,0x52,0x0A,0x6E,0x77,0x72,0x4E,0x46,0x2B,0x42,
0x6F,0x53,0x4B,0x55,0x41,0x73,0x78,0x2B,0x46,0x75,0x35,0x5A,0x4A,0x4B,0x4F,
0x66,0x79,0x4D,0x51,0x4B,0x42,0x67,0x51,0x44,0x47,0x34,0x50,0x52,0x39,0x2F,
0x58,0x58,0x6B,0x51,0x54,0x36,0x6B,0x7A,0x4B,0x64,0x34,0x50,0x6C,0x50,0x4D,
0x63,0x2B,0x4B,0x51,0x79,0x4C,0x45,0x6C,0x4B,0x39,0x71,0x47,0x0A,0x41,0x6D,
0x6E,0x2F,0x31,0x68,0x64,0x69,0x57,0x57,0x4F,0x52,0x57,0x46,0x62,0x32,0x38,
0x30,0x4D,0x77,0x76,0x77,0x41,0x64,0x78,0x72,0x66,0x65,0x4C,0x57,0x4D,0x57,
0x32,0x66,0x76,0x4C,0x59,0x4B,0x66,0x6C,0x4F,0x35,0x50,0x51,0x44,0x59,0x67,
0x4B,0x4A,0x78,0x35,0x79,0x50,0x37,0x52,0x64,0x38,0x2F,0x64,0x50,0x79,0x5A,
0x59,0x36,0x0A,0x7A,0x56,0x37,0x47,0x47,0x6B,0x51,0x5A,0x42,0x4B,0x36,0x79,
0x74,0x61,0x66,0x32,0x35,0x44,0x50,0x67,0x50,0x72,0x32,0x77,0x73,0x59,0x4D,
0x43,0x6C,0x53,0x74,0x6C,0x56,0x74,0x72,0x6D,0x4F,0x78,0x59,0x55,0x56,0x77,
0x42,0x59,0x4F,0x69,0x36,0x45,0x62,0x50,0x69,0x6B,0x78,0x47,0x48,0x5A,0x70,
0x59,0x6F,0x5A,0x5A,0x70,0x68,0x4A,0x0A,0x4E,0x61,0x38,0x4F,0x4C,0x31,0x69,
0x77,0x75,0x51,0x4B,0x42,0x67,0x51,0x44,0x42,0x55,0x55,0x31,0x54,0x79,0x5A,
0x2B,0x4A,0x5A,0x43,0x64,0x79,0x72,0x33,0x58,0x43,0x63,0x77,0x77,0x58,0x2F,
0x48,0x49,0x73,0x31,0x34,0x6B,0x4B,0x42,0x48,0x68,0x44,0x79,0x33,0x78,0x37,
0x74,0x50,0x38,0x2F,0x6F,0x48,0x54,0x6F,0x72,0x76,0x79,0x74,0x0A,0x41,0x68,
0x38,0x4B,0x36,0x4B,0x72,0x43,0x41,0x75,0x65,0x50,0x6D,0x79,0x32,0x6D,0x4F,
0x54,0x31,0x54,0x39,0x6F,0x31,0x61,0x47,0x55,0x49,0x6C,0x66,0x38,0x72,0x76,
0x33,0x2F,0x30,0x45,0x78,0x67,0x53,0x6B,0x57,0x50,0x6D,0x4F,0x41,0x38,0x35,
0x49,0x32,0x2F,0x58,0x48,0x65,0x66,0x71,0x54,0x6F,0x45,0x48,0x30,0x44,0x65,
0x41,0x4E,0x0A,0x7A,0x6C,0x4B,0x4C,0x71,0x79,0x44,0x56,0x30,0x42,0x56,0x4E,
0x76,0x48,0x42,0x57,0x79,0x32,0x49,0x51,0x35,0x62,0x50,0x42,0x57,0x76,0x30,
0x37,0x63,0x34,0x2B,0x6A,0x39,0x4E,0x62,0x57,0x67,0x64,0x44,0x43,0x43,0x35,
0x52,0x6B,0x4F,0x6A,0x70,0x33,0x4D,0x4E,0x45,0x58,0x47,0x56,0x43,0x69,0x51,
0x51,0x4B,0x42,0x67,0x43,0x7A,0x4D,0x0A,0x77,0x65,0x61,0x62,0x73,0x50,0x48,
0x68,0x44,0x4B,0x5A,0x38,0x2F,0x34,0x43,0x6A,0x73,0x61,0x62,0x4E,0x75,0x41,
0x7A,0x62,0x57,0x4B,0x52,0x42,0x38,0x37,0x44,0x61,0x58,0x46,0x78,0x6F,0x4D,
0x73,0x35,0x52,0x79,0x6F,0x38,0x55,0x4D,0x6B,0x72,0x67,0x30,0x35,0x4C,0x6F,
0x67,0x37,0x4D,0x78,0x62,0x33,0x76,0x61,0x42,0x34,0x63,0x2F,0x0A,0x52,0x57,
0x77,0x7A,0x38,0x72,0x34,0x39,0x70,0x48,0x64,0x71,0x68,0x4F,0x6D,0x63,0x6C,
0x45,0x77,0x79,0x4D,0x34,0x51,0x79,0x6A,0x39,0x52,0x6D,0x57,0x62,0x51,0x58,
0x54,0x54,0x45,0x63,0x2B,0x35,0x67,0x54,0x4B,0x50,0x4E,0x53,0x33,0x6D,0x70,
0x4D,0x54,0x36,0x39,0x46,0x45,0x74,0x2F,0x35,0x72,0x4D,0x52,0x70,0x4B,0x2B,
0x52,0x68,0x0A,0x49,0x32,0x42,0x58,0x6B,0x51,0x71,0x31,0x36,0x6E,0x72,0x31,
0x61,0x45,0x4D,0x6D,0x64,0x51,0x42,0x51,0x79,0x4B,0x59,0x4A,0x6C,0x30,0x6C,
0x50,0x68,0x69,0x42,0x2F,0x75,0x6C,0x5A,0x63,0x72,0x67,0x4C,0x70,0x41,0x6F,
0x47,0x41,0x65,0x30,0x65,0x74,0x50,0x4A,0x77,0x6D,0x51,0x46,0x6B,0x6A,0x4D,
0x70,0x66,0x4D,0x44,0x61,0x4E,0x34,0x0A,0x70,0x7A,0x71,0x45,0x51,0x72,0x52,
0x35,0x4B,0x35,0x4D,0x6E,0x54,0x48,0x76,0x47,0x67,0x2F,0x70,0x6A,0x57,0x6A,
0x43,0x57,0x58,0x56,0x48,0x67,0x35,0x76,0x36,0x46,0x6F,0x5A,0x48,0x35,0x6E,
0x59,0x2B,0x56,0x2F,0x57,0x75,0x57,0x38,0x38,0x6A,0x6C,0x4B,0x53,0x50,0x6C,
0x77,0x6A,0x50,0x7A,0x41,0x67,0x7A,0x47,0x33,0x45,0x41,0x55,0x0A,0x71,0x57,
0x6B,0x42,0x67,0x30,0x71,0x75,0x50,0x4D,0x72,0x54,0x6B,0x73,0x69,0x6E,0x58,
0x50,0x2B,0x58,0x6B,0x51,0x65,0x46,0x66,0x58,0x61,0x33,0x38,0x6A,0x72,0x70,
0x62,0x4B,0x46,0x4F,0x72,0x7A,0x49,0x6F,0x6A,0x69,0x65,0x6C,0x4B,0x55,0x4D,
0x50,0x4D,0x78,0x2F,0x78,0x70,0x53,0x6A,0x63,0x55,0x42,0x68,0x62,0x4E,0x34,
0x45,0x54,0x0A,0x4F,0x30,0x66,0x63,0x57,0x47,0x6F,0x61,0x56,0x50,0x72,0x63,
0x6E,0x38,0x62,0x58,0x4D,0x54,0x45,0x4E,0x53,0x31,0x41,0x3D,0x0A,0x2D,0x2D,
0x2D,0x2D,0x2D,0x45,0x4E,0x44,0x20,0x50,0x52,0x49,0x56,0x41,0x54,0x45,0x20,
0x4B,0x45,0x59,0x2D,0x2D,0x2D,0x2D,0x2D,0x0A
};
BYTE test_DummyMessage[64] =
@ -226,64 +227,52 @@ BYTE test_LastDummyMessage[64] =
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
};
int schannel_send(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phContext, BYTE* buffer, UINT32 length)
int schannel_send(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phContext, BYTE *buffer, UINT32 length)
{
BYTE* ioBuffer;
BYTE *ioBuffer;
UINT32 ioBufferLength;
BYTE* pMessageBuffer;
BYTE *pMessageBuffer;
SecBuffer Buffers[4];
SecBufferDesc Message;
SECURITY_STATUS status;
DWORD NumberOfBytesWritten;
SecPkgContext_StreamSizes StreamSizes;
ZeroMemory(&StreamSizes, sizeof(SecPkgContext_StreamSizes));
status = table->QueryContextAttributes(phContext, SECPKG_ATTR_STREAM_SIZES, &StreamSizes);
ioBufferLength = StreamSizes.cbHeader + StreamSizes.cbMaximumMessage + StreamSizes.cbTrailer;
ioBuffer = (BYTE*) malloc(ioBufferLength);
ioBuffer = (BYTE *) malloc(ioBufferLength);
ZeroMemory(ioBuffer, ioBufferLength);
pMessageBuffer = ioBuffer + StreamSizes.cbHeader;
CopyMemory(pMessageBuffer, buffer, length);
Buffers[0].pvBuffer = ioBuffer;
Buffers[0].cbBuffer = StreamSizes.cbHeader;
Buffers[0].BufferType = SECBUFFER_STREAM_HEADER;
Buffers[1].pvBuffer = pMessageBuffer;
Buffers[1].cbBuffer = length;
Buffers[1].BufferType = SECBUFFER_DATA;
Buffers[2].pvBuffer = pMessageBuffer + length;
Buffers[2].cbBuffer = StreamSizes.cbTrailer;
Buffers[2].BufferType = SECBUFFER_STREAM_TRAILER;
Buffers[3].pvBuffer = NULL;
Buffers[3].cbBuffer = 0;
Buffers[3].BufferType = SECBUFFER_EMPTY;
Message.ulVersion = SECBUFFER_VERSION;
Message.cBuffers = 4;
Message.pBuffers = Buffers;
ioBufferLength = Message.pBuffers[0].cbBuffer + Message.pBuffers[1].cbBuffer + Message.pBuffers[2].cbBuffer;
status = table->EncryptMessage(phContext, 0, &Message, 0);
printf("EncryptMessage status: 0x%08X\n", status);
printf("EncryptMessage output: cBuffers: %d [0]: %u / %u [1]: %u / %u [2]: %u / %u [3]: %u / %u\n", Message.cBuffers,
Message.pBuffers[0].cbBuffer, Message.pBuffers[0].BufferType,
Message.pBuffers[1].cbBuffer, Message.pBuffers[1].BufferType,
Message.pBuffers[2].cbBuffer, Message.pBuffers[2].BufferType,
Message.pBuffers[3].cbBuffer, Message.pBuffers[3].BufferType);
Message.pBuffers[0].cbBuffer, Message.pBuffers[0].BufferType,
Message.pBuffers[1].cbBuffer, Message.pBuffers[1].BufferType,
Message.pBuffers[2].cbBuffer, Message.pBuffers[2].BufferType,
Message.pBuffers[3].cbBuffer, Message.pBuffers[3].BufferType);
if (status != SEC_E_OK)
return -1;
printf("Client > Server (%d)\n", ioBufferLength);
winpr_HexDump(ioBuffer, ioBufferLength);
winpr_HexDump("sspi.test", WLOG_DEBUG, ioBuffer, ioBufferLength);
if (!WriteFile(hPipe, ioBuffer, ioBufferLength, &NumberOfBytesWritten, NULL))
{
@ -296,7 +285,7 @@ int schannel_send(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phCont
int schannel_recv(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phContext)
{
BYTE* ioBuffer;
BYTE *ioBuffer;
UINT32 ioBufferLength;
//BYTE* pMessageBuffer;
SecBuffer Buffers[4];
@ -304,12 +293,10 @@ int schannel_recv(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phCont
SECURITY_STATUS status;
DWORD NumberOfBytesRead;
SecPkgContext_StreamSizes StreamSizes;
ZeroMemory(&StreamSizes, sizeof(SecPkgContext_StreamSizes));
status = table->QueryContextAttributes(phContext, SECPKG_ATTR_STREAM_SIZES, &StreamSizes);
ioBufferLength = StreamSizes.cbHeader + StreamSizes.cbMaximumMessage + StreamSizes.cbTrailer;
ioBuffer = (BYTE*) malloc(ioBufferLength);
ioBuffer = (BYTE *) malloc(ioBufferLength);
ZeroMemory(ioBuffer, ioBufferLength);
if (!ReadFile(hPipe, ioBuffer, ioBufferLength, &NumberOfBytesRead, NULL))
@ -321,38 +308,31 @@ int schannel_recv(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phCont
Buffers[0].pvBuffer = ioBuffer;
Buffers[0].cbBuffer = NumberOfBytesRead;
Buffers[0].BufferType = SECBUFFER_DATA;
Buffers[1].pvBuffer = NULL;
Buffers[1].cbBuffer = 0;
Buffers[1].BufferType = SECBUFFER_EMPTY;
Buffers[2].pvBuffer = NULL;
Buffers[2].cbBuffer = 0;
Buffers[2].BufferType = SECBUFFER_EMPTY;
Buffers[3].pvBuffer = NULL;
Buffers[3].cbBuffer = 0;
Buffers[3].BufferType = SECBUFFER_EMPTY;
Message.ulVersion = SECBUFFER_VERSION;
Message.cBuffers = 4;
Message.pBuffers = Buffers;
status = table->DecryptMessage(phContext, &Message, 0, NULL);
printf("DecryptMessage status: 0x%08X\n", status);
printf("DecryptMessage output: cBuffers: %d [0]: %u / %u [1]: %u / %u [2]: %u / %u [3]: %u / %u\n", Message.cBuffers,
Message.pBuffers[0].cbBuffer, Message.pBuffers[0].BufferType,
Message.pBuffers[1].cbBuffer, Message.pBuffers[1].BufferType,
Message.pBuffers[2].cbBuffer, Message.pBuffers[2].BufferType,
Message.pBuffers[3].cbBuffer, Message.pBuffers[3].BufferType);
Message.pBuffers[0].cbBuffer, Message.pBuffers[0].BufferType,
Message.pBuffers[1].cbBuffer, Message.pBuffers[1].BufferType,
Message.pBuffers[2].cbBuffer, Message.pBuffers[2].BufferType,
Message.pBuffers[3].cbBuffer, Message.pBuffers[3].BufferType);
if (status != SEC_E_OK)
return -1;
printf("Decrypted Message (%d)\n", Message.pBuffers[1].cbBuffer);
winpr_HexDump((BYTE*) Message.pBuffers[1].pvBuffer, Message.pBuffers[1].cbBuffer);
winpr_HexDump("sspi.test", WLOG_DEBUG, (BYTE *) Message.pBuffers[1].pvBuffer, Message.pBuffers[1].cbBuffer);
if (memcmp(Message.pBuffers[1].pvBuffer, test_LastDummyMessage, sizeof(test_LastDummyMessage)) == 0)
return -1;
@ -360,11 +340,11 @@ int schannel_recv(PSecurityFunctionTable table, HANDLE hPipe, PCtxtHandle phCont
return 0;
}
static void* schannel_test_server_thread(void* arg)
static void *schannel_test_server_thread(void *arg)
{
BOOL extraData;
BYTE* lpTokenIn;
BYTE* lpTokenOut;
BYTE *lpTokenIn;
BYTE *lpTokenOut;
TimeStamp expiry;
UINT32 cbMaxToken;
UINT32 fContextReq;
@ -386,14 +366,10 @@ static void* schannel_test_server_thread(void* arg)
PSecPkgInfo pPackageInfo;
PSecurityFunctionTable table;
DWORD NumberOfBytesWritten;
printf("Starting Server\n");
SecInvalidateHandle(&context);
SecInvalidateHandle(&credentials);
table = InitSecurityInterface();
status = QuerySecurityPackageInfo(SCHANNEL_NAME, &pPackageInfo);
if (status != SEC_E_OK)
@ -403,7 +379,6 @@ static void* schannel_test_server_thread(void* arg)
}
cbMaxToken = pPackageInfo->cbMaxToken;
hCertStore = CertOpenSystemStore(0, _T("MY"));
if (!hCertStore)
@ -425,27 +400,19 @@ static void* schannel_test_server_thread(void* arg)
}
cchNameString = CertGetNameString(pCertContext, CERT_NAME_SIMPLE_DISPLAY_TYPE, 0, NULL, NULL, 0);
pszNameString = (LPTSTR) malloc(cchNameString * sizeof(TCHAR));
cchNameString = CertGetNameString(pCertContext, CERT_NAME_SIMPLE_DISPLAY_TYPE, 0, NULL, pszNameString, cchNameString);
_tprintf(_T("Certificate Name: %s\n"), pszNameString);
ZeroMemory(&cred, sizeof(SCHANNEL_CRED));
cred.dwVersion = SCHANNEL_CRED_VERSION;
cred.cCreds = 1;
cred.paCred = &pCertContext;
cred.cSupportedAlgs = 0;
cred.palgSupportedAlgs = NULL;
cred.grbitEnabledProtocols = SP_PROT_TLS1_SERVER;
cred.dwFlags = SCH_CRED_NO_SYSTEM_MAPPER;
status = table->AcquireCredentialsHandle(NULL, SCHANNEL_NAME,
SECPKG_CRED_INBOUND, NULL, &cred, NULL, NULL, &credentials, NULL);
SECPKG_CRED_INBOUND, NULL, &cred, NULL, NULL, &credentials, NULL);
if (status != SEC_E_OK)
{
@ -455,13 +422,11 @@ static void* schannel_test_server_thread(void* arg)
extraData = FALSE;
g_ServerWait = TRUE;
lpTokenIn = (BYTE*) malloc(cbMaxToken);
lpTokenOut = (BYTE*) malloc(cbMaxToken);
lpTokenIn = (BYTE *) malloc(cbMaxToken);
lpTokenOut = (BYTE *) malloc(cbMaxToken);
fContextReq = ASC_REQ_STREAM |
ASC_REQ_SEQUENCE_DETECT | ASC_REQ_REPLAY_DETECT |
ASC_REQ_CONFIDENTIALITY | ASC_REQ_EXTENDED_ERROR;
ASC_REQ_SEQUENCE_DETECT | ASC_REQ_REPLAY_DETECT |
ASC_REQ_CONFIDENTIALITY | ASC_REQ_EXTENDED_ERROR;
do
{
@ -483,29 +448,23 @@ static void* schannel_test_server_thread(void* arg)
extraData = FALSE;
g_ServerWait = TRUE;
SecBuffer_in[0].BufferType = SECBUFFER_TOKEN;
SecBuffer_in[0].pvBuffer = lpTokenIn;
SecBuffer_in[0].cbBuffer = NumberOfBytesRead;
SecBuffer_in[1].BufferType = SECBUFFER_EMPTY;
SecBuffer_in[1].pvBuffer = NULL;
SecBuffer_in[1].cbBuffer = 0;
SecBufferDesc_in.ulVersion = SECBUFFER_VERSION;
SecBufferDesc_in.cBuffers = 2;
SecBufferDesc_in.pBuffers = SecBuffer_in;
SecBuffer_out[0].BufferType = SECBUFFER_TOKEN;
SecBuffer_out[0].pvBuffer = lpTokenOut;
SecBuffer_out[0].cbBuffer = cbMaxToken;
SecBufferDesc_out.ulVersion = SECBUFFER_VERSION;
SecBufferDesc_out.cBuffers = 1;
SecBufferDesc_out.pBuffers = SecBuffer_out;
status = table->AcceptSecurityContext(&credentials, SecIsValidHandle(&context) ? &context : NULL,
&SecBufferDesc_in, fContextReq, 0, &context, &SecBufferDesc_out, &fContextAttr, &expiry);
&SecBufferDesc_in, fContextReq, 0, &context, &SecBufferDesc_out, &fContextAttr, &expiry);
if ((status != SEC_E_OK) && (status != SEC_I_CONTINUE_NEEDED) && (status != SEC_E_INCOMPLETE_MESSAGE))
{
@ -523,10 +482,10 @@ static void* schannel_test_server_thread(void* arg)
printf("AcceptSecurityContext status: SEC_E_INCOMPLETE_MESSAGE\n");
printf("Server cBuffers: %u pBuffers[0]: %u type: %u\n",
SecBufferDesc_out.cBuffers, SecBufferDesc_out.pBuffers[0].cbBuffer, SecBufferDesc_out.pBuffers[0].BufferType);
SecBufferDesc_out.cBuffers, SecBufferDesc_out.pBuffers[0].cbBuffer, SecBufferDesc_out.pBuffers[0].BufferType);
printf("Server Input cBuffers: %d pBuffers[0]: %u type: %u pBuffers[1]: %u type: %u\n", SecBufferDesc_in.cBuffers,
SecBufferDesc_in.pBuffers[0].cbBuffer, SecBufferDesc_in.pBuffers[0].BufferType,
SecBufferDesc_in.pBuffers[1].cbBuffer, SecBufferDesc_in.pBuffers[1].BufferType);
SecBufferDesc_in.pBuffers[0].cbBuffer, SecBufferDesc_in.pBuffers[0].BufferType,
SecBufferDesc_in.pBuffers[1].cbBuffer, SecBufferDesc_in.pBuffers[1].BufferType);
if (SecBufferDesc_in.pBuffers[1].BufferType == SECBUFFER_EXTRA)
{
@ -544,7 +503,7 @@ static void* schannel_test_server_thread(void* arg)
if (pSecBuffer->cbBuffer > 0)
{
printf("Server > Client (%d)\n", pSecBuffer->cbBuffer);
winpr_HexDump((BYTE*) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
winpr_HexDump("sspi.test", WLOG_DEBUG, (BYTE *) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
if (!WriteFile(g_ClientWritePipe, pSecBuffer->pvBuffer, pSecBuffer->cbBuffer, &NumberOfBytesWritten, NULL))
{
@ -567,59 +526,52 @@ static void* schannel_test_server_thread(void* arg)
if (schannel_recv(table, g_ServerReadPipe, &context) < 0)
break;
}
while(1);
while (1);
return NULL;
}
int dump_test_certificate_files()
{
FILE* fp;
char* fullpath;
FILE *fp;
char *fullpath;
/*
* Output Certificate File
*/
fullpath = GetCombinedPath("/tmp", "localhost.crt");
fp = fopen(fullpath, "w+");
if (fp)
{
fwrite((void*) test_localhost_crt, sizeof(test_localhost_crt), 1, fp);
fwrite((void *) test_localhost_crt, sizeof(test_localhost_crt), 1, fp);
fclose(fp);
}
free(fullpath);
/*
* Output Private Key File
*/
fullpath = GetCombinedPath("/tmp", "localhost.key");
fp = fopen(fullpath, "w+");
if (fp)
{
fwrite((void*) test_localhost_key, sizeof(test_localhost_key), 1, fp);
fwrite((void *) test_localhost_key, sizeof(test_localhost_key), 1, fp);
fclose(fp);
}
free(fullpath);
return 1;
}
int TestSchannel(int argc, char* argv[])
int TestSchannel(int argc, char *argv[])
{
int count;
DWORD index;
ALG_ID algId;
HANDLE thread;
BYTE* lpTokenIn;
BYTE* lpTokenOut;
BYTE *lpTokenIn;
BYTE *lpTokenOut;
TimeStamp expiry;
UINT32 cbMaxToken;
SCHANNEL_CRED cred;
@ -640,13 +592,9 @@ int TestSchannel(int argc, char* argv[])
SecPkgCred_SupportedAlgs SupportedAlgs;
SecPkgCred_CipherStrengths CipherStrengths;
SecPkgCred_SupportedProtocols SupportedProtocols;
return 0; /* disable by default - causes crash */
sspi_GlobalInit();
dump_test_certificate_files();
SecInvalidateHandle(&context);
SecInvalidateHandle(&credentials);
@ -663,9 +611,7 @@ int TestSchannel(int argc, char* argv[])
}
thread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE) schannel_test_server_thread, NULL, 0, NULL);
table = InitSecurityInterface();
status = QuerySecurityPackageInfo(SCHANNEL_NAME, &pPackageInfo);
if (status != SEC_E_OK)
@ -675,24 +621,18 @@ int TestSchannel(int argc, char* argv[])
}
cbMaxToken = pPackageInfo->cbMaxToken;
ZeroMemory(&cred, sizeof(SCHANNEL_CRED));
cred.dwVersion = SCHANNEL_CRED_VERSION;
cred.cCreds = 0;
cred.paCred = NULL;
cred.cSupportedAlgs = 0;
cred.palgSupportedAlgs = NULL;
cred.grbitEnabledProtocols = SP_PROT_SSL3TLS1_CLIENTS;
cred.dwFlags = SCH_CRED_NO_DEFAULT_CREDS;
cred.dwFlags |= SCH_CRED_MANUAL_CRED_VALIDATION;
cred.dwFlags |= SCH_CRED_NO_SERVERNAME_CHECK;
status = table->AcquireCredentialsHandle(NULL, SCHANNEL_NAME,
SECPKG_CRED_OUTBOUND, NULL, &cred, NULL, NULL, &credentials, NULL);
SECPKG_CRED_OUTBOUND, NULL, &cred, NULL, NULL, &credentials, NULL);
if (status != SEC_E_OK)
{
@ -714,17 +654,16 @@ int TestSchannel(int argc, char* argv[])
* 0x660E 0x6610 0x6801 0x6603 0x6601 0x8003 0x8004
* 0x800C 0x800D 0x800E 0x2400 0xAA02 0xAE06 0x2200 0x2203
*/
printf("SupportedAlgs: %d\n", SupportedAlgs.cSupportedAlgs);
for (index = 0; index < SupportedAlgs.cSupportedAlgs; index++)
{
algId = SupportedAlgs.palgSupportedAlgs[index];
printf("\t0x%04X CLASS: %d TYPE: %d SID: %d\n", algId,
((GET_ALG_CLASS(algId)) >> 13), ((GET_ALG_TYPE(algId)) >> 9), GET_ALG_SID(algId));
((GET_ALG_CLASS(algId)) >> 13), ((GET_ALG_TYPE(algId)) >> 9), GET_ALG_SID(algId));
}
printf("\n");
printf("\n");
ZeroMemory(&CipherStrengths, sizeof(SecPkgCred_CipherStrengths));
status = table->QueryCredentialsAttributes(&credentials, SECPKG_ATTR_CIPHER_STRENGTHS, &CipherStrengths);
@ -735,10 +674,8 @@ int TestSchannel(int argc, char* argv[])
}
/* CipherStrengths: Minimum: 40 Maximum: 256 */
printf("CipherStrengths: Minimum: %d Maximum: %d\n",
CipherStrengths.dwMinimumCipherStrength, CipherStrengths.dwMaximumCipherStrength);
CipherStrengths.dwMinimumCipherStrength, CipherStrengths.dwMaximumCipherStrength);
ZeroMemory(&SupportedProtocols, sizeof(SecPkgCred_SupportedProtocols));
status = table->QueryCredentialsAttributes(&credentials, SECPKG_ATTR_SUPPORTED_PROTOCOLS, &SupportedProtocols);
@ -749,22 +686,17 @@ int TestSchannel(int argc, char* argv[])
}
/* SupportedProtocols: 0x208A0 */
printf("SupportedProtocols: 0x%04X\n", SupportedProtocols.grbitProtocol);
fContextReq = ISC_REQ_STREAM |
ISC_REQ_SEQUENCE_DETECT | ISC_REQ_REPLAY_DETECT |
ISC_REQ_CONFIDENTIALITY | ISC_RET_EXTENDED_ERROR |
ISC_REQ_MANUAL_CRED_VALIDATION | ISC_REQ_INTEGRITY;
lpTokenIn = (BYTE*) malloc(cbMaxToken);
lpTokenOut = (BYTE*) malloc(cbMaxToken);
ISC_REQ_SEQUENCE_DETECT | ISC_REQ_REPLAY_DETECT |
ISC_REQ_CONFIDENTIALITY | ISC_RET_EXTENDED_ERROR |
ISC_REQ_MANUAL_CRED_VALIDATION | ISC_REQ_INTEGRITY;
lpTokenIn = (BYTE *) malloc(cbMaxToken);
lpTokenOut = (BYTE *) malloc(cbMaxToken);
ZeroMemory(&SecBuffer_in, sizeof(SecBuffer_in));
ZeroMemory(&SecBuffer_out, sizeof(SecBuffer_out));
ZeroMemory(&SecBufferDesc_in, sizeof(SecBufferDesc));
ZeroMemory(&SecBufferDesc_out, sizeof(SecBufferDesc));
g_ClientWait = FALSE;
do
@ -784,29 +716,23 @@ int TestSchannel(int argc, char* argv[])
g_ClientWait = TRUE;
printf("NumberOfBytesRead: %d\n", NumberOfBytesRead);
SecBuffer_in[0].BufferType = SECBUFFER_TOKEN;
SecBuffer_in[0].pvBuffer = lpTokenIn;
SecBuffer_in[0].cbBuffer = NumberOfBytesRead;
SecBuffer_in[1].pvBuffer = NULL;
SecBuffer_in[1].cbBuffer = 0;
SecBuffer_in[1].BufferType = SECBUFFER_EMPTY;
SecBufferDesc_in.ulVersion = SECBUFFER_VERSION;
SecBufferDesc_in.cBuffers = 2;
SecBufferDesc_in.pBuffers = SecBuffer_in;
SecBuffer_out[0].BufferType = SECBUFFER_TOKEN;
SecBuffer_out[0].pvBuffer = lpTokenOut;
SecBuffer_out[0].cbBuffer = cbMaxToken;
SecBufferDesc_out.ulVersion = SECBUFFER_VERSION;
SecBufferDesc_out.cBuffers = 1;
SecBufferDesc_out.pBuffers = SecBuffer_out;
status = table->InitializeSecurityContext(&credentials, SecIsValidHandle(&context) ? &context : NULL, _T("localhost"),
fContextReq, 0, 0, &SecBufferDesc_in, 0, &context, &SecBufferDesc_out, &fContextAttr, &expiry);
fContextReq, 0, 0, &SecBufferDesc_in, 0, &context, &SecBufferDesc_out, &fContextAttr, &expiry);
if ((status != SEC_E_OK) && (status != SEC_I_CONTINUE_NEEDED) && (status != SEC_E_INCOMPLETE_MESSAGE))
{
@ -824,10 +750,10 @@ int TestSchannel(int argc, char* argv[])
printf("InitializeSecurityContext status: SEC_E_INCOMPLETE_MESSAGE\n");
printf("Client Output cBuffers: %d pBuffers[0]: %d type: %d\n",
SecBufferDesc_out.cBuffers, SecBufferDesc_out.pBuffers[0].cbBuffer, SecBufferDesc_out.pBuffers[0].BufferType);
SecBufferDesc_out.cBuffers, SecBufferDesc_out.pBuffers[0].cbBuffer, SecBufferDesc_out.pBuffers[0].BufferType);
printf("Client Input cBuffers: %d pBuffers[0]: %d type: %d pBuffers[1]: %d type: %d\n", SecBufferDesc_in.cBuffers,
SecBufferDesc_in.pBuffers[0].cbBuffer, SecBufferDesc_in.pBuffers[0].BufferType,
SecBufferDesc_in.pBuffers[1].cbBuffer, SecBufferDesc_in.pBuffers[1].BufferType);
SecBufferDesc_in.pBuffers[0].cbBuffer, SecBufferDesc_in.pBuffers[0].BufferType,
SecBufferDesc_in.pBuffers[1].cbBuffer, SecBufferDesc_in.pBuffers[1].BufferType);
if (status != SEC_E_INCOMPLETE_MESSAGE)
{
@ -836,7 +762,7 @@ int TestSchannel(int argc, char* argv[])
if (pSecBuffer->cbBuffer > 0)
{
printf("Client > Server (%d)\n", pSecBuffer->cbBuffer);
winpr_HexDump((BYTE*) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
winpr_HexDump("sspi.test", WLOG_DEBUG, (BYTE *) pSecBuffer->pvBuffer, pSecBuffer->cbBuffer);
if (!WriteFile(g_ServerWritePipe, pSecBuffer->pvBuffer, pSecBuffer->cbBuffer, &NumberOfBytesWritten, NULL))
{
@ -852,7 +778,7 @@ int TestSchannel(int argc, char* argv[])
break;
}
}
while(1);
while (1);
count = 0;
@ -864,30 +790,22 @@ int TestSchannel(int argc, char* argv[])
for (index = 0; index < sizeof(test_DummyMessage); index++)
{
BYTE b, ln, hn;
b = test_DummyMessage[index];
ln = (b & 0x0F);
hn = ((b & 0xF0) >> 4);
ln = (ln + 1) % 0xF;
hn = (ln + 1) % 0xF;
b = (ln | (hn << 4));
test_DummyMessage[index] = b;
}
Sleep(100);
count++;
}
while(count < 3);
while (count < 3);
schannel_send(table, g_ServerWritePipe, &context, test_LastDummyMessage, sizeof(test_LastDummyMessage));
WaitForSingleObject(thread, INFINITE);
sspi_GlobalFinish();
return 0;
}

View File

@ -36,6 +36,9 @@
#ifndef _WIN32
#include "../log.h"
#define TAG "synch.critical"
VOID InitializeCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
{
InitializeCriticalSectionEx(lpCriticalSection, 0, 0);
@ -53,9 +56,9 @@ BOOL InitializeCriticalSectionEx(LPCRITICAL_SECTION lpCriticalSection, DWORD dwS
* - The RecursionCount field indicates the number of times that the owning
* thread has called EnterCriticalSection for this critical section.
*/
if (Flags != 0) {
fprintf(stderr, "warning: InitializeCriticalSectionEx Flags unimplemented\n");
if (Flags != 0)
{
WLog_WARN(TAG, "Flags unimplemented");
}
lpCriticalSection->DebugInfo = NULL;
@ -63,16 +66,13 @@ BOOL InitializeCriticalSectionEx(LPCRITICAL_SECTION lpCriticalSection, DWORD dwS
lpCriticalSection->SpinCount = 0;
lpCriticalSection->RecursionCount = 0;
lpCriticalSection->OwningThread = NULL;
lpCriticalSection->LockSemaphore = (winpr_sem_t*) malloc(sizeof(winpr_sem_t));
lpCriticalSection->LockSemaphore = (winpr_sem_t *) malloc(sizeof(winpr_sem_t));
#if defined(__APPLE__)
semaphore_create(mach_task_self(), lpCriticalSection->LockSemaphore, SYNC_POLICY_FIFO, 0);
#else
sem_init(lpCriticalSection->LockSemaphore, 0, 0);
#endif
SetCriticalSectionSpinCount(lpCriticalSection, dwSpinCount);
return TRUE;
}
@ -91,9 +91,11 @@ DWORD SetCriticalSectionSpinCount(LPCRITICAL_SECTION lpCriticalSection, DWORD dw
{
/* Don't spin on uniprocessor systems! */
GetNativeSystemInfo(&sysinfo);
if (sysinfo.dwNumberOfProcessors < 2)
dwSpinCount = 0;
}
lpCriticalSection->SpinCount = dwSpinCount;
return dwPreviousSpinCount;
#else
@ -104,18 +106,18 @@ DWORD SetCriticalSectionSpinCount(LPCRITICAL_SECTION lpCriticalSection, DWORD dw
static VOID _WaitForCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
{
#if defined(__APPLE__)
semaphore_wait(*((winpr_sem_t*) lpCriticalSection->LockSemaphore));
semaphore_wait(*((winpr_sem_t *) lpCriticalSection->LockSemaphore));
#else
sem_wait((winpr_sem_t*) lpCriticalSection->LockSemaphore);
sem_wait((winpr_sem_t *) lpCriticalSection->LockSemaphore);
#endif
}
static VOID _UnWaitCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
{
#if defined __APPLE__
semaphore_signal(*((winpr_sem_t*) lpCriticalSection->LockSemaphore));
semaphore_signal(*((winpr_sem_t *) lpCriticalSection->LockSemaphore));
#else
sem_post((winpr_sem_t*) lpCriticalSection->LockSemaphore);
sem_post((winpr_sem_t *) lpCriticalSection->LockSemaphore);
#endif
}
@ -135,9 +137,10 @@ VOID EnterCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
if (InterlockedCompareExchange(&lpCriticalSection->LockCount, 0, -1) == -1)
{
lpCriticalSection->RecursionCount = 1;
lpCriticalSection->OwningThread = (HANDLE) (ULONG_PTR) GetCurrentThreadId();
lpCriticalSection->OwningThread = (HANDLE)(ULONG_PTR) GetCurrentThreadId();
return;
}
/* Failed to get the lock. Let the scheduler know that we're spinning. */
if (sched_yield()!=0)
{
@ -156,7 +159,7 @@ VOID EnterCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
if (InterlockedIncrement(&lpCriticalSection->LockCount))
{
/* Section is already locked. Check if it is owned by the current thread. */
if (lpCriticalSection->OwningThread == (HANDLE) (ULONG_PTR) GetCurrentThreadId())
if (lpCriticalSection->OwningThread == (HANDLE)(ULONG_PTR) GetCurrentThreadId())
{
/* Recursion. No need to wait. */
lpCriticalSection->RecursionCount++;
@ -166,17 +169,18 @@ VOID EnterCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
/* Section is locked by another thread. We have to wait. */
_WaitForCriticalSection(lpCriticalSection);
}
/* We got the lock. Own it ... */
lpCriticalSection->RecursionCount = 1;
lpCriticalSection->OwningThread = (HANDLE) (ULONG_PTR) GetCurrentThreadId();
lpCriticalSection->OwningThread = (HANDLE)(ULONG_PTR) GetCurrentThreadId();
}
BOOL TryEnterCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
{
HANDLE current_thread = (HANDLE) (ULONG_PTR) GetCurrentThreadId();
HANDLE current_thread = (HANDLE)(ULONG_PTR) GetCurrentThreadId();
/* Atomically acquire the the lock if the section is free. */
if (InterlockedCompareExchange(&lpCriticalSection->LockCount, 0, -1 ) == -1)
if (InterlockedCompareExchange(&lpCriticalSection->LockCount, 0, -1) == -1)
{
lpCriticalSection->RecursionCount = 1;
lpCriticalSection->OwningThread = current_thread;
@ -202,6 +206,7 @@ VOID LeaveCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
{
/* Last recursion, clear owner, unlock and if there are other waiting threads ... */
lpCriticalSection->OwningThread = NULL;
if (InterlockedDecrement(&lpCriticalSection->LockCount) >= 0)
{
/* ...signal the semaphore to unblock the next waiting thread */
@ -224,9 +229,9 @@ VOID DeleteCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
if (lpCriticalSection->LockSemaphore != NULL)
{
#if defined __APPLE__
semaphore_destroy(mach_task_self(), *((winpr_sem_t*) lpCriticalSection->LockSemaphore));
semaphore_destroy(mach_task_self(), *((winpr_sem_t *) lpCriticalSection->LockSemaphore));
#else
sem_destroy((winpr_sem_t*) lpCriticalSection->LockSemaphore);
sem_destroy((winpr_sem_t *) lpCriticalSection->LockSemaphore);
#endif
free(lpCriticalSection->LockSemaphore);
lpCriticalSection->LockSemaphore = NULL;
@ -237,7 +242,7 @@ VOID DeleteCriticalSection(LPCRITICAL_SECTION lpCriticalSection)
#if (defined(_WIN32) && (_WIN32_WINNT < 0x0600))
typedef BOOL (WINAPI * PINITIALIZE_CRITICAL_SECTION_EX_FN)(LPCRITICAL_SECTION lpCriticalSection, DWORD dwSpinCount, DWORD Flags);
typedef BOOL (WINAPI *PINITIALIZE_CRITICAL_SECTION_EX_FN)(LPCRITICAL_SECTION lpCriticalSection, DWORD dwSpinCount, DWORD Flags);
static HMODULE g_KERNEL32_Library = NULL;
static BOOL g_InitializeCriticalSectionEx_Detected = FALSE;
@ -253,8 +258,7 @@ BOOL InitializeCriticalSectionEx(LPCRITICAL_SECTION lpCriticalSection, DWORD dwS
if (g_KERNEL32_Library)
{
g_pInitializeCriticalSectionEx = (PINITIALIZE_CRITICAL_SECTION_EX_FN)
GetProcAddress(g_KERNEL32_Library, "InitializeCriticalSectionEx");
GetProcAddress(g_KERNEL32_Library, "InitializeCriticalSectionEx");
g_InitializeCriticalSectionEx_Available = (g_pInitializeCriticalSectionEx) ? TRUE : FALSE;
}
else

View File

@ -43,14 +43,16 @@
#include "../handle/handle.h"
#include "../pipe/pipe.h"
#include "../log.h"
#define TAG "synch.event"
CRITICAL_SECTION cs = { NULL, 0, 0, NULL, NULL, 0 };
HANDLE CreateEventW(LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset, BOOL bInitialState, LPCWSTR lpName)
{
WINPR_EVENT* event;
WINPR_EVENT *event;
HANDLE handle = NULL;
event = (WINPR_EVENT*) malloc(sizeof(WINPR_EVENT));
event = (WINPR_EVENT *) malloc(sizeof(WINPR_EVENT));
if (event)
{
@ -59,30 +61,31 @@ HANDLE CreateEventW(LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset,
if (!event->bManualReset)
{
fprintf(stderr, "CreateEventW: auto-reset events not yet implemented\n");
WLog_ERR(TAG, "auto-reset events not yet implemented");
}
event->pipe_fd[0] = -1;
event->pipe_fd[1] = -1;
#ifdef HAVE_EVENTFD_H
event->pipe_fd[0] = eventfd(0, EFD_NONBLOCK);
if (event->pipe_fd[0] < 0)
{
fprintf(stderr, "CreateEventW: failed to create event\n");
WLog_ERR(TAG, "failed to create event");
free(event);
return NULL;
}
#else
if (pipe(event->pipe_fd) < 0)
{
fprintf(stderr, "CreateEventW: failed to create event\n");
WLog_ERR(TAG, "failed to create event");
free(event);
return NULL;
}
#endif
#endif
WINPR_HANDLE_SET_TYPE(event, HANDLE_TYPE_EVENT);
handle = (HANDLE) event;
@ -141,14 +144,12 @@ BOOL SetEvent(HANDLE hEvent)
PVOID Object;
int length;
BOOL status;
WINPR_EVENT* event;
WINPR_EVENT *event;
status = FALSE;
if (winpr_Handle_GetInfo(hEvent, &Type, &Object))
{
event = (WINPR_EVENT*) Object;
event = (WINPR_EVENT *) Object;
#ifdef HAVE_EVENTFD_H
eventfd_t val = 1;
@ -160,6 +161,7 @@ BOOL SetEvent(HANDLE hEvent)
status = (length == 0) ? TRUE : FALSE;
#else
if (WaitForSingleObject(hEvent, 0) != WAIT_OBJECT_0)
{
length = write(event->pipe_fd[1], "-", 1);
@ -171,6 +173,7 @@ BOOL SetEvent(HANDLE hEvent)
{
status = TRUE;
}
#endif
}
@ -183,13 +186,12 @@ BOOL ResetEvent(HANDLE hEvent)
PVOID Object;
int length;
BOOL status;
WINPR_EVENT* event;
WINPR_EVENT *event;
status = FALSE;
if (winpr_Handle_GetInfo(hEvent, &Type, &Object))
{
event = (WINPR_EVENT*) Object;
event = (WINPR_EVENT *) Object;
while (WaitForSingleObject(hEvent, 0) == WAIT_OBJECT_0)
{
@ -204,11 +206,13 @@ BOOL ResetEvent(HANDLE hEvent)
if ((length > 0) && (!status))
status = TRUE;
#else
length = read(event->pipe_fd[0], &length, 1);
if ((length == 1) && (!status))
status = TRUE;
#endif
}
}
@ -221,19 +225,16 @@ BOOL ResetEvent(HANDLE hEvent)
HANDLE CreateFileDescriptorEventW(LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL bManualReset, BOOL bInitialState, int FileDescriptor)
{
#ifndef _WIN32
WINPR_EVENT* event;
WINPR_EVENT *event;
HANDLE handle = NULL;
event = (WINPR_EVENT*) malloc(sizeof(WINPR_EVENT));
event = (WINPR_EVENT *) malloc(sizeof(WINPR_EVENT));
if (event)
{
event->bAttached = TRUE;
event->bManualReset = bManualReset;
event->pipe_fd[0] = FileDescriptor;
event->pipe_fd[1] = -1;
WINPR_HANDLE_SET_TYPE(event, HANDLE_TYPE_EVENT);
handle = (HANDLE) event;
}
@ -253,15 +254,13 @@ HANDLE CreateFileDescriptorEventA(LPSECURITY_ATTRIBUTES lpEventAttributes, BOOL
* Returns an event based on the handle returned by GetEventWaitObject()
*/
HANDLE CreateWaitObjectEvent(LPSECURITY_ATTRIBUTES lpEventAttributes,
BOOL bManualReset, BOOL bInitialState, void* pObject)
BOOL bManualReset, BOOL bInitialState, void *pObject)
{
#ifndef _WIN32
return CreateFileDescriptorEventW(lpEventAttributes, bManualReset, bInitialState, (int) (ULONG_PTR) pObject);
return CreateFileDescriptorEventW(lpEventAttributes, bManualReset, bInitialState, (int)(ULONG_PTR) pObject);
#else
HANDLE hEvent = NULL;
DuplicateHandle(GetCurrentProcess(), pObject, GetCurrentProcess(), &hEvent, 0, FALSE, DUPLICATE_SAME_ACCESS);
return hEvent;
#endif
}
@ -276,18 +275,23 @@ int GetEventFileDescriptor(HANDLE hEvent)
#ifndef _WIN32
ULONG Type;
PVOID Object;
WINPR_EVENT* event;
WINPR_EVENT *event;
if (!winpr_Handle_GetInfo(hEvent, &Type, &Object))
return -1;
event = (WINPR_EVENT*) Object;
event = (WINPR_EVENT *) Object;
if (Type == HANDLE_TYPE_NAMED_PIPE)
{
WINPR_NAMED_PIPE *named = (WINPR_NAMED_PIPE *)hEvent;
if (named->ServerMode) {
if (named->ServerMode)
{
return named->serverfd;
} else {
}
else
{
return named->clientfd;
}
}
@ -308,15 +312,13 @@ int SetEventFileDescriptor(HANDLE hEvent, int FileDescriptor)
#ifndef _WIN32
ULONG Type;
PVOID Object;
WINPR_EVENT* event;
WINPR_EVENT *event;
if (!winpr_Handle_GetInfo(hEvent, &Type, &Object))
return -1;
event = (WINPR_EVENT*) Object;
event = (WINPR_EVENT *) Object;
event->pipe_fd[0] = FileDescriptor;
return 0;
#else
return -1;
@ -333,16 +335,13 @@ int SetEventFileDescriptor(HANDLE hEvent, int FileDescriptor)
* to obtain a file descriptor usable in select()
*/
void* GetEventWaitObject(HANDLE hEvent)
void *GetEventWaitObject(HANDLE hEvent)
{
#ifndef _WIN32
int fd;
void* obj;
void *obj;
fd = GetEventFileDescriptor(hEvent);
obj = ((void*) (long) fd);
obj = ((void *)(long) fd);
return obj;
#else
return hEvent;

View File

@ -26,36 +26,39 @@
#include <winpr/synch.h>
#include <winpr/interlocked.h>
#include "../log.h"
#define TAG "com.winpr.sync"
#if (!defined(_WIN32)) || (defined(_WIN32) && (_WIN32_WINNT < 0x0600))
BOOL InitOnceBeginInitialize(LPINIT_ONCE lpInitOnce, DWORD dwFlags, PBOOL fPending, LPVOID* lpContext)
BOOL InitOnceBeginInitialize(LPINIT_ONCE lpInitOnce, DWORD dwFlags, PBOOL fPending, LPVOID *lpContext)
{
fprintf(stderr, "%s: not implemented\n", __FUNCTION__);
WLog_ERR(TAG, "not implemented");
return FALSE;
}
BOOL InitOnceComplete(LPINIT_ONCE lpInitOnce, DWORD dwFlags, LPVOID lpContext)
{
fprintf(stderr, "%s: not implemented\n", __FUNCTION__);
WLog_ERR(TAG, "not implemented");
return FALSE;
}
VOID InitOnceInitialize(PINIT_ONCE InitOnce)
{
fprintf(stderr, "%s: not implemented\n", __FUNCTION__);
WLog_ERR(TAG, "not implemented");
}
BOOL InitOnceExecuteOnce(PINIT_ONCE InitOnce, PINIT_ONCE_FN InitFn, PVOID Parameter, LPVOID* Context)
BOOL InitOnceExecuteOnce(PINIT_ONCE InitOnce, PINIT_ONCE_FN InitFn, PVOID Parameter, LPVOID *Context)
{
for (;;)
{
switch((ULONG_PTR)InitOnce->Ptr & 3)
switch ((ULONG_PTR)InitOnce->Ptr & 3)
{
case 2:
/* already completed successfully */
return TRUE;
case 0:
/* first time */
if (InterlockedCompareExchangePointer(&InitOnce->Ptr, (PVOID)1, (PVOID)0) != (PVOID)0)
{
@ -74,13 +77,11 @@ BOOL InitOnceExecuteOnce(PINIT_ONCE InitOnce, PINIT_ONCE_FN InitFn, PVOID Parame
/* the init function returned an error, reset the status */
InitOnce->Ptr = (PVOID)0;
return FALSE;
case 1:
/* in progress */
break;
default:
fprintf(stderr, "%s: internal error\n", __FUNCTION__);
WLog_ERR(TAG, "internal error");
return FALSE;
}

View File

@ -32,19 +32,21 @@
#ifndef _WIN32
#include "../handle/handle.h"
#include "../log.h"
#define TAG "synch.semaphore"
HANDLE CreateSemaphoreW(LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, LONG lInitialCount, LONG lMaximumCount, LPCWSTR lpName)
{
HANDLE handle;
WINPR_SEMAPHORE* semaphore;
WINPR_SEMAPHORE *semaphore;
semaphore = (WINPR_SEMAPHORE *) malloc(sizeof(WINPR_SEMAPHORE));
semaphore = (WINPR_SEMAPHORE*) malloc(sizeof(WINPR_SEMAPHORE));
if (!semaphore)
return NULL;
semaphore->pipe_fd[0] = -1;
semaphore->pipe_fd[0] = -1;
semaphore->sem = (winpr_sem_t*) NULL;
semaphore->sem = (winpr_sem_t *) NULL;
if (semaphore)
{
@ -52,7 +54,7 @@ HANDLE CreateSemaphoreW(LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, LONG lIniti
if (pipe(semaphore->pipe_fd) < 0)
{
fprintf(stderr, "CreateSemaphoreW: failed to create semaphore\n");
WLog_ERR(TAG, "failed to create semaphore");
free(semaphore);
return NULL;
}
@ -71,19 +73,17 @@ HANDLE CreateSemaphoreW(LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, LONG lIniti
}
#else
semaphore->sem = (winpr_sem_t*) malloc(sizeof(winpr_sem_t));
semaphore->sem = (winpr_sem_t *) malloc(sizeof(winpr_sem_t));
#if defined __APPLE__
semaphore_create(mach_task_self(), semaphore->sem, SYNC_POLICY_FIFO, lMaximumCount);
#else
sem_init(semaphore->sem, 0, lMaximumCount);
#endif
#endif
}
WINPR_HANDLE_SET_TYPE(semaphore, HANDLE_TYPE_SEMAPHORE);
handle = (HANDLE) semaphore;
return handle;
}
@ -94,11 +94,13 @@ HANDLE CreateSemaphoreA(LPSECURITY_ATTRIBUTES lpSemaphoreAttributes, LONG lIniti
HANDLE OpenSemaphoreW(DWORD dwDesiredAccess, BOOL bInheritHandle, LPCWSTR lpName)
{
WLog_ERR(TAG, "not implemented");
return NULL;
}
HANDLE OpenSemaphoreA(DWORD dwDesiredAccess, BOOL bInheritHandle, LPCSTR lpName)
{
WLog_ERR(TAG, "not implemented");
return NULL;
}
@ -106,15 +108,14 @@ BOOL ReleaseSemaphore(HANDLE hSemaphore, LONG lReleaseCount, LPLONG lpPreviousCo
{
ULONG Type;
PVOID Object;
WINPR_SEMAPHORE* semaphore;
WINPR_SEMAPHORE *semaphore;
if (!winpr_Handle_GetInfo(hSemaphore, &Type, &Object))
return FALSE;
if (Type == HANDLE_TYPE_SEMAPHORE)
{
semaphore = (WINPR_SEMAPHORE*) Object;
semaphore = (WINPR_SEMAPHORE *) Object;
#ifdef WINPR_PIPE_SEMAPHORE
if (semaphore->pipe_fd[0] != -1)
@ -129,13 +130,11 @@ BOOL ReleaseSemaphore(HANDLE hSemaphore, LONG lReleaseCount, LPLONG lpPreviousCo
}
#else
#if defined __APPLE__
semaphore_signal(*((winpr_sem_t*) semaphore->sem));
semaphore_signal(*((winpr_sem_t *) semaphore->sem));
#else
sem_post((winpr_sem_t*) semaphore->sem);
sem_post((winpr_sem_t *) semaphore->sem);
#endif
#endif
return TRUE;
}

View File

@ -39,13 +39,16 @@
#include "../handle/handle.h"
#include "../log.h"
#define TAG "synch.timer"
#ifdef WITH_POSIX_TIMER
static BOOL g_WaitableTimerSignalHandlerInstalled = FALSE;
void WaitableTimerSignalHandler(int signum, siginfo_t* siginfo, void* arg)
void WaitableTimerSignalHandler(int signum, siginfo_t *siginfo, void *arg)
{
WINPR_TIMER* timer = siginfo->si_value.sival_ptr;
WINPR_TIMER *timer = siginfo->si_value.sival_ptr;
if (!timer || (signum != SIGALRM))
return;
@ -61,7 +64,7 @@ void WaitableTimerSignalHandler(int signum, siginfo_t* siginfo, void* arg)
if ((timer_settime(timer->tid, 0, &(timer->timeout), NULL)) != 0)
{
perror("timer_settime");
WLog_ERR(TAG,"timer_settime");
}
}
}
@ -72,15 +75,11 @@ int InstallWaitableTimerSignalHandler()
if (!g_WaitableTimerSignalHandlerInstalled)
{
struct sigaction action;
sigemptyset(&action.sa_mask);
sigaddset(&action.sa_mask, SIGALRM);
action.sa_flags = SA_RESTART | SA_SIGINFO;
action.sa_sigaction = (void*) &WaitableTimerSignalHandler;
action.sa_sigaction = (void *) &WaitableTimerSignalHandler;
sigaction(SIGALRM, &action, NULL);
g_WaitableTimerSignalHandlerInstalled = TRUE;
}
@ -89,13 +88,12 @@ int InstallWaitableTimerSignalHandler()
#endif
int InitializeWaitableTimer(WINPR_TIMER* timer)
int InitializeWaitableTimer(WINPR_TIMER *timer)
{
if (!timer->lpArgToCompletionRoutine)
{
#ifdef HAVE_TIMERFD_H
int status;
timer->fd = timerfd_create(CLOCK_MONOTONIC, 0);
if (timer->fd <= 0)
@ -111,31 +109,29 @@ int InitializeWaitableTimer(WINPR_TIMER* timer)
close(timer->fd);
return -1;
}
#endif
}
else
{
#ifdef WITH_POSIX_TIMER
struct sigevent sigev;
InstallWaitableTimerSignalHandler();
ZeroMemory(&sigev, sizeof(struct sigevent));
sigev.sigev_notify = SIGEV_SIGNAL;
sigev.sigev_signo = SIGALRM;
sigev.sigev_value.sival_ptr = (void*) timer;
sigev.sigev_value.sival_ptr = (void *) timer;
if ((timer_create(CLOCK_MONOTONIC, &sigev, &(timer->tid))) != 0)
{
perror("timer_create");
WLog_ERR(TAG,"timer_create");
return -1;
}
#endif
}
timer->bInit = TRUE;
return 0;
}
@ -146,15 +142,13 @@ int InitializeWaitableTimer(WINPR_TIMER* timer)
HANDLE CreateWaitableTimerA(LPSECURITY_ATTRIBUTES lpTimerAttributes, BOOL bManualReset, LPCSTR lpTimerName)
{
HANDLE handle = NULL;
WINPR_TIMER* timer;
timer = (WINPR_TIMER*) malloc(sizeof(WINPR_TIMER));
WINPR_TIMER *timer;
timer = (WINPR_TIMER *) malloc(sizeof(WINPR_TIMER));
if (timer)
{
WINPR_HANDLE_SET_TYPE(timer, HANDLE_TYPE_TIMER);
handle = (HANDLE) timer;
timer->fd = -1;
timer->lPeriod = 0;
timer->bManualReset = bManualReset;
@ -174,9 +168,7 @@ HANDLE CreateWaitableTimerW(LPSECURITY_ATTRIBUTES lpTimerAttributes, BOOL bManua
HANDLE CreateWaitableTimerExA(LPSECURITY_ATTRIBUTES lpTimerAttributes, LPCSTR lpTimerName, DWORD dwFlags, DWORD dwDesiredAccess)
{
BOOL bManualReset;
bManualReset = (dwFlags & CREATE_WAITABLE_TIMER_MANUAL_RESET) ? TRUE : FALSE;
return CreateWaitableTimerA(lpTimerAttributes, bManualReset, lpTimerName);
}
@ -185,14 +177,14 @@ HANDLE CreateWaitableTimerExW(LPSECURITY_ATTRIBUTES lpTimerAttributes, LPCWSTR l
return NULL;
}
BOOL SetWaitableTimer(HANDLE hTimer, const LARGE_INTEGER* lpDueTime, LONG lPeriod,
PTIMERAPCROUTINE pfnCompletionRoutine, LPVOID lpArgToCompletionRoutine, BOOL fResume)
BOOL SetWaitableTimer(HANDLE hTimer, const LARGE_INTEGER *lpDueTime, LONG lPeriod,
PTIMERAPCROUTINE pfnCompletionRoutine, LPVOID lpArgToCompletionRoutine, BOOL fResume)
{
ULONG Type;
PVOID Object;
WINPR_TIMER* timer;
WINPR_TIMER *timer;
#ifdef WITH_POSIX_TIMER
LONGLONG seconds = 0;
LONGLONG seconds = 0;
LONGLONG nanoseconds = 0;
#ifdef HAVE_TIMERFD_H
int status = 0;
@ -211,8 +203,7 @@ BOOL SetWaitableTimer(HANDLE hTimer, const LARGE_INTEGER* lpDueTime, LONG lPerio
if (lPeriod < 0)
return FALSE;
timer = (WINPR_TIMER*) Object;
timer = (WINPR_TIMER *) Object;
timer->lPeriod = lPeriod; /* milliseconds */
timer->pfnCompletionRoutine = pfnCompletionRoutine;
timer->lpArgToCompletionRoutine = lpArgToCompletionRoutine;
@ -224,15 +215,12 @@ BOOL SetWaitableTimer(HANDLE hTimer, const LARGE_INTEGER* lpDueTime, LONG lPerio
}
#ifdef WITH_POSIX_TIMER
ZeroMemory(&(timer->timeout), sizeof(struct itimerspec));
if (lpDueTime->QuadPart < 0)
{
LONGLONG due = lpDueTime->QuadPart * (-1);
/* due time is in 100 nanosecond intervals */
seconds = (due / 10000000);
nanoseconds = ((due % 10000000) * 100);
}
@ -242,7 +230,7 @@ BOOL SetWaitableTimer(HANDLE hTimer, const LARGE_INTEGER* lpDueTime, LONG lPerio
}
else
{
printf("SetWaitableTimer: implement absolute time\n");
WLog_ERR(TAG, "absolute time not implemented");
return FALSE;
}
@ -270,38 +258,38 @@ BOOL SetWaitableTimer(HANDLE hTimer, const LARGE_INTEGER* lpDueTime, LONG lPerio
if (status)
{
printf("SetWaitableTimer timerfd_settime failure: %d\n", status);
WLog_ERR(TAG, "timerfd_settime failure: %d\n", status);
return FALSE;
}
#endif
}
else
{
if ((timer_settime(timer->tid, 0, &(timer->timeout), NULL)) != 0)
{
perror("timer_settime");
WLog_ERR(TAG,"timer_settime");
return FALSE;
}
}
#endif
return TRUE;
}
BOOL SetWaitableTimerEx(HANDLE hTimer, const LARGE_INTEGER* lpDueTime, LONG lPeriod,
PTIMERAPCROUTINE pfnCompletionRoutine, LPVOID lpArgToCompletionRoutine, PREASON_CONTEXT WakeContext, ULONG TolerableDelay)
BOOL SetWaitableTimerEx(HANDLE hTimer, const LARGE_INTEGER *lpDueTime, LONG lPeriod,
PTIMERAPCROUTINE pfnCompletionRoutine, LPVOID lpArgToCompletionRoutine, PREASON_CONTEXT WakeContext, ULONG TolerableDelay)
{
ULONG Type;
PVOID Object;
WINPR_TIMER* timer;
WINPR_TIMER *timer;
if (!winpr_Handle_GetInfo(hTimer, &Type, &Object))
return FALSE;
if (Type == HANDLE_TYPE_TIMER)
{
timer = (WINPR_TIMER*) Object;
timer = (WINPR_TIMER *) Object;
return TRUE;
}
@ -332,14 +320,14 @@ BOOL CancelWaitableTimer(HANDLE hTimer)
* http://www.cs.wustl.edu/~schmidt/Timer_Queue.html
*/
void timespec_add_ms(struct timespec* tspec, UINT32 ms)
void timespec_add_ms(struct timespec *tspec, UINT32 ms)
{
UINT64 ns = tspec->tv_nsec + (ms * 1000000);
tspec->tv_sec += (ns / 1000000000);
tspec->tv_nsec = (ns % 1000000000);
}
UINT64 timespec_to_ms(struct timespec* tspec)
UINT64 timespec_to_ms(struct timespec *tspec)
{
UINT64 ms;
ms = tspec->tv_sec * 1000;
@ -347,7 +335,7 @@ UINT64 timespec_to_ms(struct timespec* tspec)
return ms;
}
static void timespec_gettimeofday(struct timespec* tspec)
static void timespec_gettimeofday(struct timespec *tspec)
{
struct timeval tval;
gettimeofday(&tval, NULL);
@ -355,7 +343,7 @@ static void timespec_gettimeofday(struct timespec* tspec)
tspec->tv_nsec = tval.tv_usec * 1000;
}
static int timespec_compare(const struct timespec* tspec1, const struct timespec* tspec2)
static int timespec_compare(const struct timespec *tspec1, const struct timespec *tspec2)
{
if (tspec1->tv_sec == tspec2->tv_sec)
return (tspec1->tv_nsec - tspec2->tv_nsec);
@ -363,16 +351,16 @@ static int timespec_compare(const struct timespec* tspec1, const struct timespec
return (tspec1->tv_sec - tspec2->tv_sec);
}
static void timespec_copy(struct timespec* dst, struct timespec* src)
static void timespec_copy(struct timespec *dst, struct timespec *src)
{
dst->tv_sec = src->tv_sec;
dst->tv_nsec = src->tv_nsec;
}
void InsertTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER** pHead, WINPR_TIMER_QUEUE_TIMER* timer)
void InsertTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER **pHead, WINPR_TIMER_QUEUE_TIMER *timer)
{
WINPR_TIMER_QUEUE_TIMER* node;
WINPR_TIMER_QUEUE_TIMER *node;
if (!(*pHead))
{
*pHead = timer;
@ -381,7 +369,7 @@ void InsertTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER** pHead, WINPR_TIMER_QUEUE_TI
}
node = *pHead;
while (node->next)
{
if (timespec_compare(&(timer->ExpirationTime), &(node->ExpirationTime)) > 0)
@ -405,11 +393,11 @@ void InsertTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER** pHead, WINPR_TIMER_QUEUE_TI
}
}
void RemoveTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER** pHead, WINPR_TIMER_QUEUE_TIMER* timer)
void RemoveTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER **pHead, WINPR_TIMER_QUEUE_TIMER *timer)
{
BOOL found = FALSE;
WINPR_TIMER_QUEUE_TIMER* node;
WINPR_TIMER_QUEUE_TIMER* prevNode;
WINPR_TIMER_QUEUE_TIMER *node;
WINPR_TIMER_QUEUE_TIMER *prevNode;
if (timer == *pHead)
{
@ -432,28 +420,27 @@ void RemoveTimerQueueTimer(WINPR_TIMER_QUEUE_TIMER** pHead, WINPR_TIMER_QUEUE_TI
prevNode = node;
node = node->next;
}
if (found)
{
if (prevNode)
{
prevNode->next = timer->next;
}
timer->next = NULL;
}
}
int FireExpiredTimerQueueTimers(WINPR_TIMER_QUEUE* timerQueue)
int FireExpiredTimerQueueTimers(WINPR_TIMER_QUEUE *timerQueue)
{
struct timespec CurrentTime;
WINPR_TIMER_QUEUE_TIMER* node;
WINPR_TIMER_QUEUE_TIMER *node;
if (!timerQueue->activeHead)
return 0;
timespec_gettimeofday(&CurrentTime);
node = timerQueue->activeHead;
while (node)
@ -462,7 +449,6 @@ int FireExpiredTimerQueueTimers(WINPR_TIMER_QUEUE* timerQueue)
{
node->Callback(node->Parameter, TRUE);
node->FireCount++;
timerQueue->activeHead = node->next;
node->next = NULL;
@ -475,7 +461,7 @@ int FireExpiredTimerQueueTimers(WINPR_TIMER_QUEUE* timerQueue)
{
InsertTimerQueueTimer(&(timerQueue->inactiveHead), node);
}
node = timerQueue->activeHead;
}
else
@ -487,16 +473,15 @@ int FireExpiredTimerQueueTimers(WINPR_TIMER_QUEUE* timerQueue)
return 0;
}
static void* TimerQueueThread(void* arg)
static void *TimerQueueThread(void *arg)
{
int status;
struct timespec timeout;
WINPR_TIMER_QUEUE* timerQueue = (WINPR_TIMER_QUEUE*) arg;
WINPR_TIMER_QUEUE *timerQueue = (WINPR_TIMER_QUEUE *) arg;
while (1)
{
pthread_mutex_lock(&(timerQueue->cond_mutex));
timespec_gettimeofday(&timeout);
if (!timerQueue->activeHead)
@ -512,9 +497,7 @@ static void* TimerQueueThread(void* arg)
}
status = pthread_cond_timedwait(&(timerQueue->cond), &(timerQueue->cond_mutex), &timeout);
FireExpiredTimerQueueTimers(timerQueue);
pthread_mutex_unlock(&(timerQueue->cond_mutex));
if (timerQueue->bCancelled)
@ -524,40 +507,33 @@ static void* TimerQueueThread(void* arg)
return NULL;
}
int StartTimerQueueThread(WINPR_TIMER_QUEUE* timerQueue)
int StartTimerQueueThread(WINPR_TIMER_QUEUE *timerQueue)
{
pthread_cond_init(&(timerQueue->cond), NULL);
pthread_mutex_init(&(timerQueue->cond_mutex), NULL);
pthread_mutex_init(&(timerQueue->mutex), NULL);
pthread_attr_init(&(timerQueue->attr));
timerQueue->param.sched_priority = sched_get_priority_max(SCHED_FIFO);
pthread_attr_setschedparam(&(timerQueue->attr), &(timerQueue->param));
pthread_attr_setschedpolicy(&(timerQueue->attr), SCHED_FIFO);
pthread_create(&(timerQueue->thread), &(timerQueue->attr), TimerQueueThread, timerQueue);
return 0;
}
HANDLE CreateTimerQueue(void)
{
HANDLE handle = NULL;
WINPR_TIMER_QUEUE* timerQueue;
timerQueue = (WINPR_TIMER_QUEUE*) malloc(sizeof(WINPR_TIMER_QUEUE));
WINPR_TIMER_QUEUE *timerQueue;
timerQueue = (WINPR_TIMER_QUEUE *) malloc(sizeof(WINPR_TIMER_QUEUE));
if (timerQueue)
{
ZeroMemory(timerQueue, sizeof(WINPR_TIMER_QUEUE));
WINPR_HANDLE_SET_TYPE(timerQueue, HANDLE_TYPE_TIMER_QUEUE);
handle = (HANDLE) timerQueue;
timerQueue->activeHead = NULL;
timerQueue->inactiveHead = NULL;
timerQueue->bCancelled = FALSE;
StartTimerQueueThread(timerQueue);
}
@ -566,25 +542,20 @@ HANDLE CreateTimerQueue(void)
BOOL DeleteTimerQueueEx(HANDLE TimerQueue, HANDLE CompletionEvent)
{
void* rvalue;
WINPR_TIMER_QUEUE* timerQueue;
WINPR_TIMER_QUEUE_TIMER* node;
WINPR_TIMER_QUEUE_TIMER* nextNode;
void *rvalue;
WINPR_TIMER_QUEUE *timerQueue;
WINPR_TIMER_QUEUE_TIMER *node;
WINPR_TIMER_QUEUE_TIMER *nextNode;
if (!TimerQueue)
return FALSE;
timerQueue = (WINPR_TIMER_QUEUE*) TimerQueue;
timerQueue = (WINPR_TIMER_QUEUE *) TimerQueue;
/* Cancel and delete timer queue timers */
pthread_mutex_lock(&(timerQueue->cond_mutex));
timerQueue->bCancelled = TRUE;
pthread_cond_signal(&(timerQueue->cond));
pthread_mutex_unlock(&(timerQueue->cond_mutex));
pthread_join(timerQueue->thread, &rvalue);
if (CompletionEvent == INVALID_HANDLE_VALUE)
@ -594,9 +565,7 @@ BOOL DeleteTimerQueueEx(HANDLE TimerQueue, HANDLE CompletionEvent)
else
{
/* Cancel all timers and return immediately */
/* Move all active timers to the inactive timer list */
node = timerQueue->activeHead;
while (node)
@ -606,17 +575,13 @@ BOOL DeleteTimerQueueEx(HANDLE TimerQueue, HANDLE CompletionEvent)
}
timerQueue->activeHead = NULL;
/* Once all timers are inactive, free them */
node = timerQueue->inactiveHead;
while (node)
{
nextNode = node->next;
free(node);
node = nextNode;
}
@ -624,14 +589,10 @@ BOOL DeleteTimerQueueEx(HANDLE TimerQueue, HANDLE CompletionEvent)
}
/* Delete timer queue */
pthread_cond_destroy(&(timerQueue->cond));
pthread_mutex_destroy(&(timerQueue->cond_mutex));
pthread_mutex_destroy(&(timerQueue->mutex));
pthread_attr_destroy(&(timerQueue->attr));
free(timerQueue);
if (CompletionEvent && (CompletionEvent != INVALID_HANDLE_VALUE))
@ -646,97 +607,79 @@ BOOL DeleteTimerQueue(HANDLE TimerQueue)
}
BOOL CreateTimerQueueTimer(PHANDLE phNewTimer, HANDLE TimerQueue,
WAITORTIMERCALLBACK Callback, PVOID Parameter, DWORD DueTime, DWORD Period, ULONG Flags)
WAITORTIMERCALLBACK Callback, PVOID Parameter, DWORD DueTime, DWORD Period, ULONG Flags)
{
struct timespec CurrentTime;
WINPR_TIMER_QUEUE* timerQueue;
WINPR_TIMER_QUEUE_TIMER* timer;
WINPR_TIMER_QUEUE *timerQueue;
WINPR_TIMER_QUEUE_TIMER *timer;
if (!TimerQueue)
return FALSE;
timespec_gettimeofday(&CurrentTime);
timerQueue = (WINPR_TIMER_QUEUE*) TimerQueue;
timer = (WINPR_TIMER_QUEUE_TIMER*) malloc(sizeof(WINPR_TIMER_QUEUE_TIMER));
timerQueue = (WINPR_TIMER_QUEUE *) TimerQueue;
timer = (WINPR_TIMER_QUEUE_TIMER *) malloc(sizeof(WINPR_TIMER_QUEUE_TIMER));
if (!timer)
return FALSE;
WINPR_HANDLE_SET_TYPE(timer, HANDLE_TYPE_TIMER_QUEUE_TIMER);
*((UINT_PTR*) phNewTimer) = (UINT_PTR) (HANDLE) timer;
*((UINT_PTR *) phNewTimer) = (UINT_PTR)(HANDLE) timer;
timespec_copy(&(timer->StartTime), &CurrentTime);
timespec_add_ms(&(timer->StartTime), DueTime);
timespec_copy(&(timer->ExpirationTime), &(timer->StartTime));
timer->Flags = Flags;
timer->DueTime = DueTime;
timer->Period = Period;
timer->Callback = Callback;
timer->Parameter = Parameter;
timer->timerQueue = (WINPR_TIMER_QUEUE*) TimerQueue;
timer->timerQueue = (WINPR_TIMER_QUEUE *) TimerQueue;
timer->FireCount = 0;
timer->next = NULL;
pthread_mutex_lock(&(timerQueue->cond_mutex));
InsertTimerQueueTimer(&(timerQueue->activeHead), timer);
pthread_cond_signal(&(timerQueue->cond));
pthread_mutex_unlock(&(timerQueue->cond_mutex));
return TRUE;
}
BOOL ChangeTimerQueueTimer(HANDLE TimerQueue, HANDLE Timer, ULONG DueTime, ULONG Period)
{
struct timespec CurrentTime;
WINPR_TIMER_QUEUE* timerQueue;
WINPR_TIMER_QUEUE_TIMER* timer;
WINPR_TIMER_QUEUE *timerQueue;
WINPR_TIMER_QUEUE_TIMER *timer;
if (!TimerQueue || !Timer)
return FALSE;
timespec_gettimeofday(&CurrentTime);
timerQueue = (WINPR_TIMER_QUEUE*) TimerQueue;
timer = (WINPR_TIMER_QUEUE_TIMER*) Timer;
timerQueue = (WINPR_TIMER_QUEUE *) TimerQueue;
timer = (WINPR_TIMER_QUEUE_TIMER *) Timer;
pthread_mutex_lock(&(timerQueue->cond_mutex));
RemoveTimerQueueTimer(&(timerQueue->activeHead), timer);
RemoveTimerQueueTimer(&(timerQueue->inactiveHead), timer);
timer->DueTime = DueTime;
timer->Period = Period;
timer->next = NULL;
timespec_copy(&(timer->StartTime), &CurrentTime);
timespec_add_ms(&(timer->StartTime), DueTime);
timespec_copy(&(timer->ExpirationTime), &(timer->StartTime));
InsertTimerQueueTimer(&(timerQueue->activeHead), timer);
pthread_cond_signal(&(timerQueue->cond));
pthread_mutex_unlock(&(timerQueue->cond_mutex));
return TRUE;
}
BOOL DeleteTimerQueueTimer(HANDLE TimerQueue, HANDLE Timer, HANDLE CompletionEvent)
{
WINPR_TIMER_QUEUE* timerQueue;
WINPR_TIMER_QUEUE_TIMER* timer;
WINPR_TIMER_QUEUE *timerQueue;
WINPR_TIMER_QUEUE_TIMER *timer;
if (!TimerQueue || !Timer)
return FALSE;
timerQueue = (WINPR_TIMER_QUEUE*) TimerQueue;
timer = (WINPR_TIMER_QUEUE_TIMER*) Timer;
timerQueue = (WINPR_TIMER_QUEUE *) TimerQueue;
timer = (WINPR_TIMER_QUEUE_TIMER *) Timer;
pthread_mutex_lock(&(timerQueue->cond_mutex));
if (CompletionEvent == INVALID_HANDLE_VALUE)
@ -746,13 +689,11 @@ BOOL DeleteTimerQueueTimer(HANDLE TimerQueue, HANDLE Timer, HANDLE CompletionEve
else
{
/* Cancel timer and return immediately */
RemoveTimerQueueTimer(&(timerQueue->activeHead), timer);
}
pthread_cond_signal(&(timerQueue->cond));
pthread_mutex_unlock(&(timerQueue->cond_mutex));
free(timer);
if (CompletionEvent && (CompletionEvent != INVALID_HANDLE_VALUE))

View File

@ -49,6 +49,9 @@
#include "../thread/thread.h"
#include <winpr/thread.h>
#include "../log.h"
#define TAG "winpr.sync.wait"
/**
* WaitForSingleObject
* WaitForSingleObjectEx
@ -79,16 +82,12 @@ int clock_gettime(int clk_id, struct timespec *t)
double seconds;
double nseconds;
mach_timebase_info_data_t timebase;
mach_timebase_info(&timebase);
time = mach_absolute_time();
nseconds = ((double) time * (double) timebase.numer) / ((double) timebase.denom);
seconds = ((double) time * (double) timebase.numer) / ((double) timebase.denom * 1e9);
t->tv_sec = seconds;
t->tv_nsec = nseconds;
return 0;
}
@ -101,16 +100,15 @@ int clock_gettime(int clk_id, struct timespec *t)
#include <pthread.h>
static long long ts_difftime(const struct timespec *o,
const struct timespec *n)
const struct timespec *n)
{
long long oldValue = o->tv_sec * 1000000000LL + o->tv_nsec;
long long newValue = n->tv_sec * 1000000000LL + n->tv_nsec;
return newValue - oldValue;
}
static int pthread_timedjoin_np(pthread_t td, void **res,
struct timespec *timeout)
struct timespec *timeout)
{
struct timespec timenow;
struct timespec sleepytime;
@ -124,7 +122,6 @@ static int pthread_timedjoin_np(pthread_t td, void **res,
return pthread_join(td, res);
nanosleep(&sleepytime, NULL);
clock_gettime(CLOCK_MONOTONIC, &timenow);
if (ts_difftime(timeout, &timenow) >= 0)
@ -138,21 +135,20 @@ static int pthread_timedjoin_np(pthread_t td, void **res,
}
#if defined(__FreeBSD__)
/*the only way to get it work is to remove the static*/
int pthread_mutex_timedlock(pthread_mutex_t *mutex, const struct timespec *timeout)
/*the only way to get it work is to remove the static*/
int pthread_mutex_timedlock(pthread_mutex_t *mutex, const struct timespec *timeout)
#else
static int pthread_mutex_timedlock(pthread_mutex_t *mutex, const struct timespec *timeout)
static int pthread_mutex_timedlock(pthread_mutex_t *mutex, const struct timespec *timeout)
#endif
{
struct timespec timenow;
struct timespec sleepytime;
int retcode;
/* This is just to avoid a completely busy wait */
sleepytime.tv_sec = 0;
sleepytime.tv_nsec = 10000000; /* 10ms */
while ((retcode = pthread_mutex_trylock (mutex)) == EBUSY)
while ((retcode = pthread_mutex_trylock(mutex)) == EBUSY)
{
clock_gettime(CLOCK_MONOTONIC, &timenow);
@ -161,7 +157,7 @@ static int pthread_timedjoin_np(pthread_t td, void **res,
return ETIMEDOUT;
}
nanosleep (&sleepytime, NULL);
nanosleep(&sleepytime, NULL);
}
return retcode;
@ -172,7 +168,6 @@ static void ts_add_ms(struct timespec *ts, DWORD dwMilliseconds)
{
ts->tv_sec += dwMilliseconds / 1000L;
ts->tv_nsec += (dwMilliseconds % 1000L) * 1000000L;
ts->tv_sec += ts->tv_nsec / 1000000000L;
ts->tv_nsec = ts->tv_nsec % 1000000000L;
}
@ -180,10 +175,8 @@ static void ts_add_ms(struct timespec *ts, DWORD dwMilliseconds)
static int waitOnFd(int fd, DWORD dwMilliseconds)
{
int status;
#ifdef HAVE_POLL_H
struct pollfd pollfds;
pollfds.fd = fd;
pollfds.events = POLLIN;
pollfds.revents = 0;
@ -197,7 +190,6 @@ static int waitOnFd(int fd, DWORD dwMilliseconds)
#else
struct timeval timeout;
fd_set rfds;
FD_ZERO(&rfds);
FD_SET(fd, &rfds);
ZeroMemory(&timeout, sizeof(timeout));
@ -213,8 +205,8 @@ static int waitOnFd(int fd, DWORD dwMilliseconds)
status = select(fd + 1, &rfds, NULL, NULL, (dwMilliseconds == INFINITE) ? NULL : &timeout);
}
while (status < 0 && (errno == EINTR));
#endif
#endif
return status;
}
@ -225,17 +217,16 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if (!winpr_Handle_GetInfo(hHandle, &Type, &Object))
{
fprintf(stderr, "WaitForSingleObject failed: invalid hHandle.\n");
WLog_ERR(TAG, "invalid hHandle.");
return WAIT_FAILED;
}
if (Type == HANDLE_TYPE_THREAD)
{
int status = 0;
WINPR_THREAD* thread;
void* thread_status = NULL;
thread = (WINPR_THREAD*) Object;
WINPR_THREAD *thread;
void *thread_status = NULL;
thread = (WINPR_THREAD *) Object;
if (thread->started)
{
@ -250,7 +241,6 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
clock_gettime(CLOCK_MONOTONIC, &timeout);
ts_add_ms(&timeout, dwMilliseconds);
status = pthread_timedjoin_np(thread->thread, &thread_status, &timeout);
if (ETIMEDOUT == status)
@ -263,23 +253,22 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if (status != 0)
{
fprintf(stderr, "WaitForSingleObject: pthread_join failure: [%d] %s\n",
status, strerror(status));
WLog_ERR(TAG, "pthread_join failure: [%d] %s",
status, strerror(status));
}
if (thread_status)
thread->dwExitCode = ((DWORD) (size_t) thread_status);
thread->dwExitCode = ((DWORD)(size_t) thread_status);
}
}
else if (Type == HANDLE_TYPE_PROCESS)
{
WINPR_PROCESS* process;
process = (WINPR_PROCESS*) Object;
WINPR_PROCESS *process;
process = (WINPR_PROCESS *) Object;
if (waitpid(process->pid, &(process->status), 0) != -1)
{
fprintf(stderr, "WaitForSingleObject: waitpid failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "waitpid failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
@ -287,18 +276,15 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
}
else if (Type == HANDLE_TYPE_MUTEX)
{
WINPR_MUTEX* mutex;
mutex = (WINPR_MUTEX*) Object;
WINPR_MUTEX *mutex;
mutex = (WINPR_MUTEX *) Object;
if (dwMilliseconds != INFINITE)
{
int status;
struct timespec timeout;
clock_gettime(CLOCK_MONOTONIC, &timeout);
ts_add_ms(&timeout, dwMilliseconds);
ts_add_ms(&timeout, dwMilliseconds);
status = pthread_mutex_timedlock(&mutex->mutex, &timeout);
if (ETIMEDOUT == status)
@ -312,15 +298,13 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
else if (Type == HANDLE_TYPE_EVENT)
{
int status;
WINPR_EVENT* event;
event = (WINPR_EVENT*) Object;
WINPR_EVENT *event;
event = (WINPR_EVENT *) Object;
status = waitOnFd(event->pipe_fd[0], dwMilliseconds);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: event select() failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "event select() failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
@ -329,20 +313,19 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
}
else if (Type == HANDLE_TYPE_SEMAPHORE)
{
WINPR_SEMAPHORE* semaphore;
semaphore = (WINPR_SEMAPHORE*) Object;
WINPR_SEMAPHORE *semaphore;
semaphore = (WINPR_SEMAPHORE *) Object;
#ifdef WINPR_PIPE_SEMAPHORE
if (semaphore->pipe_fd[0] != -1)
{
int status;
int length;
status = waitOnFd(semaphore->pipe_fd[0], dwMilliseconds);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: semaphore select() failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "semaphore select() failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
@ -353,43 +336,41 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if (length != 1)
{
fprintf(stderr, "WaitForSingleObject: semaphore read failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "semaphore read failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
}
#else
#else
#if defined __APPLE__
semaphore_wait(*((winpr_sem_t*) semaphore->sem));
semaphore_wait(*((winpr_sem_t *) semaphore->sem));
#else
sem_wait((winpr_sem_t*) semaphore->sem);
sem_wait((winpr_sem_t *) semaphore->sem);
#endif
#endif
}
else if (Type == HANDLE_TYPE_TIMER)
{
WINPR_TIMER* timer;
timer = (WINPR_TIMER*) Object;
WINPR_TIMER *timer;
timer = (WINPR_TIMER *) Object;
#ifdef HAVE_EVENTFD_H
if (timer->fd != -1)
{
int status;
UINT64 expirations;
status = waitOnFd(timer->fd, dwMilliseconds);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: timer select() failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "timer select() failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
if (status != 1)
return WAIT_TIMEOUT;
status = read(timer->fd, (void*) &expirations, sizeof(UINT64));
status = read(timer->fd, (void *) &expirations, sizeof(UINT64));
if (status != 8)
{
@ -398,11 +379,11 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
if (errno == ETIMEDOUT)
return WAIT_TIMEOUT;
fprintf(stderr, "WaitForSingleObject: timer read() failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "timer read() failure [%d] %s", errno, strerror(errno));
}
else
{
fprintf(stderr, "WaitForSingleObject: timer read() failure - incorrect number of bytes read");
WLog_ERR(TAG, "timer read() failure - incorrect number of bytes read");
}
return WAIT_FAILED;
@ -410,12 +391,12 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
}
else
{
fprintf(stderr, "WaitForSingleObject: invalid timer file descriptor\n");
WLog_ERR(TAG, "invalid timer file descriptor");
return WAIT_FAILED;
}
#else
fprintf(stderr, "WaitForSingleObject: file descriptors not supported\n");
WLog_ERR(TAG, "file descriptors not supported");
return WAIT_FAILED;
#endif
}
@ -423,20 +404,20 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
{
int fd;
int status;
WINPR_NAMED_PIPE* pipe = (WINPR_NAMED_PIPE*) Object;
WINPR_NAMED_PIPE *pipe = (WINPR_NAMED_PIPE *) Object;
fd = (pipe->ServerMode) ? pipe->serverfd : pipe->clientfd;
if (fd == -1)
{
fprintf(stderr, "WaitForSingleObject: invalid pipe file descriptor\n");
WLog_ERR(TAG, "invalid pipe file descriptor");
return WAIT_FAILED;
}
status = waitOnFd(fd, dwMilliseconds);
if (status < 0)
{
fprintf(stderr, "WaitForSingleObject: named pipe select() failure [%d] %s\n", errno, strerror(errno));
WLog_ERR(TAG, "named pipe select() failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
@ -447,7 +428,7 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
}
else
{
fprintf(stderr, "WaitForSingleObject: unknown handle type %d\n", (int) Type);
WLog_ERR(TAG, "unknown handle type %d", (int) Type);
}
return WAIT_OBJECT_0;
@ -455,14 +436,14 @@ DWORD WaitForSingleObject(HANDLE hHandle, DWORD dwMilliseconds)
DWORD WaitForSingleObjectEx(HANDLE hHandle, DWORD dwMilliseconds, BOOL bAlertable)
{
fprintf(stderr, "[ERROR] %s: Function not implemented.\n", __func__);
WLog_ERR(TAG, "Function not implemented.");
assert(0);
return WAIT_OBJECT_0;
}
#define MAXIMUM_WAIT_OBJECTS 64
DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAll, DWORD dwMilliseconds)
DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE *lpHandles, BOOL bWaitAll, DWORD dwMilliseconds)
{
int fd = -1;
int index;
@ -479,7 +460,7 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
if (!nCount || (nCount > MAXIMUM_WAIT_OBJECTS))
{
fprintf(stderr, "%s: invalid handles count(%d)\n", __FUNCTION__, nCount);
WLog_ERR(TAG, "invalid handles count(%d)", nCount);
return WAIT_FAILED;
}
@ -489,12 +470,11 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
maxfd = 0;
FD_ZERO(&fds);
ZeroMemory(&timeout, sizeof(timeout));
#endif
if (bWaitAll)
{
fprintf(stderr, "%s: bWaitAll not yet implemented\n", __FUNCTION__);
WLog_ERR(TAG, "bWaitAll not yet implemented");
assert(0);
}
@ -502,61 +482,60 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
{
if (!winpr_Handle_GetInfo(lpHandles[index], &Type, &Object))
{
fprintf(stderr, "%s: invalid handle\n", __FUNCTION__);
WLog_ERR(TAG, "invalid handle");
return WAIT_FAILED;
}
if (Type == HANDLE_TYPE_EVENT)
{
fd = ((WINPR_EVENT*) Object)->pipe_fd[0];
fd = ((WINPR_EVENT *) Object)->pipe_fd[0];
if (fd == -1)
{
fprintf(stderr, "%s: invalid event file descriptor\n", __FUNCTION__);
WLog_ERR(TAG, "invalid event file descriptor");
return WAIT_FAILED;
}
}
else if (Type == HANDLE_TYPE_SEMAPHORE)
{
#ifdef WINPR_PIPE_SEMAPHORE
fd = ((WINPR_SEMAPHORE*) Object)->pipe_fd[0];
fd = ((WINPR_SEMAPHORE *) Object)->pipe_fd[0];
#else
fprintf(stderr, "%s: semaphore not supported\n", __FUNCTION__);
WLog_ERR(TAG, "semaphore not supported");
return WAIT_FAILED;
#endif
}
else if (Type == HANDLE_TYPE_TIMER)
{
WINPR_TIMER* timer = (WINPR_TIMER*) Object;
WINPR_TIMER *timer = (WINPR_TIMER *) Object;
fd = timer->fd;
if (fd == -1)
{
fprintf(stderr, "%s: invalid timer file descriptor\n", __FUNCTION__);
WLog_ERR(TAG, "invalid timer file descriptor");
return WAIT_FAILED;
}
}
else if (Type == HANDLE_TYPE_NAMED_PIPE)
{
WINPR_NAMED_PIPE* pipe = (WINPR_NAMED_PIPE*) Object;
WINPR_NAMED_PIPE *pipe = (WINPR_NAMED_PIPE *) Object;
fd = (pipe->ServerMode) ? pipe->serverfd : pipe->clientfd;
if (fd == -1)
{
fprintf(stderr, "%s: invalid timer file descriptor\n", __FUNCTION__);
WLog_ERR(TAG, "invalid timer file descriptor");
return WAIT_FAILED;
}
}
else
{
fprintf(stderr, "%s: unknown handle type %d\n", __FUNCTION__, (int) Type);
WLog_ERR(TAG, "unknown handle type %d", (int) Type);
return WAIT_FAILED;
}
if (fd == -1)
{
fprintf(stderr, "%s: invalid file descriptor\n", __FUNCTION__);
WLog_ERR(TAG, "invalid file descriptor");
return WAIT_FAILED;
}
@ -569,16 +548,20 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
if (fd > maxfd)
maxfd = fd;
#endif
}
#ifdef HAVE_POLL_H
do
{
status = poll(pollfds, nCount, dwMilliseconds);
}
while (status < 0 && errno == EINTR);
#else
if ((dwMilliseconds != INFINITE) && (dwMilliseconds != 0))
{
timeout.tv_sec = dwMilliseconds / 1000;
@ -588,14 +571,15 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
do
{
status = select(maxfd + 1, &fds, 0, 0,
(dwMilliseconds == INFINITE) ? NULL : &timeout);
(dwMilliseconds == INFINITE) ? NULL : &timeout);
}
while (status < 0 && errno == EINTR);
#endif
if (status < 0)
{
fprintf(stderr, "%s: select() failure [%d] %s\n", __FUNCTION__, errno, strerror(errno));
WLog_ERR(TAG, "select() failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
@ -608,24 +592,25 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
if (Type == HANDLE_TYPE_EVENT)
{
fd = ((WINPR_EVENT*) Object)->pipe_fd[0];
fd = ((WINPR_EVENT *) Object)->pipe_fd[0];
}
else if (Type == HANDLE_TYPE_SEMAPHORE)
{
fd = ((WINPR_SEMAPHORE*) Object)->pipe_fd[0];
fd = ((WINPR_SEMAPHORE *) Object)->pipe_fd[0];
}
else if (Type == HANDLE_TYPE_TIMER)
{
WINPR_TIMER* timer = (WINPR_TIMER*) Object;
WINPR_TIMER *timer = (WINPR_TIMER *) Object;
fd = timer->fd;
}
else if (Type == HANDLE_TYPE_NAMED_PIPE)
{
WINPR_NAMED_PIPE* pipe = (WINPR_NAMED_PIPE*) Object;
WINPR_NAMED_PIPE *pipe = (WINPR_NAMED_PIPE *) Object;
fd = (pipe->ServerMode) ? pipe->serverfd : pipe->clientfd;
}
#ifdef HAVE_POLL_H
if (pollfds[index].revents & POLLIN)
#else
if (FD_ISSET(fd, &fds))
@ -634,12 +619,11 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
if (Type == HANDLE_TYPE_SEMAPHORE)
{
int length;
length = read(fd, &length, 1);
if (length != 1)
{
fprintf(stderr, "%s: semaphore read() failure [%d] %s\n", __FUNCTION__, errno, strerror(errno));
WLog_ERR(TAG, "semaphore read() failure [%d] %s", errno, strerror(errno));
return WAIT_FAILED;
}
}
@ -647,8 +631,7 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
{
int length;
UINT64 expirations;
length = read(fd, (void*) &expirations, sizeof(UINT64));
length = read(fd, (void *) &expirations, sizeof(UINT64));
if (length != 8)
{
@ -657,11 +640,11 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
if (errno == ETIMEDOUT)
return WAIT_TIMEOUT;
fprintf(stderr, "%s: timer read() failure [%d] %s\n", __FUNCTION__, errno, strerror(errno));
WLog_ERR(TAG, "timer read() failure [%d] %s", errno, strerror(errno));
}
else
{
fprintf(stderr, "%s: timer read() failure - incorrect number of bytes read", __FUNCTION__);
WLog_ERR(TAG, "timer read() failure - incorrect number of bytes read");
}
return WAIT_FAILED;
@ -672,20 +655,20 @@ DWORD WaitForMultipleObjects(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAl
}
}
fprintf(stderr, "%s: failed (unknown error)\n", __FUNCTION__);
WLog_ERR(TAG, "failed (unknown error)");
return WAIT_FAILED;
}
DWORD WaitForMultipleObjectsEx(DWORD nCount, const HANDLE* lpHandles, BOOL bWaitAll, DWORD dwMilliseconds, BOOL bAlertable)
DWORD WaitForMultipleObjectsEx(DWORD nCount, const HANDLE *lpHandles, BOOL bWaitAll, DWORD dwMilliseconds, BOOL bAlertable)
{
fprintf(stderr, "[ERROR] %s: Function not implemented.\n", __func__);
WLog_ERR(TAG, "[ERROR] %s: Function not implemented.");
assert(0);
return 0;
}
DWORD SignalObjectAndWait(HANDLE hObjectToSignal, HANDLE hObjectToWaitOn, DWORD dwMilliseconds, BOOL bAlertable)
{
fprintf(stderr, "[ERROR] %s: Function not implemented.\n", __func__);
WLog_ERR(TAG, "Function not implemented.");
assert(0);
return 0;
}

View File

@ -68,10 +68,12 @@ defined(__OpenBSD__) || defined(__DragonFly__)
#include <sys/sysctl.h>
#endif
#include "../log.h"
#define TAG "sysinfo"
static DWORD GetProcessorArchitecture()
{
DWORD cpuArch = PROCESSOR_ARCHITECTURE_UNKNOWN;
#if defined(_M_AMD64)
cpuArch = PROCESSOR_ARCHITECTURE_AMD64;
#elif defined(_M_IX86)
@ -87,16 +89,13 @@ static DWORD GetProcessorArchitecture()
#elif defined(_M_ALPHA)
cpuArch = PROCESSOR_ARCHITECTURE_ALPHA;
#endif
return cpuArch;
}
static DWORD GetNumberOfProcessors()
{
DWORD numCPUs = 1;
/* TODO: iOS */
#if defined(__linux__) || defined(__sun) || defined(_AIX)
numCPUs = (DWORD) sysconf(_SC_NPROCESSORS_ONLN);
#elif defined(__MACOSX__) || \
@ -105,14 +104,12 @@ static DWORD GetNumberOfProcessors()
{
int mib[4];
size_t length = sizeof(numCPUs);
mib[0] = CTL_HW;
#if defined(__FreeBSD__)
mib[1] = HW_NCPU;
#else
mib[1] = HW_AVAILCPU;
#endif
#if defined(__FreeBSD__)
mib[1] = HW_NCPU;
#else
mib[1] = HW_AVAILCPU;
#endif
sysctl(mib, 2, &numCPUs, &length, NULL, 0);
if (numCPUs < 1)
@ -129,7 +126,6 @@ static DWORD GetNumberOfProcessors()
#elif defined(__sgi)
numCPUs = (DWORD) sysconf(_SC_NPROC_ONLN);
#endif
return numCPUs;
}
@ -137,17 +133,13 @@ void GetSystemInfo(LPSYSTEM_INFO lpSystemInfo)
{
lpSystemInfo->wProcessorArchitecture = GetProcessorArchitecture();
lpSystemInfo->wReserved = 0;
lpSystemInfo->dwPageSize = 0;
lpSystemInfo->lpMinimumApplicationAddress = NULL;
lpSystemInfo->lpMaximumApplicationAddress = NULL;
lpSystemInfo->dwActiveProcessorMask = 0;
lpSystemInfo->dwNumberOfProcessors = GetNumberOfProcessors();
lpSystemInfo->dwProcessorType = 0;
lpSystemInfo->dwAllocationGranularity = 0;
lpSystemInfo->wProcessorLevel = 0;
lpSystemInfo->wProcessorRevision = 0;
}
@ -159,13 +151,11 @@ void GetNativeSystemInfo(LPSYSTEM_INFO lpSystemInfo)
BOOL GetComputerNameA(LPSTR lpBuffer, LPDWORD lpnSize)
{
char* dot;
char *dot;
int length;
char hostname[256];
gethostname(hostname, sizeof(hostname));
length = strlen(hostname);
dot = strchr(hostname, '.');
if (dot)
@ -182,7 +172,6 @@ BOOL GetComputerNameA(LPSTR lpBuffer, LPDWORD lpnSize)
CopyMemory(lpBuffer, hostname, length);
lpBuffer[length] = '\0';
return TRUE;
}
@ -217,9 +206,7 @@ BOOL GetComputerNameExA(COMPUTER_NAME_FORMAT NameType, LPSTR lpBuffer, LPDWORD l
CopyMemory(lpBuffer, hostname, length);
lpBuffer[length] = '\0';
break;
default:
return FALSE;
}
@ -229,7 +216,7 @@ BOOL GetComputerNameExA(COMPUTER_NAME_FORMAT NameType, LPSTR lpBuffer, LPDWORD l
BOOL GetComputerNameExW(COMPUTER_NAME_FORMAT NameType, LPWSTR lpBuffer, LPDWORD nSize)
{
fprintf(stderr, "GetComputerNameExW unimplemented\n");
WLog_ERR(TAG, "GetComputerNameExW unimplemented\n");
return 0;
}
@ -240,9 +227,8 @@ BOOL GetComputerNameExW(COMPUTER_NAME_FORMAT NameType, LPWSTR lpBuffer, LPDWORD
BOOL GetVersionExA(LPOSVERSIONINFOA lpVersionInformation)
{
/* Windows 7 SP1 Version Info */
if ((lpVersionInformation->dwOSVersionInfoSize == sizeof(OSVERSIONINFOA)) ||
(lpVersionInformation->dwOSVersionInfoSize == sizeof(OSVERSIONINFOEXA)))
(lpVersionInformation->dwOSVersionInfoSize == sizeof(OSVERSIONINFOEXA)))
{
lpVersionInformation->dwMajorVersion = 6;
lpVersionInformation->dwMinorVersion = 1;
@ -253,7 +239,6 @@ BOOL GetVersionExA(LPOSVERSIONINFOA lpVersionInformation)
if (lpVersionInformation->dwOSVersionInfoSize == sizeof(OSVERSIONINFOEXA))
{
LPOSVERSIONINFOEXA lpVersionInformationEx = (LPOSVERSIONINFOEXA) lpVersionInformation;
lpVersionInformationEx->wServicePackMajor = 1;
lpVersionInformationEx->wServicePackMinor = 0;
lpVersionInformationEx->wSuiteMask = 0;
@ -269,27 +254,24 @@ BOOL GetVersionExA(LPOSVERSIONINFOA lpVersionInformation)
BOOL GetVersionExW(LPOSVERSIONINFOW lpVersionInformation)
{
fprintf(stderr, "GetVersionExW unimplemented\n");
WLog_ERR(TAG, "GetVersionExW unimplemented\n");
return 1;
}
void GetSystemTime(LPSYSTEMTIME lpSystemTime)
{
time_t ct = 0;
struct tm* stm = NULL;
struct tm *stm = NULL;
WORD wMilliseconds = 0;
ct = time(NULL);
wMilliseconds = (WORD) (GetTickCount() % 1000);
wMilliseconds = (WORD)(GetTickCount() % 1000);
stm = gmtime(&ct);
ZeroMemory(lpSystemTime, sizeof(SYSTEMTIME));
if (stm)
{
lpSystemTime->wYear = (WORD) (stm->tm_year + 1900);
lpSystemTime->wMonth = (WORD) (stm->tm_mon + 1);
lpSystemTime->wYear = (WORD)(stm->tm_year + 1900);
lpSystemTime->wMonth = (WORD)(stm->tm_mon + 1);
lpSystemTime->wDayOfWeek = (WORD) stm->tm_wday;
lpSystemTime->wDay = (WORD) stm->tm_mday;
lpSystemTime->wHour = (WORD) stm->tm_hour;
@ -299,7 +281,7 @@ void GetSystemTime(LPSYSTEMTIME lpSystemTime)
}
}
BOOL SetSystemTime(CONST SYSTEMTIME* lpSystemTime)
BOOL SetSystemTime(CONST SYSTEMTIME *lpSystemTime)
{
return FALSE;
}
@ -307,20 +289,17 @@ BOOL SetSystemTime(CONST SYSTEMTIME* lpSystemTime)
VOID GetLocalTime(LPSYSTEMTIME lpSystemTime)
{
time_t ct = 0;
struct tm* ltm = NULL;
struct tm *ltm = NULL;
WORD wMilliseconds = 0;
ct = time(NULL);
wMilliseconds = (WORD) (GetTickCount() % 1000);
wMilliseconds = (WORD)(GetTickCount() % 1000);
ltm = localtime(&ct);
ZeroMemory(lpSystemTime, sizeof(SYSTEMTIME));
if (ltm)
{
lpSystemTime->wYear = (WORD) (ltm->tm_year + 1900);
lpSystemTime->wMonth = (WORD) (ltm->tm_mon + 1);
lpSystemTime->wYear = (WORD)(ltm->tm_year + 1900);
lpSystemTime->wMonth = (WORD)(ltm->tm_mon + 1);
lpSystemTime->wDayOfWeek = (WORD) ltm->tm_wday;
lpSystemTime->wDay = (WORD) ltm->tm_mday;
lpSystemTime->wHour = (WORD) ltm->tm_hour;
@ -330,7 +309,7 @@ VOID GetLocalTime(LPSYSTEMTIME lpSystemTime)
}
}
BOOL SetLocalTime(CONST SYSTEMTIME* lpSystemTime)
BOOL SetLocalTime(CONST SYSTEMTIME *lpSystemTime)
{
return FALSE;
}
@ -338,14 +317,10 @@ BOOL SetLocalTime(CONST SYSTEMTIME* lpSystemTime)
VOID GetSystemTimeAsFileTime(LPFILETIME lpSystemTimeAsFileTime)
{
ULARGE_INTEGER time64;
time64.u.HighPart = 0;
/* time represented in tenths of microseconds since midnight of January 1, 1601 */
time64.QuadPart = time(NULL) + 11644473600LL; /* Seconds since January 1, 1601 */
time64.QuadPart *= 10000000; /* Convert timestamp to tenths of a microsecond */
lpSystemTimeAsFileTime->dwLowDateTime = time64.LowPart;
lpSystemTimeAsFileTime->dwHighDateTime = time64.HighPart;
}
@ -362,28 +337,23 @@ BOOL GetSystemTimeAdjustment(PDWORD lpTimeAdjustment, PDWORD lpTimeIncrement, PB
DWORD GetTickCount(void)
{
DWORD ticks = 0;
#ifdef __linux__
struct timespec ts;
if (!clock_gettime(CLOCK_MONOTONIC_RAW, &ts))
ticks = (ts.tv_sec * 1000) + (ts.tv_nsec / 1000000);
#else
/**
* FIXME: this is relative to the Epoch time, and we
* need to return a value relative to the system uptime.
*/
struct timeval tv;
if (!gettimeofday(&tv, NULL))
ticks = (tv.tv_sec * 1000) + (tv.tv_usec / 1000);
#endif
return ticks;
}
#endif // _WIN32
@ -393,32 +363,25 @@ DWORD GetTickCount(void)
ULONGLONG GetTickCount64(void)
{
ULONGLONG ticks = 0;
#if defined(__linux__)
struct timespec ts;
if (!clock_gettime(CLOCK_MONOTONIC_RAW, &ts))
ticks = (ts.tv_sec * 1000) + (ts.tv_nsec / 1000000);
#elif defined(_WIN32)
ticks = (ULONGLONG) GetTickCount();
#else
/**
* FIXME: this is relative to the Epoch time, and we
* need to return a value relative to the system uptime.
*/
struct timeval tv;
if (!gettimeofday(&tv, NULL))
ticks = (tv.tv_sec * 1000) + (tv.tv_usec / 1000);
#endif
return ticks;
}
@ -429,7 +392,7 @@ ULONGLONG GetTickCount64(void)
#if defined(__GNUC__) && defined(__AVX__)
#define xgetbv(_func_, _lo_, _hi_) \
__asm__ __volatile__ ("xgetbv" : "=a" (_lo_), "=d" (_hi_) : "c" (_func_))
__asm__ __volatile__ ("xgetbv" : "=a" (_lo_), "=d" (_hi_) : "c" (_func_))
#endif
#define D_BIT_MMX (1<<23)
@ -454,33 +417,31 @@ ULONGLONG GetTickCount64(void)
#define E_BITS_AVX (E_BIT_XMM|E_BIT_YMM)
static void cpuid(
unsigned info,
unsigned *eax,
unsigned *ebx,
unsigned *ecx,
unsigned *edx)
unsigned info,
unsigned *eax,
unsigned *ebx,
unsigned *ecx,
unsigned *edx)
{
#ifdef __GNUC__
*eax = *ebx = *ecx = *edx = 0;
__asm volatile
(
/* The EBX (or RBX register on x86_64) is used for the PIC base address
* and must not be corrupted by our inline assembly.
*/
*eax = *ebx = *ecx = *edx = 0;
__asm volatile
(
/* The EBX (or RBX register on x86_64) is used for the PIC base address
* and must not be corrupted by our inline assembly.
*/
#ifdef _M_IX86
"mov %%ebx, %%esi;"
"cpuid;"
"xchg %%ebx, %%esi;"
"mov %%ebx, %%esi;"
"cpuid;"
"xchg %%ebx, %%esi;"
#else
"mov %%rbx, %%rsi;"
"cpuid;"
"xchg %%rbx, %%rsi;"
"mov %%rbx, %%rsi;"
"cpuid;"
"xchg %%rbx, %%rsi;"
#endif
: "=a" (*eax), "=S" (*ebx), "=c" (*ecx), "=d" (*edx)
: "0" (info)
);
: "=a"(*eax), "=S"(*ebx), "=c"(*ecx), "=d"(*edx)
: "0"(info)
);
#elif defined(_MSC_VER)
int a[4];
__cpuid(a, info);
@ -518,10 +479,10 @@ static void cpuid(
// From linux kernel uapi/linux/auxvec.h
#define AT_HWCAP 16
static unsigned GetARMCPUCaps(void){
static unsigned GetARMCPUCaps(void)
{
unsigned caps = 0;
int fd = open ("/proc/self/auxv", O_RDONLY);
int fd = open("/proc/self/auxv", O_RDONLY);
if (fd == -1)
return 0;
@ -532,16 +493,20 @@ static unsigned GetARMCPUCaps(void){
unsigned a_val; /* Integer value */
} auxvec;
while (1){
while (1)
{
int num;
num = read(fd, (char *)&auxvec, sizeof(auxvec));
if (num < 1 || (auxvec.a_type == 0 && auxvec.a_val == 0))
break;
if (auxvec.a_type == AT_HWCAP)
break;
if (auxvec.a_type == AT_HWCAP)
{
caps = auxvec.a_val;
caps = auxvec.a_val;
}
}
close(fd);
return caps;
}
@ -563,50 +528,74 @@ BOOL IsProcessorFeaturePresent(DWORD ProcessorFeature)
{
case PF_ARM_NEON_INSTRUCTIONS_AVAILABLE:
case PF_ARM_NEON:
if (caps & HWCAP_NEON)
ret = TRUE;
break;
case PF_ARM_THUMB:
if (caps & HWCAP_THUMB)
ret = TRUE;
case PF_ARM_VFP_32_REGISTERS_AVAILABLE:
if (caps & HWCAP_VFPD32)
ret = TRUE;
case PF_ARM_DIVIDE_INSTRUCTION_AVAILABLE:
if ((caps & HWCAP_IDIVA) || (caps & HWCAP_IDIVT))
ret = TRUE;
case PF_ARM_VFP3:
if (caps & HWCAP_VFPv3)
ret = TRUE;
break;
case PF_ARM_JAZELLE:
if (caps & HWCAP_JAVA)
ret = TRUE;
break;
case PF_ARM_DSP:
if (caps & HWCAP_EDSP)
ret = TRUE;
break;
case PF_ARM_MPU:
if (caps & HWCAP_EDSP)
ret = TRUE;
break;
case PF_ARM_THUMB2:
if ((caps & HWCAP_IDIVT) || (caps & HWCAP_VFPv4))
ret = TRUE;
break;
case PF_ARM_T2EE:
if (caps & HWCAP_THUMBEE)
ret = TRUE;
break;
case PF_ARM_INTEL_WMMX:
if (caps & HWCAP_IWMMXT)
ret = TRUE;
break;
default:
break;
}
#elif defined(__APPLE__) // __linux__
switch (ProcessorFeature)
{
case PF_ARM_NEON_INSTRUCTIONS_AVAILABLE:
@ -614,34 +603,44 @@ BOOL IsProcessorFeaturePresent(DWORD ProcessorFeature)
ret = TRUE;
break;
}
#endif // __linux__
#elif defined(_M_IX86_AMD64)
#ifdef __GNUC__
unsigned a, b, c, d;
cpuid(1, &a, &b, &c, &d);
switch (ProcessorFeature)
{
case PF_MMX_INSTRUCTIONS_AVAILABLE:
case PF_MMX_INSTRUCTIONS_AVAILABLE:
if (d & D_BIT_MMX)
ret = TRUE;
break;
case PF_XMMI_INSTRUCTIONS_AVAILABLE:
case PF_XMMI_INSTRUCTIONS_AVAILABLE:
if (d & D_BIT_SSE)
ret = TRUE;
break;
case PF_XMMI64_INSTRUCTIONS_AVAILABLE:
case PF_XMMI64_INSTRUCTIONS_AVAILABLE:
if (d & D_BIT_SSE2)
ret = TRUE;
break;
case PF_3DNOW_INSTRUCTIONS_AVAILABLE:
if (d & D_BIT_3DN)
ret = TRUE;
break;
case PF_SSE3_INSTRUCTIONS_AVAILABLE:
case PF_SSE3_INSTRUCTIONS_AVAILABLE:
if (c & C_BIT_SSE3)
ret = TRUE;
break;
default:
break;
@ -665,26 +664,37 @@ BOOL IsProcessorFeaturePresentEx(DWORD ProcessorFeature)
switch (ProcessorFeature)
{
case PF_EX_ARM_VFP1:
if (caps & HWCAP_VFP)
ret = TRUE;
break;
case PF_EX_ARM_VFP3D16:
if (caps & HWCAP_VFPv3D16)
ret = TRUE;
break;
case PF_EX_ARM_VFP4:
if (caps & HWCAP_VFPv4)
ret = TRUE;
break;
case PF_EX_ARM_IDIVA:
if (caps & HWCAP_IDIVA)
ret = TRUE;
break;
case PF_EX_ARM_IDIVT:
if (caps & HWCAP_IDIVT)
ret = TRUE;
break;
}
#endif // __linux__
#elif defined(_M_IX86_AMD64)
unsigned a, b, c, d;
@ -693,24 +703,34 @@ BOOL IsProcessorFeaturePresentEx(DWORD ProcessorFeature)
switch (ProcessorFeature)
{
case PF_EX_LZCNT:
if (c & C_BIT_LZCNT)
ret = TRUE;
break;
case PF_EX_3DNOW_PREFETCH:
if (c & C_BIT_3DNP)
ret = TRUE;
break;
case PF_EX_SSSE3:
if (c & C_BIT_SSSE3)
ret = TRUE;
break;
case PF_EX_SSE41:
if (c & C_BIT_SSE41)
ret = TRUE;
break;
case PF_EX_SSE42:
if (c & C_BIT_SSE42)
ret = TRUE;
break;
#if defined(__GNUC__) && defined(__AVX__)
case PF_EX_AVX:
@ -734,25 +754,32 @@ BOOL IsProcessorFeaturePresentEx(DWORD ProcessorFeature)
ret = TRUE;
break;
case PF_EX_FMA:
if (c & C_BIT_FMA)
ret = TRUE;
break;
case PF_EX_AVX_AES:
if (c & C_BIT_AES)
ret = TRUE;
break;
case PF_EX_AVX_PCLMULQDQ:
if (c & C_BIT_PCLMULQDQ)
ret = TRUE;
break;
}
}
}
}
break;
#endif //__AVX__
default:
break;
}
#endif
return ret;
}

View File

@ -31,6 +31,9 @@
#include <unistd.h>
#endif
#include "../log.h"
#define TAG "thread"
/**
* CommandLineToArgvW function:
* http://msdn.microsoft.com/en-us/library/windows/desktop/bb776391/
@ -265,7 +268,7 @@ LPSTR* CommandLineToArgvA(LPCSTR lpCmdLine, int* pNumArgs)
if (p[index] != '"')
{
printf("CommandLineToArgvA parsing error: uneven number of unescaped double quotes!\n");
WLog_ERR(TAG, "parsing error: uneven number of unescaped double quotes!");
}
if (p[index] == '\0')

View File

@ -32,6 +32,9 @@
#include "wtsapi.h"
#include "../log.h"
#define TAG "wtsapi"
/**
* Remote Desktop Services API Functions:
* http://msdn.microsoft.com/en-us/library/windows/desktop/aa383464/
@ -191,9 +194,7 @@ int WtsApi32_InitializeWtsApi(void)
WTSAPI32_LOAD_PROC(GetChildSessionId, WTS_GET_CHILD_SESSION_ID_FN);
WTSAPI32_LOAD_PROC(GetActiveConsoleSessionId, WTS_GET_ACTIVE_CONSOLE_SESSION_ID_FN);
#endif
g_WtsApi = &WtsApi32_WtsApiFunctionTable;
return 1;
}
@ -224,12 +225,12 @@ BOOL WINAPI WTSConnectSessionA(ULONG LogonId, ULONG TargetLogonId, PSTR pPasswor
WTSAPI_STUB_CALL_BOOL(ConnectSessionA, LogonId, TargetLogonId, pPassword, bWait);
}
BOOL WINAPI WTSEnumerateServersW(LPWSTR pDomainName, DWORD Reserved, DWORD Version, PWTS_SERVER_INFOW* ppServerInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateServersW(LPWSTR pDomainName, DWORD Reserved, DWORD Version, PWTS_SERVER_INFOW *ppServerInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateServersW, pDomainName, Reserved, Version, ppServerInfo, pCount);
}
BOOL WINAPI WTSEnumerateServersA(LPSTR pDomainName, DWORD Reserved, DWORD Version, PWTS_SERVER_INFOA* ppServerInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateServersA(LPSTR pDomainName, DWORD Reserved, DWORD Version, PWTS_SERVER_INFOA *ppServerInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateServersA, pDomainName, Reserved, Version, ppServerInfo, pCount);
}
@ -259,32 +260,32 @@ VOID WINAPI WTSCloseServer(HANDLE hServer)
WTSAPI_STUB_CALL_VOID(CloseServer, hServer);
}
BOOL WINAPI WTSEnumerateSessionsW(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_SESSION_INFOW* ppSessionInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateSessionsW(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_SESSION_INFOW *ppSessionInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateSessionsW, hServer, Reserved, Version, ppSessionInfo, pCount);
}
BOOL WINAPI WTSEnumerateSessionsA(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_SESSION_INFOA* ppSessionInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateSessionsA(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_SESSION_INFOA *ppSessionInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateSessionsA, hServer, Reserved, Version, ppSessionInfo, pCount);
}
BOOL WINAPI WTSEnumerateSessionsExW(HANDLE hServer, DWORD* pLevel, DWORD Filter, PWTS_SESSION_INFO_1W* ppSessionInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateSessionsExW(HANDLE hServer, DWORD *pLevel, DWORD Filter, PWTS_SESSION_INFO_1W *ppSessionInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateSessionsExW, hServer, pLevel, Filter, ppSessionInfo, pCount);
}
BOOL WINAPI WTSEnumerateSessionsExA(HANDLE hServer, DWORD* pLevel, DWORD Filter, PWTS_SESSION_INFO_1A* ppSessionInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateSessionsExA(HANDLE hServer, DWORD *pLevel, DWORD Filter, PWTS_SESSION_INFO_1A *ppSessionInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateSessionsExA, hServer, pLevel, Filter, ppSessionInfo, pCount);
}
BOOL WINAPI WTSEnumerateProcessesW(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_PROCESS_INFOW* ppProcessInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateProcessesW(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_PROCESS_INFOW *ppProcessInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateProcessesW, hServer, Reserved, Version, ppProcessInfo, pCount);
}
BOOL WINAPI WTSEnumerateProcessesA(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_PROCESS_INFOA* ppProcessInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateProcessesA(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_PROCESS_INFOA *ppProcessInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateProcessesA, hServer, Reserved, Version, ppProcessInfo, pCount);
}
@ -294,22 +295,22 @@ BOOL WINAPI WTSTerminateProcess(HANDLE hServer, DWORD ProcessId, DWORD ExitCode)
WTSAPI_STUB_CALL_BOOL(TerminateProcess, hServer, ProcessId, ExitCode);
}
BOOL WINAPI WTSQuerySessionInformationW(HANDLE hServer, DWORD SessionId, WTS_INFO_CLASS WTSInfoClass, LPWSTR* ppBuffer, DWORD* pBytesReturned)
BOOL WINAPI WTSQuerySessionInformationW(HANDLE hServer, DWORD SessionId, WTS_INFO_CLASS WTSInfoClass, LPWSTR *ppBuffer, DWORD *pBytesReturned)
{
WTSAPI_STUB_CALL_BOOL(QuerySessionInformationW, hServer, SessionId, WTSInfoClass, ppBuffer, pBytesReturned);
}
BOOL WINAPI WTSQuerySessionInformationA(HANDLE hServer, DWORD SessionId, WTS_INFO_CLASS WTSInfoClass, LPSTR* ppBuffer, DWORD* pBytesReturned)
BOOL WINAPI WTSQuerySessionInformationA(HANDLE hServer, DWORD SessionId, WTS_INFO_CLASS WTSInfoClass, LPSTR *ppBuffer, DWORD *pBytesReturned)
{
WTSAPI_STUB_CALL_BOOL(QuerySessionInformationA, hServer, SessionId, WTSInfoClass, ppBuffer, pBytesReturned);
}
BOOL WINAPI WTSQueryUserConfigW(LPWSTR pServerName, LPWSTR pUserName, WTS_CONFIG_CLASS WTSConfigClass, LPWSTR* ppBuffer, DWORD* pBytesReturned)
BOOL WINAPI WTSQueryUserConfigW(LPWSTR pServerName, LPWSTR pUserName, WTS_CONFIG_CLASS WTSConfigClass, LPWSTR *ppBuffer, DWORD *pBytesReturned)
{
WTSAPI_STUB_CALL_BOOL(QueryUserConfigW, pServerName, pUserName, WTSConfigClass, ppBuffer, pBytesReturned);
}
BOOL WINAPI WTSQueryUserConfigA(LPSTR pServerName, LPSTR pUserName, WTS_CONFIG_CLASS WTSConfigClass, LPSTR* ppBuffer, DWORD* pBytesReturned)
BOOL WINAPI WTSQueryUserConfigA(LPSTR pServerName, LPSTR pUserName, WTS_CONFIG_CLASS WTSConfigClass, LPSTR *ppBuffer, DWORD *pBytesReturned)
{
WTSAPI_STUB_CALL_BOOL(QueryUserConfigA, pServerName, pUserName, WTSConfigClass, ppBuffer, pBytesReturned);
}
@ -325,17 +326,17 @@ BOOL WINAPI WTSSetUserConfigA(LPSTR pServerName, LPSTR pUserName, WTS_CONFIG_CLA
}
BOOL WINAPI WTSSendMessageW(HANDLE hServer, DWORD SessionId, LPWSTR pTitle, DWORD TitleLength,
LPWSTR pMessage, DWORD MessageLength, DWORD Style, DWORD Timeout, DWORD* pResponse, BOOL bWait)
LPWSTR pMessage, DWORD MessageLength, DWORD Style, DWORD Timeout, DWORD *pResponse, BOOL bWait)
{
WTSAPI_STUB_CALL_BOOL(SendMessageW, hServer, SessionId, pTitle, TitleLength,
pMessage, MessageLength, Style, Timeout, pResponse, bWait);
pMessage, MessageLength, Style, Timeout, pResponse, bWait);
}
BOOL WINAPI WTSSendMessageA(HANDLE hServer, DWORD SessionId, LPSTR pTitle, DWORD TitleLength,
LPSTR pMessage, DWORD MessageLength, DWORD Style, DWORD Timeout, DWORD* pResponse, BOOL bWait)
LPSTR pMessage, DWORD MessageLength, DWORD Style, DWORD Timeout, DWORD *pResponse, BOOL bWait)
{
WTSAPI_STUB_CALL_BOOL(SendMessageA, hServer, SessionId, pTitle, TitleLength,
pMessage, MessageLength, Style, Timeout, pResponse, bWait);
pMessage, MessageLength, Style, Timeout, pResponse, bWait);
}
BOOL WINAPI WTSDisconnectSession(HANDLE hServer, DWORD SessionId, BOOL bWait)
@ -353,7 +354,7 @@ BOOL WINAPI WTSShutdownSystem(HANDLE hServer, DWORD ShutdownFlag)
WTSAPI_STUB_CALL_BOOL(ShutdownSystem, hServer, ShutdownFlag);
}
BOOL WINAPI WTSWaitSystemEvent(HANDLE hServer, DWORD EventMask, DWORD* pEventFlags)
BOOL WINAPI WTSWaitSystemEvent(HANDLE hServer, DWORD EventMask, DWORD *pEventFlags)
{
WTSAPI_STUB_CALL_BOOL(WaitSystemEvent, hServer, EventMask, pEventFlags);
}
@ -393,7 +394,7 @@ BOOL WINAPI WTSVirtualChannelPurgeOutput(HANDLE hChannelHandle)
WTSAPI_STUB_CALL_BOOL(VirtualChannelPurgeOutput, hChannelHandle);
}
BOOL WINAPI WTSVirtualChannelQuery(HANDLE hChannelHandle, WTS_VIRTUAL_CLASS WtsVirtualClass, PVOID* ppBuffer, DWORD* pBytesReturned)
BOOL WINAPI WTSVirtualChannelQuery(HANDLE hChannelHandle, WTS_VIRTUAL_CLASS WtsVirtualClass, PVOID *ppBuffer, DWORD *pBytesReturned)
{
WTSAPI_STUB_CALL_BOOL(VirtualChannelQuery, hChannelHandle, WtsVirtualClass, ppBuffer, pBytesReturned);
}
@ -438,22 +439,22 @@ BOOL WINAPI WTSQueryUserToken(ULONG SessionId, PHANDLE phToken)
WTSAPI_STUB_CALL_BOOL(QueryUserToken, SessionId, phToken);
}
BOOL WINAPI WTSEnumerateProcessesExW(HANDLE hServer, DWORD* pLevel, DWORD SessionId, LPWSTR* ppProcessInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateProcessesExW(HANDLE hServer, DWORD *pLevel, DWORD SessionId, LPWSTR *ppProcessInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateProcessesExW, hServer, pLevel, SessionId, ppProcessInfo, pCount);
}
BOOL WINAPI WTSEnumerateProcessesExA(HANDLE hServer, DWORD* pLevel, DWORD SessionId, LPSTR* ppProcessInfo, DWORD* pCount)
BOOL WINAPI WTSEnumerateProcessesExA(HANDLE hServer, DWORD *pLevel, DWORD SessionId, LPSTR *ppProcessInfo, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateProcessesExA, hServer, pLevel, SessionId, ppProcessInfo, pCount);
}
BOOL WINAPI WTSEnumerateListenersW(HANDLE hServer, PVOID pReserved, DWORD Reserved, PWTSLISTENERNAMEW pListeners, DWORD* pCount)
BOOL WINAPI WTSEnumerateListenersW(HANDLE hServer, PVOID pReserved, DWORD Reserved, PWTSLISTENERNAMEW pListeners, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateListenersW, hServer, pReserved, Reserved, pListeners, pCount);
}
BOOL WINAPI WTSEnumerateListenersA(HANDLE hServer, PVOID pReserved, DWORD Reserved, PWTSLISTENERNAMEA pListeners, DWORD* pCount)
BOOL WINAPI WTSEnumerateListenersA(HANDLE hServer, PVOID pReserved, DWORD Reserved, PWTSLISTENERNAMEA pListeners, DWORD *pCount)
{
WTSAPI_STUB_CALL_BOOL(EnumerateListenersA, hServer, pReserved, Reserved, pListeners, pCount);
}
@ -469,47 +470,47 @@ BOOL WINAPI WTSQueryListenerConfigA(HANDLE hServer, PVOID pReserved, DWORD Reser
}
BOOL WINAPI WTSCreateListenerW(HANDLE hServer, PVOID pReserved, DWORD Reserved,
LPWSTR pListenerName, PWTSLISTENERCONFIGW pBuffer, DWORD flag)
LPWSTR pListenerName, PWTSLISTENERCONFIGW pBuffer, DWORD flag)
{
WTSAPI_STUB_CALL_BOOL(CreateListenerW, hServer, pReserved, Reserved, pListenerName, pBuffer, flag);
}
BOOL WINAPI WTSCreateListenerA(HANDLE hServer, PVOID pReserved, DWORD Reserved,
LPSTR pListenerName, PWTSLISTENERCONFIGA pBuffer, DWORD flag)
LPSTR pListenerName, PWTSLISTENERCONFIGA pBuffer, DWORD flag)
{
WTSAPI_STUB_CALL_BOOL(CreateListenerA, hServer, pReserved, Reserved, pListenerName, pBuffer, flag);
}
BOOL WINAPI WTSSetListenerSecurityW(HANDLE hServer, PVOID pReserved, DWORD Reserved,
LPWSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor)
LPWSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor)
{
WTSAPI_STUB_CALL_BOOL(SetListenerSecurityW, hServer, pReserved, Reserved,
pListenerName, SecurityInformation, pSecurityDescriptor);
pListenerName, SecurityInformation, pSecurityDescriptor);
}
BOOL WINAPI WTSSetListenerSecurityA(HANDLE hServer, PVOID pReserved, DWORD Reserved,
LPSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor)
LPSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor)
{
WTSAPI_STUB_CALL_BOOL(SetListenerSecurityA, hServer, pReserved, Reserved,
pListenerName, SecurityInformation, pSecurityDescriptor);
pListenerName, SecurityInformation, pSecurityDescriptor);
}
BOOL WINAPI WTSGetListenerSecurityW(HANDLE hServer, PVOID pReserved, DWORD Reserved,
LPWSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor, DWORD nLength, LPDWORD lpnLengthNeeded)
LPWSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor, DWORD nLength, LPDWORD lpnLengthNeeded)
{
WTSAPI_STUB_CALL_BOOL(GetListenerSecurityW, hServer, pReserved, Reserved, pListenerName,
SecurityInformation, pSecurityDescriptor, nLength, lpnLengthNeeded);
SecurityInformation, pSecurityDescriptor, nLength, lpnLengthNeeded);
}
BOOL WINAPI WTSGetListenerSecurityA(HANDLE hServer, PVOID pReserved, DWORD Reserved,
LPSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor, DWORD nLength, LPDWORD lpnLengthNeeded)
LPSTR pListenerName, SECURITY_INFORMATION SecurityInformation,
PSECURITY_DESCRIPTOR pSecurityDescriptor, DWORD nLength, LPDWORD lpnLengthNeeded)
{
WTSAPI_STUB_CALL_BOOL(GetListenerSecurityA, hServer, pReserved, Reserved, pListenerName,
SecurityInformation, pSecurityDescriptor, nLength, lpnLengthNeeded);
SecurityInformation, pSecurityDescriptor, nLength, lpnLengthNeeded);
}
BOOL CDECL WTSEnableChildSessions(BOOL bEnable)
@ -567,6 +568,7 @@ static BOOL LoadAndInitialize(char *library)
{
return FALSE;
}
g_WtsApi = pInitWtsApi();
return TRUE;
}
@ -574,7 +576,7 @@ static BOOL LoadAndInitialize(char *library)
void InitializeWtsApiStubs_Env()
{
DWORD nSize;
char* env = NULL;
char *env = NULL;
if (g_WtsApi)
return;
@ -597,45 +599,43 @@ void InitializeWtsApiStubs_Env()
void InitializeWtsApiStubs_FreeRDS()
{
char* prefix;
char* libdir;
wIniFile* ini;
char *prefix;
char *libdir;
wIniFile *ini;
if (g_WtsApi)
return;
ini = IniFile_New();
if (IniFile_Parse(ini, "/var/run/freerds.instance") < 0)
{
IniFile_Free(ini);
fprintf(stderr, "failed to parse freerds.instance\n");
WLog_ERR(TAG, "failed to parse freerds.instance\n");
LoadAndInitialize(FREERDS_LIBRARY_NAME);
return;
}
prefix = IniFile_GetKeyValueString(ini, "FreeRDS", "prefix");
libdir = IniFile_GetKeyValueString(ini, "FreeRDS", "libdir");
fprintf(stderr, "FreeRDS (prefix / libdir): %s / %s\n", prefix, libdir);
WLog_INFO(TAG, "FreeRDS (prefix / libdir): %s / %s\n", prefix, libdir);
if (prefix && libdir)
{
char* prefix_libdir;
char* wtsapi_library;
char *prefix_libdir;
char *wtsapi_library;
prefix_libdir = GetCombinedPath(prefix, libdir);
wtsapi_library = GetCombinedPath(prefix_libdir, FREERDS_LIBRARY_NAME);
if (wtsapi_library)
{
LoadAndInitialize(wtsapi_library);
}
free(prefix_libdir);
free(wtsapi_library);
}
IniFile_Free(ini);
}
@ -645,9 +645,7 @@ void InitializeWtsApiStubs(void)
return;
g_Initialized = TRUE;
InitializeWtsApiStubs_Env();
#ifdef _WIN32
WtsApi32_InitializeWtsApi();
#endif