Return to pkcs7_generic.c CVS log | Up to [ELWIX - Embedded LightWeight unIX -] / embedaddon / strongswan / src / libstrongswan / plugins / pkcs7 |
1.1 misho 1: /* 2: * Copyright (C) 2012 Martin Willi 3: * Copyright (C) 2012 revosec AG 4: * Copyright (C) 2012 Tobias Brunner 5: * Copyright (C) 2002-2008 Andreas Steffen 6: * Copyright (C) 2005 Jan Hutter, Martin Willi 7: * HSR Hochschule fuer Technik Rapperswil 8: * 9: * This program is free software; you can redistribute it and/or modify it 10: * under the terms of the GNU General Public License as published by the 11: * Free Software Foundation; either version 2 of the License, or (at your 12: * option) any later version. See <http://www.fsf.org/copyleft/gpl.txt>. 13: * 14: * This program is distributed in the hope that it will be useful, but 15: * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 16: * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 17: * for more details. 18: */ 19: 20: #include "pkcs7_generic.h" 21: #include "pkcs7_data.h" 22: #include "pkcs7_signed_data.h" 23: #include "pkcs7_encrypted_data.h" 24: #include "pkcs7_enveloped_data.h" 25: 26: #include <utils/debug.h> 27: #include <asn1/oid.h> 28: #include <asn1/asn1.h> 29: #include <asn1/asn1_parser.h> 30: 31: /** 32: * ASN.1 definition of the PKCS#7 ContentInfo type 33: */ 34: static const asn1Object_t contentInfoObjects[] = { 35: { 0, "contentInfo", ASN1_SEQUENCE, ASN1_NONE }, /* 0 */ 36: { 1, "contentType", ASN1_OID, ASN1_BODY }, /* 1 */ 37: { 1, "content", ASN1_CONTEXT_C_0, ASN1_OPT | 38: ASN1_BODY }, /* 2 */ 39: { 1, "end opt", ASN1_EOC, ASN1_END }, /* 3 */ 40: { 0, "exit", ASN1_EOC, ASN1_EXIT } 41: }; 42: #define PKCS7_INFO_TYPE 1 43: #define PKCS7_INFO_CONTENT 2 44: 45: /** 46: * Parse PKCS#7 contentInfo object 47: */ 48: static pkcs7_t* parse_contentInfo(chunk_t blob) 49: { 50: asn1_parser_t *parser; 51: chunk_t object, content = chunk_empty; 52: int objectID, type = OID_UNKNOWN; 53: bool success = FALSE; 54: 55: parser = asn1_parser_create(contentInfoObjects, blob); 56: parser->set_top_level(parser, 0); 57: 58: while (parser->iterate(parser, &objectID, &object)) 59: { 60: if (objectID == PKCS7_INFO_TYPE) 61: { 62: type = asn1_known_oid(object); 63: if (type < OID_PKCS7_DATA || type > OID_PKCS7_ENCRYPTED_DATA) 64: { 65: DBG1(DBG_ASN, "unknown pkcs7 content type"); 66: goto end; 67: } 68: } 69: else if (objectID == PKCS7_INFO_CONTENT) 70: { 71: content = object; 72: } 73: } 74: success = parser->success(parser); 75: 76: end: 77: parser->destroy(parser); 78: 79: if (success) 80: { 81: switch (type) 82: { 83: case OID_PKCS7_DATA: 84: return pkcs7_data_load(blob, content); 85: case OID_PKCS7_SIGNED_DATA: 86: return pkcs7_signed_data_load(blob, content); 87: case OID_PKCS7_ENVELOPED_DATA: 88: return pkcs7_enveloped_data_load(blob, content); 89: case OID_PKCS7_ENCRYPTED_DATA: 90: return pkcs7_encrypted_data_load(blob, content); 91: default: 92: DBG1(DBG_ASN, "pkcs7 content type %d not supported", type); 93: return NULL; 94: } 95: } 96: return NULL; 97: } 98: 99: 100: pkcs7_t *pkcs7_generic_load(container_type_t type, va_list args) 101: { 102: chunk_t blob = chunk_empty; 103: 104: while (TRUE) 105: { 106: switch (va_arg(args, builder_part_t)) 107: { 108: case BUILD_BLOB_ASN1_DER: 109: blob = va_arg(args, chunk_t); 110: continue; 111: case BUILD_END: 112: break; 113: default: 114: return NULL; 115: } 116: break; 117: } 118: if (blob.len) 119: { 120: if (blob.len >= 2 && 121: blob.ptr[0] == ASN1_SEQUENCE && blob.ptr[1] == 0x80) 122: { /* looks like infinite length BER encoding, but we can't handle it. 123: * ignore silently, our openssl backend can handle it */ 124: return NULL; 125: } 126: return parse_contentInfo(blob); 127: } 128: return NULL; 129: }