3 /* Id: prsa_par.y,v 1.3 2004/11/08 12:04:23 ludvigm Exp */
7 * Copyright (C) 2004 SuSE Linux AG, Nuernberg, Germany.
8 * Contributed by: Michal Ludvig <mludvig@suse.cz>, SUSE Labs
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright
17 * notice, this list of conditions and the following disclaimer in the
18 * documentation and/or other materials provided with the distribution.
19 * 3. Neither the name of the project nor the names of its contributors
20 * may be used to endorse or promote products derived from this software
21 * without specific prior written permission.
23 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
36 /* This file contains a parser for FreeS/WAN-style ipsec.secrets RSA keys. */
53 #include <netinet/in.h>
54 #include <sys/socket.h>
55 #include <arpa/inet.h>
56 #include <sys/types.h>
61 #include <openssl/bn.h>
62 #include <openssl/rsa.h>
68 #include "isakmp_var.h"
70 #include "crypto_openssl.h"
74 extern
void prsaerror
(const char *str
, ...
);
75 extern
int prsawrap
(void);
76 extern
int prsalex
(void);
78 extern
char *prsatext
;
79 extern
int prsa_cur_lineno
;
80 extern
char *prsa_cur_fname
;
83 int prsa_cur_lineno
= 0;
84 char *prsa_cur_fname
= NULL
;
85 struct genlist
*prsa_cur_list
= NULL
;
86 enum rsa_key_type prsa_cur_type
= RSA_TYPE_ANY
;
91 prsaerror
(const char *s
, ...
)
101 snprintf
(fmt
, sizeof
(fmt
), "%s:%d: %s",
102 prsa_cur_fname
, prsa_cur_lineno
, s
);
103 plogv
(LLV_ERROR
, LOCATION
, NULL
, fmt
, ap
);
108 prsawarning
(const char *s
, ...
)
118 snprintf
(fmt
, sizeof
(fmt
), "%s:%d: %s",
119 prsa_cur_fname
, prsa_cur_lineno
, s
);
120 plogv
(LLV_WARNING
, LOCATION
, NULL
, fmt
, ap
);
135 struct netaddr
*naddr
;
139 %token OBRACE EBRACE COLON HEX
140 %token TAG_RSA TAG_PUB TAG_PSK
141 %token MODULUS PUBLIC_EXPONENT PRIVATE_EXPONENT
142 %token PRIME1 PRIME2 EXPONENT1 EXPONENT2 COEFFICIENT
143 %token ADDR4 ADDR6 ADDRANY SLASH NUMBER BASE64
147 %type
<chr
> ADDR4 ADDR6 BASE64
149 %type
<rsa
> rsa_statement
151 %type
<naddr
> addr4 addr6 addr
160 addr addr COLON rsa_statement
162 rsa_key_insert
(prsa_cur_list
, $1, $2, $4);
164 | addr COLON rsa_statement
166 rsa_key_insert
(prsa_cur_list
, NULL
, $1, $3);
168 | COLON rsa_statement
170 rsa_key_insert
(prsa_cur_list
, NULL
, NULL
, $2);
175 TAG_RSA OBRACE params EBRACE
177 if
(prsa_cur_type
== RSA_TYPE_PUBLIC
) {
178 prsawarning
("Using private key for public key purpose.\n");
179 if
(!rsa_cur
->n ||
!rsa_cur
->e
) {
180 prsaerror
("Incomplete key. Mandatory parameters are missing!\n");
185 if
(!rsa_cur
->n ||
!rsa_cur
->e ||
!rsa_cur
->d
) {
186 prsaerror
("Incomplete key. Mandatory parameters are missing!\n");
189 if
(!rsa_cur
->p ||
!rsa_cur
->q ||
!rsa_cur
->dmp1
190 ||
!rsa_cur
->dmq1 ||
!rsa_cur
->iqmp
) {
191 if
(rsa_cur
->p
) BN_clear_free
(rsa_cur
->p
);
192 if
(rsa_cur
->q
) BN_clear_free
(rsa_cur
->q
);
193 if
(rsa_cur
->dmp1
) BN_clear_free
(rsa_cur
->dmp1
);
194 if
(rsa_cur
->dmq1
) BN_clear_free
(rsa_cur
->dmq1
);
195 if
(rsa_cur
->iqmp
) BN_clear_free
(rsa_cur
->iqmp
);
199 rsa_cur
->dmp1
= NULL
;
200 rsa_cur
->dmq1
= NULL
;
201 rsa_cur
->iqmp
= NULL
;
209 if
(prsa_cur_type
== RSA_TYPE_PRIVATE
) {
210 prsaerror
("Public key in private-key file!\n");
213 $$
= base64_pubkey2rsa
($2);
217 if
(prsa_cur_type
== RSA_TYPE_PRIVATE
) {
218 prsaerror
("Public key in private-key file!\n");
221 $$
= bignum_pubkey2rsa
($2);
238 struct sockaddr_in
*sap
;
240 if
($2 == -1) $2 = 32;
241 if
($2 < 0 ||
$2 > 32) {
242 prsaerror
("Invalid IPv4 prefix\n");
245 $$
= calloc
(sizeof
(struct netaddr
), 1);
247 sap
= (struct sockaddr_in
*)(&$$
->sa
);
248 sap
->sin_family
= AF_INET
;
249 err
= inet_pton
(AF_INET
, $1, (struct in_addr
*)(&sap
->sin_addr
));
251 prsaerror
("inet_pton(%s): %s\n", $1, strerror
(errno
));
261 struct sockaddr_in6
*sap
;
263 if
($2 == -1) $2 = 128;
264 if
($2 < 0 ||
$2 > 128) {
265 prsaerror
("Invalid IPv6 prefix\n");
268 $$
= calloc
(sizeof
(struct netaddr
), 1);
270 sap
= (struct sockaddr_in6
*)(&$$
->sa
);
271 sap
->sin6_family
= AF_INET6
;
272 err
= inet_pton
(AF_INET6
, $1, (struct in6_addr
*)(&sap
->sin6_addr
));
274 prsaerror
("inet_pton(%s): %s\n", $1, strerror
(errno
));
281 /* nothing */ { $$
= -1; }
282 | SLASH NUMBER
{ $$
= $2; }
291 { if
(!rsa_cur
->n
) rsa_cur
->n
= $3; else
{ prsaerror
("Modulus already defined\n"); YYABORT; } }
292 | PUBLIC_EXPONENT COLON HEX
293 { if
(!rsa_cur
->e
) rsa_cur
->e
= $3; else
{ prsaerror
("PublicExponent already defined\n"); YYABORT; } }
294 | PRIVATE_EXPONENT COLON HEX
295 { if
(!rsa_cur
->d
) rsa_cur
->d
= $3; else
{ prsaerror
("PrivateExponent already defined\n"); YYABORT; } }
297 { if
(!rsa_cur
->p
) rsa_cur
->p
= $3; else
{ prsaerror
("Prime1 already defined\n"); YYABORT; } }
299 { if
(!rsa_cur
->q
) rsa_cur
->q
= $3; else
{ prsaerror
("Prime2 already defined\n"); YYABORT; } }
300 | EXPONENT1 COLON HEX
301 { if
(!rsa_cur
->dmp1
) rsa_cur
->dmp1
= $3; else
{ prsaerror
("Exponent1 already defined\n"); YYABORT; } }
302 | EXPONENT2 COLON HEX
303 { if
(!rsa_cur
->dmq1
) rsa_cur
->dmq1
= $3; else
{ prsaerror
("Exponent2 already defined\n"); YYABORT; } }
304 | COEFFICIENT COLON HEX
305 { if
(!rsa_cur
->iqmp
) rsa_cur
->iqmp
= $3; else
{ prsaerror
("Coefficient already defined\n"); YYABORT; } }
312 prsa_parse_file
(struct genlist
*list
, char *fname
, enum rsa_key_type type
)
319 if
(type
== RSA_TYPE_PRIVATE
) {
321 if
(stat
(fname
, &st
) < 0)
323 if
(st.st_mode
& (S_IRWXG | S_IRWXO
)) {
324 plog
(LLV_ERROR
, LOCATION
, NULL
,
325 "Too slack permissions on private key '%s'\n",
327 plog
(LLV_ERROR
, LOCATION
, NULL
,
328 "Should be at most 0600, now is 0%o\n",
333 fp
= fopen
(fname
, "r");
338 prsa_cur_fname
= fname
;
339 prsa_cur_list
= list
;
340 prsa_cur_type
= type
;