1 /* ***** BEGIN LICENSE BLOCK *****
2 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
4 * The contents of this file are subject to the Mozilla Public License Version
5 * 1.1 (the "License"); you may not use this file except in compliance with
6 * the License. You may obtain a copy of the License at
7 * http://www.mozilla.org/MPL/
9 * Software distributed under the License is distributed on an "AS IS" basis,
10 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
11 * for the specific language governing rights and limitations under the
14 * The Original Code is the Netscape security libraries.
16 * The Initial Developer of the Original Code is
17 * Netscape Communications Corporation.
18 * Portions created by the Initial Developer are Copyright (C) 1994-2000
19 * the Initial Developer. All Rights Reserved.
23 * Alternatively, the contents of this file may be used under the terms of
24 * either the GNU General Public License Version 2 or later (the "GPL"), or
25 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
26 * in which case the provisions of the GPL or the LGPL are applicable instead
27 * of those above. If you wish to allow use of your version of this file only
28 * under the terms of either the GPL or the LGPL, and not to allow others to
29 * use your version of this file under the terms of the MPL, indicate your
30 * decision by deleting the provisions above and replace them with the notice
31 * and other provisions required by the GPL or the LGPL. If you do not delete
32 * the provisions above, a recipient may use your version of this file under
33 * the terms of any one of the MPL, the GPL or the LGPL.
35 * ***** END LICENSE BLOCK ***** */
38 * p7content -- A command to display pkcs7 content.
40 * $Id: p7content.c,v 1.11 2007/01/25 00:52:25 alexei.volkov.bugs%sun.com Exp $
59 #if (defined(XP_WIN) && !defined(WIN32)) || (defined(__sun) && !defined(SVR4))
60 extern int fwrite(char *, size_t, size_t, FILE*);
61 extern int fprintf(FILE *, char *, ...);
70 "Usage: %s [-d dbdir] [-i input] [-o output]\n",
73 "%-20s Key/Cert database directory (default is ~/.netscape)\n",
75 fprintf(stderr
, "%-20s Define an input file to use (default is stdin)\n",
77 fprintf(stderr
, "%-20s Define an output file to use (default is stdout)\n",
82 static PRBool saw_content
;
85 PrintBytes(void *arg
, const char *buf
, unsigned long len
)
90 fwrite (buf
, len
, 1, out
);
92 saw_content
= PR_TRUE
;
96 * XXX Someday we may want to do real policy stuff here. This allows
97 * anything to be decrypted, which is okay for a test program but does
98 * not set an example of how a real client with a real policy would
102 decryption_allowed(SECAlgorithmID
*algid
, PK11SymKey
*key
)
107 char* KeyDbPassword
= 0;
110 char* MyPK11PasswordFunc (PK11SlotInfo
*slot
, PRBool retry
, void* arg
)
114 if (retry
== PR_TRUE
)
116 ret
= PL_strdup (KeyDbPassword
);
121 DecodeAndPrintFile(FILE *out
, PRFileDesc
*in
, char *progName
)
124 SEC_PKCS7ContentInfo
*cinfo
= NULL
;
125 SEC_PKCS7DecoderContext
*dcx
;
127 if (SECU_ReadDERFromFile(&derdata
, in
, PR_FALSE
)) {
128 SECU_PrintError(progName
, "error converting der");
133 "Content printed between bars (newline added before second bar):");
134 fprintf(out
, "\n---------------------------------------------\n");
136 saw_content
= PR_FALSE
;
137 dcx
= SEC_PKCS7DecoderStart(PrintBytes
, out
, NULL
, NULL
,
138 NULL
, NULL
, decryption_allowed
);
140 #if 0 /* Test that decoder works when data is really streaming in. */
143 for (i
= 0; i
< derdata
.len
; i
++)
144 SEC_PKCS7DecoderUpdate(dcx
, derdata
.data
+ i
, 1);
147 SEC_PKCS7DecoderUpdate(dcx
, (char *)derdata
.data
, derdata
.len
);
149 cinfo
= SEC_PKCS7DecoderFinish(dcx
);
152 fprintf(out
, "\n---------------------------------------------\n");
157 fprintf(out
, "Content was%s encrypted.\n",
158 SEC_PKCS7ContentIsEncrypted(cinfo
) ? "" : " not");
160 if (SEC_PKCS7ContentIsSigned(cinfo
)) {
161 char *signer_cname
, *signer_ename
;
162 SECItem
*signing_time
;
165 fprintf(out
, "Signature is ");
167 if (SEC_PKCS7VerifySignature(cinfo
, certUsageEmailSigner
, PR_FALSE
))
168 fprintf(out
, "valid.\n");
170 fprintf(out
, "invalid (Reason: %s).\n",
171 SECU_Strerror(PORT_GetError()));
174 "Content is detached; signature cannot be verified.\n");
177 signer_cname
= SEC_PKCS7GetSignerCommonName(cinfo
);
178 if (signer_cname
!= NULL
) {
179 fprintf(out
, "The signer's common name is %s\n", signer_cname
);
180 PORT_Free(signer_cname
);
182 fprintf(out
, "No signer common name.\n");
185 signer_ename
= SEC_PKCS7GetSignerEmailAddress(cinfo
);
186 if (signer_ename
!= NULL
) {
187 fprintf(out
, "The signer's email address is %s\n", signer_ename
);
188 PORT_Free(signer_ename
);
190 fprintf(out
, "No signer email address.\n");
193 signing_time
= SEC_PKCS7GetSigningTime(cinfo
);
194 if (signing_time
!= NULL
) {
195 SECU_PrintTimeChoice(out
, signing_time
, "Signing time", 0);
197 fprintf(out
, "No signing time included.\n");
200 fprintf(out
, "Content was not signed.\n");
203 fprintf(out
, "There were%s certs or crls included.\n",
204 SEC_PKCS7ContainsCertsOrCrls(cinfo
) ? "" : " no");
206 SEC_PKCS7DestroyContentInfo(cinfo
);
212 * Print the contents of a PKCS7 message, indicating signatures, etc.
216 main(int argc
, char **argv
)
221 PLOptState
*optstate
;
225 progName
= strrchr(argv
[0], '/');
226 progName
= progName
? progName
+1 : argv
[0];
232 * Parse command line arguments
234 optstate
= PL_CreateOptState(argc
, argv
, "d:i:o:p:");
235 while ((status
= PL_GetNextOpt(optstate
)) == PL_OPT_OK
) {
236 switch (optstate
->option
) {
238 SECU_ConfigDirectory(optstate
->value
);
242 inFile
= PR_Open(optstate
->value
, PR_RDONLY
, 0);
244 fprintf(stderr
, "%s: unable to open \"%s\" for reading\n",
245 progName
, optstate
->value
);
251 outFile
= fopen(optstate
->value
, "w");
253 fprintf(stderr
, "%s: unable to open \"%s\" for writing\n",
254 progName
, optstate
->value
);
260 KeyDbPassword
= strdup (optstate
->value
);
268 if (status
== PL_OPT_BAD
)
271 if (!inFile
) inFile
= PR_STDIN
;
272 if (!outFile
) outFile
= stdout
;
274 /* Call the initialization routines */
275 PR_Init(PR_SYSTEM_THREAD
, PR_PRIORITY_NORMAL
, 1);
276 rv
= NSS_Init(SECU_ConfigDirectory(NULL
));
277 if (rv
!= SECSuccess
) {
278 SECU_PrintPRandOSError(progName
);
282 PK11_SetPasswordFunc (MyPK11PasswordFunc
);
284 if (DecodeAndPrintFile(outFile
, inFile
, progName
)) {
285 SECU_PrintError(progName
, "problem decoding data");
289 if (NSS_Shutdown() != SECSuccess
) {