visual-studio - PEM_read_bio_X509(有时)失败(OpenSSL 1.0.1p)

标签 visual-studio visual-studio-2010 ssl proxy openssl

我已经创建了一个 DSAPI 过滤器来使用客户端证书对用户进行身份验证。用户通过代理连接,代理将用户的证书添加到请求 header 中。

#define HDR_SSL_CLIENT_CERT                 "SSL_CLIENT_CERT"

我正在使用 Apache 作为 HTTPS 代理;客户使用 NGINX。我已经发现 NGINX 添加了 TABS 而不是 SPACES,并且我还确保证书数据在被我的代码解析之前具有正确的格式

#define BUFFER_SIZE 4096
char certData[BUFFER_SIZE+1] = {0,};

certData 包含证书的 Base64 表示(TABS 和 SPACES 替换为\n)

-----BEGIN CERTIFICATE-----
MIIDOTCCAiGgAwIBAgIBAjANBgkqhkiG9w0BAQsFADBGMQswCQYDVQQGEwJERTEO
MAwGA1UECgwFRE9TWVMxETAPBgNVBAsMCFRSQVZFTEVSMRQwEgYDVQQDDAtUUkFW
RUxFUiBDQTAeFw0xNjA0MTgxMzA2MjdaFw0yNjA0MTgxMzA2MjdaMBUxEzARBgNV
BAMMCkdlb3JnIER1bWEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCG
ctEsl++/4LgK8RJId2NUPJgjFKDl76jp38GNMtcCqt+ADUPvR+suoy/zeuRXs7hw
25YAx49U/FYFlu3Xlmb57ACyPtbhLPpV2Y8fJ0EXD2pY1G3oEWlKWWk6ErT2vg7V
ppOajckkx3EmkVrALhQgdOqQDHJ6Y2xQSgpKWGORmoEtYQepJ/LGWBfE4muZjUJk
euUf0fmHFehMw8X0ErPDFxDuAH+d7kjjUl+EqSQCqLqqrg50GMrM0vKIqyqqbUQF
wLQYyFllYkj0h1VQ+KhyxwVkq2snR+Z2EJe1A7xsUwY5D/9dVK5ih6xeIrpgvgCd
6Amx2KF9lh8yEZi1NMPPAgMBAAGjYzBhMB8GA1UdEQQYMBaBFEdlb3JnRHVtYUBz
dGFkdGRvLmRlMB0GA1UdDgQWBBRIX2fz2ahSFgOCf03W4pn9t/BomjAfBgNVHSME
GDAWgBR7RJ1HsYOVlc4TOAzeqIqETopeCTANBgkqhkiG9w0BAQsFAAOCAQEALWre
gJYsSD6i3e4MhJOhR0FFincqdnVEeEoVMr4GDSZRMUPSTjNMTdGLLMFHpU9p/cGZ
4b30k7dQWhIao7aLIgDOXaATr14fLXrZqRM/MXusd27nFKQRZf1ktrxr0vIZqnw4
SuniS3NP7SuVEbUeTWU8nVub17aUWX8T4C8yAHKmancSSgMXwFhXTNq0aIvwRzIv
TzyK0SDXSc68kQkf3evTRvKfvlmQGWXL6BukTGJS1870x3IrDK19Phi5PUYXQtZV
uwaRg1fRUyPno0GCIZiMxCY4rWy+AaM3CO7Ua5+KEiAdWKrBP6Jd24hZuH8ZhuZ/
9u5SSvUA1bGAT02eqQ==
-----END CERTIFICATE-----

然后我使用以下代码从 certData 获取 X509:

    BIO * bio = BIO_new(BIO_s_mem()); 
    X509 * clientCert = X509_new(); 
    bio = BIO_new_mem_buf(certData, -1);
    PEM_read_bio_X509(bio, &clientCert, 0, NULL);

    if (clientCert == NULL) {
        debugOut("PEM_read_bio_X509 failed...\n");

        if(bio) {
            BIO_free(bio);
        }

        return false;
    } 

在 Apache 中使用 DSAPI 时,我们没有发现任何问题; NGINX 也有效。但有时,PEM_read_bio_X509 会失败并且不会创建 clientCert。

