#include "hal-api-compatibility-checker-util.h"
#define HALCC_TRANSPORT_DEFAULT HALCC_TRANSPORT_PASSTHROUGH
+#define MAX_NUM_VERSION 8
typedef struct halcc_version {
int major;
typedef struct halcc_hal {
char *name;
+ halcc_version version_list[MAX_NUM_VERSION];
+ int num_version;
halcc_version version;
halcc_transport_e transport;
GHashTable *interfaces;
HALCC_HASH_COMPARE_TYPE_BACKWARD_MINOR_VERSION,
HALCC_HASH_COMPARE_TYPE_EXACT_MINOR_VERSION,
HALCC_HASH_COMPARE_TYPE_FORWARD_MINOR_VERSION,
+ HALCC_HASH_COMPARE_TYPE_ANY_VERSION,
} halcc_hash_compare_type_e;
typedef struct hash_hal_key {
if (strncmp(hal->name, key->hal.name, strlen(hal->name) + 1) != 0)
return false;
+ compare_type = key->compare_type;
+
+ if (compare_type == HALCC_HASH_COMPARE_TYPE_ANY_VERSION)
+ return true;
+
if (hal->version.major != key->hal.version.major)
return false;
- compare_type = key->compare_type;
-
switch (compare_type) {
case HALCC_HASH_COMPARE_TYPE_EXACT_MINOR_VERSION:
return hal->version.minor == key->hal.version.minor;
return 0;
}
+int halcc_manifest_find_hal_by_name(halcc_manifest *manifest,
+ const char *hal_name, halcc_hal **hal)
+{
+ halcc_hal *h;
+
+ if (!manifest || !hal_name) {
+ printf("Invalid parameter\n");
+ return -EINVAL;
+ }
+
+ h = hashtable_hal_lookup(manifest->hals,
+ hal_name, 0, 0, HALCC_HASH_COMPARE_TYPE_ANY_VERSION);
+ if (!h) {
+ printf("Failed to find hal=%s\n", hal_name);
+ return -ENOTSUP;
+ }
+
+ if (hal)
+ *hal = g_steal_pointer(&h);
+
+ return 0;
+}
+
int halcc_manifest_find_hal_raw(halcc_manifest *manifest,
halcc_hal *raw, halcc_hal **hal)
{
return 0;
}
+
+/**
+ * FIXME: It manages list of versions internally, but it only
+ * exposes the first incoming version as a representative version for the hal,
+ * and the halcc_hal_get_version(), in turn, will return the version.
+ * This will be fixed to manage the entire list for counting compatibility.
+ */
int halcc_hal_set_version(halcc_hal *hal, int major, int minor)
{
+ int i;
+
if (!hal) {
printf("Invalid parameter\n");
return -EINVAL;
}
- hal->version.major = major;
- hal->version.minor = minor;
+ assert(hal->num_version <= MAX_NUM_VERSION);
+
+
+ /* FIXME: Only the first incoming version sets hal version */
+ if (hal->num_version == 0) {
+ hal->version.major = major;
+ hal->version.minor = minor;
+ }
+
+ for (i = 0; i < hal->num_version; ++i) {
+ if (hal->version_list[i].major != major)
+ continue;
+
+ if (hal->version_list[i].minor < minor)
+ hal->version_list[i].minor = minor; /* update */
+
+ break;
+ }
+
+ if (hal->num_version > i)
+ return 0;
+
+ if (hal->num_version >= MAX_NUM_VERSION)
+ return -EOVERFLOW;
+
+ hal->version_list[hal->num_version].major = major;
+ hal->version_list[hal->num_version].minor = minor;
+
+ hal->num_version += 1;
return 0;
}
int halcc_manifest_add_hal(halcc_manifest *manifest, halcc_hal *hal);
int halcc_manifest_find_hal(halcc_manifest *manifest,
const char *hal_name, int major, int minor, halcc_hal **hal);
+int halcc_manifest_find_hal_by_name(halcc_manifest *manifest,
+ const char *hal_name, halcc_hal **hal);
int halcc_manifest_find_hal_raw(halcc_manifest *manifest,
halcc_hal *raw, halcc_hal **hal);
int halcc_manifest_find_hal_backward_compatible(halcc_manifest *manifest,
return 0;
}
-static int parse_hal(xmlNode *node, halcc_hal *hal)
+static int parse_hal(xmlNode *node, halcc_manifest *manifest)
{
int ret = 0;
+ halcc_hal *hal;
+ __xmlchar__ xmlChar *hal_name = NULL;
assert(node);
- assert(hal);
+ assert(manifest);
if (!xmlStrEqual(node->name, "hal")) {
printf("Invalid hal node, %s\n", node->name);
for (xmlNode *child = node->children; child; child = child->next) {
if (xmlStrEqual(child->name, "name")) {
- __xmlchar__ xmlChar *name = xmlNodeGetContent(child);
+ hal_name = xmlNodeGetContent(child);
+ break;
+ }
+ }
- ret = halcc_hal_set_name(hal, name);
- if (ret != 0)
- printf("Failed to halcc_hal_set_name(), name=%s, ret=%d\n", name, ret);
- } else if (xmlStrEqual(child->name, "version")) {
+ if (!hal_name) {
+ printf("Invalid hal node, name is unspecified\n");
+ return -EINVAL;
+ }
+
+ ret = halcc_manifest_find_hal_by_name(manifest, hal_name, &hal);
+ if (ret != 0) {
+ ret = halcc_hal_new(&hal);
+ if (ret != 0) {
+ printf("Failed to halcc_hal_new(), ret=%d\n", ret);
+ return ret;
+ }
+
+ halcc_hal_set_name(hal, hal_name);
+
+ ret = halcc_manifest_add_hal(manifest, hal);
+ if (ret != 0) {
+ printf("Failed to halcc_manifest_add_hal(), ret=%d\n", ret);
+ halcc_hal_free(hal);
+ hal = NULL;
+ return ret;
+ }
+ }
+
+ for (xmlNode *child = node->children; child; child = child->next) {
+ if (xmlStrEqual(child->name, "version")) {
int major, minor;
int scanned;
__xmlchar__ xmlChar *version = xmlNodeGetContent(child);
return ret;
for (xmlNode *child = node->children; child; child = child->next) {
- halcc_hal *h;
- const char *hal_name;
- int hal_major;
- int hal_minor;
- halcc_hal *hal_backward_compatible = NULL;
-
- if (!xmlStrEqual(child->name, "hal"))
- continue;
-
- ret = halcc_hal_new(&h);
- if (ret != 0) {
- printf("Failed to halcc_hal_new(), ret=%d\n", ret);
- continue;
- }
+ int ret;
- ret = parse_hal(child, h);
- if (ret != 0) {
+ ret = parse_hal(child, manifest);
+ if (ret != 0)
printf("Failed to parse_hal(), ret=%d\n", ret);
- halcc_hal_free(h);
- h = NULL;
- continue;
- }
-
- halcc_hal_get_name(h, &hal_name);
- halcc_hal_get_version(h, &hal_major, &hal_minor);
-
- if (halcc_manifest_find_hal(manifest, hal_name, hal_major, hal_minor, NULL) == 0) {
- halcc_hal_free(h);
- h = NULL;
- continue;
- }
-
- if (halcc_manifest_find_hal_forward_compatible(manifest,
- hal_name, hal_major, hal_minor, NULL) == 0) {
- halcc_hal_free(h);
- h = NULL;
- continue;
- }
-
- /**
- * Backward compatible hal can be covered by the current hal.
- * Therefore, remove it from the manifest.
- */
- if (halcc_manifest_steal_hal_backward_compatible(manifest,
- hal_name, hal_major, hal_minor, &hal_backward_compatible) == 0) {
- halcc_hal_free(hal_backward_compatible);
- hal_backward_compatible = NULL;
- }
-
- ret = halcc_manifest_add_hal(manifest, h);
- if (ret != 0) {
- printf("Failed to halcc_manifest_add_hal(), ret=%d\n", ret);
- halcc_hal_free(h);
- h = NULL;
- continue;
- }
-
- h = NULL;
}
return 0;
ASSERT_EQ(major, 2);
ASSERT_EQ(minor, 34);
}
-
-TEST_F(HalccObjectTest, manifest_find_multiple_hal_success)
-{
- halcc_hal *hal = NULL;
- const char *hal_name;
- int major, minor;
- int ret;
-
- ret = halcc_manifest_find_hal(g_manifest, "HAL_MODULE_BAR", 2, 0, &hal);
- ASSERT_NE(ret, 0); // The 2.0 has been replaced with 2.2
-
- ret = halcc_manifest_find_hal_forward_compatible(g_manifest, "HAL_MODULE_BAR", 2, 0, &hal);
- ASSERT_EQ(ret, 0); // 2.0 is covered by 2.2
-
- ret = halcc_hal_get_name(hal, &hal_name);
- ASSERT_EQ(ret, 0);
- ASSERT_STREQ(hal_name, "HAL_MODULE_BAR");
-
- ret = halcc_hal_get_version(hal, &major, &minor);
- ASSERT_EQ(ret, 0);
- ASSERT_EQ(major, 2);
- ASSERT_EQ(minor, 2);
-}