Source
1291
1291
hsize_t total_src_nbytes; /* Total number of bytes to copy */
1292
1292
size_t buf_size; /* Size of copy buffer */
1293
1293
void *buf = NULL; /* Buffer for copying data */
1294
1294
void *bkg = NULL; /* Temporary buffer for copying data */
1295
1295
void *reclaim_buf = NULL; /* Buffer for reclaiming data */
1296
1296
H5S_t *buf_space = NULL; /* Dataspace describing buffer */
1297
1297
hid_t buf_sid = -1; /* ID for buffer dataspace */
1298
1298
hsize_t buf_dim[1] = {0}; /* Dimension for buffer */
1299
1299
hbool_t is_vlen = FALSE; /* Flag to indicate that VL type conversion should occur */
1300
1300
hbool_t fix_ref = FALSE; /* Flag to indicate that ref values should be fixed */
1301
+
H5D_shared_t *shared_fo = cpy_info->shared_fo; /* Pointer to the shared struct for dataset object */
1302
+
hbool_t try_sieve = FALSE; /* Try to get data from the sieve buffer */
1303
+
haddr_t sieve_start = HADDR_UNDEF; /* Start location of sieve buffer */
1304
+
haddr_t sieve_end = HADDR_UNDEF; /* End locations of sieve buffer */
1301
1305
herr_t ret_value = SUCCEED; /* Return value */
1302
1306
1303
1307
FUNC_ENTER_PACKAGE
1304
1308
1305
1309
/* Check args */
1306
1310
HDassert(f_src);
1307
1311
HDassert(storage_src);
1308
1312
HDassert(f_dst);
1309
1313
HDassert(storage_dst);
1310
1314
HDassert(dt_src);
1411
1415
/* Need extra buffer for datatype conversions, to prevent stranding/leaking memory */
1412
1416
if(is_vlen || fix_ref) {
1413
1417
if(NULL == (reclaim_buf = H5FL_BLK_MALLOC(type_conv, buf_size)))
1414
1418
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed for copy buffer")
1415
1419
1416
1420
/* allocate temporary bkg buff for data conversion */
1417
1421
if(NULL == (bkg = H5FL_BLK_MALLOC(type_conv, buf_size)))
1418
1422
HGOTO_ERROR(H5E_RESOURCE, H5E_NOSPACE, FAIL, "memory allocation failed for copy buffer")
1419
1423
} /* end if */
1420
1424
1421
-
/* Loop over copying data */
1422
1425
addr_src = storage_src->addr;
1423
1426
addr_dst = storage_dst->addr;
1427
+
1428
+
/* If data sieving is enabled and the dataset is open in the file,
1429
+
set up to copy data out of the sieve buffer if deemed possible later */
1430
+
if(H5F_HAS_FEATURE(f_src, H5FD_FEAT_DATA_SIEVE) &&
1431
+
shared_fo && shared_fo->cache.contig.sieve_buf) {
1432
+
try_sieve = TRUE;
1433
+
sieve_start = shared_fo->cache.contig.sieve_loc;
1434
+
sieve_end = sieve_start + shared_fo->cache.contig.sieve_size;
1435
+
/*
1436
+
* It is possble for addr_src to be undefined when:
1437
+
* (a) The dataset is created and data is written to it.
1438
+
* (b) The dataset is then copied via H5Ocopy().
1439
+
* H5D_mark() in H5Dint.c is different between
1440
+
* 1.8 and develop branches:
1441
+
* 1.8--it just sets dataset->shared->layout_dirty as TRUE
1442
+
* to be flushed later.
1443
+
* develop--it will flush the layout message if it has been changed.
1444
+
*/
1445
+
if(!H5F_addr_defined(addr_src))
1446
+
addr_src = sieve_start;
1447
+
}
1448
+
1449
+
HDassert(H5F_addr_defined(addr_src));
1450
+
/* Loop over copying data */
1424
1451
while(total_src_nbytes > 0) {
1425
1452
/* Check if we should reduce the number of bytes to transfer */
1426
1453
if(total_src_nbytes < src_nbytes) {
1427
1454
/* Adjust bytes to transfer */
1428
1455
src_nbytes = (size_t)total_src_nbytes;
1429
1456
1430
1457
/* Adjust dataspace describing buffer */
1431
1458
if(is_vlen) {
1432
1459
/* Adjust destination & memory bytes to transfer */
1433
1460
nelmts = src_nbytes / src_dt_size;
1439
1466
1440
1467
/* Adjust size of buffer's dataspace */
1441
1468
if(H5S_set_extent_real(buf_space, buf_dim) < 0)
1442
1469
HGOTO_ERROR(H5E_DATASPACE, H5E_CANTSET, FAIL, "unable to change buffer dataspace size")
1443
1470
} /* end if */
1444
1471
else
1445
1472
/* Adjust destination & memory bytes to transfer */
1446
1473
dst_nbytes = mem_nbytes = src_nbytes;
1447
1474
} /* end if */
1448
1475
1449
-
/* Read raw data from source file */
1450
-
if(H5F_block_read(f_src, H5FD_MEM_DRAW, addr_src, src_nbytes, H5P_DATASET_XFER_DEFAULT, buf) < 0)
1451
-
HGOTO_ERROR(H5E_DATASET, H5E_READERROR, FAIL, "unable to read raw data")
1476
+
/* If the entire copy is within the sieve buffer, copy data from the sieve buffer */
1477
+
if(try_sieve && (addr_src >= sieve_start) && ((addr_src + src_nbytes -1) < sieve_end)) {
1478
+
unsigned char *base_sieve_buf = shared_fo->cache.contig.sieve_buf + (addr_src - sieve_start);
1479
+
1480
+
HDmemcpy(buf, base_sieve_buf, src_nbytes);
1481
+
} else
1482
+
/* Read raw data from source file */
1483
+
if(H5F_block_read(f_src, H5FD_MEM_DRAW, addr_src, src_nbytes, H5P_DATASET_XFER_DEFAULT, buf) < 0)
1484
+
HGOTO_ERROR(H5E_DATASET, H5E_READERROR, FAIL, "unable to read raw data")
1452
1485
1453
1486
/* Perform datatype conversion, if necessary */
1454
1487
if(is_vlen) {
1455
1488
/* Convert from source file to memory */
1456
-
if(H5T_convert(tpath_src_mem, tid_src, tid_mem, nelmts, (size_t)0, (size_t)0, buf, bkg, dxpl_id) < 0)
1489
+
if(H5T_convert(tpath_src_mem, tid_src, tid_mem, nelmts, (size_t)0, (size_t)0, buf, bkg, dxpl_id) < 0)
1457
1490
HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "datatype conversion failed")
1458
1491
1459
1492
/* Copy into another buffer, to reclaim memory later */
1460
1493
HDmemcpy(reclaim_buf, buf, mem_nbytes);
1461
1494
1462
1495
/* Set background buffer to all zeros */
1463
1496
HDmemset(bkg, 0, buf_size);
1464
1497
1465
1498
/* Convert from memory to destination file */
1466
-
if(H5T_convert(tpath_mem_dst, tid_mem, tid_dst, nelmts, (size_t)0, (size_t)0, buf, bkg, dxpl_id) < 0)
1499
+
if(H5T_convert(tpath_mem_dst, tid_mem, tid_dst, nelmts, (size_t)0, (size_t)0, buf, bkg, dxpl_id) < 0)
1467
1500
HGOTO_ERROR(H5E_DATATYPE, H5E_CANTINIT, FAIL, "datatype conversion failed")
1468
1501
1469
1502
/* Reclaim space from variable length data */
1470
1503
if(H5D_vlen_reclaim(tid_mem, buf_space, H5P_DATASET_XFER_DEFAULT, reclaim_buf) < 0)
1471
1504
HGOTO_ERROR(H5E_DATASET, H5E_BADITER, FAIL, "unable to reclaim variable-length data")
1472
-
} /* end if */
1505
+
} /* end if */
1473
1506
else if(fix_ref) {
1474
1507
/* Check for expanding references */
1475
1508
if(cpy_info->expand_ref) {
1476
1509
size_t ref_count;
1477
1510
1478
1511
/* Determine # of reference elements to copy */
1479
1512
ref_count = src_nbytes / H5T_get_size(dt_src);
1480
1513
1481
1514
/* Copy the reference elements */
1482
1515
if(H5O_copy_expand_ref(f_src, buf, dxpl_id, f_dst, bkg, ref_count, H5T_get_ref_type(dt_src), cpy_info) < 0)