我的代码有什么明显的错误吗?

PEM_read_bio_X509 和 NGINX 是否存在已知问题?

我目前使用的是 openSSL 1.0.1p。

更新:这是替换 TABS 和 SPACES 的代码

char szHeaderAuthToken[MAX_BUF_LEN+1] = {0,};

包含代理提交的数据

    size_t last = certLen - lastblank;

    while (szHeaderClientCert[j] != '\0') {
        c = szHeaderClientCert[j];
        // skip first and last 'space' char
        if (j == 10 || j == last) {
            c = ' ';
        } else {
            if (isspace(c) || ('\t' == c) ) c = '\n';
        }
        certData[j] = c;

        if (DEBUGOUT) {
            putchar (c);
            ofs << c;
        }

        j++;
    }

    certData[j+1] = '\0';

更新 2:好的和坏的 certData

20160512_145926  GOOD

-----BEGIN CERTIFICATE-----
MIIDOTCCAiGgAwIBAgIBAjANBgkqhkiG9w0BAQsFADBGMQswCQYDVQQGEwJERTEO
MAwGA1UECgwFRE9TWVMxETAPBgNVBAsMCFRSQVZFTEVSMRQwEgYDVQQDDAtUUkFW
RUxFUiBDQTAeFw0xNjA0MTgxMzA2MjdaFw0yNjA0MTgxMzA2MjdaMBUxEzARBgNV
BAMMCkdlb3JnIER1bWEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCG
ctEsl++/4LgK8RJId2NUPJgjFKDl76jp38GNMtcCqt+ADUPvR+suoy/zeuRXs7hw
25YAx49U/FYFlu3Xlmb57ACyPtbhLPpV2Y8fJ0EXD2pY1G3oEWlKWWk6ErT2vg7V
ppOajckkx3EmkVrALhQgdOqQDHJ6Y2xQSgpKWGORmoEtYQepJ/LGWBfE4muZjUJk
euUf0fmHFehMw8X0ErPDFxDuAH+d7kjjUl+EqSQCqLqqrg50GMrM0vKIqyqqbUQF
wLQYyFllYkj0h1VQ+KhyxwVkq2snR+Z2EJe1A7xsUwY5D/9dVK5ih6xeIrpgvgCd
6Amx2KF9lh8yEZi1NMPPAgMBAAGjYzBhMB8GA1UdEQQYMBaBFEdlb3JnRHVtYUBz
dGFkdGRvLmRlMB0GA1UdDgQWBBRIX2fz2ahSFgOCf03W4pn9t/BomjAfBgNVHSME
GDAWgBR7RJ1HsYOVlc4TOAzeqIqETopeCTANBgkqhkiG9w0BAQsFAAOCAQEALWre
gJYsSD6i3e4MhJOhR0FFincqdnVEeEoVMr4GDSZRMUPSTjNMTdGLLMFHpU9p/cGZ
4b30k7dQWhIao7aLIgDOXaATr14fLXrZqRM/MXusd27nFKQRZf1ktrxr0vIZqnw4
SuniS3NP7SuVEbUeTWU8nVub17aUWX8T4C8yAHKmancSSgMXwFhXTNq0aIvwRzIv
TzyK0SDXSc68kQkf3evTRvKfvlmQGWXL6BukTGJS1870x3IrDK19Phi5PUYXQtZV
uwaRg1fRUyPno0GCIZiMxCY4rWy+AaM3CO7Ua5+KEiAdWKrBP6Jd24hZuH8ZhuZ/
9u5SSvUA1bGAT02eqQ==
-----END CERTIFICATE-----


20160512_150227  FAIL

