KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > pdfbox > encryption > ARCFour


1 /**
2  * Copyright (c) 2003, www.pdfbox.org
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright notice,
9  * this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright notice,
11  * this list of conditions and the following disclaimer in the documentation
12  * and/or other materials provided with the distribution.
13  * 3. Neither the name of pdfbox; nor the names of its
14  * contributors may be used to endorse or promote products derived from this
15  * software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
18  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20  * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY
21  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
22  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
23  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
24  * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
26  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  *
28  * http://www.pdfbox.org
29  *
30  */

31 package org.pdfbox.encryption;
32
33 import java.io.IOException JavaDoc;
34 import java.io.InputStream JavaDoc;
35 import java.io.OutputStream JavaDoc;
36
37 /**
38  * This class is an implementation of the alleged RC4 algorithm.
39  *
40  * @author <a HREF="mailto:ben@benlitchfield.com">Ben Litchfield</a>
41  * @version $Revision: 1.8 $
42  */

43 public class ARCFour
44 {
45     private int[] salt;
46     private int b;
47     private int c;
48
49     /**
50      * Constructor.
51      *
52      */

53     public ARCFour()
54     {
55         salt = new int[256];
56     }
57
58     /**
59      * This will reset the key to be used.
60      *
61      * @param key The RC4 key used during encryption.
62     */

63     public void setKey( byte[] key )
64     {
65         b = 0;
66         c = 0;
67
68         if(key.length < 1 || key.length > 32)
69         {
70             throw new IllegalArgumentException JavaDoc("number of bytes must be between 1 and 32");
71         }
72         for(int i = 0; i < salt.length; i++)
73         {
74             salt[i] = i;
75         }
76
77         int keyIndex = 0;
78         int saltIndex = 0;
79         for( int i = 0; i < salt.length; i++)
80         {
81             saltIndex = (fixByte(key[keyIndex]) + salt[i] + saltIndex) % 256;
82             swap( salt, i, saltIndex );
83             keyIndex = (keyIndex + 1) % key.length;
84         }
85
86     }
87
88     /**
89      * Thie will ensure that the value for a byte >=0.
90      *
91      * @param aByte The byte to test against.
92      *
93      * @return A value >=0 and < 256
94      */

95     private static final int fixByte( byte aByte )
96     {
97         return aByte < 0 ? 256 + aByte : aByte;
98     }
99
100     /**
101      * This will swap two values in an array.
102      *
103      * @param data The array to swap from.
104      * @param firstIndex The index of the first element to swap.
105      * @param secondIndex The index of the second element to swap.
106      */

107     private static final void swap( int[] data, int firstIndex, int secondIndex )
108     {
109         int tmp = data[ firstIndex ];
110         data[ firstIndex ] = data[ secondIndex ];
111         data[ secondIndex ] = tmp;
112     }
113
114     /**
115      * This will encrypt and write the next byte.
116      *
117      * @param aByte The byte to encrypt.
118      * @param output The stream to write to.
119      *
120      * @throws IOException If there is an error writing to the output stream.
121      */

122     public void write( byte aByte, OutputStream JavaDoc output ) throws IOException JavaDoc
123     {
124         b = (b + 1) % 256;
125         c = (salt[b] + c) % 256;
126         swap( salt, b, c );
127         int saltIndex = (salt[b] + salt[c]) % 256;
128         output.write(aByte ^ (byte)salt[saltIndex]);
129     }
130
131     /**
132      * This will encrypt and write the data.
133      *
134      * @param data The data to encrypt.
135      * @param output The stream to write to.
136      *
137      * @throws IOException If there is an error writing to the output stream.
138      */

139     public void write( byte[] data, OutputStream JavaDoc output ) throws IOException JavaDoc
140     {
141         for( int i = 0; i < data.length; i++ )
142         {
143             write( data[i], output );
144         }
145     }
146
147     /**
148      * This will encrypt and write the data.
149      *
150      * @param data The data to encrypt.
151      * @param output The stream to write to.
152      *
153      * @throws IOException If there is an error writing to the output stream.
154      */

155     public void write( InputStream JavaDoc data, OutputStream JavaDoc output ) throws IOException JavaDoc
156     {
157         byte[] buffer = new byte[1024];
158         int amountRead = 0;
159         while( (amountRead = data.read( buffer )) != -1 )
160         {
161             write( buffer, 0, amountRead, output );
162         }
163     }
164
165     /**
166      * This will encrypt and write the data.
167      *
168      * @param data The data to encrypt.
169      * @param offset The offset into the array to start reading data from.
170      * @param len The number of bytes to attempt to read.
171      * @param output The stream to write to.
172      *
173      * @throws IOException If there is an error writing to the output stream.
174      */

175     public void write( byte[] data, int offset, int len, OutputStream JavaDoc output) throws IOException JavaDoc
176     {
177         for( int i = offset; i < offset + len; i++ )
178         {
179             write( data[i], output );
180         }
181     }
182 }
Popular Tags