home *** CD-ROM | disk | FTP | other *** search
/ PC Online 1998 September / PCO_0998.ISO / filesbbs / frei / vnc-java.arj / VNC-JAVA.ZIP / DesCipher.java < prev    next >
Encoding:
Java Source  |  1998-01-21  |  18.0 KB  |  496 lines

  1. //
  2. // This DES class has been extracted from package Acme.Crypto for use in VNC.
  3. // The bytebit[] array has been reversed so that the most significant bit
  4. // in each byte of the key is ignored, not the least significant.  Also the
  5. // unnecessary odd parity code has been removed.
  6. //
  7. // These changes are Copyright (C) 1998 Olivetti & Oracle Research Laboratory
  8. //
  9. // This software is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  12. //
  13.  
  14. // DesCipher - the DES encryption method
  15. //
  16. // The meat of this code is by Dave Zimmerman <dzimm@widget.com>, and is:
  17. //
  18. // Copyright (c) 1996 Widget Workshop, Inc. All Rights Reserved.
  19. //
  20. // Permission to use, copy, modify, and distribute this software
  21. // and its documentation for NON-COMMERCIAL or COMMERCIAL purposes and
  22. // without fee is hereby granted, provided that this copyright notice is kept 
  23. // intact. 
  24. // 
  25. // WIDGET WORKSHOP MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY
  26. // OF THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
  27. // TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
  28. // PARTICULAR PURPOSE, OR NON-INFRINGEMENT. WIDGET WORKSHOP SHALL NOT BE LIABLE
  29. // FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
  30. // DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
  31. // 
  32. // THIS SOFTWARE IS NOT DESIGNED OR INTENDED FOR USE OR RESALE AS ON-LINE
  33. // CONTROL EQUIPMENT IN HAZARDOUS ENVIRONMENTS REQUIRING FAIL-SAFE
  34. // PERFORMANCE, SUCH AS IN THE OPERATION OF NUCLEAR FACILITIES, AIRCRAFT
  35. // NAVIGATION OR COMMUNICATION SYSTEMS, AIR TRAFFIC CONTROL, DIRECT LIFE
  36. // SUPPORT MACHINES, OR WEAPONS SYSTEMS, IN WHICH THE FAILURE OF THE
  37. // SOFTWARE COULD LEAD DIRECTLY TO DEATH, PERSONAL INJURY, OR SEVERE
  38. // PHYSICAL OR ENVIRONMENTAL DAMAGE ("HIGH RISK ACTIVITIES").  WIDGET WORKSHOP
  39. // SPECIFICALLY DISCLAIMS ANY EXPRESS OR IMPLIED WARRANTY OF FITNESS FOR
  40. // HIGH RISK ACTIVITIES.
  41. //
  42. //
  43. // The rest is:
  44. //
  45. // Copyright (C) 1996 by Jef Poskanzer <jef@acme.com>.  All rights reserved.
  46. //
  47. // Redistribution and use in source and binary forms, with or without
  48. // modification, are permitted provided that the following conditions
  49. // are met:
  50. // 1. Redistributions of source code must retain the above copyright
  51. //    notice, this list of conditions and the following disclaimer.
  52. // 2. Redistributions in binary form must reproduce the above copyright
  53. //    notice, this list of conditions and the following disclaimer in the
  54. //    documentation and/or other materials provided with the distribution.
  55. //
  56. // THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
  57. // ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  58. // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  59. // ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
  60. // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  61. // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  62. // OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  63. // HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  64. // LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  65. // OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  66. // SUCH DAMAGE.
  67. //
  68. // Visit the ACME Labs Java page for up-to-date versions of this and other
  69. // fine Java utilities: http://www.acme.com/java/
  70.  
  71.  
  72. import java.io.*;
  73.  
  74. /// The DES encryption method.
  75. // <P>
  76. // This is surprisingly fast, for pure Java.  On a SPARC 20, wrapped
  77. // in Acme.Crypto.EncryptedOutputStream or Acme.Crypto.EncryptedInputStream,
  78. // it does around 7000 bytes/second.
  79. // <P>
  80. // Most of this code is by Dave Zimmerman <dzimm@widget.com>, and is
  81. // Copyright (c) 1996 Widget Workshop, Inc.  See the source file for details.
  82. // <P>
  83. // <A HREF="/resources/classes/Acme/Crypto/DesCipher.java">Fetch the software.</A><BR>
  84. // <A HREF="/resources/classes/Acme.tar.Z">Fetch the entire Acme package.</A>
  85. // <P>
  86. // @see Des3Cipher
  87. // @see EncryptedOutputStream
  88. // @see EncryptedInputStream
  89.  
  90. public class DesCipher
  91.     {
  92.  
  93.     // Constructor, byte-array key.
  94.     public DesCipher( byte[] key )
  95.     {
  96.     setKey( key );
  97.     }
  98.  
  99.     // Key routines.
  100.  
  101.     private int[] encryptKeys = new int[32];
  102.     private int[] decryptKeys = new int[32];
  103.  
  104.     /// Set the key.
  105.     public void setKey( byte[] key )
  106.     {
  107.     deskey( key, true, encryptKeys );
  108.     deskey( key, false, decryptKeys );
  109.     }
  110.  
  111.     // Turn an 8-byte key into internal keys.
  112.     private void deskey( byte[] keyBlock, boolean encrypting, int[] KnL )
  113.     {
  114.     int i, j, l, m, n;
  115.     int[] pc1m = new int[56];
  116.     int[] pcr = new int[56];
  117.     int[] kn = new int[32];
  118.  
  119.     for ( j = 0; j < 56; ++j )
  120.         {
  121.         l = pc1[j];
  122.         m = l & 07;
  123.         pc1m[j] = ( (keyBlock[l >>> 3] & bytebit[m]) != 0 )? 1: 0;
  124.         }
  125.  
  126.     for ( i = 0; i < 16; ++i )
  127.         {
  128.         if ( encrypting )
  129.         m = i << 1;
  130.         else
  131.         m = (15-i) << 1;
  132.         n = m+1;
  133.         kn[m] = kn[n] = 0;
  134.         for ( j = 0; j < 28; ++j )
  135.         {
  136.         l = j+totrot[i];
  137.         if ( l < 28 )
  138.             pcr[j] = pc1m[l];
  139.         else
  140.             pcr[j] = pc1m[l-28];
  141.         }
  142.         for ( j=28; j < 56; ++j )
  143.         {
  144.         l = j+totrot[i];
  145.         if ( l < 56 )
  146.             pcr[j] = pc1m[l];
  147.         else
  148.             pcr[j] = pc1m[l-28];
  149.         }
  150.         for ( j = 0; j < 24; ++j )
  151.         {
  152.         if ( pcr[pc2[j]] != 0 )
  153.             kn[m] |= bigbyte[j];
  154.         if ( pcr[pc2[j+24]] != 0 )
  155.             kn[n] |= bigbyte[j];
  156.         }
  157.         }
  158.     cookey( kn, KnL );
  159.     }
  160.  
  161.     private void cookey( int[] raw, int KnL[] )
  162.     {
  163.     int raw0, raw1;
  164.     int rawi, KnLi;
  165.     int i;
  166.  
  167.     for ( i = 0, rawi = 0, KnLi = 0; i < 16; ++i )
  168.         {
  169.         raw0 = raw[rawi++];
  170.         raw1 = raw[rawi++];
  171.         KnL[KnLi]  = (raw0 & 0x00fc0000) <<   6;
  172.         KnL[KnLi] |= (raw0 & 0x00000fc0) <<  10;
  173.         KnL[KnLi] |= (raw1 & 0x00fc0000) >>> 10;
  174.         KnL[KnLi] |= (raw1 & 0x00000fc0) >>>  6;
  175.         ++KnLi;
  176.         KnL[KnLi]  = (raw0 & 0x0003f000) <<  12;
  177.         KnL[KnLi] |= (raw0 & 0x0000003f) <<  16;
  178.         KnL[KnLi] |= (raw1 & 0x0003f000) >>>  4;
  179.         KnL[KnLi] |= (raw1 & 0x0000003f);
  180.         ++KnLi;
  181.         }
  182.     }
  183.  
  184.  
  185.     // Block encryption routines.
  186.  
  187.     private int[] tempInts = new int[2];
  188.  
  189.     /// Encrypt a block of eight bytes.
  190.     public void encrypt( byte[] clearText, int clearOff, byte[] cipherText, int cipherOff )
  191.     {
  192.     squashBytesToInts( clearText, clearOff, tempInts, 0, 2 );
  193.     des( tempInts, tempInts, encryptKeys );
  194.     spreadIntsToBytes( tempInts, 0, cipherText, cipherOff, 2 );
  195.     }
  196.  
  197.     /// Decrypt a block of eight bytes.
  198.     public void decrypt( byte[] cipherText, int cipherOff, byte[] clearText, int clearOff )
  199.     {
  200.     squashBytesToInts( cipherText, cipherOff, tempInts, 0, 2 );
  201.     des( tempInts, tempInts, decryptKeys );
  202.     spreadIntsToBytes( tempInts, 0, clearText, clearOff, 2 );
  203.     }
  204.  
  205.     // The DES function.
  206.     private void des( int[] inInts, int[] outInts, int[] keys )
  207.     {
  208.     int fval, work, right, leftt;
  209.     int round;
  210.     int keysi = 0;
  211.  
  212.     leftt = inInts[0];
  213.     right = inInts[1];
  214.  
  215.     work   = ((leftt >>>  4) ^ right) & 0x0f0f0f0f;
  216.     right ^= work;
  217.     leftt ^= (work << 4);
  218.  
  219.     work   = ((leftt >>> 16) ^ right) & 0x0000ffff;
  220.     right ^= work;
  221.     leftt ^= (work << 16);
  222.  
  223.     work   = ((right >>>  2) ^ leftt) & 0x33333333;
  224.     leftt ^= work;
  225.     right ^= (work << 2);
  226.  
  227.     work   = ((right >>>  8) ^ leftt) & 0x00ff00ff;
  228.     leftt ^= work;
  229.     right ^= (work << 8);
  230.     right  = (right << 1) | ((right >>> 31) & 1);
  231.  
  232.     work   = (leftt ^ right) & 0xaaaaaaaa;
  233.     leftt ^= work;
  234.     right ^= work;
  235.     leftt  = (leftt << 1) | ((leftt >>> 31) & 1);
  236.  
  237.     for ( round = 0; round < 8; ++round )
  238.         {
  239.         work   = (right << 28) | (right >>> 4);
  240.         work  ^= keys[keysi++];
  241.         fval   = SP7[ work           & 0x0000003f ];
  242.         fval  |= SP5[(work >>>  8) & 0x0000003f ];
  243.         fval  |= SP3[(work >>> 16) & 0x0000003f ];
  244.         fval  |= SP1[(work >>> 24) & 0x0000003f ];
  245.         work   = right ^ keys[keysi++];
  246.         fval  |= SP8[ work         & 0x0000003f ];
  247.         fval  |= SP6[(work >>>  8) & 0x0000003f ];
  248.         fval  |= SP4[(work >>> 16) & 0x0000003f ];
  249.         fval  |= SP2[(work >>> 24) & 0x0000003f ];
  250.         leftt ^= fval;
  251.         work   = (leftt << 28) | (leftt >>> 4);
  252.         work  ^= keys[keysi++];
  253.         fval   = SP7[ work           & 0x0000003f ];
  254.         fval  |= SP5[(work >>>  8) & 0x0000003f ];
  255.         fval  |= SP3[(work >>> 16) & 0x0000003f ];
  256.         fval  |= SP1[(work >>> 24) & 0x0000003f ];
  257.         work   = leftt ^ keys[keysi++];
  258.         fval  |= SP8[ work           & 0x0000003f ];
  259.         fval  |= SP6[(work >>>  8) & 0x0000003f ];
  260.         fval  |= SP4[(work >>> 16) & 0x0000003f ];
  261.         fval  |= SP2[(work >>> 24) & 0x0000003f ];
  262.         right ^= fval;
  263.         }
  264.  
  265.     right  = (right << 31) | (right >>> 1);
  266.     work   = (leftt ^ right) & 0xaaaaaaaa;
  267.     leftt ^= work;
  268.     right ^= work;
  269.     leftt  = (leftt << 31) | (leftt >>> 1);
  270.     work   = ((leftt >>>  8) ^ right) & 0x00ff00ff;
  271.     right ^= work;
  272.     leftt ^= (work << 8);
  273.     work   = ((leftt >>>  2) ^ right) & 0x33333333;
  274.     right ^= work;
  275.     leftt ^= (work << 2);
  276.     work   = ((right >>> 16) ^ leftt) & 0x0000ffff;
  277.     leftt ^= work;
  278.     right ^= (work << 16);
  279.     work   = ((right >>>  4) ^ leftt) & 0x0f0f0f0f;
  280.     leftt ^= work;
  281.     right ^= (work << 4);
  282.     outInts[0] = right;
  283.     outInts[1] = leftt;
  284.     }
  285.  
  286.  
  287.     // Tables, permutations, S-boxes, etc.
  288.  
  289.     private static byte[] bytebit = {
  290.     (byte)0x01, (byte)0x02, (byte)0x04, (byte)0x08,
  291.     (byte)0x10, (byte)0x20, (byte)0x40, (byte)0x80
  292.     };
  293.     private static int[] bigbyte = {
  294.     0x800000, 0x400000, 0x200000, 0x100000,
  295.     0x080000, 0x040000, 0x020000, 0x010000,
  296.     0x008000, 0x004000, 0x002000, 0x001000,
  297.     0x000800, 0x000400, 0x000200, 0x000100,
  298.     0x000080, 0x000040, 0x000020, 0x000010,
  299.     0x000008, 0x000004, 0x000002, 0x000001
  300.     };
  301.     private static byte[] pc1 = {
  302.          (byte)56, (byte)48, (byte)40, (byte)32, (byte)24, (byte)16, (byte) 8,
  303.       (byte) 0, (byte)57, (byte)49, (byte)41, (byte)33, (byte)25, (byte)17,
  304.      (byte) 9, (byte) 1, (byte)58, (byte)50, (byte)42, (byte)34, (byte)26,
  305.       (byte)18, (byte)10, (byte) 2, (byte)59, (byte)51, (byte)43, (byte)35,
  306.      (byte)62, (byte)54, (byte)46, (byte)38, (byte)30, (byte)22, (byte)14,
  307.       (byte) 6, (byte)61, (byte)53, (byte)45, (byte)37, (byte)29, (byte)21,
  308.      (byte)13, (byte) 5, (byte)60, (byte)52, (byte)44, (byte)36, (byte)28,
  309.       (byte)20, (byte)12, (byte) 4, (byte)27, (byte)19, (byte)11, (byte)3
  310.     };
  311.     private static int[] totrot = {
  312.         1, 2, 4, 6, 8, 10, 12, 14, 15, 17, 19, 21, 23, 25, 27, 28
  313.     };
  314.  
  315.     private static byte[] pc2 = {
  316.     (byte)13, (byte)16, (byte)10, (byte)23, (byte) 0, (byte) 4,
  317.               (byte) 2, (byte)27, (byte)14, (byte) 5, (byte)20, (byte) 9,
  318.     (byte)22, (byte)18, (byte)11, (byte)3 , (byte)25, (byte) 7,
  319.               (byte)15, (byte) 6, (byte)26, (byte)19, (byte)12, (byte) 1,
  320.     (byte)40, (byte)51, (byte)30, (byte)36, (byte)46, (byte)54,
  321.               (byte)29, (byte)39, (byte)50, (byte)44, (byte)32, (byte)47,
  322.     (byte)43, (byte)48, (byte)38, (byte)55, (byte)33, (byte)52,
  323.               (byte)45, (byte)41, (byte)49, (byte)35, (byte)28, (byte)31,
  324.     };
  325.  
  326.     private static int[] SP1 = {
  327.         0x01010400, 0x00000000, 0x00010000, 0x01010404,
  328.     0x01010004, 0x00010404, 0x00000004, 0x00010000,
  329.     0x00000400, 0x01010400, 0x01010404, 0x00000400,
  330.     0x01000404, 0x01010004, 0x01000000, 0x00000004,
  331.     0x00000404, 0x01000400, 0x01000400, 0x00010400,
  332.     0x00010400, 0x01010000, 0x01010000, 0x01000404,
  333.     0x00010004, 0x01000004, 0x01000004, 0x00010004,
  334.     0x00000000, 0x00000404, 0x00010404, 0x01000000,
  335.     0x00010000, 0x01010404, 0x00000004, 0x01010000,
  336.     0x01010400, 0x01000000, 0x01000000, 0x00000400,
  337.     0x01010004, 0x00010000, 0x00010400, 0x01000004,
  338.     0x00000400, 0x00000004, 0x01000404, 0x00010404,
  339.     0x01010404, 0x00010004, 0x01010000, 0x01000404,
  340.     0x01000004, 0x00000404, 0x00010404, 0x01010400,
  341.     0x00000404, 0x01000400, 0x01000400, 0x00000000,
  342.     0x00010004, 0x00010400, 0x00000000, 0x01010004
  343.     };
  344.     private static int[] SP2 = {
  345.     0x80108020, 0x80008000, 0x00008000, 0x00108020,
  346.     0x00100000, 0x00000020, 0x80100020, 0x80008020,
  347.     0x80000020, 0x80108020, 0x80108000, 0x80000000,
  348.     0x80008000, 0x00100000, 0x00000020, 0x80100020,
  349.     0x00108000, 0x00100020, 0x80008020, 0x00000000,
  350.     0x80000000, 0x00008000, 0x00108020, 0x80100000,
  351.     0x00100020, 0x80000020, 0x00000000, 0x00108000,
  352.     0x00008020, 0x80108000, 0x80100000, 0x00008020,
  353.     0x00000000, 0x00108020, 0x80100020, 0x00100000,
  354.     0x80008020, 0x80100000, 0x80108000, 0x00008000,
  355.     0x80100000, 0x80008000, 0x00000020, 0x80108020,
  356.     0x00108020, 0x00000020, 0x00008000, 0x80000000,
  357.     0x00008020, 0x80108000, 0x00100000, 0x80000020,
  358.     0x00100020, 0x80008020, 0x80000020, 0x00100020,
  359.     0x00108000, 0x00000000, 0x80008000, 0x00008020,
  360.     0x80000000, 0x80100020, 0x80108020, 0x00108000
  361.     };
  362.     private static int[] SP3 = {
  363.     0x00000208, 0x08020200, 0x00000000, 0x08020008,
  364.     0x08000200, 0x00000000, 0x00020208, 0x08000200,
  365.     0x00020008, 0x08000008, 0x08000008, 0x00020000,
  366.     0x08020208, 0x00020008, 0x08020000, 0x00000208,
  367.     0x08000000, 0x00000008, 0x08020200, 0x00000200,
  368.     0x00020200, 0x08020000, 0x08020008, 0x00020208,
  369.     0x08000208, 0x00020200, 0x00020000, 0x08000208,
  370.     0x00000008, 0x08020208, 0x00000200, 0x08000000,
  371.     0x08020200, 0x08000000, 0x00020008, 0x00000208,
  372.     0x00020000, 0x08020200, 0x08000200, 0x00000000,
  373.     0x00000200, 0x00020008, 0x08020208, 0x08000200,
  374.     0x08000008, 0x00000200, 0x00000000, 0x08020008,
  375.     0x08000208, 0x00020000, 0x08000000, 0x08020208,
  376.     0x00000008, 0x00020208, 0x00020200, 0x08000008,
  377.     0x08020000, 0x08000208, 0x00000208, 0x08020000,
  378.     0x00020208, 0x00000008, 0x08020008, 0x00020200
  379.     };
  380.     private static int[] SP4 = {
  381.     0x00802001, 0x00002081, 0x00002081, 0x00000080,
  382.     0x00802080, 0x00800081, 0x00800001, 0x00002001,
  383.     0x00000000, 0x00802000, 0x00802000, 0x00802081,
  384.     0x00000081, 0x00000000, 0x00800080, 0x00800001,
  385.     0x00000001, 0x00002000, 0x00800000, 0x00802001,
  386.     0x00000080, 0x00800000, 0x00002001, 0x00002080,
  387.     0x00800081, 0x00000001, 0x00002080, 0x00800080,
  388.     0x00002000, 0x00802080, 0x00802081, 0x00000081,
  389.     0x00800080, 0x00800001, 0x00802000, 0x00802081,
  390.     0x00000081, 0x00000000, 0x00000000, 0x00802000,
  391.     0x00002080, 0x00800080, 0x00800081, 0x00000001,
  392.     0x00802001, 0x00002081, 0x00002081, 0x00000080,
  393.     0x00802081, 0x00000081, 0x00000001, 0x00002000,
  394.     0x00800001, 0x00002001, 0x00802080, 0x00800081,
  395.     0x00002001, 0x00002080, 0x00800000, 0x00802001,
  396.     0x00000080, 0x00800000, 0x00002000, 0x00802080
  397.     };
  398.     private static int[] SP5 = {
  399.     0x00000100, 0x02080100, 0x02080000, 0x42000100,
  400.     0x00080000, 0x00000100, 0x40000000, 0x02080000,
  401.     0x40080100, 0x00080000, 0x02000100, 0x40080100,
  402.     0x42000100, 0x42080000, 0x00080100, 0x40000000,
  403.     0x02000000, 0x40080000, 0x40080000, 0x00000000,
  404.     0x40000100, 0x42080100, 0x42080100, 0x02000100,
  405.     0x42080000, 0x40000100, 0x00000000, 0x42000000,
  406.     0x02080100, 0x02000000, 0x42000000, 0x00080100,
  407.     0x00080000, 0x42000100, 0x00000100, 0x02000000,
  408.     0x40000000, 0x02080000, 0x42000100, 0x40080100,
  409.     0x02000100, 0x40000000, 0x42080000, 0x02080100,
  410.     0x40080100, 0x00000100, 0x02000000, 0x42080000,
  411.     0x42080100, 0x00080100, 0x42000000, 0x42080100,
  412.     0x02080000, 0x00000000, 0x40080000, 0x42000000,
  413.     0x00080100, 0x02000100, 0x40000100, 0x00080000,
  414.     0x00000000, 0x40080000, 0x02080100, 0x40000100
  415.     };
  416.     private static int[] SP6 = {
  417.     0x20000010, 0x20400000, 0x00004000, 0x20404010,
  418.     0x20400000, 0x00000010, 0x20404010, 0x00400000,
  419.     0x20004000, 0x00404010, 0x00400000, 0x20000010,
  420.     0x00400010, 0x20004000, 0x20000000, 0x00004010,
  421.     0x00000000, 0x00400010, 0x20004010, 0x00004000,
  422.     0x00404000, 0x20004010, 0x00000010, 0x20400010,
  423.     0x20400010, 0x00000000, 0x00404010, 0x20404000,
  424.     0x00004010, 0x00404000, 0x20404000, 0x20000000,
  425.     0x20004000, 0x00000010, 0x20400010, 0x00404000,
  426.     0x20404010, 0x00400000, 0x00004010, 0x20000010,
  427.     0x00400000, 0x20004000, 0x20000000, 0x00004010,
  428.     0x20000010, 0x20404010, 0x00404000, 0x20400000,
  429.     0x00404010, 0x20404000, 0x00000000, 0x20400010,
  430.     0x00000010, 0x00004000, 0x20400000, 0x00404010,
  431.     0x00004000, 0x00400010, 0x20004010, 0x00000000,
  432.     0x20404000, 0x20000000, 0x00400010, 0x20004010
  433.     };
  434.     private static int[] SP7 = {
  435.     0x00200000, 0x04200002, 0x04000802, 0x00000000,
  436.     0x00000800, 0x04000802, 0x00200802, 0x04200800,
  437.     0x04200802, 0x00200000, 0x00000000, 0x04000002,
  438.     0x00000002, 0x04000000, 0x04200002, 0x00000802,
  439.     0x04000800, 0x00200802, 0x00200002, 0x04000800,
  440.     0x04000002, 0x04200000, 0x04200800, 0x00200002,
  441.     0x04200000, 0x00000800, 0x00000802, 0x04200802,
  442.     0x00200800, 0x00000002, 0x04000000, 0x00200800,
  443.     0x04000000, 0x00200800, 0x00200000, 0x04000802,
  444.     0x04000802, 0x04200002, 0x04200002, 0x00000002,
  445.     0x00200002, 0x04000000, 0x04000800, 0x00200000,
  446.     0x04200800, 0x00000802, 0x00200802, 0x04200800,
  447.     0x00000802, 0x04000002, 0x04200802, 0x04200000,
  448.     0x00200800, 0x00000000, 0x00000002, 0x04200802,
  449.     0x00000000, 0x00200802, 0x04200000, 0x00000800,
  450.     0x04000002, 0x04000800, 0x00000800, 0x00200002
  451.     };
  452.     private static int[] SP8 = {
  453.     0x10001040, 0x00001000, 0x00040000, 0x10041040,
  454.     0x10000000, 0x10001040, 0x00000040, 0x10000000,
  455.     0x00040040, 0x10040000, 0x10041040, 0x00041000,
  456.     0x10041000, 0x00041040, 0x00001000, 0x00000040,
  457.     0x10040000, 0x10000040, 0x10001000, 0x00001040,
  458.     0x00041000, 0x00040040, 0x10040040, 0x10041000,
  459.     0x00001040, 0x00000000, 0x00000000, 0x10040040,
  460.     0x10000040, 0x10001000, 0x00041040, 0x00040000,
  461.     0x00041040, 0x00040000, 0x10041000, 0x00001000,
  462.     0x00000040, 0x10040040, 0x00001000, 0x00041040,
  463.     0x10001000, 0x00000040, 0x10000040, 0x10040000,
  464.     0x10040040, 0x10000000, 0x00040000, 0x10001040,
  465.     0x00000000, 0x10041040, 0x00040040, 0x10000040,
  466.     0x10040000, 0x10001000, 0x10001040, 0x00000000,
  467.     0x10041040, 0x00041000, 0x00041000, 0x00001040,
  468.     0x00001040, 0x00040040, 0x10000000, 0x10041000
  469.     };
  470.  
  471.     // Routines taken from other parts of the Acme utilities.
  472.  
  473.     /// Squash bytes down to ints.
  474.     public static void squashBytesToInts( byte[] inBytes, int inOff, int[] outInts, int outOff, int intLen )
  475.         {
  476.     for ( int i = 0; i < intLen; ++i )
  477.         outInts[outOff + i] = 
  478.         ( ( inBytes[inOff + i * 4    ] & 0xff ) << 24 ) |
  479.         ( ( inBytes[inOff + i * 4 + 1] & 0xff ) << 16 ) |
  480.         ( ( inBytes[inOff + i * 4 + 2] & 0xff ) <<  8 ) |
  481.           ( inBytes[inOff + i * 4 + 3] & 0xff );
  482.         }
  483.  
  484.     /// Spread ints into bytes.
  485.     public static void spreadIntsToBytes( int[] inInts, int inOff, byte[] outBytes, int outOff, int intLen )
  486.         {
  487.     for ( int i = 0; i < intLen; ++i )
  488.         {
  489.         outBytes[outOff + i * 4    ] = (byte) ( inInts[inOff + i] >>> 24 );
  490.         outBytes[outOff + i * 4 + 1] = (byte) ( inInts[inOff + i] >>> 16 );
  491.         outBytes[outOff + i * 4 + 2] = (byte) ( inInts[inOff + i] >>>  8 );
  492.         outBytes[outOff + i * 4 + 3] = (byte)   inInts[inOff + i];
  493.         }
  494.         }
  495.     }
  496.