[gnome-keyring/ui-widgets: 5/7] [gcr] Create new view interface and implement for certificates.
- From: Stefan Walter <stefw src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-keyring/ui-widgets: 5/7] [gcr] Create new view interface and implement for certificates.
- Date: Fri, 27 Aug 2010 03:24:55 +0000 (UTC)
commit 512141527a7675e399d7b597c145a9e55e8b11d9
Author: Stef Walter <stef memberwebs com>
Date: Mon Jun 21 02:36:43 2010 +0000
[gcr] Create new view interface and implement for certificates.
gcr/Makefile.am | 4 +-
gcr/gcr-certificate-widget.c | 198 +++++++++++++++++++++++++++++------------
gcr/gcr-simple-certificate.c | 71 +++++++---------
gcr/gcr-simple-certificate.h | 3 +
gcr/gcr-view.c | 144 ++++++++++++++++++++++++++++++
gcr/gcr-view.h | 53 +++++++++++
gcr/template/gcr-zzz.c | 59 +++++++++++++
gcr/template/gcr-zzz.h | 45 ++++++++++
gp11/gp11-attributes.c | 39 ++++++++
gp11/gp11.h | 7 ++-
10 files changed, 523 insertions(+), 100 deletions(-)
---
diff --git a/gcr/Makefile.am b/gcr/Makefile.am
index bba15bb..c4b205f 100644
--- a/gcr/Makefile.am
+++ b/gcr/Makefile.am
@@ -23,7 +23,8 @@ inc_HEADERS = \
gcr-importer.h \
gcr-parser.h \
gcr-types.h \
- gcr-unlock-options-widget.h
+ gcr-unlock-options-widget.h \
+ gcr-view.h
# ------------------------------------------------------------------
# LIBRARY
@@ -57,6 +58,7 @@ libgcr_la_SOURCES = \
gcr-simple-certificate.c gcr-simple-certificate.h \
gcr-types.h \
gcr-unlock-options-widget.c gcr-unlock-options-widget.h \
+ gcr-view.c gcr-view.h \
$(BUILT_SOURCES)
libgcr_la_CFLAGS = \
diff --git a/gcr/gcr-certificate-widget.c b/gcr/gcr-certificate-widget.c
index 7b81d7f..7d178a6 100644
--- a/gcr/gcr-certificate-widget.c
+++ b/gcr/gcr-certificate-widget.c
@@ -23,8 +23,12 @@
#include "gcr-certificate-widget.h"
#include "gcr-display-view.h"
#include "gcr-icons.h"
+#include "gcr-simple-certificate.h"
+#include "gcr-view.h"
-#include "egg/egg-asn1.h"
+#include "egg/egg-asn1x.h"
+#include "egg/egg-asn1-defs.h"
+#include "egg/egg-dn.h"
#include "egg/egg-oid.h"
#include "egg/egg-hex.h"
@@ -33,49 +37,71 @@
enum {
PROP_0,
- PROP_CERTIFICATE
+ PROP_CERTIFICATE,
+ PROP_LABEL,
+ PROP_ATTRIBUTES
};
struct _GcrCertificateWidgetPrivate {
GcrCertificate *certificate;
GcrDisplayView *view;
guint key_size;
+ gchar *label;
+ GP11Attributes *attributes;
};
-G_DEFINE_TYPE (GcrCertificateWidget, gcr_certificate_widget, GTK_TYPE_ALIGNMENT);
+static void gcr_view_iface_init (GcrViewIface *iface);
+
+G_DEFINE_TYPE_WITH_CODE (GcrCertificateWidget, gcr_certificate_widget, GTK_TYPE_ALIGNMENT,
+ G_IMPLEMENT_INTERFACE (GCR_TYPE_VIEW, gcr_view_iface_init));
/* -----------------------------------------------------------------------------
* INTERNAL
*/
+static gchar*
+calculate_label (GcrCertificateWidget *self, GNode *asn)
+{
+ gchar *label;
+
+ if (self->pv->label)
+ return g_strdup (self->pv->label);
+
+ if (self->pv->attributes) {
+ if (gp11_attributes_find_string (self->pv->attributes, CKA_LABEL, &label))
+ return label;
+ }
+
+ if (asn != NULL) {
+ label = egg_dn_read_part (egg_asn1x_node (asn, "tbsCertificate", "subject", "rdnSequence", NULL), "CN");
+ if (label != NULL)
+ return label;
+ }
+
+ return g_strdup (_("Certificate"));
+}
+
static gboolean
-append_extension (GcrCertificateWidget *self, ASN1_TYPE asn,
+append_extension (GcrCertificateWidget *self, GNode *asn,
const guchar *data, gsize n_data, gint index)
{
+ GNode *node;
GQuark oid;
- gchar *name, *display;
+ gchar *display;
gsize n_value;
const guchar *value;
const gchar *text;
gboolean critical;
- int len, res;
/* Make sure it is present */
- len = 0;
- name = g_strdup_printf ("tbsCertificate.extensions.?%u", index);
- res = asn1_read_value (asn, name, NULL, &len);
- g_free (name);
-
- if (res == ASN1_ELEMENT_NOT_FOUND)
+ node = egg_asn1x_node (asn, "tbsCertificate", "extensions", index, NULL);
+ if (node == NULL)
return FALSE;
/* Dig out the OID */
- name = g_strdup_printf ("tbsCertificate.extensions.?%u.extnID", index);
- oid = egg_asn1_read_oid (asn, name);
- g_free (name);
+ oid = egg_asn1x_get_oid_as_quark (egg_asn1x_node (node, "extnID", NULL));
g_return_val_if_fail (oid, FALSE);
-
_gcr_display_view_append_heading (self->pv->view, _("Extension"));
@@ -85,9 +111,7 @@ append_extension (GcrCertificateWidget *self, ASN1_TYPE asn,
/* Extension value */
- name = g_strdup_printf ("tbsCertificate.extensions.?%u.extnValue", index);
- value = egg_asn1_read_content (asn, data, n_data, name, &n_value);
- g_free (name);
+ value = egg_asn1x_get_raw_value (egg_asn1x_node (node, "extnValue", NULL), &n_value);
/* TODO: Parsing of extensions that we understand */
display = egg_hex_encode_full (value, n_value, TRUE, ' ', 1);
@@ -96,10 +120,8 @@ append_extension (GcrCertificateWidget *self, ASN1_TYPE asn,
/* Critical */
- name = g_strdup_printf ("tbsCertificate.extensions.?%u.critical", index);
- if (egg_asn1_read_boolean (asn, name, &critical))
+ if (egg_asn1x_get_boolean (egg_asn1x_node (node, "critical", NULL), &critical))
_gcr_display_view_append_value (self->pv->view, _("Critical"), critical ? _("Yes") : _("No"), FALSE);
- g_free (name);
return TRUE;
}
@@ -135,7 +157,7 @@ on_parsed_dn_part (guint index, GQuark oid, const guchar *value,
g_assert_not_reached ();
}
- display = egg_asn1_dn_print_value (oid, value, n_value);
+ display = egg_dn_print_value (oid, value, n_value);
if (display == NULL)
display = g_strdup ("");
@@ -148,12 +170,13 @@ static void
refresh_display (GcrCertificateWidget *self)
{
const guchar *data, *value;
- gsize n_data, n_value;
+ gsize n_data, n_value, n_raw;
const gchar *text;
- guint version, size;
- guint index;
+ gpointer raw;
+ gulong version;
+ guint bits, index;
gchar *display;
- ASN1_TYPE asn;
+ GNode *asn;
GQuark oid;
GDate date;
@@ -165,21 +188,22 @@ refresh_display (GcrCertificateWidget *self)
data = gcr_certificate_get_der_data (self->pv->certificate, &n_data);
g_return_if_fail (data);
- asn = egg_asn1_decode ("PKIX1.Certificate", data, n_data);
+ asn = egg_asn1x_create_and_decode (pkix_asn1_tab, "Certificate", data, n_data);
g_return_if_fail (asn);
- /* TODO: Calculate name properly */
- _gcr_display_view_append_title (self->pv->view, "Certificate Name");
+ display = calculate_label (self, asn);
+ _gcr_display_view_append_title (self->pv->view, display);
+ g_free (display);
- display = egg_asn1_read_dn_part (asn, "tbsCertificate.subject.rdnSequence", "CN");
+ display = egg_dn_read_part (egg_asn1x_node (asn, "tbsCertificate", "subject", "rdnSequence", NULL), "CN");
_gcr_display_view_append_content (self->pv->view, _("Identity"), display);
g_free (display);
- display = egg_asn1_read_dn_part (asn, "tbsCertificate.issuer.rdnSequence", "CN");
+ display = egg_dn_read_part (egg_asn1x_node (asn, "tbsCertificate", "issuer", "rdnSequence", NULL), "CN");
_gcr_display_view_append_content (self->pv->view, _("Verified by"), display);
g_free (display);
- if (egg_asn1_read_date (asn, "tbsCertificate.validity.notAfter", &date)) {
+ if (egg_asn1x_get_time_as_date (egg_asn1x_node (asn, "tbsCertificate", "validity", "notAfter", NULL), &date)) {
display = g_malloc0 (128);
if (!g_date_strftime (display, 128, "%x", &date))
g_return_if_reached ();
@@ -191,34 +215,35 @@ refresh_display (GcrCertificateWidget *self)
/* The subject */
_gcr_display_view_append_heading (self->pv->view, _("Subject Name"));
- egg_asn1_dn_parse (asn, "tbsCertificate.subject.rdnSequence", on_parsed_dn_part, self);
+ egg_dn_parse (egg_asn1x_node (asn, "tbsCertificate", "subject", "rdnSequence", NULL), on_parsed_dn_part, self);
/* The Issuer */
_gcr_display_view_append_heading (self->pv->view, _("Issuer Name"));
- egg_asn1_dn_parse (asn, "tbsCertificate.issuer.rdnSequence", on_parsed_dn_part, self);
+ egg_dn_parse (egg_asn1x_node (asn, "tbsCertificate", "issuer", "rdnSequence", NULL), on_parsed_dn_part, self);
/* The Issued Parameters */
_gcr_display_view_append_heading (self->pv->view, _("Issued Certificate"));
- if (!egg_asn1_read_uint (asn, "tbsCertificate.version", &version))
+ if (!egg_asn1x_get_integer_as_ulong (egg_asn1x_node (asn, "tbsCertificate", "version", NULL), &version))
g_return_if_reached ();
- display = g_strdup_printf ("%u", version + 1);
+ display = g_strdup_printf ("%lu", version + 1);
_gcr_display_view_append_value (self->pv->view, _("Version"), display, FALSE);
g_free (display);
- value = egg_asn1_read_content (asn, data, n_data, "tbsCertificate.serialNumber", &n_value);
- g_return_if_fail (value);
- display = egg_hex_encode_full (value, n_value, TRUE, ' ', 1);
+ raw = egg_asn1x_get_integer_as_raw (egg_asn1x_node (asn, "tbsCertificate", "serialNumber", NULL), NULL, &n_raw);
+ g_return_if_fail (raw);
+ display = egg_hex_encode_full (raw, n_raw, TRUE, ' ', 1);
_gcr_display_view_append_value (self->pv->view, _("Serial Number"), display, TRUE);
g_free (display);
+ g_free (raw);
display = g_malloc0 (128);
- if (egg_asn1_read_date (asn, "tbsCertificate.validity.notBefore", &date)) {
+ if (egg_asn1x_get_time_as_date (egg_asn1x_node (asn, "tbsCertificate", "validity", "notBefore", NULL), &date)) {
if (!g_date_strftime (display, 128, "%Y-%m-%d", &date))
g_return_if_reached ();
_gcr_display_view_append_value (self->pv->view, _("Not Valid Before"), display, FALSE);
}
- if (egg_asn1_read_date (asn, "tbsCertificate.validity.notAfter", &date)) {
+ if (egg_asn1x_get_time_as_date (egg_asn1x_node (asn, "tbsCertificate", "validity", "notAfter", NULL), &date)) {
if (!g_date_strftime (display, 128, "%Y-%m-%d", &date))
g_return_if_reached ();
_gcr_display_view_append_value (self->pv->view, _("Not Valid After"), display, FALSE);
@@ -228,49 +253,54 @@ refresh_display (GcrCertificateWidget *self)
/* Signature */
_gcr_display_view_append_heading (self->pv->view, _("Signature"));
- oid = egg_asn1_read_oid (asn, "signatureAlgorithm.algorithm");
+ oid = egg_asn1x_get_oid_as_quark (egg_asn1x_node (asn, "signatureAlgorithm", "algorithm", NULL));
text = egg_oid_get_description (oid);
_gcr_display_view_append_value (self->pv->view, _("Signature Algorithm"), text, FALSE);
- value = egg_asn1_read_content (asn, data, n_data, "signatureAlgorithm.parameters", &n_value);
+ value = egg_asn1x_get_raw_element (egg_asn1x_node (asn, "signatureAlgorithm", "parameters", NULL), &n_value);
if (value && n_value) {
display = egg_hex_encode_full (value, n_value, TRUE, ' ', 1);
_gcr_display_view_append_value (self->pv->view, _("Signature Parameters"), display, TRUE);
g_free (display);
}
- value = egg_asn1_read_content (asn, data, n_data, "signature", &n_value);
- g_return_if_fail (value);
- display = egg_hex_encode_full (value, n_value, TRUE, ' ', 1);
+ raw = egg_asn1x_get_bits_as_raw (egg_asn1x_node (asn, "signature", NULL), NULL, &bits);
+ g_return_if_fail (raw);
+ display = egg_hex_encode_full (raw, bits / 8, TRUE, ' ', 1);
_gcr_display_view_append_value (self->pv->view, _("Signature"), display, TRUE);
g_free (display);
+ g_free (raw);
/* Public Key Info */
_gcr_display_view_append_heading (self->pv->view, _("Public Key Info"));
- oid = egg_asn1_read_oid (asn, "tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm");
+ oid = egg_asn1x_get_oid_as_quark (egg_asn1x_node (asn, "tbsCertificate", "subjectPublicKeyInfo",
+ "algorithm", "algorithm", NULL));
text = egg_oid_get_description (oid);
_gcr_display_view_append_value (self->pv->view, _("Key Algorithm"), text, FALSE);
- value = egg_asn1_read_content (asn, data, n_data, "tbsCertificate.subjectPublicKeyInfo.algorithm.parameters", &n_value);
+ value = egg_asn1x_get_raw_element (egg_asn1x_node (asn, "tbsCertificate", "subjectPublicKeyInfo",
+ "algorithm", "parameters", NULL), &n_value);
if (value && n_value) {
display = egg_hex_encode_full (value, n_value, TRUE, ' ', 1);
_gcr_display_view_append_value (self->pv->view, _("Key Parameters"), display, TRUE);
g_free (display);
}
- size = gcr_certificate_get_key_size (self->pv->certificate);
- if (size > 0) {
- display = g_strdup_printf ("%u", size);
+ bits = gcr_certificate_get_key_size (self->pv->certificate);
+ if (bits > 0) {
+ display = g_strdup_printf ("%u", bits);
_gcr_display_view_append_value (self->pv->view, _("Key Size"), display, FALSE);
g_free (display);
}
- value = egg_asn1_read_content (asn, data, n_data, "tbsCertificate.subjectPublicKeyInfo.subjectPublicKey", &n_value);
- g_return_if_fail (value);
- display = egg_hex_encode_full (value, n_value, TRUE, ' ', 1);
+ raw = egg_asn1x_get_bits_as_raw (egg_asn1x_node (asn, "tbsCertificate", "subjectPublicKeyInfo",
+ "subjectPublicKey", NULL), NULL, &bits);
+ g_return_if_fail (raw);
+ display = egg_hex_encode_full (raw, bits / 8, TRUE, ' ', 1);
_gcr_display_view_append_value (self->pv->view, _("Public Key"), display, TRUE);
g_free (display);
+ g_free (raw);
/* Fingerprints */
_gcr_display_view_append_heading (self->pv->view, _("Fingerprints"));
@@ -284,7 +314,7 @@ refresh_display (GcrCertificateWidget *self)
break;
}
- asn1_delete_structure (&asn);
+ egg_asn1x_destroy (asn);
}
/* -----------------------------------------------------------------------------
@@ -340,19 +370,49 @@ gcr_certificate_widget_finalize (GObject *obj)
g_assert (!self->pv->certificate);
+ if (self->pv->attributes)
+ gp11_attributes_unref (self->pv->attributes);
+ self->pv->attributes = NULL;
+
+ g_free (self->pv->label);
+ self->pv->label = NULL;
+
G_OBJECT_CLASS (gcr_certificate_widget_parent_class)->finalize (obj);
}
static void
gcr_certificate_widget_set_property (GObject *obj, guint prop_id, const GValue *value,
- GParamSpec *pspec)
+ GParamSpec *pspec)
{
GcrCertificateWidget *self = GCR_CERTIFICATE_WIDGET (obj);
+ GcrCertificate *cert;
+ GP11Attribute *attr;
switch (prop_id) {
case PROP_CERTIFICATE:
gcr_certificate_widget_set_certificate (self, g_value_get_object (value));
break;
+ case PROP_LABEL:
+ g_free (self->pv->label);
+ self->pv->label = g_value_dup_string (value);
+ g_object_notify (obj, "label");
+ break;
+ case PROP_ATTRIBUTES:
+ g_return_if_fail (!self->pv->attributes);
+ self->pv->attributes = g_value_dup_boxed (value);
+ if (self->pv->attributes) {
+ attr = gp11_attributes_find (self->pv->attributes, CKA_VALUE);
+ if (attr) {
+ /* Create a new certificate object refferring to same memory */
+ cert = gcr_simple_certificate_new_static (attr->value, attr->length);
+ g_object_set_data_full (G_OBJECT (cert), "attributes",
+ gp11_attributes_ref (self->pv->attributes),
+ (GDestroyNotify)gp11_attributes_unref);
+ gcr_certificate_widget_set_certificate (self, cert);
+ g_object_unref (cert);
+ }
+ }
+ break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (obj, prop_id, pspec);
break;
@@ -361,7 +421,7 @@ gcr_certificate_widget_set_property (GObject *obj, guint prop_id, const GValue *
static void
gcr_certificate_widget_get_property (GObject *obj, guint prop_id, GValue *value,
- GParamSpec *pspec)
+ GParamSpec *pspec)
{
GcrCertificateWidget *self = GCR_CERTIFICATE_WIDGET (obj);
@@ -369,6 +429,12 @@ gcr_certificate_widget_get_property (GObject *obj, guint prop_id, GValue *value,
case PROP_CERTIFICATE:
g_value_set_object (value, self->pv->certificate);
break;
+ case PROP_LABEL:
+ g_value_take_string (value, calculate_label (self, NULL));
+ break;
+ case PROP_ATTRIBUTES:
+ g_value_set_boxed (value, self->pv->attributes);
+ break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (obj, prop_id, pspec);
break;
@@ -379,6 +445,7 @@ static void
gcr_certificate_widget_class_init (GcrCertificateWidgetClass *klass)
{
GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
+ GP11Attributes *registered;
gcr_certificate_widget_parent_class = g_type_class_peek_parent (klass);
g_type_class_add_private (klass, sizeof (GcrCertificateWidgetPrivate));
@@ -393,7 +460,22 @@ gcr_certificate_widget_class_init (GcrCertificateWidgetClass *klass)
g_param_spec_object("certificate", "Certificate", "Certificate to display.",
GCR_TYPE_CERTIFICATE, G_PARAM_READWRITE));
+ g_object_class_override_property (gobject_class, PROP_LABEL, "label");
+ g_object_class_override_property (gobject_class, PROP_ATTRIBUTES, "attributes");
+
_gcr_icons_register ();
+
+ /* Register this as a view which can be loaded */
+ registered = gp11_attributes_new ();
+ gp11_attributes_add_ulong (registered, CKA_CLASS, CKO_CERTIFICATE);
+ gcr_view_register (GCR_TYPE_CERTIFICATE_WIDGET, registered);
+ gp11_attributes_unref (registered);
+}
+
+static void
+gcr_view_iface_init (GcrViewIface *iface)
+{
+ /* Nothing to do */
}
/* -----------------------------------------------------------------------------
diff --git a/gcr/gcr-simple-certificate.c b/gcr/gcr-simple-certificate.c
index d9bf516..b3dd691 100644
--- a/gcr/gcr-simple-certificate.c
+++ b/gcr/gcr-simple-certificate.c
@@ -30,8 +30,9 @@
#include <string.h>
struct _GcrSimpleCertificatePrivate {
- guchar *owned_data;
- gsize n_owned_data;
+ const guchar *data;
+ gsize n_data;
+ guchar *owned;
};
static void gcr_certificate_iface (GcrCertificateIface *iface);
@@ -52,47 +53,21 @@ static void
gcr_simple_certificate_finalize (GObject *obj)
{
GcrSimpleCertificate *self = GCR_SIMPLE_CERTIFICATE (obj);
-
- g_free (self->pv->owned_data);
- self->pv->owned_data = NULL;
- self->pv->n_owned_data = 0;
-
- G_OBJECT_CLASS (gcr_simple_certificate_parent_class)->finalize (obj);
-}
-static void
-gcr_simple_certificate_set_property (GObject *obj, guint prop_id, const GValue *value,
- GParamSpec *pspec)
-{
- switch (prop_id) {
- default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID (obj, prop_id, pspec);
- break;
- }
-}
+ g_free (self->pv->owned);
+ self->pv->owned = NULL;
+ self->pv->data = NULL;
+ self->pv->n_data = 0;
-static void
-gcr_simple_certificate_get_property (GObject *obj, guint prop_id, GValue *value,
- GParamSpec *pspec)
-{
- switch (prop_id) {
- default:
- G_OBJECT_WARN_INVALID_PROPERTY_ID (obj, prop_id, pspec);
- break;
- }
+ G_OBJECT_CLASS (gcr_simple_certificate_parent_class)->finalize (obj);
}
static void
gcr_simple_certificate_class_init (GcrSimpleCertificateClass *klass)
{
GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
-
gobject_class->finalize = gcr_simple_certificate_finalize;
- gobject_class->set_property = gcr_simple_certificate_set_property;
- gobject_class->get_property = gcr_simple_certificate_get_property;
-
g_type_class_add_private (gobject_class, sizeof (GcrSimpleCertificatePrivate));
-
_gcr_initialize ();
}
@@ -103,11 +78,11 @@ gcr_simple_certificate_real_get_der_data (GcrCertificate *base, gsize *n_data)
g_return_val_if_fail (GCR_IS_CERTIFICATE (self), NULL);
g_return_val_if_fail (n_data, NULL);
- g_return_val_if_fail (self->pv->owned_data, NULL);
-
+ g_return_val_if_fail (self->pv->data, NULL);
+
/* This is called when we're not a base class */
- *n_data = self->pv->n_owned_data;
- return self->pv->owned_data;
+ *n_data = self->pv->n_data;
+ return self->pv->data;
}
static void
@@ -129,8 +104,24 @@ gcr_simple_certificate_new (const guchar *data, gsize n_data)
g_return_val_if_fail (n_data, NULL);
cert = g_object_new (GCR_TYPE_SIMPLE_CERTIFICATE, NULL);
-
- cert->pv->owned_data = g_memdup (data, n_data);
- cert->pv->n_owned_data = n_data;
+
+ cert->pv->data = cert->pv->owned = g_memdup (data, n_data);
+ cert->pv->n_data = n_data;
+ return GCR_CERTIFICATE (cert);
+}
+
+GcrCertificate*
+gcr_simple_certificate_new_static (const guchar *data, gsize n_data)
+{
+ GcrSimpleCertificate *cert;
+
+ g_return_val_if_fail (data, NULL);
+ g_return_val_if_fail (n_data, NULL);
+
+ cert = g_object_new (GCR_TYPE_SIMPLE_CERTIFICATE, NULL);
+
+ cert->pv->owned = NULL;
+ cert->pv->data = data;
+ cert->pv->n_data = n_data;
return GCR_CERTIFICATE (cert);
}
diff --git a/gcr/gcr-simple-certificate.h b/gcr/gcr-simple-certificate.h
index 6548be4..7089af9 100644
--- a/gcr/gcr-simple-certificate.h
+++ b/gcr/gcr-simple-certificate.h
@@ -53,6 +53,9 @@ GType gcr_simple_certificate_get_type (void);
GcrCertificate* gcr_simple_certificate_new (const guchar *data,
gsize n_data);
+GcrCertificate* gcr_simple_certificate_new_static (const guchar *data,
+ gsize n_data);
+
G_END_DECLS
#endif /* __GCR_SIMPLE_CERTIFICATE_H__ */
diff --git a/gcr/gcr-view.c b/gcr/gcr-view.c
new file mode 100644
index 0000000..ff6c763
--- /dev/null
+++ b/gcr/gcr-view.c
@@ -0,0 +1,144 @@
+/*
+ * gnome-keyring
+ *
+ * Copyright (C) 2010 Stefan Walter
+ *
+ * This program 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 program 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 program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#include "config.h"
+
+#include "gcr-view.h"
+
+#include "gp11/gp11.h"
+
+#include <gtk/gtk.h>
+
+typedef struct _GcrRegisteredView {
+ GP11Attributes *attrs;
+ GType view_type;
+} GcrRegisteredView;
+
+static GArray *registered_views = NULL;
+static gboolean registered_sorted = FALSE;
+
+static void
+gcr_view_base_init (gpointer gobject_iface)
+{
+ static gboolean initialized = FALSE;
+ if (!initialized) {
+
+ g_object_interface_install_property (gobject_iface,
+ g_param_spec_string ("label", "Label", "The label for the view",
+ "", G_PARAM_READWRITE));
+
+ g_object_interface_install_property (gobject_iface,
+ g_param_spec_boxed ("attributes", "Attributes", "The data displayed in the view",
+ GP11_TYPE_ATTRIBUTES, G_PARAM_CONSTRUCT_ONLY | G_PARAM_READWRITE));
+
+ initialized = TRUE;
+ }
+}
+
+GType
+gcr_view_get_type (void)
+{
+ static GType type = 0;
+ if (!type) {
+ static const GTypeInfo info = {
+ sizeof (GcrViewIface),
+ gcr_view_base_init, /* base init */
+ NULL, /* base finalize */
+ };
+ type = g_type_register_static (G_TYPE_INTERFACE, "GcrViewIface", &info, 0);
+ g_type_interface_add_prerequisite (type, GTK_TYPE_WIDGET);
+ }
+
+ return type;
+}
+
+static gint
+sort_registered_by_n_attrs (gconstpointer a, gconstpointer b)
+{
+ const GcrRegisteredView *ra = a;
+ const GcrRegisteredView *rb = b;
+ gulong na, nb;
+
+ g_assert (a);
+ g_assert (b);
+
+ na = gp11_attributes_count (ra->attrs);
+ nb = gp11_attributes_count (rb->attrs);
+
+ /* Note we're sorting in reverse order */
+ if (na < nb)
+ return 1;
+ return (na == nb) ? 0 : -1;
+}
+
+GcrView*
+gcr_view_create (const gchar *label, GP11Attributes *attrs)
+{
+ GcrRegisteredView *registered;
+ gboolean matched;
+ gulong n_attrs;
+ gulong j;
+ gsize i;
+
+ g_return_val_if_fail (attrs, NULL);
+
+ if (!registered_views)
+ return NULL;
+
+ if (!registered_sorted) {
+ g_array_sort (registered_views, sort_registered_by_n_attrs);
+ registered_sorted = TRUE;
+ }
+
+ for (i = 0; i < registered_views->len; ++i) {
+ registered = &(g_array_index (registered_views, GcrRegisteredView, i));
+ n_attrs = gp11_attributes_count (registered->attrs);
+
+ matched = TRUE;
+
+ for (j = 0; j < n_attrs; ++j) {
+ if (!gp11_attributes_contains (attrs, gp11_attributes_at (registered->attrs, j))) {
+ matched = FALSE;
+ break;
+ }
+ }
+
+ if (matched)
+ return g_object_new (registered->view_type, "label", label,
+ "attributes", attrs, NULL);
+ }
+
+ return NULL;
+}
+
+void
+gcr_view_register (GType view_type, GP11Attributes *attrs)
+{
+ GcrRegisteredView registered;
+
+ if (!registered_views)
+ registered_views = g_array_new (FALSE, FALSE, sizeof (GcrRegisteredView));
+
+ registered.view_type = view_type;
+ registered.attrs = gp11_attributes_ref (attrs);
+ g_array_append_val (registered_views, registered);
+ registered_sorted = FALSE;
+}
diff --git a/gcr/gcr-view.h b/gcr/gcr-view.h
new file mode 100644
index 0000000..d630756
--- /dev/null
+++ b/gcr/gcr-view.h
@@ -0,0 +1,53 @@
+/*
+ * gnome-keyring
+ *
+ * Copyright (C) 2010 Stefan Walter
+ *
+ * This program 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 program 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 program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#ifndef __GCR_VIEW_H__
+#define __GCR_VIEW_H__
+
+#include <glib-object.h>
+
+#include "gcr-types.h"
+
+G_BEGIN_DECLS
+
+#define GCR_TYPE_VIEW (gcr_view_get_type())
+#define GCR_VIEW(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GCR_TYPE_VIEW, GcrView))
+#define GCR_IS_VIEW(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GCR_TYPE_VIEW))
+#define GCR_VIEW_GET_INTERFACE(inst) (G_TYPE_INSTANCE_GET_INTERFACE ((inst), GCR_TYPE_VIEW, GcrViewIface))
+
+typedef struct _GcrView GcrView;
+typedef struct _GcrViewIface GcrViewIface;
+
+struct _GcrViewIface {
+ GTypeInterface parent;
+};
+
+GType gcr_view_get_type (void) G_GNUC_CONST;
+
+GcrView* gcr_view_create (const gchar *label,
+ struct _GP11Attributes *attrs);
+
+void gcr_view_register (GType view_type,
+ struct _GP11Attributes *attrs);
+
+G_END_DECLS
+
+#endif /* __GCR_VIEW_H__ */
diff --git a/gcr/template/gcr-zzz.c b/gcr/template/gcr-zzz.c
new file mode 100644
index 0000000..23c48fa
--- /dev/null
+++ b/gcr/template/gcr-zzz.c
@@ -0,0 +1,59 @@
+/*
+ * gnome-keyring
+ *
+ * Copyright (C) 2010 Stefan Walter
+ *
+ * This program 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 program 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 program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#include "config.h"
+
+#include "gcr-zzz.h"
+
+static void
+gcr_zzz_base_init (gpointer gobject_class)
+{
+ static volatile gsize initialized = 0;
+ if (g_once_init_enter (&initialized)) {
+ /* Add properties and signals to the interface */
+
+
+ g_once_init_leave (&initialized, 1);
+ }
+}
+
+GType
+gcr_zzz_get_type (void)
+{
+ static GType type = 0;
+ if (!type) {
+ static const GTypeInfo info = {
+ sizeof (GcrZzzIface),
+ gcr_zzz_base_init, /* base init */
+ NULL, /* base finalize */
+ NULL, /* class_init */
+ NULL, /* class finalize */
+ NULL, /* class data */
+ 0,
+ 0, /* n_preallocs */
+ NULL, /* instance init */
+ };
+ type = g_type_register_static (G_TYPE_INTERFACE, "GcrZzzIface", &info, 0);
+ g_type_interface_add_prerequisite (type, G_TYPE_OBJECT);
+ }
+
+ return type;
+}
diff --git a/gcr/template/gcr-zzz.h b/gcr/template/gcr-zzz.h
new file mode 100644
index 0000000..37ab217
--- /dev/null
+++ b/gcr/template/gcr-zzz.h
@@ -0,0 +1,45 @@
+/*
+ * gnome-keyring
+ *
+ * Copyright (C) 2010 Stefan Walter
+ *
+ * This program 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 program 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 program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
+ * 02111-1307, USA.
+ */
+
+#ifndef __GCR_ZZZ_H__
+#define __GCR_ZZZ_H__
+
+#include <glib-object.h>
+
+G_BEGIN_DECLS
+
+#define GCR_TYPE_ZZZ (gcr_zzz_get_type())
+#define GCR_ZZZ(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GCR_TYPE_ZZZ, GcrZzz))
+#define GCR_IS_ZZZ(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GCR_TYPE_ZZZ))
+#define GCR_ZZZ_GET_INTERFACE(inst) (G_TYPE_INSTANCE_GET_INTERFACE ((inst), GCR_TYPE_ZZZ, GcrZzzIface))
+
+typedef struct _GcrZzz GcrZzz;
+typedef struct _GcrZzzIface GcrZzzIface;
+
+struct _GcrZzzIface {
+ GTypeInterface parent;
+};
+
+GType gcr_zzz_get_type (void) G_GNUC_CONST;
+
+G_END_DECLS
+
+#endif /* __GCR_ZZZ_H__ */
diff --git a/gp11/gp11-attributes.c b/gp11/gp11-attributes.c
index afbd08c..7bb76cb 100644
--- a/gp11/gp11-attributes.c
+++ b/gp11/gp11-attributes.c
@@ -629,6 +629,28 @@ gp11_attribute_free (GP11Attribute *attr)
}
}
+gboolean
+gp11_attribute_equal (gconstpointer a, gconstpointer b)
+{
+ const GP11Attribute *aa = a;
+ const GP11Attribute *ab = b;
+
+ if (!a && !b)
+ return TRUE;
+ if (!a || !b)
+ return FALSE;
+
+ if (aa->type != ab->type)
+ return FALSE;
+ if (aa->length != ab->length)
+ return FALSE;
+ if (!aa->value && !ab->value)
+ return TRUE;
+ if (!aa->value || !ab->value)
+ return FALSE;
+ return memcmp (aa->value, ab->value, aa->length) == 0;
+}
+
/**
* SECTION:gp11-attributes
* @title: GP11Attributes
@@ -1337,6 +1359,23 @@ gp11_attributes_unref (GP11Attributes *attrs)
}
}
+gboolean
+gp11_attributes_contains (GP11Attributes *attrs, GP11Attribute *match)
+{
+ GP11Attribute *attr;
+ guint i;
+
+ g_return_val_if_fail (attrs && attrs->array, FALSE);
+
+ for (i = 0; i < attrs->array->len; ++i) {
+ attr = gp11_attributes_at (attrs, i);
+ if (gp11_attribute_equal (attr, match))
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
/* -------------------------------------------------------------------------------------------
* INTERNAL
*
diff --git a/gp11/gp11.h b/gp11/gp11.h
index b04d66e..ea40559 100644
--- a/gp11/gp11.h
+++ b/gp11/gp11.h
@@ -151,13 +151,15 @@ gchar* gp11_attribute_get_string (GP11Attribute *attr
void gp11_attribute_get_date (GP11Attribute *attr,
GDate* value);
+gboolean gp11_attribute_equal (gconstpointer a,
+ gconstpointer b);
+
GP11Attribute* gp11_attribute_dup (GP11Attribute *attr);
void gp11_attribute_clear (GP11Attribute *attr);
void gp11_attribute_free (GP11Attribute *attr);
-
typedef struct _GP11Attributes GP11Attributes;
#define GP11_TYPE_ATTRIBUTES (gp11_attributes_get_boxed_type ())
@@ -235,6 +237,9 @@ GP11Attributes* gp11_attributes_ref (GP11Attributes *att
void gp11_attributes_unref (GP11Attributes *attrs);
+gboolean gp11_attributes_contains (GP11Attributes *attrs,
+ GP11Attribute *match);
+
/* -------------------------------------------------------------------------
* FORWARDS
*/
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]