| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| #include "sqlite3ext.h" |
| SQLITE_EXTENSION_INIT1 |
| #include <assert.h> |
| #include <string.h> |
| #include <stdarg.h> |
|
|
| #ifndef SQLITE_AMALGAMATION |
| typedef sqlite3_uint64 u64; |
| #endif |
|
|
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| #ifndef SHA3_BYTEORDER |
| # if defined(i386) || defined(__i386__) || defined(_M_IX86) || \ |
| defined(__x86_64) || defined(__x86_64__) || defined(_M_X64) || \ |
| defined(_M_AMD64) || defined(_M_ARM) || defined(__x86) || \ |
| defined(__arm__) |
| # define SHA3_BYTEORDER 1234 |
| # elif defined(sparc) || defined(__ppc__) |
| # define SHA3_BYTEORDER 4321 |
| # else |
| # define SHA3_BYTEORDER 0 |
| # endif |
| #endif |
|
|
|
|
| |
| |
| |
| typedef struct SHA3Context SHA3Context; |
| struct SHA3Context { |
| union { |
| u64 s[25]; |
| unsigned char x[1600]; |
| } u; |
| unsigned nRate; |
| unsigned nLoaded; |
| unsigned ixMask; |
| unsigned iSize; |
| }; |
|
|
| |
| |
| |
| static void KeccakF1600Step(SHA3Context *p){ |
| int i; |
| u64 b0, b1, b2, b3, b4; |
| u64 c0, c1, c2, c3, c4; |
| u64 d0, d1, d2, d3, d4; |
| static const u64 RC[] = { |
| 0x0000000000000001ULL, 0x0000000000008082ULL, |
| 0x800000000000808aULL, 0x8000000080008000ULL, |
| 0x000000000000808bULL, 0x0000000080000001ULL, |
| 0x8000000080008081ULL, 0x8000000000008009ULL, |
| 0x000000000000008aULL, 0x0000000000000088ULL, |
| 0x0000000080008009ULL, 0x000000008000000aULL, |
| 0x000000008000808bULL, 0x800000000000008bULL, |
| 0x8000000000008089ULL, 0x8000000000008003ULL, |
| 0x8000000000008002ULL, 0x8000000000000080ULL, |
| 0x000000000000800aULL, 0x800000008000000aULL, |
| 0x8000000080008081ULL, 0x8000000000008080ULL, |
| 0x0000000080000001ULL, 0x8000000080008008ULL |
| }; |
| # define a00 (p->u.s[0]) |
| # define a01 (p->u.s[1]) |
| # define a02 (p->u.s[2]) |
| # define a03 (p->u.s[3]) |
| # define a04 (p->u.s[4]) |
| # define a10 (p->u.s[5]) |
| # define a11 (p->u.s[6]) |
| # define a12 (p->u.s[7]) |
| # define a13 (p->u.s[8]) |
| # define a14 (p->u.s[9]) |
| # define a20 (p->u.s[10]) |
| # define a21 (p->u.s[11]) |
| # define a22 (p->u.s[12]) |
| # define a23 (p->u.s[13]) |
| # define a24 (p->u.s[14]) |
| # define a30 (p->u.s[15]) |
| # define a31 (p->u.s[16]) |
| # define a32 (p->u.s[17]) |
| # define a33 (p->u.s[18]) |
| # define a34 (p->u.s[19]) |
| # define a40 (p->u.s[20]) |
| # define a41 (p->u.s[21]) |
| # define a42 (p->u.s[22]) |
| # define a43 (p->u.s[23]) |
| # define a44 (p->u.s[24]) |
| # define ROL64(a,x) ((a<<x)|(a>>(64-x))) |
|
|
| for(i=0; i<24; i+=4){ |
| c0 = a00^a10^a20^a30^a40; |
| c1 = a01^a11^a21^a31^a41; |
| c2 = a02^a12^a22^a32^a42; |
| c3 = a03^a13^a23^a33^a43; |
| c4 = a04^a14^a24^a34^a44; |
| d0 = c4^ROL64(c1, 1); |
| d1 = c0^ROL64(c2, 1); |
| d2 = c1^ROL64(c3, 1); |
| d3 = c2^ROL64(c4, 1); |
| d4 = c3^ROL64(c0, 1); |
|
|
| b0 = (a00^d0); |
| b1 = ROL64((a11^d1), 44); |
| b2 = ROL64((a22^d2), 43); |
| b3 = ROL64((a33^d3), 21); |
| b4 = ROL64((a44^d4), 14); |
| a00 = b0 ^((~b1)& b2 ); |
| a00 ^= RC[i]; |
| a11 = b1 ^((~b2)& b3 ); |
| a22 = b2 ^((~b3)& b4 ); |
| a33 = b3 ^((~b4)& b0 ); |
| a44 = b4 ^((~b0)& b1 ); |
|
|
| b2 = ROL64((a20^d0), 3); |
| b3 = ROL64((a31^d1), 45); |
| b4 = ROL64((a42^d2), 61); |
| b0 = ROL64((a03^d3), 28); |
| b1 = ROL64((a14^d4), 20); |
| a20 = b0 ^((~b1)& b2 ); |
| a31 = b1 ^((~b2)& b3 ); |
| a42 = b2 ^((~b3)& b4 ); |
| a03 = b3 ^((~b4)& b0 ); |
| a14 = b4 ^((~b0)& b1 ); |
|
|
| b4 = ROL64((a40^d0), 18); |
| b0 = ROL64((a01^d1), 1); |
| b1 = ROL64((a12^d2), 6); |
| b2 = ROL64((a23^d3), 25); |
| b3 = ROL64((a34^d4), 8); |
| a40 = b0 ^((~b1)& b2 ); |
| a01 = b1 ^((~b2)& b3 ); |
| a12 = b2 ^((~b3)& b4 ); |
| a23 = b3 ^((~b4)& b0 ); |
| a34 = b4 ^((~b0)& b1 ); |
|
|
| b1 = ROL64((a10^d0), 36); |
| b2 = ROL64((a21^d1), 10); |
| b3 = ROL64((a32^d2), 15); |
| b4 = ROL64((a43^d3), 56); |
| b0 = ROL64((a04^d4), 27); |
| a10 = b0 ^((~b1)& b2 ); |
| a21 = b1 ^((~b2)& b3 ); |
| a32 = b2 ^((~b3)& b4 ); |
| a43 = b3 ^((~b4)& b0 ); |
| a04 = b4 ^((~b0)& b1 ); |
|
|
| b3 = ROL64((a30^d0), 41); |
| b4 = ROL64((a41^d1), 2); |
| b0 = ROL64((a02^d2), 62); |
| b1 = ROL64((a13^d3), 55); |
| b2 = ROL64((a24^d4), 39); |
| a30 = b0 ^((~b1)& b2 ); |
| a41 = b1 ^((~b2)& b3 ); |
| a02 = b2 ^((~b3)& b4 ); |
| a13 = b3 ^((~b4)& b0 ); |
| a24 = b4 ^((~b0)& b1 ); |
|
|
| c0 = a00^a20^a40^a10^a30; |
| c1 = a11^a31^a01^a21^a41; |
| c2 = a22^a42^a12^a32^a02; |
| c3 = a33^a03^a23^a43^a13; |
| c4 = a44^a14^a34^a04^a24; |
| d0 = c4^ROL64(c1, 1); |
| d1 = c0^ROL64(c2, 1); |
| d2 = c1^ROL64(c3, 1); |
| d3 = c2^ROL64(c4, 1); |
| d4 = c3^ROL64(c0, 1); |
|
|
| b0 = (a00^d0); |
| b1 = ROL64((a31^d1), 44); |
| b2 = ROL64((a12^d2), 43); |
| b3 = ROL64((a43^d3), 21); |
| b4 = ROL64((a24^d4), 14); |
| a00 = b0 ^((~b1)& b2 ); |
| a00 ^= RC[i+1]; |
| a31 = b1 ^((~b2)& b3 ); |
| a12 = b2 ^((~b3)& b4 ); |
| a43 = b3 ^((~b4)& b0 ); |
| a24 = b4 ^((~b0)& b1 ); |
|
|
| b2 = ROL64((a40^d0), 3); |
| b3 = ROL64((a21^d1), 45); |
| b4 = ROL64((a02^d2), 61); |
| b0 = ROL64((a33^d3), 28); |
| b1 = ROL64((a14^d4), 20); |
| a40 = b0 ^((~b1)& b2 ); |
| a21 = b1 ^((~b2)& b3 ); |
| a02 = b2 ^((~b3)& b4 ); |
| a33 = b3 ^((~b4)& b0 ); |
| a14 = b4 ^((~b0)& b1 ); |
|
|
| b4 = ROL64((a30^d0), 18); |
| b0 = ROL64((a11^d1), 1); |
| b1 = ROL64((a42^d2), 6); |
| b2 = ROL64((a23^d3), 25); |
| b3 = ROL64((a04^d4), 8); |
| a30 = b0 ^((~b1)& b2 ); |
| a11 = b1 ^((~b2)& b3 ); |
| a42 = b2 ^((~b3)& b4 ); |
| a23 = b3 ^((~b4)& b0 ); |
| a04 = b4 ^((~b0)& b1 ); |
|
|
| b1 = ROL64((a20^d0), 36); |
| b2 = ROL64((a01^d1), 10); |
| b3 = ROL64((a32^d2), 15); |
| b4 = ROL64((a13^d3), 56); |
| b0 = ROL64((a44^d4), 27); |
| a20 = b0 ^((~b1)& b2 ); |
| a01 = b1 ^((~b2)& b3 ); |
| a32 = b2 ^((~b3)& b4 ); |
| a13 = b3 ^((~b4)& b0 ); |
| a44 = b4 ^((~b0)& b1 ); |
|
|
| b3 = ROL64((a10^d0), 41); |
| b4 = ROL64((a41^d1), 2); |
| b0 = ROL64((a22^d2), 62); |
| b1 = ROL64((a03^d3), 55); |
| b2 = ROL64((a34^d4), 39); |
| a10 = b0 ^((~b1)& b2 ); |
| a41 = b1 ^((~b2)& b3 ); |
| a22 = b2 ^((~b3)& b4 ); |
| a03 = b3 ^((~b4)& b0 ); |
| a34 = b4 ^((~b0)& b1 ); |
|
|
| c0 = a00^a40^a30^a20^a10; |
| c1 = a31^a21^a11^a01^a41; |
| c2 = a12^a02^a42^a32^a22; |
| c3 = a43^a33^a23^a13^a03; |
| c4 = a24^a14^a04^a44^a34; |
| d0 = c4^ROL64(c1, 1); |
| d1 = c0^ROL64(c2, 1); |
| d2 = c1^ROL64(c3, 1); |
| d3 = c2^ROL64(c4, 1); |
| d4 = c3^ROL64(c0, 1); |
|
|
| b0 = (a00^d0); |
| b1 = ROL64((a21^d1), 44); |
| b2 = ROL64((a42^d2), 43); |
| b3 = ROL64((a13^d3), 21); |
| b4 = ROL64((a34^d4), 14); |
| a00 = b0 ^((~b1)& b2 ); |
| a00 ^= RC[i+2]; |
| a21 = b1 ^((~b2)& b3 ); |
| a42 = b2 ^((~b3)& b4 ); |
| a13 = b3 ^((~b4)& b0 ); |
| a34 = b4 ^((~b0)& b1 ); |
|
|
| b2 = ROL64((a30^d0), 3); |
| b3 = ROL64((a01^d1), 45); |
| b4 = ROL64((a22^d2), 61); |
| b0 = ROL64((a43^d3), 28); |
| b1 = ROL64((a14^d4), 20); |
| a30 = b0 ^((~b1)& b2 ); |
| a01 = b1 ^((~b2)& b3 ); |
| a22 = b2 ^((~b3)& b4 ); |
| a43 = b3 ^((~b4)& b0 ); |
| a14 = b4 ^((~b0)& b1 ); |
|
|
| b4 = ROL64((a10^d0), 18); |
| b0 = ROL64((a31^d1), 1); |
| b1 = ROL64((a02^d2), 6); |
| b2 = ROL64((a23^d3), 25); |
| b3 = ROL64((a44^d4), 8); |
| a10 = b0 ^((~b1)& b2 ); |
| a31 = b1 ^((~b2)& b3 ); |
| a02 = b2 ^((~b3)& b4 ); |
| a23 = b3 ^((~b4)& b0 ); |
| a44 = b4 ^((~b0)& b1 ); |
|
|
| b1 = ROL64((a40^d0), 36); |
| b2 = ROL64((a11^d1), 10); |
| b3 = ROL64((a32^d2), 15); |
| b4 = ROL64((a03^d3), 56); |
| b0 = ROL64((a24^d4), 27); |
| a40 = b0 ^((~b1)& b2 ); |
| a11 = b1 ^((~b2)& b3 ); |
| a32 = b2 ^((~b3)& b4 ); |
| a03 = b3 ^((~b4)& b0 ); |
| a24 = b4 ^((~b0)& b1 ); |
|
|
| b3 = ROL64((a20^d0), 41); |
| b4 = ROL64((a41^d1), 2); |
| b0 = ROL64((a12^d2), 62); |
| b1 = ROL64((a33^d3), 55); |
| b2 = ROL64((a04^d4), 39); |
| a20 = b0 ^((~b1)& b2 ); |
| a41 = b1 ^((~b2)& b3 ); |
| a12 = b2 ^((~b3)& b4 ); |
| a33 = b3 ^((~b4)& b0 ); |
| a04 = b4 ^((~b0)& b1 ); |
|
|
| c0 = a00^a30^a10^a40^a20; |
| c1 = a21^a01^a31^a11^a41; |
| c2 = a42^a22^a02^a32^a12; |
| c3 = a13^a43^a23^a03^a33; |
| c4 = a34^a14^a44^a24^a04; |
| d0 = c4^ROL64(c1, 1); |
| d1 = c0^ROL64(c2, 1); |
| d2 = c1^ROL64(c3, 1); |
| d3 = c2^ROL64(c4, 1); |
| d4 = c3^ROL64(c0, 1); |
|
|
| b0 = (a00^d0); |
| b1 = ROL64((a01^d1), 44); |
| b2 = ROL64((a02^d2), 43); |
| b3 = ROL64((a03^d3), 21); |
| b4 = ROL64((a04^d4), 14); |
| a00 = b0 ^((~b1)& b2 ); |
| a00 ^= RC[i+3]; |
| a01 = b1 ^((~b2)& b3 ); |
| a02 = b2 ^((~b3)& b4 ); |
| a03 = b3 ^((~b4)& b0 ); |
| a04 = b4 ^((~b0)& b1 ); |
|
|
| b2 = ROL64((a10^d0), 3); |
| b3 = ROL64((a11^d1), 45); |
| b4 = ROL64((a12^d2), 61); |
| b0 = ROL64((a13^d3), 28); |
| b1 = ROL64((a14^d4), 20); |
| a10 = b0 ^((~b1)& b2 ); |
| a11 = b1 ^((~b2)& b3 ); |
| a12 = b2 ^((~b3)& b4 ); |
| a13 = b3 ^((~b4)& b0 ); |
| a14 = b4 ^((~b0)& b1 ); |
|
|
| b4 = ROL64((a20^d0), 18); |
| b0 = ROL64((a21^d1), 1); |
| b1 = ROL64((a22^d2), 6); |
| b2 = ROL64((a23^d3), 25); |
| b3 = ROL64((a24^d4), 8); |
| a20 = b0 ^((~b1)& b2 ); |
| a21 = b1 ^((~b2)& b3 ); |
| a22 = b2 ^((~b3)& b4 ); |
| a23 = b3 ^((~b4)& b0 ); |
| a24 = b4 ^((~b0)& b1 ); |
|
|
| b1 = ROL64((a30^d0), 36); |
| b2 = ROL64((a31^d1), 10); |
| b3 = ROL64((a32^d2), 15); |
| b4 = ROL64((a33^d3), 56); |
| b0 = ROL64((a34^d4), 27); |
| a30 = b0 ^((~b1)& b2 ); |
| a31 = b1 ^((~b2)& b3 ); |
| a32 = b2 ^((~b3)& b4 ); |
| a33 = b3 ^((~b4)& b0 ); |
| a34 = b4 ^((~b0)& b1 ); |
|
|
| b3 = ROL64((a40^d0), 41); |
| b4 = ROL64((a41^d1), 2); |
| b0 = ROL64((a42^d2), 62); |
| b1 = ROL64((a43^d3), 55); |
| b2 = ROL64((a44^d4), 39); |
| a40 = b0 ^((~b1)& b2 ); |
| a41 = b1 ^((~b2)& b3 ); |
| a42 = b2 ^((~b3)& b4 ); |
| a43 = b3 ^((~b4)& b0 ); |
| a44 = b4 ^((~b0)& b1 ); |
| } |
| } |
|
|
| |
| |
| |
| |
| |
| static void SHA3Init(SHA3Context *p, int iSize){ |
| memset(p, 0, sizeof(*p)); |
| p->iSize = iSize; |
| if( iSize>=128 && iSize<=512 ){ |
| p->nRate = (1600 - ((iSize + 31)&~31)*2)/8; |
| }else{ |
| p->nRate = (1600 - 2*256)/8; |
| } |
| #if SHA3_BYTEORDER==1234 |
| |
| #elif SHA3_BYTEORDER==4321 |
| p->ixMask = 7; |
| #else |
| { |
| static unsigned int one = 1; |
| if( 1==*(unsigned char*)&one ){ |
| |
| p->ixMask = 0; |
| }else{ |
| |
| p->ixMask = 7; |
| } |
| } |
| #endif |
| } |
|
|
| |
| |
| |
| |
| static void SHA3Update( |
| SHA3Context *p, |
| const unsigned char *aData, |
| unsigned int nData |
| ){ |
| unsigned int i = 0; |
| if( aData==0 ) return; |
| #if SHA3_BYTEORDER==1234 |
| if( (p->nLoaded % 8)==0 && ((aData - (const unsigned char*)0)&7)==0 ){ |
| for(; i+7<nData; i+=8){ |
| p->u.s[p->nLoaded/8] ^= *(u64*)&aData[i]; |
| p->nLoaded += 8; |
| if( p->nLoaded>=p->nRate ){ |
| KeccakF1600Step(p); |
| p->nLoaded = 0; |
| } |
| } |
| } |
| #endif |
| for(; i<nData; i++){ |
| #if SHA3_BYTEORDER==1234 |
| p->u.x[p->nLoaded] ^= aData[i]; |
| #elif SHA3_BYTEORDER==4321 |
| p->u.x[p->nLoaded^0x07] ^= aData[i]; |
| #else |
| p->u.x[p->nLoaded^p->ixMask] ^= aData[i]; |
| #endif |
| p->nLoaded++; |
| if( p->nLoaded==p->nRate ){ |
| KeccakF1600Step(p); |
| p->nLoaded = 0; |
| } |
| } |
| } |
|
|
| |
| |
| |
| |
| |
| static unsigned char *SHA3Final(SHA3Context *p){ |
| unsigned int i; |
| if( p->nLoaded==p->nRate-1 ){ |
| const unsigned char c1 = 0x86; |
| SHA3Update(p, &c1, 1); |
| }else{ |
| const unsigned char c2 = 0x06; |
| const unsigned char c3 = 0x80; |
| SHA3Update(p, &c2, 1); |
| p->nLoaded = p->nRate - 1; |
| SHA3Update(p, &c3, 1); |
| } |
| for(i=0; i<p->nRate; i++){ |
| p->u.x[i+p->nRate] = p->u.x[i^p->ixMask]; |
| } |
| return &p->u.x[p->nRate]; |
| } |
| |
| |
|
|
| |
| |
| |
| |
| |
| |
| |
| |
| |
| static void sha3Func( |
| sqlite3_context *context, |
| int argc, |
| sqlite3_value **argv |
| ){ |
| SHA3Context cx; |
| int eType = sqlite3_value_type(argv[0]); |
| int nByte = sqlite3_value_bytes(argv[0]); |
| int iSize; |
| if( argc==1 ){ |
| iSize = 256; |
| }else{ |
| iSize = sqlite3_value_int(argv[1]); |
| if( iSize!=224 && iSize!=256 && iSize!=384 && iSize!=512 ){ |
| sqlite3_result_error(context, "SHA3 size should be one of: 224 256 " |
| "384 512", -1); |
| return; |
| } |
| } |
| if( eType==SQLITE_NULL ) return; |
| SHA3Init(&cx, iSize); |
| if( eType==SQLITE_BLOB ){ |
| SHA3Update(&cx, sqlite3_value_blob(argv[0]), nByte); |
| }else{ |
| SHA3Update(&cx, sqlite3_value_text(argv[0]), nByte); |
| } |
| sqlite3_result_blob(context, SHA3Final(&cx), iSize/8, SQLITE_TRANSIENT); |
| } |
|
|
| |
| |
| |
| static void sha3_step_vformat( |
| SHA3Context *p, |
| const char *zFormat, |
| ... |
| ){ |
| va_list ap; |
| int n; |
| char zBuf[50]; |
| va_start(ap, zFormat); |
| sqlite3_vsnprintf(sizeof(zBuf),zBuf,zFormat,ap); |
| va_end(ap); |
| n = (int)strlen(zBuf); |
| SHA3Update(p, (unsigned char*)zBuf, n); |
| } |
|
|
| |
| |
| |
| static void sha3UpdateFromValue(SHA3Context *p, sqlite3_value *pVal){ |
| switch( sqlite3_value_type(pVal) ){ |
| case SQLITE_NULL: { |
| SHA3Update(p, (const unsigned char*)"N",1); |
| break; |
| } |
| case SQLITE_INTEGER: { |
| sqlite3_uint64 u; |
| int j; |
| unsigned char x[9]; |
| sqlite3_int64 v = sqlite3_value_int64(pVal); |
| memcpy(&u, &v, 8); |
| for(j=8; j>=1; j--){ |
| x[j] = u & 0xff; |
| u >>= 8; |
| } |
| x[0] = 'I'; |
| SHA3Update(p, x, 9); |
| break; |
| } |
| case SQLITE_FLOAT: { |
| sqlite3_uint64 u; |
| int j; |
| unsigned char x[9]; |
| double r = sqlite3_value_double(pVal); |
| memcpy(&u, &r, 8); |
| for(j=8; j>=1; j--){ |
| x[j] = u & 0xff; |
| u >>= 8; |
| } |
| x[0] = 'F'; |
| SHA3Update(p,x,9); |
| break; |
| } |
| case SQLITE_TEXT: { |
| int n2 = sqlite3_value_bytes(pVal); |
| const unsigned char *z2 = sqlite3_value_text(pVal); |
| sha3_step_vformat(p,"T%d:",n2); |
| SHA3Update(p, z2, n2); |
| break; |
| } |
| case SQLITE_BLOB: { |
| int n2 = sqlite3_value_bytes(pVal); |
| const unsigned char *z2 = sqlite3_value_blob(pVal); |
| sha3_step_vformat(p,"B%d:",n2); |
| SHA3Update(p, z2, n2); |
| break; |
| } |
| } |
| } |
|
|
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| static void sha3QueryFunc( |
| sqlite3_context *context, |
| int argc, |
| sqlite3_value **argv |
| ){ |
| sqlite3 *db = sqlite3_context_db_handle(context); |
| const char *zSql = (const char*)sqlite3_value_text(argv[0]); |
| sqlite3_stmt *pStmt = 0; |
| int nCol; |
| int i; |
| int rc; |
| int n; |
| const char *z; |
| SHA3Context cx; |
| int iSize; |
|
|
| if( argc==1 ){ |
| iSize = 256; |
| }else{ |
| iSize = sqlite3_value_int(argv[1]); |
| if( iSize!=224 && iSize!=256 && iSize!=384 && iSize!=512 ){ |
| sqlite3_result_error(context, "SHA3 size should be one of: 224 256 " |
| "384 512", -1); |
| return; |
| } |
| } |
| if( zSql==0 ) return; |
| SHA3Init(&cx, iSize); |
| while( zSql[0] ){ |
| rc = sqlite3_prepare_v2(db, zSql, -1, &pStmt, &zSql); |
| if( rc ){ |
| char *zMsg = sqlite3_mprintf("error SQL statement [%s]: %s", |
| zSql, sqlite3_errmsg(db)); |
| sqlite3_finalize(pStmt); |
| sqlite3_result_error(context, zMsg, -1); |
| sqlite3_free(zMsg); |
| return; |
| } |
| if( !sqlite3_stmt_readonly(pStmt) ){ |
| char *zMsg = sqlite3_mprintf("non-query: [%s]", sqlite3_sql(pStmt)); |
| sqlite3_finalize(pStmt); |
| sqlite3_result_error(context, zMsg, -1); |
| sqlite3_free(zMsg); |
| return; |
| } |
| nCol = sqlite3_column_count(pStmt); |
| z = sqlite3_sql(pStmt); |
| if( z ){ |
| n = (int)strlen(z); |
| sha3_step_vformat(&cx,"S%d:",n); |
| SHA3Update(&cx,(unsigned char*)z,n); |
| } |
|
|
| |
| while( SQLITE_ROW==sqlite3_step(pStmt) ){ |
| SHA3Update(&cx,(const unsigned char*)"R",1); |
| for(i=0; i<nCol; i++){ |
| sha3UpdateFromValue(&cx, sqlite3_column_value(pStmt,i)); |
| } |
| } |
| sqlite3_finalize(pStmt); |
| } |
| sqlite3_result_blob(context, SHA3Final(&cx), iSize/8, SQLITE_TRANSIENT); |
| } |
|
|
| |
| |
| |
| static void sha3AggStep( |
| sqlite3_context *context, |
| int argc, |
| sqlite3_value **argv |
| ){ |
| SHA3Context *p; |
| p = (SHA3Context*)sqlite3_aggregate_context(context, sizeof(*p)); |
| if( p==0 ) return; |
| if( p->nRate==0 ){ |
| int sz = 256; |
| if( argc==2 ){ |
| sz = sqlite3_value_int(argv[1]); |
| if( sz!=224 && sz!=384 && sz!=512 ){ |
| sz = 256; |
| } |
| } |
| SHA3Init(p, sz); |
| } |
| sha3UpdateFromValue(p, argv[0]); |
| } |
|
|
|
|
| |
| |
| |
| static void sha3AggFinal(sqlite3_context *context){ |
| SHA3Context *p; |
| p = (SHA3Context*)sqlite3_aggregate_context(context, sizeof(*p)); |
| if( p==0 ) return; |
| if( p->iSize ){ |
| sqlite3_result_blob(context, SHA3Final(p), p->iSize/8, SQLITE_TRANSIENT); |
| } |
| } |
|
|
|
|
|
|
| #ifdef _WIN32 |
| __declspec(dllexport) |
| #endif |
| int sqlite3_shathree_init( |
| sqlite3 *db, |
| char **pzErrMsg, |
| const sqlite3_api_routines *pApi |
| ){ |
| int rc = SQLITE_OK; |
| SQLITE_EXTENSION_INIT2(pApi); |
| (void)pzErrMsg; |
| rc = sqlite3_create_function(db, "sha3", 1, |
| SQLITE_UTF8 | SQLITE_INNOCUOUS | SQLITE_DETERMINISTIC, |
| 0, sha3Func, 0, 0); |
| if( rc==SQLITE_OK ){ |
| rc = sqlite3_create_function(db, "sha3", 2, |
| SQLITE_UTF8 | SQLITE_INNOCUOUS | SQLITE_DETERMINISTIC, |
| 0, sha3Func, 0, 0); |
| } |
| if( rc==SQLITE_OK ){ |
| rc = sqlite3_create_function(db, "sha3_agg", 1, |
| SQLITE_UTF8 | SQLITE_INNOCUOUS | SQLITE_DETERMINISTIC, |
| 0, 0, sha3AggStep, sha3AggFinal); |
| } |
| if( rc==SQLITE_OK ){ |
| rc = sqlite3_create_function(db, "sha3_agg", 2, |
| SQLITE_UTF8 | SQLITE_INNOCUOUS | SQLITE_DETERMINISTIC, |
| 0, 0, sha3AggStep, sha3AggFinal); |
| } |
| if( rc==SQLITE_OK ){ |
| rc = sqlite3_create_function(db, "sha3_query", 1, |
| SQLITE_UTF8 | SQLITE_DIRECTONLY, |
| 0, sha3QueryFunc, 0, 0); |
| } |
| if( rc==SQLITE_OK ){ |
| rc = sqlite3_create_function(db, "sha3_query", 2, |
| SQLITE_UTF8 | SQLITE_DIRECTONLY, |
| 0, sha3QueryFunc, 0, 0); |
| } |
| return rc; |
| } |
|
|