@@ -165,73 +165,76 @@ int data_write_pkcs7(FILE_FORMAT_CTX *ctx, BIO *outdata, PKCS7 *p7)
165165PKCS7 * pkcs7_create (FILE_FORMAT_CTX * ctx )
166166{
167167 int i , signer = -1 ;
168- PKCS7 * p7 ;
169168 PKCS7_SIGNER_INFO * si = NULL ;
170169 STACK_OF (X509 ) * chain = NULL ;
170+ PKCS7 * p7 = PKCS7_new ();
171+
172+ if (!p7 )
173+ return NULL ;
171174
172- p7 = PKCS7_new ();
173175 PKCS7_set_type (p7 , NID_pkcs7_signed );
174176 PKCS7_content_new (p7 , NID_pkcs7_data );
175- if (ctx -> options -> cert != NULL ) {
176- /*
177- * the private key and corresponding certificate are parsed from the PKCS12
178- * structure or loaded from the security token, so we may omit to check
179- * the consistency of a private key with the public key in an X509 certificate
180- */
181- si = PKCS7_add_signature (p7 , ctx -> options -> cert , ctx -> options -> pkey ,
182- ctx -> options -> md );
183- if (si == NULL )
184- return NULL ; /* FAILED */
185- } else {
186- /* find the signer's certificate located somewhere in the whole certificate chain */
187- for (i = 0 ; i < sk_X509_num (ctx -> options -> certs ); i ++ ) {
188- X509 * signcert = sk_X509_value (ctx -> options -> certs , i );
189- if (X509_check_private_key (signcert , ctx -> options -> pkey )) {
190- si = PKCS7_add_signature (p7 , signcert , ctx -> options -> pkey , ctx -> options -> md );
191- signer = i ;
192- break ;
193- }
194- }
195- if (si == NULL ) {
196- fprintf (stderr , "Failed to checking the consistency of a private key: %s\n" ,
197- ctx -> options -> keyfile );
198- fprintf (stderr , " with a public key in any X509 certificate: %s\n\n" ,
199- ctx -> options -> certfile );
200- return NULL ; /* FAILED */
177+
178+ /* find the signer's certificate located somewhere in the whole certificate chain */
179+ for (i = 0 ; i < sk_X509_num (ctx -> options -> certs ); i ++ ) {
180+ X509 * signcert = sk_X509_value (ctx -> options -> certs , i );
181+
182+ if (X509_check_private_key (signcert , ctx -> options -> pkey )) {
183+ si = PKCS7_add_signature (p7 , signcert , ctx -> options -> pkey , ctx -> options -> md );
184+ signer = i ;
185+ if (signer > 0 )
186+ printf ("Warning: For optimal performance, consider placing the signer certificate at the beginning of the certificate chain.\n" );
187+ break ;
201188 }
202189 }
190+ if (!si ) {
191+ fprintf (stderr , "Failed to checking the consistency of a private key: %s\n" ,
192+ ctx -> options -> keyfile );
193+ fprintf (stderr , " with a public key in any X509 certificate: %s\n\n" ,
194+ #if !defined (OPENSSL_NO_ENGINE ) || OPENSSL_VERSION_NUMBER >=0x30000000L
195+ ctx -> options -> certfile ? ctx -> options -> certfile : ctx -> options -> p11cert );
196+ #else
197+ ctx -> options -> certfile );
198+ #endif /* !defined(OPENSSL_NO_ENGINE) || OPENSSL_VERSION_NUMBER>=0x30000000L */
199+ goto err ;
200+ }
201+
203202 if (!pkcs7_signer_info_add_signing_time (si , ctx )) {
204- return NULL ; /* FAILED */
203+ goto err ;
205204 }
206205 if (!pkcs7_signer_info_add_purpose (si , ctx )) {
207- return NULL ; /* FAILED */
206+ goto err ;
208207 }
209208 if ((ctx -> options -> desc || ctx -> options -> url ) &&
210209 !pkcs7_signer_info_add_spc_sp_opus_info (si , ctx )) {
211210 fprintf (stderr , "Couldn't allocate memory for opus info\n" );
212- return NULL ; /* FAILED */
211+ goto err ;
213212 }
214213 if ((ctx -> options -> nested_number >= 0 ) &&
215214 !pkcs7_signer_info_add_sequence_number (si , ctx )) {
216- return NULL ; /* FAILED */
215+ goto err ;
217216 }
218217 /* create X509 chain sorted in ascending order by their DER encoding */
219218 chain = X509_chain_get_sorted (ctx , signer );
220- if (chain == NULL ) {
219+ if (! chain ) {
221220 fprintf (stderr , "Failed to create a sorted certificate chain\n" );
222- return NULL ; /* FAILED */
221+ goto err ;
223222 }
224223 /* add sorted certificate chain */
225224 for (i = 0 ; i < sk_X509_num (chain ); i ++ ) {
226- PKCS7_add_certificate (p7 , sk_X509_value (chain , i ));
225+ ( void ) PKCS7_add_certificate (p7 , sk_X509_value (chain , i ));
227226 }
228227 /* add crls */
229228 if (ctx -> options -> crls ) {
230229 for (i = 0 ; i < sk_X509_CRL_num (ctx -> options -> crls ); i ++ )
231- PKCS7_add_crl (p7 , sk_X509_CRL_value (ctx -> options -> crls , i ));
230+ ( void ) PKCS7_add_crl (p7 , sk_X509_CRL_value (ctx -> options -> crls , i ));
232231 }
233232 sk_X509_free (chain );
234233 return p7 ; /* OK */
234+
235+ err :
236+ PKCS7_free (p7 );
237+ return NULL ; /* FAILED */
235238}
236239
237240/*
@@ -732,11 +735,6 @@ static STACK_OF(X509) *X509_chain_get_sorted(FILE_FORMAT_CTX *ctx, int signer)
732735 int i ;
733736 STACK_OF (X509 ) * chain = sk_X509_new (X509_compare );
734737
735- /* add the signer's certificate */
736- if (ctx -> options -> cert != NULL && !sk_X509_push (chain , ctx -> options -> cert )) {
737- sk_X509_free (chain );
738- return NULL ;
739- }
740738 if (signer != -1 && !sk_X509_push (chain , sk_X509_value (ctx -> options -> certs , signer ))) {
741739 sk_X509_free (chain );
742740 return NULL ;
0 commit comments