Coverage Report

Created: 2023-03-26 08:33

/src/gnutls/lib/minitasn1/element.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * Copyright (C) 2000-2022 Free Software Foundation, Inc.
3
 *
4
 * This file is part of LIBTASN1.
5
 *
6
 * The LIBTASN1 library is free software; you can redistribute it
7
 * and/or modify it under the terms of the GNU Lesser General Public
8
 * License as published by the Free Software Foundation; either
9
 * version 2.1 of the License, or (at your option) any later version.
10
 *
11
 * This library is distributed in the hope that it will be useful, but
12
 * WITHOUT ANY WARRANTY; without even the implied warranty of
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
 * Lesser General Public License for more details.
15
 *
16
 * You should have received a copy of the GNU Lesser General Public
17
 * License along with this library; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19
 * 02110-1301, USA
20
 */
21
22
/*****************************************************/
23
/* File: element.c                                   */
24
/* Description: Functions with the read and write    */
25
/*   functions.                                      */
26
/*****************************************************/
27
28
29
#include <int.h>
30
#include "parser_aux.h"
31
#include <gstr.h>
32
#include "structure.h"
33
#include "c-ctype.h"
34
#include "element.h"
35
36
void
37
_asn1_hierarchical_name (asn1_node_const node, char *name, int name_size)
38
0
{
39
0
  asn1_node_const p;
40
0
  char tmp_name[64];
41
42
0
  p = node;
43
44
0
  name[0] = 0;
45
46
0
  while (p != NULL)
47
0
    {
48
0
      if (p->name[0] != 0)
49
0
  {
50
0
    _asn1_str_cpy (tmp_name, sizeof (tmp_name), name),
51
0
      _asn1_str_cpy (name, name_size, p->name);
52
0
    _asn1_str_cat (name, name_size, ".");
53
0
    _asn1_str_cat (name, name_size, tmp_name);
54
0
  }
55
0
      p = _asn1_find_up (p);
56
0
    }
57
58
0
  if (name[0] == 0)
59
0
    _asn1_str_cpy (name, name_size, "ROOT");
60
0
}
61
62
63
/******************************************************************/
64
/* Function : _asn1_convert_integer                               */
65
/* Description: converts an integer from a null terminated string */
66
/*              to der decoding. The convertion from a null       */
67
/*              terminated string to an integer is made with      */
68
/*              the 'strtol' function.                            */
69
/* Parameters:                                                    */
70
/*   value: null terminated string to convert.                    */
71
/*   value_out: convertion result (memory must be already         */
72
/*              allocated).                                       */
73
/*   value_out_size: number of bytes of value_out.                */
74
/*   len: number of significant byte of value_out.                */
75
/* Return: ASN1_MEM_ERROR or ASN1_SUCCESS                         */
76
/******************************************************************/
77
int
78
_asn1_convert_integer (const unsigned char *value, unsigned char *value_out,
79
           int value_out_size, int *len)
80
0
{
81
0
  char negative;
82
0
  unsigned char val[SIZEOF_UNSIGNED_LONG_INT];
83
0
  long valtmp;
84
0
  int k, k2;
85
86
0
  valtmp = _asn1_strtol (value, NULL, 10);
87
88
0
  for (k = 0; k < SIZEOF_UNSIGNED_LONG_INT; k++)
89
0
    {
90
0
      val[SIZEOF_UNSIGNED_LONG_INT - k - 1] = (valtmp >> (8 * k)) & 0xFF;
91
0
    }
92
93
0
  if (val[0] & 0x80)
94
0
    negative = 1;
95
0
  else
96
0
    negative = 0;
97
98
0
  for (k = 0; k < SIZEOF_UNSIGNED_LONG_INT - 1; k++)
99
0
    {
100
0
      if (negative && (val[k] != 0xFF))
101
0
  break;
102
0
      else if (!negative && val[k])
103
0
  break;
104
0
    }
105
106
0
  if ((negative && !(val[k] & 0x80)) || (!negative && (val[k] & 0x80)))
107
0
    k--;
108
109
0
  *len = SIZEOF_UNSIGNED_LONG_INT - k;
110
111
0
  if (SIZEOF_UNSIGNED_LONG_INT - k > value_out_size)
112
    /* VALUE_OUT is too short to contain the value conversion */
113
0
    return ASN1_MEM_ERROR;
114
115
0
  if (value_out != NULL)
116
0
    {
117
0
      for (k2 = k; k2 < SIZEOF_UNSIGNED_LONG_INT; k2++)
118
0
  value_out[k2 - k] = val[k2];
119
0
    }
120
121
#if 0
122
  printf ("_asn1_convert_integer: valueIn=%s, lenOut=%d", value, *len);
123
  for (k = 0; k < SIZEOF_UNSIGNED_LONG_INT; k++)
124
    printf (", vOut[%d]=%d", k, value_out[k]);
125
  printf ("\n");
126
#endif
127
128
0
  return ASN1_SUCCESS;
129
0
}
130
131
/* Appends a new element into the sequence (or set) defined by this
132
 * node. The new element will have a name of '?number', where number
133
 * is a monotonically increased serial number.
134
 *
135
 * The last element in the list may be provided in @pcache, to avoid
136
 * traversing the list, an expensive operation in long lists.
137
 *
138
 * On success it returns in @pcache the added element (which is the
139
 * tail in the list of added elements).
140
 */
