9e3f96c950241993e34f3a885c98640e74b8d960
[strongswan.git] / src / charon-tkm / src / tkm / tkm_private_key.c
1 /*
2 * Copyright (C) 2012-2013 Reto Buerki
3 * Copyright (C) 2012-2013 Adrian-Ken Rueegsegger
4 * Hochschule fuer Technik Rapperswil
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2 of the License, or (at your
9 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
10 *
11 * This program is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
13 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * for more details.
15 */
16
17 #include <utils/debug.h>
18 #include <tkm/constants.h>
19 #include <tkm/client.h>
20
21 #include "tkm_utils.h"
22 #include "tkm_types.h"
23 #include "tkm_private_key.h"
24
25 typedef struct private_tkm_private_key_t private_tkm_private_key_t;
26
27 /**
28 * Private data of a tkm_private_key_t object.
29 */
30 struct private_tkm_private_key_t {
31
32 /**
33 * Public interface for this signer.
34 */
35 tkm_private_key_t public;
36
37 /**
38 * Key ID.
39 */
40 identification_t *id;
41
42 /**
43 * Key type.
44 */
45 key_type_t key_type;
46
47 /**
48 * Reference count.
49 */
50 refcount_t ref;
51
52 };
53
54 METHOD(private_key_t, get_type, key_type_t,
55 private_tkm_private_key_t *this)
56 {
57 return this->key_type;
58 }
59
60 METHOD(private_key_t, sign, bool,
61 private_tkm_private_key_t *this, signature_scheme_t scheme,
62 chunk_t data, chunk_t *signature)
63 {
64 signature_type sig;
65 init_message_type msg;
66
67 if (data.ptr == NULL)
68 {
69 DBG1(DBG_LIB, "unable to get signature information");
70 return FALSE;
71 }
72 sign_info_t sign = *(sign_info_t *)(data.ptr);
73
74 chunk_to_sequence(&sign.init_message, &msg, sizeof(init_message_type));
75 const isa_id_type isa_id = sign.isa_id;
76 chunk_free(&sign.init_message);
77
78 if (ike_isa_sign(isa_id, 1, msg, &sig) != TKM_OK)
79 {
80 DBG1(DBG_LIB, "signature operation failed");
81 return FALSE;
82 }
83
84 sequence_to_chunk(sig.data, sig.size, signature);
85 return TRUE;
86 }
87
88 METHOD(private_key_t, decrypt, bool,
89 private_tkm_private_key_t *this, encryption_scheme_t scheme,
90 chunk_t crypto, chunk_t *plain)
91 {
92 return FALSE;
93 }
94
95 METHOD(private_key_t, get_keysize, int,
96 private_tkm_private_key_t *this)
97 {
98 return 0;
99 }
100
101 METHOD(private_key_t, get_public_key, public_key_t*,
102 private_tkm_private_key_t *this)
103 {
104 return NULL;
105 }
106
107 METHOD(private_key_t, get_encoding, bool,
108 private_tkm_private_key_t *this, cred_encoding_type_t type,
109 chunk_t *encoding)
110 {
111 return FALSE;
112 }
113
114 METHOD(private_key_t, get_fingerprint, bool,
115 private_tkm_private_key_t *this, cred_encoding_type_t type, chunk_t *fp)
116 {
117 *fp = this->id->get_encoding(this->id);
118 return TRUE;
119 }
120
121 METHOD(private_key_t, get_ref, private_key_t*,
122 private_tkm_private_key_t *this)
123 {
124 ref_get(&this->ref);
125 return &this->public.key;
126 }
127
128 METHOD(private_key_t, destroy, void,
129 private_tkm_private_key_t *this)
130 {
131 if (ref_put(&this->ref))
132 {
133 this->id->destroy(this->id);
134 free(this);
135 }
136 }
137
138 /**
139 * See header.
140 */
141 tkm_private_key_t *tkm_private_key_init(identification_t * const id)
142 {
143 private_tkm_private_key_t *this;
144
145 INIT(this,
146 .public = {
147 .key = {
148 .get_type = _get_type,
149 .sign = _sign,
150 .decrypt = _decrypt,
151 .get_keysize = _get_keysize,
152 .get_public_key = _get_public_key,
153 .equals = private_key_equals,
154 .belongs_to = private_key_belongs_to,
155 .get_fingerprint = _get_fingerprint,
156 .has_fingerprint = private_key_has_fingerprint,
157 .get_encoding = _get_encoding,
158 .get_ref = _get_ref,
159 .destroy = _destroy,
160 },
161 },
162 .ref = 1,
163 .id = id->clone(id),
164 );
165
166 /* get key type from associated public key */
167 certificate_t *cert;
168 cert = lib->credmgr->get_cert(lib->credmgr, CERT_ANY, KEY_ANY, id, FALSE);
169 if (!cert)
170 {
171 destroy(this);
172 return NULL;
173 }
174
175 public_key_t *pubkey = cert->get_public_key(cert);
176 if (!pubkey)
177 {
178 cert->destroy(cert);
179 destroy(this);
180 return NULL;
181 }
182 this->key_type = pubkey->get_type(pubkey);
183 pubkey->destroy(pubkey);
184 cert->destroy(cert);
185
186 return &this->public;
187 }