extern "C" { #include "utils/testMacros.h" #include "utils/zfpChecksums.h" #include "utils/zfpHash.h" } #include "src/template/codec.h" #include "gtest/gtest.h" #define SX 2 #define SY (3 * BLOCK_SIDE_LEN*SX) #define SZ (2 * BLOCK_SIDE_LEN*SY) #define SW (3 * BLOCK_SIDE_LEN*SZ) #define PX 1 #define PY 2 #define PZ 3 #define PW 4 #define DUMMY_VAL 99 void populateArray(SCALAR** dataArr) { *dataArr = new SCALAR[BLOCK_SIZE]; ASSERT_TRUE(*dataArr != nullptr); for (int i = 0; i < BLOCK_SIZE; i++) { #ifdef FL_PT_DATA (*dataArr)[i] = nextSignedRandFlPt(); #else (*dataArr)[i] = nextSignedRandInt(); #endif } } void populateStridedArray(SCALAR** dataArr, SCALAR dummyVal) { size_t i, j, k, l, countX, countY, countZ, countW; switch(DIMS) { case 1: countX = BLOCK_SIDE_LEN * SX; *dataArr = new SCALAR[countX]; ASSERT_TRUE(*dataArr != nullptr); for (i = 0; i < countX; i++) { if (i % SX) { (*dataArr)[i] = dummyVal; } else { #ifdef FL_PT_DATA (*dataArr)[i] = nextSignedRandFlPt(); #else (*dataArr)[i] = nextSignedRandInt(); #endif } } break; case 2: countX = BLOCK_SIDE_LEN * SX; countY = SY / SX; *dataArr = new SCALAR[countX * countY]; ASSERT_TRUE(*dataArr != nullptr); for (j = 0; j < countY; j++) { for (i = 0; i < countX; i++) { size_t index = countX*j + i; if (i % (countX/BLOCK_SIDE_LEN) || j % (countY/BLOCK_SIDE_LEN)) { (*dataArr)[index] = dummyVal; } else { #ifdef FL_PT_DATA (*dataArr)[index] = nextSignedRandFlPt(); #else (*dataArr)[index] = nextSignedRandInt(); #endif } } } break; case 3: countX = BLOCK_SIDE_LEN * SX; countY = SY / SX; countZ = SZ / SY; *dataArr = new SCALAR[countX * countY * countZ]; ASSERT_TRUE(*dataArr != nullptr); for (k = 0; k < countZ; k++) { for (j = 0; j < countY; j++) { for (i = 0; i < countX; i++) { size_t index = countX*countY*k + countX*j + i; if (i % (countX/BLOCK_SIDE_LEN) || j % (countY/BLOCK_SIDE_LEN) || k % (countZ/BLOCK_SIDE_LEN)) { (*dataArr)[index] = dummyVal; } else { #ifdef FL_PT_DATA (*dataArr)[index] = nextSignedRandFlPt(); #else (*dataArr)[index] = nextSignedRandInt(); #endif } } } } break; case 4: countX = BLOCK_SIDE_LEN * SX; countY = SY / SX; countZ = SZ / SY; countW = SW / SZ; *dataArr = new SCALAR[countX * countY * countZ * countW]; ASSERT_TRUE(*dataArr != nullptr); for (l = 0; l < countW; l++) { for (k = 0; k < countZ; k++) { for (j = 0; j < countY; j++) { for (i = 0; i < countX; i++) { size_t index = countX*countY*countZ*l + countX*countY*k + countX*j + i; if (i % (countX/BLOCK_SIDE_LEN) || j % (countY/BLOCK_SIDE_LEN) || k % (countZ/BLOCK_SIDE_LEN) || l % (countW/BLOCK_SIDE_LEN)) { (*dataArr)[index] = dummyVal; } else { #ifdef FL_PT_DATA (*dataArr)[index] = nextSignedRandFlPt(); #else (*dataArr)[index] = nextSignedRandInt(); #endif } } } } } break; } } void setupStream(zfp_field** field, zfp_stream** stream, bool isStrided = false) { *stream = zfp_stream_open(NULL); zfp_stream_set_rate(*stream, ZFP_RATE_PARAM_BITS, ZFP_TYPE, DIMS, zfp_false); size_t bufsizeBytes = zfp_stream_maximum_size(*stream, *field); char* buffer = (char*)calloc(bufsizeBytes, sizeof(char)); ASSERT_TRUE(buffer != nullptr); bitstream* s = stream_open(buffer, bufsizeBytes); ASSERT_TRUE(s != nullptr); if (isStrided) { switch (DIMS) { case 1: { zfp_field_set_stride_1d(*field, SX); break; } case 2: { zfp_field_set_stride_2d(*field, SX, SY); break; } case 3: { zfp_field_set_stride_3d(*field, SX, SY, SZ); break; } case 4: { zfp_field_set_stride_4d(*field, SX, SY, SZ, SW); break; } } } zfp_stream_set_bit_stream(*stream, s); } bool streamsEqual(zfp_stream** stream1, zfp_stream** stream2) { bitstream* s1 = zfp_stream_bit_stream(*stream1); size_t sz1 = stream_size(s1); char* data1 = (char*)stream_data(s1); zfp_stream_flush(*stream1); bitstream* s2 = zfp_stream_bit_stream(*stream2); size_t sz2 = stream_size(s2); char* data2 = (char*)stream_data(s2); zfp_stream_flush(*stream2); for (size_t i = 0; i < sz1; i++) if (data1[i] != data2[i]) return false; return true; } TEST(TemplatedEncodeTests, given_TemplatedEncodeBlock_resultsMatchNonTemplated) { SCALAR* dataArr; populateArray(&dataArr); zfp_field* field = ZFP_FIELD_FUNC(dataArr, ZFP_TYPE, _repeat_arg(BLOCK_SIDE_LEN, DIMS)); zfp_stream* stream = zfp_stream_open(NULL); setupStream(&field, &stream); size_t sz = ZFP_ENCODE_BLOCK_FUNC(stream, dataArr); zfp_stream* tstream = zfp_stream_open(NULL); setupStream(&field, &tstream); size_t tsz = encode_block(tstream, dataArr); ASSERT_TRUE(sz == tsz); ASSERT_TRUE(streamsEqual(&stream, &tstream)); zfp_field_free(field); stream_close(zfp_stream_bit_stream(stream)); stream_close(zfp_stream_bit_stream(tstream)); zfp_stream_close(stream); zfp_stream_close(tstream); delete[] dataArr; } TEST(TemplatedEncodeTests, given_TemplatedEncodeBlockStrided_resultsMatchNonTemplated) { SCALAR* dataArr; populateStridedArray(&dataArr, DUMMY_VAL); zfp_field* field = ZFP_FIELD_FUNC(dataArr, ZFP_TYPE, _repeat_arg(BLOCK_SIDE_LEN, DIMS)); zfp_stream* stream = zfp_stream_open(NULL); setupStream(&field, &stream, true); zfp_stream* tstream = zfp_stream_open(NULL); setupStream(&field, &tstream, true); #if DIMS == 1 size_t sz = ZFP_ENCODE_BLOCK_STRIDED_FUNC(stream, dataArr, SX); size_t tsz = encode_block_strided(tstream, dataArr, SX); #elif DIMS == 2 size_t sz = ZFP_ENCODE_BLOCK_STRIDED_FUNC(stream, dataArr, SX, SY); size_t tsz = encode_block_strided(tstream, dataArr, SX, SY); #elif DIMS == 3 size_t sz = ZFP_ENCODE_BLOCK_STRIDED_FUNC(stream, dataArr, SX, SY, SZ); size_t tsz = encode_block_strided(tstream, dataArr, SX, SY, SZ); #elif DIMS == 4 size_t sz = ZFP_ENCODE_BLOCK_STRIDED_FUNC(stream, dataArr, SX, SY, SZ, SW); size_t tsz = encode_block_strided(tstream, dataArr, SX, SY, SZ, SW); #endif ASSERT_TRUE(sz == tsz); ASSERT_TRUE(streamsEqual(&stream, &tstream)); zfp_field_free(field); stream_close(zfp_stream_bit_stream(stream)); stream_close(zfp_stream_bit_stream(tstream)); zfp_stream_close(stream); zfp_stream_close(tstream); delete[] dataArr; } TEST(TemplatedEncodeTests, given_TemplatedEncodePartialBlockStrided_resultsMatchNonTemplated) { SCALAR* dataArr; populateStridedArray(&dataArr, DUMMY_VAL); zfp_field* field = ZFP_FIELD_FUNC(dataArr, ZFP_TYPE, _repeat_arg(BLOCK_SIDE_LEN, DIMS)); zfp_stream* stream = zfp_stream_open(NULL); setupStream(&field, &stream, true); zfp_stream* tstream = zfp_stream_open(NULL); setupStream(&field, &tstream, true); #if DIMS == 1 size_t sz = ZFP_ENCODE_PARTIAL_BLOCK_STRIDED_FUNC(stream, dataArr, PX, SX); size_t tsz = encode_partial_block_strided(tstream, dataArr, PX, SX); #elif DIMS == 2 size_t sz = ZFP_ENCODE_PARTIAL_BLOCK_STRIDED_FUNC(stream, dataArr, PX, PY, SX, SY); size_t tsz = encode_partial_block_strided(tstream, dataArr, PX, PY, SX, SY); #elif DIMS == 3 size_t sz = ZFP_ENCODE_PARTIAL_BLOCK_STRIDED_FUNC(stream, dataArr, PX, PY, PZ, SX, SY, SZ); size_t tsz = encode_partial_block_strided(tstream, dataArr, PX, PY, PZ, SX, SY, SZ); #elif DIMS == 4 size_t sz = ZFP_ENCODE_PARTIAL_BLOCK_STRIDED_FUNC(stream, dataArr, PX, PY, PZ, PW, SX, SY, SZ, SW); size_t tsz = encode_partial_block_strided(tstream, dataArr, PX, PY, PZ, PW, SX, SY, SZ, SW); #endif ASSERT_TRUE(sz == tsz); ASSERT_TRUE(streamsEqual(&stream, &tstream)); zfp_field_free(field); stream_close(zfp_stream_bit_stream(stream)); stream_close(zfp_stream_bit_stream(tstream)); zfp_stream_close(stream); zfp_stream_close(tstream); delete[] dataArr; }