Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Feature request] Provide a way to bypass pkg-config's logic by providing minimal info via env #40

Open
grossws opened this issue Apr 17, 2017 · 5 comments

Comments

@grossws
Copy link

grossws commented Apr 17, 2017

Primary idea behind this feature request is that currenty build.rs script has to duplicate some logic and data structure if FOO_NO_PKG_CONFIG is passed or no pkg-config is available on target system.

E.g. if I have FOO_LIB_PATH and FOO_INC_PATH for override in my build.rs I will have a struct which stores include_paths: Vec<PathBuf> and link_paths: Vec<PathBuf> (at least) which is populated from something like

let link_paths: Vec<_> = env::var_os("FOO_LIB_PATH")
    .map(|ps| { env::split_paths(&ps).collect() })
    .or_else(Vec::with_capacity(0));
let include_paths: Vec<_> = ...;

and have to emit cargo:rustc-link-lib=... and cargo:rustc-link-search=native=... afterwards like pkg-config crate does.

If such feature is implemeted build.rs would be much simplier for such simple cases.

Would you accept PR for this or my idea has some fatal flaws which could prevent this?

@alexcrichton
Copy link
Member

Hm I'm not sure I quite follow unfortunately? Is the idea that you want something like include paths from pkg-config but lib paths from a custom location?

@grossws
Copy link
Author

grossws commented Apr 20, 2017

In first place I want to write build.rs using pkg-config crate API with support of 2 additional cases:

  • for systems which has no pkg-config binary (e.g. MacOSX and Windows);
  • for libs which have no lib<name>.pc.

So build.rs will be something like

fn main() {
    let lib = pkg_config::Config::new()
        .probe("smbclient")
        .expect("libsmbclient not found");

    // bindgen staff
    let header = find_header(&lib).unwrap().to_str().unwrap().to_string();
    let bindings = bindgen::Builer::default().header(header)
        // bindgen config
        .generate()
        .expect("failed to generate bindings");
    // write bindings to file
}

instead of

fn main() {
    let inc_path_name = "SMBCLIENT_INCLUDE_PATH";
    let lib_path_name = "SMBCLIENT_LIBRARY_PATH";
    let header = match (env::var(inc_path_name), env::var(lib_path_name)) {
        (Ok(inc_path), Ok(lib_path)) => {
            println!("cargo:rustc-link-lib=smbclient");
            println!("cargo:rustc-link-search=native={}", lib_path);
            let mut path = PathBuf::from(inc_path);
            path.push("libsmbclient.h");
            path.to_str().unwrap().to_string()
        }
        (Ok(_), Err(_)) | (Err(_), Ok(_)) =>
            panic!("Either both {} and {} should be set or none of them", inc_path_name, lib_path_name),
        (Err(_), Err(_)) => {
            let lib = pkg_config::Config::new()
                .probe("smbclient")
                .expect("libsmbclient not found");
            find_header(&lib).unwrap().to_str().unwrap().to_string()
        }
    };

    // bindgen staff
    let bindings = bindgen::Builer::default().header(header)
        // bindgen config
        .generate()
        .expect("failed to generate bindings");
    // write bindings to file
}

@alexcrichton
Copy link
Member

Ah ok I see, but I think that's beyond the scope of the pkg-config crate? That sounds like an external helper crate, though, which may internally use pkg-config.

@grossws
Copy link
Author

grossws commented Apr 20, 2017

I thought it but it seems to me as duplication. It will still have something like Library struct with almost same fields, it will have overlapping env vars (in functional sence) for static linking, similar logic for emitting cargo:rustc-* etc.

Of course, if it seems out of scope for pkg-build to you, I could write a wrapper.

@alexcrichton
Copy link
Member

Sure yeah there may be some duplication, but not too much in theory, right? The wrapper like you're indicating may also not want to have all the fields that pkg-config returns.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants