@@ -13,6 +13,25 @@ use crate::core::compiler::{CompileKind, Metadata, Unit};
13
13
use crate :: core:: Package ;
14
14
use crate :: util:: { config, CargoResult , GlobalContext } ;
15
15
16
+ /// Represents the kind of process we are creating.
17
+ #[ derive( Debug ) ]
18
+ enum ToolKind {
19
+ /// See [`Compilation::rustc_process`].
20
+ Rustc ,
21
+ /// See [`Compilation::rustdoc_process`].
22
+ Rustdoc ,
23
+ /// See [`Compilation::host_process`].
24
+ HostProcess ,
25
+ /// See [`Compilation::target_process`].
26
+ TargetProcess ,
27
+ }
28
+
29
+ impl ToolKind {
30
+ fn is_rustc_tool ( & self ) -> bool {
31
+ matches ! ( self , ToolKind :: Rustc | ToolKind :: Rustdoc )
32
+ }
33
+ }
34
+
16
35
/// Structure with enough information to run `rustdoc --test`.
17
36
pub struct Doctest {
18
37
/// What's being doctested
@@ -176,7 +195,7 @@ impl<'gctx> Compilation<'gctx> {
176
195
} ;
177
196
178
197
let cmd = fill_rustc_tool_env ( rustc, unit) ;
179
- self . fill_env ( cmd, & unit. pkg , None , unit. kind , true )
198
+ self . fill_env ( cmd, & unit. pkg , None , unit. kind , ToolKind :: Rustc )
180
199
}
181
200
182
201
/// Returns a [`ProcessBuilder`] for running `rustdoc`.
@@ -187,7 +206,7 @@ impl<'gctx> Compilation<'gctx> {
187
206
) -> CargoResult < ProcessBuilder > {
188
207
let rustdoc = ProcessBuilder :: new ( & * self . gctx . rustdoc ( ) ?) ;
189
208
let cmd = fill_rustc_tool_env ( rustdoc, unit) ;
190
- let mut cmd = self . fill_env ( cmd, & unit. pkg , script_meta, unit. kind , true ) ?;
209
+ let mut cmd = self . fill_env ( cmd, & unit. pkg , script_meta, unit. kind , ToolKind :: Rustdoc ) ?;
191
210
cmd. retry_with_argfile ( true ) ;
192
211
unit. target . edition ( ) . cmd_edition_arg ( & mut cmd) ;
193
212
@@ -214,7 +233,7 @@ impl<'gctx> Compilation<'gctx> {
214
233
pkg,
215
234
None ,
216
235
CompileKind :: Host ,
217
- false ,
236
+ ToolKind :: HostProcess ,
218
237
)
219
238
}
220
239
@@ -249,7 +268,8 @@ impl<'gctx> Compilation<'gctx> {
249
268
} else {
250
269
ProcessBuilder :: new ( cmd)
251
270
} ;
252
- let mut builder = self . fill_env ( builder, pkg, script_meta, kind, false ) ?;
271
+ let tool_kind = ToolKind :: TargetProcess ;
272
+ let mut builder = self . fill_env ( builder, pkg, script_meta, kind, tool_kind) ?;
253
273
254
274
if let Some ( client) = self . gctx . jobserver_from_env ( ) {
255
275
builder. inherit_jobserver ( client) ;
@@ -269,10 +289,22 @@ impl<'gctx> Compilation<'gctx> {
269
289
pkg : & Package ,
270
290
script_meta : Option < Metadata > ,
271
291
kind : CompileKind ,
272
- is_rustc_tool : bool ,
292
+ tool_kind : ToolKind ,
273
293
) -> CargoResult < ProcessBuilder > {
274
294
let mut search_path = Vec :: new ( ) ;
275
- if is_rustc_tool {
295
+ if tool_kind. is_rustc_tool ( ) {
296
+ if matches ! ( tool_kind, ToolKind :: Rustdoc ) {
297
+ // HACK: `rustdoc --test` not only compiles but executes doctests.
298
+ // Ideally only execution phase should have search paths appended,
299
+ // so the executions can find native libs just like other tests.
300
+ // However, there is no way to separate these two phase, so this
301
+ // hack is added for both phases.
302
+ // TODO: handle doctest-xcompile
303
+ search_path. extend ( super :: filter_dynamic_search_path (
304
+ self . native_dirs . iter ( ) ,
305
+ & self . root_output [ & CompileKind :: Host ] ,
306
+ ) ) ;
307
+ }
276
308
search_path. push ( self . deps_output [ & CompileKind :: Host ] . clone ( ) ) ;
277
309
} else {
278
310
search_path. extend ( super :: filter_dynamic_search_path (
0 commit comments