base
This commit is contained in:
@@ -0,0 +1 @@
|
||||
12
|
||||
@@ -0,0 +1 @@
|
||||
12
|
||||
+36
@@ -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,
|
||||
+24
@@ -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;
|
||||
|
||||
+4
@@ -0,0 +1,4 @@
|
||||
typedef struct {
|
||||
word32 l_key[140];
|
||||
} SERPENT_KEY;
|
||||
|
||||
+445
@@ -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 */
|
||||
+439
@@ -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;
|
||||
}
|
||||
+240
@@ -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
|
||||
+17
@@ -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_)
|
||||
BIN
Binary file not shown.
+66
@@ -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)
|
||||
+658
@@ -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;
|
||||
}
|
||||
+62
@@ -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 */
|
||||
+92
@@ -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 */
|
||||
+13
@@ -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
|
||||
+100
@@ -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 */
|
||||
+248
@@ -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;
|
||||
}
|
||||
+4
@@ -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);
|
||||
+217
@@ -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_)
|
||||
+687
@@ -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
|
||||
+378
@@ -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
|
||||
+450
@@ -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;
|
||||
}
|
||||
+46
@@ -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>
|
||||
+87
@@ -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;
|
||||
}
|
||||
+336
@@ -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;
|
||||
}
|
||||
+32
@@ -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;
|
||||
}
|
||||
+114
@@ -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 */
|
||||
+117
@@ -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 */
|
||||
+400
@@ -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
|
||||
+108
@@ -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 */
|
||||
|
||||
+12
@@ -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
|
||||
+174
@@ -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
|
||||
+53
@@ -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
|
||||
+106
@@ -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);
|
||||
}
|
||||
+270
@@ -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
|
||||
}
|
||||
+1020
File diff suppressed because it is too large
Load Diff
+1328
File diff suppressed because it is too large
Load Diff
+10
@@ -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;
|
||||
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
/* for blowfish */
|
||||
typedef struct {
|
||||
word32 S[4][256],P[18];
|
||||
} blf_ctx;
|
||||
|
||||
+673
@@ -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
|
||||
+151
@@ -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 */
|
||||
+21
@@ -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(...)
|
||||
{
|
||||
}
|
||||
}
|
||||
+727
@@ -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;
|
||||
}
|
||||
|
||||
|
||||
+176
@@ -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
|
||||
+316
@@ -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 */
|
||||
+37
@@ -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 */
|
||||
+56
@@ -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 */
|
||||
BIN
Binary file not shown.
+19
@@ -0,0 +1,19 @@
|
||||
// 컴퓨터에서 Microsoft Visual C++를 사용하여 생성한 IDispatch 래퍼 클래스입니다.
|
||||
|
||||
// 참고: 이 파일의 내용을 수정하지 마십시오. Microsoft Visual C++에서
|
||||
// 이 클래스를 다시 생성할 때 수정한 내용을 덮어씁니다.
|
||||
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ptxshtree.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CPTxShTree
|
||||
|
||||
IMPLEMENT_DYNCREATE(CPTxShTree, CTreeCtrl)
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CPTxShTree 속성입니다.
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// CPTxShTree 작업입니다.
|
||||
+47
@@ -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)
|
||||
+285
@@ -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;
|
||||
}
|
||||
+351
@@ -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
|
||||
BIN
Binary file not shown.
+89
@@ -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);
|
||||
+27
@@ -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 */
|
||||
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
typedef struct arcfour_key
|
||||
{
|
||||
byte state[256];
|
||||
byte i;
|
||||
byte j;
|
||||
} arcfour_key;
|
||||
|
||||
+167
@@ -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
|
||||
+305
@@ -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_)
|
||||
+12
@@ -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
|
||||
+414
@@ -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;
|
||||
}
|
||||
+450
@@ -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);
|
||||
}
|
||||
+32
@@ -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
|
||||
}
|
||||
+700
@@ -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
|
||||
+1
@@ -0,0 +1 @@
|
||||
void Bzero( void *s, size_t n);
|
||||
+9
@@ -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;
|
||||
|
||||
+12
@@ -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
|
||||
+323
@@ -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
|
||||
+250
@@ -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
|
||||
+545
@@ -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
|
||||
};
|
||||
|
||||
+21
@@ -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);
|
||||
};
|
||||
+54
@@ -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 */
|
||||
+53
@@ -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;
|
||||
};
|
||||
+51
@@ -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()
|
||||
};
|
||||
+63
@@ -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 */
|
||||
+1622
File diff suppressed because it is too large
Load Diff
+7
@@ -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;
|
||||
|
||||
+397
@@ -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
|
||||
+484
@@ -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
|
||||
+118
@@ -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;
|
||||
}
|
||||
+505
@@ -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
|
||||
BIN
Binary file not shown.
BIN
Binary file not shown.
+423
@@ -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
|
||||
+100
@@ -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;
|
||||
}
|
||||
+2323
File diff suppressed because it is too large
Load Diff
+245
@@ -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 */
|
||||
+831
@@ -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;
|
||||
}
|
||||
+41
@@ -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 */
|
||||
+142
@@ -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 */
|
||||
+166
@@ -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 */
|
||||
+215
@@ -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 */
|
||||
+924
@@ -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;
|
||||
}
|
||||
+73
@@ -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
|
||||
+13
@@ -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;
|
||||
|
||||
+67
@@ -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;
|
||||
}
|
||||
+1637
File diff suppressed because it is too large
Load Diff
+229
@@ -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
|
||||
+548
@@ -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,
|
||||
×tamp);
|
||||
|
||||
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 */
|
||||
+331
@@ -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
|
||||
+120
@@ -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
Reference in New Issue
Block a user