• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 package com.android.server.wifi.hotspot2;
2 
3 import com.android.server.wifi.anqp.Constants;
4 
5 import java.nio.ByteBuffer;
6 import java.util.ArrayList;
7 import java.util.Calendar;
8 import java.util.Collection;
9 import java.util.LinkedList;
10 import java.util.List;
11 import java.util.TimeZone;
12 
13 import static com.android.server.wifi.anqp.Constants.BYTE_MASK;
14 import static com.android.server.wifi.anqp.Constants.NIBBLE_MASK;
15 
16 public abstract class Utils {
17 
18     public static final long UNSET_TIME = -1;
19 
20     private static final int EUI48Length = 6;
21     private static final int EUI64Length = 8;
22     private static final long EUI48Mask = 0xffffffffffffL;
23     private static final String[] PLMNText = {"org", "3gppnetwork", "mcc*", "mnc*", "wlan" };
24 
hs2LogTag(Class c)25     public static String hs2LogTag(Class c) {
26         return "HS20";
27     }
28 
splitDomain(String domain)29     public static List<String> splitDomain(String domain) {
30 
31         if (domain.endsWith("."))
32             domain = domain.substring(0, domain.length() - 1);
33         int at = domain.indexOf('@');
34         if (at >= 0)
35             domain = domain.substring(at + 1);
36 
37         String[] labels = domain.toLowerCase().split("\\.");
38         LinkedList<String> labelList = new LinkedList<String>();
39         for (String label : labels) {
40             labelList.addFirst(label);
41         }
42 
43         return labelList;
44     }
45 
parseMac(String s)46     public static long parseMac(String s) {
47 
48         long mac = 0;
49         int count = 0;
50         for (int n = 0; n < s.length(); n++) {
51             int nibble = Utils.fromHex(s.charAt(n), true);  // Set lenient to not blow up on ':'
52             if (nibble >= 0) {                              // ... and use only legit hex.
53                 mac = (mac << 4) | nibble;
54                 count++;
55             }
56         }
57         if (count < 12 || (count&1) == 1) {
58             throw new IllegalArgumentException("Bad MAC address: '" + s + "'");
59         }
60         return mac;
61     }
62 
macToString(long mac)63     public static String macToString(long mac) {
64         int len = (mac & ~EUI48Mask) != 0 ? EUI64Length : EUI48Length;
65         StringBuilder sb = new StringBuilder();
66         boolean first = true;
67         for (int n = (len - 1)*Byte.SIZE; n >= 0; n -= Byte.SIZE) {
68             if (first) {
69                 first = false;
70             }
71             else {
72                 sb.append(':');
73             }
74             sb.append(String.format("%02x", (mac >>> n) & Constants.BYTE_MASK));
75         }
76         return sb.toString();
77     }
78 
getMccMnc(List<String> domain)79     public static String getMccMnc(List<String> domain) {
80         if (domain.size() != PLMNText.length) {
81             return null;
82         }
83 
84         for (int n = 0; n < PLMNText.length; n++ ) {
85             String expect = PLMNText[n];
86             int len = expect.endsWith("*") ? expect.length() - 1 : expect.length();
87             if (!domain.get(n).regionMatches(0, expect, 0, len)) {
88                 return null;
89             }
90         }
91 
92         String prefix = domain.get(2).substring(3) + domain.get(3).substring(3);
93         for (int n = 0; n < prefix.length(); n++) {
94             char ch = prefix.charAt(n);
95             if (ch < '0' || ch > '9') {
96                 return null;
97             }
98         }
99         return prefix;
100     }
101 
roamingConsortiumsToString(long[] ois)102     public static String roamingConsortiumsToString(long[] ois) {
103         if (ois == null) {
104             return "null";
105         }
106         List<Long> list = new ArrayList<Long>(ois.length);
107         for (long oi : ois) {
108             list.add(oi);
109         }
110         return roamingConsortiumsToString(list);
111     }
112 
roamingConsortiumsToString(Collection<Long> ois)113     public static String roamingConsortiumsToString(Collection<Long> ois) {
114         StringBuilder sb = new StringBuilder();
115         boolean first = true;
116         for (long oi : ois) {
117             if (first) {
118                 first = false;
119             } else {
120                 sb.append(", ");
121             }
122             if (Long.numberOfLeadingZeros(oi) > 40) {
123                 sb.append(String.format("%06x", oi));
124             } else {
125                 sb.append(String.format("%010x", oi));
126             }
127         }
128         return sb.toString();
129     }
130 
toUnicodeEscapedString(String s)131     public static String toUnicodeEscapedString(String s) {
132         StringBuilder sb = new StringBuilder(s.length());
133         for (int n = 0; n < s.length(); n++) {
134             char ch = s.charAt(n);
135             if (ch>= ' ' && ch < 127) {
136                 sb.append(ch);
137             }
138             else {
139                 sb.append("\\u").append(String.format("%04x", (int)ch));
140             }
141         }
142         return sb.toString();
143     }
144 
toHexString(byte[] data)145     public static String toHexString(byte[] data) {
146         if (data == null) {
147             return "null";
148         }
149         StringBuilder sb = new StringBuilder(data.length * 3);
150 
151         boolean first = true;
152         for (byte b : data) {
153             if (first) {
154                 first = false;
155             } else {
156                 sb.append(' ');
157             }
158             sb.append(String.format("%02x", b & BYTE_MASK));
159         }
160         return sb.toString();
161     }
162 
toHex(byte[] octets)163     public static String toHex(byte[] octets) {
164         StringBuilder sb = new StringBuilder(octets.length * 2);
165         for (byte o : octets) {
166             sb.append(String.format("%02x", o & BYTE_MASK));
167         }
168         return sb.toString();
169     }
170 
hexToBytes(String text)171     public static byte[] hexToBytes(String text) {
172         if ((text.length() & 1) == 1) {
173             throw new NumberFormatException("Odd length hex string: " + text.length());
174         }
175         byte[] data = new byte[text.length() >> 1];
176         int position = 0;
177         for (int n = 0; n < text.length(); n += 2) {
178             data[position] =
179                     (byte) (((fromHex(text.charAt(n), false) & NIBBLE_MASK) << 4) |
180                             (fromHex(text.charAt(n + 1), false) & NIBBLE_MASK));
181             position++;
182         }
183         return data;
184     }
185 
fromHex(char ch, boolean lenient)186     public static int fromHex(char ch, boolean lenient) throws NumberFormatException {
187         if (ch <= '9' && ch >= '0') {
188             return ch - '0';
189         } else if (ch >= 'a' && ch <= 'f') {
190             return ch + 10 - 'a';
191         } else if (ch <= 'F' && ch >= 'A') {
192             return ch + 10 - 'A';
193         } else if (lenient) {
194             return -1;
195         } else {
196             throw new NumberFormatException("Bad hex-character: " + ch);
197         }
198     }
199 
toAscii(int b)200     private static char toAscii(int b) {
201         return b >= ' ' && b < 0x7f ? (char) b : '.';
202     }
203 
isDecimal(String s)204     static boolean isDecimal(String s) {
205         for (int n = 0; n < s.length(); n++) {
206             char ch = s.charAt(n);
207             if (ch < '0' || ch > '9') {
208                 return false;
209             }
210         }
211         return true;
212     }
213 
compare(Comparable<T> c1, T c2)214     public static <T extends Comparable> int compare(Comparable<T> c1, T c2) {
215         if (c1 == null) {
216             return c2 == null ? 0 : -1;
217         }
218         else if (c2 == null) {
219             return 1;
220         }
221         else {
222             return c1.compareTo(c2);
223         }
224     }
225 
bytesToBingoCard(ByteBuffer data, int len)226     public static String bytesToBingoCard(ByteBuffer data, int len) {
227         ByteBuffer dup = data.duplicate();
228         dup.limit(dup.position() + len);
229         return bytesToBingoCard(dup);
230     }
231 
bytesToBingoCard(ByteBuffer data)232     public static String bytesToBingoCard(ByteBuffer data) {
233         ByteBuffer dup = data.duplicate();
234         StringBuilder sbx = new StringBuilder();
235         while (dup.hasRemaining()) {
236             sbx.append(String.format("%02x ", dup.get() & BYTE_MASK));
237         }
238         dup = data.duplicate();
239         sbx.append(' ');
240         while (dup.hasRemaining()) {
241             sbx.append(String.format("%c", toAscii(dup.get() & BYTE_MASK)));
242         }
243         return sbx.toString();
244     }
245 
toHMS(long millis)246     public static String toHMS(long millis) {
247         long time = millis >= 0 ? millis : -millis;
248         long tmp = time / 1000L;
249         long ms = time - tmp * 1000L;
250 
251         time = tmp;
252         tmp /= 60L;
253         long s = time - tmp * 60L;
254 
255         time = tmp;
256         tmp /= 60L;
257         long m = time - tmp * 60L;
258 
259         return String.format("%s%d:%02d:%02d.%03d", millis < 0 ? "-" : "", tmp, m, s, ms);
260     }
261 
toUTCString(long ms)262     public static String toUTCString(long ms) {
263         if (ms < 0) {
264             return "unset";
265         }
266         Calendar c = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
267         c.setTimeInMillis(ms);
268         return String.format("%4d/%02d/%02d %2d:%02d:%02dZ",
269                 c.get(Calendar.YEAR),
270                 c.get(Calendar.MONTH) + 1,
271                 c.get(Calendar.DAY_OF_MONTH),
272                 c.get(Calendar.HOUR_OF_DAY),
273                 c.get(Calendar.MINUTE),
274                 c.get(Calendar.SECOND));
275     }
276 
unquote(String s)277     public static String unquote(String s) {
278         if (s == null) {
279             return null;
280         }
281         else if (s.length() > 1 && s.startsWith("\"") && s.endsWith("\"")) {
282             return s.substring(1, s.length()-1);
283         }
284         else {
285             return s;
286         }
287     }
288 }
289