Annotation of loncom/auth/londes.js, revision 1.10
1.8 matthew 1: <script type="text/javascript" language="JavaScript">
1.9 bisitz 2: // <![CDATA[
1.1 www 3: // The LearningOnline Network with CAPA
4: // Encryption Routines according to Data Encryption Standard DES
5: // Federal Information Processing Standards Publication 46-2 (1993 Dec 30)
1.2 www 6: //
1.10 ! raeburn 7: // $Id: londes.js,v 1.9 2009/05/22 17:01:28 bisitz Exp $
1.2 www 8: //
9: // Copyright Michigan State University Board of Trustees
10: //
11: // This file is part of the LearningOnline Network with CAPA (LON-CAPA).
12: //
13: // LON-CAPA is free software; you can redistribute it and/or modify
14: // it under the terms of the GNU General Public License as published by
15: // the Free Software Foundation; either version 2 of the License, or
16: // (at your option) any later version.
17: //
18: // LON-CAPA is distributed in the hope that it will be useful,
19: // but WITHOUT ANY WARRANTY; without even the implied warranty of
20: // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21: // GNU General Public License for more details.
22: //
23: // You should have received a copy of the GNU General Public License
24: // along with LON-CAPA; if not, write to the Free Software
25: // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
26: //
27: // /home/httpd/html/adm/gpl.txt
28: //
29: // http://www.lon-capa.org/
30: //
1.1 www 31: // JavaScript Implementation by Gerd Kortemeyer
1.6 www 32: // 1997,06/27/00,06/28 Gerd Kortemeyer
1.1 www 33:
34: // Global variables
35:
36: // Array of integers with i-th bit set
37: var bit=new Array(31);
38: // Initial permutation IP for right part
39: var riparr=new Array(31);
40: // Inverse permutation IP-1
41: var liiparr=new Array(31);
42: var uiiparr=new Array(31);
43: // Key vectors
44: var uk=new Array(16);
45: var lk=new Array(16);
46: // Upper- and lower 32-bit of external key
47: var uextkey=0;
48: var lextkey=0;
49: // Upper- and lower 32-bit of block
50: var ublock=0;
51: var lblock=0;
52: // Upper and lower 24 bit of expanded right vector
53: var lexpand=0;
54: var uexpand=0;
55: // S-box array
56: var sbarr=new Array(511);
57: // E expansion
58: var etarr=new Array(47);
59: // P permutation
60: var pparr=new Array(31);
61: // r- and l-vector
62: var rv=0;
63: var lv=0;
64: // Blocks of data for text
65: var b0=0;
66: var b1=0;
67: var b2=0;
68: var b3=0;
69: // Text variable
70: var text="";
71:
72: // Initialize table arrays and perform self test
73:
74: function init() {
75: window.status="Initializing ...";
76: var rip="58504234261810 260524436282012 462544638302214 664564840322416 8";
77: var iip=" 8162432 7152331 6142230 5132129 4122028 3111927 2101826 1 91725";
78: var sb
79: sb ="14 413 1 21511 8 310 612 5 9 0 7";
80: sb+=" 015 7 414 213 110 61211 9 5 3 8";
81: sb+=" 4 114 813 6 2111512 9 7 310 5 0";
82: sb+="1512 8 2 4 9 1 7 511 31410 0 613";
83: sb+="15 1 814 611 3 4 9 7 21312 0 510";
84: sb+=" 313 4 715 2 81412 0 110 6 911 5";
85: sb+=" 014 71110 413 1 5 812 6 9 3 215";
86: sb+="13 810 1 315 4 211 6 712 0 514 9";
87: sb+="10 0 914 6 315 5 11312 711 4 2 8";
88: sb+="13 7 0 9 3 4 610 2 8 514121115 1";
89: sb+="13 6 4 9 815 3 011 1 212 51014 7";
90: sb+=" 11013 0 6 9 8 7 41514 311 5 212";
91: sb+=" 71314 3 0 6 910 1 2 8 51112 415";
92: sb+="13 811 5 615 0 3 4 7 212 11014 9";
93: sb+="10 6 9 01211 71315 1 314 5 2 8 4";
94: sb+=" 315 0 610 113 8 9 4 51112 7 214";
95: sb+=" 212 4 1 71011 6 8 5 31513 014 9";
96: sb+="1411 212 4 713 1 5 01510 3 9 8 6";
97: sb+=" 4 2 1111013 7 815 912 5 6 3 014";
98: sb+="11 812 7 114 213 615 0 910 4 5 3";
99: sb+="12 11015 9 2 6 8 013 3 414 7 511";
100: sb+="1015 4 2 712 9 5 6 11314 011 3 8";
101: sb+=" 91415 5 2 812 3 7 0 410 11311 6";
102: sb+=" 4 3 212 9 515101114 1 7 6 0 813";
103: sb+=" 411 21415 0 813 312 9 7 510 6 1";
104: sb+="13 011 7 4 9 11014 3 512 215 8 6";
105: sb+=" 1 4111312 3 7141015 6 8 0 5 9 2";
106: sb+=" 61113 8 1 410 7 9 5 01514 2 312";
107: sb+="13 2 8 4 61511 110 9 314 5 012 7";
108: sb+=" 11513 810 3 7 412 5 611 014 9 2";
109: sb+=" 711 4 1 91214 2 0 6101315 3 5 8";
110: sb+=" 2 114 7 410 8131512 9 0 3 5 611";
111: var et
112: et ="32 1 2 3 4 5 4 5 6 7 8 9 8 910111213121314151617";
113: et+="1617181920212021222324252425262728292829303132 1";
114: var pp="16 7202129122817 1152326 5183110 2 824143227 3 9191330 62211 425";
115: bit[0]=1;
116: for (var i=1; i<=31;i++) { bit[i]=bit[i-1]<<1; }
117: for (i=0; i<=31;i++) {
118: riparr[i]=parseInt(rip.substring(i*2,i*2+2));
119: pparr[i]=parseInt(pp.substring(i*2,i*2+2));
120: }
121: for (i=0;i<=15;i++) {
122: liiparr[i]=parseInt(iip.substring(i*2,i*2+2));
123: uiiparr[i]=parseInt(iip.substring(32+i*2,32+i*2+2));
124: }
125: for (i=0;i<=511;i++) {
126: sbarr[i]=parseInt(sb.substring(i*2,i*2+2));
127: }
128: for (i=0;i<=47;i++) {
129: etarr[i]=parseInt(et.substring(i*2,i*2+2));
130: }
131:
132: window.status="Ready.";
133: }
134:
135: // Return a string with hex-representation of integer
136:
137: function hexstring(i) {
138: var hstr="";
139: var hchr="0123456789abcdef";
140: for (var k=28; k>=0; k=k-4) {
141: j=0;
1.6 www 142: for (var m=0; m<=3; m++) { if ((i&bit[k+m])!=0) { j=j|bit[m]; } }
1.1 www 143: hstr+=hchr.substring(j,j+1);
144: }
145: return(hstr);
146: }
147:
148: // Shift a 28-bit register one time
149:
150: function shift(sreg) {
1.6 www 151: var bit27=(sreg&bit[0])<<27;
1.1 www 152: return (sreg>>1)|bit27;
153: }
154:
155: // Initialize key-arrays according to uextkey and lextkey
156:
157: function initkeys() {
1.7 albertel 158: init();
1.1 www 159: // Constants
160: var celements="574941332517 9 158504234261810 259514335271911 360524436";
161: var delements="63554739312315 762544638302214 661534537292113 5282012 4";
162: var lkelements="14171124 1 5 32815 62110231912 426 816 7272013 2";
163: var ukelements="415231374755304051453348444939563453464250362932";
164: var shifttimes="1122222212222221";
165: // PC-2 order
166: var ukarr=new Array(23);
167: var lkarr=new Array(23);
168: for (i=0;i<=23;i++) {
169: ukarr[i]=parseInt(ukelements.substring(i*2,i*2+2));
170: lkarr[i]=parseInt(lkelements.substring(i*2,i*2+2));
171: }
172: // Initialize c and d
173: var bt;
174: var c=0;
175: var d=0;
176: for (var i=0; i<=27;i++) {
177: bt=parseInt(celements.substring(i*2,i*2+2));
178: if (bt<=32) {
1.6 www 179: if ((uextkey & bit[31-(bt-1)]) != 0) { c=c|bit[i]; }
1.1 www 180: } else {
1.6 www 181: if ((lextkey & bit[31-(bt-33)]) != 0) { c=c|bit[i]; }
1.1 www 182: }
183: bt=parseInt(delements.substring(i*2,i*2+2));
184: if (bt<=32) {
1.6 www 185: if ((uextkey & bit[31-(bt-1)]) != 0) { d=d|bit[i]; }
1.1 www 186: } else {
1.6 www 187: if ((lextkey & bit[31-(bt-33)]) != 0) { d=d|bit[i]; }
1.1 www 188: }
189: }
190: // Initialize the k vectors
191: for (i=1;i<=16;i++) {
192: // Shift c and d
193: if (shifttimes.substring(i-1,i)=='1') {
194: c=shift(c);
195: d=shift(d);
196: } else {
197: c=shift(shift(c));
198: d=shift(shift(d));
199: }
200: uk[i]=0;
201: lk[i]=0;
202: for (j=0; j<=23;j++) {
1.6 www 203: if ((d&bit[ukarr[j]-29])!=0) { lk[i]=lk[i]|bit[23-j]; }
204: if ((c&bit[lkarr[j]-1])!=0) { uk[i]=uk[i]|bit[23-j]; }
1.1 www 205: }
206: }
207: }
208:
209: // Initial permutation of ublock and lblock into rv and lv
210:
211: function ip() {
212: var bt;
213: rv=0;
214: lv=0;
215: for (var i=0; i<=31;i++) {
216: bt=riparr[i];
217: if (bt<=32) {
1.6 www 218: if ((lblock & bit[bt-1]) != 0) { rv=rv|bit[i]; }
1.1 www 219: } else {
1.6 www 220: if ((ublock & bit[bt-33]) != 0) { rv=rv|bit[i]; }
1.1 www 221: }
222: if (bt<=33) {
1.6 www 223: if ((lblock & bit[bt-2]) != 0) { lv=lv|bit[i]; }
1.1 www 224: } else {
1.6 www 225: if ((ublock & bit[bt-34]) != 0) { lv=lv|bit[i]; }
1.1 www 226: }
227: }
228: }
229:
230: // Inverse Initial Permutation IP-1, input rv,lv, output lblock,ublock
231:
232: function invip() {
233: var bt;
234: ublock=0;
235: lblock=0;
236: for (var i=0; i<=15;i++) {
237: bt=liiparr[i];
1.6 www 238: if ((rv & bit[bt-1]) != 0) { lblock=lblock|bit[i*2]; }
239: if ((lv & bit[bt-1]) != 0) { lblock=lblock|bit[i*2+1]; }
1.1 www 240: bt=uiiparr[i];
1.6 www 241: if ((rv & bit[bt-1]) != 0) { ublock=ublock|bit[i*2]; }
242: if ((lv & bit[bt-1]) != 0) { ublock=ublock|bit[i*2+1]; }
1.1 www 243: }
244: }
245:
246: // Expansion of right vector according to E, input rv
247:
248: function expand() {
249: var bt;
250: uexpand=0;
251: lexpand=0;
252: for (var i=0; i<=23; i++) {
253: bt=etarr[i];
1.6 www 254: if (rv & bit[bt-1]) { lexpand=lexpand|bit[i]; }
1.1 www 255: }
256: for (i=24; i<=47; i++) {
257: bt=etarr[i];
1.6 www 258: if (rv & bit[bt-1]) { uexpand=uexpand|bit[i-24]; }
1.1 www 259: }
260: }
261:
262: // Permutes rv according to P, input/output rv
263:
264: function permute() {
265: var prv=rv;
266: rv=0;
267: for (var i=0; i<=31; i++) {
1.6 www 268: if ((prv&bit[31-(pparr[i]-1)])!=0) { rv=rv|bit[31-i]; }
1.1 www 269: }
270: }
271:
272: // Performs stage si of the encryption, input/output rv
273:
274: function stage(si) {
275: expand();
276: var uadd=uexpand^uk[si];
277: var ladd=lexpand^lk[si];
278: rv=0;
279: var ks=0;
280: for (var ki=42;ki>=24;ki=ki-6) {
281: rv=rv<<4;
282: var i=0;
1.6 www 283: if ((uadd&bit[ki-24])!=0) { i=i|bit[0]; }
284: if ((uadd&bit[ki-19])!=0) { i=i|bit[1]; }
1.1 www 285: var j=0;
286: for (var kj=0; kj<=3; kj++) {
1.6 www 287: if ((uadd&bit[ki-23+kj])!=0) { j=j|bit[kj]; }
1.1 www 288: }
1.6 www 289: rv=rv|sbarr[ks*64+i*16+j];
1.1 www 290: ks++;
291: }
292: for (var ki=18;ki>=0;ki=ki-6) {
293: rv=rv<<4;
294: var i=0;
1.6 www 295: if ((ladd&bit[ki] )!=0) { i=i|bit[0]; }
296: if ((ladd&bit[ki+5])!=0) { i=i|bit[1]; }
1.1 www 297: var j=0;
298: for (var kj=0; kj<=3; kj++) {
1.6 www 299: if ((ladd&bit[ki+1+kj])!=0) { j=j|bit[kj]; }
1.1 www 300: }
1.6 www 301: rv=rv|sbarr[ks*64+i*16+j];
1.1 www 302: ks++;
303: }
304: permute();
305: }
306:
307: // Encryption
308:
309: function encrypt() {
310: ip();
311: for (var i=1; i<=16; i++) {
312: var prv=rv;
313: stage(i);
314: rv=rv^lv;
315: lv=prv;
316: }
317: invip();
318: }
319:
320: // Decryption
321:
322: function decrypt() {
323: ip();
324: for (var i=16; i>=1; i--) {
325: var prv=rv;
326: stage(i);
327: rv=rv^lv;
328: lv=prv;
329: }
330: invip();
331: }
332:
333: // Put text into b0,b1,b2,b3
334:
335: function block(text) {;
336: var equiv= "*+ -./0123456789......@";
337: equiv+="ABCDEFGHIJKLMNOPQRSTUVWXYZ _ ";
338: equiv+="abcdefghijklmnopqrstuvwxyz";
339: var tl=text.length;
340: if (tl>=16) { tl=15; }
341: text+=" ";
342: text=escape(text);
343: var i;
344: var c;
345: var conv='';
346: var j=0;
347: for (i=0;i<15;i++) {
348: if (text.charAt(j)=='%') {
349: conv+=text.charAt(j+1)+text.charAt(j+2);
350: j=j+3;
351: } else {
352: c=hexstring(42+equiv.indexOf(text.charAt(j)));
353: conv+=c.substr(6,2);
354: j++;
355: }
356: }
357: b3=tl*bit[24]+parseInt("0x"+conv.substr(0,6));
358: b2=parseInt("0x"+conv.substr(6,8));
359: b1=parseInt("0x"+conv.substr(14,8));
360: b0=parseInt("0x"+conv.substr(22,8));
361:
362: }
363:
364: function crypted(text) {
365: block(text);
366: lblock=b0;
367: ublock=b1;
368: encrypt();
369: b0=lblock;
370: b1=ublock;
371: lblock=b2;
372: ublock=b3;
373: encrypt();
374: b2=lblock;
375: b3=ublock;
376: return(hexstring(b3)+hexstring(b2)+hexstring(b1)+hexstring(b0));
377: }
378:
1.10 ! raeburn 379: function getCrypted(text) {
! 380: var cryptedtext = '';
! 381: if (text.length > 0) {
! 382: var rem = text.length % 15;
! 383: var count = Math.floor(text.length/15);
! 384: if (rem > 0) {
! 385: count ++;
! 386: }
! 387: for (var i=0; i<count; i++) {
! 388: var start = i*15;
! 389: cryptedtext += crypted(text.substr(start,15));
! 390: }
! 391: }
! 392: return cryptedtext;
! 393: }
! 394:
! 395:
1.9 bisitz 396: // ]]>
1.1 www 397: </script>
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>