001    package org.apache.commons.ssl.asn1;
002    
003    import java.io.ByteArrayOutputStream;
004    import java.util.Vector;
005    
006    public final class Strings {
007        public static String fromUTF8ByteArray(byte[] bytes) {
008            int i = 0;
009            int length = 0;
010    
011            while (i < bytes.length) {
012                length++;
013                if ((bytes[i] & 0xf0) == 0xf0) {
014                    // surrogate pair
015                    length++;
016                    i += 4;
017                } else if ((bytes[i] & 0xe0) == 0xe0) {
018                    i += 3;
019                } else if ((bytes[i] & 0xc0) == 0xc0) {
020                    i += 2;
021                } else {
022                    i += 1;
023                }
024            }
025    
026            char[] cs = new char[length];
027    
028            i = 0;
029            length = 0;
030    
031            while (i < bytes.length) {
032                char ch;
033    
034                if ((bytes[i] & 0xf0) == 0xf0) {
035                    int codePoint = ((bytes[i] & 0x03) << 18) | ((bytes[i + 1] & 0x3F) << 12) | ((bytes[i + 2] & 0x3F) << 6) | (bytes[i + 3] & 0x3F);
036                    int U = codePoint - 0x10000;
037                    char W1 = (char) (0xD800 | (U >> 10));
038                    char W2 = (char) (0xDC00 | (U & 0x3FF));
039                    cs[length++] = W1;
040                    ch = W2;
041                    i += 4;
042                } else if ((bytes[i] & 0xe0) == 0xe0) {
043                    ch = (char) (((bytes[i] & 0x0f) << 12)
044                                 | ((bytes[i + 1] & 0x3f) << 6) | (bytes[i + 2] & 0x3f));
045                    i += 3;
046                } else if ((bytes[i] & 0xd0) == 0xd0) {
047                    ch = (char) (((bytes[i] & 0x1f) << 6) | (bytes[i + 1] & 0x3f));
048                    i += 2;
049                } else if ((bytes[i] & 0xc0) == 0xc0) {
050                    ch = (char) (((bytes[i] & 0x1f) << 6) | (bytes[i + 1] & 0x3f));
051                    i += 2;
052                } else {
053                    ch = (char) (bytes[i] & 0xff);
054                    i += 1;
055                }
056    
057                cs[length++] = ch;
058            }
059    
060            return new String(cs);
061        }
062    
063        public static byte[] toUTF8ByteArray(String string) {
064            ByteArrayOutputStream bOut = new ByteArrayOutputStream();
065            char[] c = string.toCharArray();
066            int i = 0;
067    
068            while (i < c.length) {
069                char ch = c[i];
070    
071                if (ch < 0x0080) {
072                    bOut.write(ch);
073                } else if (ch < 0x0800) {
074                    bOut.write(0xc0 | (ch >> 6));
075                    bOut.write(0x80 | (ch & 0x3f));
076                }
077                // surrogate pair
078                else if (ch >= 0xD800 && ch <= 0xDFFF) {
079                    // in error - can only happen, if the Java String class has a
080                    // bug.
081                    if (i + 1 >= c.length) {
082                        throw new IllegalStateException("invalid UTF-16 codepoint");
083                    }
084                    char W1 = ch;
085                    ch = c[++i];
086                    char W2 = ch;
087                    // in error - can only happen, if the Java String class has a
088                    // bug.
089                    if (W1 > 0xDBFF) {
090                        throw new IllegalStateException("invalid UTF-16 codepoint");
091                    }
092                    int codePoint = (((W1 & 0x03FF) << 10) | (W2 & 0x03FF)) + 0x10000;
093                    bOut.write(0xf0 | (codePoint >> 18));
094                    bOut.write(0x80 | ((codePoint >> 12) & 0x3F));
095                    bOut.write(0x80 | ((codePoint >> 6) & 0x3F));
096                    bOut.write(0x80 | (codePoint & 0x3F));
097                } else {
098                    bOut.write(0xe0 | (ch >> 12));
099                    bOut.write(0x80 | ((ch >> 6) & 0x3F));
100                    bOut.write(0x80 | (ch & 0x3F));
101                }
102    
103                i++;
104            }
105    
106            return bOut.toByteArray();
107        }
108    
109        /**
110         * A locale independent version of toUpperCase.
111         *
112         * @param string input to be converted
113         * @return a US Ascii uppercase version
114         */
115        public static String toUpperCase(String string) {
116            boolean changed = false;
117            char[] chars = string.toCharArray();
118    
119            for (int i = 0; i != chars.length; i++) {
120                char ch = chars[i];
121                if ('a' <= ch && 'z' >= ch) {
122                    changed = true;
123                    chars[i] = (char) (ch - 'a' + 'A');
124                }
125            }
126    
127            if (changed) {
128                return new String(chars);
129            }
130    
131            return string;
132        }
133    
134        /**
135         * A locale independent version of toLowerCase.
136         *
137         * @param string input to be converted
138         * @return a US ASCII lowercase version
139         */
140        public static String toLowerCase(String string) {
141            boolean changed = false;
142            char[] chars = string.toCharArray();
143    
144            for (int i = 0; i != chars.length; i++) {
145                char ch = chars[i];
146                if ('A' <= ch && 'Z' >= ch) {
147                    changed = true;
148                    chars[i] = (char) (ch - 'A' + 'a');
149                }
150            }
151    
152            if (changed) {
153                return new String(chars);
154            }
155    
156            return string;
157        }
158    
159        public static byte[] toByteArray(String string) {
160            byte[] bytes = new byte[string.length()];
161    
162            for (int i = 0; i != bytes.length; i++) {
163                char ch = string.charAt(i);
164    
165                bytes[i] = (byte) ch;
166            }
167    
168            return bytes;
169        }
170    
171        public static String[] split(String input, char delimiter) {
172            Vector v = new Vector();
173            boolean moreTokens = true;
174            String subString;
175    
176            while (moreTokens) {
177                int tokenLocation = input.indexOf(delimiter);
178                if (tokenLocation > 0) {
179                    subString = input.substring(0, tokenLocation);
180                    v.addElement(subString);
181                    input = input.substring(tokenLocation + 1);
182                } else {
183                    moreTokens = false;
184                    v.addElement(input);
185                }
186            }
187    
188            String[] res = new String[v.size()];
189    
190            for (int i = 0; i != res.length; i++) {
191                res[i] = (String) v.elementAt(i);
192            }
193            return res;
194        }
195    }