From: Jo-Philipp Wich Date: Mon, 27 Apr 2009 01:47:03 +0000 (+0000) Subject: lua: embed md5lib X-Git-Url: http://git.lede-project.org./?a=commitdiff_plain;h=41fe3124642be714017af98a21477738eff82d37;p=openwrt%2Fstaging%2Fjow.git lua: embed md5lib SVN-Revision: 15431 --- diff --git a/package/lua/patches/420-md5lib-embedded.patch b/package/lua/patches/420-md5lib-embedded.patch new file mode 100644 index 0000000000..bac8e5d770 --- /dev/null +++ b/package/lua/patches/420-md5lib-embedded.patch @@ -0,0 +1,484 @@ +diff -Nur lua-5.1.4.orig/src/Makefile lua-5.1.4/src/Makefile +--- lua-5.1.4.orig/src/Makefile 2009-04-27 00:36:06.000000000 +0200 ++++ lua-5.1.4/src/Makefile 2009-04-27 00:47:54.000000000 +0200 +@@ -29,7 +29,7 @@ + lobject.o lopcodes.o lparser.o lstate.o lstring.o ltable.o ltm.o \ + lundump.o lvm.o lzio.o lnum.o + LIB_O= lauxlib.o lbaselib.o ldblib.o liolib.o lmathlib.o loslib.o ltablib.o \ +- lstrlib.o loadlib.o linit.o lposix.o lbitlib.o ++ lstrlib.o loadlib.o linit.o lposix.o lbitlib.o md5.o md5lib.o + + LUA_T= lua + LUA_O= lua.o +diff -Nur lua-5.1.4.orig/src/linit.c lua-5.1.4/src/linit.c +--- lua-5.1.4.orig/src/linit.c 2009-04-27 00:36:06.000000000 +0200 ++++ lua-5.1.4/src/linit.c 2009-04-27 00:44:54.000000000 +0200 +@@ -25,6 +25,7 @@ + {LUA_DBLIBNAME, luaopen_debug}, + {LUA_POSIXLIBNAME, luaopen_posix}, + {LUA_BITLIBNAME, luaopen_bit}, ++ {LUA_MD5LIBNAME, luaopen_md5_core}, + {NULL, NULL} + }; + +diff -Nur lua-5.1.4.orig/src/lualib.h lua-5.1.4/src/lualib.h +--- lua-5.1.4.orig/src/lualib.h 2009-04-27 00:36:06.000000000 +0200 ++++ lua-5.1.4/src/lualib.h 2009-04-27 00:46:01.000000000 +0200 +@@ -45,6 +45,8 @@ + #define LUA_BITLIBNAME "bit" + LUALIB_API int (luaopen_bit) (lua_State *L); + ++#define LUA_MD5LIBNAME "md5" ++LUALIB_API int (luaopen_md5_core) (lua_State *L); + + /* open all previous libraries */ + LUALIB_API void (luaL_openlibs) (lua_State *L); +diff -Nur lua-5.1.4.orig/src/md5.c lua-5.1.4/src/md5.c +--- lua-5.1.4.orig/src/md5.c 1970-01-01 01:00:00.000000000 +0100 ++++ lua-5.1.4/src/md5.c 2008-03-24 21:59:12.000000000 +0100 +@@ -0,0 +1,214 @@ ++/** ++* $Id: md5.c,v 1.2 2008/03/24 20:59:12 mascarenhas Exp $ ++* Hash function MD5 ++* @author Marcela Ozorio Suarez, Roberto I. ++*/ ++ ++ ++#include ++ ++#include "md5.h" ++ ++ ++#define WORD 32 ++#define MASK 0xFFFFFFFF ++#if __STDC_VERSION__ >= 199901L ++#include ++typedef uint32_t WORD32; ++#else ++typedef unsigned int WORD32; ++#endif ++ ++ ++/** ++* md5 hash function. ++* @param message: aribtary string. ++* @param len: message length. ++* @param output: buffer to receive the hash value. Its size must be ++* (at least) HASHSIZE. ++*/ ++void md5 (const char *message, long len, char *output); ++ ++ ++ ++/* ++** Realiza a rotacao no sentido horario dos bits da variavel 'D' do tipo WORD32. ++** Os bits sao deslocados de 'num' posicoes ++*/ ++#define rotate(D, num) (D<>(WORD-num)) ++ ++/*Macros que definem operacoes relizadas pelo algoritmo md5 */ ++#define F(x, y, z) (((x) & (y)) | ((~(x)) & (z))) ++#define G(x, y, z) (((x) & (z)) | ((y) & (~(z)))) ++#define H(x, y, z) ((x) ^ (y) ^ (z)) ++#define I(x, y, z) ((y) ^ ((x) | (~(z)))) ++ ++ ++/*vetor de numeros utilizados pelo algoritmo md5 para embaralhar bits */ ++static const WORD32 T[64]={ ++ 0xd76aa478, 0xe8c7b756, 0x242070db, 0xc1bdceee, ++ 0xf57c0faf, 0x4787c62a, 0xa8304613, 0xfd469501, ++ 0x698098d8, 0x8b44f7af, 0xffff5bb1, 0x895cd7be, ++ 0x6b901122, 0xfd987193, 0xa679438e, 0x49b40821, ++ 0xf61e2562, 0xc040b340, 0x265e5a51, 0xe9b6c7aa, ++ 0xd62f105d, 0x02441453, 0xd8a1e681, 0xe7d3fbc8, ++ 0x21e1cde6, 0xc33707d6, 0xf4d50d87, 0x455a14ed, ++ 0xa9e3e905, 0xfcefa3f8, 0x676f02d9, 0x8d2a4c8a, ++ 0xfffa3942, 0x8771f681, 0x6d9d6122, 0xfde5380c, ++ 0xa4beea44, 0x4bdecfa9, 0xf6bb4b60, 0xbebfbc70, ++ 0x289b7ec6, 0xeaa127fa, 0xd4ef3085, 0x04881d05, ++ 0xd9d4d039, 0xe6db99e5, 0x1fa27cf8, 0xc4ac5665, ++ 0xf4292244, 0x432aff97, 0xab9423a7, 0xfc93a039, ++ 0x655b59c3, 0x8f0ccc92, 0xffeff47d, 0x85845dd1, ++ 0x6fa87e4f, 0xfe2ce6e0, 0xa3014314, 0x4e0811a1, ++ 0xf7537e82, 0xbd3af235, 0x2ad7d2bb, 0xeb86d391 ++}; ++ ++ ++static void word32tobytes (const WORD32 *input, char *output) { ++ int j = 0; ++ while (j<4*4) { ++ WORD32 v = *input++; ++ output[j++] = (char)(v & 0xff); v >>= 8; ++ output[j++] = (char)(v & 0xff); v >>= 8; ++ output[j++] = (char)(v & 0xff); v >>= 8; ++ output[j++] = (char)(v & 0xff); ++ } ++} ++ ++ ++static void inic_digest(WORD32 *d) { ++ d[0] = 0x67452301; ++ d[1] = 0xEFCDAB89; ++ d[2] = 0x98BADCFE; ++ d[3] = 0x10325476; ++} ++ ++ ++/*funcao que implemeta os quatro passos principais do algoritmo MD5 */ ++static void digest(const WORD32 *m, WORD32 *d) { ++ int j; ++ /*MD5 PASSO1 */ ++ for (j=0; j<4*4; j+=4) { ++ d[0] = d[0]+ F(d[1], d[2], d[3])+ m[j] + T[j]; d[0]=rotate(d[0], 7); ++ d[0]+=d[1]; ++ d[3] = d[3]+ F(d[0], d[1], d[2])+ m[(j)+1] + T[j+1]; d[3]=rotate(d[3], 12); ++ d[3]+=d[0]; ++ d[2] = d[2]+ F(d[3], d[0], d[1])+ m[(j)+2] + T[j+2]; d[2]=rotate(d[2], 17); ++ d[2]+=d[3]; ++ d[1] = d[1]+ F(d[2], d[3], d[0])+ m[(j)+3] + T[j+3]; d[1]=rotate(d[1], 22); ++ d[1]+=d[2]; ++ } ++ /*MD5 PASSO2 */ ++ for (j=0; j<4*4; j+=4) { ++ d[0] = d[0]+ G(d[1], d[2], d[3])+ m[(5*j+1)&0x0f] + T[(j-1)+17]; ++ d[0] = rotate(d[0],5); ++ d[0]+=d[1]; ++ d[3] = d[3]+ G(d[0], d[1], d[2])+ m[((5*(j+1)+1)&0x0f)] + T[(j+0)+17]; ++ d[3] = rotate(d[3], 9); ++ d[3]+=d[0]; ++ d[2] = d[2]+ G(d[3], d[0], d[1])+ m[((5*(j+2)+1)&0x0f)] + T[(j+1)+17]; ++ d[2] = rotate(d[2], 14); ++ d[2]+=d[3]; ++ d[1] = d[1]+ G(d[2], d[3], d[0])+ m[((5*(j+3)+1)&0x0f)] + T[(j+2)+17]; ++ d[1] = rotate(d[1], 20); ++ d[1]+=d[2]; ++ } ++ /*MD5 PASSO3 */ ++ for (j=0; j<4*4; j+=4) { ++ d[0] = d[0]+ H(d[1], d[2], d[3])+ m[(3*j+5)&0x0f] + T[(j-1)+33]; ++ d[0] = rotate(d[0], 4); ++ d[0]+=d[1]; ++ d[3] = d[3]+ H(d[0], d[1], d[2])+ m[(3*(j+1)+5)&0x0f] + T[(j+0)+33]; ++ d[3] = rotate(d[3], 11); ++ d[3]+=d[0]; ++ d[2] = d[2]+ H(d[3], d[0], d[1])+ m[(3*(j+2)+5)&0x0f] + T[(j+1)+33]; ++ d[2] = rotate(d[2], 16); ++ d[2]+=d[3]; ++ d[1] = d[1]+ H(d[2], d[3], d[0])+ m[(3*(j+3)+5)&0x0f] + T[(j+2)+33]; ++ d[1] = rotate(d[1], 23); ++ d[1]+=d[2]; ++ } ++ /*MD5 PASSO4 */ ++ for (j=0; j<4*4; j+=4) { ++ d[0] = d[0]+ I(d[1], d[2], d[3])+ m[(7*j)&0x0f] + T[(j-1)+49]; ++ d[0] = rotate(d[0], 6); ++ d[0]+=d[1]; ++ d[3] = d[3]+ I(d[0], d[1], d[2])+ m[(7*(j+1))&0x0f] + T[(j+0)+49]; ++ d[3] = rotate(d[3], 10); ++ d[3]+=d[0]; ++ d[2] = d[2]+ I(d[3], d[0], d[1])+ m[(7*(j+2))&0x0f] + T[(j+1)+49]; ++ d[2] = rotate(d[2], 15); ++ d[2]+=d[3]; ++ d[1] = d[1]+ I(d[2], d[3], d[0])+ m[(7*(j+3))&0x0f] + T[(j+2)+49]; ++ d[1] = rotate(d[1], 21); ++ d[1]+=d[2]; ++ } ++} ++ ++ ++static void bytestoword32 (WORD32 *x, const char *pt) { ++ int i; ++ for (i=0; i<16; i++) { ++ int j=i*4; ++ x[i] = (((WORD32)(unsigned char)pt[j+3] << 8 | ++ (WORD32)(unsigned char)pt[j+2]) << 8 | ++ (WORD32)(unsigned char)pt[j+1]) << 8 | ++ (WORD32)(unsigned char)pt[j]; ++ } ++ ++} ++ ++ ++static void put_length(WORD32 *x, long len) { ++ /* in bits! */ ++ x[14] = (WORD32)((len<<3) & MASK); ++ x[15] = (WORD32)(len>>(32-3) & 0x7); ++} ++ ++ ++/* ++** returned status: ++* 0 - normal message (full 64 bytes) ++* 1 - enough room for 0x80, but not for message length (two 4-byte words) ++* 2 - enough room for 0x80 plus message length (at least 9 bytes free) ++*/ ++static int converte (WORD32 *x, const char *pt, int num, int old_status) { ++ int new_status = 0; ++ char buff[64]; ++ if (num<64) { ++ memcpy(buff, pt, num); /* to avoid changing original string */ ++ memset(buff+num, 0, 64-num); ++ if (old_status == 0) ++ buff[num] = '\200'; ++ new_status = 1; ++ pt = buff; ++ } ++ bytestoword32(x, pt); ++ if (num <= (64 - 9)) ++ new_status = 2; ++ return new_status; ++} ++ ++ ++ ++void md5 (const char *message, long len, char *output) { ++ WORD32 d[4]; ++ int status = 0; ++ long i = 0; ++ inic_digest(d); ++ while (status != 2) { ++ WORD32 d_old[4]; ++ WORD32 wbuff[16]; ++ int numbytes = (len-i >= 64) ? 64 : len-i; ++ /*salva os valores do vetor digest*/ ++ d_old[0]=d[0]; d_old[1]=d[1]; d_old[2]=d[2]; d_old[3]=d[3]; ++ status = converte(wbuff, message+i, numbytes, status); ++ if (status == 2) put_length(wbuff, len); ++ digest(wbuff, d); ++ d[0]+=d_old[0]; d[1]+=d_old[1]; d[2]+=d_old[2]; d[3]+=d_old[3]; ++ i += numbytes; ++ } ++ word32tobytes(d, output); ++} ++ +diff -Nur lua-5.1.4.orig/src/md5.h lua-5.1.4/src/md5.h +--- lua-5.1.4.orig/src/md5.h 1970-01-01 01:00:00.000000000 +0100 ++++ lua-5.1.4/src/md5.h 2009-04-27 00:49:13.000000000 +0200 +@@ -0,0 +1,20 @@ ++/** ++* $Id: md5.h,v 1.2 2006/03/03 15:04:49 tomas Exp $ ++* Cryptographic module for Lua. ++* @author Roberto Ierusalimschy ++*/ ++ ++ ++#ifndef md5_h ++#define md5_h ++ ++#include "lua.h" ++ ++ ++#define HASHSIZE 16 ++ ++void md5 (const char *message, long len, char *output); ++int luaopen_md5_core (lua_State *L); ++ ++ ++#endif +diff -Nur lua-5.1.4.orig/src/md5lib.c lua-5.1.4/src/md5lib.c +--- lua-5.1.4.orig/src/md5lib.c 1970-01-01 01:00:00.000000000 +0100 ++++ lua-5.1.4/src/md5lib.c 2009-04-27 00:49:55.000000000 +0200 +@@ -0,0 +1,203 @@ ++/** ++* $Id: md5lib.c,v 1.10 2008/05/12 20:51:27 carregal Exp $ ++* Cryptographic and Hash functions for Lua ++* @author Roberto Ierusalimschy ++*/ ++ ++ ++#include ++#include ++#include ++ ++#include "lua.h" ++#include "lauxlib.h" ++ ++#if ! defined (LUA_VERSION_NUM) || LUA_VERSION_NUM < 501 ++#include "compat-5.1.h" ++#endif ++ ++#include "md5.h" ++ ++ ++/** ++* Hash function. Returns a hash for a given string. ++* @param message: arbitrary binary string. ++* @return A 128-bit hash string. ++*/ ++static int lmd5 (lua_State *L) { ++ char buff[16]; ++ size_t l; ++ const char *message = luaL_checklstring(L, 1, &l); ++ md5(message, l, buff); ++ lua_pushlstring(L, buff, 16L); ++ return 1; ++} ++ ++ ++/** ++* X-Or. Does a bit-a-bit exclusive-or of two strings. ++* @param s1: arbitrary binary string. ++* @param s2: arbitrary binary string with same length as s1. ++* @return a binary string with same length as s1 and s2, ++* where each bit is the exclusive-or of the corresponding bits in s1-s2. ++*/ ++static int ex_or (lua_State *L) { ++ size_t l1, l2; ++ const char *s1 = luaL_checklstring(L, 1, &l1); ++ const char *s2 = luaL_checklstring(L, 2, &l2); ++ luaL_Buffer b; ++ luaL_argcheck( L, l1 == l2, 2, "lengths must be equal" ); ++ luaL_buffinit(L, &b); ++ while (l1--) luaL_putchar(&b, (*s1++)^(*s2++)); ++ luaL_pushresult(&b); ++ return 1; ++} ++ ++ ++static void checkseed (lua_State *L) { ++ if (lua_isnone(L, 3)) { /* no seed? */ ++ time_t tm = time(NULL); /* for `random' seed */ ++ lua_pushlstring(L, (char *)&tm, sizeof(tm)); ++ } ++} ++ ++ ++#define MAXKEY 256 ++#define BLOCKSIZE 16 ++ ++ ++ ++static int initblock (lua_State *L, const char *seed, int lseed, char *block) { ++ size_t lkey; ++ const char *key = luaL_checklstring(L, 2, &lkey); ++ if (lkey > MAXKEY) ++ luaL_error(L, "key too long (> %d)", MAXKEY); ++ memset(block, 0, BLOCKSIZE); ++ memcpy(block, seed, lseed); ++ memcpy(block+BLOCKSIZE, key, lkey); ++ return (int)lkey+BLOCKSIZE; ++} ++ ++ ++static void codestream (lua_State *L, const char *msg, size_t lmsg, ++ char *block, int lblock) { ++ luaL_Buffer b; ++ luaL_buffinit(L, &b); ++ while (lmsg > 0) { ++ char code[BLOCKSIZE]; ++ int i; ++ md5(block, lblock, code); ++ for (i=0; i 0; i++, lmsg--) ++ code[i] ^= *msg++; ++ luaL_addlstring(&b, code, i); ++ memcpy(block, code, i); /* update seed */ ++ } ++ luaL_pushresult(&b); ++} ++ ++ ++static void decodestream (lua_State *L, const char *cypher, size_t lcypher, ++ char *block, int lblock) { ++ luaL_Buffer b; ++ luaL_buffinit(L, &b); ++ while (lcypher > 0) { ++ char code[BLOCKSIZE]; ++ int i; ++ md5(block, lblock, code); /* update seed */ ++ for (i=0; i 0; i++, lcypher--) ++ code[i] ^= *cypher++; ++ luaL_addlstring(&b, code, i); ++ memcpy(block, cypher-i, i); ++ } ++ luaL_pushresult(&b); ++} ++ ++ ++/** ++* Encrypts a string. Uses the hash function md5 in CFB (Cipher-feedback ++* mode). ++* @param message: arbitrary binary string to be encrypted. ++* @param key: arbitrary binary string to be used as a key. ++* @param [seed]: optional arbitrary binary string to be used as a seed. ++* if no seed is provided, the function uses the result of ++* time() as a seed. ++* @return The cyphertext (as a binary string). ++*/ ++static int crypt (lua_State *L) { ++ size_t lmsg; ++ const char *msg = luaL_checklstring(L, 1, &lmsg); ++ size_t lseed; ++ const char *seed; ++ int lblock; ++ char block[BLOCKSIZE+MAXKEY]; ++ checkseed(L); ++ seed = luaL_checklstring(L, 3, &lseed); ++ if (lseed > BLOCKSIZE) ++ luaL_error(L, "seed too long (> %d)", BLOCKSIZE); ++ /* put seed and seed length at the beginning of result */ ++ block[0] = (char)lseed; ++ memcpy(block+1, seed, lseed); ++ lua_pushlstring(L, block, lseed+1); /* to concat with result */ ++ lblock = initblock(L, seed, lseed, block); ++ codestream(L, msg, lmsg, block, lblock); ++ lua_concat(L, 2); ++ return 1; ++} ++ ++ ++/** ++* Decrypts a string. For any message, key, and seed, we have that ++* decrypt(crypt(msg, key, seed), key) == msg. ++* @param cyphertext: message to be decrypted (this must be the result of ++ a previous call to crypt. ++* @param key: arbitrary binary string to be used as a key. ++* @return The plaintext. ++*/ ++static int decrypt (lua_State *L) { ++ size_t lcyphertext; ++ const char *cyphertext = luaL_checklstring(L, 1, &lcyphertext); ++ size_t lseed = cyphertext[0]; ++ const char *seed = cyphertext+1; ++ int lblock; ++ char block[BLOCKSIZE+MAXKEY]; ++ luaL_argcheck(L, lcyphertext >= lseed+1 && lseed <= BLOCKSIZE, 1, ++ "invalid cyphered string"); ++ cyphertext += lseed+1; ++ lcyphertext -= lseed+1; ++ lblock = initblock(L, seed, lseed, block); ++ decodestream(L, cyphertext, lcyphertext, block, lblock); ++ return 1; ++} ++ ++ ++/* ++** Assumes the table is on top of the stack. ++*/ ++static void set_info (lua_State *L) { ++ lua_pushliteral (L, "_COPYRIGHT"); ++ lua_pushliteral (L, "Copyright (C) 2003 PUC-Rio"); ++ lua_settable (L, -3); ++ lua_pushliteral (L, "_DESCRIPTION"); ++ lua_pushliteral (L, "Basic cryptographic facilities"); ++ lua_settable (L, -3); ++ lua_pushliteral (L, "_VERSION"); ++ lua_pushliteral (L, "MD5 1.1.2"); ++ lua_settable (L, -3); ++} ++ ++ ++static struct luaL_reg md5lib[] = { ++ {"sum", lmd5}, ++ {"exor", ex_or}, ++ {"crypt", crypt}, ++ {"decrypt", decrypt}, ++ {NULL, NULL} ++}; ++ ++ ++int luaopen_md5_core (lua_State *L) { ++ luaL_register(L, "md5", md5lib); ++ set_info (L); ++ return 1; ++} ++