<html><head><meta http-equiv="Content-Type" content="text/html charset=windows-1252"></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space;">OpenSSL 1.0.1k and 1.0.1l. Problem: good certificates fail verification (test certificate and its CA cert that illustrate the problem are attached, as well as the patch/workaround).<div><br></div><div>Here’s how the problem manifests itself:</div><div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">$ openssl version -f</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">compiler: -I. -I.. -I../include  -fPIC -fno-common -DOPENSSL_PIC -DZLIB -DOPENSSL_THREADS -D_REENTRANT -DDSO_DLFCN -DHAVE_DLFCN_H -arch x86_64 -O3 -DL_ENDIAN -Wall -DOPENSSL_IA32_SSE2 -DOPENSSL_BN_ASM_MONT -DOPENSSL_BN_ASM_MONT5 -DOPENSSL_BN_ASM_GF2m -DSHA1_ASM -DSHA256_ASM -DSHA512_ASM -DMD5_ASM -DAES_ASM -DVPAES_ASM -DBSAES_ASM -DWHIRLPOOL_ASM -DGHASH_ASM</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">$ openssl verify -CAfile RabbitMQ_Test_CA.pem RabbitMQ_Test.pem</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">RabbitMQ_Test.pem: CN = RabbitMQ_Test, C = US</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">error 7 at 0 depth lookup:certificate signature failure</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">$ /usr/bin/openssl version -f</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">compiler: -arch x86_64 -fmessage-length=0 -pipe -Wno-trigraphs -fpascal-strings -fasm-blocks -O3 -D_REENTRANT -DDSO_DLFCN -DHAVE_DLFCN_H -DL_ENDIAN -DMD32_REG_T=int -DOPENSSL_NO_IDEA -DOPENSSL_PIC -DOPENSSL_THREADS -DZLIB -mmacosx-version-min=10.6</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">$ /usr/bin/openssl verify -CAfile RabbitMQ_Test_CA.pem RabbitMQ_Test.pem</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">RabbitMQ_Test.pem: OK</div><div style="margin: 0px; font-size: 14px; font-family: Menlo; color: rgb(41, 249, 20); background-color: rgb(0, 0, 0);">$ </div><div><br></div><div><br></div><div>Probable cause: certificate decoder either fails to encode <font face="Courier New">ASN.1 NULL</font> for "signature algorithm parameters” when it should, or encodes an explicit <font face="Courier New">ASN.1 NULL</font> when it shouldn’t. As a result, the comparison code <font face="Courier New">ASN1_TYPE_cmp</font> in <i>crypto/asn1/a_type.c</i> is presented with a case when one argument is empty (a null pointer), and the other one is of type <font face="Courier New">ASN.1 NULL</font> (0x5). In result, the comparison fails when it actually should return OK (0).</div><div><br></div><div>Here’s the workaround that I consider secure. I think it should be used, at least until the cause for the above decoding confusion is could and fixed.</div><div><br></div><div>Also, since I’m not an OpenSSL developer and thus am not a member of the mailing list, I’d appreciate if you could copy replies to this email as well.</div><div><br></div><div>Thanks!</div><div><br></div><div><div class="diff ctx" style="font-family: monospace; font-size: small; white-space: pre;">--- crypto/asn1/a_type.c.~1~        2015-01-15 09:43:14.000000000 -0500
+++ crypto/asn1/a_type.c        2015-01-17 15:12:17.000000000 -0500
@@ -117,7 +117,22 @@
        {
        int result = -1;

-       if (!a || !b || a->type != b->type) return -1;
+       if (!a || !b) {
+         if (!a && !b) /* both types are empty (null) */
+           return 0;
+         /* one is null, the other is maybe ASN.1 NULL (explicit) */
+         if (a && !b) {
+           if (a->type == V_ASN1_NULL)
+             return 0;
+         }
+         if (b && !a) {
+           if (b->type == V_ASN1_NULL)
+             return 0;
+         }
+         return -1; /* the non-null (present) type isn't ASN.1 NULL */
+       }
+
+       if (a->type != b->type) return -1;

        switch (a->type)
                {</div><div class="diff ctx" style="font-family: monospace; font-size: small; white-space: pre;"><br></div><div class="diff ctx" style="font-family: monospace; font-size: small; white-space: pre;">        </div><div class="diff ctx" style="font-family: monospace; font-size: small; white-space: pre;"></div></div></div></body></html>