1 /* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
2 /* gck-attribute.c - the GObject PKCS#11 wrapper library
3
4 Copyright (C) 2008, Stefan Walter
5
6 The Gnome Keyring Library is free software; you can redistribute it and/or
7 modify it under the terms of the GNU Library General Public License as
8 published by the Free Software Foundation; either version 2 of the
9 License, or (at your option) any later version.
10
11 The Gnome Keyring Library is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 Library General Public License for more details.
15
16 You should have received a copy of the GNU Library General Public
17 License along with the Gnome Library; see the file COPYING.LIB. If not,
18 see <http://www.gnu.org/licenses/>.
19
20 Author: Stef Walter <nielsen@memberwebs.com>
21 */
22
23 #include "config.h"
24
25 #include "gck.h"
26 #include "gck-private.h"
27 #include "pkcs11-trust-assertions.h"
28
29 #include "egg/egg-secure-memory.h"
30
31 #include <stdlib.h>
32 #include <string.h>
33
34 /**
35 * SECTION:gck-attribute
36 * @title: GckAttribute
37 * @short_description: A PKCS11 attribute.
38 *
39 * This structure represents a PKCS11 CK_ATTRIBUTE. These attributes contain i
40 * about a PKCS11 object. Use gck_object_get() or gck_object_set() to set and
41 * attributes on an object.
42 *
43 * Although you are free to allocate a #GckAttribute in your own code, no functions in
44 * this library will operate on such an attribute.
45 */
46
47 G_STATIC_ASSERT (sizeof (GckAttribute) == sizeof (CK_ATTRIBUTE));
48
49 #define STATE_LOCKED 1
50 #define STATE_FLOATING 8
51
52 struct _GckAttributes {
53 GckAttribute *data;
54 gulong count;
55 gint refs;
56 gint state;
57 };
58
59 typedef struct {
60 GArray *array;
61 gboolean secure;
62 gint refs;
63 } GckRealBuilder;
64
65 G_STATIC_ASSERT (sizeof (GckRealBuilder) <= sizeof (GckBuilder));
66
67 EGG_SECURE_DECLARE (attributes);
68
69 #define MAX_ALIGN 16
70
71 static guchar *
value_take(gpointer data,gsize length,gboolean secure)72 value_take (gpointer data,
73 gsize length,
74 gboolean secure)
75 {
76 gsize len = length + MAX_ALIGN;
77 guchar *value;
78
79 if (secure)
80 value = egg_secure_realloc (data, len);
81 else
82 value = g_realloc (data, len);
83 g_assert (value != NULL);
84
85 memmove (value + MAX_ALIGN, value, length);
86 g_atomic_int_set ((gint *)value, 1);
87 return value + MAX_ALIGN;
88 }
89
90 static guchar *
value_blank(gsize length,gboolean secure)91 value_blank (gsize length,
92 gboolean secure)
93 {
94 gsize len = length + MAX_ALIGN;
95 guchar *value;
96
97 if (secure)
98 value = egg_secure_alloc (len);
99 else
100 value = g_malloc (len);
101 g_assert (value != NULL);
102
103 g_atomic_int_set ((gint *)value, 1);
104 return value + MAX_ALIGN;
105 }
106
107 static guchar *
value_new(gconstpointer data,gsize length,gboolean secure)108 value_new (gconstpointer data,
109 gsize length,
110 gboolean secure)
111 {
112 guchar *result;
113
114 result = value_blank (length, secure);
115 memcpy (result, data, length);
116 return result;
117 }
118
119 static guchar *
value_ref(guchar * data)120 value_ref (guchar *data)
121 {
122 guchar *value = data - MAX_ALIGN;
123 gint previous;
124
125 g_assert (data != NULL);
126
127 previous = g_atomic_int_add ((gint *)value, 1);
128 if (G_UNLIKELY (previous <= 0)) {
129 g_warning ("An owned GckAttribute value has been modified outside of the "
130 "gck library or an invalid attribute was passed to gck_builder_add_attribute()");
131 return NULL;
132 }
133
134 return data;
135 }
136
137 static void
value_unref(guchar * data)138 value_unref (guchar *data)
139 {
140 guchar *value = data - MAX_ALIGN;
141
142 g_assert (data != NULL);
143
144 if (g_atomic_int_dec_and_test ((gint *)value)) {
145 if (egg_secure_check (value))
146 egg_secure_free (value);
147 else
148 g_free (value);
149 }
150 }
151
G_DEFINE_BOXED_TYPE(GckBuilder,gck_builder,gck_builder_ref,gck_builder_unref)152 G_DEFINE_BOXED_TYPE (GckBuilder, gck_builder,
153 gck_builder_ref, gck_builder_unref)
154
155 /**
156 * GckBuilder:
157 *
158 * A builder for a set of attributes. Add attributes to a builder, and then use
159 * gck_builder_end() to get the completed #GckAttributes.
160 *
161 * The fields of #GckBuilder are private and not to be accessed directly.
162 */
163
164 /**
165 * GckBuilderFlags:
166 * @GCK_BUILDER_NONE: no special flags
167 * @GCK_BUILDER_SECURE_MEMORY: use non-pageable memory for the values of the attributes
168 *
169 * Flags to be used with a gck_builder_init_full() and gck_builder_new().
170 */
171
172 /**
173 * GCK_BUILDER_INIT:
174 *
175 * Values that can be assigned to a #GckBuilder allocated on the stack.
176 *
177 * <informalexample><programlisting>
178 * GckBuilder builder = GCK_BUILDER_INIT;
179 * </programlisting></informalexample>
180 */
181
182 /**
183 * gck_builder_new:
184 * @flags: flags for the new builder
185 *
186 * Create a new #GckBuilder not allocated on the stack, so it can be shared
187 * across a single scope, and referenced / unreferenced.
188 *
189 * Normally a #GckBuilder is created on the stack, and simply initialized.
190 *
191 * If the %GCK_BUILDER_SECURE_MEMORY flag is specified then non-pageable memory
192 * will be used for the various values of the attributes in the builder
193 *
194 * Returns: (transfer full): a new builder, to be freed with gck_builder_unref()
195 */
196 GckBuilder *
197 gck_builder_new (GckBuilderFlags flags)
198 {
199 GckBuilder *builder;
200 GckRealBuilder *real;
201 builder = g_slice_new (GckBuilder);
202 gck_builder_init_full (builder, flags);
203 real = (GckRealBuilder *)builder;
204 real->refs = 1;
205 return builder;
206 }
207
208 /**
209 * gck_builder_ref:
210 * @builder: the builder
211 *
212 * Add a reference to a builder that was created with gck_builder_new(). The
213 * builder must later be unreferenced again with gck_builder_unref().
214 *
215 * It is an error to use this function on builders that were allocated on the
216 * stack.
217 *
218 * Returns: the builder
219 */
220 GckBuilder *
gck_builder_ref(GckBuilder * builder)221 gck_builder_ref (GckBuilder *builder)
222 {
223 GckRealBuilder *real = (GckRealBuilder *)builder;
224 gboolean stack;
225
226 g_return_val_if_fail (builder != NULL, NULL);
227
228 stack = g_atomic_int_add (&real->refs, 1) == 0;
229 if G_UNLIKELY (stack) {
230 g_warning ("Never call gck_builder_ref() on a stack allocated GckBuilder structure");
231 return NULL;
232 }
233
234 return builder;
235 }
236
237 /**
238 * gck_builder_unref:
239 * @builder: the builder
240 *
241 * Unreferences a builder. If this was the last reference then the builder
242 * is freed.
243 *
244 * It is an error to use this function on builders that were allocated on the
245 * stack.
246 */
247 void
gck_builder_unref(gpointer builder)248 gck_builder_unref (gpointer builder)
249 {
250 GckRealBuilder *real = (GckRealBuilder *)builder;
251
252 if (builder == NULL)
253 return;
254
255 if (g_atomic_int_dec_and_test (&real->refs)) {
256 gck_builder_clear (builder);
257 g_slice_free (GckBuilder, builder);
258 }
259 }
260
261 /**
262 * gck_builder_init_full:
263 * @builder: the builder
264 * @flags: the flags for the new builder
265 *
266 * Initialize a stack allocated builder, with the appropriate flags.
267 *
268 * If the %GCK_BUILDER_SECURE_MEMORY flag is specified then non-pageable memory
269 * will be used for the various values of the attributes in the builder
270 */
271 void
gck_builder_init_full(GckBuilder * builder,GckBuilderFlags flags)272 gck_builder_init_full (GckBuilder *builder,
273 GckBuilderFlags flags)
274 {
275 GckRealBuilder *real = (GckRealBuilder *)builder;
276
277 g_return_if_fail (builder != NULL);
278
279 memset (builder, 0, sizeof (GckBuilder));
280 real->secure = flags & GCK_BUILDER_SECURE_MEMORY;
281 }
282
283 /**
284 * gck_builder_init:
285 * @builder: the builder
286 *
287 * Initialize a stack allocated builder, with the default flags.
288 *
289 * This is equivalent to initializing a builder variable with the
290 * %GCK_BUILDER_INIT constant, or setting it to zeroed memory.
291 *
292 * <informalexample><programlisting>
293 * /<!-- -->* Equivalent ways of initializing a GckBuilder *<!-- -->/
294 * GckBuilder builder = GCK_BUILDER_INIT;
295 * GckBuilder builder2;
296 * GckBuilder builder3;
297 *
298 * gck_builder_init (&builder2);
299 *
300 * memset (&builder3, 0, sizeof (builder3));
301 * </programlisting></informalexample>
302 */
303 void
gck_builder_init(GckBuilder * builder)304 gck_builder_init (GckBuilder *builder)
305 {
306 gck_builder_init_full (builder, GCK_BUILDER_NONE);
307 }
308
309 static GckAttribute *
builder_push(GckBuilder * builder,gulong attr_type)310 builder_push (GckBuilder *builder,
311 gulong attr_type)
312 {
313 GckAttribute attr = { attr_type, NULL, 0 };
314 GckRealBuilder *real = (GckRealBuilder *)builder;
315 if (real->array == NULL)
316 real->array = g_array_new (FALSE, TRUE, sizeof (GckAttribute));
317 g_array_append_val (real->array, attr);
318 return &g_array_index (real->array, GckAttribute, real->array->len - 1);
319 }
320
321 static void
builder_clear(GckAttribute * attr)322 builder_clear (GckAttribute *attr)
323 {
324 attr->length = 0;
325 if (attr->value)
326 value_unref (attr->value);
327 attr->value = NULL;
328 }
329
330 static GckAttribute *
find_attribute(GckAttribute * attrs,gsize n_attrs,gulong attr_type)331 find_attribute (GckAttribute *attrs,
332 gsize n_attrs,
333 gulong attr_type)
334 {
335 guint i;
336
337 for (i = 0; i < n_attrs; ++i) {
338 if (attrs[i].type == attr_type)
339 return attrs + i;
340 }
341
342 return NULL;
343 }
344
345 static GckAttribute *
builder_clear_or_push(GckBuilder * builder,gulong attr_type)346 builder_clear_or_push (GckBuilder *builder,
347 gulong attr_type)
348 {
349 GckRealBuilder *real = (GckRealBuilder *)builder;
350 GckAttribute *attr = NULL;
351
352 if (real->array)
353 attr = find_attribute ((GckAttribute *)real->array->data,
354 real->array->len, attr_type);
355 if (attr == NULL)
356 attr = builder_push (builder, attr_type);
357 else
358 builder_clear (attr);
359 return attr;
360 }
361
362 static void
builder_copy(GckBuilder * builder,const GckAttribute * attr,gboolean performing_set)363 builder_copy (GckBuilder *builder,
364 const GckAttribute *attr,
365 gboolean performing_set)
366 {
367 GckAttribute *copy;
368
369 if (performing_set)
370 copy = builder_clear_or_push (builder, attr->type);
371 else
372 copy = builder_push (builder, attr->type);
373 if (attr->length == G_MAXULONG) {
374 copy->value = NULL;
375 copy->length = G_MAXULONG;
376 } else if (attr->value == NULL) {
377 copy->value = NULL;
378 copy->length = 0;
379 } else {
380 copy->value = value_ref (attr->value);
381 copy->length = attr->length;
382 }
383 }
384
385 /**
386 * gck_builder_copy:
387 * @builder: the builder to copy
388 *
389 * Make a copy of the builder and its state. The new builder is allocated
390 * with gck_builder_new() and should be freed with gck_builder_unref().
391 *
392 * Attribute value memory is automatically shared between the two builders,
393 * and is only freed when both are gone.
394 *
395 * Returns: (transfer full): the builder copy, which should be freed with
396 * gck_builder_unref().
397 */
398 GckBuilder *
gck_builder_copy(GckBuilder * builder)399 gck_builder_copy (GckBuilder *builder)
400 {
401 GckRealBuilder *real = (GckRealBuilder *)builder;
402 GckBuilder *copy;
403 guint i;
404
405 if (builder == NULL)
406 return NULL;
407
408 copy = gck_builder_new (real->secure ? GCK_BUILDER_SECURE_MEMORY : GCK_BUILDER_NONE);
409 for (i = 0; real->array && i < real->array->len; i++)
410 builder_copy (copy, &g_array_index (real->array, GckAttribute, i), FALSE);
411
412 return copy;
413 }
414
415 /**
416 * gck_builder_take_data:
417 * @builder: the builder
418 * @attr_type: the new attribute type
419 * @value: (transfer full) (array length=length) (nullable): the new
420 * attribute memory
421 * @length: the length of the memory
422 *
423 * Add a new attribute to the builder with an arbitrary value. Unconditionally
424 * adds a new attribute, even if one with the same @attr_type already exists.
425 *
426 * Ownership of the @value memory is taken by the builder, may be reallocated,
427 * and is eventually freed with g_free(). The memory must have been allocated
428 * using the standard GLib memory allocation routines.
429 *
430 * %NULL may be specified for the @value argument, in which case an empty
431 * attribute is created. GCK_INVALID may be specified for the length, in
432 * which case an invalid attribute is created in the PKCS\#11 style.
433 */
434 void
gck_builder_take_data(GckBuilder * builder,gulong attr_type,guchar * value,gsize length)435 gck_builder_take_data (GckBuilder *builder,
436 gulong attr_type,
437 guchar *value,
438 gsize length)
439 {
440 GckAttribute *attr;
441 gboolean secure;
442
443 g_return_if_fail (builder != NULL);
444
445 secure = value && egg_secure_check (value);
446
447 attr = builder_push (builder, attr_type);
448 if (length == G_MAXULONG) {
449 if (secure)
450 egg_secure_free (value);
451 else
452 g_free (value);
453 attr->value = NULL;
454 attr->length = G_MAXULONG;
455 } else if (value == NULL) {
456 attr->value = NULL;
457 attr->length = 0;
458 } else {
459 attr->value = value_take (value, length, secure);
460 attr->length = length;
461 }
462 }
463
464 /**
465 * gck_builder_add_data:
466 * @builder: the builder
467 * @attr_type: the new attribute type
468 * @value: (array length=length) (nullable): the new attribute memory
469 * @length: the length of the memory
470 *
471 * Add a new attribute to the builder with an arbitrary value. Unconditionally
472 * adds a new attribute, even if one with the same @attr_type already exists.
473 *
474 * The memory in @value is copied by the builder.
475 *
476 * %NULL may be specified for the @value argument, in which case an empty
477 * attribute is created. GCK_INVALID may be specified for the length, in
478 * which case an invalid attribute is created in the PKCS\#11 style.
479 */
480 void
gck_builder_add_data(GckBuilder * builder,gulong attr_type,const guchar * value,gsize length)481 gck_builder_add_data (GckBuilder *builder,
482 gulong attr_type,
483 const guchar *value,
484 gsize length)
485 {
486 GckRealBuilder *real = (GckRealBuilder *)builder;
487 GckAttribute *attr;
488
489 g_return_if_fail (builder != NULL);
490
491 attr = builder_push (builder, attr_type);
492 if (length == G_MAXULONG) {
493 attr->value = NULL;
494 attr->length = G_MAXULONG;
495 } else if (value == NULL) {
496 attr->value = NULL;
497 attr->length = 0;
498 } else {
499 attr->value = value_new (value, length,
500 real->secure || egg_secure_check (value));
501 attr->length = length;
502 }
503 }
504
505 /**
506 * gck_builder_set_data:
507 * @builder: the builder
508 * @attr_type: the attribute type
509 * @value: (array length=length) (nullable): the new attribute memory
510 * @length: the length of the memory
511 *
512 * Set a new attribute to the builder with an arbitrary value. If an attribute
513 * with @attr_type already exists in the builder then it is changed to the new
514 * value, otherwise an attribute is added.
515 *
516 * The memory in @value is copied by the builder.
517 *
518 * %NULL may be specified for the @value argument, in which case an empty
519 * attribute is created. GCK_INVALID may be specified for the length, in
520 * which case an invalid attribute is created in the PKCS\#11 style.
521 */
522 void
gck_builder_set_data(GckBuilder * builder,gulong attr_type,const guchar * value,gsize length)523 gck_builder_set_data (GckBuilder *builder,
524 gulong attr_type,
525 const guchar *value,
526 gsize length)
527 {
528 GckRealBuilder *real = (GckRealBuilder *)builder;
529 GckAttribute *attr;
530
531 g_return_if_fail (builder != NULL);
532
533 attr = builder_clear_or_push (builder, attr_type);
534 if (length == G_MAXULONG) {
535 attr->value = NULL;
536 attr->length = G_MAXULONG;
537 } else if (value == NULL) {
538 attr->value = NULL;
539 attr->length = 0;
540 } else {
541 attr->value = value_new (value, length,
542 real->secure || egg_secure_check (value));
543 attr->length = length;
544 }
545 }
546
547 /**
548 * gck_builder_add_empty:
549 * @builder: the builder
550 * @attr_type: the new attribute type
551 *
552 * Add a new attribute to the builder that is empty. Unconditionally
553 * adds a new attribute, even if one with the same @attr_type already exists.
554 */
555 void
gck_builder_add_empty(GckBuilder * builder,gulong attr_type)556 gck_builder_add_empty (GckBuilder *builder,
557 gulong attr_type)
558 {
559 g_return_if_fail (builder != NULL);
560
561 builder_push (builder, attr_type);
562 }
563
564 /**
565 * gck_builder_set_empty:
566 * @builder: the builder
567 * @attr_type: the attribute type
568 *
569 * Set an attribute on the builder that is empty. If an attribute
570 * with @attr_type already exists in the builder then it is changed to the new
571 * value, otherwise an attribute is added.
572 */
573 void
gck_builder_set_empty(GckBuilder * builder,gulong attr_type)574 gck_builder_set_empty (GckBuilder *builder,
575 gulong attr_type)
576 {
577 g_return_if_fail (builder != NULL);
578
579 builder_clear_or_push (builder, attr_type);
580 }
581
582 /**
583 * gck_builder_add_invalid:
584 * @builder: the builder
585 * @attr_type: the new attribute type
586 *
587 * Add a new attribute to the builder that is invalid in the PKCS\#11 sense.
588 * Unconditionally adds a new attribute, even if one with the same @attr_type
589 * already exists.
590 */
591 void
gck_builder_add_invalid(GckBuilder * builder,gulong attr_type)592 gck_builder_add_invalid (GckBuilder *builder,
593 gulong attr_type)
594 {
595 GckAttribute *attr;
596
597 g_return_if_fail (builder != NULL);
598
599 attr = builder_push (builder, attr_type);
600 attr->length = (gulong)-1;
601 }
602
603 /**
604 * gck_builder_set_invalid:
605 * @builder: the builder
606 * @attr_type: the attribute type
607 *
608 * Set an attribute on the builder that is invalid in the PKCS\#11 sense.
609 * If an attribute with @attr_type already exists in the builder then it is
610 * changed to the new value, otherwise an attribute is added.
611 */
612 void
gck_builder_set_invalid(GckBuilder * builder,gulong attr_type)613 gck_builder_set_invalid (GckBuilder *builder,
614 gulong attr_type)
615 {
616 GckAttribute *attr;
617
618 g_return_if_fail (builder != NULL);
619
620 attr = builder_clear_or_push (builder, attr_type);
621 attr->length = (gulong)-1;
622 }
623
624 /**
625 * gck_builder_add_ulong:
626 * @builder: the builder
627 * @attr_type: the new attribute type
628 * @value: the attribute value
629 *
630 * Add a new attribute to the builder for the unsigned long @value.
631 * Unconditionally adds a new attribute, even if one with the same @attr_type
632 * already exists.
633 */
634 void
gck_builder_add_ulong(GckBuilder * builder,gulong attr_type,gulong value)635 gck_builder_add_ulong (GckBuilder *builder,
636 gulong attr_type,
637 gulong value)
638 {
639 CK_ULONG uval = value;
640 gck_builder_add_data (builder, attr_type,
641 (const guchar *)&uval, sizeof (uval));
642 }
643
644 /**
645 * gck_builder_set_ulong:
646 * @builder: the builder
647 * @attr_type: the new attribute type
648 * @value: the attribute value
649 *
650 * Set an attribute on the builder for the unsigned long @value.
651 * If an attribute with @attr_type already exists in the builder then it is
652 * changed to the new value, otherwise an attribute is added.
653 */
654 void
gck_builder_set_ulong(GckBuilder * builder,gulong attr_type,gulong value)655 gck_builder_set_ulong (GckBuilder *builder,
656 gulong attr_type,
657 gulong value)
658 {
659 CK_ULONG uval = value;
660 gck_builder_set_data (builder, attr_type,
661 (const guchar *)&uval, sizeof (uval));
662 }
663
664 /**
665 * gck_builder_add_boolean:
666 * @builder: the builder
667 * @attr_type: the new attribute type
668 * @value: the attribute value
669 *
670 * Add a new attribute to the builder for the boolean @value.
671 * Unconditionally adds a new attribute, even if one with the same @attr_type
672 * already exists.
673 */
674 void
gck_builder_add_boolean(GckBuilder * builder,gulong attr_type,gboolean value)675 gck_builder_add_boolean (GckBuilder *builder,
676 gulong attr_type,
677 gboolean value)
678 {
679 CK_BBOOL bval = value ? CK_TRUE : CK_FALSE;
680 gck_builder_add_data (builder, attr_type,
681 (const guchar *)&bval, sizeof (bval));
682 }
683
684 /**
685 * gck_builder_set_boolean:
686 * @builder: the builder
687 * @attr_type: the new attribute type
688 * @value: the attribute value
689 *
690 * Set an attribute on the builder for the boolean @value.
691 * If an attribute with @attr_type already exists in the builder then it is
692 * changed to the new value, otherwise an attribute is added.
693 */
694 void
gck_builder_set_boolean(GckBuilder * builder,gulong attr_type,gboolean value)695 gck_builder_set_boolean (GckBuilder *builder,
696 gulong attr_type,
697 gboolean value)
698 {
699 CK_BBOOL bval = value ? CK_TRUE : CK_FALSE;
700 gck_builder_set_data (builder, attr_type,
701 (const guchar *)&bval, sizeof (bval));
702 }
703
704 static void
convert_gdate_to_ckdate(const GDate * value,CK_DATE * date)705 convert_gdate_to_ckdate (const GDate *value,
706 CK_DATE *date)
707 {
708 gchar buffer[9];
709 g_snprintf (buffer, sizeof (buffer), "%04d%02d%02d",
710 (int)g_date_get_year (value),
711 (int)g_date_get_month (value),
712 (int)g_date_get_day (value));
713 memcpy (&date->year, buffer + 0, 4);
714 memcpy (&date->month, buffer + 4, 2);
715 memcpy (&date->day, buffer + 6, 2);
716 }
717
718 /**
719 * gck_builder_add_date:
720 * @builder: the builder
721 * @attr_type: the new attribute type
722 * @value: the attribute value
723 *
724 * Add a new attribute to the builder for the date @value.
725 * Unconditionally adds a new attribute, even if one with the same @attr_type
726 * already exists.
727 */
728 void
gck_builder_add_date(GckBuilder * builder,gulong attr_type,const GDate * value)729 gck_builder_add_date (GckBuilder *builder,
730 gulong attr_type,
731 const GDate *value)
732 {
733 CK_DATE date;
734
735 g_return_if_fail (value != NULL);
736
737 convert_gdate_to_ckdate (value, &date);
738 gck_builder_add_data (builder, attr_type,
739 (const guchar *)&date, sizeof (CK_DATE));
740 }
741
742 /**
743 * gck_builder_set_date:
744 * @builder: the builder
745 * @attr_type: the new attribute type
746 * @value: the attribute value
747 *
748 * Set an attribute on the builder for the date @value.
749 * If an attribute with @attr_type already exists in the builder then it is
750 * changed to the new value, otherwise an attribute is added.
751 */
752 void
gck_builder_set_date(GckBuilder * builder,gulong attr_type,const GDate * value)753 gck_builder_set_date (GckBuilder *builder,
754 gulong attr_type,
755 const GDate *value)
756 {
757 CK_DATE date;
758
759 g_return_if_fail (value != NULL);
760
761 convert_gdate_to_ckdate (value, &date);
762 gck_builder_set_data (builder, attr_type,
763 (const guchar *)&date, sizeof (CK_DATE));
764 }
765
766 /**
767 * gck_builder_add_string:
768 * @builder: the builder
769 * @attr_type: the new attribute type
770 * @value: (nullable): the attribute value
771 *
772 * Add a new attribute to the builder for the string @value or %NULL.
773 * Unconditionally adds a new attribute, even if one with the same @attr_type
774 * already exists.
775 */
776 void
gck_builder_add_string(GckBuilder * builder,gulong attr_type,const gchar * value)777 gck_builder_add_string (GckBuilder *builder,
778 gulong attr_type,
779 const gchar *value)
780 {
781 gck_builder_add_data (builder, attr_type,
782 (const guchar *)value, value ? strlen (value) : 0);
783 }
784
785 /**
786 * gck_builder_set_string:
787 * @builder: the builder
788 * @attr_type: the new attribute type
789 * @value: the attribute value
790 *
791 * Set an attribute on the builder for the string @value or %NULL.
792 * If an attribute with @attr_type already exists in the builder then it is
793 * changed to the new value, otherwise an attribute is added.
794 */
795 void
gck_builder_set_string(GckBuilder * builder,gulong attr_type,const gchar * value)796 gck_builder_set_string (GckBuilder *builder,
797 gulong attr_type,
798 const gchar *value)
799 {
800 gck_builder_set_data (builder, attr_type,
801 (const guchar *)value, value ? strlen (value) : 0);
802 }
803
804 /**
805 * gck_builder_add_attribute:
806 * @builder: the builder
807 * @attr: the attribute to add
808 *
809 * Add an attribute to the builder. The attribute is added unconditionally whether
810 * or not an attribute with the same type already exists on the builder.
811 *
812 * The @attr attribute must have been created or owned by the Gck library.
813 * If you call this function on an arbitrary #GckAttribute that is allocated on
814 * the stack or elsewhere, then this will result in undefined behavior.
815 *
816 * As an optimization, the attribute memory value is automatically shared
817 * between the attribute and the builder.
818 */
819 void
gck_builder_add_attribute(GckBuilder * builder,const GckAttribute * attr)820 gck_builder_add_attribute (GckBuilder *builder,
821 const GckAttribute *attr)
822 {
823 g_return_if_fail (builder != NULL);
824 g_return_if_fail (attr != NULL);
825
826 builder_copy (builder, attr, FALSE);
827 }
828
829 /**
830 * gck_builder_add_all:
831 * @builder: the builder
832 * @attrs: the attributes to add
833 *
834 * Add all the @attrs attributes to the builder. The attributes are added
835 * uncondititionally whether or not attributes with the same types already
836 * exist in the builder.
837 *
838 * As an optimization, the attribute memory values are automatically shared
839 * between the attributes and the builder.
840 */
841 void
gck_builder_add_all(GckBuilder * builder,GckAttributes * attrs)842 gck_builder_add_all (GckBuilder *builder,
843 GckAttributes *attrs)
844 {
845 gulong i;
846
847 g_return_if_fail (builder != NULL);
848 g_return_if_fail (attrs != NULL);
849
850 for (i = 0; i < attrs->count; i++)
851 builder_copy (builder, &attrs->data[i], FALSE);
852 }
853
854 /**
855 * gck_builder_add_only: (skip)
856 * @builder: the builder
857 * @attrs: the attributes to add
858 * @only_type: the first type of attribute to add
859 * @...: the remaining attribute types to add, ending with %GCK_INVALID
860 *
861 * Add the attributes specified in the argument list from @attrs to the
862 * builder. The attributes are added uncondititionally whether or not
863 * attributes with the same types already exist in the builder.
864 *
865 * The variable arguments must be unsigned longs.
866 *
867 * <informalexample><programlisting>
868 * /<!-- -->* Add the CKA_ID and CKA_CLASS attributes from attrs to builder *<!-- -->/
869 * gck_builder_add_only (builder, attrs, CKA_ID, CKA_CLASS, GCK_INVALID);
870 * </programlisting></informalexample>
871 *
872 * As an optimization, the attribute memory values are automatically shared
873 * between the attributes and the builder.
874 */
875 void
gck_builder_add_only(GckBuilder * builder,GckAttributes * attrs,gulong only_type,...)876 gck_builder_add_only (GckBuilder *builder,
877 GckAttributes *attrs,
878 gulong only_type,
879 ...)
880 {
881 GArray *types;
882 va_list va;
883
884 g_return_if_fail (builder != NULL);
885 g_return_if_fail (attrs != NULL);
886
887 types = g_array_new (FALSE, FALSE, sizeof (gulong));
888
889 va_start (va, only_type);
890 while (only_type != GCK_INVALID) {
891 g_array_append_val (types, only_type);
892 only_type = va_arg (va, gulong);
893 }
894 va_end (va);
895
896 gck_builder_add_onlyv (builder, attrs, (gulong *)types->data, types->len);
897 g_array_free (types, TRUE);
898 }
899
900 /**
901 * gck_builder_add_onlyv: (rename-to gck_builder_add_only)
902 * @builder: the builder
903 * @attrs: the attributes to add
904 * @only_types: (array length=n_only_types): the types of attributes to add
905 * @n_only_types: the number of attributes
906 *
907 * Add the attributes with the types in @only_types from @attrs to the
908 * builder. The attributes are added uncondititionally whether or not
909 * attributes with the same types already exist in the builder.
910 *
911 * <informalexample><programlisting>
912 * /<!-- -->* Add the CKA_ID and CKA_CLASS attributes from attrs to builder *<!-- -->/
913 * gulong only[] = { CKA_ID, CKA_CLASS };
914 * gck_builder_add_onlyv (builder, attrs, only, 2);
915 * </programlisting></informalexample>
916 *
917 * As an optimization, the attribute memory values are automatically shared
918 * between the attributes and the builder.
919 */
920 void
gck_builder_add_onlyv(GckBuilder * builder,GckAttributes * attrs,const gulong * only_types,guint n_only_types)921 gck_builder_add_onlyv (GckBuilder *builder,
922 GckAttributes *attrs,
923 const gulong *only_types,
924 guint n_only_types)
925 {
926 gulong i;
927 guint j;
928
929 g_return_if_fail (builder != NULL);
930 g_return_if_fail (attrs != NULL);
931
932 for (i = 0; i < attrs->count; i++) {
933 for (j = 0; j < n_only_types; j++) {
934 if (attrs->data[i].type == only_types[j])
935 builder_copy (builder, &attrs->data[i], FALSE);
936 }
937 }
938 }
939
940 /**
941 * gck_builder_add_except: (skip)
942 * @builder: the builder
943 * @attrs: the attributes to add
944 * @except_type: the first type of attribute to to exclude
945 * @...: the remaining attribute types to exclude, ending with %GCK_INVALID
946 *
947 * Add the attributes in @attrs to the builder, with the exception of those
948 * in the argument list. The attributes are added uncondititionally whether or
949 * not attributes with the same types already exist in the builder.
950 *
951 * The variable arguments must be unsigned longs.
952 *
953 * <informalexample><programlisting>
954 * /<!-- -->* Add all attributes in attrs except CKA_CLASS to the builder *<!-- -->/
955 * gck_builder_add_except (builder, attrs, CKA_CLASS, GCK_INVALID);
956 * </programlisting></informalexample>
957 *
958 * As an optimization, the attribute memory values are automatically shared
959 * between the attributes and the builder.
960 */
961 void
gck_builder_add_except(GckBuilder * builder,GckAttributes * attrs,gulong except_type,...)962 gck_builder_add_except (GckBuilder *builder,
963 GckAttributes *attrs,
964 gulong except_type,
965 ...)
966 {
967 GArray *types;
968 va_list va;
969
970 g_return_if_fail (builder != NULL);
971 g_return_if_fail (attrs != NULL);
972
973 types = g_array_new (FALSE, FALSE, sizeof (gulong));
974
975 va_start (va, except_type);
976 while (except_type != GCK_INVALID) {
977 g_array_append_val (types, except_type);
978 except_type = va_arg (va, gulong);
979 }
980 va_end (va);
981
982 gck_builder_add_exceptv (builder, attrs, (gulong *)types->data, types->len);
983 g_array_free (types, TRUE);
984 }
985
986 /**
987 * gck_builder_add_exceptv: (skip)
988 * @builder: the builder
989 * @attrs: the attributes to add
990 * @except_types: (array length=n_except_types): the except types
991 * @n_except_types: the number of except types
992 *
993 * Add the attributes in @attrs to the builder, with the exception of those
994 * whose types are specified in @except_types. The attributes are added
995 * uncondititionally whether or not attributes with the same types already
996 * exist in the builder.
997 *
998 * <informalexample><programlisting>
999 * /<!-- -->* Add all attributes in attrs except CKA_CLASS to the builder *<!-- -->/
1000 * gulong except_types[] = { CKA_CLASS };
1001 * gck_builder_add_exceptv (builder, attrs, except_types, 1);
1002 * </programlisting></informalexample>
1003 *
1004 * As an optimization, the attribute memory values are automatically shared
1005 * between the attributes and the builder.
1006 */
1007 void
gck_builder_add_exceptv(GckBuilder * builder,GckAttributes * attrs,const gulong * except_types,guint n_except_types)1008 gck_builder_add_exceptv (GckBuilder *builder,
1009 GckAttributes *attrs,
1010 const gulong *except_types,
1011 guint n_except_types)
1012 {
1013 gulong i;
1014 guint j;
1015
1016 g_return_if_fail (builder != NULL);
1017 g_return_if_fail (attrs != NULL);
1018
1019 for (i = 0; i < attrs->count; i++) {
1020 for (j = 0; j < n_except_types; j++) {
1021 if (attrs->data[i].type == except_types[j])
1022 break;
1023 }
1024 if (j == n_except_types)
1025 builder_copy (builder, &attrs->data[i], FALSE);
1026 }
1027 }
1028
1029 /**
1030 * gck_builder_set_all:
1031 * @builder: the builder
1032 * @attrs: the attributes to set
1033 *
1034 * Set all the @attrs attributes to the builder. If any attributes with the
1035 * same types are already present in the builder, then those attributes are
1036 * changed to the new values.
1037 *
1038 * As an optimization, the attribute memory values are automatically shared
1039 * between the attributes and the builder.
1040 */
1041 void
gck_builder_set_all(GckBuilder * builder,GckAttributes * attrs)1042 gck_builder_set_all (GckBuilder *builder,
1043 GckAttributes *attrs)
1044 {
1045 gulong i;
1046
1047 g_return_if_fail (builder != NULL);
1048 g_return_if_fail (attrs != NULL);
1049
1050 for (i = 0; i < attrs->count; i++)
1051 builder_copy (builder, &attrs->data[i], TRUE);
1052 }
1053
1054 /**
1055 * gck_builder_find:
1056 * @builder: the builder
1057 * @attr_type: the type of attribute to find
1058 *
1059 * Find an attribute in the builder. Both valid and invalid attributes (in
1060 * the PKCS\#11 sense) are returned. If multiple attributes exist for the given
1061 * attribute type, then the first one is returned.
1062 *
1063 * The returned #GckAttribute is owned by the builder and may not be modified
1064 * in any way. It is only valid until another attribute is added to or set on
1065 * the builder, or until the builder is cleared or unreferenced.
1066 *
1067 * Returns: the attribute or %NULL if not found
1068 */
1069 const GckAttribute *
gck_builder_find(GckBuilder * builder,gulong attr_type)1070 gck_builder_find (GckBuilder *builder,
1071 gulong attr_type)
1072 {
1073 GckRealBuilder *real = (GckRealBuilder *)builder;
1074
1075 g_return_val_if_fail (builder != NULL, NULL);
1076
1077 if (real->array == NULL)
1078 return NULL;
1079
1080 return find_attribute ((GckAttribute *)real->array->data,
1081 real->array->len, attr_type);
1082 }
1083
1084 static gboolean
find_attribute_boolean(GckAttribute * attrs,gsize n_attrs,gulong attr_type,gboolean * value)1085 find_attribute_boolean (GckAttribute *attrs,
1086 gsize n_attrs,
1087 gulong attr_type,
1088 gboolean *value)
1089 {
1090 GckAttribute *attr;
1091
1092 attr = find_attribute (attrs, n_attrs, attr_type);
1093 if (!attr || gck_attribute_is_invalid (attr))
1094 return FALSE;
1095 return gck_value_to_boolean (attr->value, attr->length, value);
1096 }
1097
1098 /**
1099 * gck_builder_find_boolean:
1100 * @builder: the builder
1101 * @attr_type: the type of attribute to find
1102 * @value: (out): the location to place the found value
1103 *
1104 * Find a boolean attribute in the builder that has the type @attr_type, is
1105 * of the correct boolean size, and is not invalid in the PKCS\#11 sense.
1106 * If multiple attributes exist for the given attribute type, then the first\
1107 * one is returned.
1108 *
1109 * Returns: whether a valid boolean attribute was found
1110 */
1111 gboolean
gck_builder_find_boolean(GckBuilder * builder,gulong attr_type,gboolean * value)1112 gck_builder_find_boolean (GckBuilder *builder,
1113 gulong attr_type,
1114 gboolean *value)
1115 {
1116 GckRealBuilder *real = (GckRealBuilder *)builder;
1117
1118 g_return_val_if_fail (builder != NULL, FALSE);
1119 g_return_val_if_fail (value != NULL, FALSE);
1120
1121 if (real->array == NULL)
1122 return FALSE;
1123
1124 return find_attribute_boolean ((GckAttribute *)real->array->data,
1125 real->array->len, attr_type, value);
1126 }
1127
1128 static gboolean
find_attribute_ulong(GckAttribute * attrs,gsize n_attrs,gulong attr_type,gulong * value)1129 find_attribute_ulong (GckAttribute *attrs,
1130 gsize n_attrs,
1131 gulong attr_type,
1132 gulong *value)
1133 {
1134 GckAttribute *attr;
1135
1136 attr = find_attribute (attrs, n_attrs, attr_type);
1137 if (!attr || gck_attribute_is_invalid (attr))
1138 return FALSE;
1139 return gck_value_to_ulong (attr->value, attr->length, value);
1140 }
1141
1142 /**
1143 * gck_builder_find_ulong:
1144 * @builder: the builder
1145 * @attr_type: the type of attribute to find
1146 * @value: (out): the location to place the found value
1147 *
1148 * Find a unsigned long attribute in the builder that has the type @attr_type,
1149 * is of the correct unsigned long size, and is not invalid in the PKCS\#11 sense.
1150 * If multiple attributes exist for the given attribute type, then the first\
1151 * one is returned.
1152 *
1153 * Returns: whether a valid unsigned long attribute was found
1154 */
1155 gboolean
gck_builder_find_ulong(GckBuilder * builder,gulong attr_type,gulong * value)1156 gck_builder_find_ulong (GckBuilder *builder,
1157 gulong attr_type,
1158 gulong *value)
1159 {
1160 GckRealBuilder *real = (GckRealBuilder *)builder;
1161
1162 g_return_val_if_fail (builder != NULL, FALSE);
1163 g_return_val_if_fail (value != NULL, FALSE);
1164
1165 if (real->array == NULL)
1166 return FALSE;
1167
1168 return find_attribute_ulong ((GckAttribute *)real->array->data,
1169 real->array->len, attr_type, value);
1170 }
1171
1172 static gboolean
find_attribute_string(GckAttribute * attrs,gsize n_attrs,gulong attr_type,gchar ** value)1173 find_attribute_string (GckAttribute *attrs,
1174 gsize n_attrs,
1175 gulong attr_type,
1176 gchar **value)
1177 {
1178 GckAttribute *attr;
1179 gchar *string;
1180
1181 attr = find_attribute (attrs, n_attrs, attr_type);
1182 if (!attr || gck_attribute_is_invalid (attr))
1183 return FALSE;
1184 string = gck_attribute_get_string (attr);
1185 if (string == NULL)
1186 return FALSE;
1187 *value = string;
1188 return TRUE;
1189 }
1190
1191 /**
1192 * gck_builder_find_string:
1193 * @builder: the builder
1194 * @attr_type: the type of attribute to find
1195 * @value: (out): the location to place the found value
1196 *
1197 * Find a string attribute in the builder that has the type @attr_type, has a
1198 * non %NULL value pointer, and is not invalid in the PKCS\#11 sense.
1199 * If multiple attributes exist for the given attribute type, then the first
1200 * one is returned.
1201 *
1202 * Returns: whether a valid string attribute was found
1203 */
1204 gboolean
gck_builder_find_string(GckBuilder * builder,gulong attr_type,gchar ** value)1205 gck_builder_find_string (GckBuilder *builder,
1206 gulong attr_type,
1207 gchar **value)
1208 {
1209 GckRealBuilder *real = (GckRealBuilder *)builder;
1210
1211 g_return_val_if_fail (builder != NULL, FALSE);
1212 g_return_val_if_fail (value != NULL, FALSE);
1213
1214 if (real->array == NULL)
1215 return FALSE;
1216
1217 return find_attribute_string ((GckAttribute *)real->array->data,
1218 real->array->len, attr_type, value);
1219 }
1220
1221 static gboolean
find_attribute_date(GckAttribute * attrs,gsize n_attrs,gulong attr_type,GDate * value)1222 find_attribute_date (GckAttribute *attrs,
1223 gsize n_attrs,
1224 gulong attr_type,
1225 GDate *value)
1226 {
1227 GckAttribute *attr;
1228
1229 attr = find_attribute (attrs, n_attrs, attr_type);
1230 if (!attr || gck_attribute_is_invalid (attr))
1231 return FALSE;
1232 gck_attribute_get_date (attr, value);
1233 return TRUE;
1234 }
1235
1236 /**
1237 * gck_builder_find_date:
1238 * @builder: the builder
1239 * @attr_type: the type of attribute to find
1240 * @value: (out): the location to place the found value
1241 *
1242 * Find a date attribute in the builder that has the type @attr_type, is of
1243 * the correct date size, and is not invalid in the PKCS\#11 sense.
1244 * If multiple attributes exist for the given attribute type, then the first
1245 * one is returned.
1246 *
1247 * Returns: whether a valid date attribute was found
1248 */
1249 gboolean
gck_builder_find_date(GckBuilder * builder,gulong attr_type,GDate * value)1250 gck_builder_find_date (GckBuilder *builder,
1251 gulong attr_type,
1252 GDate *value)
1253 {
1254 GckRealBuilder *real = (GckRealBuilder *)builder;
1255
1256 g_return_val_if_fail (builder != NULL, FALSE);
1257 g_return_val_if_fail (value != NULL, FALSE);
1258
1259 if (real->array == NULL)
1260 return FALSE;
1261
1262 return find_attribute_date ((GckAttribute *)real->array->data,
1263 real->array->len, attr_type, value);
1264 }
1265
1266 /**
1267 * gck_builder_steal:
1268 * @builder: the builder
1269 *
1270 * Take the attributes that have been built in the #GckBuilder. The builder
1271 * will no longer contain any attributes after this function call.
1272 *
1273 * The returned set of attributes is a full reference, not floating.
1274 *
1275 * Returns: (transfer full): the stolen attributes, which should be freed with
1276 * gck_attributes_unref()
1277 */
1278 GckAttributes *
gck_builder_steal(GckBuilder * builder)1279 gck_builder_steal (GckBuilder *builder)
1280 {
1281 GckRealBuilder *real = (GckRealBuilder *)builder;
1282 GckAttributes *attrs;
1283 gpointer data;
1284 gulong length;
1285
1286 g_return_val_if_fail (builder != NULL, NULL);
1287
1288 if (real->array) {
1289 length = real->array->len;
1290 data = g_array_free (real->array, FALSE);
1291 real->array = NULL;
1292 } else {
1293 length = 0;
1294 data = NULL;
1295 }
1296
1297 attrs = g_slice_new0 (GckAttributes);
1298 attrs->count = length;
1299 attrs->data = data;
1300 attrs->refs = 1;
1301
1302 return attrs;
1303 }
1304
1305 /**
1306 * gck_builder_end:
1307 * @builder: the builder
1308 *
1309 * Complete the #GckBuilder, and return the attributes contained in the builder.
1310 * The #GckBuilder will be cleared after this function call, and it is no
1311 * longer necessary to use gck_builder_clear() on it, although it is also
1312 * permitted. The builder may be used again to build another set of attributes
1313 * after this function call.
1314 *
1315 * The returned set of attributes is floating, and should either be passed to
1316 * another gck library function which consumes this floating reference, or if
1317 * you wish to keep these attributes around you should ref them with
1318 * gck_attributes_ref_sink() and unref them later with gck_attributes_unref().
1319 *
1320 * Returns: (transfer none): a floating reference to the attributes created
1321 * in the builder
1322 */
1323 GckAttributes *
gck_builder_end(GckBuilder * builder)1324 gck_builder_end (GckBuilder *builder)
1325 {
1326 GckRealBuilder *real = (GckRealBuilder *)builder;
1327 GckAttributes *attrs;
1328
1329 g_return_val_if_fail (builder != NULL, NULL);
1330
1331 attrs = gck_builder_steal (builder);
1332 attrs->state |= STATE_FLOATING;
1333
1334 g_assert (real->array == NULL);
1335 return attrs;
1336 }
1337
1338 /**
1339 * gck_builder_clear:
1340 * @builder: the builder
1341 *
1342 * Clear the builder and release all allocated memory. The builder may be used
1343 * again to build another set of attributes after this function call.
1344 *
1345 * If memory is shared between this builder and other attributes, then that
1346 * memory is only freed when both of them are cleared or unreferenced.
1347 */
1348 void
gck_builder_clear(GckBuilder * builder)1349 gck_builder_clear (GckBuilder *builder)
1350 {
1351 GckRealBuilder *real = (GckRealBuilder *)builder;
1352 GckAttribute *attr;
1353 guint i;
1354
1355 g_return_if_fail (builder != NULL);
1356
1357 if (real->array == NULL)
1358 return;
1359
1360 for (i = 0; i < real->array->len; i++) {
1361 attr = &g_array_index (real->array, GckAttribute, i);
1362 builder_clear (attr);
1363 }
1364
1365 g_array_free (real->array, TRUE);
1366 real->array = NULL;
1367 }
1368
1369 /**
1370 * GckAttribute:
1371 * @type: The attribute type, such as CKA_LABEL.
1372 * @value: (array length=length): The value of the attribute. May be %NULL.
1373 * @length: The length of the attribute. May be GCK_INVALID if the attribute is invalid.
1374 *
1375 * This structure represents a PKCS11 CK_ATTRIBUTE.
1376 */
1377
1378 /**
1379 * gck_attribute_is_invalid:
1380 * @attr: The attribute to check.
1381 *
1382 * Check if the PKCS\#11 attribute represents 'invalid' or 'not found'
1383 * according to the PKCS\#11 spec. That is, having length
1384 * of (CK_ULONG)-1.
1385 *
1386 * Return value: Whether the attribute represents invalid or not.
1387 */
1388 gboolean
gck_attribute_is_invalid(const GckAttribute * attr)1389 gck_attribute_is_invalid (const GckAttribute *attr)
1390 {
1391 g_return_val_if_fail (attr, TRUE);
1392 return attr->length == (gulong)-1;
1393 }
1394
1395 /**
1396 * gck_attribute_get_boolean:
1397 * @attr: The attribute to retrieve value from.
1398 *
1399 * Get the CK_BBOOL of a PKCS\#11 attribute. No conversion
1400 * is performed. It is an error to pass an attribute to this
1401 * function unless you're know it's supposed to contain a
1402 * boolean value.
1403 *
1404 * Return value: The boolean value of the attribute.
1405 */
1406 gboolean
gck_attribute_get_boolean(const GckAttribute * attr)1407 gck_attribute_get_boolean (const GckAttribute *attr)
1408 {
1409 gboolean value;
1410
1411 g_return_val_if_fail (attr, FALSE);
1412 if (gck_attribute_is_invalid (attr))
1413 return FALSE;
1414 if (!gck_value_to_boolean (attr->value, attr->length, &value))
1415 g_return_val_if_reached (FALSE);
1416 return value;
1417 }
1418
1419 /**
1420 * gck_attribute_get_ulong:
1421 * @attr: The attribute to retrieve value from.
1422 *
1423 * Get the CK_ULONG value of a PKCS\#11 attribute. No
1424 * conversion is performed. It is an error to pass an attribute
1425 * to this function unless you're know it's supposed to contain
1426 * a value of the right type.
1427 *
1428 * Return value: The ulong value of the attribute.
1429 */
1430 gulong
gck_attribute_get_ulong(const GckAttribute * attr)1431 gck_attribute_get_ulong (const GckAttribute *attr)
1432 {
1433 gulong value;
1434
1435 g_return_val_if_fail (attr, FALSE);
1436 if (gck_attribute_is_invalid (attr))
1437 return 0;
1438 if (!gck_value_to_ulong (attr->value, attr->length, &value))
1439 g_return_val_if_reached ((gulong)-1);
1440 return value;
1441 }
1442
1443 /**
1444 * gck_attribute_get_string:
1445 * @attr: The attribute to retrieve value from.
1446 *
1447 * Get the string value of a PKCS\#11 attribute. No
1448 * conversion is performed. It is an error to pass an attribute
1449 * to this function unless you're know it's supposed to contain
1450 * a value of the right type.
1451 *
1452 * Return value: (nullable): a null terminated string, to be freed with
1453 * g_free(), or %NULL if the value was invalid
1454 */
1455 gchar*
gck_attribute_get_string(const GckAttribute * attr)1456 gck_attribute_get_string (const GckAttribute *attr)
1457 {
1458 g_return_val_if_fail (attr, NULL);
1459
1460 if (gck_attribute_is_invalid (attr))
1461 return NULL;
1462 if (!attr->value)
1463 return NULL;
1464
1465 return g_strndup ((gchar*)attr->value, attr->length);
1466 }
1467
1468 /**
1469 * gck_attribute_get_date:
1470 * @attr: The attribute to retrieve value from.
1471 * @value: The date value to fill in with the parsed date.
1472 *
1473 * Get the CK_DATE of a PKCS\#11 attribute. No
1474 * conversion is performed. It is an error to pass an attribute
1475 * to this function unless you're know it's supposed to contain
1476 * a value of the right type.
1477 */
1478 void
gck_attribute_get_date(const GckAttribute * attr,GDate * value)1479 gck_attribute_get_date (const GckAttribute *attr,
1480 GDate *value)
1481 {
1482 guint year, month, day;
1483 gchar buffer[5];
1484 CK_DATE *date;
1485 gchar *end;
1486
1487 g_return_if_fail (attr);
1488
1489 if (gck_attribute_is_invalid (attr)) {
1490 g_date_clear (value, 1);
1491 return;
1492 }
1493
1494 g_return_if_fail (attr->length == sizeof (CK_DATE));
1495 g_return_if_fail (attr->value);
1496 date = (CK_DATE*)attr->value;
1497
1498 memset (&buffer, 0, sizeof (buffer));
1499 memcpy (buffer, date->year, 4);
1500 year = strtol (buffer, &end, 10);
1501 g_return_if_fail (end != buffer && !*end);
1502
1503 memset (&buffer, 0, sizeof (buffer));
1504 memcpy (buffer, date->month, 2);
1505 month = strtol (buffer, &end, 10);
1506 g_return_if_fail (end != buffer && !*end);
1507
1508 memset (&buffer, 0, sizeof (buffer));
1509 memcpy (buffer, date->day, 2);
1510 day = strtol (buffer, &end, 10);
1511 g_return_if_fail (end != buffer && !*end);
1512
1513 g_date_set_dmy (value, day, month, year);
1514 }
1515
1516 /**
1517 * gck_attribute_get_data:
1518 * @attr: an attribute
1519 * @length: the length of the returned data
1520 *
1521 * Get the raw value in the attribute.
1522 *
1523 * This is useful from scripting languages. C callers will generally
1524 * access the #GckAttribute struct directly.
1525 *
1526 * This function will %NULL if the attribute contains empty or invalid
1527 * data. The returned data must not be modified and is only valid
1528 * as long as this @attribute.
1529 *
1530 * Returns: (transfer none) (array length=length): the value data or %NULL
1531 */
1532 const guchar *
gck_attribute_get_data(const GckAttribute * attr,gsize * length)1533 gck_attribute_get_data (const GckAttribute *attr,
1534 gsize *length)
1535 {
1536 g_return_val_if_fail (attr != NULL, NULL);
1537
1538 if (attr->length == G_MAXULONG) {
1539 *length = 0;
1540 return NULL;
1541 }
1542 *length = attr->length;
1543 return attr->value;
1544 }
1545
1546 /**
1547 * gck_attribute_init: (skip)
1548 * @attr: an uninitialized attribute
1549 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1550 * @value: (array length=length): The raw value of the attribute.
1551 * @length: The length of the raw value.
1552 *
1553 * Initialize a PKCS\#11 attribute. This copies the value memory
1554 * into an internal buffer.
1555 *
1556 * When done with the attribute you should use gck_attribute_clear()
1557 * to free the internal memory.
1558 **/
1559 void
gck_attribute_init(GckAttribute * attr,gulong attr_type,const guchar * value,gsize length)1560 gck_attribute_init (GckAttribute *attr,
1561 gulong attr_type,
1562 const guchar *value,
1563 gsize length)
1564 {
1565 g_return_if_fail (attr != NULL);
1566
1567 attr->type = attr_type;
1568 if (length == G_MAXULONG) {
1569 attr->value = NULL;
1570 attr->length = G_MAXULONG;
1571 } else if (value == NULL) {
1572 attr->value = NULL;
1573 attr->length = 0;
1574 } else {
1575 attr->value = value_new (value, length, egg_secure_check (value));
1576 attr->length = length;
1577 }
1578 }
1579
1580 /**
1581 * gck_attribute_init_invalid: (skip)
1582 * @attr: an uninitialized attribute
1583 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1584 *
1585 * Initialize a PKCS\#11 attribute to an 'invalid' or 'not found'
1586 * state. Specifically this sets the value length to (CK_ULONG)-1
1587 * as specified in the PKCS\#11 specification.
1588 *
1589 * When done with the attribute you should use gck_attribute_clear()
1590 * to free the internal memory.
1591 **/
1592 void
gck_attribute_init_invalid(GckAttribute * attr,gulong attr_type)1593 gck_attribute_init_invalid (GckAttribute *attr,
1594 gulong attr_type)
1595 {
1596 g_return_if_fail (attr != NULL);
1597 attr->type = attr_type;
1598 attr->value = NULL;
1599 attr->length = G_MAXULONG;
1600 }
1601
1602 /**
1603 * gck_attribute_init_empty: (skip)
1604 * @attr: an uninitialized attribute
1605 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1606 *
1607 * Initialize a PKCS\#11 attribute to an empty state. The attribute
1608 * type will be set, but no data will be set.
1609 *
1610 * When done with the attribute you should use gck_attribute_clear()
1611 * to free the internal memory.
1612 **/
1613 void
gck_attribute_init_empty(GckAttribute * attr,gulong attr_type)1614 gck_attribute_init_empty (GckAttribute *attr, gulong attr_type)
1615 {
1616 g_return_if_fail (attr != NULL);
1617
1618 attr->type = attr_type;
1619 attr->length = 0;
1620 attr->value = 0;
1621 }
1622
1623 /**
1624 * gck_attribute_init_boolean: (skip)
1625 * @attr: an uninitialized attribute
1626 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1627 * @value: the boolean value of the attribute
1628 *
1629 * Initialize a PKCS\#11 attribute to boolean. This will result
1630 * in a CK_BBOOL attribute from the PKCS\#11 specs.
1631 *
1632 * When done with the attribute you should use gck_attribute_clear()
1633 * to free the internal memory.
1634 **/
1635 void
gck_attribute_init_boolean(GckAttribute * attr,gulong attr_type,gboolean value)1636 gck_attribute_init_boolean (GckAttribute *attr,
1637 gulong attr_type,
1638 gboolean value)
1639 {
1640 CK_BBOOL val = value ? CK_TRUE : CK_FALSE;
1641 g_return_if_fail (attr != NULL);
1642 gck_attribute_init (attr, attr_type, &val, sizeof (val));
1643 }
1644
1645 /**
1646 * gck_attribute_init_date: (skip)
1647 * @attr: an uninitialized attribute
1648 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1649 * @value: the date value of the attribute
1650 *
1651 * Initialize a PKCS\#11 attribute to a date. This will result
1652 * in a CK_DATE attribute from the PKCS\#11 specs.
1653 *
1654 * When done with the attribute you should use gck_attribute_clear()
1655 * to free the internal memory.
1656 **/
1657 void
gck_attribute_init_date(GckAttribute * attr,gulong attr_type,const GDate * value)1658 gck_attribute_init_date (GckAttribute *attr,
1659 gulong attr_type,
1660 const GDate *value)
1661 {
1662 CK_DATE date;
1663
1664 g_return_if_fail (attr != NULL);
1665 g_return_if_fail (value != NULL);
1666
1667 convert_gdate_to_ckdate (value, &date);
1668 gck_attribute_init (attr, attr_type, (const guchar *)&date, sizeof (CK_DATE));
1669 }
1670
1671 /**
1672 * gck_attribute_init_ulong: (skip)
1673 * @attr: an uninitialized attribute
1674 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1675 * @value: the ulong value of the attribute
1676 *
1677 * Initialize a PKCS\#11 attribute to a unsigned long. This will result
1678 * in a CK_ULONG attribute from the PKCS\#11 specs.
1679 *
1680 * When done with the attribute you should use gck_attribute_clear()
1681 * to free the internal memory.
1682 **/
1683 void
gck_attribute_init_ulong(GckAttribute * attr,gulong attr_type,gulong value)1684 gck_attribute_init_ulong (GckAttribute *attr,
1685 gulong attr_type,
1686 gulong value)
1687 {
1688 CK_ULONG val = value;
1689 g_return_if_fail (attr != NULL);
1690 gck_attribute_init (attr, attr_type, (const guchar *)&val, sizeof (val));
1691 }
1692
1693 /**
1694 * gck_attribute_init_string: (skip)
1695 * @attr: an uninitialized attribute
1696 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1697 * @value: the null terminated string value of the attribute
1698 *
1699 * Initialize a PKCS\#11 attribute to a string. This will result
1700 * in an attribute containing the text, but not the null terminator.
1701 * The text in the attribute will be of the same encoding as you pass
1702 * to this function.
1703 *
1704 * When done with the attribute you should use gck_attribute_clear()
1705 * to free the internal memory.
1706 **/
1707 void
gck_attribute_init_string(GckAttribute * attr,gulong attr_type,const gchar * value)1708 gck_attribute_init_string (GckAttribute *attr,
1709 gulong attr_type,
1710 const gchar *value)
1711 {
1712 g_return_if_fail (attr != NULL);
1713 gck_attribute_init (attr, attr_type, (const guchar *)value,
1714 value ? strlen (value) : 0);
1715 }
1716
G_DEFINE_BOXED_TYPE(GckAttribute,gck_attribute,gck_attribute_dup,gck_attribute_free)1717 G_DEFINE_BOXED_TYPE (GckAttribute, gck_attribute,
1718 gck_attribute_dup, gck_attribute_free)
1719
1720 /**
1721 * gck_attribute_new:
1722 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1723 * @value: the raw value of the attribute
1724 * @length: the length of the attribute
1725 *
1726 * Create a new PKCS\#11 attribute. The value will be copied
1727 * into the new attribute.
1728 *
1729 * Returns: (transfer full): the new attribute; when done with the attribute
1730 * use gck_attribute_free() to free it
1731 **/
1732 GckAttribute *
1733 gck_attribute_new (gulong attr_type,
1734 const guchar *value,
1735 gsize length)
1736 {
1737 GckAttribute *attr = g_slice_new0 (GckAttribute);
1738 gck_attribute_init (attr, attr_type, value, length);
1739 return attr;
1740 }
1741
1742 /**
1743 * gck_attribute_new_invalid:
1744 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1745 *
1746 * Create a new PKCS\#11 attribute as 'invalid' or 'not found'
1747 * state. Specifically this sets the value length to (CK_ULONG)-1
1748 * as specified in the PKCS\#11 specification.
1749 *
1750 * Returns: (transfer full): the new attribute; when done with the attribute
1751 * use gck_attribute_free() to free it
1752 **/
1753 GckAttribute *
gck_attribute_new_invalid(gulong attr_type)1754 gck_attribute_new_invalid (gulong attr_type)
1755 {
1756 GckAttribute *attr = g_slice_new0 (GckAttribute);
1757 gck_attribute_init_invalid (attr, attr_type);
1758 return attr;
1759 }
1760
1761 /**
1762 * gck_attribute_new_empty:
1763 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1764 *
1765 * Create a new PKCS\#11 attribute with empty data.
1766 *
1767 * Returns: (transfer full): the new attribute; when done with the attribute
1768 * use gck_attribute_free() to free it
1769 */
1770 GckAttribute *
gck_attribute_new_empty(gulong attr_type)1771 gck_attribute_new_empty (gulong attr_type)
1772 {
1773 GckAttribute *attr = g_slice_new0 (GckAttribute);
1774 gck_attribute_init_empty (attr, attr_type);
1775 return attr;
1776 }
1777
1778 /**
1779 * gck_attribute_new_boolean:
1780 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1781 * @value: the boolean value of the attribute
1782 *
1783 * Initialize a PKCS\#11 attribute to boolean. This will result
1784 * in a CK_BBOOL attribute from the PKCS\#11 specs.
1785 *
1786 * Returns: (transfer full): the new attribute; when done with the attribute u
1787 * gck_attribute_free() to free it
1788 **/
1789 GckAttribute *
gck_attribute_new_boolean(gulong attr_type,gboolean value)1790 gck_attribute_new_boolean (gulong attr_type,
1791 gboolean value)
1792 {
1793 GckAttribute *attr = g_slice_new0 (GckAttribute);
1794 gck_attribute_init_boolean (attr, attr_type, value);
1795 return attr;
1796 }
1797
1798 /**
1799 * gck_attribute_new_date:
1800 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1801 * @value: the date value of the attribute
1802 *
1803 * Initialize a PKCS\#11 attribute to a date. This will result
1804 * in a CK_DATE attribute from the PKCS\#11 specs.
1805 *
1806 * Returns: (transfer full): the new attribute; when done with the attribute u
1807 * gck_attribute_free() to free it
1808 **/
1809 GckAttribute *
gck_attribute_new_date(gulong attr_type,const GDate * value)1810 gck_attribute_new_date (gulong attr_type,
1811 const GDate *value)
1812 {
1813 GckAttribute *attr = g_slice_new0 (GckAttribute);
1814 gck_attribute_init_date (attr, attr_type, value);
1815 return attr;
1816 }
1817
1818 /**
1819 * gck_attribute_new_ulong:
1820 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1821 * @value: the ulong value of the attribute
1822 *
1823 * Initialize a PKCS\#11 attribute to a unsigned long. This will result
1824 * in a CK_ULONG attribute from the PKCS\#11 specs.
1825 *
1826 * Returns: (transfer full): the new attribute; when done with the attribute u
1827 * gck_attribute_free() to free it
1828 **/
1829 GckAttribute *
gck_attribute_new_ulong(gulong attr_type,gulong value)1830 gck_attribute_new_ulong (gulong attr_type,
1831 gulong value)
1832 {
1833 GckAttribute *attr = g_slice_new0 (GckAttribute);
1834 gck_attribute_init_ulong (attr, attr_type, value);
1835 return attr;
1836 }
1837
1838 /**
1839 * gck_attribute_new_string:
1840 * @attr_type: the PKCS\#11 attribute type to set on the attribute
1841 * @value: the null-terminated string value of the attribute
1842 *
1843 * Initialize a PKCS\#11 attribute to a string. This will result
1844 * in an attribute containing the text, but not the null terminator.
1845 * The text in the attribute will be of the same encoding as you pass
1846 * to this function.
1847 *
1848 * Returns: (transfer full): the new attribute; when done with the attribute u
1849 * gck_attribute_free() to free it
1850 **/
1851 GckAttribute *
gck_attribute_new_string(gulong attr_type,const gchar * value)1852 gck_attribute_new_string (gulong attr_type,
1853 const gchar *value)
1854 {
1855 GckAttribute *attr = g_slice_new0 (GckAttribute);
1856 gck_attribute_init_string (attr, attr_type, value);
1857 return attr;
1858 }
1859
1860 /**
1861 * gck_attribute_dup:
1862 * @attr: the attribute to duplicate
1863 *
1864 * Duplicate the PKCS\#11 attribute. All value memory is
1865 * also copied.
1866 *
1867 * The @attr must have been allocated or initialized by a Gck function or
1868 * the results of this function are undefined.
1869 *
1870 * Returns: (transfer full): the duplicated attribute; use gck_attribute_free()
1871 * to free it
1872 */
1873 GckAttribute *
gck_attribute_dup(const GckAttribute * attr)1874 gck_attribute_dup (const GckAttribute *attr)
1875 {
1876 GckAttribute *copy;
1877
1878 if (!attr)
1879 return NULL;
1880
1881 copy = g_slice_new0 (GckAttribute);
1882 gck_attribute_init_copy (copy, attr);
1883 return copy;
1884 }
1885
1886 /**
1887 * gck_attribute_init_copy:
1888 * @dest: An uninitialized attribute.
1889 * @src: An attribute to copy.
1890 *
1891 * Initialize a PKCS\#11 attribute as a copy of another attribute.
1892 * This copies the value memory as well.
1893 *
1894 * When done with the copied attribute you should use
1895 * gck_attribute_clear() to free the internal memory.
1896 **/
1897 void
gck_attribute_init_copy(GckAttribute * dest,const GckAttribute * src)1898 gck_attribute_init_copy (GckAttribute *dest,
1899 const GckAttribute *src)
1900 {
1901 g_return_if_fail (dest != NULL);
1902 g_return_if_fail (src != NULL);
1903
1904 dest->type = src->type;
1905 if (src->length == G_MAXULONG) {
1906 dest->value = NULL;
1907 dest->length = G_MAXULONG;
1908 } else if (src->value == NULL) {
1909 dest->value = NULL;
1910 dest->length = 0;
1911 } else {
1912 dest->value = value_ref (src->value);
1913 dest->length = src->length;
1914 }
1915 }
1916
1917 /**
1918 * gck_attribute_clear:
1919 * @attr: Attribute to clear.
1920 *
1921 * Clear allocated memory held by a #GckAttribute.
1922 *
1923 * This attribute must have been allocated by a Gck library function, or
1924 * the results of this method are undefined.
1925 *
1926 * The type of the attribute will remain set.
1927 **/
1928 void
gck_attribute_clear(GckAttribute * attr)1929 gck_attribute_clear (GckAttribute *attr)
1930 {
1931 g_return_if_fail (attr != NULL);
1932
1933 if (attr->value != NULL)
1934 value_unref (attr->value);
1935 attr->value = NULL;
1936 attr->length = 0;
1937 }
1938
1939 /**
1940 * gck_attribute_free:
1941 * @attr: (type Gck.Attribute): attribute to free
1942 *
1943 * Free an attribute and its allocated memory. These is usually
1944 * used with attributes that are allocated by gck_attribute_new()
1945 * or a similar function.
1946 **/
1947 void
gck_attribute_free(gpointer attr)1948 gck_attribute_free (gpointer attr)
1949 {
1950 GckAttribute *a = attr;
1951 if (attr) {
1952 gck_attribute_clear (a);
1953 g_slice_free (GckAttribute, a);
1954 }
1955 }
1956
1957 /**
1958 * gck_attribute_equal:
1959 * @attr1: (type Gck.Attribute): first attribute to compare
1960 * @attr2: (type Gck.Attribute): second attribute to compare
1961 *
1962 * Compare two attributes. Useful with <code>GHashTable</code>.
1963 *
1964 * Returns: %TRUE if the attributes are equal.
1965 */
1966 gboolean
gck_attribute_equal(gconstpointer attr1,gconstpointer attr2)1967 gck_attribute_equal (gconstpointer attr1,
1968 gconstpointer attr2)
1969 {
1970 const GckAttribute *aa = attr1;
1971 const GckAttribute *ab = attr2;
1972
1973 if (!aa && !ab)
1974 return TRUE;
1975 if (!aa || !ab)
1976 return FALSE;
1977
1978 if (aa->type != ab->type)
1979 return FALSE;
1980 if (aa->length != ab->length)
1981 return FALSE;
1982 if (!aa->value && !ab->value)
1983 return TRUE;
1984 if (!aa->value || !ab->value)
1985 return FALSE;
1986 return memcmp (aa->value, ab->value, aa->length) == 0;
1987 }
1988
1989 /**
1990 * gck_attribute_hash:
1991 * @attr: (type Gck.Attribute): attribute to hash
1992 *
1993 * Hash an attribute for use in <code>GHashTable</code> keys.
1994 *
1995 * Returns: the hash code
1996 */
1997 guint
gck_attribute_hash(gconstpointer attr)1998 gck_attribute_hash (gconstpointer attr)
1999 {
2000 const GckAttribute *a = attr;
2001 const signed char *p, *e;
2002 guint32 h = 5381;
2003
2004 h ^= _gck_ulong_hash (&a->type);
2005
2006 if (a->value) {
2007 for (p = (signed char *)a->value, e = p + a->length; p != e; p++)
2008 h = (h << 5) + h + *p;
2009 }
2010
2011 return h;
2012 }
2013
2014 /**
2015 * SECTION:gck-attributes
2016 * @title: GckAttributes
2017 * @short_description: A set of PKCS11 attributes.
2018 *
2019 * A set of GckAttribute structures. These attributes contain information
2020 * about a PKCS11 object. Use gck_object_get() or gck_object_set() to set and retrieve
2021 * attributes on an object.
2022 */
2023
2024 /**
2025 * GckAttributes:
2026 *
2027 * A set of GckAttribute structures.
2028 */
2029
2030 /**
2031 * GckAllocator:
2032 * @data: Memory to allocate or deallocate.
2033 * @length: New length of memory.
2034 *
2035 * An allocator used to allocate data for the attributes in this GckAttributes set.
2036 *
2037 * This is a function that acts like g_realloc. Specifically it frees when length is
2038 * set to zero, it allocates when data is set to %NULL, and it reallocates when both
2039 * are valid.
2040 *
2041 * Returns: The allocated memory, or %NULL when freeing.
2042 **/
2043
G_DEFINE_BOXED_TYPE(GckAttributes,gck_attributes,gck_attributes_ref,gck_attributes_unref)2044 G_DEFINE_BOXED_TYPE (GckAttributes, gck_attributes,
2045 gck_attributes_ref, gck_attributes_unref)
2046
2047 GType
2048 gck_attributes_get_boxed_type (void)
2049 {
2050 /* Deprecated version */
2051 return gck_attributes_get_type ();
2052 }
2053
2054 /**
2055 * gck_attributes_new_empty:
2056 * @first_type: the first empty attribute type
2057 * @...: the other empty attribute types
2058 *
2059 * Creates an GckAttributes array with empty attributes
2060 *
2061 * Terminate the argument list with %GCK_INVALID.
2062 *
2063 * The returned set of attributes is floating, and should either be passed to
2064 * another gck library function which consumes this floating reference, or if
2065 * you wish to keep these attributes around you should ref them with
2066 * gck_attributes_ref_sink() and unref them later with gck_attributes_unref().
2067 *
2068 * Returns: (transfer none): a floating reference to an empty set of attributes
2069 **/
2070 GckAttributes *
gck_attributes_new_empty(gulong first_type,...)2071 gck_attributes_new_empty (gulong first_type,
2072 ...)
2073 {
2074 GckBuilder builder = GCK_BUILDER_INIT;
2075 va_list va;
2076
2077 va_start (va, first_type);
2078
2079 while (first_type != GCK_INVALID) {
2080 gck_builder_add_empty (&builder, first_type);
2081 first_type = va_arg (va, gulong);
2082 }
2083
2084 va_end (va);
2085 return gck_builder_end (&builder);
2086 }
2087
2088 /**
2089 * gck_attributes_at:
2090 * @attrs: The attributes array.
2091 * @index: The attribute index to retrieve.
2092 *
2093 * Get attribute at the specified index in the attribute array.
2094 *
2095 * Use gck_attributes_count() to determine how many attributes are
2096 * in the array.
2097 *
2098 * Returns: (transfer none): the specified attribute
2099 **/
2100 const GckAttribute *
gck_attributes_at(GckAttributes * attrs,guint index)2101 gck_attributes_at (GckAttributes *attrs,
2102 guint index)
2103 {
2104 g_return_val_if_fail (attrs != NULL, NULL);
2105 g_return_val_if_fail (index < attrs->count, NULL);
2106 return attrs->data + index;
2107 }
2108
2109 /**
2110 * gck_attributes_count:
2111 * @attrs: The attributes array to count.
2112 *
2113 * Get the number of attributes in this attribute array.
2114 *
2115 * Return value: The number of contained attributes.
2116 **/
2117 gulong
gck_attributes_count(GckAttributes * attrs)2118 gck_attributes_count (GckAttributes *attrs)
2119 {
2120 g_return_val_if_fail (attrs != NULL, 0);
2121 return attrs->count;
2122 }
2123
2124 /**
2125 * gck_attributes_find:
2126 * @attrs: The attributes array to search.
2127 * @attr_type: The type of attribute to find.
2128 *
2129 * Find an attribute with the specified type in the array.
2130 *
2131 * Returns: (transfer none): the first attribute found with the specified type,
2132 * or %NULL
2133 **/
2134 const GckAttribute *
gck_attributes_find(GckAttributes * attrs,gulong attr_type)2135 gck_attributes_find (GckAttributes *attrs,
2136 gulong attr_type)
2137 {
2138 g_return_val_if_fail (attrs != NULL, NULL);
2139
2140 return find_attribute (attrs->data, attrs->count, attr_type);
2141 }
2142
2143 /**
2144 * gck_attributes_find_boolean:
2145 * @attrs: The attributes array to search.
2146 * @attr_type: The type of attribute to find.
2147 * @value: (out): The resulting gboolean value.
2148 *
2149 * Find an attribute with the specified type in the array.
2150 *
2151 * The attribute (if found) must be of the right size to store
2152 * a boolean value (ie: CK_BBOOL). If the attribute is marked invalid
2153 * then it will be treated as not found.
2154 *
2155 * Return value: Whether a value was found or not.
2156 **/
2157 gboolean
gck_attributes_find_boolean(GckAttributes * attrs,gulong attr_type,gboolean * value)2158 gck_attributes_find_boolean (GckAttributes *attrs, gulong attr_type, gboolean *value)
2159 {
2160 g_return_val_if_fail (attrs != NULL, FALSE);
2161 g_return_val_if_fail (value, FALSE);
2162
2163 return find_attribute_boolean (attrs->data, attrs->count, attr_type, value);
2164 }
2165
2166 /**
2167 * gck_attributes_find_ulong:
2168 * @attrs: The attributes array to search.
2169 * @attr_type: The type of attribute to find.
2170 * @value: (out): The resulting gulong value.
2171 *
2172 * Find an attribute with the specified type in the array.
2173 *
2174 * The attribute (if found) must be of the right size to store
2175 * a unsigned long value (ie: CK_ULONG). If the attribute is marked invalid
2176 * then it will be treated as not found.
2177 *
2178 * Return value: Whether a value was found or not.
2179 **/
2180 gboolean
gck_attributes_find_ulong(GckAttributes * attrs,gulong attr_type,gulong * value)2181 gck_attributes_find_ulong (GckAttributes *attrs, gulong attr_type, gulong *value)
2182 {
2183 g_return_val_if_fail (attrs != NULL, FALSE);
2184 g_return_val_if_fail (value, FALSE);
2185
2186 return find_attribute_ulong (attrs->data, attrs->count, attr_type, value);
2187 }
2188
2189 /**
2190 * gck_attributes_find_string:
2191 * @attrs: The attributes array to search.
2192 * @attr_type: The type of attribute to find.
2193 * @value: (out): The resulting string value.
2194 *
2195 * Find an attribute with the specified type in the array.
2196 *
2197 * If the attribute is marked invalid then it will be treated as not found.
2198 * The resulting string will be null-terminated, and must be freed by the caller
2199 * using g_free().
2200 *
2201 * Return value: Whether a value was found or not.
2202 **/
2203 gboolean
gck_attributes_find_string(GckAttributes * attrs,gulong attr_type,gchar ** value)2204 gck_attributes_find_string (GckAttributes *attrs, gulong attr_type, gchar **value)
2205 {
2206 g_return_val_if_fail (attrs != NULL, FALSE);
2207 g_return_val_if_fail (value, FALSE);
2208
2209 return find_attribute_string (attrs->data, attrs->count, attr_type, value);
2210 }
2211
2212 /**
2213 * gck_attributes_find_date:
2214 * @attrs: The attributes array to search.
2215 * @attr_type: The type of attribute to find.
2216 * @value: (out): The resulting GDate value.
2217 *
2218 * Find an attribute with the specified type in the array.
2219 *
2220 * The attribute (if found) must be of the right size to store
2221 * a date value (ie: CK_DATE). If the attribute is marked invalid
2222 * then it will be treated as not found.
2223 *
2224 * Return value: Whether a value was found or not.
2225 **/
2226 gboolean
gck_attributes_find_date(GckAttributes * attrs,gulong attr_type,GDate * value)2227 gck_attributes_find_date (GckAttributes *attrs, gulong attr_type, GDate *value)
2228 {
2229 g_return_val_if_fail (attrs != NULL, FALSE);
2230 g_return_val_if_fail (value, FALSE);
2231
2232 return find_attribute_date (attrs->data, attrs->count, attr_type, value);
2233 }
2234
2235 /**
2236 * gck_attributes_ref:
2237 * @attrs: An attribute array
2238 *
2239 * Reference this attributes array.
2240 *
2241 * Returns: the attributes
2242 **/
2243 GckAttributes *
gck_attributes_ref(GckAttributes * attrs)2244 gck_attributes_ref (GckAttributes *attrs)
2245 {
2246 g_return_val_if_fail (attrs, NULL);
2247 g_atomic_int_inc (&attrs->refs);
2248 return attrs;
2249 }
2250
2251 /**
2252 * gck_attributes_ref_sink:
2253 * @attrs: an attribute array
2254 *
2255 * #GckAttributes uses a floating reference count system. gck_builder_end()
2256 * and gck_attributes_new_empty() both return floating references.
2257 *
2258 * Calling gck_attributes_ref_sink() on a #GckAttributes with a floating
2259 * reference will convert the floating reference into a full reference.
2260 * Calling gck_attributes_ref_sink() on a non-floating #GckAttributes results
2261 * in an additional normal reference being added.
2262 *
2263 * In other words, if the @attrs is floating, then this call "assumes
2264 * ownership" of the floating reference, converting it to a normal
2265 * reference. If the @attrs is not floating, then this call adds a
2266 * new normal reference increasing the reference count by one.
2267 *
2268 * All Gck library functions that assume ownership of floating references
2269 * are documented as such. Essentially any Gck function that performs
2270 * an operation using a #GckAttributes argument rather than operating on the
2271 * atributes themselves, will accept a floating reference.
2272 *
2273 * Returns: the referenced attributes
2274 */
2275 GckAttributes *
gck_attributes_ref_sink(GckAttributes * attrs)2276 gck_attributes_ref_sink (GckAttributes *attrs)
2277 {
2278 g_return_val_if_fail (attrs, NULL);
2279 g_bit_lock (&attrs->state, STATE_LOCKED);
2280
2281 if (~attrs->state & STATE_FLOATING)
2282 gck_attributes_ref (attrs);
2283 else
2284 attrs->state &= ~STATE_FLOATING;
2285
2286 g_bit_unlock (&attrs->state, STATE_LOCKED);
2287 return attrs;
2288 }
2289
2290 /**
2291 * gck_attributes_unref:
2292 * @attrs: (nullable) (type Gck.Attributes): An attribute array
2293 *
2294 * Unreference this attribute array.
2295 *
2296 * When all outstanding references are gone, the array will be freed.
2297 */
2298 void
gck_attributes_unref(gpointer attrs)2299 gck_attributes_unref (gpointer attrs)
2300 {
2301 GckAttributes *attrs_ = attrs;
2302 const GckAttribute *attr;
2303 guint i;
2304
2305 if (!attrs_)
2306 return;
2307
2308 if (g_atomic_int_dec_and_test (&attrs_->refs)) {
2309 for (i = 0; i < attrs_->count; ++i) {
2310 attr = gck_attributes_at (attrs_, i);
2311 if (attr->value)
2312 value_unref (attr->value);
2313 }
2314 g_free (attrs_->data);
2315 g_slice_free (GckAttributes, attrs_);
2316 }
2317 }
2318
2319 /**
2320 * gck_attributes_contains:
2321 * @attrs: The attributes to check
2322 * @match: The attribute to find
2323 *
2324 * Check whether the attributes contain a certain attribute.
2325 *
2326 * Returns: %TRUE if the attributes contain the attribute.
2327 */
2328 gboolean
gck_attributes_contains(GckAttributes * attrs,const GckAttribute * match)2329 gck_attributes_contains (GckAttributes *attrs,
2330 const GckAttribute *match)
2331 {
2332 const GckAttribute *attr;
2333 guint i;
2334
2335 g_return_val_if_fail (attrs != NULL, FALSE);
2336
2337 for (i = 0; i < attrs->count; ++i) {
2338 attr = gck_attributes_at (attrs, i);
2339 if (gck_attribute_equal (attr, match))
2340 return TRUE;
2341 }
2342
2343 return FALSE;
2344 }
2345
2346 CK_ATTRIBUTE_PTR
_gck_builder_prepare_in(GckBuilder * builder,CK_ULONG_PTR n_attrs)2347 _gck_builder_prepare_in (GckBuilder *builder,
2348 CK_ULONG_PTR n_attrs)
2349 {
2350 GckRealBuilder *real = (GckRealBuilder *)builder;
2351 GckAttribute *attr;
2352 guint i;
2353
2354 g_return_val_if_fail (builder != NULL, NULL);
2355 g_return_val_if_fail (n_attrs != NULL, NULL);
2356
2357 if (real->array == NULL) {
2358 *n_attrs = 0;
2359 return NULL;
2360 }
2361
2362 /* Prepare the attributes to receive their length */
2363
2364 for (i = 0; i < real->array->len; ++i) {
2365 attr = &g_array_index (real->array, GckAttribute, i);
2366 if (attr->value != NULL) {
2367 value_unref (attr->value);
2368 attr->value = NULL;
2369 }
2370 attr->length = 0;
2371 }
2372
2373 *n_attrs = real->array->len;
2374 return (CK_ATTRIBUTE_PTR)real->array->data;
2375 }
2376
2377 CK_ATTRIBUTE_PTR
_gck_builder_commit_in(GckBuilder * builder,CK_ULONG_PTR n_attrs)2378 _gck_builder_commit_in (GckBuilder *builder,
2379 CK_ULONG_PTR n_attrs)
2380 {
2381 GckRealBuilder *real = (GckRealBuilder *)builder;
2382 GckAttribute *attr;
2383 guint i;
2384
2385 g_return_val_if_fail (builder != NULL, NULL);
2386 g_return_val_if_fail (n_attrs != NULL, NULL);
2387
2388 if (real->array == NULL) {
2389 *n_attrs = 0;
2390 return NULL;
2391 }
2392
2393 /* Allocate each attribute with the length that was set */
2394
2395 for (i = 0; i < real->array->len; ++i) {
2396 attr = &g_array_index (real->array, GckAttribute, i);
2397 if (attr->length != 0 && attr->length != (gulong)-1)
2398 attr->value = value_blank (attr->length, real->secure);
2399 else
2400 attr->value = NULL;
2401 }
2402
2403 *n_attrs = real->array->len;
2404 return (CK_ATTRIBUTE_PTR)real->array->data;
2405 }
2406
2407 CK_ATTRIBUTE_PTR
_gck_attributes_commit_out(GckAttributes * attrs,CK_ULONG_PTR n_attrs)2408 _gck_attributes_commit_out (GckAttributes *attrs,
2409 CK_ULONG_PTR n_attrs)
2410 {
2411 g_return_val_if_fail (attrs != NULL, NULL);
2412 g_return_val_if_fail (n_attrs != NULL, NULL);
2413
2414 *n_attrs = attrs->count;
2415 return (CK_ATTRIBUTE_PTR)attrs->data;
2416 }
2417
2418 static gboolean
_gck_attribute_is_ulong_of_type(GckAttribute * attr,gulong attr_type)2419 _gck_attribute_is_ulong_of_type (GckAttribute *attr,
2420 gulong attr_type)
2421 {
2422 if (attr->type != attr_type)
2423 return FALSE;
2424 if (attr->length != sizeof (gulong))
2425 return FALSE;
2426 if (!attr->value)
2427 return FALSE;
2428 return TRUE;
2429 }
2430
2431 static gboolean
_gck_attribute_is_sensitive(GckAttribute * attr)2432 _gck_attribute_is_sensitive (GckAttribute *attr)
2433 {
2434 /*
2435 * Don't print any just attribute, since they may contain
2436 * sensitive data
2437 */
2438
2439 switch (attr->type) {
2440 #define X(x) case x: return FALSE;
2441 X (CKA_CLASS)
2442 X (CKA_TOKEN)
2443 X (CKA_PRIVATE)
2444 X (CKA_LABEL)
2445 X (CKA_APPLICATION)
2446 X (CKA_OBJECT_ID)
2447 X (CKA_CERTIFICATE_TYPE)
2448 X (CKA_ISSUER)
2449 X (CKA_SERIAL_NUMBER)
2450 X (CKA_AC_ISSUER)
2451 X (CKA_OWNER)
2452 X (CKA_ATTR_TYPES)
2453 X (CKA_TRUSTED)
2454 X (CKA_CERTIFICATE_CATEGORY)
2455 X (CKA_JAVA_MIDP_SECURITY_DOMAIN)
2456 X (CKA_URL)
2457 X (CKA_HASH_OF_SUBJECT_PUBLIC_KEY)
2458 X (CKA_HASH_OF_ISSUER_PUBLIC_KEY)
2459 X (CKA_CHECK_VALUE)
2460 X (CKA_KEY_TYPE)
2461 X (CKA_SUBJECT)
2462 X (CKA_ID)
2463 X (CKA_SENSITIVE)
2464 X (CKA_ENCRYPT)
2465 X (CKA_DECRYPT)
2466 X (CKA_WRAP)
2467 X (CKA_UNWRAP)
2468 X (CKA_SIGN)
2469 X (CKA_SIGN_RECOVER)
2470 X (CKA_VERIFY)
2471 X (CKA_VERIFY_RECOVER)
2472 X (CKA_DERIVE)
2473 X (CKA_START_DATE)
2474 X (CKA_END_DATE)
2475 X (CKA_MODULUS_BITS)
2476 X (CKA_PRIME_BITS)
2477 /* X (CKA_SUBPRIME_BITS) */
2478 /* X (CKA_SUB_PRIME_BITS) */
2479 X (CKA_VALUE_BITS)
2480 X (CKA_VALUE_LEN)
2481 X (CKA_EXTRACTABLE)
2482 X (CKA_LOCAL)
2483 X (CKA_NEVER_EXTRACTABLE)
2484 X (CKA_ALWAYS_SENSITIVE)
2485 X (CKA_KEY_GEN_MECHANISM)
2486 X (CKA_MODIFIABLE)
2487 X (CKA_SECONDARY_AUTH)
2488 X (CKA_AUTH_PIN_FLAGS)
2489 X (CKA_ALWAYS_AUTHENTICATE)
2490 X (CKA_WRAP_WITH_TRUSTED)
2491 X (CKA_WRAP_TEMPLATE)
2492 X (CKA_UNWRAP_TEMPLATE)
2493 X (CKA_HW_FEATURE_TYPE)
2494 X (CKA_RESET_ON_INIT)
2495 X (CKA_HAS_RESET)
2496 X (CKA_PIXEL_X)
2497 X (CKA_PIXEL_Y)
2498 X (CKA_RESOLUTION)
2499 X (CKA_CHAR_ROWS)
2500 X (CKA_CHAR_COLUMNS)
2501 X (CKA_COLOR)
2502 X (CKA_BITS_PER_PIXEL)
2503 X (CKA_CHAR_SETS)
2504 X (CKA_ENCODING_METHODS)
2505 X (CKA_MIME_TYPES)
2506 X (CKA_MECHANISM_TYPE)
2507 X (CKA_REQUIRED_CMS_ATTRIBUTES)
2508 X (CKA_DEFAULT_CMS_ATTRIBUTES)
2509 X (CKA_SUPPORTED_CMS_ATTRIBUTES)
2510 X (CKA_ALLOWED_MECHANISMS)
2511 X (CKA_X_ASSERTION_TYPE)
2512 X (CKA_X_CERTIFICATE_VALUE)
2513 X (CKA_X_PURPOSE)
2514 X (CKA_X_PEER)
2515 #undef X
2516 }
2517
2518 return TRUE;
2519 }
2520
2521 static void
_gck_format_class(GString * output,CK_OBJECT_CLASS klass)2522 _gck_format_class (GString *output,
2523 CK_OBJECT_CLASS klass)
2524 {
2525 const gchar *string = NULL;
2526
2527 switch (klass) {
2528 #define X(x) case x: string = #x; break;
2529 X (CKO_DATA)
2530 X (CKO_CERTIFICATE)
2531 X (CKO_PUBLIC_KEY)
2532 X (CKO_PRIVATE_KEY)
2533 X (CKO_SECRET_KEY)
2534 X (CKO_HW_FEATURE)
2535 X (CKO_DOMAIN_PARAMETERS)
2536 X (CKO_MECHANISM)
2537 X (CKO_X_TRUST_ASSERTION)
2538 }
2539
2540 if (string != NULL)
2541 g_string_append (output, string);
2542 else
2543 g_string_append_printf (output, "0x%08lX", klass);
2544 }
2545
2546 static void
_gck_format_assertion_type(GString * output,CK_X_ASSERTION_TYPE type)2547 _gck_format_assertion_type (GString *output,
2548 CK_X_ASSERTION_TYPE type)
2549 {
2550 const gchar *string = NULL;
2551
2552 switch (type) {
2553 #define X(x) case x: string = #x; break;
2554 X (CKT_X_UNTRUSTED_CERTIFICATE)
2555 X (CKT_X_PINNED_CERTIFICATE)
2556 X (CKT_X_ANCHORED_CERTIFICATE)
2557 #undef X
2558 }
2559
2560 if (string != NULL)
2561 g_string_append (output, string);
2562 else
2563 g_string_append_printf (output, "0x%08lX", type);
2564 }
2565
2566 static void
_gck_format_key_type(GString * output,CK_KEY_TYPE type)2567 _gck_format_key_type (GString *output,
2568 CK_KEY_TYPE type)
2569 {
2570 const gchar *string = NULL;
2571
2572 switch (type) {
2573 #define X(x) case x: string = #x; break;
2574 X (CKK_RSA)
2575 X (CKK_DSA)
2576 X (CKK_DH)
2577 /* X (CKK_ECDSA) */
2578 X (CKK_EC)
2579 X (CKK_X9_42_DH)
2580 X (CKK_KEA)
2581 X (CKK_GENERIC_SECRET)
2582 X (CKK_RC2)
2583 X (CKK_RC4)
2584 X (CKK_DES)
2585 X (CKK_DES2)
2586 X (CKK_DES3)
2587 X (CKK_CAST)
2588 X (CKK_CAST3)
2589 X (CKK_CAST128)
2590 X (CKK_RC5)
2591 X (CKK_IDEA)
2592 X (CKK_SKIPJACK)
2593 X (CKK_BATON)
2594 X (CKK_JUNIPER)
2595 X (CKK_CDMF)
2596 X (CKK_AES)
2597 X (CKK_BLOWFISH)
2598 X (CKK_TWOFISH)
2599 #undef X
2600 }
2601
2602 if (string != NULL)
2603 g_string_append (output, string);
2604 else
2605 g_string_append_printf (output, "0x%08lX", type);
2606 }
2607
2608 static void
_gck_format_certificate_type(GString * output,CK_CERTIFICATE_TYPE type)2609 _gck_format_certificate_type (GString *output,
2610 CK_CERTIFICATE_TYPE type)
2611 {
2612 const gchar *string = NULL;
2613
2614 switch (type) {
2615 #define X(x) case x: string = #x; break;
2616 X (CKC_X_509)
2617 X (CKC_X_509_ATTR_CERT)
2618 X (CKC_WTLS)
2619 }
2620
2621 if (string != NULL)
2622 g_string_append (output, string);
2623 else
2624 g_string_append_printf (output, "0x%08lX", type);
2625 }
2626
2627 static void
_gck_format_attribute_type(GString * output,gulong type)2628 _gck_format_attribute_type (GString *output,
2629 gulong type)
2630 {
2631 const gchar *string = NULL;
2632
2633 switch (type) {
2634 #define X(x) case x: string = #x; break;
2635 X (CKA_CLASS)
2636 X (CKA_TOKEN)
2637 X (CKA_PRIVATE)
2638 X (CKA_LABEL)
2639 X (CKA_APPLICATION)
2640 X (CKA_VALUE)
2641 X (CKA_OBJECT_ID)
2642 X (CKA_CERTIFICATE_TYPE)
2643 X (CKA_ISSUER)
2644 X (CKA_SERIAL_NUMBER)
2645 X (CKA_AC_ISSUER)
2646 X (CKA_OWNER)
2647 X (CKA_ATTR_TYPES)
2648 X (CKA_TRUSTED)
2649 X (CKA_CERTIFICATE_CATEGORY)
2650 X (CKA_JAVA_MIDP_SECURITY_DOMAIN)
2651 X (CKA_URL)
2652 X (CKA_HASH_OF_SUBJECT_PUBLIC_KEY)
2653 X (CKA_HASH_OF_ISSUER_PUBLIC_KEY)
2654 X (CKA_CHECK_VALUE)
2655 X (CKA_KEY_TYPE)
2656 X (CKA_SUBJECT)
2657 X (CKA_ID)
2658 X (CKA_SENSITIVE)
2659 X (CKA_ENCRYPT)
2660 X (CKA_DECRYPT)
2661 X (CKA_WRAP)
2662 X (CKA_UNWRAP)
2663 X (CKA_SIGN)
2664 X (CKA_SIGN_RECOVER)
2665 X (CKA_VERIFY)
2666 X (CKA_VERIFY_RECOVER)
2667 X (CKA_DERIVE)
2668 X (CKA_START_DATE)
2669 X (CKA_END_DATE)
2670 X (CKA_MODULUS)
2671 X (CKA_MODULUS_BITS)
2672 X (CKA_PUBLIC_EXPONENT)
2673 X (CKA_PRIVATE_EXPONENT)
2674 X (CKA_PRIME_1)
2675 X (CKA_PRIME_2)
2676 X (CKA_EXPONENT_1)
2677 X (CKA_EXPONENT_2)
2678 X (CKA_COEFFICIENT)
2679 X (CKA_PRIME)
2680 X (CKA_SUBPRIME)
2681 X (CKA_BASE)
2682 X (CKA_PRIME_BITS)
2683 /* X (CKA_SUBPRIME_BITS) */
2684 /* X (CKA_SUB_PRIME_BITS) */
2685 X (CKA_VALUE_BITS)
2686 X (CKA_VALUE_LEN)
2687 X (CKA_EXTRACTABLE)
2688 X (CKA_LOCAL)
2689 X (CKA_NEVER_EXTRACTABLE)
2690 X (CKA_ALWAYS_SENSITIVE)
2691 X (CKA_KEY_GEN_MECHANISM)
2692 X (CKA_MODIFIABLE)
2693 X (CKA_ECDSA_PARAMS)
2694 /* X (CKA_EC_PARAMS) */
2695 X (CKA_EC_POINT)
2696 X (CKA_SECONDARY_AUTH)
2697 X (CKA_AUTH_PIN_FLAGS)
2698 X (CKA_ALWAYS_AUTHENTICATE)
2699 X (CKA_WRAP_WITH_TRUSTED)
2700 X (CKA_WRAP_TEMPLATE)
2701 X (CKA_UNWRAP_TEMPLATE)
2702 X (CKA_HW_FEATURE_TYPE)
2703 X (CKA_RESET_ON_INIT)
2704 X (CKA_HAS_RESET)
2705 X (CKA_PIXEL_X)
2706 X (CKA_PIXEL_Y)
2707 X (CKA_RESOLUTION)
2708 X (CKA_CHAR_ROWS)
2709 X (CKA_CHAR_COLUMNS)
2710 X (CKA_COLOR)
2711 X (CKA_BITS_PER_PIXEL)
2712 X (CKA_CHAR_SETS)
2713 X (CKA_ENCODING_METHODS)
2714 X (CKA_MIME_TYPES)
2715 X (CKA_MECHANISM_TYPE)
2716 X (CKA_REQUIRED_CMS_ATTRIBUTES)
2717 X (CKA_DEFAULT_CMS_ATTRIBUTES)
2718 X (CKA_SUPPORTED_CMS_ATTRIBUTES)
2719 X (CKA_ALLOWED_MECHANISMS)
2720 X (CKA_X_ASSERTION_TYPE)
2721 X (CKA_X_CERTIFICATE_VALUE)
2722 X (CKA_X_PURPOSE)
2723 X (CKA_X_PEER)
2724 #undef X
2725 }
2726
2727 if (string != NULL)
2728 g_string_append (output, string);
2729 else
2730 g_string_append_printf (output, "CKA_0x%08lX", type);
2731 }
2732
2733 static void
_gck_format_some_bytes(GString * output,gconstpointer bytes,gulong length)2734 _gck_format_some_bytes (GString *output,
2735 gconstpointer bytes,
2736 gulong length)
2737 {
2738 guchar ch;
2739 const guchar *data = bytes;
2740 gulong i;
2741
2742 if (bytes == NULL) {
2743 g_string_append (output, "NULL");
2744 return;
2745 }
2746
2747 g_string_append_c (output, '\"');
2748 for (i = 0; i < length && i < 128; i++) {
2749 ch = data[i];
2750 if (ch == '\t')
2751 g_string_append (output, "\\t");
2752 else if (ch == '\n')
2753 g_string_append (output, "\\n");
2754 else if (ch == '\r')
2755 g_string_append (output, "\\r");
2756 else if (ch >= 32 && ch < 127)
2757 g_string_append_c (output, ch);
2758 else
2759 g_string_append_printf (output, "\\x%02x", ch);
2760 }
2761
2762 if (i < length)
2763 g_string_append_printf (output, "...");
2764 g_string_append_c (output, '\"');
2765 }
2766
2767 static void
_gck_format_attributes(GString * output,GckAttributes * attrs)2768 _gck_format_attributes (GString *output,
2769 GckAttributes *attrs)
2770 {
2771 GckAttribute *attr;
2772 guint count, i;
2773
2774 count = attrs->count;
2775 g_string_append_printf (output, "(%d) [", count);
2776 for (i = 0; i < count; i++) {
2777 attr = attrs->data + i;
2778 if (i > 0)
2779 g_string_append_c (output, ',');
2780 g_string_append (output, " { ");
2781 _gck_format_attribute_type (output, attr->type);
2782 g_string_append (output, " = ");
2783 if (attr->length == GCK_INVALID) {
2784 g_string_append_printf (output, " (-1) INVALID");
2785 } else if (_gck_attribute_is_ulong_of_type (attr, CKA_CLASS)) {
2786 _gck_format_class (output, (CK_OBJECT_CLASS) gck_attribute_get_ulong(attr));
2787 } else if (_gck_attribute_is_ulong_of_type (attr, CKA_X_ASSERTION_TYPE)) {
2788 _gck_format_assertion_type (output, (CK_X_ASSERTION_TYPE) gck_attribute_get_ulong(attr));
2789 } else if (_gck_attribute_is_ulong_of_type (attr, CKA_CERTIFICATE_TYPE)) {
2790 _gck_format_certificate_type (output, (CK_CERTIFICATE_TYPE) gck_attribute_get_ulong(attr));
2791 } else if (_gck_attribute_is_ulong_of_type (attr, CKA_KEY_TYPE)) {
2792 _gck_format_key_type (output, (CK_KEY_TYPE) gck_attribute_get_ulong(attr));
2793 } else if (_gck_attribute_is_sensitive (attr)) {
2794 g_string_append_printf (output, " (%lu) NOT-PRINTED", attr->length);
2795 } else {
2796 g_string_append_printf (output, " (%lu) ", attr->length);
2797 _gck_format_some_bytes (output, attr->value, attr->length);
2798 }
2799 g_string_append (output, " }");
2800 }
2801 g_string_append (output, " ]");
2802 }
2803
2804 /**
2805 * gck_attributes_to_string:
2806 * @attrs: the attributes
2807 *
2808 * Print out attributes to a string in aform that's useful for debugging
2809 * or logging.
2810 *
2811 * The format of the string returned may change in the future.
2812 *
2813 * Returns: a newly allocated string
2814 */
2815 gchar *
gck_attributes_to_string(GckAttributes * attrs)2816 gck_attributes_to_string (GckAttributes *attrs)
2817 {
2818 GString *output = g_string_sized_new (128);
2819 _gck_format_attributes (output, attrs);
2820 return g_string_free (output, FALSE);
2821 }
2822
2823 /**
2824 * gck_attributes_new:
2825 * @reserved: Should be set to always be GCK_INVALID
2826 *
2827 * Create a new empty GckAttributes array.
2828 *
2829 * The returned set of attributes is floating, and should either be passed to
2830 * another gck library function which consumes this floating reference, or if
2831 * you wish to keep these attributes around you should ref them with
2832 * gck_attributes_ref_sink() and unref them later with gck_attributes_unref().
2833 *
2834 * Returns: (transfer none): a floating reference to the new attributes array;
2835 * when done with the array release it with gck_attributes_unref().
2836 **/
2837 GckAttributes *
gck_attributes_new(gulong reserved)2838 gck_attributes_new (gulong reserved)
2839 {
2840 GckBuilder builder = GCK_BUILDER_INIT;
2841 return gck_builder_end (&builder);
2842 }
2843
2844 /**
2845 * gck_attributes_new_full: (skip)
2846 * @allocator: memory allocator for attribute data, or %NULL for default
2847 *
2848 * #GckAttributes are now immutable. This method no longer does anything.
2849 *
2850 * Deprecated: 3.4: Use gck_builder_set_all() instead.
2851 *
2852 * Returns: returns %NULL
2853 **/
2854 GckAttributes *
gck_attributes_new_full(GckAllocator allocator)2855 gck_attributes_new_full (GckAllocator allocator)
2856 {
2857 g_warning ("gck_attributes_new_full() is no no longer supported");
2858 return NULL;
2859 }
2860
2861 /**
2862 * gck_attributes_add:
2863 * @attrs: the attributes array to add to
2864 * @attr: the attribute to add
2865 *
2866 * #GckAttributes are now immutable. This method no longer does anything.
2867 *
2868 * Deprecated: 3.4: Use gck_builder_set_all() instead.
2869 *
2870 * Returns: (transfer none): returns %NULL
2871 **/
2872 GckAttribute *
gck_attributes_add(GckAttributes * attrs,GckAttribute * attr)2873 gck_attributes_add (GckAttributes *attrs,
2874 GckAttribute *attr)
2875 {
2876 g_warning ("gck_attributes_add() is no no longer supported");
2877 return NULL;
2878 }
2879
2880 /**
2881 * gck_attributes_set:
2882 * @attrs: attributes array to add to
2883 * @attr: attribute to set
2884 *
2885 * #GckAttributes are now immutable. This method no longer does anything.
2886 *
2887 * Deprecated: 3.4: Use gck_builder_set_data() instead.
2888 **/
2889 void
gck_attributes_set(GckAttributes * attrs,GckAttribute * attr)2890 gck_attributes_set (GckAttributes *attrs,
2891 GckAttribute *attr)
2892 {
2893 g_warning ("gck_attributes_set() is no no longer supported");
2894 }
2895
2896 /**
2897 * gck_attributes_add_data:
2898 * @attrs: The attributes array to add to.
2899 * @attr_type: The type of attribute to add.
2900 * @value: (array length=length): the raw memory of the attribute value
2901 * @length: The length of the attribute value.
2902 *
2903 * #GckAttributes are now immutable. This method no longer does anything.
2904 *
2905 * Deprecated: 3.4: Use gck_builder_add_data() instead.
2906 *
2907 * Returns: (transfer none): returns %NULL
2908 **/
2909 GckAttribute *
gck_attributes_add_data(GckAttributes * attrs,gulong attr_type,const guchar * value,gsize length)2910 gck_attributes_add_data (GckAttributes *attrs,
2911 gulong attr_type,
2912 const guchar *value,
2913 gsize length)
2914 {
2915 g_warning ("gck_attributes_add_data() is no no longer supported");
2916 return NULL;
2917 }
2918
2919 /**
2920 * gck_attributes_add_invalid:
2921 * @attrs: The attributes array to add to.
2922 * @attr_type: The type of attribute to add.
2923 *
2924 * #GckAttributes are now immutable. This method no longer does anything.
2925 *
2926 * Deprecated: 3.4: Use gck_builder_add_invalid() instead
2927 *
2928 * Returns: (transfer none): returns %NULL
2929 **/
2930 GckAttribute *
gck_attributes_add_invalid(GckAttributes * attrs,gulong attr_type)2931 gck_attributes_add_invalid (GckAttributes *attrs,
2932 gulong attr_type)
2933 {
2934 g_warning ("gck_attributes_add_invalid() is no no longer supported");
2935 return NULL;
2936 }
2937
2938 /**
2939 * gck_attributes_add_empty:
2940 * @attrs: The attributes array to add.
2941 * @attr_type: The type of attribute to add.
2942 *
2943 * #GckAttributes are now immutable. This method no longer does anything.
2944 *
2945 * Deprecated: 3.4: Use gck_builder_add_empty() instead.
2946 *
2947 * Returns: (transfer none): returns %NULL
2948 **/
2949 GckAttribute *
gck_attributes_add_empty(GckAttributes * attrs,gulong attr_type)2950 gck_attributes_add_empty (GckAttributes *attrs,
2951 gulong attr_type)
2952 {
2953 g_warning ("gck_attributes_add_empty() is no no longer supported");
2954 return NULL;
2955 }
2956
2957 /**
2958 * gck_attributes_add_boolean:
2959 * @attrs: the attributes array to add to
2960 * @attr_type: the type of attribute to add
2961 * @value: the boolean value to add
2962 *
2963 * #GckAttributes are now immutable. This method no longer does anything.
2964 *
2965 * Deprecated: 3.4: Use gck_builder_add_boolean() instead.
2966 *
2967 * Returns: (transfer none): returns %NULL
2968 **/
2969 GckAttribute *
gck_attributes_add_boolean(GckAttributes * attrs,gulong attr_type,gboolean value)2970 gck_attributes_add_boolean (GckAttributes *attrs,
2971 gulong attr_type,
2972 gboolean value)
2973 {
2974 g_warning ("gck_attributes_add_boolean() is no no longer supported");
2975 return NULL;
2976 }
2977
2978 /**
2979 * gck_attributes_set_boolean:
2980 * @attrs: the attributes
2981 * @attr_type: the type of attribute to set
2982 * @value: boolean value to set
2983 *
2984 * #GckAttributes are now immutable. This method no longer does anything.
2985 *
2986 * Deprecated: 3.4: Use gck_builder_set_boolean() instead.
2987 */
2988 void
gck_attributes_set_boolean(GckAttributes * attrs,gulong attr_type,gboolean value)2989 gck_attributes_set_boolean (GckAttributes *attrs,
2990 gulong attr_type,
2991 gboolean value)
2992 {
2993 g_warning ("gck_attributes_set_boolean() is no no longer supported");
2994
2995 }
2996
2997 /**
2998 * gck_attributes_add_string:
2999 * @attrs: the attributes array to add to
3000 * @attr_type: the type of attribute to add
3001 * @value: the null terminated string value to add
3002 *
3003 * #GckAttributes are now immutable. This method no longer does anything.
3004 *
3005 * Deprecated: 3.4: Use gck_builder_add_string() instead.
3006 *
3007 * Returns: (transfer none): returns %NULL
3008 **/
3009 GckAttribute *
gck_attributes_add_string(GckAttributes * attrs,gulong attr_type,const gchar * value)3010 gck_attributes_add_string (GckAttributes *attrs,
3011 gulong attr_type,
3012 const gchar *value)
3013 {
3014 g_warning ("gck_attributes_add_string() is no no longer supported");
3015 return NULL;
3016 }
3017
3018 /**
3019 * gck_attributes_set_string:
3020 * @attrs: the attributes
3021 * @attr_type: the type of attribute to set
3022 * @value: null terminated string value to set
3023 *
3024 * #GckAttributes are now immutable. This method no longer does anything.
3025 *
3026 * Deprecated: 3.4: Use gck_builder_set_string() instead.
3027 */
3028 void
gck_attributes_set_string(GckAttributes * attrs,gulong attr_type,const gchar * value)3029 gck_attributes_set_string (GckAttributes *attrs,
3030 gulong attr_type,
3031 const gchar *value)
3032 {
3033 g_warning ("gck_attributes_set_string() is no no longer supported");
3034 }
3035
3036 /**
3037 * gck_attributes_add_date:
3038 * @attrs: the attributes array to add to
3039 * @attr_type: the type of attribute to add
3040 * @value: the GDate value to add
3041 *
3042 * #GckAttributes are now immutable. This method no longer does anything.
3043 *
3044 * Deprecated: 3.4: Use gck_builder_add_date() instead.
3045 *
3046 * Returns: (transfer none): returns %NULL
3047 **/
3048 GckAttribute *
gck_attributes_add_date(GckAttributes * attrs,gulong attr_type,const GDate * value)3049 gck_attributes_add_date (GckAttributes *attrs,
3050 gulong attr_type,
3051 const GDate *value)
3052 {
3053 g_warning ("gck_attributes_add_date() is no no longer supported");
3054 return NULL;
3055 }
3056
3057 /**
3058 * gck_attributes_set_date:
3059 * @attrs: the attributes
3060 * @attr_type: the type of attribute to set
3061 * @value: date value to set
3062 *
3063 * #GckAttributes are now immutable. This method no longer does anything.
3064 *
3065 * Deprecated: 3.4: Use gck_builder_set_date() instead.
3066 */
3067 void
gck_attributes_set_date(GckAttributes * attrs,gulong attr_type,const GDate * value)3068 gck_attributes_set_date (GckAttributes *attrs,
3069 gulong attr_type,
3070 const GDate *value)
3071 {
3072 g_warning ("gck_attributes_set_date() is no no longer supported");
3073 }
3074
3075 /**
3076 * gck_attributes_add_ulong:
3077 * @attrs: the attributes array to add to
3078 * @attr_type: the type of attribute to add
3079 * @value: the gulong value to add
3080 *
3081 * #GckAttributes are now immutable. This method no longer does anything.
3082 *
3083 * Deprecated: 3.4: Use gck_builder_add_ulong() instead.
3084 *
3085 * Returns: (transfer none): returns %NULL
3086 **/
3087 GckAttribute *
gck_attributes_add_ulong(GckAttributes * attrs,gulong attr_type,gulong value)3088 gck_attributes_add_ulong (GckAttributes *attrs,
3089 gulong attr_type,
3090 gulong value)
3091 {
3092 g_warning ("gck_attributes_add_ulong() is no no longer supported");
3093 return NULL;
3094 }
3095
3096 /**
3097 * gck_attributes_set_ulong:
3098 * @attrs: the attributes
3099 * @attr_type: the type of attribute to set
3100 * @value: gulong value to set
3101 *
3102 * #GckAttributes are now immutable. This method no longer does anything.
3103 *
3104 * Deprecated: 3.4: Use gck_builder_set_ulong() instead.
3105 */
3106 void
gck_attributes_set_ulong(GckAttributes * attrs,gulong attr_type,gulong value)3107 gck_attributes_set_ulong (GckAttributes *attrs,
3108 gulong attr_type,
3109 gulong value)
3110 {
3111 g_warning ("gck_attributes_set_ulong() is no no longer supported");
3112 }
3113
3114 /**
3115 * gck_attributes_add_all:
3116 * @attrs: a set of attributes
3117 * @from: attributes to add
3118 *
3119 * #GckAttributes are now immutable. This method no longer does anything.
3120 *
3121 * Deprecated: 3.4: Use gck_builder_add_all() instead.
3122 */
3123 void
gck_attributes_add_all(GckAttributes * attrs,GckAttributes * from)3124 gck_attributes_add_all (GckAttributes *attrs,
3125 GckAttributes *from)
3126 {
3127 g_warning ("gck_attributes_add_all() is no no longer supported");
3128 }
3129
3130 /**
3131 * gck_attributes_set_all:
3132 * @attrs: set of attributes
3133 * @from: attributes to add
3134 *
3135 * #GckAttributes are now immutable. This method no longer does anything.
3136 *
3137 * Deprecated: 3.4: Use gck_builder_set_all() instead.
3138 */
3139 void
gck_attributes_set_all(GckAttributes * attrs,GckAttributes * from)3140 gck_attributes_set_all (GckAttributes *attrs,
3141 GckAttributes *from)
3142 {
3143 g_warning ("gck_attributes_set_all() is no no longer supported");
3144 }
3145
3146 /**
3147 * gck_attributes_dup:
3148 * @attrs: set of attributes to copy
3149 *
3150 * #GckAttributes are now immutable, and can be used in mulitple places.
3151 *
3152 * Deprecated: 3.4: Use gck_attributes_ref() or gck_builder_add_all() instead.
3153 *
3154 * Returns: (transfer none): a new floating #GckAttributes
3155 */
3156 GckAttributes *
gck_attributes_dup(GckAttributes * attrs)3157 gck_attributes_dup (GckAttributes *attrs)
3158 {
3159 GckBuilder builder = GCK_BUILDER_INIT;
3160
3161 if (attrs == NULL)
3162 return NULL;
3163
3164 gck_builder_add_all (&builder, attrs);
3165 return gck_builder_end (&builder);
3166 }
3167