49
49
50
50
/*
51
51
* @test
52
- * @bug 8245121
52
+ * @bug 8219014 8245121
53
53
* @summary Ensure that a bulk put of a buffer into another is correct.
54
54
* @compile --enable-preview -source ${jdk.version} BulkPutBuffer.java
55
55
* @run testng/othervm --enable-preview BulkPutBuffer
@@ -142,9 +142,11 @@ public static class BufferProxy {
142
142
MethodHandle alloc ;
143
143
MethodHandle allocBB ;
144
144
MethodHandle allocDirect ;
145
+ MethodHandle asReadOnlyBuffer ;
145
146
MethodHandle asTypeBuffer ;
146
147
MethodHandle putAbs ;
147
148
MethodHandle getAbs ;
149
+ MethodHandle putBufAbs ;
148
150
MethodHandle putBufRel ;
149
151
MethodHandle equals ;
150
152
@@ -168,6 +170,9 @@ public static class BufferProxy {
168
170
MethodType .methodType (ByteBuffer .class , int .class ));
169
171
allocDirect = lookup .findStatic (ByteBuffer .class , "allocateDirect" ,
170
172
MethodType .methodType (ByteBuffer .class , int .class ));
173
+
174
+ asReadOnlyBuffer = lookup .findVirtual (bufferType ,
175
+ "asReadOnlyBuffer" , MethodType .methodType (bufferType ));
171
176
if (elementType != byte .class ) {
172
177
asTypeBuffer = lookup .findVirtual (ByteBuffer .class ,
173
178
"as" + name + "Buffer" , MethodType .methodType (bufferType ));
@@ -177,8 +182,13 @@ public static class BufferProxy {
177
182
MethodType .methodType (bufferType , int .class , elementType ));
178
183
getAbs = lookup .findVirtual (bufferType , "get" ,
179
184
MethodType .methodType (elementType , int .class ));
185
+
186
+ putBufAbs = lookup .findVirtual (bufferType , "put" ,
187
+ MethodType .methodType (bufferType , int .class , bufferType ,
188
+ int .class , int .class ));
180
189
putBufRel = lookup .findVirtual (bufferType , "put" ,
181
190
MethodType .methodType (bufferType , bufferType ));
191
+
182
192
equals = lookup .findVirtual (bufferType , "equals" ,
183
193
MethodType .methodType (boolean .class , Object .class ));
184
194
@@ -239,6 +249,25 @@ void copy(Buffer src, int srcOff, Buffer dst, int dstOff, int length)
239
249
}
240
250
}
241
251
252
+ Buffer asReadOnlyBuffer (Buffer buf ) throws Throwable {
253
+ try {
254
+ return (Buffer )asReadOnlyBuffer .invoke (buf );
255
+ } catch (Exception e ) {
256
+ throw new AssertionError (e );
257
+ }
258
+ }
259
+
260
+ void put (Buffer src , int srcOff , Buffer dst , int dstOff , int length )
261
+ throws Throwable {
262
+ try {
263
+ putBufAbs .invoke (dst , dstOff , src , srcOff , length );
264
+ } catch (ReadOnlyBufferException ro ) {
265
+ throw ro ;
266
+ } catch (Exception e ) {
267
+ throw new AssertionError (e );
268
+ }
269
+ }
270
+
242
271
void put (Buffer src , Buffer dst ) throws Throwable {
243
272
try {
244
273
putBufRel .invoke (dst , src );
@@ -294,6 +323,40 @@ static Object[][] proxyPairs() {
294
323
return args .toArray (Object [][]::new );
295
324
}
296
325
326
+ private static void expectThrows (Class <?> exClass , Assert .ThrowingRunnable r ) {
327
+ try {
328
+ r .run ();
329
+ } catch (Throwable e ) {
330
+ if (e .getClass () != exClass && e .getCause ().getClass () != exClass ) {
331
+ throw new RuntimeException ("Expected " + exClass +
332
+ "; got " + e .getCause ().getClass (), e );
333
+ }
334
+ }
335
+ }
336
+
337
+ @ Test (dataProvider = "proxies" )
338
+ public static void testExceptions (BufferProxy bp ) throws Throwable {
339
+ int cap = 27 ;
340
+ Buffer buf = bp .create (cap );
341
+
342
+ expectThrows (IndexOutOfBoundsException .class ,
343
+ () -> bp .put (buf , -1 , buf , 0 , 1 ));
344
+ expectThrows (IndexOutOfBoundsException .class ,
345
+ () -> bp .put (buf , 0 , buf , -1 , 1 ));
346
+ expectThrows (IndexOutOfBoundsException .class ,
347
+ () -> bp .put (buf , 1 , buf , 0 , cap ));
348
+ expectThrows (IndexOutOfBoundsException .class ,
349
+ () -> bp .put (buf , 0 , buf , 1 , cap ));
350
+ expectThrows (IndexOutOfBoundsException .class ,
351
+ () -> bp .put (buf , 0 , buf , 0 , cap + 1 ));
352
+ expectThrows (IndexOutOfBoundsException .class ,
353
+ () -> bp .put (buf , 0 , buf , 0 , Integer .MAX_VALUE ));
354
+
355
+ Buffer rob = buf .isReadOnly () ? buf : bp .asReadOnlyBuffer (buf );
356
+ expectThrows (ReadOnlyBufferException .class ,
357
+ () -> bp .put (buf , 0 , rob , 0 , cap ));
358
+ }
359
+
297
360
@ Test (dataProvider = "proxies" )
298
361
public static void testSelf (BufferProxy bp ) throws Throwable {
299
362
for (int i = 0 ; i < ITERATIONS ; i ++) {
@@ -311,22 +374,27 @@ public static void testSelf(BufferProxy bp) throws Throwable {
311
374
Assert .expectThrows (ReadOnlyBufferException .class ,
312
375
() -> bp .copy (lower , 0 , lowerCopy , 0 , lowerLength ));
313
376
break ;
314
- } else {
315
- bp .copy (lower , 0 , lowerCopy , 0 , lowerLength );
316
377
}
378
+ bp .copy (lower , 0 , lowerCopy , 0 , lowerLength );
317
379
318
380
int middleOffset = RND .nextInt (1 + cap /2 );
319
381
Buffer middle = buf .slice (middleOffset , lowerLength );
382
+ Buffer middleCopy = bp .create (lowerLength );
383
+ bp .copy (middle , 0 , middleCopy , 0 , lowerLength );
320
384
321
- if (middle .isReadOnly ()) {
322
- Assert .expectThrows (ReadOnlyBufferException .class ,
323
- () -> bp .put (lower , middle ));
324
- break ;
325
- } else {
326
- bp .put (lower , middle );
327
- }
385
+ bp .put (lower , middle );
328
386
middle .flip ();
329
387
388
+ Assert .assertTrue (bp .equals (lowerCopy , middle ),
389
+ String .format ("%d %s %d %d %d %d%n" , SEED ,
390
+ buf .getClass ().getName (), cap ,
391
+ lowerOffset , lowerLength , middleOffset ));
392
+
393
+ bp .copy (lowerCopy , 0 , buf , lowerOffset , lowerLength );
394
+ bp .copy (middleCopy , 0 , buf , middleOffset , lowerLength );
395
+
396
+ bp .put (buf , lowerOffset , buf , middleOffset , lowerLength );
397
+
330
398
Assert .assertTrue (bp .equals (lowerCopy , middle ),
331
399
String .format ("%d %s %d %d %d %d%n" , SEED ,
332
400
buf .getClass ().getName (), cap ,
@@ -361,13 +429,29 @@ public static void testPairs(BufferProxy bp, BufferProxy sbp) throws Throwable {
361
429
Assert .expectThrows (ReadOnlyBufferException .class ,
362
430
() -> bp .put (src , buf ));
363
431
break ;
364
- } else {
365
- bp .put (src , buf );
366
432
}
367
433
434
+ Buffer backup = bp .create (slim - spos );
435
+ bp .copy (buf , pos , backup , 0 , backup .capacity ());
436
+ bp .put (src , buf );
437
+
368
438
buf .reset ();
369
439
src .reset ();
370
440
441
+ Assert .assertTrue (bp .equals (src , buf ),
442
+ String .format ("%d %s %d %d %d %s %d %d %d%n" , SEED ,
443
+ buf .getClass ().getName (), cap , pos , lim ,
444
+ src .getClass ().getName (), scap , spos , slim ));
445
+
446
+ src .clear ();
447
+ buf .clear ();
448
+ bp .copy (backup , 0 , buf , pos , backup .capacity ());
449
+ bp .put (src , spos , buf , pos , backup .capacity ());
450
+ src .position (spos );
451
+ src .limit (slim );
452
+ buf .position (pos );
453
+ buf .limit (lim );
454
+
371
455
Assert .assertTrue (bp .equals (src , buf ),
372
456
String .format ("%d %s %d %d %d %s %d %d %d%n" , SEED ,
373
457
buf .getClass ().getName (), cap , pos , lim ,
0 commit comments