141
int
142
_asn1_append_sequence_set (asn1_node node, struct node_tail_cache_st *pcache)
143
0
{
144
0
  asn1_node p, p2;
145
0
  char temp[LTOSTR_MAX_SIZE + 1];
146
0
  long n;
147
148
0
  if (!node || !(node->down))
149
0
    return ASN1_GENERIC_ERROR;
150
151
0
  p = node->down;
152
0
  while ((type_field (p->type) == ASN1_ETYPE_TAG)
153
0
   || (type_field (p->type) == ASN1_ETYPE_SIZE))
154
0
    p = p->right;
155
156
0
  p2 = _asn1_copy_structure3 (p);
157
0
  if (p2 == NULL)
158
0
    return ASN1_GENERIC_ERROR;
159
160
0
  if (pcache == NULL || pcache->tail == NULL || pcache->head != node)
161
0
    {
162
0
      while (p->right)
163
0
  {
164
0
    p = p->right;
165
0
  }
166
0
    }
167
0
  else
168
0
    {
169
0
      p = pcache->tail;
170
0
    }
171
172
0
  _asn1_set_right (p, p2);
173
0
  if (pcache)
174
0
    {
175
0
      pcache->head = node;
176
0
      pcache->tail = p2;
177
0
    }
178
179
0
  if (p->name[0] == 0)
180
0
    _asn1_str_cpy (temp, sizeof (temp), "?1");
181
0
  else
182
0
    {
183
0
      n = strtol (p->name + 1, NULL, 0);
184
0
      n++;
185
0
      temp[0] = '?';
186
0
      _asn1_ltostr (n, temp + 1);
187
0
    }
188
0
  _asn1_set_name (p2, temp);
189
  /*  p2->type |= CONST_OPTION; */
190
191
0
  return ASN1_SUCCESS;
192
0
}
193
194
195
/**
196
 * asn1_write_value:
197
 * @node_root: pointer to a structure
198
 * @name: the name of the element inside the structure that you want to set.
199
 * @ivalue: vector used to specify the value to set. If len is >0,
200
 *   VALUE must be a two's complement form integer.  if len=0 *VALUE
201
 *   must be a null terminated string with an integer value.
202
 * @len: number of bytes of *value to use to set the value:
203
 *   value[0]..value[len-1] or 0 if value is a null terminated string
204
 *
205
 * Set the value of one element inside a structure.
206
 *
207
 * If an element is OPTIONAL and you want to delete it, you must use
208
 * the value=NULL and len=0.  Using "pkix.asn":
209
 *
210
 * result=asn1_write_value(cert, "tbsCertificate.issuerUniqueID",
211
 * NULL, 0);
212
 *
213
 * Description for each type:
214
 *
215
 * INTEGER: VALUE must contain a two's complement form integer.
216
 *
217
 *            value[0]=0xFF ,               len=1 -> integer=-1.
218
 *            value[0]=0xFF value[1]=0xFF , len=2 -> integer=-1.
219
 *            value[0]=0x01 ,               len=1 -> integer= 1.
220
 *            value[0]=0x00 value[1]=0x01 , len=2 -> integer= 1.
221
 *            value="123"                 , len=0 -> integer= 123.
222
 *
223
 * ENUMERATED: As INTEGER (but only with not negative numbers).
224
 *
225
 * BOOLEAN: VALUE must be the null terminated string "TRUE" or
226
 *   "FALSE" and LEN != 0.
227
 *
228
 *            value="TRUE" , len=1 -> boolean=TRUE.
229
 *            value="FALSE" , len=1 -> boolean=FALSE.
230
 *
231
 * OBJECT IDENTIFIER: VALUE must be a null terminated string with
232
 *   each number separated by a dot (e.g. "1.2.3.543.1").  LEN != 0.
233
 *
234
 *            value="1 2 840 10040 4 3" , len=1 -> OID=dsa-with-sha.
235
 *
236
 * UTCTime: VALUE must be a null terminated string in one of these
237
 *   formats: "YYMMDDhhmmssZ", "YYMMDDhhmmssZ",
238
 *   "YYMMDDhhmmss+hh'mm'", "YYMMDDhhmmss-hh'mm'",
239
 *   "YYMMDDhhmm+hh'mm'", or "YYMMDDhhmm-hh'mm'".  LEN != 0.
240
 *
241
 *            value="9801011200Z" , len=1 -> time=Jannuary 1st, 1998
242
 *            at 12h 00m Greenwich Mean Time
243
 *
244
 * GeneralizedTime: VALUE must be in one of this format:
245
 *   "YYYYMMDDhhmmss.sZ", "YYYYMMDDhhmmss.sZ",
246
 *   "YYYYMMDDhhmmss.s+hh'mm'", "YYYYMMDDhhmmss.s-hh'mm'",
247
 *   "YYYYMMDDhhmm+hh'mm'", or "YYYYMMDDhhmm-hh'mm'" where ss.s
248
 *   indicates the seconds with any precision like "10.1" or "01.02".
249
 *   LEN != 0
250
 *
251
 *            value="2001010112001.12-0700" , len=1 -> time=Jannuary
252
 *            1st, 2001 at 12h 00m 01.12s Pacific Daylight Time
253
 *
254
 * OCTET STRING: VALUE contains the octet string and LEN is the
255
 *   number of octets.
256
 *
257
 *            value="$\backslash$x01$\backslash$x02$\backslash$x03" ,
258
 *            len=3 -> three bytes octet string
259
 *
260
 * GeneralString: VALUE contains the generalstring and LEN is the
261
 *   number of octets.
262
 *
263
 *            value="$\backslash$x01$\backslash$x02$\backslash$x03" ,
264
 *            len=3 -> three bytes generalstring
265
 *
266
 * BIT STRING: VALUE contains the bit string organized by bytes and
267
 *   LEN is the number of bits.
268
 *
269
 *   value="$\backslash$xCF" , len=6 -> bit string="110011" (six
270
 *   bits)
271
 *
272
 * CHOICE: if NAME indicates a choice type, VALUE must specify one of
273
 *   the alternatives with a null terminated string. LEN != 0. Using
274
 *   "pkix.asn"\:
275
 *
276
 *           result=asn1_write_value(cert,
277
 *           "certificate1.tbsCertificate.subject", "rdnSequence",
278
 *           1);
279
 *
280
 * ANY: VALUE indicates the der encoding of a structure.  LEN != 0.
281
 *
282
 * SEQUENCE OF: VALUE must be the null terminated string "NEW" and
283
 *   LEN != 0. With this instruction another element is appended in
284
 *   the sequence. The name of this element will be "?1" if it's the
285
 *   first one, "?2" for the second and so on.
286
 *
287
 *   Using "pkix.asn"\:
288
 *
289
 *   result=asn1_write_value(cert,
290
 *   "certificate1.tbsCertificate.subject.rdnSequence", "NEW", 1);
291
 *
292
 * SET OF: the same as SEQUENCE OF.  Using "pkix.asn":
293
 *
294
 *           result=asn1_write_value(cert,
295
 *           "tbsCertificate.subject.rdnSequence.?LAST", "NEW", 1);
296
 *
297
 * Returns: %ASN1_SUCCESS if the value was set,
298
 *   %ASN1_ELEMENT_NOT_FOUND if @name is not a valid element, and
299
 *   %ASN1_VALUE_NOT_VALID if @ivalue has a wrong format.
300
 **/
