Browse Source

[crypto] Add asynchronous certificate validator

To allow for automatic download of cross-signing certificates and for
OCSP, the validation of certificates must be an asynchronous process.
Create a stub validator which uses a job-control interface to report
the result of certificate validation.

Signed-off-by: Michael Brown <mcb30@ipxe.org>
tags/v1.20.1
Michael Brown 12 years ago
parent
commit
29dcb0631b
3 changed files with 196 additions and 0 deletions
  1. 1
    0
      src/include/ipxe/errfile.h
  2. 17
    0
      src/include/ipxe/validator.h
  3. 178
    0
      src/net/validator.c

+ 1
- 0
src/include/ipxe/errfile.h View File

@@ -258,6 +258,7 @@ FILE_LICENCE ( GPL2_OR_LATER );
258 258
 #define ERRFILE_imgtrust	      ( ERRFILE_OTHER | 0x002b0000 )
259 259
 #define ERRFILE_menu_ui		      ( ERRFILE_OTHER | 0x002c0000 )
260 260
 #define ERRFILE_menu_cmd	      ( ERRFILE_OTHER | 0x002d0000 )
261
+#define ERRFILE_validator	      ( ERRFILE_OTHER | 0x002e0000 )
261 262
 
262 263
 /** @} */
263 264
 

+ 17
- 0
src/include/ipxe/validator.h View File

@@ -0,0 +1,17 @@
1
+#ifndef _IPXE_VALIDATOR_H
2
+#define _IPXE_VALIDATOR_H
3
+
4
+/** @file
5
+ *
6
+ * Certificate validator
7
+ *
8
+ */
9
+
10
+FILE_LICENCE ( GPL2_OR_LATER );
11
+
12
+#include <ipxe/interface.h>
13
+#include <ipxe/x509.h>
14
+
15
+extern int create_validator ( struct interface *job, struct x509_chain *chain );
16
+
17
+#endif /* _IPXE_VALIDATOR_H */

+ 178
- 0
src/net/validator.c View File

