syntax.ypp 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314
  1. // Part of the Carbon Language project, under the Apache License v2.0 with LLVM
  2. // Exceptions. See /LICENSE for license information.
  3. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  4. %code top {
  5. #include <algorithm>
  6. #include <cstdarg>
  7. #include <cstdio>
  8. #include <cstdlib>
  9. #include <iostream>
  10. #include <list>
  11. #include "executable_semantics/syntax_helpers.h"
  12. }
  13. %code requires {
  14. #include "executable_semantics/ast/declaration.h"
  15. #include "executable_semantics/ast/expression_or_field_list.h"
  16. #include "executable_semantics/ast/function_definition.h"
  17. }
  18. %code {
  19. extern int yylineno;
  20. extern int yylex();
  21. void yyerror(char* error) {
  22. Carbon::PrintSyntaxError(error, yylineno);
  23. }
  24. // void yyerror(char* error, ...);
  25. }
  26. %union {
  27. char* str;
  28. int num;
  29. Carbon::Expression* expression;
  30. std::list<std::pair<std::string, Carbon::Expression*>>* field_types;
  31. Carbon::Statement* statement;
  32. Carbon::Statement* statement_list;
  33. Carbon::FunctionDefinition* function_definition;
  34. Carbon::Declaration* declaration;
  35. std::list<Carbon::Declaration*>* declaration_list;
  36. Carbon::Member* member;
  37. std::list<Carbon::Member*>* member_list;
  38. Carbon::ExpOrFieldList* field_list;
  39. std::pair<std::string, Carbon::Expression*>* alternative;
  40. std::list<std::pair<std::string, Carbon::Expression*>>* alternative_list;
  41. std::pair<Carbon::Expression*, Carbon::Statement*>* clause;
  42. std::list<std::pair<Carbon::Expression*, Carbon::Statement*>>* clause_list;
  43. Carbon::Expression* fun_type;
  44. };
  45. %token <num> integer_literal
  46. %token <str> identifier
  47. %type <str> designator
  48. %type <declaration> declaration
  49. %type <function_definition> function_declaration
  50. %type <function_definition> function_definition
  51. %type <declaration_list> declaration_list
  52. %type <statement> statement
  53. %type <statement_list> statement_list
  54. %type <expression> expression
  55. %type <expression> pattern
  56. %type <expression> return_type
  57. %type <expression> tuple
  58. %type <member> member
  59. %type <member_list> member_list
  60. %type <field_list> field
  61. %type <field_list> field_list
  62. %type <alternative> alternative
  63. %type <alternative_list> alternative_list
  64. %type <clause> clause
  65. %type <clause_list> clause_list
  66. %token AND
  67. %token OR
  68. %token NOT
  69. %token INT
  70. %token BOOL
  71. %token TYPE
  72. %token FN
  73. %token FNTY
  74. %token ARROW
  75. %token VAR
  76. %token EQUAL
  77. %token IF
  78. %token ELSE
  79. %token WHILE
  80. %token BREAK
  81. %token CONTINUE
  82. %token RETURN
  83. %token TRUE
  84. %token FALSE
  85. %token STRUCT
  86. %token CHOICE
  87. %token MATCH
  88. %token CASE
  89. %token DBLARROW
  90. %token DEFAULT
  91. %token AUTO
  92. %nonassoc '{' '}'
  93. %nonassoc ':' ',' DBLARROW
  94. %left OR AND
  95. %nonassoc EQUAL NOT
  96. %left '+' '-'
  97. %left '.' ARROW
  98. %nonassoc '(' ')' '[' ']'
  99. %start input
  100. %locations
  101. %%
  102. input: declaration_list
  103. { Carbon::ExecProgram($1); }
  104. ;
  105. pattern:
  106. expression
  107. { $$ = $1; }
  108. ;
  109. expression:
  110. identifier
  111. { $$ = Carbon::MakeVar(yylineno, $1); }
  112. | expression designator
  113. { $$ = Carbon::MakeGetField(yylineno, $1, $2); }
  114. | expression '[' expression ']'
  115. { $$ = Carbon::MakeIndex(yylineno, $1, $3); }
  116. | expression ':' identifier
  117. { $$ = Carbon::MakeVarPat(yylineno, $3, $1); }
  118. | integer_literal
  119. { $$ = Carbon::MakeInt(yylineno, $1); }
  120. | TRUE
  121. { $$ = Carbon::MakeBool(yylineno, true); }
  122. | FALSE
  123. { $$ = Carbon::MakeBool(yylineno, false); }
  124. | INT
  125. { $$ = Carbon::MakeIntType(yylineno); }
  126. | BOOL
  127. { $$ = Carbon::MakeBoolType(yylineno); }
  128. | TYPE
  129. { $$ = Carbon::MakeTypeType(yylineno); }
  130. | AUTO
  131. { $$ = Carbon::MakeAutoType(yylineno); }
  132. | tuple { $$ = $1; }
  133. | expression EQUAL expression
  134. { $$ = Carbon::MakeBinOp(yylineno, Carbon::Operator::Eq, $1, $3); }
  135. | expression '+' expression
  136. { $$ = Carbon::MakeBinOp(yylineno, Carbon::Operator::Add, $1, $3); }
  137. | expression '-' expression
  138. { $$ = Carbon::MakeBinOp(yylineno, Carbon::Operator::Sub, $1, $3); }
  139. | expression AND expression
  140. { $$ = Carbon::MakeBinOp(yylineno, Carbon::Operator::And, $1, $3); }
  141. | expression OR expression
  142. { $$ = Carbon::MakeBinOp(yylineno, Carbon::Operator::Or, $1, $3); }
  143. | NOT expression
  144. { $$ = Carbon::MakeUnOp(yylineno, Carbon::Operator::Not, $2); }
  145. | '-' expression
  146. { $$ = Carbon::MakeUnOp(yylineno, Carbon::Operator::Neg, $2); }
  147. | expression tuple
  148. {
  149. if ($2->tag == Carbon::ExpressionKind::Tuple) {
  150. $$ = Carbon::MakeCall(yylineno, $1, $2);
  151. } else {
  152. auto vec =
  153. new std::vector<std::pair<std::string, Carbon::Expression*>>();
  154. vec->push_back(std::make_pair("", $2));
  155. $$ = Carbon::MakeCall(yylineno, $1, Carbon::MakeTuple(yylineno, vec));
  156. }
  157. }
  158. | FNTY tuple return_type
  159. { $$ = Carbon::MakeFunType(yylineno, $2, $3); }
  160. ;
  161. designator: '.' identifier { $$ = $2; }
  162. ;
  163. tuple: '(' field_list ')'
  164. {
  165. switch ($2->tag) {
  166. case Carbon::ExpOrFieldListKind::Exp:
  167. $$ = $2->u.exp;
  168. break;
  169. case Carbon::ExpOrFieldListKind::FieldList:
  170. auto vec = new std::vector<std::pair<std::string,Carbon::Expression*>>(
  171. $2->u.fields->begin(), $2->u.fields->end());
  172. $$ = Carbon::MakeTuple(yylineno, vec);
  173. break;
  174. }
  175. }
  176. ;
  177. field:
  178. pattern
  179. { $$ = Carbon::MakeExp($1); }
  180. | designator '=' pattern
  181. {
  182. auto fields =
  183. new std::list<std::pair<std::string, Carbon::Expression*>>();
  184. fields->push_back(std::make_pair($1, $3));
  185. $$ = Carbon::MakeFieldList(fields);
  186. }
  187. ;
  188. field_list:
  189. // Empty
  190. {
  191. $$ = Carbon::MakeFieldList(
  192. new std::list<std::pair<std::string, Carbon::Expression*>>());
  193. }
  194. | field
  195. { $$ = $1; }
  196. | field ',' field_list
  197. { $$ = Carbon::MakeConsField($1, $3); }
  198. ;
  199. clause:
  200. CASE pattern DBLARROW statement
  201. { $$ = new std::pair<Carbon::Expression*, Carbon::Statement*>($2, $4); }
  202. | DEFAULT DBLARROW statement
  203. {
  204. auto vp = Carbon::MakeVarPat(yylineno, "_",
  205. Carbon::MakeAutoType(yylineno));
  206. $$ = new std::pair<Carbon::Expression*, Carbon::Statement*>(vp, $3);
  207. }
  208. ;
  209. clause_list:
  210. // Empty
  211. {
  212. $$ = new std::list<std::pair<Carbon::Expression*, Carbon::Statement*>>();
  213. }
  214. | clause clause_list
  215. { $$ = $2; $$->push_front(*$1); }
  216. ;
  217. statement:
  218. expression '=' expression ';'
  219. { $$ = Carbon::MakeAssign(yylineno, $1, $3); }
  220. | VAR pattern '=' expression ';'
  221. { $$ = Carbon::MakeVarDef(yylineno, $2, $4); }
  222. | expression ';'
  223. { $$ = Carbon::MakeExpStmt(yylineno, $1); }
  224. | IF '(' expression ')' statement ELSE statement
  225. { $$ = Carbon::MakeIf(yylineno, $3, $5, $7); }
  226. | WHILE '(' expression ')' statement
  227. { $$ = Carbon::MakeWhile(yylineno, $3, $5); }
  228. | BREAK ';'
  229. { $$ = Carbon::MakeBreak(yylineno); }
  230. | CONTINUE ';'
  231. { $$ = Carbon::MakeContinue(yylineno); }
  232. | RETURN expression ';'
  233. { $$ = Carbon::MakeReturn(yylineno, $2); }
  234. | '{' statement_list '}'
  235. { $$ = Carbon::MakeBlock(yylineno, $2); }
  236. | MATCH '(' expression ')' '{' clause_list '}'
  237. { $$ = Carbon::MakeMatch(yylineno, $3, $6); }
  238. ;
  239. statement_list:
  240. // Empty
  241. { $$ = 0; }
  242. | statement statement_list
  243. { $$ = Carbon::MakeSeq(yylineno, $1, $2); }
  244. ;
  245. return_type:
  246. // Empty
  247. {
  248. $$ = Carbon::MakeTuple(
  249. yylineno,
  250. new std::vector<std::pair<std::string, Carbon::Expression*>>());
  251. }
  252. | ARROW expression
  253. { $$ = $2; }
  254. ;
  255. function_definition:
  256. FN identifier tuple return_type '{' statement_list '}'
  257. { $$ = MakeFunDef(yylineno, $2, $4, $3, $6); }
  258. | FN identifier tuple DBLARROW expression ';'
  259. {
  260. $$ = Carbon::MakeFunDef(yylineno, $2, Carbon::MakeAutoType(yylineno), $3,
  261. Carbon::MakeReturn(yylineno, $5));
  262. }
  263. ;
  264. function_declaration:
  265. FN identifier tuple return_type ';'
  266. { $$ = MakeFunDef(yylineno, $2, $4, $3, 0); }
  267. ;
  268. member:
  269. VAR expression ':' identifier ';'
  270. { $$ = MakeField(yylineno, $4, $2); }
  271. ;
  272. member_list:
  273. // Empty
  274. { $$ = new std::list<Carbon::Member*>(); }
  275. | member member_list
  276. { $$ = $2; $$->push_front($1); }
  277. ;
  278. alternative:
  279. identifier tuple ';'
  280. { $$ = new std::pair<std::string, Carbon::Expression*>($1, $2); }
  281. ;
  282. alternative_list:
  283. // Empty
  284. { $$ = new std::list<std::pair<std::string, Carbon::Expression*>>(); }
  285. | alternative alternative_list
  286. { $$ = $2; $$->push_front(*$1); }
  287. ;
  288. declaration:
  289. function_definition
  290. { $$ = Carbon::MakeFunDecl($1); }
  291. | function_declaration
  292. { $$ = Carbon::MakeFunDecl($1); }
  293. | STRUCT identifier '{' member_list '}'
  294. { $$ = Carbon::MakeStructDecl(yylineno, $2, $4); }
  295. | CHOICE identifier '{' alternative_list '}'
  296. { $$ = Carbon::MakeChoiceDecl(yylineno, $2, $4); }
  297. ;
  298. declaration_list:
  299. // Empty
  300. { $$ = new std::list<Carbon::Declaration*>(); }
  301. | declaration declaration_list
  302. {
  303. $$ = $2;
  304. $$->push_front($1);
  305. }
  306. ;
  307. %%