Add syntax for package and library (#792)

Doesn't add much logic, only takes advantage of parser structure for the ordering enforcement.

Note import_nonexistent tests should probably fail, but writing import tests needs a chain of functionality, and I figured I'd just start adding some to validate the syntax (not adding existent imports because that'd require multi-file structure).
This commit is contained in:
Jon Meow
2021-09-02 16:01:15 -07:00
committed by GitHub
parent 0980df65cd
commit a03536a196
152 changed files with 433 additions and 63 deletions
+1
View File
@@ -37,6 +37,7 @@ cc_library(
"//common:check",
"//common:ostream",
"//common:string_helpers",
"//executable_semantics/ast",
"//executable_semantics/ast:declaration",
"//executable_semantics/ast:expression",
"//executable_semantics/ast:paren_contents",
+10
View File
@@ -30,6 +30,7 @@ SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
/* Table begin. */
AND "and"
API "api"
ARROW "->"
AUTO "auto"
AWAIT "__await"
@@ -53,13 +54,17 @@ FALSE "false"
FN "fn"
FNTY "fnty"
IF "if"
IMPL "impl"
IMPORT "import"
LEFT_CURLY_BRACE "{"
LEFT_PARENTHESIS "("
LEFT_SQUARE_BRACKET "["
LIBRARY "library"
MATCH "match"
MINUS "-"
NOT "not"
OR "or"
PACKAGE "package"
PERIOD "."
PLUS "+"
RETURN "return"
@@ -119,6 +124,7 @@ string_literal \"([^\\\"\n\v\f\r]|\\.)*\"
/* Table begin. */
{AND} { return SIMPLE_TOKEN(AND); }
{API} { return SIMPLE_TOKEN(API); }
{ARROW} { return SIMPLE_TOKEN(ARROW); }
{AUTO} { return SIMPLE_TOKEN(AUTO); }
{AWAIT} { return SIMPLE_TOKEN(AWAIT); }
@@ -142,13 +148,17 @@ string_literal \"([^\\\"\n\v\f\r]|\\.)*\"
{FNTY} { return SIMPLE_TOKEN(FNTY); }
{FN} { return SIMPLE_TOKEN(FN); }
{IF} { return SIMPLE_TOKEN(IF); }
{IMPL} { return SIMPLE_TOKEN(IMPL); }
{IMPORT} { return SIMPLE_TOKEN(IMPORT); }
{LEFT_PARENTHESIS} { return SIMPLE_TOKEN(LEFT_PARENTHESIS); }
{LEFT_CURLY_BRACE} { return SIMPLE_TOKEN(LEFT_CURLY_BRACE); }
{LEFT_SQUARE_BRACKET} { return SIMPLE_TOKEN(LEFT_SQUARE_BRACKET); }
{LIBRARY} { return SIMPLE_TOKEN(LIBRARY); }
{MATCH} { return SIMPLE_TOKEN(MATCH); }
{MINUS} { return SIMPLE_TOKEN(MINUS); }
{NOT} { return SIMPLE_TOKEN(NOT); }
{OR} { return SIMPLE_TOKEN(OR); }
{PACKAGE} { return SIMPLE_TOKEN(PACKAGE); }
{PERIOD} { return SIMPLE_TOKEN(PERIOD); }
{PLUS} { return SIMPLE_TOKEN(PLUS); }
{RETURN} { return SIMPLE_TOKEN(RETURN); }
+1 -1
View File
@@ -8,7 +8,7 @@
#include <string>
#include <variant>
#include "executable_semantics/ast/abstract_syntax_tree.h"
#include "executable_semantics/ast/ast.h"
namespace Carbon {
@@ -7,7 +7,7 @@
#include <variant>
#include "executable_semantics/ast/abstract_syntax_tree.h"
#include "executable_semantics/ast/ast.h"
#include "executable_semantics/syntax/parser.h" // from parser.ypp
namespace Carbon {
+47 -3
View File
@@ -65,7 +65,7 @@
%code requires {
#include <optional>
#include "executable_semantics/ast/abstract_syntax_tree.h"
#include "executable_semantics/ast/ast.h"
#include "executable_semantics/ast/declaration.h"
#include "executable_semantics/ast/expression.h"
#include "executable_semantics/ast/function_definition.h"
@@ -93,6 +93,11 @@
%token <std::string> sized_type_literal
%token <std::string> string_literal
%type <std::string> designator
%type <std::pair<LibraryName, bool>> package_directive
%type <LibraryName> import_directive
%type <std::vector<LibraryName>> import_directives
%type <std::string> optional_library_path
%type <bool> api_or_impl
%type <BisonWrap<Ptr<const Declaration>>> declaration
%type <BisonWrap<Ptr<const FunctionDefinition>>> function_declaration
%type <BisonWrap<Ptr<const FunctionDefinition>>> function_definition
@@ -133,6 +138,7 @@
%token
// Most tokens have their spelling defined in lexer.lpp.
AND
API
ARROW
AUTO
AWAIT
@@ -156,13 +162,17 @@
FN
FNTY
IF
IMPL
IMPORT
LEFT_CURLY_BRACE
LEFT_PARENTHESIS
LEFT_SQUARE_BRACKET
LIBRARY
MATCH
MINUS
NOT
OR
PACKAGE
PERIOD
PLUS
RETURN
@@ -217,8 +227,42 @@
%start input
%%
input: declaration_list
{ parsed_program = $1; }
input: package_directive import_directives declaration_list
{
parsed_program = AST({.package = $1.first,
.is_api = $1.second,
.imports = std::move($2),
.declarations = std::move($3)});
}
;
package_directive:
PACKAGE identifier optional_library_path api_or_impl SEMICOLON
{ $$ = {LibraryName({.package = $2, .path = $3}), $4}; }
;
import_directive:
IMPORT identifier optional_library_path SEMICOLON
{ $$ = LibraryName({.package = $2, .path = $3}); }
;
import_directives:
// Empty
{ $$ = std::vector<LibraryName>(); }
| import_directives import_directive
{
$$ = std::move($1);
$$.push_back($2);
}
;
optional_library_path:
// Empty
{ $$ = ""; }
| LIBRARY string_literal
{ $$ = $2; }
;
api_or_impl:
API
{ $$ = true; }
| IMPL
{ $$ = false; }
;
expression:
identifier