301
int
302
asn1_write_value (asn1_node node_root, const char *name,
303
      const void *ivalue, int len)
304
0
{
305
0
  asn1_node node, p, p2;
306
0
  unsigned char *temp, *value_temp = NULL, *default_temp = NULL;
307
0
  int len2, k, k2, negative;
308
0
  size_t i;
309
0
  const unsigned char *value = ivalue;
310
0
  unsigned int type;
311
312
0
  node = asn1_find_node (node_root, name);
313
0
  if (node == NULL)
314
0
    return ASN1_ELEMENT_NOT_FOUND;
315
316
0
  if ((node->type & CONST_OPTION) && (value == NULL) && (len == 0))
317
0
    {
318
0
      asn1_delete_structure (&node);
319
0
      return ASN1_SUCCESS;
320
0
    }
321
322
0
  type = type_field (node->type);
323
324
0
  if ((type == ASN1_ETYPE_SEQUENCE_OF || type == ASN1_ETYPE_SET_OF)
325
0
      && (value == NULL) && (len == 0))
326
0
    {
327
0
      p = node->down;
328
0
      while ((type_field (p->type) == ASN1_ETYPE_TAG)
329
0
       || (type_field (p->type) == ASN1_ETYPE_SIZE))
330
0
  p = p->right;
331
332
0
      while (p->right)
333
0
  asn1_delete_structure (&p->right);
334
335
0
      return ASN1_SUCCESS;
336
0
    }
337
338
  /* Don't allow element deletion for other types */
339
0
  if (value == NULL)
340
0
    {
341
0
      return ASN1_VALUE_NOT_VALID;
342
0
    }
343
344
0
  switch (type)
345
0
    {
346
0
    case ASN1_ETYPE_BOOLEAN:
347
0
      if (!_asn1_strcmp (value, "TRUE"))
348
0
  {
349
0
    if (node->type & CONST_DEFAULT)
350
0
      {
351
0
        p = node->down;
352
0
        while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
353
0
    p = p->right;
354
0
        if (p->type & CONST_TRUE)
355
0
    _asn1_set_value (node, NULL, 0);
356
0
        else
357
0
    _asn1_set_value (node, "T", 1);
358
0
      }
359
0
    else
360
0
      _asn1_set_value (node, "T", 1);
361
0
  }
362
0
      else if (!_asn1_strcmp (value, "FALSE"))
363
0
  {
364
0
    if (node->type & CONST_DEFAULT)
365
0
      {
366
0
        p = node->down;
367
0
        while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
368
0
    p = p->right;
369
0
        if (p->type & CONST_FALSE)
370
0
    _asn1_set_value (node, NULL, 0);
371
0
        else
372
0
    _asn1_set_value (node, "F", 1);
373
0
      }
374
0
    else
375
0
      _asn1_set_value (node, "F", 1);
376
0
  }
377
0
      else
378
0
  return ASN1_VALUE_NOT_VALID;
379
0
      break;
380
0
    case ASN1_ETYPE_INTEGER:
381
0
    case ASN1_ETYPE_ENUMERATED:
382
0
      if (len == 0)
383
0
  {
384
0
    if ((c_isdigit (value[0])) || (value[0] == '-'))
385
0
      {
386
0
        value_temp = malloc (SIZEOF_UNSIGNED_LONG_INT);
387
0
        if (value_temp == NULL)
388
0
    return ASN1_MEM_ALLOC_ERROR;
389
390
0
        _asn1_convert_integer (value, value_temp,
391
0
             SIZEOF_UNSIGNED_LONG_INT, &len);
392
0
      }
393
0
    else
394
0
      {     /* is an identifier like v1 */
395
0
        if (!(node->type & CONST_LIST))
396
0
    return ASN1_VALUE_NOT_VALID;
397
0
        p = node->down;
398
0
        while (p)
399
0
    {
400
0
      if (type_field (p->type) == ASN1_ETYPE_CONSTANT)
401
0
        {
402
0
          if (!_asn1_strcmp (p->name, value))
403
0
      {
404
0
        value_temp = malloc (SIZEOF_UNSIGNED_LONG_INT);
405
0
        if (value_temp == NULL)
406
0
          return ASN1_MEM_ALLOC_ERROR;
407
408
0
        _asn1_convert_integer (p->value,
409
0
             value_temp,
410
0
             SIZEOF_UNSIGNED_LONG_INT,
411
0
             &len);
412
0
        break;
413
0
      }
414
0
        }
415
0
      p = p->right;
416
0
    }
417
0
        if (p == NULL)
418
0
    return ASN1_VALUE_NOT_VALID;
419
0
      }
420
0
  }
421
0
      else
422
0
  {     /* len != 0 */
423
0
    value_temp = malloc (len);
424
0
    if (value_temp == NULL)
425
0
      return ASN1_MEM_ALLOC_ERROR;
426
0
    memcpy (value_temp, value, len);
427
0
  }
428
429
0
      if (value_temp[0] & 0x80)
430
0
  negative = 1;
431
0
      else
432
0
  negative = 0;
433
434
0
      if (negative && (type_field (node->type) == ASN1_ETYPE_ENUMERATED))
435
0
  {
436
0
    free (value_temp);
437
0
    return ASN1_VALUE_NOT_VALID;
438
0
  }
439
440
0
      for (k = 0; k < len - 1; k++)
441
0
  if (negative && (value_temp[k] != 0xFF))
442
0
    break;
443
0
  else if (!negative && value_temp[k])
444
0
    break;
445
446
0
      if ((negative && !(value_temp[k] & 0x80)) ||
447
0
    (!negative && (value_temp[k] & 0x80)))
448
0
  k--;
449
450
0
      _asn1_set_value_lv (node, value_temp + k, len - k);
451
452
0
      if (node->type & CONST_DEFAULT)
453
0
  {
454
0
    p = node->down;
455
0
    while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
456
0
      p = p->right;
457
0
    if ((c_isdigit (p->value[0])) || (p->value[0] == '-'))
458
0
      {
459
0
        default_temp = malloc (SIZEOF_UNSIGNED_LONG_INT);
460
0
        if (default_temp == NULL)
461
0
    {
462
0
      free (value_temp);
463
0
      return ASN1_MEM_ALLOC_ERROR;
464
0
    }
465
466
0
        _asn1_convert_integer (p->value, default_temp,
467
0
             SIZEOF_UNSIGNED_LONG_INT, &len2);
468
0
      }
469
0
    else
470
0
      {     /* is an identifier like v1 */
471
0
        if (!(node->type & CONST_LIST))
472
0
    {
473
0
      free (value_temp);
474
0
      return ASN1_VALUE_NOT_VALID;
475
0
    }
476
0
        p2 = node->down;
477
0
        while (p2)
478
0
    {
479
0
      if (type_field (p2->type) == ASN1_ETYPE_CONSTANT)
480
0
        {
481
0
          if (!_asn1_strcmp (p2->name, p->value))
482
0
      {
483
0
        default_temp = malloc (SIZEOF_UNSIGNED_LONG_INT);
484
0
        if (default_temp == NULL)
485
0
          {
486
0
            free (value_temp);
487
0
            return ASN1_MEM_ALLOC_ERROR;
488
0
          }
489
490
0
        _asn1_convert_integer (p2->value,
491
0
             default_temp,
492
0
             SIZEOF_UNSIGNED_LONG_INT,
493
0
             &len2);
494
0
        break;
495
0
      }
496
0
        }
497
0
      p2 = p2->right;
498
0
    }
499
0
        if (p2 == NULL)
500
0
    {
501
0
      free (value_temp);
502
0
      return ASN1_VALUE_NOT_VALID;
503
0
    }
504
0
      }
505
506
507
0
    if ((len - k) == len2)
508
0
      {
509
0
        for (k2 = 0; k2 < len2; k2++)
510
0
    if (value_temp[k + k2] != default_temp[k2])
511
0
      {
512
0
        break;
513
0
      }
514
0
        if (k2 == len2)
515
0
    _asn1_set_value (node, NULL, 0);
516
0
      }
517
0
    free (default_temp);
518
0
  }
519
0
      free (value_temp);
520
0
      break;
521
0
    case ASN1_ETYPE_OBJECT_ID:
522
0
      for (i = 0; i < _asn1_strlen (value); i++)
523
0
  if ((!c_isdigit (value[i])) && (value[i] != '.') && (value[i] != '+'))
524
0
    return ASN1_VALUE_NOT_VALID;
525
0
      if (node->type & CONST_DEFAULT)
526
0
  {
527
0
    p = node->down;
528
0
    while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
529
0
      p = p->right;
530
0
    if (!_asn1_strcmp (value, p->value))
531
0
      {
532
0
        _asn1_set_value (node, NULL, 0);
533
0
        break;
534
0
      }
535
0
  }
536
0
      _asn1_set_value (node, value, _asn1_strlen (value) + 1);
537
0
      break;
538
0
    case ASN1_ETYPE_UTC_TIME:
539
0
      {
540
0
  len = _asn1_strlen (value);
541
0
  if (len < 11)
542
0
    return ASN1_VALUE_NOT_VALID;
543
0
  for (k = 0; k < 10; k++)
544
0
    if (!c_isdigit (value[k]))
545
0
      return ASN1_VALUE_NOT_VALID;
546
0
  switch (len)
547
0
    {
548
0
    case 11:
549
0
      if (value[10] != 'Z')
550
0
        return ASN1_VALUE_NOT_VALID;
551
0
      break;
552
0
    case 13:
553
0
      if ((!c_isdigit (value[10])) || (!c_isdigit (value[11])) ||
554
0
    (value[12] != 'Z'))
555
0
        return ASN1_VALUE_NOT_VALID;
556
0
      break;
557
0
    case 15:
558
0
      if ((value[10] != '+') && (value[10] != '-'))
559
0
        return ASN1_VALUE_NOT_VALID;
560
0
      for (k = 11; k < 15; k++)
561
0
        if (!c_isdigit (value[k]))
562
0
    return ASN1_VALUE_NOT_VALID;
563
0
      break;
564
0
    case 17:
565
0
      if ((!c_isdigit (value[10])) || (!c_isdigit (value[11])))
566
0
        return ASN1_VALUE_NOT_VALID;
567
0
      if ((value[12] != '+') && (value[12] != '-'))
568
0
        return ASN1_VALUE_NOT_VALID;
569
0
      for (k = 13; k < 17; k++)
570
0
        if (!c_isdigit (value[k]))
571
0
    return ASN1_VALUE_NOT_VALID;
572
0
      break;
573
0
    default:
574
0
      return ASN1_VALUE_NOT_FOUND;
575
0
    }
576
0
  _asn1_set_value (node, value, len);
577
0
      }
578
0
      break;
579
0
    case ASN1_ETYPE_GENERALIZED_TIME:
580
0
      len = _asn1_strlen (value);
581
0
      _asn1_set_value (node, value, len);
582
0
      break;
583
0
    case ASN1_ETYPE_OCTET_STRING:
584
0
    case ASN1_ETYPE_GENERALSTRING:
585
0
    case ASN1_ETYPE_NUMERIC_STRING:
586
0
    case ASN1_ETYPE_IA5_STRING:
587
0
    case ASN1_ETYPE_TELETEX_STRING:
588
0
    case ASN1_ETYPE_PRINTABLE_STRING:
589
0
    case ASN1_ETYPE_UNIVERSAL_STRING:
590
0
    case ASN1_ETYPE_BMP_STRING:
591
0
    case ASN1_ETYPE_UTF8_STRING:
592
0
    case ASN1_ETYPE_VISIBLE_STRING:
593
0
      if (len == 0)
594
0
  len = _asn1_strlen (value);
595
0
      _asn1_set_value_lv (node, value, len);
596
0
      break;
597
0
    case ASN1_ETYPE_BIT_STRING:
598
0
      if (len == 0)
599
0
  len = _asn1_strlen (value);
600
0
      asn1_length_der ((len >> 3) + 2, NULL, &len2);
601
0
      temp = malloc ((len >> 3) + 2 + len2);
602
0
      if (temp == NULL)
603
0
  return ASN1_MEM_ALLOC_ERROR;
604
605
0
      asn1_bit_der (value, len, temp, &len2);
606
0
      _asn1_set_value_m (node, temp, len2);
607
0
      temp = NULL;
608
0
      break;
609
0
    case ASN1_ETYPE_CHOICE:
610
0
      p = node->down;
611
0
      while (p)
612
0
  {
613
0
    if (!_asn1_strcmp (p->name, value))
614
0
      {
615
0
        p2 = node->down;
616
0
        while (p2)
617
0
    {
618
0
      if (p2 != p)
619
0
        {
620
0
          asn1_delete_structure (&p2);
621
0
          p2 = node->down;
622
0
        }
623
0
      else
624
0
        p2 = p2->right;
625
0
    }
626
0
        break;
627
0
      }
628
0
    p = p->right;
629
0
  }
630
0
      if (!p)
631
0
  return ASN1_ELEMENT_NOT_FOUND;
632
0
      break;
633
0
    case ASN1_ETYPE_ANY:
634
0
      _asn1_set_value_lv (node, value, len);
635
0
      break;
636
0
    case ASN1_ETYPE_SEQUENCE_OF:
637
0
    case ASN1_ETYPE_SET_OF:
638
0
      if (_asn1_strcmp (value, "NEW"))
639
0
  return ASN1_VALUE_NOT_VALID;
640
0
      _asn1_append_sequence_set (node, NULL);
641
0
      break;
642
0
    default:
643
0
      return ASN1_ELEMENT_NOT_FOUND;
644
0
      break;
645
0
    }
646
647
0
  return ASN1_SUCCESS;
648
0
}
649
650
651
#define PUT_VALUE( ptr, ptr_size, data, data_size) \
652
0
  *len = data_size; \
653
0
  if (ptr_size < data_size) { \
654
0
    return ASN1_MEM_ERROR; \
655
0
  } else { \
656
0
    if (ptr && data_size > 0) \
657
0
      memcpy (ptr, data, data_size); \
658
0
  }
659
660
#define PUT_STR_VALUE( ptr, ptr_size, data) \
661
0
  *len = _asn1_strlen (data) + 1; \
662
0
  if (ptr_size < *len) { \
663
0
    return ASN1_MEM_ERROR; \
664
0
  } else { \
665
0
    /* this strcpy is checked */ \
666
0
    if (ptr) { \
667
0
      _asn1_strcpy (ptr, data); \
668
0
    } \
669
0
  }
670
671
#define PUT_AS_STR_VALUE( ptr, ptr_size, data, data_size) \
672
0
  *len = data_size + 1; \
673
0
  if (ptr_size < *len) { \
674
0
    return ASN1_MEM_ERROR; \
675
0
  } else { \
676
0
    /* this strcpy is checked */ \
677
0
    if (ptr) { \
678
0
      if (data_size > 0) \
679
0
        memcpy (ptr, data, data_size); \
680
0
      ptr[data_size] = 0; \
681
0
    } \
682
0
  }
683
684
#define ADD_STR_VALUE( ptr, ptr_size, data) \
685
0
        *len += _asn1_strlen(data); \
