Commit 6ef819f9 authored by Steven Fackler's avatar Steven Fackler
Browse files

Fix builds against 0.9.x OpenSSL

Namely builds on OSX
parent b41f3dd7
Loading
Loading
Loading
Loading
+0 −11
Original line number Diff line number Diff line
@@ -40,17 +40,6 @@ Rust install's libs folder. The default should be:
respectively.
5. Run `cargo build`.

###OS X

OS X is shipped with extremely outdated openssl. We recommend to update it. If you're using Homebrew it should be as easy as:

```bash
brew install openssl
brew link openssl --force
```

Note that you need to execute `cargo clean` in your project directory to rebuild `rust-openssl` with the new version of `openssl`.

###Testing
Several tests expect a local test server to be running to bounce requests off
of. It's easy to do this. Open a separate terminal window and `cd` to the
+2 −1
Original line number Diff line number Diff line
@@ -18,7 +18,8 @@ sslv2 = []
aes_xts = []

[build-dependencies]
pkg-config = "0.1.1"
pkg-config = "0.2"
gcc = "0.1"

[target.le32-unknown-nacl.dependencies]
libressl-pnacl-sys = "2.1.0"
+36 −30
Original line number Diff line number Diff line
#![feature(core, collections, env)]
#![feature(env)]

extern crate "pkg-config" as pkg_config;
extern crate gcc;

use std::env;
use std::default::Default;

