Remove old autovect-branch by moving to "dead" directory.
[official-gcc.git] / old-autovect-branch / libjava / java / nio / charset / Charset.java
blob14b6db83b0fd073dcd2514de855265e1eb55e919
1 /* Charset.java --
2 Copyright (C) 2002, 2004, 2005 Free Software Foundation, Inc.
4 This file is part of GNU Classpath.
6 GNU Classpath is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
11 GNU Classpath is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GNU Classpath; see the file COPYING. If not, write to the
18 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19 02110-1301 USA.
21 Linking this library statically or dynamically with other modules is
22 making a combined work based on this library. Thus, the terms and
23 conditions of the GNU General Public License cover the whole
24 combination.
26 As a special exception, the copyright holders of this library give you
27 permission to link this library with independent modules to produce an
28 executable, regardless of the license terms of these independent
29 modules, and to copy and distribute the resulting executable under
30 terms of your choice, provided that you also meet, for each linked
31 independent module, the terms and conditions of the license of that
32 module. An independent module is a module which is not derived from
33 or based on this library. If you modify this library, you may extend
34 this exception to your version of the library, but you are not
35 obligated to do so. If you do not wish to do so, delete this
36 exception statement from your version. */
39 package java.nio.charset;
41 import gnu.java.nio.charset.Provider;
43 import java.io.BufferedReader;
44 import java.io.InputStreamReader;
45 import java.net.URL;
46 import java.nio.ByteBuffer;
47 import java.nio.CharBuffer;
48 import java.nio.charset.spi.CharsetProvider;
49 import java.util.Collections;
50 import java.util.Enumeration;
51 import java.util.HashSet;
52 import java.util.Iterator;
53 import java.util.LinkedHashSet;
54 import java.util.Locale;
55 import java.util.Set;
56 import java.util.SortedMap;
57 import java.util.TreeMap;
59 /**
60 * @author Jesse Rosenstock
61 * @since 1.4
63 public abstract class Charset implements Comparable
65 private CharsetEncoder cachedEncoder;
66 private CharsetDecoder cachedDecoder;
68 /**
69 * Charset providers.
71 private static CharsetProvider[] providers;
73 private final String canonicalName;
74 private final String[] aliases;
76 protected Charset (String canonicalName, String[] aliases)
78 checkName (canonicalName);
79 if (aliases != null)
81 int n = aliases.length;
82 for (int i = 0; i < n; ++i)
83 checkName (aliases[i]);
86 cachedEncoder = null;
87 cachedDecoder = null;
88 this.canonicalName = canonicalName;
89 this.aliases = aliases;
92 /**
93 * @throws IllegalCharsetNameException if the name is illegal
95 private static void checkName (String name)
97 int n = name.length ();
99 if (n == 0)
100 throw new IllegalCharsetNameException (name);
102 char ch = name.charAt (0);
103 if (!(('A' <= ch && ch <= 'Z')
104 || ('a' <= ch && ch <= 'z')
105 || ('0' <= ch && ch <= '9')))
106 throw new IllegalCharsetNameException (name);
108 for (int i = 1; i < n; ++i)
110 ch = name.charAt (i);
111 if (!(('A' <= ch && ch <= 'Z')
112 || ('a' <= ch && ch <= 'z')
113 || ('0' <= ch && ch <= '9')
114 || ch == '-' || ch == '.' || ch == ':' || ch == '_'))
115 throw new IllegalCharsetNameException (name);
119 public static boolean isSupported (String charsetName)
121 return charsetForName (charsetName) != null;
125 * Returns the Charset instance for the charset of the given name.
127 * @param charsetName
128 * @return
129 * @throws UnsupportedCharsetException if this VM does not support
130 * the charset of the given name.
131 * @throws IllegalCharsetNameException if the given charset name is
132 * legal.
133 * @throws IllegalArgumentException if <code>charsetName</code> is null.
135 public static Charset forName (String charsetName)
137 // Throws IllegalArgumentException as the JDK does.
138 if(charsetName == null)
139 throw new IllegalArgumentException("Charset name must not be null.");
141 Charset cs = charsetForName (charsetName);
142 if (cs == null)
143 throw new UnsupportedCharsetException (charsetName);
144 return cs;
148 * Retrieves a charset for the given charset name.
150 * @return A charset object for the charset with the specified name, or
151 * <code>null</code> if no such charset exists.
153 * @throws IllegalCharsetNameException if the name is illegal
155 private static Charset charsetForName(String charsetName)
157 checkName (charsetName);
158 Charset cs = null;
159 CharsetProvider[] providers = providers2();
160 for (int i = 0; i < providers.length; i++)
162 cs = providers[i].charsetForName(charsetName);
163 if (cs != null)
164 break;
166 return cs;
169 public static SortedMap availableCharsets()
171 TreeMap charsets = new TreeMap(String.CASE_INSENSITIVE_ORDER);
173 CharsetProvider[] providers = providers2();
174 for (int j = 0; j < providers.length; j++)
176 for (Iterator i = providers[j].charsets(); i.hasNext(); )
178 Charset cs = (Charset) i.next();
179 charsets.put(cs.name(), cs);
183 return Collections.unmodifiableSortedMap(charsets);
186 private static CharsetProvider provider()
190 String s = System.getProperty("charset.provider");
191 if (s != null)
193 CharsetProvider p =
194 (CharsetProvider) ((Class.forName(s)).newInstance());
195 return p;
198 catch (Exception e)
200 // Ignore.
203 return Provider.provider();
207 * We need to support multiple providers, reading them from
208 * java.nio.charset.spi.CharsetProvider in the resource directory
209 * META-INF/services.
211 private static CharsetProvider[] providers2()
213 if (providers == null)
217 Enumeration en = ClassLoader.getSystemResources
218 ("META-INF/services/java.nio.charset.spi.CharsetProvider");
219 LinkedHashSet set = new LinkedHashSet();
220 set.add(provider());
221 while (en.hasMoreElements())
223 BufferedReader rdr = new BufferedReader(new InputStreamReader
224 (((URL) (en.nextElement())).openStream()));
225 while (true)
227 String s = rdr.readLine();
228 if (s == null)
229 break;
230 CharsetProvider p =
231 (CharsetProvider) ((Class.forName(s)).newInstance());
232 set.add(p);
236 providers = new CharsetProvider[set.size()];
237 set.toArray(providers);
239 catch (Exception e)
241 throw new RuntimeException(e);
244 return providers;
247 public final String name ()
249 return canonicalName;
252 public final Set aliases ()
254 if (aliases == null)
255 return Collections.EMPTY_SET;
257 // should we cache the aliasSet instead?
258 int n = aliases.length;
259 HashSet aliasSet = new HashSet (n);
260 for (int i = 0; i < n; ++i)
261 aliasSet.add (aliases[i]);
262 return Collections.unmodifiableSet (aliasSet);
265 public String displayName ()
267 return canonicalName;
270 public String displayName (Locale locale)
272 return canonicalName;
275 public final boolean isRegistered ()
277 return (!canonicalName.startsWith ("x-")
278 && !canonicalName.startsWith ("X-"));
281 public abstract boolean contains (Charset cs);
283 public abstract CharsetDecoder newDecoder ();
285 public abstract CharsetEncoder newEncoder ();
287 public boolean canEncode ()
289 return true;
292 // NB: This implementation serializes different threads calling
293 // Charset.encode(), a potential performance problem. It might
294 // be better to remove the cache, or use ThreadLocal to cache on
295 // a per-thread basis.
296 public final synchronized ByteBuffer encode (CharBuffer cb)
300 if (cachedEncoder == null)
302 cachedEncoder = newEncoder ()
303 .onMalformedInput (CodingErrorAction.REPLACE)
304 .onUnmappableCharacter (CodingErrorAction.REPLACE);
305 } else
306 cachedEncoder.reset();
307 return cachedEncoder.encode (cb);
309 catch (CharacterCodingException e)
311 throw new AssertionError (e);
315 public final ByteBuffer encode (String str)
317 return encode (CharBuffer.wrap (str));
320 // NB: This implementation serializes different threads calling
321 // Charset.decode(), a potential performance problem. It might
322 // be better to remove the cache, or use ThreadLocal to cache on
323 // a per-thread basis.
324 public final synchronized CharBuffer decode (ByteBuffer bb)
328 if (cachedDecoder == null)
330 cachedDecoder = newDecoder ()
331 .onMalformedInput (CodingErrorAction.REPLACE)
332 .onUnmappableCharacter (CodingErrorAction.REPLACE);
333 } else
334 cachedDecoder.reset();
336 return cachedDecoder.decode (bb);
338 catch (CharacterCodingException e)
340 throw new AssertionError (e);
344 public final int compareTo (Object ob)
346 return canonicalName.compareToIgnoreCase (((Charset) ob).canonicalName);
349 public final int hashCode ()
351 return canonicalName.hashCode ();
354 public final boolean equals (Object ob)
356 if (ob instanceof Charset)
357 return canonicalName.equalsIgnoreCase (((Charset) ob).canonicalName);
358 else
359 return false;
362 public final String toString ()
364 return canonicalName;