2607 lines
134 KiB
C++
2607 lines
134 KiB
C++
// Copyright (c) 2014, Google Inc.
|
|
// SPDX-License-Identifier: ISC
|
|
|
|
#include <gtest/gtest.h>
|
|
|
|
#include <openssl/bytestring.h>
|
|
#include <openssl/crypto.h>
|
|
#include <openssl/mem.h>
|
|
#include <openssl/pem.h>
|
|
#include <openssl/pkcs7.h>
|
|
#include <openssl/stack.h>
|
|
#include <openssl/x509.h>
|
|
|
|
#include "../bytestring/internal.h"
|
|
#include "../internal.h"
|
|
#include "../test/test_util.h"
|
|
#include "internal.h"
|
|
|
|
std::string GetTestData(const char *path);
|
|
|
|
// kPKCS7NSS contains the certificate chain of mail.google.com, as saved by NSS
|
|
// using the Chrome UI.
|
|
static const uint8_t kPKCS7NSS[] = {
|
|
0x30, 0x80, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07,
|
|
0x02, 0xa0, 0x80, 0x30, 0x80, 0x02, 0x01, 0x01, 0x31, 0x00, 0x30, 0x80,
|
|
0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01, 0x00,
|
|
0x00, 0xa0, 0x82, 0x0b, 0x1e, 0x30, 0x82, 0x03, 0x54, 0x30, 0x82, 0x02,
|
|
0x3c, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x03, 0x02, 0x34, 0x56, 0x30,
|
|
0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05,
|
|
0x05, 0x00, 0x30, 0x42, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04,
|
|
0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x16, 0x30, 0x14, 0x06, 0x03, 0x55,
|
|
0x04, 0x0a, 0x13, 0x0d, 0x47, 0x65, 0x6f, 0x54, 0x72, 0x75, 0x73, 0x74,
|
|
0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x1b, 0x30, 0x19, 0x06, 0x03, 0x55,
|
|
0x04, 0x03, 0x13, 0x12, 0x47, 0x65, 0x6f, 0x54, 0x72, 0x75, 0x73, 0x74,
|
|
0x20, 0x47, 0x6c, 0x6f, 0x62, 0x61, 0x6c, 0x20, 0x43, 0x41, 0x30, 0x1e,
|
|
0x17, 0x0d, 0x30, 0x32, 0x30, 0x35, 0x32, 0x31, 0x30, 0x34, 0x30, 0x30,
|
|
0x30, 0x30, 0x5a, 0x17, 0x0d, 0x32, 0x32, 0x30, 0x35, 0x32, 0x31, 0x30,
|
|
0x34, 0x30, 0x30, 0x30, 0x30, 0x5a, 0x30, 0x42, 0x31, 0x0b, 0x30, 0x09,
|
|
0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x16, 0x30,
|
|
0x14, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13, 0x0d, 0x47, 0x65, 0x6f, 0x54,
|
|
0x72, 0x75, 0x73, 0x74, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x1b, 0x30,
|
|
0x19, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x12, 0x47, 0x65, 0x6f, 0x54,
|
|
0x72, 0x75, 0x73, 0x74, 0x20, 0x47, 0x6c, 0x6f, 0x62, 0x61, 0x6c, 0x20,
|
|
0x43, 0x41, 0x30, 0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86,
|
|
0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x01,
|
|
0x0f, 0x00, 0x30, 0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00, 0xda,
|
|
0xcc, 0x18, 0x63, 0x30, 0xfd, 0xf4, 0x17, 0x23, 0x1a, 0x56, 0x7e, 0x5b,
|
|
0xdf, 0x3c, 0x6c, 0x38, 0xe4, 0x71, 0xb7, 0x78, 0x91, 0xd4, 0xbc, 0xa1,
|
|
0xd8, 0x4c, 0xf8, 0xa8, 0x43, 0xb6, 0x03, 0xe9, 0x4d, 0x21, 0x07, 0x08,
|
|
0x88, 0xda, 0x58, 0x2f, 0x66, 0x39, 0x29, 0xbd, 0x05, 0x78, 0x8b, 0x9d,
|
|
0x38, 0xe8, 0x05, 0xb7, 0x6a, 0x7e, 0x71, 0xa4, 0xe6, 0xc4, 0x60, 0xa6,
|
|
0xb0, 0xef, 0x80, 0xe4, 0x89, 0x28, 0x0f, 0x9e, 0x25, 0xd6, 0xed, 0x83,
|
|
0xf3, 0xad, 0xa6, 0x91, 0xc7, 0x98, 0xc9, 0x42, 0x18, 0x35, 0x14, 0x9d,
|
|
0xad, 0x98, 0x46, 0x92, 0x2e, 0x4f, 0xca, 0xf1, 0x87, 0x43, 0xc1, 0x16,
|
|
0x95, 0x57, 0x2d, 0x50, 0xef, 0x89, 0x2d, 0x80, 0x7a, 0x57, 0xad, 0xf2,
|
|
0xee, 0x5f, 0x6b, 0xd2, 0x00, 0x8d, 0xb9, 0x14, 0xf8, 0x14, 0x15, 0x35,
|
|
0xd9, 0xc0, 0x46, 0xa3, 0x7b, 0x72, 0xc8, 0x91, 0xbf, 0xc9, 0x55, 0x2b,
|
|
0xcd, 0xd0, 0x97, 0x3e, 0x9c, 0x26, 0x64, 0xcc, 0xdf, 0xce, 0x83, 0x19,
|
|
0x71, 0xca, 0x4e, 0xe6, 0xd4, 0xd5, 0x7b, 0xa9, 0x19, 0xcd, 0x55, 0xde,
|
|
0xc8, 0xec, 0xd2, 0x5e, 0x38, 0x53, 0xe5, 0x5c, 0x4f, 0x8c, 0x2d, 0xfe,
|
|
0x50, 0x23, 0x36, 0xfc, 0x66, 0xe6, 0xcb, 0x8e, 0xa4, 0x39, 0x19, 0x00,
|
|
0xb7, 0x95, 0x02, 0x39, 0x91, 0x0b, 0x0e, 0xfe, 0x38, 0x2e, 0xd1, 0x1d,
|
|
0x05, 0x9a, 0xf6, 0x4d, 0x3e, 0x6f, 0x0f, 0x07, 0x1d, 0xaf, 0x2c, 0x1e,
|
|
0x8f, 0x60, 0x39, 0xe2, 0xfa, 0x36, 0x53, 0x13, 0x39, 0xd4, 0x5e, 0x26,
|
|
0x2b, 0xdb, 0x3d, 0xa8, 0x14, 0xbd, 0x32, 0xeb, 0x18, 0x03, 0x28, 0x52,
|
|
0x04, 0x71, 0xe5, 0xab, 0x33, 0x3d, 0xe1, 0x38, 0xbb, 0x07, 0x36, 0x84,
|
|
0x62, 0x9c, 0x79, 0xea, 0x16, 0x30, 0xf4, 0x5f, 0xc0, 0x2b, 0xe8, 0x71,
|
|
0x6b, 0xe4, 0xf9, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x53, 0x30, 0x51,
|
|
0x30, 0x0f, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x01, 0x01, 0xff, 0x04, 0x05,
|
|
0x30, 0x03, 0x01, 0x01, 0xff, 0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x0e,
|
|
0x04, 0x16, 0x04, 0x14, 0xc0, 0x7a, 0x98, 0x68, 0x8d, 0x89, 0xfb, 0xab,
|
|
0x05, 0x64, 0x0c, 0x11, 0x7d, 0xaa, 0x7d, 0x65, 0xb8, 0xca, 0xcc, 0x4e,
|
|
0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80,
|
|
0x14, 0xc0, 0x7a, 0x98, 0x68, 0x8d, 0x89, 0xfb, 0xab, 0x05, 0x64, 0x0c,
|
|
0x11, 0x7d, 0xaa, 0x7d, 0x65, 0xb8, 0xca, 0xcc, 0x4e, 0x30, 0x0d, 0x06,
|
|
0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00,
|
|
0x03, 0x82, 0x01, 0x01, 0x00, 0x35, 0xe3, 0x29, 0x6a, 0xe5, 0x2f, 0x5d,
|
|
0x54, 0x8e, 0x29, 0x50, 0x94, 0x9f, 0x99, 0x1a, 0x14, 0xe4, 0x8f, 0x78,
|
|
0x2a, 0x62, 0x94, 0xa2, 0x27, 0x67, 0x9e, 0xd0, 0xcf, 0x1a, 0x5e, 0x47,
|
|
0xe9, 0xc1, 0xb2, 0xa4, 0xcf, 0xdd, 0x41, 0x1a, 0x05, 0x4e, 0x9b, 0x4b,
|
|
0xee, 0x4a, 0x6f, 0x55, 0x52, 0xb3, 0x24, 0xa1, 0x37, 0x0a, 0xeb, 0x64,
|
|
0x76, 0x2a, 0x2e, 0x2c, 0xf3, 0xfd, 0x3b, 0x75, 0x90, 0xbf, 0xfa, 0x71,
|
|
0xd8, 0xc7, 0x3d, 0x37, 0xd2, 0xb5, 0x05, 0x95, 0x62, 0xb9, 0xa6, 0xde,
|
|
0x89, 0x3d, 0x36, 0x7b, 0x38, 0x77, 0x48, 0x97, 0xac, 0xa6, 0x20, 0x8f,
|
|
0x2e, 0xa6, 0xc9, 0x0c, 0xc2, 0xb2, 0x99, 0x45, 0x00, 0xc7, 0xce, 0x11,
|
|
0x51, 0x22, 0x22, 0xe0, 0xa5, 0xea, 0xb6, 0x15, 0x48, 0x09, 0x64, 0xea,
|
|
0x5e, 0x4f, 0x74, 0xf7, 0x05, 0x3e, 0xc7, 0x8a, 0x52, 0x0c, 0xdb, 0x15,
|
|
0xb4, 0xbd, 0x6d, 0x9b, 0xe5, 0xc6, 0xb1, 0x54, 0x68, 0xa9, 0xe3, 0x69,
|
|
0x90, 0xb6, 0x9a, 0xa5, 0x0f, 0xb8, 0xb9, 0x3f, 0x20, 0x7d, 0xae, 0x4a,
|
|
0xb5, 0xb8, 0x9c, 0xe4, 0x1d, 0xb6, 0xab, 0xe6, 0x94, 0xa5, 0xc1, 0xc7,
|
|
0x83, 0xad, 0xdb, 0xf5, 0x27, 0x87, 0x0e, 0x04, 0x6c, 0xd5, 0xff, 0xdd,
|
|
0xa0, 0x5d, 0xed, 0x87, 0x52, 0xb7, 0x2b, 0x15, 0x02, 0xae, 0x39, 0xa6,
|
|
0x6a, 0x74, 0xe9, 0xda, 0xc4, 0xe7, 0xbc, 0x4d, 0x34, 0x1e, 0xa9, 0x5c,
|
|
0x4d, 0x33, 0x5f, 0x92, 0x09, 0x2f, 0x88, 0x66, 0x5d, 0x77, 0x97, 0xc7,
|
|
0x1d, 0x76, 0x13, 0xa9, 0xd5, 0xe5, 0xf1, 0x16, 0x09, 0x11, 0x35, 0xd5,
|
|
0xac, 0xdb, 0x24, 0x71, 0x70, 0x2c, 0x98, 0x56, 0x0b, 0xd9, 0x17, 0xb4,
|
|
0xd1, 0xe3, 0x51, 0x2b, 0x5e, 0x75, 0xe8, 0xd5, 0xd0, 0xdc, 0x4f, 0x34,
|
|
0xed, 0xc2, 0x05, 0x66, 0x80, 0xa1, 0xcb, 0xe6, 0x33, 0x30, 0x82, 0x03,
|
|
0xba, 0x30, 0x82, 0x02, 0xa2, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x08,
|
|
0x3e, 0xa3, 0xe4, 0x78, 0x99, 0x38, 0x13, 0x9d, 0x30, 0x0d, 0x06, 0x09,
|
|
0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00, 0x30,
|
|
0x49, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02,
|
|
0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13,
|
|
0x0a, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x20, 0x49, 0x6e, 0x63, 0x31,
|
|
0x25, 0x30, 0x23, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x1c, 0x47, 0x6f,
|
|
0x6f, 0x67, 0x6c, 0x65, 0x20, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65,
|
|
0x74, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x20,
|
|
0x47, 0x32, 0x30, 0x1e, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x37, 0x31, 0x36,
|
|
0x31, 0x32, 0x32, 0x31, 0x34, 0x30, 0x5a, 0x17, 0x0d, 0x31, 0x34, 0x31,
|
|
0x30, 0x31, 0x34, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x5a, 0x30, 0x69,
|
|
0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55,
|
|
0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a,
|
|
0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16,
|
|
0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x0c, 0x0d, 0x4d, 0x6f, 0x75,
|
|
0x6e, 0x74, 0x61, 0x69, 0x6e, 0x20, 0x56, 0x69, 0x65, 0x77, 0x31, 0x13,
|
|
0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x0c, 0x0a, 0x47, 0x6f, 0x6f,
|
|
0x67, 0x6c, 0x65, 0x20, 0x49, 0x6e, 0x63, 0x31, 0x18, 0x30, 0x16, 0x06,
|
|
0x03, 0x55, 0x04, 0x03, 0x0c, 0x0f, 0x6d, 0x61, 0x69, 0x6c, 0x2e, 0x67,
|
|
0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x30, 0x59, 0x30,
|
|
0x13, 0x06, 0x07, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02, 0x01, 0x06, 0x08,
|
|
0x2a, 0x86, 0x48, 0xce, 0x3d, 0x03, 0x01, 0x07, 0x03, 0x42, 0x00, 0x04,
|
|
0xb2, 0x68, 0x6e, 0x3f, 0x03, 0x9e, 0x43, 0x85, 0x16, 0xb7, 0x89, 0x0b,
|
|
0x16, 0x2a, 0xbe, 0x26, 0x36, 0xdd, 0x68, 0x0a, 0x53, 0x4e, 0x20, 0x40,
|
|
0xf8, 0xd1, 0xdd, 0x63, 0xcb, 0x46, 0x73, 0x09, 0x96, 0x36, 0xde, 0x2c,
|
|
0x45, 0x71, 0x2e, 0x8a, 0x79, 0xeb, 0x40, 0x2f, 0x65, 0x83, 0x81, 0xdb,
|
|
0x37, 0x03, 0x84, 0xa1, 0x9a, 0xd0, 0x22, 0x3b, 0x73, 0x38, 0x45, 0xd3,
|
|
0xd5, 0x91, 0xb2, 0x52, 0xa3, 0x82, 0x01, 0x4f, 0x30, 0x82, 0x01, 0x4b,
|
|
0x30, 0x1d, 0x06, 0x03, 0x55, 0x1d, 0x25, 0x04, 0x16, 0x30, 0x14, 0x06,
|
|
0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01, 0x06, 0x08, 0x2b,
|
|
0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x02, 0x30, 0x1a, 0x06, 0x03, 0x55,
|
|
0x1d, 0x11, 0x04, 0x13, 0x30, 0x11, 0x82, 0x0f, 0x6d, 0x61, 0x69, 0x6c,
|
|
0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x30,
|
|
0x0b, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x04, 0x04, 0x03, 0x02, 0x07, 0x80,
|
|
0x30, 0x68, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01,
|
|
0x04, 0x5c, 0x30, 0x5a, 0x30, 0x2b, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05,
|
|
0x05, 0x07, 0x30, 0x02, 0x86, 0x1f, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f,
|
|
0x2f, 0x70, 0x6b, 0x69, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e,
|
|
0x63, 0x6f, 0x6d, 0x2f, 0x47, 0x49, 0x41, 0x47, 0x32, 0x2e, 0x63, 0x72,
|
|
0x74, 0x30, 0x2b, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x30,
|
|
0x01, 0x86, 0x1f, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x63, 0x6c,
|
|
0x69, 0x65, 0x6e, 0x74, 0x73, 0x31, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c,
|
|
0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x6f, 0x63, 0x73, 0x70, 0x30, 0x1d,
|
|
0x06, 0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x75, 0xc6, 0xb0,
|
|
0x4a, 0x46, 0x61, 0x83, 0xff, 0x91, 0x46, 0x45, 0x35, 0xa7, 0x0f, 0xd0,
|
|
0x5b, 0xe9, 0xdd, 0x94, 0x1b, 0x30, 0x0c, 0x06, 0x03, 0x55, 0x1d, 0x13,
|
|
0x01, 0x01, 0xff, 0x04, 0x02, 0x30, 0x00, 0x30, 0x1f, 0x06, 0x03, 0x55,
|
|
0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14, 0x4a, 0xdd, 0x06, 0x16,
|
|
0x1b, 0xbc, 0xf6, 0x68, 0xb5, 0x76, 0xf5, 0x81, 0xb6, 0xbb, 0x62, 0x1a,
|
|
0xba, 0x5a, 0x81, 0x2f, 0x30, 0x17, 0x06, 0x03, 0x55, 0x1d, 0x20, 0x04,
|
|
0x10, 0x30, 0x0e, 0x30, 0x0c, 0x06, 0x0a, 0x2b, 0x06, 0x01, 0x04, 0x01,
|
|
0xd6, 0x79, 0x02, 0x05, 0x01, 0x30, 0x30, 0x06, 0x03, 0x55, 0x1d, 0x1f,
|
|
0x04, 0x29, 0x30, 0x27, 0x30, 0x25, 0xa0, 0x23, 0xa0, 0x21, 0x86, 0x1f,
|
|
0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x70, 0x6b, 0x69, 0x2e, 0x67,
|
|
0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x47, 0x49,
|
|
0x41, 0x47, 0x32, 0x2e, 0x63, 0x72, 0x6c, 0x30, 0x0d, 0x06, 0x09, 0x2a,
|
|
0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00, 0x03, 0x82,
|
|
0x01, 0x01, 0x00, 0x7f, 0x41, 0xf5, 0x57, 0x18, 0x3c, 0x75, 0xf5, 0x23,
|
|
0x66, 0xc3, 0xf0, 0xf2, 0x3e, 0x70, 0x34, 0x56, 0xca, 0x78, 0xec, 0xc7,
|
|
0x81, 0x58, 0x0d, 0xdf, 0xf0, 0xfd, 0x86, 0xe6, 0xe6, 0x50, 0x3d, 0xf6,
|
|
0x09, 0x9a, 0x4d, 0xca, 0x60, 0x37, 0x9a, 0xd4, 0xca, 0x51, 0x7c, 0xf0,
|
|
0x66, 0x23, 0xea, 0x5e, 0x6a, 0x6f, 0x7b, 0xa6, 0x7a, 0x38, 0x97, 0x42,
|
|
0x58, 0x1a, 0x1b, 0x42, 0xae, 0x28, 0xde, 0x18, 0x7f, 0xcc, 0x76, 0x18,
|
|
0x58, 0x05, 0xbf, 0xea, 0xef, 0x14, 0xad, 0x34, 0xe5, 0x5f, 0x25, 0xab,
|
|
0xa1, 0x5f, 0x78, 0x5b, 0x6f, 0xe6, 0x69, 0xd8, 0x74, 0x8c, 0x19, 0x59,
|
|
0xb0, 0x1a, 0xfb, 0x8e, 0xdf, 0x61, 0xac, 0xeb, 0x2b, 0x0a, 0x1c, 0xab,
|
|
0x30, 0x0d, 0x64, 0x25, 0x78, 0xdf, 0x81, 0x71, 0xe3, 0xbd, 0xde, 0x9c,
|
|
0x3f, 0xdd, 0xe9, 0xf8, 0xb6, 0x98, 0x2d, 0x13, 0xa3, 0x7b, 0x14, 0x6f,
|
|
0xe3, 0x8b, 0xfc, 0x4e, 0x31, 0x26, 0xba, 0x10, 0xb4, 0x12, 0xe9, 0xc9,
|
|
0x49, 0x60, 0xf0, 0xaa, 0x1f, 0x44, 0x68, 0x19, 0xd2, 0xb3, 0xc8, 0x46,
|
|
0x22, 0x6b, 0xe1, 0x21, 0x77, 0xfd, 0x72, 0x33, 0x13, 0x21, 0x27, 0x81,
|
|
0xe4, 0x7a, 0xc9, 0xe4, 0x1c, 0x05, 0x04, 0x73, 0x13, 0xda, 0x47, 0xfe,
|
|
0x59, 0x41, 0x9c, 0x11, 0xc5, 0xf6, 0xb5, 0xd0, 0x01, 0xcb, 0x40, 0x19,
|
|
0xf5, 0xfe, 0xb3, 0x3c, 0x1f, 0x61, 0x8f, 0x4d, 0xdb, 0x81, 0x2a, 0x8a,
|
|
0xed, 0xb8, 0x53, 0xc7, 0x19, 0x6b, 0xfa, 0x8b, 0xfc, 0xe3, 0x2e, 0x12,
|
|
0x4e, 0xbd, 0xc5, 0x44, 0x9d, 0x1c, 0x7f, 0x3b, 0x09, 0x51, 0xd7, 0x0a,
|
|
0x0f, 0x22, 0x0a, 0xfd, 0x8c, 0x90, 0x14, 0xed, 0x10, 0xcb, 0x50, 0xcf,
|
|
0xa5, 0x45, 0xce, 0xb0, 0x21, 0x28, 0xcb, 0xd6, 0xf5, 0x6e, 0xb2, 0x3e,
|
|
0xfa, 0x35, 0x0c, 0x3d, 0x09, 0x0d, 0x81, 0x30, 0x82, 0x04, 0x04, 0x30,
|
|
0x82, 0x02, 0xec, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x03, 0x02, 0x3a,
|
|
0x69, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
|
|
0x01, 0x05, 0x05, 0x00, 0x30, 0x42, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03,
|
|
0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x16, 0x30, 0x14, 0x06,
|
|
0x03, 0x55, 0x04, 0x0a, 0x13, 0x0d, 0x47, 0x65, 0x6f, 0x54, 0x72, 0x75,
|
|
0x73, 0x74, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x1b, 0x30, 0x19, 0x06,
|
|
0x03, 0x55, 0x04, 0x03, 0x13, 0x12, 0x47, 0x65, 0x6f, 0x54, 0x72, 0x75,
|
|
0x73, 0x74, 0x20, 0x47, 0x6c, 0x6f, 0x62, 0x61, 0x6c, 0x20, 0x43, 0x41,
|
|
0x30, 0x1e, 0x17, 0x0d, 0x31, 0x33, 0x30, 0x34, 0x30, 0x35, 0x31, 0x35,
|
|
0x31, 0x35, 0x35, 0x35, 0x5a, 0x17, 0x0d, 0x31, 0x35, 0x30, 0x34, 0x30,
|
|
0x34, 0x31, 0x35, 0x31, 0x35, 0x35, 0x35, 0x5a, 0x30, 0x49, 0x31, 0x0b,
|
|
0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31,
|
|
0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13, 0x0a, 0x47, 0x6f,
|
|
0x6f, 0x67, 0x6c, 0x65, 0x20, 0x49, 0x6e, 0x63, 0x31, 0x25, 0x30, 0x23,
|
|
0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x1c, 0x47, 0x6f, 0x6f, 0x67, 0x6c,
|
|
0x65, 0x20, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x20, 0x41,
|
|
0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x20, 0x47, 0x32, 0x30,
|
|
0x82, 0x01, 0x22, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7,
|
|
0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x82, 0x01, 0x0f, 0x00, 0x30,
|
|
0x82, 0x01, 0x0a, 0x02, 0x82, 0x01, 0x01, 0x00, 0x9c, 0x2a, 0x04, 0x77,
|
|
0x5c, 0xd8, 0x50, 0x91, 0x3a, 0x06, 0xa3, 0x82, 0xe0, 0xd8, 0x50, 0x48,
|
|
0xbc, 0x89, 0x3f, 0xf1, 0x19, 0x70, 0x1a, 0x88, 0x46, 0x7e, 0xe0, 0x8f,
|
|
0xc5, 0xf1, 0x89, 0xce, 0x21, 0xee, 0x5a, 0xfe, 0x61, 0x0d, 0xb7, 0x32,
|
|
0x44, 0x89, 0xa0, 0x74, 0x0b, 0x53, 0x4f, 0x55, 0xa4, 0xce, 0x82, 0x62,
|
|
0x95, 0xee, 0xeb, 0x59, 0x5f, 0xc6, 0xe1, 0x05, 0x80, 0x12, 0xc4, 0x5e,
|
|
0x94, 0x3f, 0xbc, 0x5b, 0x48, 0x38, 0xf4, 0x53, 0xf7, 0x24, 0xe6, 0xfb,
|
|
0x91, 0xe9, 0x15, 0xc4, 0xcf, 0xf4, 0x53, 0x0d, 0xf4, 0x4a, 0xfc, 0x9f,
|
|
0x54, 0xde, 0x7d, 0xbe, 0xa0, 0x6b, 0x6f, 0x87, 0xc0, 0xd0, 0x50, 0x1f,
|
|
0x28, 0x30, 0x03, 0x40, 0xda, 0x08, 0x73, 0x51, 0x6c, 0x7f, 0xff, 0x3a,
|
|
0x3c, 0xa7, 0x37, 0x06, 0x8e, 0xbd, 0x4b, 0x11, 0x04, 0xeb, 0x7d, 0x24,
|
|
0xde, 0xe6, 0xf9, 0xfc, 0x31, 0x71, 0xfb, 0x94, 0xd5, 0x60, 0xf3, 0x2e,
|
|
0x4a, 0xaf, 0x42, 0xd2, 0xcb, 0xea, 0xc4, 0x6a, 0x1a, 0xb2, 0xcc, 0x53,
|
|
0xdd, 0x15, 0x4b, 0x8b, 0x1f, 0xc8, 0x19, 0x61, 0x1f, 0xcd, 0x9d, 0xa8,
|
|
0x3e, 0x63, 0x2b, 0x84, 0x35, 0x69, 0x65, 0x84, 0xc8, 0x19, 0xc5, 0x46,
|
|
0x22, 0xf8, 0x53, 0x95, 0xbe, 0xe3, 0x80, 0x4a, 0x10, 0xc6, 0x2a, 0xec,
|
|
0xba, 0x97, 0x20, 0x11, 0xc7, 0x39, 0x99, 0x10, 0x04, 0xa0, 0xf0, 0x61,
|
|
0x7a, 0x95, 0x25, 0x8c, 0x4e, 0x52, 0x75, 0xe2, 0xb6, 0xed, 0x08, 0xca,
|
|
0x14, 0xfc, 0xce, 0x22, 0x6a, 0xb3, 0x4e, 0xcf, 0x46, 0x03, 0x97, 0x97,
|
|
0x03, 0x7e, 0xc0, 0xb1, 0xde, 0x7b, 0xaf, 0x45, 0x33, 0xcf, 0xba, 0x3e,
|
|
0x71, 0xb7, 0xde, 0xf4, 0x25, 0x25, 0xc2, 0x0d, 0x35, 0x89, 0x9d, 0x9d,
|
|
0xfb, 0x0e, 0x11, 0x79, 0x89, 0x1e, 0x37, 0xc5, 0xaf, 0x8e, 0x72, 0x69,
|
|
0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x81, 0xfb, 0x30, 0x81, 0xf8, 0x30,
|
|
0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14,
|
|
0xc0, 0x7a, 0x98, 0x68, 0x8d, 0x89, 0xfb, 0xab, 0x05, 0x64, 0x0c, 0x11,
|
|
0x7d, 0xaa, 0x7d, 0x65, 0xb8, 0xca, 0xcc, 0x4e, 0x30, 0x1d, 0x06, 0x03,
|
|
0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x4a, 0xdd, 0x06, 0x16, 0x1b,
|
|
0xbc, 0xf6, 0x68, 0xb5, 0x76, 0xf5, 0x81, 0xb6, 0xbb, 0x62, 0x1a, 0xba,
|
|
0x5a, 0x81, 0x2f, 0x30, 0x12, 0x06, 0x03, 0x55, 0x1d, 0x13, 0x01, 0x01,
|
|
0xff, 0x04, 0x08, 0x30, 0x06, 0x01, 0x01, 0xff, 0x02, 0x01, 0x00, 0x30,
|
|
0x0e, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x01, 0x01, 0xff, 0x04, 0x04, 0x03,
|
|
0x02, 0x01, 0x06, 0x30, 0x3a, 0x06, 0x03, 0x55, 0x1d, 0x1f, 0x04, 0x33,
|
|
0x30, 0x31, 0x30, 0x2f, 0xa0, 0x2d, 0xa0, 0x2b, 0x86, 0x29, 0x68, 0x74,
|
|
0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x63, 0x72, 0x6c, 0x2e, 0x67, 0x65, 0x6f,
|
|
0x74, 0x72, 0x75, 0x73, 0x74, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x63, 0x72,
|
|
0x6c, 0x73, 0x2f, 0x67, 0x74, 0x67, 0x6c, 0x6f, 0x62, 0x61, 0x6c, 0x2e,
|
|
0x63, 0x72, 0x6c, 0x30, 0x3d, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05,
|
|
0x07, 0x01, 0x01, 0x04, 0x31, 0x30, 0x2f, 0x30, 0x2d, 0x06, 0x08, 0x2b,
|
|
0x06, 0x01, 0x05, 0x05, 0x07, 0x30, 0x01, 0x86, 0x21, 0x68, 0x74, 0x74,
|
|
0x70, 0x3a, 0x2f, 0x2f, 0x67, 0x74, 0x67, 0x6c, 0x6f, 0x62, 0x61, 0x6c,
|
|
0x2d, 0x6f, 0x63, 0x73, 0x70, 0x2e, 0x67, 0x65, 0x6f, 0x74, 0x72, 0x75,
|
|
0x73, 0x74, 0x2e, 0x63, 0x6f, 0x6d, 0x30, 0x17, 0x06, 0x03, 0x55, 0x1d,
|
|
0x20, 0x04, 0x10, 0x30, 0x0e, 0x30, 0x0c, 0x06, 0x0a, 0x2b, 0x06, 0x01,
|
|
0x04, 0x01, 0xd6, 0x79, 0x02, 0x05, 0x01, 0x30, 0x0d, 0x06, 0x09, 0x2a,
|
|
0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00, 0x03, 0x82,
|
|
0x01, 0x01, 0x00, 0x36, 0xd7, 0x06, 0x80, 0x11, 0x27, 0xad, 0x2a, 0x14,
|
|
0x9b, 0x38, 0x77, 0xb3, 0x23, 0xa0, 0x75, 0x58, 0xbb, 0xb1, 0x7e, 0x83,
|
|
0x42, 0xba, 0x72, 0xda, 0x1e, 0xd8, 0x8e, 0x36, 0x06, 0x97, 0xe0, 0xf0,
|
|
0x95, 0x3b, 0x37, 0xfd, 0x1b, 0x42, 0x58, 0xfe, 0x22, 0xc8, 0x6b, 0xbd,
|
|
0x38, 0x5e, 0xd1, 0x3b, 0x25, 0x6e, 0x12, 0xeb, 0x5e, 0x67, 0x76, 0x46,
|
|
0x40, 0x90, 0xda, 0x14, 0xc8, 0x78, 0x0d, 0xed, 0x95, 0x66, 0xda, 0x8e,
|
|
0x86, 0x6f, 0x80, 0xa1, 0xba, 0x56, 0x32, 0x95, 0x86, 0xdc, 0xdc, 0x6a,
|
|
0xca, 0x04, 0x8c, 0x5b, 0x7f, 0xf6, 0xbf, 0xcc, 0x6f, 0x85, 0x03, 0x58,
|
|
0xc3, 0x68, 0x51, 0x13, 0xcd, 0xfd, 0xc8, 0xf7, 0x79, 0x3d, 0x99, 0x35,
|
|
0xf0, 0x56, 0xa3, 0xbd, 0xe0, 0x59, 0xed, 0x4f, 0x44, 0x09, 0xa3, 0x9e,
|
|
0x38, 0x7a, 0xf6, 0x46, 0xd1, 0x1d, 0x12, 0x9d, 0x4f, 0xbe, 0xd0, 0x40,
|
|
0xfc, 0x55, 0xfe, 0x06, 0x5e, 0x3c, 0xda, 0x1c, 0x56, 0xbd, 0x96, 0x51,
|
|
0x7b, 0x6f, 0x57, 0x2a, 0xdb, 0xa2, 0xaa, 0x96, 0xdc, 0x8c, 0x74, 0xc2,
|
|
0x95, 0xbe, 0xf0, 0x6e, 0x95, 0x13, 0xff, 0x17, 0xf0, 0x3c, 0xac, 0xb2,
|
|
0x10, 0x8d, 0xcc, 0x73, 0xfb, 0xe8, 0x8f, 0x02, 0xc6, 0xf0, 0xfb, 0x33,
|
|
0xb3, 0x95, 0x3b, 0xe3, 0xc2, 0xcb, 0x68, 0x58, 0x73, 0xdb, 0xa8, 0x24,
|
|
0x62, 0x3b, 0x06, 0x35, 0x9d, 0x0d, 0xa9, 0x33, 0xbd, 0x78, 0x03, 0x90,
|
|
0x2e, 0x4c, 0x78, 0x5d, 0x50, 0x3a, 0x81, 0xd4, 0xee, 0xa0, 0xc8, 0x70,
|
|
0x38, 0xdc, 0xb2, 0xf9, 0x67, 0xfa, 0x87, 0x40, 0x5d, 0x61, 0xc0, 0x51,
|
|
0x8f, 0x6b, 0x83, 0x6b, 0xcd, 0x05, 0x3a, 0xca, 0xe1, 0xa7, 0x05, 0x78,
|
|
0xfc, 0xca, 0xda, 0x94, 0xd0, 0x2c, 0x08, 0x3d, 0x7e, 0x16, 0x79, 0xc8,
|
|
0xa0, 0x50, 0x20, 0x24, 0x54, 0x33, 0x71, 0x31, 0x00, 0x00, 0x00, 0x00,
|
|
0x00, 0x00, 0x00,
|
|
};
|
|
|
|
// Cribbed from
|
|
// https://github.com/bcgit/bc-java/blob/main/pkix/src/test/resources/org/bouncycastle/openssl/test/pkcs7.pem
|
|
static const uint8_t kPKCS7EnvelopedData[] = {
|
|
0x30, 0x82, 0x09, 0xA2, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D,
|
|
0x01, 0x07, 0x03, 0xA0, 0x82, 0x09, 0x93, 0x30, 0x82, 0x09, 0x8F, 0x02,
|
|
0x01, 0x00, 0x31, 0x81, 0xF8, 0x30, 0x81, 0xF5, 0x02, 0x01, 0x00, 0x30,
|
|
0x5E, 0x30, 0x59, 0x31, 0x0B, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06,
|
|
0x13, 0x02, 0x47, 0x42, 0x31, 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04,
|
|
0x08, 0x13, 0x09, 0x42, 0x65, 0x72, 0x6B, 0x73, 0x68, 0x69, 0x72, 0x65,
|
|
0x31, 0x10, 0x30, 0x0E, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x07, 0x4E,
|
|
0x65, 0x77, 0x62, 0x75, 0x72, 0x79, 0x31, 0x17, 0x30, 0x15, 0x06, 0x03,
|
|
0x55, 0x04, 0x0A, 0x13, 0x0E, 0x4D, 0x79, 0x20, 0x43, 0x6F, 0x6D, 0x70,
|
|
0x61, 0x6E, 0x79, 0x20, 0x4C, 0x74, 0x64, 0x31, 0x0B, 0x30, 0x09, 0x06,
|
|
0x03, 0x55, 0x04, 0x03, 0x13, 0x02, 0x58, 0x58, 0x02, 0x01, 0x00, 0x30,
|
|
0x0D, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x01,
|
|
0x05, 0x00, 0x04, 0x81, 0x80, 0x22, 0x91, 0xBF, 0x5C, 0x0F, 0x7F, 0x68,
|
|
0x0D, 0x8A, 0x4C, 0x1F, 0x32, 0xEE, 0xA8, 0x0E, 0x01, 0xA2, 0x73, 0x69,
|
|
0x3F, 0x1F, 0xA3, 0x62, 0xDA, 0xA5, 0x50, 0x86, 0x89, 0xBF, 0x7D, 0x15,
|
|
0xD3, 0x79, 0xD4, 0xCF, 0x53, 0x0B, 0x9B, 0xB2, 0x07, 0xED, 0x31, 0x6D,
|
|
0x66, 0x12, 0xFA, 0x05, 0x70, 0x1B, 0x74, 0x2D, 0xA2, 0xC2, 0x4E, 0xB6,
|
|
0x29, 0x54, 0xBA, 0xE9, 0x90, 0x8B, 0x04, 0xA7, 0x6C, 0xAA, 0xD0, 0xF7,
|
|
0xC3, 0xD3, 0x76, 0x1E, 0xDC, 0x53, 0x11, 0x6E, 0x80, 0x75, 0xA3, 0x47,
|
|
0x28, 0xD5, 0x1B, 0xEB, 0x3F, 0x37, 0xC9, 0xAA, 0xCD, 0x40, 0x6C, 0xC1,
|
|
0xEB, 0xB9, 0x65, 0x66, 0x37, 0x82, 0x2D, 0xE8, 0xA9, 0x3F, 0xB4, 0x56,
|
|
0x22, 0xF0, 0x59, 0x71, 0x5D, 0x0E, 0xA2, 0xA0, 0xA0, 0x2D, 0xCA, 0x59,
|
|
0x92, 0x96, 0x6A, 0xCE, 0xB9, 0xB3, 0xE4, 0xC8, 0xF1, 0x4C, 0x29, 0x81,
|
|
0xFC, 0x30, 0x82, 0x08, 0x8D, 0x06, 0x09, 0x2A, 0x86, 0x48, 0x86, 0xF7,
|
|
0x0D, 0x01, 0x07, 0x01, 0x30, 0x14, 0x06, 0x08, 0x2A, 0x86, 0x48, 0x86,
|
|
0xF7, 0x0D, 0x03, 0x07, 0x04, 0x08, 0x8D, 0xAF, 0x67, 0x1A, 0x1B, 0x90,
|
|
0x13, 0x51, 0x80, 0x82, 0x08, 0x68, 0x72, 0xCC, 0x21, 0x7B, 0x93, 0x19,
|
|
0x46, 0x8B, 0xFD, 0x66, 0x8D, 0x60, 0x9C, 0x1D, 0xB9, 0x4B, 0x43, 0xFC,
|
|
0x33, 0x0D, 0xF8, 0xEB, 0x75, 0x5A, 0x39, 0xC6, 0xFE, 0x96, 0x35, 0xF5,
|
|
0x99, 0x79, 0x13, 0xDD, 0xF8, 0xAF, 0x90, 0x1B, 0xF4, 0xA6, 0x52, 0xE5,
|
|
0x99, 0x54, 0xFE, 0x9B, 0xE0, 0x91, 0x81, 0xCC, 0xEE, 0xA7, 0xDA, 0x76,
|
|
0xD7, 0xEB, 0x75, 0x3A, 0xAB, 0x1D, 0x68, 0x84, 0xCD, 0x23, 0x2A, 0xC6,
|
|
0x85, 0x84, 0x95, 0x11, 0x35, 0xB2, 0x14, 0x0F, 0xD8, 0x9F, 0xB7, 0x50,
|
|
0xBA, 0x92, 0xBE, 0x71, 0xD0, 0x9A, 0x54, 0xB2, 0x82, 0xDE, 0x54, 0xFC,
|
|
0x7F, 0x5D, 0xE2, 0x3E, 0xB5, 0x38, 0xD3, 0x09, 0xDB, 0x7A, 0x8E, 0x19,
|
|
0x2A, 0x2D, 0xAF, 0x6E, 0xFF, 0xD7, 0xDE, 0xE5, 0x38, 0x7D, 0x13, 0x19,
|
|
0xC1, 0x29, 0x72, 0x73, 0x31, 0x68, 0xCD, 0xCB, 0xE2, 0x51, 0x85, 0x11,
|
|
0xB4, 0x0E, 0x4C, 0x65, 0xA4, 0xB6, 0x7B, 0xAF, 0xF6, 0xAF, 0x57, 0x8B,
|
|
0x65, 0xC5, 0x25, 0x71, 0x9D, 0x01, 0x0D, 0xCB, 0x83, 0xF8, 0x53, 0x5D,
|
|
0xAF, 0x21, 0x9B, 0x2B, 0x3B, 0x52, 0x59, 0xAD, 0xB2, 0x7B, 0x46, 0x26,
|
|
0x52, 0x29, 0x6E, 0xF8, 0x60, 0x19, 0xAF, 0x90, 0x90, 0x8B, 0x72, 0x31,
|
|
0xA5, 0x1C, 0x43, 0xAA, 0xB4, 0xBE, 0x45, 0x44, 0x19, 0x36, 0x59, 0x5C,
|
|
0x83, 0xC9, 0xC6, 0x67, 0x65, 0x0F, 0xE5, 0x6F, 0x05, 0x8C, 0x7F, 0x99,
|
|
0xE7, 0xAF, 0x0D, 0x27, 0xB7, 0x63, 0xA3, 0x38, 0x82, 0x5F, 0x41, 0x07,
|
|
0xC9, 0xDE, 0x2F, 0xA7, 0xE8, 0x34, 0x2D, 0x11, 0xB6, 0x76, 0x48, 0x46,
|
|
0x5C, 0x87, 0xDF, 0xE2, 0xE7, 0xCE, 0xD9, 0x4D, 0xD0, 0x38, 0x08, 0x02,
|
|
0x20, 0xEB, 0x99, 0x98, 0x6E, 0x58, 0x4A, 0x94, 0x4D, 0xD9, 0x4E, 0xC5,
|
|
0xE9, 0x3F, 0x16, 0xFC, 0x5C, 0x12, 0x84, 0x53, 0xB5, 0xBB, 0xE4, 0x07,
|
|
0x61, 0xDB, 0x80, 0xDE, 0x90, 0x3F, 0xE4, 0xAF, 0x88, 0x0D, 0xF0, 0x9B,
|
|
0x11, 0x90, 0xCC, 0x5B, 0x39, 0xDD, 0xD7, 0x79, 0x53, 0x11, 0x94, 0x25,
|
|
0x2D, 0x25, 0xD5, 0xED, 0xD2, 0xCD, 0x0A, 0xAA, 0x51, 0xDF, 0x42, 0x56,
|
|
0xA4, 0x68, 0x3D, 0xE7, 0xAA, 0xC9, 0x47, 0x49, 0x36, 0x6D, 0x3E, 0xC6,
|
|
0x28, 0x54, 0xD7, 0x85, 0x25, 0x0A, 0xFC, 0xFB, 0x9A, 0x73, 0x9C, 0xBA,
|
|
0x21, 0x59, 0x89, 0xC0, 0xFC, 0x6A, 0x02, 0x48, 0xC7, 0xFB, 0x18, 0xD7,
|
|
0xA4, 0x4D, 0xF6, 0xFC, 0x07, 0x11, 0x1E, 0x2E, 0xFB, 0x2D, 0xAD, 0xE7,
|
|
0x2A, 0x9D, 0x5A, 0x40, 0x42, 0xA8, 0xE6, 0xE1, 0xE0, 0xEC, 0x71, 0x20,
|
|
0xC3, 0x5E, 0xB4, 0x4B, 0x52, 0xD4, 0x7A, 0x72, 0x52, 0xA9, 0xC9, 0x8E,
|
|
0xBA, 0x4E, 0x57, 0x5A, 0xF3, 0x35, 0xC1, 0xDB, 0x14, 0x26, 0x5E, 0x50,
|
|
0x93, 0x89, 0xBD, 0x6B, 0x45, 0x72, 0xA2, 0xF2, 0xCF, 0x9B, 0xF4, 0x6B,
|
|
0x9E, 0xE9, 0x4C, 0xB5, 0x48, 0xD1, 0xBA, 0x0C, 0x49, 0x2D, 0xF6, 0x4A,
|
|
0xDB, 0xB3, 0x62, 0xBC, 0xEA, 0xCB, 0x97, 0xD8, 0x7F, 0x5A, 0x6E, 0x81,
|
|
0x5D, 0x8A, 0xB8, 0x3E, 0x88, 0x4C, 0xE5, 0xDF, 0xB9, 0xCC, 0xF6, 0x2A,
|
|
0xBA, 0x99, 0xF9, 0x8A, 0x92, 0x87, 0xB0, 0x0E, 0xBC, 0x3E, 0xCE, 0xEB,
|
|
0x9C, 0x31, 0x06, 0x4B, 0x75, 0x73, 0x39, 0x0D, 0xF6, 0x86, 0xAB, 0xB8,
|
|
0x91, 0xD9, 0xBA, 0xC4, 0x8D, 0xB3, 0x2D, 0x62, 0xB4, 0xFB, 0xA9, 0x90,
|
|
0x9E, 0xEB, 0x01, 0x3C, 0xED, 0x08, 0x03, 0x1B, 0x63, 0x6B, 0xA0, 0x4F,
|
|
0xCF, 0xCB, 0xD3, 0x32, 0x55, 0xA3, 0x66, 0xD5, 0x99, 0x80, 0x42, 0x0C,
|
|
0xA6, 0x94, 0x0C, 0x85, 0x02, 0x4A, 0x04, 0x44, 0x06, 0xE8, 0x74, 0xD5,
|
|
0xCF, 0xEF, 0xE0, 0x90, 0x57, 0x6C, 0xDA, 0x91, 0x4E, 0xD2, 0xFF, 0x29,
|
|
0x2D, 0xC3, 0x01, 0xCB, 0xDF, 0xBC, 0x9E, 0xA8, 0x73, 0xC0, 0x66, 0x9C,
|
|
0xCA, 0x69, 0xEE, 0xA5, 0x72, 0x73, 0x07, 0xA9, 0x77, 0x82, 0x89, 0xF6,
|
|
0xB7, 0xF7, 0xB6, 0xCC, 0x98, 0xC0, 0x3C, 0xA5, 0x12, 0x09, 0xB1, 0xC8,
|
|
0x42, 0x10, 0xA3, 0x5B, 0x62, 0x4A, 0xF6, 0xD1, 0x8A, 0x4D, 0xB1, 0x78,
|
|
0xD2, 0xE6, 0x0C, 0x50, 0x63, 0x08, 0x3E, 0x1C, 0x6B, 0xEE, 0x3D, 0x6E,
|
|
0xE0, 0xB2, 0x8D, 0x12, 0x12, 0x82, 0x36, 0x19, 0x54, 0xCF, 0xCD, 0x8D,
|
|
0x4A, 0xC7, 0x49, 0xD3, 0x46, 0x0D, 0x41, 0xDC, 0x2E, 0x0C, 0xC5, 0x8D,
|
|
0x09, 0x30, 0x04, 0xF7, 0xF4, 0x93, 0x99, 0x11, 0x85, 0xDD, 0x91, 0xD3,
|
|
0xF4, 0xA5, 0xA6, 0xCF, 0x93, 0x10, 0x10, 0x2A, 0x7F, 0xA4, 0x63, 0x91,
|
|
0x0F, 0xB2, 0xED, 0x39, 0x0B, 0x25, 0x6D, 0x46, 0x22, 0x30, 0x7E, 0x68,
|
|
0x09, 0x83, 0xF5, 0x8C, 0x3F, 0x1E, 0x33, 0xE2, 0xB1, 0x0A, 0x58, 0xEF,
|
|
0xD6, 0x91, 0x4F, 0x7F, 0xEB, 0x19, 0x76, 0x96, 0xE8, 0x02, 0x47, 0x5A,
|
|
0x5C, 0xA7, 0x19, 0x56, 0x72, 0xAA, 0x3A, 0xE3, 0xC1, 0x3F, 0x76, 0x35,
|
|
0x8C, 0x19, 0x0B, 0x09, 0x9C, 0xA4, 0x82, 0x75, 0xE4, 0x55, 0xB1, 0x18,
|
|
0x33, 0xB8, 0x12, 0x76, 0xFB, 0x02, 0x18, 0xAE, 0x76, 0x19, 0xCC, 0x47,
|
|
0xCA, 0x2F, 0xE0, 0x3A, 0x17, 0xCE, 0x22, 0x0C, 0xB0, 0x98, 0x50, 0x77,
|
|
0x07, 0x86, 0x24, 0xE2, 0x60, 0xED, 0x53, 0xCE, 0x16, 0xA4, 0xAE, 0x6C,
|
|
0x56, 0x5A, 0xD9, 0xDA, 0xF6, 0x6E, 0x4D, 0xA0, 0x26, 0x38, 0x76, 0x93,
|
|
0x22, 0x45, 0x4C, 0xBE, 0x4A, 0xB7, 0xD0, 0x5F, 0xE3, 0xA5, 0x5C, 0xB7,
|
|
0x38, 0x5E, 0x2F, 0xF7, 0xF1, 0x1B, 0x10, 0x02, 0x46, 0xBF, 0xAA, 0xEA,
|
|
0x1C, 0xC8, 0x4A, 0x9A, 0xE2, 0x07, 0x3F, 0x9D, 0xF4, 0x08, 0xAB, 0x56,
|
|
0x91, 0x45, 0x1F, 0x1A, 0xFE, 0xEA, 0x42, 0x29, 0x59, 0xD5, 0x08, 0xBA,
|
|
0x37, 0x21, 0x49, 0x25, 0x37, 0xDB, 0xD5, 0xB8, 0x72, 0x10, 0xD2, 0x6D,
|
|
0x8F, 0xC0, 0x35, 0x41, 0x01, 0x48, 0x60, 0x70, 0xF3, 0x32, 0x89, 0x66,
|
|
0x52, 0x84, 0x20, 0xA8, 0xE5, 0xC9, 0xFF, 0xAC, 0x5C, 0xF4, 0x0B, 0x42,
|
|
0xBF, 0x47, 0xD4, 0xD8, 0xB8, 0xA3, 0x2D, 0x43, 0x45, 0x8C, 0x1E, 0x2B,
|
|
0x6A, 0x92, 0x60, 0x82, 0x8E, 0x54, 0x9D, 0x91, 0x3D, 0xF3, 0xE2, 0x2A,
|
|
0x50, 0x04, 0xFB, 0xB5, 0x66, 0xA5, 0xA5, 0xB1, 0x62, 0xB0, 0xE7, 0x57,
|
|
0xE4, 0x3C, 0xB9, 0xF3, 0x68, 0x61, 0xBD, 0xC1, 0x67, 0xFF, 0x50, 0xC3,
|
|
0xA4, 0x84, 0x97, 0xA4, 0x5D, 0x24, 0x80, 0x4F, 0x13, 0x57, 0xFB, 0x30,
|
|
0x90, 0x9E, 0xF3, 0xBA, 0xEF, 0xA1, 0x3B, 0xF6, 0x23, 0xD4, 0x73, 0x5D,
|
|
0x73, 0x01, 0xBA, 0x34, 0x2F, 0x7E, 0xC1, 0x40, 0xA3, 0x69, 0x1A, 0x80,
|
|
0xA1, 0xB0, 0x6D, 0xBC, 0xF4, 0x32, 0x2B, 0xAE, 0xBA, 0x23, 0xC0, 0xB5,
|
|
0xDA, 0x99, 0xD6, 0xD0, 0x07, 0xAE, 0xAA, 0xDC, 0xE7, 0x9D, 0x9B, 0xDE,
|
|
0xD8, 0x1D, 0x3F, 0x6B, 0xCD, 0xC4, 0x09, 0x2D, 0x2D, 0x52, 0x6C, 0x42,
|
|
0x3C, 0xEF, 0x73, 0xBF, 0xD4, 0x4D, 0xC1, 0xC6, 0xA4, 0xCA, 0x79, 0x25,
|
|
0xAE, 0xEA, 0x70, 0xEC, 0x1E, 0x0F, 0x71, 0x71, 0x1A, 0x11, 0xBC, 0x69,
|
|
0xBC, 0x71, 0x3E, 0xFF, 0x33, 0x4B, 0x81, 0xFA, 0xCF, 0x46, 0x08, 0x28,
|
|
0x15, 0xDA, 0x92, 0x21, 0x11, 0x52, 0xF7, 0x14, 0x11, 0x3C, 0x4F, 0x53,
|
|
0xB8, 0xEE, 0xE3, 0x12, 0x1F, 0xAD, 0xCA, 0x1E, 0xF4, 0x78, 0xBA, 0x9C,
|
|
0x7B, 0x68, 0xEA, 0x2A, 0x94, 0x70, 0xC4, 0x8B, 0x59, 0xB2, 0xDD, 0xC0,
|
|
0x05, 0x3E, 0x57, 0x6A, 0xB2, 0x7A, 0xBD, 0xF1, 0xB1, 0xC5, 0xCB, 0x39,
|
|
0xE6, 0xC2, 0x46, 0xEF, 0x18, 0xEF, 0xE7, 0x6C, 0x6E, 0x32, 0x29, 0x18,
|
|
0x80, 0xE6, 0xA0, 0x48, 0xAA, 0x44, 0x4D, 0x17, 0x64, 0x78, 0x4D, 0x5A,
|
|
0x02, 0x62, 0xB0, 0xA5, 0xAF, 0xEF, 0x10, 0x5B, 0xB6, 0x27, 0x83, 0xAA,
|
|
0xD4, 0x08, 0xAF, 0xF8, 0x3D, 0x86, 0x73, 0xB1, 0xB4, 0xE1, 0xC3, 0xAC,
|
|
0x75, 0xCF, 0xBA, 0x3F, 0xE3, 0x7D, 0x10, 0x4B, 0xFB, 0xD2, 0xFD, 0x11,
|
|
0xDC, 0xD0, 0x38, 0xBE, 0x0D, 0xE0, 0x4C, 0x17, 0x0E, 0xDF, 0x0C, 0x70,
|
|
0x9C, 0x96, 0x40, 0x4B, 0xB1, 0xB0, 0x50, 0x93, 0x9C, 0xAE, 0xA0, 0xB5,
|
|
0x70, 0x06, 0x90, 0x91, 0xCE, 0x4D, 0x47, 0x49, 0x54, 0xC7, 0x49, 0x4C,
|
|
0xCE, 0x05, 0x96, 0x0C, 0x34, 0xB9, 0xA8, 0xA5, 0xFE, 0x63, 0x02, 0x14,
|
|
0xEC, 0xA1, 0x10, 0x8B, 0x28, 0x6A, 0x43, 0xBE, 0x2B, 0x91, 0xFE, 0xA1,
|
|
0xC5, 0x0C, 0x9F, 0x7A, 0xC6, 0x81, 0xC6, 0xAC, 0x42, 0x65, 0x99, 0x22,
|
|
0x91, 0xBC, 0x01, 0x1E, 0x50, 0xD9, 0xC2, 0x83, 0xDF, 0xC2, 0x77, 0xEB,
|
|
0x57, 0x85, 0xF8, 0xFF, 0x1C, 0xA8, 0xDD, 0xCA, 0x82, 0xA9, 0xB8, 0x5F,
|
|
0x14, 0x59, 0x47, 0x38, 0x05, 0xE2, 0xB2, 0xCC, 0xF5, 0xE3, 0x0B, 0x13,
|
|
0x3E, 0x1E, 0x17, 0x42, 0xE9, 0xA3, 0xE5, 0x16, 0x52, 0x9F, 0x08, 0xFC,
|
|
0x80, 0x62, 0xB6, 0xC6, 0x8B, 0xBD, 0x1F, 0xDC, 0x0C, 0xAF, 0x0B, 0x99,
|
|
0xD9, 0xE0, 0x13, 0xFF, 0x72, 0xF7, 0x3A, 0xD6, 0xC8, 0xAF, 0xF4, 0xB3,
|
|
0x09, 0xBA, 0x7C, 0x63, 0xDE, 0x53, 0xCF, 0xC1, 0x60, 0x9A, 0xB2, 0x57,
|
|
0xBF, 0x28, 0x0C, 0x54, 0xED, 0x71, 0xBF, 0xBE, 0xCF, 0x03, 0x50, 0xF3,
|
|
0x13, 0xD4, 0x8B, 0x88, 0xBC, 0x81, 0xE9, 0x32, 0xFC, 0x96, 0xCC, 0x45,
|
|
0x43, 0x56, 0x45, 0xD8, 0x3F, 0x09, 0x86, 0x90, 0xDE, 0x20, 0xFA, 0x63,
|
|
0x2F, 0x49, 0x36, 0xBD, 0x3A, 0xE6, 0x0A, 0x01, 0x0D, 0x27, 0xEB, 0x42,
|
|
0x73, 0x49, 0xE0, 0x64, 0xEE, 0x79, 0x66, 0x04, 0x5B, 0xA3, 0x57, 0xDB,
|
|
0x07, 0xF4, 0x54, 0x7E, 0x44, 0xD1, 0x80, 0x42, 0x85, 0xF5, 0x69, 0x89,
|
|
0x62, 0x79, 0x57, 0x51, 0x5A, 0x21, 0xEF, 0xB9, 0x19, 0xD1, 0xC7, 0x3D,
|
|
0x63, 0xE2, 0xAC, 0xB9, 0xE1, 0x19, 0xA7, 0x5C, 0x28, 0x49, 0x3C, 0xB0,
|
|
0x25, 0xBD, 0xED, 0x73, 0xF8, 0xD7, 0x79, 0x11, 0x92, 0x99, 0xC6, 0x96,
|
|
0x7B, 0xAA, 0x5A, 0xD0, 0x37, 0x1F, 0x33, 0x9D, 0x1C, 0xA1, 0x5D, 0x32,
|
|
0xE2, 0x5C, 0x35, 0x79, 0xD9, 0xC4, 0x57, 0x7C, 0xE4, 0x03, 0x5A, 0xF8,
|
|
0xCD, 0x5B, 0x54, 0x07, 0x0F, 0x17, 0xBE, 0xBF, 0x46, 0x29, 0xC3, 0x5F,
|
|
0x59, 0xD9, 0xAA, 0x80, 0x82, 0x4A, 0xB1, 0x0A, 0xDA, 0xAB, 0xA5, 0x82,
|
|
0x78, 0x8C, 0x42, 0x3C, 0xF2, 0x70, 0xEF, 0x4F, 0x3E, 0xFD, 0x11, 0x11,
|
|
0x40, 0x1A, 0x14, 0xA1, 0xB5, 0xC8, 0xE3, 0xE2, 0x5A, 0xB7, 0x0F, 0xF3,
|
|
0x5E, 0x25, 0x7D, 0x4A, 0x3A, 0xE3, 0x2B, 0xD9, 0xC9, 0xE0, 0x7D, 0x58,
|
|
0x2B, 0x23, 0xA3, 0xCB, 0x3D, 0xD2, 0x01, 0xB7, 0x98, 0xAE, 0x07, 0x60,
|
|
0xAD, 0x31, 0xAF, 0x90, 0x44, 0xC2, 0x3C, 0x00, 0x0B, 0x6F, 0xEE, 0x11,
|
|
0x83, 0x51, 0x47, 0xCA, 0x64, 0x8C, 0x7C, 0x3A, 0xAE, 0xC0, 0xEB, 0x01,
|
|
0xEB, 0x73, 0x1D, 0x97, 0xAD, 0xC3, 0x22, 0x42, 0x69, 0x89, 0xC0, 0x3A,
|
|
0x09, 0x8E, 0xB2, 0x93, 0xF2, 0xE0, 0x38, 0x00, 0xD0, 0xCC, 0x48, 0xA9,
|
|
0x8D, 0xC7, 0x4A, 0xAB, 0x34, 0x0E, 0x8E, 0x56, 0xF8, 0x86, 0xC4, 0x19,
|
|
0xC4, 0xDF, 0x37, 0x93, 0x31, 0x89, 0x89, 0x60, 0x74, 0xA9, 0x93, 0x8B,
|
|
0x5D, 0x52, 0xEB, 0x19, 0x73, 0xF8, 0xC5, 0x16, 0x12, 0xD9, 0xB5, 0x05,
|
|
0x07, 0x44, 0xFC, 0xA6, 0x89, 0xF4, 0x2B, 0x9A, 0xAC, 0x67, 0xDA, 0x0A,
|
|
0x29, 0xFF, 0x87, 0x65, 0xA1, 0xCC, 0x62, 0x49, 0xE2, 0xE3, 0x71, 0x1F,
|
|
0xF4, 0x84, 0x40, 0xD2, 0xA7, 0x83, 0x97, 0x81, 0x5F, 0x02, 0xEA, 0x40,
|
|
0x90, 0xBD, 0x25, 0x2E, 0x70, 0x63, 0x80, 0x64, 0x47, 0x73, 0xAA, 0xCC,
|
|
0x07, 0x2E, 0x2A, 0x2F, 0x5F, 0x31, 0x46, 0x34, 0xED, 0x47, 0xD8, 0x6C,
|
|
0x9F, 0x86, 0x7F, 0xA5, 0x88, 0x48, 0x82, 0xA3, 0x26, 0xDD, 0x01, 0x15,
|
|
0x90, 0xAF, 0xDA, 0x3A, 0x04, 0xCE, 0x97, 0x05, 0xC7, 0x74, 0x8C, 0x2E,
|
|
0xF8, 0x7B, 0xF3, 0xC7, 0x46, 0x3F, 0x06, 0x03, 0x1D, 0x09, 0x94, 0xA5,
|
|
0xAE, 0xCA, 0x4F, 0x6D, 0x00, 0x43, 0x82, 0xB9, 0x56, 0xCE, 0xBF, 0x8F,
|
|
0x8D, 0xC8, 0xC4, 0xBC, 0x37, 0xF7, 0x2D, 0x88, 0xFD, 0xC2, 0x1B, 0x51,
|
|
0x24, 0xFE, 0x5C, 0x5D, 0x5C, 0x62, 0x62, 0xA8, 0xBF, 0x4A, 0x90, 0xA4,
|
|
0x1A, 0x1C, 0xB8, 0xED, 0x17, 0xCD, 0x61, 0xF9, 0x24, 0x26, 0xCF, 0xE0,
|
|
0x6E, 0x88, 0xE5, 0x3B, 0xF9, 0x43, 0xBC, 0xCF, 0x28, 0xA3, 0xE5, 0xCF,
|
|
0x8B, 0x6D, 0xB3, 0x00, 0xDE, 0xB2, 0x14, 0xBB, 0xB1, 0xAF, 0xAE, 0x65,
|
|
0x25, 0x92, 0xBB, 0x40, 0x8B, 0xDA, 0x6C, 0x7B, 0xD3, 0x90, 0x42, 0x0D,
|
|
0xC2, 0x6A, 0x67, 0x59, 0xC4, 0x47, 0xF8, 0xCC, 0x1C, 0x15, 0x93, 0xB7,
|
|
0xC8, 0xAB, 0x7A, 0x97, 0x16, 0x3B, 0x9C, 0x95, 0xAE, 0x5B, 0x98, 0x61,
|
|
0xF0, 0xEE, 0xE4, 0xE3, 0xFA, 0x0D, 0xD2, 0x93, 0x5D, 0x1A, 0xDB, 0xF5,
|
|
0xFF, 0x65, 0xE0, 0x5C, 0x53, 0x82, 0x44, 0x44, 0x38, 0x09, 0xC3, 0xE7,
|
|
0x66, 0x6F, 0xEF, 0x5D, 0x42, 0xCB, 0x08, 0x28, 0x7B, 0xA0, 0xFF, 0x91,
|
|
0xCA, 0x49, 0x67, 0xC3, 0x27, 0x9D, 0xBD, 0xF7, 0x92, 0x7D, 0x8E, 0x25,
|
|
0xA6, 0x57, 0x70, 0xC8, 0x70, 0x88, 0xB1, 0x8C, 0x98, 0x99, 0xF6, 0x47,
|
|
0x33, 0x0D, 0xF6, 0xCE, 0xA1, 0xF9, 0x8C, 0x29, 0xD2, 0xC5, 0x90, 0x38,
|
|
0x7C, 0x70, 0x6B, 0x6E, 0x5A, 0xF8, 0x32, 0x3F, 0xF9, 0x8F, 0x21, 0xCB,
|
|
0x50, 0x5E, 0x71, 0x1A, 0xC2, 0x5D, 0x9B, 0x94, 0x6D, 0x0D, 0xFC, 0x09,
|
|
0x59, 0xEE, 0x8D, 0x7A, 0x53, 0xBF, 0x90, 0x93, 0x2C, 0xDF, 0x95, 0x23,
|
|
0x03, 0xA7, 0x61, 0x48, 0xE7, 0xC7, 0x12, 0x4C, 0x3B, 0xDC, 0xCE, 0x4F,
|
|
0x8D, 0xC4, 0x68, 0xD4, 0xEB, 0x58, 0x64, 0x6B, 0xB5, 0xF7, 0x1D, 0x90,
|
|
0x82, 0xE8, 0x48, 0x2E, 0x96, 0x71, 0xB8, 0x0B, 0xCD, 0xB4, 0xBA, 0x4E,
|
|
0xB7, 0xCF, 0x33, 0xDC, 0xFB, 0x6C, 0xC4, 0x0E, 0x85, 0x73, 0x40, 0x46,
|
|
0xA5, 0x05, 0xCF, 0x25, 0x36, 0x30, 0xB5, 0x78, 0x8F, 0x7F, 0x59, 0x63,
|
|
0x7D, 0x47, 0x79, 0x28, 0x5B, 0x0F, 0xA2, 0x13, 0xC9, 0x38, 0x81, 0x09,
|
|
0x01, 0xA1, 0x47, 0x2F, 0x71, 0x93, 0xC2, 0x65, 0x85, 0xB4, 0xAD, 0x5D,
|
|
0x1E, 0x87, 0xCF, 0x42, 0xE9, 0x22, 0x39, 0x36, 0xFA, 0xA4, 0x2E, 0xB2,
|
|
0x2A, 0x53, 0x3F, 0xCC, 0x65, 0x8B, 0x3B, 0x2C, 0xD3, 0x33, 0x8A, 0x8F,
|
|
0x52, 0xFB, 0x94, 0x4B, 0x08, 0x35, 0x51, 0x8F, 0x06, 0xA6, 0x50, 0x9E,
|
|
0xAA, 0x10, 0x89, 0x35, 0x38, 0x9E, 0x36, 0x6C, 0x98, 0xEF, 0x4B, 0xF3,
|
|
0x1B, 0x60, 0x96, 0x72, 0x8B, 0x40, 0xC1, 0x13, 0xDE, 0x55, 0xBA, 0x5A,
|
|
0xE0, 0xC1, 0x16, 0x45, 0x71, 0xDF, 0xF5, 0xFB, 0x78, 0x31, 0xAC, 0x1B,
|
|
0xAA, 0x7D, 0x89, 0xE3, 0xC8, 0x96, 0xE1, 0x98, 0x21, 0xF3, 0x6B, 0xC5,
|
|
0x1C, 0xD6, 0x1C, 0x19, 0x18, 0xCA, 0x44, 0x9A, 0x8B, 0xCE, 0x9E, 0x15,
|
|
0x06, 0x7F, 0xEA, 0xA5, 0x16, 0x97, 0xF9, 0xA5, 0x84, 0xB1, 0xD5, 0xEA,
|
|
0xE2, 0xC8, 0x51, 0x80, 0x53, 0x80, 0x38, 0xAC, 0x90, 0x34, 0xC7, 0xB1,
|
|
0x19, 0x9C, 0x9D, 0xF5, 0xA9, 0xA4, 0x6E, 0x5A, 0xA3, 0x10, 0xE3, 0x84,
|
|
0xCF, 0x3C, 0x4F, 0x51, 0xD9, 0xAD, 0xF2, 0x4F, 0x90, 0x12, 0x6F, 0x89,
|
|
0x0B, 0xCD, 0x0D, 0x47, 0x6B, 0x2F, 0xD6, 0x6C, 0x3C, 0xD0, 0xFA, 0x94,
|
|
0xFE, 0x18, 0xAC, 0xE7, 0x35, 0x09, 0xD4, 0x08, 0xF8, 0xB7, 0x39, 0x05,
|
|
0x7E, 0x2E, 0x23, 0xCB, 0x69, 0xCF, 0x36, 0xF5, 0x52, 0xA6, 0x35, 0xA2,
|
|
0x00, 0x8E, 0x9C, 0xA5, 0x9B, 0x1B, 0x76, 0x17, 0x61, 0xF6, 0x26, 0xB2,
|
|
0x8A, 0x3E, 0x18, 0x75, 0x08, 0x37, 0x1C, 0x1D, 0xB4, 0xFB, 0x52, 0xBD,
|
|
0x55, 0xC1, 0x67, 0x4E, 0x60, 0x6A, 0x2C, 0xA8, 0x81, 0x6C, 0x6D, 0xA8,
|
|
0xE2, 0x85, 0xF6, 0xA0, 0xD3, 0xC4, 0xF5, 0x5A, 0xF7, 0x1F, 0xD6, 0x3C,
|
|
0x61, 0xA5, 0x68, 0x79, 0x45, 0x3E, 0x2A, 0x2A, 0xA8, 0xE6,
|
|
};
|
|
|
|
// kPKCS7Windows is the Equifax root certificate, as exported by Windows 7.
|
|
static const uint8_t kPKCS7Windows[] = {
|
|
0x30, 0x82, 0x02, 0xb1, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
|
|
0x01, 0x07, 0x02, 0xa0, 0x82, 0x02, 0xa2, 0x30, 0x82, 0x02, 0x9e, 0x02,
|
|
0x01, 0x01, 0x31, 0x00, 0x30, 0x0b, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
|
|
0xf7, 0x0d, 0x01, 0x07, 0x01, 0xa0, 0x82, 0x02, 0x86, 0x30, 0x82, 0x02,
|
|
0x82, 0x30, 0x82, 0x01, 0xeb, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x01,
|
|
0x04, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
|
|
0x01, 0x04, 0x05, 0x00, 0x30, 0x53, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03,
|
|
0x55, 0x04, 0x06, 0x13, 0x02, 0x55, 0x53, 0x31, 0x1c, 0x30, 0x1a, 0x06,
|
|
0x03, 0x55, 0x04, 0x0a, 0x13, 0x13, 0x45, 0x71, 0x75, 0x69, 0x66, 0x61,
|
|
0x78, 0x20, 0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x20, 0x49, 0x6e, 0x63,
|
|
0x2e, 0x31, 0x26, 0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x1d,
|
|
0x45, 0x71, 0x75, 0x69, 0x66, 0x61, 0x78, 0x20, 0x53, 0x65, 0x63, 0x75,
|
|
0x72, 0x65, 0x20, 0x65, 0x42, 0x75, 0x73, 0x69, 0x6e, 0x65, 0x73, 0x73,
|
|
0x20, 0x43, 0x41, 0x2d, 0x31, 0x30, 0x1e, 0x17, 0x0d, 0x39, 0x39, 0x30,
|
|
0x36, 0x32, 0x31, 0x30, 0x34, 0x30, 0x30, 0x30, 0x30, 0x5a, 0x17, 0x0d,
|
|
0x32, 0x30, 0x30, 0x36, 0x32, 0x31, 0x30, 0x34, 0x30, 0x30, 0x30, 0x30,
|
|
0x5a, 0x30, 0x53, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06,
|
|
0x13, 0x02, 0x55, 0x53, 0x31, 0x1c, 0x30, 0x1a, 0x06, 0x03, 0x55, 0x04,
|
|
0x0a, 0x13, 0x13, 0x45, 0x71, 0x75, 0x69, 0x66, 0x61, 0x78, 0x20, 0x53,
|
|
0x65, 0x63, 0x75, 0x72, 0x65, 0x20, 0x49, 0x6e, 0x63, 0x2e, 0x31, 0x26,
|
|
0x30, 0x24, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x1d, 0x45, 0x71, 0x75,
|
|
0x69, 0x66, 0x61, 0x78, 0x20, 0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x20,
|
|
0x65, 0x42, 0x75, 0x73, 0x69, 0x6e, 0x65, 0x73, 0x73, 0x20, 0x43, 0x41,
|
|
0x2d, 0x31, 0x30, 0x81, 0x9f, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48,
|
|
0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03, 0x81, 0x8d, 0x00,
|
|
0x30, 0x81, 0x89, 0x02, 0x81, 0x81, 0x00, 0xce, 0x2f, 0x19, 0xbc, 0x17,
|
|
0xb7, 0x77, 0xde, 0x93, 0xa9, 0x5f, 0x5a, 0x0d, 0x17, 0x4f, 0x34, 0x1a,
|
|
0x0c, 0x98, 0xf4, 0x22, 0xd9, 0x59, 0xd4, 0xc4, 0x68, 0x46, 0xf0, 0xb4,
|
|
0x35, 0xc5, 0x85, 0x03, 0x20, 0xc6, 0xaf, 0x45, 0xa5, 0x21, 0x51, 0x45,
|
|
0x41, 0xeb, 0x16, 0x58, 0x36, 0x32, 0x6f, 0xe2, 0x50, 0x62, 0x64, 0xf9,
|
|
0xfd, 0x51, 0x9c, 0xaa, 0x24, 0xd9, 0xf4, 0x9d, 0x83, 0x2a, 0x87, 0x0a,
|
|
0x21, 0xd3, 0x12, 0x38, 0x34, 0x6c, 0x8d, 0x00, 0x6e, 0x5a, 0xa0, 0xd9,
|
|
0x42, 0xee, 0x1a, 0x21, 0x95, 0xf9, 0x52, 0x4c, 0x55, 0x5a, 0xc5, 0x0f,
|
|
0x38, 0x4f, 0x46, 0xfa, 0x6d, 0xf8, 0x2e, 0x35, 0xd6, 0x1d, 0x7c, 0xeb,
|
|
0xe2, 0xf0, 0xb0, 0x75, 0x80, 0xc8, 0xa9, 0x13, 0xac, 0xbe, 0x88, 0xef,
|
|
0x3a, 0x6e, 0xab, 0x5f, 0x2a, 0x38, 0x62, 0x02, 0xb0, 0x12, 0x7b, 0xfe,
|
|
0x8f, 0xa6, 0x03, 0x02, 0x03, 0x01, 0x00, 0x01, 0xa3, 0x66, 0x30, 0x64,
|
|
0x30, 0x11, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01,
|
|
0x01, 0x04, 0x04, 0x03, 0x02, 0x00, 0x07, 0x30, 0x0f, 0x06, 0x03, 0x55,
|
|
0x1d, 0x13, 0x01, 0x01, 0xff, 0x04, 0x05, 0x30, 0x03, 0x01, 0x01, 0xff,
|
|
0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80,
|
|
0x14, 0x4a, 0x78, 0x32, 0x52, 0x11, 0xdb, 0x59, 0x16, 0x36, 0x5e, 0xdf,
|
|
0xc1, 0x14, 0x36, 0x40, 0x6a, 0x47, 0x7c, 0x4c, 0xa1, 0x30, 0x1d, 0x06,
|
|
0x03, 0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x4a, 0x78, 0x32, 0x52,
|
|
0x11, 0xdb, 0x59, 0x16, 0x36, 0x5e, 0xdf, 0xc1, 0x14, 0x36, 0x40, 0x6a,
|
|
0x47, 0x7c, 0x4c, 0xa1, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
|
|
0xf7, 0x0d, 0x01, 0x01, 0x04, 0x05, 0x00, 0x03, 0x81, 0x81, 0x00, 0x75,
|
|
0x5b, 0xa8, 0x9b, 0x03, 0x11, 0xe6, 0xe9, 0x56, 0x4c, 0xcd, 0xf9, 0xa9,
|
|
0x4c, 0xc0, 0x0d, 0x9a, 0xf3, 0xcc, 0x65, 0x69, 0xe6, 0x25, 0x76, 0xcc,
|
|
0x59, 0xb7, 0xd6, 0x54, 0xc3, 0x1d, 0xcd, 0x99, 0xac, 0x19, 0xdd, 0xb4,
|
|
0x85, 0xd5, 0xe0, 0x3d, 0xfc, 0x62, 0x20, 0xa7, 0x84, 0x4b, 0x58, 0x65,
|
|
0xf1, 0xe2, 0xf9, 0x95, 0x21, 0x3f, 0xf5, 0xd4, 0x7e, 0x58, 0x1e, 0x47,
|
|
0x87, 0x54, 0x3e, 0x58, 0xa1, 0xb5, 0xb5, 0xf8, 0x2a, 0xef, 0x71, 0xe7,
|
|
0xbc, 0xc3, 0xf6, 0xb1, 0x49, 0x46, 0xe2, 0xd7, 0xa0, 0x6b, 0xe5, 0x56,
|
|
0x7a, 0x9a, 0x27, 0x98, 0x7c, 0x46, 0x62, 0x14, 0xe7, 0xc9, 0xfc, 0x6e,
|
|
0x03, 0x12, 0x79, 0x80, 0x38, 0x1d, 0x48, 0x82, 0x8d, 0xfc, 0x17, 0xfe,
|
|
0x2a, 0x96, 0x2b, 0xb5, 0x62, 0xa6, 0xa6, 0x3d, 0xbd, 0x7f, 0x92, 0x59,
|
|
0xcd, 0x5a, 0x2a, 0x82, 0xb2, 0x37, 0x79, 0x31, 0x00,
|
|
};
|
|
|
|
|
|
// kPKCS7SignedWithSignerInfo has content SignedData, but unlike other test
|
|
// objects, it contains SignerInfos as well.
|
|
static const uint8_t kPKCS7SignedWithSignerInfo[]{
|
|
0x30, 0x82, 0x03, 0x54, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
|
|
0x01, 0x07, 0x02, 0xa0, 0x82, 0x03, 0x45, 0x30, 0x82, 0x03, 0x41, 0x02,
|
|
0x01, 0x01, 0x31, 0x0f, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01,
|
|
0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00, 0x30, 0x82, 0x00, 0x25, 0x06,
|
|
0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01, 0xa0, 0x82,
|
|
0x00, 0x16, 0x04, 0x82, 0x00, 0x12, 0x49, 0x6e, 0x69, 0x7a, 0x69, 0x6f,
|
|
0x20, 0x63, 0x6f, 0x6e, 0x74, 0x65, 0x6e, 0x75, 0x74, 0x6f, 0x2e, 0x0a,
|
|
0xa0, 0x82, 0x01, 0x72, 0x30, 0x82, 0x01, 0x6e, 0x30, 0x82, 0x01, 0x14,
|
|
0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x10, 0x60, 0x5c, 0xd2, 0xd5, 0x26,
|
|
0x75, 0xb3, 0x92, 0xa5, 0xaa, 0x9b, 0x02, 0xb2, 0x6a, 0x55, 0x66, 0x30,
|
|
0x0a, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x02, 0x30,
|
|
0x0f, 0x31, 0x0d, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c, 0x04,
|
|
0x54, 0x65, 0x73, 0x74, 0x30, 0x1e, 0x17, 0x0d, 0x31, 0x38, 0x30, 0x37,
|
|
0x31, 0x36, 0x31, 0x34, 0x35, 0x36, 0x33, 0x35, 0x5a, 0x17, 0x0d, 0x31,
|
|
0x39, 0x30, 0x37, 0x31, 0x36, 0x31, 0x34, 0x35, 0x36, 0x33, 0x35, 0x5a,
|
|
0x30, 0x0f, 0x31, 0x0d, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x04, 0x03, 0x0c,
|
|
0x04, 0x54, 0x65, 0x73, 0x74, 0x30, 0x59, 0x30, 0x13, 0x06, 0x07, 0x2a,
|
|
0x86, 0x48, 0xce, 0x3d, 0x02, 0x01, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce,
|
|
0x3d, 0x03, 0x01, 0x07, 0x03, 0x42, 0x00, 0x04, 0x24, 0x4c, 0xb6, 0xcc,
|
|
0x1c, 0x69, 0x21, 0xff, 0x49, 0xd8, 0xbe, 0x26, 0x3e, 0x0b, 0x7c, 0xd0,
|
|
0x5a, 0x28, 0x65, 0x5a, 0x84, 0x6c, 0x82, 0x5e, 0xca, 0xe6, 0xec, 0xe6,
|
|
0x9a, 0x6a, 0x21, 0xc4, 0xe4, 0xf2, 0x20, 0x24, 0xc0, 0xe9, 0xf4, 0xe4,
|
|
0x74, 0x9c, 0x98, 0xa1, 0xad, 0xf2, 0x5f, 0x90, 0xde, 0x6e, 0xf9, 0x48,
|
|
0x2b, 0x67, 0x18, 0x83, 0xa7, 0x0e, 0xb4, 0xb7, 0xab, 0x9f, 0x06, 0x43,
|
|
0xa3, 0x52, 0x30, 0x50, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x01,
|
|
0x01, 0xff, 0x04, 0x04, 0x03, 0x02, 0x04, 0xf0, 0x30, 0x1d, 0x06, 0x03,
|
|
0x55, 0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0xc3, 0xc0, 0x84, 0xdf, 0x7b,
|
|
0x04, 0x0d, 0xb0, 0x38, 0xaf, 0x51, 0x8c, 0xe3, 0x97, 0xf6, 0xec, 0x20,
|
|
0xd6, 0x26, 0xe6, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18,
|
|
0x30, 0x16, 0x80, 0x14, 0xc3, 0xc0, 0x84, 0xdf, 0x7b, 0x04, 0x0d, 0xb0,
|
|
0x38, 0xaf, 0x51, 0x8c, 0xe3, 0x97, 0xf6, 0xec, 0x20, 0xd6, 0x26, 0xe6,
|
|
0x30, 0x0a, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x02,
|
|
0x03, 0x48, 0x00, 0x30, 0x45, 0x02, 0x21, 0x00, 0xde, 0x60, 0x1e, 0x57,
|
|
0x3d, 0xaf, 0xb5, 0x9b, 0xc5, 0x51, 0xd5, 0x8e, 0x3e, 0x7b, 0x9e, 0xda,
|
|
0x06, 0x12, 0xdd, 0x01, 0x12, 0x80, 0x5a, 0x22, 0x17, 0xb7, 0x34, 0x75,
|
|
0x9b, 0x88, 0x44, 0x17, 0x02, 0x20, 0x67, 0xc3, 0xfd, 0xe6, 0x07, 0x80,
|
|
0xd4, 0x1c, 0x1d, 0x7a, 0x3b, 0x90, 0x29, 0x1f, 0x3d, 0x39, 0xc4, 0xdc,
|
|
0x2f, 0x20, 0x6d, 0xcc, 0xba, 0x2f, 0x98, 0x2c, 0x06, 0xb6, 0x7c, 0x09,
|
|
0xb2, 0x32, 0x31, 0x82, 0x01, 0x8a, 0x30, 0x82, 0x01, 0x86, 0x02, 0x01,
|
|
0x01, 0x30, 0x23, 0x30, 0x0f, 0x31, 0x0d, 0x30, 0x0b, 0x06, 0x03, 0x55,
|
|
0x04, 0x03, 0x0c, 0x04, 0x54, 0x65, 0x73, 0x74, 0x02, 0x10, 0x60, 0x5c,
|
|
0xd2, 0xd5, 0x26, 0x75, 0xb3, 0x92, 0xa5, 0xaa, 0x9b, 0x02, 0xb2, 0x6a,
|
|
0x55, 0x66, 0x30, 0x0d, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03,
|
|
0x04, 0x02, 0x01, 0x05, 0x00, 0xa0, 0x81, 0xf7, 0x30, 0x18, 0x06, 0x09,
|
|
0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x03, 0x31, 0x0b, 0x06,
|
|
0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01, 0x30, 0x1c,
|
|
0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x05, 0x31,
|
|
0x0f, 0x17, 0x0d, 0x31, 0x38, 0x30, 0x37, 0x31, 0x36, 0x31, 0x34, 0x35,
|
|
0x36, 0x33, 0x35, 0x5a, 0x30, 0x2a, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
|
|
0xf7, 0x0d, 0x01, 0x09, 0x34, 0x31, 0x1d, 0x30, 0x1b, 0x30, 0x0d, 0x06,
|
|
0x09, 0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01, 0x05, 0x00,
|
|
0xa1, 0x0a, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x02,
|
|
0x30, 0x2f, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09,
|
|
0x04, 0x31, 0x22, 0x04, 0x20, 0x72, 0x4c, 0x51, 0xbb, 0xe7, 0x6d, 0xa0,
|
|
0x5a, 0xfb, 0x20, 0xcb, 0xe8, 0xeb, 0x03, 0x7c, 0xda, 0xe1, 0xaf, 0xd7,
|
|
0x13, 0x12, 0x5d, 0x2d, 0xc1, 0x3d, 0x55, 0x2d, 0xa9, 0xf4, 0x42, 0xd2,
|
|
0x4d, 0x30, 0x60, 0x06, 0x0b, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
|
|
0x09, 0x10, 0x02, 0x2f, 0x31, 0x51, 0x30, 0x4f, 0x30, 0x4d, 0x30, 0x4b,
|
|
0x04, 0x20, 0xba, 0xbc, 0x08, 0x43, 0x4c, 0x58, 0x26, 0x73, 0x01, 0xe0,
|
|
0x06, 0x86, 0x1d, 0x27, 0xec, 0xa1, 0x25, 0x67, 0x0e, 0x79, 0x27, 0x97,
|
|
0x24, 0x8e, 0x76, 0xa5, 0x71, 0x7a, 0x5b, 0xf9, 0x93, 0xc2, 0x30, 0x27,
|
|
0x30, 0x13, 0xa4, 0x11, 0x30, 0x0f, 0x31, 0x0d, 0x30, 0x0b, 0x06, 0x03,
|
|
0x55, 0x04, 0x03, 0x0c, 0x04, 0x54, 0x65, 0x73, 0x74, 0x02, 0x10, 0x60,
|
|
0x5c, 0xd2, 0xd5, 0x26, 0x75, 0xb3, 0x92, 0xa5, 0xaa, 0x9b, 0x02, 0xb2,
|
|
0x6a, 0x55, 0x66, 0x30, 0x0a, 0x06, 0x08, 0x2a, 0x86, 0x48, 0xce, 0x3d,
|
|
0x04, 0x03, 0x02, 0x04, 0x47, 0x30, 0x45, 0x02, 0x21, 0x00, 0xf1, 0x04,
|
|
0x30, 0x2e, 0xab, 0xb4, 0x28, 0xec, 0xc8, 0xe7, 0x1c, 0xe2, 0xe3, 0x8f,
|
|
0x6c, 0xbe, 0xd8, 0x48, 0xa8, 0xe9, 0xa2, 0xb5, 0xd5, 0xda, 0x19, 0x93,
|
|
0x3e, 0x48, 0x5c, 0x83, 0xcc, 0x71, 0x02, 0x20, 0x0c, 0xbb, 0x40, 0xa0,
|
|
0xb7, 0xb9, 0xb2, 0xe0, 0x48, 0x92, 0x06, 0x22, 0xfb, 0x28, 0x6f, 0xd1,
|
|
0x46, 0x95, 0xf2, 0x4c, 0xf6, 0x50, 0xbd, 0xaa, 0x40, 0xb8, 0x85, 0xf8,
|
|
0x4c, 0x34, 0xbb, 0xb9,
|
|
};
|
|
|
|
// kOpenSSLCRL is the Equifax CRL, converted to PKCS#7 form by:
|
|
// openssl crl2pkcs7 -inform DER -in secureca.crl
|
|
static const uint8_t kOpenSSLCRL[] = {
|
|
0x30, 0x82, 0x03, 0x85, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
|
|
0x01, 0x07, 0x02, 0xa0, 0x82, 0x03, 0x76, 0x30, 0x82, 0x03, 0x72, 0x02,
|
|
0x01, 0x01, 0x31, 0x00, 0x30, 0x0b, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86,
|
|
0xf7, 0x0d, 0x01, 0x07, 0x01, 0xa0, 0x00, 0xa1, 0x82, 0x03, 0x58, 0x30,
|
|
0x82, 0x03, 0x54, 0x30, 0x82, 0x02, 0xbd, 0x30, 0x0d, 0x06, 0x09, 0x2a,
|
|
0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00, 0x30, 0x4e,
|
|
0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x55,
|
|
0x53, 0x31, 0x10, 0x30, 0x0e, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13, 0x07,
|
|
0x45, 0x71, 0x75, 0x69, 0x66, 0x61, 0x78, 0x31, 0x2d, 0x30, 0x2b, 0x06,
|
|
0x03, 0x55, 0x04, 0x0b, 0x13, 0x24, 0x45, 0x71, 0x75, 0x69, 0x66, 0x61,
|
|
0x78, 0x20, 0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x20, 0x43, 0x65, 0x72,
|
|
0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x65, 0x20, 0x41, 0x75, 0x74,
|
|
0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x17, 0x0d, 0x31, 0x35, 0x30, 0x32,
|
|
0x32, 0x37, 0x30, 0x31, 0x32, 0x33, 0x30, 0x30, 0x5a, 0x17, 0x0d, 0x31,
|
|
0x35, 0x30, 0x33, 0x30, 0x39, 0x30, 0x31, 0x32, 0x33, 0x30, 0x30, 0x5a,
|
|
0x30, 0x82, 0x02, 0x3c, 0x30, 0x14, 0x02, 0x03, 0x0f, 0x58, 0xe4, 0x17,
|
|
0x0d, 0x31, 0x34, 0x30, 0x34, 0x32, 0x37, 0x30, 0x38, 0x31, 0x39, 0x32,
|
|
0x32, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x14, 0x76, 0x19, 0x17, 0x0d, 0x31,
|
|
0x34, 0x30, 0x36, 0x31, 0x38, 0x31, 0x35, 0x30, 0x30, 0x30, 0x33, 0x5a,
|
|
0x30, 0x14, 0x02, 0x03, 0x0f, 0x9a, 0xfb, 0x17, 0x0d, 0x31, 0x34, 0x30,
|
|
0x34, 0x32, 0x39, 0x31, 0x38, 0x30, 0x39, 0x31, 0x37, 0x5a, 0x30, 0x14,
|
|
0x02, 0x03, 0x14, 0x8b, 0xc0, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x37, 0x30,
|
|
0x39, 0x31, 0x39, 0x34, 0x36, 0x33, 0x33, 0x5a, 0x30, 0x14, 0x02, 0x03,
|
|
0x14, 0xe4, 0x9c, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x34, 0x31, 0x36, 0x32,
|
|
0x33, 0x33, 0x39, 0x33, 0x35, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x0f, 0x86,
|
|
0x07, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x35, 0x32, 0x31, 0x31, 0x35, 0x35,
|
|
0x30, 0x35, 0x33, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x12, 0xe2, 0x29, 0x17,
|
|
0x0d, 0x31, 0x34, 0x30, 0x36, 0x31, 0x37, 0x31, 0x38, 0x35, 0x35, 0x31,
|
|
0x35, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x0d, 0x42, 0x66, 0x17, 0x0d, 0x31,
|
|
0x32, 0x30, 0x36, 0x32, 0x37, 0x31, 0x37, 0x31, 0x30, 0x35, 0x33, 0x5a,
|
|
0x30, 0x14, 0x02, 0x03, 0x03, 0x1e, 0x33, 0x17, 0x0d, 0x30, 0x32, 0x30,
|
|
0x35, 0x31, 0x35, 0x31, 0x33, 0x30, 0x36, 0x31, 0x31, 0x5a, 0x30, 0x14,
|
|
0x02, 0x03, 0x12, 0xe2, 0x23, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x36, 0x30,
|
|
0x36, 0x32, 0x30, 0x34, 0x30, 0x32, 0x31, 0x5a, 0x30, 0x14, 0x02, 0x03,
|
|
0x13, 0x9c, 0xab, 0x17, 0x0d, 0x31, 0x30, 0x30, 0x37, 0x32, 0x39, 0x31,
|
|
0x36, 0x34, 0x34, 0x33, 0x39, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x12, 0xc6,
|
|
0x0a, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x36, 0x30, 0x36, 0x32, 0x32, 0x32,
|
|
0x31, 0x33, 0x39, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x03, 0x25, 0x85, 0x17,
|
|
0x0d, 0x30, 0x32, 0x30, 0x35, 0x31, 0x34, 0x31, 0x38, 0x31, 0x31, 0x35,
|
|
0x37, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x14, 0x86, 0xe6, 0x17, 0x0d, 0x31,
|
|
0x34, 0x30, 0x37, 0x32, 0x35, 0x30, 0x32, 0x30, 0x30, 0x33, 0x38, 0x5a,
|
|
0x30, 0x14, 0x02, 0x03, 0x13, 0x9c, 0xa1, 0x17, 0x0d, 0x31, 0x30, 0x30,
|
|
0x37, 0x32, 0x39, 0x31, 0x36, 0x34, 0x37, 0x33, 0x32, 0x5a, 0x30, 0x14,
|
|
0x02, 0x03, 0x15, 0x4d, 0x5c, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x34, 0x33,
|
|
0x30, 0x30, 0x30, 0x30, 0x34, 0x34, 0x32, 0x5a, 0x30, 0x14, 0x02, 0x03,
|
|
0x0f, 0xfa, 0x2d, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x36, 0x31, 0x37, 0x31,
|
|
0x38, 0x35, 0x30, 0x31, 0x31, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x13, 0x75,
|
|
0x55, 0x17, 0x0d, 0x31, 0x35, 0x30, 0x31, 0x31, 0x38, 0x30, 0x32, 0x32,
|
|
0x31, 0x33, 0x33, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x0f, 0x56, 0x96, 0x17,
|
|
0x0d, 0x31, 0x34, 0x30, 0x36, 0x32, 0x34, 0x31, 0x32, 0x33, 0x31, 0x30,
|
|
0x32, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x0b, 0x80, 0x8a, 0x17, 0x0d, 0x31,
|
|
0x32, 0x30, 0x36, 0x32, 0x37, 0x31, 0x37, 0x31, 0x30, 0x32, 0x35, 0x5a,
|
|
0x30, 0x14, 0x02, 0x03, 0x0f, 0x94, 0x16, 0x17, 0x0d, 0x31, 0x30, 0x30,
|
|
0x33, 0x30, 0x31, 0x31, 0x33, 0x34, 0x35, 0x33, 0x31, 0x5a, 0x30, 0x14,
|
|
0x02, 0x03, 0x14, 0x16, 0xb3, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x36, 0x31,
|
|
0x38, 0x31, 0x34, 0x33, 0x32, 0x35, 0x36, 0x5a, 0x30, 0x14, 0x02, 0x03,
|
|
0x0a, 0xe1, 0x85, 0x17, 0x0d, 0x31, 0x32, 0x30, 0x36, 0x32, 0x37, 0x31,
|
|
0x37, 0x31, 0x30, 0x31, 0x37, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x14, 0xcc,
|
|
0x3e, 0x17, 0x0d, 0x31, 0x34, 0x30, 0x37, 0x31, 0x31, 0x31, 0x32, 0x35,
|
|
0x35, 0x33, 0x31, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x10, 0x5b, 0xcb, 0x17,
|
|
0x0d, 0x31, 0x30, 0x30, 0x37, 0x33, 0x30, 0x32, 0x31, 0x33, 0x31, 0x32,
|
|
0x30, 0x5a, 0x30, 0x14, 0x02, 0x03, 0x15, 0x6a, 0x1f, 0x17, 0x0d, 0x31,
|
|
0x34, 0x30, 0x32, 0x32, 0x36, 0x31, 0x32, 0x33, 0x35, 0x31, 0x39, 0x5a,
|
|
0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
|
|
0x05, 0x05, 0x00, 0x03, 0x81, 0x81, 0x00, 0x1d, 0x5c, 0x27, 0x07, 0x11,
|
|
0x03, 0xf2, 0x00, 0xbd, 0xf4, 0x46, 0x3e, 0x71, 0xfd, 0x10, 0x84, 0x83,
|
|
0xd9, 0xd2, 0xd2, 0x19, 0xa0, 0x20, 0xf7, 0x1a, 0x43, 0x3d, 0xac, 0xda,
|
|
0x33, 0xfc, 0xb7, 0x42, 0x60, 0x1a, 0xa4, 0xa8, 0xb2, 0x07, 0x5c, 0x51,
|
|
0x16, 0xc0, 0x42, 0x80, 0x0a, 0x0f, 0xf0, 0x47, 0x5b, 0x4b, 0x78, 0x90,
|
|
0xaf, 0xc7, 0xac, 0x48, 0xf8, 0xca, 0x3c, 0x13, 0x5e, 0xf6, 0xd1, 0x88,
|
|
0xae, 0x55, 0xa3, 0x0c, 0x8a, 0x62, 0x47, 0x29, 0xf8, 0x72, 0xb8, 0x24,
|
|
0x17, 0xaf, 0xb2, 0x06, 0x1e, 0xa7, 0x72, 0x76, 0xab, 0x96, 0x1d, 0xe0,
|
|
0x7c, 0xd4, 0x0c, 0x42, 0x82, 0x3d, 0x4a, 0x8e, 0x15, 0x77, 0x2f, 0x3c,
|
|
0x2a, 0x8c, 0x3a, 0x04, 0x10, 0x55, 0xdc, 0xbb, 0xba, 0xb1, 0x91, 0xee,
|
|
0x7b, 0xe7, 0x23, 0xc5, 0x71, 0x13, 0xae, 0x6b, 0x21, 0x35, 0xd3, 0x64,
|
|
0xf0, 0x00, 0x54, 0x31, 0x00,
|
|
};
|
|
|
|
// kPEMCert is the result of exporting the mail.google.com certificate from
|
|
// Chrome and then running it through:
|
|
// openssl pkcs7 -inform DER -in mail.google.com -outform PEM
|
|
static const char kPEMCert[] =
|
|
"-----BEGIN PKCS7-----\n"
|
|
"MIID+wYJKoZIhvcNAQcCoIID7DCCA+gCAQExADALBgkqhkiG9w0BBwGgggPQMIID\n"
|
|
"zDCCArSgAwIBAgIIWesoywKxoNQwDQYJKoZIhvcNAQELBQAwSTELMAkGA1UEBhMC\n"
|
|
"VVMxEzARBgNVBAoTCkdvb2dsZSBJbmMxJTAjBgNVBAMTHEdvb2dsZSBJbnRlcm5l\n"
|
|
"dCBBdXRob3JpdHkgRzIwHhcNMTUwMjExMTQxNTA2WhcNMTUwNTEyMDAwMDAwWjBp\n"
|
|
"MQswCQYDVQQGEwJVUzETMBEGA1UECAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91\n"
|
|
"bnRhaW4gVmlldzETMBEGA1UECgwKR29vZ2xlIEluYzEYMBYGA1UEAwwPbWFpbC5n\n"
|
|
"b29nbGUuY29tMFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE7MdALmCkcRRf/tzQ\n"
|
|
"a8eu3J7S5CTQa5ns0ReF9ktlbB1RL56BVGAu4p7BrT32D6gDpiggXq3gxN81A0TG\n"
|
|
"C2yICKOCAWEwggFdMB0GA1UdJQQWMBQGCCsGAQUFBwMBBggrBgEFBQcDAjAsBgNV\n"
|
|
"HREEJTAjgg9tYWlsLmdvb2dsZS5jb22CEGluYm94Lmdvb2dsZS5jb20wCwYDVR0P\n"
|
|
"BAQDAgeAMGgGCCsGAQUFBwEBBFwwWjArBggrBgEFBQcwAoYfaHR0cDovL3BraS5n\n"
|
|
"b29nbGUuY29tL0dJQUcyLmNydDArBggrBgEFBQcwAYYfaHR0cDovL2NsaWVudHMx\n"
|
|
"Lmdvb2dsZS5jb20vb2NzcDAdBgNVHQ4EFgQUQqsYsRoWLiG6qmV2N1mpYaHawxAw\n"
|
|
"DAYDVR0TAQH/BAIwADAfBgNVHSMEGDAWgBRK3QYWG7z2aLV29YG2u2IaulqBLzAX\n"
|
|
"BgNVHSAEEDAOMAwGCisGAQQB1nkCBQEwMAYDVR0fBCkwJzAloCOgIYYfaHR0cDov\n"
|
|
"L3BraS5nb29nbGUuY29tL0dJQUcyLmNybDANBgkqhkiG9w0BAQsFAAOCAQEAKNh3\n"
|
|
"isNuGBisPKVlekOsZR6S8oP/fS/xt6Hqvg0EwFXvhxoJ40rxAB2LMykY17e+ln3P\n"
|
|
"MwBBlRkwY1btcDT15JwzgaZb38rq/r+Pkb5Qgmx/InA/pw0QHDtwHQp5uXZuvu6p\n"
|
|
"J/SlCwyq7EOvByWdVQcMU/dhGa3idXEkn/zwfqcG6YjdWKoDmXWZYv3RiP3wJcRB\n"
|
|
"9+3U1wOe3uebnZLRWO6/w0to1XY8TFHklyw5rwIE5sbxOx5N3Ne8+GgPrUDvGAz0\n"
|
|
"rAUKnh3b7GNXL1qlZh2qkhB6rUzvtPpg397Asg3xVtExCHOk4zPqzzicttoEbVVy\n"
|
|
"0T8rIMUNwC4Beh4JVjEA\n"
|
|
"-----END PKCS7-----\n";
|
|
|
|
// kPEMCRL is the result of downloading the Equifax CRL and running:
|
|
// openssl crl2pkcs7 -inform DER -in secureca.crl */
|
|
static const char kPEMCRL[] =
|
|
"-----BEGIN PKCS7-----\n"
|
|
"MIIDhQYJKoZIhvcNAQcCoIIDdjCCA3ICAQExADALBgkqhkiG9w0BBwGgAKGCA1gw\n"
|
|
"ggNUMIICvTANBgkqhkiG9w0BAQUFADBOMQswCQYDVQQGEwJVUzEQMA4GA1UEChMH\n"
|
|
"RXF1aWZheDEtMCsGA1UECxMkRXF1aWZheCBTZWN1cmUgQ2VydGlmaWNhdGUgQXV0\n"
|
|
"aG9yaXR5Fw0xNTAyMjcwMTIzMDBaFw0xNTAzMDkwMTIzMDBaMIICPDAUAgMPWOQX\n"
|
|
"DTE0MDQyNzA4MTkyMlowFAIDFHYZFw0xNDA2MTgxNTAwMDNaMBQCAw+a+xcNMTQw\n"
|
|
"NDI5MTgwOTE3WjAUAgMUi8AXDTE0MDcwOTE5NDYzM1owFAIDFOScFw0xNDA0MTYy\n"
|
|
"MzM5MzVaMBQCAw+GBxcNMTQwNTIxMTU1MDUzWjAUAgMS4ikXDTE0MDYxNzE4NTUx\n"
|
|
"NVowFAIDDUJmFw0xMjA2MjcxNzEwNTNaMBQCAwMeMxcNMDIwNTE1MTMwNjExWjAU\n"
|
|
"AgMS4iMXDTE0MDYwNjIwNDAyMVowFAIDE5yrFw0xMDA3MjkxNjQ0MzlaMBQCAxLG\n"
|
|
"ChcNMTQwNjA2MjIyMTM5WjAUAgMDJYUXDTAyMDUxNDE4MTE1N1owFAIDFIbmFw0x\n"
|
|
"NDA3MjUwMjAwMzhaMBQCAxOcoRcNMTAwNzI5MTY0NzMyWjAUAgMVTVwXDTE0MDQz\n"
|
|
"MDAwMDQ0MlowFAIDD/otFw0xNDA2MTcxODUwMTFaMBQCAxN1VRcNMTUwMTE4MDIy\n"
|
|
"MTMzWjAUAgMPVpYXDTE0MDYyNDEyMzEwMlowFAIDC4CKFw0xMjA2MjcxNzEwMjVa\n"
|
|
"MBQCAw+UFhcNMTAwMzAxMTM0NTMxWjAUAgMUFrMXDTE0MDYxODE0MzI1NlowFAID\n"
|
|
"CuGFFw0xMjA2MjcxNzEwMTdaMBQCAxTMPhcNMTQwNzExMTI1NTMxWjAUAgMQW8sX\n"
|
|
"DTEwMDczMDIxMzEyMFowFAIDFWofFw0xNDAyMjYxMjM1MTlaMA0GCSqGSIb3DQEB\n"
|
|
"BQUAA4GBAB1cJwcRA/IAvfRGPnH9EISD2dLSGaAg9xpDPazaM/y3QmAapKiyB1xR\n"
|
|
"FsBCgAoP8EdbS3iQr8esSPjKPBNe9tGIrlWjDIpiRyn4crgkF6+yBh6ncnarlh3g\n"
|
|
"fNQMQoI9So4Vdy88Kow6BBBV3Lu6sZHue+cjxXETrmshNdNk8ABUMQA=\n"
|
|
"-----END PKCS7-----\n";
|
|
|
|
static void TestCertReparse(const uint8_t *der_bytes, size_t der_len) {
|
|
bssl::UniquePtr<STACK_OF(X509)> certs(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
bssl::UniquePtr<STACK_OF(X509)> certs2(sk_X509_new_null());
|
|
ASSERT_TRUE(certs2);
|
|
uint8_t *result_data, *result2_data;
|
|
size_t result_len, result2_len;
|
|
|
|
CBS pkcs7;
|
|
CBS_init(&pkcs7, der_bytes, der_len);
|
|
ASSERT_TRUE(PKCS7_get_certificates(certs.get(), &pkcs7));
|
|
EXPECT_EQ(0u, CBS_len(&pkcs7));
|
|
|
|
// Some test cases contain indefinite-length BER input
|
|
CBS der_conv_out;
|
|
uint8_t *der_conv = nullptr;
|
|
CBS_init(&pkcs7, der_bytes, der_len);
|
|
ASSERT_TRUE(CBS_asn1_ber_to_der(&pkcs7, &der_conv_out, &der_conv));
|
|
bool is_ber = der_conv != nullptr;
|
|
bssl::UniquePtr<uint8_t> free_der_conv(der_conv);
|
|
|
|
bssl::ScopedCBB cbb;
|
|
ASSERT_TRUE(CBB_init(cbb.get(), der_len));
|
|
ASSERT_TRUE(PKCS7_bundle_certificates(cbb.get(), certs.get()));
|
|
ASSERT_TRUE(CBB_finish(cbb.get(), &result_data, &result_len));
|
|
bssl::UniquePtr<uint8_t> free_result_data(result_data);
|
|
|
|
CBS_init(&pkcs7, result_data, result_len);
|
|
ASSERT_TRUE(PKCS7_get_certificates(certs2.get(), &pkcs7));
|
|
EXPECT_EQ(0u, CBS_len(&pkcs7));
|
|
|
|
// PKCS#7 stores certificates in a SET OF, so |PKCS7_bundle_certificates| may
|
|
// not preserve the original order. All of our test inputs are already sorted,
|
|
// but this check should be relaxed if we add others.
|
|
ASSERT_EQ(sk_X509_num(certs.get()), sk_X509_num(certs2.get()));
|
|
for (size_t i = 0; i < sk_X509_num(certs.get()); i++) {
|
|
X509 *a = sk_X509_value(certs.get(), i);
|
|
X509 *b = sk_X509_value(certs2.get(), i);
|
|
ASSERT_EQ(0, X509_cmp(a, b));
|
|
}
|
|
|
|
ASSERT_TRUE(CBB_init(cbb.get(), der_len));
|
|
ASSERT_TRUE(PKCS7_bundle_certificates(cbb.get(), certs2.get()));
|
|
ASSERT_TRUE(CBB_finish(cbb.get(), &result2_data, &result2_len));
|
|
bssl::UniquePtr<uint8_t> free_result2_data(result2_data);
|
|
|
|
EXPECT_EQ(Bytes(result_data, result_len), Bytes(result2_data, result2_len));
|
|
|
|
// Parse with the legacy API instead.
|
|
const uint8_t *ptr = der_bytes;
|
|
bssl::UniquePtr<PKCS7> pkcs7_obj(d2i_PKCS7(nullptr, &ptr, der_len));
|
|
ASSERT_TRUE(pkcs7_obj);
|
|
// |ASN1_item_d2i| natively handles BER, so the pointer always advances by
|
|
// the full input length regardless of whether the input is BER or DER.
|
|
EXPECT_EQ(ptr, der_bytes + der_len);
|
|
bssl::UniquePtr<PKCS7> pkcs7_dup(PKCS7_dup(pkcs7_obj.get()));
|
|
ASSERT_TRUE(pkcs7_dup);
|
|
EXPECT_EQ(OBJ_obj2nid(pkcs7_obj.get()->type),
|
|
OBJ_obj2nid(pkcs7_dup.get()->type));
|
|
|
|
ASSERT_TRUE(PKCS7_type_is_signed(pkcs7_obj.get()));
|
|
const STACK_OF(X509) *certs3 = pkcs7_obj->d.sign->cert;
|
|
ASSERT_EQ(sk_X509_num(certs.get()), sk_X509_num(certs3));
|
|
for (size_t i = 0; i < sk_X509_num(certs.get()); i++) {
|
|
X509 *a = sk_X509_value(certs.get(), i);
|
|
X509 *b = sk_X509_value(certs3, i);
|
|
ASSERT_EQ(0, X509_cmp(a, b));
|
|
}
|
|
|
|
// Serialize the original object. This should echo back the original saved
|
|
// bytes.
|
|
uint8_t *result3_data = nullptr;
|
|
int result3_len = i2d_PKCS7(pkcs7_obj.get(), &result3_data);
|
|
ASSERT_GT(result3_len, 0);
|
|
bssl::UniquePtr<uint8_t> free_result3_data(result3_data);
|
|
if (is_ber) {
|
|
EXPECT_EQ(Bytes(der_conv, CBS_len(&der_conv_out)),
|
|
Bytes(result3_data, result3_len));
|
|
} else {
|
|
EXPECT_EQ(Bytes(der_bytes, der_len), Bytes(result3_data, result3_len));
|
|
}
|
|
|
|
// Make a new object with the legacy API.
|
|
pkcs7_obj.reset(
|
|
PKCS7_sign(nullptr, nullptr, certs.get(), nullptr, PKCS7_DETACHED));
|
|
ASSERT_TRUE(pkcs7_obj);
|
|
|
|
ASSERT_TRUE(PKCS7_type_is_signed(pkcs7_obj.get()));
|
|
const STACK_OF(X509) *certs4 = pkcs7_obj->d.sign->cert;
|
|
ASSERT_EQ(sk_X509_num(certs.get()), sk_X509_num(certs4));
|
|
for (size_t i = 0; i < sk_X509_num(certs.get()); i++) {
|
|
X509 *a = sk_X509_value(certs.get(), i);
|
|
X509 *b = sk_X509_value(certs4, i);
|
|
ASSERT_EQ(0, X509_cmp(a, b));
|
|
}
|
|
|
|
// This new object should serialize canonically.
|
|
uint8_t *result4_data = nullptr;
|
|
int result4_len = i2d_PKCS7(pkcs7_obj.get(), &result4_data);
|
|
ASSERT_GT(result4_len, 0);
|
|
bssl::UniquePtr<uint8_t> free_result4_data(result4_data);
|
|
EXPECT_EQ(Bytes(result_data, result_len), Bytes(result4_data, result4_len));
|
|
}
|
|
|
|
static void TestCRLReparse(const uint8_t *der_bytes, size_t der_len) {
|
|
bssl::UniquePtr<STACK_OF(X509_CRL)> crls(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(crls);
|
|
bssl::UniquePtr<STACK_OF(X509_CRL)> crls2(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(crls2);
|
|
uint8_t *result_data, *result2_data;
|
|
size_t result_len, result2_len;
|
|
|
|
CBS pkcs7;
|
|
CBS_init(&pkcs7, der_bytes, der_len);
|
|
ASSERT_TRUE(PKCS7_get_CRLs(crls.get(), &pkcs7));
|
|
EXPECT_EQ(0u, CBS_len(&pkcs7));
|
|
|
|
bssl::ScopedCBB cbb;
|
|
ASSERT_TRUE(CBB_init(cbb.get(), der_len));
|
|
ASSERT_TRUE(PKCS7_bundle_CRLs(cbb.get(), crls.get()));
|
|
ASSERT_TRUE(CBB_finish(cbb.get(), &result_data, &result_len));
|
|
bssl::UniquePtr<uint8_t> free_result_data(result_data);
|
|
|
|
CBS_init(&pkcs7, result_data, result_len);
|
|
ASSERT_TRUE(PKCS7_get_CRLs(crls2.get(), &pkcs7));
|
|
EXPECT_EQ(0u, CBS_len(&pkcs7));
|
|
|
|
// PKCS#7 stores CRLs in a SET OF, so |PKCS7_bundle_CRLs| may not preserve the
|
|
// original order. All of our test inputs are already sorted, but this check
|
|
// should be relaxed if we add others.
|
|
ASSERT_EQ(sk_X509_CRL_num(crls.get()), sk_X509_CRL_num(crls.get()));
|
|
for (size_t i = 0; i < sk_X509_CRL_num(crls.get()); i++) {
|
|
X509_CRL *a = sk_X509_CRL_value(crls.get(), i);
|
|
X509_CRL *b = sk_X509_CRL_value(crls2.get(), i);
|
|
ASSERT_EQ(0, X509_CRL_cmp(a, b));
|
|
}
|
|
|
|
ASSERT_TRUE(CBB_init(cbb.get(), der_len));
|
|
ASSERT_TRUE(PKCS7_bundle_CRLs(cbb.get(), crls2.get()));
|
|
ASSERT_TRUE(CBB_finish(cbb.get(), &result2_data, &result2_len));
|
|
bssl::UniquePtr<uint8_t> free_result2_data(result2_data);
|
|
|
|
EXPECT_EQ(Bytes(result_data, result_len), Bytes(result2_data, result2_len));
|
|
|
|
// Parse with the legacy API instead.
|
|
const uint8_t *ptr = der_bytes;
|
|
bssl::UniquePtr<PKCS7> pkcs7_obj(d2i_PKCS7(nullptr, &ptr, der_len));
|
|
ASSERT_TRUE(pkcs7_obj);
|
|
EXPECT_EQ(ptr, der_bytes + der_len);
|
|
|
|
ASSERT_TRUE(PKCS7_type_is_signed(pkcs7_obj.get()));
|
|
const STACK_OF(X509_CRL) *crls3 = pkcs7_obj->d.sign->crl;
|
|
ASSERT_EQ(sk_X509_CRL_num(crls.get()), sk_X509_CRL_num(crls3));
|
|
for (size_t i = 0; i < sk_X509_CRL_num(crls.get()); i++) {
|
|
X509_CRL *a = sk_X509_CRL_value(crls.get(), i);
|
|
X509_CRL *b = sk_X509_CRL_value(crls3, i);
|
|
ASSERT_EQ(0, X509_CRL_cmp(a, b));
|
|
}
|
|
|
|
ptr = result_data;
|
|
pkcs7_obj.reset(d2i_PKCS7(nullptr, &ptr, result_len));
|
|
ASSERT_TRUE(pkcs7_obj);
|
|
EXPECT_EQ(ptr, result_data + result_len);
|
|
|
|
ASSERT_TRUE(PKCS7_type_is_signed(pkcs7_obj.get()));
|
|
const STACK_OF(X509_CRL) *crls4 = pkcs7_obj->d.sign->crl;
|
|
ASSERT_EQ(sk_X509_CRL_num(crls.get()), sk_X509_CRL_num(crls4));
|
|
for (size_t i = 0; i < sk_X509_CRL_num(crls.get()); i++) {
|
|
X509_CRL *a = sk_X509_CRL_value(crls.get(), i);
|
|
X509_CRL *b = sk_X509_CRL_value(crls4, i);
|
|
ASSERT_EQ(0, X509_CRL_cmp(a, b));
|
|
}
|
|
}
|
|
|
|
static void TestPEMCerts(const char *pem) {
|
|
bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<STACK_OF(X509)> certs(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
|
|
ASSERT_TRUE(PKCS7_get_PEM_certificates(certs.get(), bio.get()));
|
|
ASSERT_EQ(1u, sk_X509_num(certs.get()));
|
|
}
|
|
|
|
static void TestPEMCRLs(const char *pem) {
|
|
bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(pem, strlen(pem)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<STACK_OF(X509_CRL)> crls(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(crls);
|
|
|
|
ASSERT_TRUE(PKCS7_get_PEM_CRLs(crls.get(), bio.get()));
|
|
ASSERT_EQ(1u, sk_X509_CRL_num(crls.get()));
|
|
}
|
|
|
|
TEST(PKCS7Test, CertReparseNSS) {
|
|
TestCertReparse(kPKCS7NSS, sizeof(kPKCS7NSS));
|
|
}
|
|
|
|
TEST(PKCS7Test, CertReparseWindows) {
|
|
TestCertReparse(kPKCS7Windows, sizeof(kPKCS7Windows));
|
|
}
|
|
|
|
TEST(PKCS7Test, CertSignedWithSignerInfos) {
|
|
TestCertReparse(kPKCS7SignedWithSignerInfo,
|
|
sizeof(kPKCS7SignedWithSignerInfo));
|
|
}
|
|
|
|
TEST(PKCS7Test, CrlReparse) {
|
|
TestCRLReparse(kOpenSSLCRL, sizeof(kOpenSSLCRL));
|
|
}
|
|
|
|
TEST(PKCS7Test, PEMCerts) { TestPEMCerts(kPEMCert); }
|
|
|
|
TEST(PKCS7Test, PEMCRLs) { TestPEMCRLs(kPEMCRL); }
|
|
|
|
// Test that we output certificates in the canonical DER order.
|
|
TEST(PKCS7Test, SortCerts) {
|
|
// kPKCS7NSS contains three certificates in the canonical DER order.
|
|
CBS pkcs7;
|
|
CBS_init(&pkcs7, kPKCS7NSS, sizeof(kPKCS7NSS));
|
|
bssl::UniquePtr<STACK_OF(X509)> certs(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
ASSERT_TRUE(PKCS7_get_certificates(certs.get(), &pkcs7));
|
|
ASSERT_EQ(3u, sk_X509_num(certs.get()));
|
|
|
|
X509 *cert1 = sk_X509_value(certs.get(), 0);
|
|
X509 *cert2 = sk_X509_value(certs.get(), 1);
|
|
X509 *cert3 = sk_X509_value(certs.get(), 2);
|
|
|
|
auto check_order = [&](X509 *new_cert1, X509 *new_cert2, X509 *new_cert3) {
|
|
// Bundle the certificates in the new order.
|
|
bssl::UniquePtr<STACK_OF(X509)> new_certs(sk_X509_new_null());
|
|
ASSERT_TRUE(new_certs);
|
|
ASSERT_TRUE(bssl::PushToStack(new_certs.get(), bssl::UpRef(new_cert1)));
|
|
ASSERT_TRUE(bssl::PushToStack(new_certs.get(), bssl::UpRef(new_cert2)));
|
|
ASSERT_TRUE(bssl::PushToStack(new_certs.get(), bssl::UpRef(new_cert3)));
|
|
bssl::ScopedCBB cbb;
|
|
ASSERT_TRUE(CBB_init(cbb.get(), sizeof(kPKCS7NSS)));
|
|
ASSERT_TRUE(PKCS7_bundle_certificates(cbb.get(), new_certs.get()));
|
|
|
|
// The bundle should be sorted back to the original order.
|
|
CBS cbs;
|
|
CBS_init(&cbs, CBB_data(cbb.get()), CBB_len(cbb.get()));
|
|
bssl::UniquePtr<STACK_OF(X509)> result(sk_X509_new_null());
|
|
ASSERT_TRUE(result);
|
|
ASSERT_TRUE(PKCS7_get_certificates(result.get(), &cbs));
|
|
ASSERT_EQ(sk_X509_num(certs.get()), sk_X509_num(result.get()));
|
|
for (size_t i = 0; i < sk_X509_num(certs.get()); i++) {
|
|
X509 *a = sk_X509_value(certs.get(), i);
|
|
X509 *b = sk_X509_value(result.get(), i);
|
|
EXPECT_EQ(0, X509_cmp(a, b));
|
|
}
|
|
};
|
|
|
|
check_order(cert1, cert2, cert3);
|
|
check_order(cert3, cert2, cert1);
|
|
check_order(cert2, cert3, cert1);
|
|
}
|
|
|
|
// Test that we output certificates in the canonical DER order, using the
|
|
// CRYPTO_BUFFER version of the parse and bundle functions.
|
|
TEST(PKCS7Test, SortCertsRaw) {
|
|
// kPKCS7NSS contains three certificates in the canonical DER order.
|
|
CBS pkcs7;
|
|
CBS_init(&pkcs7, kPKCS7NSS, sizeof(kPKCS7NSS));
|
|
bssl::UniquePtr<STACK_OF(CRYPTO_BUFFER)> certs(sk_CRYPTO_BUFFER_new_null());
|
|
ASSERT_TRUE(certs);
|
|
ASSERT_TRUE(PKCS7_get_raw_certificates(certs.get(), &pkcs7, nullptr));
|
|
ASSERT_EQ(3u, sk_CRYPTO_BUFFER_num(certs.get()));
|
|
|
|
CRYPTO_BUFFER *cert1 = sk_CRYPTO_BUFFER_value(certs.get(), 0);
|
|
CRYPTO_BUFFER *cert2 = sk_CRYPTO_BUFFER_value(certs.get(), 1);
|
|
CRYPTO_BUFFER *cert3 = sk_CRYPTO_BUFFER_value(certs.get(), 2);
|
|
|
|
auto check_order = [&](CRYPTO_BUFFER *new_cert1, CRYPTO_BUFFER *new_cert2,
|
|
CRYPTO_BUFFER *new_cert3) {
|
|
// Bundle the certificates in the new order.
|
|
bssl::UniquePtr<STACK_OF(CRYPTO_BUFFER)> new_certs(
|
|
sk_CRYPTO_BUFFER_new_null());
|
|
ASSERT_TRUE(new_certs);
|
|
ASSERT_TRUE(bssl::PushToStack(new_certs.get(), bssl::UpRef(new_cert1)));
|
|
ASSERT_TRUE(bssl::PushToStack(new_certs.get(), bssl::UpRef(new_cert2)));
|
|
ASSERT_TRUE(bssl::PushToStack(new_certs.get(), bssl::UpRef(new_cert3)));
|
|
bssl::ScopedCBB cbb;
|
|
ASSERT_TRUE(CBB_init(cbb.get(), sizeof(kPKCS7NSS)));
|
|
ASSERT_TRUE(PKCS7_bundle_raw_certificates(cbb.get(), new_certs.get()));
|
|
|
|
// The bundle should be sorted back to the original order.
|
|
CBS cbs;
|
|
CBS_init(&cbs, CBB_data(cbb.get()), CBB_len(cbb.get()));
|
|
bssl::UniquePtr<STACK_OF(CRYPTO_BUFFER)> result(
|
|
sk_CRYPTO_BUFFER_new_null());
|
|
ASSERT_TRUE(result);
|
|
ASSERT_TRUE(PKCS7_get_raw_certificates(result.get(), &cbs, nullptr));
|
|
ASSERT_EQ(sk_CRYPTO_BUFFER_num(certs.get()),
|
|
sk_CRYPTO_BUFFER_num(result.get()));
|
|
for (size_t i = 0; i < sk_CRYPTO_BUFFER_num(certs.get()); i++) {
|
|
CRYPTO_BUFFER *a = sk_CRYPTO_BUFFER_value(certs.get(), i);
|
|
CRYPTO_BUFFER *b = sk_CRYPTO_BUFFER_value(result.get(), i);
|
|
EXPECT_EQ(Bytes(CRYPTO_BUFFER_data(a), CRYPTO_BUFFER_len(a)),
|
|
Bytes(CRYPTO_BUFFER_data(b), CRYPTO_BUFFER_len(b)));
|
|
}
|
|
};
|
|
|
|
check_order(cert1, cert2, cert3);
|
|
check_order(cert3, cert2, cert1);
|
|
check_order(cert2, cert3, cert1);
|
|
}
|
|
|
|
// Test that we output CRLs in the canonical DER order.
|
|
TEST(PKCS7Test, SortCRLs) {
|
|
static const char kCRL1[] = R"(
|
|
-----BEGIN X509 CRL-----
|
|
MIIBpzCBkAIBATANBgkqhkiG9w0BAQsFADBOMQswCQYDVQQGEwJVUzETMBEGA1UE
|
|
CAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzESMBAGA1UECgwJ
|
|
Qm9yaW5nU1NMFw0xNjA5MjYxNTEwNTVaFw0xNjEwMjYxNTEwNTVaoA4wDDAKBgNV
|
|
HRQEAwIBATANBgkqhkiG9w0BAQsFAAOCAQEAnrBKKgvd9x9zwK9rtUvVeFeJ7+LN
|
|
ZEAc+a5oxpPNEsJx6hXoApYEbzXMxuWBQoCs5iEBycSGudct21L+MVf27M38KrWo
|
|
eOkq0a2siqViQZO2Fb/SUFR0k9zb8xl86Zf65lgPplALun0bV/HT7MJcl04Tc4os
|
|
dsAReBs5nqTGNEd5AlC1iKHvQZkM//MD51DspKnDpsDiUVi54h9C1SpfZmX8H2Vv
|
|
diyu0fZ/bPAM3VAGawatf/SyWfBMyKpoPXEG39oAzmjjOj8en82psn7m474IGaho
|
|
/vBbhl1ms5qQiLYPjm4YELtnXQoFyC72tBjbdFd/ZE9k4CNKDbxFUXFbkw==
|
|
-----END X509 CRL-----
|
|
)";
|
|
static const char kCRL2[] = R"(
|
|
-----BEGIN X509 CRL-----
|
|
MIIBvjCBpwIBATANBgkqhkiG9w0BAQsFADBOMQswCQYDVQQGEwJVUzETMBEGA1UE
|
|
CAwKQ2FsaWZvcm5pYTEWMBQGA1UEBwwNTW91bnRhaW4gVmlldzESMBAGA1UECgwJ
|
|
Qm9yaW5nU1NMFw0xNjA5MjYxNTEyNDRaFw0xNjEwMjYxNTEyNDRaMBUwEwICEAAX
|
|
DTE2MDkyNjE1MTIyNlqgDjAMMAoGA1UdFAQDAgECMA0GCSqGSIb3DQEBCwUAA4IB
|
|
AQCUGaM4DcWzlQKrcZvI8TMeR8BpsvQeo5BoI/XZu2a8h//PyRyMwYeaOM+3zl0d
|
|
sjgCT8b3C1FPgT+P2Lkowv7rJ+FHJRNQkogr+RuqCSPTq65ha4WKlRGWkMFybzVH
|
|
NloxC+aU3lgp/NlX9yUtfqYmJek1CDrOOGPrAEAwj1l/BUeYKNGqfBWYJQtPJu+5
|
|
OaSvIYGpETCZJscUWODmLEb/O3DM438vLvxonwGqXqS0KX37+CHpUlyhnSovxXxp
|
|
Pz4aF+L7OtczxL0GYtD2fR9B7TDMqsNmHXgQrixvvOY7MUdLGbd4RfJL3yA53hyO
|
|
xzfKY2TzxLiOmctG0hXFkH5J
|
|
-----END X509 CRL-----
|
|
)";
|
|
|
|
bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(kCRL1, strlen(kCRL1)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<X509_CRL> crl1(
|
|
PEM_read_bio_X509_CRL(bio.get(), nullptr, nullptr, nullptr));
|
|
ASSERT_TRUE(crl1);
|
|
bio.reset(BIO_new_mem_buf(kCRL2, strlen(kCRL2)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<X509_CRL> crl2(
|
|
PEM_read_bio_X509_CRL(bio.get(), nullptr, nullptr, nullptr));
|
|
ASSERT_TRUE(crl2);
|
|
|
|
// DER's SET OF ordering sorts by tag, then length, so |crl1| comes before
|
|
// |crl2|.
|
|
auto check_order = [&](X509_CRL *new_crl1, X509_CRL *new_crl2) {
|
|
// Bundle the CRLs in the new order.
|
|
bssl::UniquePtr<STACK_OF(X509_CRL)> new_crls(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(new_crls);
|
|
ASSERT_TRUE(bssl::PushToStack(new_crls.get(), bssl::UpRef(new_crl1)));
|
|
ASSERT_TRUE(bssl::PushToStack(new_crls.get(), bssl::UpRef(new_crl2)));
|
|
bssl::ScopedCBB cbb;
|
|
ASSERT_TRUE(CBB_init(cbb.get(), 64));
|
|
ASSERT_TRUE(PKCS7_bundle_CRLs(cbb.get(), new_crls.get()));
|
|
|
|
// The bundle should be sorted back to the original order.
|
|
CBS cbs;
|
|
CBS_init(&cbs, CBB_data(cbb.get()), CBB_len(cbb.get()));
|
|
bssl::UniquePtr<STACK_OF(X509_CRL)> result(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(result);
|
|
ASSERT_TRUE(PKCS7_get_CRLs(result.get(), &cbs));
|
|
ASSERT_EQ(2u, sk_X509_CRL_num(result.get()));
|
|
EXPECT_EQ(0, X509_CRL_cmp(crl1.get(), sk_X509_CRL_value(result.get(), 0)));
|
|
EXPECT_EQ(0, X509_CRL_cmp(crl2.get(), sk_X509_CRL_value(result.get(), 1)));
|
|
};
|
|
|
|
check_order(crl1.get(), crl2.get());
|
|
check_order(crl2.get(), crl1.get());
|
|
}
|
|
|
|
TEST(PKCS7Test, KernelModuleSigning) {
|
|
// Sign a message with the same call that the Linux kernel's sign-file.c
|
|
// makes.
|
|
static const char kCert[] = R"(
|
|
-----BEGIN CERTIFICATE-----
|
|
MIIFazCCA1OgAwIBAgIURVkPzF/4dwy7419Qk75uhIuyf0EwDQYJKoZIhvcNAQEL
|
|
BQAwRTELMAkGA1UEBhMCQVUxEzARBgNVBAgMClNvbWUtU3RhdGUxITAfBgNVBAoM
|
|
GEludGVybmV0IFdpZGdpdHMgUHR5IEx0ZDAeFw0yMTA5MjExOTIyMTJaFw0yMjA5
|
|
MjExOTIyMTJaMEUxCzAJBgNVBAYTAkFVMRMwEQYDVQQIDApTb21lLVN0YXRlMSEw
|
|
HwYDVQQKDBhJbnRlcm5ldCBXaWRnaXRzIFB0eSBMdGQwggIiMA0GCSqGSIb3DQEB
|
|
AQUAA4ICDwAwggIKAoICAQC1+MOn+BopcEVR4QMvjXdAxGkWFllXyQFDToL+qOiP
|
|
RU1yN7C8KCtkbOAFttJIO4O/i0iZ7KqYbnmB6YUA/ONAcakocnrdoESgRJcVMeAx
|
|
Dk/11OtMF5yIfeOOO/TUeVNmAUaT63gFbKy/adpqhzJtOv9BBl5VcYNGGSE+0wtb
|
|
mjpmNsxunEQR1KLDc97fGYHeRfKoSyrCIEE8IaAEpKGR2Sku3v9Jwh7RpjupgiUA
|
|
kH6pJk7VMZm5vl2wFjYvfysgjeN5ZtsxFDMaPYZStpxMxpNd5C9DsO2Ljp5NMpGf
|
|
NGmG4ZqiaQg8z2cIM6ESmN1zDJdUh5IXed1fOxBZD/poUFH0wDRFWnvzlaPmjJEF
|
|
rYLMK8svnE5nEQp9vu93ISFBx7cofs+niMaUXPEqaRSqruifN2M1it3kOf/8YZl1
|
|
vurs+VtHD6nOJo6bd11+37aBidIB/BaWnzLrDmSTcPFa1tkTHwoLqc9+jThTq9jZ
|
|
6w3lAMPpsoenyD19UmQB589+4kNp2SIO/TtzVQCGgQPXE2jDCl6G9aIPMkfvpPZK
|
|
4THVil3WQRCFYnYdDO4HQXo2ZuC4RiqgY5ygfeoL+fa9k383lgxxAHQLS7xsbaVB
|
|
40RmfdbdevgPYIwZNNO78ddRmMdSv6IknSW9gydGzY//btY+t1SWcBZWzn1Ewq8g
|
|
2QIDAQABo1MwUTAdBgNVHQ4EFgQUotZD9ajEvnQYVezIWzcW4pzvMcUwHwYDVR0j
|
|
BBgwFoAUotZD9ajEvnQYVezIWzcW4pzvMcUwDwYDVR0TAQH/BAUwAwEB/zANBgkq
|
|
hkiG9w0BAQsFAAOCAgEAqCe42PIWoyLDx9bR+5cSp99N5xo5lLiSLtWx2emDbZB2
|
|
AunqKYeEgIV+TWNF2w1SZ/ckFgV7SlL2Yl73N/veSNRfNAnpjLksGDFpdJb7YXrx
|
|
cUvxdy1mr8oau6J7PC9JGjBTBrnhqwCQX1FtcAxODKll2Lsfuj6+bdC3rCK7KBEo
|
|
ENamMJZIeo8lRP9qFF2xwCEzZjRv2zvB6O5o9045aTUcdCrwUfKE2sqY6EXRzFTC
|
|
waK0HRCd1FLv9omhz/Ug5PMHP4d6MZfnAbFm+AzAhnpkrk/9TJYSOoNTNLWsuqhp
|
|
dN0rKqiFWv1zIwfknXvTh1P1Ap+G5jffAca0zWUH1oKjE7ZZioSsaZ6gySnD8+WQ
|
|
TPbOYtG+n0mhCH1TrU8Dqi3rd8g5IbC8loYLRH94QtodOnevD4Qo9Orfrsr8hGOW
|
|
ABespanZArhoQ03DAtpNhtHm2NWJQF2uHNqcTrkq0omqZBTbMD1GKMBujoNooAUu
|
|
w51U9r+RycPJTFqEGHb0nd7EjoyXEXtuX1Ld5fTZjQ9SszmQKQ8w3lHqRGNlkSiO
|
|
e3IOOq2ruXmq1jykxpmi82IcTRUE8TZBfL/yz0nxpHKAYC1VwMezrkgZDGz4npxf
|
|
1z2+qd58xU6/jsf7/+3xdPFubeEJujdbCkWQsQC5Rzm48zDWGq/pyzFji44K3TA=
|
|
-----END CERTIFICATE-----
|
|
)";
|
|
|
|
static const char kKey[] = R"(
|
|
-----BEGIN PRIVATE KEY-----
|
|
MIIJQQIBADANBgkqhkiG9w0BAQEFAASCCSswggknAgEAAoICAQC1+MOn+BopcEVR
|
|
4QMvjXdAxGkWFllXyQFDToL+qOiPRU1yN7C8KCtkbOAFttJIO4O/i0iZ7KqYbnmB
|
|
6YUA/ONAcakocnrdoESgRJcVMeAxDk/11OtMF5yIfeOOO/TUeVNmAUaT63gFbKy/
|
|
adpqhzJtOv9BBl5VcYNGGSE+0wtbmjpmNsxunEQR1KLDc97fGYHeRfKoSyrCIEE8
|
|
IaAEpKGR2Sku3v9Jwh7RpjupgiUAkH6pJk7VMZm5vl2wFjYvfysgjeN5ZtsxFDMa
|
|
PYZStpxMxpNd5C9DsO2Ljp5NMpGfNGmG4ZqiaQg8z2cIM6ESmN1zDJdUh5IXed1f
|
|
OxBZD/poUFH0wDRFWnvzlaPmjJEFrYLMK8svnE5nEQp9vu93ISFBx7cofs+niMaU
|
|
XPEqaRSqruifN2M1it3kOf/8YZl1vurs+VtHD6nOJo6bd11+37aBidIB/BaWnzLr
|
|
DmSTcPFa1tkTHwoLqc9+jThTq9jZ6w3lAMPpsoenyD19UmQB589+4kNp2SIO/Ttz
|
|
VQCGgQPXE2jDCl6G9aIPMkfvpPZK4THVil3WQRCFYnYdDO4HQXo2ZuC4RiqgY5yg
|
|
feoL+fa9k383lgxxAHQLS7xsbaVB40RmfdbdevgPYIwZNNO78ddRmMdSv6IknSW9
|
|
gydGzY//btY+t1SWcBZWzn1Ewq8g2QIDAQABAoICAFQ/liZAIaypxA5ChP0RG/Mq
|
|
fBSzyC1ybFlDEjbg8LrUNST6T6LtXhmipp0+pWC33SljTPumrNzh2POir+djLbt6
|
|
Y/zL88KEHwGsf95aNxe/Lpn8N+wEyn4O+rmxXIq6mTgSwyBc1jZ8uAXu9iZ37YrQ
|
|
07jBQA+C/GoJ3HB/uTRx1TPZjxBu3Lz8m1auYLMd1hiYfd4Y3vT9hfZXAwTjS8KA
|
|
riZ7K+p0K1yY/+pczNDUFTAvAjSGQEvUrP+HaRLYZ5ks1/IvArBYT8iIT5Yf4YFS
|
|
NowzxwYp9fC02OmYzf7Nf0XpUXR7+EpfI66SaLJ5f51yaOXD1olz7F/YsprpYN7+
|
|
oQd7EKar1bY3ROM6naUZtsIoEblg6B0mkyHWQgZ9wZRbcN7Zmuc/tIpLat7se+MP
|
|
xQeAcH4Yhgnd2G6EELpmJBcyJ0Ss3atpI1eenU+ly++L4XbDQH9norKQ1PEDXYbV
|
|
XMAV5uIsplBL7hGIa6/u/cRMM5eN3TJchtzIHFhq9+ENMvjTOfo0bflcYR+tNxGD
|
|
6agWlD/Apedaapu/3Xp7ekyCiy/YTIwgT4U3rprYplzFM5HbzYtZ9ThxUm+CmnYj
|
|
ZSCKiLoaQq+11/M9zH1Je0uJP5aK0CxOii2LVRXZYaQfbDtiHNWUSM7uPIZMnDgE
|
|
IPTpl9CEfk7U3pgiUlg5AoIBAQDjUeikACPaRuewIjLqwTT2/j+ZO+/dCG4atFZa
|
|
W+gdZ1NVDCdowQPBZWg6bqejRr1MvORg2L83kqZDQjaT9y59qxsFhXCy26xKp7aP
|
|
Z4pEvUQmQnnf3RYHk3EBtOHyyMetTaghTGzL3MlPGo3uGbCiYtVoPKXZXGWeiOFN
|
|
s9RNDh/7m6harB2bmX2cK+QPdJ1roVBXQDLkjh2mvLnC5vrsw81GWSkbWQpYmnVi
|
|
YdLhytM+UTYjTrSugtrKk9e2KOFf2uR8PVaPeINEM4uubxW5YUy6gwF8ePtWYAtZ
|
|
Skw3kdBdShhGzHORSY3NsRTJZL6AUdkhHYFTl/rlfj1WXsdnAoIBAQDM7i0u2T+E
|
|
HmroTGiQAIRUEwUZQFDRkcEnM75jpkQT39jXF+zmhjzS1slJF2x0E0jUBV0juVWh
|
|
mz1kHjTMV0j3/mvCeVv0iTcdIbHYRtTwmOjzkwTsZGh6T7okYck3KexRjpyhPpcX
|
|
hOHOPJKS/muG0ZuaJjTEbJOzrSPU0rt0ppL7nOwd5jIOoGAciWiP17G1Lyyitrv4
|
|
mKBK6mFQQWjAgEGy3jvBocbUo7Qo8Aucm6Y4eF1fUyC/X07RBzERHS4TuM+AQlDN
|
|
T+LgTgcwTjE+Nzow2WMwCIbhVQqFRScuWqcJ6NQ6S/dV0R+aGJ90Ey+DtiZ9N9uV
|
|
j0omAGvM8u2/AoIBADXF94FsIw8MfNw2itLrl2riJAtMmWYxC1K33EGNwi/KdHUG
|
|
5f+qwQerxGcmK/O81STk/iVGwJ0VzMzWSfDgpRfHNSIuOcWln3EdkVsFBDlUiF2A
|
|
ljH1q7NpFm9v6Y80HcAKQb52xLnI5boXrwFnBFi1hoQc7KKpb8R73sgxxQPhVoF/
|
|
hejFFE/tlEAwRce+L0r5ovaw0hks4SjDNjI7z5nYi6ObjdTRUFg7WY9HUspk32m7
|
|
blIV2Tn67GTFal7F9uJk9m3JWMOhn3OvudguoPX0ZWEtgll+iP4axDSAFd2DWcXn
|
|
tCxzStdQjgHdZOxrL4FNW06xGxm6Nvi4zyuySfsCggEAOuIpC3ATBxRyZYMm/FGZ
|
|
tEquyV2omz8FQA1nJFzu7MMCHHPcdzSVH4Pl3GGloQi1gW51H8GuMDxZ/H2NcDWY
|
|
WuG49u1GFdKjinRXFKztnKBjNzHEVWRYfOSRuMh8N6SNKbYPnWlNos1k0IypFSGT
|
|
pe5uhnF58gK8wgD67bkLce43B6NEWSb+tSMx2qFE8SfqAQSoD6zv//NjA4OrKJNS
|
|
1RVFS279vpqMdib/qk+nFn3G2i0Dr1NEcpihHgCyAZff2Hze6pyjeQr+RrNE74VY
|
|
MudNiiG8lV2t2+tClZ6ULoaPvpIvAP04+WiYav+uOX0VxwO8tXgqWSQOCzNNxlr7
|
|
IwKCAQA7odNjE6Sc2qiecrOu13kEi3gT0heshIyZ0XhePrS1vgHfCouIRvNMw4FT
|
|
45ZZUFDSdOxhrew5GuMeLvo2YILBjmkX3UqTojQMbur7FcGH8/P0Sm0f20Vc06oS
|
|
sQF5Ji4LSyf6t9oQKePjFIGoIc6pf6BXJZYP4rBnzQzUQjH2yzDYDY3TuV7bFJJU
|
|
DcSTGM6nP0fRMmgBtB14o7A6Gsy6X/N2ElgbvWT8YhmUC6H8DIzmZwHRKaG6C6g5
|
|
eEjuAYenYNM4jxeteC1neUDIdGxH/BA7JrAqcGaN9GT+R47YIfiS2WrEssD1Pi5h
|
|
hJTbHtjEDJ7BHLC/CNUhXbpyyu1y
|
|
-----END PRIVATE KEY-----
|
|
)";
|
|
|
|
bssl::UniquePtr<BIO> cert_bio(
|
|
BIO_new_mem_buf(const_cast<char *>(kCert), sizeof(kCert) - 1));
|
|
bssl::UniquePtr<X509> cert(
|
|
PEM_read_bio_X509(cert_bio.get(), nullptr, nullptr, nullptr));
|
|
|
|
bssl::UniquePtr<BIO> key_bio(
|
|
BIO_new_mem_buf(const_cast<char *>(kKey), sizeof(kKey) - 1));
|
|
bssl::UniquePtr<EVP_PKEY> key(
|
|
PEM_read_bio_PrivateKey(key_bio.get(), nullptr, nullptr, nullptr));
|
|
|
|
static const char kSignedData[] = "signed data";
|
|
bssl::UniquePtr<BIO> data_bio(BIO_new_mem_buf(const_cast<char *>(kSignedData),
|
|
sizeof(kSignedData) - 1));
|
|
|
|
bssl::UniquePtr<PKCS7> pkcs7(
|
|
PKCS7_sign(cert.get(), key.get(), /*certs=*/nullptr, data_bio.get(),
|
|
PKCS7_NOATTR | PKCS7_BINARY | PKCS7_NOCERTS | PKCS7_DETACHED));
|
|
ASSERT_TRUE(pkcs7);
|
|
|
|
uint8_t *pkcs7_bytes = nullptr;
|
|
const int pkcs7_len = i2d_PKCS7(pkcs7.get(), &pkcs7_bytes);
|
|
ASSERT_GE(pkcs7_len, 0);
|
|
bssl::UniquePtr<uint8_t> pkcs7_storage(pkcs7_bytes);
|
|
|
|
// RSA signatures are deterministic so the output should not change.
|
|
static const uint8_t kExpectedOutput[] = {
|
|
0x30, 0x82, 0x02, 0xbc, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
|
|
0x01, 0x07, 0x02, 0xa0, 0x82, 0x02, 0xad, 0x30, 0x82, 0x02, 0xa9, 0x02,
|
|
0x01, 0x01, 0x31, 0x0d, 0x30, 0x0b, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01,
|
|
0x65, 0x03, 0x04, 0x02, 0x01, 0x30, 0x0b, 0x06, 0x09, 0x2a, 0x86, 0x48,
|
|
0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01, 0x31, 0x82, 0x02, 0x86, 0x30, 0x82,
|
|
0x02, 0x82, 0x02, 0x01, 0x01, 0x30, 0x5d, 0x30, 0x45, 0x31, 0x0b, 0x30,
|
|
0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13, 0x02, 0x41, 0x55, 0x31, 0x13,
|
|
0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x0c, 0x0a, 0x53, 0x6f, 0x6d,
|
|
0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65, 0x31, 0x21, 0x30, 0x1f, 0x06,
|
|
0x03, 0x55, 0x04, 0x0a, 0x0c, 0x18, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x6e,
|
|
0x65, 0x74, 0x20, 0x57, 0x69, 0x64, 0x67, 0x69, 0x74, 0x73, 0x20, 0x50,
|
|
0x74, 0x79, 0x20, 0x4c, 0x74, 0x64, 0x02, 0x14, 0x45, 0x59, 0x0f, 0xcc,
|
|
0x5f, 0xf8, 0x77, 0x0c, 0xbb, 0xe3, 0x5f, 0x50, 0x93, 0xbe, 0x6e, 0x84,
|
|
0x8b, 0xb2, 0x7f, 0x41, 0x30, 0x0b, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01,
|
|
0x65, 0x03, 0x04, 0x02, 0x01, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48,
|
|
0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x04, 0x82, 0x02, 0x00,
|
|
0x54, 0xd4, 0x7c, 0xdc, 0x19, 0x86, 0xa1, 0xb2, 0xbe, 0xe3, 0xa4, 0x5e,
|
|
0xad, 0x16, 0x6f, 0x7c, 0xf9, 0xa6, 0x40, 0x90, 0xb8, 0x78, 0x85, 0xf1,
|
|
0x02, 0x59, 0xe5, 0x9f, 0x83, 0xfb, 0x20, 0xcf, 0x29, 0x52, 0xb6, 0x35,
|
|
0x5c, 0xf9, 0xef, 0x4e, 0xc5, 0xd3, 0xa6, 0x45, 0x6e, 0xfa, 0x0a, 0xa7,
|
|
0x53, 0xc8, 0xf4, 0xf9, 0xd6, 0xc5, 0xd8, 0xd8, 0x04, 0x3d, 0xb4, 0x15,
|
|
0xa7, 0x7a, 0x53, 0xdd, 0x27, 0xfa, 0x58, 0x2e, 0x5e, 0xc4, 0xcd, 0x45,
|
|
0xaa, 0xc2, 0x7b, 0xf9, 0x3d, 0xd7, 0x22, 0x20, 0x90, 0xbb, 0xa5, 0x62,
|
|
0xd5, 0xaa, 0x39, 0x8f, 0xc1, 0x00, 0xef, 0x4b, 0x03, 0x2c, 0x32, 0xc0,
|
|
0xad, 0x27, 0xb6, 0xfe, 0x86, 0xe5, 0x9d, 0xf0, 0xbe, 0xb1, 0x0d, 0xa4,
|
|
0xa3, 0x40, 0xe0, 0xaa, 0x0a, 0x13, 0x6e, 0x61, 0x9a, 0x3b, 0xae, 0x78,
|
|
0xd4, 0x6f, 0x2d, 0x1d, 0x40, 0x4b, 0xe3, 0x5f, 0xf8, 0xe8, 0x21, 0x89,
|
|
0x35, 0x73, 0x6d, 0x7e, 0x41, 0xc6, 0x0f, 0x0c, 0x01, 0x64, 0x61, 0xa8,
|
|
0x37, 0xef, 0x2b, 0x95, 0xb7, 0x34, 0xac, 0xc7, 0xdb, 0x66, 0x87, 0x45,
|
|
0xb4, 0x0f, 0x60, 0x01, 0x07, 0x29, 0x74, 0x32, 0x0b, 0xae, 0xbc, 0x08,
|
|
0x88, 0x15, 0xc3, 0x79, 0x4a, 0x1c, 0x5a, 0x9c, 0xc2, 0xfb, 0x4f, 0xd3,
|
|
0x17, 0xc2, 0x40, 0x71, 0x37, 0xea, 0xa6, 0x1e, 0xf0, 0x5b, 0xa5, 0xd7,
|
|
0x9b, 0x9e, 0x57, 0x44, 0x74, 0xc5, 0xd5, 0x5f, 0xba, 0xbc, 0xd7, 0xe1,
|
|
0xae, 0xd0, 0xd3, 0xb5, 0x10, 0xc6, 0x8b, 0xb1, 0x83, 0x7c, 0xaa, 0x3a,
|
|
0xbb, 0xe8, 0x7f, 0x56, 0xc4, 0x3b, 0x9d, 0x45, 0x09, 0x9b, 0x34, 0xc9,
|
|
0xfb, 0x5a, 0xa1, 0xab, 0xd0, 0x07, 0x79, 0x43, 0x58, 0x44, 0xd7, 0x40,
|
|
0xc4, 0xa7, 0xd3, 0xe9, 0x18, 0xb9, 0x78, 0x1d, 0x93, 0x0b, 0xc1, 0xdb,
|
|
0xc3, 0xae, 0xc9, 0xe8, 0x2c, 0xa7, 0x8c, 0x7e, 0x31, 0x1e, 0xec, 0x1c,
|
|
0xab, 0x83, 0xa0, 0x5d, 0x0e, 0xc3, 0x6a, 0x7c, 0x97, 0x09, 0xcf, 0x00,
|
|
0xa9, 0x66, 0xda, 0x21, 0x85, 0xaa, 0x47, 0xd8, 0xea, 0x8f, 0x72, 0x54,
|
|
0x03, 0x6c, 0xbc, 0x4b, 0xf9, 0x92, 0xae, 0x82, 0x75, 0x33, 0x10, 0x4d,
|
|
0x65, 0x4d, 0x0e, 0x73, 0x5d, 0x6f, 0x09, 0xee, 0x56, 0x78, 0x87, 0x0b,
|
|
0xa3, 0xaa, 0xc2, 0x5f, 0x49, 0x73, 0x0d, 0x78, 0xfa, 0x40, 0xc1, 0x25,
|
|
0x2f, 0x5d, 0x8a, 0xe1, 0xbf, 0x38, 0x2c, 0xd0, 0x26, 0xbd, 0xf5, 0x6e,
|
|
0x02, 0x01, 0x2e, 0x9e, 0x27, 0x64, 0x4b, 0x61, 0x8c, 0x68, 0x6e, 0x09,
|
|
0xfe, 0x0b, 0xf8, 0x36, 0x4e, 0x84, 0xb7, 0x76, 0xcb, 0x41, 0xf0, 0x40,
|
|
0x72, 0xc9, 0x74, 0x64, 0x5f, 0xbe, 0x9e, 0xfe, 0x9e, 0xce, 0x89, 0x84,
|
|
0x68, 0x81, 0x57, 0x2a, 0xdb, 0xd6, 0x01, 0xa8, 0x1b, 0x6e, 0x5d, 0xc4,
|
|
0x65, 0xbd, 0x0d, 0x98, 0x54, 0xa3, 0x18, 0x23, 0x09, 0x4a, 0x8d, 0x6c,
|
|
0xc6, 0x2e, 0xfe, 0x7a, 0xa9, 0x11, 0x92, 0x8b, 0xd0, 0xc1, 0xe7, 0x76,
|
|
0x71, 0xec, 0x34, 0xfc, 0xc8, 0x2a, 0x5e, 0x38, 0x52, 0xe6, 0xc8, 0xa5,
|
|
0x1d, 0x0b, 0xce, 0xf5, 0xc0, 0xe5, 0x0b, 0x88, 0xa9, 0x55, 0x88, 0x6c,
|
|
0xfa, 0xea, 0xaa, 0x39, 0x66, 0xdd, 0x80, 0x52, 0xe0, 0x7e, 0x45, 0x8e,
|
|
0x51, 0x2c, 0x36, 0x07, 0xd7, 0x2b, 0xf1, 0x46, 0x00, 0x66, 0xb2, 0x5a,
|
|
0x39, 0xbe, 0xf7, 0x26, 0x15, 0xbc, 0x55, 0xdb, 0xe9, 0x01, 0xdd, 0x54,
|
|
0x27, 0x2b, 0xfe, 0x86, 0x52, 0xef, 0xc6, 0x27, 0xa3, 0xf7, 0x55, 0x55,
|
|
0xb8, 0xe2, 0x1f, 0xcb, 0x32, 0xd8, 0xba, 0xd6, 0x69, 0xde, 0x8d, 0xa7,
|
|
0xfa, 0xad, 0xf6, 0x2a, 0xc0, 0x6f, 0x86, 0x50, 0x27, 0x5a, 0xe2, 0xe3,
|
|
0xf6, 0xb9, 0x01, 0xec, 0x01, 0x37, 0x84, 0x01,
|
|
};
|
|
EXPECT_EQ(Bytes(pkcs7_bytes, pkcs7_len),
|
|
Bytes(kExpectedOutput, sizeof(kExpectedOutput)));
|
|
|
|
ERR_clear_error();
|
|
}
|
|
|
|
TEST(PKCS7Test, GettersSetters) {
|
|
bssl::UniquePtr<PKCS7> p7;
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
EXPECT_FALSE(PKCS7_set_type(p7.get(), NID_undef));
|
|
EXPECT_FALSE(PKCS7_content_new(p7.get(), NID_undef));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
// set type redundantly to ensure we're properly freeing up existing
|
|
// resources on subsequent set.
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
EXPECT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
EXPECT_TRUE(PKCS7_content_new(p7.get(), NID_pkcs7_signed));
|
|
EXPECT_FALSE(PKCS7_set_cipher(p7.get(), EVP_aes_128_gcm()));
|
|
EXPECT_FALSE(PKCS7_add_recipient_info(p7.get(), nullptr));
|
|
EXPECT_FALSE(PKCS7_get_signer_info(nullptr));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_digest));
|
|
// set type redundantly to ensure we're properly freeing up existing
|
|
// resources on subsequent set.
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_digest));
|
|
EXPECT_TRUE(PKCS7_type_is_digest(p7.get()));
|
|
EXPECT_TRUE(PKCS7_content_new(p7.get(), NID_pkcs7_digest));
|
|
EXPECT_FALSE(PKCS7_add_certificate(p7.get(), nullptr));
|
|
EXPECT_FALSE(PKCS7_add_crl(p7.get(), nullptr));
|
|
EXPECT_FALSE(PKCS7_add_signer(p7.get(), nullptr));
|
|
EXPECT_FALSE(PKCS7_get_signer_info(p7.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7.get());
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_data));
|
|
// set type redundantly to ensure we're properly freeing up existing
|
|
// resources on subsequent set.
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_data));
|
|
EXPECT_TRUE(PKCS7_type_is_data(p7.get()));
|
|
EXPECT_FALSE(PKCS7_set_content(p7.get(), p7.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7.get());
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
// set type redundantly to ensure we're properly freeing up existing
|
|
// resources on subsequent set.
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
EXPECT_TRUE(PKCS7_type_is_signedAndEnveloped(p7.get()));
|
|
EXPECT_TRUE(PKCS7_set_cipher(p7.get(), EVP_aes_128_gcm()));
|
|
EXPECT_FALSE(PKCS7_set_content(p7.get(), p7.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7.get());
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
// set type redundantly to ensure we're properly freeing up existing
|
|
// resources on subsequent set.
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
EXPECT_TRUE(PKCS7_set_cipher(p7.get(), EVP_aes_128_gcm()));
|
|
EXPECT_FALSE(PKCS7_set_content(p7.get(), p7.get()));
|
|
|
|
// Ruby requires that we can set type NID_pkcs7_encrypted even though we don't
|
|
// really support it for most functions.
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7.get());
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_encrypted));
|
|
// set type redundantly to ensure we're properly freeing up existing
|
|
// resources on subsequent set.
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_encrypted));
|
|
EXPECT_TRUE(PKCS7_type_is_encrypted(p7.get()));
|
|
EXPECT_FALSE(PKCS7_set_content(p7.get(), p7.get()));
|
|
|
|
// |d2i_*| functions advance the input reference by number of bytes parsed,
|
|
// so save off a local reference and reset it for each test case.
|
|
const uint8_t *p7_der = kPKCS7SignedWithSignerInfo;
|
|
const size_t p7_der_len = sizeof(kPKCS7SignedWithSignerInfo);
|
|
p7.reset(d2i_PKCS7(nullptr, &p7_der, p7_der_len));
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
STACK_OF(PKCS7_SIGNER_INFO) *sk_p7si_signed = PKCS7_get_signer_info(p7.get());
|
|
ASSERT_TRUE(sk_p7si_signed);
|
|
ASSERT_GT(sk_PKCS7_SIGNER_INFO_num(sk_p7si_signed), 0UL);
|
|
PKCS7_SIGNER_INFO *p7si = sk_PKCS7_SIGNER_INFO_value(sk_p7si_signed, 0);
|
|
ASSERT_TRUE(p7si);
|
|
EXPECT_FALSE(PKCS7_get_signed_attribute(
|
|
p7si, NID_md5)); // hash nid not valid x509 attr
|
|
ASN1_TYPE *signing_time =
|
|
PKCS7_get_signed_attribute(p7si, NID_pkcs9_signingTime);
|
|
ASSERT_TRUE(signing_time);
|
|
EVP_PKEY *pkey;
|
|
X509_ALGOR *pdig;
|
|
X509_ALGOR *psig;
|
|
PKCS7_SIGNER_INFO_get0_algs(p7si, &pkey, &pdig, &psig);
|
|
ASSERT_FALSE(pkey); // no attached pkey
|
|
ASSERT_TRUE(psig);
|
|
ASSERT_TRUE(pdig);
|
|
|
|
// Negative lengths not valid
|
|
EXPECT_FALSE(d2i_PKCS7(nullptr, &p7_der, -1));
|
|
|
|
bssl::UniquePtr<PKCS7> p7_dup(PKCS7_dup(p7.get()));
|
|
ASSERT_TRUE(p7_dup);
|
|
EXPECT_TRUE(PKCS7_type_is_signed(p7_dup.get()));
|
|
|
|
p7_der = kPKCS7SignedWithSignerInfo;
|
|
bssl::UniquePtr<BIO> bio(BIO_new_mem_buf(p7_der, p7_der_len));
|
|
p7.reset(d2i_PKCS7_bio(bio.get(), nullptr));
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(i2d_PKCS7_bio(bio.get(), p7.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
bio.reset(BIO_new_mem_buf(kPEMCert, strlen(kPEMCert)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<STACK_OF(X509)> certs(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
ASSERT_TRUE(PKCS7_get_PEM_certificates(certs.get(), bio.get()));
|
|
ASSERT_EQ(1U, sk_X509_num(certs.get()));
|
|
EXPECT_TRUE(PKCS7_add_certificate(p7.get(), sk_X509_value(certs.get(), 0U)));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
bio.reset(BIO_new_mem_buf(kPEMCRL, strlen(kPEMCRL)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<STACK_OF(X509_CRL)> crls(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(crls);
|
|
ASSERT_TRUE(PKCS7_get_PEM_CRLs(crls.get(), bio.get()));
|
|
ASSERT_EQ(1U, sk_X509_CRL_num(crls.get()));
|
|
EXPECT_TRUE(PKCS7_add_crl(p7.get(), sk_X509_CRL_value(crls.get(), 0U)));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
bio.reset(BIO_new_mem_buf(kPEMCert, strlen(kPEMCert)));
|
|
ASSERT_TRUE(bio);
|
|
certs.reset(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
ASSERT_TRUE(PKCS7_get_PEM_certificates(certs.get(), bio.get()));
|
|
ASSERT_EQ(1U, sk_X509_num(certs.get()));
|
|
EXPECT_TRUE(PKCS7_add_certificate(p7.get(), sk_X509_value(certs.get(), 0U)));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
bio.reset(BIO_new_mem_buf(kPEMCRL, strlen(kPEMCRL)));
|
|
ASSERT_TRUE(bio);
|
|
crls.reset(sk_X509_CRL_new_null());
|
|
ASSERT_TRUE(crls);
|
|
ASSERT_TRUE(PKCS7_get_PEM_CRLs(crls.get(), bio.get()));
|
|
ASSERT_EQ(1U, sk_X509_CRL_num(crls.get()));
|
|
EXPECT_TRUE(PKCS7_add_crl(p7.get(), sk_X509_CRL_value(crls.get(), 0U)));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
bssl::UniquePtr<RSA> rsa(RSA_new());
|
|
ASSERT_TRUE(rsa);
|
|
ASSERT_TRUE(RSA_generate_key_fips(rsa.get(), 2048, nullptr));
|
|
bssl::UniquePtr<EVP_PKEY> rsa_pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(rsa_pkey);
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(rsa_pkey.get(), rsa.get()));
|
|
bssl::UniquePtr<X509> rsa_x509(sk_X509_pop(certs.get()));
|
|
ASSERT_EQ(0U, sk_X509_num(certs.get()));
|
|
ASSERT_TRUE(rsa_x509);
|
|
p7si = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(p7si);
|
|
EXPECT_TRUE(PKCS7_SIGNER_INFO_set(p7si, rsa_x509.get(), rsa_pkey.get(),
|
|
EVP_sha256()));
|
|
EXPECT_FALSE(PKCS7_SIGNER_INFO_set(p7si, nullptr, nullptr, nullptr));
|
|
EXPECT_TRUE(PKCS7_add_signer(p7.get(), p7si));
|
|
EXPECT_TRUE(PKCS7_get_signer_info(p7.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7.get());
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
p7si = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(p7si);
|
|
bssl::UniquePtr<X509> ecdsa_x509(X509_new());
|
|
ASSERT_TRUE(ecdsa_x509);
|
|
bssl::UniquePtr<EVP_PKEY_CTX> ctx(EVP_PKEY_CTX_new_id(EVP_PKEY_EC, nullptr));
|
|
ASSERT_TRUE(ctx);
|
|
ASSERT_TRUE(EVP_PKEY_keygen_init(ctx.get()));
|
|
ASSERT_TRUE(
|
|
EVP_PKEY_CTX_set_ec_paramgen_curve_nid(ctx.get(), NID_X9_62_prime256v1));
|
|
bssl::UniquePtr<EVP_PKEY> ecdsa_pkey(EVP_PKEY_new());
|
|
EVP_PKEY *ecdsa_pkey_ptr = ecdsa_pkey.get();
|
|
ASSERT_TRUE(EVP_PKEY_keygen(ctx.get(), &ecdsa_pkey_ptr));
|
|
EXPECT_TRUE(PKCS7_SIGNER_INFO_set(p7si, ecdsa_x509.get(), ecdsa_pkey.get(),
|
|
EVP_sha256()));
|
|
EXPECT_TRUE(PKCS7_add_signer(p7.get(), p7si));
|
|
EXPECT_TRUE(PKCS7_get_signer_info(p7.get()));
|
|
|
|
// Cover overlap between |p7| and signer info message digest algorithms
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
X509_ALGOR *md_alg1 = X509_ALGOR_new();
|
|
X509_ALGOR_set_md(md_alg1, EVP_sha384());
|
|
sk_X509_ALGOR_push(p7->d.sign->md_algs, md_alg1);
|
|
X509_ALGOR *md_alg2 = X509_ALGOR_new();
|
|
X509_ALGOR_set_md(md_alg2, EVP_sha256());
|
|
sk_X509_ALGOR_push(p7->d.sign->md_algs, md_alg2);
|
|
|
|
p7si = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(p7si);
|
|
EXPECT_TRUE(PKCS7_SIGNER_INFO_set(p7si, ecdsa_x509.get(), ecdsa_pkey.get(),
|
|
EVP_sha256()));
|
|
EXPECT_TRUE(PKCS7_add_signer(p7.get(), p7si));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7.get());
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
p7si = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(p7si);
|
|
ecdsa_x509.reset(X509_new());
|
|
ASSERT_TRUE(ecdsa_x509);
|
|
ctx.reset(EVP_PKEY_CTX_new_id(EVP_PKEY_ED25519, nullptr));
|
|
ASSERT_TRUE(ctx);
|
|
ASSERT_TRUE(EVP_PKEY_keygen_init(ctx.get()));
|
|
ecdsa_pkey.reset(EVP_PKEY_new());
|
|
ecdsa_pkey_ptr = ecdsa_pkey.get();
|
|
ASSERT_TRUE(EVP_PKEY_keygen(ctx.get(), &ecdsa_pkey_ptr));
|
|
EXPECT_FALSE(PKCS7_SIGNER_INFO_set(p7si, ecdsa_x509.get(), ecdsa_pkey.get(),
|
|
EVP_sha256()));
|
|
PKCS7_SIGNER_INFO_free(p7si);
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
ASSERT_TRUE(X509_set_pubkey(rsa_x509.get(), rsa_pkey.get()));
|
|
PKCS7_RECIP_INFO *p7ri = PKCS7_RECIP_INFO_new();
|
|
EXPECT_TRUE(PKCS7_RECIP_INFO_set(p7ri, rsa_x509.get()));
|
|
EXPECT_FALSE(PKCS7_RECIP_INFO_set(p7ri, nullptr));
|
|
X509_ALGOR *penc = NULL;
|
|
PKCS7_RECIP_INFO_get0_alg(p7ri, &penc);
|
|
ASSERT_TRUE(penc);
|
|
EXPECT_TRUE(PKCS7_add_recipient_info(p7.get(), p7ri));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
ASSERT_TRUE(X509_set_pubkey(rsa_x509.get(), rsa_pkey.get()));
|
|
p7ri = PKCS7_RECIP_INFO_new();
|
|
EXPECT_TRUE(PKCS7_RECIP_INFO_set(p7ri, rsa_x509.get()));
|
|
PKCS7_RECIP_INFO_get0_alg(p7ri, &penc);
|
|
ASSERT_TRUE(penc);
|
|
EXPECT_TRUE(PKCS7_add_recipient_info(p7.get(), p7ri));
|
|
}
|
|
|
|
TEST(PKCS7Test, DataInitFinal) {
|
|
bssl::UniquePtr<PKCS7> p7;
|
|
bssl::UniquePtr<BIO> bio, bio_in;
|
|
bssl::UniquePtr<STACK_OF(X509)> certs;
|
|
bssl::UniquePtr<X509> rsa_x509;
|
|
bssl::UniquePtr<uint8_t> p7_der;
|
|
size_t p7_der_len;
|
|
const uint8_t *p7_ptr;
|
|
|
|
p7_ptr = kPKCS7SignedWithSignerInfo;
|
|
p7_der_len = sizeof(kPKCS7SignedWithSignerInfo);
|
|
p7.reset(d2i_PKCS7(nullptr, &p7_ptr, p7_der_len));
|
|
ASSERT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
ASSERT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
// parse a cert for use with recipient infos
|
|
bssl::UniquePtr<RSA> rsa(RSA_new());
|
|
ASSERT_TRUE(rsa);
|
|
ASSERT_TRUE(RSA_generate_key_fips(rsa.get(), 2048, nullptr));
|
|
bssl::UniquePtr<EVP_PKEY> rsa_pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(rsa_pkey);
|
|
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(rsa_pkey.get(), rsa.get()));
|
|
bio.reset(BIO_new_mem_buf(kPEMCert, strlen(kPEMCert)));
|
|
ASSERT_TRUE(bio);
|
|
certs.reset(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
ASSERT_TRUE(PKCS7_get_PEM_certificates(certs.get(), bio.get()));
|
|
ASSERT_EQ(1U, sk_X509_num(certs.get()));
|
|
rsa_x509.reset(sk_X509_pop(certs.get()));
|
|
ASSERT_TRUE(X509_set_pubkey(rsa_x509.get(), rsa_pkey.get()));
|
|
|
|
p7_ptr = kPKCS7EnvelopedData;
|
|
p7_der_len = sizeof(kPKCS7EnvelopedData);
|
|
p7.reset(d2i_PKCS7(nullptr, &p7_ptr, p7_der_len));
|
|
ASSERT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
// need to initialize cipher for enveloped data
|
|
EXPECT_TRUE(PKCS7_set_cipher(p7.get(), EVP_aes_128_ctr()));
|
|
// attach a (non-serialized, unrelated) cert to |p7ri_sk|
|
|
STACK_OF(PKCS7_RECIP_INFO) *p7ri_sk = PKCS7_get_recipient_info(p7.get());
|
|
PKCS7_RECIP_INFO *p7ri = sk_PKCS7_RECIP_INFO_value(p7ri_sk, 0);
|
|
ASSERT_TRUE(p7ri);
|
|
EXPECT_TRUE(PKCS7_RECIP_INFO_set(p7ri, rsa_x509.get()));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
ASSERT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
bio.reset(nullptr);
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signedAndEnveloped));
|
|
ASSERT_TRUE(PKCS7_set_cipher(p7.get(), EVP_aes_128_ctr()));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_digest));
|
|
ASSERT_TRUE(PKCS7_set_digest(p7.get(), EVP_sha256()));
|
|
ASSERT_TRUE(PKCS7_content_new(p7.get(), NID_pkcs7_data));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_data));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
ASSERT_TRUE(PKCS7_set_cipher(p7.get(), EVP_aes_128_ctr()));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
// pre-existing BIO?
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
ASSERT_TRUE(PKCS7_set_cipher(p7.get(), EVP_aes_128_ctr()));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_TRUE(bio);
|
|
EXPECT_TRUE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
// Error cases
|
|
|
|
// type NID_pkcs7_encrypted is not supported by the BIO functions
|
|
p7.reset(PKCS7_new());
|
|
bio_in.reset(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_encrypted));
|
|
bio.reset(PKCS7_dataInit(p7.get(), bio_in.get()));
|
|
EXPECT_FALSE(bio);
|
|
EXPECT_FALSE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
|
|
// NID_pkcs7_enveloped and NID_pkcs7_signedAndEnveloped require a cipher
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_FALSE(bio);
|
|
EXPECT_FALSE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
bio.reset(PKCS7_dataInit(p7.get(), nullptr));
|
|
EXPECT_FALSE(bio);
|
|
EXPECT_FALSE(PKCS7_dataFinal(p7.get(), bio.get()));
|
|
}
|
|
|
|
TEST(PKCS7Test, TestEnveloped) {
|
|
bssl::UniquePtr<PKCS7> p7;
|
|
bssl::UniquePtr<BIO> bio;
|
|
bssl::UniquePtr<STACK_OF(X509)> certs;
|
|
bssl::UniquePtr<X509> rsa_x509;
|
|
const size_t pt_len = 64;
|
|
// NOTE: we make |buf| larger than |pt_len| in case padding gets added.
|
|
// without the extra room, we sometimes overflow into the next variable on the
|
|
// stack.
|
|
uint8_t buf[pt_len + EVP_MAX_BLOCK_LENGTH];
|
|
uint8_t decrypted[pt_len + EVP_MAX_BLOCK_LENGTH];
|
|
|
|
OPENSSL_cleanse(buf, sizeof(buf));
|
|
OPENSSL_memset(buf, 'A', pt_len);
|
|
|
|
// parse a cert for use with recipient infos
|
|
bssl::UniquePtr<RSA> rsa(RSA_new());
|
|
ASSERT_TRUE(rsa);
|
|
ASSERT_TRUE(RSA_generate_key_fips(rsa.get(), 2048, nullptr));
|
|
bssl::UniquePtr<EVP_PKEY> rsa_pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(rsa_pkey);
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(rsa_pkey.get(), rsa.get()));
|
|
certs.reset(sk_X509_new_null());
|
|
bio.reset(BIO_new_mem_buf(kPEMCert, strlen(kPEMCert)));
|
|
ASSERT_TRUE(bio);
|
|
certs.reset(sk_X509_new_null());
|
|
ASSERT_TRUE(certs);
|
|
ASSERT_TRUE(PKCS7_get_PEM_certificates(certs.get(), bio.get()));
|
|
ASSERT_EQ(1U, sk_X509_num(certs.get()));
|
|
rsa_x509.reset(sk_X509_value(certs.get(), 0));
|
|
ASSERT_TRUE(X509_set_pubkey(rsa_x509.get(), rsa_pkey.get()));
|
|
X509_up_ref(rsa_x509.get());
|
|
|
|
// standard success case
|
|
bio.reset(BIO_new_mem_buf(buf, pt_len));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_cbc(), /*flags*/ 0));
|
|
EXPECT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
EXPECT_TRUE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), rsa_x509.get(), bio.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_EQ(pt_len, BIO_pending(bio.get()));
|
|
OPENSSL_cleanse(decrypted, sizeof(decrypted));
|
|
ASSERT_EQ(pt_len, (size_t)BIO_read(bio.get(), decrypted, sizeof(decrypted)));
|
|
EXPECT_EQ(Bytes(buf, pt_len), Bytes(decrypted, pt_len));
|
|
|
|
// no certs provided for decryption
|
|
bio.reset(BIO_new_mem_buf(buf, pt_len));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_cbc(), /*flags*/ 0));
|
|
EXPECT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
EXPECT_TRUE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), /*certs*/ nullptr,
|
|
bio.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_EQ(pt_len, BIO_pending(bio.get()));
|
|
OPENSSL_cleanse(decrypted, sizeof(decrypted));
|
|
ASSERT_EQ(pt_len, (size_t)BIO_read(bio.get(), decrypted, sizeof(decrypted)));
|
|
EXPECT_EQ(Bytes(buf, pt_len), Bytes(decrypted, pt_len));
|
|
|
|
// empty plaintext
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(BIO_set_mem_eof_return(bio.get(), 0));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_cbc(), /*flags*/ 0));
|
|
EXPECT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(BIO_set_mem_eof_return(bio.get(), 0));
|
|
EXPECT_TRUE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), rsa_x509.get(), bio.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_EQ(0UL, BIO_pending(bio.get()));
|
|
EXPECT_EQ(0, BIO_read(bio.get(), decrypted, sizeof(decrypted)));
|
|
EXPECT_FALSE(BIO_should_retry(bio.get()));
|
|
|
|
// unsupported content type, with and without content
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
EXPECT_FALSE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), nullptr, bio.get(), 0));
|
|
ASSERT_TRUE(PKCS7_content_new(p7.get(), NID_pkcs7_data));
|
|
EXPECT_FALSE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), nullptr, bio.get(), 0));
|
|
|
|
// test multiple recipients using the same recipient twice. elide |cert| to
|
|
// exercise iterative decryption attempt behavior with multiple (2) successful
|
|
// decryptions.
|
|
sk_X509_push(certs.get(), rsa_x509.get());
|
|
bio.reset(BIO_new_mem_buf(buf, pt_len));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_cbc(), /*flags*/ 0));
|
|
ASSERT_TRUE(p7);
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
// set |rsa_pkey| back to original RSA key
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(rsa_pkey.get(), rsa.get()));
|
|
EXPECT_TRUE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), /*cert*/ nullptr,
|
|
bio.get(),
|
|
/*flags*/ 0));
|
|
ASSERT_TRUE(sk_X509_pop(certs.get()));
|
|
ASSERT_EQ(1LU, sk_X509_num(certs.get()));
|
|
|
|
// test "MMA" decrypt with mismatched cert pub key/pkey private key and block
|
|
// cipher used for content encryption
|
|
bio.reset(BIO_new_mem_buf(buf, pt_len));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_cbc(), /*flags*/ 0));
|
|
EXPECT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
// set new RSA key, cert pub key and PKEY private key now mismatch
|
|
rsa.reset(RSA_new());
|
|
ASSERT_TRUE(RSA_generate_key_fips(rsa.get(), 2048, nullptr));
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(rsa_pkey.get(), rsa.get()));
|
|
// attempt decryption with the new, mismatched keypair. content key decryption
|
|
// should "succeed" and produce random, useless content decryption key.
|
|
// The content is "decrypted" with the useless key, so nonsense gets written
|
|
// to the output |bio|. The cipher ends up in an unhealthy state due to bad
|
|
// padding (what should be the final pad block is now just random bytes), so
|
|
// the overall |PKCS7_decrypt| operation fails.
|
|
int decrypt_ok =
|
|
PKCS7_decrypt(p7.get(), rsa_pkey.get(), /*certs*/ nullptr, bio.get(),
|
|
/*flags*/ 0);
|
|
EXPECT_LE(pt_len, BIO_pending(bio.get()));
|
|
OPENSSL_cleanse(decrypted, sizeof(decrypted));
|
|
// There's a fun edge case here for block ciphers using conventional PKCS#7
|
|
// padding. In this padding scheme, the last byte of the padded plaintext
|
|
// determines how many bytes of padding have been appended and must be
|
|
// stripped, A random MMA-defense-garbled padded plaintext with last byte of
|
|
// 0x01 will trick the EVP API into thinking that byte is a valid padding
|
|
// byte, so it (and only it) will be stripped. This leaves the other
|
|
// block_size-1 bytes of the padding block in place, resulting in a larger
|
|
// "decrypted plaintext" than anticipated. However, this doesn't only apply to
|
|
// one byte of padding. With probability 16^-2, it applies to pad 0x02 0x02
|
|
// and so on with increasingly small probabilities. So, we give slack up to
|
|
// 16^-4 which means this test will erroneously fail 0.001526% of the time in
|
|
// expectation. Ideally we'd find a way to access the padded plaintext and
|
|
// account for this deterministically by checking the random "padding" and
|
|
// adusting accordingly.
|
|
const size_t max_decrypt = pt_len + EVP_CIPHER_block_size(EVP_aes_128_cbc());
|
|
const size_t decrypted_len =
|
|
(size_t)BIO_read(bio.get(), decrypted, sizeof(decrypted));
|
|
ASSERT_LE(decrypted_len, sizeof(decrypted));
|
|
if (decrypted_len > pt_len) {
|
|
EXPECT_LT(max_decrypt - 4, decrypted_len);
|
|
EXPECT_TRUE(decrypt_ok);
|
|
EXPECT_FALSE(ERR_GET_REASON(ERR_peek_error()));
|
|
} else {
|
|
EXPECT_EQ(pt_len, decrypted_len);
|
|
EXPECT_FALSE(decrypt_ok);
|
|
EXPECT_EQ(CIPHER_R_BAD_DECRYPT, ERR_GET_REASON(ERR_peek_error()));
|
|
}
|
|
// Of course, plaintext shouldn't equal decrypted in any case here
|
|
EXPECT_NE(Bytes(buf, pt_len), Bytes(decrypted, sizeof(decrypted)));
|
|
|
|
// test "MMA" decrypt as above, but with stream cipher. stream cipher has no
|
|
// padding, so content encryption should "succeed" but return nonsense because
|
|
// the content decryption key is just randomly generated bytes.
|
|
bio.reset(BIO_new_mem_buf(buf, pt_len));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_ctr(), /*flags*/ 0));
|
|
EXPECT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_enveloped(p7.get()));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
// content decryption "succeeds"...
|
|
EXPECT_TRUE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), /*certs*/ nullptr,
|
|
bio.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_EQ(pt_len, BIO_pending(bio.get()));
|
|
OPENSSL_cleanse(decrypted, sizeof(decrypted));
|
|
ASSERT_EQ(pt_len, (size_t)BIO_read(bio.get(), decrypted, sizeof(decrypted)));
|
|
// ...but it produces pseudo-random nonsense
|
|
EXPECT_NE(Bytes(buf, pt_len), Bytes(decrypted, sizeof(decrypted)));
|
|
EXPECT_FALSE(ERR_GET_REASON(ERR_peek_error()));
|
|
|
|
// mismatched cert + pkey on decrypt
|
|
bio.reset(BIO_new_mem_buf(buf, pt_len));
|
|
p7.reset(
|
|
PKCS7_encrypt(certs.get(), bio.get(), EVP_aes_128_cbc(), /*flags*/ 0));
|
|
bio.reset(BIO_new(BIO_s_mem()));
|
|
bssl::UniquePtr<RSA> rsa2(RSA_new());
|
|
ASSERT_TRUE(RSA_generate_key_fips(rsa2.get(), 2048, nullptr));
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(rsa_pkey.get(), rsa2.get()));
|
|
EXPECT_FALSE(PKCS7_decrypt(p7.get(), rsa_pkey.get(), rsa_x509.get(),
|
|
bio.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_EQ(X509_R_KEY_VALUES_MISMATCH, ERR_GET_REASON(ERR_peek_error()));
|
|
}
|
|
|
|
TEST(PKCS7Test, TestSigned) {
|
|
bssl::UniquePtr<PKCS7> p7;
|
|
bssl::UniquePtr<BIO> bio_in, bio_out;
|
|
bssl::UniquePtr<STACK_OF(X509)> certs;
|
|
bssl::UniquePtr<X509_STORE> store;
|
|
bssl::UniquePtr<X509_STORE_CTX> store_ctx;
|
|
bssl::UniquePtr<ASN1_TIME> not_before, not_after;
|
|
bssl::UniquePtr<RSA> root_rsa, leaf_rsa;
|
|
bssl::UniquePtr<EVP_PKEY> root_pkey, leaf_pkey;
|
|
uint8_t buf[64], out_buf[sizeof(buf)];
|
|
|
|
OPENSSL_memset(buf, 'A', sizeof(buf));
|
|
OPENSSL_memset(out_buf, '\0', sizeof(out_buf));
|
|
|
|
root_rsa.reset(RSA_new());
|
|
ASSERT_TRUE(RSA_generate_key_fips(root_rsa.get(), 2048, nullptr));
|
|
root_pkey.reset(EVP_PKEY_new());
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(root_pkey.get(), root_rsa.get()));
|
|
leaf_rsa.reset(RSA_new());
|
|
ASSERT_TRUE(RSA_generate_key_fips(leaf_rsa.get(), 2048, nullptr));
|
|
leaf_pkey.reset(EVP_PKEY_new());
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(leaf_pkey.get(), leaf_rsa.get()));
|
|
|
|
// |PKCS7_verify| creates its own X509_STORE_CTX internally, so we can't set
|
|
// relative validity time on the store it uses from here (by default
|
|
// X509_STORE_CTX uses std's |time|). So, we set a wide validity gap here.
|
|
// |not_after| won't need to be updated until December 9999 and |not_before|
|
|
// would only need to be reconsidered in the advent of a time machine.
|
|
not_before.reset(ASN1_TIME_set_posix(nullptr, 0L));
|
|
not_after.reset(ASN1_TIME_set_posix(nullptr, INT64_C(253402300799)));
|
|
|
|
bssl::UniquePtr<X509> root =
|
|
MakeTestCert("Root", "Root", root_pkey.get(), /*is_ca=*/true);
|
|
ASSERT_TRUE(root);
|
|
ASSERT_TRUE(X509_set_notBefore(root.get(), not_before.get()));
|
|
ASSERT_TRUE(X509_set_notAfter(root.get(), not_after.get()));
|
|
// Root signs itself
|
|
ASSERT_TRUE(X509_sign(root.get(), root_pkey.get(), EVP_sha256()));
|
|
|
|
bssl::UniquePtr<X509> leaf =
|
|
MakeTestCert("Root", "Leaf", leaf_pkey.get(), /*is_ca=*/false);
|
|
ASSERT_TRUE(leaf);
|
|
ASSERT_TRUE(X509_set_notBefore(leaf.get(), not_before.get()));
|
|
ASSERT_TRUE(X509_set_notAfter(leaf.get(), not_after.get()));
|
|
// Root signs leaf
|
|
ASSERT_TRUE(X509_sign(leaf.get(), root_pkey.get(), EVP_sha256()));
|
|
X509_up_ref(leaf.get());
|
|
X509_up_ref(leaf.get());
|
|
|
|
store.reset(X509_STORE_new());
|
|
ASSERT_TRUE(X509_STORE_add_cert(store.get(), root.get()));
|
|
|
|
certs.reset(sk_X509_new_null());
|
|
ASSERT_TRUE(sk_X509_push(certs.get(), leaf.get()));
|
|
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
p7.reset(PKCS7_sign(leaf.get(), leaf_pkey.get(), nullptr, bio_in.get(),
|
|
/*flags*/ 0));
|
|
ASSERT_TRUE(p7);
|
|
EXPECT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
|
|
STACK_OF(X509) *signers = PKCS7_get0_signers(p7.get(), certs.get(), 0);
|
|
EXPECT_TRUE(signers);
|
|
sk_X509_free(signers);
|
|
EXPECT_FALSE(PKCS7_is_detached(p7.get()));
|
|
|
|
// attached, check |outdata|
|
|
bio_out.reset(BIO_new(BIO_s_mem()));
|
|
// passing non-null |indata| with attached content should fail
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), certs.get(), store.get(), bio_in.get(),
|
|
bio_out.get(), /*flags*/ 0));
|
|
// but otherwise, it should succeed
|
|
EXPECT_TRUE(PKCS7_verify(p7.get(), certs.get(), store.get(), nullptr,
|
|
bio_out.get(), /*flags*/ 0));
|
|
ASSERT_EQ((int)sizeof(out_buf),
|
|
BIO_read(bio_out.get(), out_buf, sizeof(out_buf)));
|
|
EXPECT_EQ(Bytes(buf, sizeof(buf)), Bytes(out_buf, sizeof(out_buf)));
|
|
|
|
// attached, but no |outdata|
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
p7.reset(PKCS7_sign(leaf.get(), leaf_pkey.get(), nullptr, bio_in.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_TRUE(PKCS7_verify(p7.get(), certs.get(), store.get(),
|
|
/*indata*/ nullptr,
|
|
/*outdata*/ nullptr, /*flags*/ 0));
|
|
|
|
// attached, but specify |PKCS7_NOINTERN| to ignore bundled certs. this should
|
|
// fail when we elide the |certs| parameter to verify and succeed when we
|
|
// provide it.
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
p7.reset(PKCS7_sign(leaf.get(), leaf_pkey.get(), nullptr, bio_in.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), /*certs*/ nullptr, store.get(),
|
|
/*indata*/ nullptr,
|
|
/*outdata*/ nullptr, /*flags*/ PKCS7_NOINTERN));
|
|
EXPECT_TRUE(PKCS7_verify(p7.get(), certs.get(), store.get(),
|
|
/*indata*/ nullptr,
|
|
/*outdata*/ nullptr, /*flags*/ PKCS7_NOINTERN));
|
|
|
|
// detached
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
// PKCS7_NOCERTS isn't supported
|
|
ASSERT_FALSE(PKCS7_sign(leaf.get(), leaf_pkey.get(), nullptr, bio_in.get(),
|
|
(PKCS7_DETACHED | PKCS7_NOCERTS)));
|
|
// but this should work fine without it
|
|
p7.reset(PKCS7_sign(leaf.get(), leaf_pkey.get(), nullptr, bio_in.get(),
|
|
PKCS7_DETACHED));
|
|
EXPECT_TRUE(PKCS7_is_detached(p7.get()));
|
|
certs.reset(sk_X509_new_null());
|
|
ASSERT_TRUE(sk_X509_push(certs.get(), leaf.get()));
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
bio_out.reset(BIO_new(BIO_s_mem()));
|
|
// detached mode requires data to be passed in via |indata
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), certs.get(), store.get(), nullptr,
|
|
bio_out.get(), /*flags*/ 0));
|
|
// but once we provide the |indata|, it should work
|
|
EXPECT_TRUE(PKCS7_verify(p7.get(), certs.get(), store.get(), bio_in.get(),
|
|
bio_out.get(), /*flags*/ 0));
|
|
OPENSSL_memset(out_buf, '\0', sizeof(out_buf));
|
|
ASSERT_EQ((int)sizeof(out_buf),
|
|
BIO_read(bio_out.get(), out_buf, sizeof(out_buf)));
|
|
EXPECT_EQ(Bytes(buf, sizeof(buf)), Bytes(out_buf, sizeof(out_buf)));
|
|
|
|
// Error cases
|
|
p7.reset(PKCS7_new());
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_enveloped));
|
|
BIO *bio_tmp = nullptr;
|
|
EXPECT_FALSE(SMIME_read_PKCS7(bio_in.get(), &bio_tmp));
|
|
ASSERT_FALSE(bio_tmp); // never gets allocated
|
|
EXPECT_FALSE(SMIME_write_PKCS7(bio_in.get(), p7.get(), bio_tmp, 0));
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), nullptr, store.get(), bio_in.get(),
|
|
bio_out.get(), 0)); // |p7| is wrong type
|
|
EXPECT_FALSE(PKCS7_get_signer_info(p7.get())); // |p7| is wrong type
|
|
|
|
// Misatched sign/verify keys
|
|
bssl::UniquePtr<RSA> other_rsa;
|
|
bssl::UniquePtr<EVP_PKEY> other_pkey;
|
|
other_rsa.reset(RSA_new());
|
|
ASSERT_TRUE(RSA_generate_key_fips(other_rsa.get(), 2048, nullptr));
|
|
other_pkey.reset(EVP_PKEY_new());
|
|
ASSERT_TRUE(EVP_PKEY_set1_RSA(other_pkey.get(), other_rsa.get()));
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
p7.reset(PKCS7_sign(leaf.get(), other_pkey.get(), nullptr, bio_in.get(),
|
|
/*flags*/ 0));
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), nullptr, store.get(), nullptr,
|
|
bio_out.get(), /*flags*/ 0));
|
|
|
|
// Use different detached indata to induce signature mismatch
|
|
bio_in.reset(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
p7.reset(PKCS7_sign(leaf.get(), leaf_pkey.get(), nullptr, bio_in.get(),
|
|
PKCS7_DETACHED));
|
|
uint8_t other_data[sizeof(buf)];
|
|
OPENSSL_memset(other_data, 'B', sizeof(other_data));
|
|
bio_in.reset(BIO_new_mem_buf(other_data, sizeof(other_data)));
|
|
bio_out.reset(BIO_new(BIO_s_mem()));
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), certs.get(), store.get(), bio_in.get(),
|
|
bio_out.get(), /*flags*/ 0));
|
|
}
|
|
|
|
// Regression test: PKCS7_verify with detached data and multiple digest
|
|
// algorithms must free all intermediate digest BIOs, not just the head.
|
|
TEST(PKCS7Test, VerifyDetachedMultiDigestNoLeak) {
|
|
// Generate two distinct ECDSA key-pairs and leaf certificates so that each
|
|
// signer can use a different digest algorithm.
|
|
bssl::UniquePtr<EC_KEY> root_ec(EC_KEY_new_by_curve_name(NID_X9_62_prime256v1));
|
|
ASSERT_TRUE(root_ec);
|
|
ASSERT_TRUE(EC_KEY_generate_key(root_ec.get()));
|
|
bssl::UniquePtr<EVP_PKEY> root_pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(EVP_PKEY_set1_EC_KEY(root_pkey.get(), root_ec.get()));
|
|
|
|
bssl::UniquePtr<EC_KEY> leaf1_ec(EC_KEY_new_by_curve_name(NID_X9_62_prime256v1));
|
|
ASSERT_TRUE(leaf1_ec);
|
|
ASSERT_TRUE(EC_KEY_generate_key(leaf1_ec.get()));
|
|
bssl::UniquePtr<EVP_PKEY> leaf1_pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(EVP_PKEY_set1_EC_KEY(leaf1_pkey.get(), leaf1_ec.get()));
|
|
|
|
bssl::UniquePtr<EC_KEY> leaf2_ec(EC_KEY_new_by_curve_name(NID_X9_62_prime256v1));
|
|
ASSERT_TRUE(leaf2_ec);
|
|
ASSERT_TRUE(EC_KEY_generate_key(leaf2_ec.get()));
|
|
bssl::UniquePtr<EVP_PKEY> leaf2_pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(EVP_PKEY_set1_EC_KEY(leaf2_pkey.get(), leaf2_ec.get()));
|
|
|
|
bssl::UniquePtr<ASN1_TIME> not_before(ASN1_TIME_set_posix(nullptr, 0L));
|
|
bssl::UniquePtr<ASN1_TIME> not_after(
|
|
ASN1_TIME_set_posix(nullptr, INT64_C(253402300799)));
|
|
|
|
bssl::UniquePtr<X509> root =
|
|
MakeTestCert("Root", "Root", root_pkey.get(), /*is_ca=*/true);
|
|
ASSERT_TRUE(root);
|
|
ASSERT_TRUE(X509_set_notBefore(root.get(), not_before.get()));
|
|
ASSERT_TRUE(X509_set_notAfter(root.get(), not_after.get()));
|
|
ASSERT_TRUE(X509_sign(root.get(), root_pkey.get(), EVP_sha256()));
|
|
|
|
bssl::UniquePtr<X509> leaf1 =
|
|
MakeTestCert("Root", "Leaf1", leaf1_pkey.get(), /*is_ca=*/false);
|
|
ASSERT_TRUE(leaf1);
|
|
ASSERT_TRUE(X509_set_notBefore(leaf1.get(), not_before.get()));
|
|
ASSERT_TRUE(X509_set_notAfter(leaf1.get(), not_after.get()));
|
|
ASSERT_TRUE(X509_sign(leaf1.get(), root_pkey.get(), EVP_sha256()));
|
|
|
|
bssl::UniquePtr<X509> leaf2 =
|
|
MakeTestCert("Root", "Leaf2", leaf2_pkey.get(), /*is_ca=*/false);
|
|
ASSERT_TRUE(leaf2);
|
|
ASSERT_TRUE(X509_set_notBefore(leaf2.get(), not_before.get()));
|
|
ASSERT_TRUE(X509_set_notAfter(leaf2.get(), not_after.get()));
|
|
ASSERT_TRUE(X509_sign(leaf2.get(), root_pkey.get(), EVP_sha256()));
|
|
|
|
// Build a PKCS7 signed structure with two signers using *different* digest
|
|
// algorithms. This causes PKCS7_dataInit to create two digest BIOs.
|
|
bssl::UniquePtr<PKCS7> p7(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
ASSERT_TRUE(PKCS7_content_new(p7.get(), NID_pkcs7_data));
|
|
|
|
// Signer 1: SHA-256
|
|
PKCS7_SIGNER_INFO *si1 = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(si1);
|
|
ASSERT_TRUE(
|
|
PKCS7_SIGNER_INFO_set(si1, leaf1.get(), leaf1_pkey.get(), EVP_sha256()));
|
|
ASSERT_TRUE(PKCS7_add_signer(p7.get(), si1));
|
|
ASSERT_TRUE(PKCS7_add_certificate(p7.get(), leaf1.get()));
|
|
|
|
// Signer 2: SHA-384 (different digest => second digest BIO in chain)
|
|
PKCS7_SIGNER_INFO *si2 = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(si2);
|
|
ASSERT_TRUE(
|
|
PKCS7_SIGNER_INFO_set(si2, leaf2.get(), leaf2_pkey.get(), EVP_sha384()));
|
|
ASSERT_TRUE(PKCS7_add_signer(p7.get(), si2));
|
|
ASSERT_TRUE(PKCS7_add_certificate(p7.get(), leaf2.get()));
|
|
|
|
// Make it a detached signature.
|
|
ASN1_OCTET_STRING_free(p7->d.sign->contents->d.data);
|
|
p7->d.sign->contents->d.data = NULL;
|
|
|
|
// The signatures don't need to be valid for this leak test -- the leak
|
|
// happens during teardown regardless of verification outcome. Just add dummy
|
|
// signer info entries so PKCS7_get_signer_info returns them and the code
|
|
// path that builds the BIO chain in PKCS7_dataInit is reached.
|
|
|
|
// Call PKCS7_verify with detached indata. The BIO chain teardown is where
|
|
// intermediate digest BIOs are leaked.
|
|
uint8_t buf[64];
|
|
OPENSSL_memset(buf, 'A', sizeof(buf));
|
|
bssl::UniquePtr<X509_STORE> store(X509_STORE_new());
|
|
ASSERT_TRUE(X509_STORE_add_cert(store.get(), root.get()));
|
|
|
|
bssl::UniquePtr<BIO> indata(BIO_new_mem_buf(buf, sizeof(buf)));
|
|
ASSERT_TRUE(indata);
|
|
bssl::UniquePtr<BIO> outdata(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(outdata);
|
|
|
|
// Verification will fail (signatures are not computed), but the BIO chain
|
|
// teardown still runs to exercise the leak.
|
|
PKCS7_verify(p7.get(), nullptr, store.get(), indata.get(), outdata.get(),
|
|
PKCS7_NOVERIFY);
|
|
}
|
|
|
|
TEST(PKCS7Test, PKCS7PrintNoop) {
|
|
bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
|
|
bssl::UniquePtr<PKCS7> p7(PKCS7_new());
|
|
ASSERT_TRUE(PKCS7_print_ctx(bio.get(), p7.get(), 0, nullptr));
|
|
|
|
const uint8_t *contents;
|
|
size_t len;
|
|
ASSERT_TRUE(BIO_mem_contents(bio.get(), &contents, &len));
|
|
EXPECT_EQ(Bytes(contents, len), Bytes("PKCS7 printing is not supported"));
|
|
}
|
|
|
|
TEST(PKCS7Test, SetDetached) {
|
|
bssl::UniquePtr<PKCS7> p7(PKCS7_new());
|
|
// |PKCS7_set_detached| does not work on an uninitialized |PKCS7|.
|
|
EXPECT_FALSE(PKCS7_set_detached(p7.get(), 0));
|
|
EXPECT_FALSE(PKCS7_set_detached(p7.get(), 1));
|
|
EXPECT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
EXPECT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
|
|
PKCS7 *p7_internal = PKCS7_new();
|
|
EXPECT_TRUE(PKCS7_set_type(p7_internal, NID_pkcs7_data));
|
|
EXPECT_TRUE(PKCS7_type_is_data(p7_internal));
|
|
EXPECT_TRUE(PKCS7_set_content(p7.get(), p7_internal));
|
|
|
|
// Access the |p7|'s internal contents to verify that |PKCS7_set_detached|
|
|
// has the right behavior.
|
|
EXPECT_TRUE(p7.get()->d.sign->contents->d.data);
|
|
EXPECT_TRUE(PKCS7_set_detached(p7.get(), 0));
|
|
EXPECT_TRUE(p7.get()->d.sign->contents->d.data);
|
|
EXPECT_FALSE(PKCS7_set_detached(p7.get(), 2));
|
|
EXPECT_TRUE(p7.get()->d.sign->contents->d.data);
|
|
// data is "detached" when |PKCS7_set_detached| is set with 1.
|
|
EXPECT_TRUE(PKCS7_set_detached(p7.get(), 1));
|
|
EXPECT_FALSE(p7.get()->d.sign->contents->d.data);
|
|
}
|
|
|
|
TEST(PKCS7Test, PKCS7SignedAttributes) {
|
|
// This file was generated with the following command:
|
|
// openssl smime -sign -in input.txt -signer crypto/ocsp/aws/ca_cert.pem
|
|
// -inkey crypto/ocsp/aws/ca_key.pem -out signed.p7s -outform PEM
|
|
// -nodetach -md sha512
|
|
//
|
|
// Files with signed attributes aren't generatable with AWS-LC for now, as
|
|
// |PKCS7_NOATTR| is always assumed with |PKCS7_sign|. See |PKCS7_sign|
|
|
// for more details.
|
|
static const char kPKCS7SignedAttributes[] = R"(
|
|
-----BEGIN PKCS7-----
|
|
MIII8QYJKoZIhvcNAQcCoIII4jCCCN4CAQExDzANBglghkgBZQMEAgMFADAcBgkq
|
|
hkiG9w0BBwGgDwQNc2lnbmVkIGRhdGENCqCCBTwwggU4MIIDIKADAgECAgkAhs29
|
|
IYxE13cwDQYJKoZIhvcNAQELBQAwKDELMAkGA1UEBhMCVVMxCzAJBgNVBAgMAldB
|
|
MQwwCgYDVQQKDANzMm4wIBcNMTcwOTA1MDUxNTA1WhgPMjExNzA4MTIwNTE1MDVa
|
|
MCgxCzAJBgNVBAYTAlVTMQswCQYDVQQIDAJXQTEMMAoGA1UECgwDczJuMIICIjAN
|
|
BgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAvjgKgqLJvaDndXS3qPpNA+hodYcO
|
|
lP+jit7DwI00OL42sgEW0Xmk9u2kGTwIFW1iQPCPo0kB0wMTxSwXruZJpzI2asMY
|
|
bNpkVGxMBBT94p9OJcnljeaCYsEe2Wdcm930ixl2w9MjG3au7iawmAL+R6cG06Vp
|
|
kTlTH9b6+Y1MQUM99jPmyqHr2g53Ocw0eL2WcnULsfOFQONxTLQPaKFrdAcJdB+g
|
|
y6yA86J7CASdPjyPqEMqpexGisUwTX2bi8a5r7J9E5mmXSpLVSHubrZfn1UuoZcr
|
|
8Kzo99JAbXyEvOkxi9IxH+sjduN02bPBs6PsYQTizpsATfgtIujriKZW6RLqFrst
|
|
4nCHy8MPbY/ZoPisMaIA3+aFdULypGvzDJesivaFSmnjaIlXLNUdYNGSrh1TfXFs
|
|
2yP/z0USH5c5iK4ztmB4dX8h7z2evvy85+/SIIyAIWzKSkVn7y8MLbabqkauXnxV
|
|
1jn13qMe2k21BhafUHnDEHHS6A8d3S5HIG+TzOsh/0DrRCxDnoXeKYkLp1H7hHwz
|
|
y3zhabqwNABW+PJijL27h7istdPkgwUcaMjtV1qEDQGYgHMEt85vplRfadrRyQa9
|
|
W7wMKub2Uk/U1ike5DdbYfCzX6swPRREmpnL8PZu20/FWBP/kqoJKmYGO+y/a6dN
|
|
/FVtkidBAW23vSUCAwEAAaNjMGEwHQYDVR0OBBYEFBLfgXVxypLTzhssK3c7njN3
|
|
8/dvMB8GA1UdIwQYMBaAFBLfgXVxypLTzhssK3c7njN38/dvMA8GA1UdEwEB/wQF
|
|
MAMBAf8wDgYDVR0PAQH/BAQDAgGGMA0GCSqGSIb3DQEBCwUAA4ICAQCzYLV5JyGy
|
|
1nvBRo58nj/hPZvNn5o+lv2pH2tT6ejxCmpbRM4/klE5trSakPehGtLyESKGnZQ+
|
|
kcgjUlGrPK2rkYczqtb2yjDEmqGGnjovG0Coh4vWTY8HncT1Qhq/iR/gLV47faI7
|
|
TSd0r9+5bGS7/3mQgLujmlBqMKSwSR4SgrHqhSnpG3YoAasQiamgQ/iqrDcY3wau
|
|
e0LSz4V9liyuP8pMlxBAGDXyDtRjquPR1vU7FsortRK9DM9aHtzWZA8gVh9Oe+fc
|
|
oDXitS5ZJbk0X0RvqvC5zMJaHPJ2/P3jN5Yxise4PAktu0sG/p/oI8+aVp0bwGkY
|
|
oFven2XwXN+9RW0C2kEVw9njQd6Y07nSRTbtuU2am8sKzodwnT+aDP5tU0OSRfIH
|
|
U9IdtWppYUnhKn+ajiWI2BAEaAN+iQL/j6GTfQQyfzBaMgtuZ2eqJRJcTCugSLWo
|
|
1W/88n3tkE6lDHTV1x+24LEEitBICnduxuC46iIL+0CgY+xinEcd9+YcUP7ZZkOs
|
|
FgrDOXhLuPj81G3nsN0tny12YtChbIU+OY/JEksWEiotKuWZmBPb8U045hGBn5ni
|
|
5qgRlV1n1guPpH7Bbg0GLkr6x3X9H5HsSz2JAWpJgpdok2HSxu9U6h9fr9OoFqmZ
|
|
xtW7c1tGdToKxzZiB1jhZ03QbQANYLSLwDGCA2gwggNkAgEBMDUwKDELMAkGA1UE
|
|
BhMCVVMxCzAJBgNVBAgMAldBMQwwCgYDVQQKDANzMm4CCQCGzb0hjETXdzANBglg
|
|
hkgBZQMEAgMFAKCCAQQwGAYJKoZIhvcNAQkDMQsGCSqGSIb3DQEHATAcBgkqhkiG
|
|
9w0BCQUxDxcNMjUwMzExMjMyOTEzWjBPBgkqhkiG9w0BCQQxQgRAl16N1XX/Z/y4
|
|
jlWkbg/ueaFtxN8mCp2+bj3k+NmIMCQLKjkqbEine7DDaGNDb4BN15Px1ymLNy5O
|
|
5RK2D+PRGTB5BgkqhkiG9w0BCQ8xbDBqMAsGCWCGSAFlAwQBKjALBglghkgBZQME
|
|
ARYwCwYJYIZIAWUDBAECMAoGCCqGSIb3DQMHMA4GCCqGSIb3DQMCAgIAgDANBggq
|
|
hkiG9w0DAgIBQDAHBgUrDgMCBzANBggqhkiG9w0DAgIBKDANBgkqhkiG9w0BAQEF
|
|
AASCAgAE9Yb3N3wPKRn3hkA2Bc6pyv4ZnNEId1uFLi/zgZ+BGl7KBa6yoRBu8tBS
|
|
FqfYah4c4X//bPWbEw8MrNEQqaRBUpMaDwHWf595RSYdYo3i0GxzKi7QFpB5SflP
|
|
yvtcdspWw/M0rwY6KmNbATtsjKAMBBeTU743inBViRUuhae29FztNMlociVz1lBt
|
|
rQ9AYswKKXbrLu7tJNGp1bYZSnmDlqzoBL/DzyQ380uTGOnRJP84Xjpsgc4IdNoW
|
|
CuWDjK5lvLQaVUS0ew0Egci29ZYGBHGOXQRIPoqndVzDwvfY9VZqK2Ip/HV1cWfa
|
|
QtMz8qGghzAMvovEmRL3qRXCQSU3KZuiJbQvV6dC5FSHWrRMYCN0seseIqHvRMtt
|
|
z6QpSj86Th7VizR5AMoYsE/R8vZ2BhecrFED2thMWyL1e94819SExYmuTghplo2s
|
|
ZxoZAOeu0qvV8JysG0DvM7qM1zG2vVTBnr+X7DoqFjRN/tdkKqNBqvtQ/ha4aDrX
|
|
EHTfIzMfpQdJz/DR7PtljxI8ASPtPCWo6Ks5pa1oq0Kf/AGkYVaAu3J0jvb++XFo
|
|
iWjrtmwM/HRbFEg2THS9b/vkiTsNSRCR9goaq9KPqXuJJsjJIoMA8IBHSLVvFnLf
|
|
1IVRuFDgmKSAyCQp2MjkDmgbthvHru4rmBBhhG5APJw0uUcFwA==
|
|
-----END PKCS7-----
|
|
)";
|
|
|
|
// Timestamp for March 11, 2025.
|
|
static const int64_t kReferencePKCS7Time = 1741824000;
|
|
|
|
const bssl::UniquePtr<BIO> bio(
|
|
BIO_new_mem_buf(kPKCS7SignedAttributes, strlen(kPKCS7SignedAttributes)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<PKCS7> pkcs7(
|
|
PEM_read_bio_PKCS7(bio.get(), nullptr, nullptr, nullptr));
|
|
ASSERT_TRUE(pkcs7);
|
|
ASSERT_TRUE(PKCS7_type_is_signed(pkcs7.get()));
|
|
STACK_OF(X509) *signers = PKCS7_get0_signers(pkcs7.get(), nullptr, 0);
|
|
EXPECT_TRUE(signers);
|
|
sk_X509_free(signers);
|
|
|
|
// Set up trust store for verification.
|
|
bssl::UniquePtr<X509_STORE> store(X509_STORE_new());
|
|
bssl::UniquePtr<X509> ca_cert(CertFromPEM(
|
|
GetTestData(std::string("crypto/ocsp/test/aws/ca_cert.pem").c_str())
|
|
.c_str()));
|
|
ASSERT_TRUE(X509_STORE_add_cert(store.get(), ca_cert.get()));
|
|
|
|
// Set a valid time to avoid time bomb in tests.
|
|
X509_VERIFY_PARAM *param = X509_STORE_get0_param(store.get());
|
|
X509_VERIFY_PARAM_set_time_posix(param, kReferencePKCS7Time);
|
|
|
|
bssl::UniquePtr<BIO> out(BIO_new(BIO_s_mem()));
|
|
EXPECT_TRUE(PKCS7_verify(pkcs7.get(), nullptr, store.get(), nullptr,
|
|
out.get(), /*flags*/ 0));
|
|
|
|
// Run |PKCS7_verify| again to check that we're consuming a copy of the
|
|
// underlying |EVP_MD_CTX|.
|
|
EXPECT_TRUE(PKCS7_verify(pkcs7.get(), nullptr, store.get(), nullptr,
|
|
out.get(), /*flags*/ 0));
|
|
}
|
|
|
|
TEST(PKCS7Test, PKCS7SignedAttributesRuby) {
|
|
// The following test file was taken from ruby/openssl's pkcs7 tests.
|
|
static const char kPKCS7Ruby[] = R"(
|
|
-----BEGIN PKCS7-----
|
|
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
|
|
-----END PKCS7-----
|
|
)";
|
|
|
|
// The test has an expected output. Check that we output the same contents
|
|
// as OpenSSL.
|
|
static const char kPKCS7RubyOpenSSLOutput[] =
|
|
R"(-----BEGIN PKCS7-----
|
|
MIIDawYJKoZIhvcNAQcDoIIDXDCCA1gCAQAxggEQMIIBDAIBADB1MHAxEDAOBgNV
|
|
BAoMB2V4YW1wbGUxFzAVBgNVBAMMDlRBUk1BQyBST09UIENBMSIwIAYJKoZIhvcN
|
|
AQkBFhNzb21lb25lQGV4YW1wbGUub3JnMQswCQYDVQQGEwJVUzESMBAGA1UEBwwJ
|
|
VG93biBIYWxsAgFmMA0GCSqGSIb3DQEBAQUABIGAbKV17HvGYRtRRBNz1QLpW763
|
|
UedhVj5KXi70o4BJGM04lItAgt6aFC9SruZjpWr1gCYKCaRSAg273DeGTQwsDoZ8
|
|
6CPXzBpptYLz0MteQXYYWUaPZT+xmvx4NgDyk9P9MoT7JifsPrtXuzqCRFXhGdu8
|
|
d/ru+OWxhHLvKH+bYekwggI9BgkqhkiG9w0BBwEwFAYIKoZIhvcNAwcECBNs2U5m
|
|
Msd/gIICGFOnLq/EAc9Nv+HjKR3ZVPSJMq0TImjGf5Mvc3nDgI572Hdo2aku0YXM
|
|
6WjSWkpYtxpg7Cqxfl6hPSefLPUnBqlIoM2qbrE7MSKEVD6+2bW9GqYPFVg4qQLL
|
|
sOxnxJIMfOvLFfd7guL+iLH424XfiUUxaf8EdZE4u2IEl4REvkS1FoEGwyA4BEGM
|
|
SeVPedQCbZ0qY7Pc2tmZE3XfEUhIsyStG0Nb6i6AKcAFYGapbgE6kAB0gwsYcHlW
|
|
MOvsvdAfcTq6jwtHlO1s68qtvkWquTQ9lpX+fzddUUNxEHSqv5eU3oo6fT3Vj5ZF
|
|
IVlaA5ThZMrI5PgRPuwJM4GL8/VLwY5mbDLFqn/irGeEvP99J3S87ornLLunjpxS
|
|
y1/AymcVep2H32Tj82WS/IRQXBOzz4EnQRJGszKxAV6tY+Zje3sWyTTgObhlsiTQ
|
|
TDgnvtSW8RvVHqKrwgkxxEsRHg7u8UdzZ0jg+O5+3F8B6/NWMyts0OaFqT9wvI8y
|
|
O7VIy3dUtGdz7Hde6Ggp/iTn1LbgdJ3N8Hzxf1j6NMWUKHVsadvwpRJbUeqq9c3+
|
|
QuxsJi8wWemxxQCE+tPyc1dP+ej5/M7bERbSOHMGgX03758IvP7A/fy2DjGPv2+l
|
|
AwlEke0Uze1367QKgxM0nc3SZDlptY7zPIJC5saWXb8Rt2bw2JxEBOTavrp+ZwJ8
|
|
tcH961onq8Tme2ICaCzk
|
|
-----END PKCS7-----
|
|
)";
|
|
|
|
const bssl::UniquePtr<BIO> bio(
|
|
BIO_new_mem_buf(kPKCS7Ruby, strlen(kPKCS7Ruby)));
|
|
ASSERT_TRUE(bio);
|
|
bssl::UniquePtr<PKCS7> pkcs7(
|
|
PEM_read_bio_PKCS7(bio.get(), nullptr, nullptr, nullptr));
|
|
ASSERT_TRUE(pkcs7);
|
|
ASSERT_TRUE(PKCS7_type_is_signed(pkcs7.get()));
|
|
|
|
// Verify the file how Ruby's tests do it.
|
|
bssl::UniquePtr<X509_STORE> store(X509_STORE_new());
|
|
bssl::UniquePtr<BIO> out(BIO_new(BIO_s_mem()));
|
|
EXPECT_TRUE(PKCS7_verify(pkcs7.get(), nullptr, store.get(), nullptr,
|
|
out.get(), /*flags*/ PKCS7_NOVERIFY));
|
|
|
|
// The following is bit wonky with the pkcs7 bytes being read and rewritten,
|
|
// but that's how Ruby's underlying PKCS7 test gets the PEM output.
|
|
BUF_MEM *buf;
|
|
BIO_get_mem_ptr(out.get(), &buf);
|
|
bssl::UniquePtr<BIO> out2(BIO_new_mem_buf(buf->data, buf->length));
|
|
bssl::UniquePtr<PKCS7> new_pk7(d2i_PKCS7_bio(out2.get(), nullptr));
|
|
ASSERT_TRUE(new_pk7);
|
|
|
|
bssl::UniquePtr<BIO> out3(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(PEM_write_bio_PKCS7(out3.get(), new_pk7.get()));
|
|
BIO_get_mem_ptr(out3.get(), &buf);
|
|
EXPECT_EQ(Bytes(buf->data, buf->length), Bytes(kPKCS7RubyOpenSSLOutput));
|
|
}
|
|
|
|
|
|
static const unsigned char test_data[] = {0x30, 0x02, 0x01, 0x02};
|
|
|
|
static bssl::UniquePtr<PKCS7> pkcs7_with_other(const unsigned char *data,
|
|
int data_len) {
|
|
bssl::UniquePtr<PKCS7> p7(PKCS7_new());
|
|
if (!p7) {
|
|
return nullptr;
|
|
}
|
|
|
|
bssl::UniquePtr<ASN1_STRING> seq(ASN1_STRING_new());
|
|
if (!seq || !ASN1_STRING_set(seq.get(), data, data_len)) {
|
|
return nullptr;
|
|
}
|
|
|
|
// Set up the ASN.1 structure
|
|
p7->d.other = ASN1_TYPE_new();
|
|
if (!p7->d.other) {
|
|
return nullptr;
|
|
}
|
|
|
|
ASN1_TYPE_set(p7->d.other, V_ASN1_OCTET_STRING, seq.release());
|
|
|
|
return p7;
|
|
}
|
|
|
|
TEST(PKCS7Test, OtherFieldMemoryLeak) {
|
|
// Set up the ASN.1 structure
|
|
// |p7->type| is intentionally undefined. OpenSSL frees all contents whether
|
|
// it's defined or not.
|
|
bssl::UniquePtr<PKCS7> p7(pkcs7_with_other(test_data, sizeof(test_data)));
|
|
|
|
ASSERT_EQ(p7->d.other->type, V_ASN1_OCTET_STRING);
|
|
EXPECT_EQ(p7->d.other->value.sequence->length,
|
|
static_cast<int>(sizeof(test_data)));
|
|
EXPECT_EQ(OPENSSL_memcmp(p7->d.other->value.sequence->data, test_data,
|
|
sizeof(test_data)),
|
|
0);
|
|
}
|
|
|
|
TEST(PKCS7Test, SerdeOtherField) {
|
|
// Create PKCS7 and required ASN.1 structures. |p7->type | needs to be defined
|
|
// to be properly serialized.
|
|
bssl::UniquePtr<PKCS7> p7(pkcs7_with_other(test_data, sizeof(test_data)));
|
|
p7->type = OBJ_nid2obj(NID_pkcs7);
|
|
|
|
// Serialize the original object. This should echo back the original saved
|
|
// bytes.
|
|
uint8_t *bytes = nullptr;
|
|
int bytes_len = i2d_PKCS7(p7.get(), &bytes);
|
|
ASSERT_GT(bytes_len, 0);
|
|
bssl::UniquePtr<uint8_t> free_bytes(bytes);
|
|
|
|
const uint8_t *ptr = bytes;
|
|
bssl::UniquePtr<PKCS7> pkcs7_obj(d2i_PKCS7(nullptr, &ptr, bytes_len));
|
|
ASSERT_TRUE(pkcs7_obj);
|
|
ASSERT_EQ(p7->d.other->type, V_ASN1_OCTET_STRING);
|
|
EXPECT_EQ(p7->d.other->value.sequence->length,
|
|
static_cast<int>(sizeof(test_data)));
|
|
EXPECT_EQ(OPENSSL_memcmp(p7->d.other->value.sequence->data, test_data,
|
|
sizeof(test_data)),
|
|
0);
|
|
}
|
|
|
|
// Test for signature bypass when authenticated attributes contain a
|
|
// malformed attribute that causes ASN.1 re-encoding to fail.
|
|
TEST(PKCS7Test, SignatureBypassWithMalformedAuthAttr) {
|
|
const unsigned char original_data[] = "Original legitimate content";
|
|
const size_t original_len = sizeof(original_data) - 1;
|
|
const unsigned char malicious_data[] = "MALICIOUS MODIFIED CONTENT!";
|
|
const size_t malicious_len = sizeof(malicious_data) - 1;
|
|
|
|
// Generate RSA key pair
|
|
bssl::UniquePtr<EVP_PKEY> pkey(EVP_PKEY_new());
|
|
ASSERT_TRUE(pkey);
|
|
bssl::UniquePtr<EVP_PKEY_CTX> pkey_ctx(
|
|
EVP_PKEY_CTX_new_id(EVP_PKEY_RSA, nullptr));
|
|
ASSERT_TRUE(pkey_ctx);
|
|
ASSERT_TRUE(EVP_PKEY_keygen_init(pkey_ctx.get()));
|
|
ASSERT_TRUE(EVP_PKEY_CTX_set_rsa_keygen_bits(pkey_ctx.get(), 2048));
|
|
EVP_PKEY *pkey_raw = nullptr;
|
|
ASSERT_TRUE(EVP_PKEY_keygen(pkey_ctx.get(), &pkey_raw));
|
|
pkey.reset(pkey_raw);
|
|
|
|
// Create self-signed certificate
|
|
bssl::UniquePtr<X509> cert(X509_new());
|
|
ASSERT_TRUE(cert);
|
|
ASSERT_TRUE(X509_set_version(cert.get(), 2));
|
|
ASSERT_TRUE(ASN1_INTEGER_set(X509_get_serialNumber(cert.get()), 1));
|
|
X509_gmtime_adj(X509_get_notBefore(cert.get()), 0);
|
|
X509_gmtime_adj(X509_get_notAfter(cert.get()), 31536000L);
|
|
ASSERT_TRUE(X509_set_pubkey(cert.get(), pkey.get()));
|
|
X509_NAME *name = X509_get_subject_name(cert.get());
|
|
ASSERT_TRUE(X509_NAME_add_entry_by_txt(name, "CN", MBSTRING_ASC,
|
|
(const unsigned char *)"Test",
|
|
-1, -1, 0));
|
|
ASSERT_TRUE(X509_set_issuer_name(cert.get(), name));
|
|
ASSERT_TRUE(X509_sign(cert.get(), pkey.get(), EVP_sha256()));
|
|
|
|
// Set up trust store
|
|
bssl::UniquePtr<X509_STORE> store(X509_STORE_new());
|
|
ASSERT_TRUE(store);
|
|
ASSERT_TRUE(X509_STORE_add_cert(store.get(), cert.get()));
|
|
|
|
// Compute SHA-256 digest of original data
|
|
unsigned char md[SHA256_DIGEST_LENGTH];
|
|
SHA256(original_data, original_len, md);
|
|
|
|
// Create the PKCS7 SignedData structure
|
|
bssl::UniquePtr<PKCS7> p7(PKCS7_new());
|
|
ASSERT_TRUE(p7);
|
|
ASSERT_TRUE(PKCS7_set_type(p7.get(), NID_pkcs7_signed));
|
|
ASSERT_TRUE(PKCS7_content_new(p7.get(), NID_pkcs7_data));
|
|
|
|
// Set the content payload
|
|
ASSERT_TRUE(ASN1_OCTET_STRING_set(p7->d.sign->contents->d.data,
|
|
original_data, (int)original_len));
|
|
|
|
// Add SHA-256 to the digest algorithms set
|
|
X509_ALGOR *alg = X509_ALGOR_new();
|
|
ASSERT_TRUE(alg);
|
|
ASSERT_TRUE(
|
|
X509_ALGOR_set0(alg, OBJ_nid2obj(NID_sha256), V_ASN1_NULL, nullptr));
|
|
ASSERT_TRUE(sk_X509_ALGOR_push(p7->d.sign->md_algs, alg));
|
|
|
|
// Create and configure SIGNER_INFO
|
|
PKCS7_SIGNER_INFO *sinfo = PKCS7_SIGNER_INFO_new();
|
|
ASSERT_TRUE(sinfo);
|
|
ASSERT_TRUE(
|
|
PKCS7_SIGNER_INFO_set(sinfo, cert.get(), pkey.get(), EVP_sha256()));
|
|
|
|
// Build authenticated attributes: contentType + messageDigest
|
|
sinfo->auth_attr = sk_X509_ATTRIBUTE_new_null();
|
|
ASSERT_TRUE(sinfo->auth_attr);
|
|
|
|
// Add contentType attribute (pkcs7-data)
|
|
ASN1_OBJECT *content_type_obj = OBJ_dup(OBJ_nid2obj(NID_pkcs7_data));
|
|
ASSERT_TRUE(content_type_obj);
|
|
X509_ATTRIBUTE *ct_attr = X509_ATTRIBUTE_create(
|
|
NID_pkcs9_contentType, V_ASN1_OBJECT, content_type_obj);
|
|
ASSERT_TRUE(ct_attr);
|
|
ASSERT_TRUE(sk_X509_ATTRIBUTE_push(sinfo->auth_attr, ct_attr));
|
|
|
|
// Add messageDigest attribute
|
|
ASN1_OCTET_STRING *digest_os = ASN1_OCTET_STRING_new();
|
|
ASSERT_TRUE(digest_os);
|
|
ASSERT_TRUE(ASN1_OCTET_STRING_set(digest_os, md, SHA256_DIGEST_LENGTH));
|
|
X509_ATTRIBUTE *md_attr = X509_ATTRIBUTE_create(
|
|
NID_pkcs9_messageDigest, V_ASN1_OCTET_STRING, digest_os);
|
|
ASSERT_TRUE(md_attr);
|
|
ASSERT_TRUE(sk_X509_ATTRIBUTE_push(sinfo->auth_attr, md_attr));
|
|
|
|
// DER-encode the authenticated attributes for signing
|
|
unsigned char *attr_der = nullptr;
|
|
int attr_der_len = ASN1_item_i2d((ASN1_VALUE *)sinfo->auth_attr, &attr_der,
|
|
ASN1_ITEM_rptr(PKCS7_ATTR_VERIFY));
|
|
ASSERT_GT(attr_der_len, 0);
|
|
ASSERT_TRUE(attr_der);
|
|
|
|
// Sign the DER-encoded authenticated attributes
|
|
bssl::UniquePtr<EVP_MD_CTX> md_ctx(EVP_MD_CTX_new());
|
|
ASSERT_TRUE(md_ctx);
|
|
ASSERT_TRUE(EVP_DigestSignInit(md_ctx.get(), nullptr, EVP_sha256(), nullptr,
|
|
pkey.get()));
|
|
ASSERT_TRUE(EVP_DigestSignUpdate(md_ctx.get(), attr_der, attr_der_len));
|
|
|
|
size_t sig_len = 0;
|
|
ASSERT_TRUE(EVP_DigestSignFinal(md_ctx.get(), nullptr, &sig_len));
|
|
unsigned char *sig =
|
|
(unsigned char *)OPENSSL_malloc(sig_len);
|
|
ASSERT_TRUE(sig);
|
|
ASSERT_TRUE(EVP_DigestSignFinal(md_ctx.get(), sig, &sig_len));
|
|
|
|
// Set the signature on the signer info
|
|
ASSERT_TRUE(
|
|
ASN1_OCTET_STRING_set(sinfo->enc_digest, sig, (int)sig_len));
|
|
OPENSSL_free(sig);
|
|
OPENSSL_free(attr_der);
|
|
|
|
// Attach signer info and certificate to the PKCS7
|
|
ASSERT_TRUE(sk_PKCS7_SIGNER_INFO_push(p7->d.sign->signer_info, sinfo));
|
|
ASSERT_TRUE(PKCS7_add_certificate(p7.get(), cert.get()));
|
|
|
|
// Verify the original (unmodified) message succeeds
|
|
bssl::UniquePtr<BIO> out_bio(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(out_bio);
|
|
EXPECT_TRUE(PKCS7_verify(p7.get(), nullptr, store.get(), nullptr,
|
|
out_bio.get(), /*flags*/ 0));
|
|
|
|
// Now tamper with the message to attempt bypass
|
|
|
|
// Get the signer info back for modification
|
|
STACK_OF(PKCS7_SIGNER_INFO) *sinfos = PKCS7_get_signer_info(p7.get());
|
|
ASSERT_TRUE(sinfos);
|
|
ASSERT_GT(sk_PKCS7_SIGNER_INFO_num(sinfos), (size_t)0);
|
|
PKCS7_SIGNER_INFO *sinfo_ptr = sk_PKCS7_SIGNER_INFO_value(sinfos, 0);
|
|
ASSERT_TRUE(sinfo_ptr);
|
|
|
|
// Modify the content to malicious data
|
|
ASSERT_TRUE(PKCS7_type_is_signed(p7.get()));
|
|
ASSERT_TRUE(p7->d.sign && p7->d.sign->contents);
|
|
ASSERT_EQ(OBJ_obj2nid(p7->d.sign->contents->type), NID_pkcs7_data);
|
|
ASSERT_TRUE(ASN1_OCTET_STRING_set(p7->d.sign->contents->d.data,
|
|
malicious_data, (int)malicious_len));
|
|
|
|
// Update the messageDigest attribute to match the malicious content
|
|
unsigned char new_md[SHA256_DIGEST_LENGTH];
|
|
SHA256(malicious_data, malicious_len, new_md);
|
|
ASN1_TYPE *md_type =
|
|
PKCS7_get_signed_attribute(sinfo_ptr, NID_pkcs9_messageDigest);
|
|
ASSERT_TRUE(md_type);
|
|
ASSERT_EQ(md_type->type, V_ASN1_OCTET_STRING);
|
|
ASSERT_TRUE(ASN1_OCTET_STRING_set(md_type->value.octet_string, new_md,
|
|
SHA256_DIGEST_LENGTH));
|
|
|
|
// Add a malformed attribute whose ASN1_OBJECT has zero length.
|
|
// This causes ASN1_item_i2d() to fail with ASN1_R_ILLEGAL_OBJECT when
|
|
// pkcs7_signature_verify() tries to re-encode auth_attr for signature
|
|
// verification.
|
|
ASN1_OCTET_STRING *bad_os = ASN1_OCTET_STRING_new();
|
|
ASSERT_TRUE(bad_os);
|
|
ASSERT_TRUE(
|
|
ASN1_OCTET_STRING_set(bad_os, (const unsigned char *)"test", 4));
|
|
X509_ATTRIBUTE *bad_attr = X509_ATTRIBUTE_create(
|
|
NID_id_smime_aa_signingCertificate, V_ASN1_OCTET_STRING, bad_os);
|
|
ASSERT_TRUE(bad_attr);
|
|
|
|
// Create an ASN1_OBJECT with zero-length OID data. When ASN1_item_i2d
|
|
// tries to encode this, i2d_ASN1_OBJECT returns -1 because length <= 0,
|
|
// which makes the overall encoding fail safely.
|
|
bssl::UniquePtr<ASN1_OBJECT> empty_obj(
|
|
ASN1_OBJECT_create(NID_undef, nullptr, 0, nullptr, nullptr));
|
|
ASSERT_TRUE(empty_obj);
|
|
ASSERT_TRUE(X509_ATTRIBUTE_set1_object(bad_attr, empty_obj.get()));
|
|
|
|
ASSERT_TRUE(sk_X509_ATTRIBUTE_push(sinfo_ptr->auth_attr, bad_attr));
|
|
|
|
// Verify that the tampered message is correctly rejected
|
|
out_bio.reset(BIO_new(BIO_s_mem()));
|
|
ASSERT_TRUE(out_bio);
|
|
EXPECT_FALSE(PKCS7_verify(p7.get(), nullptr, store.get(), nullptr,
|
|
out_bio.get(), /*flags*/ 0));
|
|
}
|