hid_t H5PTcreate_fl ( hid_t loc_id, const char *dset_name, hid_t dtype_id, hsize_t chunk_size, int compression ) { htbl_t * table = NULL; hid_t dset_id = H5I_BADID; hid_t space_id = H5I_BADID; hid_t plist_id = H5I_BADID; hsize_t dims[1]; hsize_t dims_chunk[1]; hsize_t maxdims[1]; hid_t ret_value; /* Register the packet table ID type if this is the first table created */ if(H5PT_ptable_id_type < 0) if((H5PT_ptable_id_type = H5Iregister_type((size_t)H5PT_HASH_TABLE_SIZE, 0, (H5I_free_t)free)) < 0) goto out; /* Get memory for the table identifier */ table = (htbl_t *)malloc(sizeof(htbl_t)); /* Create a simple data space with unlimited size */ dims[0] = 0; dims_chunk[0] = chunk_size; maxdims[0] = H5S_UNLIMITED; if((space_id = H5Screate_simple(1, dims, maxdims)) < 0) goto out; /* Modify dataset creation properties to enable chunking */ plist_id = H5Pcreate(H5P_DATASET_CREATE); if(H5Pset_chunk(plist_id, 1, dims_chunk) < 0) goto out; if(compression >= 0 && compression <= 9) if(H5Pset_deflate(plist_id, (unsigned)compression) < 0) goto out; /* Create the dataset. */ if((dset_id = H5Dcreate2(loc_id, dset_name, dtype_id, space_id, H5P_DEFAULT, plist_id, H5P_DEFAULT)) < 0) goto out; /* Terminate access to the data space. */ if(H5Sclose(space_id) < 0) goto out; /* End access to the property list */ if(H5Pclose(plist_id) < 0) goto out; /* Create the table identifier */ table->dset_id = dset_id; if((table->type_id = H5Tcopy(dtype_id)) < 0) goto out; H5PT_create_index(table); table->size = 0; /* Get an ID for this table */ ret_value = H5Iregister(H5PT_ptable_id_type, table); if(ret_value != H5I_INVALID_HID) H5PT_ptable_count++; else H5PT_close(table); return ret_value; out: H5E_BEGIN_TRY H5Sclose(space_id); H5Pclose(plist_id); H5Dclose(dset_id); if(table) free(table); H5E_END_TRY return H5I_INVALID_HID; }
/*------------------------------------------------------------------------- * Function: H5PTopen * * Purpose: Opens a dataset containing a table and returns the Identifier * of the table. * * Return: Success: table ID, Failure: Negative * * Programmer: Nat Furrer, [email protected] * James Laird, [email protected] * * Date: March 10, 2004 * * Comments: * * Modifications: * * John Mainzer -- 4/23/08 * Added error check on malloc of table, initialized fields * in table to keep lower level code from choking on bogus * data in error cases. * *------------------------------------------------------------------------- */ hid_t H5PTopen( hid_t loc_id, const char *dset_name ) { hid_t type_id=H5I_BADID; hid_t space_id=H5I_BADID; htbl_t * table = NULL; hid_t ret_value; hsize_t dims[1]; /* Register the packet table ID type if this is the first table created */ if( H5PT_ptable_id_type < 0) if((H5PT_ptable_id_type = H5Iregister_type((size_t)H5PT_HASH_TABLE_SIZE, 0, (H5I_free_t)free)) < 0) goto out; table = (htbl_t *)malloc(sizeof(htbl_t)); if ( table == NULL ) { goto out; } table->dset_id = H5I_BADID; table->type_id = H5I_BADID; /* Open the dataset */ if((table->dset_id = H5Dopen2(loc_id, dset_name, H5P_DEFAULT)) < 0) goto out; if(table->dset_id < 0) goto out; /* Get the dataset's disk datatype */ if((type_id = H5Dget_type(table->dset_id)) < 0) goto out; /* Get the table's native datatype */ if((table->type_id = H5Tget_native_type(type_id, H5T_DIR_ASCEND)) < 0) goto out; if(H5Tclose(type_id) < 0) goto out; /* Initialize the current record pointer */ if((H5PT_create_index(table)) < 0) goto out; /* Get number of records in table */ if((space_id=H5Dget_space(table->dset_id)) < 0) goto out; if( H5Sget_simple_extent_dims( space_id, dims, NULL) < 0) goto out; if(H5Sclose(space_id) < 0) goto out; table->size = dims[0]; /* Get an ID for this table */ ret_value = H5Iregister(H5PT_ptable_id_type, table); if(ret_value != H5I_INVALID_HID) H5PT_ptable_count++; else H5PT_close(table); return ret_value; out: H5E_BEGIN_TRY H5Tclose(type_id); H5Sclose(space_id); if(table) { H5Dclose(table->dset_id); H5Tclose(table->type_id); free(table); } H5E_END_TRY return H5I_INVALID_HID; }
/* H5I_NTYPES is defined in h5public.h, H5I_MAX_NUM_TYPES is defined in h5pkg.h */ static int test_id_type_list(void) { H5I_type_t startType; /* The first type ID we were assigned in this test */ H5I_type_t currentType; H5I_type_t testType; int i; /* Just a counter variable */ startType = H5Iregister_type((size_t)8, 0, (H5I_free_t) free ); CHECK(startType, H5I_BADID, "H5Iregister_type"); if(startType == H5I_BADID) goto out; /* Sanity check */ if(startType >= H5I_MAX_NUM_TYPES || startType < H5I_NTYPES) { /* Error condition, throw an error */ CHECK(1, 1, "H5Iregister_type"); goto out; } /* Create types up to H5I_MAX_NUM_TYPES */ for(i = startType + 1; i < H5I_MAX_NUM_TYPES; i++) { currentType = H5Iregister_type((size_t)8, 0, (H5I_free_t) free ); CHECK(currentType, H5I_BADID, "H5Iregister_type"); if(currentType == H5I_BADID) goto out; } /* Wrap around to low type ID numbers */ for(i = H5I_NTYPES; i < startType; i++) { currentType = H5Iregister_type((size_t)8, 0, (H5I_free_t) free ); CHECK(currentType, H5I_BADID, "H5Iregister_type"); if(currentType == H5I_BADID) goto out; } /* There should be no room at the inn for a new ID type*/ H5E_BEGIN_TRY testType = H5Iregister_type((size_t)8, 0, (H5I_free_t) free ); H5E_END_TRY VERIFY(testType, H5I_BADID, "H5Iregister_type"); if(testType != H5I_BADID) goto out; /* Now delete a type and try to insert again */ H5Idestroy_type(H5I_NTYPES); testType = H5Iregister_type((size_t)8, 0, (H5I_free_t) free ); VERIFY(testType, H5I_NTYPES, "H5Iregister_type"); if(testType != H5I_NTYPES) goto out; /* Cleanup. Destroy all types. */ for(i = H5I_NTYPES; i < H5I_MAX_NUM_TYPES; i++) H5Idestroy_type((H5I_type_t) i); return 0; out: /* Cleanup. For simplicity, just destroy all types and ignore errors. */ H5E_BEGIN_TRY for(i = H5I_NTYPES; i < H5I_MAX_NUM_TYPES; i++) H5Idestroy_type((H5I_type_t) i); H5E_END_TRY return -1; }
/* Test function */ static int test_remove_clear_type(void) { H5I_type_t obj_type; test_rct_list_t obj_list; test_rct_obj_t list[TEST_RCT_MAX_NOBJS]; long i, j; long nobjs_found; hsize_t nmembers; herr_t ret; /* return value */ /* Register type */ obj_type = H5Iregister_type((size_t)8, 0, test_rct_free); CHECK(obj_type, H5I_BADID, "H5Iregister_type"); if(obj_type == H5I_BADID) goto out; /* Init obj_list.list */ obj_list.list = list; for(i = 0; i < TEST_RCT_NITER; i++) { /* Build object list */ obj_list.nobjs = obj_list.nobjs_rem = TEST_RCT_MIN_NOBJS + (HDrandom() % (long)(TEST_RCT_MAX_NOBJS - TEST_RCT_MIN_NOBJS + 1)); for(j = 0; j < obj_list.nobjs; j++) { list[j].nfrees = 0; list[j].freeing = FALSE; list[j].obj_list = &obj_list; list[j].id = H5Iregister(obj_type, &list[j]); CHECK(list[j].id, FAIL, "H5Iregister"); if(list[j].id == FAIL) goto out; if(HDrandom() % 2) { ret = H5Iinc_ref(list[j].id); CHECK(ret, FAIL, "H5Iinc_ref"); if(ret == FAIL) goto out; } /* end if */ } /* end for */ /* Clear the type */ ret = H5Iclear_type(obj_type, FALSE); CHECK(ret, FAIL, "H5Iclear_type"); if(ret == FAIL) goto out; /* Verify list */ nobjs_found = 0; for(j = 0; j < obj_list.nobjs; j++) { if(list[j].nfrees == 0) nobjs_found++; else { VERIFY(list[j].nfrees, (long)1, "list[j].nfrees"); if(list[j].nfrees != (long)1) goto out; } /* end else */ VERIFY(list[j].freeing, FALSE, "list[j].freeing"); if(list[j].freeing != FALSE) goto out; } /* end for */ /* Verify number of objects */ VERIFY(obj_list.nobjs_rem, nobjs_found, "obj_list.nobjs_rem"); if(obj_list.nobjs_rem != nobjs_found) goto out; ret = H5Inmembers(obj_type, &nmembers); CHECK(ret, FAIL, "H5Inmembers"); if(ret == FAIL) goto out; VERIFY(nmembers, (size_t)nobjs_found, "H5Inmembers"); if(nmembers != (size_t)nobjs_found) goto out; /* Clear the type with force set to TRUE */ ret = H5Iclear_type(obj_type, TRUE); CHECK(ret, FAIL, "H5Iclear_type"); if(ret == FAIL) goto out; /* Verify list */ for(j = 0; j < obj_list.nobjs; j++) { VERIFY(list[j].nfrees, (long)1, "list[j].nfrees"); if(list[j].nfrees != (long)1) goto out; VERIFY(list[j].freeing, FALSE, "list[j].freeing"); if(list[j].freeing != FALSE) goto out; } /* end for */ /* Verify number of objects is 0 */ VERIFY(obj_list.nobjs_rem, (long)0, "obj_list.nobjs_rem"); if(obj_list.nobjs_rem != (long)0) goto out; ret = H5Inmembers(obj_type, &nmembers); CHECK(ret, FAIL, "H5Inmembers"); if(ret == FAIL) goto out; VERIFY(nmembers, (size_t)0, "H5Inmembers"); if(nmembers != (size_t)0) goto out; } /* end for */ /* Destroy type */ ret = H5Idestroy_type(obj_type); CHECK(ret, FAIL, "H5Idestroy_type"); if(ret == FAIL) goto out; return 0; out: /* Cleanup. For simplicity, just destroy the types and ignore errors. */ H5E_BEGIN_TRY H5Idestroy_type(obj_type); H5E_END_TRY return -1; } /* end test_remove_clear_type() */
/* Test basic functionality of registering and deleting types and IDs */ static int basic_id_test(void) { H5I_type_t myType = H5I_BADID; hid_t arrayID = H5I_INVALID_HID; void* testObj = NULL; void* testPtr = NULL; char nameString[10]; hid_t testID; ssize_t testSize = -1; herr_t err; int num_ref; hsize_t num_members; /* Try to register an ID with ficticious types */ H5E_BEGIN_TRY arrayID = H5Iregister((H5I_type_t) 420, testObj); H5E_END_TRY VERIFY(arrayID, H5I_INVALID_HID, "H5Iregister"); if(arrayID != H5I_INVALID_HID) goto out; H5E_BEGIN_TRY arrayID = H5Iregister((H5I_type_t) -1, testObj); H5E_END_TRY VERIFY(arrayID, H5I_INVALID_HID, "H5Iregister"); if(arrayID != H5I_INVALID_HID) goto out; /* Try to access IDs with ficticious types */ H5E_BEGIN_TRY testPtr = H5Iobject_verify((hid_t)100, (H5I_type_t) 0); H5E_END_TRY VERIFY(testPtr, NULL, "H5Iobject_verify"); if(testPtr != NULL) goto out; H5E_BEGIN_TRY testPtr = H5Iobject_verify((hid_t)700, (H5I_type_t) 700); H5E_END_TRY VERIFY(testPtr, NULL, "H5Iobject_verify"); if(testPtr != NULL) goto out; /* Register a type */ myType = H5Iregister_type((size_t)64, 0, (H5I_free_t) free ); CHECK(myType, H5I_BADID, "H5Iregister_type"); if(myType == H5I_BADID) goto out; /* Register an ID and retrieve the object it points to. * Once the ID has been registered, testObj will be freed when * its ID type is destroyed. */ testObj = HDmalloc(7 * sizeof(int)); arrayID = H5Iregister(myType, testObj); CHECK(arrayID, H5I_INVALID_HID, "H5Iregister"); if(arrayID == H5I_INVALID_HID) { HDfree(testObj); goto out; } testPtr = (int *) H5Iobject_verify(arrayID, myType); VERIFY(testPtr, testObj, "H5Iobject_verify"); if(testPtr != testObj) goto out; /* Ensure that H5Iget_file_id and H5Iget_name() fail, since this * is an hid_t for the wrong kind of object */ H5E_BEGIN_TRY testID = H5Iget_file_id(arrayID); H5E_END_TRY VERIFY(testID, H5I_INVALID_HID, "H5Iget_file_id"); if(testID != H5I_INVALID_HID) goto out; H5E_BEGIN_TRY testSize = H5Iget_name(arrayID, nameString, (size_t)9); H5E_END_TRY VERIFY(testSize, -1, "H5Iget_name"); if(testSize != -1) goto out; /* Make sure H5Iremove_verify catches objects of the wrong type */ H5E_BEGIN_TRY testPtr = (int*) H5Iremove_verify(arrayID, (H5I_type_t) 0); H5E_END_TRY VERIFY(testPtr, NULL, "H5Iremove_verify"); if(testPtr != NULL) goto out; H5E_BEGIN_TRY testPtr = (int*) H5Iremove_verify(arrayID, (H5I_type_t) ((int) myType-1)); H5E_END_TRY VERIFY(testPtr, NULL, "H5Iremove_verify"); if(testPtr != NULL) goto out; /* Remove an ID and make sure we can't access it */ testPtr = (int*) H5Iremove_verify(arrayID, myType); CHECK(testPtr, NULL, "H5Iremove_verify"); if(testPtr == NULL) goto out; H5E_BEGIN_TRY testPtr = (int*) H5Iobject_verify(arrayID, myType); H5E_END_TRY VERIFY(testPtr, NULL, "H5Iobject_verify"); if(testPtr != NULL) goto out; /* Delete the type and make sure we can't access objects within it */ arrayID = H5Iregister(myType, testObj); err = H5Idestroy_type(myType); VERIFY(err, 0, "H5Idestroy_type"); if( err != 0) goto out; VERIFY(H5Itype_exists(myType), 0, "H5Itype_exists"); if(H5Itype_exists(myType) != 0) goto out; H5E_BEGIN_TRY VERIFY(H5Inmembers(myType, NULL), -1, "H5Inmembers"); if(H5Inmembers(myType, NULL) != -1) goto out; H5E_END_TRY /* Register another type and another object in that type */ myType = H5Iregister_type((size_t)64, 0, (H5I_free_t) free ); CHECK(myType, H5I_BADID, "H5Iregister_type"); if(myType == H5I_BADID) goto out; /* The memory that testObj pointed to should already have been * freed when the previous type was destroyed. Allocate new * memory for it. */ testObj = HDmalloc(7 * sizeof(int)); arrayID = H5Iregister(myType, testObj); CHECK(arrayID, H5I_INVALID_HID, "H5Iregister"); if(arrayID == H5I_INVALID_HID) { HDfree(testObj); goto out; } err = H5Inmembers(myType, &num_members); CHECK(err, -1, "H5Inmembers"); if (err < 0) goto out; VERIFY(num_members, 1, "H5Inmembers"); if(num_members != 1) goto out; /* Increment references to type and ensure that dec_type_ref doesn't destroy the type */ num_ref = H5Iinc_type_ref(myType); VERIFY(num_ref, 2, "H5Iinc_type_ref"); if( num_ref != 2) goto out; num_ref = H5Idec_type_ref(myType); VERIFY(num_ref, 1, "H5Idec_type_ref"); if(num_ref != 1) goto out; err = H5Inmembers(myType, &num_members); CHECK(err, -1, "H5Inmembers"); if (err < 0) goto out; VERIFY(num_members, 1, "H5Inmembers"); if(num_members != 1) goto out; /* This call to dec_type_ref should destroy the type */ num_ref = H5Idec_type_ref(myType); VERIFY(num_ref, 0, "H5Idec_type_ref"); if(num_ref != 0) goto out; VERIFY(H5Itype_exists(myType), 0, "H5Itype_exists"); if (H5Itype_exists(myType) != 0) goto out; H5E_BEGIN_TRY err = H5Inmembers(myType, &num_members); if(err >= 0) goto out; H5E_END_TRY return 0; out: /* Clean up type if it has been allocated and free memory used * by testObj */ if(myType >= 0) H5Idestroy_type(myType); return -1; }