From 9b358efea13017f3e033acce9c4a2c6c947d9a4d Mon Sep 17 00:00:00 2001 From: Dzmitry Malyshau Date: Thu, 11 Feb 2021 16:41:09 -0500 Subject: [PATCH] [wgsl] support 'elseif' construct --- src/front/wgsl/mod.rs | 20 +++++++++++++++++++- src/front/wgsl/tests.rs | 5 +++++ 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/src/front/wgsl/mod.rs b/src/front/wgsl/mod.rs index 38aaf4095b..c2bb94e922 100644 --- a/src/front/wgsl/mod.rs +++ b/src/front/wgsl/mod.rs @@ -1669,11 +1669,29 @@ impl Parser { lexer.expect(Token::Paren(')'))?; let accept = self.parse_block(lexer, context.reborrow(), false)?; - let reject = if lexer.skip(Token::Word("else")) { + let mut elsif_stack = Vec::new(); + while lexer.skip(Token::Word("elseif")) { + lexer.expect(Token::Paren('('))?; + let other_condition = + self.parse_general_expression(lexer, context.as_expression())?; + lexer.expect(Token::Paren(')'))?; + let other_block = self.parse_block(lexer, context.reborrow(), false)?; + elsif_stack.push((other_condition, other_block)); + } + let mut reject = if lexer.skip(Token::Word("else")) { self.parse_block(lexer, context.reborrow(), false)? } else { Vec::new() }; + // reverse-fold the else-if blocks + //Note: we may consider uplifting this to the IR + for (other_cond, other_block) in elsif_stack.drain(..).rev() { + reject = vec![crate::Statement::If { + condition: other_cond, + accept: other_block, + reject, + }]; + } Some(crate::Statement::If { condition, diff --git a/src/front/wgsl/tests.rs b/src/front/wgsl/tests.rs index c0408415e1..4fdfc1088b 100644 --- a/src/front/wgsl/tests.rs +++ b/src/front/wgsl/tests.rs @@ -104,6 +104,11 @@ fn parse_if() { discard; } else {} if (0 != 1) {} + if (false) { + return; + } elseif (true) { + return; + } else {} } ", )