On Tue, Mar 26, 2019 at 1:05 PM Fabiano Fidêncio <fidencio@xxxxxxxxxx> wrote: > > osinfo-db schema allows that, but libosinfo never really had an API to > support it. > > https://gitlab.com/libosinfo/libosinfo/issues/16 > > Signed-off-by: Fabiano Fidêncio <fidencio@xxxxxxxxxx> > --- > osinfo/osinfo_loader.c | 17 ++++++++- > osinfo/osinfo_os.c | 2 ++ > osinfo/osinfo_tree.c | 70 +++++++++++++++++++++++++++++++++++- > osinfo/osinfo_tree.h | 2 ++ > osinfo/osinfo_tree_private.h | 29 +++++++++++++++ > 5 files changed, 118 insertions(+), 2 deletions(-) > create mode 100644 osinfo/osinfo_tree_private.h > > diff --git a/osinfo/osinfo_loader.c b/osinfo/osinfo_loader.c > index f71aea9..e30148b 100644 > --- a/osinfo/osinfo_loader.c > +++ b/osinfo/osinfo_loader.c > @@ -1242,9 +1242,24 @@ static OsinfoTree *osinfo_loader_tree(OsinfoLoader *loader, > OsinfoTree *tree = osinfo_tree_new(id, arch); > xmlFree(arch); > > + gint nnodes = osinfo_loader_nodeset("./variant", loader, ctxt, &nodes, err); > + if (error_is_set(err)) { > + g_object_unref(tree); > + return NULL; > + } > + > + for (i = 0; i < nnodes; i++) { > + gchar *variant_id = (gchar *)xmlGetProp(nodes[i], BAD_CAST "id"); > + osinfo_entity_add_param(OSINFO_ENTITY(tree), > + OSINFO_TREE_PROP_VARIANT, > + variant_id); > + xmlFree(variant_id); > + } > + g_free(nodes); > + > osinfo_loader_entity(loader, OSINFO_ENTITY(tree), keys, ctxt, root, err); > > - gint nnodes = osinfo_loader_nodeset("./treeinfo/*", loader, ctxt, &nodes, err); > + nnodes = osinfo_loader_nodeset("./treeinfo/*", loader, ctxt, &nodes, err); > if (error_is_set(err)) { > g_object_unref(G_OBJECT(tree)); > return NULL; > diff --git a/osinfo/osinfo_os.c b/osinfo/osinfo_os.c > index dbea421..a406980 100644 > --- a/osinfo/osinfo_os.c > +++ b/osinfo/osinfo_os.c > @@ -28,6 +28,7 @@ > #include "osinfo_media_private.h" > #include "osinfo/osinfo_product_private.h" > #include "osinfo/osinfo_resources_private.h" > +#include "osinfo/osinfo_tree_private.h" > #include <glib/gi18n-lib.h> > > G_DEFINE_TYPE(OsinfoOs, osinfo_os, OSINFO_TYPE_PRODUCT); > @@ -673,6 +674,7 @@ void osinfo_os_add_tree(OsinfoOs *os, OsinfoTree *tree) > g_return_if_fail(OSINFO_IS_TREE(tree)); > > osinfo_list_add(OSINFO_LIST(os->priv->trees), OSINFO_ENTITY(tree)); > + osinfo_tree_set_os(tree, os); > } > > /** > diff --git a/osinfo/osinfo_tree.c b/osinfo/osinfo_tree.c > index 55c6aa1..1446f53 100644 > --- a/osinfo/osinfo_tree.c > +++ b/osinfo/osinfo_tree.c > @@ -26,6 +26,7 @@ > #include <config.h> > > #include <osinfo/osinfo.h> > +#include "osinfo_tree_private.h" > #include <gio/gio.h> > #include <stdlib.h> > #include <string.h> > @@ -96,7 +97,7 @@ G_DEFINE_TYPE(OsinfoTree, osinfo_tree, OSINFO_TYPE_ENTITY); > > struct _OsinfoTreePrivate > { > - gboolean unused; > + GWeakRef os; > }; > > enum { > @@ -264,6 +265,15 @@ osinfo_tree_finalize(GObject *object) > G_OBJECT_CLASS(osinfo_tree_parent_class)->finalize(object); > } > > +static void osinfo_tree_dispose(GObject *obj) > +{ > + OsinfoTree *tree = OSINFO_TREE(obj); > + > + g_weak_ref_clear(&tree->priv->os); > + > + G_OBJECT_CLASS(osinfo_tree_parent_class)->dispose(obj); > +} > + > /* Init functions */ > static void > osinfo_tree_class_init(OsinfoTreeClass *klass) > @@ -271,6 +281,7 @@ osinfo_tree_class_init(OsinfoTreeClass *klass) > GObjectClass *g_klass = G_OBJECT_CLASS(klass); > GParamSpec *pspec; > > + g_klass->dispose = osinfo_tree_dispose; > g_klass->finalize = osinfo_tree_finalize; > g_klass->get_property = osinfo_tree_get_property; > g_klass->set_property = osinfo_tree_set_property; > @@ -411,6 +422,8 @@ static void > osinfo_tree_init(OsinfoTree *tree) > { > tree->priv = OSINFO_TREE_GET_PRIVATE(tree); > + > + g_weak_ref_init(&tree->priv->os, NULL); > } > > OsinfoTree *osinfo_tree_new(const gchar *id, > @@ -918,3 +931,58 @@ gboolean osinfo_tree_has_treeinfo(OsinfoTree *tree) > return osinfo_entity_get_param_value_boolean(OSINFO_ENTITY(tree), > OSINFO_TREE_PROP_HAS_TREEINFO); > } > + > +OsinfoOs *osinfo_tree_get_os(OsinfoTree *tree) > +{ > + g_return_val_if_fail(OSINFO_IS_TREE(tree), NULL); > + > + return g_weak_ref_get(&tree->priv->os); > +} > + > +void osinfo_tree_set_os(OsinfoTree *tree, OsinfoOs *os) > +{ > + g_return_if_fail(OSINFO_IS_TREE(tree)); > + > + g_object_ref(os); > + g_weak_ref_set(&tree->priv->os, os); > + g_object_unref(os); > +} > + > +/** > + * osinfo_tree_get_os_variant_list: > + * @tree: an #OsinfoTree instance > + * > + * Gets the variants of the associated operating system. > + * > + * Returns: (transfer full): the operating system variant, or NULL > + */ > +OsinfoOsVariantList *osinfo_tree_get_os_variants(OsinfoTree *tree) > +{ > + OsinfoOs *os; > + OsinfoOsVariantList *os_variants; > + OsinfoOsVariantList *tree_variants; > + GList *ids, *node; > + OsinfoFilter *filter; > + > + g_return_val_if_fail(OSINFO_IS_TREE(tree), NULL); > + os = osinfo_tree_get_os(tree); > + os_variants = osinfo_os_get_variant_list(os); > + g_object_unref(os); > + > + ids = osinfo_entity_get_param_value_list(OSINFO_ENTITY(tree), > + OSINFO_TREE_PROP_VARIANT); > + filter = osinfo_filter_new(); > + tree_variants = osinfo_os_variantlist_new(); > + for (node = ids; node != NULL; node = node->next) { > + osinfo_filter_clear_constraints(filter); > + osinfo_filter_add_constraint(filter, > + OSINFO_ENTITY_PROP_ID, > + (const char *) node->data); > + osinfo_list_add_filtered(OSINFO_LIST(tree_variants), > + OSINFO_LIST(os_variants), > + filter); > + } > + g_object_unref(os_variants); > + > + return tree_variants; > +} > diff --git a/osinfo/osinfo_tree.h b/osinfo/osinfo_tree.h > index 40a2a29..7ff1840 100644 > --- a/osinfo/osinfo_tree.h > +++ b/osinfo/osinfo_tree.h > @@ -62,6 +62,7 @@ typedef struct _OsinfoTreePrivate OsinfoTreePrivate; > #define OSINFO_TREE_PROP_KERNEL "kernel" > #define OSINFO_TREE_PROP_INITRD "initrd" > #define OSINFO_TREE_PROP_HAS_TREEINFO "has-treeinfo" > +#define OSINFO_TREE_PROP_VARIANT "variant" > > > /* object */ > @@ -109,6 +110,7 @@ const gchar *osinfo_tree_get_treeinfo_arch(OsinfoTree *tree); > const gchar *osinfo_tree_get_boot_iso_path(OsinfoTree *tree); > const gchar *osinfo_tree_get_kernel_path(OsinfoTree *tree); > const gchar *osinfo_tree_get_initrd_path(OsinfoTree *tree); > +OsinfoOsVariantList *osinfo_tree_get_os_variants(OsinfoTree *tree); > /* XXX Xen kernel/initrd paths ? */ > > #endif /* __OSINFO_TREE_H__ */ > diff --git a/osinfo/osinfo_tree_private.h b/osinfo/osinfo_tree_private.h > new file mode 100644 > index 0000000..7113f98 > --- /dev/null > +++ b/osinfo/osinfo_tree_private.h > @@ -0,0 +1,29 @@ > +/* > + * libosinfo: An installation tree for a (guest) OS > + * > + * Copyright (C) 2019 Red Hat, Inc. > + * > + * This library is free software; you can redistribute it and/or > + * modify it under the terms of the GNU Lesser General Public > + * License as published by the Free Software Foundation; either > + * version 2.1 of the License, or (at your option) any later version. > + * > + * This library is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU > + * Lesser General Public License for more details. > + * > + * You should have received a copy of the GNU Lesser General Public > + * License along with this library. If not, see > + * <http://www.gnu.org/licenses/>. > + */ > + > +#include <osinfo/osinfo_tree.h> > + > +#ifndef __OSINFO_TREE_PRIVATE_H__ > +#define __OSINFO_TREE_PRIVATE_H__ > + > +OsinfoOs *osinfo_tree_get_os(OsinfoTree *tree); > +void osinfo_tree_set_os(OsinfoTree *tree, OsinfoOs *os); > + > +#endif /* __OSINFO_TREE_PRIVATE_H__ */ > -- > 2.20.1 > The following patch has to be squashed to this one: fidencio@dahmer ~/src/upstream/libosinfo $ git diff diff --git a/osinfo/libosinfo.syms b/osinfo/libosinfo.syms index aa8e6d7..14f766e 100644 --- a/osinfo/libosinfo.syms +++ b/osinfo/libosinfo.syms @@ -572,6 +572,8 @@ LIBOSINFO_1.5.0 { global: osinfo_install_config_get_installation_url; osinfo_install_config_set_installation_url; + + osinfo_tree_get_os_variants; } LIBOSINFO_1.4.0; /* Symbols in next release... _______________________________________________ Libosinfo mailing list Libosinfo@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libosinfo