in source/hack_parallel/hack_parallel/heap/hh_shared.c [2792:2852]
CAMLprim value hh_save_table_keys_sqlite(value out_filename, value keys) {
CAMLparam2(out_filename, keys);
assert_master();
struct timeval tv = {0};
struct timeval tv2 = {0};
gettimeofday(&tv, NULL);
sqlite3* db_out = NULL;
assert_sql(sqlite3_open(String_val(out_filename), &db_out), SQLITE_OK);
make_all_tables(db_out);
write_sqlite_header(db_out, BuildInfo_kRevision);
const char* sql =
"CREATE TABLE IF NOT EXISTS HASHTABLE("
" KEY_VERTEX INT PRIMARY KEY NOT NULL,"
" VALUE_VERTEX BLOB NOT NULL"
");";
assert_sql(sqlite3_exec(db_out, sql, NULL, 0, NULL), SQLITE_OK);
assert_sql(
sqlite3_exec(db_out, "PRAGMA synchronous = OFF", NULL, 0, NULL),
SQLITE_OK);
assert_sql(
sqlite3_exec(db_out, "PRAGMA journal_mode = MEMORY", NULL, 0, NULL),
SQLITE_OK);
assert_sql(
sqlite3_exec(db_out, "BEGIN TRANSACTION", NULL, 0, NULL), SQLITE_OK);
sqlite3_stmt* insert_stmt = NULL;
sql = "INSERT INTO HASHTABLE (KEY_VERTEX, VALUE_VERTEX) VALUES (?,?)";
assert_sql(
sqlite3_prepare_v2(db_out, sql, -1, &insert_stmt, NULL), SQLITE_OK);
int n_keys = Wosize_val(keys);
for (int i = 0; i < n_keys; ++i) {
unsigned int slot = find_slot(Field(keys, i));
uint64_t slot_hash = hashtbl[slot].hash;
if (slot_hash == 0 || hashtbl[slot].addr == NULL) {
continue;
}
char* value = hashtbl[slot].addr->data;
size_t value_size = Heap_entry_total_size(hashtbl[slot].addr->header);
assert_sql(sqlite3_bind_int64(insert_stmt, 1, slot_hash), SQLITE_OK);
assert_sql(
sqlite3_bind_blob(insert_stmt, 2, value, value_size, SQLITE_TRANSIENT),
SQLITE_OK);
assert_sql(sqlite3_step(insert_stmt), SQLITE_DONE);
assert_sql(sqlite3_clear_bindings(insert_stmt), SQLITE_OK);
assert_sql(sqlite3_reset(insert_stmt), SQLITE_OK);
}
assert_sql(sqlite3_finalize(insert_stmt), SQLITE_OK);
assert_sql(sqlite3_exec(db_out, "END TRANSACTION", NULL, 0, NULL), SQLITE_OK);
assert_sql(sqlite3_close(db_out), SQLITE_OK);
gettimeofday(&tv2, NULL);
int secs = tv2.tv_sec - tv.tv_sec;
CAMLreturn(Val_long(secs));
}