1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141
|
use std::env;
use std::fs;
use std::path::PathBuf;
const SKIP_FILENAMES: &[&str] = &["crc32_small", "crc64_small"];
const MIN_LIBLZMA: &str = "5.6.2";
fn main() {
let target = env::var("TARGET").unwrap();
println!("cargo:rerun-if-changed=build.rs");
println!("cargo:rerun-if-env-changed=LZMA_API_STATIC");
let want_static = cfg!(feature = "static") || env::var("LZMA_API_STATIC").is_ok();
let msvc = target.contains("msvc");
// If a static link is desired, we compile from source.
// If we're compiling for MSVC, pkg-config runs a risk of picking up MinGW
// libraries by accident, so disable it.
//
// Otherwise, check the system to see if it has a lzma library already
// installed that we can use.
let pkg = pkg_config::Config::new()
.atleast_version(MIN_LIBLZMA)
.probe("liblzma");
if !want_static && !msvc && pkg.is_ok() {
return;
}
let want_parallel = cfg!(feature = "parallel");
let out_dir = env::var("OUT_DIR").unwrap();
println!("cargo:root={}", out_dir);
let include_dir = env::current_dir().unwrap().join("xz/src/liblzma/api");
println!("cargo:include={}", include_dir.display());
let mut src_files = [
"xz/src/liblzma/common",
"xz/src/liblzma/lzma",
"xz/src/liblzma/lz",
"xz/src/liblzma/check",
"xz/src/liblzma/delta",
"xz/src/liblzma/rangecoder",
"xz/src/liblzma/simple",
]
.iter()
.flat_map(|dir| read_dir_files(dir))
.chain(vec![
"xz/src/common/tuklib_cpucores.c".into(),
"xz/src/common/tuklib_physmem.c".into(),
])
.collect::<Vec<_>>();
if !want_parallel {
src_files = src_files
.into_iter()
.filter(|path| !path.file_stem().unwrap().to_str().unwrap().ends_with("mt"))
.collect::<Vec<_>>();
}
// sort to make build reproducible.
src_files.sort();
let mut build = cc::Build::new();
if !cfg!(debug_assertions) {
build.define("NDEBUG", None);
}
build
.files(src_files)
// all C preproc defines are in `./config.h`
.define("HAVE_CONFIG_H", "1")
.include("xz/src/liblzma/api")
.include("xz/src/liblzma/lzma")
.include("xz/src/liblzma/lz")
.include("xz/src/liblzma/check")
.include("xz/src/liblzma/simple")
.include("xz/src/liblzma/delta")
.include("xz/src/liblzma/common")
.include("xz/src/liblzma/rangecoder")
.include("xz/src/common")
.include(env::current_dir().unwrap());
if !target.ends_with("msvc") {
build.flag("-std=c99");
if want_parallel {
build.flag("-pthread");
}
}
if want_parallel {
build.define("LZMA_SYS_ENABLE_THREADS", "1");
}
if let Ok(s) = env::var("CARGO_CFG_TARGET_ENDIAN") {
if s == "big" {
build.define("WORDS_BIGENDIAN", None);
}
}
// List out the WASM targets that need wasm-shim.
// Note that Emscripten already provides its own C standard library so
// wasm32-unknown-emscripten should not be included here.
let need_wasm_shim = target == "wasm32-unknown-unknown" || target.starts_with("wasm32-wasi");
if need_wasm_shim {
println!("cargo:rerun-if-changed=wasm-shim/stdlib.h");
build.include("wasm-shim/");
}
build.compile("liblzma.a");
println!("dh-cargo:deb-built-using=lzma=0={}", env::var("CARGO_MANIFEST_DIR").unwrap());
}
fn read_dir_files(dir: &str) -> impl Iterator<Item = PathBuf> {
fs::read_dir(dir)
.unwrap_or_else(|_| panic!("failed to read dir {}", dir))
.filter_map(|ent| {
let ent = ent.expect("failed to read entry");
if ent.file_type().unwrap().is_dir() {
return None;
}
let path = ent.path();
if path.extension().unwrap() != "c" {
return None;
}
{
let file_stem = path.file_stem().unwrap().to_str().unwrap();
if SKIP_FILENAMES.contains(&file_stem) {
return None;
}
if file_stem.ends_with("tablegen") {
return None;
}
}
Some(path)
})
}
|