1 /*
2  * Copyright (c) 2000, 2020, 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 /* Type-specific source code for unit test
25  *
26  * Regenerate the BasicX classes via genBasic.sh whenever this file changes.
27  * We check in the generated source files so that the test tree can be used
28  * independently of the rest of the source tree.
29  */
30 package test.java.nio.Buffer;
31 
32 // -- This file was mechanically generated: Do not edit! -- //
33 
34 
35 import java.io.IOException;
36 import java.io.UncheckedIOException;
37 
38 import java.nio.*;
39 import java.util.function.Supplier;
40 
41 import java.nio.channels.FileChannel;
42 import java.nio.file.Files;
43 import java.nio.file.Path;
44 import java.util.Random;
45 
46 
47 
48 import static org.testng.Assert.assertEquals;
49 
50 
51 public class BasicByte
52     extends Basic
53 {
54 
55     private static final byte[] VALUES = {
56         Byte.MIN_VALUE,
57         (byte) -1,
58         (byte) 0,
59         (byte) 1,
60         Byte.MAX_VALUE,
61 
62 
63 
64 
65 
66 
67 
68 
69 
70 
71 
72 
73     };
74 
relGet(ByteBuffer b)75     private static void relGet(ByteBuffer b) {
76         int n = b.capacity();
77         for (int i = 0; i < n; i++)
78             ck(b, (long)b.get(), (long)((byte)ic(i)));
79         b.rewind();
80     }
81 
relGet(ByteBuffer b, int start)82     private static void relGet(ByteBuffer b, int start) {
83         int n = b.remaining();
84         for (int i = start; i < n; i++)
85             ck(b, (long)b.get(), (long)((byte)ic(i)));
86         b.rewind();
87     }
88 
absGet(ByteBuffer b)89     private static void absGet(ByteBuffer b) {
90         int n = b.capacity();
91         for (int i = 0; i < n; i++)
92             ck(b, (long)b.get(), (long)((byte)ic(i)));
93         b.rewind();
94     }
95 
bulkGet(ByteBuffer b)96     private static void bulkGet(ByteBuffer b) {
97         int n = b.capacity();
98         byte[] a = new byte[n + 7];
99         b.get(a, 7, n);
100         for (int i = 0; i < n; i++) {
101             ck(b, (long)a[i + 7], (long)((byte)ic(i)));
102         }
103     }
104 
absBulkGet(ByteBuffer b)105     private static void absBulkGet(ByteBuffer b) {
106         int n = b.capacity();
107         int len = n - 7*2;
108         byte[] a = new byte[n + 7];
109         b.position(42);
110         b.get(7, a, 7, len);
111         ck(b, b.position() == 42);
112         for (int i = 0; i < len; i++) {
113             ck(b, (long)a[i + 7], (long)((byte)ic(i)));
114         }
115     }
116 
relPut(ByteBuffer b)117     private static void relPut(ByteBuffer b) {
118         int n = b.capacity();
119         b.clear();
120         for (int i = 0; i < n; i++)
121             b.put((byte)ic(i));
122         b.flip();
123     }
124 
absPut(ByteBuffer b)125     private static void absPut(ByteBuffer b) {
126         int n = b.capacity();
127         b.clear();
128         for (int i = 0; i < n; i++)
129             b.put(i, (byte)ic(i));
130         b.limit(n);
131         b.position(0);
132     }
133 
bulkPutArray(ByteBuffer b)134     private static void bulkPutArray(ByteBuffer b) {
135         int n = b.capacity();
136         b.clear();
137         byte[] a = new byte[n + 7];
138         for (int i = 0; i < n; i++)
139             a[i + 7] = (byte)ic(i);
140         b.put(a, 7, n);
141         b.flip();
142     }
143 
bulkPutBuffer(ByteBuffer b)144     private static void bulkPutBuffer(ByteBuffer b) {
145         int n = b.capacity();
146         b.clear();
147         ByteBuffer c = ByteBuffer.allocate(n + 7);
148         c.position(7);
149         for (int i = 0; i < n; i++)
150             c.put((byte)ic(i));
151         c.flip();
152         c.position(7);
153         b.put(c);
154         b.flip();
155         try {
156             b.put(b);
157             fail("IllegalArgumentException expected for put into same buffer");
158         } catch (IllegalArgumentException e) {
159             if (e.getMessage() == null) {
160                 fail("Non-null IllegalArgumentException message expected from"
161                      + " put into same buffer");
162             }
163         }
164     }
165 
absBulkPutArray(ByteBuffer b)166     private static void absBulkPutArray(ByteBuffer b) {
167         int n = b.capacity();
168         b.clear();
169         int lim = n - 7;
170         int len = lim - 7;
171         b.limit(lim);
172         byte[] a = new byte[len + 7];
173         for (int i = 0; i < len; i++)
174             a[i + 7] = (byte)ic(i);
175         b.position(42);
176         b.put(7, a, 7, len);
177         ck(b, b.position() == 42);
178     }
179 
180     //6231529
callReset(ByteBuffer b)181     private static void callReset(ByteBuffer b) {
182         b.position(0);
183         b.mark();
184 
185         b.duplicate().reset();
186         b.asReadOnlyBuffer().reset();
187     }
188 
189 
190 
191 
192 
193 
194 
195 
196 
197 
198 
199 
200 
201 
202 
203 
204 
205 
206 
207 
208 
209 
210 
211 
212 
213 
214 
215 
216 
217 
218 
219 
220 
221 
222 
223 
224 
225 
226 
227 
228 
checkSlice(ByteBuffer b, ByteBuffer slice)229     private static void checkSlice(ByteBuffer b, ByteBuffer slice) {
230         ck(slice, 0, slice.position());
231         ck(slice, b.remaining(), slice.limit());
232         ck(slice, b.remaining(), slice.capacity());
233         if (b.isDirect() != slice.isDirect())
234             fail("Lost direction", slice);
235         if (b.isReadOnly() != slice.isReadOnly())
236             fail("Lost read-only", slice);
237     }
238 
239 
240 
checkBytes(ByteBuffer b, byte[] bs)241     private static void checkBytes(ByteBuffer b, byte[] bs) {
242         int n = bs.length;
243         int p = b.position();
244         if (b.order() == ByteOrder.BIG_ENDIAN) {
245             for (int i = 0; i < n; i++) {
246                 ck(b, b.get(), bs[i]);
247             }
248         } else {
249             for (int i = n - 1; i >= 0; i--) {
250                 ck(b, b.get(), bs[i]);
251             }
252         }
253         b.position(p);
254     }
255 
compact(Buffer b)256     private static void compact(Buffer b) {
257         try {
258             Class<?> cl = b.getClass();
259             java.lang.reflect.Method m = cl.getDeclaredMethod("compact");
260             m.setAccessible(true);
261             m.invoke(b);
262         } catch (Exception e) {
263             fail(e.getMessage(), b);
264         }
265     }
266 
checkInvalidMarkException(final Buffer b)267     private static void checkInvalidMarkException(final Buffer b) {
268         tryCatch(b, InvalidMarkException.class, () -> {
269                 b.mark();
270                 compact(b);
271                 b.reset();
272             });
273     }
274 
testViews(int level, ByteBuffer b, boolean direct)275     private static void testViews(int level, ByteBuffer b, boolean direct) {
276 
277         ShortBuffer sb = b.asShortBuffer();
278         BasicShort.test(level, sb, direct);
279         checkBytes(b, new byte[] { 0, (byte)ic(0) });
280         checkInvalidMarkException(sb);
281 
282         CharBuffer cb = b.asCharBuffer();
283         BasicChar.test(level, cb, direct);
284         checkBytes(b, new byte[] { 0, (byte)ic(0) });
285         checkInvalidMarkException(cb);
286 
287         IntBuffer ib = b.asIntBuffer();
288         BasicInt.test(level, ib, direct);
289         checkBytes(b, new byte[] { 0, 0, 0, (byte)ic(0) });
290         checkInvalidMarkException(ib);
291 
292         LongBuffer lb = b.asLongBuffer();
293         BasicLong.test(level, lb, direct);
294         checkBytes(b, new byte[] { 0, 0, 0, 0, 0, 0, 0, (byte)ic(0) });
295         checkInvalidMarkException(lb);
296 
297         FloatBuffer fb = b.asFloatBuffer();
298         BasicFloat.test(level, fb, direct);
299         checkBytes(b, new byte[] { 0x42, (byte)0xc2, 0, 0 });
300         checkInvalidMarkException(fb);
301 
302         DoubleBuffer db = b.asDoubleBuffer();
303         BasicDouble.test(level, db, direct);
304         checkBytes(b, new byte[] { 0x40, 0x58, 0x40, 0, 0, 0, 0, 0 });
305         checkInvalidMarkException(db);
306     }
307 
testHet(int level, ByteBuffer b)308     private static void testHet(int level, ByteBuffer b) {
309 
310         int p = b.position();
311         b.limit(b.capacity());
312         show(level, b);
313         out.print("    put:");
314 
315         b.putChar((char)1);
316         b.putChar((char)Character.MAX_VALUE);
317         out.print(" char");
318 
319         b.putShort((short)1);
320         b.putShort((short)Short.MAX_VALUE);
321         out.print(" short");
322 
323         b.putInt(1);
324         b.putInt(Integer.MAX_VALUE);
325         out.print(" int");
326 
327         b.putLong((long)1);
328         b.putLong((long)Long.MAX_VALUE);
329         out.print(" long");
330 
331         b.putFloat((float)1);
332         b.putFloat((float)Float.MIN_VALUE);
333         b.putFloat((float)Float.MAX_VALUE);
334         out.print(" float");
335 
336         b.putDouble((double)1);
337         b.putDouble((double)Double.MIN_VALUE);
338         b.putDouble((double)Double.MAX_VALUE);
339         out.print(" double");
340 
341         out.println();
342         b.limit(b.position());
343         b.position(p);
344         show(level, b);
345         out.print("    get:");
346 
347         ck(b, b.getChar(), 1);
348         ck(b, b.getChar(), Character.MAX_VALUE);
349         out.print(" char");
350 
351         ck(b, b.getShort(), 1);
352         ck(b, b.getShort(), Short.MAX_VALUE);
353         out.print(" short");
354 
355         ck(b, b.getInt(), 1);
356         ck(b, b.getInt(), Integer.MAX_VALUE);
357         out.print(" int");
358 
359         ck(b, b.getLong(), 1);
360         ck(b, b.getLong(), Long.MAX_VALUE);
361         out.print(" long");
362 
363         ck(b, (long)b.getFloat(), 1);
364         ck(b, (long)b.getFloat(), (long)Float.MIN_VALUE);
365         ck(b, (long)b.getFloat(), (long)Float.MAX_VALUE);
366         out.print(" float");
367 
368         ck(b, (long)b.getDouble(), 1);
369         ck(b, (long)b.getDouble(), (long)Double.MIN_VALUE);
370         ck(b, (long)b.getDouble(), (long)Double.MAX_VALUE);
371         out.print(" double");
372 
373         out.println();
374 
375     }
376 
testAlign(final ByteBuffer b, boolean direct)377     private static void testAlign(final ByteBuffer b, boolean direct) {
378         // index out-of bounds
379         catchIllegalArgument(b, () -> b.alignmentOffset(-1, (short) 1));
380 
381         // unit size values
382         catchIllegalArgument(b, () -> b.alignmentOffset(0, (short) 0));
383         for (int us = 1; us < 65; us++) {
384             int _us = us;
385             if ((us & (us - 1)) != 0) {
386                 // unit size not a power of two
387                 catchIllegalArgument(b, () -> b.alignmentOffset(0, _us));
388             } else {
389                 if (direct || us <= 8) {
390                     b.alignmentOffset(0, us);
391                 } else {
392                     // unit size > 8 with non-direct buffer
393                     tryCatch(b, UnsupportedOperationException.class,
394                             () -> b.alignmentOffset(0, _us));
395                 }
396             }
397         }
398 
399         // Probe for long misalignment at index zero for a newly created buffer
400         ByteBuffer empty =
401                 direct ? ByteBuffer.allocateDirect(0) : ByteBuffer.allocate(0);
402         int longMisalignmentAtZero = empty.alignmentOffset(0, 8);
403 
404         if (direct) {
405             // Freshly created direct byte buffers should be aligned at index 0
406             // for ref and primitive values (see Unsafe.allocateMemory)
407             if (longMisalignmentAtZero != 0) {
408                 fail("Direct byte buffer misaligned at index 0"
409                         + " for ref and primitive values "
410                         + longMisalignmentAtZero);
411             }
412         } else {
413             // For heap byte buffers misalignment may occur on 32-bit systems
414             // where Unsafe.ARRAY_BYTE_BASE_OFFSET % 8 == 4 and not 0
415             // Note the GC will preserve alignment of the base address of the
416             // array
417             if (jdk.internal.misc.Unsafe.ARRAY_BYTE_BASE_OFFSET % 8
418                     != longMisalignmentAtZero) {
419                 fail("Heap byte buffer misaligned at index 0"
420                         + " for ref and primitive values "
421                         + longMisalignmentAtZero);
422             }
423         }
424 
425         // Ensure test buffer is correctly aligned at index 0
426         if (b.alignmentOffset(0, 8) != longMisalignmentAtZero)
427             fail("Test input buffer not correctly aligned at index 0", b);
428 
429         // Test misalignment values
430         for (int us : new int[]{1, 2, 4, 8}) {
431             for (int i = 0; i < us * 2; i++) {
432                 int am = b.alignmentOffset(i, us);
433                 int expectedAm = (longMisalignmentAtZero + i) % us;
434 
435                 if (am != expectedAm) {
436                     String f = "b.alignmentOffset(%d, %d) == %d incorrect, expected %d";
437                     fail(String.format(f, i, us, am, expectedAm));
438                 }
439             }
440         }
441 
442         // Created aligned slice to test against
443         int ap = 8 - longMisalignmentAtZero;
444         int al = b.limit() - b.alignmentOffset(b.limit(), 8);
445         // Android-changed: Explicit casting due to @CovariantReturnType methods invisible to javac.
446         ByteBuffer ab = (ByteBuffer) b.position(ap).limit(al).
447                 slice();
448         if (ab.limit() == 0) {
449             fail("Test input buffer not sufficiently sized to cover" +
450                     " an aligned region for all values", b);
451         }
452         if (ab.alignmentOffset(0, 8) != 0)
453             fail("Aligned test input buffer not correctly aligned at index 0", ab);
454 
455         for (int us : new int[]{1, 2, 4, 8}) {
456             for (int p = 1; p < 16; p++) {
457                 int l = ab.limit() - p;
458 
459                 // Android-changed: Explicit casting due to @CovariantReturnType methods.
460                 ByteBuffer as = ((ByteBuffer) ab.slice().position(p).limit(l)).
461                         alignedSlice(us);
462 
463                 ck(as, 0, as.position());
464                 ck(as, as.capacity(), as.limit());
465                 if (b.isDirect() != as.isDirect())
466                     fail("Lost direction", as);
467                 if (b.isReadOnly() != as.isReadOnly())
468                     fail("Lost read-only", as);
469 
470                 if (as.alignmentOffset(0, us) != 0)
471                     fail("Buffer not correctly aligned at index 0", as);
472 
473                 if (as.alignmentOffset(as.limit(), us) != 0)
474                     fail("Buffer not correctly aligned at limit", as);
475 
476                 int p_mod = ab.alignmentOffset(p, us);
477                 int l_mod = ab.alignmentOffset(l, us);
478                 // Round up position
479                 p = (p_mod > 0) ? p + (us - p_mod) : p;
480                 // Round down limit
481                 l = l - l_mod;
482 
483                 int ec = l - p;
484                 if (as.limit() != ec) {
485                     fail("Buffer capacity incorrect, expected: " + ec, as);
486                 }
487             }
488         }
489 
490         // mapped buffers
491         try {
492             for (MappedByteBuffer bb : mappedBuffers()) {
493                 try {
494                     int offset = bb.alignmentOffset(1, 4);
495                     ck(bb, offset >= 0);
496                 } catch (UnsupportedOperationException e) {
497                     System.out.println("Not applicable, UOE thrown: ");
498                 }
499             }
500         } catch (IOException e) {
501             throw new UncheckedIOException(e);
502         }
503 
504         // alignment identities
505         final int maxPow2 = 12;
506         ByteBuffer bb = ByteBuffer.allocateDirect(1 << maxPow2); // cap 4096
507 
508         Random rnd = new Random();
509         long seed = rnd.nextLong();
510         rnd = new Random(seed);
511 
512         for (int i = 0; i < 100; i++) {
513             // 1 == 2^0 <= unitSize == 2^k <= bb.capacity()/2
514             int unitSize = 1 << rnd.nextInt(maxPow2);
515             // 0 <= index < 2*unitSize
516             int index = rnd.nextInt(unitSize << 1);
517             int value = bb.alignmentOffset(index, unitSize);
518             try {
519                 if (value < 0 || value >= unitSize) {
520                     throw new RuntimeException(value + " < 0 || " +
521                         value + " >= " + unitSize);
522                 }
523                 if (value <= index &&
524                     bb.alignmentOffset(index - value, unitSize) != 0)
525                     throw new RuntimeException("Identity 1");
526                 if (bb.alignmentOffset(index + (unitSize - value),
527                     unitSize) != 0)
528                     throw new RuntimeException("Identity 2");
529             } catch (RuntimeException re) {
530                 System.err.format("seed %d, index %d, unitSize %d, value %d%n",
531                     seed, index, unitSize, value);
532                 throw re;
533             }
534         }
535     }
536 
mappedBuffers()537     private static MappedByteBuffer[] mappedBuffers() throws IOException {
538         return new MappedByteBuffer[]{
539                 createMappedBuffer(new byte[]{0, 1, 2, 3}),
540                 createMappedBuffer(new byte[]{0, 1, 2, -3,
541                     45, 6, 7, 78, 3, -7, 6, 7, -128, 127}),
542         };
543     }
544 
createMappedBuffer(byte[] contents)545     private static MappedByteBuffer createMappedBuffer(byte[] contents)
546         throws IOException {
547         Path tempFile = Files.createTempFile("mbb", null);
548         tempFile.toFile().deleteOnExit();
549         Files.write(tempFile, contents);
550         try (FileChannel fc = FileChannel.open(tempFile)) {
551             MappedByteBuffer map =
552                 fc.map(FileChannel.MapMode.READ_ONLY, 0, contents.length);
553             map.load();
554             return map;
555         }
556     }
557 
558 
fail(String problem, ByteBuffer xb, ByteBuffer yb, byte x, byte y)559     private static void fail(String problem,
560                              ByteBuffer xb, ByteBuffer yb,
561                              byte x, byte y) {
562         fail(problem + String.format(": x=%s y=%s", x, y), xb, yb);
563     }
564 
catchNullArgument(Buffer b, Runnable thunk)565     private static void catchNullArgument(Buffer b, Runnable thunk) {
566         tryCatch(b, NullPointerException.class, thunk);
567     }
568 
catchIllegalArgument(Buffer b, Runnable thunk)569     private static void catchIllegalArgument(Buffer b, Runnable thunk) {
570         tryCatch(b, IllegalArgumentException.class, thunk);
571     }
572 
catchReadOnlyBuffer(Buffer b, Runnable thunk)573     private static void catchReadOnlyBuffer(Buffer b, Runnable thunk) {
574         tryCatch(b, ReadOnlyBufferException.class, thunk);
575     }
576 
catchIndexOutOfBounds(Buffer b, Runnable thunk)577     private static void catchIndexOutOfBounds(Buffer b, Runnable thunk) {
578         tryCatch(b, IndexOutOfBoundsException.class, thunk);
579     }
580 
catchIndexOutOfBounds(byte[] t, Runnable thunk)581     private static void catchIndexOutOfBounds(byte[] t, Runnable thunk) {
582         tryCatch(t, IndexOutOfBoundsException.class, thunk);
583     }
584 
tryCatch(Buffer b, Class<?> ex, Runnable thunk)585     private static void tryCatch(Buffer b, Class<?> ex, Runnable thunk) {
586         boolean caught = false;
587         try {
588             thunk.run();
589         } catch (Throwable x) {
590             if (ex.isAssignableFrom(x.getClass())) {
591                 caught = true;
592             } else {
593                 String s = x.getMessage();
594                 if (s == null)
595                     s = x.getClass().getName();
596                 fail(s + " not expected");
597             }
598         }
599         if (!caught) {
600             fail(ex.getName() + " not thrown", b);
601         }
602     }
603 
tryCatch(byte[] t, Class<?> ex, Runnable thunk)604     private static void tryCatch(byte[] t, Class<?> ex, Runnable thunk) {
605         tryCatch(ByteBuffer.wrap(t), ex, thunk);
606     }
607 
608     // Android-changed: Add @SuppressWarnings as the operation is tested to be reflexive.
609     @SuppressWarnings({"SelfComparison", "SelfEquals"})
test(int level, final ByteBuffer b, boolean direct)610     public static void test(int level, final ByteBuffer b, boolean direct) {
611 
612         show(level, b);
613 
614         if (direct != b.isDirect())
615             fail("Wrong direction", b);
616 
617         // Gets and puts
618 
619         relPut(b);
620         relGet(b);
621         absGet(b);
622         bulkGet(b);
623 
624         absPut(b);
625         relGet(b);
626         absGet(b);
627         bulkGet(b);
628 
629         bulkPutArray(b);
630         relGet(b);
631 
632         bulkPutBuffer(b);
633         relGet(b);
634 
635         absBulkPutArray(b);
636         absBulkGet(b);
637 
638 
639 
640 
641 
642 
643 
644 
645 
646 
647 
648 
649 
650 
651 
652 
653 
654 
655 
656 
657 
658 
659 
660 
661 
662 
663 
664 
665 
666 
667 
668 
669 
670 
671 
672 
673 
674         // Compact
675 
676         relPut(b);
677         b.position(13);
678         b.compact();
679         b.flip();
680         relGet(b, 13);
681 
682         // Exceptions
683 
684         relPut(b);
685         b.limit(b.capacity() / 2);
686         b.position(b.limit());
687 
688         tryCatch(b, BufferUnderflowException.class, () -> b.get());
689         tryCatch(b, BufferOverflowException.class, () -> b.put((byte)42));
690         // The index must be non-negative and less than the buffer's limit.
691         catchIndexOutOfBounds(b, () -> b.get(b.limit()));
692         catchIndexOutOfBounds(b, () -> b.get(-1));
693         catchIndexOutOfBounds(b, () -> b.put(b.limit(), (byte)42));
694         tryCatch(b, InvalidMarkException.class,
695                 // Android-changed: Explicit casting due to @CovariantReturnType methods.
696                 // () -> b.position(0).mark().compact().reset());
697                 () -> ((ByteBuffer) b.position(0).mark()).compact().reset());
698 
699         try {
700             b.position(b.limit() + 1);
701             fail("IllegalArgumentException expected for position beyond limit");
702         } catch (IllegalArgumentException e) {
703             if (e.getMessage() == null) {
704                 fail("Non-null IllegalArgumentException message expected for"
705                      + " position beyond limit");
706             }
707         }
708 
709         try {
710             b.position(-1);
711             fail("IllegalArgumentException expected for negative position");
712         } catch (IllegalArgumentException e) {
713             if (e.getMessage() == null) {
714                 fail("Non-null IllegalArgumentException message expected for"
715                      + " negative position");
716             }
717         }
718 
719         try {
720             b.limit(b.capacity() + 1);
721             fail("IllegalArgumentException expected for limit beyond capacity");
722         } catch (IllegalArgumentException e) {
723             if (e.getMessage() == null) {
724                 fail("Non-null IllegalArgumentException message expected for"
725                      + " limit beyond capacity");
726             }
727         }
728 
729         try {
730             b.limit(-1);
731             fail("IllegalArgumentException expected for negative limit");
732         } catch (IllegalArgumentException e) {
733             if (e.getMessage() == null) {
734                 fail("Non-null IllegalArgumentException message expected for"
735                      + " negative limit");
736             }
737         }
738 
739         // Exceptions in absolute bulk and slice operations
740 
741         catchNullArgument(b, () -> b.get(7, null, 0, 42));
742         catchNullArgument(b, () -> b.put(7, (byte[])null, 0, 42));
743 
744         byte[] tmpa = new byte[42];
745         catchIndexOutOfBounds(b, () -> b.get(7, tmpa, -1, 42));
746         catchIndexOutOfBounds(b, () -> b.get(7, tmpa, 42, 1));
747         catchIndexOutOfBounds(b, () -> b.get(7, tmpa, 41, -1));
748         catchIndexOutOfBounds(b, () -> b.get(-1, tmpa, 0, 1));
749         catchIndexOutOfBounds(b, () -> b.get(b.limit(), tmpa, 0, 1));
750         catchIndexOutOfBounds(b, () -> b.get(b.limit() - 41, tmpa, 0, 42));
751 
752         catchIndexOutOfBounds(b, () -> b.put(7, tmpa, -1, 42));
753         catchIndexOutOfBounds(b, () -> b.put(7, tmpa, 42, 1));
754         catchIndexOutOfBounds(b, () -> b.put(7, tmpa, 41, -1));
755         catchIndexOutOfBounds(b, () -> b.put(-1, tmpa, 0, 1));
756         catchIndexOutOfBounds(b, () -> b.put(b.limit(), tmpa, 0, 1));
757         catchIndexOutOfBounds(b, () -> b.put(b.limit() - 41, tmpa, 0, 42));
758 
759         catchIndexOutOfBounds(b, () -> b.slice(-1, 7));
760         catchIndexOutOfBounds(b, () -> b.slice(b.limit() + 1, 7));
761         catchIndexOutOfBounds(b, () -> b.slice(0, -1));
762         catchIndexOutOfBounds(b, () -> b.slice(7, b.limit() - 7 + 1));
763 
764         // Values
765 
766         b.clear();
767         b.put((byte)0);
768         b.put((byte)-1);
769         b.put((byte)1);
770         b.put(Byte.MAX_VALUE);
771         b.put(Byte.MIN_VALUE);
772 
773 
774 
775 
776 
777 
778 
779 
780 
781 
782 
783 
784 
785 
786 
787 
788 
789         b.flip();
790         ck(b, b.get(), 0);
791         ck(b, b.get(), (byte)-1);
792         ck(b, b.get(), 1);
793         ck(b, b.get(), Byte.MAX_VALUE);
794         ck(b, b.get(), Byte.MIN_VALUE);
795 
796 
797 
798 
799 
800 
801 
802 
803 
804 
805 
806 
807 
808 
809 
810 
811 
812 
813 
814 
815 
816 
817 
818 
819 
820 
821 
822         // Comparison
823         b.rewind();
824         ByteBuffer b2 = ByteBuffer.allocate(b.capacity());
825         b2.put(b);
826         b2.flip();
827         b.position(2);
828         b2.position(2);
829         if (!b.equals(b2)) {
830             for (int i = 2; i < b.limit(); i++) {
831                 byte x = b.get(i);
832                 byte y = b2.get(i);
833                 if (x != y
834 
835 
836 
837 
838 
839 
840                     ) {
841                     out.println("[" + i + "] " + x + " != " + y);
842                 }
843             }
844             fail("Identical buffers not equal", b, b2);
845         }
846         if (b.compareTo(b2) != 0) {
847             fail("Comparison to identical buffer != 0", b, b2);
848         }
849         b.limit(b.limit() + 1);
850         b.position(b.limit() - 1);
851         b.put((byte)99);
852         b.rewind();
853         b2.rewind();
854         if (b.equals(b2))
855             fail("Non-identical buffers equal", b, b2);
856         if (b.compareTo(b2) <= 0)
857             fail("Comparison to shorter buffer <= 0", b, b2);
858         b.limit(b.limit() - 1);
859 
860         b.put(2, (byte)42);
861         if (b.equals(b2))
862             fail("Non-identical buffers equal", b, b2);
863         if (b.compareTo(b2) <= 0)
864             fail("Comparison to lesser buffer <= 0", b, b2);
865 
866         // Check equals and compareTo with interesting values
867         for (byte x : VALUES) {
868             ByteBuffer xb = ByteBuffer.wrap(new byte[] { x });
869             if (xb.compareTo(xb) != 0) {
870                 fail("compareTo not reflexive", xb, xb, x, x);
871             }
872             if (!xb.equals(xb)) {
873                 fail("equals not reflexive", xb, xb, x, x);
874             }
875             for (byte y : VALUES) {
876                 ByteBuffer yb = ByteBuffer.wrap(new byte[] { y });
877                 if (xb.compareTo(yb) != - yb.compareTo(xb)) {
878                     fail("compareTo not anti-symmetric",
879                          xb, yb, x, y);
880                 }
881                 if ((xb.compareTo(yb) == 0) != xb.equals(yb)) {
882                     fail("compareTo inconsistent with equals",
883                          xb, yb, x, y);
884                 }
885                 if (xb.compareTo(yb) != Byte.compare(x, y)) {
886 
887 
888 
889 
890 
891 
892                     fail("Incorrect results for ByteBuffer.compareTo",
893                          xb, yb, x, y);
894                 }
895 
896 
897 
898 
899 
900 
901 
902 
903 
904                 if (xb.equals(yb) != (x == y)) {
905                     fail("Incorrect results for ByteBuffer.equals",
906                          xb, yb, x, y);
907                 }
908 
909 
910 
911 
912 
913 
914 
915             }
916         }
917 
918         // Sub, dup
919 
920         relPut(b);
921         relGet(b.duplicate());
922         b.position(13);
923         relGet(b.duplicate(), 13);
924         relGet(b.duplicate().slice(), 13);
925         relGet(b.slice(), 13);
926         relGet(b.slice().duplicate(), 13);
927 
928         // Slice
929 
930         b.position(5);
931         ByteBuffer sb = b.slice();
932         checkSlice(b, sb);
933         b.position(0);
934         ByteBuffer sb2 = sb.slice();
935         checkSlice(sb, sb2);
936 
937         if (!sb.equals(sb2))
938             fail("Sliced slices do not match", sb, sb2);
939         if ((sb.hasArray()) && (sb.arrayOffset() != sb2.arrayOffset())) {
940             fail("Array offsets do not match: "
941                  + sb.arrayOffset() + " != " + sb2.arrayOffset(), sb, sb2);
942         }
943 
944         int bPos = b.position();
945         int bLim = b.limit();
946 
947         b.position(7);
948         b.limit(42);
949         ByteBuffer rsb = b.slice();
950         b.position(0);
951         b.limit(b.capacity());
952         ByteBuffer asb = b.slice(7, 35);
953         checkSlice(rsb, asb);
954 
955         b.position(bPos);
956         b.limit(bLim);
957 
958 
959 
960         // Views
961 
962         b.clear();
963         b.order(ByteOrder.BIG_ENDIAN);
964         testViews(level + 1, b, direct);
965 
966         for (int i = 1; i <= 9; i++) {
967             b.position(i);
968             show(level + 1, b);
969             testViews(level + 2, b, direct);
970         }
971 
972         b.position(0);
973         b.order(ByteOrder.LITTLE_ENDIAN);
974         testViews(level + 1, b, direct);
975 
976         // Heterogeneous accessors
977 
978         b.order(ByteOrder.BIG_ENDIAN);
979         for (int i = 0; i <= 9; i++) {
980             b.position(i);
981             testHet(level + 1, b);
982         }
983         b.order(ByteOrder.LITTLE_ENDIAN);
984         b.position(3);
985         testHet(level + 1, b);
986 
987 
988 
989         // Read-only views
990 
991         b.rewind();
992         final ByteBuffer rb = b.asReadOnlyBuffer();
993         if (!b.equals(rb))
994             fail("Buffer not equal to read-only view", b, rb);
995         show(level + 1, rb);
996 
997         catchReadOnlyBuffer(b, () -> relPut(rb));
998         catchReadOnlyBuffer(b, () -> absPut(rb));
999         catchReadOnlyBuffer(b, () -> bulkPutArray(rb));
1000         catchReadOnlyBuffer(b, () -> bulkPutBuffer(rb));
1001         catchReadOnlyBuffer(b, () -> absBulkPutArray(rb));
1002 
1003         // put(ByteBuffer) should not change source position
1004         final ByteBuffer src = ByteBuffer.allocate(1);
1005         catchReadOnlyBuffer(b, () -> rb.put(src));
1006         ck(src, src.position(), 0);
1007 
1008         catchReadOnlyBuffer(b, () -> rb.compact());
1009 
1010 
1011 
1012         catchReadOnlyBuffer(b, () -> rb.putChar((char)1));
1013         catchReadOnlyBuffer(b, () -> rb.putChar(0, (char)1));
1014         catchReadOnlyBuffer(b, () -> rb.putShort((short)1));
1015         catchReadOnlyBuffer(b, () -> rb.putShort(0, (short)1));
1016         catchReadOnlyBuffer(b, () -> rb.putInt(1));
1017         catchReadOnlyBuffer(b, () -> rb.putInt(0, 1));
1018         catchReadOnlyBuffer(b, () -> rb.putLong((long)1));
1019         catchReadOnlyBuffer(b, () -> rb.putLong(0, (long)1));
1020         catchReadOnlyBuffer(b, () -> rb.putFloat((float)1));
1021         catchReadOnlyBuffer(b, () -> rb.putFloat(0, (float)1));
1022         catchReadOnlyBuffer(b, () -> rb.putDouble((double)1));
1023         catchReadOnlyBuffer(b, () -> rb.putDouble(0, (double)1));
1024 
1025 
1026 
1027 
1028 
1029 
1030 
1031 
1032 
1033 
1034 
1035         if (rb.getClass().getName().startsWith("java.nio.Heap")) {
1036             catchReadOnlyBuffer(b, () -> rb.array());
1037             catchReadOnlyBuffer(b, () -> rb.arrayOffset());
1038             if (rb.hasArray()) {
1039                 fail("Read-only heap buffer's backing array is accessible", rb);
1040             }
1041         }
1042 
1043         // Bulk puts from read-only buffers
1044 
1045         b.clear();
1046         rb.rewind();
1047         b.put(rb);
1048 
1049 
1050         // For byte buffers, test both the direct and non-direct cases
1051         ByteBuffer ob
1052             = (b.isDirect()
1053                ? ByteBuffer.allocate(rb.capacity())
1054                : ByteBuffer.allocateDirect(rb.capacity()));
1055         rb.rewind();
1056         ob.put(rb);
1057 
1058 
1059         relPut(b);                       // Required by testViews
1060 
1061 
1062         // Test alignment
1063 
1064         testAlign(b, direct);
1065 
1066     }
1067 
1068 
1069 
1070 
1071 
1072 
1073 
1074 
1075 
1076 
1077 
1078 
1079 
1080 
1081 
1082 
1083 
1084 
1085 
1086 
1087 
1088 
1089 
1090 
1091 
1092 
1093 
1094 
1095 
1096 
1097 
1098 
1099 
1100 
1101 
1102 
1103 
1104 
1105 
1106 
1107 
1108 
1109 
1110 
1111 
1112 
1113 
1114 
1115 
1116 
1117 
test(final byte [] ba)1118     public static void test(final byte [] ba) {
1119         int offset = 47;
1120         int length = 900;
1121         final ByteBuffer b = ByteBuffer.wrap(ba, offset, length);
1122         show(0, b);
1123         ck(b, b.capacity(), ba.length);
1124         ck(b, b.position(), offset);
1125         ck(b, b.limit(), offset + length);
1126 
1127         // The offset must be non-negative and no larger than <array.length>.
1128         catchIndexOutOfBounds(ba, () -> ByteBuffer.wrap(ba, -1, ba.length));
1129         catchIndexOutOfBounds(ba, () -> ByteBuffer.wrap(ba, ba.length + 1, ba.length));
1130         catchIndexOutOfBounds(ba, () -> ByteBuffer.wrap(ba, 0, -1));
1131         catchIndexOutOfBounds(ba, () -> ByteBuffer.wrap(ba, 0, ba.length + 1));
1132 
1133         // A NullPointerException will be thrown if the array is null.
1134         tryCatch(ba, NullPointerException.class,
1135                 () -> ByteBuffer.wrap((byte []) null, 0, 5));
1136         tryCatch(ba, NullPointerException.class,
1137                 () -> ByteBuffer.wrap((byte []) null));
1138     }
1139 
testAllocate()1140     private static void testAllocate() {
1141         // An IllegalArgumentException will be thrown for negative capacities.
1142         catchIllegalArgument((Buffer) null, () -> ByteBuffer.allocate(-1));
1143         try {
1144             ByteBuffer.allocate(-1);
1145         } catch (IllegalArgumentException e) {
1146             if (e.getMessage() == null) {
1147                 fail("Non-null IllegalArgumentException message expected for"
1148                      + " attempt to allocate negative capacity buffer");
1149             }
1150         }
1151 
1152         catchIllegalArgument((Buffer) null, () -> ByteBuffer.allocateDirect(-1));
1153         try {
1154             ByteBuffer.allocateDirect(-1);
1155         } catch (IllegalArgumentException e) {
1156             if (e.getMessage() == null) {
1157                 fail("Non-null IllegalArgumentException message expected for"
1158                      + " attempt to allocate negative capacity direct buffer");
1159             }
1160         }
1161 
1162     }
1163 
testToString()1164     public static void testToString() {
1165         final int cap = 10;
1166 
1167 
1168         ByteBuffer direct1 = ByteBuffer.allocateDirect(cap);
1169         if (!direct1.toString().equals(Basic.toString(direct1))) {
1170            fail("Direct buffer toString is incorrect: "
1171                   + direct1.toString() + " vs " + Basic.toString(direct1));
1172         }
1173 
1174 
1175 
1176         ByteBuffer nondirect1 = ByteBuffer.allocate(cap);
1177         if (!nondirect1.toString().equals(Basic.toString(nondirect1))) {
1178            fail("Heap buffer toString is incorrect: "
1179                   + nondirect1.toString() + " vs " + Basic.toString(nondirect1));
1180         }
1181 
1182     }
1183 
test()1184     public static void test() {
1185         testAllocate();
1186         test(0, ByteBuffer.allocate(7 * 1024), false);
1187         test(0, ByteBuffer.wrap(new byte[7 * 1024], 0, 7 * 1024), false);
1188         test(new byte[1024]);
1189 
1190         ByteBuffer b = ByteBuffer.allocateDirect(7 * 1024);
1191         for (b.position(0); b.position() < b.limit(); )
1192             ck(b, b.get(), 0);
1193         test(0, b, true);
1194 
1195 
1196 
1197 
1198 
1199         callReset(ByteBuffer.allocate(10));
1200 
1201 
1202 
1203 
1204 
1205 
1206         testToString();
1207 
1208         // Android-added: Add API coverage for get(), put().
1209         testGetPutArrayWithIndex();
1210 
1211 
1212 
1213     }
1214 
1215     // BEGIN Android-added: Add API coverage for get(), put().
testGetPutArrayWithIndex()1216     private static void testGetPutArrayWithIndex() {
1217         ByteBuffer buf = ByteBuffer.allocate(16);
1218         byte firstElement = 11, secondElement = 12;
1219         buf.put(firstElement);
1220         buf.put(secondElement);
1221         buf.position(0);
1222         byte[] arr = new byte[] { 4, 3, 2, 1 };
1223         buf.put(2, arr);
1224         byte[] actual = new byte[4];
1225         buf.get(2, actual);
1226         assertEquals(actual, arr);
1227         buf.get(0, actual);
1228         assertEquals(actual, new byte[] {firstElement, secondElement, 4, 3});
1229     }
1230 
1231 
1232 
1233 
1234 
1235 
1236 
1237 
1238 
1239 
1240 
1241 
1242 
1243 
1244 
1245 
1246 
1247 
1248 
1249 
1250 
1251 
1252 
1253 
1254 
1255 
1256 
1257 
1258 
1259 
1260 
1261 
1262 
1263 
1264 
1265 
1266 
1267 
1268 
1269 
1270 
1271 
1272 
1273 
1274 
1275 
1276 
1277 
1278 
1279 
1280     // END Android-added: Add API coverage for get(), put().
1281 }
1282