Skip to content

Commit 93f4e79

Browse files
authored
Merge pull request #422 from JacobBarthelmeh/pkcs7-examples
add example of no certs bundle and stream mode
2 parents eafcbee + e2809a9 commit 93f4e79

File tree

4 files changed

+243
-14
lines changed

4 files changed

+243
-14
lines changed

pkcs7/envelopedData-ktri.c

+18-5
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,8 @@ static int write_file_buffer(const char* fileName, byte* in, word32 inSz)
7979
}
8080

8181
static int envelopedData_encrypt(byte* cert, word32 certSz, byte* key,
82-
word32 keySz, byte* out, word32 outSz)
82+
word32 keySz, byte* out, word32 outSz,
83+
byte useStreamMode)
8384
{
8485
int ret;
8586
PKCS7* pkcs7;
@@ -93,6 +94,10 @@ static int envelopedData_encrypt(byte* cert, word32 certSz, byte* key,
9394
pkcs7->contentOID = DATA;
9495
pkcs7->encryptOID = AES256CBCb;
9596

97+
if (useStreamMode) {
98+
wc_PKCS7_SetStreamMode(pkcs7, 1);
99+
}
100+
96101
/* add recipient using RSA certificate (KTRI type) */
97102
ret = wc_PKCS7_AddRecipient_KTRI(pkcs7, cert, certSz, 0);
98103
if (ret < 0) {
@@ -109,8 +114,8 @@ static int envelopedData_encrypt(byte* cert, word32 certSz, byte* key,
109114
return -1;
110115

111116
} else {
112-
printf("Successfully encoded EnvelopedData bundle (%s)\n",
113-
encodedFileKTRI);
117+
printf("Successfully encoded EnvelopedData bundle (%s), stream mode"
118+
" %d\n", encodedFileKTRI, useStreamMode);
114119

115120
if (write_file_buffer(encodedFileKTRI, out, ret) != 0) {
116121
printf("ERROR: error writing encoded to output file\n");
@@ -177,7 +182,7 @@ int main(int argc, char** argv)
177182
byte key[2048];
178183
byte encrypted[1024];
179184
byte decrypted[1024];
180-
185+
181186
#ifdef DEBUG_WOLFSSL
182187
wolfSSL_Debugging_ON();
183188
#endif
@@ -189,10 +194,18 @@ int main(int argc, char** argv)
189194
return -1;
190195

191196
encryptedSz = envelopedData_encrypt(cert, certSz, key, keySz,
192-
encrypted, sizeof(encrypted));
197+
encrypted, sizeof(encrypted), 0);
193198
if (encryptedSz < 0)
194199
return -1;
195200

201+
#ifdef ASN_BER_TO_DER
202+
/* recreate the bundle with BER encoding */
203+
encryptedSz = envelopedData_encrypt(cert, certSz, key, keySz,
204+
encrypted, sizeof(encrypted), 1);
205+
if (encryptedSz < 0)
206+
return -1;
207+
#endif
208+
196209
#ifdef DEBUG_WOLFSSL
197210
printf("EnvelopedData DER (%d byte):\n", encryptedSz);
198211
WOLFSSL_BUFFER(encrypted, encryptedSz);

pkcs7/envelopedDataDecode.c

+184
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,184 @@
1+
/* envelopedDataDecode.c
2+
*
3+
* Copyright (C) 2006-2020 wolfSSL Inc.
4+
*
5+
* This file is part of wolfSSL. (formerly known as CyaSSL)
6+
*
7+
* wolfSSL is free software; you can redistribute it and/or modify
8+
* it under the terms of the GNU General Public License as published by
9+
* the Free Software Foundation; either version 2 of the License, or
10+
* (at your option) any later version.
11+
*
12+
* wolfSSL is distributed in the hope that it will be useful,
13+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15+
* GNU General Public License for more details.
16+
*
17+
* You should have received a copy of the GNU General Public License
18+
* along with this program; if not, write to the Free Software
19+
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
20+
*/
21+
22+
23+
#include <wolfssl/options.h>
24+
#include <wolfssl/wolfcrypt/settings.h>
25+
#include <wolfssl/wolfcrypt/pkcs7.h>
26+
#include <wolfssl/wolfcrypt/error-crypt.h>
27+
#include <wolfssl/wolfcrypt/logging.h>
28+
29+
static int load_certs(const char* certFile, byte* cert, word32* certSz,
30+
const char* keyFile, byte* key, word32* keySz)
31+
{
32+
FILE* file;
33+
34+
/* certificate file */
35+
file = fopen(certFile, "rb");
36+
if (!file)
37+
return -1;
38+
39+
*certSz = (word32)fread(cert, 1, *certSz, file);
40+
fclose(file);
41+
42+
/* key file */
43+
file = fopen(keyFile, "rb");
44+
if (!file)
45+
return -1;
46+
47+
*keySz = (word32)fread(key, 1, *keySz, file);
48+
fclose(file);
49+
50+
return 0;
51+
}
52+
53+
54+
static int envelopedData_decrypt(byte* in, word32 inSz, byte* cert,
55+
word32 certSz, byte* key, word32 keySz,
56+
byte* out, word32 outSz)
57+
{
58+
int ret;
59+
PKCS7* pkcs7;
60+
61+
pkcs7 = wc_PKCS7_New(NULL, INVALID_DEVID);
62+
if (pkcs7 == NULL)
63+
return -1;
64+
65+
/* init with recipient cert */
66+
ret = wc_PKCS7_InitWithCert(pkcs7, cert, certSz);
67+
if (ret != 0) {
68+
wc_PKCS7_Free(pkcs7);
69+
return -1;
70+
}
71+
72+
/* set recipient private key */
73+
ret = wc_PKCS7_SetKey(pkcs7, key, keySz);
74+
if (ret != 0) {
75+
wc_PKCS7_Free(pkcs7);
76+
return -1;
77+
}
78+
79+
/* decode envelopedData, returns size */
80+
ret = wc_PKCS7_DecodeEnvelopedData(pkcs7, in, inSz, out, outSz);
81+
wc_PKCS7_Free(pkcs7);
82+
83+
if (ret <= 0) {
84+
printf("Failed to decode EnvelopedData bundle error of %d\n", ret);
85+
}
86+
else {
87+
printf("Successfully decoded EnvelopedData bundle\n");
88+
}
89+
90+
91+
return ret;
92+
}
93+
94+
#ifdef HAVE_PKCS7
95+
96+
int main(int argc, char** argv)
97+
{
98+
int ret;
99+
int encryptedSz, decryptedSz;
100+
word32 certSz, keySz;
101+
102+
byte cert[2048];
103+
byte key[2048];
104+
byte* encrypted;
105+
byte* decrypted;
106+
107+
#ifdef DEBUG_WOLFSSL
108+
wolfSSL_Debugging_ON();
109+
#endif
110+
111+
if (argc != 4) {
112+
printf("expecting DER cert, key, and encrypted bundle as args\n");
113+
printf("%s <DER cert> <DER key> <Encrypted bundle>\n", argv[0]);
114+
return -1;
115+
}
116+
117+
certSz = sizeof(cert);
118+
keySz = sizeof(key);
119+
ret = load_certs(argv[1], cert, &certSz, argv[2], key, &keySz);
120+
if (ret != 0) {
121+
printf("Error loading cert and key\n");
122+
return -1;
123+
}
124+
125+
/* read encrypted bundle */
126+
{
127+
FILE* file;
128+
129+
file = fopen(argv[3], "rb");
130+
if (!file) {
131+
printf("unable to open file %s\n", argv[3]);
132+
return -1;
133+
}
134+
fseek(file, 0, SEEK_END);
135+
encryptedSz = (int)ftell(file);
136+
rewind(file);
137+
138+
encrypted = (byte*)malloc(encryptedSz);
139+
if (encrypted == NULL) {
140+
printf("malloc failed\n");
141+
return -1;
142+
}
143+
144+
decryptedSz = encryptedSz;
145+
decrypted = (byte*)malloc(decryptedSz);
146+
if (decrypted == NULL) {
147+
printf("malloc failed\n");
148+
free(encrypted);
149+
return -1;
150+
}
151+
152+
encryptedSz = (word32)fread(encrypted, 1, encryptedSz, file);
153+
printf("encrypted bundle size read = %d\n", encryptedSz);
154+
fclose(file);
155+
}
156+
157+
decryptedSz = envelopedData_decrypt(encrypted, encryptedSz,
158+
cert, certSz, key, keySz,
159+
decrypted, decryptedSz);
160+
free(encrypted);
161+
if (decryptedSz < 0) {
162+
free(decrypted);
163+
return -1;
164+
}
165+
166+
#ifdef DEBUG_WOLFSSL
167+
printf("Decrypted content (%d byte):\n", decryptedSz);
168+
WOLFSSL_BUFFER(decrypted, decryptedSz);
169+
#endif
170+
free(decrypted);
171+
172+
return 0;
173+
}
174+
175+
#else
176+
177+
int main(int argc, char** argv)
178+
{
179+
printf("Must build wolfSSL using ./configure --enable-pkcs7\n");
180+
return 0;
181+
}
182+
183+
#endif
184+

pkcs7/scripts/runall.sh

+6-1
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ fileArray=(
3232

3333
# CMS EnvelopedData example apps
3434
"envelopedData-kari"
35+
"envelopedDataDecode"
3536
"envelopedData-kekri"
3637
"envelopedData-ktri"
3738
"envelopedData-ori"
@@ -53,7 +54,11 @@ echo ""
5354
for i in "${fileArray[@]}"
5455
do
5556
if [ -f $i ]; then
56-
eval "./$i"
57+
if [ "$i" == "envelopedDataDecode" ]; then
58+
eval "./$i ../certs/client-cert.der ../certs/client-key.der envelopedDataKTRI.der"
59+
else
60+
eval "./$i"
61+
fi
5762
if [ $? -ne 0 ]
5863
then
5964
echo "Test FAILED"

pkcs7/signedData.c

+35-8
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,8 @@ static int write_file_buffer(const char* fileName, byte* in, word32 inSz)
7979
}
8080

8181
static int signedData_sign_noattrs(byte* cert, word32 certSz, byte* key,
82-
word32 keySz, byte* out, word32 outSz)
82+
word32 keySz, byte* out, word32 outSz,
83+
byte streamMode, byte noCerts)
8384
{
8485
int ret;
8586
PKCS7* pkcs7;
@@ -118,6 +119,14 @@ static int signedData_sign_noattrs(byte* cert, word32 certSz, byte* key,
118119
pkcs7->signedAttribs = NULL;
119120
pkcs7->signedAttribsSz = 0;
120121

122+
if (streamMode) {
123+
wc_PKCS7_SetStreamMode(pkcs7, 1);
124+
}
125+
126+
if (noCerts) {
127+
wc_PKCS7_SetNoCerts(pkcs7, 1);
128+
}
129+
121130
/* encode signedData, returns size */
122131
ret = wc_PKCS7_EncodeSignedData(pkcs7, out, outSz);
123132
if (ret <= 0) {
@@ -127,8 +136,9 @@ static int signedData_sign_noattrs(byte* cert, word32 certSz, byte* key,
127136
return -1;
128137

129138
} else {
130-
printf("Successfully encoded SignedData bundle (%s)\n",
131-
encodedFileNoAttrs);
139+
printf("Successfully encoded SignedData bundle (%s) %s %s\n",
140+
encodedFileNoAttrs, (noCerts)? ", No Certs Added":"",
141+
(streamMode)? ", Using Stream Mode": "");
132142

133143
#ifdef DEBUG_WOLFSSL
134144
printf("Encoded DER (%d bytes):\n", ret);
@@ -244,10 +254,14 @@ static int signedData_verify(byte* in, word32 inSz, byte* cert,
244254

245255
if (ret < 0 || (pkcs7->contentSz != sizeof(data)) ||
246256
(XMEMCMP(pkcs7->content, data, pkcs7->contentSz) != 0)) {
247-
printf("ERROR: Failed to verify SignedData bundle, ret = %d\n", ret);
248-
wc_PKCS7_Free(pkcs7);
249-
return -1;
250-
257+
if (ret == PKCS7_SIGNEEDS_CHECK) {
258+
printf("WARNING: Parsed through bundle but no certificates found to"
259+
" verify signature with\n");
260+
}
261+
else {
262+
printf("ERROR: Failed to verify SignedData bundle, ret = %d\n",
263+
ret);
264+
}
251265
} else {
252266
printf("Successfully verified SignedData bundle.\n");
253267

@@ -287,7 +301,7 @@ int main(int argc, char** argv)
287301

288302
/* no attributes */
289303
encryptedSz = signedData_sign_noattrs(cert, certSz, key, keySz,
290-
encrypted, sizeof(encrypted));
304+
encrypted, sizeof(encrypted), 0, 0);
291305
if (encryptedSz < 0)
292306
return -1;
293307

@@ -297,6 +311,19 @@ int main(int argc, char** argv)
297311
if (decryptedSz < 0)
298312
return -1;
299313

314+
/* no attributes, stream mode, and no certs */
315+
encryptedSz = signedData_sign_noattrs(cert, certSz, key, keySz,
316+
encrypted, sizeof(encrypted), 1, 1);
317+
if (encryptedSz < 0)
318+
return -1;
319+
320+
decryptedSz = signedData_verify(encrypted, encryptedSz,
321+
cert, certSz, key, keySz,
322+
decrypted, sizeof(decrypted));
323+
/* should be error to warn that the signature needs checked */
324+
if (decryptedSz != PKCS7_SIGNEEDS_CHECK)
325+
return -1;
326+
300327
/* default attributes + messageType attribute */
301328
encryptedSz = signedData_sign_attrs(cert, certSz, key, keySz,
302329
encrypted, sizeof(encrypted));

0 commit comments

Comments
 (0)