@@ -16,8 +16,8 @@ pub type PanicHookInfo<'a> = std::panic::PanicInfo<'a>;
1616
1717use anyhow:: Context ;
1818use cargo_metadata:: { camino:: Utf8Path , semver:: Version , Artifact , CrateType , MetadataCommand } ;
19- use filetime:: FileTime ;
2019use clap:: Parser ;
20+ use filetime:: FileTime ;
2121
2222use crate :: {
2323 cargo:: { build_env, clang_target} ,
@@ -156,7 +156,6 @@ fn derive_ndk_path(shell: &mut Shell) -> Option<(PathBuf, String)> {
156156 highest_version_ndk_in_path ( & ndk_dir) . map ( |path| ( path, "standard location" . to_string ( ) ) )
157157}
158158
159-
160159fn default_ndk_dir ( ) -> PathBuf {
161160 #[ cfg( windows) ]
162161 let dir = pathos:: user:: local_dir ( )
@@ -302,7 +301,6 @@ pub fn run_env(args: Vec<String>) -> anyhow::Result<()> {
302301 println ! ( "{} {}" , env!( "CARGO_PKG_NAME" ) , env!( "CARGO_PKG_VERSION" ) ) ;
303302 std:: process:: exit ( 0 ) ;
304303 }
305-
306304
307305 let color = args
308306 . iter ( )
@@ -383,6 +381,78 @@ pub fn run_env(args: Vec<String>) -> anyhow::Result<()> {
383381 Ok ( ( ) )
384382}
385383
384+ /// Parse arguments that can appear both before and after the cargo subcommand
385+ fn parse_mixed_args ( args : Vec < String > ) -> anyhow:: Result < Args > {
386+ use clap:: CommandFactory ;
387+
388+ let mut global_args = vec ! [ "cargo-ndk" . to_string( ) ] ;
389+ let mut cargo_args = Vec :: new ( ) ;
390+
391+ // Skip the "ndk" subcommand name (always the first argument)
392+ let mut i = 1 ;
393+
394+ // Get all flags from the Args struct programmatically
395+ let cmd = Args :: command ( ) ;
396+ let mut global_flags = Vec :: new ( ) ;
397+ let mut value_flags = Vec :: new ( ) ;
398+
399+ for arg in cmd. get_arguments ( ) {
400+ // Skip the cargo_args field since it's not a real flag
401+ if arg. get_id ( ) == "cargo_args" {
402+ continue ;
403+ }
404+
405+ if let Some ( long) = arg. get_long ( ) {
406+ let long_flag = format ! ( "--{}" , long) ;
407+ global_flags. push ( long_flag. clone ( ) ) ;
408+
409+ // Check if this flag takes a value (not a boolean flag)
410+ if arg. get_action ( ) . takes_values ( ) {
411+ value_flags. push ( long_flag) ;
412+ }
413+ }
414+ if let Some ( short) = arg. get_short ( ) {
415+ let short_flag = format ! ( "-{}" , short) ;
416+ global_flags. push ( short_flag. clone ( ) ) ;
417+
418+ // Check if this flag takes a value (not a boolean flag)
419+ if arg. get_action ( ) . takes_values ( ) {
420+ value_flags. push ( short_flag) ;
421+ }
422+ }
423+ }
424+
425+ while i < args. len ( ) {
426+ let arg = & args[ i] ;
427+
428+ // Check if this is a global flag
429+ if global_flags. contains ( & arg. to_string ( ) ) {
430+ global_args. push ( arg. clone ( ) ) ;
431+
432+ // Check if this flag takes a value
433+ if value_flags. contains ( & arg. to_string ( ) ) {
434+ if i + 1 < args. len ( ) {
435+ i += 1 ;
436+ global_args. push ( args[ i] . clone ( ) ) ;
437+ }
438+ }
439+ } else {
440+ // This is a cargo arg
441+ cargo_args. push ( arg. clone ( ) ) ;
442+ }
443+
444+ i += 1 ;
445+ }
446+
447+ // Parse the extracted global args
448+ let mut parsed_args = Args :: try_parse_from ( & global_args) ?;
449+
450+ // Set the cleaned cargo_args directly
451+ parsed_args. cargo_args = cargo_args;
452+
453+ Ok ( parsed_args)
454+ }
455+
386456pub fn run ( args : Vec < String > ) -> anyhow:: Result < ( ) > {
387457 // Check for help/version before parsing to avoid required arg errors
388458 if args. is_empty ( ) || args. contains ( & "--help" . to_string ( ) ) || args. contains ( & "-h" . to_string ( ) ) {
@@ -445,7 +515,7 @@ pub fn run(args: Vec<String>) -> anyhow::Result<()> {
445515 . unwrap_or ( BuildMode :: Debug )
446516 } ;
447517
448- let args = match Args :: try_parse_from ( & args) {
518+ let args = match parse_mixed_args ( args) {
449519 Ok ( args) => args,
450520 Err ( e) => {
451521 shell. error ( e) ?;
0 commit comments