fn main() {
    let target = env::var_string("TARGET").unwrap();
    let is_android = target.find_str("android").is_some();

    // Without hackory, pkg-config will only look for host libraries.
    // So, abandon ship if we're cross compiling.
    if !is_android && !pkg_config::target_supported() {
        panic!("unsupported target");
    if target.contains("android") {
        let path = env::var_string("OPENSSL_PATH").ok()
            .expect("Android does not provide openssl libraries, please build them yourself \
                     (instructions in the README) and provide their location through \
                     $OPENSSL_PATH.");
        println!("cargo:rustc-flags=-L native={} -l crypto:static -l ssl:static", path);
        return;
    }

    if pkg_config::find_library("openssl").is_err() {
        let mut flags = if is_android {
            " -l crypto:static -l ssl:static"
        } else {
            " -l crypto -l ssl"
        }.to_string();

        let win_pos = target.find_str("windows")
                            .or(target.find_str("win32"))
                            .or(target.find_str("win64"));

        // It's fun, but it looks like win32 and win64 both
        // have all the libs with 32 sufix
        if win_pos.is_some() {
           flags.push_str(" -l gdi32 -l wsock32");
    if target.contains("win32") || target.contains("win64") {
        println!("cargo:rustc-flags=-l crypto -l ssl -l gdi32 -l wsock32");
        return;
    }

        if is_android {
            let path = env::var_string("OPENSSL_PATH").ok()
                .expect("Android does not provide openssl libraries, please build them yourselves \
                         (instructions in the README) and provide their location through \
                         $OPENSSL_PATH.");
            flags.push_str(format!(" -L {}", path).as_slice());
    if pkg_config::Config::new().atleast_version("1.0.0").find("openssl").is_ok() {
        build_old_openssl_shim(false);
        return;
    }

        println!("cargo:rustc-flags={}", flags);
    if pkg_config::find_library("openssl").is_ok() {
        build_old_openssl_shim(true);
        return;
    }

    panic!("Unable to find openssl libraries");
}

fn build_old_openssl_shim(is_old: bool) {
        let mut config: gcc::Config = Default::default();
        if is_old {
            config.definitions.push(("OLD_OPENSSL".to_string(), None));
        }

        gcc::compile_library("libold_openssl_shim.a",
                             &config,
                             &["src/old_openssl_shim.c"]);
        let out_dir = env::var_string("OUT_DIR").unwrap();
        println!("cargo:rustc-flags=-L native={} -l old_openssl_shim:static", out_dir);
}
+8 −0
Original line number Diff line number Diff line
@@ -382,12 +382,20 @@ extern "C" {
    pub fn EVP_PKEY_set1_RSA(k: *mut EVP_PKEY, r: *mut RSA) -> c_int;

    pub fn HMAC_CTX_init(ctx: *mut HMAC_CTX);
    #[deprecated = "use HMAC_Init_ex_shim instead"]
    pub fn HMAC_Init_ex(ctx: *mut HMAC_CTX, key: *const u8, keylen: c_int, md: *const EVP_MD, imple: *const ENGINE) -> c_int;
    #[deprecated = "use HMAC_Final_shim instead"]
    pub fn HMAC_Final(ctx: *mut HMAC_CTX, output: *mut u8, len: *mut c_uint) -> c_int;
    #[deprecated = "use HMAC_Update_shim instead"]
    pub fn HMAC_Update(ctx: *mut HMAC_CTX, input: *const u8, len: c_uint) -> c_int;
    pub fn HMAC_CTX_cleanup(ctx: *mut HMAC_CTX);
    pub fn HMAC_CTX_copy(dst: *mut HMAC_CTX, src: *const HMAC_CTX) -> c_int;

    // Pre-1.0 versions of these didn't return anything, so the shims bridge that gap
    pub fn HMAC_Init_ex_shim(ctx: *mut HMAC_CTX, key: *const u8, keylen: c_int, md: *const EVP_MD, imple: *const ENGINE) -> c_int;
    pub fn HMAC_Final_shim(ctx: *mut HMAC_CTX, output: *mut u8, len: *mut c_uint) -> c_int;
    pub fn HMAC_Update_shim(ctx: *mut HMAC_CTX, input: *const u8, len: c_uint) -> c_int;


    pub fn PEM_read_bio_X509(bio: *mut BIO, out: *mut *mut X509, callback: Option<PasswordCallback>,
                             user_data: *mut c_void) -> *mut X509;
+49 −0
Original line number Diff line number Diff line
#include <openssl/hmac.h>

#ifdef OLD_OPENSSL
// Copied from openssl crypto/hmac/hmac.c
int HMAC_CTX_copy(HMAC_CTX *dctx, HMAC_CTX *sctx)
     {
     if (!EVP_MD_CTX_copy(&dctx->i_ctx, &sctx->i_ctx))
         goto err;
     if (!EVP_MD_CTX_copy(&dctx->o_ctx, &sctx->o_ctx))
         goto err;
     if (!EVP_MD_CTX_copy(&dctx->md_ctx, &sctx->md_ctx))
         goto err;
     memcpy(dctx->key, sctx->key, HMAC_MAX_MD_CBLOCK);
     dctx->key_length = sctx->key_length;
     dctx->md = sctx->md;
     return 1;
     err:
     return 0;
     }

int HMAC_Init_ex_shim(HMAC_CTX *ctx, const void *key, int key_len, const EVP_MD *md, ENGINE *impl) {
    HMAC_Init_ex(ctx, key, key_len, md, impl);
    return 1;
}

int HMAC_Update_shim(HMAC_CTX *ctx, const unsigned char *data, int len) {
    HMAC_Update(ctx, data, len);
    return 1;
}

int HMAC_Final_shim(HMAC_CTX *ctx, unsigned char *md, unsigned int *len) {
    HMAC_Final(ctx, md, len);
    return 1;
}

#else /* OLD_OPENSSL */

int HMAC_Init_ex_shim(HMAC_CTX *ctx, const void *key, int key_len, const EVP_MD *md, ENGINE *impl) {
    return HMAC_Init_ex(ctx, key, key_len, md, impl);
}

int HMAC_Update_shim(HMAC_CTX *ctx, const unsigned char *data, int len) {
    return HMAC_Update(ctx, data, len);
}

int HMAC_Final_shim(HMAC_CTX *ctx, unsigned char *md, unsigned int *len) {
    return HMAC_Final(ctx, md, len);
}
#endif /* OLD_OPENSSL */
Loading