1 /*
2  * Copyright (c) 2006, 2015, Oracle and/or its affiliates. All rights reserved.
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * This code is free software; you can redistribute it and/or modify it
6  * under the terms of the GNU General Public License version 2 only, as
7  * published by the Free Software Foundation.
8  *
9  * This code is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12  * version 2 for more details (a copy is included in the LICENSE file that
13  * accompanied this code).
14  *
15  * You should have received a copy of the GNU General Public License version
16  * 2 along with this work; if not, write to the Free Software Foundation,
17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18  *
19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20  * or visit www.oracle.com if you need additional information or have any
21  * questions.
22  */
23 
24 /*
25  * @test
26  * @bug 6267067 6351336 6389198
27  * @summary unit test for javac List
28  * @modules jdk.compiler/com.sun.tools.javac.util
29  */
30 
31 import java.util.*;
32 import com.sun.tools.javac.util.List;
33 
34 public class TList {
main(String[] args)35     public static void main(String[] args) {
36         new TList().run();
37     }
38 
39     String[][] data = {
40         { },
41         { "1" },
42         { "1", "2" },
43         { "1", "2" }, // different but equal
44         { "1", "2", "3", "4", "X", "X", "X", "8", "9", "10" } // contains duplicates
45     };
46 
47     Map<java.util.List<String>,List<String>> examples;
48 
run()49     void run() {
50         examples = new LinkedHashMap<java.util.List<String>,List<String>>();
51         for (String[] values: data)
52             examples.put(Arrays.asList(values), createList(values));
53 
54         // 6351336: com.sun.tools.javac.util.List shouldn't extend java.util.AbstractList
55         test_AbstractList();
56 
57         // general unit tests for java.util.List methods, including...
58         // 6389198: com.sun.tools.javac.util.List.equals() violates java.util.List.equals() contract
59         test_add_E();
60         test_add_int_E();
61         test_addAll_Collection();
62         test_addAll_int_Collection();
63         test_clear();
64         test_contains_Object();
65         test_contains_All();
66         test_equals_Object();
67         test_get_int();
68         test_hashCode();
69         test_indexOf_Object();
70         test_isEmpty();
71         test_iterator();
72         test_lastIndexOf_Object();
73         test_listIterator();
74         test_listIterator_int();
75         test_remove_int();
76         test_remove_Object();
77         test_removeAll_Collection();
78         test_retainAll_Collection();
79         test_set_int_E();
80         test_size();
81         test_subList_int_int();
82         test_toArray();
83         test_toArray_TArray();
84 
85         // tests for additional methods
86         test_prependList_List();
87         test_reverse();
88     }
89 
90     // 6351336
test_AbstractList()91     void test_AbstractList() {
92         System.err.println("test AbstractList");
93         if (AbstractList.class.isAssignableFrom(List.class))
94             throw new AssertionError();
95     }
96 
test_add_E()97     void test_add_E() {
98         System.err.println("test add(E)");
99         for (List<String> l: examples.values()) {
100             try {
101                 l.add("test");
102                 throw new AssertionError();
103             } catch (UnsupportedOperationException ex) {
104             }
105         }
106     }
107 
test_add_int_E()108     void test_add_int_E() {
109         System.err.println("test add(int,E)");
110         for (List<String> l: examples.values()) {
111             try {
112                 l.add(0, "test");
113                 throw new AssertionError();
114             } catch (UnsupportedOperationException ex) {
115             }
116         }
117     }
118 
test_addAll_Collection()119     void test_addAll_Collection() {
120         System.err.println("test addAll(Collection)");
121         for (List<String> l: examples.values()) {
122             int l_size = l.size();
123             for (java.util.List<String> arg: examples.keySet()) {
124                 try {
125                     boolean modified = l.addAll(arg);
126                     if (modified)
127                         throw new AssertionError();
128                 } catch (UnsupportedOperationException e) {
129                 }
130                 if (l.size() != l_size)
131                     throw new AssertionError();
132             }
133         }
134     }
135 
test_addAll_int_Collection()136     void test_addAll_int_Collection() {
137         System.err.println("test addAll(int,Collection)");
138         for (List<String> l: examples.values()) {
139             int l_size = l.size();
140             for (java.util.List<String> arg: examples.keySet()) {
141                 try {
142                     boolean modified = l.addAll(0, arg);
143                     if (modified)
144                         throw new AssertionError();
145                 } catch (UnsupportedOperationException e) {
146                 }
147                 if (l.size() != l_size)
148                     throw new AssertionError();
149             }
150         }
151     }
152 
test_clear()153     void test_clear() {
154         System.err.println("test clear()");
155         for (List<String> l: examples.values()) {
156             int l_size = l.size();
157             try {
158                 l.clear();
159                 if (l_size > 0)
160                     throw new AssertionError();
161             } catch (UnsupportedOperationException e) {
162             }
163             if (l.size() != l_size)
164                 throw new AssertionError();
165         }
166     }
167 
test_contains_Object()168     void test_contains_Object() {
169         System.err.println("test contains(Object)");
170         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
171             java.util.List<String> ref = e.getKey();
172             List<String> l = e.getValue();
173             boolean expect = ref.contains("1");
174             boolean found = l.contains("1");
175             if (expect != found)
176                 throw new AssertionError();
177         }
178     }
179 
test_contains_All()180     void test_contains_All() {
181         System.err.println("test containsAll()");
182         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
183             java.util.List<String> ref = e.getKey();
184             List<String> l = e.getValue();
185             for (java.util.List<String> arg: examples.keySet()) {
186                 boolean expect = ref.containsAll(arg);
187                 boolean found = l.containsAll(arg);
188                 if (expect != found)
189                     throw new AssertionError();
190             }
191         }
192     }
193 
194     // 6389198
test_equals_Object()195     void test_equals_Object() {
196         System.err.println("test equals(Object)");
197         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
198             java.util.List<String> ref = e.getKey();
199             List<String> l = e.getValue();
200             for (java.util.List<String> arg: examples.keySet()) {
201                 boolean expect = ref.equals(arg);
202                 boolean found = l.equals(arg);
203                 if (expect != found) {
204                     System.err.println("ref: " + ref);
205                     System.err.println("l: " + l);
206                     System.err.println("arg: " + arg);
207                     System.err.println("expect: " + expect + ", found: " + found);
208                     throw new AssertionError();
209                 }
210             }
211         }
212     }
213 
test_get_int()214     void test_get_int() {
215         System.err.println("test get(int)");
216         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
217             java.util.List<String> ref = e.getKey();
218             List<String> l = e.getValue();
219             for (int i = -1; i <= ref.size(); i++) {
220                 boolean expectException = i < 0 || i >= ref.size();
221                 String expectValue = (expectException ? null : ref.get(i));
222                 try {
223                     String foundValue = l.get(i);
224                     if (expectException || !equal(expectValue, foundValue))
225                         throw new AssertionError();
226                 } catch (IndexOutOfBoundsException ex) {
227                     if (!expectException)
228                         throw new AssertionError();
229                 }
230             }
231         }
232     }
233 
test_hashCode()234     void test_hashCode() {
235         System.err.println("test hashCode()");
236         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
237             java.util.List<String> ref = e.getKey();
238             List<String> l = e.getValue();
239             long expect = ref.hashCode();
240             long found = l.hashCode();
241             if (expect != found) {
242                 System.err.println("ref: " + ref);
243                 System.err.println("l: " + l);
244                 System.err.println("expect: " + expect);
245                 System.err.println("found: " + found);
246                 throw new AssertionError();
247             }
248         }
249     }
250 
test_indexOf_Object()251     void test_indexOf_Object() {
252         System.err.println("test indexOf(Object)");
253         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
254             java.util.List<String> ref = e.getKey();
255             List<String> l = e.getValue();
256             for (int i = -1; i < ref.size(); i++) {
257                 String arg = (i == -1 ? "NOT IN LIST" : ref.get(i));
258                 int expect = ref.indexOf(arg);
259                 int found = l.indexOf(arg);
260                 if (expect != found)
261                     throw new AssertionError();
262             }
263         }
264     }
265 
test_isEmpty()266     void test_isEmpty() {
267         System.err.println("test isEmpty()");
268         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
269             java.util.List<String> ref = e.getKey();
270             List<String> l = e.getValue();
271             boolean expect = ref.isEmpty();
272             boolean found = l.isEmpty();
273             if (expect != found)
274                 throw new AssertionError();
275         }
276     }
277 
test_iterator()278     void test_iterator() {
279         System.err.println("test iterator()");
280         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
281             java.util.List<String> ref = e.getKey();
282             List<String> l = e.getValue();
283             if (!equal(l.iterator(), ref.iterator()))
284                 throw new AssertionError();
285         }
286     }
287 
test_lastIndexOf_Object()288     void test_lastIndexOf_Object() {
289         System.err.println("test lastIndexOf(Object)");
290         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
291             java.util.List<String> ref = e.getKey();
292             List<String> l = e.getValue();
293             for (int i = -1; i < ref.size(); i++) {
294                 String arg = (i == -1 ? "NOT IN LIST" : ref.get(i));
295                 int expect = ref.lastIndexOf(arg);
296                 int found = l.lastIndexOf(arg);
297                 if (expect != found)
298                     throw new AssertionError();
299             }
300         }
301     }
302 
test_listIterator()303     void test_listIterator() {
304         System.err.println("test listIterator()");
305         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
306             java.util.List<String> ref = e.getKey();
307             List<String> l = e.getValue();
308             if (!equal(l.listIterator(), ref.listIterator()))
309                 throw new AssertionError();
310         }
311     }
312 
test_listIterator_int()313     void test_listIterator_int() {
314         System.err.println("test listIterator(int)");
315         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
316             java.util.List<String> ref = e.getKey();
317             List<String> l = e.getValue();
318             for (int i = 0; i < ref.size(); i++) {
319                 if (!equal(l.listIterator(i), ref.listIterator(i)))
320                     throw new AssertionError();
321             }
322         }
323     }
324 
test_remove_int()325     void test_remove_int() {
326         System.err.println("test remove(int)");
327         for (List<String> l: examples.values()) {
328             try {
329                 l.remove(0);
330                 throw new AssertionError();
331             } catch (UnsupportedOperationException ex) {
332             }
333         }
334     }
335 
test_remove_Object()336     void test_remove_Object() {
337         System.err.println("test remove(Object)");
338         for (List<String> l: examples.values()) {
339             boolean hasX = l.contains("X");
340             try {
341                 l.remove("X");
342                 if (hasX)
343                     throw new AssertionError();
344             } catch (UnsupportedOperationException ex) {
345             }
346         }
347     }
348 
test_removeAll_Collection()349     void test_removeAll_Collection() {
350         System.err.println("test removeAll(Collection)");
351         for (List<String> l: examples.values()) {
352             int l_size = l.size();
353             for (java.util.List<String> arg: examples.keySet()) {
354                 try {
355                     boolean modified = l.removeAll(arg);
356                     if (modified)
357                         throw new AssertionError();
358                 } catch (UnsupportedOperationException e) {
359                 }
360                 if (l.size() != l_size)
361                     throw new AssertionError();
362             }
363         }
364     }
365 
test_retainAll_Collection()366     void test_retainAll_Collection() {
367         System.err.println("test retainAll(Collection)");
368         for (List<String> l: examples.values()) {
369             int l_size = l.size();
370             for (java.util.List<String> arg: examples.keySet()) {
371                 try {
372                     boolean modified = l.retainAll(arg);
373                     if (modified)
374                         throw new AssertionError();
375                 } catch (UnsupportedOperationException e) {
376                 }
377                 if (l.size() != l_size)
378                     throw new AssertionError();
379             }
380         }
381     }
382 
test_set_int_E()383     void test_set_int_E() {
384         System.err.println("test set(int,E)");
385         for (List<String> l: examples.values()) {
386             try {
387                 l.set(0, "X");
388                 throw new AssertionError();
389             } catch (UnsupportedOperationException ex) {
390             }
391         }
392     }
393 
test_size()394     void test_size() {
395         System.err.println("test size()");
396         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
397             java.util.List<String> ref = e.getKey();
398             List<String> l = e.getValue();
399             int  expect = ref.size();
400             int found = l.size();
401             if (expect != found)
402                 throw new AssertionError();
403         }
404     }
405 
test_subList_int_int()406     void test_subList_int_int() {
407         System.err.println("test subList(int,int)");
408         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
409             java.util.List<String> ref = e.getKey();
410             List<String> l = e.getValue();
411             for (int lwb = 0; lwb < ref.size(); lwb++) {
412                 for (int upb = lwb; upb <= ref.size(); upb++) {
413                     if (!equal(l.subList(lwb, upb), ref.subList(lwb,upb)))
414                     throw new AssertionError();
415                 }
416             }
417         }
418     }
419 
test_toArray()420     void test_toArray() {
421         System.err.println("test toArray()");
422         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
423             java.util.List<String> ref = e.getKey();
424             List<String> l = e.getValue();
425             if (!equal(l.toArray(), ref.toArray()))
426                 throw new AssertionError();
427         }
428     }
429 
test_toArray_TArray()430     void test_toArray_TArray() {
431         System.err.println("test toArray(E[])");
432         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
433             java.util.List<String> ref = e.getKey();
434             List<String> l = e.getValue();
435             if (!equal(l.toArray(new String[0]), ref.toArray(new String[0])))
436                 throw new AssertionError();
437         }
438     }
439 
test_prependList_List()440     void test_prependList_List() {
441         System.err.println("test prependList(List<E>)");
442         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
443             java.util.List<String> ref = e.getKey();
444             List<String> l = e.getValue();
445             for (Map.Entry<java.util.List<String>, List<String>> arg_e: examples.entrySet()) {
446                 java.util.List<String> arg_ref = arg_e.getKey();
447                 List<String> arg = arg_e.getValue();
448                 java.util.List<String> expect = join(arg, ref);
449                 List<String> found = l.prependList(arg);
450                 // verify results, and that original and arg lists are unchanged
451                 if (!equal(expect, found)) {
452                     System.err.println("ref: " + ref);
453                     System.err.println("l: " + l);
454                     System.err.println("arg: " + arg);
455                     System.err.println("expect: " + expect);
456                     System.err.println("found: " + found);
457                     throw new AssertionError();
458                 }
459                 if (!equal(l, ref))
460                     throw new AssertionError();
461                 if (!equal(arg, arg_ref))
462                     throw new AssertionError();
463             }
464         }
465     }
466 
test_reverse()467     void test_reverse() {
468         System.err.println("test reverse()");
469         for (Map.Entry<java.util.List<String>,List<String>> e: examples.entrySet()) {
470             java.util.List<String> ref = e.getKey();
471             List<String> l = e.getValue();
472             java.util.List<String> expect = reverse(ref);
473             List<String> found = l.reverse();
474             if (l.size() < 2 && found != l)  // reverse of empty or singleton list is itself
475                 throw new AssertionError();
476             if (!equal(l, ref)) // orginal should be unchanged
477                 throw new AssertionError();
478             if (!equal(expect, found))
479                 throw new AssertionError();
480         }
481     }
482 
createList(List<T> d)483     static <T> com.sun.tools.javac.util.List<T> createList(List<T> d) {
484         com.sun.tools.javac.util.List<T> l = com.sun.tools.javac.util.List.nil();
485         for (ListIterator<T> iter = d.listIterator(d.size()); iter.hasPrevious(); )
486             l = l.prepend(iter.previous());
487         return l;
488     }
489 
createList(T... d)490     static <T> com.sun.tools.javac.util.List<T> createList(T... d) {
491         com.sun.tools.javac.util.List<T> l = com.sun.tools.javac.util.List.nil();
492         for (int i = d.length - 1; i >= 0; i--)
493             l = l.prepend(d[i]);
494         return l;
495     }
496 
equal(T t1, T t2)497     static <T> boolean equal(T t1, T t2) {
498         return (t1 == null ? t2 == null : t1.equals(t2));
499     }
500 
equal(Iterator<T> iter1, Iterator<T> iter2)501     static <T> boolean equal(Iterator<T> iter1, Iterator<T> iter2) {
502         if (iter1 == null || iter2 == null)
503             return (iter1 == iter2);
504 
505         while (iter1.hasNext() && iter2.hasNext()) {
506             if (!equal(iter1.next(), iter2.next()))
507                 return false;
508         }
509 
510         return (!iter1.hasNext() && !iter2.hasNext());
511     }
512 
equal(ListIterator<T> iter1, ListIterator<T> iter2)513     static <T> boolean equal(ListIterator<T> iter1, ListIterator<T> iter2) {
514         if (iter1 == null || iter2 == null)
515             return (iter1 == iter2);
516 
517         if (iter1.previousIndex() != iter2.previousIndex())
518             return false;
519 
520         while (iter1.hasPrevious() && iter2.hasPrevious()) {
521             iter1.previous();
522             iter2.previous();
523         }
524 
525         return equal((Iterator<T>) iter1, (Iterator<T>) iter2);
526     }
527 
equal(T[] a1, T[] a2)528     static <T> boolean equal(T[] a1, T[] a2) {
529         if (a1 == null || a2 == null)
530             return (a1 == a2);
531 
532         if (a1.length != a2.length)
533             return false;
534 
535         for (int i = 0; i < a1.length; i++) {
536             if (!equal(a1[i], a2[i]))
537                 return false;
538         }
539 
540         return true;
541     }
542 
join(java.util.List<T>.... lists)543     static <T> java.util.List<T> join(java.util.List<T>... lists) {
544         java.util.List<T> r = new ArrayList<T>();
545         for (java.util.List<T> l: lists)
546             r.addAll(l);
547         return r;
548     }
549 
reverse(java.util.List<T> l)550     static <T> java.util.List<T> reverse(java.util.List<T> l) {
551         java.util.List<T> r = new ArrayList<T>(l.size());
552         for (T t: l)
553             r.add(0, t);
554         return r;
555     }
556 }
557