1use serde::{Deserialize, Serialize};
23pub use crate::extensions::heredoc_ast::HereDocInfo;
24
25#[derive(Debug, Clone, Serialize, Deserialize)]
27pub struct ZshProgram {
28 pub lists: Vec<ZshList>,
29}
30
31#[derive(Debug, Clone, Serialize, Deserialize)]
33pub struct ZshList {
34 pub sublist: ZshSublist,
35 pub flags: ListFlags,
36}
37
38#[derive(Debug, Clone, Copy, Default, Serialize, Deserialize)]
39pub struct ListFlags {
40 pub async_: bool,
42 pub disown: bool,
44}
45
46#[derive(Debug, Clone, Serialize, Deserialize)]
48pub struct ZshSublist {
49 pub pipe: ZshPipe,
50 pub next: Option<(SublistOp, Box<ZshSublist>)>,
51 pub flags: SublistFlags,
52}
53
54#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
55pub enum SublistOp {
56 And, Or, }
59
60#[derive(Debug, Clone, Copy, Default, Serialize, Deserialize)]
61pub struct SublistFlags {
62 pub coproc: bool,
64 pub not: bool,
66}
67
68#[derive(Debug, Clone, Serialize, Deserialize)]
70pub struct ZshPipe {
71 pub cmd: ZshCommand,
72 pub next: Option<Box<ZshPipe>>,
73 pub lineno: u64,
74 #[serde(default)]
78 pub merge_stderr: bool,
79}
80
81#[derive(Debug, Clone, Serialize, Deserialize)]
83pub enum ZshCommand {
84 Simple(ZshSimple),
85 Subsh(Box<ZshProgram>), Cursh(Box<ZshProgram>), For(ZshFor),
88 Case(ZshCase),
89 If(ZshIf),
90 While(ZshWhile),
91 Until(ZshWhile),
92 Repeat(ZshRepeat),
93 FuncDef(ZshFuncDef),
94 Time(Option<Box<ZshSublist>>),
95 Cond(ZshCond), Arith(String), Try(ZshTry), Redirected(Box<ZshCommand>, Vec<ZshRedir>),
103}
104
105#[derive(Debug, Clone, Serialize, Deserialize)]
107pub struct ZshSimple {
108 pub assigns: Vec<ZshAssign>,
109 pub words: Vec<String>,
110 pub redirs: Vec<ZshRedir>,
111}
112
113#[derive(Debug, Clone, Serialize, Deserialize)]
115pub struct ZshAssign {
116 pub name: String,
117 pub value: ZshAssignValue,
118 pub append: bool, }
120
121#[derive(Debug, Clone, Serialize, Deserialize)]
122pub enum ZshAssignValue {
123 Scalar(String),
124 Array(Vec<String>),
125}
126
127#[derive(Debug, Clone, Serialize, Deserialize)]
129pub struct ZshRedir {
130 pub rtype: i32,
131 pub fd: i32,
132 pub name: String,
133 pub heredoc: Option<HereDocInfo>,
134 pub varid: Option<String>, #[serde(skip)]
140 pub heredoc_idx: Option<usize>,
141}
142
143#[derive(Debug, Clone, Serialize, Deserialize)]
145pub struct ZshFor {
146 pub var: String,
147 pub list: ForList,
148 pub body: Box<ZshProgram>,
149 #[serde(default)]
152 pub is_select: bool,
153}
154
155#[derive(Debug, Clone, Serialize, Deserialize)]
156pub enum ForList {
157 Words(Vec<String>),
158 CStyle {
159 init: String,
160 cond: String,
161 step: String,
162 },
163 Positional,
164}
165
166#[derive(Debug, Clone, Serialize, Deserialize)]
168pub struct ZshCase {
169 pub word: String,
170 pub arms: Vec<CaseArm>,
171}
172
173#[derive(Debug, Clone, Serialize, Deserialize)]
174pub struct CaseArm {
175 pub patterns: Vec<String>,
176 pub body: ZshProgram,
177 pub terminator: CaseTerm,
178}
179
180#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
181pub enum CaseTerm {
182 Break, Continue, TestNext, }
186
187#[derive(Debug, Clone, Serialize, Deserialize)]
189pub struct ZshIf {
190 pub cond: Box<ZshProgram>,
191 pub then: Box<ZshProgram>,
192 pub elif: Vec<(ZshProgram, ZshProgram)>,
193 pub else_: Option<Box<ZshProgram>>,
194}
195
196#[derive(Debug, Clone, Serialize, Deserialize)]
198pub struct ZshWhile {
199 pub cond: Box<ZshProgram>,
200 pub body: Box<ZshProgram>,
201 pub until: bool,
202}
203
204#[derive(Debug, Clone, Serialize, Deserialize)]
206pub struct ZshRepeat {
207 pub count: String,
208 pub body: Box<ZshProgram>,
209}
210
211#[derive(Debug, Clone, Serialize, Deserialize)]
213pub struct ZshFuncDef {
214 pub names: Vec<String>,
215 pub body: Box<ZshProgram>,
216 pub tracing: bool,
217 #[serde(default)]
222 pub auto_call_args: Option<Vec<String>>,
223 #[serde(default)]
231 pub body_source: Option<String>,
232}
233
234#[derive(Debug, Clone, Serialize, Deserialize)]
236pub enum ZshCond {
237 Not(Box<ZshCond>),
238 And(Box<ZshCond>, Box<ZshCond>),
239 Or(Box<ZshCond>, Box<ZshCond>),
240 Unary(String, String), Binary(String, String, String), Regex(String, String), }
244
245#[derive(Debug, Clone, Serialize, Deserialize)]
247pub struct ZshTry {
248 pub try_block: Box<ZshProgram>,
249 pub always: Box<ZshProgram>,
250}
251
252#[derive(Debug, Clone, Serialize, Deserialize)]
254pub enum ZshParamFlag {
255 Lower, Upper, Capitalize, Join(String), JoinNewline, Split(String), SplitLines, SplitWords, Type, Words, Quote, QuoteIfNeeded, DoubleQuote, DollarQuote, QuoteBackslash, Unique, Reverse, Sort, NumericSort, IndexSort, Keys, Values, Length, CountChars, Expand, PromptExpand, PromptExpandFull, Visible, Directory, Head(usize), Tail(usize), PadLeft(usize, char), PadRight(usize, char), Width(usize), Match, Remove, Subscript, Parameter, Glob, At,
299}
300
301#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
303pub enum ListOp {
304 And, Or, Semi, Amp, Newline, }
310
311#[derive(Debug, Clone, Serialize, Deserialize)]
313pub enum ShellWord {
314 Literal(String),
318 Concat(Vec<ShellWord>),
322}
323
324#[derive(Debug, Clone, Serialize, Deserialize)]
326pub enum VarModifier {
327 Default(ShellWord),
328 DefaultAssign(ShellWord),
329 Error(ShellWord),
330 Alternate(ShellWord),
331 Length,
332 Substring(i64, Option<i64>),
333 RemovePrefix(ShellWord),
334 RemovePrefixLong(ShellWord),
335 RemoveSuffix(ShellWord),
336 RemoveSuffixLong(ShellWord),
337 Replace(ShellWord, ShellWord),
338 ReplaceAll(ShellWord, ShellWord),
339 ReplacePrefix(ShellWord, ShellWord),
342 ReplaceSuffix(ShellWord, ShellWord),
345 Upper,
346 Lower,
347}
348
349#[derive(Debug, Clone, Serialize, Deserialize)]
351pub enum ShellCommand {
352 Simple(SimpleCommand),
353 Pipeline(Vec<ShellCommand>, bool),
354 List(Vec<(ShellCommand, ListOp)>),
355 Compound(CompoundCommand),
356 FunctionDef(String, Box<ShellCommand>),
357}
358
359#[derive(Debug, Clone, Serialize, Deserialize)]
361pub struct SimpleCommand {
362 pub assignments: Vec<(String, ShellWord, bool)>,
363 pub words: Vec<ShellWord>,
364 pub redirects: Vec<Redirect>,
365}
366
367#[derive(Debug, Clone, Serialize, Deserialize)]
369pub struct Redirect {
370 pub fd: Option<i32>,
371 pub op: RedirectOp,
372 pub target: ShellWord,
373 pub heredoc_content: Option<String>,
374 pub fd_var: Option<String>,
375}
376
377#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
379pub enum RedirectOp {
380 Write,
381 Append,
382 Read,
383 ReadWrite,
384 Clobber,
385 DupRead,
386 DupWrite,
387 HereDoc,
388 HereString,
389 WriteBoth,
390 AppendBoth,
391}
392
393#[derive(Debug, Clone, Serialize, Deserialize)]
395pub enum CompoundCommand {
396 BraceGroup(Vec<ShellCommand>),
397 Subshell(Vec<ShellCommand>),
398 If {
399 conditions: Vec<(Vec<ShellCommand>, Vec<ShellCommand>)>,
400 else_part: Option<Vec<ShellCommand>>,
401 },
402 For {
403 var: String,
404 words: Option<Vec<ShellWord>>,
405 body: Vec<ShellCommand>,
406 },
407 ForArith {
408 init: String,
409 cond: String,
410 step: String,
411 body: Vec<ShellCommand>,
412 },
413 While {
414 condition: Vec<ShellCommand>,
415 body: Vec<ShellCommand>,
416 },
417 Until {
418 condition: Vec<ShellCommand>,
419 body: Vec<ShellCommand>,
420 },
421 Case {
422 word: ShellWord,
423 cases: Vec<(Vec<ShellWord>, Vec<ShellCommand>, CaseTerminator)>,
424 },
425 Select {
426 var: String,
427 words: Option<Vec<ShellWord>>,
428 body: Vec<ShellCommand>,
429 },
430 Coproc {
431 name: Option<String>,
432 body: Box<ShellCommand>,
433 },
434 Repeat {
436 count: String,
437 body: Vec<ShellCommand>,
438 },
439 Try {
441 try_body: Vec<ShellCommand>,
442 always_body: Vec<ShellCommand>,
443 },
444 Arith(String),
445 WithRedirects(Box<ShellCommand>, Vec<Redirect>),
446}
447
448#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
450pub enum CaseTerminator {
451 Break,
452 Fallthrough,
453 Continue,
454}