001: //##header
002: /**
003: *******************************************************************************
004: * Copyright (C) 2001-2006, International Business Machines Corporation and *
005: * others. All Rights Reserved. *
006: *******************************************************************************
007: */package com.ibm.icu.dev.test;
008:
009: import java.io.BufferedReader;
010: import java.io.FileInputStream;
011: import java.io.IOException;
012: import java.io.InputStream;
013: import java.io.InputStreamReader;
014: import java.io.File;
015:
016: public final class TestUtil {
017: /**
018: * Path to test data in icu4jtest.jar
019: */
020: public static final String LOCAL_DATA_PATH = "/com/ibm/icu/dev/data/";
021:
022: /**
023: * Standard path to the test data in the file system.
024: */
025: public static final String DATA_PATH = "/src" + LOCAL_DATA_PATH;
026:
027: /**
028: * Property for user-defined data path.
029: */
030: public static final String DATA_PATH_PROPERTY = "ICUDataPath";
031:
032: /**
033: * Property for modular build.
034: */
035: public static final String DATA_MODULAR_BUILD_PROPERTY = "ICUModularBuild";
036:
037: /**
038: * Compute a full data path using the ICUDataPath, if defined, or the user.dir, if we
039: * are allowed access to it.
040: */
041: private static final String dataPath(String fileName) {
042: String s = System.getProperty(DATA_PATH_PROPERTY);
043: if (s == null) {
044: // assume user.dir is directly above src directory
045: // data path must end in '/' or '\', fileName should not start with one
046: s = System.getProperty("user.dir"); // protected property
047: s = s + DATA_PATH;
048: }
049: return s + fileName;
050: }
051:
052: /**
053: * Return an input stream on the data file at path 'name' rooted at the data path
054: */
055: public static final InputStream getDataStream(String name)
056: throws IOException {
057: InputStream is = null;
058: try {
059: is = new FileInputStream(dataPath(name));
060: } catch (Throwable e) {
061: try {
062: is = TestUtil.class.getResourceAsStream(LOCAL_DATA_PATH
063: + name);
064: } catch (Throwable t) {
065: IOException ex = new IOException("data resource '"
066: + name + "' not found");
067: //#ifndef FOUNDATION
068: //initCause API was introduced in JDK 1.4
069: ex.initCause(t);
070: //#else
071: //## t.printStackTrace();
072: //#endif
073:
074: throw ex;
075: }
076: }
077: return is;
078: }
079:
080: /**
081: * Return a buffered reader on the data file at path 'name' rooted at the data path.
082: */
083: public static final BufferedReader getDataReader(String name,
084: String charset) throws IOException {
085: InputStream is = getDataStream(name);
086: InputStreamReader isr = charset == null ? new InputStreamReader(
087: is)
088: : new InputStreamReader(is, charset);
089: return new BufferedReader(isr);
090: }
091:
092: /**
093: * Return a buffered reader on the data file at path 'name' rooted at the data path,
094: * using the provided encoding.
095: */
096: public static final BufferedReader getDataReader(String name)
097: throws IOException {
098: return getDataReader(name, null);
099: }
100:
101: static final char DIGITS[] = { '0', '1', '2', '3', '4', '5', '6',
102: '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I',
103: 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U',
104: 'V', 'W', 'X', 'Y', 'Z' };
105:
106: /**
107: * Return true if the character is NOT printable ASCII. The tab,
108: * newline and linefeed characters are considered unprintable.
109: */
110: public static boolean isUnprintable(int c) {
111: return !(c >= 0x20 && c <= 0x7E);
112: }
113:
114: /**
115: * Escape unprintable characters using <backslash>uxxxx notation
116: * for U+0000 to U+FFFF and <backslash>Uxxxxxxxx for U+10000 and
117: * above. If the character is printable ASCII, then do nothing
118: * and return FALSE. Otherwise, append the escaped notation and
119: * return TRUE.
120: */
121: public static boolean escapeUnprintable(StringBuffer result, int c) {
122: if (isUnprintable(c)) {
123: result.append('\\');
124: if ((c & ~0xFFFF) != 0) {
125: result.append('U');
126: result.append(DIGITS[0xF & (c >> 28)]);
127: result.append(DIGITS[0xF & (c >> 24)]);
128: result.append(DIGITS[0xF & (c >> 20)]);
129: result.append(DIGITS[0xF & (c >> 16)]);
130: } else {
131: result.append('u');
132: }
133: result.append(DIGITS[0xF & (c >> 12)]);
134: result.append(DIGITS[0xF & (c >> 8)]);
135: result.append(DIGITS[0xF & (c >> 4)]);
136: result.append(DIGITS[0xF & c]);
137: return true;
138: }
139: return false;
140: }
141:
142: static class Lock {
143: private int count;
144:
145: synchronized void inc() {
146: ++count;
147: }
148:
149: synchronized void dec() {
150: --count;
151: }
152:
153: synchronized int count() {
154: return count;
155: }
156:
157: void go() {
158: try {
159: while (count() > 0) {
160: synchronized (this ) {
161: notifyAll();
162: }
163: Thread.sleep(50);
164: }
165: } catch (InterruptedException e) {
166: }
167: }
168: }
169:
170: static class TestThread extends Thread {
171: Lock lock;
172: Runnable target;
173:
174: TestThread(Lock lock, Runnable target) {
175: this .lock = lock;
176: this .target = target;
177:
178: lock.inc();
179: }
180:
181: public void run() {
182: try {
183: synchronized (lock) {
184: lock.wait();
185: }
186: target.run();
187: } catch (InterruptedException e) {
188: }
189:
190: lock.dec();
191: }
192: }
193:
194: public static void runUntilDone(Runnable[] targets) {
195: if (targets == null) {
196: throw new IllegalArgumentException("targets is null");
197: }
198: if (targets.length == 0) {
199: return;
200: }
201:
202: Lock lock = new Lock();
203: for (int i = 0; i < targets.length; ++i) {
204: new TestThread(lock, targets[i]).start();
205: }
206:
207: lock.go();
208: }
209:
210: public static BufferedReader openUTF8Reader(String dir,
211: String filename) throws IOException {
212: return openReader(dir, filename, "UTF-8");
213: }
214:
215: public static BufferedReader openReader(String dir,
216: String filename, String encoding) throws IOException {
217: File file = new File(dir + filename);
218: return new BufferedReader(new InputStreamReader(
219: new FileInputStream(file), encoding), 4 * 1024);
220: }
221:
222: }
|