diff --git a/.github/workflows/bindgen.yml b/.github/workflows/bindgen.yml index d459fc2fc2..ba95e42e23 100644 --- a/.github/workflows/bindgen.yml +++ b/.github/workflows/bindgen.yml @@ -201,12 +201,27 @@ jobs: ./mdbook build book ./mdbook test book + # FIXME(pvdrz): this should be done inside `bindgen-test` instead + test-no-headers: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + + - name: Test `--help` + run: cargo run -- --help + + - name: Test `--version` + run: cargo run -- --version + + - name: Test `--generate-shell-completions` + run: cargo run -- --generate-shell-completions=bash + # One job that "summarizes" the success state of this pipeline. This can then # be added to branch protection, rather than having to add each job # separately. success: runs-on: ubuntu-latest - needs: [rustfmt-clippy, msrv, minimal, docs, quickchecking, test-expectations, test, check-cfg, test-book] + needs: [rustfmt-clippy, msrv, minimal, docs, quickchecking, test-expectations, test, check-cfg, test-book, test-no-headers] # GitHub branch protection is exceedingly silly and treats "jobs skipped # because a dependency failed" as success. So we have to do some # contortions to ensure the job fails if any of its dependencies fails. diff --git a/bindgen/options/cli.rs b/bindgen/options/cli.rs index 9d5cea3dc6..8c4c05bc84 100644 --- a/bindgen/options/cli.rs +++ b/bindgen/options/cli.rs @@ -146,7 +146,7 @@ fn parse_custom_attribute( #[allow(clippy::doc_markdown)] struct BindgenCommand { /// C or C++ header file. - header: String, + header: Option, /// Path to write depfile to. #[arg(long)] depfile: Option, @@ -657,6 +657,33 @@ where clang_args, } = command; + if let Some(shell) = generate_shell_completions { + clap_complete::generate( + shell, + &mut BindgenCommand::command(), + "bindgen", + &mut io::stdout(), + ); + + exit(0) + } + + if version { + println!( + "bindgen {}", + option_env!("CARGO_PKG_VERSION").unwrap_or("unknown") + ); + if verbose { + println!("Clang: {}", crate::clang_version().full); + } + + exit(0) + } + + if header.is_none() { + return Err(io::Error::new(io::ErrorKind::Other, "Header not found")); + } + let mut builder = builder(); #[derive(Debug)] @@ -804,31 +831,8 @@ where } } - let header = Some(header); - builder = apply_args!( builder { - generate_shell_completions => |_, shell| { - clap_complete::generate( - shell, - &mut BindgenCommand::command(), - "bindgen", - &mut io::stdout(), - ); - - exit(0) - }, - version => |_, _| { - println!( - "bindgen {}", - option_env!("CARGO_PKG_VERSION").unwrap_or("unknown") - ); - if verbose { - println!("Clang: {}", crate::clang_version().full); - } - - exit(0) - }, header, rust_target, rust_edition,