686
0
        if (ptr_size < (int) *len) { \
687
0
                (*len)++; \
688
0
                return ASN1_MEM_ERROR; \
689
0
        } else { \
690
0
                /* this strcat is checked */ \
691
0
                if (ptr) _asn1_strcat (ptr, data); \
692
0
        }
693
694
/**
695
 * asn1_read_value:
696
 * @root: pointer to a structure.
697
 * @name: the name of the element inside a structure that you want to read.
698
 * @ivalue: vector that will contain the element's content, must be a
699
 *   pointer to memory cells already allocated (may be %NULL).
700
 * @len: number of bytes of *value: value[0]..value[len-1]. Initialy
701
 *   holds the sizeof value.
702
 *
703
 * Returns the value of one element inside a structure.
704
 * If an element is OPTIONAL and this returns
705
 * %ASN1_ELEMENT_NOT_FOUND, it means that this element wasn't present
706
 * in the der encoding that created the structure.  The first element
707
 * of a SEQUENCE_OF or SET_OF is named "?1". The second one "?2" and
708
 * so on. If the @root provided is a node to specific sequence element,
709
 * then the keyword "?CURRENT" is also acceptable and indicates the
710
 * current sequence element of this node.
711
 *
712
 * Note that there can be valid values with length zero. In these case
713
 * this function will succeed and @len will be zero.
714
 *
715
 * INTEGER: VALUE will contain a two's complement form integer.
716
 *
717
 *            integer=-1  -> value[0]=0xFF , len=1.
718
 *            integer=1   -> value[0]=0x01 , len=1.
719
 *
720
 * ENUMERATED: As INTEGER (but only with not negative numbers).
721
 *
722
 * BOOLEAN: VALUE will be the null terminated string "TRUE" or
723
 *   "FALSE" and LEN=5 or LEN=6.
724
 *
725
 * OBJECT IDENTIFIER: VALUE will be a null terminated string with
726
 *   each number separated by a dot (i.e. "1.2.3.543.1").
727
 *
728
 *                      LEN = strlen(VALUE)+1
729
 *
730
 * UTCTime: VALUE will be a null terminated string in one of these
731
 *   formats: "YYMMDDhhmmss+hh'mm'" or "YYMMDDhhmmss-hh'mm'".
732
 *   LEN=strlen(VALUE)+1.
733
 *
734
 * GeneralizedTime: VALUE will be a null terminated string in the
735
 *   same format used to set the value.
736
 *
737
 * OCTET STRING: VALUE will contain the octet string and LEN will be
738
 *   the number of octets.
739
 *
740
 * GeneralString: VALUE will contain the generalstring and LEN will
741
 *   be the number of octets.
742
 *
743
 * BIT STRING: VALUE will contain the bit string organized by bytes
744
 *   and LEN will be the number of bits.
745
 *
746
 * CHOICE: If NAME indicates a choice type, VALUE will specify the
747
 *   alternative selected.
748
 *
749
 * ANY: If NAME indicates an any type, VALUE will indicate the DER
750
 *   encoding of the structure actually used.
751
 *
752
 * Returns: %ASN1_SUCCESS if value is returned,
753
 *   %ASN1_ELEMENT_NOT_FOUND if @name is not a valid element,
754
 *   %ASN1_VALUE_NOT_FOUND if there isn't any value for the element
755
 *   selected, and %ASN1_MEM_ERROR if The value vector isn't big enough
756
 *   to store the result, and in this case @len will contain the number of
757
 *   bytes needed. On the occasion that the stored data are of zero-length
758
 *   this function may return %ASN1_SUCCESS even if the provided @len is zero.
759
 **/
