aboutsummaryrefslogtreecommitdiffstats
path: root/src/libstrongswan
diff options
context:
space:
mode:
authorMartin Willi <martin@revosec.ch>2012-11-26 12:40:23 +0100
committerMartin Willi <martin@revosec.ch>2012-12-19 10:32:07 +0100
commit9de6a7a85cc64da9951d28b1cf7728ba93a3c97b (patch)
tree16930a063735d2292eb4efe73d5ad28b00b53592 /src/libstrongswan
parentbd20f040fd76832995b6ccffb96cde63baefcd44 (diff)
downloadstrongswan-9de6a7a85cc64da9951d28b1cf7728ba93a3c97b.tar.bz2
strongswan-9de6a7a85cc64da9951d28b1cf7728ba93a3c97b.tar.xz
Implement generic PKCS#7 contentInfo parsing
Diffstat (limited to 'src/libstrongswan')
-rw-r--r--src/libstrongswan/plugins/pkcs7/Makefile.am1
-rw-r--r--src/libstrongswan/plugins/pkcs7/pkcs7_generic.c111
-rw-r--r--src/libstrongswan/plugins/pkcs7/pkcs7_generic.h38
-rw-r--r--src/libstrongswan/plugins/pkcs7/pkcs7_plugin.c3
4 files changed, 153 insertions, 0 deletions
diff --git a/src/libstrongswan/plugins/pkcs7/Makefile.am b/src/libstrongswan/plugins/pkcs7/Makefile.am
index fce51e335..f133851df 100644
--- a/src/libstrongswan/plugins/pkcs7/Makefile.am
+++ b/src/libstrongswan/plugins/pkcs7/Makefile.am
@@ -10,6 +10,7 @@ plugin_LTLIBRARIES = libstrongswan-pkcs7.la
endif
libstrongswan_pkcs7_la_SOURCES = \
+ pkcs7_generic.h pkcs7_generic.c \
pkcs7_plugin.h pkcs7_plugin.c
libstrongswan_pkcs7_la_LDFLAGS = -module -avoid-version
diff --git a/src/libstrongswan/plugins/pkcs7/pkcs7_generic.c b/src/libstrongswan/plugins/pkcs7/pkcs7_generic.c
new file mode 100644
index 000000000..9e6bc3306
--- /dev/null
+++ b/src/libstrongswan/plugins/pkcs7/pkcs7_generic.c
@@ -0,0 +1,111 @@
+/*
+ * Copyright (C) 2012 Martin Willi
+ * Copyright (C) 2012 revosec AG
+ * Copyright (C) 2012 Tobias Brunner
+ * Copyright (C) 2002-2008 Andreas Steffen
+ * Copyright (C) 2005 Jan Hutter, Martin Willi
+ * Hochschule fuer Technik Rapperswil, Switzerland
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * for more details.
+ */
+
+#include "pkcs7_generic.h"
+
+#include <utils/debug.h>
+#include <asn1/oid.h>
+#include <asn1/asn1.h>
+#include <asn1/asn1_parser.h>
+
+/**
+ * ASN.1 definition of the PKCS#7 ContentInfo type
+ */
+static const asn1Object_t contentInfoObjects[] = {
+ { 0, "contentInfo", ASN1_SEQUENCE, ASN1_NONE }, /* 0 */
+ { 1, "contentType", ASN1_OID, ASN1_BODY }, /* 1 */
+ { 1, "content", ASN1_CONTEXT_C_0, ASN1_OPT |
+ ASN1_BODY }, /* 2 */
+ { 1, "end opt", ASN1_EOC, ASN1_END }, /* 3 */
+ { 0, "exit", ASN1_EOC, ASN1_EXIT }
+};
+#define PKCS7_INFO_TYPE 1
+#define PKCS7_INFO_CONTENT 2
+
+/**
+ * Parse PKCS#7 contentInfo object
+ */
+static pkcs7_t* parse_contentInfo(chunk_t blob)
+{
+ asn1_parser_t *parser;
+ chunk_t object, content = chunk_empty;
+ int objectID, type = OID_UNKNOWN;
+ bool success = FALSE;
+
+ parser = asn1_parser_create(contentInfoObjects, blob);
+ parser->set_top_level(parser, 0);
+
+ while (parser->iterate(parser, &objectID, &object))
+ {
+ if (objectID == PKCS7_INFO_TYPE)
+ {
+ type = asn1_known_oid(object);
+ if (type < OID_PKCS7_DATA || type > OID_PKCS7_ENCRYPTED_DATA)
+ {
+ DBG1(DBG_ASN, "unknown pkcs7 content type");
+ goto end;
+ }
+ }
+ else if (objectID == PKCS7_INFO_CONTENT)
+ {
+ content = object;
+ }
+ }
+ success = parser->success(parser);
+
+end:
+ parser->destroy(parser);
+
+ if (success)
+ {
+ switch (type)
+ {
+ default:
+ DBG1(DBG_ASN, "pkcs7 content type %d not supported", type);
+ return NULL;
+ }
+ }
+ return NULL;
+}
+
+
+pkcs7_t *pkcs7_generic_load(container_type_t type, va_list args)
+{
+ chunk_t blob = chunk_empty;
+
+ while (TRUE)
+ {
+ switch (va_arg(args, builder_part_t))
+ {
+ case BUILD_BLOB_ASN1_DER:
+ blob = va_arg(args, chunk_t);
+ continue;
+ case BUILD_END:
+ break;
+ default:
+ return NULL;
+ }
+ break;
+ }
+ if (blob.len)
+ {
+ return parse_contentInfo(blob);
+ }
+ return NULL;
+}
diff --git a/src/libstrongswan/plugins/pkcs7/pkcs7_generic.h b/src/libstrongswan/plugins/pkcs7/pkcs7_generic.h
new file mode 100644
index 000000000..8bdc62b36
--- /dev/null
+++ b/src/libstrongswan/plugins/pkcs7/pkcs7_generic.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2012 Martin Willi
+ * Copyright (C) 2012 revosec AG
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the
+ * Free Software Foundation; either version 2 of the License, or (at your
+ * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+ * for more details.
+ */
+
+/**
+ * @defgroup pkcs7_generic pkcs7_generic
+ * @{ @ingroup pkcs7
+ */
+
+#ifndef PKCS7_GENERIC_H_
+#define PKCS7_GENERIC_H_
+
+#include <credentials/builder.h>
+#include <credentials/containers/pkcs7.h>
+
+/**
+ * Load a generic PKCS#7 container.
+ *
+ * The argument list must contain a single BUILD_BLOB_ASN1_DER argument.
+ *
+ * @param type type of the container, CONTAINER_PKCS7
+ * @param args builder_part_t argument list
+ * @return container, NULL on failure
+ */
+pkcs7_t *pkcs7_generic_load(container_type_t type, va_list args);
+
+#endif /** PKCS7_GENERIC_H_ @}*/
diff --git a/src/libstrongswan/plugins/pkcs7/pkcs7_plugin.c b/src/libstrongswan/plugins/pkcs7/pkcs7_plugin.c
index 1615ede90..e4e5764cf 100644
--- a/src/libstrongswan/plugins/pkcs7/pkcs7_plugin.c
+++ b/src/libstrongswan/plugins/pkcs7/pkcs7_plugin.c
@@ -14,6 +14,7 @@
*/
#include "pkcs7_plugin.h"
+#include "pkcs7_generic.h"
#include <library.h>
@@ -40,6 +41,8 @@ METHOD(plugin_t, get_features, int,
private_pkcs7_plugin_t *this, plugin_feature_t *features[])
{
static plugin_feature_t f[] = {
+ PLUGIN_REGISTER(CONTAINER_DECODE, pkcs7_generic_load, TRUE),
+ PLUGIN_PROVIDE(CONTAINER_DECODE, CONTAINER_PKCS7),
};
*features = f;
return countof(f);