続 IO::Socket::SSL で証明書の検証をする

この間の日記の続き。
コメントに貴重な情報をいただいたので、少し調べてみた。まだうまくいっていないので経過報告といったところだが、ひとつ変なことに気がついたので、記しておく。

検証のために書いたコードは Gist に置いた。まず、imap.mail.me.com の証明書を検証するために必要な、「Verisign Class 3 Public Primary Certification Authority - G3」と「VeriSign Class 3 Public Primary Certification Authority - G5」の証明書だけを入れたファイルを使い、検証をさせてみた。$Net::SSLeay::trace = 3 にしても、検証過程が読みとれなかったので、コールバックを使って経過を確認してみた。
すると、最初に呼ばれた際の Issuer (正確には Issuer と Subject をつないだもののようで、二つめの「/C=US」以降は Subject と思われる)が

/C=US/O=VeriSign, Inc./OU=Class 3 Public Primary Certification Authority/C=US/O=VeriSign, Inc./OU=VeriSign Trust Network/OU=(c) 2006 VeriSign, Inc. - For authorized use only/CN=VeriSign Class 3 Public Primary Certification Authority - G5

となっている。Issuer の OU は、「VeriSign Class 3 Public Primary Certification Authority - G5」になるべきところではないのか。なぜか「Class 3 Public Primary Certification Authority」になっている。これはおかしい(たぶん)。
エラー番号の「20」は、openssl/x509_vfy.h を見ると、「X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY」のことらしい。Issuer の証明書が見つからなかった、ってことかな。
では、ca-bundle_tiny.crt に入っている証明書がおかしいのかと思い、G5 の部分だけを抜きだしたファイルを作成し、

openssl x509 -in 05_verisign_class3_g5.crt -text

で内容を表示させてみると、

Issuer: C=US, O=VeriSign, Inc., OU=VeriSign Trust Network, OU=(c) 2006 VeriSign, Inc. - For authorized use only, CN=VeriSign Class 3 Public Primary Certification Authority - G5

Subject: C=US, O=VeriSign, Inc., OU=VeriSign Trust Network, OU=(c) 2006 VeriSign, Inc. - For authorized use only, CN=VeriSign Class 3 Public Primary Certification Authority - G5

と、こちらは正常っぽい? 元になった certdata.txt でも同じなので、たぶんこれは問題なさそう?

ということで、なんだか Net::SSLeay (あるいはリンクされてる OpenSSL) のバグっぽい感じもするのだけど、そもそも「Class 3 Public Primary Certification Authority」がどこからきたもの? ってのが謎。imap.gmail.com では、「Google Internet Authority G2」→「GeoTrust Global CA」→「Equifax Secure Certificate Authority」の順できれいにつながってる感じなのに。
Mac OS X だけの問題かと思って Windows 上の ActivePerl で試してみたが、同じ症状だった。IO::Socket::SSL を使わず、Net::SSLeay だけで検証させてみても同じ結果。余計にわからなくなってしまった...。