760
int
761
asn1_read_value (asn1_node_const root, const char *name, void *ivalue,
762
     int *len)
763
0
{
764
0
  return asn1_read_value_type (root, name, ivalue, len, NULL);
765
0
}
766
767
/**
768
 * asn1_read_value_type:
769
 * @root: pointer to a structure.
770
 * @name: the name of the element inside a structure that you want to read.
771
 * @ivalue: vector that will contain the element's content, must be a
772
 *   pointer to memory cells already allocated (may be %NULL).
773
 * @len: number of bytes of *value: value[0]..value[len-1]. Initialy
774
 *   holds the sizeof value.
775
 * @etype: The type of the value read (ASN1_ETYPE)
776
 *
777
 * Returns the type and value of one element inside a structure.
778
 * If an element is OPTIONAL and this returns
779
 * %ASN1_ELEMENT_NOT_FOUND, it means that this element wasn't present
780
 * in the der encoding that created the structure.  The first element
781
 * of a SEQUENCE_OF or SET_OF is named "?1". The second one "?2" and
782
 * so on. If the @root provided is a node to specific sequence element,
783
 * then the keyword "?CURRENT" is also acceptable and indicates the
784
 * current sequence element of this node.
785
 *
786
 * Note that there can be valid values with length zero. In these case
787
 * this function will succeed and @len will be zero.
788
 *
789
 *
790
 * INTEGER: VALUE will contain a two's complement form integer.
791
 *
792
 *            integer=-1  -> value[0]=0xFF , len=1.
793
 *            integer=1   -> value[0]=0x01 , len=1.
794
 *
795
 * ENUMERATED: As INTEGER (but only with not negative numbers).
796
 *
797
 * BOOLEAN: VALUE will be the null terminated string "TRUE" or
798
 *   "FALSE" and LEN=5 or LEN=6.
799
 *
800
 * OBJECT IDENTIFIER: VALUE will be a null terminated string with
801
 *   each number separated by a dot (i.e. "1.2.3.543.1").
802
 *
803
 *                      LEN = strlen(VALUE)+1
804
 *
805
 * UTCTime: VALUE will be a null terminated string in one of these
806
 *   formats: "YYMMDDhhmmss+hh'mm'" or "YYMMDDhhmmss-hh'mm'".
807
 *   LEN=strlen(VALUE)+1.
808
 *
809
 * GeneralizedTime: VALUE will be a null terminated string in the
810
 *   same format used to set the value.
811
 *
812
 * OCTET STRING: VALUE will contain the octet string and LEN will be
813
 *   the number of octets.
814
 *
815
 * GeneralString: VALUE will contain the generalstring and LEN will
816
 *   be the number of octets.
817
 *
818
 * BIT STRING: VALUE will contain the bit string organized by bytes
819
 *   and LEN will be the number of bits.
820
 *
821
 * CHOICE: If NAME indicates a choice type, VALUE will specify the
822
 *   alternative selected.
823
 *
824
 * ANY: If NAME indicates an any type, VALUE will indicate the DER
825
 *   encoding of the structure actually used.
826
 *
827
 * Returns: %ASN1_SUCCESS if value is returned,
828
 *   %ASN1_ELEMENT_NOT_FOUND if @name is not a valid element,
829
 *   %ASN1_VALUE_NOT_FOUND if there isn't any value for the element
830
 *   selected, and %ASN1_MEM_ERROR if The value vector isn't big enough
831
 *   to store the result, and in this case @len will contain the number of
832
 *   bytes needed. On the occasion that the stored data are of zero-length
833
 *   this function may return %ASN1_SUCCESS even if the provided @len is zero.
834
 **/
