Go to the documentation of this file.00001
00027 #include <string.h>
00028
00029 #include "../../dprint.h"
00030 #include "../../md5.h"
00031 #include "../../crc.h"
00032 #include "../../mem/mem.h"
00033 #include "th_mask.h"
00034
00035 #define TH_EB64I \
00036 "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.-"
00037
00038 char _th_EB64[65];
00039 int _th_DB64[256];
00040 char *_th_PD64 = "*";
00041
00042 extern str _th_key;
00043
00044 void th_shuffle(char *in, int size)
00045 {
00046 char tmp;
00047 int last;
00048 unsigned int r;
00049 unsigned char md5[16];
00050 unsigned int *md5i;
00051 unsigned int crc;
00052 MD5_CTX ctx;
00053
00054 MD5Init(&ctx);
00055 MD5Update(&ctx, _th_key.s, _th_key.len);
00056 MD5Update(&ctx, _th_key.s, _th_key.len);
00057 U_MD5Final(md5, &ctx);
00058
00059 md5i = (unsigned int*)md5;
00060
00061 crc = (unsigned int)crcitt_string(_th_key.s, _th_key.len);
00062 for (last = size; last > 1; last--)
00063 {
00064 r = (md5i[(crc+last+_th_key.len)%4]
00065 + _th_key.s[(crc+last+_th_key.len)%_th_key.len]) % last;
00066 tmp = in[r];
00067 in[r] = in[last - 1];
00068 in[last - 1] = tmp;
00069 }
00070 }
00071
00072 void th_mask_init(void)
00073 {
00074 int i;
00075
00076 _th_key.len = strlen(_th_key.s);
00077 memcpy(_th_EB64, TH_EB64I, sizeof(TH_EB64I));
00078 th_shuffle(_th_EB64, 64);
00079 LM_ERR("+++ %s\n", TH_EB64I);
00080 LM_ERR("+++ %s\n", _th_EB64);
00081 for(i=0; i<256; i++)
00082 _th_DB64[i] = -1;
00083 for(i=0; i<64; i++)
00084 _th_DB64[(int)_th_EB64[i]] = i;
00085
00086 return;
00087 }
00088
00089 char* th_mask_encode(char *in, int ilen, str *prefix, int *olen)
00090 {
00091 char *out;
00092 int left;
00093 int idx;
00094 int i;
00095 int r;
00096 char *p;
00097 int block;
00098
00099 *olen = (((ilen+2)/3)<<2) + ((prefix!=NULL&&prefix->len>0)?prefix->len:0);
00100 out = (char*)pkg_malloc((*olen+1)*sizeof(char));
00101 if(out==NULL)
00102 {
00103 LM_ERR("no more pkg\n");
00104 *olen = 0;
00105 return NULL;
00106 }
00107 memset(out, 0, (*olen+1)*sizeof(char));
00108 if(prefix!=NULL&&prefix->len>0)
00109 memcpy(out, prefix->s, prefix->len);
00110
00111 p = out + (int)((prefix!=NULL&&prefix->len>0)?prefix->len:0);
00112 for(idx=0; idx<ilen; idx+=3)
00113 {
00114 left = ilen - idx - 1 ;
00115 left = (left>1)?2:left;
00116
00117 block = 0;
00118 for(i=0, r=16; i<=left; i++, r-=8)
00119 block += ((unsigned char)in[idx+i]) << r;
00120
00121 *(p++) = _th_EB64[(block >> 18) & 0x3f];
00122 *(p++) = _th_EB64[(block >> 12) & 0x3f];
00123 *(p++) = (left>0)?_th_EB64[(block >> 6) & 0x3f]:_th_PD64[0];
00124 *(p++) = (left>1)?_th_EB64[block & 0x3f]:_th_PD64[0];
00125 }
00126
00127 return out;
00128 }
00129
00130 char* th_mask_decode(char *in, int ilen, str *prefix, int extra, int *olen)
00131 {
00132 char *out;
00133 int n;
00134 int block;
00135 int idx;
00136 int i;
00137 int j;
00138 int end;
00139 char c;
00140
00141 for(n=0,i=ilen-1; in[i]==_th_PD64[0]; i--)
00142 n++;
00143
00144 *olen = (((ilen-((prefix!=NULL&&prefix->len>0)?prefix->len:0)) * 6) >> 3)
00145 - n;
00146 out = (char*)pkg_malloc((*olen+1+extra)*sizeof(char));
00147
00148 if(out==NULL)
00149 {
00150 LM_ERR("no more pkg\n");
00151 *olen = 0;
00152 return NULL;
00153 }
00154 memset(out, 0, (*olen+1+extra)*sizeof(char));
00155
00156 end = ilen - n;
00157 i = (prefix!=NULL&&prefix->len>0)?prefix->len:0;
00158 for(idx=0; i<end; idx+=3)
00159 {
00160 block = 0;
00161 for(j=0; j<4 && i<end ; j++)
00162 {
00163 c = _th_DB64[(int)in[i++]];
00164 if(c<0)
00165 {
00166 LM_ERR("invalid input string\"%.*s\"\n", ilen, in);
00167 pkg_free(out);
00168 *olen = 0;
00169 return NULL;
00170 }
00171 block += c << (18 - 6*j);
00172 }
00173
00174 for(j=0, n=16; j<3 && idx+j< *olen; j++, n-=8)
00175 out[idx+j] = (char)((block >> n) & 0xff);
00176 }
00177
00178 return out;
00179 }
00180
00181