src/share/classes/java/util/Collections.java

Print this page
rev 10180 : 8047795: Collections.checkedList checking bypassed by List.replaceAll
Reviewed-by: duke

*** 3029,3053 **** private static final long serialVersionUID = 1578914078182001775L; final Collection<E> c; final Class<E> type; ! void typeCheck(Object o) { if (o != null && !type.isInstance(o)) throw new ClassCastException(badElementMsg(o)); } private String badElementMsg(Object o) { return "Attempt to insert " + o.getClass() + " element into collection with element type " + type; } CheckedCollection(Collection<E> c, Class<E> type) { ! if (c==null || type == null) ! throw new NullPointerException(); ! this.c = c; ! this.type = type; } public int size() { return c.size(); } public boolean isEmpty() { return c.isEmpty(); } public boolean contains(Object o) { return c.contains(o); } --- 3029,3052 ---- private static final long serialVersionUID = 1578914078182001775L; final Collection<E> c; final Class<E> type; ! E typeCheck(Object o) { if (o != null && !type.isInstance(o)) throw new ClassCastException(badElementMsg(o)); + return (E) o; } private String badElementMsg(Object o) { return "Attempt to insert " + o.getClass() + " element into collection with element type " + type; } CheckedCollection(Collection<E> c, Class<E> type) { ! this.c = Objects.requireNonNull(c, "c"); ! this.type = Objects.requireNonNull(type, "type"); } public int size() { return c.size(); } public boolean isEmpty() { return c.isEmpty(); } public boolean contains(Object o) { return c.contains(o); }
*** 3089,3099 **** (zeroLengthElementArray = zeroLengthArray(type)); } @SuppressWarnings("unchecked") Collection<E> checkedCopyOf(Collection<? extends E> coll) { ! Object[] a = null; try { E[] z = zeroLengthElementArray(); a = coll.toArray(z); // Defend against coll violating the toArray contract if (a.getClass() != z.getClass()) --- 3088,3098 ---- (zeroLengthElementArray = zeroLengthArray(type)); } @SuppressWarnings("unchecked") Collection<E> checkedCopyOf(Collection<? extends E> coll) { ! Object[] a; try { E[] z = zeroLengthElementArray(); a = coll.toArray(z); // Defend against coll violating the toArray contract if (a.getClass() != z.getClass())
*** 3485,3498 **** public List<E> subList(int fromIndex, int toIndex) { return new CheckedList<>(list.subList(fromIndex, toIndex), type); } @Override public void replaceAll(UnaryOperator<E> operator) { ! list.replaceAll(operator); } @Override public void sort(Comparator<? super E> c) { list.sort(c); } } --- 3484,3504 ---- public List<E> subList(int fromIndex, int toIndex) { return new CheckedList<>(list.subList(fromIndex, toIndex), type); } + /** + * {@inheritDoc} + * + * @throws ClassCastException if the class of an element returned by the + * operator prevents it from being added to this collection + */ @Override public void replaceAll(UnaryOperator<E> operator) { ! list.replaceAll(e -> typeCheck(operator.apply(e))); } + @Override public void sort(Comparator<? super E> c) { list.sort(c); } }