Added add_segment() method to TCG/SEG attributes
[strongswan.git] / src / libimcv / imcv.c
1 /*
2 * Copyright (C) 2011 Andreas Steffen, HSR Hochschule fuer Technik Rapperswil
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms of the GNU General Public License as published by the
6 * Free Software Foundation; either version 2 of the License, or (at your
7 * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
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 MERCHANTABILITY
11 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * for more details.
13 */
14
15 #include "imcv.h"
16 #include "ietf/ietf_attr.h"
17 #include "ita/ita_attr.h"
18 #include "tcg/tcg_attr.h"
19 #include "pts/components/pts_component.h"
20 #include "pts/components/pts_component_manager.h"
21 #include "pts/components/tcg/tcg_comp_func_name.h"
22 #include "pts/components/ita/ita_comp_func_name.h"
23 #include "pts/components/ita/ita_comp_ima.h"
24 #include "pts/components/ita/ita_comp_tboot.h"
25 #include "pts/components/ita/ita_comp_tgrub.h"
26
27 #include <utils/debug.h>
28 #include <utils/utils.h>
29 #include <pen/pen.h>
30
31 #ifdef HAVE_SYSLOG
32 #include <syslog.h>
33 #endif
34
35 #define IMCV_DEBUG_LEVEL 1
36 #define IMCV_DEFAULT_POLICY_SCRIPT "ipsec _imv_policy"
37
38
39 /**
40 * PA-TNC attribute manager
41 */
42 pa_tnc_attr_manager_t *imcv_pa_tnc_attributes;
43
44 /**
45 * Global list of IMV sessions
46 */
47 imv_session_manager_t *imcv_sessions;
48
49 /**
50 * Global IMV database
51 */
52 imv_database_t *imcv_db;
53
54 /**
55 * PTS Functional Component manager
56 */
57 pts_component_manager_t *imcv_pts_components;
58
59 /**
60 * Reference count for libimcv
61 */
62 static refcount_t libimcv_ref = 0;
63
64 /**
65 * Reference count for libstrongswan
66 */
67 static refcount_t libstrongswan_ref = 0;
68
69 /**
70 * Global configuration of imcv dbg function
71 */
72 static int imcv_debug_level;
73 static bool imcv_stderr_quiet;
74
75 /**
76 * imvc dbg function
77 */
78 static void imcv_dbg(debug_t group, level_t level, char *fmt, ...)
79 {
80 va_list args;
81
82 if (level <= imcv_debug_level)
83 {
84 if (!imcv_stderr_quiet)
85 {
86 va_start(args, fmt);
87 fprintf(stderr, "[HSR] ");
88 vfprintf(stderr, fmt, args);
89 fprintf(stderr, "\n");
90 va_end(args);
91 }
92
93 #ifdef HAVE_SYSLOG
94 {
95 int priority = LOG_INFO;
96 char buffer[8192];
97 char *current = buffer, *next;
98
99 /* write in memory buffer first */
100 va_start(args, fmt);
101 vsnprintf(buffer, sizeof(buffer), fmt, args);
102 va_end(args);
103
104 /* do a syslog with every line */
105 while (current)
106 {
107 next = strchr(current, '\n');
108 if (next)
109 {
110 *(next++) = '\0';
111 }
112 syslog(priority, "[HSR] %s\n", current);
113 current = next;
114 }
115 }
116 #endif /* HAVE_SYSLOG */
117 }
118 }
119
120 /**
121 * Described in header.
122 */
123 bool libimcv_init(bool is_imv)
124 {
125 /* initialize libstrongswan library only once */
126 if (lib)
127 {
128 /* did main program initialize libstrongswan? */
129 if (libstrongswan_ref == 0)
130 {
131 ref_get(&libstrongswan_ref);
132 }
133 }
134 else
135 {
136 /* we are the first to initialize libstrongswan */
137 if (!library_init(NULL, "libimcv"))
138 {
139 return FALSE;
140 }
141
142 /* set the debug level and stderr output */
143 imcv_debug_level = lib->settings->get_int(lib->settings,
144 "libimcv.debug_level", IMCV_DEBUG_LEVEL);
145 imcv_stderr_quiet = lib->settings->get_int(lib->settings,
146 "libimcv.stderr_quiet", FALSE);
147
148 /* activate the imcv debugging hook */
149 dbg = imcv_dbg;
150 #ifdef HAVE_SYSLOG
151 openlog("imcv", 0, LOG_DAEMON);
152 #endif
153
154 if (!lib->plugins->load(lib->plugins,
155 lib->settings->get_str(lib->settings, "libimcv.load",
156 "random nonce gmp pubkey x509")))
157 {
158 library_deinit();
159 return FALSE;
160 }
161 }
162 ref_get(&libstrongswan_ref);
163
164 lib->settings->add_fallback(lib->settings, "%s.imcv", "libimcv", lib->ns);
165 lib->settings->add_fallback(lib->settings, "%s.plugins", "libimcv.plugins",
166 lib->ns);
167
168 if (libimcv_ref == 0)
169 {
170 char *uri, *script;
171
172 /* initialize the PA-TNC attribute manager */
173 imcv_pa_tnc_attributes = pa_tnc_attr_manager_create();
174 imcv_pa_tnc_attributes->add_vendor(imcv_pa_tnc_attributes, PEN_IETF,
175 ietf_attr_create_from_data, ietf_attr_names);
176 imcv_pa_tnc_attributes->add_vendor(imcv_pa_tnc_attributes, PEN_ITA,
177 ita_attr_create_from_data, ita_attr_names);
178 imcv_pa_tnc_attributes->add_vendor(imcv_pa_tnc_attributes, PEN_TCG,
179 tcg_attr_create_from_data, tcg_attr_names);
180
181 imcv_pts_components = pts_component_manager_create();
182 imcv_pts_components->add_vendor(imcv_pts_components, PEN_TCG,
183 pts_tcg_comp_func_names, PTS_TCG_QUALIFIER_TYPE_SIZE,
184 pts_tcg_qualifier_flag_names, pts_tcg_qualifier_type_names);
185 imcv_pts_components->add_vendor(imcv_pts_components, PEN_ITA,
186 pts_ita_comp_func_names, PTS_ITA_QUALIFIER_TYPE_SIZE,
187 pts_ita_qualifier_flag_names, pts_ita_qualifier_type_names);
188
189 imcv_pts_components->add_component(imcv_pts_components, PEN_ITA,
190 PTS_ITA_COMP_FUNC_NAME_TGRUB,
191 pts_ita_comp_tgrub_create);
192 imcv_pts_components->add_component(imcv_pts_components, PEN_ITA,
193 PTS_ITA_COMP_FUNC_NAME_TBOOT,
194 pts_ita_comp_tboot_create);
195 imcv_pts_components->add_component(imcv_pts_components, PEN_ITA,
196 PTS_ITA_COMP_FUNC_NAME_IMA,
197 pts_ita_comp_ima_create);
198 if (is_imv)
199 {
200 /* instantiate global IMV session manager */
201 imcv_sessions = imv_session_manager_create();
202
203 /* instantiate and attach global IMV database if URI is valid */
204 uri = lib->settings->get_str(lib->settings,
205 "%s.imcv.database", NULL, lib->ns);
206 script = lib->settings->get_str(lib->settings,
207 "%s.imcv.policy_script", IMCV_DEFAULT_POLICY_SCRIPT,
208 lib->ns);
209 if (uri)
210 {
211 imcv_db = imv_database_create(uri, script);
212 }
213 }
214 DBG1(DBG_LIB, "libimcv initialized");
215 }
216 ref_get(&libimcv_ref);
217
218 return TRUE;
219 }
220
221 /**
222 * Described in header.
223 */
224 void libimcv_deinit(void)
225 {
226 if (ref_put(&libimcv_ref))
227 {
228 imcv_pts_components->remove_vendor(imcv_pts_components, PEN_TCG);
229 imcv_pts_components->remove_vendor(imcv_pts_components, PEN_ITA);
230 imcv_pts_components->destroy(imcv_pts_components);
231
232 imcv_pa_tnc_attributes->remove_vendor(imcv_pa_tnc_attributes, PEN_IETF);
233 imcv_pa_tnc_attributes->remove_vendor(imcv_pa_tnc_attributes, PEN_ITA);
234 imcv_pa_tnc_attributes->remove_vendor(imcv_pa_tnc_attributes, PEN_TCG);
235 DESTROY_IF(imcv_pa_tnc_attributes);
236 imcv_pa_tnc_attributes = NULL;
237 DESTROY_IF(imcv_db);
238 DESTROY_IF(imcv_sessions);
239 DBG1(DBG_LIB, "libimcv terminated");
240 }
241 if (ref_put(&libstrongswan_ref))
242 {
243 library_deinit();
244 }
245 }