rustflags/
render.rs

1use crate::write::WriteFmt;
2use crate::{Flag, LibraryKind, LinkKind};
3use std::ffi::{OsStr, OsString};
4
5impl IntoIterator for Flag {
6    type Item = OsString;
7    type IntoIter = iter::Iter;
8
9    fn into_iter(self) -> Self::IntoIter {
10        let mut flags = Vec::new();
11
12        match self {
13            Flag::Help => {
14                flags.push(OsString::from("--help"));
15            }
16
17            Flag::Cfg { name, value } => {
18                flags.push(OsString::from("--cfg"));
19                if let Some(value) = value {
20                    flags.push(OsString::from(format!("{}=\"{}\"", name, value)));
21                } else {
22                    flags.push(OsString::from(name));
23                }
24            }
25
26            Flag::LibrarySearchPath { kind, path } => {
27                flags.push(OsString::from("-L"));
28                if kind == LibraryKind::All {
29                    flags.push(OsString::from(path));
30                } else {
31                    let mut flag = OsString::new();
32                    write!(flag, "{}=", kind);
33                    flag.push(path);
34                    flags.push(flag);
35                }
36            }
37
38            Flag::Link {
39                kind,
40                modifiers,
41                name,
42                rename,
43            } => {
44                flags.push(OsString::from("-l"));
45                let mut flag = OsString::new();
46                if kind != LinkKind::default() || !modifiers.is_empty() {
47                    write!(flag, "{}", kind);
48                }
49                for (i, (prefix, modifier)) in modifiers.iter().enumerate() {
50                    flag.push(if i == 0 { ":" } else { "," });
51                    write!(flag, "{}{}", prefix, modifier);
52                }
53                if !flag.is_empty() {
54                    flag.push("=");
55                }
56                flag.push(name);
57                if let Some(rename) = rename {
58                    flag.push(":");
59                    flag.push(rename);
60                }
61                flags.push(flag);
62            }
63
64            Flag::CrateType(crate_type) => {
65                flags.push(OsString::from("--crate-type"));
66                flags.push(OsString::from(crate_type.to_string()));
67            }
68
69            Flag::CrateName(crate_name) => {
70                flags.push(OsString::from("--crate-name"));
71                flags.push(OsString::from(crate_name));
72            }
73
74            Flag::Edition(edition) => {
75                flags.push(OsString::from("--edition"));
76                flags.push(OsString::from(edition.to_string()));
77            }
78
79            Flag::Emit(emit) => {
80                flags.push(OsString::from("--emit"));
81                flags.push(OsString::from(emit.to_string()));
82            }
83
84            Flag::Print(print) => {
85                flags.push(OsString::from("--print"));
86                flags.push(OsString::from(print));
87            }
88
89            Flag::Out(filename) => {
90                flags.push(OsString::from("-o"));
91                flags.push(OsString::from(filename));
92            }
93
94            Flag::OutDir(dir) => {
95                flags.push(OsString::from("--out-dir"));
96                flags.push(OsString::from(dir));
97            }
98
99            Flag::Explain(code) => {
100                flags.push(OsString::from("--explain"));
101                flags.push(OsString::from(code));
102            }
103
104            Flag::Test => {
105                flags.push(OsString::from("--test"));
106            }
107
108            Flag::Target(target) => {
109                flags.push(OsString::from("--target"));
110                flags.push(OsString::from(target));
111            }
112
113            Flag::Allow(lint) => {
114                flags.push(OsString::from("--allow"));
115                flags.push(OsString::from(lint));
116            }
117
118            Flag::Warn(lint) => {
119                flags.push(OsString::from("--warn"));
120                flags.push(OsString::from(lint));
121            }
122
123            Flag::ForceWarn(lint) => {
124                flags.push(OsString::from("--force-warn"));
125                flags.push(OsString::from(lint));
126            }
127
128            Flag::Deny(lint) => {
129                flags.push(OsString::from("--deny"));
130                flags.push(OsString::from(lint));
131            }
132
133            Flag::Forbid(lint) => {
134                flags.push(OsString::from("--forbid"));
135                flags.push(OsString::from(lint));
136            }
137
138            Flag::CapLints(lint_level) => {
139                flags.push(OsString::from("--cap-lints"));
140                flags.push(OsString::from(lint_level.to_string()));
141            }
142
143            Flag::Codegen { opt, value } => {
144                flags.push(OsString::from("-C"));
145                if let Some(value) = value {
146                    flags.push(OsString::from(format!("{}={}", opt, value)));
147                } else {
148                    flags.push(OsString::from(opt));
149                }
150            }
151
152            Flag::Version => {
153                flags.push(OsString::from("--version"));
154            }
155
156            Flag::Verbose => {
157                flags.push(OsString::from("--verbose"));
158            }
159
160            Flag::Extern { name, path } => {
161                flags.push(OsString::from("--extern"));
162                if let Some(path) = path {
163                    flags.push(kv(name, path));
164                } else {
165                    flags.push(OsString::from(name));
166                }
167            }
168
169            Flag::ExternLocation { name, location } => {
170                flags.push(OsString::from("--extern-location"));
171                flags.push(kv(name, location));
172            }
173
174            Flag::Sysroot(sysroot) => {
175                flags.push(OsString::from("--sysroot"));
176                flags.push(OsString::from(sysroot));
177            }
178
179            Flag::Z(flag) => {
180                flags.push(OsString::from("-Z"));
181                flags.push(OsString::from(flag));
182            }
183
184            Flag::ErrorFormat(error_format) => {
185                flags.push(OsString::from("--error-format"));
186                flags.push(OsString::from(error_format.to_string()));
187            }
188
189            Flag::Json(json) => {
190                flags.push(OsString::from("--json"));
191                flags.push(OsString::from(json));
192            }
193
194            Flag::Color(color) => {
195                flags.push(OsString::from("--color"));
196                flags.push(OsString::from(color.to_string()));
197            }
198
199            Flag::RemapPathPrefix { from, to } => {
200                flags.push(OsString::from("--remap-path-prefix"));
201                flags.push(kv(from, to));
202            }
203        }
204
205        iter::Iter {
206            items: flags.into_iter(),
207        }
208    }
209}
210
211fn kv(k: impl AsRef<OsStr>, v: impl AsRef<OsStr>) -> OsString {
212    let k = k.as_ref();
213    let v = v.as_ref();
214    let mut string = OsString::with_capacity(k.len() + 1 + v.len());
215    string.push(k);
216    string.push("=");
217    string.push(v);
218    string
219}
220
221mod iter {
222    use std::ffi::OsString;
223    use std::vec;
224
225    pub struct Iter {
226        pub(crate) items: vec::IntoIter<OsString>,
227    }
228
229    impl Iterator for Iter {
230        type Item = OsString;
231
232        fn next(&mut self) -> Option<Self::Item> {
233            self.items.next()
234        }
235    }
236}