835
int
836
asn1_read_value_type (asn1_node_const root, const char *name, void *ivalue,
837
          int *len, unsigned int *etype)
838
0
{
839
0
  asn1_node_const node, p, p2;
840
0
  int len2, len3, result;
841
0
  int value_size = *len;
842
0
  unsigned char *value = ivalue;
843
0
  unsigned type;
844
845
0
  node = asn1_find_node (root, name);
846
0
  if (node == NULL)
847
0
    return ASN1_ELEMENT_NOT_FOUND;
848
849
0
  type = type_field (node->type);
850
851
0
  if ((type != ASN1_ETYPE_NULL) &&
852
0
      (type != ASN1_ETYPE_CHOICE) &&
853
0
      !(node->type & CONST_DEFAULT) && !(node->type & CONST_ASSIGN) &&
854
0
      (node->value == NULL))
855
0
    return ASN1_VALUE_NOT_FOUND;
856
857
0
  if (etype)
858
0
    *etype = type;
859
0
  switch (type)
860
0
    {
861
0
    case ASN1_ETYPE_NULL:
862
0
      PUT_STR_VALUE (value, value_size, "NULL");
863
0
      break;
864
0
    case ASN1_ETYPE_BOOLEAN:
865
0
      if ((node->type & CONST_DEFAULT) && (node->value == NULL))
866
0
  {
867
0
    p = node->down;
868
0
    while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
869
0
      p = p->right;
870
0
    if (p->type & CONST_TRUE)
871
0
      {
872
0
        PUT_STR_VALUE (value, value_size, "TRUE");
873
0
      }
874
0
    else
875
0
      {
876
0
        PUT_STR_VALUE (value, value_size, "FALSE");
877
0
      }
878
0
  }
879
0
      else if (node->value[0] == 'T')
880
0
  {
881
0
    PUT_STR_VALUE (value, value_size, "TRUE");
882
0
  }
883
0
      else
884
0
  {
885
0
    PUT_STR_VALUE (value, value_size, "FALSE");
886
0
  }
887
0
      break;
888
0
    case ASN1_ETYPE_INTEGER:
889
0
    case ASN1_ETYPE_ENUMERATED:
890
0
      if ((node->type & CONST_DEFAULT) && (node->value == NULL))
891
0
  {
892
0
    p = node->down;
893
0
    while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
894
0
      p = p->right;
895
0
    if ((c_isdigit (p->value[0])) || (p->value[0] == '-')
896
0
        || (p->value[0] == '+'))
897
0
      {
898
0
        result = _asn1_convert_integer
899
0
    (p->value, value, value_size, len);
900
0
        if (result != ASN1_SUCCESS)
901
0
    return result;
902
0
      }
903
0
    else
904
0
      {     /* is an identifier like v1 */
905
0
        p2 = node->down;
906
0
        while (p2)
907
0
    {
908
0
      if (type_field (p2->type) == ASN1_ETYPE_CONSTANT)
909
0
        {
910
0
          if (!_asn1_strcmp (p2->name, p->value))
911
0
      {
912
0
        result = _asn1_convert_integer
913
0
          (p2->value, value, value_size, len);
914
0
        if (result != ASN1_SUCCESS)
915
0
          return result;
916
0
        break;
917
0
      }
918
0
        }
919
0
      p2 = p2->right;
920
0
    }
921
0
      }
922
0
  }
923
0
      else
924
0
  {
925
0
    len2 = -1;
926
0
    result = asn1_get_octet_der
927
0
      (node->value, node->value_len, &len2, value, value_size, len);
928
0
    if (result != ASN1_SUCCESS)
929
0
      return result;
930
0
  }
931
0
      break;
932
0
    case ASN1_ETYPE_OBJECT_ID:
933
0
      if (node->type & CONST_ASSIGN)
934
0
  {
935
0
    *len = 0;
936
0
    if (value)
937
0
      value[0] = 0;
938
0
    p = node->down;
939
0
    while (p)
940
0
      {
941
0
        if (type_field (p->type) == ASN1_ETYPE_CONSTANT)
942
0
    {
943
0
      ADD_STR_VALUE (value, value_size, p->value);
944
0
      if (p->right)
945
0
        {
946
0
          ADD_STR_VALUE (value, value_size, ".");
947
0
        }
948
0
    }
949
0
        p = p->right;
950
0
      }
951
0
    (*len)++;
952
0
  }
953
0
      else if ((node->type & CONST_DEFAULT) && (node->value == NULL))
954
0
  {
955
0
    p = node->down;
956
0
    while (type_field (p->type) != ASN1_ETYPE_DEFAULT)
957
0
      p = p->right;
958
0
    PUT_STR_VALUE (value, value_size, p->value);
959
0
  }
960
0
      else
961
0
  {
962
0
    PUT_STR_VALUE (value, value_size, node->value);
963
0
  }
964
0
      break;
965
0
    case ASN1_ETYPE_GENERALIZED_TIME:
966
0
    case ASN1_ETYPE_UTC_TIME:
967
0
      PUT_AS_STR_VALUE (value, value_size, node->value, node->value_len);
968
0
      break;
969
0
    case ASN1_ETYPE_OCTET_STRING:
970
0
    case ASN1_ETYPE_GENERALSTRING:
971
0
    case ASN1_ETYPE_NUMERIC_STRING:
972
0
    case ASN1_ETYPE_IA5_STRING:
973
0
    case ASN1_ETYPE_TELETEX_STRING:
974
0
    case ASN1_ETYPE_PRINTABLE_STRING:
975
0
    case ASN1_ETYPE_UNIVERSAL_STRING:
976
0
    case ASN1_ETYPE_BMP_STRING:
977
0
    case ASN1_ETYPE_UTF8_STRING:
978
0
    case ASN1_ETYPE_VISIBLE_STRING:
979
0
      len2 = -1;
980
0
      result = asn1_get_octet_der
981
0
  (node->value, node->value_len, &len2, value, value_size, len);
982
0
      if (result != ASN1_SUCCESS)
983
0
  return result;
984
0
      break;
985
0
    case ASN1_ETYPE_BIT_STRING:
986
0
      len2 = -1;
987
0
      result = asn1_get_bit_der
988
0
  (node->value, node->value_len, &len2, value, value_size, len);
989
0
      if (result != ASN1_SUCCESS)
990
0
  return result;
991
0
      break;
992
0
    case ASN1_ETYPE_CHOICE:
993
0
      PUT_STR_VALUE (value, value_size, node->down->name);
994
0
      break;
995
0
    case ASN1_ETYPE_ANY:
996
0
      len3 = -1;
997
0
      len2 = asn1_get_length_der (node->value, node->value_len, &len3);
998
0
      if (len2 < 0)
999
0
  return ASN1_DER_ERROR;
1000
0
      PUT_VALUE (value, value_size, node->value + len3, len2);
1001
0
      break;
1002
0
    default:
1003
0
      return ASN1_ELEMENT_NOT_FOUND;
1004
0
      break;
1005
0
    }
1006
0
  return ASN1_SUCCESS;
1007
0
}
1008
1009
1010
/**
1011
 * asn1_read_tag:
1012
 * @root: pointer to a structure
1013
 * @name: the name of the element inside a structure.
1014
 * @tagValue:  variable that will contain the TAG value.
1015
 * @classValue: variable that will specify the TAG type.
1016
 *
1017
 * Returns the TAG and the CLASS of one element inside a structure.
1018
 * CLASS can have one of these constants: %ASN1_CLASS_APPLICATION,
1019
 * %ASN1_CLASS_UNIVERSAL, %ASN1_CLASS_PRIVATE or
1020
 * %ASN1_CLASS_CONTEXT_SPECIFIC.
1021
 *
1022
 * Returns: %ASN1_SUCCESS if successful, %ASN1_ELEMENT_NOT_FOUND if
1023
 *   @name is not a valid element.
1024
 **/
