Skip to content

Commit

Permalink
Allow to read tensor with only metadata.
Browse files Browse the repository at this point in the history
  • Loading branch information
liuliu committed Dec 5, 2023
1 parent ff5563f commit 5fcd54a
Show file tree
Hide file tree
Showing 8 changed files with 94 additions and 33 deletions.
4 changes: 2 additions & 2 deletions bin/nnc/iwslt.c
Original file line number Diff line number Diff line change
Expand Up @@ -327,10 +327,10 @@ static void eval_wmt(const int max_length, const int embedding_size, const char*
if (SQLITE_OK == sqlite3_open("wmt.checkpoint", &conn))
{
ccv_nnc_tensor_t* src_vocab_vec_ = ccv_nnc_tensor_from_variable(dynamic_graph, src_vocab_vec);
ccv_nnc_tensor_read(conn, "src_vocab", 0, 0, 0, &src_vocab_vec_);
ccv_nnc_tensor_read(conn, "src_vocab", 0, 0, 0, 0, &src_vocab_vec_);
assert(src_vocab_vec_ == ccv_nnc_tensor_from_variable(dynamic_graph, src_vocab_vec));
ccv_nnc_tensor_t* tgt_vocab_vec_ = ccv_nnc_tensor_from_variable(dynamic_graph, tgt_vocab_vec);
ccv_nnc_tensor_read(conn, "tgt_vocab", 0, 0, 0, &tgt_vocab_vec_);
ccv_nnc_tensor_read(conn, "tgt_vocab", 0, 0, 0, 0, &tgt_vocab_vec_);
assert(tgt_vocab_vec_ == ccv_nnc_tensor_from_variable(dynamic_graph, tgt_vocab_vec));
sqlite3_close(conn);
}
Expand Down
4 changes: 2 additions & 2 deletions bin/nnc/wmt.c
Original file line number Diff line number Diff line change
Expand Up @@ -326,10 +326,10 @@ static void eval_wmt(const int max_length, const int embedding_size, const char*
if (SQLITE_OK == sqlite3_open("wmt.checkpoint", &conn))
{
ccv_nnc_tensor_t* src_vocab_vec_ = ccv_nnc_tensor_from_variable(dynamic_graph, src_vocab_vec);
ccv_nnc_tensor_read(conn, "src_vocab", 0, 0, 0, &src_vocab_vec_);
ccv_nnc_tensor_read(conn, "src_vocab", 0, 0, 0, 0, &src_vocab_vec_);
assert(src_vocab_vec_ == ccv_nnc_tensor_from_variable(dynamic_graph, src_vocab_vec));
ccv_nnc_tensor_t* tgt_vocab_vec_ = ccv_nnc_tensor_from_variable(dynamic_graph, tgt_vocab_vec);
ccv_nnc_tensor_read(conn, "tgt_vocab", 0, 0, 0, &tgt_vocab_vec_);
ccv_nnc_tensor_read(conn, "tgt_vocab", 0, 0, 0, 0, &tgt_vocab_vec_);
assert(tgt_vocab_vec_ == ccv_nnc_tensor_from_variable(dynamic_graph, tgt_vocab_vec));
sqlite3_close(conn);
}
Expand Down
2 changes: 1 addition & 1 deletion lib/nnc/ccv_cnnp_model_io.c
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ static inline int _model_tensor_read(const ccv_cnnp_model_t* const self, void* c
{
if (self->rw.reader)
return self->rw.reader(handle, name, dir, options, info, tensor_out);
return ccv_nnc_tensor_read(handle, name, dir, options, &info, tensor_out);
return ccv_nnc_tensor_read(handle, name, dir, options, 0, &info, tensor_out);
}

int ccv_cnnp_model_read(void* const handle, const char* const name, const ccv_nnc_tensor_io_option_t* const options, const ccv_cnnp_model_t* const model_out)
Expand Down
7 changes: 6 additions & 1 deletion lib/nnc/ccv_nnc.h
Original file line number Diff line number Diff line change
Expand Up @@ -659,17 +659,22 @@ typedef struct {
* @return CCV_IO_FINAL for success, otherwise error.
*/
int ccv_nnc_tensor_write(const ccv_nnc_tensor_t* const tensor, void* const handle, const char* const name, const ccv_nnc_tensor_io_option_t* const options);

enum {
CCV_NNC_TENSOR_READ_METADATA_ONLY = 0x1, /**< Read tensor that data is nil, with only metadata. */
};
/**
* Read a tensor from a SQLite database with a given name.
* @param handle The SQLite handle.
* @param name The name to find the tensor in the database.
* @param dir If the dir is provided, the tensor we read will be backed by a file at this path if possible (depending on underlying implementation, right now only MPS backend supported this feature).
* @param options If provided, we will use this to decode any data that identifier != 0.
* @param flags Additional flag to configure how we read tensor.
* @param tensor_params If provided, we will use this to create the tensor if tensor_out is not provided.
* @param tensor_out The pointer to hold the tensor. If you supply the tensor yourself, we will read the data into the existing tensor.
* @return CCV_IO_FINAL for success, otherwise error.
*/
int ccv_nnc_tensor_read(void* const handle, const char* const name, const char* const dir, const ccv_nnc_tensor_io_option_t* const options, const ccv_nnc_tensor_param_t* const tensor_params, ccv_nnc_tensor_t** const tensor_out);
int ccv_nnc_tensor_read(void* const handle, const char* const name, const char* const dir, const ccv_nnc_tensor_io_option_t* const options, const int flags, const ccv_nnc_tensor_param_t* const tensor_params, ccv_nnc_tensor_t** const tensor_out);
/**
* Swap a tensor to be backed by a file instead. Currently, once swapped, there is no way to swap back.
* @param tensor The tensor.
Expand Down
2 changes: 1 addition & 1 deletion lib/nnc/ccv_nnc_tensor.c
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ ccv_nnc_tensor_t* ccv_nnc_tensor_new(const void* const ptr, const ccv_nnc_tensor
ccv_nnc_tensor_t* tensor;
// this specific form can be toll-free bridging to ccv_dense_matrix_t (On CPU, and 3 dims (channels, rows, cols), and channels is smaller than max channels of ccv_dense_matrix_t).
const int tfb = (CCV_TENSOR_GET_MEMORY(params.type) == CCV_TENSOR_CPU_MEMORY && params.format == CCV_TENSOR_FORMAT_NHWC && params.dim[2] > 0 && params.dim[2] <= CCV_MAX_CHANNEL && params.dim[0] > 0 && params.dim[1] > 0 && params.dim[3] == 0);
if (ptr)
if (ptr || (flags & CCV_NO_DATA_ALLOC))
{
tensor = (ccv_nnc_tensor_t*)ccmalloc(sizeof(ccv_nnc_tensor_t));
tensor->dataof = 0;
Expand Down
20 changes: 18 additions & 2 deletions lib/nnc/ccv_nnc_tensor_io.c
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ int ccv_nnc_tensor_write(const ccv_nnc_tensor_t* const tensor, void* const handl
return CCV_IO_FINAL;
}

int ccv_nnc_tensor_read(void* const handle, const char* const name, const char* const dir, const ccv_nnc_tensor_io_option_t* const options, const ccv_nnc_tensor_param_t* const tensor_params_optional, ccv_nnc_tensor_t** const tensor_out)
int ccv_nnc_tensor_read(void* const handle, const char* const name, const char* const dir, const ccv_nnc_tensor_io_option_t* const options, const int flags, const ccv_nnc_tensor_param_t* const tensor_params_optional, ccv_nnc_tensor_t** const tensor_out)
{
assert(name);
sqlite3* conn = (sqlite3*)handle;
Expand Down Expand Up @@ -150,6 +150,7 @@ int ccv_nnc_tensor_read(void* const handle, const char* const name, const char*
identifier = (sqlite3_column_int64(tensor_select_stmt, 1) >> 32) & 0xffffffff;
datatype = sqlite3_column_int64(tensor_select_stmt, 3) & 0xffffffff;
tensor_params = *tensor_params_optional;
assert(!(flags & CCV_NNC_TENSOR_READ_METADATA_ONLY));
} else {
const sqlite_int64 type = sqlite3_column_int64(tensor_select_stmt, 1);
identifier = (type >> 32) & 0xffffffff;
Expand All @@ -162,11 +163,26 @@ int ccv_nnc_tensor_read(void* const handle, const char* const name, const char*
memcpy(tensor_params.dim, dim, ccv_min(sizeof(tensor_params.dim), sqlite3_column_bytes(tensor_select_stmt, 4)));
}
if (!options || !options->decode)
*tensor_out = tensor = ccv_nnc_tensor_new(0, tensor_params, 0);
{
if (flags & CCV_NNC_TENSOR_READ_METADATA_ONLY)
{
*tensor_out = tensor = ccv_nnc_tensor_new(0, tensor_params, CCV_NO_DATA_ALLOC); // Set the data point to 1 so it is allocated without data.
assert(tensor->data.u8 == 0); // Set it back to 0.
// Already done loading metadata, return.
sqlite3_reset(tensor_select_stmt);
sqlite3_clear_bindings(tensor_select_stmt);
sqlite3_finalize(tensor_select_stmt);
return CCV_IO_FINAL;
} else
*tensor_out = tensor = ccv_nnc_tensor_new(0, tensor_params, 0);
} else {
assert(!(flags & CCV_NNC_TENSOR_READ_METADATA_ONLY));
}
} else {
identifier = (sqlite3_column_int64(tensor_select_stmt, 1) >> 32) & 0xffffffff;
datatype = sqlite3_column_int(tensor_select_stmt, 3) & 0xffffffff;
tensor_params = tensor->info;
assert(!(flags & CCV_NNC_TENSOR_READ_METADATA_ONLY));
}
const void* const data = sqlite3_column_blob(tensor_select_stmt, 0);
int dim[CCV_NNC_MAX_DIM_ALLOC];
Expand Down
24 changes: 12 additions & 12 deletions test/int/nnc/tensor.tests.c
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,9 @@ TEST_CASE("tensor persistence, to / from GPU")
handle = 0;
sqlite3_open("tensors_g.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, &tensor2);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, 0, &tensor2);
sqlite3_close(handle);
ccv_nnc_tensor_t* const tensor1c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10, 20, 30), 0);
ccv_nnc_cmd_exec(CMD_DATA_TRANSFER_FORWARD(), ccv_nnc_no_hint, 0, TENSOR_LIST(tensor1), TENSOR_LIST(tensor1c), 0);
Expand Down Expand Up @@ -111,9 +111,9 @@ TEST_CASE("tensor persistence with encoder / decoder, to / from GPU")
handle = 0;
sqlite3_open("tensors_de_g.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
ccv_nnc_tensor_t* tensor1c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10, 20, 30), 0);
ccv_nnc_cmd_exec(CMD_DATA_TRANSFER_FORWARD(), ccv_nnc_no_hint, 0, TENSOR_LIST(tensor1), TENSOR_LIST(tensor1c), 0);
Expand Down Expand Up @@ -150,9 +150,9 @@ TEST_CASE("tensor persistence with noop encoder / decoder, to / from GPU")
handle = 0;
sqlite3_open("tensors_noop_de_g.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
ccv_nnc_tensor_t* tensor1c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10, 20, 30), 0);
ccv_nnc_cmd_exec(CMD_DATA_TRANSFER_FORWARD(), ccv_nnc_no_hint, 0, TENSOR_LIST(tensor1), TENSOR_LIST(tensor1c), 0);
Expand Down Expand Up @@ -192,10 +192,10 @@ TEST_CASE("tensor persistence with type coercion, to / from GPU")
sqlite3_open("tensors_tc_g.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = ccv_nnc_tensor_new(0, GPU_TENSOR_NHWC(000, 32F, 10), 0);
ccv_nnc_tensor_t* tensor1c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, GPU_TENSOR_NHWC(000, 16F, 10), 0);
ccv_nnc_tensor_t* tensor2c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, 0, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, 0, 0, 0, &tensor2);
ccv_nnc_cmd_exec(CMD_DATA_TRANSFER_FORWARD(), ccv_nnc_no_hint, 0, TENSOR_LIST(tensor1, tensor2), TENSOR_LIST(tensor1c, tensor2c), 0);
sqlite3_close(handle);
float* tensor1_ref = (float*)ccmalloc(sizeof(float) * 10);
Expand Down Expand Up @@ -249,10 +249,10 @@ TEST_CASE("tensor persistence with type coercion and encoder / decoder, to / fro
sqlite3_open("tensors_tc_de_g.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = ccv_nnc_tensor_new(0, GPU_TENSOR_NHWC(000, 32F, 10), 0);
ccv_nnc_tensor_t* tensor1c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, GPU_TENSOR_NHWC(000, 16F, 10), 0);
ccv_nnc_tensor_t* tensor2c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
ccv_nnc_cmd_exec(CMD_DATA_TRANSFER_FORWARD(), ccv_nnc_no_hint, 0, TENSOR_LIST(tensor1, tensor2), TENSOR_LIST(tensor1c, tensor2c), 0);
float* tensor1_ref = (float*)ccmalloc(sizeof(float) * 10);
Expand Down Expand Up @@ -306,10 +306,10 @@ TEST_CASE("tensor persistence with type coercion and noop encoder / decoder, to
sqlite3_open("tensors_tc_noop_de_g.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = ccv_nnc_tensor_new(0, GPU_TENSOR_NHWC(000, 32F, 10), 0);
ccv_nnc_tensor_t* tensor1c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, GPU_TENSOR_NHWC(000, 16F, 10), 0);
ccv_nnc_tensor_t* tensor2c = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
ccv_nnc_cmd_exec(CMD_DATA_TRANSFER_FORWARD(), ccv_nnc_no_hint, 0, TENSOR_LIST(tensor1, tensor2), TENSOR_LIST(tensor1c, tensor2c), 0);
float* tensor1_ref = (float*)ccmalloc(sizeof(float) * 10);
Expand Down
64 changes: 52 additions & 12 deletions test/unit/nnc/tensor.tests.c
Original file line number Diff line number Diff line change
Expand Up @@ -137,9 +137,9 @@ TEST_CASE("tensor persistence")
handle = 0;
sqlite3_open("tensors.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, &tensor2);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, 0, &tensor2);
sqlite3_close(handle);
REQUIRE_TENSOR_EQ(tensor1, tensor, "the first tensor should equal to the second");
REQUIRE_ARRAY_EQ_WITH_TOLERANCE(float, tensor2->data.f32, tensor->data.f32, 10, 1e-5, "the first 10 element should be equal");
Expand Down Expand Up @@ -211,9 +211,9 @@ TEST_CASE("tensor persistence with encoder / decoder")
handle = 0;
sqlite3_open("tensors_de.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
REQUIRE_TENSOR_EQ(tensor1, tensor, "the first tensor should equal to the second");
REQUIRE_ARRAY_EQ_WITH_TOLERANCE(float, tensor2->data.f32, tensor->data.f32, 10, 1e-5, "the first 10 element should be equal");
Expand Down Expand Up @@ -243,9 +243,9 @@ TEST_CASE("tensor persistence with noop encoder / decoder")
handle = 0;
sqlite3_open("tensors_noop_de.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
REQUIRE_TENSOR_EQ(tensor1, tensor, "the first tensor should equal to the second");
REQUIRE_ARRAY_EQ_WITH_TOLERANCE(float, tensor2->data.f32, tensor->data.f32, 10, 1e-5, "the first 10 element should be equal");
Expand All @@ -256,6 +256,46 @@ TEST_CASE("tensor persistence with noop encoder / decoder")
ccv_nnc_tensor_free(tensor);
}

TEST_CASE("tensor persistence and read metadata only")
{
sqlite3* handle;
sqlite3_open("tensors_md.sqlite3", &handle);
ccv_nnc_tensor_t* const tensorf32 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10, 20, 30), 0);
int i;
dsfmt_t dsfmt;
dsfmt_init_gen_rand(&dsfmt, 1);
for (i = 0; i < 10 * 20 * 30; i++)
tensorf32->data.f32[i] = dsfmt_genrand_open_close(&dsfmt) * 2 - 1;
ccv_nnc_tensor_t* const tensorf16 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10, 20, 30), 0);
ccv_float_to_half_precision(tensorf32->data.f32, (uint16_t*)tensorf16->data.f16, 10 * 20 * 30);
for (i = 0; i < 10 * 20 * 30; i++)
tensorf32->data.f32[i] = dsfmt_genrand_open_close(&dsfmt) * 2 - 1;
ccv_nnc_tensor_write(tensorf16, handle, "x", 0);
ccv_nnc_tensor_write(tensorf32, handle, "y", 0);
sqlite3_close(handle);
handle = 0;
sqlite3_open("tensors_md.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = 0;
ccv_nnc_tensor_read(handle, "x", 0, 0, CCV_NNC_TENSOR_READ_METADATA_ONLY, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = 0;
ccv_nnc_tensor_read(handle, "y", 0, 0, CCV_NNC_TENSOR_READ_METADATA_ONLY, 0, &tensor2);
sqlite3_close(handle);
REQUIRE(tensor1->data.u8 == 0, "should have no data");
REQUIRE(tensor2->data.u8 == 0, "should have no data");
REQUIRE_EQ(tensor1->info.dim[0], 10, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor2->info.dim[0], 10, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor1->info.dim[1], 20, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor2->info.dim[1], 20, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor1->info.dim[2], 30, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor2->info.dim[2], 30, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor1->info.dim[3], 0, "should be 3-d tensor with 10, 20, 30");
REQUIRE_EQ(tensor2->info.dim[3], 0, "should be 3-d tensor with 10, 20, 30");
ccv_nnc_tensor_free(tensor1);
ccv_nnc_tensor_free(tensor2);
ccv_nnc_tensor_free(tensorf16);
ccv_nnc_tensor_free(tensorf32);
}

TEST_CASE("tensor persistence with type coercion")
{
sqlite3* handle;
Expand All @@ -276,9 +316,9 @@ TEST_CASE("tensor persistence with type coercion")
handle = 0;
sqlite3_open("tensors_tc.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, 0, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, 0, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, 0, 0, 0, &tensor2);
sqlite3_close(handle);
float* tensor1_ref = (float*)ccmalloc(sizeof(float) * 10);
ccv_half_precision_to_float((uint16_t*)tensorf16->data.f16, tensor1_ref, 10);
Expand Down Expand Up @@ -322,9 +362,9 @@ TEST_CASE("tensor persistence with type coercion and encoder / decoder")
handle = 0;
sqlite3_open("tensors_tc_de.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
float* tensor1_ref = (float*)ccmalloc(sizeof(float) * 10);
ccv_half_precision_to_float((uint16_t*)tensorf16->data.f16, tensor1_ref, 10);
Expand Down Expand Up @@ -368,9 +408,9 @@ TEST_CASE("tensor persistence with type coercion and noop encoder / decoder")
handle = 0;
sqlite3_open("tensors_tc_noop_de.sqlite3", &handle);
ccv_nnc_tensor_t* tensor1 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(32F, 10), 0);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, &tensor1);
ccv_nnc_tensor_read(handle, "x", 0, &options, 0, 0, &tensor1);
ccv_nnc_tensor_t* tensor2 = ccv_nnc_tensor_new(0, CPU_TENSOR_NHWC(16F, 10), 0);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, &tensor2);
ccv_nnc_tensor_read(handle, "y", 0, &options, 0, 0, &tensor2);
sqlite3_close(handle);
float* tensor1_ref = (float*)ccmalloc(sizeof(float) * 10);
ccv_half_precision_to_float((uint16_t*)tensorf16->data.f16, tensor1_ref, 10);
Expand Down

0 comments on commit 5fcd54a

Please sign in to comment.