This commit is contained in:
biosvos
2026-08-07 17:38:18 +09:00
commit 873193a243
9613 changed files with 2755992 additions and 0 deletions
@@ -0,0 +1 @@
12
@@ -0,0 +1 @@
12
@@ -0,0 +1,36 @@
/* Copyright (c) 1998, 1999 Thai Open Source Software Center Ltd
See the file COPYING for copying permission.
*/
/* 0x00 */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML,
/* 0x04 */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML,
/* 0x08 */ BT_NONXML, BT_S, BT_LF, BT_NONXML,
/* 0x0C */ BT_NONXML, BT_CR, BT_NONXML, BT_NONXML,
/* 0x10 */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML,
/* 0x14 */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML,
/* 0x18 */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML,
/* 0x1C */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML,
/* 0x20 */ BT_S, BT_EXCL, BT_QUOT, BT_NUM,
/* 0x24 */ BT_OTHER, BT_PERCNT, BT_AMP, BT_APOS,
/* 0x28 */ BT_LPAR, BT_RPAR, BT_AST, BT_PLUS,
/* 0x2C */ BT_COMMA, BT_MINUS, BT_NAME, BT_SOL,
/* 0x30 */ BT_DIGIT, BT_DIGIT, BT_DIGIT, BT_DIGIT,
/* 0x34 */ BT_DIGIT, BT_DIGIT, BT_DIGIT, BT_DIGIT,
/* 0x38 */ BT_DIGIT, BT_DIGIT, BT_COLON, BT_SEMI,
/* 0x3C */ BT_LT, BT_EQUALS, BT_GT, BT_QUEST,
/* 0x40 */ BT_OTHER, BT_HEX, BT_HEX, BT_HEX,
/* 0x44 */ BT_HEX, BT_HEX, BT_HEX, BT_NMSTRT,
/* 0x48 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x4C */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x50 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x54 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x58 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_LSQB,
/* 0x5C */ BT_OTHER, BT_RSQB, BT_OTHER, BT_NMSTRT,
/* 0x60 */ BT_OTHER, BT_HEX, BT_HEX, BT_HEX,
/* 0x64 */ BT_HEX, BT_HEX, BT_HEX, BT_NMSTRT,
/* 0x68 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x6C */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x70 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x74 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_NMSTRT,
/* 0x78 */ BT_NMSTRT, BT_NMSTRT, BT_NMSTRT, BT_OTHER,
/* 0x7C */ BT_VERBAR, BT_OTHER, BT_OTHER, BT_OTHER,
@@ -0,0 +1,24 @@
#define Q_TABLES
#define M_TABLE
#define MK_TABLE
#define ONE_STEP
typedef struct twofish_instance {
word32 k_len;
word32 l_key[40];
word32 s_key[4];
#ifdef Q_TABLES
word32 qt_gen;
byte q_tab[2][256];
#endif
#ifdef M_TABLE
word32 mt_gen;
word32 m_tab[4][256];
#endif
#ifdef ONE_STEP
word32 mk_tab[4][256];
#else
byte sb[4][256];
#endif
} TWI;
@@ -0,0 +1,4 @@
typedef struct {
word32 l_key[140];
} SERPENT_KEY;
@@ -0,0 +1,445 @@
/*
Handling of compressed HTTP responses
Copyright (C) 2001-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include "ne_request.h"
#include "ne_compress.h"
#include "ne_utils.h"
#include "ne_i18n.h"
#include "ne_private.h"
#ifdef NE_HAVE_ZLIB
#include <zlib.h>
/* Adds support for the 'gzip' Content-Encoding in HTTP. gzip is a
* file format which wraps the DEFLATE compression algorithm. zlib
* implements DEFLATE: we have to unwrap the gzip format (specified in
* RFC1952) as it comes off the wire, and hand off chunks of data to
* be inflated. */
struct ne_decompress_s {
ne_request *request; /* associated request. */
ne_session *session; /* associated session. */
/* temporary buffer for holding inflated data. */
char outbuf[NE_BUFSIZ];
z_stream zstr;
int zstrinit; /* non-zero if zstr has been initialized */
/* pass blocks back to this. */
ne_block_reader reader;
ne_accept_response acceptor;
void *userdata;
/* buffer for gzip header bytes. */
unsigned char header[10];
size_t hdrcount; /* bytes in header */
unsigned char footer[8];
size_t footcount; /* bytes in footer. */
/* CRC32 checksum: odd that zlib uses uLong for this since it is a
* 64-bit integer on LP64 platforms. */
uLong checksum;
/* current state. */
enum state {
NE_Z_BEFORE_DATA, /* not received any response blocks yet. */
NE_Z_PASSTHROUGH, /* response not compressed: passing through. */
NE_Z_IN_HEADER, /* received a few bytes of response data, but not
* got past the gzip header yet. */
NE_Z_POST_HEADER, /* waiting for the end of the NUL-terminated bits. */
NE_Z_INFLATING, /* inflating response bytes. */
NE_Z_AFTER_DATA, /* after data; reading CRC32 & ISIZE */
NE_Z_FINISHED /* stream is finished. */
} state;
};
/* Convert 'buf' to unsigned int; 'buf' must be 'unsigned char *' */
#define BUF2UINT(buf) (((buf)[3]<<24) + ((buf)[2]<<16) + ((buf)[1]<<8) + (buf)[0])
#define ID1 0x1f
#define ID2 0x8b
#define HDR_DONE 0
#define HDR_EXTENDED 1
#define HDR_ERROR 2
#define HDR_ID1(ctx) ((ctx)->header[0])
#define HDR_ID2(ctx) ((ctx)->header[1])
#define HDR_CMETH(ctx) ((ctx)->header[2])
#define HDR_FLAGS(ctx) ((ctx)->header[3])
#define HDR_MTIME(ctx) (BUF2UINT(&(ctx)->header[4]))
#define HDR_XFLAGS(ctx) ((ctx)->header[8])
#define HDR_OS(ctx) ((ctx)->header[9])
/* parse_header parses the gzip header, sets the next state and returns
* HDR_DONE: all done, bytes following are raw DEFLATE data.
* HDR_EXTENDED: all done, expect a NUL-termianted string
* before the DEFLATE data
* HDR_ERROR: invalid header, give up (session error is set).
*/
static int parse_header(ne_decompress *ctx)
{
NE_DEBUG(NE_DBG_HTTP, "ID1: %d ID2: %d, cmeth %d, flags %d\n",
HDR_ID1(ctx), HDR_ID2(ctx), HDR_CMETH(ctx), HDR_FLAGS(ctx));
if (HDR_ID1(ctx) != ID1 || HDR_ID2(ctx) != ID2 || HDR_CMETH(ctx) != 8) {
ne_set_error(ctx->session, "Compressed stream invalid");
return HDR_ERROR;
}
NE_DEBUG(NE_DBG_HTTP, "mtime: %d, xflags: %d, os: %d\n",
HDR_MTIME(ctx), HDR_XFLAGS(ctx), HDR_OS(ctx));
/* TODO: we can only handle one NUL-terminated extensions field
* currently. Really, we should count the number of bits set, and
* skip as many fields as bits set (bailing if any reserved bits
* are set. */
if (HDR_FLAGS(ctx) == 8) {
ctx->state = NE_Z_POST_HEADER;
return HDR_EXTENDED;
} else if (HDR_FLAGS(ctx) != 0) {
ne_set_error(ctx->session, "Compressed stream not supported");
return HDR_ERROR;
}
NE_DEBUG(NE_DBG_HTTP, "compress: Good stream.\n");
ctx->state = NE_Z_INFLATING;
return HDR_DONE;
}
/* Process extra 'len' bytes of 'buf' which were received after the
* DEFLATE data. */
static int process_footer(ne_decompress *ctx,
const unsigned char *buf, size_t len)
{
if (len + ctx->footcount > 8) {
ne_set_error(ctx->session,
"Too many bytes (%" NE_FMT_SIZE_T ") in gzip footer",
len);
return -1;
} else {
memcpy(ctx->footer + ctx->footcount, buf, len);
ctx->footcount += len;
if (ctx->footcount == 8) {
uLong crc = BUF2UINT(ctx->footer) & 0xFFFFFFFF;
if (crc == ctx->checksum) {
ctx->state = NE_Z_FINISHED;
NE_DEBUG(NE_DBG_HTTP, "compress: End of response; checksum match.\n");
} else {
NE_DEBUG(NE_DBG_HTTP, "compress: End of response; checksum mismatch: "
"given %lu vs computed %lu\n", crc, ctx->checksum);
ne_set_error(ctx->session,
"Checksum invalid for compressed stream");
return -1;
}
}
}
return 0;
}
/* A zlib function failed with 'code'; set the session error string
* appropriately. */
static void set_zlib_error(ne_decompress *ctx, const char *msg, int code)
{
if (ctx->zstr.msg)
ne_set_error(ctx->session, _("%s: %s"), msg, ctx->zstr.msg);
else {
const char *err;
switch (code) {
case Z_STREAM_ERROR: err = "stream error"; break;
case Z_DATA_ERROR: err = "data corrupt"; break;
case Z_MEM_ERROR: err = "out of memory"; break;
case Z_BUF_ERROR: err = "buffer error"; break;
case Z_VERSION_ERROR: err = "library version mismatch"; break;
default: err = "unknown error"; break;
}
ne_set_error(ctx->session, _("%s: %s (code %d)"), msg, err, code);
}
}
/* Inflate response buffer 'buf' of length 'len'. */
static int do_inflate(ne_decompress *ctx, const char *buf, size_t len)
{
int ret;
ctx->zstr.avail_in = len;
ctx->zstr.next_in = (unsigned char *)buf;
ctx->zstr.total_in = 0;
do {
ctx->zstr.avail_out = sizeof ctx->outbuf;
ctx->zstr.next_out = (unsigned char *)ctx->outbuf;
ctx->zstr.total_out = 0;
ret = inflate(&ctx->zstr, Z_NO_FLUSH);
NE_DEBUG(NE_DBG_HTTP,
"compress: inflate %d, %ld bytes out, %d remaining\n",
ret, ctx->zstr.total_out, ctx->zstr.avail_in);
#if 0
NE_DEBUG(NE_DBG_HTTPBODY,
"Inflated body block (%ld):\n[%.*s]\n",
ctx->zstr.total_out, (int)ctx->zstr.total_out,
ctx->outbuf);
#endif
/* update checksum. */
ctx->checksum = crc32(ctx->checksum, (unsigned char *)ctx->outbuf,
ctx->zstr.total_out);
/* pass on the inflated data, if any */
if (ctx->zstr.total_out > 0) {
int rret = ctx->reader(ctx->userdata, ctx->outbuf,
ctx->zstr.total_out);
if (rret) return rret;
}
} while (ret == Z_OK && ctx->zstr.avail_in > 0);
if (ret == Z_STREAM_END) {
NE_DEBUG(NE_DBG_HTTP, "compress: end of data stream, %d bytes remain.\n",
ctx->zstr.avail_in);
/* process the footer. */
ctx->state = NE_Z_AFTER_DATA;
return process_footer(ctx, ctx->zstr.next_in, ctx->zstr.avail_in);
} else if (ret != Z_OK) {
set_zlib_error(ctx, _("Could not inflate data"), ret);
return NE_ERROR;
}
return 0;
}
/* Callback which is passed blocks of the response body. */
static int gz_reader(void *ud, const char *buf, size_t len)
{
ne_decompress *ctx = ud;
const char *zbuf;
size_t count;
const char *hdr;
if (len == 0) {
/* End of response: */
switch (ctx->state) {
case NE_Z_BEFORE_DATA:
hdr = ne_get_response_header(ctx->request, "Content-Encoding");
if (hdr && strcasecmp(hdr, "gzip") == 0) {
/* response was truncated: return error. */
break;
}
/* else, fall through */
case NE_Z_FINISHED: /* complete gzip response */
case NE_Z_PASSTHROUGH: /* complete uncompressed response */
return ctx->reader(ctx->userdata, buf, 0);
default:
/* invalid state: truncated response. */
break;
}
/* else: truncated response, fail. */
ne_set_error(ctx->session, "Compressed response was truncated");
return NE_ERROR;
}
switch (ctx->state) {
case NE_Z_PASSTHROUGH:
/* move along there. */
return ctx->reader(ctx->userdata, buf, len);
case NE_Z_FINISHED:
/* Could argue for tolerance, and ignoring trailing content;
* but it could mean something more serious. */
if (len > 0) {
ne_set_error(ctx->session,
"Unexpected content received after compressed stream");
return NE_ERROR;
}
break;
case NE_Z_BEFORE_DATA:
/* work out whether this is a compressed response or not. */
hdr = ne_get_response_header(ctx->request, "Content-Encoding");
if (hdr && strcasecmp(hdr, "gzip") == 0) {
int ret;
NE_DEBUG(NE_DBG_HTTP, "compress: got gzipped stream.\n");
/* inflateInit2() works here where inflateInit() doesn't. */
ret = inflateInit2(&ctx->zstr, -MAX_WBITS);
if (ret != Z_OK) {
set_zlib_error(ctx, _("Could not initialize zlib"), ret);
return -1;
}
ctx->zstrinit = 1;
} else {
/* No Content-Encoding header: pass it on. TODO: we could
* hack it and register the real callback now. But that
* would require add_resp_body_rdr to have defined
* ordering semantics etc etc */
ctx->state = NE_Z_PASSTHROUGH;
return ctx->reader(ctx->userdata, buf, len);
}
ctx->state = NE_Z_IN_HEADER;
/* FALLTHROUGH */
case NE_Z_IN_HEADER:
/* copy as many bytes as possible into the buffer. */
if (len + ctx->hdrcount > 10) {
count = 10 - ctx->hdrcount;
} else {
count = len;
}
memcpy(ctx->header + ctx->hdrcount, buf, count);
ctx->hdrcount += count;
/* have we got the full header yet? */
if (ctx->hdrcount != 10) {
return 0;
}
buf += count;
len -= count;
switch (parse_header(ctx)) {
case HDR_EXTENDED:
if (len == 0)
return 0;
break;
case HDR_ERROR:
return NE_ERROR;
case HDR_DONE:
if (len > 0) {
return do_inflate(ctx, buf, len);
}
break;
}
/* FALLTHROUGH */
case NE_Z_POST_HEADER:
/* eating the filename string. */
zbuf = memchr(buf, '\0', len);
if (zbuf == NULL) {
/* not found it yet. */
return 0;
}
NE_DEBUG(NE_DBG_HTTP,
"compresss: skipped %" NE_FMT_SIZE_T " header bytes.\n",
zbuf - buf);
/* found end of string. */
len -= (1 + zbuf - buf);
buf = zbuf + 1;
ctx->state = NE_Z_INFLATING;
if (len == 0) {
/* end of string was at end of buffer. */
return 0;
}
/* FALLTHROUGH */
case NE_Z_INFLATING:
return do_inflate(ctx, buf, len);
case NE_Z_AFTER_DATA:
return process_footer(ctx, (unsigned char *)buf, len);
}
return 0;
}
/* Prepare for a compressed response */
static void gz_pre_send(ne_request *r, void *ud, ne_buffer *req)
{
ne_decompress *ctx = ud;
NE_DEBUG(NE_DBG_HTTP, "compress: Initialization.\n");
/* (Re-)Initialize the context */
ctx->state = NE_Z_BEFORE_DATA;
if (ctx->zstrinit) inflateEnd(&ctx->zstr);
ctx->zstrinit = 0;
ctx->hdrcount = ctx->footcount = 0;
ctx->checksum = crc32(0L, Z_NULL, 0);
}
void ne_decompress_destroy(ne_decompress *ctx)
{
if (ctx->zstrinit)
/* inflateEnd only fails if it's passed NULL etc; ignore
* return value. */
inflateEnd(&ctx->zstr);
ne_free(ctx);
}
/* Wrapper for user-passed acceptor function. */
static int gz_acceptor(void *userdata, ne_request *req, const ne_status *st)
{
ne_decompress *ctx = userdata;
return ctx->acceptor(ctx->userdata, req, st);
}
ne_decompress *ne_decompress_reader(ne_request *req, ne_accept_response acpt,
ne_block_reader rdr, void *userdata)
{
ne_decompress *ctx = ne_calloc(sizeof *ctx);
ne_add_request_header(req, "Accept-Encoding", "gzip");
ne_add_response_body_reader(req, gz_acceptor, gz_reader, ctx);
ctx->reader = rdr;
ctx->userdata = userdata;
ctx->session = ne_get_session(req);
ctx->request = req;
ctx->acceptor = acpt;
ne__reqhook_pre_send(req, gz_pre_send, ctx);
return ctx;
}
#else /* !NE_HAVE_ZLIB */
/* Pass-through interface present to provide ABI compatibility. */
ne_decompress *ne_decompress_reader(ne_request *req, ne_accept_response acpt,
ne_block_reader rdr, void *userdata)
{
ne_add_response_body_reader(req, acpt, rdr, userdata);
/* an arbitrary return value: don't confuse them by returning NULL. */
return (ne_decompress *)req;
}
void ne_decompress_destroy(ne_decompress *dc)
{
}
#endif /* NE_HAVE_ZLIB */
@@ -0,0 +1,439 @@
/*
* Copyright (C) 1998,1999,2001 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it under the terms of the
* GNU Library General Public License as published by the Free Software
* Foundation; either version 2 of the License, or (at your option) any
* later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
/* $Id: mcrypt_extra.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
#include <libdefs.h>
#include <bzero.h>
#include <xmemory.h>
#include <mcrypt_internal.h>
int mcrypt_algorithm_module_ok(const char *file, const char *directory);
int mcrypt_mode_module_ok(const char *file, const char *directory);
void *mcrypt_dlopen(mcrypt_dlhandle * handle, const char *a_directory,
const char *m_directory, const char *filename);
#ifdef HAVE_READDIR_R
# define MAXPATHLEN 256
#endif
WIN32DLL_DEFINE char *mcrypt_readdir(DIR * dirstream)
{
char *result;
struct dirent *ret = NULL;
#ifdef HAVE_READDIR_R
struct dirent ret2[sizeof(struct dirent) + MAXPATHLEN];
#endif
#ifdef HAVE_READDIR_R
readdir_r(dirstream, ret2, &ret);
#else
ret = readdir(dirstream);
#endif
if (ret == NULL)
return NULL;
result = strdup(ret->d_name);
if (result == NULL) {
return NULL;
}
return result;
}
extern const mcrypt_preloaded mps[];
WIN32DLL_DEFINE char **mcrypt_list_algorithms(const char *libdir,
int *size)
{
DIR *pdir;
char directory[512];
char *dirname;
char **filename = NULL, *ptr;
int tmpsize, i = 0;
*size = 0;
while (mps[i].name != 0 || mps[i].address != 0) {
if (mps[i].name != NULL && mps[i].address == NULL) {
if (mcrypt_algorithm_module_ok(mps[i].name, NULL) >
0) {
filename =
realloc(filename,
((*size) +
1) * sizeof(char *));
if (filename == NULL) {
goto freeall;
}
filename[*size] = strdup(mps[i].name);
if (filename[*size] == NULL)
goto freeall;
(*size)++;
}
}
i++;
}
#ifdef USE_LTDL
if (libdir == NULL) {
strncpy(directory, LIBDIR, sizeof(directory)-1);
} else {
strncpy(directory, libdir, sizeof(directory)-1);
}
directory[ sizeof(directory)-1] = 0;
pdir = opendir(directory);
if (pdir == NULL) {
#ifdef DEBUG
fprintf(stderr, "Unable to open directory %s.\n",
directory);
#endif
return filename;
}
for (;;) {
dirname = mcrypt_readdir(pdir);
if (dirname != NULL) {
tmpsize = strlen(dirname);
if (tmpsize > 3) {
if (mcrypt_algorithm_module_ok
(dirname, directory) > 0) {
ptr = strrchr(dirname, '.');
if (ptr != NULL) {
*ptr = '\0';
tmpsize = strlen(dirname);
}
if (_mcrypt_search_symlist_lib
(dirname) != NULL) {
free(dirname);
continue; /* it's already in the list,
* since it's included in the lib.
*/
}
filename =
realloc(filename,
(*size +
1) * sizeof(char *));
if (filename == NULL) {
free(dirname);
goto freeall;
}
filename[*size] = strdup(dirname);
if (filename[*size] == NULL) {
free(dirname);
goto freeall;
}
(*size)++;
}
}
free(dirname);
} else break;
}
closedir(pdir);
#endif
return filename;
freeall:
for (i = 0; i < (*size); i++) {
free(filename[i]);
}
free(filename);
return NULL;
}
WIN32DLL_DEFINE char **mcrypt_list_modes(const char *libdir, int *size)
{
DIR *pdir;
char directory[512];
char *dirname;
char **filename = NULL, *ptr;
int tmpsize;
int i = 0;
*size = 0;
while (mps[i].name != 0 || mps[i].address != 0) {
if (mps[i].name != NULL && mps[i].address == NULL) {
if (mcrypt_mode_module_ok(mps[i].name, NULL) > 0) {
filename =
realloc(filename,
(*size + 1) * sizeof(char *));
if (filename == NULL) {
goto freeall;
}
filename[*size] = strdup(mps[i].name);
if (filename[*size] == NULL)
goto freeall;
(*size)++;
}
}
i++;
}
#ifdef USE_LTDL
if (libdir == NULL) {
strncpy(directory, LIBDIR, sizeof(directory)-1);
} else {
strncpy(directory, libdir, sizeof(directory)-1);
}
directory[ sizeof(directory)-1] = 0;
pdir = opendir(directory);
if (pdir == NULL) {
#ifdef DEBUG
fprintf(stderr, "Unable to open directory %s.\n",
directory);
#endif
return filename;
}
for (;;) {
dirname = mcrypt_readdir(pdir);
if (dirname != NULL) {
tmpsize = strlen(dirname);
if (tmpsize > 3) {
if (mcrypt_mode_module_ok
(dirname, directory) > 0) {
ptr = strrchr(dirname, '.');
if (ptr != NULL) {
*ptr = '\0';
tmpsize = strlen(dirname);
}
if (_mcrypt_search_symlist_lib
(dirname) != NULL) {
free(dirname);
continue; /* it's already in the list,
* since it's included in the lib.
*/
}
filename =
realloc(filename,
(*size +
1) * sizeof(char *));
if (filename == NULL) {
free(dirname);
goto freeall;
}
filename[*size] = strdup(dirname);
if (filename[*size] == NULL) {
free(dirname);
goto freeall;
}
(*size)++;
}
}
free(dirname);
} else {
break;
}
}
closedir(pdir);
#endif
return filename;
freeall:
for (i = 0; i < (*size); i++) {
free(filename[i]);
}
free(filename);
return NULL;
}
WIN32DLL_DEFINE void mcrypt_free_p(char **p, int size)
{
int i;
for (i = 0; i < size; i++) {
free(p[i]);
}
free(p);
}
WIN32DLL_DEFINE
int mcrypt_algorithm_module_ok(const char *file, const char *directory)
{
word32 ret = 1;
mcrypt_dlhandle _handle;
void *rr;
int (*_version) (void);
if (file == NULL && directory == NULL) {
return MCRYPT_UNKNOWN_ERROR;
}
if (lt_dlinit() != 0) {
return MCRYPT_UNKNOWN_ERROR;
}
rr = mcrypt_dlopen(&_handle, directory, NULL, file);
if (!rr) {
lt_dlexit();
return MCRYPT_UNKNOWN_ERROR;
}
_version = mcrypt_dlsym(_handle, "_mcrypt_algorithm_version");
if (_version == NULL) {
mcrypt_dlclose(_handle);
lt_dlexit();
return MCRYPT_UNKNOWN_ERROR;
}
ret = _version();
mcrypt_dlclose(_handle);
lt_dlexit();
return ret;
}
WIN32DLL_DEFINE
int mcrypt_mode_module_ok(const char *file, const char *directory)
{
word32 ret;
mcrypt_dlhandle _handle;
void *rr;
int (*_version) (void);
if (file == NULL && directory == NULL) {
return MCRYPT_UNKNOWN_ERROR;
}
if (lt_dlinit() != 0) {
return MCRYPT_UNKNOWN_ERROR;
}
rr = mcrypt_dlopen(&_handle, directory, NULL, file);
if (!rr) {
lt_dlexit();
return MCRYPT_UNKNOWN_ERROR;
}
_version = mcrypt_dlsym(_handle, "_mcrypt_mode_version");
if (_version == NULL) {
mcrypt_dlclose(_handle);
lt_dlexit();
return MCRYPT_UNKNOWN_ERROR;
}
ret = _version();
mcrypt_dlclose(_handle);
lt_dlexit();
return ret;
}
/* Taken from libgcrypt */
static const char *parse_version_number(const char *s, int *number)
{
int val = 0;
if (*s == '0' && isdigit(s[1]))
return NULL; /* leading zeros are not allowed */
for (; isdigit(*s); s++) {
val *= 10;
val += *s - '0';
}
*number = val;
return val < 0 ? NULL : s;
}
static const char *parse_version_string(const char *s, int *major,
int *minor, int *micro)
{
s = parse_version_number(s, major);
if (!s || *s != '.')
return NULL;
s++;
s = parse_version_number(s, minor);
if (!s || *s != '.')
return NULL;
s++;
s = parse_version_number(s, micro);
if (!s)
return NULL;
return s; /* patchlevel */
}
/****************
* Check that the the version of the library is at minimum the requested one
* and return the version string; return NULL if the condition is not
* satisfied. If a NULL is passed to this function, no check is done,
* but the version string is simply returned.
*/
const char *mcrypt_check_version(const char *req_version)
{
const char *ver = VERSION;
int my_major, my_minor, my_micro;
int rq_major, rq_minor, rq_micro;
const char *my_plvl, *rq_plvl;
if (!req_version)
return ver;
my_plvl =
parse_version_string(ver, &my_major, &my_minor, &my_micro);
if (!my_plvl)
return NULL; /* very strange our own version is bogus */
rq_plvl = parse_version_string(req_version, &rq_major, &rq_minor,
&rq_micro);
if (!rq_plvl)
return NULL; /* req version string is invalid */
if (my_major > rq_major
|| (my_major == rq_major && my_minor > rq_minor)
|| (my_major == rq_major && my_minor == rq_minor
&& my_micro > rq_micro)
|| (my_major == rq_major && my_minor == rq_minor
&& my_micro == rq_micro
&& strcmp(my_plvl, rq_plvl) >= 0)) {
return ver;
}
return NULL;
}
@@ -0,0 +1,240 @@
/**********************************************************
TEA - Tiny Encryption Algorithm
Feistel cipher by David Wheeler & Roger M. Needham
(extended version)
**********************************************************/
/* $Id: xtea.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _mcrypt_set_key xtea_LTX__mcrypt_set_key
#define _mcrypt_encrypt xtea_LTX__mcrypt_encrypt
#define _mcrypt_decrypt xtea_LTX__mcrypt_decrypt
#define _mcrypt_get_size xtea_LTX__mcrypt_get_size
#define _mcrypt_get_block_size xtea_LTX__mcrypt_get_block_size
#define _is_block_algorithm xtea_LTX__is_block_algorithm
#define _mcrypt_get_key_size xtea_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes xtea_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name xtea_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test xtea_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version xtea_LTX__mcrypt_algorithm_version
#define ROUNDS 32
#define DELTA 0x9e3779b9 /* sqr(5)-1 * 2^31 */
/**********************************************************
Input values: k[4] 128-bit key
v[2] 64-bit plaintext block
Output values: v[2] 64-bit ciphertext block
**********************************************************/
WIN32DLL_DEFINE
int _mcrypt_set_key(word32 * k, word32 * input_key, int len)
{
k[0] = 0;
k[2] = 0;
k[1] = 0;
k[3] = 0;
memmove(k, input_key, len);
return 0;
}
WIN32DLL_DEFINE void _mcrypt_encrypt(word32 * k, word32 * v)
{
#ifdef WORDS_BIGENDIAN
word32 y = v[0], z = v[1];
#else
word32 y = byteswap32(v[0]), z = byteswap32(v[1]);
#endif
word32 limit, sum = 0;
int N = ROUNDS;
limit = DELTA * N;
#ifdef WORDS_BIGENDIAN
while (sum != limit) {
y += (((z << 4) ^ (z >> 5)) + z) ^ (sum + k[sum & 3]);
sum += DELTA;
z += (((y << 4) ^ (y >> 5)) + y) ^ (sum +
k[(sum >> 11) & 3]);
}
#else
while (sum != limit) {
y += (((z << 4) ^ (z >> 5)) + z) ^ (sum +
byteswap32(k
[sum & 3]));
sum += DELTA;
z += (((y << 4) ^ (y >> 5)) + y) ^ (sum +
byteswap32(k
[(sum >>
11) &
3]));
}
#endif
#ifdef WORDS_BIGENDIAN
v[0] = y;
v[1] = z;
#else
v[0] = byteswap32(y);
v[1] = byteswap32(z);
#endif
}
WIN32DLL_DEFINE void _mcrypt_decrypt(word32 * k, word32 * v)
{
#ifdef WORDS_BIGENDIAN
word32 y = v[0], z = v[1];
#else
word32 y = byteswap32(v[0]), z = byteswap32(v[1]);
#endif
word32 limit, sum = 0;
int N = (-ROUNDS);
limit = DELTA * N;
#ifdef WORDS_BIGENDIAN
sum = DELTA * (-N);
while (sum) {
z -= (((y << 4) ^ (y >> 5)) + y) ^ (sum +
k[(sum >> 11) & 3]);
sum -= DELTA;
y -= (((z << 4) ^ (z >> 5)) + z) ^ (sum + k[sum & 3]);
#else
sum = DELTA * (-N);
while (sum) {
z -= (((y << 4) ^ (y >> 5)) + y) ^ (sum +
byteswap32(k
[(sum >>
11) &
3]));
sum -= DELTA;
y -= (((z << 4) ^ (z >> 5)) + z) ^ (sum +
byteswap32(k
[sum & 3]));
#endif
}
#ifdef WORDS_BIGENDIAN
v[0] = y;
v[1] = z;
#else
v[0] = byteswap32(y);
v[1] = byteswap32(z);
#endif
}
/*
void _mcrypt_encrypt(word32 * k, word32 * v)
{
_mcrypt_tean(k, v, ROUNDS);
}
void _mcrypt_decrypt(word32 * k, word32 * v)
{
_mcrypt_tean(k, v, -ROUNDS);
}
*/
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return 4 * sizeof(word32);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 8;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 16;
}
static const int key_sizes[] = { 16 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE const char *_mcrypt_get_algorithms_name()
{
return "xTEA";
}
#define CIPHER "f61e7ff6da7cdb27"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL)
return -1;
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,17 @@
#if !defined(AFX_CRYPT_H__613C5174_16F0_42A5_9493_C7489534C080__INCLUDED_)
#define AFX_CRYPT_H__613C5174_16F0_42A5_9493_C7489534C080__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
class CCrypt
{
static char *m_pszKey;
public:
static CString Decrypt(CString sString);
static CString Encrypt(CString sString);
};
#endif // !defined(AFX_CRYPT_H__613C5174_16F0_42A5_9493_C7489534C080__INCLUDED_)
@@ -0,0 +1,66 @@
## Process this file with automake to produce Makefile.in
DEFS = @DEFS@
INCLUDES = -I. -I../.. $(INCLTDL) -I../../lib
EXTRA_DIST = twofish.h saferplus.h rijndael.h \
rc2.h serpent.h cast-256.h blowfish.h \
cast-128.h cast-128_sboxes.h des.h tripledes.h \
3-way.h enigma.h arcfour.h wake.h \
safer.h xtea.h panama.h
pkglib_LTLIBRARIES = @INSTALL_ALGORITHM_MODULES@
EXTRA_LTLIBRARIES = twofish.la rijndael-128.la \
rijndael-192.la rijndael-256.la saferplus.la rc2.la xtea.la \
serpent.la safer-sk64.la safer-sk128.la cast-256.la loki97.la \
gost.la threeway.la cast-128.la blowfish.la des.la blowfish-compat.la \
tripledes.la enigma.la arcfour.la panama.la wake.la
noinst_LTLIBRARIES = @NOINSTALL_ALGORITHM_MODULES@
twofish_la_SOURCES = twofish.c
twofish_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
wake_la_SOURCES = wake.c
wake_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
panama_la_SOURCES = panama.c
panama_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
rijndael_128_la_SOURCES = rijndael-128.c
rijndael_128_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
rijndael_192_la_SOURCES = rijndael-192.c
rijndael_192_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
rijndael_256_la_SOURCES = rijndael-256.c
rijndael_256_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
saferplus_la_SOURCES = saferplus.c
saferplus_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
serpent_la_SOURCES = serpent.c
serpent_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
xtea_la_SOURCES = xtea.c
xtea_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
rc2_la_SOURCES = rc2.c
rc2_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
safer_sk64_la_SOURCES = safer64.c
safer_sk64_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
safer_sk128_la_SOURCES = safer128.c
safer_sk128_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
cast_256_la_SOURCES = cast-256.c
cast_256_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
loki97_la_SOURCES = loki97.c
loki97_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
gost_la_SOURCES = gost.c
gost_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
threeway_la_SOURCES = 3-way.c
threeway_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
blowfish_la_SOURCES = blowfish.c
blowfish_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
blowfish_compat_la_SOURCES = blowfish-compat.c
blowfish_compat_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
cast_128_la_SOURCES = cast-128.c
cast_128_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
des_la_SOURCES = des.c
des_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
tripledes_la_SOURCES = tripledes.c
tripledes_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
enigma_la_SOURCES = enigma.c
enigma_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
arcfour_la_SOURCES = arcfour.c
arcfour_la_LDFLAGS = -module -avoid-version -rpath $(pkglibdir)
@@ -0,0 +1,658 @@
/*
Wrapper interface to XML parser
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif
#include "ne_i18n.h"
#include "ne_alloc.h"
#include "ne_xml.h"
#include "ne_utils.h"
#include "ne_string.h"
#if defined(HAVE_EXPAT)
/* expat support: */
#ifdef HAVE_XMLPARSE_H
#include "xmlparse.h"
#else
#include <expat.h>
#endif
typedef XML_Char ne_xml_char;
#if !defined(XML_MAJOR_VERSION) || (XML_MAJOR_VERSION < 2 \
&& XML_MINOR_VERSION == 95 \
&& XML_MICRO_VERSION < 2)
#define NEED_BOM_HANDLING
#endif
#elif defined(HAVE_LIBXML)
/* libxml2 support: */
#include <libxml/xmlversion.h>
#include <libxml/parser.h>
typedef xmlChar ne_xml_char;
#if LIBXML_VERSION < 20619
/* 2.6.19 and earlier have broken BOM handling */
#define NEED_BOM_HANDLING
#endif
#else /* not HAVE_LIBXML */
# error need an XML parser
#endif /* not HAVE_EXPAT */
/* Approx. one screen of text: */
#define ERR_SIZE (2048)
struct handler {
ne_xml_startelm_cb *startelm_cb; /* start-element callback */
ne_xml_endelm_cb *endelm_cb; /* end-element callback */
ne_xml_cdata_cb *cdata_cb; /* character-data callback. */
void *userdata; /* userdata for the above. */
struct handler *next; /* next handler in stack. */
};
#ifdef HAVE_LIBXML
static void sax_error(void *ctx, const char *msg, ...);
#endif
struct element {
const ne_xml_char *nspace;
ne_xml_char *name;
int state; /* opaque state integer */
/* Namespaces declared in this element */
ne_xml_char *default_ns; /* A default namespace */
struct namespace *nspaces; /* List of other namespace scopes */
struct handler *handler; /* Handler for this element */
struct element *parent; /* parent element, or NULL */
};
/* We pass around a ne_xml_parser as the userdata in the parsing
* library. This maintains the current state of the parse and various
* other bits and bobs. Within the parse, we store the current branch
* of the tree, i.e., the current element and all its parents, up to
* the root, but nothing other than that. */
struct ne_xml_parser_s {
struct element *root; /* the root of the document */
struct element *current; /* current element in the branch */
struct handler *top_handlers; /* always points at the
* handler on top of the stack. */
int failure; /* zero whilst parse should continue */
int prune; /* if non-zero, depth within a dead branch */
#ifdef NEED_BOM_HANDLING
int bom_pos;
#endif
#ifdef HAVE_EXPAT
XML_Parser parser;
char *encoding;
#else
xmlParserCtxtPtr parser;
#endif
char error[ERR_SIZE];
};
/* The callback handlers */
static void start_element(void *userdata, const ne_xml_char *name, const ne_xml_char **atts);
static void end_element(void *userdata, const ne_xml_char *name);
static void char_data(void *userdata, const ne_xml_char *cdata, int len);
static const char *resolve_nspace(const struct element *elm,
const char *prefix, size_t pfxlen);
/* Linked list of namespace scopes */
struct namespace {
ne_xml_char *name;
ne_xml_char *uri;
struct namespace *next;
};
#ifdef HAVE_LIBXML
/* Could be const as far as we care, but libxml doesn't want that */
static xmlSAXHandler sax_handler = {
NULL, /* internalSubset */
NULL, /* isStandalone */
NULL, /* hasInternalSubset */
NULL, /* hasExternalSubset */
NULL, /* resolveEntity */
NULL, /* getEntity */
NULL, /* entityDecl */
NULL, /* notationDecl */
NULL, /* attributeDecl */
NULL, /* elementDecl */
NULL, /* unparsedEntityDecl */
NULL, /* setDocumentLocator */
NULL, /* startDocument */
NULL, /* endDocument */
start_element, /* startElement */
end_element, /* endElement */
NULL, /* reference */
char_data, /* characters */
NULL, /* ignorableWhitespace */
NULL, /* processingInstruction */
NULL, /* comment */
NULL, /* xmlParserWarning */
sax_error, /* xmlParserError */
sax_error, /* fatal error (never called by libxml2?) */
NULL, /* getParameterEntity */
char_data /* cdataBlock */
};
/* empty attributes array to mimic expat behaviour */
static const char *empty_atts[] = {NULL, NULL};
/* macro for determining the attributes array to pass */
#define PASS_ATTS(atts) (atts ? (const char **)(atts) : empty_atts)
#else
#define PASS_ATTS(atts) ((const char **)(atts))
/* XML declaration callback for expat. */
static void decl_handler(void *userdata,
const XML_Char *version, const XML_Char *encoding,
int standalone)
{
ne_xml_parser *p = userdata;
if (encoding) p->encoding = ne_strdup(encoding);
}
#endif /* HAVE_LIBXML */
int ne_xml_currentline(ne_xml_parser *p)
{
#ifdef HAVE_EXPAT
return XML_GetCurrentLineNumber(p->parser);
#else
return p->parser->input->line;
#endif
}
const char *ne_xml_doc_encoding(const ne_xml_parser *p)
{
#ifdef HAVE_LIBXML
return p->parser->encoding;
#else
return p->encoding;
#endif
}
/* The first character of the REC-xml-names "NCName" rule excludes
* "Digit | '.' | '-' | '_' | CombiningChar | Extender"; the XML
* parser will not enforce this rule in a namespace declaration since
* it treats the entire attribute name as a REC-xml "Name" rule. It's
* too hard to check for all of CombiningChar | Digit | Extender here,
* but the valid_ncname_ch1 macro catches some of the rest. */
/* Return non-zero if 'ch' is an invalid start character for an NCName: */
#define invalid_ncname_ch1(ch) ((ch) == '\0' || strchr("-.0123456789", (ch)) != NULL)
/* Subversion repositories have been deployed which use property names
* marshalled as NCNames including a colon character; these should
* also be rejected but will be allowed for the time being. */
#define invalid_ncname(xn) (invalid_ncname_ch1((xn)[0]))
/* Extract the namespace prefix declarations from 'atts'. */
static int declare_nspaces(ne_xml_parser *p, struct element *elm,
const ne_xml_char **atts)
{
int n;
for (n = 0; atts && atts[n]; n += 2) {
if (strcmp(atts[n], "xmlns") == 0) {
/* New default namespace */
elm->default_ns = ne_strdup(atts[n+1]);
} else if (strncmp(atts[n], "xmlns:", 6) == 0) {
struct namespace *ns;
/* Reject some invalid NCNames as namespace prefix, and an
* empty URI as the namespace URI */
if (invalid_ncname(atts[n] + 6) || atts[n+1][0] == '\0') {
ne_snprintf(p->error, ERR_SIZE,
("XML parse error at line %d: invalid namespace "
"declaration"), ne_xml_currentline(p));
return -1;
}
/* New namespace scope */
ns = ne_calloc(sizeof(*ns));
ns->next = elm->nspaces;
elm->nspaces = ns;
ns->name = ne_strdup(atts[n]+6); /* skip the xmlns= */
ns->uri = ne_strdup(atts[n+1]);
}
}
return 0;
}
/* Expand an XML qualified name, which may include a namespace prefix
* as well as the local part. */
static int expand_qname(ne_xml_parser *p, struct element *elm,
const ne_xml_char *qname)
{
const ne_xml_char *pfx;
pfx = strchr(qname, ':');
if (pfx == NULL) {
struct element *e = elm;
/* Find default namespace; guaranteed to terminate as the root
* element always has default_ns="". */
while (e->default_ns == NULL)
e = e->parent;
elm->name = ne_strdup(qname);
elm->nspace = e->default_ns;
} else if (invalid_ncname(pfx + 1) || qname == pfx) {
ne_snprintf(p->error, ERR_SIZE,
_("XML parse error at line %d: invalid element name"),
ne_xml_currentline(p));
return -1;
} else {
const char *uri = resolve_nspace(elm, qname, pfx-qname);
if (uri) {
elm->name = ne_strdup(pfx+1);
elm->nspace = uri;
} else {
ne_snprintf(p->error, ERR_SIZE,
("XML parse error at line %d: undeclared namespace prefix"),
ne_xml_currentline(p));
return -1;
}
}
return 0;
}
/* Called with the start of a new element. */
static void start_element(void *userdata, const ne_xml_char *name,
const ne_xml_char **atts)
{
ne_xml_parser *p = userdata;
struct element *elm;
struct handler *hand;
int state = NE_XML_DECLINE;
if (p->failure) return;
if (p->prune) {
p->prune++;
return;
}
/* Create a new element */
elm = ne_calloc(sizeof *elm);
elm->parent = p->current;
p->current = elm;
if (declare_nspaces(p, elm, atts) || expand_qname(p, elm, name)) {
p->failure = 1;
return;
}
/* Find a handler which will accept this element (or abort the parse) */
for (hand = elm->parent->handler; hand && state == NE_XML_DECLINE;
hand = hand->next) {
elm->handler = hand;
state = hand->startelm_cb(hand->userdata, elm->parent->state,
elm->nspace, elm->name, PASS_ATTS(atts));
}
NE_DEBUG(NE_DBG_XML, "XML: start-element (%d, {%s, %s}) => %d\n",
elm->parent->state, elm->nspace, elm->name, state);
if (state > 0)
elm->state = state;
else if (state == NE_XML_DECLINE)
/* prune this branch. */
p->prune++;
else /* state < 0 => abort parse */
p->failure = state;
}
/* Destroys an element structure. */
static void destroy_element(struct element *elm)
{
struct namespace *this_ns, *next_ns;
ne_free(elm->name);
/* Free the namespaces */
this_ns = elm->nspaces;
while (this_ns != NULL) {
next_ns = this_ns->next;
ne_free(this_ns->name);
ne_free(this_ns->uri);
ne_free(this_ns);
this_ns = next_ns;
}
if (elm->default_ns)
ne_free(elm->default_ns);
ne_free(elm);
}
/* cdata SAX callback */
static void char_data(void *userdata, const ne_xml_char *data, int len)
{
ne_xml_parser *p = userdata;
struct element *elm = p->current;
if (p->failure || p->prune) return;
if (elm->handler->cdata_cb) {
p->failure = elm->handler->cdata_cb(elm->handler->userdata, elm->state, data, len);
NE_DEBUG(NE_DBG_XML, "XML: char-data (%d) returns %d\n",
elm->state, p->failure);
}
}
/* Called with the end of an element */
static void end_element(void *userdata, const ne_xml_char *name)
{
ne_xml_parser *p = userdata;
struct element *elm = p->current;
if (p->failure) return;
if (p->prune) {
if (p->prune-- > 1) return;
} else if (elm->handler->endelm_cb) {
p->failure = elm->handler->endelm_cb(elm->handler->userdata, elm->state,
elm->nspace, elm->name);
if (p->failure) {
NE_DEBUG(NE_DBG_XML, "XML: end-element for %d failed with %d.\n",
elm->state, p->failure);
}
}
NE_DEBUG(NE_DBG_XML, "XML: end-element (%d, {%s, %s})\n",
elm->state, elm->nspace, elm->name);
/* move back up the tree */
p->current = elm->parent;
p->prune = 0;
destroy_element(elm);
}
/* Find a namespace definition for 'prefix' in given element, where
* length of prefix is 'pfxlen'. Returns the URI or NULL. */
static const char *resolve_nspace(const struct element *elm,
const char *prefix, size_t pfxlen)
{
const struct element *s;
/* Search up the tree. */
for (s = elm; s != NULL; s = s->parent) {
const struct namespace *ns;
/* Iterate over defined spaces on this node. */
for (ns = s->nspaces; ns != NULL; ns = ns->next) {
if (strlen(ns->name) == pfxlen &&
memcmp(ns->name, prefix, pfxlen) == 0)
return ns->uri;
}
}
return NULL;
}
ne_xml_parser *ne_xml_create(void)
{
ne_xml_parser *p = ne_calloc(sizeof *p);
/* Placeholder for the root element */
p->current = p->root = ne_calloc(sizeof *p->root);
p->root->default_ns = "";
p->root->state = 0;
strcpy(p->error, _("Unknown error"));
#ifdef HAVE_EXPAT
p->parser = XML_ParserCreate(NULL);
if (p->parser == NULL) {
abort();
}
XML_SetElementHandler(p->parser, start_element, end_element);
XML_SetCharacterDataHandler(p->parser, char_data);
XML_SetUserData(p->parser, (void *) p);
XML_SetXmlDeclHandler(p->parser, decl_handler);
#else
p->parser = xmlCreatePushParserCtxt(&sax_handler,
(void *)p, NULL, 0, NULL);
if (p->parser == NULL) {
abort();
}
p->parser->replaceEntities = 1;
#endif
return p;
}
void ne_xml_push_handler(ne_xml_parser *p,
ne_xml_startelm_cb *startelm_cb,
ne_xml_cdata_cb *cdata_cb,
ne_xml_endelm_cb *endelm_cb,
void *userdata)
{
struct handler *hand = ne_calloc(sizeof(struct handler));
hand->startelm_cb = startelm_cb;
hand->cdata_cb = cdata_cb;
hand->endelm_cb = endelm_cb;
hand->userdata = userdata;
/* If this is the first handler registered, update the
* base pointer too. */
if (p->top_handlers == NULL) {
p->root->handler = hand;
p->top_handlers = hand;
} else {
p->top_handlers->next = hand;
p->top_handlers = hand;
}
}
int ne_xml_parse_v(void *userdata, const char *block, size_t len)
{
ne_xml_parser *p = userdata;
return ne_xml_parse(p, (const ne_xml_char *)block, len);
}
#define BOM_UTF8 "\xEF\xBB\xBF" /* UTF-8 BOM */
int ne_xml_parse(ne_xml_parser *p, const char *block, size_t len)
{
int ret, flag;
/* duck out if it's broken */
if (p->failure) {
NE_DEBUG(NE_DBG_XMLPARSE, "XML: Failed; ignoring %" NE_FMT_SIZE_T
" bytes.\n", len);
return p->failure;
}
if (len == 0) {
flag = -1;
block = "";
NE_DEBUG(NE_DBG_XMLPARSE, "XML: End of document.\n");
} else {
NE_DEBUG(NE_DBG_XMLPARSE, "XML: Parsing %" NE_FMT_SIZE_T " bytes.\n", len);
flag = 0;
}
#ifdef NEED_BOM_HANDLING
if (p->bom_pos < 3) {
NE_DEBUG(NE_DBG_XMLPARSE, "Checking for UTF-8 BOM.\n");
while (len > 0 && p->bom_pos < 3 &&
block[0] == BOM_UTF8[p->bom_pos]) {
block++;
len--;
p->bom_pos++;
}
if (len == 0)
return 0;
if (p->bom_pos == 0) {
p->bom_pos = 3; /* no BOM */
} else if (p->bom_pos > 0 && p->bom_pos < 3) {
strcpy(p->error, _("Invalid Byte Order Mark"));
return p->failure = 1;
}
}
#endif
/* Note, don't write a parser error if p->failure, since an error
* will already have been written in that case. */
#ifdef HAVE_EXPAT
ret = XML_Parse(p->parser, block, len, flag);
NE_DEBUG(NE_DBG_XMLPARSE, "XML: XML_Parse returned %d\n", ret);
if (ret == 0 && p->failure == 0) {
ne_snprintf(p->error, ERR_SIZE,
"XML parse error at line %d: %s",
XML_GetCurrentLineNumber(p->parser),
XML_ErrorString(XML_GetErrorCode(p->parser)));
p->failure = 1;
NE_DEBUG(NE_DBG_XMLPARSE, "XML: Parse error: %s\n", p->error);
}
#else
ret = xmlParseChunk(p->parser, block, len, flag);
NE_DEBUG(NE_DBG_XMLPARSE, "XML: xmlParseChunk returned %d\n", ret);
/* Parse errors are normally caught by the sax_error() callback,
* which clears p->valid. */
if (p->parser->errNo && p->failure == 0) {
ne_snprintf(p->error, ERR_SIZE, "XML parse error at line %d.",
ne_xml_currentline(p));
p->failure = 1;
NE_DEBUG(NE_DBG_XMLPARSE, "XML: Parse error: %s\n", p->error);
}
#endif
return p->failure;
}
int ne_xml_failed(ne_xml_parser *p)
{
return p->failure;
}
void ne_xml_destroy(ne_xml_parser *p)
{
struct element *elm, *parent;
struct handler *hand, *next;
/* Free up the handlers on the stack: the root element has the
* pointer to the base of the handler stack. */
for (hand = p->root->handler; hand!=NULL; hand=next) {
next = hand->next;
ne_free(hand);
}
/* Clean up remaining elements */
for (elm = p->current; elm != p->root; elm = parent) {
parent = elm->parent;
destroy_element(elm);
}
/* free root element */
ne_free(p->root);
#ifdef HAVE_EXPAT
XML_ParserFree(p->parser);
if (p->encoding) ne_free(p->encoding);
#else
xmlFreeParserCtxt(p->parser);
#endif
ne_free(p);
}
void ne_xml_set_error(ne_xml_parser *p, const char *msg)
{
ne_snprintf(p->error, ERR_SIZE, "%s", msg);
}
#ifdef HAVE_LIBXML
static void sax_error(void *ctx, const char *msg, ...)
{
ne_xml_parser *p = ctx;
va_list ap;
char buf[1024];
va_start(ap, msg);
ne_vsnprintf(buf, 1024, msg, ap);
va_end(ap);
if (p->failure == 0) {
ne_snprintf(p->error, ERR_SIZE,
_("XML parse error at line %d: %s."),
p->parser->input->line, buf);
p->failure = 1;
}
}
#endif
const char *ne_xml_get_error(ne_xml_parser *p)
{
return p->error;
}
const char *
ne_xml_get_attr(ne_xml_parser *p, const char **attrs,
const char *nspace, const char *name)
{
int n;
for (n = 0; attrs[n] != NULL; n += 2) {
char *pnt = strchr(attrs[n], ':');
if (!nspace && !pnt && strcmp(attrs[n], name) == 0) {
return attrs[n+1];
} else if (nspace && pnt) {
/* If a namespace is given, and the local part matches,
* then resolve the namespace and compare that too. */
if (strcmp(pnt + 1, name) == 0) {
const char *uri = resolve_nspace(p->current,
attrs[n], pnt - attrs[n]);
if (uri && strcmp(uri, nspace) == 0)
return attrs[n+1];
}
}
}
return NULL;
}
int ne_xml_mapid(const struct ne_xml_idmap map[], size_t maplen,
const char *nspace, const char *name)
{
size_t n;
for (n = 0; n < maplen; n++)
if (strcmp(name, map[n].name) == 0 &&
strcmp(nspace, map[n].nspace) == 0)
return map[n].id;
return 0;
}
@@ -0,0 +1,62 @@
/*
HTTP authentication routines
Copyright (C) 1999-2002, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_AUTH_H
#define NE_AUTH_H
#include "ne_session.h" /* for ne_session */
BEGIN_NEON_DECLS
/* Size of username/password buffers passed to ne_auth_creds
* callback. */
#define NE_ABUFSIZ (256)
/* The callback used to request the username and password in the given
* realm. The username and password must be copied into the buffers
* which are both of size NE_ABUFSIZ. The 'attempt' parameter is zero
* on the first call to the callback, and increases by one each time
* an attempt to authenticate fails.
*
* The callback must return zero to indicate that authentication
* should be attempted with the username/password, or non-zero to
* cancel the request. (if non-zero, username and password are
* ignored.) */
typedef int (*ne_auth_creds)(void *userdata, const char *realm, int attempt,
char *username, char *password);
/* TOP TIP: if you just wish to try authenticating once (even if the
* user gets the username/password wrong), have your implementation of
* the callback return the 'attempt' value. */
/* Set callbacks to provide credentials for server and proxy
* authentication. userdata is passed as the first argument to the
* callback. The callback is called *indefinitely* until either it
* returns non-zero, or authentication is successful. */
void ne_set_server_auth(ne_session *sess, ne_auth_creds creds, void *userdata);
void ne_set_proxy_auth(ne_session *sess, ne_auth_creds creds, void *userdata);
/* Clear any stored authentication details for the given session. */
void ne_forget_auth(ne_session *sess);
END_NEON_DECLS
#endif /* NE_AUTH_H */
@@ -0,0 +1,92 @@
/* Copyright (c) 1998, 1999, 2000 Thai Open Source Software Center Ltd
See the file COPYING for copying permission.
*/
/* External API definitions */
#if defined(_MSC_EXTENSIONS) && !defined(__BEOS__) && !defined(__CYGWIN__)
#define XML_USE_MSC_EXTENSIONS 1
#endif
/* Expat tries very hard to make the API boundary very specifically
defined. There are two macros defined to control this boundary;
each of these can be defined before including this header to
achieve some different behavior, but doing so it not recommended or
tested frequently.
XMLCALL - The calling convention to use for all calls across the
"library boundary." This will default to cdecl, and
try really hard to tell the compiler that's what we
want.
XMLIMPORT - Whatever magic is needed to note that a function is
to be imported from a dynamically loaded library
(.dll, .so, or .sl, depending on your platform).
The XMLCALL macro was added in Expat 1.95.7. The only one which is
expected to be directly useful in client code is XMLCALL.
Note that on at least some Unix versions, the Expat library must be
compiled with the cdecl calling convention as the default since
system headers may assume the cdecl convention.
*/
#ifndef XMLCALL
#if defined(XML_USE_MSC_EXTENSIONS)
#define XMLCALL __cdecl
#elif defined(__GNUC__) && defined(__i386)
#define XMLCALL __attribute__((cdecl))
#else
/* For any platform which uses this definition and supports more than
one calling convention, we need to extend this definition to
declare the convention used on that platform, if it's possible to
do so.
If this is the case for your platform, please file a bug report
with information on how to identify your platform via the C
pre-processor and how to specify the same calling convention as the
platform's malloc() implementation.
*/
#define XMLCALL
#endif
#endif /* not defined XMLCALL */
#if !defined(XML_STATIC) && !defined(XMLIMPORT)
#ifndef XML_BUILDING_EXPAT
/* using Expat from an application */
#ifdef XML_USE_MSC_EXTENSIONS
#define XMLIMPORT __declspec(dllimport)
#endif
#endif
#endif /* not defined XML_STATIC */
/* If we didn't define it above, define it away: */
#ifndef XMLIMPORT
#define XMLIMPORT
#endif
#define XMLPARSEAPI(type) XMLIMPORT type XMLCALL
#ifdef __cplusplus
extern "C" {
#endif
#ifdef XML_UNICODE_WCHAR_T
#define XML_UNICODE
#endif
#ifdef XML_UNICODE /* Information is UTF-16 encoded. */
#ifdef XML_UNICODE_WCHAR_T
typedef wchar_t XML_Char;
typedef wchar_t XML_LChar;
#else
typedef unsigned short XML_Char;
typedef char XML_LChar;
#endif /* XML_UNICODE_WCHAR_T */
#else /* Information is UTF-8 encoded. */
typedef char XML_Char;
typedef char XML_LChar;
#endif /* XML_UNICODE */
@@ -0,0 +1,13 @@
#pragma once
#define AXSTATE_COMPLETE 1
#define AXSTATE_SKIPED 2
#define AXSTATE_CANCELED 3
#define AXSTATE_ERROR 4
#define AXCLOSE_COMPLETE 1
#define AXCLOSE_CANCELED 2
#define AXCLOSE_WITHERROR 3
#define AXERROR_INVALID_PROPERTIES 20001
#define AXERROR_TRANSFER_IS_BUSY 20002
@@ -0,0 +1,100 @@
/*
WebDAV 207 multi-status response handling
Copyright (C) 1999-2004, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef DAV207_H
#define DAV207_H
#include "ne_xml.h"
#include "ne_request.h" /* for ne_request */
BEGIN_NEON_DECLS
/* The defined state integer for the '{DAV:}prop' element. */
#define NE_207_STATE_PROP (50)
/* This interface reserves the state integers 'x' where 0 < x < 100 */
#define NE_207_STATE_TOP (100)
/* Handling of 207 multistatus XML documents. A "multistatus"
* document is made up of a set of responses, each concerned with a
* particular resource. Each response may have an associated result
* status and failure description. A response is made up of a set of
* propstats, each of which again may have an associated result status
* and failure description. */
/* Start and end response callbacks trigger at the start and end of
* each "response" within the multistatus body. 'href' gives the URI
* of the resource which is subject of this response. The return
* value of a 'start_response' callback is passed as the 'response'
* parameter to the corresponding 'end_response' parameter. */
typedef void *ne_207_start_response(void *userdata, const char *href);
typedef void ne_207_end_response(void *userdata, void *response,
const ne_status *status,
const char *description);
/* Similarly, start and end callbacks for each propstat within the
* response. The return value of the 'start_response' callback for
* the response in which this propstat is contains is passed as the
* 'response' parameter. The return value of each 'start_propstat' is
* passed as the 'propstat' parameter' to the corresponding
* 'end_propstat' callback. If the start_propstat callback returns
* NULL, parsing is aborted (the XML parser error must be set by the
* callback). */
typedef void *ne_207_start_propstat(void *userdata, void *response);
typedef void ne_207_end_propstat(void *userdata, void *propstat,
const ne_status *status,
const char *description);
typedef struct ne_207_parser_s ne_207_parser;
/* Create 207 parser an add the handlers the the given parser's
* handler stack. */
ne_207_parser *ne_207_create(ne_xml_parser *parser, void *userdata);
/* Register response handling callbacks. */
void ne_207_set_response_handlers(ne_207_parser *p,
ne_207_start_response *start,
ne_207_end_response *end);
/* Register propstat handling callbacks. */
void ne_207_set_propstat_handlers(ne_207_parser *p,
ne_207_start_propstat *start,
ne_207_end_propstat *end);
/* Destroy the parser */
void ne_207_destroy(ne_207_parser *p);
/* An acceptance function which only accepts 207 responses */
int ne_accept_207(void *userdata, ne_request *req, const ne_status *status);
void *ne_207_get_current_propstat(ne_207_parser *p);
void *ne_207_get_current_response(ne_207_parser *p);
/* Dispatch request 'req', returning:
* NE_ERROR: for a dispatch error, or a non-2xx response, or a
* 207 response which contained a non-2xx propstat
* NE_OK: for a 2xx response or a 207 response which contained
* only 2xx-class propstats.
* The request object is destroyed in both cases. */
int ne_simple_request(ne_session *sess, ne_request *req);
END_NEON_DECLS
#endif /* DAV207_H */
@@ -0,0 +1,248 @@
/*
Date manipulation routines
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
Copyright (C) 2004 Jiang Lei <tristone@deluxe.ocn.ne.jp>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#include <sys/types.h>
#include <time.h>
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include <stdio.h>
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef WIN32
#include <windows.h> /* for TIME_ZONE_INFORMATION */
#endif
#include "ne_alloc.h"
#include "ne_dates.h"
#include "ne_string.h"
/* Generic date manipulation routines. */
/* ISO8601: 2001-01-01T12:30:00Z */
#define ISO8601_FORMAT_Z "%04d-%02d-%02dT%02d:%02d:%lfZ"
#define ISO8601_FORMAT_M "%04d-%02d-%02dT%02d:%02d:%lf-%02d:%02d"
#define ISO8601_FORMAT_P "%04d-%02d-%02dT%02d:%02d:%lf+%02d:%02d"
/* RFC1123: Sun, 06 Nov 1994 08:49:37 GMT */
#define RFC1123_FORMAT "%3s, %02d %3s %4d %02d:%02d:%02d GMT"
/* RFC850: Sunday, 06-Nov-94 08:49:37 GMT */
#define RFC1036_FORMAT "%10s %2d-%3s-%2d %2d:%2d:%2d GMT"
/* asctime: Wed Jun 30 21:49:08 1993 */
#define ASCTIME_FORMAT "%3s %3s %2d %2d:%2d:%2d %4d"
static const char *const rfc1123_weekdays[7] = {
"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"
};
static const char *const short_months[12] = {
"Jan", "Feb", "Mar", "Apr", "May", "Jun",
"Jul", "Aug", "Sep", "Oct", "Nov", "Dec"
};
#if defined(HAVE_STRUCT_TM_TM_GMTOFF)
#define GMTOFF(t) ((t).tm_gmtoff)
#elif defined(HAVE_STRUCT_TM___TM_GMTOFF)
#define GMTOFF(t) ((t).__tm_gmtoff)
#elif defined(WIN32)
#define GMTOFF(t) (gmt_to_local_win32())
#else
/* FIXME: work out the offset anyway. */
#define GMTOFF(t) (0)
#endif
#ifdef WIN32
time_t gmt_to_local_win32(void)
{
TIME_ZONE_INFORMATION tzinfo;
DWORD dwStandardDaylight;
long bias;
dwStandardDaylight = GetTimeZoneInformation(&tzinfo);
bias = tzinfo.Bias;
if (dwStandardDaylight == TIME_ZONE_ID_STANDARD)
bias += tzinfo.StandardBias;
if (dwStandardDaylight == TIME_ZONE_ID_DAYLIGHT)
bias += tzinfo.DaylightBias;
return (- bias * 60);
}
#endif
/* Returns the time/date GMT, in RFC1123-type format: eg
* Sun, 06 Nov 1994 08:49:37 GMT. */
char *ne_rfc1123_date(time_t anytime) {
struct tm *gmt;
char *ret;
gmt = gmtime(&anytime);
if (gmt == NULL)
return NULL;
ret = ne_malloc(29 + 1); /* dates are 29 chars long */
/* it goes: Sun, 06 Nov 1994 08:49:37 GMT */
ne_snprintf(ret, 30, RFC1123_FORMAT,
rfc1123_weekdays[gmt->tm_wday], gmt->tm_mday,
short_months[gmt->tm_mon], 1900 + gmt->tm_year,
gmt->tm_hour, gmt->tm_min, gmt->tm_sec);
return ret;
}
/* Takes an ISO-8601-formatted date string and returns the time_t.
* Returns (time_t)-1 if the parse fails. */
time_t ne_iso8601_parse(const char *date)
{
struct tm gmt = {0};
int off_hour, off_min;
double sec;
off_t fix;
int n;
/* it goes: ISO8601: 2001-01-01T12:30:00+03:30 */
if ((n = sscanf(date, ISO8601_FORMAT_P,
&gmt.tm_year, &gmt.tm_mon, &gmt.tm_mday,
&gmt.tm_hour, &gmt.tm_min, &sec,
&off_hour, &off_min)) == 8) {
gmt.tm_sec = (int)sec;
fix = - off_hour * 3600 - off_min * 60;
}
/* it goes: ISO8601: 2001-01-01T12:30:00-03:30 */
else if ((n = sscanf(date, ISO8601_FORMAT_M,
&gmt.tm_year, &gmt.tm_mon, &gmt.tm_mday,
&gmt.tm_hour, &gmt.tm_min, &sec,
&off_hour, &off_min)) == 8) {
gmt.tm_sec = (int)sec;
fix = off_hour * 3600 + off_min * 60;
}
/* it goes: ISO8601: 2001-01-01T12:30:00Z */
else if ((n = sscanf(date, ISO8601_FORMAT_Z,
&gmt.tm_year, &gmt.tm_mon, &gmt.tm_mday,
&gmt.tm_hour, &gmt.tm_min, &sec)) == 6) {
gmt.tm_sec = (int)sec;
fix = 0;
}
else {
return (time_t)-1;
}
gmt.tm_year -= 1900;
gmt.tm_isdst = -1;
gmt.tm_mon--;
return mktime(&gmt) + fix + GMTOFF(gmt);
}
/* Takes an RFC1123-formatted date string and returns the time_t.
* Returns (time_t)-1 if the parse fails. */
time_t ne_rfc1123_parse(const char *date)
{
struct tm gmt = {0};
char wkday[4], mon[4];
int n;
/* it goes: Sun, 06 Nov 1994 08:49:37 GMT */
n = sscanf(date, RFC1123_FORMAT,
wkday, &gmt.tm_mday, mon, &gmt.tm_year, &gmt.tm_hour,
&gmt.tm_min, &gmt.tm_sec);
/* Is it portable to check n==7 here? */
gmt.tm_year -= 1900;
for (n=0; n<12; n++)
if (strcmp(mon, short_months[n]) == 0)
break;
/* tm_mon comes out as 12 if the month is corrupt, which is desired,
* since the mktime will then fail */
gmt.tm_mon = n;
gmt.tm_isdst = -1;
return mktime(&gmt) + GMTOFF(gmt);
}
/* Takes a string containing a RFC1036-style date and returns the time_t */
time_t ne_rfc1036_parse(const char *date)
{
struct tm gmt = {0};
int n;
char wkday[11], mon[4];
/* RFC850/1036 style dates: Sunday, 06-Nov-94 08:49:37 GMT */
n = sscanf(date, RFC1036_FORMAT,
wkday, &gmt.tm_mday, mon, &gmt.tm_year,
&gmt.tm_hour, &gmt.tm_min, &gmt.tm_sec);
if (n != 7) {
return (time_t)-1;
}
/* portable to check n here? */
for (n=0; n<12; n++)
if (strcmp(mon, short_months[n]) == 0)
break;
/* tm_mon comes out as 12 if the month is corrupt, which is desired,
* since the mktime will then fail */
/* Defeat Y2K bug. */
if (gmt.tm_year < 50)
gmt.tm_year += 100;
gmt.tm_mon = n;
gmt.tm_isdst = -1;
return mktime(&gmt) + GMTOFF(gmt);
}
/* (as)ctime dates are like:
* Wed Jun 30 21:49:08 1993
*/
time_t ne_asctime_parse(const char *date)
{
struct tm gmt = {0};
int n;
char wkday[4], mon[4];
n = sscanf(date, ASCTIME_FORMAT,
wkday, mon, &gmt.tm_mday,
&gmt.tm_hour, &gmt.tm_min, &gmt.tm_sec,
&gmt.tm_year);
/* portable to check n here? */
for (n=0; n<12; n++)
if (strcmp(mon, short_months[n]) == 0)
break;
/* tm_mon comes out as 12 if the month is corrupt, which is desired,
* since the mktime will then fail */
gmt.tm_mon = n;
gmt.tm_isdst = -1;
return mktime(&gmt) + GMTOFF(gmt);
}
/* HTTP-date parser */
time_t ne_httpdate_parse(const char *date)
{
time_t tmp;
tmp = ne_rfc1123_parse(date);
if (tmp == -1) {
tmp = ne_rfc1036_parse(date);
if (tmp == -1)
tmp = ne_asctime_parse(date);
}
return tmp;
}
@@ -0,0 +1,4 @@
void *mxmalloc(size_t size);
void *mxcalloc(size_t nmemb, size_t size);
void *mxrealloc(void *ptr, size_t size);
void mxfree( void *ptr, size_t size);
@@ -0,0 +1,217 @@
// SmartInterfacePtr.h: interface for the TInterfacePtr class.
//
/////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2000-2001 by Paolo Messina
// (http://www.geocities.com/ppescher - ppescher@yahoo.com)
//
// The contents of this file are subject to the Artistic License (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.opensource.org/licenses/artistic-license.html
//
// If you find this code useful, credits would be nice!
//
/////////////////////////////////////////////////////////////////////////////
#if !defined(AFX_SHELLWRAPPERS_H__B0E1BBE7_A5D8_4A80_9A36_ED5553FE74F6__INCLUDED_)
#define AFX_SHELLWRAPPERS_H__B0E1BBE7_A5D8_4A80_9A36_ED5553FE74F6__INCLUDED_
#include <shlobj.h>
#include "SmartInterfacePtr.h"
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
class SMallocPtr : public TStaticInterfacePtr<IMalloc>
{
public:
SMallocPtr()
{
if (m_pIface == NULL)
SHGetMalloc(&m_pIface);
else
m_pIface->AddRef();
}
};
class SDesktopFolderPtr : public TStaticInterfacePtr<IShellFolder>
{
public:
SDesktopFolderPtr()
{
if (m_pIface == NULL)
SHGetDesktopFolder(&m_pIface);
else
m_pIface->AddRef();
}
};
class SShellFolderPtr : public TInterfacePtr<IShellFolder>
{
public:
SShellFolderPtr() {}
SShellFolderPtr(IShellFolder* pFolder) { Copy(pFolder); }
SShellFolderPtr(IShellFolder* pParentFolder, LPCITEMIDLIST pidlRel)
{
if (pidlRel != NULL && pidlRel->mkid.cb == 0)
{
// it's a root element, copy the parent folder
Copy(pParentFolder);
}
else
{
pParentFolder->BindToObject(pidlRel,
NULL, IID_IShellFolder, (LPVOID*)&m_pIface);
}
}
SShellFolderPtr(LPCITEMIDLIST pidlAbs)
{
SDesktopFolderPtr pDesktopFolder;
if (pidlAbs != NULL && pidlAbs->mkid.cb == 0)
{
// it's a root element, copy the parent folder
Copy(pDesktopFolder);
}
else
{
pDesktopFolder->BindToObject(pidlAbs,
NULL, IID_IShellFolder, (LPVOID*)&m_pIface);
}
}
};
class SEnumIDListPtr : public TInterfacePtr<IEnumIDList>
{
public:
SEnumIDListPtr(IShellFolder* pParentFolder, UINT nFlags, HWND hOwner = NULL)
{
pParentFolder->EnumObjects(hOwner, nFlags, &m_pIface);
}
};
class SContextMenuPtr : public TInterfacePtr<IContextMenu>
{
public:
SContextMenuPtr() {}
SContextMenuPtr(IShellFolder* pParentFolder, LPCITEMIDLIST pidlRel, HWND hOwner = NULL)
{
pParentFolder->GetUIObjectOf(hOwner, 1, &pidlRel,
IID_IContextMenu, NULL, (LPVOID*)&m_pIface);
}
};
class SContextMenu2Ptr : public TInterfacePtr<IContextMenu2>
{
public:
SContextMenu2Ptr(IContextMenu* pIface)
{
if (pIface != NULL)
pIface->QueryInterface(IID_IContextMenu2, (LPVOID*)&m_pIface);
}
};
// templates
template <class TYPE>
class TSharedObject
{
public:
~TSharedObject()
{ Destroy(); }
protected:
TYPE* m_pObj;
TSharedObject()
{ m_pObj = NULL; }
TSharedObject(const TSharedObject& shobj)
{ Copy(shobj); }
void Copy(const TSharedObject& shobj);
public:
operator const TYPE * () const
{ return m_pObj; }
const TSharedObject& operator = (const TSharedObject& shobj)
{
Destroy();
Copy(shobj);
return *this;
}
BOOL IsValid() const
{ return m_pObj != NULL; }
void Attach(TYPE* pObj)
{
ASSERT(m_pObj == NULL); // can't attach two times!
m_pObj = pObj;
}
TYPE* Detach()
{
TYPE* ret = m_pObj;
m_pObj = NULL;
return ret;
}
// obtain a void object by pointer
TYPE** GetPointer()
{
Destroy();
return &m_pObj;
}
#ifdef _DEBUG
void DumpRaw(CDumpContext& dc) const
{
dc << "addr = " << (void*)m_pObj << "\n";
if (m_pObj == NULL)
return;
SMallocPtr pMalloc;
ULONG size = pMalloc->GetSize((void*)m_pObj);
cd << "[hex dump]\n";
dc.HexDump(".", (BYTE*)m_pObj, (int)size, 16);
dc << "\n";
}
#endif //_DEBUG
protected:
void Destroy()
{
SMallocPtr pMalloc;
pMalloc->Free(Detach());
}
};
template <class TYPE>
void TSharedObject<TYPE>::Copy(const TSharedObject& shobj)
{
m_pObj = NULL;
if (shobj.m_pObj == NULL)
return;
// obj to copy must have been allocated this way
SMallocPtr pMalloc;
ULONG size = (ULONG)pMalloc->GetSize((void*)shobj.m_pObj);
ASSERT(size > 0);
if (shobj.m_pObj != NULL)
{
m_pObj = (TYPE*)pMalloc->Alloc(size);
CopyMemory(m_pObj, shobj.m_pObj, size);
}
}
#endif //!defined(AFX_SHELLWRAPPERS_H__B0E1BBE7_A5D8_4A80_9A36_ED5553FE74F6__INCLUDED_)
@@ -0,0 +1,687 @@
/* This is an independent implementation of the encryption algorithm: */
/* */
/* SAFER+ by Cylink */
/* */
/* which is a candidate algorithm in the Advanced Encryption Standard */
/* programme of the US National Institute of Standards and Technology. */
/* */
/* Copyright in this implementation is held by Dr B R Gladman but I */
/* hereby give permission for its free direct or derivative use subject */
/* to acknowledgment of its origin and compliance with any conditions */
/* that the originators of the algorithm place on its exploitation. */
/* */
/* Dr Brian Gladman (gladman@seven77.demon.co.uk) 14th January 1999 */
/* $Id: saferplus.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* Timing data for SAFER+ (safer.c)
Core timing without I/O endian conversion:
128 bit key:
Key Setup: 4278 cycles
Encrypt: 1722 cycles = 14.9 mbits/sec
Decrypt: 1709 cycles = 15.0 mbits/sec
Mean: 1716 cycles = 14.9 mbits/sec
192 bit key:
Key Setup: 7426 cycles
Encrypt: 2555 cycles = 10.0 mbits/sec
Decrypt: 2530 cycles = 10.1 mbits/sec
Mean: 2543 cycles = 10.1 mbits/sec
256 bit key:
Key Setup: 11313 cycles
Encrypt: 3391 cycles = 7.5 mbits/sec
Decrypt: 3338 cycles = 7.7 mbits/sec
Mean: 3365 cycles = 7.6 mbits/sec
Full timing with I/O endian conversion:
128 bit key:
Key Setup: 3977 cycles
Encrypt: 1751 cycles = 14.6 mbits/sec
Decrypt: 1734 cycles = 14.8 mbits/sec
Mean: 1743 cycles = 14.7 mbits/sec
192 bit key:
Key Setup: 6490 cycles
Encrypt: 2574 cycles = 9.9 mbits/sec
Decrypt: 2549 cycles = 10.0 mbits/sec
Mean: 2562 cycles = 10.0 mbits/sec
256 bit key:
Key Setup: 9487 cycles
Encrypt: 3412 cycles = 7.5 mbits/sec
Decrypt: 3372 cycles = 7.6 mbits/sec
Mean: 3392 cycles = 7.5 mbits/sec
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "saferplus.h"
#include <stdlib.h>
#define _mcrypt_set_key saferplus_LTX__mcrypt_set_key
#define _mcrypt_encrypt saferplus_LTX__mcrypt_encrypt
#define _mcrypt_decrypt saferplus_LTX__mcrypt_decrypt
#define _mcrypt_get_size saferplus_LTX__mcrypt_get_size
#define _mcrypt_get_block_size saferplus_LTX__mcrypt_get_block_size
#define _is_block_algorithm saferplus_LTX__is_block_algorithm
#define _mcrypt_get_key_size saferplus_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes saferplus_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name saferplus_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test saferplus_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version saferplus_LTX__mcrypt_algorithm_version
byte safer_expf[256] =
{ 1, 45, 226, 147, 190, 69, 21, 174, 120, 3, 135, 164, 184, 56, 207,
63,
8, 103, 9, 148, 235, 38, 168, 107, 189, 24, 52, 27, 187, 191, 114,
247,
64, 53, 72, 156, 81, 47, 59, 85, 227, 192, 159, 216, 211, 243, 141,
177,
255, 167, 62, 220, 134, 119, 215, 166, 17, 251, 244, 186, 146, 145,
100, 131,
241, 51, 239, 218, 44, 181, 178, 43, 136, 209, 153, 203, 140, 132,
29, 20,
129, 151, 113, 202, 95, 163, 139, 87, 60, 130, 196, 82, 92, 28,
232, 160,
4, 180, 133, 74, 246, 19, 84, 182, 223, 12, 26, 142, 222, 224, 57,
252,
32, 155, 36, 78, 169, 152, 158, 171, 242, 96, 208, 108, 234, 250,
199, 217,
0, 212, 31, 110, 67, 188, 236, 83, 137, 254, 122, 93, 73, 201, 50,
194,
249, 154, 248, 109, 22, 219, 89, 150, 68, 233, 205, 230, 70, 66,
143, 10,
193, 204, 185, 101, 176, 210, 198, 172, 30, 65, 98, 41, 46, 14,
116, 80,
2, 90, 195, 37, 123, 138, 42, 91, 240, 6, 13, 71, 111, 112, 157,
126,
16, 206, 18, 39, 213, 76, 79, 214, 121, 48, 104, 54, 117, 125, 228,
237,
128, 106, 144, 55, 162, 94, 118, 170, 197, 127, 61, 175, 165, 229,
25, 97,
253, 77, 124, 183, 11, 238, 173, 75, 34, 245, 231, 115, 35, 33,
200, 5,
225, 102, 221, 179, 88, 105, 99, 86, 15, 161, 49, 149, 23, 7, 58,
40
};
byte safer_logf[512] = {
128, 0, 176, 9, 96, 239, 185, 253, 16, 18, 159, 228, 105, 186, 173,
248,
192, 56, 194, 101, 79, 6, 148, 252, 25, 222, 106, 27, 93, 78, 168,
130,
112, 237, 232, 236, 114, 179, 21, 195, 255, 171, 182, 71, 68, 1,
172, 37,
201, 250, 142, 65, 26, 33, 203, 211, 13, 110, 254, 38, 88, 218, 50,
15,
32, 169, 157, 132, 152, 5, 156, 187, 34, 140, 99, 231, 197, 225,
115, 198,
175, 36, 91, 135, 102, 39, 247, 87, 244, 150, 177, 183, 92, 139,
213, 84,
121, 223, 170, 246, 62, 163, 241, 17, 202, 245, 209, 23, 123, 147,
131, 188,
189, 82, 30, 235, 174, 204, 214, 53, 8, 200, 138, 180, 226, 205,
191, 217,
208, 80, 89, 63, 77, 98, 52, 10, 72, 136, 181, 86, 76, 46, 107,
158,
210, 61, 60, 3, 19, 251, 151, 81, 117, 74, 145, 113, 35, 190, 118,
42,
95, 249, 212, 85, 11, 220, 55, 49, 22, 116, 215, 119, 167, 230, 7,
219,
164, 47, 70, 243, 97, 69, 103, 227, 12, 162, 59, 28, 133, 24, 4,
29,
41, 160, 143, 178, 90, 216, 166, 126, 238, 141, 83, 75, 161, 154,
193, 14,
122, 73, 165, 44, 129, 196, 199, 54, 43, 127, 67, 149, 51, 242,
108, 104,
109, 240, 2, 40, 206, 221, 155, 234, 94, 153, 124, 20, 134, 207,
229, 66,
184, 64, 120, 45, 58, 233, 100, 31, 146, 144, 125, 57, 111, 224,
137, 48,
128, 0, 176, 9, 96, 239, 185, 253, 16, 18, 159, 228, 105, 186, 173,
248,
192, 56, 194, 101, 79, 6, 148, 252, 25, 222, 106, 27, 93, 78, 168,
130,
112, 237, 232, 236, 114, 179, 21, 195, 255, 171, 182, 71, 68, 1,
172, 37,
201, 250, 142, 65, 26, 33, 203, 211, 13, 110, 254, 38, 88, 218, 50,
15,
32, 169, 157, 132, 152, 5, 156, 187, 34, 140, 99, 231, 197, 225,
115, 198,
175, 36, 91, 135, 102, 39, 247, 87, 244, 150, 177, 183, 92, 139,
213, 84,
121, 223, 170, 246, 62, 163, 241, 17, 202, 245, 209, 23, 123, 147,
131, 188,
189, 82, 30, 235, 174, 204, 214, 53, 8, 200, 138, 180, 226, 205,
191, 217,
208, 80, 89, 63, 77, 98, 52, 10, 72, 136, 181, 86, 76, 46, 107,
158,
210, 61, 60, 3, 19, 251, 151, 81, 117, 74, 145, 113, 35, 190, 118,
42,
95, 249, 212, 85, 11, 220, 55, 49, 22, 116, 215, 119, 167, 230, 7,
219,
164, 47, 70, 243, 97, 69, 103, 227, 12, 162, 59, 28, 133, 24, 4,
29,
41, 160, 143, 178, 90, 216, 166, 126, 238, 141, 83, 75, 161, 154,
193, 14,
122, 73, 165, 44, 129, 196, 199, 54, 43, 127, 67, 149, 51, 242,
108, 104,
109, 240, 2, 40, 206, 221, 155, 234, 94, 153, 124, 20, 134, 207,
229, 66,
184, 64, 120, 45, 58, 233, 100, 31, 146, 144, 125, 57, 111, 224,
137, 48
};
/* byte l_key[33 * 16]; */
/* word32 k_bytes; */
WIN32DLL_DEFINE
int _mcrypt_set_key(SPI * sp_key, const word32 * in_key,
const word32 key_len)
{
word32 wlk[9]; /* 36 bytes */
byte *lk = (void*)wlk, by; /* lk should have 33 bytes */
word32 i, j, k, l, m, *lkp = wlk;
memset( wlk, 0, sizeof(wlk));
for (i = 0; i < key_len / sizeof(word32); ++i) {
lkp[i] = in_key[(key_len / sizeof(word32)) - i - 1];
}
sp_key->k_bytes = key_len;
lk[sp_key->k_bytes] = 0;
for (i = 0; i < sp_key->k_bytes; ++i) {
lk[sp_key->k_bytes] ^= lk[i];
sp_key->l_key[i] = lk[i];
}
for (i = 0; i < sp_key->k_bytes; ++i) {
for (j = 0; j <= sp_key->k_bytes; ++j) {
by = lk[j];
lk[j] = by << 3 | by >> 5;
}
k = 17 * i + 35;
l = 16 * i + 16;
m = i + 1;
if (i < 16) {
for (j = 0; j < 16; ++j) {
sp_key->l_key[l + j] =
lk[m] +
safer_expf[safer_expf[(k + j) & 255]];
m = (m == sp_key->k_bytes ? 0 : m + 1);
}
} else {
for (j = 0; j < 16; ++j) {
sp_key->l_key[l + j] =
lk[m] + safer_expf[(k + j) & 255];
m = (m == sp_key->k_bytes ? 0 : m + 1);
}
}
}
return 0;
}
void do_fr(byte x[16], byte * kp)
{
byte t;
x[0] = safer_expf[x[0] ^ kp[0]] + kp[16];
x[1] = safer_logf[x[1] + kp[1]] ^ kp[17];
x[2] = safer_logf[x[2] + kp[2]] ^ kp[18];
x[3] = safer_expf[x[3] ^ kp[3]] + kp[19];
x[4] = safer_expf[x[4] ^ kp[4]] + kp[20];
x[5] = safer_logf[x[5] + kp[5]] ^ kp[21];
x[6] = safer_logf[x[6] + kp[6]] ^ kp[22];
x[7] = safer_expf[x[7] ^ kp[7]] + kp[23];
x[8] = safer_expf[x[8] ^ kp[8]] + kp[24];
x[9] = safer_logf[x[9] + kp[9]] ^ kp[25];
x[10] = safer_logf[x[10] + kp[10]] ^ kp[26];
x[11] = safer_expf[x[11] ^ kp[11]] + kp[27];
x[12] = safer_expf[x[12] ^ kp[12]] + kp[28];
x[13] = safer_logf[x[13] + kp[13]] ^ kp[29];
x[14] = safer_logf[x[14] + kp[14]] ^ kp[30];
x[15] = safer_expf[x[15] ^ kp[15]] + kp[31];
x[1] += x[0];
x[0] += x[1];
x[3] += x[2];
x[2] += x[3];
x[5] += x[4];
x[4] += x[5];
x[7] += x[6];
x[6] += x[7];
x[9] += x[8];
x[8] += x[9];
x[11] += x[10];
x[10] += x[11];
x[13] += x[12];
x[12] += x[13];
x[15] += x[14];
x[14] += x[15];
x[7] += x[0];
x[0] += x[7];
x[1] += x[2];
x[2] += x[1];
x[3] += x[4];
x[4] += x[3];
x[5] += x[6];
x[6] += x[5];
x[11] += x[8];
x[8] += x[11];
x[9] += x[10];
x[10] += x[9];
x[15] += x[12];
x[12] += x[15];
x[13] += x[14];
x[14] += x[13];
x[3] += x[0];
x[0] += x[3];
x[15] += x[2];
x[2] += x[15];
x[7] += x[4];
x[4] += x[7];
x[1] += x[6];
x[6] += x[1];
x[5] += x[8];
x[8] += x[5];
x[13] += x[10];
x[10] += x[13];
x[11] += x[12];
x[12] += x[11];
x[9] += x[14];
x[14] += x[9];
x[13] += x[0];
x[0] += x[13];
x[5] += x[2];
x[2] += x[5];
x[9] += x[4];
x[4] += x[9];
x[11] += x[6];
x[6] += x[11];
x[15] += x[8];
x[8] += x[15];
x[1] += x[10];
x[10] += x[1];
x[3] += x[12];
x[12] += x[3];
x[7] += x[14];
x[14] += x[7];
t = x[0];
x[0] = x[14];
x[14] = x[12];
x[12] = x[10];
x[10] = x[2];
x[2] = x[8];
x[8] = x[4];
x[4] = t;
t = x[1];
x[1] = x[7];
x[7] = x[11];
x[11] = x[5];
x[5] = x[13];
x[13] = t;
t = x[15];
x[15] = x[3];
x[3] = t;
}
void do_ir(byte x[16], byte * kp)
{
byte t;
t = x[3];
x[3] = x[15];
x[15] = t;
t = x[13];
x[13] = x[5];
x[5] = x[11];
x[11] = x[7];
x[7] = x[1];
x[1] = t;
t = x[4];
x[4] = x[8];
x[8] = x[2];
x[2] = x[10];
x[10] = x[12];
x[12] = x[14];
x[14] = x[0];
x[0] = t;
x[14] -= x[7];
x[7] -= x[14];
x[12] -= x[3];
x[3] -= x[12];
x[10] -= x[1];
x[1] -= x[10];
x[8] -= x[15];
x[15] -= x[8];
x[6] -= x[11];
x[11] -= x[6];
x[4] -= x[9];
x[9] -= x[4];
x[2] -= x[5];
x[5] -= x[2];
x[0] -= x[13];
x[13] -= x[0];
x[14] -= x[9];
x[9] -= x[14];
x[12] -= x[11];
x[11] -= x[12];
x[10] -= x[13];
x[13] -= x[10];
x[8] -= x[5];
x[5] -= x[8];
x[6] -= x[1];
x[1] -= x[6];
x[4] -= x[7];
x[7] -= x[4];
x[2] -= x[15];
x[15] -= x[2];
x[0] -= x[3];
x[3] -= x[0];
x[14] -= x[13];
x[13] -= x[14];
x[12] -= x[15];
x[15] -= x[12];
x[10] -= x[9];
x[9] -= x[10];
x[8] -= x[11];
x[11] -= x[8];
x[6] -= x[5];
x[5] -= x[6];
x[4] -= x[3];
x[3] -= x[4];
x[2] -= x[1];
x[1] -= x[2];
x[0] -= x[7];
x[7] -= x[0];
x[14] -= x[15];
x[15] -= x[14];
x[12] -= x[13];
x[13] -= x[12];
x[10] -= x[11];
x[11] -= x[10];
x[8] -= x[9];
x[9] -= x[8];
x[6] -= x[7];
x[7] -= x[6];
x[4] -= x[5];
x[5] -= x[4];
x[2] -= x[3];
x[3] -= x[2];
x[0] -= x[1];
x[1] -= x[0];
x[0] = safer_logf[x[0] - kp[16] + 256] ^ kp[0];
x[1] = safer_expf[x[1] ^ kp[17]] - kp[1];
x[2] = safer_expf[x[2] ^ kp[18]] - kp[2];
x[3] = safer_logf[x[3] - kp[19] + 256] ^ kp[3];
x[4] = safer_logf[x[4] - kp[20] + 256] ^ kp[4];
x[5] = safer_expf[x[5] ^ kp[21]] - kp[5];
x[6] = safer_expf[x[6] ^ kp[22]] - kp[6];
x[7] = safer_logf[x[7] - kp[23] + 256] ^ kp[7];
x[8] = safer_logf[x[8] - kp[24] + 256] ^ kp[8];
x[9] = safer_expf[x[9] ^ kp[25]] - kp[9];
x[10] = safer_expf[x[10] ^ kp[26]] - kp[10];
x[11] = safer_logf[x[11] - kp[27] + 256] ^ kp[11];
x[12] = safer_logf[x[12] - kp[28] + 256] ^ kp[12];
x[13] = safer_expf[x[13] ^ kp[29]] - kp[13];
x[14] = safer_expf[x[14] ^ kp[30]] - kp[14];
x[15] = safer_logf[x[15] - kp[31] + 256] ^ kp[15];
}
WIN32DLL_DEFINE void _mcrypt_encrypt(SPI * spi, word32 * _blk)
{
byte *kp;
word32 __blk[16];
byte *blk = (void *) __blk;
__blk[3] = _blk[0];
__blk[2] = _blk[1];
__blk[1] = _blk[2];
__blk[0] = _blk[3];
do_fr(blk, spi->l_key);
do_fr(blk, spi->l_key + 32);
do_fr(blk, spi->l_key + 64);
do_fr(blk, spi->l_key + 96);
do_fr(blk, spi->l_key + 128);
do_fr(blk, spi->l_key + 160);
do_fr(blk, spi->l_key + 192);
do_fr(blk, spi->l_key + 224);
if (spi->k_bytes > 16) {
do_fr(blk, spi->l_key + 256);
do_fr(blk, spi->l_key + 288);
do_fr(blk, spi->l_key + 320);
do_fr(blk, spi->l_key + 352);
}
if (spi->k_bytes > 24) {
do_fr(blk, spi->l_key + 384);
do_fr(blk, spi->l_key + 416);
do_fr(blk, spi->l_key + 448);
do_fr(blk, spi->l_key + 480);
}
kp = spi->l_key + 16 * spi->k_bytes;
blk[0] ^= kp[0];
blk[1] += kp[1];
blk[2] += kp[2];
blk[3] ^= kp[3];
blk[4] ^= kp[4];
blk[5] += kp[5];
blk[6] += kp[6];
blk[7] ^= kp[7];
blk[8] ^= kp[8];
blk[9] += kp[9];
blk[10] += kp[10];
blk[11] ^= kp[11];
blk[12] ^= kp[12];
blk[13] += kp[13];
blk[14] += kp[14];
blk[15] ^= kp[15];
_blk[3] = (__blk[0]);
_blk[2] = (__blk[1]);
_blk[1] = (__blk[2]);
_blk[0] = (__blk[3]);
}
WIN32DLL_DEFINE void _mcrypt_decrypt(SPI * spi, word32 * _blk)
{
byte *kp;
word32 __blk[16];
byte *blk = (void *) __blk;
__blk[3] = _blk[0];
__blk[2] = _blk[1];
__blk[1] = _blk[2];
__blk[0] = _blk[3];
kp = spi->l_key + 16 * spi->k_bytes;
blk[0] ^= kp[0];
blk[1] -= kp[1];
blk[2] -= kp[2];
blk[3] ^= kp[3];
blk[4] ^= kp[4];
blk[5] -= kp[5];
blk[6] -= kp[6];
blk[7] ^= kp[7];
blk[8] ^= kp[8];
blk[9] -= kp[9];
blk[10] -= kp[10];
blk[11] ^= kp[11];
blk[12] ^= kp[12];
blk[13] -= kp[13];
blk[14] -= kp[14];
blk[15] ^= kp[15];
if (spi->k_bytes > 24) {
do_ir(blk, spi->l_key + 480);
do_ir(blk, spi->l_key + 448);
do_ir(blk, spi->l_key + 416);
do_ir(blk, spi->l_key + 384);
}
if (spi->k_bytes > 16) {
do_ir(blk, spi->l_key + 352);
do_ir(blk, spi->l_key + 320);
do_ir(blk, spi->l_key + 288);
do_ir(blk, spi->l_key + 256);
}
do_ir(blk, spi->l_key + 224);
do_ir(blk, spi->l_key + 192);
do_ir(blk, spi->l_key + 160);
do_ir(blk, spi->l_key + 128);
do_ir(blk, spi->l_key + 96);
do_ir(blk, spi->l_key + 64);
do_ir(blk, spi->l_key + 32);
do_ir(blk, spi->l_key);
_blk[3] = (__blk[0]);
_blk[2] = (__blk[1]);
_blk[1] = (__blk[2]);
_blk[0] = (__blk[3]);
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return sizeof(SPI);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 16;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 32;
}
static const int key_sizes[] = { 16,24,32 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE char *_mcrypt_get_algorithms_name()
{
return "Safer+";
}
#define CIPHER "97fa76704bf6b578549f65c6f75b228b"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL)
return -1;
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,378 @@
/*
* Copyright (C) 1998,1999,2000,2001 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Library General Public License as published
* by the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "wake.h"
#define _mcrypt_set_key wake_LTX__mcrypt_set_key
#define _mcrypt_encrypt wake_LTX__mcrypt_encrypt
#define _mcrypt_decrypt wake_LTX__mcrypt_decrypt
#define _mcrypt_get_size wake_LTX__mcrypt_get_size
#define _mcrypt_get_block_size wake_LTX__mcrypt_get_block_size
#define _is_block_algorithm wake_LTX__is_block_algorithm
#define _mcrypt_get_key_size wake_LTX__mcrypt_get_key_size
#define _mcrypt_get_algo_iv_size wake_LTX__mcrypt_get_algo_iv_size
#define _mcrypt_get_supported_key_sizes wake_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name wake_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test wake_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version wake_LTX__mcrypt_algorithm_version
/* WAKE reference C-code, based on the description in David J. Wheeler's
* paper "A bulk Data Encryption Algorithm"
*/
/* #define USE_IV */
/* IV is an mcrypt extension */
static const word32 tt[10] = {
0x726a8f3bUL,
0xe69a3b5cUL,
0xd3c71fe5UL,
0xab3c73d2UL,
0x4d3a8eb3UL,
0x0396d6e8UL,
0x3d4c2f7aUL,
0x9ee27cf3UL
};
WIN32DLL_DEFINE
int _mcrypt_set_key(WAKE_KEY * wake_key, word32 * key, int len,
word32 * IV, int ivlen)
{
word32 x, z, p;
word32 k[4];
/* the key must be exactly 256 bits */
if (len != 32)
return -1;
#ifdef WORDS_BIGENDIAN
k[0] = byteswap32(key[0]);
k[1] = byteswap32(key[1]);
k[2] = byteswap32(key[2]);
k[3] = byteswap32(key[3]);
#else
k[0] = key[0];
k[1] = key[1];
k[2] = key[2];
k[3] = key[3];
#endif
for (p = 0; p < 4; p++) {
wake_key->t[p] = k[p];
}
for (p = 4; p < 256; p++) {
x = wake_key->t[p - 4] + wake_key->t[p - 1];
wake_key->t[p] = x >> 3 ^ tt[x & 7];
}
for (p = 0; p < 23; p++)
wake_key->t[p] += wake_key->t[p + 89];
x = wake_key->t[33];
z = wake_key->t[59] | 0x01000001;
z &= 0xff7fffff;
for (p = 0; p < 256; p++) {
x = (x & 0xff7fffff) + z;
wake_key->t[p] = (wake_key->t[p] & 0x00ffffff) ^ x;
}
wake_key->t[256] = wake_key->t[0];
x &= 0xff;
for (p = 0; p < 256; p++) {
wake_key->t[p] = wake_key->t[x =
(wake_key->t[p ^ x] ^ x) &
0xff];
wake_key->t[x] = wake_key->t[p + 1];
}
wake_key->counter = 0;
wake_key->r[0] = k[0];
wake_key->r[1] = k[1];
wake_key->r[2] = k[2];
#ifdef WORDS_BIGENDIAN
wake_key->r[3] = byteswap32(k[3]);
#else
wake_key->r[3] = k[3];
#endif
#ifdef USE_IV
wake_key->started = 0;
if (ivlen > 32)
wake_key->ivsize = 32;
else
wake_key->ivsize = ivlen / 4 * 4;
if (IV == NULL)
wake_key->ivsize = 0;
if (wake_key->ivsize > 0 && IV != NULL)
memcpy(&wake_key->iv, IV, wake_key->ivsize);
#endif
return 0;
}
/* in order to read the code easier */
#define r2 wake_key->tmp
#define r1 wake_key->tmp
#define counter wake_key->counter
/* M(X,Y) = (X+Y)>>8 XOR t[(X+Y) & 0xff] */
#define M(X,Y) _int_M(X,Y, wake_key)
//inline
static word32 _int_M(word32 X, word32 Y, WAKE_KEY * wake_key)
{
register word32 TMP;
TMP = X + Y;
return ((((TMP) >> 8) & 0x00ffffff) ^ wake_key->t[(TMP) & 0xff]);
}
WIN32DLL_DEFINE
void _mcrypt_encrypt(WAKE_KEY * wake_key, byte * input, int len)
{
register word32 r3, r4, r5;
word32 r6;
int i;
if (len == 0)
return;
r3 = wake_key->r[0];
r4 = wake_key->r[1];
r5 = wake_key->r[2];
r6 = wake_key->r[3];
#ifdef USE_IV
if (wake_key->started == 0) {
wake_key->started = 1;
_mcrypt_encrypt(wake_key, (byte *) & wake_key->iv,
wake_key->ivsize);
}
#endif
for (i = 0; i < len; i++) {
/* R1 = V[n] = V[n] XOR R6 - here we do it per byte --sloooow */
/* R1 is ignored */
input[i] ^= ((byte *) & r6)[counter];
/* R2 = V[n] = R1 - per byte also */
((byte *) & r2)[counter] = input[i];
counter++;
if (counter == 4) { /* r6 was used - update it! */
counter = 0;
#ifdef WORDS_BIGENDIAN
/* these swaps are because we do operations per byte */
r2 = byteswap32(r2);
r6 = byteswap32(r6);
#endif
r3 = M(r3, r2);
r4 = M(r4, r3);
r5 = M(r5, r4);
r6 = M(r6, r5);
#ifdef WORDS_BIGENDIAN
r6 = byteswap32(r6);
#endif
}
}
wake_key->r[0] = r3;
wake_key->r[1] = r4;
wake_key->r[2] = r5;
wake_key->r[3] = r6;
}
WIN32DLL_DEFINE
void _mcrypt_decrypt(WAKE_KEY * wake_key, byte * input, int len)
{
register word32 r3, r4, r5;
word32 r6;
int i;
if (len == 0)
return;
r3 = wake_key->r[0];
r4 = wake_key->r[1];
r5 = wake_key->r[2];
r6 = wake_key->r[3];
#ifdef USE_IV
if (wake_key->started == 0) {
wake_key->started = 1;
_mcrypt_encrypt(wake_key, (byte *) & wake_key->iv,
wake_key->ivsize);
wake_key->r[0] = r3;
wake_key->r[1] = r4;
wake_key->r[2] = r5;
wake_key->r[3] = r6;
_mcrypt_decrypt(wake_key, (byte *) & wake_key->iv,
wake_key->ivsize);
}
#endif
for (i = 0; i < len; i++) {
/* R1 = V[n] */
((byte *) & r1)[counter] = input[i];
/* R2 = V[n] = V[n] ^ R6 */
/* R2 is ignored */
input[i] ^= ((byte *) & r6)[counter];
counter++;
if (counter == 4) {
counter = 0;
#ifdef WORDS_BIGENDIAN
r1 = byteswap32(r1);
r6 = byteswap32(r6);
#endif
r3 = M(r3, r1);
r4 = M(r4, r3);
r5 = M(r5, r4);
r6 = M(r6, r5);
#ifdef WORDS_BIGENDIAN
r6 = byteswap32(r6);
#endif
}
}
wake_key->r[0] = r3;
wake_key->r[1] = r4;
wake_key->r[2] = r5;
wake_key->r[3] = r6;
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return sizeof(WAKE_KEY);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_algo_iv_size()
{
#ifdef USE_IV
return 32;
#else
return 0;
#endif
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 0;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 32;
}
static const int key_sizes[] = { 32 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE const char *_mcrypt_get_algorithms_name()
{
return "WAKE";
}
#define CIPHER "434d575db053acfe6e4076f05298bedbd5f4f000be555d029b1367cffc7cd51bba61c76aa17da3530fb7d9"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
unsigned char *keyword;
unsigned char plaintext[43];
unsigned char ciphertext[43];
int blocksize = 43, j;
void *key, *key2;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = (j * 5 + 10) & 0xff;
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = (j + 5) % 0xff;
}
key = malloc(_mcrypt_get_size());
key2 = malloc(_mcrypt_get_size());
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size(),
NULL, 0);
_mcrypt_encrypt(key, (void *) ciphertext, blocksize);
free(key);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
free(key2);
return -1;
}
_mcrypt_set_key(key2, (void *) keyword, _mcrypt_get_key_size(),
NULL, 0);
free(keyword);
_mcrypt_decrypt(key2, (void *) ciphertext, blocksize);
free(key2);
if (memcmp(ciphertext, plaintext, blocksize) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,450 @@
// WaitingTreeCtrl.cpp : implementation file
//
/////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2000-2001 by Paolo Messina
// (http://www.geocities.com/ppescher - ppescher@yahoo.com)
//
// The contents of this file are subject to the Artistic License (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.opensource.org/licenses/artistic-license.html
//
// If you find this code useful, credits would be nice!
//
/////////////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#include "WaitingTreeCtrl.h"
#pragma warning(push)
#pragma warning(disable: 4201)
#include <mmsystem.h>
#pragma warning(pop)
#pragma comment(lib, "winmm.lib")
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CWaitingTreeCtrl
CWaitingTreeCtrl::CWaitingTreeCtrl()
{
m_bDrawSnapshot = FALSE;
m_sWaitMsg = _T("Loading...");
m_bShowWaitMsg = FALSE;
m_hIconMsg = NULL; // default: blank icon
m_nTimerDelay = 0; // default: no timer
m_hRedrawEvent = NULL;
m_hTimerEvent = NULL;
m_hThread = NULL;
}
CWaitingTreeCtrl::~CWaitingTreeCtrl()
{
}
BEGIN_MESSAGE_MAP(CWaitingTreeCtrl, CTreeCtrl)
//{{AFX_MSG_MAP(CWaitingTreeCtrl)
ON_NOTIFY_REFLECT(TVN_ITEMEXPANDING, OnItemExpanding)
ON_NOTIFY_REFLECT(TVN_ITEMEXPANDED, OnItemExpanded)
ON_WM_ERASEBKGND()
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CWaitingTreeCtrl message handlers
void CWaitingTreeCtrl::OnItemExpanding(NMHDR* pNMHDR, LRESULT* pResult)
{
NM_TREEVIEW* pNMTreeView = (NM_TREEVIEW*)pNMHDR;
if (pNMTreeView->action & TVE_EXPAND)
PreExpandItem(pNMTreeView->itemNew.hItem);
*pResult = 0;
}
void CWaitingTreeCtrl::OnItemExpanded(NMHDR* pNMHDR, LRESULT* pResult)
{
NM_TREEVIEW* pNMTreeView = (NM_TREEVIEW*)pNMHDR;
if (pNMTreeView->action & TVE_EXPAND)
ExpandItem(pNMTreeView->itemNew.hItem);
else if (pNMTreeView->action & TVE_COLLAPSE)
{
if (WantsRefresh(pNMTreeView->itemNew.hItem))
{
// delete child items
DeleteChildren(pNMTreeView->itemNew.hItem);
}
}
*pResult = 0;
}
void CWaitingTreeCtrl::PreAnimation(HTREEITEM hItemMsg)
{
UNREFERENCED_PARAMETER(hItemMsg);
}
void CWaitingTreeCtrl::PostAnimation()
{
}
void CWaitingTreeCtrl::DoAnimation(BOOL bTimerEvent, int iMaxSteps, int iStep)
{
UNREFERENCED_PARAMETER(bTimerEvent);
UNREFERENCED_PARAMETER(iMaxSteps);
UNREFERENCED_PARAMETER(iStep);
}
int CWaitingTreeCtrl::GetPopulationCount(int *piMaxSubItems)
{
if (piMaxSubItems != NULL)
*piMaxSubItems = m_iItemCount;
return m_iItemIndex;
}
void CWaitingTreeCtrl::SetPopulationCount(int iMaxSubItems, int iFirstSubItem)
{
m_iItemCount = iMaxSubItems;
m_iItemIndex = iFirstSubItem;
SetEvent(m_hRedrawEvent);
}
void CWaitingTreeCtrl::UpdatePopulation(int iSubItems)
{
m_iItemIndex = iSubItems;
SetEvent(m_hRedrawEvent);
}
void CWaitingTreeCtrl::IncreasePopulation(int iSubItemsToAdd)
{
m_iItemIndex += iSubItemsToAdd;
SetEvent(m_hRedrawEvent);
}
void CWaitingTreeCtrl::SetAnimationDelay(UINT nMilliseconds)
{
// if greater than zero, periodic DoAnimation() will be called
m_nTimerDelay = nMilliseconds;
}
DWORD WINAPI CWaitingTreeCtrl::AnimationThreadProc(LPVOID pThis)
{
CWaitingTreeCtrl* me = (CWaitingTreeCtrl*)pThis;
HANDLE events[2] = { me->m_hTimerEvent, me->m_hRedrawEvent };
while (!me->m_bAbortAnimation)
{
DWORD wait = WaitForMultipleObjects(2, events, FALSE, INFINITE);
if (me->m_bAbortAnimation || wait == WAIT_FAILED)
break;
if (wait == WAIT_OBJECT_0) // timer event
me->DoAnimation(TRUE, me->m_iItemCount, me->m_iItemIndex);
else // redraw event
me->DoAnimation(FALSE, me->m_iItemCount, me->m_iItemIndex);
}
return 0;
}
void CWaitingTreeCtrl::StartAnimation()
{
// user-defined setup
PreAnimation(m_hItemMsg);
// animation can go
m_bAbortAnimation = FALSE;
// automatic reset events, signaled
m_hTimerEvent = CreateEvent(NULL, FALSE, TRUE, NULL);
m_hRedrawEvent = CreateEvent(NULL, FALSE, TRUE, NULL);
// start animation thread
DWORD dwThreadID = 0;
m_hThread = CreateThread(NULL, 0, AnimationThreadProc, this,
THREAD_PRIORITY_HIGHEST, &dwThreadID);
// setup timer, if specified
if (m_nTimerDelay > 0)
m_nTimerID = (UINT)timeSetEvent(m_nTimerDelay, 5, (LPTIMECALLBACK)m_hTimerEvent,
0, TIME_PERIODIC | TIME_CALLBACK_EVENT_SET);
}
void CWaitingTreeCtrl::StopAnimation()
{
// stop and destroy timer
timeKillEvent(m_nTimerID);
// signal thread to terminate
m_bAbortAnimation = TRUE;
SetEvent(m_hRedrawEvent); // make sure it can see the signal
// wait thread termination
WaitForSingleObject(m_hThread, INFINITE);
// clean up
CloseHandle(m_hTimerEvent);
m_hTimerEvent = NULL;
CloseHandle(m_hRedrawEvent);
m_hRedrawEvent = NULL;
CloseHandle(m_hThread);
m_hThread = NULL;
// user-defined cleanup
PostAnimation();
}
void CWaitingTreeCtrl::PopulateRoot()
{
PreExpandItem(TVI_ROOT);
ExpandItem(TVI_ROOT);
// force update, don't scroll
SetRedraw(FALSE);
SCROLLINFO si;
GetScrollInfo(SB_HORZ, &si);
EnsureVisible(GetChildItem(TVI_ROOT));
SetScrollInfo(SB_HORZ, &si, FALSE);
SetRedraw();
}
void CWaitingTreeCtrl::PreExpandItem(HTREEITEM hItem)
{
if (!NeedsChildren(hItem))
{
if (WantsRefresh(hItem))
{
// delete child items before populating
DeleteChildren(hItem);
}
else
{
// doesn't want new items
m_hItemToPopulate = NULL;
return;
}
}
// if it wants new child items, go on
m_hItemToPopulate = hItem;
// fix redraw when expanded programatically
UpdateWindow();
// hide changes until it's expanded
SetRedraw(FALSE);
// add wait msg, to allow item expansion
m_hItemMsg = InsertItem(m_sWaitMsg, m_hItemToPopulate);
// zero progress
m_iItemCount = 1;
m_iItemIndex = 0;
}
void CWaitingTreeCtrl::ExpandItem(HTREEITEM hItem)
{
if (m_hItemToPopulate == NULL)
return; // just expand, doesn't want new items
ASSERT(hItem == m_hItemToPopulate); // should never fail!!!
if (m_bShowWaitMsg)
{
// display wait msg now, make sure it's visible
SetRedraw();
EnsureVisible(m_hItemMsg);
UpdateWindow();
}
// setup animation thread, call PreAnimation
StartAnimation();
// draw icon
if (m_bShowWaitMsg)
DrawUserIcon();
// delay redraw after populating
SetRedraw(FALSE);
// take a snapshot of the background
TakeSnapshot();
// del temporary item (wait msg still shown)
DeleteItem(m_hItemMsg);
// fill in with sub items
BOOL bCheckChildren = PopulateItem(hItem);
// clean up animation thread, call PostAnimation
StopAnimation();
// change parent to reflect current children number
if (hItem != TVI_ROOT)
{
TVITEM item;
item.hItem = hItem;
item.mask = TVIF_HANDLE | TVIF_CHILDREN;
item.cChildren = NeedsChildren(hItem) ? 0 : 1;
if (bCheckChildren)
SetItem(&item);
else if (item.cChildren == 0)
// restore item's plus button if no children inserted
SetItemState(hItem, 0, TVIS_EXPANDED);
}
// clean up snapshot
DestroySnapshot();
// redraw now
SetRedraw(TRUE);
// scroll like in a standard expansion
HTREEITEM hChild = GetChildItem(hItem);
while (hChild != NULL && GetFirstVisibleItem() != hItem)
{
// EnsureVisible(hChild);
hChild = GetNextSiblingItem(hChild);
}
}
BOOL CWaitingTreeCtrl::WantsRefresh(HTREEITEM hItem)
{
UNREFERENCED_PARAMETER(hItem);
// default implementation, no refresh
return FALSE;
}
BOOL CWaitingTreeCtrl::GetItemImageRect(HTREEITEM hItem, LPRECT pRect)
{
if (GetImageList(TVSIL_NORMAL) == NULL)
return FALSE; // no images
CRect rc;
// get item rect
if (!GetItemRect(hItem, &rc, TRUE))
return FALSE;
int cx = GetSystemMetrics(SM_CXSMICON);
int cy = GetSystemMetrics(SM_CYSMICON);
// move onto the icon space
int margin = (rc.Height()-cy)/2;
rc.OffsetRect(-cx-3 , margin);
rc.right = rc.left + cx; // make it square
rc.bottom = rc.top + cy; // make it square
*pRect = rc;
return TRUE;
}
void CWaitingTreeCtrl::DrawUserIcon()
{
// draw user defined icon
CRect rcIcon;
if (!GetItemImageRect(m_hItemMsg, &rcIcon))
return; // no image
// create background brush with current bg color (take rgb part only)
HBRUSH hBrush = CreateSolidBrush(GetBkColor() & 0x00FFFFFF);
CClientDC dc(this);
if (m_hIconMsg != NULL)
DrawIconEx(dc.GetSafeHdc(), rcIcon.left, rcIcon.top, m_hIconMsg,
rcIcon.Width(), rcIcon.Height(), 0, hBrush, DI_NORMAL);
else
FillRect(dc.GetSafeHdc(), &rcIcon, hBrush);
DeleteObject(hBrush);
}
void CWaitingTreeCtrl::SetWaitMessage(LPCTSTR pszText, HICON hIcon)
{
m_sWaitMsg = pszText;
m_hIconMsg = hIcon;
}
void CWaitingTreeCtrl::RefreshSubItems(HTREEITEM hParent)
{
if (hParent != TVI_ROOT && !ItemHasChildren(hParent))
return;
SetRedraw(FALSE);
DeleteChildren(hParent);
if (hParent == TVI_ROOT)
PopulateRoot();
else
{
PreExpandItem(hParent);
ExpandItem(hParent);
}
SetRedraw(TRUE);
}
inline BOOL CWaitingTreeCtrl::NeedsChildren(HTREEITEM hParent)
{
return (GetChildItem(hParent) == NULL);
}
void CWaitingTreeCtrl::DeleteChildren(HTREEITEM hParent)
{
HTREEITEM hChild = GetChildItem(hParent);
HTREEITEM hNext;
while (hChild != NULL)
{
hNext = GetNextSiblingItem(hChild);
DeleteItem(hChild);
hChild = hNext;
}
}
BOOL CWaitingTreeCtrl::OnEraseBkgnd(CDC* pDC)
{
if (!m_bDrawSnapshot)
return CTreeCtrl::OnEraseBkgnd(pDC);
DrawSnapshot(pDC);
SetEvent(m_hRedrawEvent);
return TRUE;
}
void CWaitingTreeCtrl::TakeSnapshot()
{
CClientDC dc(this);
CRect rcClient;
GetClientRect(&rcClient);
int width = rcClient.Width(), height = rcClient.Height();
// create the snapshot
CDC dcSnapshot;
dcSnapshot.CreateCompatibleDC(&dc);
m_bmpSnapshot.CreateCompatibleBitmap(&dc, width, height);
// copy the control's background
CBitmap* pOldBmp = dcSnapshot.SelectObject(&m_bmpSnapshot);
dcSnapshot.BitBlt(0, 0, width, height, &dc, 0, 0, SRCCOPY);
dcSnapshot.SelectObject(pOldBmp);
m_bDrawSnapshot = TRUE;
}
void CWaitingTreeCtrl::DrawSnapshot(CDC *pDC)
{
BITMAP bm;
m_bmpSnapshot.GetBitmap(&bm);
// prepare the snapshot
CDC dcSnapshot;
dcSnapshot.CreateCompatibleDC(pDC);
// copy to the control's background
CBitmap* pOldBmp = dcSnapshot.SelectObject(&m_bmpSnapshot);
pDC->BitBlt(0, 0, bm.bmWidth, bm.bmHeight, &dcSnapshot, 0, 0, SRCCOPY);
dcSnapshot.SelectObject(pOldBmp);
}
void CWaitingTreeCtrl::DestroySnapshot()
{
m_bmpSnapshot.DeleteObject();
m_bDrawSnapshot = FALSE;
}
@@ -0,0 +1,46 @@
/*
Copyright (c) 1998, 1999 Thai Open Source Software Center Ltd
See the file COPYING for copying permission.
*/
enum {
BT_NONXML,
BT_MALFORM,
BT_LT,
BT_AMP,
BT_RSQB,
BT_LEAD2,
BT_LEAD3,
BT_LEAD4,
BT_TRAIL,
BT_CR,
BT_LF,
BT_GT,
BT_QUOT,
BT_APOS,
BT_EQUALS,
BT_QUEST,
BT_EXCL,
BT_SOL,
BT_SEMI,
BT_NUM,
BT_LSQB,
BT_S,
BT_NMSTRT,
BT_COLON,
BT_HEX,
BT_DIGIT,
BT_NAME,
BT_MINUS,
BT_OTHER, /* known not to be a name or name start character */
BT_NONASCII, /* might be a name or name start character */
BT_PERCNT,
BT_LPAR,
BT_RPAR,
BT_AST,
BT_PLUS,
BT_COMMA,
BT_VERBAR
};
#include <stddef.h>
@@ -0,0 +1,87 @@
#include "stdafx.h"
#include "TransLogger.h"
CTransLogger::CTransLogger()
{
}
CTransLogger::~CTransLogger()
{
}
HANDLE CTransLogger::m_hFile = INVALID_HANDLE_VALUE;
///////////////////////////////////////////////////////////////////////////////////////////
/// Operations
///////////////////////////////////////////////////////////////////////////////////////////
bool CTransLogger::Create(LPCTSTR lpszPathName, bool bOverwrite)
{
if(m_hFile != INVALID_HANDLE_VALUE)
return true;
m_hFile = ::CreateFile(lpszPathName, GENERIC_WRITE, FILE_SHARE_READ, NULL, bOverwrite ? CREATE_ALWAYS : OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if(m_hFile == INVALID_HANDLE_VALUE)
return false;
if(!bOverwrite)
::SetFilePointer(m_hFile, 0, NULL, FILE_END);
return true;
}
bool CTransLogger::Close()
{
if(m_hFile == INVALID_HANDLE_VALUE)
return false;
bool bClose = ::CloseHandle(m_hFile) ? true :false;
m_hFile = INVALID_HANDLE_VALUE;
return bClose;
}
bool CTransLogger::Flush()
{
if(m_hFile == INVALID_HANDLE_VALUE)
return false;
return ::FlushFileBuffers(m_hFile) ? true : false;
}
DWORD CTransLogger::Write(LPCTSTR lpszFormat, ...)
{
if(m_hFile == INVALID_HANDLE_VALUE)
return -1;
TCHAR* pszMessage = NULL;
DWORD dwSize = 0;
va_list listArgument;
va_start(listArgument, lpszFormat);
dwSize = (DWORD)::_vsctprintf(lpszFormat, listArgument) + 1;
pszMessage = new TCHAR[dwSize];
::memset(pszMessage, NULL, dwSize);
dwSize = (DWORD)::_vstprintf(pszMessage, lpszFormat, listArgument);
va_end(listArgument);
if(dwSize < 0)
{
delete [] pszMessage;
return -1;
}
DWORD dwWritten = 0;
bool bWritten = false;
bWritten = ::WriteFile(m_hFile, pszMessage, dwSize, &dwWritten, NULL) ? true : false;
if(bWritten)
Flush();
delete [] pszMessage;
return bWritten ? dwWritten : -1;
}
@@ -0,0 +1,336 @@
/*
URI manipulation routines.
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include <stdio.h>
#include <ctype.h>
#include "ne_string.h" /* for ne_buffer */
#include "ne_alloc.h"
#include "ne_uri.h"
char *ne_path_parent(const char *uri)
{
size_t len = strlen(uri);
const char *pnt = uri + len - 1;
/* skip trailing slash (parent of "/foo/" is "/") */
if (pnt >= uri && *pnt == '/')
pnt--;
/* find previous slash */
while (pnt > uri && *pnt != '/')
pnt--;
if (pnt < uri || (pnt == uri && *pnt != '/'))
return NULL;
return ne_strndup(uri, pnt - uri + 1);
}
int ne_path_has_trailing_slash(const char *uri)
{
size_t len = strlen(uri);
return ((len > 0) &&
(uri[len-1] == '/'));
}
unsigned int ne_uri_defaultport(const char *scheme)
{
/* RFC2616/3.2.3 says use case-insensitive comparisons here. */
if (strcasecmp(scheme, "http") == 0)
return 80;
else if (strcasecmp(scheme, "https") == 0)
return 443;
else
return 0;
}
/* TODO: Also, maybe stop malloc'ing here, take a "char *" uri, modify
* it in-place, and have fields point inside passed uri. More work
* for the caller then though. */
/* TODO: not a proper URI parser */
int ne_uri_parse(const char *uri, ne_uri *parsed)
{
const char *pnt, *slash, *colon, *atsign, *openbk;
parsed->port = 0;
parsed->host = NULL;
parsed->path = NULL;
parsed->scheme = NULL;
parsed->authinfo = NULL;
if (uri[0] == '\0') {
return -1;
}
pnt = strstr(uri, "://");
if (pnt) {
parsed->scheme = ne_strndup(uri, pnt - uri);
pnt += 3; /* start of hostport segment */
} else {
pnt = uri;
}
atsign = strchr(pnt, '@');
slash = strchr(pnt, '/');
openbk = strchr(pnt, '[');
/* Check for an authinfo segment in the hostport segment. */
if (atsign != NULL && (slash == NULL || atsign < slash)) {
parsed->authinfo = ne_strndup(pnt, atsign - pnt);
pnt = atsign + 1;
}
if (openbk && (!slash || openbk < slash)) {
const char *closebk = strchr(openbk, ']');
if (closebk == NULL)
return -1;
colon = strchr(closebk + 1, ':');
} else {
colon = strchr(pnt, ':');
}
if (slash == NULL) {
parsed->path = ne_strdup("/");
if (colon == NULL) {
parsed->host = ne_strdup(pnt);
} else {
parsed->port = atoi(colon+1);
parsed->host = ne_strndup(pnt, colon - pnt);
}
} else {
if (colon == NULL || colon > slash) {
/* No port segment */
if (slash != uri) {
parsed->host = ne_strndup(pnt, slash - pnt);
} else {
/* No hostname segment. */
}
} else {
/* Port segment */
parsed->port = atoi(colon + 1);
parsed->host = ne_strndup(pnt, colon - pnt);
}
parsed->path = ne_strdup(slash);
}
return 0;
}
void ne_uri_free(ne_uri *u)
{
if (u->host) ne_free(u->host);
if (u->path) ne_free(u->path);
if (u->scheme) ne_free(u->scheme);
if (u->authinfo) ne_free(u->authinfo);
memset(u, 0, sizeof *u);
}
char *ne_path_unescape(const char *uri)
{
const char *pnt;
char *ret, *retpos, buf[5] = { "0x00\0" };
retpos = ret = ne_malloc(strlen(uri) + 1);
for (pnt = uri; *pnt != '\0'; pnt++) {
if (*pnt == '%') {
if (!isxdigit((unsigned char) pnt[1]) ||
!isxdigit((unsigned char) pnt[2])) {
/* Invalid URI */
ne_free(ret);
return NULL;
}
buf[2] = *++pnt; buf[3] = *++pnt; /* bit faster than memcpy */
*retpos++ = (char)strtol(buf, NULL, 16);
} else {
*retpos++ = *pnt;
}
}
*retpos = '\0';
return ret;
}
/* ABNF definitions derived from RFC3986, except with "/" removed from
* gen-delims since it's special: */
#define GD (1) /* gen-delims = ":" / "?" / "#" / "[" / "]" / "@" */
#define SD (1) /* sub-delims = "!" / "$" / "&" / "'" / "(" / ")"
/ "*" / "+" / "," / ";" / "=" */
#define SL (0) /* forward-slash = "/" */
#define UN (0) /* unreserved = ALPHA / DIGIT / "-" / "." / "_" / "~" */
#define OT (1) /* others */
/* Lookup table for percent-encoding logic: value is non-zero if
* character should be percent-encoded. */
static const unsigned char uri_chars[128] = {
/* 0xXX x0 x2 x4 x6 x8 xA xC xE */
/* 0x */ OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT,
/* 1x */ OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT, OT,
/* 2x */ OT, SD, OT, GD, SD, OT, SD, SD, SD, SD, SD, SD, SD, UN, UN, SL,
/* 3x */ UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, GD, SD, OT, SD, OT, GD,
/* 4x */ GD, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN,
/* 5x */ UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, GD, OT, GD, OT, OT,
/* 6x */ OT, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN,
/* 7x */ UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, UN, OT, OT, OT, UN, OT
};
#undef SD
#undef GD
#undef SL
#undef UN
#undef OT
/* CH must be an unsigned char; evaluates to 1 if CH should be
* percent-encoded. */
#define path_escape_ch(ch) ((ch) > 127 || uri_chars[(ch)])
char *ne_path_escape(const char *path)
{
const unsigned char *pnt;
char *ret, *p;
size_t count = 0;
for (pnt = (const unsigned char *)path; *pnt != '\0'; pnt++) {
count += path_escape_ch(*pnt);
}
if (count == 0) {
return ne_strdup(path);
}
p = ret = ne_malloc(strlen(path) + 2 * count + 1);
for (pnt = (const unsigned char *)path; *pnt != '\0'; pnt++) {
if (path_escape_ch(*pnt)) {
/* Escape it - %<hex><hex> */
sprintf(p, "%%%02x", (unsigned char) *pnt);
p += 3;
} else {
*p++ = *pnt;
}
}
*p = '\0';
return ret;
}
#undef path_escape_ch
#define CASECMP(field) do { \
n = strcasecmp(u1->field, u2->field); if (n) return n; } while(0)
#define CMP(field) do { \
n = strcmp(u1->field, u2->field); if (n) return n; } while(0)
/* As specified by RFC 2616, section 3.2.3. */
int ne_uri_cmp(const ne_uri *u1, const ne_uri *u2)
{
int n;
if (u1->path[0] == '\0' && strcmp(u2->path, "/") == 0)
return 0;
if (u2->path[0] == '\0' && strcmp(u1->path, "/") == 0)
return 0;
CMP(path);
CASECMP(host);
CASECMP(scheme);
if (u1->port > u2->port)
return 1;
else if (u1->port < u2->port)
return -1;
return 0;
}
#undef CMP
#undef CASECMP
#ifndef WIN32
#undef min
#define min(a,b) ((a)<(b)?(a):(b))
#endif
/* TODO: implement properly */
int ne_path_compare(const char *a, const char *b)
{
int ret = strcasecmp(a, b);
if (ret) {
/* This logic says: "If the lengths of the two URIs differ by
* exactly one, and the LONGER of the two URIs has a trailing
* slash and the SHORTER one DOESN'T, then..." */
int traila = ne_path_has_trailing_slash(a),
trailb = ne_path_has_trailing_slash(b),
lena = strlen(a), lenb = strlen(b);
if (traila != trailb && abs(lena - lenb) == 1 &&
((traila && lena > lenb) || (trailb && lenb > lena))) {
/* Compare them, ignoring the trailing slash on the longer
* URI */
if (strncasecmp(a, b, min(lena, lenb)) == 0)
ret = 0;
}
}
return ret;
}
char *ne_uri_unparse(const ne_uri *uri)
{
ne_buffer *buf = ne_buffer_create();
ne_buffer_concat(buf, uri->scheme, "://", uri->host, NULL);
if (uri->port > 0 && ne_uri_defaultport(uri->scheme) != uri->port) {
char str[20];
ne_snprintf(str, 20, ":%d", uri->port);
ne_buffer_zappend(buf, str);
}
ne_buffer_zappend(buf, uri->path);
return ne_buffer_finish(buf);
}
/* Give it a path segment, it returns non-zero if child is
* a child of parent. */
int ne_path_childof(const char *parent, const char *child)
{
char *root = ne_strdup(child);
int ret;
if (strlen(parent) >= strlen(child)) {
ret = 0;
} else {
/* root is the first of child, equal to length of parent */
root[strlen(parent)] = '\0';
ret = (ne_path_compare(parent, root) == 0);
}
ne_free(root);
return ret;
}
@@ -0,0 +1,32 @@
// dibpal.cpp
//
#include "stdafx.h"
#include "dib256.h"
#include "dibpal.h"
CBmpPalette::CBmpPalette( CDIBitmap* pBmp )
{
ASSERT( pBmp );
int cPaletteEntries = pBmp->GetPalEntries();
int cPalette = sizeof(LOGPALETTE) +
sizeof(PALETTEENTRY) * cPaletteEntries;
// Since the LOGPALETTE structure is open-ended, you
// must dynamically allocate it, rather than using one
// off the stack.
LOGPALETTE* pPal = (LOGPALETTE*)new BYTE[cPalette];
RGBQUAD* pColorTab = pBmp->GetColorTablePtr();
pPal->palVersion = 0x300;
pPal->palNumEntries = cPaletteEntries;
// Roll through the color table, and add each color to
// the logical palette.
for( int ndx = 0; ndx < cPaletteEntries; ndx++ )
{
pPal->palPalEntry[ndx].peRed = pColorTab[ndx].rgbRed;
pPal->palPalEntry[ndx].peGreen = pColorTab[ndx].rgbGreen;
pPal->palPalEntry[ndx].peBlue = pColorTab[ndx].rgbBlue;
pPal->palPalEntry[ndx].peFlags = NULL;
}
VERIFY( CreatePalette( pPal ) );
delete [] (BYTE*)pPal;
}
@@ -0,0 +1,114 @@
/* Copyright (c) 1998, 1999 Thai Open Source Software Center Ltd
See the file COPYING for copying permission.
*/
#ifndef XmlRole_INCLUDED
#define XmlRole_INCLUDED 1
#ifdef __VMS
/* 0 1 2 3 0 1 2 3
1234567890123456789012345678901 1234567890123456789012345678901 */
#define XmlPrologStateInitExternalEntity XmlPrologStateInitExternalEnt
#endif
#include "xmltok.h"
#ifdef __cplusplus
extern "C" {
#endif
enum {
XML_ROLE_ERROR = -1,
XML_ROLE_NONE = 0,
XML_ROLE_XML_DECL,
XML_ROLE_INSTANCE_START,
XML_ROLE_DOCTYPE_NONE,
XML_ROLE_DOCTYPE_NAME,
XML_ROLE_DOCTYPE_SYSTEM_ID,
XML_ROLE_DOCTYPE_PUBLIC_ID,
XML_ROLE_DOCTYPE_INTERNAL_SUBSET,
XML_ROLE_DOCTYPE_CLOSE,
XML_ROLE_GENERAL_ENTITY_NAME,
XML_ROLE_PARAM_ENTITY_NAME,
XML_ROLE_ENTITY_NONE,
XML_ROLE_ENTITY_VALUE,
XML_ROLE_ENTITY_SYSTEM_ID,
XML_ROLE_ENTITY_PUBLIC_ID,
XML_ROLE_ENTITY_COMPLETE,
XML_ROLE_ENTITY_NOTATION_NAME,
XML_ROLE_NOTATION_NONE,
XML_ROLE_NOTATION_NAME,
XML_ROLE_NOTATION_SYSTEM_ID,
XML_ROLE_NOTATION_NO_SYSTEM_ID,
XML_ROLE_NOTATION_PUBLIC_ID,
XML_ROLE_ATTRIBUTE_NAME,
XML_ROLE_ATTRIBUTE_TYPE_CDATA,
XML_ROLE_ATTRIBUTE_TYPE_ID,
XML_ROLE_ATTRIBUTE_TYPE_IDREF,
XML_ROLE_ATTRIBUTE_TYPE_IDREFS,
XML_ROLE_ATTRIBUTE_TYPE_ENTITY,
XML_ROLE_ATTRIBUTE_TYPE_ENTITIES,
XML_ROLE_ATTRIBUTE_TYPE_NMTOKEN,
XML_ROLE_ATTRIBUTE_TYPE_NMTOKENS,
XML_ROLE_ATTRIBUTE_ENUM_VALUE,
XML_ROLE_ATTRIBUTE_NOTATION_VALUE,
XML_ROLE_ATTLIST_NONE,
XML_ROLE_ATTLIST_ELEMENT_NAME,
XML_ROLE_IMPLIED_ATTRIBUTE_VALUE,
XML_ROLE_REQUIRED_ATTRIBUTE_VALUE,
XML_ROLE_DEFAULT_ATTRIBUTE_VALUE,
XML_ROLE_FIXED_ATTRIBUTE_VALUE,
XML_ROLE_ELEMENT_NONE,
XML_ROLE_ELEMENT_NAME,
XML_ROLE_CONTENT_ANY,
XML_ROLE_CONTENT_EMPTY,
XML_ROLE_CONTENT_PCDATA,
XML_ROLE_GROUP_OPEN,
XML_ROLE_GROUP_CLOSE,
XML_ROLE_GROUP_CLOSE_REP,
XML_ROLE_GROUP_CLOSE_OPT,
XML_ROLE_GROUP_CLOSE_PLUS,
XML_ROLE_GROUP_CHOICE,
XML_ROLE_GROUP_SEQUENCE,
XML_ROLE_CONTENT_ELEMENT,
XML_ROLE_CONTENT_ELEMENT_REP,
XML_ROLE_CONTENT_ELEMENT_OPT,
XML_ROLE_CONTENT_ELEMENT_PLUS,
XML_ROLE_PI,
XML_ROLE_COMMENT,
#ifdef XML_DTD
XML_ROLE_TEXT_DECL,
XML_ROLE_IGNORE_SECT,
XML_ROLE_INNER_PARAM_ENTITY_REF,
#endif /* XML_DTD */
XML_ROLE_PARAM_ENTITY_REF
};
typedef struct prolog_state {
int (PTRCALL *handler) (struct prolog_state *state,
int tok,
const char *ptr,
const char *end,
const ENCODING *enc);
unsigned level;
int role_none;
#ifdef XML_DTD
unsigned includeLevel;
int documentEntity;
int inEntityValue;
#endif /* XML_DTD */
} PROLOG_STATE;
void XmlPrologStateInit(PROLOG_STATE *);
#ifdef XML_DTD
void XmlPrologStateInitExternalEntity(PROLOG_STATE *);
#endif /* XML_DTD */
#define XmlTokenRole(state, tok, ptr, end, enc) \
(((state)->handler)(state, tok, ptr, end, enc))
#ifdef __cplusplus
}
#endif
#endif /* not XmlRole_INCLUDED */
@@ -0,0 +1,117 @@
/*
HTTP utility functions
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_UTILS_H
#define NE_UTILS_H
#include <sys/types.h>
#include <stdarg.h>
#include <stdio.h>
#include "ne_defs.h"
#ifdef NEON_TRIO
/* no HAVE_TRIO_H check so this works from outside neon build tree. */
#include <trio.h>
#endif
BEGIN_NEON_DECLS
/* Returns a human-readable version string like:
* "neon 0.2.0: Library build, OpenSSL support"
*/
const char *ne_version_string(void);
/* Returns non-zero if library version is not of major version
* 'major', or if minor version is not greater than or equal to
* 'minor'. For neon versions with major == 0, all minor versions are
* presumed to be incompatible. */
int ne_version_match(int major, int minor);
#define NE_FEATURE_SSL (1) /* SSL/TLS support */
#define NE_FEATURE_ZLIB (2) /* zlib compression in compress interface */
#define NE_FEATURE_IPV6 (3) /* IPv6 is supported in resolver */
#define NE_FEATURE_LFS (4) /* large file support */
#define NE_FEATURE_SOCKS (5) /* SOCKSv5 support */
/* Returns non-zero if neon has support for given feature code
* NE_FEATURE_*. */
int ne_has_support(int feature);
/* CONSIDER: mutt has a nicer way of way of doing debugging output... maybe
* switch to like that. */
#ifndef NE_DEBUGGING
#define NE_DEBUG if (0) ne_debug
#else /* DEBUGGING */
#define NE_DEBUG ne_debug
#endif /* DEBUGGING */
#define NE_DBG_SOCKET (1<<0)
#define NE_DBG_HTTP (1<<1)
#define NE_DBG_XML (1<<2)
#define NE_DBG_HTTPAUTH (1<<3)
#define NE_DBG_HTTPPLAIN (1<<4)
#define NE_DBG_LOCKS (1<<5)
#define NE_DBG_XMLPARSE (1<<6)
#define NE_DBG_HTTPBODY (1<<7)
#define NE_DBG_SSL (1<<8)
#define NE_DBG_FLUSH (1<<30)
/* Send debugging output to 'stream', for all of the given debug
* channels. To disable debugging, pass 'stream' as NULL and 'mask'
* as 0. */
void ne_debug_init(FILE *stream, int mask);
/* The current debug mask and stream set by the last call to
* ne_debug_init. */
extern int ne_debug_mask;
extern FILE *ne_debug_stream;
/* Produce debug output if any of channels 'ch' is enabled for
* debugging. */
void ne_debug(int ch, const char *, ...) ne_attribute((format(printf, 2, 3)));
/* Storing an HTTP status result */
typedef struct {
int major_version;
int minor_version;
int code; /* Status-Code value */
int klass; /* Class of Status-Code (1-5) */
char *reason_phrase;
} ne_status;
/* NB: couldn't use 'class' in ne_status because it would clash with
* the C++ reserved word. */
/* Parser for strings which follow the Status-Line grammar from
* RFC2616. s->reason_phrase is malloc-allocated if non-NULL, and
* must be free'd by the caller.
* Returns:
* 0 on success, *s will be filled in.
* -1 on parse error.
*/
int ne_parse_statusline(const char *status_line, ne_status *s);
END_NEON_DECLS
#endif /* NE_UTILS_H */
@@ -0,0 +1,400 @@
/*
* $Id: cast-128.c,v 1.1 2007/07/19 06:11:48 pizon Exp $
*
* CAST-128 in C
* Written by Steve Reid <sreid@sea-to-sky.net>
* 100% Public Domain - no warranty
* Released 1997.10.11
*/
/* Adapted to the pike cryptographic toolkit by Niels Möller */
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: cast-128.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "cast-128.h"
#define _mcrypt_set_key cast_128_LTX__mcrypt_set_key
#define _mcrypt_encrypt cast_128_LTX__mcrypt_encrypt
#define _mcrypt_decrypt cast_128_LTX__mcrypt_decrypt
#define _mcrypt_get_size cast_128_LTX__mcrypt_get_size
#define _mcrypt_get_block_size cast_128_LTX__mcrypt_get_block_size
#define _is_block_algorithm cast_128_LTX__is_block_algorithm
#define _mcrypt_get_key_size cast_128_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes cast_128_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name cast_128_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test cast_128_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version cast_128_LTX__mcrypt_algorithm_version
#define u8 byte
#define u32 word32
#include "cast-128_sboxes.h"
/* Macros to access 8-bit bytes out of a 32-bit word */
#define U8a(x) ( (u8) (x>>24) )
#define U8b(x) ( (u8) ((x>>16)&255) )
#define U8c(x) ( (u8) ((x>>8)&255) )
#define U8d(x) ( (u8) ((x)&255) )
/* Circular left shift */
#define ROL(x, n) ( ((x)<<(n)) | ((x)>>(32-(n))) )
/* CAST-128 uses three different round functions */
#define F1(l, r, i) \
t = ROL(key->xkey[i] + r, key->xkey[i+16]); \
l ^= ((cast_sbox1[U8a(t)] ^ cast_sbox2[U8b(t)]) \
- cast_sbox3[U8c(t)]) + cast_sbox4[U8d(t)];
#define F2(l, r, i) \
t = ROL(key->xkey[i] ^ r, key->xkey[i+16]); \
l ^= ((cast_sbox1[U8a(t)] - cast_sbox2[U8b(t)]) \
+ cast_sbox3[U8c(t)]) ^ cast_sbox4[U8d(t)];
#define F3(l, r, i) \
t = ROL(key->xkey[i] - r, key->xkey[i+16]); \
l ^= ((cast_sbox1[U8a(t)] + cast_sbox2[U8b(t)]) \
^ cast_sbox3[U8c(t)]) - cast_sbox4[U8d(t)];
/***** Encryption Function *****/
WIN32DLL_DEFINE void _mcrypt_encrypt(CAST_KEY * key, u8 * block)
{
u32 t, l, r;
/* Get inblock into l,r */
l = ((u32) block[0] << 24) | ((u32) block[1] << 16)
| ((u32) block[2] << 8) | (u32) block[3];
r = ((u32) block[4] << 24) | ((u32) block[5] << 16)
| ((u32) block[6] << 8) | (u32) block[7];
/* Do the work */
F1(l, r, 0);
F2(r, l, 1);
F3(l, r, 2);
F1(r, l, 3);
F2(l, r, 4);
F3(r, l, 5);
F1(l, r, 6);
F2(r, l, 7);
F3(l, r, 8);
F1(r, l, 9);
F2(l, r, 10);
F3(r, l, 11);
/* Only do full 16 rounds if key length > 80 bits */
if (key->rounds > 12) {
F1(l, r, 12);
F2(r, l, 13);
F3(l, r, 14);
F1(r, l, 15);
}
/* Put l,r into outblock */
block[0] = U8a(r);
block[1] = U8b(r);
block[2] = U8c(r);
block[3] = U8d(r);
block[4] = U8a(l);
block[5] = U8b(l);
block[6] = U8c(l);
block[7] = U8d(l);
/* Wipe clean */
t = l = r = 0;
}
/***** Decryption Function *****/
WIN32DLL_DEFINE void _mcrypt_decrypt(CAST_KEY * key, u8 * block)
{
u32 t, l, r;
/* Get inblock into l,r */
r = ((u32) block[0] << 24) | ((u32) block[1] << 16)
| ((u32) block[2] << 8) | (u32) block[3];
l = ((u32) block[4] << 24) | ((u32) block[5] << 16)
| ((u32) block[6] << 8) | (u32) block[7];
/* Do the work */
/* Only do full 16 rounds if key length > 80 bits */
if (key->rounds > 12) {
F1(r, l, 15);
F3(l, r, 14);
F2(r, l, 13);
F1(l, r, 12);
}
F3(r, l, 11);
F2(l, r, 10);
F1(r, l, 9);
F3(l, r, 8);
F2(r, l, 7);
F1(l, r, 6);
F3(r, l, 5);
F2(l, r, 4);
F1(r, l, 3);
F3(l, r, 2);
F2(r, l, 1);
F1(l, r, 0);
/* Put l,r into outblock */
block[0] = U8a(l);
block[1] = U8b(l);
block[2] = U8c(l);
block[3] = U8d(l);
block[4] = U8a(r);
block[5] = U8b(r);
block[6] = U8c(r);
block[7] = U8d(r);
/* Wipe clean */
t = l = r = 0;
}
/***** Key Schedual *****/
WIN32DLL_DEFINE
int _mcrypt_set_key(CAST_KEY * key, u8 * rawkey, unsigned keybytes)
{
u32 t[4], z[4], x[4];
unsigned i;
/* Set number of rounds to 12 or 16, depending on key length */
key->rounds = (keybytes <= CAST_SMALL_KEY)
? CAST_SMALL_ROUNDS : CAST_FULL_ROUNDS;
/* Copy key to workspace x */
for (i = 0; i < 4; i++) {
x[i] = 0;
if ((i * 4 + 0) < keybytes)
x[i] = (u32) rawkey[i * 4 + 0] << 24;
if ((i * 4 + 1) < keybytes)
x[i] |= (u32) rawkey[i * 4 + 1] << 16;
if ((i * 4 + 2) < keybytes)
x[i] |= (u32) rawkey[i * 4 + 2] << 8;
if ((i * 4 + 3) < keybytes)
x[i] |= (u32) rawkey[i * 4 + 3];
}
/* Generate 32 subkeys, four at a time */
for (i = 0; i < 32; i += 4) {
switch (i & 4) {
case 0:
t[0] = z[0] = x[0] ^ cast_sbox5[U8b(x[3])]
^ cast_sbox6[U8d(x[3])] ^ cast_sbox7[U8a(x[3])]
^ cast_sbox8[U8c(x[3])] ^
cast_sbox7[U8a(x[2])];
t[1] = z[1] = x[2] ^ cast_sbox5[U8a(z[0])]
^ cast_sbox6[U8c(z[0])] ^ cast_sbox7[U8b(z[0])]
^ cast_sbox8[U8d(z[0])] ^
cast_sbox8[U8c(x[2])];
t[2] = z[2] = x[3] ^ cast_sbox5[U8d(z[1])]
^ cast_sbox6[U8c(z[1])] ^ cast_sbox7[U8b(z[1])]
^ cast_sbox8[U8a(z[1])] ^
cast_sbox5[U8b(x[2])];
t[3] = z[3] =
x[1] ^ cast_sbox5[U8c(z[2])] ^
cast_sbox6[U8b(z[2])] ^ cast_sbox7[U8d(z[2])]
^ cast_sbox8[U8a(z[2])] ^
cast_sbox6[U8d(x[2])];
break;
case 4:
t[0] = x[0] = z[2] ^ cast_sbox5[U8b(z[1])]
^ cast_sbox6[U8d(z[1])] ^ cast_sbox7[U8a(z[1])]
^ cast_sbox8[U8c(z[1])] ^
cast_sbox7[U8a(z[0])];
t[1] = x[1] = z[0] ^ cast_sbox5[U8a(x[0])]
^ cast_sbox6[U8c(x[0])] ^ cast_sbox7[U8b(x[0])]
^ cast_sbox8[U8d(x[0])] ^
cast_sbox8[U8c(z[0])];
t[2] = x[2] = z[1] ^ cast_sbox5[U8d(x[1])]
^ cast_sbox6[U8c(x[1])] ^ cast_sbox7[U8b(x[1])]
^ cast_sbox8[U8a(x[1])] ^
cast_sbox5[U8b(z[0])];
t[3] = x[3] = z[3] ^ cast_sbox5[U8c(x[2])]
^ cast_sbox6[U8b(x[2])] ^ cast_sbox7[U8d(x[2])]
^ cast_sbox8[U8a(x[2])] ^
cast_sbox6[U8d(z[0])];
break;
}
switch (i & 12) {
case 0:
case 12:
key->xkey[i + 0] =
cast_sbox5[U8a(t[2])] ^ cast_sbox6[U8b(t[2])]
^ cast_sbox7[U8d(t[1])] ^
cast_sbox8[U8c(t[1])];
key->xkey[i + 1] =
cast_sbox5[U8c(t[2])] ^ cast_sbox6[U8d(t[2])]
^ cast_sbox7[U8b(t[1])] ^
cast_sbox8[U8a(t[1])];
key->xkey[i + 2] =
cast_sbox5[U8a(t[3])] ^ cast_sbox6[U8b(t[3])]
^ cast_sbox7[U8d(t[0])] ^
cast_sbox8[U8c(t[0])];
key->xkey[i + 3] =
cast_sbox5[U8c(t[3])] ^ cast_sbox6[U8d(t[3])]
^ cast_sbox7[U8b(t[0])] ^
cast_sbox8[U8a(t[0])];
break;
case 4:
case 8:
key->xkey[i + 0] =
cast_sbox5[U8d(t[0])] ^ cast_sbox6[U8c(t[0])]
^ cast_sbox7[U8a(t[3])] ^
cast_sbox8[U8b(t[3])];
key->xkey[i + 1] =
cast_sbox5[U8b(t[0])] ^ cast_sbox6[U8a(t[0])]
^ cast_sbox7[U8c(t[3])] ^
cast_sbox8[U8d(t[3])];
key->xkey[i + 2] =
cast_sbox5[U8d(t[1])] ^ cast_sbox6[U8c(t[1])]
^ cast_sbox7[U8a(t[2])] ^
cast_sbox8[U8b(t[2])];
key->xkey[i + 3] =
cast_sbox5[U8b(t[1])] ^ cast_sbox6[U8a(t[1])]
^ cast_sbox7[U8c(t[2])] ^
cast_sbox8[U8d(t[2])];
break;
}
switch (i & 12) {
case 0:
key->xkey[i + 0] ^= cast_sbox5[U8c(z[0])];
key->xkey[i + 1] ^= cast_sbox6[U8c(z[1])];
key->xkey[i + 2] ^= cast_sbox7[U8b(z[2])];
key->xkey[i + 3] ^= cast_sbox8[U8a(z[3])];
break;
case 4:
key->xkey[i + 0] ^= cast_sbox5[U8a(x[2])];
key->xkey[i + 1] ^= cast_sbox6[U8b(x[3])];
key->xkey[i + 2] ^= cast_sbox7[U8d(x[0])];
key->xkey[i + 3] ^= cast_sbox8[U8d(x[1])];
break;
case 8:
key->xkey[i + 0] ^= cast_sbox5[U8b(z[2])];
key->xkey[i + 1] ^= cast_sbox6[U8a(z[3])];
key->xkey[i + 2] ^= cast_sbox7[U8c(z[0])];
key->xkey[i + 3] ^= cast_sbox8[U8c(z[1])];
break;
case 12:
key->xkey[i + 0] ^= cast_sbox5[U8d(x[0])];
key->xkey[i + 1] ^= cast_sbox6[U8d(x[1])];
key->xkey[i + 2] ^= cast_sbox7[U8a(x[2])];
key->xkey[i + 3] ^= cast_sbox8[U8b(x[3])];
break;
}
if (i >= 16) {
key->xkey[i + 0] &= 31;
key->xkey[i + 1] &= 31;
key->xkey[i + 2] &= 31;
key->xkey[i + 3] &= 31;
}
}
/* Wipe clean */
for (i = 0; i < 4; i++) {
t[i] = x[i] = z[i] = 0;
}
return 0;
}
/* Made in Canada */
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return sizeof(CAST_KEY);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 8;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 16;
}
static const int key_sizes[] = { 16 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE const char *_mcrypt_get_algorithms_name()
{
return "CAST-128";
}
#define CIPHER "434e25460c8c9525"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL)
return -1;
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,108 @@
#ifndef ILIBDEFS_H
# define ILIBDEFS_H
/* MAX_THREADS removed by Steve Underwood 1999/12/10 */
#ifdef HAVE_CONFIG_H
# include <config.h>
#endif
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#include "win32_comp.h"
#ifdef USE_LTDL
# include <ltdl.h>
#else
# define lt_dlexit() 0
# define lt_dlinit() 0
# define lt_dlclose(x) 0
# define lt_dlsym(x,y) 0
# define lt_dlhandle void*
# define lt_ptr_t void*
# define lt_dlerror() 0
# define lt_dlopenext(x) 0
# define lt_dlsetsearchpath(x) 0
#endif
#ifdef STDC_HEADERS
# include <stdlib.h>
# include <stdio.h>
# include <ctype.h>
# include <string.h>
#endif
#ifdef HAVE_STRINGS_H
# include <strings.h>
#endif
#ifdef HAVE_UNISTD_H
# include <unistd.h>
#endif
#ifdef HAVE_SYS_ENDIAN_H
# include <sys/endian.h>
#endif
#ifdef HAVE_MACHINE_ENDIAN_H
# include <machine/endian.h>
#endif
#ifdef HAVE_ENDIAN_H
# include <endian.h>
#endif
#ifdef HAVE_BYTESWAP_H
# include <byteswap.h>
#endif
#ifdef HAVE_READDIR_R
# define _POSIX_C_SOURCE 199506L
#endif
#ifdef HAVE_DIRENT_H
# include <dirent.h>
#endif
#if SIZEOF_UNSIGNED_LONG_INT == 4
typedef unsigned long word32;
typedef signed long sword32;
#elif SIZEOF_UNSIGNED_INT == 4
typedef unsigned int word32;
typedef signed int sword32;
#else
# error "Cannot find a 32 bit integer in your system, sorry."
#endif
#if SIZEOF_UNSIGNED_INT == 2
typedef unsigned int word16;
#elif SIZEOF_UNSIGNED_SHORT_INT == 2
typedef unsigned short word16;
#else
# error "Cannot find a 16 bit integer in your system, sorry."
#endif
#if SIZEOF_UNSIGNED_CHAR == 1
typedef unsigned char byte;
#else
# error "Cannot find an 8 bit char in your system, sorry."
#endif
#ifndef HAVE_MEMMOVE
# ifdef HAVE_BCOPY
# define memmove(d, s, n) bcopy ((s), (d), (n))
# else
# error "Neither memmove nor bcopy exists on your system."
# endif
#endif
#ifdef USE_DMALLOC
# include <dmalloc.h>
#endif
#endif /* LIBDEFS_H */
@@ -0,0 +1,12 @@
#ifndef USE_MODULES
int _ecb_init_mcrypt( int td, void* buf, void *key, int lenofkey, void *IV);
int _mcrypt_ecb(int td, void* buf,void *plaintext, int len);
int _mdecrypt_ecb(int td, void* buf, void *plaintext, int len);
int _ecb_is_block_mode();
int _ecb_has_iv();
int _ecb_is_block_algorithm_mode();
char *_mcrypt_ecb_get_modes_name();
int _mcrypt_ecb_mode_get_size ();
int _mcrypt_ecb_get_iv_size(int td);
word32 _mcrypt_ecb_mode_version();
#endif
@@ -0,0 +1,174 @@
/*
* Copyright (C) 1998,1999,2000,2001,2002 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Library General Public License as published
* by the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _init_mcrypt ofb_LTX__init_mcrypt
#define _mcrypt_set_state ofb_LTX__mcrypt_set_state
#define _mcrypt_get_state ofb_LTX__mcrypt_get_state
#define _end_mcrypt ofb_LTX__end_mcrypt
#define _mcrypt ofb_LTX__mcrypt
#define _mdecrypt ofb_LTX__mdecrypt
#define _has_iv ofb_LTX__has_iv
#define _is_block_mode ofb_LTX__is_block_mode
#define _is_block_algorithm_mode ofb_LTX__is_block_algorithm_mode
#define _mcrypt_get_modes_name ofb_LTX__mcrypt_get_modes_name
#define _mcrypt_mode_get_size ofb_LTX__mcrypt_mode_get_size
#define _mcrypt_mode_version ofb_LTX__mcrypt_mode_version
typedef struct ofb_buf {
byte* s_register;
byte* enc_s_register;
int blocksize;
} OFB_BUFFER;
/* OFB MODE */
int _init_mcrypt( OFB_BUFFER* buf, void *key, int lenofkey, void *IV, int size)
{
buf->s_register = buf->enc_s_register = NULL;
buf->blocksize = size;
/* For ofb */
buf->s_register=malloc( size);
if (buf->s_register==NULL) goto freeall;
buf->enc_s_register=malloc( size);
if (buf->enc_s_register==NULL) goto freeall;
if (IV!=NULL) {
memcpy(buf->s_register, IV, size);
} else {
memset(buf->s_register, 0, size);
}
/* End ofb */
return 0;
freeall:
free(buf->s_register);
free(buf->enc_s_register);
return -1;
}
int _mcrypt_get_state( OFB_BUFFER* buf, byte *IV, int *size)
{
if (*size < buf->blocksize) {
*size = buf->blocksize;
return -1;
}
*size = buf->blocksize;
memcpy( IV, buf->s_register, buf->blocksize);
return 0;
}
int _mcrypt_set_state( OFB_BUFFER* buf, void *IV, int size)
{
memcpy(buf->enc_s_register, IV, size);
memcpy(buf->s_register, IV, size);
return 0;
}
void _end_mcrypt( OFB_BUFFER* buf) {
free(buf->s_register);
free(buf->enc_s_register);
}
int _mcrypt( OFB_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*) )
{ /* plaintext is 1 byte (8bit ofb) */
char *plain = plaintext;
int i, j;
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
for (j = 0; j < len; j++) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
plain[j] ^= buf->enc_s_register[0];
/* Shift the register */
for (i = 0; i < (blocksize - 1); i++)
buf->s_register[i] = buf->s_register[i + 1];
buf->s_register[blocksize - 1] = buf->enc_s_register[0];
}
return 0;
}
int _mdecrypt( OFB_BUFFER* buf, void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext is 1 byte (8bit ofb) */
char *plain = plaintext;
int i, j;
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
for (j = 0; j < len; j++) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
/* Shift the register */
for (i = 0; i < (blocksize - 1); i++)
buf->s_register[i] = buf->s_register[i + 1];
buf->s_register[blocksize - 1] = buf->enc_s_register[0];
plain[j] ^= buf->enc_s_register[0];
}
return 0;
}
int _is_block_mode() { return 0; }
int _has_iv() { return 1; }
int _is_block_algorithm_mode() { return 1; }
char *_mcrypt_get_modes_name() { return "OFB"; }
int _mcrypt_mode_get_size () {return sizeof(OFB_BUFFER);}
word32 _mcrypt_mode_version() {
return 20010310;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,53 @@
/*
Standard definitions for neon headers
Copyright (C) 2003-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#undef BEGIN_NEON_DECLS
#undef END_NEON_DECLS
#ifdef __cplusplus
# define BEGIN_NEON_DECLS extern "C" {
# define END_NEON_DECLS }
#else
# define BEGIN_NEON_DECLS /* empty */
# define END_NEON_DECLS /* empty */
#endif
/* define ssize_t for Win32 */
#if defined(WIN32) && !defined(ssize_t)
#define ssize_t int
#endif
#ifdef __GNUC__
#if __GNUC__ >= 3
#define ne_attribute_malloc __attribute__((malloc))
#else
#define ne_attribute_malloc
#endif
#define ne_attribute(x) __attribute__(x)
#else
#define ne_attribute(x)
#define ne_attribute_malloc
#endif
#ifndef NE_BUFSIZ
//#define NE_BUFSIZ 8192*2*2
#define NE_BUFSIZ 65536
//#define NE_BUFSIZ 8192*10
#endif
@@ -0,0 +1,106 @@
const ENCODING *
NS(XmlGetUtf8InternalEncoding)(void)
{
return &ns(internal_utf8_encoding).enc;
}
const ENCODING *
NS(XmlGetUtf16InternalEncoding)(void)
{
#if BYTEORDER == 1234
return &ns(internal_little2_encoding).enc;
#elif BYTEORDER == 4321
return &ns(internal_big2_encoding).enc;
#else
const short n = 1;
return (*(const char *)&n
? &ns(internal_little2_encoding).enc
: &ns(internal_big2_encoding).enc);
#endif
}
static const ENCODING *NS(encodings)[] = {
&ns(latin1_encoding).enc,
&ns(ascii_encoding).enc,
&ns(utf8_encoding).enc,
&ns(big2_encoding).enc,
&ns(big2_encoding).enc,
&ns(little2_encoding).enc,
&ns(utf8_encoding).enc /* NO_ENC */
};
static int PTRCALL
NS(initScanProlog)(const ENCODING *enc, const char *ptr, const char *end,
const char **nextTokPtr)
{
return initScan(NS(encodings), (const INIT_ENCODING *)enc,
XML_PROLOG_STATE, ptr, end, nextTokPtr);
}
static int PTRCALL
NS(initScanContent)(const ENCODING *enc, const char *ptr, const char *end,
const char **nextTokPtr)
{
return initScan(NS(encodings), (const INIT_ENCODING *)enc,
XML_CONTENT_STATE, ptr, end, nextTokPtr);
}
int
NS(XmlInitEncoding)(INIT_ENCODING *p, const ENCODING **encPtr,
const char *name)
{
int i = getEncodingIndex(name);
if (i == UNKNOWN_ENC)
return 0;
SET_INIT_ENC_INDEX(p, i);
p->initEnc.scanners[XML_PROLOG_STATE] = NS(initScanProlog);
p->initEnc.scanners[XML_CONTENT_STATE] = NS(initScanContent);
p->initEnc.updatePosition = initUpdatePosition;
p->encPtr = encPtr;
*encPtr = &(p->initEnc);
return 1;
}
static const ENCODING *
NS(findEncoding)(const ENCODING *enc, const char *ptr, const char *end)
{
#define ENCODING_MAX 128
char buf[ENCODING_MAX];
char *p = buf;
int i;
XmlUtf8Convert(enc, &ptr, end, &p, p + ENCODING_MAX - 1);
if (ptr != end)
return 0;
*p = 0;
if (streqci(buf, KW_UTF_16) && enc->minBytesPerChar == 2)
return enc;
i = getEncodingIndex(buf);
if (i == UNKNOWN_ENC)
return 0;
return NS(encodings)[i];
}
int
NS(XmlParseXmlDecl)(int isGeneralTextEntity,
const ENCODING *enc,
const char *ptr,
const char *end,
const char **badPtr,
const char **versionPtr,
const char **versionEndPtr,
const char **encodingName,
const ENCODING **encoding,
int *standalone)
{
return doParseXmlDecl(NS(findEncoding),
isGeneralTextEntity,
enc,
ptr,
end,
badPtr,
versionPtr,
versionEndPtr,
encodingName,
encoding,
standalone);
}
@@ -0,0 +1,270 @@
/*
HTTP session handling
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
Portions are:
Copyright (C) 1999-2000 Tommi Komulainen <Tommi.Komulainen@iki.fi>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_ERRNO_H
#include <errno.h>
#endif
#include "ne_session.h"
#include "ne_alloc.h"
#include "ne_utils.h"
#include "ne_i18n.h"
#include "ne_string.h"
#include "ne_private.h"
/* Destroy a a list of hooks. */
static void destroy_hooks(struct hook *hooks)
{
struct hook *nexthk;
while (hooks) {
nexthk = hooks->next;
ne_free(hooks);
hooks = nexthk;
}
}
void ne_session_destroy(ne_session *sess)
{
struct hook *hk;
NE_DEBUG(NE_DBG_HTTP, "ne_session_destroy called.\n");
/* Run the destroy hooks. */
for (hk = sess->destroy_sess_hooks; hk != NULL; hk = hk->next) {
ne_destroy_sess_fn fn = (ne_destroy_sess_fn)hk->fn;
fn(hk->userdata);
}
destroy_hooks(sess->create_req_hooks);
destroy_hooks(sess->pre_send_hooks);
destroy_hooks(sess->post_send_hooks);
destroy_hooks(sess->destroy_req_hooks);
destroy_hooks(sess->destroy_sess_hooks);
destroy_hooks(sess->private);
ne_free(sess->scheme);
ne_free(sess->server.hostname);
ne_free(sess->server.hostport);
if (sess->server.address) ne_addr_destroy(sess->server.address);
if (sess->proxy.address) ne_addr_destroy(sess->proxy.address);
if (sess->proxy.hostname) ne_free(sess->proxy.hostname);
if (sess->user_agent) ne_free(sess->user_agent);
if (sess->connected) {
ne_close_connection(sess);
}
#ifdef NE_HAVE_SSL
if (sess->ssl_context)
ne_ssl_context_destroy(sess->ssl_context);
if (sess->server_cert)
ne_ssl_cert_free(sess->server_cert);
if (sess->client_cert)
ne_ssl_clicert_free(sess->client_cert);
#endif
ne_free(sess);
}
int ne_version_pre_http11(ne_session *s)
{
return !s->is_http11;
}
/* Stores the "hostname[:port]" segment */
static void set_hostport(struct host_info *host, unsigned int defaultport)
{
size_t len = strlen(host->hostname);
host->hostport = ne_malloc(len + 10);
strcpy(host->hostport, host->hostname);
if (host->port != defaultport)
ne_snprintf(host->hostport + len, 9, ":%u", host->port);
}
/* Stores the hostname/port in *info, setting up the "hostport"
* segment correctly. */
static void
set_hostinfo(struct host_info *info, const char *hostname, unsigned int port)
{
info->hostname = ne_strdup(hostname);
info->port = port;
}
ne_session *ne_session_create(const char *scheme,
const char *hostname, unsigned int port)
{
ne_session *sess = ne_calloc(sizeof *sess);
NE_DEBUG(NE_DBG_HTTP, "HTTP session to %s://%s:%d begins.\n",
scheme, hostname, port);
strcpy(sess->error, "Unknown error.");
/* use SSL if scheme is https */
sess->use_ssl = !strcmp(scheme, "https");
/* set the hostname/port */
set_hostinfo(&sess->server, hostname, port);
set_hostport(&sess->server, sess->use_ssl?443:80);
#ifdef NE_HAVE_SSL
if (sess->use_ssl) {
sess->ssl_context = ne_ssl_context_create(0);
}
#endif
sess->scheme = ne_strdup(scheme);
return sess;
}
void ne_session_proxy(ne_session *sess, const char *hostname,
unsigned int port)
{
sess->use_proxy = 1;
if (sess->proxy.hostname) ne_free(sess->proxy.hostname);
set_hostinfo(&sess->proxy, hostname, port);
}
void ne_set_addrlist(ne_session *sess, const ne_inet_addr **addrs, size_t n)
{
sess->addrlist = addrs;
sess->numaddrs = n;
}
void ne_set_error(ne_session *sess, const char *format, ...)
{
va_list params;
va_start(params, format);
ne_vsnprintf(sess->error, sizeof sess->error, format, params);
va_end(params);
}
void ne_set_progress(ne_session *sess,
ne_progress progress, void *userdata)
{
sess->progress_cb = progress;
sess->progress_ud = userdata;
}
void ne_set_status(ne_session *sess,
ne_notify_status status, void *userdata)
{
sess->notify_cb = status;
sess->notify_ud = userdata;
}
void ne_set_persist(ne_session *sess, int persist)
{
sess->no_persist = !persist;
}
void ne_set_read_timeout(ne_session *sess, int timeout)
{
sess->rdtimeout = timeout;
}
#define UAHDR "User-Agent: "
#define AGENT " neon/" NEON_VERSION "\r\n"
void ne_set_useragent(ne_session *sess, const char *token)
{
if (sess->user_agent) ne_free(sess->user_agent);
sess->user_agent = ne_malloc(strlen(UAHDR) + strlen(AGENT) +
strlen(token) + 1);
#ifdef HAVE_STPCPY
strcpy(stpcpy(stpcpy(sess->user_agent, UAHDR), token), AGENT);
#else
strcat(strcat(strcpy(sess->user_agent, UAHDR), token), AGENT);
#endif
}
const char *ne_get_server_hostport(ne_session *sess)
{
return sess->server.hostport;
}
const char *ne_get_scheme(ne_session *sess)
{
return sess->scheme;
}
void ne_fill_server_uri(ne_session *sess, ne_uri *uri)
{
uri->host = ne_strdup(sess->server.hostname);
uri->port = sess->server.port;
uri->scheme = ne_strdup(sess->scheme);
}
const char *ne_get_error(ne_session *sess)
{
return sess->error;
}
void ne_close_connection(ne_session *sess)
{
if (sess->connected) {
NE_DEBUG(NE_DBG_SOCKET, "Closing connection.\n");
ne_sock_close(sess->socket);
sess->socket = NULL;
NE_DEBUG(NE_DBG_SOCKET, "Connection closed.\n");
} else {
NE_DEBUG(NE_DBG_SOCKET, "(Not closing closed connection!).\n");
}
sess->connected = 0;
}
void ne_ssl_set_verify(ne_session *sess, ne_ssl_verify_fn fn, void *userdata)
{
sess->ssl_verify_fn = fn;
sess->ssl_verify_ud = userdata;
}
void ne_ssl_provide_clicert(ne_session *sess,
ne_ssl_provide_fn fn, void *userdata)
{
sess->ssl_provide_fn = fn;
sess->ssl_provide_ud = userdata;
}
void ne_ssl_trust_cert(ne_session *sess, const ne_ssl_certificate *cert)
{
#ifdef NE_HAVE_SSL
ne_ssl_context_trustcert(sess->ssl_context, cert);
#endif
}
@@ -0,0 +1,10 @@
typedef struct wake_key {
word32 t[257];
word32 r[4];
int counter;
word32 tmp; /* used as r1 or r2 */
int started;
word32 iv[8];
int ivsize;
} WAKE_KEY;
@@ -0,0 +1,5 @@
/* for blowfish */
typedef struct {
word32 S[4][256],P[18];
} blf_ctx;
@@ -0,0 +1,673 @@
/* Sofware DES functions
* written 12 Dec 1986 by Phil Karn, KA9Q; large sections adapted from
* the 1977 public-domain program by Jim Gillogly
* Modified for additional speed - 6 December 1988 Phil Karn
* Modified for parameterized key schedules - Jan 1991 Phil Karn
* Callers now allocate a key schedule as follows:
* kn = (char (*)[8])malloc(sizeof(char) * 8 * 16);
* or
* char kn[16][8];
*/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: des.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "des.h"
#define _mcrypt_set_key des_LTX__mcrypt_set_key
#define _mcrypt_encrypt des_LTX__mcrypt_encrypt
#define _mcrypt_decrypt des_LTX__mcrypt_decrypt
#define _mcrypt_get_size des_LTX__mcrypt_get_size
#define _mcrypt_get_block_size des_LTX__mcrypt_get_block_size
#define _is_block_algorithm des_LTX__is_block_algorithm
#define _mcrypt_get_key_size des_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes des_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name des_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test des_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version des_LTX__mcrypt_algorithm_version
/* #define NULL 0 */
static void permute_ip(), permute_fp(), perminit_ip(), spinit(),
perminit_fp();
static word32 f();
/* Tables defined in the Data Encryption Standard documents */
/* initial permutation IP */
static char ip[] = {
58, 50, 42, 34, 26, 18, 10, 2,
60, 52, 44, 36, 28, 20, 12, 4,
62, 54, 46, 38, 30, 22, 14, 6,
64, 56, 48, 40, 32, 24, 16, 8,
57, 49, 41, 33, 25, 17, 9, 1,
59, 51, 43, 35, 27, 19, 11, 3,
61, 53, 45, 37, 29, 21, 13, 5,
63, 55, 47, 39, 31, 23, 15, 7
};
/* final permutation IP^-1 */
static char fp[] = {
40, 8, 48, 16, 56, 24, 64, 32,
39, 7, 47, 15, 55, 23, 63, 31,
38, 6, 46, 14, 54, 22, 62, 30,
37, 5, 45, 13, 53, 21, 61, 29,
36, 4, 44, 12, 52, 20, 60, 28,
35, 3, 43, 11, 51, 19, 59, 27,
34, 2, 42, 10, 50, 18, 58, 26,
33, 1, 41, 9, 49, 17, 57, 25
};
/* expansion operation matrix
* This is for reference only; it is unused in the code
* as the f() function performs it implicitly for speed
*/
#ifdef notdef
static char ei[] = {
32, 1, 2, 3, 4, 5,
4, 5, 6, 7, 8, 9,
8, 9, 10, 11, 12, 13,
12, 13, 14, 15, 16, 17,
16, 17, 18, 19, 20, 21,
20, 21, 22, 23, 24, 25,
24, 25, 26, 27, 28, 29,
28, 29, 30, 31, 32, 1
};
#endif
/* permuted choice table (key) */
static char pc1[] = {
57, 49, 41, 33, 25, 17, 9,
1, 58, 50, 42, 34, 26, 18,
10, 2, 59, 51, 43, 35, 27,
19, 11, 3, 60, 52, 44, 36,
63, 55, 47, 39, 31, 23, 15,
7, 62, 54, 46, 38, 30, 22,
14, 6, 61, 53, 45, 37, 29,
21, 13, 5, 28, 20, 12, 4
};
/* number left rotations of pc1 */
static char totrot[] = {
1, 2, 4, 6, 8, 10, 12, 14, 15, 17, 19, 21, 23, 25, 27, 28
};
/* permuted choice key (table) */
static char pc2[] = {
14, 17, 11, 24, 1, 5,
3, 28, 15, 6, 21, 10,
23, 19, 12, 4, 26, 8,
16, 7, 27, 20, 13, 2,
41, 52, 31, 37, 47, 55,
30, 40, 51, 45, 33, 48,
44, 49, 39, 56, 34, 53,
46, 42, 50, 36, 29, 32
};
/* The (in)famous S-boxes */
static char si[8][64] = {
/* S1 */
{14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7,
0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8,
4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0,
15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13},
/* S2 */
{15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10,
3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5,
0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15,
13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9},
/* S3 */
{10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8,
13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1,
13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7,
1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12},
/* S4 */
{7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15,
13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9,
10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4,
3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14},
/* S5 */
{2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9,
14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6,
4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14,
11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3},
/* S6 */
{12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11,
10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8,
9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6,
4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13},
/* S7 */
{4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1,
13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6,
1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2,
6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12},
/* S8 */
{13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7,
1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2,
7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8,
2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11},
};
/* 32-bit permutation function P used on the output of the S-boxes */
static char p32i[] = {
16, 7, 20, 21,
29, 12, 28, 17,
1, 15, 23, 26,
5, 18, 31, 10,
2, 8, 24, 14,
32, 27, 3, 9,
19, 13, 30, 6,
22, 11, 4, 25
};
/* End of DES-defined tables */
/* Lookup tables initialized once only at startup by desinit() */
/* bit 0 is left-most in byte */
static int bytebit[] = {
0200, 0100, 040, 020, 010, 04, 02, 01
};
static int nibblebit[] = {
010, 04, 02, 01
};
/* Allocate space and initialize DES lookup arrays
* mode == 0: standard Data Encryption Algorithm
*/
static int _mcrypt_desinit(DES_KEY * key)
{
spinit(key);
perminit_ip(key);
perminit_fp(key);
return 0;
}
/* Set key (initialize key schedule array) */
WIN32DLL_DEFINE
int _mcrypt_set_key(DES_KEY * dkey, char *user_key, int len)
{
char pc1m[56]; /* place to modify pc1 into */
char pcr[56]; /* place to rotate pc1 into */
register int i, j, l;
int m;
Bzero(dkey, sizeof(DES_KEY));
_mcrypt_desinit(dkey);
/* Clear key schedule */
for (j = 0; j < 56; j++) { /* convert pc1 to bits of key */
l = pc1[j] - 1; /* integer bit location */
m = l & 07; /* find bit */
pc1m[j] = (user_key[l >> 3] & /* find which key byte l is in */
bytebit[m]) /* and which bit of that byte */
? 1 : 0; /* and store 1-bit result */
}
for (i = 0; i < 16; i++) { /* key chunk for each iteration */
for (j = 0; j < 56; j++) /* rotate pc1 the right amount */
pcr[j] =
pc1m[(l = j + totrot[i]) <
(j < 28 ? 28 : 56) ? l : l - 28];
/* rotate left and right halves independently */
for (j = 0; j < 48; j++) { /* select bits individually */
/* check bit that goes to kn[j] */
if (pcr[pc2[j] - 1]) {
/* mask it in if it's there */
l = j % 6;
dkey->kn[i][j / 6] |= bytebit[l] >> 2;
}
}
}
return 0;
}
/* In-place encryption of 64-bit block */
WIN32DLL_DEFINE void _mcrypt_encrypt(DES_KEY * key, char *block)
{
register word32 left, right;
register char *knp;
word32 work[2]; /* Working data storage */
permute_ip(block, key, (char *) work); /* Initial Permutation */
#ifndef WORDS_BIGENDIAN
left = byteswap32(work[0]);
right = byteswap32(work[1]);
#else
left = work[0];
right = work[1];
#endif
/* Do the 16 rounds.
* The rounds are numbered from 0 to 15. On even rounds
* the right half is fed to f() and the result exclusive-ORs
* the left half; on odd rounds the reverse is done.
*/
knp = &key->kn[0][0];
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
knp += 8;
left ^= f(key, right, knp);
knp += 8;
right ^= f(key, left, knp);
/* Left/right half swap, plus byte swap if little-endian */
#ifndef WORDS_BIGENDIAN
work[1] = byteswap32(left);
work[0] = byteswap32(right);
#else
work[0] = right;
work[1] = left;
#endif
permute_fp((char *) work, key, block); /* Inverse initial permutation */
}
/* In-place decryption of 64-bit block. This function is the mirror
* image of encryption; exactly the same steps are taken, but in
* reverse order
*/
WIN32DLL_DEFINE void _mcrypt_decrypt(DES_KEY * key, char *block)
{
register word32 left, right;
register char *knp;
word32 work[2]; /* Working data storage */
permute_ip(block, key, (char *) work); /* Initial permutation */
/* Left/right half swap, plus byte swap if little-endian */
#ifndef WORDS_BIGENDIAN
right = byteswap32(work[0]);
left = byteswap32(work[1]);
#else
right = work[0];
left = work[1];
#endif
/* Do the 16 rounds in reverse order.
* The rounds are numbered from 15 to 0. On even rounds
* the right half is fed to f() and the result exclusive-ORs
* the left half; on odd rounds the reverse is done.
*/
knp = &key->kn[15][0];
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
knp -= 8;
right ^= f(key, left, knp);
knp -= 8;
left ^= f(key, right, knp);
#ifndef WORDS_BIGENDIAN
work[0] = byteswap32(left);
work[1] = byteswap32(right);
#else
work[0] = left;
work[1] = right;
#endif
permute_fp((char *) work, key, block); /* Inverse initial permutation */
}
/* Permute inblock with perm */
static void permute_ip(char *inblock, DES_KEY * key, char *outblock)
{
register char *ib, *ob; /* ptr to input or output block */
register char *p, *q;
register int j;
/* Clear output block */
Bzero(outblock, 8);
ib = inblock;
for (j = 0; j < 16; j += 2, ib++) { /* for each input nibble */
ob = outblock;
p = key->iperm[j][(*ib >> 4) & 0xf];
q = key->iperm[j + 1][*ib & 0xf];
/* and each output byte, OR the masks together */
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
}
}
/* Permute inblock with perm */
static void permute_fp(char *inblock, DES_KEY * key, char *outblock)
{
register char *ib, *ob; /* ptr to input or output block */
register char *p, *q;
register int j;
/* Clear output block */
Bzero(outblock, 8);
ib = inblock;
for (j = 0; j < 16; j += 2, ib++) { /* for each input nibble */
ob = outblock;
p = key->fperm[j][(*ib >> 4) & 0xf];
q = key->fperm[j + 1][*ib & 0xf];
/* and each output byte, OR the masks together */
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
*ob++ |= *p++ | *q++;
}
}
/* The nonlinear function f(r,k), the heart of DES */
static word32 f(DES_KEY * key, register word32 r, register char *subkey)
{
register word32 *spp;
register word32 rval, rt;
register int er;
#ifdef TRACE
printf("f(%08lx, %02x %02x %02x %02x %02x %02x %02x %02x) = ",
r,
subkey[0], subkey[1], subkey[2],
subkey[3], subkey[4], subkey[5], subkey[6], subkey[7]);
#endif
/* Run E(R) ^ K through the combined S & P boxes.
* This code takes advantage of a convenient regularity in
* E, namely that each group of 6 bits in E(R) feeding
* a single S-box is a contiguous segment of R.
*/
subkey += 7;
/* Compute E(R) for each block of 6 bits, and run thru boxes */
er = ((int) r << 1) | ((r & 0x80000000) ? 1 : 0);
spp = &key->sp[7][0];
rval = spp[(er ^ *subkey--) & 0x3f];
spp -= 64;
rt = (word32) r >> 3;
rval |= spp[((int) rt ^ *subkey--) & 0x3f];
spp -= 64;
rt >>= 4;
rval |= spp[((int) rt ^ *subkey--) & 0x3f];
spp -= 64;
rt >>= 4;
rval |= spp[((int) rt ^ *subkey--) & 0x3f];
spp -= 64;
rt >>= 4;
rval |= spp[((int) rt ^ *subkey--) & 0x3f];
spp -= 64;
rt >>= 4;
rval |= spp[((int) rt ^ *subkey--) & 0x3f];
spp -= 64;
rt >>= 4;
rval |= spp[((int) rt ^ *subkey--) & 0x3f];
spp -= 64;
rt >>= 4;
rt |= (r & 1) << 5;
rval |= spp[((int) rt ^ *subkey) & 0x3f];
#ifdef TRACE
printf(" %08lx\n", rval);
#endif
return rval;
}
/* initialize a perm array */
static void perminit_ip(DES_KEY * key)
{
register int l, j, k;
int i, m;
/* Clear the permutation array */
Bzero(key->iperm, 16 * 16 * 8);
for (i = 0; i < 16; i++) /* each input nibble position */
for (j = 0; j < 16; j++) /* each possible input nibble */
for (k = 0; k < 64; k++) { /* each output bit position */
l = ip[k] - 1; /* where does this bit come from */
if ((l >> 2) != i) /* does it come from input posn? */
continue; /* if not, bit k is 0 */
if (!(j & nibblebit[l & 3]))
continue; /* any such bit in input? */
m = k & 07; /* which bit is this in the byte */
key->iperm[i][j][k >> 3] |= bytebit[m];
}
}
static void perminit_fp(DES_KEY * key)
{
register int l, j, k;
int i, m;
/* Clear the permutation array */
Bzero(key->fperm, 16 * 16 * 8);
for (i = 0; i < 16; i++) /* each input nibble position */
for (j = 0; j < 16; j++) /* each possible input nibble */
for (k = 0; k < 64; k++) { /* each output bit position */
l = fp[k] - 1; /* where does this bit come from */
if ((l >> 2) != i) /* does it come from input posn? */
continue; /* if not, bit k is 0 */
if (!(j & nibblebit[l & 3]))
continue; /* any such bit in input? */
m = k & 07; /* which bit is this in the byte */
key->fperm[i][j][k >> 3] |= bytebit[m];
}
}
/* Initialize the lookup table for the combined S and P boxes */
static void spinit(DES_KEY * key)
{
char pbox[32];
int p, i, s, j, rowcol;
word32 val;
/* Compute pbox, the inverse of p32i.
* This is easier to work with
*/
for (p = 0; p < 32; p++) {
for (i = 0; i < 32; i++) {
if (p32i[i] - 1 == p) {
pbox[p] = i;
break;
}
}
}
for (s = 0; s < 8; s++) { /* For each S-box */
for (i = 0; i < 64; i++) { /* For each possible input */
val = 0;
/* The row number is formed from the first and last
* bits; the column number is from the middle 4
*/
rowcol =
(i & 32) | ((i & 1) ? 16 : 0) | ((i >> 1) &
0xf);
for (j = 0; j < 4; j++) { /* For each output bit */
if (si[s][rowcol] & (8 >> j)) {
val |=
1L << (31 - pbox[4 * s + j]);
}
}
key->sp[s][i] = val;
#ifdef DEBUG
printf("sp[%d][%2d] = %08lx\n", s, i,
key->sp[s][i]);
#endif
}
}
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return sizeof(DES_KEY);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 8;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 8;
}
static const int key_sizes[] = { 8 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE const char *_mcrypt_get_algorithms_name()
{
return "DES";
}
#define CIPHER "a1502d70ba1320c8"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,151 @@
/*
neon XML parser interface
Copyright (C) 1999-2004, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_XML_H
#define NE_XML_H
#include <sys/types.h> /* for size_t */
#include "ne_defs.h"
BEGIN_NEON_DECLS
/* The neon XML interface filters a streamed XML tree through a stack
* of SAX "handlers". A handler is made up of three callbacks
* (start-element, char-data, end-element). Each start-element event
* is passed to each handler in the stack in turn until one until one
* accepts the element. This handler then receives subsequent
* char-data and end-element events for the element.
*
* For each new start-element event, the search up the handler stack
* begins with the handler for the parent element (for the root
* element, at the base of the stack).
*
* For each accepted element, a "state" integer is stored, which is
* passed to the corresponding char-data and end-element callbacks for
* the element. This integer is also passed to the start-element
* callback of child elements so they can determine context.
*
* If no handler in the stack accepts a particular element, it (and
* its children, if any) is ignored. */
#define NE_XML_DECLINE (0)
#define NE_XML_ABORT (-1)
/* A start-element callback for element with given namespace/name.
* The callback may return:
* <0 => abort the parse (NE_XML_ABORT)
* 0 => decline this element (NE_XML_DECLINE)
* >0 => accept this element; value is state for this element.
*
* The 'parent' integer is the state returned by the handler of the
* parent element. The attributes array gives name/value pairs
* in atts[n] and atts[n+1] from n=0 up to atts[n]==NULL. */
typedef int ne_xml_startelm_cb(void *userdata, int parent,
const char *nspace, const char *name,
const char **atts);
/* state for the root element */
#define NE_XML_STATEROOT (0)
/* Character data callback; may return non-zero to abort the parse. */
typedef int ne_xml_cdata_cb(void *userdata, int state,
const char *cdata, size_t len);
/* End element callback; may return non-zero to abort the parse. */
typedef int ne_xml_endelm_cb(void *userdata, int state,
const char *nspace, const char *name);
typedef struct ne_xml_parser_s ne_xml_parser;
/* Create an XML parser. */
ne_xml_parser *ne_xml_create(void);
/* Push a new handler on the stack of parser 'p'. 'cdata' and/or
* 'endelm' may be NULL; startelm must be non-NULL. */
void ne_xml_push_handler(ne_xml_parser *p,
ne_xml_startelm_cb *startelm,
ne_xml_cdata_cb *cdata,
ne_xml_endelm_cb *endelm,
void *userdata);
/* ne_xml_failed returns non-zero if there was an error during
* parsing, or zero if the parse completed successfully. The return
* value is equal to that of the last ne_xml_parse call for this
* parser. */
int ne_xml_failed(ne_xml_parser *p);
/* Set error string for parser: the string may be truncated. */
void ne_xml_set_error(ne_xml_parser *p, const char *msg);
/* Return the error string (never NULL). After ne_xml_failed returns
* >0, this will describe the parse error. Otherwise it will be a
* default error string. */
const char *ne_xml_get_error(ne_xml_parser *p);
/* Destroy the parser object. */
void ne_xml_destroy(ne_xml_parser *p);
/* Parse the given block of input of length len. Parser must be
* called with len=0 to signify the end of the document (for that
* case, the block argument is ignored). Returns zero on success, or
* non-zero on error: for an XML syntax error, a positive number is
* returned; if parsing is aborted by a caller-supplied callback, that
* callback's return value is returned. */
int ne_xml_parse(ne_xml_parser *p, const char *block, size_t len);
/* As above, casting (ne_xml_parser *)userdata internally.
* (This function can be passed to ne_add_response_body_reader) */
int ne_xml_parse_v(void *userdata, const char *block, size_t len);
/* Return current parse line for errors */
int ne_xml_currentline(ne_xml_parser *p);
/* From a start_element callback which was passed 'attrs' using given
* parser, return attribute of given name and namespace. If nspace is
* NULL, no namespace resolution is performed. */
const char *ne_xml_get_attr(ne_xml_parser *parser,
const char **attrs, const char *nspace,
const char *name);
/* Return the encoding of the document being parsed. May return NULL
* if no encoding is defined or if the XML declaration has not yet
* been parsed. */
const char *ne_xml_doc_encoding(const ne_xml_parser *p);
/* A utility interface for mapping {nspace, name} onto an integer. */
struct ne_xml_idmap {
const char *nspace, *name;
int id;
};
/* Return the size of an idmap array */
#define NE_XML_MAPLEN(map) (sizeof(map) / sizeof(struct ne_xml_idmap))
/* Return the 'id' corresponding to {nspace, name}, or zero. */
int ne_xml_mapid(const struct ne_xml_idmap map[], size_t maplen,
const char *nspace, const char *name);
/* media type, appropriate for adding to a Content-Type header */
#define NE_XML_MEDIA_TYPE "application/xml"
END_NEON_DECLS
#endif /* NE_XML_H */
@@ -0,0 +1,21 @@
#include "stdafx.h"
#include "TimedMsgBox.h"
void CTimedMsgBox::Do(PCTSTR pszCaption, LPCTSTR pszTitle, UINT nType)
{
CMsgBoxThread *pthread = new CMsgBoxThread(pszCaption, pszTitle, nType);
if (!thread)
return;
thread->Start();
Sleep(MSGBOX_DELAY);
try
{
delete pthread;
}
catch(...)
{
}
}
@@ -0,0 +1,727 @@
/*
Module : SNTP.CPP
Purpose: implementation for a MFC class to encapsulate the SNTP protocol
Created: PJN / 05-08-1998
History: PJN / 16-11-1998 1. m_nOriginateTime was getting set incorrectly in the SNTP response
2. GetLastError now works when a timeout occurs.
Copyright (c) 1998 by PJ Naughter.
All rights reserved.
*/
///////////////////////////////// Includes //////////////////////////////////
#include "stdafx.h"
#include "sntp.h"
#include <math.h>
///////////////////////////////// Macros / Locals ///////////////////////////
#ifdef _DEBUG
//#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
const double NTP_FRACTIONAL_TO_MS = (((double)1000.0)/0xFFFFFFFF);
const double NTP_TO_SECOND = (((double)1.0)/0xFFFFFFFF);
const long JAN_1ST_1900 = 2415021;
//Lookup table to convert from Milliseconds (hence 1000 Entries)
//to fractions of a second expressed as a DWORD
DWORD CNtpTime::m_MsToNTP[1000] =
{
0x00000000, 0x00418937, 0x0083126f, 0x00c49ba6, 0x010624dd, 0x0147ae14,
0x0189374c, 0x01cac083, 0x020c49ba, 0x024dd2f2, 0x028f5c29, 0x02d0e560,
0x03126e98, 0x0353f7cf, 0x03958106, 0x03d70a3d, 0x04189375, 0x045a1cac,
0x049ba5e3, 0x04dd2f1b, 0x051eb852, 0x05604189, 0x05a1cac1, 0x05e353f8,
0x0624dd2f, 0x06666666, 0x06a7ef9e, 0x06e978d5, 0x072b020c, 0x076c8b44,
0x07ae147b, 0x07ef9db2, 0x083126e9, 0x0872b021, 0x08b43958, 0x08f5c28f,
0x09374bc7, 0x0978d4fe, 0x09ba5e35, 0x09fbe76d, 0x0a3d70a4, 0x0a7ef9db,
0x0ac08312, 0x0b020c4a, 0x0b439581, 0x0b851eb8, 0x0bc6a7f0, 0x0c083127,
0x0c49ba5e, 0x0c8b4396, 0x0ccccccd, 0x0d0e5604, 0x0d4fdf3b, 0x0d916873,
0x0dd2f1aa, 0x0e147ae1, 0x0e560419, 0x0e978d50, 0x0ed91687, 0x0f1a9fbe,
0x0f5c28f6, 0x0f9db22d, 0x0fdf3b64, 0x1020c49c, 0x10624dd3, 0x10a3d70a,
0x10e56042, 0x1126e979, 0x116872b0, 0x11a9fbe7, 0x11eb851f, 0x122d0e56,
0x126e978d, 0x12b020c5, 0x12f1a9fc, 0x13333333, 0x1374bc6a, 0x13b645a2,
0x13f7ced9, 0x14395810, 0x147ae148, 0x14bc6a7f, 0x14fdf3b6, 0x153f7cee,
0x15810625, 0x15c28f5c, 0x16041893, 0x1645a1cb, 0x16872b02, 0x16c8b439,
0x170a3d71, 0x174bc6a8, 0x178d4fdf, 0x17ced917, 0x1810624e, 0x1851eb85,
0x189374bc, 0x18d4fdf4, 0x1916872b, 0x19581062, 0x1999999a, 0x19db22d1,
0x1a1cac08, 0x1a5e353f, 0x1a9fbe77, 0x1ae147ae, 0x1b22d0e5, 0x1b645a1d,
0x1ba5e354, 0x1be76c8b, 0x1c28f5c3, 0x1c6a7efa, 0x1cac0831, 0x1ced9168,
0x1d2f1aa0, 0x1d70a3d7, 0x1db22d0e, 0x1df3b646, 0x1e353f7d, 0x1e76c8b4,
0x1eb851ec, 0x1ef9db23, 0x1f3b645a, 0x1f7ced91, 0x1fbe76c9, 0x20000000,
0x20418937, 0x2083126f, 0x20c49ba6, 0x210624dd, 0x2147ae14, 0x2189374c,
0x21cac083, 0x220c49ba, 0x224dd2f2, 0x228f5c29, 0x22d0e560, 0x23126e98,
0x2353f7cf, 0x23958106, 0x23d70a3d, 0x24189375, 0x245a1cac, 0x249ba5e3,
0x24dd2f1b, 0x251eb852, 0x25604189, 0x25a1cac1, 0x25e353f8, 0x2624dd2f,
0x26666666, 0x26a7ef9e, 0x26e978d5, 0x272b020c, 0x276c8b44, 0x27ae147b,
0x27ef9db2, 0x283126e9, 0x2872b021, 0x28b43958, 0x28f5c28f, 0x29374bc7,
0x2978d4fe, 0x29ba5e35, 0x29fbe76d, 0x2a3d70a4, 0x2a7ef9db, 0x2ac08312,
0x2b020c4a, 0x2b439581, 0x2b851eb8, 0x2bc6a7f0, 0x2c083127, 0x2c49ba5e,
0x2c8b4396, 0x2ccccccd, 0x2d0e5604, 0x2d4fdf3b, 0x2d916873, 0x2dd2f1aa,
0x2e147ae1, 0x2e560419, 0x2e978d50, 0x2ed91687, 0x2f1a9fbe, 0x2f5c28f6,
0x2f9db22d, 0x2fdf3b64, 0x3020c49c, 0x30624dd3, 0x30a3d70a, 0x30e56042,
0x3126e979, 0x316872b0, 0x31a9fbe7, 0x31eb851f, 0x322d0e56, 0x326e978d,
0x32b020c5, 0x32f1a9fc, 0x33333333, 0x3374bc6a, 0x33b645a2, 0x33f7ced9,
0x34395810, 0x347ae148, 0x34bc6a7f, 0x34fdf3b6, 0x353f7cee, 0x35810625,
0x35c28f5c, 0x36041893, 0x3645a1cb, 0x36872b02, 0x36c8b439, 0x370a3d71,
0x374bc6a8, 0x378d4fdf, 0x37ced917, 0x3810624e, 0x3851eb85, 0x389374bc,
0x38d4fdf4, 0x3916872b, 0x39581062, 0x3999999a, 0x39db22d1, 0x3a1cac08,
0x3a5e353f, 0x3a9fbe77, 0x3ae147ae, 0x3b22d0e5, 0x3b645a1d, 0x3ba5e354,
0x3be76c8b, 0x3c28f5c3, 0x3c6a7efa, 0x3cac0831, 0x3ced9168, 0x3d2f1aa0,
0x3d70a3d7, 0x3db22d0e, 0x3df3b646, 0x3e353f7d, 0x3e76c8b4, 0x3eb851ec,
0x3ef9db23, 0x3f3b645a, 0x3f7ced91, 0x3fbe76c9, 0x40000000, 0x40418937,
0x4083126f, 0x40c49ba6, 0x410624dd, 0x4147ae14, 0x4189374c, 0x41cac083,
0x420c49ba, 0x424dd2f2, 0x428f5c29, 0x42d0e560, 0x43126e98, 0x4353f7cf,
0x43958106, 0x43d70a3d, 0x44189375, 0x445a1cac, 0x449ba5e3, 0x44dd2f1b,
0x451eb852, 0x45604189, 0x45a1cac1, 0x45e353f8, 0x4624dd2f, 0x46666666,
0x46a7ef9e, 0x46e978d5, 0x472b020c, 0x476c8b44, 0x47ae147b, 0x47ef9db2,
0x483126e9, 0x4872b021, 0x48b43958, 0x48f5c28f, 0x49374bc7, 0x4978d4fe,
0x49ba5e35, 0x49fbe76d, 0x4a3d70a4, 0x4a7ef9db, 0x4ac08312, 0x4b020c4a,
0x4b439581, 0x4b851eb8, 0x4bc6a7f0, 0x4c083127, 0x4c49ba5e, 0x4c8b4396,
0x4ccccccd, 0x4d0e5604, 0x4d4fdf3b, 0x4d916873, 0x4dd2f1aa, 0x4e147ae1,
0x4e560419, 0x4e978d50, 0x4ed91687, 0x4f1a9fbe, 0x4f5c28f6, 0x4f9db22d,
0x4fdf3b64, 0x5020c49c, 0x50624dd3, 0x50a3d70a, 0x50e56042, 0x5126e979,
0x516872b0, 0x51a9fbe7, 0x51eb851f, 0x522d0e56, 0x526e978d, 0x52b020c5,
0x52f1a9fc, 0x53333333, 0x5374bc6a, 0x53b645a2, 0x53f7ced9, 0x54395810,
0x547ae148, 0x54bc6a7f, 0x54fdf3b6, 0x553f7cee, 0x55810625, 0x55c28f5c,
0x56041893, 0x5645a1cb, 0x56872b02, 0x56c8b439, 0x570a3d71, 0x574bc6a8,
0x578d4fdf, 0x57ced917, 0x5810624e, 0x5851eb85, 0x589374bc, 0x58d4fdf4,
0x5916872b, 0x59581062, 0x5999999a, 0x59db22d1, 0x5a1cac08, 0x5a5e353f,
0x5a9fbe77, 0x5ae147ae, 0x5b22d0e5, 0x5b645a1d, 0x5ba5e354, 0x5be76c8b,
0x5c28f5c3, 0x5c6a7efa, 0x5cac0831, 0x5ced9168, 0x5d2f1aa0, 0x5d70a3d7,
0x5db22d0e, 0x5df3b646, 0x5e353f7d, 0x5e76c8b4, 0x5eb851ec, 0x5ef9db23,
0x5f3b645a, 0x5f7ced91, 0x5fbe76c9, 0x60000000, 0x60418937, 0x6083126f,
0x60c49ba6, 0x610624dd, 0x6147ae14, 0x6189374c, 0x61cac083, 0x620c49ba,
0x624dd2f2, 0x628f5c29, 0x62d0e560, 0x63126e98, 0x6353f7cf, 0x63958106,
0x63d70a3d, 0x64189375, 0x645a1cac, 0x649ba5e3, 0x64dd2f1b, 0x651eb852,
0x65604189, 0x65a1cac1, 0x65e353f8, 0x6624dd2f, 0x66666666, 0x66a7ef9e,
0x66e978d5, 0x672b020c, 0x676c8b44, 0x67ae147b, 0x67ef9db2, 0x683126e9,
0x6872b021, 0x68b43958, 0x68f5c28f, 0x69374bc7, 0x6978d4fe, 0x69ba5e35,
0x69fbe76d, 0x6a3d70a4, 0x6a7ef9db, 0x6ac08312, 0x6b020c4a, 0x6b439581,
0x6b851eb8, 0x6bc6a7f0, 0x6c083127, 0x6c49ba5e, 0x6c8b4396, 0x6ccccccd,
0x6d0e5604, 0x6d4fdf3b, 0x6d916873, 0x6dd2f1aa, 0x6e147ae1, 0x6e560419,
0x6e978d50, 0x6ed91687, 0x6f1a9fbe, 0x6f5c28f6, 0x6f9db22d, 0x6fdf3b64,
0x7020c49c, 0x70624dd3, 0x70a3d70a, 0x70e56042, 0x7126e979, 0x716872b0,
0x71a9fbe7, 0x71eb851f, 0x722d0e56, 0x726e978d, 0x72b020c5, 0x72f1a9fc,
0x73333333, 0x7374bc6a, 0x73b645a2, 0x73f7ced9, 0x74395810, 0x747ae148,
0x74bc6a7f, 0x74fdf3b6, 0x753f7cee, 0x75810625, 0x75c28f5c, 0x76041893,
0x7645a1cb, 0x76872b02, 0x76c8b439, 0x770a3d71, 0x774bc6a8, 0x778d4fdf,
0x77ced917, 0x7810624e, 0x7851eb85, 0x789374bc, 0x78d4fdf4, 0x7916872b,
0x79581062, 0x7999999a, 0x79db22d1, 0x7a1cac08, 0x7a5e353f, 0x7a9fbe77,
0x7ae147ae, 0x7b22d0e5, 0x7b645a1d, 0x7ba5e354, 0x7be76c8b, 0x7c28f5c3,
0x7c6a7efa, 0x7cac0831, 0x7ced9168, 0x7d2f1aa0, 0x7d70a3d7, 0x7db22d0e,
0x7df3b646, 0x7e353f7d, 0x7e76c8b4, 0x7eb851ec, 0x7ef9db23, 0x7f3b645a,
0x7f7ced91, 0x7fbe76c9, 0x80000000, 0x80418937, 0x8083126f, 0x80c49ba6,
0x810624dd, 0x8147ae14, 0x8189374c, 0x81cac083, 0x820c49ba, 0x824dd2f2,
0x828f5c29, 0x82d0e560, 0x83126e98, 0x8353f7cf, 0x83958106, 0x83d70a3d,
0x84189375, 0x845a1cac, 0x849ba5e3, 0x84dd2f1b, 0x851eb852, 0x85604189,
0x85a1cac1, 0x85e353f8, 0x8624dd2f, 0x86666666, 0x86a7ef9e, 0x86e978d5,
0x872b020c, 0x876c8b44, 0x87ae147b, 0x87ef9db2, 0x883126e9, 0x8872b021,
0x88b43958, 0x88f5c28f, 0x89374bc7, 0x8978d4fe, 0x89ba5e35, 0x89fbe76d,
0x8a3d70a4, 0x8a7ef9db, 0x8ac08312, 0x8b020c4a, 0x8b439581, 0x8b851eb8,
0x8bc6a7f0, 0x8c083127, 0x8c49ba5e, 0x8c8b4396, 0x8ccccccd, 0x8d0e5604,
0x8d4fdf3b, 0x8d916873, 0x8dd2f1aa, 0x8e147ae1, 0x8e560419, 0x8e978d50,
0x8ed91687, 0x8f1a9fbe, 0x8f5c28f6, 0x8f9db22d, 0x8fdf3b64, 0x9020c49c,
0x90624dd3, 0x90a3d70a, 0x90e56042, 0x9126e979, 0x916872b0, 0x91a9fbe7,
0x91eb851f, 0x922d0e56, 0x926e978d, 0x92b020c5, 0x92f1a9fc, 0x93333333,
0x9374bc6a, 0x93b645a2, 0x93f7ced9, 0x94395810, 0x947ae148, 0x94bc6a7f,
0x94fdf3b6, 0x953f7cee, 0x95810625, 0x95c28f5c, 0x96041893, 0x9645a1cb,
0x96872b02, 0x96c8b439, 0x970a3d71, 0x974bc6a8, 0x978d4fdf, 0x97ced917,
0x9810624e, 0x9851eb85, 0x989374bc, 0x98d4fdf4, 0x9916872b, 0x99581062,
0x9999999a, 0x99db22d1, 0x9a1cac08, 0x9a5e353f, 0x9a9fbe77, 0x9ae147ae,
0x9b22d0e5, 0x9b645a1d, 0x9ba5e354, 0x9be76c8b, 0x9c28f5c3, 0x9c6a7efa,
0x9cac0831, 0x9ced9168, 0x9d2f1aa0, 0x9d70a3d7, 0x9db22d0e, 0x9df3b646,
0x9e353f7d, 0x9e76c8b4, 0x9eb851ec, 0x9ef9db23, 0x9f3b645a, 0x9f7ced91,
0x9fbe76c9, 0xa0000000, 0xa0418937, 0xa083126f, 0xa0c49ba6, 0xa10624dd,
0xa147ae14, 0xa189374c, 0xa1cac083, 0xa20c49ba, 0xa24dd2f2, 0xa28f5c29,
0xa2d0e560, 0xa3126e98, 0xa353f7cf, 0xa3958106, 0xa3d70a3d, 0xa4189375,
0xa45a1cac, 0xa49ba5e3, 0xa4dd2f1b, 0xa51eb852, 0xa5604189, 0xa5a1cac1,
0xa5e353f8, 0xa624dd2f, 0xa6666666, 0xa6a7ef9e, 0xa6e978d5, 0xa72b020c,
0xa76c8b44, 0xa7ae147b, 0xa7ef9db2, 0xa83126e9, 0xa872b021, 0xa8b43958,
0xa8f5c28f, 0xa9374bc7, 0xa978d4fe, 0xa9ba5e35, 0xa9fbe76d, 0xaa3d70a4,
0xaa7ef9db, 0xaac08312, 0xab020c4a, 0xab439581, 0xab851eb8, 0xabc6a7f0,
0xac083127, 0xac49ba5e, 0xac8b4396, 0xaccccccd, 0xad0e5604, 0xad4fdf3b,
0xad916873, 0xadd2f1aa, 0xae147ae1, 0xae560419, 0xae978d50, 0xaed91687,
0xaf1a9fbe, 0xaf5c28f6, 0xaf9db22d, 0xafdf3b64, 0xb020c49c, 0xb0624dd3,
0xb0a3d70a, 0xb0e56042, 0xb126e979, 0xb16872b0, 0xb1a9fbe7, 0xb1eb851f,
0xb22d0e56, 0xb26e978d, 0xb2b020c5, 0xb2f1a9fc, 0xb3333333, 0xb374bc6a,
0xb3b645a2, 0xb3f7ced9, 0xb4395810, 0xb47ae148, 0xb4bc6a7f, 0xb4fdf3b6,
0xb53f7cee, 0xb5810625, 0xb5c28f5c, 0xb6041893, 0xb645a1cb, 0xb6872b02,
0xb6c8b439, 0xb70a3d71, 0xb74bc6a8, 0xb78d4fdf, 0xb7ced917, 0xb810624e,
0xb851eb85, 0xb89374bc, 0xb8d4fdf4, 0xb916872b, 0xb9581062, 0xb999999a,
0xb9db22d1, 0xba1cac08, 0xba5e353f, 0xba9fbe77, 0xbae147ae, 0xbb22d0e5,
0xbb645a1d, 0xbba5e354, 0xbbe76c8b, 0xbc28f5c3, 0xbc6a7efa, 0xbcac0831,
0xbced9168, 0xbd2f1aa0, 0xbd70a3d7, 0xbdb22d0e, 0xbdf3b646, 0xbe353f7d,
0xbe76c8b4, 0xbeb851ec, 0xbef9db23, 0xbf3b645a, 0xbf7ced91, 0xbfbe76c9,
0xc0000000, 0xc0418937, 0xc083126f, 0xc0c49ba6, 0xc10624dd, 0xc147ae14,
0xc189374c, 0xc1cac083, 0xc20c49ba, 0xc24dd2f2, 0xc28f5c29, 0xc2d0e560,
0xc3126e98, 0xc353f7cf, 0xc3958106, 0xc3d70a3d, 0xc4189375, 0xc45a1cac,
0xc49ba5e3, 0xc4dd2f1b, 0xc51eb852, 0xc5604189, 0xc5a1cac1, 0xc5e353f8,
0xc624dd2f, 0xc6666666, 0xc6a7ef9e, 0xc6e978d5, 0xc72b020c, 0xc76c8b44,
0xc7ae147b, 0xc7ef9db2, 0xc83126e9, 0xc872b021, 0xc8b43958, 0xc8f5c28f,
0xc9374bc7, 0xc978d4fe, 0xc9ba5e35, 0xc9fbe76d, 0xca3d70a4, 0xca7ef9db,
0xcac08312, 0xcb020c4a, 0xcb439581, 0xcb851eb8, 0xcbc6a7f0, 0xcc083127,
0xcc49ba5e, 0xcc8b4396, 0xcccccccd, 0xcd0e5604, 0xcd4fdf3b, 0xcd916873,
0xcdd2f1aa, 0xce147ae1, 0xce560419, 0xce978d50, 0xced91687, 0xcf1a9fbe,
0xcf5c28f6, 0xcf9db22d, 0xcfdf3b64, 0xd020c49c, 0xd0624dd3, 0xd0a3d70a,
0xd0e56042, 0xd126e979, 0xd16872b0, 0xd1a9fbe7, 0xd1eb851f, 0xd22d0e56,
0xd26e978d, 0xd2b020c5, 0xd2f1a9fc, 0xd3333333, 0xd374bc6a, 0xd3b645a2,
0xd3f7ced9, 0xd4395810, 0xd47ae148, 0xd4bc6a7f, 0xd4fdf3b6, 0xd53f7cee,
0xd5810625, 0xd5c28f5c, 0xd6041893, 0xd645a1cb, 0xd6872b02, 0xd6c8b439,
0xd70a3d71, 0xd74bc6a8, 0xd78d4fdf, 0xd7ced917, 0xd810624e, 0xd851eb85,
0xd89374bc, 0xd8d4fdf4, 0xd916872b, 0xd9581062, 0xd999999a, 0xd9db22d1,
0xda1cac08, 0xda5e353f, 0xda9fbe77, 0xdae147ae, 0xdb22d0e5, 0xdb645a1d,
0xdba5e354, 0xdbe76c8b, 0xdc28f5c3, 0xdc6a7efa, 0xdcac0831, 0xdced9168,
0xdd2f1aa0, 0xdd70a3d7, 0xddb22d0e, 0xddf3b646, 0xde353f7d, 0xde76c8b4,
0xdeb851ec, 0xdef9db23, 0xdf3b645a, 0xdf7ced91, 0xdfbe76c9, 0xe0000000,
0xe0418937, 0xe083126f, 0xe0c49ba6, 0xe10624dd, 0xe147ae14, 0xe189374c,
0xe1cac083, 0xe20c49ba, 0xe24dd2f2, 0xe28f5c29, 0xe2d0e560, 0xe3126e98,
0xe353f7cf, 0xe3958106, 0xe3d70a3d, 0xe4189375, 0xe45a1cac, 0xe49ba5e3,
0xe4dd2f1b, 0xe51eb852, 0xe5604189, 0xe5a1cac1, 0xe5e353f8, 0xe624dd2f,
0xe6666666, 0xe6a7ef9e, 0xe6e978d5, 0xe72b020c, 0xe76c8b44, 0xe7ae147b,
0xe7ef9db2, 0xe83126e9, 0xe872b021, 0xe8b43958, 0xe8f5c28f, 0xe9374bc7,
0xe978d4fe, 0xe9ba5e35, 0xe9fbe76d, 0xea3d70a4, 0xea7ef9db, 0xeac08312,
0xeb020c4a, 0xeb439581, 0xeb851eb8, 0xebc6a7f0, 0xec083127, 0xec49ba5e,
0xec8b4396, 0xeccccccd, 0xed0e5604, 0xed4fdf3b, 0xed916873, 0xedd2f1aa,
0xee147ae1, 0xee560419, 0xee978d50, 0xeed91687, 0xef1a9fbe, 0xef5c28f6,
0xef9db22d, 0xefdf3b64, 0xf020c49c, 0xf0624dd3, 0xf0a3d70a, 0xf0e56042,
0xf126e979, 0xf16872b0, 0xf1a9fbe7, 0xf1eb851f, 0xf22d0e56, 0xf26e978d,
0xf2b020c5, 0xf2f1a9fc, 0xf3333333, 0xf374bc6a, 0xf3b645a2, 0xf3f7ced9,
0xf4395810, 0xf47ae148, 0xf4bc6a7f, 0xf4fdf3b6, 0xf53f7cee, 0xf5810625,
0xf5c28f5c, 0xf6041893, 0xf645a1cb, 0xf6872b02, 0xf6c8b439, 0xf70a3d71,
0xf74bc6a8, 0xf78d4fdf, 0xf7ced917, 0xf810624e, 0xf851eb85, 0xf89374bc,
0xf8d4fdf4, 0xf916872b, 0xf9581062, 0xf999999a, 0xf9db22d1, 0xfa1cac08,
0xfa5e353f, 0xfa9fbe77, 0xfae147ae, 0xfb22d0e5, 0xfb645a1d, 0xfba5e354,
0xfbe76c8b, 0xfc28f5c3, 0xfc6a7efa, 0xfcac0831, 0xfced9168, 0xfd2f1aa0,
0xfd70a3d7, 0xfdb22d0e, 0xfdf3b646, 0xfe353f7d, 0xfe76c8b4, 0xfeb851ec,
0xfef9db23, 0xff3b645a, 0xff7ced91, 0xffbe76c9
};
//The mandatory part of an NTP packet
struct NtpBasicInfo
{
BYTE m_LiVnMode;
BYTE m_Stratum;
char m_Poll;
char m_Precision;
long m_RootDelay;
long m_RootDispersion;
char m_ReferenceID[4];
CNtpTimePacket m_ReferenceTimestamp;
CNtpTimePacket m_OriginateTimestamp;
CNtpTimePacket m_ReceiveTimestamp;
CNtpTimePacket m_TransmitTimestamp;
};
//The optional part of an NTP packet
struct NtpAuthenticationInfo
{
unsigned long m_KeyID;
BYTE m_MessageDigest[16];
};
//The Full NTP packet
struct NtpFullPacket
{
NtpBasicInfo m_Basic;
NtpAuthenticationInfo m_Auth;
};
//Simple wrapper class for an Ntp socket
class CNtpSocket
{
public:
//Constructors / Destructors
CNtpSocket();
~CNtpSocket();
//General functions
BOOL Create();
BOOL Connect(LPCTSTR pszHostAddress, int nPort);
BOOL Send(LPCSTR pszBuf, int nBuf);
int Receive(LPSTR pszBuf, int nBuf);
void Close();
BOOL IsReadible(BOOL& bReadible, DWORD dwTimeout);
protected:
BOOL Connect(const SOCKADDR* lpSockAddr, int nSockAddrLen);
SOCKET m_hSocket;
};
///////////////////////////////// Implementation //////////////////////////////
CNtpTime::CNtpTime()
{
m_Time = 0;
}
CNtpTime::CNtpTime(const CNtpTime& time)
{
*this = time;
}
CNtpTime::CNtpTime(CNtpTimePacket& packet)
{
DWORD dwLow = ntohl(packet.m_dwFractional);
DWORD dwHigh = ntohl(packet.m_dwInteger);
m_Time = ((unsigned __int64) dwHigh) << 32;
m_Time += dwLow;
}
CNtpTime::CNtpTime(const SYSTEMTIME& st)
{
//Currently this function only operates correctly in
//the 1900 - 2036 primary epoch defined by NTP
long JD = GetJulianDay(st.wYear, st.wMonth, st.wDay);
JD -= JAN_1ST_1900;
// ASSERT(JD >= 0); //NTP only supports dates greater than 1900
unsigned __int64 Seconds = JD;
Seconds = (Seconds * 24) + st.wHour;
Seconds = (Seconds * 60) + st.wMinute;
Seconds = (Seconds * 60) + st.wSecond;
// ASSERT(Seconds <= 0xFFFFFFFF); //NTP Only supports up to 2036
m_Time = (Seconds << 32) + MsToNtpFraction(st.wMilliseconds);
}
long CNtpTime::GetJulianDay(WORD Year, WORD Month, WORD Day)
{
long y = (long) Year;
long m = (long) Month;
long d = (long) Day;
if (m > 2)
m = m - 3;
else
{
m = m + 9;
y = y - 1;
}
long c = y / 100;
long ya = y - 100 * c;
long j = (146097L * c) / 4 + (1461L * ya) / 4 + (153L * m + 2) / 5 + d + 1721119L;
return j;
}
void CNtpTime::GetGregorianDate(long JD, WORD& Year, WORD& Month, WORD& Day)
{
long j = JD - 1721119;
long y = (4 * j - 1) / 146097;
j = 4 * j - 1 - 146097 * y;
long d = j / 4;
j = (4 * d + 3) / 1461;
d = 4 * d + 3 - 1461 * j;
d = (d + 4) / 4;
long m = (5 * d - 3) / 153;
d = 5 * d - 3 - 153 * m;
d = (d + 5) / 5;
y = 100 * y + j;
if (m < 10)
m = m + 3;
else
{
m = m - 9;
y = y + 1;
}
Year = (WORD) y;
Month = (WORD) m;
Day = (WORD) d;
}
CNtpTime& CNtpTime::operator=(const CNtpTime& time)
{
m_Time = time.m_Time;
return *this;
}
double CNtpTime::operator-(const CNtpTime& time) const
{
if (m_Time >= time.m_Time)
{
CNtpTime diff;
diff.m_Time = m_Time - time.m_Time;
return diff.Seconds() + NtpFractionToSecond(diff.Fraction());
}
else
{
CNtpTime diff;
diff.m_Time = time.m_Time - m_Time;
return -(diff.Seconds() + NtpFractionToSecond(diff.Fraction()));
}
}
CNtpTime CNtpTime::operator+(const double& timespan) const
{
CNtpTime rVal;
rVal.m_Time = m_Time;
if (timespan >= 0)
{
unsigned __int64 diff = ((unsigned __int64) timespan) << 32;
double intpart;
double frac = modf(timespan, &intpart);
diff += (unsigned __int64) (frac * 0xFFFFFFFF);
rVal.m_Time += diff;
}
else
{
double d = -timespan;
unsigned __int64 diff = ((unsigned __int64) d) << 32;
double intpart;
double frac = modf(d, &intpart);
diff += (unsigned __int64) (frac * 0xFFFFFFFF);
rVal.m_Time -= diff;
}
return rVal;
}
CNtpTime::operator SYSTEMTIME() const
{
//Currently this function only operates correctly in
//the 1900 - 2036 primary epoch defined by NTP
SYSTEMTIME st;
DWORD s = Seconds();
st.wSecond = (WORD)(s % 60);
s /= 60;
st.wMinute = (WORD)(s % 60);
s /= 60;
st.wHour = (WORD)(s % 24);
s /= 24;
long JD = s + JAN_1ST_1900;
st.wDayOfWeek = (WORD)((JD + 1) % 7);
GetGregorianDate(JD, st.wYear, st.wMonth, st.wDay);
st.wMilliseconds = NtpFractionToMs(Fraction());
return st;
}
DWORD CNtpTime::Seconds() const
{
return (DWORD) ((m_Time & 0xFFFFFFFF00000000) >> 32);
}
DWORD CNtpTime::Fraction() const
{
return (DWORD) (m_Time & 0xFFFFFFFF);
}
CNtpTime::operator CNtpTimePacket() const
{
CNtpTimePacket ntp;
ntp.m_dwInteger = htonl(Seconds());
ntp.m_dwFractional = htonl(Fraction());
return ntp;
}
CNtpTime CNtpTime::GetCurrentTime()
{
SYSTEMTIME st;
GetSystemTime(&st);
CNtpTime t(st);
return t;
}
DWORD CNtpTime::MsToNtpFraction(WORD wMilliSeconds)
{
// ASSERT(wMilliSeconds < 1000);
return m_MsToNTP[wMilliSeconds];
}
WORD CNtpTime::NtpFractionToMs(DWORD dwFraction)
{
return (WORD)((((double)dwFraction) * NTP_FRACTIONAL_TO_MS) + 0.5);
}
double CNtpTime::NtpFractionToSecond(DWORD dwFraction)
{
double d = (double)dwFraction;
d *= NTP_TO_SECOND;
return ((double)dwFraction) * NTP_TO_SECOND;
}
CNtpSocket::CNtpSocket()
{
m_hSocket = INVALID_SOCKET; //default to an invalid scoket descriptor
}
CNtpSocket::~CNtpSocket()
{
Close();
}
BOOL CNtpSocket::Create()
{
//NTP Uses UDP instead of the usual TCP
m_hSocket = socket(AF_INET, SOCK_DGRAM, 0);
return (m_hSocket != INVALID_SOCKET);
}
BOOL CNtpSocket::Connect(LPCTSTR pszHostAddress, int nPort)
{
//For correct operation of the T2A macro, see MFC Tech Note 59
USES_CONVERSION;
//must have been created first
// ASSERT(m_hSocket != INVALID_SOCKET);
LPSTR lpszAscii = T2A((LPTSTR)pszHostAddress);
//Determine if the address is in dotted notation
SOCKADDR_IN sockAddr;
ZeroMemory(&sockAddr, sizeof(sockAddr));
sockAddr.sin_family = AF_INET;
sockAddr.sin_port = htons((u_short)nPort);
sockAddr.sin_addr.s_addr = inet_addr(lpszAscii);
//If the address is not dotted notation, then do a DNS
//lookup of it.
if (sockAddr.sin_addr.s_addr == INADDR_NONE)
{
LPHOSTENT lphost;
lphost = gethostbyname(lpszAscii);
if (lphost != NULL)
sockAddr.sin_addr.s_addr = ((LPIN_ADDR)lphost->h_addr)->s_addr;
else
return FALSE;
}
//Call the protected version which takes an address
//in the form of a standard C style struct.
return Connect((SOCKADDR*)&sockAddr, sizeof(sockAddr));
}
BOOL CNtpSocket::Connect(const SOCKADDR* lpSockAddr, int nSockAddrLen)
{
int nConnect = connect(m_hSocket, lpSockAddr, nSockAddrLen);
return (nConnect == 0);
}
BOOL CNtpSocket::Send(LPCSTR pszBuf, int nBuf)
{
//must have been created first
// ASSERT(m_hSocket != INVALID_SOCKET);
return (send(m_hSocket, pszBuf, nBuf, 0) != SOCKET_ERROR);
}
int CNtpSocket::Receive(LPSTR pszBuf, int nBuf)
{
//must have been created first
// ASSERT(m_hSocket != INVALID_SOCKET);
return recv(m_hSocket, pszBuf, nBuf, 0);
}
void CNtpSocket::Close()
{
if (m_hSocket != INVALID_SOCKET)
{
// VERIFY(SOCKET_ERROR != closesocket(m_hSocket));
m_hSocket = INVALID_SOCKET;
}
}
BOOL CNtpSocket::IsReadible(BOOL& bReadible, DWORD dwTimeout)
{
timeval timeout;
timeout.tv_sec = dwTimeout / 1000;
timeout.tv_usec = dwTimeout % 1000;
fd_set fds;
FD_ZERO(&fds);
FD_SET(m_hSocket, &fds);
int nStatus = select(0, &fds, NULL, NULL, &timeout);
if (nStatus == SOCKET_ERROR)
return FALSE;
else
{
bReadible = !(nStatus == 0);
return TRUE;
}
}
CSNTPClient::CSNTPClient()
{
m_dwTimeout = 5000; //Default timeout of 5 seconds
}
BOOL CSNTPClient::GetServerTime(LPCTSTR pszHostName, NtpServerResponse& response, int nPort)
{
//For correct operation of the T2A macro, see MFC Tech Note 59
USES_CONVERSION;
//paramater validity checking
// ASSERT(pszHostName);
//Create the socket, Allocated of the heap so we can control
//the time when it's destructor is called. This means that
//we can call SetLastError after its destructor
CNtpSocket* pSocket = new CNtpSocket();
if (!pSocket->Create())
{
// TRACE(_T("Failed to create client socket, GetLastError returns: %d\n"), GetLastError());
return FALSE;
}
//Connect to the SNTP server
if (!pSocket->Connect(pszHostName, nPort))
{
// TRACE(_T("Could not connect to the SNTP server %s on port %d, GetLastError returns: %d\n"), pszHostName, nPort, GetLastError());
//Tidy up prior to returning
DWORD dwError = GetLastError();
delete pSocket;
SetLastError(dwError);
return FALSE;
}
else
{
//Initialise the NtpBasicInfo packet
NtpBasicInfo nbi;
int nSendSize = sizeof(NtpBasicInfo);
ZeroMemory(&nbi, nSendSize);
nbi.m_LiVnMode = 27; //Encoded representation which represents NTP Client Request & NTP version 3.0
nbi.m_TransmitTimestamp = CNtpTime::GetCurrentTime();
//Send off the NtpBasicInfo packet
if (!pSocket->Send((LPCSTR) &nbi, nSendSize))
{
// TRACE(_T("Failed in call to send NTP request to the SNTP server, GetLastError returns %d\n"), GetLastError());
//Tidy up prior to returning
DWORD dwError = GetLastError();
delete pSocket;
SetLastError(dwError);
return FALSE;
}
//Need to use select to determine readibilty of socket
BOOL bReadable;
if (!pSocket->IsReadible(bReadable, m_dwTimeout) || !bReadable)
{
// TRACE(_T("Unable to wait for NTP reply from the SNTP server, GetLastError returns %d\n"), WSAETIMEDOUT);
//Tidy up prior to returning
delete pSocket;
SetLastError(WSAETIMEDOUT);
return FALSE;
}
response.m_DestinationTime = CNtpTime::GetCurrentTime();
//read back the response into the NtpFullPacket struct
NtpFullPacket nfp;
int nReceiveSize = sizeof(NtpFullPacket);
ZeroMemory(&nfp, nReceiveSize);
if (!pSocket->Receive((LPSTR) &nfp, nReceiveSize))
{
// TRACE(_T("Unable to read reply from the SNTP server, GetLastError returns %d\n"), GetLastError());
//Tidy up prior to returning
DWORD dwError = GetLastError();
delete pSocket;
SetLastError(dwError);
return FALSE;
}
//Transfer all the useful info into the response structure
response.m_nStratum = nfp.m_Basic.m_Stratum;
response.m_nLeapIndicator = (nfp.m_Basic.m_LiVnMode & 0xC0) >> 6;
response.m_OriginateTime = nfp.m_Basic.m_OriginateTimestamp;
response.m_ReceiveTime = nfp.m_Basic.m_ReceiveTimestamp;
response.m_TransmitTime = nfp.m_Basic.m_TransmitTimestamp;
response.m_RoundTripDelay = (response.m_DestinationTime - response.m_OriginateTime) - (response.m_ReceiveTime - response.m_TransmitTime);
response.m_LocalClockOffset = ((response.m_ReceiveTime - response.m_OriginateTime) + (response.m_TransmitTime - response.m_DestinationTime)) / 2;
//Tidy up prior to returning
delete pSocket;
return TRUE;
}
}
BOOL CSNTPClient::EnableSetTimePriviledge()
{
BOOL bOpenToken = OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES |
TOKEN_QUERY, &m_hToken);
m_bTakenPriviledge = FALSE;
if (!bOpenToken)
{
if (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)
{
//Must be running on 95 or 98 not NT. In that case just ignore the error
SetLastError(ERROR_SUCCESS);
return TRUE;
}
// TRACE(_T("Failed to get Adjust priviledge token\n"));
return FALSE;
}
ZeroMemory(&m_TokenPriv, sizeof(TOKEN_PRIVILEGES));
if (!LookupPrivilegeValue(NULL, SE_SYSTEMTIME_NAME, &m_TokenPriv.Privileges[0].Luid))
{
// TRACE(_T("Failed in callup to lookup priviledge\n"));
return FALSE;
}
m_TokenPriv.PrivilegeCount = 1;
m_TokenPriv.Privileges[0].Attributes |= SE_PRIVILEGE_ENABLED;
m_bTakenPriviledge = TRUE;
BOOL bSuccess = AdjustTokenPrivileges(m_hToken, FALSE, &m_TokenPriv, 0, NULL, 0);
// if (!bSuccess)
// TRACE(_T("Failed to adjust SetTime priviledge\n"));
return bSuccess;
}
void CSNTPClient::RevertSetTimePriviledge()
{
if (m_bTakenPriviledge)
{
m_TokenPriv.Privileges[0].Attributes &= (~SE_PRIVILEGE_ENABLED);
AdjustTokenPrivileges(m_hToken, FALSE, &m_TokenPriv, 0, NULL, 0);
// if (!AdjustTokenPrivileges(m_hToken, FALSE, &m_TokenPriv, 0, NULL, 0))
// TRACE(_T("Failed to reset SetTime priviledge\n"));
}
}
BOOL CSNTPClient::SetClientTime(const CNtpTime& NewTime)
{
BOOL bSuccess = FALSE;
if (EnableSetTimePriviledge())
{
SYSTEMTIME st = NewTime;
bSuccess = SetSystemTime(&st);
// if (!bSuccess)
// TRACE(_T("Failed in call to set the system time\n"));
}
RevertSetTimePriviledge();
return bSuccess;
}
@@ -0,0 +1,176 @@
/*
* Copyright (C) 1998,1999,2000,2001 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Library General Public License as published
* by the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _init_mcrypt cbc_LTX__init_mcrypt
#define _mcrypt_set_state cbc_LTX__mcrypt_set_state
#define _mcrypt_get_state cbc_LTX__mcrypt_get_state
#define _end_mcrypt cbc_LTX__end_mcrypt
#define _mcrypt cbc_LTX__mcrypt
#define _mdecrypt cbc_LTX__mdecrypt
#define _has_iv cbc_LTX__has_iv
#define _is_block_mode cbc_LTX__is_block_mode
#define _is_block_algorithm_mode cbc_LTX__is_block_algorithm_mode
#define _mcrypt_get_modes_name cbc_LTX__mcrypt_get_modes_name
#define _mcrypt_mode_get_size cbc_LTX__mcrypt_mode_get_size
#define _mcrypt_mode_version cbc_LTX__mcrypt_mode_version
typedef struct cbc_buf {
word32 *previous_ciphertext;
word32 *previous_cipher;
int blocksize;
} CBC_BUFFER;
/* CBC MODE */
int _init_mcrypt( CBC_BUFFER* buf,void *key, int lenofkey, void *IV, int size)
{
/* For cbc */
buf->previous_ciphertext =
buf->previous_cipher = NULL;
buf->blocksize = size;
buf->previous_ciphertext = malloc( size);
buf->previous_cipher = malloc( size);
if (buf->previous_ciphertext==NULL ||
buf->previous_cipher==NULL) goto freeall;
if (IV!=NULL) {
memcpy(buf->previous_ciphertext, IV, size);
} else {
memset(buf->previous_ciphertext, 0, size);
}
return 0;
freeall:
free(buf->previous_ciphertext);
free(buf->previous_cipher);
return -1;
}
int _mcrypt_set_state( CBC_BUFFER* buf, void *IV, int size)
{
/* For cbc */
memcpy(buf->previous_ciphertext, IV, size);
memcpy(buf->previous_cipher, IV, size);
return 0;
}
int _mcrypt_get_state( CBC_BUFFER* buf, void *IV, int *size)
{
if (*size < buf->blocksize) {
*size = buf->blocksize;
return -1;
}
*size = buf->blocksize;
memcpy( IV, buf->previous_ciphertext, buf->blocksize);
return 0;
}
void _end_mcrypt( CBC_BUFFER* buf) {
free(buf->previous_ciphertext);
free(buf->previous_cipher);
}
int _mcrypt( CBC_BUFFER* buf, void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{
word32 *fplain = plaintext;
word32 *plain;
int i, j;
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
for (j = 0; j < len / blocksize; j++) {
plain = &fplain[j * blocksize / sizeof(word32)];
for (i = 0; i < blocksize / sizeof(word32); i++) {
plain[i] ^= buf->previous_ciphertext[i];
}
_mcrypt_block_encrypt(akey, plain);
/* Copy the ciphertext to prev_ciphertext */
memcpy(buf->previous_ciphertext, plain, blocksize);
}
if (j==0 && len!=0) return -1;
return 0;
}
int _mdecrypt( CBC_BUFFER* buf, void *ciphertext, int len, int blocksize,void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{
word32 *cipher;
word32 *fcipher = ciphertext;
int i, j;
void (*_mcrypt_block_decrypt) (void *, void *);
_mcrypt_block_decrypt = func2;
for (j = 0; j < len / blocksize; j++) {
cipher = &fcipher[j * blocksize / sizeof(word32)];
memcpy(buf->previous_cipher, cipher, blocksize);
_mcrypt_block_decrypt(akey, cipher);
for (i = 0; i < blocksize / sizeof(word32); i++) {
cipher[i] ^= buf->previous_ciphertext[i];
}
/* Copy the ciphertext to prev_cipher */
memcpy(buf->previous_ciphertext, buf->previous_cipher, blocksize);
}
if (j==0 && len!=0) return -1;
return 0;
}
int _has_iv() { return 1; }
int _is_block_mode() { return 1; }
int _is_block_algorithm_mode() { return 1; }
const char *_mcrypt_get_modes_name() { return "CBC";}
int _mcrypt_mode_get_size () {return sizeof(CBC_BUFFER);}
word32 _mcrypt_mode_version() {
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,316 @@
/* Copyright (c) 1998, 1999 Thai Open Source Software Center Ltd
See the file COPYING for copying permission.
*/
#ifndef XmlTok_INCLUDED
#define XmlTok_INCLUDED 1
#ifdef __cplusplus
extern "C" {
#endif
/* The following token may be returned by XmlContentTok */
#define XML_TOK_TRAILING_RSQB -5 /* ] or ]] at the end of the scan; might be
start of illegal ]]> sequence */
/* The following tokens may be returned by both XmlPrologTok and
XmlContentTok.
*/
#define XML_TOK_NONE -4 /* The string to be scanned is empty */
#define XML_TOK_TRAILING_CR -3 /* A CR at the end of the scan;
might be part of CRLF sequence */
#define XML_TOK_PARTIAL_CHAR -2 /* only part of a multibyte sequence */
#define XML_TOK_PARTIAL -1 /* only part of a token */
#define XML_TOK_INVALID 0
/* The following tokens are returned by XmlContentTok; some are also
returned by XmlAttributeValueTok, XmlEntityTok, XmlCdataSectionTok.
*/
#define XML_TOK_START_TAG_WITH_ATTS 1
#define XML_TOK_START_TAG_NO_ATTS 2
#define XML_TOK_EMPTY_ELEMENT_WITH_ATTS 3 /* empty element tag <e/> */
#define XML_TOK_EMPTY_ELEMENT_NO_ATTS 4
#define XML_TOK_END_TAG 5
#define XML_TOK_DATA_CHARS 6
#define XML_TOK_DATA_NEWLINE 7
#define XML_TOK_CDATA_SECT_OPEN 8
#define XML_TOK_ENTITY_REF 9
#define XML_TOK_CHAR_REF 10 /* numeric character reference */
/* The following tokens may be returned by both XmlPrologTok and
XmlContentTok.
*/
#define XML_TOK_PI 11 /* processing instruction */
#define XML_TOK_XML_DECL 12 /* XML decl or text decl */
#define XML_TOK_COMMENT 13
#define XML_TOK_BOM 14 /* Byte order mark */
/* The following tokens are returned only by XmlPrologTok */
#define XML_TOK_PROLOG_S 15
#define XML_TOK_DECL_OPEN 16 /* <!foo */
#define XML_TOK_DECL_CLOSE 17 /* > */
#define XML_TOK_NAME 18
#define XML_TOK_NMTOKEN 19
#define XML_TOK_POUND_NAME 20 /* #name */
#define XML_TOK_OR 21 /* | */
#define XML_TOK_PERCENT 22
#define XML_TOK_OPEN_PAREN 23
#define XML_TOK_CLOSE_PAREN 24
#define XML_TOK_OPEN_BRACKET 25
#define XML_TOK_CLOSE_BRACKET 26
#define XML_TOK_LITERAL 27
#define XML_TOK_PARAM_ENTITY_REF 28
#define XML_TOK_INSTANCE_START 29
/* The following occur only in element type declarations */
#define XML_TOK_NAME_QUESTION 30 /* name? */
#define XML_TOK_NAME_ASTERISK 31 /* name* */
#define XML_TOK_NAME_PLUS 32 /* name+ */
#define XML_TOK_COND_SECT_OPEN 33 /* <![ */
#define XML_TOK_COND_SECT_CLOSE 34 /* ]]> */
#define XML_TOK_CLOSE_PAREN_QUESTION 35 /* )? */
#define XML_TOK_CLOSE_PAREN_ASTERISK 36 /* )* */
#define XML_TOK_CLOSE_PAREN_PLUS 37 /* )+ */
#define XML_TOK_COMMA 38
/* The following token is returned only by XmlAttributeValueTok */
#define XML_TOK_ATTRIBUTE_VALUE_S 39
/* The following token is returned only by XmlCdataSectionTok */
#define XML_TOK_CDATA_SECT_CLOSE 40
/* With namespace processing this is returned by XmlPrologTok for a
name with a colon.
*/
#define XML_TOK_PREFIXED_NAME 41
#ifdef XML_DTD
#define XML_TOK_IGNORE_SECT 42
#endif /* XML_DTD */
#ifdef XML_DTD
#define XML_N_STATES 4
#else /* not XML_DTD */
#define XML_N_STATES 3
#endif /* not XML_DTD */
#define XML_PROLOG_STATE 0
#define XML_CONTENT_STATE 1
#define XML_CDATA_SECTION_STATE 2
#ifdef XML_DTD
#define XML_IGNORE_SECTION_STATE 3
#endif /* XML_DTD */
#define XML_N_LITERAL_TYPES 2
#define XML_ATTRIBUTE_VALUE_LITERAL 0
#define XML_ENTITY_VALUE_LITERAL 1
/* The size of the buffer passed to XmlUtf8Encode must be at least this. */
#define XML_UTF8_ENCODE_MAX 4
/* The size of the buffer passed to XmlUtf16Encode must be at least this. */
#define XML_UTF16_ENCODE_MAX 2
typedef struct position {
/* first line and first column are 0 not 1 */
unsigned long lineNumber;
unsigned long columnNumber;
} POSITION;
typedef struct {
const char *name;
const char *valuePtr;
const char *valueEnd;
char normalized;
} ATTRIBUTE;
struct encoding;
typedef struct encoding ENCODING;
typedef int (PTRCALL *SCANNER)(const ENCODING *,
const char *,
const char *,
const char **);
struct encoding {
SCANNER scanners[XML_N_STATES];
SCANNER literalScanners[XML_N_LITERAL_TYPES];
int (PTRCALL *sameName)(const ENCODING *,
const char *,
const char *);
int (PTRCALL *nameMatchesAscii)(const ENCODING *,
const char *,
const char *,
const char *);
int (PTRFASTCALL *nameLength)(const ENCODING *, const char *);
const char *(PTRFASTCALL *skipS)(const ENCODING *, const char *);
int (PTRCALL *getAtts)(const ENCODING *enc,
const char *ptr,
int attsMax,
ATTRIBUTE *atts);
int (PTRFASTCALL *charRefNumber)(const ENCODING *enc, const char *ptr);
int (PTRCALL *predefinedEntityName)(const ENCODING *,
const char *,
const char *);
void (PTRCALL *updatePosition)(const ENCODING *,
const char *ptr,
const char *end,
POSITION *);
int (PTRCALL *isPublicId)(const ENCODING *enc,
const char *ptr,
const char *end,
const char **badPtr);
void (PTRCALL *utf8Convert)(const ENCODING *enc,
const char **fromP,
const char *fromLim,
char **toP,
const char *toLim);
void (PTRCALL *utf16Convert)(const ENCODING *enc,
const char **fromP,
const char *fromLim,
unsigned short **toP,
const unsigned short *toLim);
int minBytesPerChar;
char isUtf8;
char isUtf16;
};
/* Scan the string starting at ptr until the end of the next complete
token, but do not scan past eptr. Return an integer giving the
type of token.
Return XML_TOK_NONE when ptr == eptr; nextTokPtr will not be set.
Return XML_TOK_PARTIAL when the string does not contain a complete
token; nextTokPtr will not be set.
Return XML_TOK_INVALID when the string does not start a valid
token; nextTokPtr will be set to point to the character which made
the token invalid.
Otherwise the string starts with a valid token; nextTokPtr will be
set to point to the character following the end of that token.
Each data character counts as a single token, but adjacent data
characters may be returned together. Similarly for characters in
the prolog outside literals, comments and processing instructions.
*/
#define XmlTok(enc, state, ptr, end, nextTokPtr) \
(((enc)->scanners[state])(enc, ptr, end, nextTokPtr))
#define XmlPrologTok(enc, ptr, end, nextTokPtr) \
XmlTok(enc, XML_PROLOG_STATE, ptr, end, nextTokPtr)
#define XmlContentTok(enc, ptr, end, nextTokPtr) \
XmlTok(enc, XML_CONTENT_STATE, ptr, end, nextTokPtr)
#define XmlCdataSectionTok(enc, ptr, end, nextTokPtr) \
XmlTok(enc, XML_CDATA_SECTION_STATE, ptr, end, nextTokPtr)
#ifdef XML_DTD
#define XmlIgnoreSectionTok(enc, ptr, end, nextTokPtr) \
XmlTok(enc, XML_IGNORE_SECTION_STATE, ptr, end, nextTokPtr)
#endif /* XML_DTD */
/* This is used for performing a 2nd-level tokenization on the content
of a literal that has already been returned by XmlTok.
*/
#define XmlLiteralTok(enc, literalType, ptr, end, nextTokPtr) \
(((enc)->literalScanners[literalType])(enc, ptr, end, nextTokPtr))
#define XmlAttributeValueTok(enc, ptr, end, nextTokPtr) \
XmlLiteralTok(enc, XML_ATTRIBUTE_VALUE_LITERAL, ptr, end, nextTokPtr)
#define XmlEntityValueTok(enc, ptr, end, nextTokPtr) \
XmlLiteralTok(enc, XML_ENTITY_VALUE_LITERAL, ptr, end, nextTokPtr)
#define XmlSameName(enc, ptr1, ptr2) (((enc)->sameName)(enc, ptr1, ptr2))
#define XmlNameMatchesAscii(enc, ptr1, end1, ptr2) \
(((enc)->nameMatchesAscii)(enc, ptr1, end1, ptr2))
#define XmlNameLength(enc, ptr) \
(((enc)->nameLength)(enc, ptr))
#define XmlSkipS(enc, ptr) \
(((enc)->skipS)(enc, ptr))
#define XmlGetAttributes(enc, ptr, attsMax, atts) \
(((enc)->getAtts)(enc, ptr, attsMax, atts))
#define XmlCharRefNumber(enc, ptr) \
(((enc)->charRefNumber)(enc, ptr))
#define XmlPredefinedEntityName(enc, ptr, end) \
(((enc)->predefinedEntityName)(enc, ptr, end))
#define XmlUpdatePosition(enc, ptr, end, pos) \
(((enc)->updatePosition)(enc, ptr, end, pos))
#define XmlIsPublicId(enc, ptr, end, badPtr) \
(((enc)->isPublicId)(enc, ptr, end, badPtr))
#define XmlUtf8Convert(enc, fromP, fromLim, toP, toLim) \
(((enc)->utf8Convert)(enc, fromP, fromLim, toP, toLim))
#define XmlUtf16Convert(enc, fromP, fromLim, toP, toLim) \
(((enc)->utf16Convert)(enc, fromP, fromLim, toP, toLim))
typedef struct {
ENCODING initEnc;
const ENCODING **encPtr;
} INIT_ENCODING;
int XmlParseXmlDecl(int isGeneralTextEntity,
const ENCODING *enc,
const char *ptr,
const char *end,
const char **badPtr,
const char **versionPtr,
const char **versionEndPtr,
const char **encodingNamePtr,
const ENCODING **namedEncodingPtr,
int *standalonePtr);
int XmlInitEncoding(INIT_ENCODING *, const ENCODING **, const char *name);
const ENCODING *XmlGetUtf8InternalEncoding(void);
const ENCODING *XmlGetUtf16InternalEncoding(void);
int FASTCALL XmlUtf8Encode(int charNumber, char *buf);
int FASTCALL XmlUtf16Encode(int charNumber, unsigned short *buf);
int XmlSizeOfUnknownEncoding(void);
typedef int (XMLCALL *CONVERTER) (void *userData, const char *p);
ENCODING *
XmlInitUnknownEncoding(void *mem,
int *table,
CONVERTER convert,
void *userData);
int XmlParseXmlDeclNS(int isGeneralTextEntity,
const ENCODING *enc,
const char *ptr,
const char *end,
const char **badPtr,
const char **versionPtr,
const char **versionEndPtr,
const char **encodingNamePtr,
const ENCODING **namedEncodingPtr,
int *standalonePtr);
int XmlInitEncodingNS(INIT_ENCODING *, const ENCODING **, const char *name);
const ENCODING *XmlGetUtf8InternalEncodingNS(void);
const ENCODING *XmlGetUtf16InternalEncodingNS(void);
ENCODING *
XmlInitUnknownEncodingNS(void *mem,
int *table,
CONVERTER convert,
void *userData);
#ifdef __cplusplus
}
#endif
#endif /* not XmlTok_INCLUDED */
@@ -0,0 +1,37 @@
/*
Internationalization of neon
Copyright (C) 1999-2002, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NEON_I18N_H
#define NEON_I18N_H
#undef _
#ifdef ENABLE_NLS
#include <libintl.h>
#define _(str) gettext(str)
#else
#define _(str) (str)
#endif /* ENABLE_NLS */
#define N_(str) (str)
/* Initialize i18n in neon */
void neon_i18n_init(void);
#endif /* NEON_I18N_H */
@@ -0,0 +1,56 @@
/*
Access control
Copyright (C) 2001, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_ACL_H
#define NE_ACL_H
#include "ne_session.h"
BEGIN_NEON_DECLS
typedef struct
{
enum {
ne_acl_href,
ne_acl_property,
ne_acl_all
} apply;
enum {
ne_acl_grant,
ne_acl_deny
} type;
char *principal;
int read;
int read_acl;
int write;
int write_acl;
int read_cuprivset;
} ne_acl_entry;
/* Set the ACL for the given resource to the list of ACL entries. */
int ne_acl_set(ne_session *sess, const char *uri,
ne_acl_entry entries[], int numentries);
END_NEON_DECLS
#endif /* NE_ACL_H */
@@ -0,0 +1,19 @@
// 컴퓨터에서 Microsoft Visual C++를 사용하여 생성한 IDispatch 래퍼 클래스입니다.
// 참고: 이 파일의 내용을 수정하지 마십시오. Microsoft Visual C++에서
// 이 클래스를 다시 생성할 때 수정한 내용을 덮어씁니다.
#include "stdafx.h"
#include "ptxshtree.h"
/////////////////////////////////////////////////////////////////////////////
// CPTxShTree
IMPLEMENT_DYNCREATE(CPTxShTree, CTreeCtrl)
/////////////////////////////////////////////////////////////////////////////
// CPTxShTree 속성입니다.
/////////////////////////////////////////////////////////////////////////////
// CPTxShTree 작업입니다.
@@ -0,0 +1,47 @@
#define rotl32(x,n) (((x) << ((word32)(n))) | ((x) >> (32 - (word32)(n))))
#define rotr32(x,n) (((x) >> ((word32)(n))) | ((x) << (32 - (word32)(n))))
#define rotl16(x,n) (((x) << ((word16)(n))) | ((x) >> (16 - (word16)(n))))
#define rotr16(x,n) (((x) >> ((word16)(n))) | ((x) << (16 - (word16)(n))))
/* Use hardware rotations.. when available */
#ifdef swap32
# define byteswap32(x) swap32(x)
#else
# ifdef swap_32
# define byteswap32(x) swap_32(x)
# else
# ifdef bswap_32
# define byteswap32(x) bswap_32(x)
# else
# define byteswap32(x) ((rotl32(x, 8) & 0x00ff00ff) | (rotr32(x, 8) & 0xff00ff00))
# endif
# endif
#endif
#ifdef swap16
# define byteswap16(x) swap16(x)
#else
# ifdef swap_16
# define byteswap16(x) swap_16(x)
# else
# ifdef bswap_16
# define byteswap16(x) bswap_16(x)
# else
# define byteswap16(x) ((rotl16(x, 8) & 0x00ff) | (rotr16(x, 8) & 0xff00))
# endif
# endif
#endif
//inline
static void memxor(unsigned char *o1, unsigned char *o2, int length)
{
int i;
for (i = 0; i < length; i++) {
o1[i] ^= o2[i];
}
return;
}
#define Bzero(x, y) memset(x, 0, y)
@@ -0,0 +1,285 @@
// DSLog.cpp: implementation of the Log class.
//
#include "stdafx.h"
#include "DSLog.h"
const DWORD CDSLog::modeDebug = 0x01;
const DWORD CDSLog::modeFile = 0x02;
const DWORD CDSLog::modeConsole = 0x04;
const CHAR CDSLog::m_szExt[] = ".log";
const static int LINE_BUFFER_SIZE = 1024;
// Create a new dslog object.
// nMode - specifies where output should go, using combination
// of flags above.
// nFlag - the flag
// pszFileName - if flag CDSLog::modeFile is specified in the type,
// a filename must be specified here.
// bAppend - if logging to a file, whether or not to append to any
// existing log.
// bDaily - if logging to a file, whether or not to replace log every day.
CDSLog::CDSLog(DWORD dwMode, DWORD dwLevel, LPSTR pszFileName, BOOL bAppend, BOOL bDaily)
{
m_nLastLogTime = 0;
m_szLastLogDay[0] = 0;
m_pszFileName = NULL;
m_hFile = NULL;
m_pszEventSource = NULL;
m_bDebugMode = false;
m_bFileMode = false;
m_bConsoleMode = false;
m_bAppend = false;
m_bDaily = false;
m_dwLevel = dwLevel;
SetFile(pszFileName, bAppend, bDaily);
SetMode(dwMode);
}
CDSLog::~CDSLog()
{
if (m_pszFileName)
free(m_pszFileName);
if (m_pszEventSource)
free(m_pszEventSource);
CloseFile();
}
void CDSLog::EventLog(WORD wType, LPSTR pszFormat, ...)
{
va_list val;
va_start(val, pszFormat);
if (m_pszEventSource) {
HANDLE hEventSource;
CHAR szBuf[256];
LPSTR ppszBuf[2];
vsprintf(szBuf, pszFormat, val);
hEventSource = RegisterEventSource(NULL, m_pszEventSource);
ppszBuf[0] = m_pszEventSource;
ppszBuf[1] = szBuf;
if (hEventSource) {
ReportEvent(
hEventSource, // handle of event source
wType, // event type
0, // event category
0, // event ID
NULL, // current user's SID
2, // strings in 'strings'
0, // no bytes of raw data
(const char **)ppszBuf, // array of error strings
NULL); // no raw data
DeregisterEventSource(hEventSource);
}
}
if (DSLL_STATE & m_dwLevel)
_Print(pszFormat, val);
va_end(val);
}
void CDSLog::EventLogError(LPSTR pszMsg)
{
DWORD dwError = GetLastError();
TCHAR szBuf[256];
wsprintf(szBuf, "%s, error code : %d", pszMsg, dwError);
EventLog(EVENTLOG_ERROR_TYPE, szBuf);
}
void CDSLog::EventLogWSAError(LPSTR pszMsg)
{
// DWORD dwError = WSAGetLastError();
// TCHAR szBuf[256];
// wsprintf(szBuf, "%s, WSA error code : %d", pszMsg, dwError);
// EventLog(EVENTLOG_ERROR_TYPE, szBuf);
}
void CDSLog::SetMode(DWORD dwMode)
{
m_bDebugMode = dwMode & modeDebug;
if (dwMode & modeFile) {
if (!m_bFileMode)
OpenFile();
}
else {
CloseFile();
m_bFileMode = false;
}
if (dwMode & modeConsole) {
if (!m_bConsoleMode)
AllocConsole();
m_bConsoleMode = true;
}
else {
m_bConsoleMode = false;
}
}
void CDSLog::SetLevel(DWORD dwLevel)
{
m_dwLevel = dwLevel;
}
void CDSLog::SetFile(LPSTR pszFileName, BOOL bAppend, BOOL bDaily)
{
CloseFile();
if (m_pszFileName)
free(m_pszFileName);
if (pszFileName)
m_pszFileName = strdup(pszFileName);
m_bAppend = bAppend;
m_bDaily = bDaily;
if (m_bFileMode)
OpenFile();
}
void CDSLog::SetEventSource(LPSTR pszEventSource)
{
if (m_pszEventSource)
free(m_pszEventSource);
if (pszEventSource)
m_pszEventSource = strdup(pszEventSource);
}
void CDSLog::_Print(LPSTR pszFormat, va_list val)
{
UINT64 nCurrentTime = _time64(0);
if (m_bFileMode && m_bDaily && m_hFile) {
CHAR szDate[7];
MakeSurfix(szDate);
if (szDate[6] != m_szLastLogDay[6] || szDate[5] != m_szLastLogDay[5]) {
CloseFile();
OpenFile();
}
}
if (nCurrentTime != m_nLastLogTime) {
m_nLastLogTime = nCurrentTime;
_PrintLine(_ctime64((__time64_t*)&m_nLastLogTime));
}
// - Write the log message
TCHAR szLine[LINE_BUFFER_SIZE];
vsprintf(szLine, pszFormat, val);
_PrintLine(szLine);
}
inline void CDSLog::_PrintLine(LPSTR pszLine)
{
if (m_bDebugMode)
OutputDebugString(pszLine);
DWORD dwWritten;
if (m_bConsoleMode)
WriteConsole(GetStdHandle(STD_OUTPUT_HANDLE), pszLine, (DWORD)strlen(pszLine), &dwWritten, NULL);
if (m_bFileMode && m_hFile)
WriteFile(m_hFile, pszLine, (DWORD)strlen(pszLine), &dwWritten, NULL);
}
void CDSLog::OpenFile()
{
if (!m_pszFileName) {
m_bDebugMode = true;
m_bFileMode = false;
Print(0, "Error opening log file\n");
return;
}
char szFileName[MAX_PATH];
strcpy(szFileName, m_pszFileName);
if (m_bDaily) {
CHAR szDate[7];
MakeSurfix(szDate);
strcat(szFileName, szDate);
strcpy(m_szLastLogDay, szDate);
}
strcat(szFileName, m_szExt);
m_bFileMode = true;
m_hFile = CreateFile(szFileName, GENERIC_WRITE, FILE_SHARE_READ, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if (m_hFile == INVALID_HANDLE_VALUE) {
m_bDebugMode = true;
m_bFileMode = false;
Print(0, "Error opening log file %s\n", szFileName);
return;
}
if (m_bAppend)
SetFilePointer(m_hFile, 0, NULL, FILE_END);
else
SetEndOfFile(m_hFile);
}
void CDSLog::CloseFile()
{
if (m_hFile) {
CloseHandle(m_hFile);
m_hFile = NULL;
}
}
void CDSLog::MakeSurfix(CHAR *pszBuf)
{
WORD wMonth, wDay, wYear;
SYSTEMTIME st;
GetLocalTime(&st);
wYear = st.wYear % 100;
wMonth = st.wMonth;
wDay = st.wDay;
pszBuf[0] = (CHAR)(wYear / 10 + '0');
pszBuf[1] = (CHAR)(wYear % 10 + '0');
pszBuf[2] = (CHAR)(wMonth / 10 + '0');
pszBuf[3] = (CHAR)(wMonth % 10 + '0');
pszBuf[4] = (CHAR)(wDay / 10 + '0');
pszBuf[5] = (CHAR)(wDay % 10 + '0');
pszBuf[6] = 0;
}
@@ -0,0 +1,351 @@
/********************************************************************\
* *
* C specification of the threeway block cipher *
* *
* found in ftp://ftp.funet.fi/pub/crypt/ *
\********************************************************************/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: 3-way.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "3-way.h"
#define STRT_E 0x0b0b /* round constant of first encryption round */
#define STRT_D 0xb1b1 /* round constant of first decryption round */
#define NMBR 11 /* number of rounds is 11 */
#define _mcrypt_set_key threeway_LTX__mcrypt_set_key
#define _mcrypt_encrypt threeway_LTX__mcrypt_encrypt
#define _mcrypt_decrypt threeway_LTX__mcrypt_decrypt
#define _mcrypt_get_size threeway_LTX__mcrypt_get_size
#define _mcrypt_get_block_size threeway_LTX__mcrypt_get_block_size
#define _is_block_algorithm threeway_LTX__is_block_algorithm
#define _mcrypt_get_key_size threeway_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes threeway_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name threeway_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test threeway_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version threeway_LTX__mcrypt_algorithm_version
WIN32DLL_DEFINE
int _mcrypt_set_key(word32 * k, word32 * input_key, int len)
{
k[0] = 0;
k[2] = 0;
k[1] = 0;
memmove(k, input_key, len);
return 0;
}
void mu(word32 * a)
{ /* inverts the order of the bits of a */
int i;
word32 b[3];
b[0] = b[1] = b[2] = 0;
for (i = 0; i < 32; i++) {
b[0] <<= 1;
b[1] <<= 1;
b[2] <<= 1;
if (a[0] & 1)
b[2] |= 1;
if (a[1] & 1)
b[1] |= 1;
if (a[2] & 1)
b[0] |= 1;
a[0] >>= 1;
a[1] >>= 1;
a[2] >>= 1;
}
a[0] = b[0];
a[1] = b[1];
a[2] = b[2];
}
void gamma(word32 * a)
{ /* the nonlinear step */
word32 b[3];
b[0] = a[0] ^ (a[1] | (~a[2]));
b[1] = a[1] ^ (a[2] | (~a[0]));
b[2] = a[2] ^ (a[0] | (~a[1]));
a[0] = b[0];
a[1] = b[1];
a[2] = b[2];
}
void theta(word32 * a)
{ /* the linear step */
word32 b[3];
b[0] =
a[0] ^ (a[0] >> 16) ^ (a[1] << 16) ^ (a[1] >> 16) ^ (a[2] <<
16) ^
(a[1] >> 24) ^ (a[2] << 8) ^ (a[2] >> 8) ^ (a[0] << 24) ^ (a[2]
>>
16)
^ (a[0] << 16) ^ (a[2] >> 24) ^ (a[0] << 8);
b[1] =
a[1] ^ (a[1] >> 16) ^ (a[2] << 16) ^ (a[2] >> 16) ^ (a[0] <<
16) ^
(a[2] >> 24) ^ (a[0] << 8) ^ (a[0] >> 8) ^ (a[1] << 24) ^ (a[0]
>>
16)
^ (a[1] << 16) ^ (a[0] >> 24) ^ (a[1] << 8);
b[2] =
a[2] ^ (a[2] >> 16) ^ (a[0] << 16) ^ (a[0] >> 16) ^ (a[1] <<
16) ^
(a[0] >> 24) ^ (a[1] << 8) ^ (a[1] >> 8) ^ (a[2] << 24) ^ (a[1]
>>
16)
^ (a[2] << 16) ^ (a[1] >> 24) ^ (a[2] << 8);
a[0] = b[0];
a[1] = b[1];
a[2] = b[2];
}
void pi_1(word32 * a)
{
a[0] = (a[0] >> 10) ^ (a[0] << 22);
a[2] = (a[2] << 1) ^ (a[2] >> 31);
}
void pi_2(word32 * a)
{
a[0] = (a[0] << 1) ^ (a[0] >> 31);
a[2] = (a[2] >> 10) ^ (a[2] << 22);
}
void rho(word32 * a)
{ /* the round function */
theta(a);
pi_1(a);
gamma(a);
pi_2(a);
}
void rndcon_gen(word32 strt, word32 * rtab)
{ /* generates the round constants */
int i;
for (i = 0; i <= NMBR; i++) {
rtab[i] = strt;
strt <<= 1;
if (strt & 0x10000)
strt ^= 0x11011;
}
}
WIN32DLL_DEFINE void _mcrypt_encrypt(word32 * tk, word32 * ta)
{
int i;
word32 rcon[NMBR + 1];
word32 a[3], k[3];
/* Added to make it compatible with bigendian machines
* --nikos
*/
#ifndef WORDS_BIGENDIAN
a[0] = byteswap32(ta[0]);
a[1] = byteswap32(ta[1]);
a[2] = byteswap32(ta[2]);
k[0] = byteswap32(tk[0]);
k[1] = byteswap32(tk[1]);
k[2] = byteswap32(tk[2]);
#else
a[0] = ta[0];
a[1] = ta[1];
a[2] = ta[2];
k[0] = (tk[0]);
k[1] = (tk[1]);
k[2] = (tk[2]);
#endif
rndcon_gen(STRT_E, rcon);
for (i = 0; i < NMBR; i++) {
a[0] ^= k[0] ^ (rcon[i] << 16);
a[1] ^= k[1];
a[2] ^= k[2] ^ rcon[i];
rho(a);
}
a[0] ^= k[0] ^ (rcon[NMBR] << 16);
a[1] ^= k[1];
a[2] ^= k[2] ^ rcon[NMBR];
theta(a);
#ifndef WORDS_BIGENDIAN
ta[0] = byteswap32(a[0]);
ta[1] = byteswap32(a[1]);
ta[2] = byteswap32(a[2]);
#else
ta[0] = a[0];
ta[1] = a[1];
ta[2] = a[2];
#endif
}
WIN32DLL_DEFINE void _mcrypt_decrypt(word32 * k, word32 * ta)
{
int i;
word32 ki[3]; /* the `inverse' key */
word32 rcon[NMBR + 1]; /* the `inverse' round constants */
word32 a[3];
#ifndef WORDS_BIGENDIAN
a[0] = byteswap32(ta[0]);
a[1] = byteswap32(ta[1]);
a[2] = byteswap32(ta[2]);
ki[0] = byteswap32(k[0]);
ki[1] = byteswap32(k[1]);
ki[2] = byteswap32(k[2]);
#else
a[0] = ta[0];
a[1] = ta[1];
a[2] = ta[2];
ki[0] = k[0];
ki[1] = k[1];
ki[2] = k[2];
#endif
theta(ki);
mu(ki);
rndcon_gen(STRT_D, rcon);
mu(a);
for (i = 0; i < NMBR; i++) {
a[0] ^= ki[0] ^ (rcon[i] << 16);
a[1] ^= ki[1];
a[2] ^= ki[2] ^ rcon[i];
rho(a);
}
a[0] ^= ki[0] ^ (rcon[NMBR] << 16);
a[1] ^= ki[1];
a[2] ^= ki[2] ^ rcon[NMBR];
theta(a);
mu(a);
#ifndef WORDS_BIGENDIAN
ta[0] = byteswap32(a[0]);
ta[1] = byteswap32(a[1]);
ta[2] = byteswap32(a[2]);
#else
ta[0] = a[0];
ta[1] = a[1];
ta[2] = a[2];
#endif
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return 3 * sizeof(word32);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 12;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 12;
}
static const int key_sizes[] = { 12 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE const char *_mcrypt_get_algorithms_name()
{
return "3-WAY";
}
#define CIPHER "46823287358d68f6e034ca62"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL)
return -1;
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,89 @@
#ifndef LIBDEFS_H
#define LIBDEFS_H
#include <libdefs.h>
#endif
/* Local Defines */
#ifndef lt_ptr
/* older version of libltdl */
# define lt_ptr lt_ptr_t
#endif
typedef struct {
char* name;
lt_ptr address;
} mcrypt_preloaded;
typedef struct {
lt_dlhandle handle;
char name[64];
} mcrypt_dlhandle;
#define MCRYPT_INTERNAL_HANDLER (void*)-1
typedef struct {
mcrypt_dlhandle algorithm_handle;
mcrypt_dlhandle mode_handle;
/* Holds the algorithm's internal key */
byte *akey;
byte *abuf; /* holds the mode's internal buffers */
/* holds the key */
byte *keyword_given;
/* These were included to speed up encryption/decryption proccess, so
* there is not need for resolving symbols every time.
*/
lt_ptr m_encrypt;
lt_ptr m_decrypt;
lt_ptr a_encrypt;
lt_ptr a_decrypt;
lt_ptr a_block_size;
} CRYPT_STREAM;
typedef CRYPT_STREAM* MCRYPT;
#define MCRYPT_FAILED 0x0
int mcrypt_module_close(MCRYPT td);
/* frontends */
int end_mcrypt( MCRYPT td, void *buf);
int mcrypt_enc_get_size(MCRYPT td);
int mcrypt_mode_get_size(MCRYPT td);
int mcrypt_set_key(MCRYPT td, void *a, const void *, int c, const void *, int e);
int mcrypt_enc_get_block_size(MCRYPT td);
int __mcrypt_get_block_size(MCRYPT td);
int mcrypt_enc_get_algo_iv_size(MCRYPT td);
int mcrypt_enc_get_iv_size(MCRYPT td);
int mcrypt_enc_get_key_size(MCRYPT td);
int* mcrypt_enc_get_supported_key_sizes(MCRYPT td, int* out_size);
int mcrypt_enc_is_block_algorithm(MCRYPT td);
char *mcrypt_enc_get_algorithms_name(MCRYPT td);
int init_mcrypt(MCRYPT td, void*buf, const void *, int, const void *);
int mcrypt(MCRYPT td, void* buf, void *a, int b);
int mdecrypt(MCRYPT td, void* buf, void *a, int b);
char *mcrypt_enc_get_modes_name(MCRYPT td);
int mcrypt_enc_is_block_mode(MCRYPT td);
int mcrypt_enc_mode_has_iv(MCRYPT td);
int mcrypt_enc_is_block_algorithm_mode(MCRYPT td);
int mcrypt_module_algorithm_version(const char *algorithm, const char *a_directory);
int mcrypt_module_mode_version(const char *mode, const char *m_directory);
int mcrypt_get_size(MCRYPT td);
#define MCRYPT_UNKNOWN_ERROR -1
#define MCRYPT_ALGORITHM_MODE_INCOMPATIBILITY -2
#define MCRYPT_KEY_LEN_ERROR -3
#define MCRYPT_MEMORY_ALLOCATION_ERROR -4
#define MCRYPT_UNKNOWN_MODE -5
#define MCRYPT_UNKNOWN_ALGORITHM -6
lt_ptr mcrypt_dlsym( mcrypt_dlhandle, char* str);
void mcrypt_dlclose( mcrypt_dlhandle mod);
lt_ptr _mcrypt_search_symlist_lib(const char* name);
lt_ptr _mcrypt_search_symlist_sym(mcrypt_dlhandle handle, const char* _name);
@@ -0,0 +1,27 @@
/*
* $Id: cast-128.h,v 1.1 2007/07/19 06:11:48 pizon Exp $
*
* CAST-128 in C
* Written by Steve Reid <sreid@sea-to-sky.net>
* 100% Public Domain - no warranty
* Released 1997.10.11
*/
#ifndef _CAST_H_INCLUDED
#define _CAST_H_INCLUDED
#define CAST_MIN_KEYSIZE 5
#define CAST_MAX_KEYSIZE 16
#define CAST_BLOCKSIZE 8
#define CAST_SMALL_KEY 10
#define CAST_SMALL_ROUNDS 12
#define CAST_FULL_ROUNDS 16
typedef struct cast_key {
word32 xkey[32]; /* Key, after expansion */
unsigned rounds; /* Number of rounds to use, 12 or 16 */
} CAST_KEY;
#endif /* ifndef _CAST_H_INCLUDED */
@@ -0,0 +1,7 @@
typedef struct arcfour_key
{
byte state[256];
byte i;
byte j;
} arcfour_key;
@@ -0,0 +1,167 @@
/*
SSL/TLS abstraction layer for neon
Copyright (C) 2003-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
/* ne_ssl.h defines an interface for loading and accessing the
* properties of SSL certificates. */
#ifndef NE_SSL_H
#define NE_SSL_H 1
#include "ne_defs.h"
BEGIN_NEON_DECLS
/* A "distinguished name"; a unique name for some entity. */
typedef struct ne_ssl_dname_s ne_ssl_dname;
/* Returns a single-line string representation of a distinguished
* name, intended to be human-readable (e.g. "Acme Ltd., Norfolk,
* GB"). Return value is a UTF-8-encoded malloc-allocated string and
* must be free'd by the caller. */
char *ne_ssl_readable_dname(const ne_ssl_dname *dn);
/* Returns zero if 'dn1' and 'dn2' refer to same name, or non-zero if
* they are different. */
int ne_ssl_dname_cmp(const ne_ssl_dname *dn1, const ne_ssl_dname *dn2);
/* An SSL certificate. */
typedef struct ne_ssl_certificate_s ne_ssl_certificate;
/* Read a certificate from a file in PEM format; returns NULL if the
* certificate could not be parsed. */
ne_ssl_certificate *ne_ssl_cert_read(const char *filename);
/* Write a certificate to a file in PEM format; returns non-zero if
* the certificate could not be written. */
int ne_ssl_cert_write(const ne_ssl_certificate *cert, const char *filename);
/* Export a certificate to a base64-encoded, NUL-terminated string.
* The returned string is malloc-allocated and must be free()d by the
* caller. */
char *ne_ssl_cert_export(const ne_ssl_certificate *cert);
/* Import a certificate from a base64-encoded string as returned by
* ne_ssl_cert_export(). Returns a certificate object or NULL if
* 'data' was not valid. */
ne_ssl_certificate *ne_ssl_cert_import(const char *data);
/* Returns the identity of the certificate, or NULL if none is given.
* For a server certificate this will be the hostname of the server to
* whom the cert was issued. String returned is UTF-8-encoded. */
const char *ne_ssl_cert_identity(const ne_ssl_certificate *cert);
/* Return the certificate of the entity which signed certificate
* 'cert'. Returns NULL if 'cert' is self-signed or the issuer
* certificate is not available. */
const ne_ssl_certificate *ne_ssl_cert_signedby(const ne_ssl_certificate *cert);
/* Returns the distinguished name of the certificate issuer. */
const ne_ssl_dname *ne_ssl_cert_issuer(const ne_ssl_certificate *cert);
/* Returns the distinguished name of the certificate subject. */
const ne_ssl_dname *ne_ssl_cert_subject(const ne_ssl_certificate *cert);
#define NE_SSL_DIGESTLEN (60)
/* Calculate the certificate digest ("fingerprint") and format it as a
* NUL-terminated hex string in 'digest', of the form "aa:bb:...:ff".
* Returns zero on success or non-zero if there was an internal error
* whilst calculating the digest. 'digest' must be at least
* NE_SSL_DIGESTLEN bytes in length. */
int ne_ssl_cert_digest(const ne_ssl_certificate *cert, char *digest);
#define NE_SSL_VDATELEN (30)
/* Copy the validity dates into buffers 'from' and 'until' as
* NUL-terminated human-readable strings. The buffers must be at
* least NE_SSL_VDATELEN bytes in length. */
void ne_ssl_cert_validity(const ne_ssl_certificate *cert,
char *from, char *until);
/* Returns zero if 'c1' and 'c2' refer to the same certificate, or
* non-zero otherwise. */
int ne_ssl_cert_cmp(const ne_ssl_certificate *c1,
const ne_ssl_certificate *c2);
/* Deallocate memory associated with certificate. */
void ne_ssl_cert_free(ne_ssl_certificate *cert);
/* A client certificate (and private key). */
typedef struct ne_ssl_client_cert_s ne_ssl_client_cert;
/* Read a client certificate and private key from a PKCS12 file;
* returns NULL if the file could not be parsed. If the client cert
* is encrypted, it must be decrypted before use. */
ne_ssl_client_cert *ne_ssl_clicert_read(const char *filename);
/* Returns the "friendly name" given for the client cert, or NULL if
* none given. This can be called before or after the client cert has
* been decrypted. Returns a NUL-terminated, UTF-8-encoded string. */
const char *ne_ssl_clicert_name(const ne_ssl_client_cert *ccert);
/* Returns non-zero if client cert is encrypted. */
int ne_ssl_clicert_encrypted(const ne_ssl_client_cert *ccert);
/* Decrypt the encrypted client cert using given password. Returns
* non-zero on failure, in which case, the function can be called
* again with a different password. For a ccert on which _encrypted()
* returns 0, calling _decrypt results in undefined behaviour. */
int ne_ssl_clicert_decrypt(ne_ssl_client_cert *ccert, const char *password);
/* Return the actual certificate part of the client certificate (never
* returns NULL). */
const ne_ssl_certificate *ne_ssl_clicert_owner(const ne_ssl_client_cert *ccert);
/* Deallocate memory associated with a client certificate. */
void ne_ssl_clicert_free(ne_ssl_client_cert *ccert);
/* SSL context object. The interfaces to manipulate an SSL context
* are only needed when interfacing directly with ne_socket.h. */
typedef struct ne_ssl_context_s ne_ssl_context;
/* Context creation modes: */
#define NE_SSL_CTX_CLIENT (0) /* client context */
#define NE_SSL_CTX_SERVER (1) /* default server context */
#define NE_SSL_CTX_SERVERv2 (2) /* SSLv2-specific server context */
/* Create an SSL context. */
ne_ssl_context *ne_ssl_context_create(int mode);
/* Client mode: trust the given certificate 'cert' in context 'ctx'. */
void ne_ssl_context_trustcert(ne_ssl_context *ctx, const ne_ssl_certificate *cert);
/* Server mode: use given cert and key (filenames to PEM certificates). */
int ne_ssl_context_keypair(ne_ssl_context *ctx,
const char *cert, const char *key);
/* Server mode: set client cert verification options: required is non-zero if
* a client cert is required, if ca_names is non-NULL it is a filename containing
* a set of PEM certs from which CA names are sent in the ccert request. */
int ne_ssl_context_set_verify(ne_ssl_context *ctx, int required,
const char *ca_names, const char *verify_cas);
/* Destroy an SSL context. */
void ne_ssl_context_destroy(ne_ssl_context *ctx);
END_NEON_DECLS
#endif
@@ -0,0 +1,305 @@
//////////////////////////////////////////////////////////////////////
// PictureEx.cpp: implementation of the CPictureEx class.
//
// Picture displaying control with support for the following formats:
// GIF (including animated GIF87a and GIF89a), JPEG, BMP, WMF, ICO, CUR
//
// Written by Oleg Bykov (oleg_bykoff@rsdn.ru)
// Copyright (c) 2001
//
// To use CPictureEx, follow these steps:
// - place a static control on your dialog (either a text or a bitmap)
// - change its identifier to something else (e.g. IDC_MYPIC)
// - associate a CStatic with it using ClassWizard
// - in your dialog's header file replace CStatic with CPictureEx
// (don't forget to #include "PictureEx.h" and add
// PictureEx.h and PictureEx.cpp to your project)
// - call one of the overloaded CPictureEx::Load() functions somewhere
// (OnInitDialog is a good place to start)
// - if the preceding Load() succeeded call Draw()
//
// You can also add the control by defining a member variable of type
// CPictureEx, calling CPictureEx::Create (derived from CStatic), then
// CPictureEx::Load and CPictureEx::Draw.
//
// By default, the control initializes its background to COLOR_3DFACE
// (see CPictureEx::PrepareDC()). You can change the background by
// calling CPictureEx::SetBkColor(COLORREF) after CPictureEx::Load().
//
// I decided to leave in the class the functions to write separate frames from
// animated GIF to disk. If you want to use them, uncomment #define GIF_TRACING
// and an appropriate section in CPictureEx::Load(HGLOBAL, DWORD). These functions
// won't be compiled and linked to your project unless you uncomment #define GIF_TRACING,
// so you don't have to worry.
//
// Warning: this code hasn't been subject to a heavy testing, so
// use it on your own risk. The author accepts no liability for the
// possible damage caused by this code.
//
// Version 1.0 7 Aug 2001
// Initial release
//
// Version 1.1 6 Sept 2001
// ATL version of the class
//
// Version 1.2 14 Oct 2001
// - Fixed a problem with loading GIFs from resources
// in MFC-version of the class for multi-modules apps.
// Thanks to Ruben Avila-Carretero for finding this out.
//
// - Got rid of waitable timer in ThreadAnimation()
// Now CPictureEx[Wnd] works in Win95 too.
// Thanks to Alex Egiazarov and Wayne King for the idea.
//
// - Fixed a visual glitch of using SetBkColor.
// Thanks to Kwangjin Lee for finding this out.
//
// Version 1.3 10 Nov 2001
// - Fixed a DC leak. One DC leaked per each UnLoad()
// (forgot to put a ReleaseDC() in the end of
// CPictureExWnd::PrepareDC() function).
//
// - Now it is possible to set a clipping rectangle using
// CPictureEx[Wnd]::SetPaintRect(const LPRECT) function.
// The LPRECT parameter tells the class what portion of
// a picture should it display. If the clipping rect is
// not set, the whole picture is shown.
// Thanks to Fabrice Rodriguez for the idea.
//
// - Added support for Stop/Draw. Now you can Stop() an
// animated GIF, then Draw() it again, it will continue
// animation from the frame it was stopped on. You can
// also know if a GIF is currently playing with the
// IsPlaying() function.
//
// - Got rid of math.h and made m_bExitThread volatile.
// Thanks to Piotr Sawicki for the suggestion.
//
//////////////////////////////////////////////////////////////////////
#if !defined(AFX_PICTUREEX_H__0EFE5DE0_7B68_4DB7_8B34_5DC634948438__INCLUDED_)
#define AFX_PICTUREEX_H__0EFE5DE0_7B68_4DB7_8B34_5DC634948438__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#include <vector>
//#define GIF_TRACING // uncomment it if you want detailed TRACEs
class CPictureEx : public CStatic
{
public:
struct TFrame // structure that keeps a single frame info
{
IPicture *m_pPicture; // pointer to the interface used for drawing
SIZE m_frameSize;
SIZE m_frameOffset;
UINT m_nDelay; // delay (in 1/100s of a second)
UINT m_nDisposal; // disposal method
};
#pragma pack(1) // turn byte alignment on
enum GIFBlockTypes
{
BLOCK_UNKNOWN,
BLOCK_APPEXT,
BLOCK_COMMEXT,
BLOCK_CONTROLEXT,
BLOCK_PLAINTEXT,
BLOCK_IMAGE,
BLOCK_TRAILER
};
enum ControlExtValues // graphic control extension packed field values
{
GCX_PACKED_DISPOSAL, // disposal method
GCX_PACKED_USERINPUT,
GCX_PACKED_TRANSPCOLOR
};
enum LSDPackedValues // logical screen descriptor packed field values
{
LSD_PACKED_GLOBALCT,
LSD_PACKED_CRESOLUTION,
LSD_PACKED_SORT,
LSD_PACKED_GLOBALCTSIZE
};
enum IDPackedValues // image descriptor packed field values
{
ID_PACKED_LOCALCT,
ID_PACKED_INTERLACE,
ID_PACKED_SORT,
ID_PACKED_LOCALCTSIZE
};
struct TGIFHeader // GIF header
{
char m_cSignature[3]; // Signature - Identifies the GIF Data Stream
// This field contains the fixed value 'GIF'
char m_cVersion[3]; // Version number. May be one of the following:
// "87a" or "89a"
};
struct TGIFLSDescriptor // Logical Screen Descriptor
{
WORD m_wWidth; // 2 bytes. Logical screen width
WORD m_wHeight; // 2 bytes. Logical screen height
unsigned char m_cPacked; // packed field
unsigned char m_cBkIndex; // 1 byte. Background color index
unsigned char m_cPixelAspect; // 1 byte. Pixel aspect ratio
inline int GetPackedValue(enum LSDPackedValues Value);
};
struct TGIFAppExtension // application extension block
{
unsigned char m_cExtIntroducer; // extension introducer (0x21)
unsigned char m_cExtLabel; // app. extension label (0xFF)
unsigned char m_cBlockSize; // fixed value of 11
char m_cAppIdentifier[8]; // application identifier
char m_cAppAuth[3]; // application authentication code
};
struct TGIFControlExt // graphic control extension block
{
unsigned char m_cExtIntroducer; // extension introducer (0x21)
unsigned char m_cControlLabel; // control extension label (0xF9)
unsigned char m_cBlockSize; // fixed value of 4
unsigned char m_cPacked; // packed field
WORD m_wDelayTime; // delay time
unsigned char m_cTColorIndex; // transparent color index
unsigned char m_cBlockTerm; // block terminator (0x00)
public:
inline int GetPackedValue(enum ControlExtValues Value);
};
struct TGIFCommentExt // comment extension block
{
unsigned char m_cExtIntroducer; // extension introducer (0x21)
unsigned char m_cCommentLabel; // comment extension label (0xFE)
};
struct TGIFPlainTextExt // plain text extension block
{
unsigned char m_cExtIntroducer; // extension introducer (0x21)
unsigned char m_cPlainTextLabel; // text extension label (0x01)
unsigned char m_cBlockSize; // fixed value of 12
WORD m_wLeftPos; // text grid left position
WORD m_wTopPos; // text grid top position
WORD m_wGridWidth; // text grid width
WORD m_wGridHeight; // text grid height
unsigned char m_cCellWidth; // character cell width
unsigned char m_cCellHeight; // character cell height
unsigned char m_cFgColor; // text foreground color index
unsigned char m_cBkColor; // text background color index
};
struct TGIFImageDescriptor // image descriptor block
{
unsigned char m_cImageSeparator; // image separator byte (0x2C)
WORD m_wLeftPos; // image left position
WORD m_wTopPos; // image top position
WORD m_wWidth; // image width
WORD m_wHeight; // image height
unsigned char m_cPacked; // packed field
inline int GetPackedValue(enum IDPackedValues Value);
};
#pragma pack() // turn byte alignment off
public:
BOOL GetPaintRect(RECT *lpRect);
BOOL SetPaintRect(const RECT *lpRect);
CPictureEx();
virtual ~CPictureEx();
void Stop(); // stops animation
void UnLoad(); // stops animation plus releases all resources
BOOL IsGIF() const;
BOOL IsPlaying() const;
BOOL IsAnimatedGIF() const;
SIZE GetSize() const;
int GetFrameCount() const;
COLORREF GetBkColor() const;
void SetBkColor(COLORREF clr);
// draws the picture (starts an animation thread if needed)
// if an animation was previously stopped by Stop(),
// continues it from the last displayed frame
BOOL Draw();
// loads a picture from a file
// i.e. Load(_T("mypic.gif"));
BOOL Load(LPCTSTR szFileName);
// loads a picture from a global memory block (allocated by GlobalAlloc)
// Warning: this function DOES NOT free the global memory, pointed to by hGlobal
BOOL Load(HGLOBAL hGlobal, DWORD dwSize);
// loads a picture from a program resource
// i.e. Load(MAKEINTRESOURCE(IDR_MYPIC),_T("GIFTYPE"));
BOOL Load(LPCTSTR szResourceName,LPCTSTR szResourceType);
protected:
#ifdef GIF_TRACING
void EnumGIFBlocks();
void WriteDataOnDisk(CString szFileName, HGLOBAL hData, DWORD dwSize);
#endif // GIF_TRACING
RECT m_PaintRect;
SIZE m_PictureSize;
COLORREF m_clrBackground;
UINT m_nCurrFrame;
UINT m_nDataSize;
UINT m_nCurrOffset;
UINT m_nGlobalCTSize;
BOOL m_bIsGIF;
BOOL m_bIsPlaying;
volatile BOOL m_bExitThread;
BOOL m_bIsInitialized;
HDC m_hMemDC;
HDC m_hDispMemDC;
HBITMAP m_hDispMemBM;
HBITMAP m_hDispOldBM;
HBITMAP m_hBitmap;
HBITMAP m_hOldBitmap;
HANDLE m_hThread;
HANDLE m_hExitEvent;
IPicture * m_pPicture;
TGIFHeader * m_pGIFHeader;
unsigned char * m_pRawData;
TGIFLSDescriptor * m_pGIFLSDescriptor;
std::vector<TFrame> m_arrFrames;
void ThreadAnimation();
static UINT WINAPI _ThreadAnimation(LPVOID pParam);
int GetNextBlockLen() const;
BOOL SkipNextBlock();
BOOL SkipNextGraphicBlock();
BOOL PrepareDC(int nWidth, int nHeight);
void ResetDataPointer();
enum GIFBlockTypes GetNextBlock() const;
UINT GetSubBlocksLen(UINT nStartingOffset) const;
HGLOBAL GetNextGraphicBlock(UINT *pBlockLen, UINT *pDelay,
SIZE *pBlockSize, SIZE *pBlockOffset, UINT *pDisposal);
// Generated message map functions
//{{AFX_MSG(CPictureEx)
afx_msg void OnDestroy();
afx_msg void OnPaint();
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};
#endif // !defined(AFX_PICTUREEX_H__0EFE5DE0_7B68_4DB7_8B34_5DC634948438__INCLUDED_)
@@ -0,0 +1,12 @@
#ifndef USE_MODULES
int _cfb_init_mcrypt( int td, void* buf, void *key, int lenofkey, void *IV);
int _mcrypt_cfb(int td, void* buf,void *plaintext, int len);
int _mdecrypt_cfb(int td, void* buf, void *plaintext, int len);
int _cfb_is_block_mode();
int _cfb_has_iv();
int _cfb_is_block_algorithm_mode();
char *_mcrypt_cfb_get_modes_name();
int _mcrypt_cfb_mode_get_size ();
int _mcrypt_cfb_get_iv_size(int td);
word32 _mcrypt_cfb_mode_version();
#endif
@@ -0,0 +1,414 @@
// ShellTreeCtrl.cpp : implementation file
//
/////////////////////////////////////////////////////////////////////////////
//
// Copyright (C) 2000-2001 by Paolo Messina
// (http://www.geocities.com/ppescher - ppescher@yahoo.com)
//
// The contents of this file are subject to the Artistic License (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.opensource.org/licenses/artistic-license.html
//
// If you find this code useful, credits would be nice!
//
/////////////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#include "ShellTreeCtrl.h"
#include ".\shelltreectrl.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CShellTreeCtrl
CShellTreeCtrl::CShellTreeCtrl()
{
m_nCallbackMask = 0;
}
CShellTreeCtrl::~CShellTreeCtrl()
{
}
BEGIN_MESSAGE_MAP(CShellTreeCtrl, CWaitingTreeCtrl)
//{{AFX_MSG_MAP(CShellTreeCtrl)
ON_NOTIFY_REFLECT(TVN_DELETEITEM, OnDeleteItem)
ON_NOTIFY_REFLECT(TVN_GETDISPINFO, OnGetDispInfo)
//}}AFX_MSG_MAP
// ON_NOTIFY_REFLECT(TVN_SELCHANGED, OnTvnSelchanged)
// ON_NOTIFY_REFLECT(TVN_ITEMEXPANDED, OnTvnItemexpanded)
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CShellTreeCtrl message handlers
BOOL CShellTreeCtrl::PopulateItem(HTREEITEM hParent)
{
if (hParent == TVI_ROOT)
{
// not handled yet, do nothing in Release builds
ASSERT(FALSE);
return TRUE;
}
TVITEMDATA* pData = (TVITEMDATA*)GetItemData(hParent);
if (pData == NULL)
return TRUE; // invalid shell item, ignore it silently
// get parent pidl
ASSERT(pData->IsValid());
CShellPidl& pidlParent = pData->pidlAbs;
if (!EnumFolderItems(hParent, pidlParent, pData->nFlags))
return TRUE; // failed, won't try anymore!
// TODO: change this method!!
// do not check for children if parent is a removable media
// (just try: if it's a filesystem object, it has a path)
TCHAR path[MAX_PATH];
if (SHGetPathFromIDList(pidlParent, path))
{
path[3] = 0;
UINT type = GetDriveType(path);
if (type != DRIVE_FIXED)
return FALSE;
}
return TRUE;
}
void CShellTreeCtrl::PreSubclassWindow()
{
InitializeControl();
CWaitingTreeCtrl::PreSubclassWindow();
}
void CShellTreeCtrl::InitializeControl()
{
// Attach to the system image list
CShellPidl pidl((UINT)CSIDL_DESKTOP, m_hWnd);
SHFILEINFO sfi;
ZeroMemory(&sfi, sizeof(SHFILEINFO));
HIMAGELIST hSysImageList = (HIMAGELIST) SHGetFileInfo((LPCTSTR)(LPCITEMIDLIST)pidl,
0, &sfi, sizeof(SHFILEINFO), SHGFI_PIDL | SHGFI_SYSICONINDEX | SHGFI_SMALLICON);
//TreeView_SetImageList(m_hWnd, hSysImageList, TVSIL_NORMAL);
// postpone imagelist attaching
// (seems it doesn't like a sendmessage when dynamically created
// maybe because it has not received the WM_CREATE message yet?)
PostMessage(TVM_SETIMAGELIST, TVSIL_NORMAL, (LPARAM)hSysImageList);
}
void CShellTreeCtrl::AddRootFolderContent(LPCITEMIDLIST pidlFolder, UINT nFlags)
{
if (pidlFolder == NULL)
{
CShellPidl pidl((UINT)CSIDL_DESKTOP, m_hWnd);
InsertSubItem(TVI_ROOT, m_pDesktopFolder, NULL, pidl, nFlags);
//HTREEITEM root = GetRootItem();
//Expand(root, TVE_EXPAND);
//AfxMessageBox(GetItemText(GetChildItem(root)));
//PopulateItem(GetRootItem());
//Expand(GetRootItem(), 1);
return;
}
SetRedraw(FALSE);
EnumFolderItems(TVI_ROOT, pidlFolder, nFlags);
SetRedraw(TRUE);
}
int CALLBACK CShellTreeCtrl::CompareFunc(LPARAM lParam1,
LPARAM lParam2, LPARAM /*lParamSort*/)
{
TVITEMDATA* pData1 = (TVITEMDATA*)lParam1;
TVITEMDATA* pData2 = (TVITEMDATA*)lParam2;
ASSERT(pData1->IsValid() && pData2->IsValid());
// TODO: parent folders should be checked some day
SShellFolderPtr pParentFolder = pData2->pParentFolder;
HRESULT hr = pParentFolder->CompareIDs(0,
pData1->pidlAbs.GetLastChild(),
pData2->pidlAbs.GetLastChild() );
if (FAILED(hr))
return 0; // error, don't sort
short ret = (short)HRESULT_CODE(hr);
if (ret < 0)
return -1;
if (ret > 0)
return 1;
return 0;
}
void CShellTreeCtrl::FillItem(TVITEM& item)
{
DWORD dwAttributes;
// get item data
TVITEMDATA* pData = (TVITEMDATA*)item.lParam;
ASSERT(pData->IsValid());
// get a relative pidl
LPCITEMIDLIST pidlRel = pData->pidlAbs.GetLastChild();
if (item.mask & TVIF_TEXT)
{
// get display name
CString sName;
CShellString str;
if (pData->nFlags & STCF_SHOWPATH)
{
// use an absolute or relative path, if possible
sName = pData->pidlAbs.GetPath();
if (!sName.IsEmpty() && !(pData->nFlags & STCF_SHOWFULLNAME))
sName = sName.Right(sName.ReverseFind(_T('\\')));
}
if (sName.IsEmpty())
{
// use a global or contextual displayname
DWORD uDisplayFlags = SHGDN_INFOLDER;
if (pData->nFlags & STCF_SHOWFULLNAME)
uDisplayFlags = SHGDN_NORMAL;
// pData->pParentFolder->GetDisplayNameOf(pidlRel, uDisplayFlags
// | SHGDN_INCLUDE_NONFILESYS, str.GetPointer(pidlRel));
pData->pParentFolder->GetDisplayNameOf(pidlRel, uDisplayFlags, str.GetPointer(pidlRel));
sName = str; // copy to string
}
// set item text
lstrcpyn(item.pszText, (LPCTSTR)sName, item.cchTextMax);
}
if (item.mask & (TVIF_IMAGE | TVIF_SELECTEDIMAGE))
{
// get some attributes
dwAttributes = SFGAO_FOLDER | SFGAO_LINK | SFGAO_SHARE | SFGAO_GHOSTED;
pData->pParentFolder->GetAttributesOf(1, &pidlRel, &dwAttributes);
// set correct icon
if (dwAttributes & SFGAO_GHOSTED)
{
item.mask |= LVIF_STATE;
item.stateMask |= LVIS_CUT;
item.state |= LVIS_CUT;
}
if (dwAttributes & SFGAO_SHARE)
{
item.mask |= LVIF_STATE;
item.state &= ~LVIS_OVERLAYMASK;
item.state |= INDEXTOOVERLAYMASK(1);
item.stateMask |= LVIS_OVERLAYMASK;
}
else if (dwAttributes & SFGAO_LINK)
{
item.mask |= LVIF_STATE;
item.state &= ~LVIS_OVERLAYMASK;
item.state |= INDEXTOOVERLAYMASK(2);
item.stateMask |= LVIS_OVERLAYMASK;
}
if (item.mask & TVIF_IMAGE)
{
item.iImage = pData->pidlAbs.GetIconIndex(SHGFI_SMALLICON);
item.iSelectedImage = item.iImage;
}
if ((item.mask & TVIF_SELECTEDIMAGE)
&& (dwAttributes & SFGAO_FOLDER))
{
item.iSelectedImage = pData->pidlAbs.GetIconIndex(SHGFI_SMALLICON
|SHGFI_OPENICON);
}
}
if (item.mask & TVIF_CHILDREN)
{
// get some attributes
dwAttributes = SFGAO_FOLDER;
pData->pParentFolder->GetAttributesOf(1, &pidlRel, &dwAttributes);
// get children
item.cChildren = 0;
if (dwAttributes & SFGAO_FOLDER)
{
if (pData->nFlags & STCF_INCLUDEFILES)
item.cChildren = 1;
else if (dwAttributes & SFGAO_REMOVABLE)
item.cChildren = 1;
else
{
dwAttributes = SFGAO_HASSUBFOLDER;
pData->pParentFolder->GetAttributesOf(1, &pidlRel, &dwAttributes);
item.cChildren = (dwAttributes & SFGAO_HASSUBFOLDER) ? 1 : 0;
}
}
}
}
void CShellTreeCtrl::OnDeleteItem(NMHDR* pNMHDR, LRESULT* pResult)
{
TVITEM& item = ((LPNMTREEVIEW)pNMHDR)->itemOld;
// free item data, ignore invalid shell items
if (item.lParam != 0)
delete (TVITEMDATA*)item.lParam;
*pResult = 0;
}
void CShellTreeCtrl::OnGetDispInfo(NMHDR* pNMHDR, LRESULT* pResult)
{
TVITEM& item = ((LPNMTVDISPINFO)pNMHDR)->item;
// use the provided buffer for text
FillItem(item);
*pResult = 0;
}
CShellPidl CShellTreeCtrl::GetItemIDList(HTREEITEM hItem)
{
TVITEMDATA* pData = (TVITEMDATA*)GetItemData(hItem);
if (pData != NULL)
{
ASSERT(pData->IsValid());
return pData->pidlAbs;
}
return CShellPidl(); // invalid pidl
}
void CShellTreeCtrl::InsertSubItem(HTREEITEM hParent, LPSHELLFOLDER pParentFolder, LPCITEMIDLIST pidlParent, LPCITEMIDLIST pidl, UINT nFlags)
{
TVINSERTSTRUCT tvis;
ZeroMemory(&tvis, sizeof(TVINSERTSTRUCT));
tvis.hParent = hParent;
tvis.hInsertAfter = TVI_LAST;
// provide a buffer for the item text
TCHAR szText[MAX_PATH];
tvis.item.pszText = szText;
tvis.item.cchTextMax = MAX_PATH;
// used fields
const UINT nTVIFlags = TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE
| TVIF_CHILDREN | TVIF_PARAM;
// prepare item data
TVITEMDATA* pData = new TVITEMDATA;
pData->pidlAbs.Combine(pidlParent, pidl);
pData->pParentFolder = pParentFolder;
pData->nFlags = nFlags;
// set item data
ASSERT(pData->IsValid());
tvis.item.lParam = (LPARAM)pData;
// fill with pidl, text, icons and children - handle callbacks
tvis.item.mask = nTVIFlags & ~m_nCallbackMask;
FillItem(tvis.item);
if (m_nCallbackMask & TVIF_IMAGE)
tvis.item.iImage = I_IMAGECALLBACK;
if (m_nCallbackMask & TVIF_SELECTEDIMAGE)
tvis.item.iSelectedImage = I_IMAGECALLBACK;
if (m_nCallbackMask & TVIF_TEXT)
tvis.item.pszText = LPSTR_TEXTCALLBACK;
if (m_nCallbackMask & TVIF_CHILDREN)
tvis.item.cChildren = I_CHILDRENCALLBACK;
tvis.item.mask |= nTVIFlags;
// then insert new item
InsertItem(&tvis);
}
void CShellTreeCtrl::AddRootItem(LPCITEMIDLIST pidlRoot, UINT nFlags)
{
// not needed if pParentFolder is an argument
CShellPidl pidlParent;
pidlParent.CloneLastParent(pidlRoot);
SShellFolderPtr pParentFolder(m_pDesktopFolder, pidlParent);
InsertSubItem(TVI_ROOT, pParentFolder, NULL, pidlRoot, nFlags);
}
BOOL CShellTreeCtrl::EnumFolderItems(HTREEITEM hParent, LPCITEMIDLIST pidlParent, UINT nFlags)
{
// get parent shell folder
SShellFolderPtr pParentFolder(m_pDesktopFolder, pidlParent);
// not a valid folder object
if (!pParentFolder.IsValid())
return FALSE; // failed!
// enum child pidls
SEnumIDListPtr pEnumIDList(pParentFolder, SHCONTF_FOLDERS
| ((nFlags & STCF_INCLUDEFILES) ? SHCONTF_NONFOLDERS : 0)
| ((nFlags & STCF_INCLUDEHIDDEN) ? SHCONTF_INCLUDEHIDDEN : 0), m_hWnd);
if (pEnumIDList.IsValid())
{
SetPopulationCount(0);
CShellPidl pidl;
while (NOERROR == pEnumIDList->Next(1, pidl.GetPointer(), NULL))
{
// add child item, inherit some flags (inclusion)
InsertSubItem(hParent, pParentFolder, pidlParent, pidl,
nFlags & STCF_INCLUDEMASK);
// notify progress
IncreasePopulation();
}
}
if (GetPopulationCount() > 0)
{
// sort items
TVSORTCB tvscb;
tvscb.hParent = hParent;
tvscb.lpfnCompare = CompareFunc;
// tvscb.lParam = 0; // not meaningful yet
SortChildrenCB(&tvscb);
}
// notify progress
SetPopulationCount(1,1);
// success!
return TRUE;
}
BOOL CShellTreeCtrl::GetItemContextMenu(HTREEITEM hItem, CShellContextMenu& rCtxMenu)
{
TVITEMDATA* pData = (TVITEMDATA*)GetItemData(hItem);
if (!pData->IsValid())
return FALSE;
return rCtxMenu.Create(pData->pParentFolder,
pData->pidlAbs.GetLastChild());
}
void CShellTreeCtrl::SetCallbackMask(UINT nMask)
{
m_nCallbackMask = nMask &
(TVIF_TEXT | TVIF_IMAGE | TVIF_SELECTEDIMAGE | TVIF_CHILDREN);
}
UINT CShellTreeCtrl::GetCallbackMask()
{
return m_nCallbackMask;
}
@@ -0,0 +1,450 @@
/*
String utility functions
Copyright (C) 1999-2004, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif
#include <stdio.h>
#include <ctype.h> /* for isprint() etc in ne_strclean() */
#include "ne_alloc.h"
#include "ne_string.h"
#include "ne_md5.h"
char *ne_token(char **str, char separator)
{
char *ret = *str, *pnt = strchr(*str, separator);
if (pnt) {
*pnt = '\0';
*str = pnt + 1;
} else {
/* no separator found: return end of string. */
*str = NULL;
}
return ret;
}
char *ne_qtoken(char **str, char separator, const char *quotes)
{
char *pnt, *ret = NULL;
for (pnt = *str; *pnt != '\0'; pnt++) {
char *quot = strchr(quotes, *pnt);
if (quot) {
char *qclose = strchr(pnt+1, *quot);
if (!qclose) {
/* no closing quote: invalid string. */
return NULL;
}
pnt = qclose;
} else if (*pnt == separator) {
/* found end of token. */
*pnt = '\0';
ret = *str;
*str = pnt + 1;
return ret;
}
}
/* no separator found: return end of string. */
ret = *str;
*str = NULL;
return ret;
}
char *ne_shave(char *str, const char *whitespace)
{
char *pnt, *ret = str;
while (*ret != '\0' && strchr(whitespace, *ret) != NULL) {
ret++;
}
/* pnt points at the NUL terminator. */
pnt = &ret[strlen(ret)];
while (pnt > ret && strchr(whitespace, *(pnt-1)) != NULL) {
pnt--;
}
*pnt = '\0';
return ret;
}
void ne_buffer_clear(ne_buffer *buf)
{
memset(buf->data, 0, buf->length);
buf->used = 1;
}
/* Grows for given size, returns 0 on success, -1 on error. */
void ne_buffer_grow(ne_buffer *buf, size_t newsize)
{
#define NE_BUFFER_GROWTH 512
if (newsize > buf->length) {
/* If it's not big enough already... */
buf->length = ((newsize / NE_BUFFER_GROWTH) + 1) * NE_BUFFER_GROWTH;
/* Reallocate bigger buffer */
buf->data = ne_realloc(buf->data, buf->length);
}
}
static size_t count_concat(va_list *ap)
{
size_t total = 0;
char *next;
while ((next = va_arg(*ap, char *)) != NULL)
total += strlen(next);
return total;
}
static void do_concat(char *str, va_list *ap)
{
char *next;
while ((next = va_arg(*ap, char *)) != NULL) {
#ifdef HAVE_STPCPY
str = stpcpy(str, next);
#else
size_t len = strlen(next);
memcpy(str, next, len);
str += len;
#endif
}
}
void ne_buffer_concat(ne_buffer *buf, ...)
{
va_list ap;
ssize_t total;
va_start(ap, buf);
total = buf->used + count_concat(&ap);
va_end(ap);
/* Grow the buffer */
ne_buffer_grow(buf, total);
va_start(ap, buf);
do_concat(buf->data + buf->used - 1, &ap);
va_end(ap);
buf->used = total;
buf->data[total - 1] = '\0';
}
char *ne_concat(const char *str, ...)
{
va_list ap;
size_t total, slen = strlen(str);
char *ret;
va_start(ap, str);
total = slen + count_concat(&ap);
va_end(ap);
ret = memcpy(ne_malloc(total + 1), str, slen);
va_start(ap, str);
do_concat(ret + slen, &ap);
va_end(ap);
ret[total] = '\0';
return ret;
}
/* Append zero-terminated string... returns 0 on success or -1 on
* realloc failure. */
void ne_buffer_zappend(ne_buffer *buf, const char *str)
{
ne_buffer_append(buf, str, strlen(str));
}
void ne_buffer_append(ne_buffer *buf, const char *data, size_t len)
{
ne_buffer_grow(buf, buf->used + len);
memcpy(buf->data + buf->used - 1, data, len);
buf->used += len;
buf->data[buf->used - 1] = '\0';
}
ne_buffer *ne_buffer_create(void)
{
return ne_buffer_ncreate(512);
}
ne_buffer *ne_buffer_ncreate(size_t s)
{
ne_buffer *buf = ne_malloc(sizeof(*buf));
buf->data = ne_malloc(s);
buf->data[0] = '\0';
buf->length = s;
buf->used = 1;
return buf;
}
void ne_buffer_destroy(ne_buffer *buf)
{
ne_free(buf->data);
ne_free(buf);
}
char *ne_buffer_finish(ne_buffer *buf)
{
char *ret = buf->data;
ne_free(buf);
return ret;
}
void ne_buffer_altered(ne_buffer *buf)
{
buf->used = strlen(buf->data) + 1;
}
static const char b64_alphabet[] =
"ABCDEFGHIJKLMNOPQRSTUVWXYZ"
"abcdefghijklmnopqrstuvwxyz"
"0123456789+/=";
char *ne_base64(const unsigned char *text, size_t inlen)
{
/* The tricky thing about this is doing the padding at the end,
* doing the bit manipulation requires a bit of concentration only */
char *buffer, *point;
size_t outlen;
/* Use 'buffer' to store the output. Work out how big it should be...
* This must be a multiple of 4 bytes */
outlen = (inlen*4)/3;
if ((inlen % 3) > 0) /* got to pad */
outlen += 4 - (inlen % 3);
buffer = ne_malloc(outlen + 1); /* +1 for the \0 */
/* now do the main stage of conversion, 3 bytes at a time,
* leave the trailing bytes (if there are any) for later */
for (point=buffer; inlen>=3; inlen-=3, text+=3) {
*(point++) = b64_alphabet[ (*text)>>2 ];
*(point++) = b64_alphabet[ ((*text)<<4 & 0x30) | (*(text+1))>>4 ];
*(point++) = b64_alphabet[ ((*(text+1))<<2 & 0x3c) | (*(text+2))>>6 ];
*(point++) = b64_alphabet[ (*(text+2)) & 0x3f ];
}
/* Now deal with the trailing bytes */
if (inlen > 0) {
/* We always have one trailing byte */
*(point++) = b64_alphabet[ (*text)>>2 ];
*(point++) = b64_alphabet[ (((*text)<<4 & 0x30) |
(inlen==2?(*(text+1))>>4:0)) ];
*(point++) = (inlen==1?'=':b64_alphabet[ (*(text+1))<<2 & 0x3c ]);
*(point++) = '=';
}
/* Null-terminate */
*point = '\0';
return buffer;
}
/* VALID_B64: fail if 'ch' is not a valid base64 character */
#define VALID_B64(ch) (((ch) >= 'A' && (ch) <= 'Z') || \
((ch) >= 'a' && (ch) <= 'z') || \
((ch) >= '0' && (ch) <= '9') || \
(ch) == '/' || (ch) == '+' || (ch) == '=')
/* DECODE_B64: decodes a valid base64 character. */
#define DECODE_B64(ch) ((ch) >= 'a' ? ((ch) + 26 - 'a') : \
((ch) >= 'A' ? ((ch) - 'A') : \
((ch) >= '0' ? ((ch) + 52 - '0') : \
((ch) == '+' ? 62 : 63))))
size_t ne_unbase64(const char *data, unsigned char **out)
{
size_t inlen = strlen(data);
unsigned char *outp;
const unsigned char *in;
if (inlen == 0 || (inlen % 4) != 0) return 0;
outp = *out = ne_malloc(inlen * 3 / 4);
for (in = (const unsigned char *)data; *in; in += 4) {
unsigned int tmp;
if (!VALID_B64(in[0]) || !VALID_B64(in[1]) || !VALID_B64(in[2]) ||
!VALID_B64(in[3]) || in[0] == '=' || in[1] == '=' ||
(in[2] == '=' && in[3] != '=')) {
ne_free(*out);
return 0;
}
tmp = (DECODE_B64(in[0]) & 0x3f) << 18 |
(DECODE_B64(in[1]) & 0x3f) << 12;
*outp++ = (tmp >> 16) & 0xff;
if (in[2] != '=') {
tmp |= (DECODE_B64(in[2]) & 0x3f) << 6;
*outp++ = (tmp >> 8) & 0xff;
if (in[3] != '=') {
tmp |= DECODE_B64(in[3]) & 0x3f;
*outp++ = tmp & 0xff;
}
}
}
return outp - *out;
}
/* Character map array; ascii_clean[n] = isprint(n) ? n : 0x20. Used
* by ne_strclean as a locale-independent isprint(). */
static const unsigned char ascii_clean[256] = {
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,
0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,
0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,
0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,
0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20
};
char *ne_strclean(char *str)
{
unsigned char *pnt;
for (pnt = (unsigned char *)str; *pnt; pnt++)
*pnt = (char)ascii_clean[*pnt];
return str;
}
char *ne_strerror(int errnum, char *buf, size_t buflen)
{
#ifdef HAVE_STRERROR_R
#ifdef STRERROR_R_CHAR_P
/* glibc-style strerror_r which may-or-may-not use provided buffer. */
char *ret = strerror_r(errnum, buf, buflen);
if (ret != buf)
ne_strnzcpy(buf, ret, buflen);
#else /* POSIX-style strerror_r: */
strerror_r(errnum, buf, buflen);
#endif
#else /* no strerror_r: */
ne_strnzcpy(buf, strerror(errnum), buflen);
#endif
return buf;
}
/* Wrapper for ne_snprintf. */
size_t ne_snprintf(char *str, size_t size, const char *fmt, ...)
{
va_list ap;
va_start(ap, fmt);
#ifdef HAVE_TRIO
trio_vsnprintf(str, size, fmt, ap);
#else
vsnprintf(str, size, fmt, ap);
#endif
va_end(ap);
str[size-1] = '\0';
return strlen(str);
}
/* Wrapper for ne_vsnprintf. */
size_t ne_vsnprintf(char *str, size_t size, const char *fmt, va_list ap)
{
#ifdef HAVE_TRIO
trio_vsnprintf(str, size, fmt, ap);
#else
vsnprintf(str, size, fmt, ap);
#endif
str[size-1] = '\0';
return strlen(str);
}
void ne_md5_buffer(const char *buffer, char *digest)
{
unsigned char md5_buf[16];
struct ne_md5_ctx ctx;
ne_md5_init_ctx(&ctx);
ne_md5_process_bytes(buffer, strlen(buffer), &ctx);
ne_md5_finish_ctx(&ctx, md5_buf);
ne_md5_to_ascii(md5_buf, digest);
}
void ne_md5_buffer_bin(const char *buffer, char *digest)
{
unsigned char md5_buf[16];
struct ne_md5_ctx ctx;
ne_md5_init_ctx(&ctx);
ne_md5_process_bytes(buffer, strlen(buffer), &ctx);
ne_md5_finish_ctx(&ctx, md5_buf);
memcpy(digest,md5_buf,16);
}
@@ -0,0 +1,32 @@
/*
Internationalization of neon
Copyright (C) 1999-2003, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
void neon_i18n_init(void)
{
#if defined(ENABLE_NLS) && defined(NEON_IS_LIBRARY)
/* if neon is build bundled in (i.e., not as a standalone
* library), then there is probably no point in this, since the
* messages won't be pointing in the right direction.
* there's not really any point in doing this if neon is
* a library since the messages aren't i18n'ized, but... */
bindtextdomain("neon", LOCALEDIR);
#endif
}
@@ -0,0 +1,700 @@
/* panama_x.c */
/* $Id: panama.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
/* daemen.j@protonworld.com */
/**************************************************************************+
*
* PANAMA high-performance reference C-code, based on the description in
* the paper 'Fast Hashing and Stream Encryption with PANAMA', presented
* at the Fast Software Encryption Workshop, Paris, 1998, see "Fast
* Software Encryption - 5th International Workshop, FSE'98", edited by
* Serge Vaudenay, LNCS-1372, Springer-Verlag, 1998, pp 60-74, also
* available on-line at http://standard.pictel.com/ftp/research/security
*
* Algorithm design by Joan Daemen and Craig Clapp
*
* panama_x.c - Core routines for the Panama stream/hash module, this
* exportable version excludes an encryption routine.
*
*
* History:
*
* 29-Oct-98 Craig Clapp Implemention for Dr. Dobbs, Dec. 1998 issue,
* based on earlier performance-benchmark code.
*
*
* Notes: This code is supplied for the purposes of evaluating the
* performance of the Panama stream/hash module and as a
* reference implementation for generating test vectors for
* compatibility / interoperability verification.
*
*
+**************************************************************************/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "panama.h"
#define _mcrypt_set_key panama_LTX__mcrypt_set_key
#define _mcrypt_encrypt panama_LTX__mcrypt_encrypt
#define _mcrypt_decrypt panama_LTX__mcrypt_decrypt
#define _mcrypt_get_size panama_LTX__mcrypt_get_size
#define _mcrypt_get_block_size panama_LTX__mcrypt_get_block_size
#define _is_block_algorithm panama_LTX__is_block_algorithm
#define _mcrypt_get_key_size panama_LTX__mcrypt_get_key_size
#define _mcrypt_get_algo_iv_size panama_LTX__mcrypt_get_algo_iv_size
#define _mcrypt_get_supported_key_sizes panama_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name panama_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test panama_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version panama_LTX__mcrypt_algorithm_version
/**************************************************************************+
* Panama internal routines *
+**************************************************************************/
/* tau, rotate word 'a' to the left by rol_bits bit positions */
#define tau(a, rol_bits) ROTL32(a, rol_bits)
/**************************************************************************/
/* move state between memory and local registers */
#define READ_STATE_i(i) state_##i = state->word[i]
#define WRITE_STATE_i(i) state->word[i] = state_##i
#define READ_STATE \
\
READ_STATE_i(0); \
READ_STATE_i(1); \
READ_STATE_i(2); \
READ_STATE_i(3); \
READ_STATE_i(4); \
READ_STATE_i(5); \
READ_STATE_i(6); \
READ_STATE_i(7); \
READ_STATE_i(8); \
READ_STATE_i(9); \
READ_STATE_i(10); \
READ_STATE_i(11); \
READ_STATE_i(12); \
READ_STATE_i(13); \
READ_STATE_i(14); \
READ_STATE_i(15); \
READ_STATE_i(16)
#define WRITE_STATE \
\
WRITE_STATE_i(0); \
WRITE_STATE_i(1); \
WRITE_STATE_i(2); \
WRITE_STATE_i(3); \
WRITE_STATE_i(4); \
WRITE_STATE_i(5); \
WRITE_STATE_i(6); \
WRITE_STATE_i(7); \
WRITE_STATE_i(8); \
WRITE_STATE_i(9); \
WRITE_STATE_i(10); \
WRITE_STATE_i(11); \
WRITE_STATE_i(12); \
WRITE_STATE_i(13); \
WRITE_STATE_i(14); \
WRITE_STATE_i(15); \
WRITE_STATE_i(16)
/**************************************************************************/
/* gamma, shift-invariant transformation a[i] XOR (a[i+1] OR NOT a[i+2]) */
#define gamma_in_(i) state_##i
#define gamma_out_(i) gamma_##i
#define GAMMA_i(i, i_plus_1, i_plus_2) \
\
gamma_out_(i) = gamma_in_(i) ^ (gamma_in_(i_plus_1) | ~gamma_in_(i_plus_2))
#define GAMMA \
\
GAMMA_i( 0, 1, 2); \
GAMMA_i( 1, 2, 3); \
GAMMA_i( 2, 3, 4); \
GAMMA_i( 3, 4, 5); \
GAMMA_i( 4, 5, 6); \
GAMMA_i( 5, 6, 7); \
GAMMA_i( 6, 7, 8); \
GAMMA_i( 7, 8, 9); \
GAMMA_i( 8, 9, 10); \
GAMMA_i( 9, 10, 11); \
GAMMA_i(10, 11, 12); \
GAMMA_i(11, 12, 13); \
GAMMA_i(12, 13, 14); \
GAMMA_i(13, 14, 15); \
GAMMA_i(14, 15, 16); \
GAMMA_i(15, 16, 0); \
GAMMA_i(16, 0, 1)
/**************************************************************************/
/* pi, permute and cyclicly rotate the state words */
#define pi_in_(i) gamma_##i
#define pi_out_(i) pi_##i
#define PI_i(i, j, k) pi_out_(i) = tau(pi_in_(j), k)
#define PI \
\
pi_out_(0) = pi_in_(0); \
PI_i( 1, 7, 1); \
PI_i( 2, 14, 3); \
PI_i( 3, 4, 6); \
PI_i( 4, 11, 10); \
PI_i( 5, 1, 15); \
PI_i( 6, 8, 21); \
PI_i( 7, 15, 28); \
PI_i( 8, 5, 4); \
PI_i( 9, 12, 13); \
PI_i(10, 2, 23); \
PI_i(11, 9, 2); \
PI_i(12, 16, 14); \
PI_i(13, 6, 27); \
PI_i(14, 13, 9); \
PI_i(15, 3, 24); \
PI_i(16, 10, 8)
/**************************************************************************/
/* theta, shift-invariant transformation a[i] XOR a[i+1] XOR a[i+4] */
#define theta_in_(i) pi_##i
#define theta_out_(i) theta_##i
#define THETA_i(i, i_plus_1, i_plus_4) \
\
theta_out_(i) = theta_in_(i) ^ theta_in_(i_plus_1) ^ theta_in_(i_plus_4)
#define THETA \
\
THETA_i( 0, 1, 4); \
THETA_i( 1, 2, 5); \
THETA_i( 2, 3, 6); \
THETA_i( 3, 4, 7); \
THETA_i( 4, 5, 8); \
THETA_i( 5, 6, 9); \
THETA_i( 6, 7, 10); \
THETA_i( 7, 8, 11); \
THETA_i( 8, 9, 12); \
THETA_i( 9, 10, 13); \
THETA_i(10, 11, 14); \
THETA_i(11, 12, 15); \
THETA_i(12, 13, 16); \
THETA_i(13, 14, 0); \
THETA_i(14, 15, 1); \
THETA_i(15, 16, 2); \
THETA_i(16, 0, 3)
/**************************************************************************/
/* sigma, merge two buffer stages with current state */
#define sigma_in_(i) theta_##i
#define sigma_out_(i) state_##i
#define SIGMA_L_i(i) sigma_out_(i) = sigma_in_(i) ^ L->word[i-1]
#define SIGMA_B_i(i) sigma_out_(i) = sigma_in_(i) ^ b->word[i-9]
#define SIGMA \
\
sigma_out_(0) = sigma_in_(0) ^ 0x00000001L; \
\
SIGMA_L_i(1); \
SIGMA_L_i(2); \
SIGMA_L_i(3); \
SIGMA_L_i(4); \
SIGMA_L_i(5); \
SIGMA_L_i(6); \
SIGMA_L_i(7); \
SIGMA_L_i(8); \
\
SIGMA_B_i(9); \
SIGMA_B_i(10); \
SIGMA_B_i(11); \
SIGMA_B_i(12); \
SIGMA_B_i(13); \
SIGMA_B_i(14); \
SIGMA_B_i(15); \
SIGMA_B_i(16)
/**************************************************************************/
/* lambda, update the 256-bit wide by 32-stage LFSR buffer */
#define LAMBDA_25_i(i) \
ptap_25->word[i] = ptap_25->word[i] ^ ptap_0->word[(i+2) & (PAN_STAGE_SIZE-1)]
#define LAMBDA_0_i(i, source) ptap_0->word[i] = source ^ ptap_0->word[i]
#define LAMBDA_25_UPDATE \
\
LAMBDA_25_i(0); \
LAMBDA_25_i(1); \
LAMBDA_25_i(2); \
LAMBDA_25_i(3); \
LAMBDA_25_i(4); \
LAMBDA_25_i(5); \
LAMBDA_25_i(6); \
LAMBDA_25_i(7)
#define LAMBDA_0_PULL \
\
LAMBDA_0_i(0, state_1); \
LAMBDA_0_i(1, state_2); \
LAMBDA_0_i(2, state_3); \
LAMBDA_0_i(3, state_4); \
LAMBDA_0_i(4, state_5); \
LAMBDA_0_i(5, state_6); \
LAMBDA_0_i(6, state_7); \
LAMBDA_0_i(7, state_8)
#define LAMBDA_0_PUSH \
\
LAMBDA_0_i(0, L->word[0]); \
LAMBDA_0_i(1, L->word[1]); \
LAMBDA_0_i(2, L->word[2]); \
LAMBDA_0_i(3, L->word[3]); \
LAMBDA_0_i(4, L->word[4]); \
LAMBDA_0_i(5, L->word[5]); \
LAMBDA_0_i(6, L->word[6]); \
LAMBDA_0_i(7, L->word[7])
/* avoid temporary register for tap 31 by finishing updating tap 25 before updating tap 0 */
#define LAMBDA_PULL \
LAMBDA_25_UPDATE; \
LAMBDA_0_PULL
#define LAMBDA_PUSH \
LAMBDA_25_UPDATE; \
LAMBDA_0_PUSH
/**************************************************************************/
#define regs(i) state_##i, gamma_##i, pi_##i, theta_##i
/**************************************************************************/
/**************************************************************************+
* Panama external routines *
+**************************************************************************/
/**************************************************************************+
*
* pan_pull() - Performs multiple iterations of the Panama 'Pull' operation.
* The input and output arrays are treated as integer multiples
* of Panama's natural 256-bit block size.
*
* Input and output arrays may be disjoint or coincident but
* may not be overlapped if offset from one another.
*
* If 'In' is a NULL pointer then output is taken direct from
* the state machine (used for hash output). If 'Out' is a NULL
* pointer then a dummy 'Pull' is performed. Otherwise 'In' is
* XOR combined with the state machine to produce 'Out'
* (used for stream encryption / decryption).
*
+**************************************************************************/
static void pan_pull(word32 * restrict In, /* input array */
word32 * restrict Out, /* output array */
word32 pan_blocks, /* number of blocks to be Pulled */
PAN_BUFFER * restrict buffer, /* LFSR buffer */
PAN_STATE * restrict state)
{ /* 17-word finite-state machine */
int i;
word32 regs(0), regs(1), regs(2), regs(3), regs(4);
word32 regs(5), regs(6), regs(7), regs(8), regs(9);
word32 regs(10), regs(11), regs(12), regs(13), regs(14);
word32 regs(15), regs(16);
word32 tap_0;
PAN_STAGE *restrict ptap_0, *restrict ptap_25;
PAN_STAGE *restrict L, *restrict b;
/* configure routine according to which PULL mode is intended */
static word32 null_in[PAN_STAGE_SIZE] = { 0, 0, 0, 0, 0, 0, 0, 0 };
word32 dummy_out[PAN_STAGE_SIZE];
word32 in_step, out_step;
in_step = out_step = PAN_STAGE_SIZE;
if (In == NULL || Out == NULL) {
In = null_in;
in_step = 0;
}
if (Out == NULL) {
Out = dummy_out;
out_step = 0;
}
/* copy buffer pointers and state to registers */
tap_0 = buffer->tap_0;
READ_STATE;
/* rho, cascade of state update operations */
for (i = 0; i < pan_blocks; i++) {
/* apply state output to crypto buffer */
Out[0] = In[0] ^ gamma_in_(9);
Out[1] = In[1] ^ gamma_in_(10);
Out[2] = In[2] ^ gamma_in_(11);
Out[3] = In[3] ^ gamma_in_(12);
Out[4] = In[4] ^ gamma_in_(13);
Out[5] = In[5] ^ gamma_in_(14);
Out[6] = In[6] ^ gamma_in_(15);
Out[7] = In[7] ^ gamma_in_(16);
Out += out_step;
In += in_step;
GAMMA; /* perform non-linearity stage */
PI; /* perform bit-dispersion stage */
THETA; /* perform diffusion stage */
/* calculate pointers to taps 4 and 16 for sigma based on current position of tap 0 */
L = &buffer->stage[(tap_0 + 4) & (PAN_STAGES - 1)];
b = &buffer->stage[(tap_0 + 16) & (PAN_STAGES - 1)];
/* move tap_0 left by one stage, equivalent to shifting LFSR one stage right */
tap_0 = (tap_0 - 1) & (PAN_STAGES - 1);
/* set tap pointers for use by lambda */
ptap_0 = &buffer->stage[tap_0];
ptap_25 = &buffer->stage[(tap_0 + 25) & (PAN_STAGES - 1)];
LAMBDA_PULL; /* update the LFSR buffer */
/* postpone sigma until after lambda in order to avoid extra temporaries for feedback path */
/* note that sigma gets to use the old positions of taps 4 and 16 */
SIGMA; /* perform buffer injection stage */
}
/* write buffer pointer and state back to memory */
buffer->tap_0 = tap_0;
WRITE_STATE;
}
/**************************************************************************+
*
* pan_push() - Performs multiple iterations of the Panama 'Push' operation.
* The input array is treated as an integer multiple of the
* 256-bit blocks which are Panama's natural input size.
*
+**************************************************************************/
static void pan_push(word32 * restrict In, /* input array */
word32 pan_blocks, /* number of blocks to be Pushed */
PAN_BUFFER * restrict buffer, /* LFSR buffer */
PAN_STATE * restrict state)
{ /* 17-word finite-state machine */
int i;
word32 regs(0), regs(1), regs(2), regs(3), regs(4);
word32 regs(5), regs(6), regs(7), regs(8), regs(9);
word32 regs(10), regs(11), regs(12), regs(13), regs(14);
word32 regs(15), regs(16);
word32 tap_0;
PAN_STAGE *restrict ptap_0, *restrict ptap_25;
PAN_STAGE *restrict L, *restrict b;
/* copy buffer pointers and state to registers */
tap_0 = buffer->tap_0;
READ_STATE;
/* assert((word32 *) ((PAN_STAGE *) In) == In); */
L = (PAN_STAGE *) In; /* we assume pointer to input buffer is compatible with pointer to PAN_STAGE */
#ifdef WORDS_BIGENDIAN
if (L != NULL)
for (i = 0; i < PAN_STAGE_SIZE; i++) {
L->word[i] = byteswap32(L->word[i]);
}
#endif
/* rho, cascade of state update operations */
for (i = 0; i < pan_blocks; i++) {
GAMMA; /* perform non-linearity stage */
PI; /* perform bit-dispersion stage */
THETA; /* perform diffusion stage */
/* calculate pointer to tap 16 for sigma based on current position of tap 0 */
b = &buffer->stage[(tap_0 + 16) & (PAN_STAGES - 1)];
/* move tap_0 left by one stage, equivalent to shifting LFSR one stage right */
tap_0 = (tap_0 - 1) & (PAN_STAGES - 1);
/* set tap pointers for use by lambda */
ptap_0 = &buffer->stage[tap_0];
ptap_25 = &buffer->stage[(tap_0 + 25) & (PAN_STAGES - 1)];
LAMBDA_PUSH; /* update the LFSR buffer */
/* postpone sigma until after lambda in order to avoid extra temporaries for feedback path */
/* note that sigma gets to use the old positions of taps 4 and 16 */
SIGMA; /* perform buffer injection stage */
L++; /* In += PAN_STAGE_SIZE; */
}
/* write buffer pointer and state back to memory */
buffer->tap_0 = tap_0;
WRITE_STATE;
}
/**************************************************************************+
*
* pan_reset() - Initializes an LFSR buffer and Panama state machine to
* all zeros, ready for a new hash to be accumulated or to
* re-synchronize or start up an encryption key-stream.
*
+**************************************************************************/
static void pan_reset(PAN_BUFFER * buffer, PAN_STATE * state)
{
int i, j;
buffer->tap_0 = 0;
for (j = 0; j < PAN_STAGES; j++) {
for (i = 0; i < PAN_STAGE_SIZE; i++) {
buffer->stage[j].word[i] = 0L;
}
}
for (i = 0; i < PAN_STATE_SIZE; i++) {
state->word[i] = 0L;
}
}
/**************************************************************************+
*
* pan_crypt() - Performs stream encryption or decryption.
*
+**************************************************************************/
WIN32DLL_DEFINE
int _mcrypt_set_key(PANAMA_KEY * pan_key, char *in_key, int keysize,
char *init_vec, int vecsize)
{
byte key[32];
int keyblocks = (8 * keysize) / (PAN_STAGE_SIZE * WORDLENGTH);
int vecblocks = (8 * vecsize) / (PAN_STAGE_SIZE * WORDLENGTH);
int i;
pan_key->keymat = (void*) pan_key->wkeymat;
/* initialize the Panama state machine for a fresh crypting operation */
pan_reset(&pan_key->buffer, &pan_key->state);
pan_push((void *) in_key, keyblocks, &pan_key->buffer,
&pan_key->state);
if (init_vec != NULL)
pan_push((void *) init_vec, vecblocks, &pan_key->buffer,
&pan_key->state);
pan_pull(NULL, NULL, 32, &pan_key->buffer, &pan_key->state);
pan_pull(NULL, pan_key->wkeymat, 1, &pan_key->buffer,
&pan_key->state);
pan_key->keymat_pointer = 0;
#ifdef WORDS_BIGENDIAN
for (i = 0; i < 8; i++) {
pan_key->wkeymat[i] =
byteswap32( pan_key->wkeymat[i]);
}
#endif
return 0;
}
WIN32DLL_DEFINE void _mcrypt_encrypt(PANAMA_KEY * pan_key, /* the key from pan_init */
byte * buf, /* input array */
int length)
{ /* length to be encrypted, in bits */
int i;
#ifdef WORDS_BIGENDIAN
int j;
#endif
/* initialize the Panama state machine for a fresh crypting operation */
for (i = 0; i < length; i++) {
if (pan_key->keymat_pointer == 32) {
pan_pull(NULL, (void *) pan_key->wkeymat, 1,
&pan_key->buffer, &pan_key->state);
pan_key->keymat_pointer = 0;
#ifdef WORDS_BIGENDIAN
for (j = 0; j < 8; j++) {
pan_key->wkeymat[j] =
byteswap32( pan_key->wkeymat[j]);
}
#endif
}
buf[i] ^= pan_key->keymat[pan_key->keymat_pointer];
pan_key->keymat_pointer++;
}
}
WIN32DLL_DEFINE void _mcrypt_decrypt(PANAMA_KEY * pan_key, /* the key from pan_init */
byte * buf, /* input array */
int length)
{ /* length to be encrypted, in bits */
_mcrypt_encrypt(pan_key, buf, length);
}
/**************************************************************************/
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return sizeof(PANAMA_KEY);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_algo_iv_size()
{
return 32;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 0;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 32;
}
static const int key_sizes[] = { 32 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE char *_mcrypt_get_algorithms_name()
{
return "PANAMA";
}
#define CIPHER "d76e3c2243feadd2c99edfcb95c64c852ba6c59f"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[20];
unsigned char ciphertext[20];
int blocksize = 20, j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size(),
NULL, 0);
_mcrypt_encrypt(key, (void *) ciphertext, blocksize);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(keyword);
free(key);
return -1;
}
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size(),
NULL, 0);
free(keyword);
_mcrypt_decrypt(key, (void *) ciphertext, blocksize);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version(void)
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1 @@
void Bzero( void *s, size_t n);
@@ -0,0 +1,9 @@
typedef struct triple_des_key {
char kn[3][16][8];
word32 sp[3][8][64];
char iperm[16][16][8];
char fperm[16][16][8];
} TRIPLEDES_KEY;
@@ -0,0 +1,12 @@
#ifndef USE_MODULES
int _cbc_init_mcrypt( int td, void* buf, void *key, int lenofkey, void *IV);
int _mcrypt_cbc(int td, void* buf,void *plaintext, int len);
int _mdecrypt_cbc(int td, void* buf, void *plaintext, int len);
int _cbc_is_block_mode();
int _cbc_has_iv();
int _cbc_is_block_algorithm_mode();
char *_mcrypt_cbc_get_modes_name();
int _mcrypt_cbc_mode_get_size ();
int _mcrypt_cbc_get_iv_size(int td);
word32 _mcrypt_cbc_mode_version();
#endif
@@ -0,0 +1,323 @@
/**********************************************************************\
* To commemorate the 1996 RSA Data Security Conference, the following *
* code is released into the public domain by its author. Prost! *
* *
* This cipher uses 16-bit words and little-endian byte ordering. *
* I wonder which processor it was optimized for? *
* *
* Thanks to CodeView, SoftIce, and D86 for helping bring this code to *
* the public. *
\**********************************************************************/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: rc2.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
#include <libdefs.h>
#include <mcrypt_modules.h>
/* #include <assert.h> */
#include "rc2.h"
#define _mcrypt_set_key rc2_LTX__mcrypt_set_key
#define _mcrypt_encrypt rc2_LTX__mcrypt_encrypt
#define _mcrypt_decrypt rc2_LTX__mcrypt_decrypt
#define _mcrypt_get_size rc2_LTX__mcrypt_get_size
#define _mcrypt_get_block_size rc2_LTX__mcrypt_get_block_size
#define _is_block_algorithm rc2_LTX__is_block_algorithm
#define _mcrypt_get_key_size rc2_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes rc2_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name rc2_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test rc2_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version rc2_LTX__mcrypt_algorithm_version
/**********************************************************************\
* Expand a variable-length user key (between 1 and 128 bytes) to a *
* 64-short working rc2 key, of at most "bits" effective key bits. *
* The effective key bits parameter looks like an export control hack. *
* For normal use, it should always be set to 1024. For convenience, *
* zero is accepted as an alias for 1024. *
\**********************************************************************/
WIN32DLL_DEFINE
int _mcrypt_set_key(word16 * xkey, const byte * key, unsigned int len)
{
unsigned int j;
byte *xkey_p = (void *) xkey;
int i;
/* 256-entry permutation table, probably derived somehow from pi */
static const byte permute[256] = {
217, 120, 249, 196, 25, 221, 181, 237, 40, 233, 253, 121,
74, 160, 216, 157,
198, 126, 55, 131, 43, 118, 83, 142, 98, 76, 100, 136,
68, 139, 251, 162,
23, 154, 89, 245, 135, 179, 79, 19, 97, 69, 109, 141, 9,
129, 125, 50,
189, 143, 64, 235, 134, 183, 123, 11, 240, 149, 33, 34,
92, 107, 78, 130,
84, 214, 101, 147, 206, 96, 178, 28, 115, 86, 192, 20,
167, 140, 241, 220,
18, 117, 202, 31, 59, 190, 228, 209, 66, 61, 212, 48,
163, 60, 182, 38,
111, 191, 14, 218, 70, 105, 7, 87, 39, 242, 29, 155, 188,
148, 67, 3,
248, 17, 199, 246, 144, 239, 62, 231, 6, 195, 213, 47,
200, 102, 30, 215,
8, 232, 234, 222, 128, 82, 238, 247, 132, 170, 114, 172,
53, 77, 106, 42,
150, 26, 210, 113, 90, 21, 73, 116, 75, 159, 208, 94, 4,
24, 164, 236,
194, 224, 65, 110, 15, 81, 203, 204, 36, 145, 175, 80,
161, 244, 112, 57,
153, 124, 58, 133, 35, 184, 180, 122, 252, 2, 54, 91, 37,
85, 151, 49,
45, 93, 250, 152, 227, 138, 146, 174, 5, 223, 41, 16,
103, 108, 186, 201,
211, 0, 230, 207, 225, 158, 168, 44, 99, 22, 1, 63, 88,
226, 137, 169,
13, 56, 52, 27, 171, 51, 255, 176, 187, 72, 12, 95, 185,
177, 205, 46,
197, 243, 219, 71, 229, 165, 156, 119, 10, 166, 32, 104,
254, 127, 193, 173
};
/* assert(len > 0 && len <= 128); */
memmove(xkey, key, len);
/* Phase 1: Expand input key to 128 bytes */
for (j = len; j < 128; j++) {
xkey_p[j] =
permute[(xkey_p[j - len] + xkey_p[j - 1]) % 256];
}
xkey_p[0] = permute[xkey_p[0]];
/* Phase 2 - reduce effective key size to "bits" */
/* stripped */
/* Phase 3 - copy to xkey in little-endian order */
i = 63;
do {
xkey[i] = xkey_p[2 * i] + (xkey_p[2 * i + 1] << 8);
} while (i--);
return 0;
}
/**********************************************************************\
* Encrypt an 8-byte block of plaintext using the given key. *
\**********************************************************************/
WIN32DLL_DEFINE void _mcrypt_encrypt(const word16 * xkey, word16 * plain)
{
word16 x3, x2, x1, x0, i;
#ifdef WORDS_BIGENDIAN
x3 = byteswap16(plain[3]);
x2 = byteswap16(plain[2]);
x1 = byteswap16(plain[1]);
x0 = byteswap16(plain[0]);
#else
x3 = plain[3];
x2 = plain[2];
x1 = plain[1];
x0 = plain[0];
#endif
for (i = 0; i < 16; i++) {
x0 += (x1 & ~x3) + (x2 & x3) + xkey[4 * i + 0];
x0 = rotl16(x0, 1);
x1 += (x2 & ~x0) + (x3 & x0) + xkey[4 * i + 1];
x1 = rotl16(x1, 2);
x2 += (x3 & ~x1) + (x0 & x1) + xkey[4 * i + 2];
x2 = rotl16(x2, 3);
x3 += (x0 & ~x2) + (x1 & x2) + xkey[4 * i + 3];
x3 = rotl16(x3, 5);
if (i == 4 || i == 10) {
x0 += xkey[x3 & 63];
x1 += xkey[x0 & 63];
x2 += xkey[x1 & 63];
x3 += xkey[x2 & 63];
}
}
#ifdef WORDS_BIGENDIAN
plain[0] = byteswap16(x0);
plain[1] = byteswap16(x1);
plain[2] = byteswap16(x2);
plain[3] = byteswap16(x3);
#else
plain[0] = (x0);
plain[1] = (x1);
plain[2] = (x2);
plain[3] = (x3);
#endif
}
/**********************************************************************\
* Decrypt an 8-byte block of ciphertext using the given key. *
\**********************************************************************/
WIN32DLL_DEFINE void _mcrypt_decrypt(const word16 * xkey, word16 * plain)
{
word16 x3, x2, x1, x0, i;
#ifndef WORDS_BIGENDIAN
x3 = plain[3];
x2 = plain[2];
x1 = plain[1];
x0 = plain[0];
#else
x3 = byteswap16(plain[3]);
x2 = byteswap16(plain[2]);
x1 = byteswap16(plain[1]);
x0 = byteswap16(plain[0]);
#endif
i = 15;
do {
x3 = rotr16(x3, 5);
x3 -= (x0 & ~x2) + (x1 & x2) + xkey[4 * i + 3];
x2 = rotr16(x2, 3);
x2 -= (x3 & ~x1) + (x0 & x1) + xkey[4 * i + 2];
x1 = rotr16(x1, 2);
x1 -= (x2 & ~x0) + (x3 & x0) + xkey[4 * i + 1];
x0 = rotr16(x0, 1);
x0 -= (x1 & ~x3) + (x2 & x3) + xkey[4 * i + 0];
if (i == 5 || i == 11) {
x3 -= xkey[x2 & 63];
x2 -= xkey[x1 & 63];
x1 -= xkey[x0 & 63];
x0 -= xkey[x3 & 63];
}
} while (i--);
#ifdef WORDS_BIGENDIAN
plain[0] = byteswap16(x0);
plain[1] = byteswap16(x1);
plain[2] = byteswap16(x2);
plain[3] = byteswap16(x3);
#else
plain[0] = x0;
plain[1] = x1;
plain[2] = x2;
plain[3] = x3;
#endif
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return 64 * sizeof(word16);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 8;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 128;
}
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = 0;
return NULL;
}
WIN32DLL_DEFINE char *_mcrypt_get_algorithms_name()
{
return "RC2";
}
#define CIPHER "becbe4c8e6237a14"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,250 @@
/*
* Copyright (C) 2002 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Library General Public License as published
* by the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _init_mcrypt ctr_LTX__init_mcrypt
#define _mcrypt_set_state ctr_LTX__mcrypt_set_state
#define _mcrypt_get_state ctr_LTX__mcrypt_get_state
#define _end_mcrypt ctr_LTX__end_mcrypt
#define _mcrypt ctr_LTX__mcrypt
#define _mdecrypt ctr_LTX__mdecrypt
#define _has_iv ctr_LTX__has_iv
#define _is_block_mode ctr_LTX__is_block_mode
#define _is_block_algorithm_mode ctr_LTX__is_block_algorithm_mode
#define _mcrypt_get_modes_name ctr_LTX__mcrypt_get_modes_name
#define _mcrypt_mode_get_size ctr_LTX__mcrypt_mode_get_size
#define _mcrypt_mode_version ctr_LTX__mcrypt_mode_version
typedef struct ctr_buf {
byte* enc_counter;
byte* c_counter;
int c_counter_pos;
int blocksize;
} CTR_BUFFER;
/* CTR MODE */
/* This function will add one to the given number (as a byte string).
* has been reached.
*/
static void increase_counter( byte *x, int x_size) {
register int i, y=0;
for (i=x_size-1;i>=0;i--) {
y = 0;
if ( x[i] == 0xff) {
x[i] = 0;
y = 1;
} else x[i]++;
if (y==0) break;
}
return;
}
/* size holds the size of the IV (counter in this mode).
* This is the block size.
*/
int _init_mcrypt( CTR_BUFFER* buf, void *key, int lenofkey, void *IV, int size)
{
buf->c_counter = buf->enc_counter = NULL;
/* For ctr */
buf->c_counter_pos = 0;
buf->blocksize = size;
buf->c_counter=calloc( 1, size);
if (buf->c_counter==NULL) goto freeall;
buf->enc_counter=calloc( 1, size);
if (buf->enc_counter==NULL) goto freeall;
if (IV!=NULL) {
memcpy(buf->enc_counter, IV, size);
memcpy(buf->c_counter, IV, size);
}
/* End ctr */
return 0;
freeall:
free(buf->c_counter);
free(buf->enc_counter);
return -1;
}
int _mcrypt_set_state( CTR_BUFFER* buf, byte *IV, int size)
{
buf->c_counter_pos = IV[0];
memcpy(buf->c_counter, &IV[1], size-1);
memcpy(buf->enc_counter, &IV[1], size-1);
return 0;
}
int _mcrypt_get_state( CTR_BUFFER* buf, byte *IV, int *size)
{
if (*size < buf->blocksize + 1) {
*size = buf->blocksize + 1;
return -1;
}
*size = buf->blocksize + 1;
IV[0] = buf->c_counter_pos;
memcpy( &IV[1], buf->c_counter, buf->blocksize);
return 0;
}
void _end_mcrypt( CTR_BUFFER* buf) {
free(buf->c_counter);
free(buf->enc_counter);
}
//inline
static void xor_stuff( CTR_BUFFER *buf, void* akey, void (*func)(void*,void*), byte* plain, int blocksize, int xor_size)
{
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
if (xor_size == blocksize) {
if (buf->c_counter_pos == 0) {
memcpy( buf->enc_counter, buf->c_counter, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_counter);
memxor( plain, buf->enc_counter, blocksize);
increase_counter( buf->c_counter, blocksize);
} else {
int size = blocksize - buf->c_counter_pos;
memxor( plain, &buf->enc_counter[buf->c_counter_pos],
size);
increase_counter( buf->c_counter, blocksize);
memcpy( buf->enc_counter, buf->c_counter, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_counter);
memxor( &plain[size], buf->enc_counter,
buf->c_counter_pos);
/* buf->c_counter_pos remains the same */
}
} else { /* xor_size != blocksize */
if (buf->c_counter_pos == 0) {
memcpy( buf->enc_counter, buf->c_counter, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_counter);
memxor( plain, buf->enc_counter, xor_size);
buf->c_counter_pos = xor_size;
} else {
int size = blocksize - buf->c_counter_pos;
int min_size = size < xor_size ? size: xor_size;
memxor( plain, &buf->enc_counter[buf->c_counter_pos],
min_size);
buf->c_counter_pos += min_size;
if (min_size >= xor_size)
return;
increase_counter( buf->c_counter, blocksize);
memcpy( buf->enc_counter, buf->c_counter, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_counter);
memxor( &plain[min_size], buf->enc_counter,
xor_size - min_size);
buf->c_counter_pos = xor_size - min_size;
}
}
return;
}
int _mcrypt( CTR_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext can be any size */
byte *plain;
word32 *fplain = plaintext;
int i, j=0;
int modlen;
plain = plaintext;
for (j = 0; j < len / blocksize; j++) {
xor_stuff( buf, akey, func, plain, blocksize, blocksize);
plain += blocksize;
/* Put the new register */
}
modlen = len % blocksize;
if (modlen > 0) {
/* This is only usefull if encrypting the
* final block. Otherwise you'll not be
* able to decrypt it.
*/
xor_stuff( buf, akey, func, plain, blocksize, modlen);
}
return 0;
}
int _mdecrypt( CTR_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext can be any size */
return _mcrypt( buf, plaintext, len, blocksize, akey, func, func2);
}
int _has_iv() { return 1; }
int _is_block_mode() { return 0; }
int _is_block_algorithm_mode() { return 1; }
const char *_mcrypt_get_modes_name() { return "CTR";}
int _mcrypt_mode_get_size () {return sizeof(CTR_BUFFER);}
word32 _mcrypt_mode_version() {
return 20020307;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,545 @@
/*
* $Id: cast-128_sboxes.h,v 1.1 2007/07/19 06:11:48 pizon Exp $
*
* CAST-128 in C
* Written by Steve Reid <sreid@sea-to-sky.net>
* 100% Public Domain - no warranty
* Released 1997.10.11
*/
static const u32 cast_sbox1[256] = {
0x30FB40D4, 0x9FA0FF0B, 0x6BECCD2F, 0x3F258C7A,
0x1E213F2F, 0x9C004DD3, 0x6003E540, 0xCF9FC949,
0xBFD4AF27, 0x88BBBDB5, 0xE2034090, 0x98D09675,
0x6E63A0E0, 0x15C361D2, 0xC2E7661D, 0x22D4FF8E,
0x28683B6F, 0xC07FD059, 0xFF2379C8, 0x775F50E2,
0x43C340D3, 0xDF2F8656, 0x887CA41A, 0xA2D2BD2D,
0xA1C9E0D6, 0x346C4819, 0x61B76D87, 0x22540F2F,
0x2ABE32E1, 0xAA54166B, 0x22568E3A, 0xA2D341D0,
0x66DB40C8, 0xA784392F, 0x004DFF2F, 0x2DB9D2DE,
0x97943FAC, 0x4A97C1D8, 0x527644B7, 0xB5F437A7,
0xB82CBAEF, 0xD751D159, 0x6FF7F0ED, 0x5A097A1F,
0x827B68D0, 0x90ECF52E, 0x22B0C054, 0xBC8E5935,
0x4B6D2F7F, 0x50BB64A2, 0xD2664910, 0xBEE5812D,
0xB7332290, 0xE93B159F, 0xB48EE411, 0x4BFF345D,
0xFD45C240, 0xAD31973F, 0xC4F6D02E, 0x55FC8165,
0xD5B1CAAD, 0xA1AC2DAE, 0xA2D4B76D, 0xC19B0C50,
0x882240F2, 0x0C6E4F38, 0xA4E4BFD7, 0x4F5BA272,
0x564C1D2F, 0xC59C5319, 0xB949E354, 0xB04669FE,
0xB1B6AB8A, 0xC71358DD, 0x6385C545, 0x110F935D,
0x57538AD5, 0x6A390493, 0xE63D37E0, 0x2A54F6B3,
0x3A787D5F, 0x6276A0B5, 0x19A6FCDF, 0x7A42206A,
0x29F9D4D5, 0xF61B1891, 0xBB72275E, 0xAA508167,
0x38901091, 0xC6B505EB, 0x84C7CB8C, 0x2AD75A0F,
0x874A1427, 0xA2D1936B, 0x2AD286AF, 0xAA56D291,
0xD7894360, 0x425C750D, 0x93B39E26, 0x187184C9,
0x6C00B32D, 0x73E2BB14, 0xA0BEBC3C, 0x54623779,
0x64459EAB, 0x3F328B82, 0x7718CF82, 0x59A2CEA6,
0x04EE002E, 0x89FE78E6, 0x3FAB0950, 0x325FF6C2,
0x81383F05, 0x6963C5C8, 0x76CB5AD6, 0xD49974C9,
0xCA180DCF, 0x380782D5, 0xC7FA5CF6, 0x8AC31511,
0x35E79E13, 0x47DA91D0, 0xF40F9086, 0xA7E2419E,
0x31366241, 0x051EF495, 0xAA573B04, 0x4A805D8D,
0x548300D0, 0x00322A3C, 0xBF64CDDF, 0xBA57A68E,
0x75C6372B, 0x50AFD341, 0xA7C13275, 0x915A0BF5,
0x6B54BFAB, 0x2B0B1426, 0xAB4CC9D7, 0x449CCD82,
0xF7FBF265, 0xAB85C5F3, 0x1B55DB94, 0xAAD4E324,
0xCFA4BD3F, 0x2DEAA3E2, 0x9E204D02, 0xC8BD25AC,
0xEADF55B3, 0xD5BD9E98, 0xE31231B2, 0x2AD5AD6C,
0x954329DE, 0xADBE4528, 0xD8710F69, 0xAA51C90F,
0xAA786BF6, 0x22513F1E, 0xAA51A79B, 0x2AD344CC,
0x7B5A41F0, 0xD37CFBAD, 0x1B069505, 0x41ECE491,
0xB4C332E6, 0x032268D4, 0xC9600ACC, 0xCE387E6D,
0xBF6BB16C, 0x6A70FB78, 0x0D03D9C9, 0xD4DF39DE,
0xE01063DA, 0x4736F464, 0x5AD328D8, 0xB347CC96,
0x75BB0FC3, 0x98511BFB, 0x4FFBCC35, 0xB58BCF6A,
0xE11F0ABC, 0xBFC5FE4A, 0xA70AEC10, 0xAC39570A,
0x3F04442F, 0x6188B153, 0xE0397A2E, 0x5727CB79,
0x9CEB418F, 0x1CACD68D, 0x2AD37C96, 0x0175CB9D,
0xC69DFF09, 0xC75B65F0, 0xD9DB40D8, 0xEC0E7779,
0x4744EAD4, 0xB11C3274, 0xDD24CB9E, 0x7E1C54BD,
0xF01144F9, 0xD2240EB1, 0x9675B3FD, 0xA3AC3755,
0xD47C27AF, 0x51C85F4D, 0x56907596, 0xA5BB15E6,
0x580304F0, 0xCA042CF1, 0x011A37EA, 0x8DBFAADB,
0x35BA3E4A, 0x3526FFA0, 0xC37B4D09, 0xBC306ED9,
0x98A52666, 0x5648F725, 0xFF5E569D, 0x0CED63D0,
0x7C63B2CF, 0x700B45E1, 0xD5EA50F1, 0x85A92872,
0xAF1FBDA7, 0xD4234870, 0xA7870BF3, 0x2D3B4D79,
0x42E04198, 0x0CD0EDE7, 0x26470DB8, 0xF881814C,
0x474D6AD7, 0x7C0C5E5C, 0xD1231959, 0x381B7298,
0xF5D2F4DB, 0xAB838653, 0x6E2F1E23, 0x83719C9E,
0xBD91E046, 0x9A56456E, 0xDC39200C, 0x20C8C571,
0x962BDA1C, 0xE1E696FF, 0xB141AB08, 0x7CCA89B9,
0x1A69E783, 0x02CC4843, 0xA2F7C579, 0x429EF47D,
0x427B169C, 0x5AC9F049, 0xDD8F0F00, 0x5C8165BF
};
static const u32 cast_sbox2[256] = {
0x1F201094, 0xEF0BA75B, 0x69E3CF7E, 0x393F4380,
0xFE61CF7A, 0xEEC5207A, 0x55889C94, 0x72FC0651,
0xADA7EF79, 0x4E1D7235, 0xD55A63CE, 0xDE0436BA,
0x99C430EF, 0x5F0C0794, 0x18DCDB7D, 0xA1D6EFF3,
0xA0B52F7B, 0x59E83605, 0xEE15B094, 0xE9FFD909,
0xDC440086, 0xEF944459, 0xBA83CCB3, 0xE0C3CDFB,
0xD1DA4181, 0x3B092AB1, 0xF997F1C1, 0xA5E6CF7B,
0x01420DDB, 0xE4E7EF5B, 0x25A1FF41, 0xE180F806,
0x1FC41080, 0x179BEE7A, 0xD37AC6A9, 0xFE5830A4,
0x98DE8B7F, 0x77E83F4E, 0x79929269, 0x24FA9F7B,
0xE113C85B, 0xACC40083, 0xD7503525, 0xF7EA615F,
0x62143154, 0x0D554B63, 0x5D681121, 0xC866C359,
0x3D63CF73, 0xCEE234C0, 0xD4D87E87, 0x5C672B21,
0x071F6181, 0x39F7627F, 0x361E3084, 0xE4EB573B,
0x602F64A4, 0xD63ACD9C, 0x1BBC4635, 0x9E81032D,
0x2701F50C, 0x99847AB4, 0xA0E3DF79, 0xBA6CF38C,
0x10843094, 0x2537A95E, 0xF46F6FFE, 0xA1FF3B1F,
0x208CFB6A, 0x8F458C74, 0xD9E0A227, 0x4EC73A34,
0xFC884F69, 0x3E4DE8DF, 0xEF0E0088, 0x3559648D,
0x8A45388C, 0x1D804366, 0x721D9BFD, 0xA58684BB,
0xE8256333, 0x844E8212, 0x128D8098, 0xFED33FB4,
0xCE280AE1, 0x27E19BA5, 0xD5A6C252, 0xE49754BD,
0xC5D655DD, 0xEB667064, 0x77840B4D, 0xA1B6A801,
0x84DB26A9, 0xE0B56714, 0x21F043B7, 0xE5D05860,
0x54F03084, 0x066FF472, 0xA31AA153, 0xDADC4755,
0xB5625DBF, 0x68561BE6, 0x83CA6B94, 0x2D6ED23B,
0xECCF01DB, 0xA6D3D0BA, 0xB6803D5C, 0xAF77A709,
0x33B4A34C, 0x397BC8D6, 0x5EE22B95, 0x5F0E5304,
0x81ED6F61, 0x20E74364, 0xB45E1378, 0xDE18639B,
0x881CA122, 0xB96726D1, 0x8049A7E8, 0x22B7DA7B,
0x5E552D25, 0x5272D237, 0x79D2951C, 0xC60D894C,
0x488CB402, 0x1BA4FE5B, 0xA4B09F6B, 0x1CA815CF,
0xA20C3005, 0x8871DF63, 0xB9DE2FCB, 0x0CC6C9E9,
0x0BEEFF53, 0xE3214517, 0xB4542835, 0x9F63293C,
0xEE41E729, 0x6E1D2D7C, 0x50045286, 0x1E6685F3,
0xF33401C6, 0x30A22C95, 0x31A70850, 0x60930F13,
0x73F98417, 0xA1269859, 0xEC645C44, 0x52C877A9,
0xCDFF33A6, 0xA02B1741, 0x7CBAD9A2, 0x2180036F,
0x50D99C08, 0xCB3F4861, 0xC26BD765, 0x64A3F6AB,
0x80342676, 0x25A75E7B, 0xE4E6D1FC, 0x20C710E6,
0xCDF0B680, 0x17844D3B, 0x31EEF84D, 0x7E0824E4,
0x2CCB49EB, 0x846A3BAE, 0x8FF77888, 0xEE5D60F6,
0x7AF75673, 0x2FDD5CDB, 0xA11631C1, 0x30F66F43,
0xB3FAEC54, 0x157FD7FA, 0xEF8579CC, 0xD152DE58,
0xDB2FFD5E, 0x8F32CE19, 0x306AF97A, 0x02F03EF8,
0x99319AD5, 0xC242FA0F, 0xA7E3EBB0, 0xC68E4906,
0xB8DA230C, 0x80823028, 0xDCDEF3C8, 0xD35FB171,
0x088A1BC8, 0xBEC0C560, 0x61A3C9E8, 0xBCA8F54D,
0xC72FEFFA, 0x22822E99, 0x82C570B4, 0xD8D94E89,
0x8B1C34BC, 0x301E16E6, 0x273BE979, 0xB0FFEAA6,
0x61D9B8C6, 0x00B24869, 0xB7FFCE3F, 0x08DC283B,
0x43DAF65A, 0xF7E19798, 0x7619B72F, 0x8F1C9BA4,
0xDC8637A0, 0x16A7D3B1, 0x9FC393B7, 0xA7136EEB,
0xC6BCC63E, 0x1A513742, 0xEF6828BC, 0x520365D6,
0x2D6A77AB, 0x3527ED4B, 0x821FD216, 0x095C6E2E,
0xDB92F2FB, 0x5EEA29CB, 0x145892F5, 0x91584F7F,
0x5483697B, 0x2667A8CC, 0x85196048, 0x8C4BACEA,
0x833860D4, 0x0D23E0F9, 0x6C387E8A, 0x0AE6D249,
0xB284600C, 0xD835731D, 0xDCB1C647, 0xAC4C56EA,
0x3EBD81B3, 0x230EABB0, 0x6438BC87, 0xF0B5B1FA,
0x8F5EA2B3, 0xFC184642, 0x0A036B7A, 0x4FB089BD,
0x649DA589, 0xA345415E, 0x5C038323, 0x3E5D3BB9,
0x43D79572, 0x7E6DD07C, 0x06DFDF1E, 0x6C6CC4EF,
0x7160A539, 0x73BFBE70, 0x83877605, 0x4523ECF1
};
static const u32 cast_sbox3[256] = {
0x8DEFC240, 0x25FA5D9F, 0xEB903DBF, 0xE810C907,
0x47607FFF, 0x369FE44B, 0x8C1FC644, 0xAECECA90,
0xBEB1F9BF, 0xEEFBCAEA, 0xE8CF1950, 0x51DF07AE,
0x920E8806, 0xF0AD0548, 0xE13C8D83, 0x927010D5,
0x11107D9F, 0x07647DB9, 0xB2E3E4D4, 0x3D4F285E,
0xB9AFA820, 0xFADE82E0, 0xA067268B, 0x8272792E,
0x553FB2C0, 0x489AE22B, 0xD4EF9794, 0x125E3FBC,
0x21FFFCEE, 0x825B1BFD, 0x9255C5ED, 0x1257A240,
0x4E1A8302, 0xBAE07FFF, 0x528246E7, 0x8E57140E,
0x3373F7BF, 0x8C9F8188, 0xA6FC4EE8, 0xC982B5A5,
0xA8C01DB7, 0x579FC264, 0x67094F31, 0xF2BD3F5F,
0x40FFF7C1, 0x1FB78DFC, 0x8E6BD2C1, 0x437BE59B,
0x99B03DBF, 0xB5DBC64B, 0x638DC0E6, 0x55819D99,
0xA197C81C, 0x4A012D6E, 0xC5884A28, 0xCCC36F71,
0xB843C213, 0x6C0743F1, 0x8309893C, 0x0FEDDD5F,
0x2F7FE850, 0xD7C07F7E, 0x02507FBF, 0x5AFB9A04,
0xA747D2D0, 0x1651192E, 0xAF70BF3E, 0x58C31380,
0x5F98302E, 0x727CC3C4, 0x0A0FB402, 0x0F7FEF82,
0x8C96FDAD, 0x5D2C2AAE, 0x8EE99A49, 0x50DA88B8,
0x8427F4A0, 0x1EAC5790, 0x796FB449, 0x8252DC15,
0xEFBD7D9B, 0xA672597D, 0xADA840D8, 0x45F54504,
0xFA5D7403, 0xE83EC305, 0x4F91751A, 0x925669C2,
0x23EFE941, 0xA903F12E, 0x60270DF2, 0x0276E4B6,
0x94FD6574, 0x927985B2, 0x8276DBCB, 0x02778176,
0xF8AF918D, 0x4E48F79E, 0x8F616DDF, 0xE29D840E,
0x842F7D83, 0x340CE5C8, 0x96BBB682, 0x93B4B148,
0xEF303CAB, 0x984FAF28, 0x779FAF9B, 0x92DC560D,
0x224D1E20, 0x8437AA88, 0x7D29DC96, 0x2756D3DC,
0x8B907CEE, 0xB51FD240, 0xE7C07CE3, 0xE566B4A1,
0xC3E9615E, 0x3CF8209D, 0x6094D1E3, 0xCD9CA341,
0x5C76460E, 0x00EA983B, 0xD4D67881, 0xFD47572C,
0xF76CEDD9, 0xBDA8229C, 0x127DADAA, 0x438A074E,
0x1F97C090, 0x081BDB8A, 0x93A07EBE, 0xB938CA15,
0x97B03CFF, 0x3DC2C0F8, 0x8D1AB2EC, 0x64380E51,
0x68CC7BFB, 0xD90F2788, 0x12490181, 0x5DE5FFD4,
0xDD7EF86A, 0x76A2E214, 0xB9A40368, 0x925D958F,
0x4B39FFFA, 0xBA39AEE9, 0xA4FFD30B, 0xFAF7933B,
0x6D498623, 0x193CBCFA, 0x27627545, 0x825CF47A,
0x61BD8BA0, 0xD11E42D1, 0xCEAD04F4, 0x127EA392,
0x10428DB7, 0x8272A972, 0x9270C4A8, 0x127DE50B,
0x285BA1C8, 0x3C62F44F, 0x35C0EAA5, 0xE805D231,
0x428929FB, 0xB4FCDF82, 0x4FB66A53, 0x0E7DC15B,
0x1F081FAB, 0x108618AE, 0xFCFD086D, 0xF9FF2889,
0x694BCC11, 0x236A5CAE, 0x12DECA4D, 0x2C3F8CC5,
0xD2D02DFE, 0xF8EF5896, 0xE4CF52DA, 0x95155B67,
0x494A488C, 0xB9B6A80C, 0x5C8F82BC, 0x89D36B45,
0x3A609437, 0xEC00C9A9, 0x44715253, 0x0A874B49,
0xD773BC40, 0x7C34671C, 0x02717EF6, 0x4FEB5536,
0xA2D02FFF, 0xD2BF60C4, 0xD43F03C0, 0x50B4EF6D,
0x07478CD1, 0x006E1888, 0xA2E53F55, 0xB9E6D4BC,
0xA2048016, 0x97573833, 0xD7207D67, 0xDE0F8F3D,
0x72F87B33, 0xABCC4F33, 0x7688C55D, 0x7B00A6B0,
0x947B0001, 0x570075D2, 0xF9BB88F8, 0x8942019E,
0x4264A5FF, 0x856302E0, 0x72DBD92B, 0xEE971B69,
0x6EA22FDE, 0x5F08AE2B, 0xAF7A616D, 0xE5C98767,
0xCF1FEBD2, 0x61EFC8C2, 0xF1AC2571, 0xCC8239C2,
0x67214CB8, 0xB1E583D1, 0xB7DC3E62, 0x7F10BDCE,
0xF90A5C38, 0x0FF0443D, 0x606E6DC6, 0x60543A49,
0x5727C148, 0x2BE98A1D, 0x8AB41738, 0x20E1BE24,
0xAF96DA0F, 0x68458425, 0x99833BE5, 0x600D457D,
0x282F9350, 0x8334B362, 0xD91D1120, 0x2B6D8DA0,
0x642B1E31, 0x9C305A00, 0x52BCE688, 0x1B03588A,
0xF7BAEFD5, 0x4142ED9C, 0xA4315C11, 0x83323EC5,
0xDFEF4636, 0xA133C501, 0xE9D3531C, 0xEE353783
};
static const u32 cast_sbox4[256] = {
0x9DB30420, 0x1FB6E9DE, 0xA7BE7BEF, 0xD273A298,
0x4A4F7BDB, 0x64AD8C57, 0x85510443, 0xFA020ED1,
0x7E287AFF, 0xE60FB663, 0x095F35A1, 0x79EBF120,
0xFD059D43, 0x6497B7B1, 0xF3641F63, 0x241E4ADF,
0x28147F5F, 0x4FA2B8CD, 0xC9430040, 0x0CC32220,
0xFDD30B30, 0xC0A5374F, 0x1D2D00D9, 0x24147B15,
0xEE4D111A, 0x0FCA5167, 0x71FF904C, 0x2D195FFE,
0x1A05645F, 0x0C13FEFE, 0x081B08CA, 0x05170121,
0x80530100, 0xE83E5EFE, 0xAC9AF4F8, 0x7FE72701,
0xD2B8EE5F, 0x06DF4261, 0xBB9E9B8A, 0x7293EA25,
0xCE84FFDF, 0xF5718801, 0x3DD64B04, 0xA26F263B,
0x7ED48400, 0x547EEBE6, 0x446D4CA0, 0x6CF3D6F5,
0x2649ABDF, 0xAEA0C7F5, 0x36338CC1, 0x503F7E93,
0xD3772061, 0x11B638E1, 0x72500E03, 0xF80EB2BB,
0xABE0502E, 0xEC8D77DE, 0x57971E81, 0xE14F6746,
0xC9335400, 0x6920318F, 0x081DBB99, 0xFFC304A5,
0x4D351805, 0x7F3D5CE3, 0xA6C866C6, 0x5D5BCCA9,
0xDAEC6FEA, 0x9F926F91, 0x9F46222F, 0x3991467D,
0xA5BF6D8E, 0x1143C44F, 0x43958302, 0xD0214EEB,
0x022083B8, 0x3FB6180C, 0x18F8931E, 0x281658E6,
0x26486E3E, 0x8BD78A70, 0x7477E4C1, 0xB506E07C,
0xF32D0A25, 0x79098B02, 0xE4EABB81, 0x28123B23,
0x69DEAD38, 0x1574CA16, 0xDF871B62, 0x211C40B7,
0xA51A9EF9, 0x0014377B, 0x041E8AC8, 0x09114003,
0xBD59E4D2, 0xE3D156D5, 0x4FE876D5, 0x2F91A340,
0x557BE8DE, 0x00EAE4A7, 0x0CE5C2EC, 0x4DB4BBA6,
0xE756BDFF, 0xDD3369AC, 0xEC17B035, 0x06572327,
0x99AFC8B0, 0x56C8C391, 0x6B65811C, 0x5E146119,
0x6E85CB75, 0xBE07C002, 0xC2325577, 0x893FF4EC,
0x5BBFC92D, 0xD0EC3B25, 0xB7801AB7, 0x8D6D3B24,
0x20C763EF, 0xC366A5FC, 0x9C382880, 0x0ACE3205,
0xAAC9548A, 0xECA1D7C7, 0x041AFA32, 0x1D16625A,
0x6701902C, 0x9B757A54, 0x31D477F7, 0x9126B031,
0x36CC6FDB, 0xC70B8B46, 0xD9E66A48, 0x56E55A79,
0x026A4CEB, 0x52437EFF, 0x2F8F76B4, 0x0DF980A5,
0x8674CDE3, 0xEDDA04EB, 0x17A9BE04, 0x2C18F4DF,
0xB7747F9D, 0xAB2AF7B4, 0xEFC34D20, 0x2E096B7C,
0x1741A254, 0xE5B6A035, 0x213D42F6, 0x2C1C7C26,
0x61C2F50F, 0x6552DAF9, 0xD2C231F8, 0x25130F69,
0xD8167FA2, 0x0418F2C8, 0x001A96A6, 0x0D1526AB,
0x63315C21, 0x5E0A72EC, 0x49BAFEFD, 0x187908D9,
0x8D0DBD86, 0x311170A7, 0x3E9B640C, 0xCC3E10D7,
0xD5CAD3B6, 0x0CAEC388, 0xF73001E1, 0x6C728AFF,
0x71EAE2A1, 0x1F9AF36E, 0xCFCBD12F, 0xC1DE8417,
0xAC07BE6B, 0xCB44A1D8, 0x8B9B0F56, 0x013988C3,
0xB1C52FCA, 0xB4BE31CD, 0xD8782806, 0x12A3A4E2,
0x6F7DE532, 0x58FD7EB6, 0xD01EE900, 0x24ADFFC2,
0xF4990FC5, 0x9711AAC5, 0x001D7B95, 0x82E5E7D2,
0x109873F6, 0x00613096, 0xC32D9521, 0xADA121FF,
0x29908415, 0x7FBB977F, 0xAF9EB3DB, 0x29C9ED2A,
0x5CE2A465, 0xA730F32C, 0xD0AA3FE8, 0x8A5CC091,
0xD49E2CE7, 0x0CE454A9, 0xD60ACD86, 0x015F1919,
0x77079103, 0xDEA03AF6, 0x78A8565E, 0xDEE356DF,
0x21F05CBE, 0x8B75E387, 0xB3C50651, 0xB8A5C3EF,
0xD8EEB6D2, 0xE523BE77, 0xC2154529, 0x2F69EFDF,
0xAFE67AFB, 0xF470C4B2, 0xF3E0EB5B, 0xD6CC9876,
0x39E4460C, 0x1FDA8538, 0x1987832F, 0xCA007367,
0xA99144F8, 0x296B299E, 0x492FC295, 0x9266BEAB,
0xB5676E69, 0x9BD3DDDA, 0xDF7E052F, 0xDB25701C,
0x1B5E51EE, 0xF65324E6, 0x6AFCE36C, 0x0316CC04,
0x8644213E, 0xB7DC59D0, 0x7965291F, 0xCCD6FD43,
0x41823979, 0x932BCDF6, 0xB657C34D, 0x4EDFD282,
0x7AE5290C, 0x3CB9536B, 0x851E20FE, 0x9833557E,
0x13ECF0B0, 0xD3FFB372, 0x3F85C5C1, 0x0AEF7ED2
};
static const u32 cast_sbox5[256] = {
0x7EC90C04, 0x2C6E74B9, 0x9B0E66DF, 0xA6337911,
0xB86A7FFF, 0x1DD358F5, 0x44DD9D44, 0x1731167F,
0x08FBF1FA, 0xE7F511CC, 0xD2051B00, 0x735ABA00,
0x2AB722D8, 0x386381CB, 0xACF6243A, 0x69BEFD7A,
0xE6A2E77F, 0xF0C720CD, 0xC4494816, 0xCCF5C180,
0x38851640, 0x15B0A848, 0xE68B18CB, 0x4CAADEFF,
0x5F480A01, 0x0412B2AA, 0x259814FC, 0x41D0EFE2,
0x4E40B48D, 0x248EB6FB, 0x8DBA1CFE, 0x41A99B02,
0x1A550A04, 0xBA8F65CB, 0x7251F4E7, 0x95A51725,
0xC106ECD7, 0x97A5980A, 0xC539B9AA, 0x4D79FE6A,
0xF2F3F763, 0x68AF8040, 0xED0C9E56, 0x11B4958B,
0xE1EB5A88, 0x8709E6B0, 0xD7E07156, 0x4E29FEA7,
0x6366E52D, 0x02D1C000, 0xC4AC8E05, 0x9377F571,
0x0C05372A, 0x578535F2, 0x2261BE02, 0xD642A0C9,
0xDF13A280, 0x74B55BD2, 0x682199C0, 0xD421E5EC,
0x53FB3CE8, 0xC8ADEDB3, 0x28A87FC9, 0x3D959981,
0x5C1FF900, 0xFE38D399, 0x0C4EFF0B, 0x062407EA,
0xAA2F4FB1, 0x4FB96976, 0x90C79505, 0xB0A8A774,
0xEF55A1FF, 0xE59CA2C2, 0xA6B62D27, 0xE66A4263,
0xDF65001F, 0x0EC50966, 0xDFDD55BC, 0x29DE0655,
0x911E739A, 0x17AF8975, 0x32C7911C, 0x89F89468,
0x0D01E980, 0x524755F4, 0x03B63CC9, 0x0CC844B2,
0xBCF3F0AA, 0x87AC36E9, 0xE53A7426, 0x01B3D82B,
0x1A9E7449, 0x64EE2D7E, 0xCDDBB1DA, 0x01C94910,
0xB868BF80, 0x0D26F3FD, 0x9342EDE7, 0x04A5C284,
0x636737B6, 0x50F5B616, 0xF24766E3, 0x8ECA36C1,
0x136E05DB, 0xFEF18391, 0xFB887A37, 0xD6E7F7D4,
0xC7FB7DC9, 0x3063FCDF, 0xB6F589DE, 0xEC2941DA,
0x26E46695, 0xB7566419, 0xF654EFC5, 0xD08D58B7,
0x48925401, 0xC1BACB7F, 0xE5FF550F, 0xB6083049,
0x5BB5D0E8, 0x87D72E5A, 0xAB6A6EE1, 0x223A66CE,
0xC62BF3CD, 0x9E0885F9, 0x68CB3E47, 0x086C010F,
0xA21DE820, 0xD18B69DE, 0xF3F65777, 0xFA02C3F6,
0x407EDAC3, 0xCBB3D550, 0x1793084D, 0xB0D70EBA,
0x0AB378D5, 0xD951FB0C, 0xDED7DA56, 0x4124BBE4,
0x94CA0B56, 0x0F5755D1, 0xE0E1E56E, 0x6184B5BE,
0x580A249F, 0x94F74BC0, 0xE327888E, 0x9F7B5561,
0xC3DC0280, 0x05687715, 0x646C6BD7, 0x44904DB3,
0x66B4F0A3, 0xC0F1648A, 0x697ED5AF, 0x49E92FF6,
0x309E374F, 0x2CB6356A, 0x85808573, 0x4991F840,
0x76F0AE02, 0x083BE84D, 0x28421C9A, 0x44489406,
0x736E4CB8, 0xC1092910, 0x8BC95FC6, 0x7D869CF4,
0x134F616F, 0x2E77118D, 0xB31B2BE1, 0xAA90B472,
0x3CA5D717, 0x7D161BBA, 0x9CAD9010, 0xAF462BA2,
0x9FE459D2, 0x45D34559, 0xD9F2DA13, 0xDBC65487,
0xF3E4F94E, 0x176D486F, 0x097C13EA, 0x631DA5C7,
0x445F7382, 0x175683F4, 0xCDC66A97, 0x70BE0288,
0xB3CDCF72, 0x6E5DD2F3, 0x20936079, 0x459B80A5,
0xBE60E2DB, 0xA9C23101, 0xEBA5315C, 0x224E42F2,
0x1C5C1572, 0xF6721B2C, 0x1AD2FFF3, 0x8C25404E,
0x324ED72F, 0x4067B7FD, 0x0523138E, 0x5CA3BC78,
0xDC0FD66E, 0x75922283, 0x784D6B17, 0x58EBB16E,
0x44094F85, 0x3F481D87, 0xFCFEAE7B, 0x77B5FF76,
0x8C2302BF, 0xAAF47556, 0x5F46B02A, 0x2B092801,
0x3D38F5F7, 0x0CA81F36, 0x52AF4A8A, 0x66D5E7C0,
0xDF3B0874, 0x95055110, 0x1B5AD7A8, 0xF61ED5AD,
0x6CF6E479, 0x20758184, 0xD0CEFA65, 0x88F7BE58,
0x4A046826, 0x0FF6F8F3, 0xA09C7F70, 0x5346ABA0,
0x5CE96C28, 0xE176EDA3, 0x6BAC307F, 0x376829D2,
0x85360FA9, 0x17E3FE2A, 0x24B79767, 0xF5A96B20,
0xD6CD2595, 0x68FF1EBF, 0x7555442C, 0xF19F06BE,
0xF9E0659A, 0xEEB9491D, 0x34010718, 0xBB30CAB8,
0xE822FE15, 0x88570983, 0x750E6249, 0xDA627E55,
0x5E76FFA8, 0xB1534546, 0x6D47DE08, 0xEFE9E7D4
};
static const u32 cast_sbox6[256] = {
0xF6FA8F9D, 0x2CAC6CE1, 0x4CA34867, 0xE2337F7C,
0x95DB08E7, 0x016843B4, 0xECED5CBC, 0x325553AC,
0xBF9F0960, 0xDFA1E2ED, 0x83F0579D, 0x63ED86B9,
0x1AB6A6B8, 0xDE5EBE39, 0xF38FF732, 0x8989B138,
0x33F14961, 0xC01937BD, 0xF506C6DA, 0xE4625E7E,
0xA308EA99, 0x4E23E33C, 0x79CBD7CC, 0x48A14367,
0xA3149619, 0xFEC94BD5, 0xA114174A, 0xEAA01866,
0xA084DB2D, 0x09A8486F, 0xA888614A, 0x2900AF98,
0x01665991, 0xE1992863, 0xC8F30C60, 0x2E78EF3C,
0xD0D51932, 0xCF0FEC14, 0xF7CA07D2, 0xD0A82072,
0xFD41197E, 0x9305A6B0, 0xE86BE3DA, 0x74BED3CD,
0x372DA53C, 0x4C7F4448, 0xDAB5D440, 0x6DBA0EC3,
0x083919A7, 0x9FBAEED9, 0x49DBCFB0, 0x4E670C53,
0x5C3D9C01, 0x64BDB941, 0x2C0E636A, 0xBA7DD9CD,
0xEA6F7388, 0xE70BC762, 0x35F29ADB, 0x5C4CDD8D,
0xF0D48D8C, 0xB88153E2, 0x08A19866, 0x1AE2EAC8,
0x284CAF89, 0xAA928223, 0x9334BE53, 0x3B3A21BF,
0x16434BE3, 0x9AEA3906, 0xEFE8C36E, 0xF890CDD9,
0x80226DAE, 0xC340A4A3, 0xDF7E9C09, 0xA694A807,
0x5B7C5ECC, 0x221DB3A6, 0x9A69A02F, 0x68818A54,
0xCEB2296F, 0x53C0843A, 0xFE893655, 0x25BFE68A,
0xB4628ABC, 0xCF222EBF, 0x25AC6F48, 0xA9A99387,
0x53BDDB65, 0xE76FFBE7, 0xE967FD78, 0x0BA93563,
0x8E342BC1, 0xE8A11BE9, 0x4980740D, 0xC8087DFC,
0x8DE4BF99, 0xA11101A0, 0x7FD37975, 0xDA5A26C0,
0xE81F994F, 0x9528CD89, 0xFD339FED, 0xB87834BF,
0x5F04456D, 0x22258698, 0xC9C4C83B, 0x2DC156BE,
0x4F628DAA, 0x57F55EC5, 0xE2220ABE, 0xD2916EBF,
0x4EC75B95, 0x24F2C3C0, 0x42D15D99, 0xCD0D7FA0,
0x7B6E27FF, 0xA8DC8AF0, 0x7345C106, 0xF41E232F,
0x35162386, 0xE6EA8926, 0x3333B094, 0x157EC6F2,
0x372B74AF, 0x692573E4, 0xE9A9D848, 0xF3160289,
0x3A62EF1D, 0xA787E238, 0xF3A5F676, 0x74364853,
0x20951063, 0x4576698D, 0xB6FAD407, 0x592AF950,
0x36F73523, 0x4CFB6E87, 0x7DA4CEC0, 0x6C152DAA,
0xCB0396A8, 0xC50DFE5D, 0xFCD707AB, 0x0921C42F,
0x89DFF0BB, 0x5FE2BE78, 0x448F4F33, 0x754613C9,
0x2B05D08D, 0x48B9D585, 0xDC049441, 0xC8098F9B,
0x7DEDE786, 0xC39A3373, 0x42410005, 0x6A091751,
0x0EF3C8A6, 0x890072D6, 0x28207682, 0xA9A9F7BE,
0xBF32679D, 0xD45B5B75, 0xB353FD00, 0xCBB0E358,
0x830F220A, 0x1F8FB214, 0xD372CF08, 0xCC3C4A13,
0x8CF63166, 0x061C87BE, 0x88C98F88, 0x6062E397,
0x47CF8E7A, 0xB6C85283, 0x3CC2ACFB, 0x3FC06976,
0x4E8F0252, 0x64D8314D, 0xDA3870E3, 0x1E665459,
0xC10908F0, 0x513021A5, 0x6C5B68B7, 0x822F8AA0,
0x3007CD3E, 0x74719EEF, 0xDC872681, 0x073340D4,
0x7E432FD9, 0x0C5EC241, 0x8809286C, 0xF592D891,
0x08A930F6, 0x957EF305, 0xB7FBFFBD, 0xC266E96F,
0x6FE4AC98, 0xB173ECC0, 0xBC60B42A, 0x953498DA,
0xFBA1AE12, 0x2D4BD736, 0x0F25FAAB, 0xA4F3FCEB,
0xE2969123, 0x257F0C3D, 0x9348AF49, 0x361400BC,
0xE8816F4A, 0x3814F200, 0xA3F94043, 0x9C7A54C2,
0xBC704F57, 0xDA41E7F9, 0xC25AD33A, 0x54F4A084,
0xB17F5505, 0x59357CBE, 0xEDBD15C8, 0x7F97C5AB,
0xBA5AC7B5, 0xB6F6DEAF, 0x3A479C3A, 0x5302DA25,
0x653D7E6A, 0x54268D49, 0x51A477EA, 0x5017D55B,
0xD7D25D88, 0x44136C76, 0x0404A8C8, 0xB8E5A121,
0xB81A928A, 0x60ED5869, 0x97C55B96, 0xEAEC991B,
0x29935913, 0x01FDB7F1, 0x088E8DFA, 0x9AB6F6F5,
0x3B4CBF9F, 0x4A5DE3AB, 0xE6051D35, 0xA0E1D855,
0xD36B4CF1, 0xF544EDEB, 0xB0E93524, 0xBEBB8FBD,
0xA2D762CF, 0x49C92F54, 0x38B5F331, 0x7128A454,
0x48392905, 0xA65B1DB8, 0x851C97BD, 0xD675CF2F
};
static const u32 cast_sbox7[256] = {
0x85E04019, 0x332BF567, 0x662DBFFF, 0xCFC65693,
0x2A8D7F6F, 0xAB9BC912, 0xDE6008A1, 0x2028DA1F,
0x0227BCE7, 0x4D642916, 0x18FAC300, 0x50F18B82,
0x2CB2CB11, 0xB232E75C, 0x4B3695F2, 0xB28707DE,
0xA05FBCF6, 0xCD4181E9, 0xE150210C, 0xE24EF1BD,
0xB168C381, 0xFDE4E789, 0x5C79B0D8, 0x1E8BFD43,
0x4D495001, 0x38BE4341, 0x913CEE1D, 0x92A79C3F,
0x089766BE, 0xBAEEADF4, 0x1286BECF, 0xB6EACB19,
0x2660C200, 0x7565BDE4, 0x64241F7A, 0x8248DCA9,
0xC3B3AD66, 0x28136086, 0x0BD8DFA8, 0x356D1CF2,
0x107789BE, 0xB3B2E9CE, 0x0502AA8F, 0x0BC0351E,
0x166BF52A, 0xEB12FF82, 0xE3486911, 0xD34D7516,
0x4E7B3AFF, 0x5F43671B, 0x9CF6E037, 0x4981AC83,
0x334266CE, 0x8C9341B7, 0xD0D854C0, 0xCB3A6C88,
0x47BC2829, 0x4725BA37, 0xA66AD22B, 0x7AD61F1E,
0x0C5CBAFA, 0x4437F107, 0xB6E79962, 0x42D2D816,
0x0A961288, 0xE1A5C06E, 0x13749E67, 0x72FC081A,
0xB1D139F7, 0xF9583745, 0xCF19DF58, 0xBEC3F756,
0xC06EBA30, 0x07211B24, 0x45C28829, 0xC95E317F,
0xBC8EC511, 0x38BC46E9, 0xC6E6FA14, 0xBAE8584A,
0xAD4EBC46, 0x468F508B, 0x7829435F, 0xF124183B,
0x821DBA9F, 0xAFF60FF4, 0xEA2C4E6D, 0x16E39264,
0x92544A8B, 0x009B4FC3, 0xABA68CED, 0x9AC96F78,
0x06A5B79A, 0xB2856E6E, 0x1AEC3CA9, 0xBE838688,
0x0E0804E9, 0x55F1BE56, 0xE7E5363B, 0xB3A1F25D,
0xF7DEBB85, 0x61FE033C, 0x16746233, 0x3C034C28,
0xDA6D0C74, 0x79AAC56C, 0x3CE4E1AD, 0x51F0C802,
0x98F8F35A, 0x1626A49F, 0xEED82B29, 0x1D382FE3,
0x0C4FB99A, 0xBB325778, 0x3EC6D97B, 0x6E77A6A9,
0xCB658B5C, 0xD45230C7, 0x2BD1408B, 0x60C03EB7,
0xB9068D78, 0xA33754F4, 0xF430C87D, 0xC8A71302,
0xB96D8C32, 0xEBD4E7BE, 0xBE8B9D2D, 0x7979FB06,
0xE7225308, 0x8B75CF77, 0x11EF8DA4, 0xE083C858,
0x8D6B786F, 0x5A6317A6, 0xFA5CF7A0, 0x5DDA0033,
0xF28EBFB0, 0xF5B9C310, 0xA0EAC280, 0x08B9767A,
0xA3D9D2B0, 0x79D34217, 0x021A718D, 0x9AC6336A,
0x2711FD60, 0x438050E3, 0x069908A8, 0x3D7FEDC4,
0x826D2BEF, 0x4EEB8476, 0x488DCF25, 0x36C9D566,
0x28E74E41, 0xC2610ACA, 0x3D49A9CF, 0xBAE3B9DF,
0xB65F8DE6, 0x92AEAF64, 0x3AC7D5E6, 0x9EA80509,
0xF22B017D, 0xA4173F70, 0xDD1E16C3, 0x15E0D7F9,
0x50B1B887, 0x2B9F4FD5, 0x625ABA82, 0x6A017962,
0x2EC01B9C, 0x15488AA9, 0xD716E740, 0x40055A2C,
0x93D29A22, 0xE32DBF9A, 0x058745B9, 0x3453DC1E,
0xD699296E, 0x496CFF6F, 0x1C9F4986, 0xDFE2ED07,
0xB87242D1, 0x19DE7EAE, 0x053E561A, 0x15AD6F8C,
0x66626C1C, 0x7154C24C, 0xEA082B2A, 0x93EB2939,
0x17DCB0F0, 0x58D4F2AE, 0x9EA294FB, 0x52CF564C,
0x9883FE66, 0x2EC40581, 0x763953C3, 0x01D6692E,
0xD3A0C108, 0xA1E7160E, 0xE4F2DFA6, 0x693ED285,
0x74904698, 0x4C2B0EDD, 0x4F757656, 0x5D393378,
0xA132234F, 0x3D321C5D, 0xC3F5E194, 0x4B269301,
0xC79F022F, 0x3C997E7E, 0x5E4F9504, 0x3FFAFBBD,
0x76F7AD0E, 0x296693F4, 0x3D1FCE6F, 0xC61E45BE,
0xD3B5AB34, 0xF72BF9B7, 0x1B0434C0, 0x4E72B567,
0x5592A33D, 0xB5229301, 0xCFD2A87F, 0x60AEB767,
0x1814386B, 0x30BCC33D, 0x38A0C07D, 0xFD1606F2,
0xC363519B, 0x589DD390, 0x5479F8E6, 0x1CB8D647,
0x97FD61A9, 0xEA7759F4, 0x2D57539D, 0x569A58CF,
0xE84E63AD, 0x462E1B78, 0x6580F87E, 0xF3817914,
0x91DA55F4, 0x40A230F3, 0xD1988F35, 0xB6E318D2,
0x3FFA50BC, 0x3D40F021, 0xC3C0BDAE, 0x4958C24C,
0x518F36B2, 0x84B1D370, 0x0FEDCE83, 0x878DDADA,
0xF2A279C7, 0x94E01BE8, 0x90716F4B, 0x954B8AA3
};
static const u32 cast_sbox8[256] = {
0xE216300D, 0xBBDDFFFC, 0xA7EBDABD, 0x35648095,
0x7789F8B7, 0xE6C1121B, 0x0E241600, 0x052CE8B5,
0x11A9CFB0, 0xE5952F11, 0xECE7990A, 0x9386D174,
0x2A42931C, 0x76E38111, 0xB12DEF3A, 0x37DDDDFC,
0xDE9ADEB1, 0x0A0CC32C, 0xBE197029, 0x84A00940,
0xBB243A0F, 0xB4D137CF, 0xB44E79F0, 0x049EEDFD,
0x0B15A15D, 0x480D3168, 0x8BBBDE5A, 0x669DED42,
0xC7ECE831, 0x3F8F95E7, 0x72DF191B, 0x7580330D,
0x94074251, 0x5C7DCDFA, 0xABBE6D63, 0xAA402164,
0xB301D40A, 0x02E7D1CA, 0x53571DAE, 0x7A3182A2,
0x12A8DDEC, 0xFDAA335D, 0x176F43E8, 0x71FB46D4,
0x38129022, 0xCE949AD4, 0xB84769AD, 0x965BD862,
0x82F3D055, 0x66FB9767, 0x15B80B4E, 0x1D5B47A0,
0x4CFDE06F, 0xC28EC4B8, 0x57E8726E, 0x647A78FC,
0x99865D44, 0x608BD593, 0x6C200E03, 0x39DC5FF6,
0x5D0B00A3, 0xAE63AFF2, 0x7E8BD632, 0x70108C0C,
0xBBD35049, 0x2998DF04, 0x980CF42A, 0x9B6DF491,
0x9E7EDD53, 0x06918548, 0x58CB7E07, 0x3B74EF2E,
0x522FFFB1, 0xD24708CC, 0x1C7E27CD, 0xA4EB215B,
0x3CF1D2E2, 0x19B47A38, 0x424F7618, 0x35856039,
0x9D17DEE7, 0x27EB35E6, 0xC9AFF67B, 0x36BAF5B8,
0x09C467CD, 0xC18910B1, 0xE11DBF7B, 0x06CD1AF8,
0x7170C608, 0x2D5E3354, 0xD4DE495A, 0x64C6D006,
0xBCC0C62C, 0x3DD00DB3, 0x708F8F34, 0x77D51B42,
0x264F620F, 0x24B8D2BF, 0x15C1B79E, 0x46A52564,
0xF8D7E54E, 0x3E378160, 0x7895CDA5, 0x859C15A5,
0xE6459788, 0xC37BC75F, 0xDB07BA0C, 0x0676A3AB,
0x7F229B1E, 0x31842E7B, 0x24259FD7, 0xF8BEF472,
0x835FFCB8, 0x6DF4C1F2, 0x96F5B195, 0xFD0AF0FC,
0xB0FE134C, 0xE2506D3D, 0x4F9B12EA, 0xF215F225,
0xA223736F, 0x9FB4C428, 0x25D04979, 0x34C713F8,
0xC4618187, 0xEA7A6E98, 0x7CD16EFC, 0x1436876C,
0xF1544107, 0xBEDEEE14, 0x56E9AF27, 0xA04AA441,
0x3CF7C899, 0x92ECBAE6, 0xDD67016D, 0x151682EB,
0xA842EEDF, 0xFDBA60B4, 0xF1907B75, 0x20E3030F,
0x24D8C29E, 0xE139673B, 0xEFA63FB8, 0x71873054,
0xB6F2CF3B, 0x9F326442, 0xCB15A4CC, 0xB01A4504,
0xF1E47D8D, 0x844A1BE5, 0xBAE7DFDC, 0x42CBDA70,
0xCD7DAE0A, 0x57E85B7A, 0xD53F5AF6, 0x20CF4D8C,
0xCEA4D428, 0x79D130A4, 0x3486EBFB, 0x33D3CDDC,
0x77853B53, 0x37EFFCB5, 0xC5068778, 0xE580B3E6,
0x4E68B8F4, 0xC5C8B37E, 0x0D809EA2, 0x398FEB7C,
0x132A4F94, 0x43B7950E, 0x2FEE7D1C, 0x223613BD,
0xDD06CAA2, 0x37DF932B, 0xC4248289, 0xACF3EBC3,
0x5715F6B7, 0xEF3478DD, 0xF267616F, 0xC148CBE4,
0x9052815E, 0x5E410FAB, 0xB48A2465, 0x2EDA7FA4,
0xE87B40E4, 0xE98EA084, 0x5889E9E1, 0xEFD390FC,
0xDD07D35B, 0xDB485694, 0x38D7E5B2, 0x57720101,
0x730EDEBC, 0x5B643113, 0x94917E4F, 0x503C2FBA,
0x646F1282, 0x7523D24A, 0xE0779695, 0xF9C17A8F,
0x7A5B2121, 0xD187B896, 0x29263A4D, 0xBA510CDF,
0x81F47C9F, 0xAD1163ED, 0xEA7B5965, 0x1A00726E,
0x11403092, 0x00DA6D77, 0x4A0CDD61, 0xAD1F4603,
0x605BDFB0, 0x9EEDC364, 0x22EBE6A8, 0xCEE7D28A,
0xA0E736A0, 0x5564A6B9, 0x10853209, 0xC7EB8F37,
0x2DE705CA, 0x8951570F, 0xDF09822B, 0xBD691A6C,
0xAA12E4F2, 0x87451C0F, 0xE0F6A27A, 0x3ADA4819,
0x4CF1764F, 0x0D771C2B, 0x67CDB156, 0x350D8384,
0x5938FA0F, 0x42399EF3, 0x36997B07, 0x0E84093D,
0x4AA93E61, 0x8360D87B, 0x1FA98B0C, 0x1149382C,
0xE97625A5, 0x0614D1B7, 0x0E25244B, 0x0C768347,
0x589E8D82, 0x0D2059D1, 0xA466BB1E, 0xF8DA0A82,
0x04F19130, 0xBA6E4EC0, 0x99265164, 0x1EE7230D,
0x50B2AD80, 0xEAEE6801, 0x8DB2A283, 0xEA8BF59E
};
@@ -0,0 +1,21 @@
#pragma once
class CMD5
{
typedef struct {
UINT state[4]; // state (ABCD)
UINT count[2]; // number of bits, modulo 2^64 (lsb first)
BYTE buffer[64]; // input buffer
} MD5_CTX;
public:
CMD5();
virtual ~CMD5();
static void GetHash(LPSTR pszStr, LPSTR pszHash);
protected:
static void MD5Init(MD5_CTX* ctx);
static void MD5Update(MD5_CTX* ctx, BYTE* input, UINT inputlen);
static void MD5Final(BYTE* digest, MD5_CTX* ctx);
};
@@ -0,0 +1,54 @@
/*
Date manipulation routines
Copyright (C) 1999-2002, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef DATES_H
#define DATES_H
#include <sys/types.h>
#include "ne_defs.h"
BEGIN_NEON_DECLS
/* Date manipulation routines as per RFC1123 and RFC1036 */
/* Return current date/time in RFC1123 format */
char *ne_rfc1123_date(time_t anytime);
/* Returns time from date/time using the subset of the ISO8601 format
* referenced in RFC2518 (e.g as used in the creationdate property in
* the DAV: namespace). */
time_t ne_iso8601_parse(const char *date);
/* Returns time from date/time in RFC1123 format */
time_t ne_rfc1123_parse(const char *date);
time_t ne_rfc1036_parse(const char *date);
/* Parses asctime date string */
time_t ne_asctime_parse(const char *date);
/* Parse an HTTP-date as per RFC2616 */
time_t ne_httpdate_parse(const char *date);
END_NEON_DECLS
#endif /* DATES_H */
@@ -0,0 +1,53 @@
#pragma once
#include "shlobj.h"
class CPathDialog;
class CPathDialogSub : public CWnd
{
friend CPathDialog;
public:
CPathDialog* m_pdlg;
protected:
afx_msg void OnOK(); // OK button clicked
afx_msg void OnChangeEditPath();
DECLARE_MESSAGE_MAP()
};
/////////////////////////////////////////////////////////////////////////////
// CPathDialog dialog
class CPathDialog
{
friend CPathDialogSub;
// Construction
public:
CPathDialog(LPCTSTR pszCaption = NULL, LPCTSTR pszTitle = NULL, LPCTSTR pszInitialPath = NULL, CWnd* pParent = NULL);
CString GetPathName();
virtual int DoModal();
static int Touch(LPCTSTR pszPath, BOOL bValidate = TRUE);
static int MakeSurePathExists(LPCTSTR pszPath);
static BOOL IsValidFileName(LPCTSTR pszFileName);
static int ConcatPath(LPTSTR pszRoot, LPCTSTR pszMorePath);
private:
static int CALLBACK BrowseCallbackProc(HWND hwnd, UINT uMsg,LPARAM lParam, LPARAM pData);
LPCTSTR m_pszCaption;
LPCTSTR m_pszInitialPath;
TCHAR m_szPathName[MAX_PATH];
BROWSEINFO m_bi;
HWND m_hWnd;
CWnd* m_pwndParent;
BOOL m_bSuccess;
CPathDialogSub m_dlg;
};
@@ -0,0 +1,51 @@
// GdStatic.h : header file
//
#if _MSC_VER >= 1000
#pragma once
#endif // _MSC_VER >= 1000
class CGdStatic : public CStatic
{
// Construction
public:
CGdStatic();
// Attributes
public:
// Operations
public:
CString m_sFontName;
int m_nFontSize, m_nFontWeight;
BOOL m_bGrayText;
COLORREF m_crText;
void SetConstantText(LPCTSTR lpszText) {m_sConstantText = lpszText;}
// Overrides
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CGdStatic)
//}}AFX_VIRTUAL
// Implementation
public:
virtual ~CGdStatic();
protected:
CFont m_fontCaption, m_fontName;
CBitmap m_bitmap;
CString m_sConstantText;
void MakeCaptionBitmap();
// Generated message map functions
protected:
//{{AFX_MSG(CGdStatic)
afx_msg void OnPaint();
afx_msg BOOL OnEraseBkgnd(CDC* pDC);
afx_msg LRESULT OnSetText(WPARAM wParam, LPARAM lParam);
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};
@@ -0,0 +1,63 @@
/*
SSL interface definitions internal to neon.
Copyright (C) 2003, 2004, Joe Orton <joe@manyfish.co.uk>
Copyright (C) 2004, Aleix Conchillo Flaque <aleix@member.fsf.org>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
/* THIS IS NOT A PUBLIC INTERFACE. You CANNOT include this header file
* from an application. */
#ifndef NE_PRIVSSL_H
#define NE_PRIVSSL_H
/* This is the private interface between ne_socket, ne_gnutls and
* ne_openssl. */
#include "ne_ssl.h"
#include "ne_socket.h"
#ifdef HAVE_OPENSSL
#include <openssl/ssl.h>
struct ne_ssl_context_s {
SSL_CTX *ctx;
SSL_SESSION *sess;
};
typedef SSL *ne_ssl_socket;
#endif /* HAVE_OPENSSL */
#ifdef HAVE_GNUTLS
#include <gnutls/gnutls.h>
struct ne_ssl_context_s {
gnutls_certificate_credentials cred;
/* TODO: store session here too */
};
typedef gnutls_session ne_ssl_socket;
#endif /* HAVE_GNUTLS */
ne_ssl_socket ne__sock_sslsock(ne_socket *sock);
#endif /* NE_PRIVSSL_H */
@@ -0,0 +1,7 @@
typedef struct des_key {
char kn[16][8];
word32 sp[8][64];
char iperm[16][16][8];
char fperm[16][16][8];
} DES_KEY;
@@ -0,0 +1,397 @@
/*******************************************************************************
*
* FILE: safer.c
*
* DESCRIPTION: block-cipher algorithm SAFER (Secure And Fast Encryption
* Routine) in its four versions: SAFER K-64, SAFER K-128,
* SAFER SK-64 and SAFER SK-128.
*
* AUTHOR: Richard De Moliner (demoliner@isi.ee.ethz.ch)
* Signal and Information Processing Laboratory
* Swiss Federal Institute of Technology
* CH-8092 Zuerich, Switzerland
*
* DATE: September 9, 1995
*
* CHANGE HISTORY:
*
*******************************************************************************/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: safer128.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
/******************* External Headers *****************************************/
/******************* Local Headers ********************************************/
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "safer.h"
#define _mcrypt_set_key safer_sk128_LTX__mcrypt_set_key
#define _mcrypt_encrypt safer_sk128_LTX__mcrypt_encrypt
#define _mcrypt_decrypt safer_sk128_LTX__mcrypt_decrypt
#define _mcrypt_get_size safer_sk128_LTX__mcrypt_get_size
#define _mcrypt_get_block_size safer_sk128_LTX__mcrypt_get_block_size
#define _is_block_algorithm safer_sk128_LTX__is_block_algorithm
#define _mcrypt_get_key_size safer_sk128_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes safer_sk128_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name safer_sk128_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test safer_sk128_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version safer_sk128_LTX__mcrypt_algorithm_version
/******************* Constants ************************************************/
#define TAB_LEN 256
static int _safer128_init = 0;
/******************* Assertions ***********************************************/
/******************* Macros ***************************************************/
#define ROL(x, n) ((unsigned char)((unsigned int)(x) << (n)\
|(unsigned int)((x) & 0xFF) >> (8 - (n))))
#define EXP(x) exp_tab128[(x) & 0xFF]
#define LOG(x) log_tab128[(x) & 0xFF]
#define PHT(x, y) { y += x; x += y; }
#define IPHT(x, y) { x -= y; y -= x; }
/******************* Types ****************************************************/
static unsigned char exp_tab128[TAB_LEN];
static unsigned char log_tab128[TAB_LEN];
/******************* Module Data **********************************************/
/******************* Functions ************************************************/
/******************************************************************************/
static void _mcrypt_Safer_Init_Module(void)
{
unsigned int i, exp;
exp = 1;
for (i = 0; i < TAB_LEN; i++) {
exp_tab128[i] = (unsigned char) (exp & 0xFF);
log_tab128[exp_tab128[i]] = (unsigned char) i;
exp = exp * 45 % 257;
}
} /* Safer_Init_Module */
/******************************************************************************/
WIN32DLL_DEFINE
int _mcrypt_set_key(safer_key_t * key, safer_block_t * userkey,
int len)
{
unsigned int i, j;
unsigned char ka[SAFER_BLOCK_LEN + 1];
unsigned char kb[SAFER_BLOCK_LEN + 1];
int nof_rounds = SAFER_SK64_DEFAULT_NOF_ROUNDS;
int strengthened = 1;
unsigned char *userkey_1 = &userkey[0];
unsigned char *userkey_2 = &userkey[8];
if (_safer128_init == 0) {
_mcrypt_Safer_Init_Module();
_safer128_init = 1;
}
if (SAFER_MAX_NOF_ROUNDS < nof_rounds)
nof_rounds = SAFER_MAX_NOF_ROUNDS;
*key++ = (unsigned char) nof_rounds;
ka[SAFER_BLOCK_LEN] = 0;
kb[SAFER_BLOCK_LEN] = 0;
for (j = 0; j < SAFER_BLOCK_LEN; j++) {
ka[SAFER_BLOCK_LEN] ^= ka[j] = ROL(userkey_1[j], 5);
kb[SAFER_BLOCK_LEN] ^= kb[j] = *key++ = userkey_2[j];
}
for (i = 1; i <= nof_rounds; i++) {
for (j = 0; j < SAFER_BLOCK_LEN + 1; j++) {
ka[j] = ROL(ka[j], 6);
kb[j] = ROL(kb[j], 6);
}
for (j = 0; j < SAFER_BLOCK_LEN; j++)
if (strengthened)
*key++ =
(ka
[(j + 2 * i - 1) %
(SAFER_BLOCK_LEN + 1)] +
exp_tab128[exp_tab128[18 * i + j + 1]]) &
0xFF;
else
*key++ =
(ka[j] +
exp_tab128[exp_tab128[18 * i + j + 1]]) &
0xFF;
for (j = 0; j < SAFER_BLOCK_LEN; j++)
if (strengthened)
*key++ =
(kb
[(j + 2 * i) %
(SAFER_BLOCK_LEN + 1)] +
exp_tab128[exp_tab128[18 * i + j + 10]]) &
0xFF;
else
*key++ =
(kb[j] +
exp_tab128[exp_tab128[18 * i + j + 10]]) &
0xFF;
}
for (j = 0; j < SAFER_BLOCK_LEN + 1; j++)
ka[j] = kb[j] = 0;
return 0;
} /* Safer_Expand_Userkey */
/******************************************************************************/
WIN32DLL_DEFINE
void _mcrypt_encrypt(const safer_key_t * key, safer_block_t * block_in)
{
unsigned char a, b, c, d, e, f, g, h, t;
unsigned int round;
a = block_in[0];
b = block_in[1];
c = block_in[2];
d = block_in[3];
e = block_in[4];
f = block_in[5];
g = block_in[6];
h = block_in[7];
if (SAFER_MAX_NOF_ROUNDS < (round = *key))
round = SAFER_MAX_NOF_ROUNDS;
while (round--) {
a ^= *++key;
b += *++key;
c += *++key;
d ^= *++key;
e ^= *++key;
f += *++key;
g += *++key;
h ^= *++key;
a = EXP(a) + *++key;
b = LOG(b) ^ *++key;
c = LOG(c) ^ *++key;
d = EXP(d) + *++key;
e = EXP(e) + *++key;
f = LOG(f) ^ *++key;
g = LOG(g) ^ *++key;
h = EXP(h) + *++key;
PHT(a, b);
PHT(c, d);
PHT(e, f);
PHT(g, h);
PHT(a, c);
PHT(e, g);
PHT(b, d);
PHT(f, h);
PHT(a, e);
PHT(b, f);
PHT(c, g);
PHT(d, h);
t = b;
b = e;
e = c;
c = t;
t = d;
d = f;
f = g;
g = t;
}
a ^= *++key;
b += *++key;
c += *++key;
d ^= *++key;
e ^= *++key;
f += *++key;
g += *++key;
h ^= *++key;
block_in[0] = a & 0xFF;
block_in[1] = b & 0xFF;
block_in[2] = c & 0xFF;
block_in[3] = d & 0xFF;
block_in[4] = e & 0xFF;
block_in[5] = f & 0xFF;
block_in[6] = g & 0xFF;
block_in[7] = h & 0xFF;
} /* Safer_Encrypt_Block */
/******************************************************************************/
WIN32DLL_DEFINE
void _mcrypt_decrypt(const safer_key_t * key, safer_block_t * block_in)
{
safer_block_t a, b, c, d, e, f, g, h, t;
unsigned int round;
a = block_in[0];
b = block_in[1];
c = block_in[2];
d = block_in[3];
e = block_in[4];
f = block_in[5];
g = block_in[6];
h = block_in[7];
if (SAFER_MAX_NOF_ROUNDS < (round = *key))
round = SAFER_MAX_NOF_ROUNDS;
key += SAFER_BLOCK_LEN * (1 + 2 * round);
h ^= *key;
g -= *--key;
f -= *--key;
e ^= *--key;
d ^= *--key;
c -= *--key;
b -= *--key;
a ^= *--key;
while (round--) {
t = e;
e = b;
b = c;
c = t;
t = f;
f = d;
d = g;
g = t;
IPHT(a, e);
IPHT(b, f);
IPHT(c, g);
IPHT(d, h);
IPHT(a, c);
IPHT(e, g);
IPHT(b, d);
IPHT(f, h);
IPHT(a, b);
IPHT(c, d);
IPHT(e, f);
IPHT(g, h);
h -= *--key;
g ^= *--key;
f ^= *--key;
e -= *--key;
d -= *--key;
c ^= *--key;
b ^= *--key;
a -= *--key;
h = LOG(h) ^ *--key;
g = EXP(g) - *--key;
f = EXP(f) - *--key;
e = LOG(e) ^ *--key;
d = LOG(d) ^ *--key;
c = EXP(c) - *--key;
b = EXP(b) - *--key;
a = LOG(a) ^ *--key;
}
block_in[0] = a & 0xFF;
block_in[1] = b & 0xFF;
block_in[2] = c & 0xFF;
block_in[3] = d & 0xFF;
block_in[4] = e & 0xFF;
block_in[5] = f & 0xFF;
block_in[6] = g & 0xFF;
block_in[7] = h & 0xFF;
} /* Safer_Decrypt_Block */
/******************************************************************************/
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return (1 + SAFER_BLOCK_LEN * (1 + 2 * SAFER_MAX_NOF_ROUNDS));
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 8;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 16;
}
static const int key_sizes[] = { 16 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE char *_mcrypt_get_algorithms_name()
{
return "SAFER-SK128";
}
#define CIPHER "35ed856e2cf90947"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,484 @@
/* This is an independent implementation of the encryption algorithm: */
/* */
/* LOKI97 by Brown and Pieprzyk */
/* */
/* which is a candidate algorithm in the Advanced Encryption Standard */
/* programme of the US National Institute of Standards and Technology. */
/* */
/* Copyright in this implementation is held by Dr B R Gladman but I */
/* hereby give permission for its free direct or derivative use subject */
/* to acknowledgment of its origin and compliance with any conditions */
/* that the originators of the algorithm place on its exploitation. */
/* */
/* Dr Brian Gladman (gladman@seven77.demon.co.uk) 14th January 1999 */
/* $Id: loki97.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* Timing data for LOKI97 (loki.c)
Core timing without I/O endian conversion:
128 bit key:
Key Setup: 7430 cycles
Encrypt: 2134 cycles = 12.0 mbits/sec
Decrypt: 2192 cycles = 11.7 mbits/sec
Mean: 2163 cycles = 11.8 mbits/sec
192 bit key:
Key Setup: 7303 cycles
Encrypt: 2138 cycles = 12.0 mbits/sec
Decrypt: 2189 cycles = 11.7 mbits/sec
Mean: 2164 cycles = 11.8 mbits/sec
256 bit key:
Key Setup: 7166 cycles
Encrypt: 2131 cycles = 12.0 mbits/sec
Decrypt: 2184 cycles = 11.7 mbits/sec
Mean: 2158 cycles = 11.9 mbits/sec
Full timing with I/O endian conversion:
128 bit key:
Key Setup: 7582 cycles
Encrypt: 2174 cycles = 11.8 mbits/sec
Decrypt: 2235 cycles = 11.5 mbits/sec
Mean: 2205 cycles = 11.6 mbits/sec
192 bit key:
Key Setup: 7477 cycles
Encrypt: 2167 cycles = 11.8 mbits/sec
Decrypt: 2223 cycles = 11.5 mbits/sec
Mean: 2195 cycles = 11.7 mbits/sec
256 bit key:
Key Setup: 7365 cycles
Encrypt: 2177 cycles = 11.8 mbits/sec
Decrypt: 2194 cycles = 11.7 mbits/sec
Mean: 2186 cycles = 11.7 mbits/sec
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _mcrypt_set_key loki97_LTX__mcrypt_set_key
#define _mcrypt_encrypt loki97_LTX__mcrypt_encrypt
#define _mcrypt_decrypt loki97_LTX__mcrypt_decrypt
#define _mcrypt_get_size loki97_LTX__mcrypt_get_size
#define _mcrypt_get_block_size loki97_LTX__mcrypt_get_block_size
#define _is_block_algorithm loki97_LTX__is_block_algorithm
#define _mcrypt_get_key_size loki97_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes loki97_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name loki97_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test loki97_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version loki97_LTX__mcrypt_algorithm_version
#define byte(x,n) ((byte)((x) >> (8 * n)))
#define S1_SIZE 13
#define S1_LEN (1 << S1_SIZE)
#define S1_MASK (S1_LEN - 1)
#define S1_HMASK (S1_MASK & ~0xff)
#define S1_POLY 0x2911
#define S2_SIZE 11
#define S2_LEN (1 << S2_SIZE)
#define S2_MASK (S2_LEN - 1)
#define S2_HMASK (S2_MASK & ~0xff)
#define S2_POLY 0x0aa7
word32 delta[2] = { 0x7f4a7c15, 0x9e3779b9 };
byte sb1[S1_LEN]; /* GF(2^11) S box */
byte sb2[S2_LEN]; /* GF(2^11) S box */
word32 prm[256][2];
word32 init_done = 0;
/* word32 l_key[96]; */
#define add_eq(x,y) (x)[1] += (y)[1] + (((x)[0] += (y)[0]) < (y)[0] ? 1 : 0)
#define sub_eq(x,y) xs = (x)[0]; (x)[1] -= (y)[1] + (((x)[0] -= (y)[0]) > xs ? 1 : 0)
word32 ff_mult(word32 a, word32 b, word32 tpow, word32 mpol)
{
word32 r, s, m;
r = s = 0;
m = (1 << tpow);
while (b) {
if (b & 1)
s ^= a;
b >>= 1;
a <<= 1;
if (a & m)
a ^= mpol;
}
return s;
}
void init_tables(void)
{
word32 i, j, v;
/* initialise S box 1 */
for (i = 0; i < S1_LEN; ++i) {
j = v = i ^ S1_MASK;
v = ff_mult(v, j, S1_SIZE, S1_POLY);
sb1[i] = (byte) ff_mult(v, j, S1_SIZE, S1_POLY);
}
/* initialise S box 2 */
for (i = 0; i < S2_LEN; ++i) {
j = v = i ^ S2_MASK;
v = ff_mult(v, j, S2_SIZE, S2_POLY);
sb2[i] = (byte) ff_mult(v, j, S2_SIZE, S2_POLY);
}
/* initialise permutation table */
for (i = 0; i < 256; ++i) {
prm[i][0] =
((i & 1) << 7) | ((i & 2) << 14) | ((i & 4) << 21) |
((i & 8) << 28);
prm[i][1] =
((i & 16) << 3) | ((i & 32) << 10) | ((i & 64) << 17) |
((i & 128) << 24);
}
}
void f_fun(word32 res[2], const word32 in[2], const word32 key[2])
{
word32 i, tt[2], pp[2];
/* tt[0] = in[0] & ~key[0] | in[1] & key[0];
* tt[1] = in[1] & ~key[0] | in[0] & key[0];
*/
tt[0] = (in[0] & ~key[0]) | (in[1] & key[0]);
tt[1] = (in[1] & ~key[0]) | (in[0] & key[0]);
i = sb1[((tt[1] >> 24) | (tt[0] << 8)) & S1_MASK];
pp[0] = prm[i][0] >> 7;
pp[1] = prm[i][1] >> 7;
i = sb2[(tt[1] >> 16) & S2_MASK];
pp[0] |= prm[i][0] >> 6;
pp[1] |= prm[i][1] >> 6;
i = sb1[(tt[1] >> 8) & S1_MASK];
pp[0] |= prm[i][0] >> 5;
pp[1] |= prm[i][1] >> 5;
i = sb2[tt[1] & S2_MASK];
pp[0] |= prm[i][0] >> 4;
pp[1] |= prm[i][1] >> 4;
i = sb2[((tt[0] >> 24) | (tt[1] << 8)) & S2_MASK];
pp[0] |= prm[i][0] >> 3;
pp[1] |= prm[i][1] >> 3;
i = sb1[(tt[0] >> 16) & S1_MASK];
pp[0] |= prm[i][0] >> 2;
pp[1] |= prm[i][1] >> 2;
i = sb2[(tt[0] >> 8) & S2_MASK];
pp[0] |= prm[i][0] >> 1;
pp[1] |= prm[i][1] >> 1;
i = sb1[tt[0] & S1_MASK];
pp[0] |= prm[i][0];
pp[1] |= prm[i][1];
/*
res[0] ^= sb1[byte(pp[0], 0) | (key[1] << 8) & S1_HMASK]
| (sb1[byte(pp[0], 1) | (key[1] << 3) & S1_HMASK] << 8)
| (sb2[byte(pp[0], 2) | (key[1] >> 2) & S2_HMASK] << 16)
| (sb2[byte(pp[0], 3) | (key[1] >> 5) & S2_HMASK] << 24);
res[1] ^= sb1[byte(pp[1], 0) | (key[1] >> 8) & S1_HMASK]
| (sb1[byte(pp[1], 1) | (key[1] >> 13) & S1_HMASK] << 8)
| (sb2[byte(pp[1], 2) | (key[1] >> 18) & S2_HMASK] << 16)
| (sb2[byte(pp[1], 3) | (key[1] >> 21) & S2_HMASK] << 24);
*/
res[0] ^= sb1[byte(pp[0], 0) | ((key[1] << 8) & S1_HMASK)]
| ((sb1[byte(pp[0], 1) | ((key[1] << 3) & S1_HMASK)] << 8))
| ((sb2[byte(pp[0], 2) | ((key[1] >> 2) & S2_HMASK)] << 16))
| ((sb2[byte(pp[0], 3) | ((key[1] >> 5) & S2_HMASK)] << 24));
res[1] ^= sb1[byte(pp[1], 0) | ((key[1] >> 8) & S1_HMASK)]
| ((sb1[byte(pp[1], 1) | ((key[1] >> 13) & S1_HMASK)] << 8))
| ((sb2[byte(pp[1], 2) | ((key[1] >> 18) & S2_HMASK)] << 16))
| ((sb2[byte(pp[1], 3) | ((key[1] >> 21) & S2_HMASK)] << 24));
}
/* 256 bit version only */
WIN32DLL_DEFINE
int _mcrypt_set_key(word32 * l_key, const word32 in_key[],
const word32 key_len)
{
word32 i, k1[2], k2[2], k3[2], k4[2], del[2], tt[2], sk[2];
if (!init_done) {
init_tables();
init_done = 1;
}
#ifdef WORDS_BIGENDIAN
k4[0] = byteswap32(in_key[1]);
k4[1] = byteswap32(in_key[0]);
k3[0] = byteswap32(in_key[3]);
k3[1] = byteswap32(in_key[2]);
#else
k4[0] = (in_key[1]);
k4[1] = (in_key[0]);
k3[0] = (in_key[3]);
k3[1] = (in_key[2]);
#endif
#ifdef WORDS_BIGENDIAN
k2[0] = byteswap32(in_key[5]);
k2[1] = byteswap32(in_key[4]);
k1[0] = byteswap32(in_key[7]);
k1[1] = byteswap32(in_key[6]);
#else
k2[0] = (in_key[5]);
k2[1] = (in_key[4]);
k1[0] = (in_key[7]);
k1[1] = (in_key[6]);
#endif
del[0] = delta[0];
del[1] = delta[1];
for (i = 0; i < 48; ++i) {
tt[0] = k1[0];
tt[1] = k1[1];
add_eq(tt, k3);
add_eq(tt, del);
add_eq(del, delta);
sk[0] = k4[0];
sk[1] = k4[1];
k4[0] = k3[0];
k4[1] = k3[1];
k3[0] = k2[0];
k3[1] = k2[1];
k2[0] = k1[0];
k2[1] = k1[1];
k1[0] = sk[0];
k1[1] = sk[1];
f_fun(k1, tt, k3);
l_key[i + i] = k1[0];
l_key[i + i + 1] = k1[1];
}
return 0;
}
#define r_fun(l,r,k) \
add_eq((l),(k)); \
f_fun((r),(l),(k) + 2); \
add_eq((l), (k) + 4)
WIN32DLL_DEFINE void _mcrypt_encrypt(word32 * l_key, word32 * _blk)
{
word32 blk[4];
#ifdef WORDS_BIGENDIAN
blk[3] = byteswap32(_blk[0]);
blk[2] = byteswap32(_blk[1]);
blk[1] = byteswap32(_blk[2]);
blk[0] = byteswap32(_blk[3]);
#else
blk[3] = (_blk[0]);
blk[2] = (_blk[1]);
blk[1] = (_blk[2]);
blk[0] = (_blk[3]);
#endif
r_fun(blk, blk + 2, l_key + 0);
r_fun(blk + 2, blk, l_key + 6);
r_fun(blk, blk + 2, l_key + 12);
r_fun(blk + 2, blk, l_key + 18);
r_fun(blk, blk + 2, l_key + 24);
r_fun(blk + 2, blk, l_key + 30);
r_fun(blk, blk + 2, l_key + 36);
r_fun(blk + 2, blk, l_key + 42);
r_fun(blk, blk + 2, l_key + 48);
r_fun(blk + 2, blk, l_key + 54);
r_fun(blk, blk + 2, l_key + 60);
r_fun(blk + 2, blk, l_key + 66);
r_fun(blk, blk + 2, l_key + 72);
r_fun(blk + 2, blk, l_key + 78);
r_fun(blk, blk + 2, l_key + 84);
r_fun(blk + 2, blk, l_key + 90);
#ifdef WORDS_BIGENDIAN
_blk[3] = byteswap32(blk[2]);
_blk[2] = byteswap32(blk[3]);
_blk[1] = byteswap32(blk[0]);
_blk[0] = byteswap32(blk[1]);
#else
_blk[3] = (blk[2]);
_blk[2] = (blk[3]);
_blk[1] = (blk[0]);
_blk[0] = (blk[1]);
#endif
}
#define ir_fun(l,r,k) \
sub_eq((l),(k) + 4); \
f_fun((r),(l),(k) + 2); \
sub_eq((l),(k))
WIN32DLL_DEFINE void _mcrypt_decrypt(word32 * l_key, word32 * _blk)
{
word32 xs, blk[4];
#ifdef WORDS_BIGENDIAN
blk[3] = byteswap32(_blk[0]);
blk[2] = byteswap32(_blk[1]);
blk[1] = byteswap32(_blk[2]);
blk[0] = byteswap32(_blk[3]);
#else
blk[3] = (_blk[0]);
blk[2] = (_blk[1]);
blk[1] = (_blk[2]);
blk[0] = (_blk[3]);
#endif
ir_fun(blk, blk + 2, l_key + 90);
ir_fun(blk + 2, blk, l_key + 84);
ir_fun(blk, blk + 2, l_key + 78);
ir_fun(blk + 2, blk, l_key + 72);
ir_fun(blk, blk + 2, l_key + 66);
ir_fun(blk + 2, blk, l_key + 60);
ir_fun(blk, blk + 2, l_key + 54);
ir_fun(blk + 2, blk, l_key + 48);
ir_fun(blk, blk + 2, l_key + 42);
ir_fun(blk + 2, blk, l_key + 36);
ir_fun(blk, blk + 2, l_key + 30);
ir_fun(blk + 2, blk, l_key + 24);
ir_fun(blk, blk + 2, l_key + 18);
ir_fun(blk + 2, blk, l_key + 12);
ir_fun(blk, blk + 2, l_key + 6);
ir_fun(blk + 2, blk, l_key);
#ifdef WORDS_BIGENDIAN
_blk[3] = byteswap32(blk[2]);
_blk[2] = byteswap32(blk[3]);
_blk[1] = byteswap32(blk[0]);
_blk[0] = byteswap32(blk[1]);
#else
_blk[3] = (blk[2]);
_blk[2] = (blk[3]);
_blk[1] = (blk[0]);
_blk[0] = (blk[1]);
#endif
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return 96 * sizeof(word32);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 16;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 32;
}
static const int key_sizes[] = { 16, 24, 32 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE char *_mcrypt_get_algorithms_name()
{
return "LOKI97";
}
#define CIPHER "8cb28c958024bae27a94c698f96f12a9"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,118 @@
// ImplDispatch.cpp (IDispatch for Extending Dynamic HTML Object Model)
#include "stdafx.h"
#include "ImpIDispatch.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
// Hardcoded information for extending the Object Model
// Typically this would be supplied through a TypeInfo
// In this case the name "xxyyzz" maps to DISPID_Extend
const WCHAR pszExtend[10]=L"xxyyzz";
#define DISPID_Extend 12345
CImpIDispatch::CImpIDispatch(void)
{
m_cRef = 0;
}
CImpIDispatch::~CImpIDispatch(void)
{
ASSERT(m_cRef == 0);
}
STDMETHODIMP CImpIDispatch::QueryInterface(REFIID riid, void **ppv)
{
*ppv = NULL;
if (IID_IDispatch == riid)
*ppv = this;
if (NULL != *ppv) {
((LPUNKNOWN)*ppv)->AddRef();
return NOERROR;
}
return E_NOINTERFACE;
}
STDMETHODIMP_(ULONG) CImpIDispatch::AddRef(void)
{
return ++m_cRef;
}
STDMETHODIMP_(ULONG) CImpIDispatch::Release(void)
{
return --m_cRef;
}
STDMETHODIMP CImpIDispatch::GetTypeInfoCount(UINT* /*pctinfo*/)
{
return E_NOTIMPL;
}
STDMETHODIMP CImpIDispatch::GetTypeInfo(
/* [in] */ UINT /*iTInfo*/,
/* [in] */ LCID /*lcid*/,
/* [out] */ ITypeInfo** /*ppTInfo*/)
{
return E_NOTIMPL;
}
STDMETHODIMP CImpIDispatch::GetIDsOfNames(
/* [in] */ REFIID riid,
/* [size_is][in] */ OLECHAR** rgszNames,
/* [in] */ UINT cNames,
/* [in] */ LCID lcid,
/* [size_is][out] */ DISPID* rgDispId)
{
HRESULT hr = NOERROR;
// Hardcoded mapping for this sample
// A more usual procedure would be to use a TypeInfo
for (UINT i = 0; i < cNames; i++) {
if (2 == CompareString(lcid, NORM_IGNOREWIDTH, (char*)pszExtend, 3, (char*)rgszNames[i], 3)) {
rgDispId[i] = DISPID_Extend;
}
else {
// One or more are unknown so set the return code accordingly
hr = ResultFromScode(DISP_E_UNKNOWNNAME);
rgDispId[i] = DISPID_UNKNOWN;
}
}
return hr;
}
STDMETHODIMP CImpIDispatch::Invoke(
/* [in] */ DISPID dispIdMember,
/* [in] */ REFIID /*riid*/,
/* [in] */ LCID /*lcid*/,
/* [in] */ WORD wFlags,
/* [out][in] */ DISPPARAMS* pDispParams,
/* [out] */ VARIANT* pVarResult,
/* [out] */ EXCEPINFO* /*pExcepInfo*/,
/* [out] */ UINT* puArgErr)
{
// For this sample we only support a Property Get on DISPID_Extend
// returning a BSTR with "Wibble" as the value
if (dispIdMember == DISPID_Extend) {
if (wFlags & DISPATCH_PROPERTYGET) {
if (pVarResult != NULL) {
WCHAR buff[10] = L"Wibble";
BSTR bstrRet = SysAllocString(buff);
VariantInit(pVarResult);
V_VT(pVarResult) = VT_BSTR;
V_BSTR(pVarResult) = bstrRet;
}
}
}
return S_OK;
}
@@ -0,0 +1,505 @@
/* Rijndael Cipher
Written by Mike Scott 21st April 1999
Copyright (c) 1999 Mike Scott
See rijndael documentation
Permission for free direct or derivative use is granted subject
to compliance with any conditions that the originators of the
algorithm place on its exploitation.
Inspiration from Brian Gladman's implementation is acknowledged.
Written for clarity, rather than speed.
Full implementation.
Endian indifferent.
*/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: rijndael-192.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
#include <libdefs.h>
#include <mcrypt_modules.h>
#include "rijndael.h"
#define _mcrypt_set_key rijndael_192_LTX__mcrypt_set_key
#define _mcrypt_encrypt rijndael_192_LTX__mcrypt_encrypt
#define _mcrypt_decrypt rijndael_192_LTX__mcrypt_decrypt
#define _mcrypt_get_size rijndael_192_LTX__mcrypt_get_size
#define _mcrypt_get_block_size rijndael_192_LTX__mcrypt_get_block_size
#define _is_block_algorithm rijndael_192_LTX__is_block_algorithm
#define _mcrypt_get_key_size rijndael_192_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes rijndael_192_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name rijndael_192_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test rijndael_192_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version rijndael_192_LTX__mcrypt_algorithm_version
/* rotates x one bit to the left */
#define ROTL(x) (((x)>>7)|((x)<<1))
/* Rotates 32-bit word left by 1, 2 or 3 byte */
#define ROTL8(x) (((x)<<8)|((x)>>24))
#define ROTL16(x) (((x)<<16)|((x)>>16))
#define ROTL24(x) (((x)<<24)|((x)>>8))
/* Fixed Data */
static byte InCo[4] = { 0xB, 0xD, 0x9, 0xE }; /* Inverse Coefficients */
static byte fbsub[256];
static byte rbsub[256];
static byte ptab[256], ltab[256];
static word32 ftable[256];
static word32 rtable[256];
static word32 rco[30];
static int tables_ok = 0;
/* Parameter-dependent data */
/* in "rijndael.h" */
static word32 pack(byte * b)
{ /* pack bytes into a 32-bit Word */
return ((word32) b[3] << 24) | ((word32) b[2] << 16) | ((word32)
b[1] << 8)
| (word32) b[0];
}
static void unpack(word32 a, byte * b)
{ /* unpack bytes from a word */
b[0] = (byte) a;
b[1] = (byte) (a >> 8);
b[2] = (byte) (a >> 16);
b[3] = (byte) (a >> 24);
}
static byte xtime(byte a)
{
byte b;
if (a & 0x80)
b = 0x1B;
else
b = 0;
a <<= 1;
a ^= b;
return a;
}
static byte bmul(byte x, byte y)
{ /* x.y= AntiLog(Log(x) + Log(y)) */
if (x && y)
return ptab[(ltab[x] + ltab[y]) % 255];
else
return 0;
}
static word32 SubByte(word32 a)
{
byte b[4];
unpack(a, b);
b[0] = fbsub[b[0]];
b[1] = fbsub[b[1]];
b[2] = fbsub[b[2]];
b[3] = fbsub[b[3]];
return pack(b);
}
static byte product(word32 x, word32 y)
{ /* dot product of two 4-byte arrays */
byte xb[4], yb[4];
unpack(x, xb);
unpack(y, yb);
return bmul(xb[0], yb[0]) ^ bmul(xb[1], yb[1]) ^ bmul(xb[2],
yb[2]) ^
bmul(xb[3], yb[3]);
}
static word32 InvMixCol(word32 x)
{ /* matrix Multiplication */
word32 y, m;
byte b[4];
m = pack(InCo);
b[3] = product(m, x);
m = ROTL24(m);
b[2] = product(m, x);
m = ROTL24(m);
b[1] = product(m, x);
m = ROTL24(m);
b[0] = product(m, x);
y = pack(b);
return y;
}
static byte ByteSub(byte x)
{
byte y = ptab[255 - ltab[x]]; /* multiplicative inverse */
x = y;
x = ROTL(x);
y ^= x;
x = ROTL(x);
y ^= x;
x = ROTL(x);
y ^= x;
x = ROTL(x);
y ^= x;
y ^= 0x63;
return y;
}
static void _mcrypt_rijndael_gentables(void)
{ /* generate tables */
int i;
byte y, b[4];
/* use 3 as primitive root to generate power and log tables */
ltab[0] = 0;
ptab[0] = 1;
ltab[1] = 0;
ptab[1] = 3;
ltab[3] = 1;
for (i = 2; i < 256; i++) {
ptab[i] = ptab[i - 1] ^ xtime(ptab[i - 1]);
ltab[ptab[i]] = i;
}
/* affine transformation:- each bit is xored with itself shifted one bit */
fbsub[0] = 0x63;
rbsub[0x63] = 0;
for (i = 1; i < 256; i++) {
y = ByteSub((byte) i);
fbsub[i] = y;
rbsub[y] = i;
}
for (i = 0, y = 1; i < 30; i++) {
rco[i] = y;
y = xtime(y);
}
/* calculate forward and reverse tables */
for (i = 0; i < 256; i++) {
y = fbsub[i];
b[3] = y ^ xtime(y);
b[2] = y;
b[1] = y;
b[0] = xtime(y);
ftable[i] = pack(b);
y = rbsub[i];
b[3] = bmul(InCo[0], y);
b[2] = bmul(InCo[1], y);
b[1] = bmul(InCo[2], y);
b[0] = bmul(InCo[3], y);
rtable[i] = pack(b);
}
}
WIN32DLL_DEFINE int _mcrypt_set_key(RI * rinst, byte * key, int nk)
{ /* blocksize=32*nb bits. Key=32*nk bits */
/* currently nb,bk = 4, 6 or 8 */
/* key comes as 4*rinst->Nk bytes */
/* Key Scheduler. Create expanded encryption key */
int nb = 6; /* 192 block size */
int i, j, k, m, N;
int C1, C2, C3;
word32 CipherKey[8];
nk /= 4;
if (tables_ok == 0) {
_mcrypt_rijndael_gentables();
tables_ok = 1;
}
rinst->Nb = nb;
rinst->Nk = nk;
/* rinst->Nr is number of rounds */
if (rinst->Nb >= rinst->Nk)
rinst->Nr = 6 + rinst->Nb;
else
rinst->Nr = 6 + rinst->Nk;
C1 = 1;
if (rinst->Nb < 8) {
C2 = 2;
C3 = 3;
} else {
C2 = 3;
C3 = 4;
}
/* pre-calculate forward and reverse increments */
for (m = j = 0; j < nb; j++, m += 3) {
rinst->fi[m] = (j + C1) % nb;
rinst->fi[m + 1] = (j + C2) % nb;
rinst->fi[m + 2] = (j + C3) % nb;
rinst->ri[m] = (nb + j - C1) % nb;
rinst->ri[m + 1] = (nb + j - C2) % nb;
rinst->ri[m + 2] = (nb + j - C3) % nb;
}
N = rinst->Nb * (rinst->Nr + 1);
for (i = j = 0; i < rinst->Nk; i++, j += 4) {
CipherKey[i] = pack(&key[j]);
}
for (i = 0; i < rinst->Nk; i++)
rinst->fkey[i] = CipherKey[i];
for (j = rinst->Nk, k = 0; j < N; j += rinst->Nk, k++) {
rinst->fkey[j] =
rinst->fkey[j -
rinst->Nk] ^ SubByte(ROTL24(rinst->
fkey[j -
1])) ^
rco[k];
if (rinst->Nk <= 6) {
for (i = 1; i < rinst->Nk && (i + j) < N; i++)
rinst->fkey[i + j] =
rinst->fkey[i + j -
rinst->Nk] ^ rinst->
fkey[i + j - 1];
} else {
for (i = 1; i < 4 && (i + j) < N; i++)
rinst->fkey[i + j] =
rinst->fkey[i + j -
rinst->Nk] ^ rinst->
fkey[i + j - 1];
if ((j + 4) < N)
rinst->fkey[j + 4] =
rinst->fkey[j + 4 -
rinst->
Nk] ^ SubByte(rinst->
fkey[j + 3]);
for (i = 5; i < rinst->Nk && (i + j) < N; i++)
rinst->fkey[i + j] =
rinst->fkey[i + j -
rinst->Nk] ^ rinst->
fkey[i + j - 1];
}
}
/* now for the expanded decrypt key in reverse order */
for (j = 0; j < rinst->Nb; j++)
rinst->rkey[j + N - rinst->Nb] = rinst->fkey[j];
for (i = rinst->Nb; i < N - rinst->Nb; i += rinst->Nb) {
k = N - rinst->Nb - i;
for (j = 0; j < rinst->Nb; j++)
rinst->rkey[k + j] = InvMixCol(rinst->fkey[i + j]);
}
for (j = N - rinst->Nb; j < N; j++)
rinst->rkey[j - N + rinst->Nb] = rinst->fkey[j];
return 0;
}
/* There is an obvious time/space trade-off possible here. *
* Instead of just one ftable[], I could have 4, the other *
* 3 pre-rotated to save the ROTL8, ROTL16 and ROTL24 overhead */
WIN32DLL_DEFINE void _mcrypt_encrypt(RI * rinst, byte * buff)
{
int i, j, k, m;
word32 a[8], b[8], *x, *y, *t;
for (i = j = 0; i < rinst->Nb; i++, j += 4) {
a[i] = pack(&buff[j]);
a[i] ^= rinst->fkey[i];
}
k = rinst->Nb;
x = a;
y = b;
/* State alternates between a and b */
for (i = 1; i < rinst->Nr; i++) { /* rinst->Nr is number of rounds. May be odd. */
/* if rinst->Nb is fixed - unroll this next
loop and hard-code in the values of fi[] */
for (m = j = 0; j < rinst->Nb; j++, m += 3) { /* deal with each 32-bit element of the State */
/* This is the time-critical bit */
y[j] = rinst->fkey[k++] ^ ftable[(byte) x[j]] ^
ROTL8(ftable[(byte) (x[rinst->fi[m]] >> 8)]) ^
ROTL16(ftable
[(byte) (x[rinst->fi[m + 1]] >> 16)]) ^
ROTL24(ftable[x[rinst->fi[m + 2]] >> 24]);
}
t = x;
x = y;
y = t; /* swap pointers */
}
/* Last Round - unroll if possible */
for (m = j = 0; j < rinst->Nb; j++, m += 3) {
y[j] = rinst->fkey[k++] ^ (word32) fbsub[(byte) x[j]] ^
ROTL8((word32) fbsub[(byte) (x[rinst->fi[m]] >> 8)]) ^
ROTL16((word32)
fbsub[(byte) (x[rinst->fi[m + 1]] >> 16)]) ^
ROTL24((word32) fbsub[x[rinst->fi[m + 2]] >> 24]);
}
for (i = j = 0; i < rinst->Nb; i++, j += 4) {
unpack(y[i], &buff[j]);
x[i] = y[i] = 0; /* clean up stack */
}
return;
}
WIN32DLL_DEFINE void _mcrypt_decrypt(RI * rinst, byte * buff)
{
int i, j, k, m;
word32 a[8], b[8], *x, *y, *t;
for (i = j = 0; i < rinst->Nb; i++, j += 4) {
a[i] = pack(&buff[j]);
a[i] ^= rinst->rkey[i];
}
k = rinst->Nb;
x = a;
y = b;
/* State alternates between a and b */
for (i = 1; i < rinst->Nr; i++) { /* rinst->Nr is number of rounds. May be odd. */
/* if rinst->Nb is fixed - unroll this next
loop and hard-code in the values of ri[] */
for (m = j = 0; j < rinst->Nb; j++, m += 3) { /* This is the time-critical bit */
y[j] = rinst->rkey[k++] ^ rtable[(byte) x[j]] ^
ROTL8(rtable[(byte) (x[rinst->ri[m]] >> 8)]) ^
ROTL16(rtable
[(byte) (x[rinst->ri[m + 1]] >> 16)]) ^
ROTL24(rtable[x[rinst->ri[m + 2]] >> 24]);
}
t = x;
x = y;
y = t; /* swap pointers */
}
/* Last Round - unroll if possible */
for (m = j = 0; j < rinst->Nb; j++, m += 3) {
y[j] = rinst->rkey[k++] ^ (word32) rbsub[(byte) x[j]] ^
ROTL8((word32) rbsub[(byte) (x[rinst->ri[m]] >> 8)]) ^
ROTL16((word32)
rbsub[(byte) (x[rinst->ri[m + 1]] >> 16)]) ^
ROTL24((word32) rbsub[x[rinst->ri[m + 2]] >> 24]);
}
for (i = j = 0; i < rinst->Nb; i++, j += 4) {
unpack(y[i], &buff[j]);
x[i] = y[i] = 0; /* clean up stack */
}
return;
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return sizeof(RI);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 24;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 32;
}
static const int key_sizes[] = { 16, 24, 32 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE char *_mcrypt_get_algorithms_name()
{
return "Rijndael-192";
}
#define CIPHER "380ee49a5de1dbd4b9cc11af60b8c8ff669e367af8948a8a"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[32];
unsigned char ciphertext[32];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,423 @@
/*
* The GOST 28147-89 cipher
*
* This is based on the 25 Movember 1993 draft translation
* by Aleksandr Malchik, with Whitfield Diffie, of the Government
* Standard of the U.S.S.R. GOST 28149-89, "Cryptographic Transformation
* Algorithm", effective 1 July 1990. (Whitfield.Diffie@eng.sun.com)
*
* That is a draft, and may contain errors, which will be faithfully
* reflected here, along with possible exciting new bugs.
*
* Some details have been cleared up by the paper "Soviet Encryption
* Algorithm" by Josef Pieprzyk and Leonid Tombak of the University
* of Wollongong, New South Wales. (josef/leo@cs.adfa.oz.au)
*
* The standard is written by A. Zabotin (project leader), G.P. Glazkov,
* and V.B. Isaeva. It was accepted and introduced into use by the
* action of the State Standards Committee of the USSR on 2 June 89 as
* No. 1409. It was to be reviewed in 1993, but whether anyone wishes
* to take on this obligation from the USSR is questionable.
*
* This code is placed in the public domain.
*/
/* modified in order to use the libmcrypt API by Nikos Mavroyanopoulos
* All modifications are placed under the license of libmcrypt.
*/
/* $Id: gost.c,v 1.1 2007/07/19 06:11:48 pizon Exp $ */
/*
* If you read the standard, it belabors the point of copying corresponding
* bits from point A to point B quite a bit. It helps to understand that
* the standard is uniformly little-endian, although it numbers bits from
* 1 rather than 0, so bit n has value 2^(n-1). The least significant bit
* of the 32-bit words that are manipulated in the algorithm is the first,
* lowest-numbered, in the bit string.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _mcrypt_set_key gost_LTX__mcrypt_set_key
#define _mcrypt_encrypt gost_LTX__mcrypt_encrypt
#define _mcrypt_decrypt gost_LTX__mcrypt_decrypt
#define _mcrypt_get_size gost_LTX__mcrypt_get_size
#define _mcrypt_get_block_size gost_LTX__mcrypt_get_block_size
#define _is_block_algorithm gost_LTX__is_block_algorithm
#define _mcrypt_get_key_size gost_LTX__mcrypt_get_key_size
#define _mcrypt_get_supported_key_sizes gost_LTX__mcrypt_get_supported_key_sizes
#define _mcrypt_get_algorithms_name gost_LTX__mcrypt_get_algorithms_name
#define _mcrypt_self_test gost_LTX__mcrypt_self_test
#define _mcrypt_algorithm_version gost_LTX__mcrypt_algorithm_version
void _mcrypt_kboxinit(void);
/*
* The standard does not specify the contents of the 8 4 bit->4 bit
* substitution boxes, saying they're a parameter of the network
* being set up. For illustration purposes here, I have used
* the first rows of the 8 S-boxes from the DES. (Note that the
* DES S-boxes are numbered starting from 1 at the msb. In keeping
* with the rest of the GOST, I have used little-endian numbering.
* Thus, k8 is S-box 1.
*
* Obviously, a careful look at the cryptographic properties of the cipher
* must be undertaken before "production" substitution boxes are defined.
*
* The standard also does not specify a standard bit-string representation
* for the contents of these blocks.
*/
/* These are NOT the original s-boxes. I replaced them with the ones
* found in Applied Cryptography book by Bruce Schneier. These were
* used in an application for the Central Bank of the Russian Federation
* --Nikos
*/
static int init = 0;
static unsigned char const gost_k1[16] = {
1, 15, 13, 0, 5, 7, 10, 4, 9, 2, 3, 14, 6, 11, 8, 2
};
static unsigned char const gost_k2[16] = {
13, 11, 4, 1, 3, 15, 5, 9, 0, 10, 14, 7, 6, 8, 2, 12
};
static unsigned char const gost_k3[16] = {
4, 11, 10, 0, 7, 2, 1, 13, 3, 6, 8, 5, 9, 12, 15, 14
};
static unsigned char const gost_k4[16] = {
6, 12, 7, 1, 5, 15, 13, 8, 4, 10, 9, 14, 0, 3, 11, 2
};
static unsigned char const gost_k5[16] = {
7, 13, 10, 1, 0, 8, 9, 15, 14, 4, 6, 12, 11, 2, 5, 3
};
static unsigned char const gost_k6[16] = {
5, 8, 1, 13, 10, 3, 4, 2, 14, 15, 12, 7, 6, 0, 9, 11
};
static unsigned char const gost_k7[16] = {
14, 11, 4, 12, 6, 13, 15, 10, 2, 3, 8, 1, 0, 7, 5, 9
};
static unsigned char const gost_k8[16] = {
4, 10, 9, 2, 13, 8, 0, 14, 6, 11, 1, 12, 7, 15, 5, 3
};
/* Byte-at-a-time substitution boxes */
static unsigned char gost_k87[256];
static unsigned char gost_k65[256];
static unsigned char gost_k43[256];
static unsigned char gost_k21[256];
/*
* Build byte-at-a-time subtitution tables.
* This must be called once for global setup.
*/
WIN32DLL_DEFINE int _mcrypt_set_key(word32 * inst, word32 * key, int len)
{
_mcrypt_kboxinit();
inst[0] = 0;
inst[1] = 0;
inst[2] = 0;
inst[3] = 0;
inst[4] = 0;
inst[5] = 0;
inst[6] = 0;
inst[7] = 0;
memmove(inst, key, len);
#ifdef WORDS_BIGENDIAN
inst[0] = byteswap32(inst[0]);
inst[1] = byteswap32(inst[1]);
inst[2] = byteswap32(inst[2]);
inst[3] = byteswap32(inst[3]);
inst[4] = byteswap32(inst[4]);
inst[5] = byteswap32(inst[5]);
inst[6] = byteswap32(inst[6]);
inst[7] = byteswap32(inst[7]);
#endif
return 0;
}
void _mcrypt_kboxinit(void)
{
int i;
if (init == 0) {
init = 1;
for (i = 0; i < 256; i++) {
gost_k87[i] = gost_k8[i >> 4] << 4 | gost_k7[i & 15];
gost_k65[i] = gost_k6[i >> 4] << 4 | gost_k5[i & 15];
gost_k43[i] = gost_k4[i >> 4] << 4 | gost_k3[i & 15];
gost_k21[i] = gost_k2[i >> 4] << 4 | gost_k1[i & 15];
}
}
}
/*
* Do the substitution and rotation that are the core of the operation,
* like the expansion, substitution and permutation of the DES.
* It would be possible to perform DES-like optimisations and store
* the table entries as 32-bit words, already rotated, but the
* efficiency gain is questionable.
*
* This should be inlined for maximum speed
*/
static word32 f(word32 x)
{
/* Do substitutions */
# if 0
/* This is annoyingly slow */
x = k8[x >> 28 & 15] << 28 | k7[x >> 24 & 15] << 24 |
k6[x >> 20 & 15] << 20 | k5[x >> 16 & 15] << 16 |
k4[x >> 12 & 15] << 12 | k3[x >> 8 & 15] << 8 |
k2[x >> 4 & 15] << 4 | k1[x & 15];
# else
/* This is faster */
x = gost_k87[x >> 24 & 255] << 24 | gost_k65[x >> 16 & 255] << 16 |
gost_k43[x >> 8 & 255] << 8 | gost_k21[x & 255];
# endif
/* Rotate left 11 bits */
return x << 11 | x >> (32 - 11);
}
/*
* The GOST standard defines the input in terms of bits 1..64, with
* bit 1 being the lsb of in[0] and bit 64 being the msb of in[1].
*
* The keys are defined similarly, with bit 256 being the msb of key[7].
*/
WIN32DLL_DEFINE void _mcrypt_encrypt(word32 const key[8], word32 * in)
{
register word32 n1, n2; /* As named in the GOST */
/* Added to make it compatible with bigendian machines
* --nikos
*/
#ifndef WORDS_BIGENDIAN
n1 = byteswap32(in[0]);
n2 = byteswap32(in[1]);
#else
n1 = in[0];
n2 = in[1];
#endif
/* Instead of swapping halves, swap names each round */
n2 ^= f(n1 + key[0]);
n1 ^= f(n2 + key[1]);
n2 ^= f(n1 + key[2]);
n1 ^= f(n2 + key[3]);
n2 ^= f(n1 + key[4]);
n1 ^= f(n2 + key[5]);
n2 ^= f(n1 + key[6]);
n1 ^= f(n2 + key[7]);
n2 ^= f(n1 + key[0]);
n1 ^= f(n2 + key[1]);
n2 ^= f(n1 + key[2]);
n1 ^= f(n2 + key[3]);
n2 ^= f(n1 + key[4]);
n1 ^= f(n2 + key[5]);
n2 ^= f(n1 + key[6]);
n1 ^= f(n2 + key[7]);
n2 ^= f(n1 + key[0]);
n1 ^= f(n2 + key[1]);
n2 ^= f(n1 + key[2]);
n1 ^= f(n2 + key[3]);
n2 ^= f(n1 + key[4]);
n1 ^= f(n2 + key[5]);
n2 ^= f(n1 + key[6]);
n1 ^= f(n2 + key[7]);
n2 ^= f(n1 + key[7]);
n1 ^= f(n2 + key[6]);
n2 ^= f(n1 + key[5]);
n1 ^= f(n2 + key[4]);
n2 ^= f(n1 + key[3]);
n1 ^= f(n2 + key[2]);
n2 ^= f(n1 + key[1]);
n1 ^= f(n2 + key[0]);
/* There is no swap after the last round */
#ifndef WORDS_BIGENDIAN
in[0] = byteswap32(n2);
in[1] = byteswap32(n1);
#else
in[0] = n2;
in[1] = n1;
#endif
}
/*
* The key schedule is somewhat different for decryption.
* (The key table is used once forward and three times backward.)
* You could define an expanded key, or just write the code twice,
* as done here.
*/
WIN32DLL_DEFINE void _mcrypt_decrypt(word32 const key[8], word32 * in)
{
register word32 n1, n2; /* As named in the GOST */
#ifndef WORDS_BIGENDIAN
n1 = byteswap32(in[0]);
n2 = byteswap32(in[1]);
#else
n1 = in[0];
n2 = in[1];
#endif
n2 ^= f(n1 + key[0]);
n1 ^= f(n2 + key[1]);
n2 ^= f(n1 + key[2]);
n1 ^= f(n2 + key[3]);
n2 ^= f(n1 + key[4]);
n1 ^= f(n2 + key[5]);
n2 ^= f(n1 + key[6]);
n1 ^= f(n2 + key[7]);
n2 ^= f(n1 + key[7]);
n1 ^= f(n2 + key[6]);
n2 ^= f(n1 + key[5]);
n1 ^= f(n2 + key[4]);
n2 ^= f(n1 + key[3]);
n1 ^= f(n2 + key[2]);
n2 ^= f(n1 + key[1]);
n1 ^= f(n2 + key[0]);
n2 ^= f(n1 + key[7]);
n1 ^= f(n2 + key[6]);
n2 ^= f(n1 + key[5]);
n1 ^= f(n2 + key[4]);
n2 ^= f(n1 + key[3]);
n1 ^= f(n2 + key[2]);
n2 ^= f(n1 + key[1]);
n1 ^= f(n2 + key[0]);
n2 ^= f(n1 + key[7]);
n1 ^= f(n2 + key[6]);
n2 ^= f(n1 + key[5]);
n1 ^= f(n2 + key[4]);
n2 ^= f(n1 + key[3]);
n1 ^= f(n2 + key[2]);
n2 ^= f(n1 + key[1]);
n1 ^= f(n2 + key[0]);
#ifndef WORDS_BIGENDIAN
in[0] = byteswap32(n2);
in[1] = byteswap32(n1);
#else
in[0] = n2;
in[1] = n1;
#endif
}
WIN32DLL_DEFINE int _mcrypt_get_size()
{
return 8 * sizeof(word32);
}
WIN32DLL_DEFINE int _mcrypt_get_block_size()
{
return 8;
}
WIN32DLL_DEFINE int _is_block_algorithm()
{
return 1;
}
WIN32DLL_DEFINE int _mcrypt_get_key_size()
{
return 32;
}
static const int key_sizes[] = { 32 };
WIN32DLL_DEFINE const int *_mcrypt_get_supported_key_sizes(int *len)
{
*len = sizeof(key_sizes)/sizeof(int);
return key_sizes;
}
WIN32DLL_DEFINE const char *_mcrypt_get_algorithms_name()
{
return "GOST";
}
#define CIPHER "e498cf78cdf1d4a5"
WIN32DLL_DEFINE int _mcrypt_self_test()
{
char *keyword;
unsigned char plaintext[16];
unsigned char ciphertext[16];
int blocksize = _mcrypt_get_block_size(), j;
void *key;
unsigned char cipher_tmp[200];
keyword = calloc(1, _mcrypt_get_key_size());
if (keyword == NULL)
return -1;
for (j = 0; j < _mcrypt_get_key_size(); j++) {
keyword[j] = ((j * 2 + 10) % 256);
}
for (j = 0; j < blocksize; j++) {
plaintext[j] = j % 256;
}
key = malloc(_mcrypt_get_size());
if (key == NULL) {
free(keyword);
return -1;
}
memcpy(ciphertext, plaintext, blocksize);
_mcrypt_set_key(key, (void *) keyword, _mcrypt_get_key_size());
free(keyword);
_mcrypt_encrypt(key, (void *) ciphertext);
for (j = 0; j < blocksize; j++) {
sprintf(&((char *) cipher_tmp)[2 * j], "%.2x",
ciphertext[j]);
}
if (strcmp((char *) cipher_tmp, CIPHER) != 0) {
printf("failed compatibility\n");
printf("Expected: %s\nGot: %s\n", CIPHER,
(char *) cipher_tmp);
free(key);
return -1;
}
_mcrypt_decrypt(key, (void *) ciphertext);
free(key);
if (strcmp(ciphertext, plaintext) != 0) {
printf("failed internally\n");
return -1;
}
return 0;
}
WIN32DLL_DEFINE word32 _mcrypt_algorithm_version()
{
return 20010801;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,100 @@
// RegUtil.cpp: implementation of the CRegUtil class.
//
#include "stdafx.h"
#include "RegUtil.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
CRegUtil::CRegUtil()
{
m_hKey = NULL;
}
CRegUtil::~CRegUtil()
{
if (!m_hKey)
CloseKey();
}
BOOL CRegUtil::OpenKey(HKEY hKey, CString sKey)
{
LONG lRet = RegOpenKeyEx(hKey, TEXT(sKey), 0, KEY_ALL_ACCESS, &m_hKey);
if (lRet == ERROR_SUCCESS)
return TRUE;
else {
DWORD dwDisp;
lRet = RegCreateKeyEx(hKey, TEXT(sKey), 0, "REG_BINARY", REG_OPTION_NON_VOLATILE, KEY_ALL_ACCESS, 0, &m_hKey, &dwDisp);
if(lRet == ERROR_SUCCESS)
return TRUE;
else
return FALSE;
}
}
void CRegUtil::CloseKey()
{
if (m_hKey)
RegCloseKey(m_hKey);
m_hKey = NULL;
}
BOOL CRegUtil::SetStrValue(CString sName, CString sValue)
{
TCHAR szValue[MAX_PATH] = {'\0'};
_tcscpy(szValue, sValue);
LONG lRet = RegSetValueEx(m_hKey, TEXT(sName), NULL, REG_SZ, (PBYTE)&szValue, (DWORD)strlen(szValue));
if (lRet == ERROR_SUCCESS)
return TRUE;
else
return FALSE;
}
CString CRegUtil::GetStrValue(CString sName)
{
DWORD dwType = REG_SZ;
char szValue[MAX_PATH];
DWORD dwLength = sizeof(szValue);
LONG lRet = RegQueryValueEx(m_hKey, TEXT(sName), NULL, &dwType, (PBYTE)szValue, &dwLength);
if (lRet == ERROR_SUCCESS) {
szValue[dwLength] = NULL;
return CString(szValue);
}
else
return "";
}
BOOL CRegUtil::SetNumValue(CString sName, UINT nValue)
{
LONG lRet = RegSetValueEx(m_hKey, TEXT(sName), NULL, REG_DWORD, (PBYTE)&nValue, (DWORD)sizeof(nValue));
if (lRet == ERROR_SUCCESS)
return TRUE;
else
return FALSE;
}
UINT CRegUtil::GetNumValue(CString sName)
{
DWORD dwType = REG_DWORD;
DWORD dwValue;
DWORD dwLength = sizeof(DWORD);
LONG lRet = RegQueryValueEx(m_hKey, TEXT(sName), NULL, &dwType, (PBYTE)&dwValue, &dwLength);
if (lRet == ERROR_SUCCESS)
return (UINT)dwValue;
else
return 0;
}
@@ -0,0 +1,245 @@
/*
WebDAV Properties manipulation
Copyright (C) 1999-2004, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_PROPS_H
#define NE_PROPS_H
#include "ne_request.h"
#include "ne_207.h"
BEGIN_NEON_DECLS
/* There are two interfaces for fetching properties. The first is
* 'ne_simple_propfind', which is relatively simple, and easy to use,
* but only lets you fetch FLAT properties, i.e. properties which are
* just a string of bytes. The complex interface is 'ne_propfind_*',
* which is complicated, and hard to use, but lets you parse
* structured properties, i.e. properties which have XML content. */
/* The 'ne_simple_propfind' interface. ***
*
* ne_simple_propfind allows you to fetch a set of properties for a
* single resource, or a tree of resources. You set the operation
* going by passing these arguments:
*
* - the session which should be used.
* - the URI and the depth of the operation (0, 1, infinite)
* - the names of the properties which you want to fetch
* - a results callback, and the userdata for the callback.
*
* For each resource found, the results callback is called, passing
* you two things along with the userdata you passed in originally:
*
* - the URI of the resource (const char *href)
* - the properties results set (const ne_prop_result_set *results)
* */
/* The name of a WebDAV property. 'nspace' may be NULL. */
typedef struct {
const char *nspace, *name;
} ne_propname;
typedef struct ne_prop_result_set_s ne_prop_result_set;
/* Get the value of a given property. Will return NULL if there was an
* error fetching this property on this resource. Call
* ne_propset_result to get the response-status if so. */
const char *ne_propset_value(const ne_prop_result_set *set,
const ne_propname *propname);
/* Returns the status structure for fetching the given property on
* this resource. This function will return NULL if the server did not
* return the property (which is a server error). */
const ne_status *ne_propset_status(const ne_prop_result_set *set,
const ne_propname *propname);
/* Returns the private pointer for the given propset. */
void *ne_propset_private(const ne_prop_result_set *set);
/* Return language string of property (may be NULL). */
const char *ne_propset_lang(const ne_prop_result_set *set,
const ne_propname *pname);
/* ne_propset_iterate iterates over a properties result set,
* calling the callback for each property in the set. userdata is
* passed as the first argument to the callback. value may be NULL,
* indicating an error occurred fetching this property: look at
* status for the error in that case.
*
* If the iterator returns non-zero, ne_propset_iterate will return
* immediately with that value.
*/
typedef int (*ne_propset_iterator)(void *userdata,
const ne_propname *pname,
const char *value,
const ne_status *status);
/* Iterate over all the properties in 'set', calling 'iterator'
* for each, passing 'userdata' as the first argument to callback.
*
* Returns:
* whatever value iterator returns.
*/
int ne_propset_iterate(const ne_prop_result_set *set,
ne_propset_iterator iterator, void *userdata);
/* Callback for handling the results of fetching properties for a
* single resource (named by 'href'). The results are stored in the
* result set 'results': use ne_propset_* to examine this object. */
typedef void (*ne_props_result)(void *userdata, const char *href,
const ne_prop_result_set *results);
/* Fetch properties for a resource (if depth == NE_DEPTH_ZERO),
* or a tree of resources (if depth == NE_DEPTH_ONE or _INFINITE).
*
* Names of the properties required must be given in 'props',
* or if props is NULL, *all* properties are fetched.
*
* 'results' is called for each resource in the response, userdata is
* passed as the first argument to the callback. It is important to
* note that the callback is called as the response is read off the
* socket, so don't do anything silly in it (e.g. sleep(100), or call
* any functions which use this session).
*
* Note that if 'depth' is NE_DEPTH_INFINITY, some servers may refuse
* the request.
*
* Returns NE_*. */
int ne_simple_propfind(ne_session *sess, const char *path, int depth,
const ne_propname *props,
ne_props_result results, void *userdata);
/* The properties of a resource can be manipulated using ne_proppatch.
* A single proppatch request may include any number of individual
* "set" and "remove" operations, and is defined to have
* "all-or-nothing" semantics, so either all the operations succeed,
* or none do. */
/* A proppatch operation may either set a property to have a new
* value, in which case 'type' must be ne_propset, and 'value' must be
* non-NULL; or it can remove a property; in which case 'type' must be
* ne_propremove, and 'value' is ignored. In both cases, 'name' must
* be set to the name of the property to alter. */
enum ne_proppatch_optype {
ne_propset,
ne_propremove
};
typedef struct {
const ne_propname *name;
enum ne_proppatch_optype type;
const char *value;
} ne_proppatch_operation;
/* Execute a set of property operations 'ops' on 'path'. 'ops' is an
* array terminated by an operation with a NULL 'name' field. Returns
* NE_*. */
int ne_proppatch(ne_session *sess, const char *path,
const ne_proppatch_operation *ops);
/* Retrieve property names for the resources at 'path'. 'results'
* callback is called for each resource. Use 'ne_propset_iterate' on
* the passed results object to retrieve the list of property names.
* */
int ne_propnames(ne_session *sess, const char *path, int depth,
ne_props_result results, void *userdata);
/* The complex, you-do-all-the-work, property fetch interface:
*/
struct ne_propfind_handler_s;
typedef struct ne_propfind_handler_s ne_propfind_handler;
/* Retrieve the 'private' pointer for the current propset for the
* given handler, as returned by the ne_props_create_complex callback
* installed using 'ne_propfind_set_private'. If this callback was
* not registered, this function will return NULL. */
void *ne_propfind_current_private(ne_propfind_handler *handler);
/* Create a PROPFIND handler, for the given resource or set of
* resources.
*
* Depth must be one of NE_DEPTH_*. */
ne_propfind_handler *
ne_propfind_create(ne_session *sess, const char *path, int depth);
/* Return the XML parser for the given handler (only need if you want
* to handle complex properties). */
ne_xml_parser *ne_propfind_get_parser(ne_propfind_handler *handler);
/* This interface reserves the state integer range 'x' where 0 < x
* and x < NE_PROPS_STATE_TOP. */
#define NE_PROPS_STATE_TOP (NE_207_STATE_TOP + 100)
/* Return the request object for the given handler. You MUST NOT use
* ne_set_request_body_* on this request object. (this call is only
* needed if for instance, you want to add extra headers to the
* PROPFIND request). The result of using the request pointer after
* ne_propfind_destroy(handler) has been called is undefined. */
ne_request *ne_propfind_get_request(ne_propfind_handler *handler);
/* A "complex property" has a value which is structured XML. To handle
* complex properties, you must set up and register an XML handler
* which will understand the elements which make up such properties.
* The handler must be registered with the parser returned by
* 'ne_propfind_get_parser'.
*
* To store the parsed value of the property, a 'private' structure is
* allocated in each propset (i.e. one per resource). When parsing the
* property value elements, for each new resource encountered in the
* response, the 'creator' callback is called to retrieve a 'private'
* structure for this resource.
*
* Whilst in XML element callbacks you will have registered to handle
* complex properties, you can use the 'ne_propfind_current_private'
* call to retrieve the pointer to this private structure.
*
* To retrieve this 'private' structure from the propset in the
* results callback, simply call 'ne_propset_private'.
* */
typedef void *(*ne_props_create_complex)(void *userdata,
const char *href);
void ne_propfind_set_private(ne_propfind_handler *handler,
ne_props_create_complex creator,
void *userdata);
/* Fetch all properties.
*
* Returns NE_*. */
int ne_propfind_allprop(ne_propfind_handler *handler,
ne_props_result result, void *userdata);
/* Fetch all properties with names listed in array 'names', which is
* terminated by a property with a NULL name field. For each resource
* encountered, the result callback will be invoked, passing in
* 'userdata' as the first argument.
*
* Returns NE_*. */
int ne_propfind_named(ne_propfind_handler *handler,
const ne_propname *names,
ne_props_result result, void *userdata);
/* Destroy a propfind handler after use. */
void ne_propfind_destroy(ne_propfind_handler *handler);
END_NEON_DECLS
#endif /* NE_PROPS_H */
@@ -0,0 +1,831 @@
/*
WebDAV Class 2 locking operations
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_LIMITS_H
#include <limits.h>
#endif
#include <ctype.h> /* for isdigit() */
#include "ne_alloc.h"
#include "ne_request.h"
#include "ne_xml.h"
#include "ne_locks.h"
#include "ne_uri.h"
#include "ne_basic.h"
#include "ne_props.h"
#include "ne_207.h"
#include "ne_i18n.h"
#include "ne_xmlreq.h"
#define HOOK_ID "http://webdav.org/neon/hooks/webdav-locking"
#define EOL "\r\n"
/* A list of lock objects. */
struct lock_list {
struct ne_lock *lock;
struct lock_list *next, *prev;
};
struct ne_lock_store_s {
struct lock_list *locks;
struct lock_list *cursor; /* current position in 'locks' */
};
struct lh_req_cookie {
const ne_lock_store *store;
struct lock_list *submit;
};
/* Context for PROPFIND/lockdiscovery callbacks */
struct discover_ctx {
ne_session *session;
ne_lock_result results;
void *userdata;
ne_buffer *cdata;
};
/* Context for handling LOCK response */
struct lock_ctx {
struct ne_lock active; /* activelock */
ne_request *req; /* the request in question */
char *token; /* the token we're after. */
int found;
ne_buffer *cdata;
};
/* use the "application" state space. */
#define ELM_LOCK_FIRST (NE_PROPS_STATE_TOP + 66)
#define ELM_lockdiscovery (ELM_LOCK_FIRST)
#define ELM_activelock (ELM_LOCK_FIRST + 1)
#define ELM_lockscope (ELM_LOCK_FIRST + 2)
#define ELM_locktype (ELM_LOCK_FIRST + 3)
#define ELM_depth (ELM_LOCK_FIRST + 4)
#define ELM_owner (ELM_LOCK_FIRST + 5)
#define ELM_timeout (ELM_LOCK_FIRST + 6)
#define ELM_locktoken (ELM_LOCK_FIRST + 7)
#define ELM_lockinfo (ELM_LOCK_FIRST + 8)
#define ELM_write (ELM_LOCK_FIRST + 9)
#define ELM_exclusive (ELM_LOCK_FIRST + 10)
#define ELM_shared (ELM_LOCK_FIRST + 11)
#define ELM_href (ELM_LOCK_FIRST + 12)
#define ELM_prop (NE_207_STATE_PROP)
static const struct ne_xml_idmap element_map[] = {
#define ELM(x) { "DAV:", #x, ELM_ ## x }
ELM(lockdiscovery), ELM(activelock), ELM(prop), ELM(lockscope),
ELM(locktype), ELM(depth), ELM(owner), ELM(timeout), ELM(locktoken),
ELM(lockinfo), ELM(lockscope), ELM(locktype), ELM(write), ELM(exclusive),
ELM(shared), ELM(href)
/* no "lockentry" */
#undef ELM
};
static const ne_propname lock_props[] = {
{ "DAV:", "lockdiscovery" },
{ NULL }
};
/* this simply registers the accessor for the function. */
static void lk_create(ne_request *req, void *session,
const char *method, const char *uri)
{
struct lh_req_cookie *lrc = ne_malloc(sizeof *lrc);
lrc->store = session;
lrc->submit = NULL;
ne_set_request_private(req, HOOK_ID, lrc);
}
static void lk_pre_send(ne_request *r, void *userdata, ne_buffer *req)
{
struct lh_req_cookie *lrc = ne_get_request_private(r, HOOK_ID);
if (lrc->submit != NULL) {
struct lock_list *item;
/* Add in the If header */
ne_buffer_zappend(req, "If:");
for (item = lrc->submit; item != NULL; item = item->next) {
char *uri = ne_uri_unparse(&item->lock->uri);
ne_buffer_concat(req, " <", uri, "> (<",
item->lock->token, ">)", NULL);
ne_free(uri);
}
ne_buffer_zappend(req, EOL);
}
}
/* Insert 'lock' into lock list *list. */
static void insert_lock(struct lock_list **list, struct ne_lock *lock)
{
struct lock_list *item = ne_malloc(sizeof *item);
if (*list != NULL) {
(*list)->prev = item;
}
item->prev = NULL;
item->next = *list;
item->lock = lock;
*list = item;
}
static void free_list(struct lock_list *list, int destroy)
{
struct lock_list *next;
while (list != NULL) {
next = list->next;
if (destroy)
ne_lock_destroy(list->lock);
ne_free(list);
list = next;
}
}
static void lk_destroy(ne_request *req, void *userdata)
{
struct lh_req_cookie *lrc = ne_get_request_private(req, HOOK_ID);
free_list(lrc->submit, 0);
ne_free(lrc);
}
void ne_lockstore_destroy(ne_lock_store *store)
{
free_list(store->locks, 1);
ne_free(store);
}
ne_lock_store *ne_lockstore_create(void)
{
return ne_calloc(sizeof(ne_lock_store));
}
#define CURSOR_RET(s) ((s)->cursor?(s)->cursor->lock:NULL)
struct ne_lock *ne_lockstore_first(ne_lock_store *store)
{
store->cursor = store->locks;
return CURSOR_RET(store);
}
struct ne_lock *ne_lockstore_next(ne_lock_store *store)
{
store->cursor = store->cursor->next;
return CURSOR_RET(store);
}
void ne_lockstore_register(ne_lock_store *store, ne_session *sess)
{
/* Register the hooks */
ne_hook_create_request(sess, lk_create, store);
ne_hook_pre_send(sess, lk_pre_send, store);
ne_hook_destroy_request(sess, lk_destroy, store);
}
/* Submit the given lock for the given URI */
static void submit_lock(struct lh_req_cookie *lrc, struct ne_lock *lock)
{
struct lock_list *item;
/* Check for dups */
for (item = lrc->submit; item != NULL; item = item->next) {
if (strcasecmp(item->lock->token, lock->token) == 0)
return;
}
insert_lock(&lrc->submit, lock);
}
struct ne_lock *ne_lockstore_findbyuri(ne_lock_store *store,
const ne_uri *uri)
{
struct lock_list *cur;
for (cur = store->locks; cur != NULL; cur = cur->next) {
if (ne_uri_cmp(&cur->lock->uri, uri) == 0) {
return cur->lock;
}
}
return NULL;
}
void ne_lock_using_parent(ne_request *req, const char *path)
{
struct lh_req_cookie *lrc = ne_get_request_private(req, HOOK_ID);
ne_uri u;
struct lock_list *item;
char *parent;
if (lrc == NULL)
return;
parent = ne_path_parent(path);
if (parent == NULL)
return;
u.authinfo = NULL;
ne_fill_server_uri(ne_get_session(req), &u);
for (item = lrc->store->locks; item != NULL; item = item->next) {
/* Only care about locks which are on this server. */
u.path = item->lock->uri.path;
if (ne_uri_cmp(&u, &item->lock->uri))
continue;
/* This lock is needed if it is an infinite depth lock which
* covers the parent, or a lock on the parent itself. */
if ((item->lock->depth == NE_DEPTH_INFINITE &&
ne_path_childof(item->lock->uri.path, parent)) ||
ne_path_compare(item->lock->uri.path, parent) == 0) {
NE_DEBUG(NE_DBG_LOCKS, "Locked parent, %s on %s\n",
item->lock->token, item->lock->uri.path);
submit_lock(lrc, item->lock);
}
}
u.path = parent; /* handy: makes u.path valid and ne_free(parent). */
ne_uri_free(&u);
}
void ne_lock_using_resource(ne_request *req, const char *uri, int depth)
{
struct lh_req_cookie *lrc = ne_get_request_private(req, HOOK_ID);
struct lock_list *item;
int match;
if (lrc == NULL)
return;
/* Iterate over the list of stored locks to see if any of them
* apply to this resource */
for (item = lrc->store->locks; item != NULL; item = item->next) {
match = 0;
if (depth == NE_DEPTH_INFINITE &&
ne_path_childof(uri, item->lock->uri.path)) {
/* Case 1: this is a depth-infinity request which will
* modify a lock somewhere inside the collection. */
NE_DEBUG(NE_DBG_LOCKS, "Has child: %s\n", item->lock->token);
match = 1;
}
else if (ne_path_compare(uri, item->lock->uri.path) == 0) {
/* Case 2: this request is directly on a locked resource */
NE_DEBUG(NE_DBG_LOCKS, "Has direct lock: %s\n", item->lock->token);
match = 1;
}
else if (item->lock->depth == NE_DEPTH_INFINITE &&
ne_path_childof(item->lock->uri.path, uri)) {
/* Case 3: there is a higher-up infinite-depth lock which
* covers the resource that this request will modify. */
NE_DEBUG(NE_DBG_LOCKS, "Is child of: %s\n", item->lock->token);
match = 1;
}
if (match) {
submit_lock(lrc, item->lock);
}
}
}
void ne_lockstore_add(ne_lock_store *store, struct ne_lock *lock)
{
insert_lock(&store->locks, lock);
}
void ne_lockstore_remove(ne_lock_store *store, struct ne_lock *lock)
{
struct lock_list *item;
/* Find the lock */
for (item = store->locks; item != NULL; item = item->next)
if (item->lock == lock)
break;
if (item->prev != NULL) {
item->prev->next = item->next;
} else {
store->locks = item->next;
}
if (item->next != NULL) {
item->next->prev = item->prev;
}
ne_free(item);
}
struct ne_lock *ne_lock_copy(const struct ne_lock *lock)
{
struct ne_lock *ret = ne_calloc(sizeof *ret);
ret->uri.path = ne_strdup(lock->uri.path);
ret->uri.host = ne_strdup(lock->uri.host);
ret->uri.scheme = ne_strdup(lock->uri.scheme);
ret->uri.port = lock->uri.port;
ret->token = ne_strdup(lock->token);
ret->depth = lock->depth;
ret->type = lock->type;
ret->scope = lock->scope;
if (lock->owner) ret->owner = ne_strdup(lock->owner);
ret->timeout = lock->timeout;
return ret;
}
struct ne_lock *ne_lock_create(void)
{
struct ne_lock *lock = ne_calloc(sizeof *lock);
lock->depth = NE_DEPTH_ZERO;
lock->type = ne_locktype_write;
lock->scope = ne_lockscope_exclusive;
lock->timeout = NE_TIMEOUT_INVALID;
return lock;
}
void ne_lock_free(struct ne_lock *lock)
{
ne_uri_free(&lock->uri);
if (lock->owner) {
ne_free(lock->owner);
lock->owner = NULL;
}
if (lock->token) {
ne_free(lock->token);
lock->token = NULL;
}
}
void ne_lock_destroy(struct ne_lock *lock)
{
ne_lock_free(lock);
ne_free(lock);
}
int ne_unlock(ne_session *sess, const struct ne_lock *lock)
{
ne_request *req = ne_request_create(sess, "UNLOCK", lock->uri.path);
int ret;
ne_print_request_header(req, "Lock-Token", "<%s>", lock->token);
/* UNLOCK of a lock-null resource removes the resource from the
* parent collection; so an UNLOCK may modify the parent
* collection. (somewhat counter-intuitive, and not easily derived
* from 2518.) */
ne_lock_using_parent(req, lock->uri.path);
ret = ne_request_dispatch(req);
if (ret == NE_OK && ne_get_status(req)->klass != 2) {
ret = NE_ERROR;
}
ne_request_destroy(req);
return ret;
}
static int parse_depth(const char *depth)
{
if (strcasecmp(depth, "infinity") == 0) {
return NE_DEPTH_INFINITE;
} else if (isdigit(depth[0])) {
return atoi(depth);
} else {
return -1;
}
}
static long parse_timeout(const char *timeout)
{
if (strcasecmp(timeout, "infinite") == 0) {
return NE_TIMEOUT_INFINITE;
} else if (strncasecmp(timeout, "Second-", 7) == 0) {
long to = strtol(timeout+7, NULL, 10);
if (to == LONG_MIN || to == LONG_MAX)
return NE_TIMEOUT_INVALID;
return to;
} else {
return NE_TIMEOUT_INVALID;
}
}
static void discover_results(void *userdata, const char *href,
const ne_prop_result_set *set)
{
struct discover_ctx *ctx = userdata;
struct ne_lock *lock = ne_propset_private(set);
const ne_status *status = ne_propset_status(set, &lock_props[0]);
/* Require at least that the lock has a token. */
if (lock->token) {
if (status && status->klass != 2) {
ctx->results(ctx->userdata, NULL, lock->uri.path, status);
} else {
ctx->results(ctx->userdata, lock, lock->uri.path, NULL);
}
}
else if (status) {
ctx->results(ctx->userdata, NULL, href, status);
}
ne_lock_destroy(lock);
NE_DEBUG(NE_DBG_LOCKS, "End of response for %s\n", href);
}
static int
end_element_common(struct ne_lock *l, int state, const char *cdata)
{
switch (state) {
case ELM_write:
l->type = ne_locktype_write;
break;
case ELM_exclusive:
l->scope = ne_lockscope_exclusive;
break;
case ELM_shared:
l->scope = ne_lockscope_shared;
break;
case ELM_depth:
NE_DEBUG(NE_DBG_LOCKS, "Got depth: %s\n", cdata);
l->depth = parse_depth(cdata);
if (l->depth == -1) {
return -1;
}
break;
case ELM_timeout:
NE_DEBUG(NE_DBG_LOCKS, "Got timeout: %s\n", cdata);
l->timeout = parse_timeout(cdata);
if (l->timeout == NE_TIMEOUT_INVALID) {
return -1;
}
break;
case ELM_owner:
l->owner = strdup(cdata);
break;
case ELM_href:
l->token = strdup(cdata);
break;
}
return 0;
}
/* End-element handler for lock discovery PROPFIND response */
static int end_element_ldisc(void *userdata, int state,
const char *nspace, const char *name)
{
struct ne_lock *lock = ne_propfind_current_private(userdata);
struct discover_ctx *ctx = userdata;
return end_element_common(lock, state, ctx->cdata->data);
}
static inline int can_accept(int parent, int id)
{
return (parent == NE_XML_STATEROOT && id == ELM_prop) ||
(parent == ELM_prop && id == ELM_lockdiscovery) ||
(parent == ELM_lockdiscovery && id == ELM_activelock) ||
(parent == ELM_activelock &&
(id == ELM_lockscope || id == ELM_locktype ||
id == ELM_depth || id == ELM_owner ||
id == ELM_timeout || id == ELM_locktoken)) ||
(parent == ELM_lockscope &&
(id == ELM_exclusive || id == ELM_shared)) ||
(parent == ELM_locktype && id == ELM_write) ||
(parent == ELM_locktoken && id == ELM_href);
}
static int ld_startelm(void *userdata, int parent,
const char *nspace, const char *name,
const char **atts)
{
struct discover_ctx *ctx = userdata;
int id = ne_xml_mapid(element_map, NE_XML_MAPLEN(element_map),
nspace, name);
ne_buffer_clear(ctx->cdata);
if (can_accept(parent, id))
return id;
else
return NE_XML_DECLINE;
}
#define MAX_CDATA (256)
static int lk_cdata(void *userdata, int state,
const char *cdata, size_t len)
{
struct lock_ctx *ctx = userdata;
if (ctx->cdata->used + len < MAX_CDATA)
ne_buffer_append(ctx->cdata, cdata, len);
return 0;
}
static int ld_cdata(void *userdata, int state,
const char *cdata, size_t len)
{
struct discover_ctx *ctx = userdata;
if (ctx->cdata->used + len < MAX_CDATA)
ne_buffer_append(ctx->cdata, cdata, len);
return 0;
}
static int lk_startelm(void *userdata, int parent,
const char *nspace, const char *name,
const char **atts)
{
struct lock_ctx *ctx = userdata;
int id;
id = ne_xml_mapid(element_map, NE_XML_MAPLEN(element_map), nspace, name);
NE_DEBUG(NE_DBG_LOCKS, "lk_startelm: %s => %d\n", name, id);
if (id == 0)
return NE_XML_DECLINE;
if (parent == 0 && ctx->token == NULL) {
const char *token = ne_get_response_header(ctx->req, "Lock-Token");
/* at the root element; retrieve the Lock-Token header,
* and bail if it wasn't given. */
if (token == NULL) {
ne_set_error(ne_get_session(ctx->req), "%s",
_("LOCK response missing Lock-Token header"));
return NE_XML_ABORT;
}
if (token[0] == '<') token++;
ctx->token = ne_strdup(token);
ne_shave(ctx->token, ">");
NE_DEBUG(NE_DBG_LOCKS, "lk_startelm: Finding token %s\n",
ctx->token);
}
/* TODO: only accept 'prop' as root for LOCK response */
if (!can_accept(parent, id))
return NE_XML_DECLINE;
if (id == ELM_activelock && !ctx->found) {
/* a new activelock */
ne_lock_free(&ctx->active);
memset(&ctx->active, 0, sizeof ctx->active);
ctx->active.timeout = NE_TIMEOUT_INVALID;
}
ne_buffer_clear(ctx->cdata);
return id;
}
/* End-element handler for LOCK response */
static int lk_endelm(void *userdata, int state,
const char *nspace, const char *name)
{
struct lock_ctx *ctx = userdata;
if (ctx->found)
return 0;
if (end_element_common(&ctx->active, state, ctx->cdata->data))
return -1;
if (state == ELM_activelock) {
if (ctx->active.token && strcmp(ctx->active.token, ctx->token) == 0) {
ctx->found = 1;
}
}
return 0;
}
static void *ld_create(void *userdata, const char *href)
{
struct discover_ctx *ctx = userdata;
struct ne_lock *lk = ne_lock_create();
if (ne_uri_parse(href, &lk->uri) != 0) {
ne_lock_destroy(lk);
return NULL;
}
if (!lk->uri.host)
ne_fill_server_uri(ctx->session, &lk->uri);
return lk;
}
/* Discover all locks on URI */
int ne_lock_discover(ne_session *sess, const char *uri,
ne_lock_result callback, void *userdata)
{
ne_propfind_handler *handler;
struct discover_ctx ctx = {0};
int ret;
ctx.results = callback;
ctx.userdata = userdata;
ctx.session = sess;
ctx.cdata = ne_buffer_create();
handler = ne_propfind_create(sess, uri, NE_DEPTH_ZERO);
ne_propfind_set_private(handler, ld_create, &ctx);
ne_xml_push_handler(ne_propfind_get_parser(handler),
ld_startelm, ld_cdata, end_element_ldisc, handler);
ret = ne_propfind_named(handler, lock_props, discover_results, &ctx);
ne_buffer_destroy(ctx.cdata);
ne_propfind_destroy(handler);
return ret;
}
static void add_timeout_header(ne_request *req, long timeout)
{
if (timeout == NE_TIMEOUT_INFINITE) {
ne_add_request_header(req, "Timeout", "Infinite");
}
else if (timeout != NE_TIMEOUT_INVALID && timeout > 0) {
ne_print_request_header(req, "Timeout", "Second-%ld", timeout);
}
/* just ignore it if timeout == 0 or invalid. */
}
int ne_lock(ne_session *sess, struct ne_lock *lock)
{
ne_request *req = ne_request_create(sess, "LOCK", lock->uri.path);
ne_buffer *body = ne_buffer_create();
ne_xml_parser *parser = ne_xml_create();
int ret, parse_failed;
struct lock_ctx ctx;
memset(&ctx, 0, sizeof ctx);
ctx.cdata = ne_buffer_create();
ctx.req = req;
ne_xml_push_handler(parser, lk_startelm, lk_cdata, lk_endelm, &ctx);
/* Create the body */
ne_buffer_concat(body, "<?xml version=\"1.0\" encoding=\"utf-8\"?>" EOL
"<lockinfo xmlns='DAV:'>" EOL " <lockscope>",
lock->scope==ne_lockscope_exclusive?
"<exclusive/>":"<shared/>",
"</lockscope>" EOL
"<locktype><write/></locktype>", NULL);
if (lock->owner) {
ne_buffer_concat(body, "<owner>", lock->owner, "</owner>" EOL, NULL);
}
ne_buffer_zappend(body, "</lockinfo>" EOL);
ne_set_request_body_buffer(req, body->data, ne_buffer_size(body));
ne_add_request_header(req, "Content-Type", NE_XML_MEDIA_TYPE);
ne_add_depth_header(req, lock->depth);
add_timeout_header(req, lock->timeout);
/* TODO:
* By 2518, we need this only if we are creating a lock-null resource.
* Since we don't KNOW whether the lock we're given is a lock-null
* or not, we cover our bases.
*/
ne_lock_using_parent(req, lock->uri.path);
/* This one is clearer from 2518 sec 8.10.4. */
ne_lock_using_resource(req, lock->uri.path, lock->depth);
ret = ne_xml_dispatch_request(req, parser);
ne_buffer_destroy(body);
ne_buffer_destroy(ctx.cdata);
parse_failed = ne_xml_failed(parser);
if (ret == NE_OK && ne_get_status(req)->klass == 2) {
if (ctx.token == NULL) {
ret = NE_ERROR;
ne_set_error(sess, _("No Lock-Token header given"));
}
else if (parse_failed) {
ret = NE_ERROR;
ne_set_error(sess, "%s", ne_xml_get_error(parser));
}
else if (ne_get_status(req)->code == 207) {
ret = NE_ERROR;
/* TODO: set the error string appropriately */
}
else if (ctx.found) {
/* it worked: copy over real lock details if given. */
if (lock->token) ne_free(lock->token);
lock->token = ctx.token;
ctx.token = NULL;
if (ctx.active.timeout != NE_TIMEOUT_INVALID)
lock->timeout = ctx.active.timeout;
lock->scope = ctx.active.scope;
lock->type = ctx.active.type;
if (ctx.active.depth >= 0)
lock->depth = ctx.active.depth;
if (ctx.active.owner) {
if (lock->owner) ne_free(lock->owner);
lock->owner = ctx.active.owner;
ctx.active.owner = NULL;
}
} else {
ret = NE_ERROR;
ne_set_error(sess, _("Response missing activelock for %s"),
ctx.token);
}
} else if (ret == NE_OK /* && status != 2xx */) {
ret = NE_ERROR;
}
ne_lock_free(&ctx.active);
if (ctx.token) ne_free(ctx.token);
ne_request_destroy(req);
ne_xml_destroy(parser);
return ret;
}
int ne_lock_refresh(ne_session *sess, struct ne_lock *lock)
{
ne_request *req = ne_request_create(sess, "LOCK", lock->uri.path);
ne_xml_parser *parser = ne_xml_create();
int ret;
struct lock_ctx ctx;
memset(&ctx, 0, sizeof ctx);
ctx.cdata = ne_buffer_create();
ctx.req = req;
ctx.token = lock->token;
/* Handle the response and update *lock appropriately. */
ne_xml_push_handler(parser, lk_startelm, lk_cdata, lk_endelm, &ctx);
/* For a lock refresh, submitting only this lock token must be
* sufficient. */
ne_print_request_header(req, "If", "(<%s>)", lock->token);
add_timeout_header(req, lock->timeout);
ret = ne_xml_dispatch_request(req, parser);
if (ret == NE_OK) {
if (ne_get_status(req)->klass != 2) {
ret = NE_ERROR; /* and use default session error */
} else if (ne_xml_failed(parser)) {
ret = NE_ERROR;
ne_set_error(sess, "%s", ne_xml_get_error(parser));
} else if (!ctx.found) {
ne_set_error(sess, _("No activelock for <%s> returned in "
"LOCK refresh response"), lock->token);
ret = NE_ERROR;
} else /* success! */ {
/* update timeout for passed-in lock structure. */
lock->timeout = ctx.active.timeout;
}
}
ne_lock_free(&ctx.active);
ne_buffer_destroy(ctx.cdata);
ne_request_destroy(req);
ne_xml_destroy(parser);
return ret;
}
@@ -0,0 +1,41 @@
/*
HTTP-redirect support
Copyright (C) 1999-2002, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_REDIRECT_H
#define NE_REDIRECT_H
#include "ne_request.h"
BEGIN_NEON_DECLS
/* Register redirect handling: if a redirection response is given, the
* request will fail with the NE_REDIRECT code, and the destinsation
* of the redirect can be retrieved using ne_redirect_location(). */
void ne_redirect_register(ne_session *sess);
/* Returns location of last redirect. Will return NULL if no redirect
* has been encountered for given session, or the last redirect
* encountered could not be parsed. */
const ne_uri *ne_redirect_location(ne_session *sess);
END_NEON_DECLS
#endif /* NE_REDIRECT_H */
@@ -0,0 +1,142 @@
/*
String utility functions
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_STRING_H
#define NE_STRING_H
#include "ne_defs.h"
#include "ne_alloc.h"
#include <stdarg.h>
BEGIN_NEON_DECLS
/* ne_token and ne_qtoken return the next token in *str between *str
* and separator character 'sep' or the NUL terminator. ne_qtoken
* skips over any parts quoted using a pair of any one of the
* characters given in 'quotes'. After returning, *str will point to
* the next character after the separator, or NULL if no more
* separator characters were found.
*
* ne_qtoken may return NULL if unterminated quotes are found. */
char *ne_token(char **str, char sep);
char *ne_qtoken(char **str, char sep, const char *quotes);
/* Return portion of 'str' with any characters in 'whitespace' shaved
* off the beginning and end. Modifies str. */
char *ne_shave(char *str, const char *whitespace);
/* Cleanse 'str' of non-printable characters. 'str' is modified
* in-place, and returned. */
char *ne_strclean(char *str);
/* A base64 encoder: converts 'len' bytes of 'text' to base64.
* Returns malloc-allocated buffer; caller must free(). */
char *ne_base64(const unsigned char *text, size_t len);
/* Base64 decoder; decodes NUL-terminated base64-encoded string
* 'data', places malloc-allocated raw data in '*out', returns length,
* or zero on decode error (in which case *out is undefined). */
size_t ne_unbase64(const char *data, unsigned char **out);
/* String buffer handling. (Strings are zero-terminated still). A
* string buffer ne_buffer * which grows dynamically with the
* string. */
typedef struct {
char *data; /* contents: null-terminated string. */
size_t used; /* used bytes in buffer */
size_t length; /* length of buffer */
} ne_buffer;
/* Returns size of data in buffer, equiv to strlen(ne_buffer_data(buf)) */
#define ne_buffer_size(buf) ((buf)->used - 1)
/* Concatenate all given strings onto the end of the buffer. The
* strings must all be NUL-terminated, and MUST be followed by a NULL
* argument marking the end of the list. */
void ne_buffer_concat(ne_buffer *buf, ...);
/* Create a new ne_buffer. */
ne_buffer *ne_buffer_create(void);
/* Create a new ne_buffer of given minimum size. */
ne_buffer *ne_buffer_ncreate(size_t size);
/* Destroys (deallocates) a buffer */
void ne_buffer_destroy(ne_buffer *buf);
/* Append a NUL-terminated string 'str' to buf. */
void ne_buffer_zappend(ne_buffer *buf, const char *str);
/* Append 'len' bytes of 'data' to buf. 'data' does not need to be
* NUL-terminated. The resultant string will have a NUL-terminator,
* either way. */
void ne_buffer_append(ne_buffer *buf, const char *data, size_t len);
/* Append a literal constant string 'str' to buffer 'buf'. */
#define ne_buffer_czappend(buf, str) \
ne_buffer_append((buf), (str), sizeof((str)) - 1)
/* Empties the contents of buf; makes the buffer zero-length. */
void ne_buffer_clear(ne_buffer *buf);
/* Grows the ne_buffer to a minimum size. */
void ne_buffer_grow(ne_buffer *buf, size_t size);
void ne_buffer_altered(ne_buffer *buf);
/* Destroys a buffer, WITHOUT freeing the data, and returns the
* data. */
char *ne_buffer_finish(ne_buffer *buf);
/* Thread-safe strerror() wrapper; place system error for errno value
* 'errnum' in 'buffer', which is of length 'buflen'. Returns
* 'buffer'. */
char *ne_strerror(int errnum, char *buffer, size_t buflen);
/* ne_strnzcpy copies at most 'n'-1 bytes of 'src' to 'dest', and
* ensures that 'dest' is subsequently NUL-terminated. */
#define ne_strnzcpy(dest, src, n) do { \
strncpy(dest, src, n-1); dest[n-1] = '\0'; } while (0)
/* Return malloc-allocated concatenation of all NUL-terminated string
* arguments, up to a terminating NULL. */
char *ne_concat(const char *str, ...);
#define NE_ASC2HEX(x) (((x) <= '9') ? ((x) - '0') : (tolower((x)) + 10 - 'a'))
#define NE_HEX2ASC(x) ((char) ((x) > 9 ? ((x) - 10 + 'a') : ((x) + '0')))
/* Wrapper for snprintf: always NUL-terminates returned buffer, and
* returns strlen(str). */
size_t ne_snprintf(char *str, size_t size, const char *fmt, ...)
ne_attribute((format(printf, 3, 4)));
/* Wrapper for vsnprintf. */
size_t ne_vsnprintf(char *str, size_t size, const char *fmt, va_list ap)
ne_attribute((format(printf, 3, 0)));
void ne_md5_buffer(const char *buffer, char *digest) ;
void ne_md5_buffer_bin(const char *buffer, char *digest) ;
END_NEON_DECLS
#endif /* NE_STRING_H */
@@ -0,0 +1,166 @@
/*
WebDAV Class 2 locking operations
Copyright (C) 1999-2002, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#ifndef NE_LOCKS_H
#define NE_LOCKS_H
#include "ne_request.h" /* for ne_session + ne_request */
#include "ne_uri.h" /* for ne_uri */
BEGIN_NEON_DECLS
/* The scope of a lock */
enum ne_lock_scope {
ne_lockscope_exclusive,
ne_lockscope_shared
};
/* Lock type. Only write locks are defined in RFC2518. */
enum ne_lock_type {
ne_locktype_write
};
/* A lock object. */
struct ne_lock {
ne_uri uri;
int depth; /* the depth of the lock (NE_DEPTH_*). */
enum ne_lock_type type;
enum ne_lock_scope scope;
char *token; /* the lock token: uniquely identifies this lock. */
char *owner; /* string describing the owner of the lock. */
long timeout; /* timeout in seconds. (or NE_TIMEOUT_*) */
};
/* NB: struct ne_lock Would be typedef'ed to ne_lock except lock is
* a verb and a noun, so we already have ne_lock the function. Damn
* the English language. */
#define NE_TIMEOUT_INFINITE -1
#define NE_TIMEOUT_INVALID -2
/* Create a depth zero, exclusive write lock, with default timeout
* (allowing a server to pick a default). token, owner and uri are
* unset. */
struct ne_lock *ne_lock_create(void);
/* HINT: to initialize uri host/port/scheme for the lock's URI, use
* ne_fill_server_uri from ne_session.h. */
/* Deep-copy a lock structure: strdup's any of path, token, owner,
* hostport which are set. */
struct ne_lock *ne_lock_copy(const struct ne_lock *lock);
/* Free a lock structure; free's any of any of the URI, token and
* owner which are set, but not the lock object itself. */
void ne_lock_free(struct ne_lock *lock);
/* Like ne_lock_free; but free's the lock object itself too. */
void ne_lock_destroy(struct ne_lock *lock);
/* ne_lock_store: an opaque type which is used to store a set of lock
* objects. */
typedef struct ne_lock_store_s ne_lock_store;
/* Create a lock store. */
ne_lock_store *ne_lockstore_create(void);
/* Register the lock store 'store' with the HTTP session 'sess': any
* operations made using 'sess' which operate on a locked resource,
* can use the locks from 'store' if needed. */
void ne_lockstore_register(ne_lock_store *store, ne_session *sess);
/* Destroy a lock store, free'ing any locks remaining inside. */
void ne_lockstore_destroy(ne_lock_store *store);
/* Add a lock to the store: the store then "owns" the lock object, and
* you must not free it. The lock MUST have all of:
* - a completed URI structure: scheme, host, port, and path all set
* - a valid lock token
* - a valid depth
*/
void ne_lockstore_add(ne_lock_store *store, struct ne_lock *lock);
/* Remove given lock object from store: 'lock' MUST point to a lock
* object which is known to be in the store. */
void ne_lockstore_remove(ne_lock_store *store, struct ne_lock *lock);
/* Returns the first lock in the lock store, or NULL if the store is
* empty. */
struct ne_lock *ne_lockstore_first(ne_lock_store *store);
/* After ne_lockstore_first has been called; returns the next lock in
* the lock store, or NULL if there are no more locks stored.
* Behaviour is undefined if ne_lockstore_first has not been called on
* 'store' since the store was created, or the last time this function
* returned NULL for the store.. */
struct ne_lock *ne_lockstore_next(ne_lock_store *store);
/* Find a lock in the store for the given server, and with the given
* path. */
struct ne_lock *ne_lockstore_findbyuri(ne_lock_store *store,
const ne_uri *uri);
/* Issue a LOCK request for the given lock. Requires that the uri,
* depth, type, scope, and timeout members of 'lock' are filled in.
* owner and token must be malloc-allocated if not NULL; and may be
* free()d by this function. On successful return, lock->token will
* contain the lock token. */
int ne_lock(ne_session *sess, struct ne_lock *lock);
/* Issue an UNLOCK request for the given lock */
int ne_unlock(ne_session *sess, const struct ne_lock *lock);
/* Refresh a lock. Updates lock->timeout appropriately. */
int ne_lock_refresh(ne_session *sess, struct ne_lock *lock);
/* Callback for lock discovery. If 'lock' is NULL, something went
* wrong performing lockdiscovery for the resource, look at 'status'
* for the details.
*
* If lock is non-NULL, at least lock->uri and lock->token will be
* filled in; and status will be NULL. */
typedef void (*ne_lock_result)(void *userdata, const struct ne_lock *lock,
const char *uri, const ne_status *status);
/* Perform lock discovery on the given path. 'result' is called with
* the results (possibly >1 times). */
int ne_lock_discover(ne_session *sess, const char *path,
ne_lock_result result, void *userdata);
/* The ne_lock_using_* functions should be used before dispatching a
* request which modify resources. If a lock store has been
* registered with the session associated with the request, and locks
* are present in the lock store which cover the resources which are
* being modified by the request, then the appropriate lock tokens are
* submitted in the request headers. */
/* Indicate that request 'req' will modify the resource at 'path', and
* is an operation of given 'depth'. */
void ne_lock_using_resource(ne_request *req, const char *path, int depth);
/* Indicate that request 'req' will modify the parent collection of
* the resource found at 'path' (for instance when removing the
* resource from the collection). */
void ne_lock_using_parent(ne_request *req, const char *path);
END_NEON_DECLS
#endif /* NE_LOCKS_H */
@@ -0,0 +1,215 @@
/*
Replacement memory allocation handling etc.
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#include <stdio.h>
#include "ne_alloc.h"
static ne_oom_callback_fn oom;
void ne_oom_callback(ne_oom_callback_fn callback)
{
oom = callback;
}
#ifndef NEON_MEMLEAK
#define DO_MALLOC(ptr, len) do { \
ptr = malloc((len)); \
if (!ptr) { \
if (oom != NULL) \
oom(); \
abort(); \
} \
} while(0);
void *ne_malloc(size_t len)
{
void *ptr;
DO_MALLOC(ptr, len);
return ptr;
}
void *ne_calloc(size_t len)
{
void *ptr;
DO_MALLOC(ptr, len);
return memset(ptr, 0, len);
}
void *ne_realloc(void *ptr, size_t len)
{
void *ret = realloc(ptr, len);
if (!ret) {
if (oom)
oom();
abort();
}
return ret;
}
char *ne_strdup(const char *s)
{
char *ret;
DO_MALLOC(ret, strlen(s) + 1);
return strcpy(ret, s);
}
char *ne_strndup(const char *s, size_t n)
{
char *new;
DO_MALLOC(new, n+1);
new[n] = '\0';
memcpy(new, s, n);
return new;
}
#else /* NEON_MEMLEAK */
#include <assert.h>
/* Memory-leak detection implementation: ne_malloc and friends are
* #defined to ne_malloc_ml etc by memleak.h, which is conditionally
* included by config.h. */
/* memory allocated be ne_*alloc, but not freed. */
size_t ne_alloc_used = 0;
static struct block {
void *ptr;
size_t len;
const char *file;
int line;
struct block *next;
} *blocks = NULL;
void ne_alloc_dump(FILE *f)
{
struct block *b;
for (b = blocks; b != NULL; b = b->next)
fprintf(f, "%" NE_FMT_SIZE_T "b@%s:%d%s", b->len, b->file, b->line,
b->next?", ":"");
}
static void *tracking_malloc(size_t len, const char *file, int line)
{
void *ptr = malloc((len));
struct block *block;
if (!ptr) {
if (oom) oom();
abort();
}
block = malloc(sizeof *block);
if (block != NULL) {
block->ptr = ptr;
block->len = len;
block->file = file;
block->line = line;
block->next = blocks;
blocks = block;
ne_alloc_used += len;
}
return ptr;
}
void *ne_malloc_ml(size_t size, const char *file, int line)
{
return tracking_malloc(size, file, line);
}
void *ne_calloc_ml(size_t size, const char *file, int line)
{
return memset(tracking_malloc(size, file, line), 0, size);
}
void *ne_realloc_ml(void *ptr, size_t s, const char *file, int line)
{
void *ret;
struct block *b;
if (ptr == NULL)
return tracking_malloc(s, file, line);
ret = realloc(ptr, s);
if (!ret) {
if (oom) oom();
abort();
}
for (b = blocks; b != NULL; b = b->next) {
if (b->ptr == ptr) {
ne_alloc_used += s - b->len;
b->ptr = ret;
b->len = s;
break;
}
}
assert(b != NULL);
return ret;
}
char *ne_strdup_ml(const char *s, const char *file, int line)
{
return strcpy(tracking_malloc(strlen(s) + 1, file, line), s);
}
char *ne_strndup_ml(const char *s, size_t n, const char *file, int line)
{
char *ret = tracking_malloc(n + 1, file, line);
ret[n] = '\0';
return memcpy(ret, s, n);
}
void ne_free_ml(void *ptr)
{
struct block *b, *last = NULL;
for (b = blocks; b != NULL; last = b, b = b->next) {
if (b->ptr == ptr) {
ne_alloc_used -= b->len;
if (last)
last->next = b->next;
else
blocks = b->next;
free(b);
break;
}
}
free(ptr);
}
#endif /* NEON_MEMLEAK */
@@ -0,0 +1,924 @@
/*
neon SSL/TLS support using OpenSSL
Copyright (C) 2002-2005, Joe Orton <joe@manyfish.co.uk>
Portions are:
Copyright (C) 1999-2000 Tommi Komulainen <Tommi.Komulainen@iki.fi>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#include <sys/types.h>
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#include <stdio.h>
#include <openssl/ssl.h>
#include <openssl/err.h>
#include <openssl/pkcs12.h>
#include <openssl/x509v3.h>
#include <openssl/rand.h>
#include "ne_ssl.h"
#include "ne_string.h"
#include "ne_session.h"
#include "ne_i18n.h"
#include "ne_private.h"
#include "ne_privssl.h"
/* OpenSSL 0.9.6 compatibility */
#if OPENSSL_VERSION_NUMBER < 0x0090700fL
#define PKCS12_unpack_authsafes M_PKCS12_unpack_authsafes
#define PKCS12_unpack_p7data M_PKCS12_unpack_p7data
/* cast away lack of const-ness */
#define OBJ_cmp(a,b) OBJ_cmp((ASN1_OBJECT *)(a), (ASN1_OBJECT *)(b))
#endif
struct ne_ssl_dname_s {
X509_NAME *dn;
};
struct ne_ssl_certificate_s {
ne_ssl_dname subj_dn, issuer_dn;
X509 *subject;
ne_ssl_certificate *issuer;
char *identity;
};
struct ne_ssl_client_cert_s {
PKCS12 *p12;
int decrypted; /* non-zero if successfully decrypted. */
ne_ssl_certificate cert;
EVP_PKEY *pkey;
char *friendly_name;
};
/* Append an ASN.1 DirectoryString STR to buffer BUF as UTF-8.
* Returns zero on success or non-zero on error. */
static int append_dirstring(ne_buffer *buf, ASN1_STRING *str)
{
unsigned char *tmp = (unsigned char *)""; /* initialize to workaround 0.9.6 bug */
int len;
switch (str->type) {
case V_ASN1_UTF8STRING:
case V_ASN1_IA5STRING: /* definitely ASCII */
case V_ASN1_VISIBLESTRING: /* probably ASCII */
case V_ASN1_PRINTABLESTRING: /* subset of ASCII */
ne_buffer_append(buf, (char *)str->data, str->length);
break;
case V_ASN1_UNIVERSALSTRING:
case V_ASN1_T61STRING: /* let OpenSSL convert it as ISO-8859-1 */
case V_ASN1_BMPSTRING:
len = ASN1_STRING_to_UTF8(&tmp, str);
if (len > 0) {
ne_buffer_append(buf, (char *)tmp, len);
OPENSSL_free(tmp);
break;
} else {
ERR_clear_error();
return -1;
}
break;
default:
NE_DEBUG(NE_DBG_SSL, "Could not convert DirectoryString type %d\n",
str->type);
return -1;
}
return 0;
}
/* Returns a malloc-allocate version of IA5 string AS. Really only
* here to prevent char * vs unsigned char * type mismatches without
* losing all hope at type-safety. */
static char *dup_ia5string(const ASN1_IA5STRING *as)
{
unsigned char *data = as->data;
return ne_strndup((char *)data, as->length);
}
char *ne_ssl_readable_dname(const ne_ssl_dname *name)
{
int n, flag = 0;
ne_buffer *dump = ne_buffer_create();
const ASN1_OBJECT * const cname = OBJ_nid2obj(NID_commonName),
* const email = OBJ_nid2obj(NID_pkcs9_emailAddress);
for (n = X509_NAME_entry_count(name->dn); n > 0; n--) {
X509_NAME_ENTRY *ent = X509_NAME_get_entry(name->dn, n-1);
/* Skip commonName or emailAddress except if there is no other
* attribute in dname. */
if ((OBJ_cmp(ent->object, cname) && OBJ_cmp(ent->object, email)) ||
(!flag && n == 1)) {
if (flag++)
ne_buffer_append(dump, ", ", 2);
if (append_dirstring(dump, ent->value))
ne_buffer_czappend(dump, "???");
}
}
return ne_buffer_finish(dump);
}
int ne_ssl_dname_cmp(const ne_ssl_dname *dn1, const ne_ssl_dname *dn2)
{
return X509_NAME_cmp(dn1->dn, dn2->dn);
}
void ne_ssl_clicert_free(ne_ssl_client_cert *cc)
{
if (cc->p12)
PKCS12_free(cc->p12);
if (cc->decrypted) {
if (cc->cert.identity) ne_free(cc->cert.identity);
EVP_PKEY_free(cc->pkey);
X509_free(cc->cert.subject);
}
if (cc->friendly_name) ne_free(cc->friendly_name);
ne_free(cc);
}
/* Map a server cert verification into a string. */
static void verify_err(ne_session *sess, int failures)
{
struct {
int bit;
const char *str;
} reasons[] = {
{ NE_SSL_NOTYETVALID, N_("certificate is not yet valid") },
{ NE_SSL_EXPIRED, N_("certificate has expired") },
{ NE_SSL_IDMISMATCH, N_("certificate issued for a different hostname") },
{ NE_SSL_UNTRUSTED, N_("issuer is not trusted") },
{ 0, NULL }
};
int n, flag = 0;
strcpy(sess->error, _("Server certificate verification failed: "));
for (n = 0; reasons[n].bit; n++) {
if (failures & reasons[n].bit) {
if (flag) strncat(sess->error, ", ", sizeof sess->error);
strncat(sess->error, _(reasons[n].str), sizeof sess->error);
flag = 1;
}
}
}
/* Format an ASN1 time to a string. 'buf' must be at least of size
* 'NE_SSL_VDATELEN'. */
static void asn1time_to_string(ASN1_TIME *tm, char *buf)
{
BIO *bio;
strncpy(buf, _("[invalid date]"), NE_SSL_VDATELEN-1);
bio = BIO_new(BIO_s_mem());
if (bio) {
if (ASN1_TIME_print(bio, tm))
BIO_read(bio, buf, NE_SSL_VDATELEN-1);
BIO_free(bio);
}
}
void ne_ssl_cert_validity(const ne_ssl_certificate *cert,
char *from, char *until)
{
ASN1_TIME *notBefore = X509_get_notBefore(cert->subject);
ASN1_TIME *notAfter = X509_get_notAfter(cert->subject);
if (from) asn1time_to_string(notBefore, from);
if (until) asn1time_to_string(notAfter, until);
}
/* Return non-zero if hostname from certificate (cn) matches hostname
* used for session (hostname). (Wildcard matching is no longer
* mandated by RFC3280, but certs are deployed which use wildcards) */
static int match_hostname(char *cn, const char *hostname)
{
const char *dot;
NE_DEBUG(NE_DBG_SSL, "Match %s on %s...\n", cn, hostname);
dot = strchr(hostname, '.');
if (dot == NULL) {
char *pnt = strchr(cn, '.');
/* hostname is not fully-qualified; unqualify the cn. */
if (pnt != NULL) {
*pnt = '\0';
}
}
else if (strncmp(cn, "*.", 2) == 0) {
hostname = dot + 1;
cn += 2;
}
return !strcasecmp(cn, hostname);
}
/* Check certificate identity. Returns zero if identity matches; 1 if
* identity does not match, or <0 if the certificate had no identity.
* If 'identity' is non-NULL, store the malloc-allocated identity in
* *identity. */
static int check_identity(const char *hostname, X509 *cert, char **identity)
{
STACK_OF(GENERAL_NAME) *names;
int match = 0, found = 0;
names = X509_get_ext_d2i(cert, NID_subject_alt_name, NULL, NULL);
if (names) {
int n;
/* subjectAltName contains a sequence of GeneralNames */
for (n = 0; n < sk_GENERAL_NAME_num(names) && !match; n++) {
GENERAL_NAME *nm = sk_GENERAL_NAME_value(names, n);
/* handle dNSName and iPAddress name extensions only. */
if (nm->type == GEN_DNS) {
char *name = dup_ia5string(nm->d.ia5);
if (identity && !found) *identity = ne_strdup(name);
match = match_hostname(name, hostname);
ne_free(name);
found = 1;
} else if (nm->type == GEN_IPADD) {
/* compare IP address with server IP address. */
ne_inet_addr *ia;
if (nm->d.ip->length == 4)
ia = ne_iaddr_make(ne_iaddr_ipv4, nm->d.ip->data);
else if (nm->d.ip->length == 16)
ia = ne_iaddr_make(ne_iaddr_ipv6, nm->d.ip->data);
else
ia = NULL;
/* ne_iaddr_make returns NULL if address type is unsupported */
if (ia != NULL) { /* address type was supported. */
char buf[128];
match = strcmp(hostname,
ne_iaddr_print(ia, buf, sizeof buf)) == 0;
found = 1;
ne_iaddr_free(ia);
} else {
NE_DEBUG(NE_DBG_SSL, "iPAddress name with unsupported "
"address type (length %d), skipped.\n",
nm->d.ip->length);
}
} /* TODO: handle uniformResourceIdentifier too */
}
/* free the whole stack. */
sk_GENERAL_NAME_pop_free(names, GENERAL_NAME_free);
}
/* Check against the commonName if no DNS alt. names were found,
* as per RFC3280. */
if (!found) {
X509_NAME *subj = X509_get_subject_name(cert);
X509_NAME_ENTRY *entry;
ne_buffer *cname = ne_buffer_ncreate(30);
int idx = -1, lastidx;
/* find the most specific commonName attribute. */
do {
lastidx = idx;
idx = X509_NAME_get_index_by_NID(subj, NID_commonName, lastidx);
} while (idx >= 0);
if (lastidx < 0) {
/* no commonNmae attributes at all. */
ne_buffer_destroy(cname);
return -1;
}
/* extract the string from the entry */
entry = X509_NAME_get_entry(subj, lastidx);
if (append_dirstring(cname, X509_NAME_ENTRY_get_data(entry))) {
ne_buffer_destroy(cname);
return -1;
}
if (identity) *identity = ne_strdup(cname->data);
match = match_hostname(cname->data, hostname);
ne_buffer_destroy(cname);
}
NE_DEBUG(NE_DBG_SSL, "Identity match for '%s': %s\n", hostname,
match ? "good" : "bad");
return match ? 0 : 1;
}
/* Populate an ne_ssl_certificate structure from an X509 object. */
static ne_ssl_certificate *populate_cert(ne_ssl_certificate *cert, X509 *x5)
{
cert->subj_dn.dn = X509_get_subject_name(x5);
cert->issuer_dn.dn = X509_get_issuer_name(x5);
cert->issuer = NULL;
cert->subject = x5;
/* Retrieve the cert identity; pass a dummy hostname to match. */
cert->identity = NULL;
check_identity("", x5, &cert->identity);
return cert;
}
/* Return a linked list of certificate objects from an OpenSSL chain. */
static ne_ssl_certificate *make_chain(STACK_OF(X509) *chain)
{
int n, count = sk_X509_num(chain);
ne_ssl_certificate *top = NULL, *current = NULL;
NE_DEBUG(NE_DBG_SSL, "Chain depth: %d\n", count);
for (n = 0; n < count; n++) {
ne_ssl_certificate *cert = ne_malloc(sizeof *cert);
populate_cert(cert, X509_dup(sk_X509_value(chain, n)));
#ifdef NE_DEBUGGING
if (ne_debug_mask & NE_DBG_SSL) {
fprintf(ne_debug_stream, "Cert #%d:\n", n);
X509_print_fp(ne_debug_stream, cert->subject);
}
#endif
if (top == NULL) {
current = top = cert;
} else {
current->issuer = cert;
current = cert;
}
}
return top;
}
/* Verifies an SSL server certificate. */
static int check_certificate(ne_session *sess, SSL *ssl, ne_ssl_certificate *chain)
{
X509 *cert = chain->subject;
ASN1_TIME *notBefore = X509_get_notBefore(cert);
ASN1_TIME *notAfter = X509_get_notAfter(cert);
int ret, failures = 0;
long result;
/* check expiry dates */
if (X509_cmp_current_time(notBefore) >= 0)
failures |= NE_SSL_NOTYETVALID;
else if (X509_cmp_current_time(notAfter) <= 0)
failures |= NE_SSL_EXPIRED;
/* Check certificate was issued to this server; pass network
* address of server if a proxy is not in use. */
ret = check_identity(sess->server.hostname, cert, NULL);
if (ret < 0) {
ne_set_error(sess, _("Server certificate was missing commonName "
"attribute in subject name"));
return NE_ERROR;
} else if (ret > 0) failures |= NE_SSL_IDMISMATCH;
/* get the result of the cert verification out of OpenSSL */
result = SSL_get_verify_result(ssl);
NE_DEBUG(NE_DBG_SSL, "Verify result: %ld = %s\n", result,
X509_verify_cert_error_string(result));
switch (result) {
case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY:
case X509_V_ERR_SELF_SIGNED_CERT_IN_CHAIN:
case X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT:
/* TODO: and probably more result codes here... */
failures |= NE_SSL_UNTRUSTED;
break;
/* ignore these, since we've already noticed them: */
case X509_V_ERR_CERT_NOT_YET_VALID:
case X509_V_ERR_CERT_HAS_EXPIRED:
/* cert was trusted: */
case X509_V_OK:
break;
default:
/* TODO: tricky to handle the 30-odd failure cases OpenSSL
* presents here (see x509_vfy.h), and present a useful API to
* the application so it in turn can then present a meaningful
* UI to the user. The only thing to do really would be to
* pass back the error string, but that's not localisable. So
* just fail the verification here - better safe than
* sorry. */
ne_set_error(sess, _("Certificate verification error: %s"),
X509_verify_cert_error_string(result));
return NE_ERROR;
}
if (failures == 0) {
/* verified OK! */
ret = NE_OK;
} else {
/* Set up the error string. */
verify_err(sess, failures);
ret = NE_ERROR;
/* Allow manual override */
if (sess->ssl_verify_fn &&
sess->ssl_verify_fn(sess->ssl_verify_ud, failures, chain) == 0)
ret = NE_OK;
}
return ret;
}
/* Duplicate a client certificate, which must be in the decrypted state. */
static ne_ssl_client_cert *dup_client_cert(const ne_ssl_client_cert *cc)
{
ne_ssl_client_cert *newcc = ne_calloc(sizeof *newcc);
newcc->decrypted = 1;
newcc->pkey = cc->pkey;
if (cc->friendly_name)
newcc->friendly_name = ne_strdup(cc->friendly_name);
populate_cert(&newcc->cert, cc->cert.subject);
cc->cert.subject->references++;
cc->pkey->references++;
return newcc;
}
/* Callback invoked when the SSL server requests a client certificate. */
static int provide_client_cert(SSL *ssl, X509 **cert, EVP_PKEY **pkey)
{
ne_session *const sess = SSL_get_app_data(ssl);
if (!sess->client_cert && sess->ssl_provide_fn) {
ne_ssl_dname **dnames = NULL;
int n, count = 0;
STACK_OF(X509_NAME) *ca_list = SSL_get_client_CA_list(ssl);
count = ca_list ? sk_X509_NAME_num(ca_list) : 0;
if (count > 0) {
dnames = ne_malloc(count * sizeof(ne_ssl_dname *));
for (n = 0; n < count; n++) {
dnames[n] = ne_malloc(sizeof(ne_ssl_dname));
dnames[n]->dn = sk_X509_NAME_value(ca_list, n);
}
}
NE_DEBUG(NE_DBG_SSL, "Calling client certificate provider...\n");
sess->ssl_provide_fn(sess->ssl_provide_ud, sess,
(const ne_ssl_dname *const *)dnames, count);
if (count) {
for (n = 0; n < count; n++)
ne_free(dnames[n]);
ne_free(dnames);
}
}
if (sess->client_cert) {
ne_ssl_client_cert *const cc = sess->client_cert;
NE_DEBUG(NE_DBG_SSL, "Supplying client certificate.\n");
cc->pkey->references++;
cc->cert.subject->references++;
*cert = cc->cert.subject;
*pkey = cc->pkey;
return 1;
} else {
NE_DEBUG(NE_DBG_SSL, "No client certificate supplied.\n");
return 0;
}
}
void ne_ssl_set_clicert(ne_session *sess, const ne_ssl_client_cert *cc)
{
sess->client_cert = dup_client_cert(cc);
}
ne_ssl_context *ne_ssl_context_create(int mode)
{
ne_ssl_context *ctx = ne_calloc(sizeof *ctx);
if (mode == NE_SSL_CTX_CLIENT) {
ctx->ctx = SSL_CTX_new(SSLv23_client_method());
ctx->sess = NULL;
/* set client cert callback. */
SSL_CTX_set_client_cert_cb(ctx->ctx, provide_client_cert);
/* enable workarounds for buggy SSL server implementations */
SSL_CTX_set_options(ctx->ctx, SSL_OP_ALL);
} else if (mode == NE_SSL_CTX_SERVER) {
ctx->ctx = SSL_CTX_new(SSLv23_server_method());
} else {
ctx->ctx = SSL_CTX_new(SSLv2_server_method());
}
return ctx;
}
int ne_ssl_context_keypair(ne_ssl_context *ctx, const char *cert,
const char *key)
{
int ret;
ret = SSL_CTX_use_PrivateKey_file(ctx->ctx, key, SSL_FILETYPE_PEM);
if (ret == 1) {
ret = SSL_CTX_use_certificate_file(ctx->ctx, cert, SSL_FILETYPE_PEM);
}
return ret == 1 ? 0 : -1;
}
int ne_ssl_context_set_verify(ne_ssl_context *ctx,
int required,
const char *ca_names,
const char *verify_cas)
{
if (required) {
SSL_CTX_set_verify(ctx->ctx, SSL_VERIFY_PEER |
SSL_VERIFY_FAIL_IF_NO_PEER_CERT, NULL);
}
if (ca_names) {
SSL_CTX_set_client_CA_list(ctx->ctx,
SSL_load_client_CA_file(ca_names));
}
if (verify_cas) {
SSL_CTX_load_verify_locations(ctx->ctx, verify_cas, NULL);
}
return 0;
}
void ne_ssl_context_destroy(ne_ssl_context *ctx)
{
SSL_CTX_free(ctx->ctx);
if (ctx->sess)
SSL_SESSION_free(ctx->sess);
ne_free(ctx);
}
/* For internal use only. */
int ne__negotiate_ssl(ne_request *req)
{
ne_session *sess = ne_get_session(req);
ne_ssl_context *ctx = sess->ssl_context;
SSL *ssl;
STACK_OF(X509) *chain;
int freechain = 0; /* non-zero if chain should be free'd. */
NE_DEBUG(NE_DBG_SSL, "Doing SSL negotiation.\n");
if (ne_sock_connect_ssl(sess->socket, ctx, sess)) {
if (ctx->sess) {
/* remove cached session. */
SSL_SESSION_free(ctx->sess);
ctx->sess = NULL;
}
ne_set_error(sess, _("SSL negotiation failed: %s"),
ne_sock_error(sess->socket));
return NE_ERROR;
}
ssl = ne__sock_sslsock(sess->socket);
chain = SSL_get_peer_cert_chain(ssl);
/* For an SSLv2 connection, the cert chain will always be NULL. */
if (chain == NULL) {
X509 *cert = SSL_get_peer_certificate(ssl);
if (cert) {
chain = sk_X509_new_null();
sk_X509_push(chain, cert);
freechain = 1;
}
}
if (chain == NULL || sk_X509_num(chain) == 0) {
ne_set_error(sess, _("SSL server did not present certificate"));
return NE_ERROR;
}
if (sess->server_cert) {
int diff = X509_cmp(sk_X509_value(chain, 0), sess->server_cert->subject);
if (freechain) sk_X509_free(chain); /* no longer need the chain */
if (diff) {
/* This could be a MITM attack: fail the request. */
ne_set_error(sess, _("Server certificate changed: "
"connection intercepted?"));
return NE_ERROR;
}
/* certificate has already passed verification: no need to
* verify it again. */
} else {
/* new connection: create the chain. */
ne_ssl_certificate *cert = make_chain(chain);
if (freechain) sk_X509_free(chain); /* no longer need the chain */
if (check_certificate(sess, ssl, cert)) {
NE_DEBUG(NE_DBG_SSL, "SSL certificate checks failed: %s\n",
sess->error);
ne_ssl_cert_free(cert);
return NE_ERROR;
}
/* remember the chain. */
sess->server_cert = cert;
}
if (ctx->sess) {
SSL_SESSION *newsess = SSL_get0_session(ssl);
/* Replace the session if it has changed. */
if (newsess != ctx->sess || SSL_SESSION_cmp(ctx->sess, newsess)) {
SSL_SESSION_free(ctx->sess);
ctx->sess = SSL_get1_session(ssl); /* bumping the refcount */
}
} else {
/* Store the session. */
ctx->sess = SSL_get1_session(ssl);
}
if (sess->notify_cb) {
sess->notify_cb(sess->notify_ud, ne_conn_secure,
SSL_get_version(ssl));
}
return NE_OK;
}
const ne_ssl_dname *ne_ssl_cert_issuer(const ne_ssl_certificate *cert)
{
return &cert->issuer_dn;
}
const ne_ssl_dname *ne_ssl_cert_subject(const ne_ssl_certificate *cert)
{
return &cert->subj_dn;
}
const ne_ssl_certificate *ne_ssl_cert_signedby(const ne_ssl_certificate *cert)
{
return cert->issuer;
}
const char *ne_ssl_cert_identity(const ne_ssl_certificate *cert)
{
return cert->identity;
}
void ne_ssl_context_trustcert(ne_ssl_context *ctx, const ne_ssl_certificate *cert)
{
X509_STORE *store = SSL_CTX_get_cert_store(ctx->ctx);
X509_STORE_add_cert(store, cert->subject);
}
void ne_ssl_trust_default_ca(ne_session *sess)
{
X509_STORE *store = SSL_CTX_get_cert_store(sess->ssl_context->ctx);
X509_STORE_set_default_paths(store);
}
/* Find a friendly name in a PKCS12 structure the hard way, without
* decrypting the parts which are encrypted.. */
static char *find_friendly_name(PKCS12 *p12)
{
STACK_OF(PKCS7) *safes = PKCS12_unpack_authsafes(p12);
int n, m;
char *name = NULL;
if (safes == NULL) return NULL;
/* Iterate over the unpacked authsafes: */
for (n = 0; n < sk_PKCS7_num(safes) && !name; n++) {
PKCS7 *safe = sk_PKCS7_value(safes, n);
STACK_OF(PKCS12_SAFEBAG) *bags;
/* Only looking for unencrypted authsafes. */
if (OBJ_obj2nid(safe->type) != NID_pkcs7_data) continue;
bags = PKCS12_unpack_p7data(safe);
if (!bags) continue;
/* Iterate through the bags, picking out a friendly name */
for (m = 0; m < sk_PKCS12_SAFEBAG_num(bags) && !name; m++) {
PKCS12_SAFEBAG *bag = sk_PKCS12_SAFEBAG_value(bags, m);
name = PKCS12_get_friendlyname(bag);
}
sk_PKCS12_SAFEBAG_pop_free(bags, PKCS12_SAFEBAG_free);
}
sk_PKCS7_pop_free(safes, PKCS7_free);
return name;
}
ne_ssl_client_cert *ne_ssl_clicert_read(const char *filename)
{
PKCS12 *p12;
FILE *fp;
X509 *cert;
EVP_PKEY *pkey;
ne_ssl_client_cert *cc;
fp = fopen(filename, "rb");
if (fp == NULL)
return NULL;
p12 = d2i_PKCS12_fp(fp, NULL);
fclose(fp);
if (p12 == NULL) {
ERR_clear_error();
return NULL;
}
/* Try parsing with no password. */
if (PKCS12_parse(p12, NULL, &pkey, &cert, NULL) == 1) {
/* Success - no password needed for decryption. */
int len = 0;
unsigned char *name = X509_alias_get0(cert, &len);
cc = ne_calloc(sizeof *cc);
cc->pkey = pkey;
cc->decrypted = 1;
if (name && len > 0)
cc->friendly_name = ne_strndup((char *)name, len);
populate_cert(&cc->cert, cert);
PKCS12_free(p12);
return cc;
} else {
/* Failed to parse the file */
int err = ERR_get_error();
ERR_clear_error();
if (ERR_GET_LIB(err) == ERR_LIB_PKCS12 &&
ERR_GET_REASON(err) == PKCS12_R_MAC_VERIFY_FAILURE) {
/* Decryption error due to bad password. */
cc = ne_calloc(sizeof *cc);
cc->friendly_name = find_friendly_name(p12);
cc->p12 = p12;
return cc;
} else {
/* Some parse error, give up. */
PKCS12_free(p12);
return NULL;
}
}
}
int ne_ssl_clicert_encrypted(const ne_ssl_client_cert *cc)
{
return !cc->decrypted;
}
int ne_ssl_clicert_decrypt(ne_ssl_client_cert *cc, const char *password)
{
X509 *cert;
EVP_PKEY *pkey;
if (PKCS12_parse(cc->p12, password, &pkey, &cert, NULL) != 1) {
ERR_clear_error();
return -1;
}
PKCS12_free(cc->p12);
populate_cert(&cc->cert, cert);
cc->pkey = pkey;
cc->decrypted = 1;
cc->p12 = NULL;
return 0;
}
const ne_ssl_certificate *ne_ssl_clicert_owner(const ne_ssl_client_cert *cc)
{
return &cc->cert;
}
const char *ne_ssl_clicert_name(const ne_ssl_client_cert *ccert)
{
return ccert->friendly_name;
}
ne_ssl_certificate *ne_ssl_cert_read(const char *filename)
{
FILE *fp = fopen(filename, "r");
X509 *cert;
if (fp == NULL)
return NULL;
cert = PEM_read_X509(fp, NULL, NULL, NULL);
fclose(fp);
if (cert == NULL) {
NE_DEBUG(NE_DBG_SSL, "d2i_X509_fp failed: %s\n",
ERR_reason_error_string(ERR_get_error()));
ERR_clear_error();
return NULL;
}
return populate_cert(ne_calloc(sizeof(struct ne_ssl_certificate_s)), cert);
}
int ne_ssl_cert_write(const ne_ssl_certificate *cert, const char *filename)
{
FILE *fp = fopen(filename, "w");
if (fp == NULL) return -1;
if (PEM_write_X509(fp, cert->subject) != 1) {
ERR_clear_error();
fclose(fp);
return -1;
}
if (fclose(fp) != 0)
return -1;
return 0;
}
void ne_ssl_cert_free(ne_ssl_certificate *cert)
{
X509_free(cert->subject);
if (cert->issuer)
ne_ssl_cert_free(cert->issuer);
if (cert->identity)
ne_free(cert->identity);
ne_free(cert);
}
int ne_ssl_cert_cmp(const ne_ssl_certificate *c1, const ne_ssl_certificate *c2)
{
return X509_cmp(c1->subject, c2->subject);
}
/* The certificate import/export format is the base64 encoding of the
* raw DER; PEM without the newlines and wrapping. */
ne_ssl_certificate *ne_ssl_cert_import(const char *data)
{
unsigned char *der, *p;
size_t len;
X509 *x5;
/* decode the base64 to get the raw DER representation */
len = ne_unbase64(data, &der);
if (len == 0) return NULL;
p = der;
x5 = d2i_X509(NULL, &p, len); /* p is incremented */
ne_free(der);
if (x5 == NULL) {
ERR_clear_error();
return NULL;
}
return populate_cert(ne_calloc(sizeof(struct ne_ssl_certificate_s)), x5);
}
char *ne_ssl_cert_export(const ne_ssl_certificate *cert)
{
int len;
unsigned char *der, *p;
char *ret;
/* find the length of the DER encoding. */
len = i2d_X509(cert->subject, NULL);
p = der = ne_malloc(len);
i2d_X509(cert->subject, &p); /* p is incremented */
ret = ne_base64(der, len);
ne_free(der);
return ret;
}
#if SHA_DIGEST_LENGTH != 20
# error SHA digest length is not 20 bytes
#endif
int ne_ssl_cert_digest(const ne_ssl_certificate *cert, char *digest)
{
unsigned char sha1[EVP_MAX_MD_SIZE];
unsigned int len, j;
char *p;
if (!X509_digest(cert->subject, EVP_sha1(), sha1, &len) || len != 20) {
ERR_clear_error();
return -1;
}
for (j = 0, p = digest; j < 20; j++) {
*p++ = NE_HEX2ASC((sha1[j] >> 4) & 0x0f);
*p++ = NE_HEX2ASC(sha1[j] & 0x0f);
*p++ = ':';
}
p[-1] = '\0';
return 0;
}
@@ -0,0 +1,73 @@
/* internal.h
Internal definitions used by Expat. This is not needed to compile
client code.
The following calling convention macros are defined for frequently
called functions:
FASTCALL - Used for those internal functions that have a simple
body and a low number of arguments and local variables.
PTRCALL - Used for functions called though function pointers.
PTRFASTCALL - Like PTRCALL, but for low number of arguments.
inline - Used for selected internal functions for which inlining
may improve performance on some platforms.
Note: Use of these macros is based on judgement, not hard rules,
and therefore subject to change.
*/
#if defined(__GNUC__) && defined(__i386__)
/* We'll use this version by default only where we know it helps.
regparm() generates warnings on Solaris boxes. See SF bug #692878.
Instability reported with egcs on a RedHat Linux 7.3.
Let's comment out:
#define FASTCALL __attribute__((stdcall, regparm(3)))
and let's try this:
*/
#define FASTCALL __attribute__((regparm(3)))
#define PTRFASTCALL __attribute__((regparm(3)))
#endif
/* Using __fastcall seems to have an unexpected negative effect under
MS VC++, especially for function pointers, so we won't use it for
now on that platform. It may be reconsidered for a future release
if it can be made more effective.
Likely reason: __fastcall on Windows is like stdcall, therefore
the compiler cannot perform stack optimizations for call clusters.
*/
/* Make sure all of these are defined if they aren't already. */
#ifndef FASTCALL
#define FASTCALL
#endif
#ifndef PTRCALL
#define PTRCALL
#endif
#ifndef PTRFASTCALL
#define PTRFASTCALL
#endif
#ifndef XML_MIN_SIZE
#if !defined(__cplusplus) && !defined(inline)
#ifdef __GNUC__
#define inline __inline
#endif /* __GNUC__ */
#endif
#endif /* XML_MIN_SIZE */
#ifdef __cplusplus
#define inline inline
#else
#ifndef inline
#define inline
#endif
#endif
@@ -0,0 +1,13 @@
#define E_ECHO 010
#define ROTORSZ 256
#define MASK 0377
typedef struct crypt_key {
char t1[ROTORSZ];
char t2[ROTORSZ];
char t3[ROTORSZ];
char deck[ROTORSZ];
char cbuf[13];
int n1, n2, nr1, nr2;
} CRYPT_KEY;
@@ -0,0 +1,67 @@
// Crypt.h
//
#include "stdafx.h"
#include "crypt.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif
char* CCrypt::m_pszKey = "SPConsole1234567890ABCDEFGHIJKLMNOPQRSTUVWXYZ";
CString CCrypt::Encrypt(CString sString)
{
USES_CONVERSION;
int nKeyLen = (int)strlen(m_pszKey);
int iPos = (int)sString.GetLength() % nKeyLen;
CString sRet;
LPCSTR pszAscii = T2CA(sString);
for (unsigned int i = 0;i < strlen(pszAscii); i++) {
CString sTemp = sRet;
sRet.Format(_T("%s%03d"), sTemp, (unsigned char)pszAscii[i] ^ m_pszKey[(i + iPos) % nKeyLen]);
}
return sRet;
}
CString CCrypt::Decrypt(CString sString)
{
USES_CONVERSION;
LPCSTR pszAscii = T2CA(sString);
int nKeyLen = (int)strlen(m_pszKey);
int iPos = ((int)strlen(pszAscii) / 3) % nKeyLen;
CString sRet;
TCHAR szTemp[2];
szTemp[1] = 0;
for (unsigned int i = 0; i < strlen(pszAscii) / 3; i++) {
int nDigit, nNumber = 0;
nDigit = pszAscii[i * 3];
if (nDigit < '0' || nDigit > '9')
return _T("");
nNumber += (nDigit - '0') * 100;
nDigit = pszAscii[i * 3 + 1];
if (nDigit < '0' || nDigit > '9')
return _T("");
nNumber += (nDigit - '0') * 10;
nDigit = pszAscii[i * 3 + 2];
if (nDigit < '0' || nDigit > '9')
return _T("");
nNumber += nDigit - '0';
szTemp[0] = nNumber ^ m_pszKey[(i + iPos) % nKeyLen];
sRet += szTemp;
}
return sRet;
}
@@ -0,0 +1,229 @@
/*
* Copyright (C) 1998,1999,2000,2001 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Library General Public License as published
* by the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _init_mcrypt nofb_LTX__init_mcrypt
#define _mcrypt_set_state nofb_LTX__mcrypt_set_state
#define _mcrypt_get_state nofb_LTX__mcrypt_get_state
#define _end_mcrypt nofb_LTX__end_mcrypt
#define _mcrypt nofb_LTX__mcrypt
#define _mdecrypt nofb_LTX__mdecrypt
#define _has_iv nofb_LTX__has_iv
#define _is_block_mode nofb_LTX__is_block_mode
#define _is_block_algorithm_mode nofb_LTX__is_block_algorithm_mode
#define _mcrypt_get_modes_name nofb_LTX__mcrypt_get_modes_name
#define _mcrypt_mode_get_size nofb_LTX__mcrypt_mode_get_size
#define _mcrypt_mode_version nofb_LTX__mcrypt_mode_version
typedef struct ncfb_buf {
byte* enc_s_register;
byte* s_register;
int s_register_pos;
int blocksize;
} nOFB_BUFFER;
/* nOFB MODE */
int _init_mcrypt( nOFB_BUFFER* buf, void *key, int lenofkey, void *IV, int size)
{
buf->enc_s_register = buf->s_register = NULL;
buf->s_register_pos = 0;
buf->blocksize = size;
/* For ofb */
buf->enc_s_register=malloc( size);
if (buf->enc_s_register==NULL) goto freeall;
buf->s_register=malloc( size);
if (buf->s_register==NULL) goto freeall;
if (IV!=NULL) {
memcpy(buf->enc_s_register, IV, size);
memcpy(buf->s_register, IV, size);
} else {
memset(buf->enc_s_register, 0, size);
memset(buf->s_register, 0, size);
}
/* End nofb */
return 0;
freeall:
free(buf->enc_s_register);
free(buf->s_register);
return -1;
}
int _mcrypt_set_state( nOFB_BUFFER* buf, byte *IV, int size)
{
buf->s_register_pos = IV[0];
memcpy(buf->enc_s_register, &IV[1], size-1);
memcpy(buf->s_register, &IV[1], size-1);
return 0;
}
int _mcrypt_get_state( nOFB_BUFFER* buf, byte *IV, int *size)
{
if (*size < buf->blocksize + 1) {
*size = buf->blocksize + 1;
return -1;
}
*size = buf->blocksize + 1;
IV[0] = buf->s_register_pos;
memcpy( &IV[1], buf->s_register, buf->blocksize);
return 0;
}
void _end_mcrypt( nOFB_BUFFER* buf) {
free(buf->s_register);
free(buf->enc_s_register);
}
//inline
static void xor_stuff( nOFB_BUFFER *buf, void* akey, void (*func)(void*,void*), byte* plain, int blocksize, int xor_size)
{
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
if (xor_size == blocksize) {
if (buf->s_register_pos == 0) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy(buf->s_register, buf->enc_s_register, blocksize);
memxor( plain, buf->enc_s_register, blocksize);
} else {
int size = blocksize - buf->s_register_pos;
memxor( plain, &buf->enc_s_register[buf->s_register_pos],
size);
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy( buf->s_register,
buf->enc_s_register, blocksize);
memxor( &plain[size], buf->enc_s_register,
buf->s_register_pos);
/* buf->s_register_pos remains the same */
}
} else { /* xor_size != blocksize */
if (buf->s_register_pos == 0) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy(buf->s_register, buf->enc_s_register, blocksize);
memxor( plain, buf->enc_s_register, xor_size);
buf->s_register_pos = xor_size;
} else {
int size = blocksize - buf->s_register_pos;
int min_size = size < xor_size ? size: xor_size;
memxor( plain, &buf->enc_s_register[buf->s_register_pos],
min_size);
buf->s_register_pos += min_size;
if (min_size >= xor_size)
return;
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy(buf->s_register, buf->enc_s_register, blocksize);
memxor( &plain[min_size], buf->s_register,
xor_size - min_size);
buf->s_register_pos = xor_size - min_size;
}
}
return;
}
int _mcrypt( nOFB_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext is n*blocksize bytes (nbit cfb) */
byte* plain;
int i, j=0;
void (*_mcrypt_block_encrypt) (void *, void *);
int modlen;
_mcrypt_block_encrypt = func;
plain = plaintext;
for (j = 0; j < len / blocksize; j++) {
xor_stuff( buf, akey, func, plain, blocksize, blocksize);
plain += blocksize;
}
modlen = len % blocksize;
if (modlen > 0) {
xor_stuff( buf, akey, func, plain, blocksize, modlen);
}
return 0;
}
int _mdecrypt( nOFB_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext is n*blocksize bytes (nbit cfb) */
return _mcrypt( buf, plaintext, len, blocksize, akey, func, func2);
}
int _has_iv() { return 1; }
int _is_block_mode() { return 0; }
int _is_block_algorithm_mode() { return 1; }
char *_mcrypt_get_modes_name() { return "nOFB";}
int _mcrypt_mode_get_size () {return sizeof(nOFB_BUFFER);}
word32 _mcrypt_mode_version() {
return 20020307;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,548 @@
/*
Microsoft SSPI based authentication routines
Copyright (C) 2004-2005, Vladimir Berezniker @ http://public.xdi.org/=vmpn
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
#include "config.h"
#include "ne_utils.h"
#include "ne_string.h"
#include "ne_sspi.h"
#ifdef HAVE_SSPI
#define SEC_SUCCESS(Status) ((Status) >= 0)
struct SSPIContextStruct {
CtxtHandle context;
char *serverName;
CredHandle credentials;
int continueNeeded;
char *mechanism;
int ntlm;
ULONG maxTokenSize;
};
typedef struct SSPIContextStruct SSPIContext;
static ULONG negotiateMaxTokenSize = 0;
static ULONG ntlmMaxTokenSize = 0;
static HINSTANCE hSecDll = NULL;
static PSecurityFunctionTable pSFT = NULL;
static int initialized = 0;
/*
* Query specified package for it's maximum token size.
*/
static int getMaxTokenSize(char *package, ULONG * maxTokenSize)
{
SECURITY_STATUS status;
SecPkgInfo *packageSecurityInfo = NULL;
status = pSFT->QuerySecurityPackageInfo(package, &packageSecurityInfo);
if (status == SEC_E_OK) {
*maxTokenSize = packageSecurityInfo->cbMaxToken;
if (pSFT->FreeContextBuffer(packageSecurityInfo) != SEC_E_OK) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Unable to free security package info.");
}
} else {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: QuerySecurityPackageInfo [failed] [%x].", status);
return -1;
}
return 0;
}
/*
* Initialize all the SSPI data
*/
static void initDll(HINSTANCE hSecDll)
{
INIT_SECURITY_INTERFACE initSecurityInterface = NULL;
initSecurityInterface =
(INIT_SECURITY_INTERFACE) GetProcAddress(hSecDll,
SECURITY_ENTRYPOINT);
if (initSecurityInterface == NULL) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Obtaining security interface [fail].\n");
initialized = -1;
return;
} else {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Obtaining security interface [ok].\n");
}
pSFT = (initSecurityInterface) ();
if (pSFT == NULL) {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Security Function Table [fail].\n");
initialized = -2;
return;
} else {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Security Function Table [ok].\n");
}
if (getMaxTokenSize("Negotiate", &negotiateMaxTokenSize)) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Unable to get negotiate maximum packet size");
initialized = -3;
}
if (getMaxTokenSize("NTLM", &ntlmMaxTokenSize)) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Unable to get negotiate maximum packet size");
initialized = -3;
}
}
/*
* This function needs to be called at least once before using any other.
*/
int ne_sspi_init(void)
{
if (initialized) {
return 0;
}
NE_DEBUG(NE_DBG_SOCKET, "sspiInit\n");
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Loading security dll.\n");
hSecDll = LoadLibrary("security.dll");
if (hSecDll == NULL) {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Loading of security dll [fail].\n");
} else {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Loading of security dll [ok].\n");
initDll(hSecDll);
if (initialized == 0) {
initialized = 1;
}
}
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: sspiInit [%d].\n", initialized);
if (initialized < 0) {
return initialized;
} else {
return 0;
}
}
/*
* This function can be called to free resources used by SSPI.
*/
int ne_sspi_deinit(void)
{
NE_DEBUG(NE_DBG_SOCKET, "sspi: DeInit\n");
if (initialized <= 0) {
return initialized;
}
pSFT = NULL;
if (hSecDll != NULL) {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Unloading security dll.\n");
if (FreeLibrary(hSecDll)) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Unloading of security dll [ok].\n");
} else {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Unloading of security dll [fail].\n");
return -1;
}
hSecDll = NULL;
}
initialized = 0;
return 0;
}
/*
* Simplification wrapper arround AcquireCredentialsHandle as most of
* the parameters do not change.
*/
static int acquireCredentialsHandle(CredHandle * credentials, char *package)
{
SECURITY_STATUS status;
TimeStamp timestamp;
status =
pSFT->AcquireCredentialsHandle(NULL, package, SECPKG_CRED_OUTBOUND,
NULL, NULL, NULL, NULL, credentials,
&timestamp);
if (status != SEC_E_OK) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: AcquireCredentialsHandle [fail] [%x].\n", status);
return -1;
}
return 0;
}
/*
* Wrapper arround initializeSecurityContext. Supplies several
* default parameters as well as logging in case of errors.
*/
static SECURITY_STATUS
initializeSecurityContext(CredHandle * credentials, CtxtHandle * context,
char *spn, ULONG contextReq,
SecBufferDesc * inBuffer, CtxtHandle * newContext,
SecBufferDesc * outBuffer)
{
ULONG contextAttributes;
SECURITY_STATUS status;
status =
pSFT->InitializeSecurityContext(credentials, context, spn, contextReq,
0, SECURITY_NETWORK_DREP, inBuffer, 0,
newContext, outBuffer,
&contextAttributes, NULL);
if (!SEC_SUCCESS(status)) {
if (status == SEC_E_INVALID_TOKEN) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"InitializeSecurityContext [fail] SEC_E_INVALID_TOKEN.\n");
} else if (status == SEC_E_UNSUPPORTED_FUNCTION) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"InitializeSecurityContext [fail] SEC_E_UNSUPPORTED_FUNCTION.\n");
} else {
NE_DEBUG(NE_DBG_HTTPAUTH,
"InitializeSecurityContext [fail] [%x].\n", status);
}
}
return status;
}
/*
* Validates that the pointer is not NULL and converts it to its real type.
*/
static int getContext(void *context, SSPIContext **sspiContext)
{
if (!context) {
return -1;
}
*sspiContext = context;
return 0;
}
/*
* Verifies that the buffer descriptor point only to one buffer and
* returns the pointer to it.
*/
static int getSingleBufferDescriptor(SecBufferDesc *secBufferDesc,
SecBuffer **secBuffer)
{
if (secBufferDesc->cBuffers != 1) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: fillBufferDescriptor "
"[fail] numbers of descriptor buffers. 1 != [%d].\n",
secBufferDesc->cBuffers);
return -1;
}
*secBuffer = secBufferDesc->pBuffers;
return 0;
}
/*
* Decodes BASE64 string into SSPI SecBuffer
*/
static int base64ToBuffer(const char *token, SecBufferDesc * secBufferDesc)
{
SecBuffer *buffer;
if (getSingleBufferDescriptor(secBufferDesc, &buffer)) {
return -1;
}
buffer->BufferType = SECBUFFER_TOKEN;
buffer->cbBuffer =
ne_unbase64(token, &((unsigned char *) buffer->pvBuffer));
if (buffer->cbBuffer == 0) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: Unable to decode BASE64 SSPI token.\n");
return -1;
}
return 0;
}
/*
* Creates a SecBuffer of a specified size.
*/
static int makeBuffer(SecBufferDesc * secBufferDesc, ULONG size)
{
SecBuffer *buffer;
if (getSingleBufferDescriptor(secBufferDesc, &buffer)) {
return -1;
}
buffer->BufferType = SECBUFFER_TOKEN;
buffer->cbBuffer = size;
buffer->pvBuffer = ne_calloc(size);
return 0;
}
/*
* Frees data allocated in the buffer.
*/
static int freeBuffer(SecBufferDesc * secBufferDesc)
{
SecBuffer *buffer;
if (getSingleBufferDescriptor(secBufferDesc, &buffer)) {
return -1;
}
if (buffer->cbBuffer > 0 && buffer->pvBuffer) {
ne_free(buffer->pvBuffer);
buffer->cbBuffer = 0;
buffer->pvBuffer = NULL;
}
return 0;
}
/*
* Returns mechanism string for the specified context.
*/
int ne_sspi_get_mechanism(void *context, char const **mechanism)
{
int status;
SSPIContext *sspiContext;
if (initialized <= 0) {
return -1;
}
status = getContext(context, &sspiContext);
if (status) {
return status;
}
*mechanism = sspiContext->mechanism;
return 0;
}
/*
* Create a context to authenticate to specified server, using either
* ntlm or negotiate.
*/
int ne_sspi_create_context(void **context, char *serverName, int ntlm)
{
SSPIContext *sspiContext;
if (initialized <= 0) {
return -1;
}
sspiContext = ne_calloc(sizeof(SSPIContext));
sspiContext->continueNeeded = 0;
if (ntlm) {
sspiContext->mechanism = "NTLM";
sspiContext->serverName = ne_strdup(serverName);
sspiContext->maxTokenSize = ntlmMaxTokenSize;
} else {
sspiContext->mechanism = "Negotiate";
sspiContext->serverName = ne_concat("HTTP/", serverName, NULL);
sspiContext->maxTokenSize = negotiateMaxTokenSize;
}
sspiContext->ntlm = ntlm;
*context = sspiContext;
return 0;
}
/*
* Resets the context
*/
static void resetContext(SSPIContext * sspiContext)
{
pSFT->DeleteSecurityContext(&(sspiContext->context));
pSFT->FreeCredentialHandle(&(sspiContext->credentials));
sspiContext->continueNeeded = 0;
}
/*
* Initializes supplied SecBufferDesc to point to supplied SecBuffer
* that is also initialized;
*/
static void
initSingleEmptyBuffer(SecBufferDesc * bufferDesc, SecBuffer * buffer)
{
buffer->BufferType = SECBUFFER_EMPTY;
buffer->cbBuffer = 0;
buffer->pvBuffer = NULL;
bufferDesc->cBuffers = 1;
bufferDesc->ulVersion = SECBUFFER_VERSION;
bufferDesc->pBuffers = buffer;
}
/*
* Destroyes the supplied context.
*/
int ne_sspi_destroy_context(void *context)
{
int status;
SSPIContext *sspiContext;
if (initialized <= 0) {
return -1;
}
status = getContext(context, &sspiContext);
if (status) {
return status;
}
resetContext(sspiContext);
if (sspiContext->serverName) {
ne_free(sspiContext->serverName);
sspiContext->serverName = NULL;
}
ne_free(sspiContext);
return 0;
}
/*
* Processes received authentication tokens as well as supplies the
* response token.
*/
int ne_sspi_authenticate(void *context, const char *base64Token, char **responseToken)
{
SecBufferDesc outBufferDesc;
SecBuffer outBuffer;
int status;
SECURITY_STATUS securityStatus;
ULONG contextFlags;
SSPIContext *sspiContext;
if (initialized <= 0) {
return -1;
}
status = getContext(context, &sspiContext);
if (status) {
return status;
}
/* TODO: Not sure what flags should be set. joe: this needs to be
* driven by the ne_auth interface; the GSSAPI code needs similar
* flags. */
contextFlags = ISC_REQ_CONFIDENTIALITY | ISC_REQ_MUTUAL_AUTH;
initSingleEmptyBuffer(&outBufferDesc, &outBuffer);
status = makeBuffer(&outBufferDesc, sspiContext->maxTokenSize);
if (status) {
return status;
}
if (base64Token) {
SecBufferDesc inBufferDesc;
SecBuffer inBuffer;
if (!sspiContext->continueNeeded) {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Got an unexpected token.\n");
return -1;
}
initSingleEmptyBuffer(&inBufferDesc, &inBuffer);
status = base64ToBuffer(base64Token, &inBufferDesc);
if (status) {
return status;
}
securityStatus =
initializeSecurityContext(&sspiContext->credentials,
&(sspiContext->context),
sspiContext->serverName, contextFlags,
&inBufferDesc, &(sspiContext->context),
&outBufferDesc);
freeBuffer(&inBufferDesc);
} else {
if (sspiContext->continueNeeded) {
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: Expected a token from server.\n");
return -1;
}
/* Reset any existing context since we are starting over */
resetContext(sspiContext);
if (acquireCredentialsHandle
(&sspiContext->credentials, sspiContext->mechanism) != SEC_E_OK) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: acquireCredentialsHandle failed.\n");
return -1;
}
securityStatus =
initializeSecurityContext(&sspiContext->credentials, NULL,
sspiContext->serverName, contextFlags,
NULL, &(sspiContext->context),
&outBufferDesc);
}
if (securityStatus == SEC_I_COMPLETE_AND_CONTINUE
|| securityStatus == SEC_I_COMPLETE_NEEDED) {
SECURITY_STATUS compleStatus =
pSFT->CompleteAuthToken(&(sspiContext->context), &outBufferDesc);
if (compleStatus != SEC_E_OK) {
freeBuffer(&outBufferDesc);
NE_DEBUG(NE_DBG_HTTPAUTH, "sspi: CompleteAuthToken failed.\n");
return -1;
}
}
if (securityStatus == SEC_I_COMPLETE_AND_CONTINUE
|| securityStatus == SEC_I_CONTINUE_NEEDED) {
sspiContext->continueNeeded = 1;
} else {
sspiContext->continueNeeded = 0;
}
if (!(securityStatus == SEC_I_COMPLETE_AND_CONTINUE
|| securityStatus == SEC_I_COMPLETE_NEEDED
|| securityStatus == SEC_I_CONTINUE_NEEDED
|| securityStatus == SEC_E_OK)) {
NE_DEBUG(NE_DBG_HTTPAUTH,
"sspi: initializeSecurityContext [failed] [%x].\n",
securityStatus);
freeBuffer(&outBufferDesc);
return -1;
}
*responseToken = ne_base64(outBufferDesc.pBuffers->pvBuffer,
outBufferDesc.pBuffers->cbBuffer);
freeBuffer(&outBufferDesc);
return 0;
}
#endif /* HAVE_SSPI */
@@ -0,0 +1,331 @@
/*
* Copyright (C) 1998,1999,2000,2001 Nikos Mavroyanopoulos
*
* This library is free software; you can redistribute it and/or modify it
* under the terms of the GNU Library General Public License as published
* by the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
#include <libdefs.h>
#include <mcrypt_modules.h>
#define _init_mcrypt ncfb_LTX__init_mcrypt
#define _mcrypt_set_state ncfb_LTX__mcrypt_set_state
#define _mcrypt_get_state ncfb_LTX__mcrypt_get_state
#define _end_mcrypt ncfb_LTX__end_mcrypt
#define _mcrypt ncfb_LTX__mcrypt
#define _mdecrypt ncfb_LTX__mdecrypt
#define _has_iv ncfb_LTX__has_iv
#define _is_block_mode ncfb_LTX__is_block_mode
#define _is_block_algorithm_mode ncfb_LTX__is_block_algorithm_mode
#define _mcrypt_get_modes_name ncfb_LTX__mcrypt_get_modes_name
#define _mcrypt_mode_get_size ncfb_LTX__mcrypt_mode_get_size
#define _mcrypt_mode_version ncfb_LTX__mcrypt_mode_version
typedef struct ncfb_buf {
byte* enc_s_register;
byte* s_register;
int s_register_pos;
int blocksize;
} nCFB_BUFFER;
/* nCFB MODE */
int _init_mcrypt( nCFB_BUFFER* buf, void *key, int lenofkey, void *IV, int size)
{
buf->enc_s_register = buf->s_register = NULL;
buf->s_register_pos = 0;
buf->blocksize = size;
/* For cfb */
buf->enc_s_register=malloc( size);
if (buf->enc_s_register==NULL) goto freeall;
buf->s_register=malloc( size);
if (buf->s_register==NULL) goto freeall;
if (IV!=NULL) {
memcpy(buf->enc_s_register, IV, size);
memcpy(buf->s_register, IV, size);
} else {
memset(buf->enc_s_register, 0, size);
memset(buf->s_register, 0, size);
}
/* End ncfb */
return 0;
freeall:
free(buf->enc_s_register);
free(buf->s_register);
return -1;
}
int _mcrypt_set_state( nCFB_BUFFER* buf, byte *IV, int size)
{
buf->s_register_pos = IV[0];
memcpy(buf->enc_s_register, &IV[1], size-1);
memcpy(buf->s_register, &IV[1], size-1);
return 0;
}
int _mcrypt_get_state( nCFB_BUFFER* buf, byte *IV, int *size)
{
if (*size < buf->blocksize + 1) {
*size = buf->blocksize + 1;
return -1;
}
*size = buf->blocksize + 1;
IV[0] = buf->s_register_pos;
memcpy( &IV[1], buf->s_register, buf->blocksize);
return 0;
}
void _end_mcrypt( nCFB_BUFFER* buf) {
free(buf->enc_s_register);
free(buf->s_register);
}
//inline
static void xor_stuff_en( nCFB_BUFFER *buf, void* akey, void (*func)(void*,void*), byte* plain, int blocksize, int xor_size)
{
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
if (xor_size == blocksize) {
if (buf->s_register_pos == 0) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memxor( plain, buf->enc_s_register, blocksize);
memcpy(buf->s_register, plain, blocksize);
} else {
int size = blocksize - buf->s_register_pos;
memxor( plain, &buf->enc_s_register[buf->s_register_pos],
size);
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memxor( &plain[size], buf->enc_s_register,
buf->s_register_pos);
memcpy( &buf->s_register[size],
plain, buf->s_register_pos);
/* buf->s_register_pos remains the same */
}
} else { /* xor_size != blocksize */
if (buf->s_register_pos == 0) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memxor( plain, buf->enc_s_register, xor_size);
memcpy(buf->s_register, plain, xor_size);
buf->s_register_pos = xor_size;
} else {
int size = blocksize - buf->s_register_pos;
int min_size = size < xor_size ? size: xor_size;
memxor( plain, &buf->enc_s_register[buf->s_register_pos],
min_size);
memcpy( &buf->s_register[buf->s_register_pos], plain, min_size);
buf->s_register_pos += min_size;
if (min_size >= xor_size)
return;
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memxor( &plain[min_size], buf->s_register,
xor_size - min_size);
buf->s_register_pos = xor_size - min_size;
memcpy(buf->s_register, plain, xor_size - min_size);
}
}
return;
}
//inline
static void xor_stuff_de( nCFB_BUFFER *buf, void* akey, void (*func)(void*,void*), byte* cipher, int blocksize, int xor_size)
{
void (*_mcrypt_block_encrypt) (void *, void *);
_mcrypt_block_encrypt = func;
if (xor_size == blocksize) {
if (buf->s_register_pos == 0) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy(buf->s_register, cipher, blocksize);
memxor( cipher, buf->enc_s_register, blocksize);
} else {
int size = blocksize - buf->s_register_pos;
memxor( cipher, &buf->enc_s_register[buf->s_register_pos],
size);
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy( &buf->s_register[size],
cipher, buf->s_register_pos);
memxor( &cipher[size], buf->enc_s_register,
buf->s_register_pos);
/* buf->s_register_pos remains the same */
}
} else { /* xor_size != blocksize */
if (buf->s_register_pos == 0) {
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy(buf->s_register, cipher, xor_size);
memxor( cipher, buf->enc_s_register, xor_size);
buf->s_register_pos = xor_size;
} else {
int size = blocksize - buf->s_register_pos;
int min_size = size < xor_size ? size: xor_size;
memxor( cipher, &buf->enc_s_register[buf->s_register_pos],
min_size);
memcpy( &buf->s_register[buf->s_register_pos], cipher, min_size);
buf->s_register_pos += min_size;
if (min_size >= xor_size)
return;
memcpy(buf->enc_s_register, buf->s_register, blocksize);
_mcrypt_block_encrypt(akey, buf->enc_s_register);
memcpy(buf->s_register, cipher, xor_size - min_size);
memxor( &cipher[min_size], buf->s_register,
xor_size - min_size);
buf->s_register_pos = xor_size - min_size;
}
}
return;
}
int _mcrypt( nCFB_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext is n*blocksize bytes (nbit cfb) */
byte* plain;
int i, j=0;
void (*_mcrypt_block_encrypt) (void *, void *);
int modlen;
_mcrypt_block_encrypt = func;
plain = plaintext;
for (j = 0; j < len / blocksize; j++) {
xor_stuff_en( buf, akey, func, plain, blocksize, blocksize);
plain += blocksize;
}
modlen = len % blocksize;
if (modlen > 0) {
xor_stuff_en( buf, akey, func, plain, blocksize, modlen);
}
return 0;
}
int _mdecrypt( nCFB_BUFFER* buf,void *plaintext, int len, int blocksize, void* akey, void (*func)(void*,void*), void (*func2)(void*,void*))
{ /* plaintext is n*blocksize bytes (nbit cfb) */
byte* plain;
int i, j=0;
void (*_mcrypt_block_encrypt) (void *, void *);
int modlen;
_mcrypt_block_encrypt = func;
plain = plaintext;
for (j = 0; j < len / blocksize; j++) {
xor_stuff_de( buf, akey, func, plain, blocksize, blocksize);
plain += blocksize;
}
modlen = len % blocksize;
if (modlen > 0) {
xor_stuff_de( buf, akey, func, plain, blocksize, modlen);
}
return 0;
}
int _has_iv() { return 1; }
int _is_block_mode() { return 0; }
int _is_block_algorithm_mode() { return 1; }
const char *_mcrypt_get_modes_name() { return "nCFB";}
int _mcrypt_mode_get_size () {return sizeof(nCFB_BUFFER);}
word32 _mcrypt_mode_version() {
return 20020307;
}
#ifdef WIN32
# ifdef USE_LTDL
WIN32DLL_DEFINE int main (void)
{
/* empty main function to avoid linker error (see cygwin FAQ) */
}
# endif
#endif
@@ -0,0 +1,120 @@
/*
HTTP Request Handling
Copyright (C) 1999-2005, Joe Orton <joe@manyfish.co.uk>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
MA 02111-1307, USA
*/
/* THIS IS NOT A PUBLIC INTERFACE. You CANNOT include this header file
* from an application. */
#ifndef NE_PRIVATE_H
#define NE_PRIVATE_H
#include "ne_request.h"
#include "ne_socket.h"
#include "ne_ssl.h"
struct host_info {
char *hostname;
unsigned int port;
ne_sock_addr *address; /* if non-NULL, result of resolving 'hostname'. */
/* current network address obtained from 'address' being used. */
const ne_inet_addr *current;
char *hostport; /* URI hostport segment */
};
/* Store every registered callback in a generic container, and cast
* the function pointer when calling it. */
struct hook {
void (*fn)(void);
void *userdata;
const char *id; /* non-NULL for accessors. */
struct hook *next;
};
#define HAVE_HOOK(st,func) (st->hook->hooks->func != NULL)
#define HOOK_FUNC(st, func) (*st->hook->hooks->func)
/* Session support. */
struct ne_session_s {
/* Connection information */
ne_socket *socket;
/* non-zero if connection has been established. */
int connected;
/* non-zero if connection has persisted beyond one request. */
int persisted;
int is_http11; /* >0 if connected server is known to be
* HTTP/1.1 compliant. */
char *scheme;
struct host_info server, proxy;
/* application-provided address list */
const ne_inet_addr **addrlist;
size_t numaddrs, curaddr;
/* Settings */
unsigned int use_proxy:1; /* do we have a proxy server? */
unsigned int no_persist:1; /* set to disable persistent connections */
unsigned int use_ssl:1; /* whether a secure connection is required */
unsigned int in_connect:1; /* doing a proxy CONNECT */
ne_progress progress_cb;
void *progress_ud;
ne_notify_status notify_cb;
void *notify_ud;
int rdtimeout; /* read timeout. */
struct hook *create_req_hooks, *pre_send_hooks, *post_send_hooks;
struct hook *destroy_req_hooks, *destroy_sess_hooks, *private;
char *user_agent; /* full User-Agent: header field */
#ifdef NE_HAVE_SSL
ne_ssl_client_cert *client_cert;
ne_ssl_certificate *server_cert;
ne_ssl_context *ssl_context;
#endif
/* Server cert verification callback: */
ne_ssl_verify_fn ssl_verify_fn;
void *ssl_verify_ud;
/* Client cert provider callback: */
ne_ssl_provide_fn ssl_provide_fn;
void *ssl_provide_ud;
/* Error string */
char error[512];
};
/* Pushes block of 'count' bytes at 'buf'. Returns non-zero on
* error. */
typedef int (*ne_push_fn)(void *userdata, const char *buf, size_t count);
/* Do the SSL negotiation. */
int ne__negotiate_ssl(ne_request *req);
/* Hack to fix ne_compress layer problems */
void ne__reqhook_pre_send(ne_request *sess, ne_pre_send_fn fn, void *userdata);
#endif /* HTTP_PRIVATE_H */

Some files were not shown because too many files have changed in this diff Show More