1025
int
1026
asn1_read_tag (asn1_node_const root, const char *name, int *tagValue,
1027
         int *classValue)
1028
0
{
1029
0
  asn1_node node, p, pTag;
1030
1031
0
  node = asn1_find_node (root, name);
1032
0
  if (node == NULL)
1033
0
    return ASN1_ELEMENT_NOT_FOUND;
1034
1035
0
  p = node->down;
1036
1037
  /* pTag will points to the IMPLICIT TAG */
1038
0
  pTag = NULL;
1039
0
  if (node->type & CONST_TAG)
1040
0
    {
1041
0
      while (p)
1042
0
  {
1043
0
    if (type_field (p->type) == ASN1_ETYPE_TAG)
1044
0
      {
1045
0
        if ((p->type & CONST_IMPLICIT) && (pTag == NULL))
1046
0
    pTag = p;
1047
0
        else if (p->type & CONST_EXPLICIT)
1048
0
    pTag = NULL;
1049
0
      }
1050
0
    p = p->right;
1051
0
  }
1052
0
    }
1053
1054
0
  if (pTag)
1055
0
    {
1056
0
      *tagValue = _asn1_strtoul (pTag->value, NULL, 10);
1057
1058
0
      if (pTag->type & CONST_APPLICATION)
1059
0
  *classValue = ASN1_CLASS_APPLICATION;
1060
0
      else if (pTag->type & CONST_UNIVERSAL)
1061
0
  *classValue = ASN1_CLASS_UNIVERSAL;
1062
0
      else if (pTag->type & CONST_PRIVATE)
1063
0
  *classValue = ASN1_CLASS_PRIVATE;
1064
0
      else
1065
0
  *classValue = ASN1_CLASS_CONTEXT_SPECIFIC;
1066
0
    }
1067
0
  else
1068
0
    {
1069
0
      unsigned type = type_field (node->type);
1070
0
      *classValue = ASN1_CLASS_UNIVERSAL;
1071
1072
0
      switch (type)
1073
0
  {
1074
0
  CASE_HANDLED_ETYPES:
1075
0
    *tagValue = _asn1_tags[type].tag;
1076
0
    break;
1077
0
  case ASN1_ETYPE_TAG:
1078
0
  case ASN1_ETYPE_CHOICE:
1079
0
  case ASN1_ETYPE_ANY:
1080
0
    *tagValue = -1;
1081
0
    break;
1082
0
  default:
1083
0
    break;
1084
0
  }
1085
0
    }
1086
1087
0
  return ASN1_SUCCESS;
1088
0
}
1089
1090
/**
1091
 * asn1_read_node_value:
1092
 * @node: pointer to a node.
1093
 * @data: a point to a asn1_data_node_st
1094
 *
1095
 * Returns the value a data node inside a asn1_node structure.
1096
 * The data returned should be handled as constant values.
1097
 *
1098
 * Returns: %ASN1_SUCCESS if the node exists.
1099
 **/
1100
int
1101
asn1_read_node_value (asn1_node_const node, asn1_data_node_st * data)
1102
0
{
1103
0
  data->name = node->name;
1104
0
  data->value = node->value;
1105
0
  data->value_len = node->value_len;
1106
0
  data->type = type_field (node->type);
1107
1108
0
  return ASN1_SUCCESS;
1109
0
}