@@ -0,0 +1,178 @@
1
+/*
2
+ * Copyright (C) 2012 Michael Brown <mbrown@fensystems.co.uk>.
3
+ *
4
+ * This program is free software; you can redistribute it and/or
5
+ * modify it under the terms of the GNU General Public License as
6
+ * published by the Free Software Foundation; either version 2 of the
7
+ * License, or (at your option) any later version.
8
+ *
9
+ * This program is distributed in the hope that it will be useful, but
10
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12
+ * General Public License for more details.
13
+ *
14
+ * You should have received a copy of the GNU General Public License
15
+ * along with this program; if not, write to the Free Software
16
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17
+ * 02110-1301, USA.
18
+ */
19
+
20
+FILE_LICENCE ( GPL2_OR_LATER );
21
+
22
+#include <string.h>
23
+#include <errno.h>
24
+#include <ipxe/refcnt.h>
25
+#include <ipxe/malloc.h>
26
+#include <ipxe/interface.h>
27
+#include <ipxe/process.h>
28
+#include <ipxe/x509.h>
29
+#include <ipxe/validator.h>
30
+
31
+/** @file
32
+ *
33
+ * Certificate validator
34
+ *
35
+ */
36
+
37
+/** A certificate validator */
38
+struct validator {
39
+	/** Reference count */
40
+	struct refcnt refcnt;
41
+	/** Job control interface */
42
+	struct interface job;
43
+	/** Process */
44
+	struct process process;
45
+	/** X.509 certificate chain */
46
+	struct x509_chain *chain;
47
+};
48
+
49
+/**
50
+ * Free certificate validator
51
+ *
52
+ * @v refcnt		Reference count
53
+ */
54
+static void validator_free ( struct refcnt *refcnt ) {
55
+	struct validator *validator =
56
+		container_of ( refcnt, struct validator, refcnt );
57
+
58
+	DBGC ( validator, "VALIDATOR %p freed\n", validator );
59
+	x509_chain_put ( validator->chain );
60
+	free ( validator );
61
+}
62
+
63
+/**
64
+ * Mark certificate validation as finished
65
+ *
66
+ * @v validator		Certificate validator
67
+ * @v rc		Reason for finishing
68
+ */
69
+static void validator_finished ( struct validator *validator, int rc ) {
70
+
71
+	/* Remove process */
72
+	process_del ( &validator->process );
73
+
74
+	/* Close all interfaces */
75
+	intf_shutdown ( &validator->job, rc );
76
+}
77
+
78
+/****************************************************************************
79
+ *
80
+ * Job control interface
81
+ *
82
+ */
83
+
84
+/** Certificate validator job control interface operations */
85
+static struct interface_operation validator_job_operations[] = {
86
+	INTF_OP ( intf_close, struct validator *, validator_finished ),
87
+};
88
+
89
+/** Certificate validator job control interface descriptor */
90
+static struct interface_descriptor validator_job_desc =
91
+	INTF_DESC ( struct validator, job, validator_job_operations );
92
+
93
+/****************************************************************************
94
+ *
95
+ * Validation process
96
+ *
97
+ */
98
+
99
+/**
100
+ * Certificate validation process
101
+ *
102
+ * @v validator		Certificate validator
103
+ */
104
+static void validator_step ( struct validator *validator ) {
105
+	time_t now;
106
+	int rc;
107
+
108
+	/* Attempt to validate certificate chain */
109
+	now = time ( NULL );
110
+	if ( ( rc = x509_validate_chain ( validator->chain, now,
111
+					  NULL ) ) != 0 ) {
112
+		DBGC ( validator, "VALIDATOR %p could not validate chain: %s\n",
113
+		       validator, strerror ( rc ) );
114
+		goto err_validate;
115
+	}
116
+
117
+	/* Mark validation as complete */
118
+	validator_finished ( validator, 0 );
119
+
120
+	return;
121
+
122
+ err_validate:
123
+	validator_finished ( validator, rc );
124
+}
125
+
126
+/** Certificate validator process descriptor */
127
+static struct process_descriptor validator_process_desc =
128
+	PROC_DESC_ONCE ( struct validator, process, validator_step );
129
+
130
+/****************************************************************************
131
+ *
132
+ * Instantiator
133
+ *
134
+ */
135
+
136
+/**
137
+ * Instantiate a certificate validator
138
+ *
139
+ * @v job		Job control interface
140
+ * @v chain		X.509 certificate chain
141
+ * @ret rc		Return status code
142
+ */
143
+int create_validator ( struct interface *job, struct x509_chain *chain ) {
144
+	struct validator *validator;
145
+	int rc;
146
+
147
+	/* Sanity check */
148
+	if ( ! chain ) {
149
+		rc = -EINVAL;
150
+		goto err_sanity;
151
+	}
152
+
153
+	/* Allocate and initialise structure */
154
+	validator = zalloc ( sizeof ( *validator ) );
155
+	if ( ! validator ) {
156
+		rc = -ENOMEM;
157
+		goto err_alloc;
158
+	}
159
+	ref_init ( &validator->refcnt, validator_free );
160
+	intf_init ( &validator->job, &validator_job_desc,
161
+		    &validator->refcnt );
162
+	process_init ( &validator->process, &validator_process_desc,
163
+		       &validator->refcnt );
164
+	validator->chain = x509_chain_get ( chain );
165
+
166
+	/* Attach parent interface, mortalise self, and return */
167
+	intf_plug_plug ( &validator->job, job );
168
+	ref_put ( &validator->refcnt );
169
+	DBGC ( validator, "VALIDATOR %p validating X509 chain %p\n",
170
+	       validator, validator->chain );
171
+	return 0;
172
+
173
+	validator_finished ( validator, rc );
174
+	ref_put ( &validator->refcnt );
175
+ err_alloc:
176
+ err_sanity:
177
+	return rc;
178
+}

Loading…
Cancel
Save