Compile lmdb with opt level O2

LMDB segfaults reliably with newer GCC versions when compiled with O3.
Regression test included.

fixes #21
without.crypto
Dan Burkert 7 years ago committed by Dan Burkert
parent ee5968dd25
commit 547841a3e2
  1. 1
      .travis.yml
  2. 1
      Cargo.toml
  3. 3
      lmdb-sys/Cargo.toml
  4. 16
      lmdb-sys/build.rs
  5. 32
      src/lib.rs

@ -17,4 +17,5 @@ script:
- cargo build --verbose
- if [[ $TRAVIS_RUST_VERSION = nightly* ]]; then
env RUST_BACKTRACE=1 cargo test --all -v;
env RUST_BACKTRACE=1 cargo test --all -v --release;
fi

@ -25,3 +25,4 @@ lmdb-sys = { path = "lmdb-sys" }
[dev-dependencies]
rand = "0.3"
tempdir = "0.3"
byteorder = "1.0"

@ -20,4 +20,5 @@ libc = "0.2"
[build-dependencies]
pkg-config = "0.3"
gcc = "0.3"
# https://github.com/alexcrichton/gcc-rs/issues/240
gcc = "=0.3.51"

@ -5,21 +5,17 @@ use std::env;
use std::path::PathBuf;
fn main() {
let mut lmdb: PathBuf = PathBuf::from(&env::var("CARGO_MANIFEST_DIR").unwrap());
lmdb.push("lmdb");
lmdb.push("libraries");
lmdb.push("liblmdb");
let mut mdb: PathBuf = lmdb.clone();
let mut midl: PathBuf = lmdb.clone();
mdb.push("mdb.c");
midl.push("midl.c");
if !pkg_config::find_library("liblmdb").is_ok() {
gcc::compile_library("liblmdb.a",
&[(*mdb).to_str().unwrap(),
(*midl).to_str().unwrap()]);
gcc::Config::new()
.file(lmdb.join("mdb.c"))
.file(lmdb.join("midl.c"))
// https://github.com/LMDB/lmdb/blob/LMDB_0.9.21/libraries/liblmdb/Makefile#L25
.opt_level(2)
.compile("liblmdb.a")
}
}

@ -62,6 +62,9 @@ mod transaction;
#[cfg(test)]
mod test_utils {
extern crate byteorder;
use self::byteorder::{ByteOrder, LittleEndian};
use tempdir::TempDir;
use super::*;
@ -88,4 +91,33 @@ mod test_utils {
}
(dir, env)
}
/// Regression test for https://github.com/danburkert/lmdb-rs/issues/21.
/// This test reliably segfaults when run against lmbdb compiled with opt level -O3 and newer
/// GCC compilers.
#[test]
fn issue_21_regression() {
const HEIGHT_KEY: [u8; 1] = [0];
let dir = TempDir::new("test").unwrap();
let env = {
let mut builder = Environment::new();
builder.set_max_dbs(2);
builder.set_map_size(1_000_000);
builder.open(dir.path()).expect("open lmdb env")
};
let index = env.create_db(None, DUP_SORT).expect("open index db");
for height in 0..1000 {
let mut value = [0u8; 8];
LittleEndian::write_u64(&mut value, height);
let mut tx = env.begin_rw_txn().expect("begin_rw_txn");
tx.put(index,
&HEIGHT_KEY,
&value,
WriteFlags::empty()).expect("tx.put");
tx.commit().expect("ts.commit")
}
}
}

Loading…
Cancel
Save