summaryrefslogtreecommitdiffstats
path: root/test/vfd_plugin.c
diff options
context:
space:
mode:
authorjhendersonHDF <jhenderson@hdfgroup.org>2021-09-29 18:28:12 (GMT)
committerGitHub <noreply@github.com>2021-09-29 18:28:12 (GMT)
commit3da0802c40d58759995916bf9d0880e19f0af44d (patch)
tree809ada78cec1cbaaf6ec2ace5b4429a56d0f6574 /test/vfd_plugin.c
parent0fa5836cc5f037dd9f2cdd7f9a1051ddcc1c9ad0 (diff)
downloadhdf5-3da0802c40d58759995916bf9d0880e19f0af44d.zip
hdf5-3da0802c40d58759995916bf9d0880e19f0af44d.tar.gz
hdf5-3da0802c40d58759995916bf9d0880e19f0af44d.tar.bz2
VFD plugins (#602)
* Implement support for loading of Virtual File Drivers as plugins Fix plugin caching for VOL connector and VFD plugins Fix plugin iteration to skip paths that can't be opened * Enable dynamic loading of VFDs with HDF5_DRIVER environment variable * Temporarily disable error reporting during H5F_open double file open * Default to using HDstat in h5_get_file_size for unknown VFDs * Use macros for some environment variables that HDF5 interprets * Update "null" and "ctl testing" VFDs
Diffstat (limited to 'test/vfd_plugin.c')
-rw-r--r--test/vfd_plugin.c388
1 files changed, 388 insertions, 0 deletions
diff --git a/test/vfd_plugin.c b/test/vfd_plugin.c
new file mode 100644
index 0000000..df211cc
--- /dev/null
+++ b/test/vfd_plugin.c
@@ -0,0 +1,388 @@
+/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
+ * Copyright by The HDF Group. *
+ * All rights reserved. *
+ * *
+ * This file is part of HDF5. The full HDF5 copyright notice, including *
+ * terms governing use, modification, and redistribution, is contained in *
+ * the COPYING file, which can be found at the root of the source code *
+ * distribution tree, or in https://www.hdfgroup.org/licenses. *
+ * If you do not have access to either file, you may request a copy from *
+ * help@hdfgroup.org. *
+ * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
+
+/*
+ * Purpose: Tests basic VFD plugin operations. Uses a basic testing VFD
+ * which is loaded as a dynamic plugin.
+ */
+
+#include "h5test.h"
+
+#include "null_vfd_plugin.h"
+
+#define DEFAULT_DRIVER_NAME "sec2"
+
+/*-------------------------------------------------------------------------
+ * Function: test_set_by_name()
+ *
+ * Purpose: Tests if we can load and register a VFD plugin by name.
+ *
+ * Return: SUCCEED/FAIL
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+test_set_by_name(void)
+{
+ htri_t is_registered = FAIL;
+ hid_t driver_id = H5I_INVALID_HID;
+ hid_t fapl_id = H5I_INVALID_HID;
+
+ TESTING("VFD plugin registration by name");
+
+ /* The null VFD should not be registered at the start of the test */
+ if ((is_registered = H5FDis_driver_registered_by_name(NULL_VFD_NAME)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ /* Register the null VFD by name */
+ if ((fapl_id = H5Pcreate(H5P_FILE_ACCESS)) < 0)
+ TEST_ERROR;
+ if (H5Pset_driver_by_name(fapl_id, NULL_VFD_NAME, NULL) < 0)
+ TEST_ERROR;
+
+ /* The null VFD should be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_name(NULL_VFD_NAME)) < 0)
+ TEST_ERROR;
+ if (FALSE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD was not registered");
+
+ /* Unregister the null VFD */
+ if ((driver_id = H5Pget_driver(fapl_id)) < 0)
+ TEST_ERROR;
+ if (H5FDunregister(driver_id) < 0)
+ TEST_ERROR;
+
+ /* Close FAPL, which holds last reference to null VFD */
+ if (H5Pclose(fapl_id) < 0)
+ TEST_ERROR;
+
+ /* The null VFD should not be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_name(NULL_VFD_NAME)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ PASSED();
+
+ return SUCCEED;
+
+error:
+ H5E_BEGIN_TRY
+ {
+ H5Pclose(fapl_id);
+ }
+ H5E_END_TRY;
+
+ return FAIL;
+}
+
+/*-------------------------------------------------------------------------
+ * Function: test_set_by_value()
+ *
+ * Purpose: Tests if we can load and register a VFD plugin by value
+ * (ID).
+ *
+ * Return: SUCCEED/FAIL
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+test_set_by_value(void)
+{
+ htri_t is_registered = FAIL;
+ hid_t driver_id = H5I_INVALID_HID;
+ hid_t fapl_id = H5I_INVALID_HID;
+
+ TESTING("VFD plugin registration by value (ID)");
+
+ /* The null VFD should not be registered at the start of the test */
+ if ((is_registered = H5FDis_driver_registered_by_value(NULL_VFD_VALUE)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ /* Register the null VFD by value */
+ if ((fapl_id = H5Pcreate(H5P_FILE_ACCESS)) < 0)
+ TEST_ERROR;
+ if (H5Pset_driver_by_value(fapl_id, NULL_VFD_VALUE, NULL) < 0)
+ TEST_ERROR;
+
+ /* The null VFD should be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_value(NULL_VFD_VALUE)) < 0)
+ TEST_ERROR;
+ if (FALSE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD was not registered");
+
+ /* Unregister the null VFD */
+ if ((driver_id = H5Pget_driver(fapl_id)) < 0)
+ TEST_ERROR;
+ if (H5FDunregister(driver_id) < 0)
+ TEST_ERROR;
+
+ /* Close FAPL, which holds last reference to null VFD */
+ if (H5Pclose(fapl_id) < 0)
+ TEST_ERROR;
+
+ /* The null VFD should not be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_value(NULL_VFD_VALUE)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ PASSED();
+
+ return SUCCEED;
+
+error:
+ H5E_BEGIN_TRY
+ {
+ H5Pclose(fapl_id);
+ }
+ H5E_END_TRY;
+
+ return FAIL;
+}
+
+/*-------------------------------------------------------------------------
+ * Function: test_set_multi()
+ *
+ * Purpose: Tests if we can register a VFD plugin multiple times.
+ *
+ * Return: SUCCEED/FAIL
+ *
+ *-------------------------------------------------------------------------
+ */
+#define N_REGISTRATIONS 10
+static herr_t
+test_set_multi(void)
+{
+ htri_t is_registered = FAIL;
+ hid_t driver_id = H5I_INVALID_HID;
+ hid_t fapl_id = H5I_INVALID_HID;
+ int i;
+
+ TESTING("registering a VFD plugin multiple times");
+
+ /* The null VFD should not be registered at the start of the test */
+ if ((is_registered = H5FDis_driver_registered_by_name(NULL_VFD_NAME)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ /* Register the VFD multiple times */
+ if ((fapl_id = H5Pcreate(H5P_FILE_ACCESS)) < 0)
+ TEST_ERROR;
+ for (i = 0; i < N_REGISTRATIONS; i++) {
+ if (H5Pset_driver_by_name(fapl_id, NULL_VFD_NAME, NULL) < 0)
+ TEST_ERROR;
+ }
+
+ /* The null VFD should be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_name(NULL_VFD_NAME)) < 0)
+ TEST_ERROR;
+ if (FALSE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD was not registered");
+
+ /* Unregister the null VFD */
+ if ((driver_id = H5Pget_driver(fapl_id)) < 0)
+ TEST_ERROR;
+ for (i = 0; i < N_REGISTRATIONS; i++) {
+ if (H5FDunregister(driver_id) < 0)
+ TEST_ERROR;
+ }
+
+ /* Close FAPL, which holds last reference to null VFD */
+ if (H5Pclose(fapl_id) < 0)
+ TEST_ERROR;
+
+ /* The null VFD should not be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_name(NULL_VFD_NAME)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ /* Repeat testing with the _by_value routines */
+
+ /* The null VFD should not be registered at the start of the test */
+ if ((is_registered = H5FDis_driver_registered_by_value(NULL_VFD_VALUE)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ /* Register the VFD multiple times */
+ if ((fapl_id = H5Pcreate(H5P_FILE_ACCESS)) < 0)
+ TEST_ERROR;
+ for (i = 0; i < N_REGISTRATIONS; i++) {
+ if (H5Pset_driver_by_value(fapl_id, NULL_VFD_VALUE, NULL) < 0)
+ TEST_ERROR;
+ }
+
+ /* The null VFD should be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_value(NULL_VFD_VALUE)) < 0)
+ TEST_ERROR;
+ if (FALSE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD was not registered");
+
+ /* Unregister the null VFD */
+ if ((driver_id = H5Pget_driver(fapl_id)) < 0)
+ TEST_ERROR;
+ for (i = 0; i < N_REGISTRATIONS; i++) {
+ if (H5FDunregister(driver_id) < 0)
+ TEST_ERROR;
+ }
+
+ /* Close FAPL, which holds last reference to null VFD */
+ if (H5Pclose(fapl_id) < 0)
+ TEST_ERROR;
+
+ /* The null VFD should not be registered now */
+ if ((is_registered = H5FDis_driver_registered_by_value(NULL_VFD_VALUE)) < 0)
+ TEST_ERROR;
+ if (TRUE == is_registered)
+ FAIL_PUTS_ERROR("NULL VFD is inappropriately registered");
+
+ PASSED();
+
+ return SUCCEED;
+
+error:
+ H5E_BEGIN_TRY
+ {
+ H5Pclose(fapl_id);
+ }
+ H5E_END_TRY;
+
+ return FAIL;
+}
+#undef N_REGISTRATIONS
+
+/*-------------------------------------------------------------------------
+ * Function: test_get_config_str()
+ *
+ * Purpose: Tests if we can retrieve a configuration string set for a
+ * VFL driver.
+ *
+ * Return: SUCCEED/FAIL
+ *
+ *-------------------------------------------------------------------------
+ */
+static herr_t
+test_get_config_str(void)
+{
+ const char *const config_str = "{name: sec2}";
+ ssize_t config_str_len = 0;
+ hid_t fapl_id = H5I_INVALID_HID;
+ char config_str_buf[128];
+
+ TESTING("Retrieval of VFD configuration string");
+
+ if ((fapl_id = H5Pcreate(H5P_FILE_ACCESS)) < 0)
+ TEST_ERROR;
+
+ /* Try to retrieve length of default configuration string - should be 0 */
+ HDmemset(config_str_buf, 0, 128);
+
+ if ((config_str_len = H5Pget_driver_config_str(fapl_id, config_str_buf, 128)) < 0)
+ TEST_ERROR;
+ if (0 != config_str_len)
+ TEST_ERROR;
+ if (HDstrlen(config_str_buf) > 0)
+ TEST_ERROR;
+
+ /* Set a new configuration string on the FAPL and retrieve it */
+ if (H5Pset_driver_by_name(fapl_id, DEFAULT_DRIVER_NAME, config_str) < 0)
+ TEST_ERROR;
+ if ((config_str_len = H5Pget_driver_config_str(fapl_id, config_str_buf, 128)) < 0)
+ TEST_ERROR;
+ if (HDstrlen(config_str) != config_str_len)
+ TEST_ERROR;
+ if (HDstrncmp(config_str_buf, config_str, 128))
+ TEST_ERROR;
+
+ if (H5Pclose(fapl_id) < 0)
+ TEST_ERROR;
+
+ /* Set default driver and driver configuration using environment variables */
+ if (HDsetenv(HDF5_DRIVER, "sec2", 1) < 0)
+ TEST_ERROR;
+ if (HDsetenv(HDF5_DRIVER_CONFIG, config_str, 1) < 0)
+ TEST_ERROR;
+
+ /* Close and re-open HDF5 to have it parse the environment variables */
+ if (H5close() < 0)
+ TEST_ERROR;
+ if (H5open() < 0)
+ TEST_ERROR;
+
+ /* Retrieve configuration string from default FAPL */
+ HDmemset(config_str_buf, 0, 128);
+ if ((config_str_len = H5Pget_driver_config_str(H5P_FILE_ACCESS_DEFAULT, config_str_buf, 128)) < 0)
+ TEST_ERROR;
+ if (HDstrlen(config_str) != config_str_len)
+ TEST_ERROR;
+ if (HDstrncmp(config_str_buf, config_str, 128))
+ TEST_ERROR;
+
+ /* Unset environment variables */
+ if (HDsetenv(HDF5_DRIVER, "", 1) < 0)
+ TEST_ERROR;
+ if (HDsetenv(HDF5_DRIVER_CONFIG, "", 1) < 0)
+ TEST_ERROR;
+
+ PASSED();
+
+ return SUCCEED;
+
+error:
+ H5E_BEGIN_TRY
+ {
+ H5Pclose(fapl_id);
+ }
+ H5E_END_TRY;
+
+ return FAIL;
+}
+
+/*-------------------------------------------------------------------------
+ * Function: main
+ *
+ * Purpose: Tests VFD plugin operations
+ *
+ * Return: EXIT_SUCCESS/EXIT_FAILURE
+ *
+ *-------------------------------------------------------------------------
+ */
+int
+main(void)
+{
+ int nerrors = 0;
+
+ h5_reset();
+
+ HDputs("Testing VFD plugin functionality.");
+
+ nerrors += (test_set_by_name() < 0) ? 1 : 0;
+ nerrors += (test_set_by_value() < 0) ? 1 : 0;
+ nerrors += (test_set_multi() < 0) ? 1 : 0;
+ nerrors += (test_get_config_str() < 0) ? 1 : 0;
+
+ if (nerrors) {
+ HDprintf("***** %d VFD plugin TEST%s FAILED! *****\n", nerrors, nerrors > 1 ? "S" : "");
+ HDexit(EXIT_FAILURE);
+ }
+
+ HDputs("All VFD plugin tests passed.");
+
+ HDexit(EXIT_SUCCESS);
+}