source: trunk/gcc/libjava/java/security/MessageDigest.java

Last change on this file was 1392, checked in by bird, 21 years ago

This commit was generated by cvs2svn to compensate for changes in r1391,
which included commits to RCS files with non-trunk default branches.

  • Property cvs2svn:cvs-rev set to 1.1.1.2
  • Property svn:eol-style set to native
  • Property svn:executable set to *
File size: 10.2 KB
Line 
1
2/* MessageDigest.java --- The message digest interface.
3 Copyright (C) 1999, 2002 Free Software Foundation, Inc.
4
5This file is part of GNU Classpath.
6
7GNU Classpath is free software; you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 2, or (at your option)
10any later version.
11
12GNU Classpath is distributed in the hope that it will be useful, but
13WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with GNU Classpath; see the file COPYING. If not, write to the
19Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
2002111-1307 USA.
21
22Linking this library statically or dynamically with other modules is
23making a combined work based on this library. Thus, the terms and
24conditions of the GNU General Public License cover the whole
25combination.
26
27As a special exception, the copyright holders of this library give you
28permission to link this library with independent modules to produce an
29executable, regardless of the license terms of these independent
30modules, and to copy and distribute the resulting executable under
31terms of your choice, provided that you also meet, for each linked
32independent module, the terms and conditions of the license of that
33module. An independent module is a module which is not derived from
34or based on this library. If you modify this library, you may extend
35this exception to your version of the library, but you are not
36obligated to do so. If you do not wish to do so, delete this
37exception statement from your version. */
38
39package java.security;
40
41public abstract class MessageDigest extends MessageDigestSpi
42{
43 private String algorithm;
44 Provider provider;
45 private byte[] lastDigest;
46
47 /**
48 Creates a MessageDigest representing the specified
49 algorithm.
50
51 @param algorithm the name of digest algorithm to choose
52 */
53 protected MessageDigest(String algorithm)
54 {
55 this.algorithm = algorithm;
56 provider = null;
57 }
58
59 /**
60 Gets an instance of the MessageDigest class representing
61 the specified digest. If the algorithm is not found then,
62 it throws NoSuchAlgorithmException.
63
64 @param algorithm the name of digest algorithm to choose
65 @return a MessageDigest representing the desired algorithm
66
67 @exception NoSuchAlgorithmException if the algorithm is not implemented by
68 providers
69 */
70 public static MessageDigest getInstance(String algorithm)
71 throws NoSuchAlgorithmException
72 {
73 Provider[] p = Security.getProviders();
74 for (int i = 0; i < p.length; i++)
75 {
76 try
77 {
78 return getInstance(algorithm, p[i]);
79 }
80 catch (NoSuchAlgorithmException ignored) {}
81 }
82
83 throw new NoSuchAlgorithmException(algorithm);
84 }
85
86 /**
87 Gets an instance of the MessageDigest class representing
88 the specified digest from the specified provider. If the
89 algorithm is not found then, it throws NoSuchAlgorithmException.
90 If the provider is not found, then it throws
91 NoSuchProviderException.
92
93 @param algorithm the name of digest algorithm to choose
94 @param provider the name of the provider to find the algorithm in
95 @return a MessageDigest representing the desired algorithm
96
97 @exception NoSuchAlgorithmException if the algorithm is not implemented by
98 the provider
99 @exception NoSuchProviderException if the provider is not found
100 */
101
102 public static MessageDigest getInstance(String algorithm, String provider)
103 throws NoSuchAlgorithmException, NoSuchProviderException
104 {
105 Provider p = Security.getProvider(provider);
106
107 if (p == null)
108 throw new NoSuchProviderException(provider);
109
110 return getInstance(algorithm, p);
111 }
112
113 private static MessageDigest getInstance(String algorithm, Provider p)
114 throws NoSuchAlgorithmException
115 {
116 // try the name as is
117 String className = p.getProperty("MessageDigest." + algorithm);
118 if (className == null) { // try all uppercase
119 String upper = algorithm.toUpperCase();
120 className = p.getProperty("MessageDigest." + upper);
121 if (className == null) { // try if it's an alias
122 String alias = p.getProperty("Alg.Alias.MessageDigest." +algorithm);
123 if (alias == null) { // try all-uppercase alias name
124 alias = p.getProperty("Alg.Alias.MessageDigest." +upper);
125 if (alias == null) { // spit the dummy
126 throw new NoSuchAlgorithmException(algorithm);
127 }
128 }
129 className = p.getProperty("MessageDigest." + alias);
130 if (className == null) {
131 throw new NoSuchAlgorithmException(algorithm);
132 }
133 }
134 }
135 return getInstance(className, algorithm, p);
136 }
137
138 private static MessageDigest getInstance(String classname,
139 String algorithm,
140 Provider provider)
141 throws NoSuchAlgorithmException
142 {
143 if (classname == null)
144 throw new NoSuchAlgorithmException(algorithm);
145
146 MessageDigest result = null;
147 try
148 {
149 Object obj = Class.forName(classname).newInstance();
150 if (obj instanceof MessageDigest) {
151 result = (MessageDigest) obj;
152 result.algorithm = algorithm;
153 } else if (obj instanceof MessageDigestSpi) {
154 result = new DummyMessageDigest((MessageDigestSpi) obj, algorithm);
155 } else {
156 throw new ClassCastException("Class "+classname+" from Provider "
157 +provider.getName()
158 +" does not extend java.security.MessageDigestSpi");
159 }
160 result.provider = provider;
161 return result;
162 }
163 catch (ClassNotFoundException cnfe)
164 {
165 throw new NoSuchAlgorithmException(algorithm + ": Class not found.");
166 }
167 catch (InstantiationException ie)
168 {
169 throw new NoSuchAlgorithmException(algorithm
170 + ": Class instantiation failed.");
171 }
172 catch (IllegalAccessException iae)
173 {
174 throw new NoSuchAlgorithmException(algorithm + ": Illegal Access");
175 }
176 }
177
178
179 /**
180 Gets the provider that the MessageDigest is from.
181
182 @return the provider the this MessageDigest
183 */
184 public final Provider getProvider()
185 {
186 return provider;
187 }
188
189 /**
190 Updates the digest with the byte.
191
192 @param input byte to update the digest with
193 */
194 public void update(byte input)
195 {
196 engineUpdate(input);
197 }
198
199 /**
200 Updates the digest with the bytes from the array from the
201 specified offset to the specified length.
202
203 @param input bytes to update the digest with
204 @param offset the offset to start at
205 @param len length of the data to update with
206 */
207 public void update(byte[]input, int offset, int len)
208 {
209 engineUpdate(input, offset, len);
210 }
211
212 /**
213 Updates the digest with the bytes from the array.
214
215 @param input bytes to update the digest with
216 */
217 public void update(byte[]input)
218 {
219 engineUpdate(input, 0, input.length);
220 }
221
222 /**
223 Computes the digest of the stored data.
224
225 @return a byte array representing the message digest
226 */
227 public byte[] digest()
228 {
229 return lastDigest = engineDigest();
230 }
231
232 /**
233 Computes the final digest of the stored bytes and returns
234 them.
235
236 @param buf An array of bytes to store the digest
237 @param offset An offset to start storing the digest at
238 @param len The length of the buffer
239 @return Returns the length of the buffer
240 */
241 public int digest(byte[]buf, int offset, int len) throws DigestException
242 {
243 return engineDigest(buf, offset, len);
244 }
245
246 /**
247 Computes a final update using the input array of bytes,
248 then computes a final digest and returns it. It calls
249 update(input) and then digest();
250
251 @param input An array of bytes to perform final update with
252 @return a byte array representing the message digest
253 */
254 public byte[] digest(byte[]input)
255 {
256 update(input);
257 return digest();
258 }
259
260 /**
261 Returns a representation of the MessageDigest as a String.
262
263 @return a string representing the message digest
264 */
265 public String toString()
266 {
267 return (getClass()).getName()
268 + " Message Digest <" + digestToString() + ">";
269 }
270
271 /**
272 Does a simple byte comparison of the two digests.
273
274 @param digesta first digest to compare
275 @param digestb second digest to compare
276 @return true if they are equal, false otherwise
277 */
278 public static boolean isEqual(byte[]digesta, byte[]digestb)
279 {
280 if (digesta.length != digestb.length)
281 return false;
282
283 for (int i = digesta.length - 1; i >= 0; --i)
284 if (digesta[i] != digestb[i])
285 return false;
286
287 return true;
288 }
289
290
291 /**
292 Resets the message digest.
293 */
294 public void reset()
295 {
296 engineReset();
297 }
298
299 /**
300 Gets the name of the algorithm currently used.
301 The names of algorithms are usually SHA-1 or MD5.
302
303 @return name of algorithm.
304 */
305 public final String getAlgorithm()
306 {
307 return algorithm;
308 }
309
310 /**
311 Gets the length of the message digest.
312 The default is zero which means that this message digest
313 does not implement this function.
314
315 @return length of the message digest
316 */
317 public final int getDigestLength()
318 {
319 return engineGetDigestLength();
320 }
321
322 /**
323 Returns a clone of this class if supported.
324 If it does not then it throws CloneNotSupportedException.
325 The cloning of this class depends on whether the subclass
326 MessageDigestSpi implements Cloneable which contains the
327 actual implementation of the appropriate algorithm.
328
329 @return clone of this class
330
331 @exception CloneNotSupportedException this class does not support cloning
332 */
333 public Object clone() throws CloneNotSupportedException
334 {
335 if (this instanceof Cloneable)
336 return super.clone();
337 else
338 throw new CloneNotSupportedException();
339 }
340
341 private String digestToString()
342 {
343 byte[] digest = lastDigest;
344
345 if (digest == null)
346 return "incomplete";
347
348 StringBuffer buf = new StringBuffer();
349 int len = digest.length;
350 for (int i = 0; i < len; ++i)
351 {
352 byte b = digest[i];
353 byte high = (byte) ((b & 0xff) >>> 4);
354 byte low = (byte) (b & 0xf);
355
356 buf.append(high > 9 ? ('a' - 10) + high : '0' + high);
357 buf.append(low > 9 ? ('a' - 10) + low : '0' + low);
358 }
359
360 return buf.toString();
361 }
362
363}
Note: See TracBrowser for help on using the repository browser.