@@ -51,10 +51,8 @@ pub enum RepositoryError<
5151 AskpassDeviceMismatch ,
5252 #[ error( "failed to perform askpass security check; executable mismatch" ) ]
5353 AskpassExecutableMismatch ,
54- #[ error(
55- "askpass binary at '{path}' not found. Run `cargo build -p gitbutler-git` to get the binaries needed"
56- ) ]
57- AskpassExecutableNotFound { path : String } ,
54+ #[ error( "Run `{prefix}cargo build -p gitbutler-git` to get the askpass binary at '{path}'" ) ]
55+ AskpassExecutableNotFound { path : String , prefix : String } ,
5856}
5957
6058/// Higher level errors that can occur when interacting with the CLI.
@@ -95,29 +93,47 @@ where
9593 #[ cfg( feature = "test-askpass-path" ) ]
9694 let current_exe = current_exe. parent ( ) . unwrap ( ) ;
9795
98- let askpath_path = current_exe
99- . with_file_name ( {
100- #[ cfg( unix) ]
101- {
102- "gitbutler-git-askpass"
103- }
104- #[ cfg( windows) ]
105- {
106- "gitbutler-git-askpass.exe"
107- }
108- } )
109- . to_string_lossy ( )
110- . into_owned ( ) ;
96+ let askpath_path = current_exe. with_file_name ( {
97+ #[ cfg( unix) ]
98+ {
99+ "gitbutler-git-askpass"
100+ }
101+ #[ cfg( windows) ]
102+ {
103+ "gitbutler-git-askpass.exe"
104+ }
105+ } ) ;
111106
112107 #[ cfg( unix) ]
113- let setsid_path = current_exe
114- . with_file_name ( "gitbutler-git-setsid" )
115- . to_string_lossy ( )
116- . into_owned ( ) ;
108+ let setsid_path = current_exe. with_file_name ( "gitbutler-git-setsid" ) ;
117109
118110 let res = executor. stat ( & askpath_path) . await . map_err ( Error :: < E > :: Exec ) ;
119111 if res. is_err ( ) {
120- return Err ( Error :: < E > :: AskpassExecutableNotFound { path : askpath_path } ) ;
112+ let ( path, prefix) = if let Some ( workdir) = std:: env:: current_dir ( ) . ok ( ) . and_then ( |cwd| {
113+ gix:: discover:: upwards ( & cwd)
114+ . ok ( )
115+ . and_then ( |p| p. 0 . into_repository_and_work_tree_directories ( ) . 1 )
116+ } ) {
117+ let prefix = std:: env:: var_os ( "CARGO_TARGET_DIR" )
118+ . map ( std:: path:: PathBuf :: from)
119+ . map ( |path| {
120+ format ! (
121+ "CARGO_TARGET_DIR={path} " ,
122+ path = path. strip_prefix( & workdir) . unwrap_or( & path) . display( )
123+ )
124+ } )
125+ . unwrap_or_default ( ) ;
126+ (
127+ askpath_path. strip_prefix ( & workdir) . unwrap_or ( & askpath_path) ,
128+ prefix,
129+ )
130+ } else {
131+ ( askpath_path. as_path ( ) , "" . into ( ) )
132+ } ;
133+ return Err ( Error :: < E > :: AskpassExecutableNotFound {
134+ path : path. display ( ) . to_string ( ) ,
135+ prefix,
136+ } ) ;
121137 }
122138 let askpath_stat = res?;
123139
@@ -145,7 +161,7 @@ where
145161 let mut envs = envs. unwrap_or_default ( ) ;
146162 envs. insert ( "GITBUTLER_ASKPASS_PIPE" . into ( ) , sock_server. to_string ( ) ) ;
147163 envs. insert ( "GITBUTLER_ASKPASS_SECRET" . into ( ) , secret. clone ( ) ) ;
148- envs. insert ( "SSH_ASKPASS" . into ( ) , askpath_path) ;
164+ envs. insert ( "SSH_ASKPASS" . into ( ) , askpath_path. display ( ) . to_string ( ) ) ;
149165
150166 // DISPLAY is required by SSH to check SSH_ASKPASS.
151167 // Please don't ask us why, it's unclear.
@@ -177,7 +193,7 @@ where
177193 {
178194 #[ cfg( unix) ]
179195 {
180- format!( "'{setsid_path}' " )
196+ format!( "'{setsid_path}' " , setsid_path = setsid_path . display ( ) )
181197 }
182198 #[ cfg( windows) ]
183199 {
0 commit comments