1use std::str::FromStr;
2
3use crate::{
4 error::Error,
5 lexer::{Lexer, Token, TokenIterator},
6 syntax::*,
7};
8
9use lalrpop_util::lalrpop_mod;
10
11lalrpop_mod!(
12 #[allow(clippy::all, reason = "generated code")]
13 wgsl
14);
15lalrpop_mod!(
16 #[allow(clippy::all, reason = "generated code")]
17 wgsl_recognize
18);
19
20pub use crate::parser_support::ParseEntryPoint;
21use wgsl::EntryPointParser;
22
23macro_rules! parse {
24 ($source:expr, $token:ident, $entrypoint:ident) => {{
25 match parse_tokens(Lexer::new($source), Token::$token) {
26 Ok(ParseEntryPoint::$entrypoint(res)) => Ok(res),
27 Ok(_) => unreachable!("parser parsed the wrong entrypoint"),
28 Err(e) => Err(e),
29 }
30 }};
31}
32
33pub fn parse_tokens(
40 lexer: impl TokenIterator,
41 entrypoint: Token,
42) -> Result<ParseEntryPoint, Error> {
43 let lexer = std::iter::once(Ok((0, entrypoint, 0))).chain(lexer);
44 let parser = EntryPointParser::new();
45 parser.parse(lexer).map_err(Into::into)
46}
47
48pub fn parse_str(source: &str) -> Result<TranslationUnit, Error> {
52 parse!(source, EntryPointTranslationUnit, TranslationUnit)
53}
54
55pub fn recognize_str(source: &str) -> Result<(), Error> {
59 let lexer = Lexer::new(source);
60 let parser = wgsl_recognize::TranslationUnitParser::new();
61 parser.parse(lexer).map_err(Into::into)
62}
63
64pub fn recognize_template_list(lexer: impl TokenIterator) -> Result<(), Error> {
65 match parse_tokens(lexer, Token::EntryPointTryTemplateList) {
66 Ok(ParseEntryPoint::TryTemplateList(_)) => Ok(()),
67 Ok(_) => unreachable!("parser parsed the wrong entrypoint"),
68 Err(e) => Err(e),
69 }
70}
71
72impl FromStr for TranslationUnit {
73 type Err = Error;
74
75 fn from_str(source: &str) -> Result<Self, Self::Err> {
76 parse!(source, EntryPointTranslationUnit, TranslationUnit)
77 }
78}
79impl FromStr for GlobalDirective {
80 type Err = Error;
81
82 fn from_str(source: &str) -> Result<Self, Self::Err> {
83 parse!(source, EntryPointGlobalDirective, GlobalDirective)
84 }
85}
86impl FromStr for GlobalDeclaration {
87 type Err = Error;
88
89 fn from_str(source: &str) -> Result<Self, Self::Err> {
90 parse!(source, EntryPointGlobalDecl, GlobalDecl)
91 }
92}
93impl FromStr for Statement {
94 type Err = Error;
95
96 fn from_str(source: &str) -> Result<Self, Self::Err> {
97 parse!(source, EntryPointStatement, Statement)
98 }
99}
100impl FromStr for Expression {
101 type Err = Error;
102
103 fn from_str(source: &str) -> Result<Self, Self::Err> {
104 parse!(source, EntryPointExpression, Expression)
105 }
106}
107impl FromStr for LiteralExpression {
108 type Err = Error;
109
110 fn from_str(source: &str) -> Result<Self, Self::Err> {
111 parse!(source, EntryPointLiteral, Literal)
112 }
113}
114#[cfg(feature = "imports")]
115impl FromStr for crate::syntax::ImportStatement {
116 type Err = Error;
117
118 fn from_str(source: &str) -> Result<Self, Self::Err> {
119 parse!(source, EntryPointImportStatement, ImportStatement)
120 }
121}