-----BEGIN CERTIFICATE-----
MIIDOTCCAiGgAwIBAgIBAjANBgkqhkiG9w0BAQsFADBGMQswCQYDVQQGEwJERTEO
MAwGA1UECgwFRE9TWVMxETAPBgNVBAsMCFRSQVZFTEVSMRQwEgYDVQQDDAtUUkFW
RUxFUiBDQTAeFw0xNjA0MTgxMzA2MjdaFw0yNjA0MTgxMzA2MjdaMBUxEzARBgNV
BAMMCkdlb3JnIER1bWEwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCG
ctEsl++/4LgK8RJId2NUPJgjFKDl76jp38GNMtcCqt+ADUPvR+suoy/zeuRXs7hw
25YAx49U/FYFlu3Xlmb57ACyPtbhLPpV2Y8fJ0EXD2pY1G3oEWlKWWk6ErT2vg7V
ppOajckkx3EmkVrALhQgdOqQDHJ6Y2xQSgpKWGORmoEtYQepJ/LGWBfE4muZjUJk
euUf0fmHFehMw8X0ErPDFxDuAH+d7kjjUl+EqSQCqLqqrg50GMrM0vKIqyqqbUQF
wLQYyFllYkj0h1VQ+KhyxwVkq2snR+Z2EJe1A7xsUwY5D/9dVK5ih6xeIrpgvgCd
6Amx2KF9lh8yEZi1NMPPAgMBAAGjYzBhMB8GA1UdEQQYMBaBFEdlb3JnRHVtYUBz
dGFkdGRvLmRlMB0GA1UdDgQWBBRIX2fz2ahSFgOCf03W4pn9t/BomjAfBgNVHSME
GDAWgBR7RJ1HsYOVlc4TOAzeqIqETopeCTANBgkqhkiG9w0BAQsFAAOCAQEALWre
gJYsSD6i3e4MhJOhR0FFincqdnVEeEoVMr4GDSZRMUPSTjNMTdGLLMFHpU9p/cGZ
4b30k7dQWhIao7aLIgDOXaATr14fLXrZqRM/MXusd27nFKQRZf1ktrxr0vIZqnw4
SuniS3NP7SuVEbUeTWU8nVub17aUWX8T4C8yAHKmancSSgMXwFhXTNq0aIvwRzIv
TzyK0SDXSc68kQkf3evTRvKfvlmQGWXL6BukTGJS1870x3IrDK19Phi5PUYXQtZV
uwaRg1fRUyPno0GCIZiMxCY4rWy+AaM3CO7Ua5+KEiAdWKrBP6Jd24hZuH8ZhuZ/
9u5SSvUA1bGAT02eqQ==
-----END CERTIFICATE-----
20160512_150227 PEM_read_bio_X509 failed...

最佳答案

感谢所有提示和建议。

我重写了我的代码;不确定,这是否真的能解决客户方面的问题。

我现在使用 boost 库来格式化 PEM 数据

#include <boost/algorithm/string.hpp>
#include <boost/algorithm/string/trim_all.hpp>

std::string cert_data(szHeaderClientCert);
boost::erase_all(cert_data, "-----BEGIN CERTIFICATE-----");
boost::erase_all(cert_data, "-----END CERTIFICATE-----");

if (boost::contains(cert_data, "\t"))
        boost::replace_all(cert_data, "\t", " ");

boost::trim_all(cert_data);
boost::replace_all(cert_data, " ", "\n");

std::vector<std::string> vec;
vec.push_back("-----BEGIN CERTIFICATE-----");
vec.push_back(cert_data);
vec.push_back("-----END CERTIFICATE-----");

std::string szCertData = boost::algorithm::join(vec, "\n");

然后得到一个(有效的)证书

BIO * bio = BIO_new(BIO_s_mem());
BIO_puts(bio, szCertData.c_str());

X509 * clientCert;

clientCert = PEM_read_bio_X509(bio, NULL, 0, NULL);
        if (clientCert == NULL) { 

...

关于visual-studio - PEM_read_bio_X509(有时)失败(OpenSSL 1.0.1p),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37202804/

相关文章:

c# - 从 .lib 文件创建 .dll 文件

asp.net-mvc - Visual Studio 2010 未发布所有 App_Data

c# - 程序集错误building app - Encountered multiple versions of assembly

Apache Openssl 压缩

tomcat - 配置 Tomcat 以通过 SSL 使用 Web 服务

c# - 如何在 ngrok 上部署 visual studio 项目?

c - 在 Visual Studio 中放置要用作命令行参数的文件的位置

C++ 对象初始化(堆栈)

c# - 读取 excel 但值以不同的格式出现

c# - 如何在 WPF WebBrowser 控件中允许不受信任的 SSL