diff options
-rw-r--r-- | osinfo/libosinfo.syms | 6 | ||||
-rw-r--r-- | osinfo/osinfo_os.c | 106 | ||||
-rw-r--r-- | osinfo/osinfo_os.h | 1 | ||||
-rw-r--r-- | tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-1.xml | 12 | ||||
-rw-r--r-- | tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit1.xml | 11 | ||||
-rw-r--r-- | tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit2.xml | 12 | ||||
-rw-r--r-- | tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit3.xml | 12 | ||||
-rw-r--r-- | tests/test-os.c | 136 |
8 files changed, 296 insertions, 0 deletions
diff --git a/osinfo/libosinfo.syms b/osinfo/libosinfo.syms index 7576fcc..a561788 100644 --- a/osinfo/libosinfo.syms +++ b/osinfo/libosinfo.syms @@ -636,6 +636,12 @@ LIBOSINFO_1.8.0 { osinfo_os_get_cloud_image_username; } LIBOSINFO_1.7.0; +LIBOSINFO_1.10.0 { + global: + + osinfo_os_get_complete_firmware_list; +} LIBOSINFO_1.8.0; + /* Symbols in next release... LIBOSINFO_0.0.2 { diff --git a/osinfo/osinfo_os.c b/osinfo/osinfo_os.c index eeafee1..022bfe4 100644 --- a/osinfo/osinfo_os.c +++ b/osinfo/osinfo_os.c @@ -1523,6 +1523,112 @@ OsinfoFirmwareList *osinfo_os_get_firmware_list(OsinfoOs *os, OsinfoFilter *filt return foreach_data.firmwares; } +static void get_all_firmwares_cb(OsinfoProduct *product, gpointer user_data) +{ + OsinfoFirmwareList *out; + OsinfoOs *os = OSINFO_OS(product); + gsize len, i; + gsize current_list_len, j; + struct GetAllFirmwaresData *foreach_data = user_data; + + g_return_if_fail(OSINFO_IS_OS(os)); + + out = OSINFO_FIRMWARELIST(osinfo_list_new_copy(OSINFO_LIST(foreach_data->firmwares))); + + len = osinfo_list_get_length(OSINFO_LIST(os->priv->firmwares)); + current_list_len = osinfo_list_get_length(OSINFO_LIST(foreach_data->firmwares)); + for (i = 0; i < len; i++) { + OsinfoFirmware *firmware; + const gchar *arch; + const gchar *type; + gboolean requested_by_caller; + gboolean already_in = FALSE; + + firmware = OSINFO_FIRMWARE(osinfo_list_get_nth(OSINFO_LIST(os->priv->firmwares), i)); + arch = osinfo_firmware_get_architecture(firmware); + type = osinfo_firmware_get_firmware_type(firmware); + requested_by_caller = TRUE; + + /* + * In case there's no filter, the firmware can be considered as + * requested_by_caller. + * + * In case there's a filter, let's ensure the firmware matches the + * filter before adding it to the final firmwares' list. + */ + if (foreach_data->filter != NULL && + !osinfo_filter_matches(foreach_data->filter, OSINFO_ENTITY(firmware))) + requested_by_caller = FALSE; + + /* + * In case the firmware is valid to be added, let's ensure the firmware + * is not already part of the firmware list. + * + * We can safely do this check here as the _foreach() function ensures + * we iterate through the latest child all the way back to the parent. + */ + if (requested_by_caller) { + for (j = 0; j < current_list_len; j++) { + OsinfoFirmware *in; + const gchar *in_arch; + const gchar *in_type; + + in = OSINFO_FIRMWARE( + osinfo_list_get_nth(OSINFO_LIST(foreach_data->firmwares), j)); + in_arch = osinfo_firmware_get_architecture(in); + in_type = osinfo_firmware_get_firmware_type(in); + + if (g_str_equal(arch, in_arch) && + g_str_equal(type, in_type)) { + already_in = TRUE; + break; + } + } + } + + /* + * Only add the firmware to the final list of firmwares in case it is + * requested by the caller and a newer entry is not yet part of the + * list. + */ + if (requested_by_caller && !already_in) + osinfo_list_add(OSINFO_LIST(out), OSINFO_ENTITY(firmware)); + } + + g_object_unref(foreach_data->firmwares); + foreach_data->firmwares = out; +} + +/** + * osinfo_os_get_complete_firmware_list: + * @os: an operating system + * @filter: (allow-none)(transfer none): an optional firmware property filter + * + * Get the complete firmwares matching a given filter, including the non-supported ones. + * + * Returns: (transfer full): A list of firmwares + * + * Since: 1.10.0 + */ +OsinfoFirmwareList *osinfo_os_get_complete_firmware_list(OsinfoOs *os, OsinfoFilter *filter) +{ + struct GetAllFirmwaresData foreach_data; + + g_return_val_if_fail(OSINFO_IS_OS(os), NULL); + g_return_val_if_fail(!filter || OSINFO_IS_FILTER(filter), NULL); + + foreach_data.filter = filter; + foreach_data.firmwares = osinfo_firmwarelist_new(); + + osinfo_product_foreach_related(OSINFO_PRODUCT(os), + OSINFO_PRODUCT_FOREACH_FLAG_DERIVES_FROM | + OSINFO_PRODUCT_FOREACH_FLAG_CLONES, + get_all_firmwares_cb, + &foreach_data); + + return foreach_data.firmwares; +} + /** * osinfo_os_add_firmware: * @os: an operating system diff --git a/osinfo/osinfo_os.h b/osinfo/osinfo_os.h index 2ea51a2..8358c71 100644 --- a/osinfo/osinfo_os.h +++ b/osinfo/osinfo_os.h @@ -113,6 +113,7 @@ void osinfo_os_add_device_driver(OsinfoOs *os, OsinfoDeviceDriver *driver); const gchar *osinfo_os_get_kernel_url_argument(OsinfoOs *os); OsinfoFirmwareList *osinfo_os_get_firmware_list(OsinfoOs *os, OsinfoFilter *filter); +OsinfoFirmwareList *osinfo_os_get_complete_firmware_list(OsinfoOs *os, OsinfoFilter *filter); void osinfo_os_add_firmware(OsinfoOs *os, OsinfoFirmware *firmware); const gchar *osinfo_os_get_cloud_image_username(OsinfoOs *os); diff --git a/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-1.xml b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-1.xml new file mode 100644 index 0000000..5f438f6 --- /dev/null +++ b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-1.xml @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<libosinfo version="0.0.1"> + <os id="http://libosinfo.org/test/os/firmwares/complete/1"> + <short-id>firmwarescomplete1</short-id> + <name>Firmwares Complete 1</name> + <vendor>libosinfo.org</vendor> + <family>test</family> + + <firmware arch="x86_64" type="bios" supported="false"/> + <firmware arch="x86_64" type="efi"/> + </os> +</libosinfo> diff --git a/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit1.xml b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit1.xml new file mode 100644 index 0000000..25bbe76 --- /dev/null +++ b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit1.xml @@ -0,0 +1,11 @@ +<?xml version="1.0" encoding="UTF-8"?> +<libosinfo version="0.0.1"> + <os id="http://libosinfo.org/test/os/firmwares/complete/inherit1"> + <short-id>completeinherit1</short-id> + <name>Complete Inherit 1</name> + <vendor>libosinfo.org</vendor> + <family>test</family> + + <firmware arch="x86_64" type="bios"/> + </os> +</libosinfo> diff --git a/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit2.xml b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit2.xml new file mode 100644 index 0000000..a5cc499 --- /dev/null +++ b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit2.xml @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<libosinfo version="0.0.1"> + <os id="http://libosinfo.org/test/os/firmwares/complete/inherit2"> + <short-id>completeinherit2</short-id> + <name>Complete Inherit 2</name> + <vendor>libosinfo.org</vendor> + <family>test</family> + <derives-from id="http://libosinfo.org/test/os/firmwares/complete/inherit1"/> + + <firmware arch="aarch64" type="bios"/> + </os> +</libosinfo> diff --git a/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit3.xml b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit3.xml new file mode 100644 index 0000000..72df346 --- /dev/null +++ b/tests/dbdata/os/libosinfo.org/test-os-firmwares-complete-inherit3.xml @@ -0,0 +1,12 @@ +<?xml version="1.0" encoding="UTF-8"?> +<libosinfo version="0.0.1"> + <os id="http://libosinfo.org/test/os/firmwares/complete/inherit3"> + <short-id>completeinherit3</short-id> + <name>Complete Inherit 3</name> + <vendor>libosinfo.org</vendor> + <family>test</family> + <derives-from id="http://libosinfo.org/test/os/firmwares/complete/inherit2"/> + + <firmware arch="x86_64" type="bios" supported="false"/> + </os> +</libosinfo> diff --git a/tests/test-os.c b/tests/test-os.c index 299aa94..be3ea20 100644 --- a/tests/test-os.c +++ b/tests/test-os.c @@ -850,6 +850,140 @@ test_firmwares_inheritance(void) } static void +test_firmwares_complete_list(void) +{ + OsinfoLoader *loader = osinfo_loader_new(); + OsinfoDb *db; + OsinfoOs *os; + OsinfoFirmwareList *firmwarelist; + GError *error = NULL; + + loader = osinfo_loader_new(); + osinfo_loader_process_path(loader, SRCDIR "/tests/dbdata", &error); + g_assert_no_error(error); + db = osinfo_loader_get_db(loader); + + g_debug("Testing http://libosinfo.org/test/os/firmwares/complete/1\n"); + os = osinfo_db_get_os(db, "http://libosinfo.org/test/os/firmwares/complete/1"); + g_assert_nonnull(os); + + /** + * This is using the function to get the list of SUPPORTED firmwares. + * The db entry has: + * - bios -> false + * - efi -> true + * Thus, the expected result is the list having only one element, the EFI one. + */ + firmwarelist = osinfo_os_get_firmware_list(os, NULL); + g_assert_cmpint(osinfo_list_get_length(OSINFO_LIST(firmwarelist)), ==, 1); + g_object_unref(firmwarelist); + + /** + * This is using the function to get the COMPLETE list of firmwares. + * The db entry has: + * - bios -> false + * - efi -> true + * Thus, the expected result is the list having both firmwares there. + */ + firmwarelist = osinfo_os_get_complete_firmware_list(os, NULL); + g_assert_cmpint(osinfo_list_get_length(OSINFO_LIST(firmwarelist)), ==, 2); + g_object_unref(firmwarelist); + g_object_unref(loader); +} + +static void +test_firmwares_complete_list_inheritance(void) +{ + OsinfoLoader *loader = osinfo_loader_new(); + OsinfoDb *db; + OsinfoOs *os; + OsinfoFirmware *firmware; + OsinfoFirmwareList *firmwarelist; + GError *error = NULL; + + loader = osinfo_loader_new(); + osinfo_loader_process_path(loader, SRCDIR "/tests/dbdata", &error); + g_assert_no_error(error); + db = osinfo_loader_get_db(loader); + + /** + * inherit1: + * - bios | x86_64 + * + * expected results: + * - 1 item + * - bios | x96_64 + */ + g_debug("Testing http://libosinfo.org/test/os/firmwares/complete/inherit1\n"); + os = osinfo_db_get_os(db, "http://libosinfo.org/test/os/firmwares/complete/inherit1"); + g_assert_nonnull(os); + + firmwarelist = osinfo_os_get_complete_firmware_list(os, NULL); + g_assert_cmpint(osinfo_list_get_length(OSINFO_LIST(firmwarelist)), ==, 1); + + firmware = OSINFO_FIRMWARE(osinfo_list_get_nth(OSINFO_LIST(firmwarelist), 0)); + g_assert_cmpstr(osinfo_firmware_get_firmware_type(firmware), ==, "bios"); + g_assert_cmpstr(osinfo_firmware_get_architecture(firmware), ==, "x86_64"); + g_assert_true(osinfo_firmware_is_supported(firmware)); + g_object_unref(firmwarelist); + + /** + * inherit2: + * - bios | aarch64 + * + * expected results: + * - 2 items + * - bios | aarch64 + * - bios | x86_64 + */ + g_debug("Testing http://libosinfo.org/test/os/firmwares/complete/inherit2\n"); + os = osinfo_db_get_os(db, "http://libosinfo.org/test/os/firmwares/complete/inherit2"); + g_assert_nonnull(os); + + firmwarelist = osinfo_os_get_complete_firmware_list(os, NULL); + g_assert_cmpint(osinfo_list_get_length(OSINFO_LIST(firmwarelist)), ==, 2); + + firmware = OSINFO_FIRMWARE(osinfo_list_get_nth(OSINFO_LIST(firmwarelist), 0)); + g_assert_cmpstr(osinfo_firmware_get_firmware_type(firmware), ==, "bios"); + g_assert_cmpstr(osinfo_firmware_get_architecture(firmware), ==, "aarch64"); + g_assert_true(osinfo_firmware_is_supported(firmware)); + + firmware = OSINFO_FIRMWARE(osinfo_list_get_nth(OSINFO_LIST(firmwarelist), 1)); + g_assert_cmpstr(osinfo_firmware_get_firmware_type(firmware), ==, "bios"); + g_assert_cmpstr(osinfo_firmware_get_architecture(firmware), ==, "x86_64"); + g_assert_true(osinfo_firmware_is_supported(firmware)); + + /** + * inherit3: + * - bios | x86_64 | not supported + * + * expected results: + * - 2 items + * - bios | x86_64 | not supported + * - bios | aarch64 + */ + g_debug("Testing http://libosinfo.org/test/os/firmwares/complete/inherit3\n"); + os = osinfo_db_get_os(db, "http://libosinfo.org/test/os/firmwares/complete/inherit3"); + g_assert_nonnull(os); + + firmwarelist = osinfo_os_get_complete_firmware_list(os, NULL); + g_assert_cmpint(osinfo_list_get_length(OSINFO_LIST(firmwarelist)), ==, 2); + + firmware = OSINFO_FIRMWARE(osinfo_list_get_nth(OSINFO_LIST(firmwarelist), 0)); + g_assert_cmpstr(osinfo_firmware_get_firmware_type(firmware), ==, "bios"); + g_assert_cmpstr(osinfo_firmware_get_architecture(firmware), ==, "x86_64"); + g_assert_false(osinfo_firmware_is_supported(firmware)); + + firmware = OSINFO_FIRMWARE(osinfo_list_get_nth(OSINFO_LIST(firmwarelist), 1)); + g_assert_cmpstr(osinfo_firmware_get_firmware_type(firmware), ==, "bios"); + g_assert_cmpstr(osinfo_firmware_get_architecture(firmware), ==, "aarch64"); + g_assert_true(osinfo_firmware_is_supported(firmware)); + + g_object_unref(firmwarelist); + g_object_unref(loader); +} + +static void test_cloud_image_username_arg(void) { OsinfoLoader *loader; @@ -908,6 +1042,8 @@ main(int argc, char *argv[]) g_test_add_func("/os/mulitple_short_ids", test_multiple_short_ids); g_test_add_func("/os/kernel_url_arg", test_kernel_url_arg); g_test_add_func("/os/firmwares/inheritance", test_firmwares_inheritance); + g_test_add_func("/os/firmwares/complete_list", test_firmwares_complete_list); + g_test_add_func("/os/firmwares/complete_list/inheritance", test_firmwares_complete_list_inheritance); g_test_add_func("/os/cloud_image_username_arg", test_cloud_image_username_arg); /* Upfront so we don't confuse valgrind */ |