Coverage Report

Created: 2025-11-24 06:43

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/opensc/src/libopensc/pkcs15-dtrust.c
Line
Count
Source
1
/*
2
 * PKCS15 emulation layer for D-Trust card.
3
 *
4
 * Copyright (C) 2024, Mario Haustein <mario.haustein@hrz.tu-chemnitz.de>
5
 *
6
 * This library is free software; you can redistribute it and/or
7
 * 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,
12
 * but 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 02110-1301 USA
19
 */
20
21
#include <string.h>
22
23
#ifdef HAVE_CONFIG_H
24
#include "config.h"
25
#endif
26
27
#include "internal.h"
28
#include "pkcs15.h"
29
30
static int
31
_dtrust_parse_df(struct sc_pkcs15_card *p15card, struct sc_pkcs15_df *df)
32
0
{
33
0
  struct sc_context *ctx = p15card->card->ctx;
34
0
  struct sc_pkcs15_object *pkobjs[32];
35
0
  struct sc_pkcs15_prkey_info *prkey_info;
36
0
  int rv, i, count;
37
38
0
  LOG_FUNC_CALLED(ctx);
39
40
0
  if (!df)
41
0
    LOG_FUNC_RETURN(ctx, SC_ERROR_INVALID_ARGUMENTS);
42
43
0
  if (df->enumerated)
44
0
    LOG_FUNC_RETURN(ctx, SC_SUCCESS);
45
46
0
  rv = sc_pkcs15_parse_df(p15card, df);
47
0
  LOG_TEST_RET(ctx, rv, "DF parse error");
48
49
0
  if (df->type != SC_PKCS15_PRKDF)
50
0
    LOG_FUNC_RETURN(ctx, SC_SUCCESS);
51
52
0
  rv = sc_pkcs15_get_objects(p15card, SC_PKCS15_TYPE_PRKEY, pkobjs, sizeof(pkobjs) / sizeof(pkobjs[0]));
53
0
  LOG_TEST_RET(ctx, rv, "Cannot get PRKEY objects list");
54
55
0
  count = rv;
56
0
  for (i = 0; i < count; i++) {
57
0
    prkey_info = (struct sc_pkcs15_prkey_info *)pkobjs[i]->data;
58
59
0
    switch (p15card->card->type) {
60
    /* Cards with EC keys, don't encode the curve size in the
61
     * private key directory file. We need to set the field_length
62
     * element after parsing the private key directory file. */
63
0
    case SC_CARD_TYPE_DTRUST_V4_1_MULTI:
64
0
    case SC_CARD_TYPE_DTRUST_V4_1_M100:
65
0
    case SC_CARD_TYPE_DTRUST_V4_4_MULTI:
66
0
      prkey_info->field_length = 256;
67
0
      break;
68
69
0
    case SC_CARD_TYPE_DTRUST_V5_1_MULTI:
70
0
    case SC_CARD_TYPE_DTRUST_V5_1_M100:
71
0
    case SC_CARD_TYPE_DTRUST_V5_4_MULTI:
72
0
      prkey_info->field_length = 384;
73
0
      break;
74
0
    }
75
0
  }
76
77
0
  LOG_FUNC_RETURN(ctx, SC_SUCCESS);
78
0
}
79
80
static int
81
dtrust_pkcs15emu_detect_card(sc_pkcs15_card_t *p15card)
82
8.31k
{
83
8.31k
  if (p15card->card->type < SC_CARD_TYPE_DTRUST_V4_1_STD)
84
8.31k
    return SC_ERROR_WRONG_CARD;
85
86
0
  if (p15card->card->type > SC_CARD_TYPE_DTRUST_V5_4_MULTI)
87
0
    return SC_ERROR_WRONG_CARD;
88
89
0
  return SC_SUCCESS;
90
0
}
91
92
static int
93
sc_pkcs15emu_dtrust_init(struct sc_pkcs15_card *p15card, struct sc_aid *aid)
94
0
{
95
0
  struct sc_context *ctx = p15card->card->ctx;
96
0
  int rv;
97
98
0
  LOG_FUNC_CALLED(ctx);
99
100
0
  rv = sc_pkcs15_bind_internal(p15card, aid);
101
102
0
  p15card->ops.parse_df = _dtrust_parse_df;
103
104
0
#if defined(ENABLE_SM) && defined(ENABLE_OPENPACE)
105
0
  struct sc_pkcs15_search_key sk;
106
0
  struct sc_pkcs15_object *objs[8];
107
0
  int i, len;
108
109
0
  memset(&sk, 0, sizeof(sk));
110
0
  sk.class_mask = SC_PKCS15_SEARCH_CLASS_AUTH;
111
0
  len = sc_pkcs15_search_objects(p15card, &sk, (struct sc_pkcs15_object **)&objs, sizeof(objs) / sizeof(struct sc_pkcs15_object *));
112
0
  for (i = 0; i < len; i++) {
113
0
    if (!strcmp(objs[i]->label, "CAN")) {
114
      /* Mark "Card CAN" as NOT a PIN object, so that it doesn't get it's own PKCS#11 slot */
115
0
      objs[i]->type &= ~SC_PKCS15_TYPE_AUTH_PIN;
116
0
    }
117
0
  }
118
0
#endif
119
120
0
  LOG_FUNC_RETURN(ctx, rv);
121
0
}
122
123
int
124
sc_pkcs15emu_dtrust_init_ex(struct sc_pkcs15_card *p15card, struct sc_aid *aid)
125
8.31k
{
126
8.31k
  if (dtrust_pkcs15emu_detect_card(p15card))
127
8.31k
    return SC_ERROR_WRONG_CARD;
128
129
0
  return sc_pkcs15emu_dtrust_init(p15card, aid);
130
8.31k
}