Imported Upstream version 58.1
[platform/upstream/icu.git] / source / test / intltest / trnserr.cpp
1 // Copyright (C) 2016 and later: Unicode, Inc. and others.
2 // License & terms of use: http://www.unicode.org/copyright.html
3 /********************************************************************
4  * Copyright (c) 2001-2009, International Business Machines
5  * Corporation and others. All Rights Reserved.
6  *********************************************************************
7  *   This test program is intended for testing error conditions of the 
8  *   transliterator APIs to make sure the exceptions are raised where
9  *   necessary.
10  *
11  *   Date        Name        Description
12  *   11/14/2001  hshih       Creation.
13  * 
14  ********************************************************************/
15
16 #include "unicode/utypes.h"
17
18 #if !UCONFIG_NO_TRANSLITERATION
19
20 #include "ittrans.h"
21 #include "trnserr.h"
22 #include "unicode/utypes.h"
23 #include "unicode/translit.h"
24 #include "unicode/uniset.h"
25 #include "unicode/unifilt.h"
26 #include "cpdtrans.h"
27 #include <string.h>
28 #include <stdio.h>
29 #include <stdlib.h>
30 #include "unicode/rep.h"
31 #include "unicode/locid.h"
32
33 //---------------------------------------------
34 // runIndexedTest
35 //---------------------------------------------
36
37 void
38 TransliteratorErrorTest::runIndexedTest(int32_t index, UBool exec,
39                                       const char* &name, char* /*par*/) {
40     switch (index) {
41         TESTCASE(0,TestTransliteratorErrors);
42         TESTCASE(1, TestUnicodeSetErrors);
43         TESTCASE(2, TestRBTErrors);
44         TESTCASE(3, TestCoverage);
45         //TESTCASE(3, TestUniToHexErrors);
46         //TESTCASE(4, TestHexToUniErrors);
47         // TODO: Add a subclass to test clone().
48         default: name = ""; break;
49     }
50 }
51
52
53 void TransliteratorErrorTest::TestTransliteratorErrors() {
54     UnicodeString trans="Latin-Greek";
55     UnicodeString bogusID="LATINGREEK-GREEKLATIN";
56     UnicodeString newID="Bogus-Latin";
57     UnicodeString newIDRules="zzz > Z; f <> ph";
58     UnicodeString bogusRules="a } [b-g m-p ";
59     UParseError parseError;
60     UErrorCode status = U_ZERO_ERROR;
61     UnicodeString testString="A quick fox jumped over the lazy dog.";
62     UnicodeString insertString="cats and dogs";
63     int32_t stoppedAt = 0, len;
64     UTransPosition pos;
65
66     Transliterator* t= Transliterator::createInstance(trans, UTRANS_FORWARD, parseError, status);
67     if(t==0 || U_FAILURE(status)){
68         dataerrln("FAIL: construction of Latin-Greek - %s", u_errorName(status));
69         return;
70     }
71     pos.contextLimit = 0;
72     pos.contextStart = 0;
73     pos.limit = 0;
74     pos.start = 0;
75     len = testString.length();
76     stoppedAt = t->transliterate(testString, 0, 100);
77     if (stoppedAt != -1) {
78         errln("FAIL: Out of bounds check failed (1).");
79     } else if (testString.length() != len) {
80         testString="A quick fox jumped over the lazy dog.";        
81         errln("FAIL: Transliterate fails and the target string was modified.");
82     }
83     stoppedAt = t->transliterate(testString, 100, testString.length()-1);
84     if (stoppedAt != -1)
85         errln("FAIL: Out of bounds check failed (2).");
86     else if (testString.length() != len) {
87         testString="A quick fox jumped over the lazy dog.";        
88         errln("FAIL: Transliterate fails and the target string was modified.");
89     }
90     pos.start = 100;
91     pos.limit = testString.length();
92     t->transliterate(testString, pos, status);
93     if (U_SUCCESS(status)) {
94         errln("FAIL: Start offset is out of bounds, error not reported.\n");
95     }
96     status = U_ZERO_ERROR;
97     pos.limit = 100;
98     pos.start = 0;
99     t->transliterate(testString, pos, status);
100     if (U_SUCCESS(status)) {
101         errln("FAIL: Limit offset is out of bounds, error not reported.\n");
102     }
103     status = U_ZERO_ERROR;
104     len = pos.contextLimit = testString.length();
105     pos.contextStart = 0;
106     pos.limit = len - 1;
107     pos.start = 5;
108     t->transliterate(testString, pos, insertString, status);
109     if (len == pos.limit) {
110         errln("FAIL: Test insertion with string: the transliteration position limit didn't change as expected.");
111         if (U_SUCCESS(status)) {
112             errln("FAIL: Error code wasn't set either.");
113         }
114     }
115     status = U_ZERO_ERROR;
116     pos.contextStart = 0;
117     pos.contextLimit = testString.length();
118     pos.limit = testString.length() -1;
119     pos.start = 5;
120     t->transliterate(testString, pos, (UChar32)0x0061, status);
121     if (len == pos.limit) {
122         errln("FAIL: Test insertion with character: the transliteration position limit didn't change as expected.");
123         if (U_SUCCESS(status)) {
124             errln("FAIL: Error code wasn't set either.");
125         }
126     }
127     status = U_ZERO_ERROR;
128     len = pos.limit = testString.length();
129     pos.contextStart = 0;
130     pos.contextLimit = testString.length() - 1;
131     pos.start = 5;
132     t->transliterate(testString, pos, insertString, status);
133     if (U_SUCCESS(status)) {
134         errln("FAIL: Out of bounds check failed (3).");
135         if (testString.length() != len)
136             errln("FAIL: The input string was modified though the offsets were out of bounds.");
137     }
138     Transliterator* t1= Transliterator::createInstance(bogusID, UTRANS_FORWARD, parseError, status);
139     if(t1!=0 || U_SUCCESS(status)){
140         delete t1;
141         errln("FAIL: construction of bogus ID \"LATINGREEK-GREEKLATIN\"");
142     }
143     status = U_ZERO_ERROR;
144     Transliterator* t2 = Transliterator::createFromRules(newID, newIDRules, UTRANS_FORWARD, parseError, status);
145     if (U_SUCCESS(status)) {
146         Transliterator* t3 = t2->createInverse(status);
147         if (U_SUCCESS(status)) {
148             delete t3;
149             errln("FAIL: The newID transliterator was not registered so createInverse should fail.");
150         } else {
151             delete t3;
152         }
153     }
154     status = U_ZERO_ERROR;
155     Transliterator* t4 = Transliterator::createFromRules(newID, bogusRules, UTRANS_FORWARD, parseError, status);
156     if (t4 != NULL || U_SUCCESS(status)) {
157         errln("FAIL: The rules is malformed but error was not reported.");
158         if (parseError.offset != -1) {
159             errln("FAIL: The parse error offset isn't set correctly when fails.");
160         } else if (parseError.postContext[0] == 0 || parseError.preContext[0] == 0) {
161             errln("FAIL: The parse error pre/post context isn't reset properly.");
162         }
163         delete t4;
164     }    
165     delete t;
166     delete t2;
167 }
168
169 void TransliteratorErrorTest::TestUnicodeSetErrors() {
170     UnicodeString badPattern="[[:L:]-[0x0300-0x0400]";
171     UnicodeSet set;
172     UErrorCode status = U_ZERO_ERROR;
173     UnicodeString result;
174
175     if (!set.isEmpty()) {
176         errln("FAIL: The default ctor of UnicodeSet created a non-empty object.");
177     }
178     set.applyPattern(badPattern, status);
179     if (U_SUCCESS(status)) {
180         errln("FAIL: Applied a bad pattern to the UnicodeSet object okay.");
181     }
182     status = U_ZERO_ERROR;
183     UnicodeSet *set1 = new UnicodeSet(badPattern, status);
184     if (U_SUCCESS(status)) {
185         errln("FAIL: Created a UnicodeSet based on bad patterns.");
186     }
187     delete set1;
188 }
189
190 //void TransliteratorErrorTest::TestUniToHexErrors() {
191 //    UErrorCode status = U_ZERO_ERROR;
192 //    Transliterator *t = new UnicodeToHexTransliterator("", TRUE, NULL, status);
193 //    if (U_SUCCESS(status)) {
194 //        errln("FAIL: Created a UnicodeToHexTransliterator with an empty pattern.");
195 //    }
196 //    delete t;
197 //
198 //    status = U_ZERO_ERROR;
199 //    t = new UnicodeToHexTransliterator("\\x", TRUE, NULL, status);
200 //    if (U_SUCCESS(status)) {
201 //        errln("FAIL: Created a UnicodeToHexTransliterator with a bad pattern.");
202 //    }
203 //    delete t;
204 //
205 //    status = U_ZERO_ERROR;
206 //    t = new UnicodeToHexTransliterator();
207 //    ((UnicodeToHexTransliterator*)t)->applyPattern("\\x", status);
208 //    if (U_SUCCESS(status)) {
209 //        errln("FAIL: UnicodeToHexTransliterator::applyPattern succeeded with a bad pattern.");
210 //    }
211 //    delete t;
212 //}
213
214 void TransliteratorErrorTest::TestRBTErrors() {
215
216     UnicodeString rules="ab>y";
217     UnicodeString id="MyRandom-YReverse";
218     //UnicodeString goodPattern="[[:L:]&[\\u0000-\\uFFFF]]"; /* all BMP letters */
219     UErrorCode status = U_ZERO_ERROR;
220     UParseError parseErr;
221     /*UnicodeSet *set = new UnicodeSet(goodPattern, status);
222     if (U_FAILURE(status)) {
223         errln("FAIL: Was not able to create a good UnicodeSet based on valid patterns.");
224         return;
225     }*/
226     Transliterator *t = Transliterator::createFromRules(id, rules, UTRANS_REVERSE, parseErr, status);
227     if (U_FAILURE(status)) {
228         errln("FAIL: Was not able to create a good RBT to test registration.");
229         //delete set;
230         return;
231     }
232     Transliterator::registerInstance(t);
233     Transliterator::unregister(id);
234     status = U_ZERO_ERROR;
235     Transliterator* t1= Transliterator::createInstance(id, UTRANS_REVERSE, parseErr, status);
236     if(U_SUCCESS(status)){
237         delete t1;
238         errln("FAIL: construction of unregistered ID failed.");
239     } 
240 }
241
242 //void TransliteratorErrorTest::TestHexToUniErrors() {
243 //    UErrorCode status = U_ZERO_ERROR;
244 //    Transliterator *t = new HexToUnicodeTransliterator("", NULL, status);
245 //    if (U_FAILURE(status)) {
246 //        errln("FAIL: Could not create a HexToUnicodeTransliterator with an empty pattern.");
247 //    }
248 //    delete t;
249 //    status = U_ZERO_ERROR;
250 //    t = new HexToUnicodeTransliterator("\\x", NULL, status);
251 //    if (U_SUCCESS(status)) {
252 //        errln("FAIL: Created a HexToUnicodeTransliterator with a bad pattern.");
253 //    }
254 //    delete t;
255 //    status = U_ZERO_ERROR;
256 //    t = new HexToUnicodeTransliterator();
257 //    ((HexToUnicodeTransliterator*)t)->applyPattern("\\x", status);
258 //    if (U_SUCCESS(status)) {
259 //        errln("FAIL: HexToUnicodeTransliterator::applyPattern succeeded with a bad pattern.");
260 //    }
261 //    delete t;
262 //}
263
264 class StubTransliterator: public Transliterator{
265 public:
266     StubTransliterator(): Transliterator(UNICODE_STRING_SIMPLE("Any-Null"), 0) {}
267     virtual void handleTransliterate(Replaceable& ,UTransPosition& offsets,UBool) const {
268         offsets.start = offsets.limit;
269     }
270
271     virtual UClassID getDynamicClassID() const{
272         static char classID = 0;
273         return (UClassID)&classID; 
274     }
275 };
276
277 void TransliteratorErrorTest::TestCoverage() {
278     StubTransliterator stub;
279
280     if (stub.clone() != NULL){
281         errln("FAIL: default Transliterator::clone() should return NULL");
282     }
283 }
284
285 #endif /* #if !UCONFIG_NO_TRANSLITERATION */