Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactoring to environment #86

Merged
merged 30 commits into from
Feb 9, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
1ef9ae0
Merge pull request #85 from melt-umn/develop
krame505 Oct 25, 2017
afc9b29
Merge branch 'develop'
krame505 Oct 26, 2017
166f22d
Refactor Scope into something more generally useful
krame505 Oct 29, 2017
bf8a37b
Adding file that I forgot to commit
krame505 Oct 29, 2017
6b52a7e
Get failing tutorial to compile
krame505 Oct 30, 2017
79b577a
Bug fix: check that a name actually is a value in declRefExpr
krame505 Oct 30, 2017
61910e7
Closing item nonterminals
krame505 Oct 30, 2017
e095d66
Tweak to forward flowtype on Name
krame505 Oct 31, 2017
6509532
Fix long-standing bug with broken argument counts in error messages
krame505 Nov 1, 2017
f8fbc93
Begin work on splitting out seperate label env, lots of flow errors r…
krame505 Nov 10, 2017
d038332
Fix most flow errors
krame505 Nov 10, 2017
443ed7e
Try to fix flow errors?
krame505 Nov 10, 2017
7c81dd5
Fix flow errors, keeping circular dependancy for now
krame505 Nov 10, 2017
28de0ac
Rename isItemTypedef -> isItemType
krame505 Nov 11, 2017
557242a
Remove flow dependancy for labelDefs on reference set
krame505 Nov 11, 2017
1d4ddc5
Delete redefinition of host in substitution grammar that was probably…
krame505 Dec 4, 2017
968777d
Remove unneeded semicolon in declStmt pp, causing problems for old ve…
krame505 Dec 5, 2017
dd15ffb
Re-merge labelEnv into env
krame505 Dec 28, 2017
76cf957
Refactoring
krame505 Dec 28, 2017
aba2134
Fix missed compilation error
krame505 Dec 28, 2017
9a3832f
Get tutorials to compile
krame505 Dec 28, 2017
9aa75fd
Delete outdated comment
krame505 Dec 28, 2017
9189da9
Update tutorial section on functionDefs
krame505 Dec 28, 2017
398234f
Print label and misc namespaces for debugging
krame505 Dec 28, 2017
ae67177
Fix typos in comments
krame505 Feb 2, 2018
c2f1e1c
Bug fix: Substitute expressions into direct function calls
krame505 Feb 2, 2018
f69d181
Fix minor bug
krame505 Feb 2, 2018
febff5a
Workaround for bug with builtin functions
krame505 Feb 8, 2018
7451560
Refactor parsing construction helper driver functions
krame505 Feb 8, 2018
e599ee4
Add a comment
krame505 Feb 9, 2018
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ imports edu:umn:cs:melt:ableC:abstractsyntax:env;

-- The environment used at the top-level.
global initialEnv :: Decorated Env =
openScope(
openScopeEnv(
addEnv(getInitialEnvDefs(),
emptyEnv()));

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,46 +42,7 @@ parser exprParser :: cst:Expr_c {
}

-- Wrapper functions to call parsers and return asts
function parseDecls
Decls ::= text::String
{
local result::ParseResult<cst:TranslationUnit_c> =
declsParser(text, s"parseDecls(\"\"\"\n${foldLineNums(text)}\n\"\"\")");
return
if result.parseSuccess
then foldDecl(result.parseTree.ast)
else error("Syntax errors in parseDecls string:\n" ++ result.parseErrors);
}

function parseDecl
Decl ::= text::String
{
local result::ParseResult<cst:ExternalDeclaration_c> =
declParser(text, s"parseDecl(\"\"\"\n${foldLineNums(text)}\n\"\"\")");
return
if result.parseSuccess
then result.parseTree.ast
else error("Syntax errors in parseDecl string:\n" ++ result.parseErrors);
}

function parseStmt
Stmt ::= text::String
{
local result::ParseResult<cst:BlockItemList_c> =
stmtParser(text, s"parseStmt(\"\"\"\n${foldLineNums(text)}\n\"\"\")");
return
if result.parseSuccess
then foldStmt(result.parseTree.ast)
else error("Syntax errors in parseStmt string:\n" ++ result.parseErrors);
}

function parseExpr
Expr ::= text::String
{
local result::ParseResult<cst:Expr_c> =
exprParser(text, s"parseExpr(\"\"\"\n${foldLineNums(text)}\n\"\"\")");
return
if result.parseSuccess
then result.parseTree.ast
else error("Syntax errors in parseExpr string:\n" ++ result.parseErrors);
}
global parseDecls::(Decls ::= String) = \ text::String -> foldDecl(parseInline("Decls", declsParser, text).ast);
global parseDecl::(Decl ::= String) = \ text::String -> parseInline("Decl", declParser, text).ast;
global parseStmt::(Stmt ::= String) = \ text::String -> foldStmt(parseInline("Stmt", stmtParser, text).ast);
global parseExpr::(Expr ::= String) = \ text::String -> parseInline("Expr", exprParser, text).ast;
Original file line number Diff line number Diff line change
@@ -1,5 +1,16 @@
grammar edu:umn:cs:melt:ableC:abstractsyntax:construction:parsing;

function parseInline
a ::= nt::String parser::(ParseResult<a> ::= String String) text::String
{
local result::ParseResult<a> =
parser(text, s"parse${nt}(\"\"\"\n${foldLineNums(text)}\n\"\"\")");
return
if result.parseSuccess
then result.parseTree
else error("Syntax errors in parse${nt} string:\n" ++ result.parseErrors);
}

-- TODO: Maybe these belong in core or langutil?
function padRight
String ::= len::Integer s::String
Expand All @@ -16,4 +27,4 @@ String ::= text::String
local lineNums::[Integer] = 1 :: map(\i::Integer -> i + 1, lineNums); -- Lazyness is awesome.
local lines::[String] = explode("\n", text);
return implode("\n", zipWith(\lineNum::Integer line::String -> padRight(3, toString(lineNum)) ++ line, lineNums, lines));
}
}
1 change: 0 additions & 1 deletion edu.umn.cs.melt.ableC/abstractsyntax/env/Def.sv
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
grammar edu:umn:cs:melt:ableC:abstractsyntax:env;


abstract production labelDef
top::Def ::= s::String l::LabelItem
{
Expand Down
42 changes: 17 additions & 25 deletions edu.umn.cs.melt.ableC/abstractsyntax/env/Env.sv
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
grammar edu:umn:cs:melt:ableC:abstractsyntax:env;

imports edu:umn:cs:melt:ableC:abstractsyntax:host;
imports silver:util:raw:treemap as tm;

{--
- The environment values that get passed around and used to look up names.
Expand Down Expand Up @@ -34,9 +33,10 @@ closed nonterminal Def
synthesized attribute defs :: [Def] with ++;
{--
- For Function-Scope definitions (e.g. Labels in functions)
- @see defs for normal definitions
- Note that since the env may determine the forward, and functionDefs on a production determine the env provided to that
- production, functionDefs must be computed without using the forward.
-}
synthesized attribute functiondefs :: [Def] with ++;
synthesized attribute functionDefs :: [Def] with ++;
{--
- For local-scope only definitions (e.g. struct and union fields)
- Used in conjunction with 'tagEnv'.
Expand All @@ -46,7 +46,7 @@ synthesized attribute functiondefs :: [Def] with ++;
-
- @see defs for normal definitions
-}
synthesized attribute localdefs :: [Def] with ++;
synthesized attribute localDefs :: [Def] with ++;
{--
- The environment, on which all lookups are performed.
-}
Expand All @@ -56,14 +56,18 @@ autocopy attribute env :: Decorated Env;
-}
synthesized attribute tagEnv :: Decorated Env;


-- Environment manipulation functions

function emptyEnv
Decorated Env ::=
{
return decorate emptyEnv_i() with {};
}
function openScopeEnv
Decorated Env ::= e::Decorated Env
{
return decorate openScopeEnv_i(e) with {};
}
function addEnv
Decorated Env ::= d::[Def] e::Decorated Env
{
Expand All @@ -74,11 +78,6 @@ Decorated Env ::= d::Defs e::Decorated Env
{
return decorate addEnv_i(d, e) with {};
}
function openScope
Decorated Env ::= e::Decorated Env
{
return decorate openScope_i(e) with {};
}
function globalEnv
Decorated Env ::= e::Decorated Env
{
Expand All @@ -90,50 +89,43 @@ Decorated Env ::= e::Decorated Env
function lookupValue
[ValueItem] ::= n::String e::Decorated Env
{
return readScope_i(n, e.values);
return lookupScope(n, e.values);
}
function lookupTag
[TagItem] ::= n::String e::Decorated Env
{
return readScope_i(n, e.tags);
return lookupScope(n, e.tags);
}
function lookupLabel
[LabelItem] ::= n::String e::Decorated Env
{
return readScope_i(n, e.labels);
return lookupScope(n, e.labels);
}
function lookupRefId
[RefIdItem] ::= n::String e::Decorated Env
{
return readScope_i(n, e.refIds);
return lookupScope(n, e.refIds);
}

function lookupMisc
[MiscItem] ::= n::String e::Decorated Env
{
return readScope_i(n, e.misc);
return lookupScope(n, e.misc);
}


function lookupValueInLocalScope
[ValueItem] ::= n::String e::Decorated Env
{
return tm:lookup(n, head(e.values));
return lookupInLocalScope(n, e.values);
}
function lookupTagInLocalScope
[TagItem] ::= n::String e::Decorated Env
{
return tm:lookup(n, head(e.tags));
}
function lookupLabelInLocalScope
[LabelItem] ::= n::String e::Decorated Env
{
return tm:lookup(n, head(e.labels));
return lookupInLocalScope(n, e.tags);
}

function lookupMiscInLocalScope
[MiscItem] ::= n::String e::Decorated Env
{
return tm:lookup(n, head(e.misc));
return lookupInLocalScope(n, e.misc);
}

92 changes: 30 additions & 62 deletions edu.umn.cs.melt.ableC/abstractsyntax/env/EnvPlumbing.sv
Original file line number Diff line number Diff line change
@@ -1,22 +1,17 @@
grammar edu:umn:cs:melt:ableC:abstractsyntax:env;

{-
- The enivronment in ableC is represented as a nonterminal which is used to build up various lists
- of 'scopes'. Each scope is a treemap that is used to look up a value. If the value is not
- found in the current scope, then the next one is tried, etc. The last scope represents the
- global level. This is to allow names in the environment to be shadowed by a name in a lower
- scope, while still preventing a name from being declared twice in the local scope.
- Contribs is just a list of items to add to a scope.
- The enivronment in ableC is represented as a nonterminal 'Env' which is used to build up various
- scopes, reperesenting the contents of each namespace.
- Contributions to an environment are represented as another nonterminal 'Defs', which is used to
- build up contributions to each individual scope in an Env.
-}

type Scope<a> = [tm:Map<String a>];
type Contribs<a> = [Pair<String a>];

synthesized attribute labels :: Scope<LabelItem>;
synthesized attribute tags :: Scope<TagItem>;
synthesized attribute values :: Scope<ValueItem>;
synthesized attribute refIds :: Scope<RefIdItem>;
synthesized attribute misc :: Scope<MiscItem>;
synthesized attribute labels :: Scopes<LabelItem>;
synthesized attribute tags :: Scopes<TagItem>;
synthesized attribute values :: Scopes<ValueItem>;
synthesized attribute refIds :: Scopes<RefIdItem>;
synthesized attribute misc :: Scopes<MiscItem>;
synthesized attribute globalEnv :: Decorated Env;

synthesized attribute labelContribs :: Contribs<LabelItem>;
Expand All @@ -26,33 +21,6 @@ synthesized attribute refIdContribs :: Contribs<RefIdItem>;
synthesized attribute miscContribs :: Contribs<MiscItem>;
synthesized attribute globalDefs :: [Def];

{-- Adds contributions to the innermost scope -}
function augmentScope_i
Scope<a> ::= d::Contribs<a> s::Scope<a>
{
return tm:add(d, head(s)) :: tail(s);
}
{-- Adds contributions to the outermost scope -}
function augmentGlobalScope_i
Scope<a> ::= d::Contribs<a> s::Scope<a>
{
return case d, s of
| [], _ -> s
| _, [_] -> augmentScope_i(d, s)
| _, h :: t -> h :: augmentGlobalScope_i(d, t)
end;
}
{-- Looks up an identifier in the closest scope that has a match -}
function readScope_i
[a] ::= name::String scope::Scope<a>
{
-- Laziness is awesome.
return case dropWhile(null, map(tm:lookup(name, _), scope)) of
| h :: _ -> h
| [] -> []
end;
}

{- Environment representation productions provide implementations for env functions
- emptyEnv_i creates the basic environment with empty global scopes
- addEnv_i adds provided defs to the current (first on list) scope, and global defs to the global (last on list) scope
Expand All @@ -63,40 +31,40 @@ function readScope_i
abstract production emptyEnv_i
top::Env ::=
{
top.labels = [tm:empty(compareString)];
top.tags = [tm:empty(compareString)];
top.values = [tm:empty(compareString)];
top.refIds = [tm:empty(compareString)];
top.misc = [tm:empty(compareString)];
top.labels = emptyScope();
top.tags = emptyScope();
top.values = emptyScope();
top.refIds = emptyScope();
top.misc = emptyScope();
}
abstract production addEnv_i
top::Env ::= d::Defs e::Decorated Env
{
production gd::Defs = foldr(consDefs, nilDefs(), d.globalDefs);

top.labels = augmentGlobalScope_i(gd.labelContribs, augmentScope_i(d.labelContribs, e.labels));
top.tags = augmentGlobalScope_i(gd.tagContribs, augmentScope_i(d.tagContribs, e.tags));
top.values = augmentGlobalScope_i(gd.valueContribs, augmentScope_i(d.valueContribs, e.values));
top.refIds = augmentGlobalScope_i(gd.refIdContribs, augmentScope_i(d.refIdContribs, e.refIds));
top.misc = augmentGlobalScope_i(gd.miscContribs, augmentScope_i(d.miscContribs, e.misc));
top.labels = addGlobalScope(gd.labelContribs, addScope(d.labelContribs, e.labels));
top.tags = addGlobalScope(gd.tagContribs, addScope(d.tagContribs, e.tags));
top.values = addGlobalScope(gd.valueContribs, addScope(d.valueContribs, e.values));
top.refIds = addGlobalScope(gd.refIdContribs, addScope(d.refIdContribs, e.refIds));
top.misc = addGlobalScope(gd.miscContribs, addScope(d.miscContribs, e.misc));
}
abstract production openScope_i
abstract production openScopeEnv_i
top::Env ::= e::Decorated Env
{
top.labels = tm:empty(compareString) :: e.labels;
top.tags = tm:empty(compareString) :: e.tags;
top.values = tm:empty(compareString) :: e.values;
top.refIds = tm:empty(compareString) :: e.refIds;
top.misc = tm:empty(compareString) :: e.misc;
top.labels = openScope(e.labels);
top.tags = openScope(e.tags);
top.values = openScope(e.values);
top.refIds = openScope(e.refIds);
top.misc = openScope(e.misc);
}
abstract production globalEnv_i
top::Env ::= e::Decorated Env
{
top.labels = [last(e.labels)];
top.tags = [last(e.tags)];
top.values = [last(e.values)];
top.refIds = [last(e.refIds)];
top.misc = [last(e.misc)];
top.labels = globalScope(e.labels);
top.tags = globalScope(e.tags);
top.values = globalScope(e.values);
top.refIds = globalScope(e.refIds);
top.misc = globalScope(e.misc);
}

{- Definition list productions provide a way of folding up defs into Contribs lists
Expand Down
12 changes: 7 additions & 5 deletions edu.umn.cs.melt.ableC/abstractsyntax/env/LabelItem.sv
Original file line number Diff line number Diff line change
@@ -1,17 +1,19 @@
grammar edu:umn:cs:melt:ableC:abstractsyntax:env;

nonterminal LabelItem;

-- TODO: Should consider whether we want to change the Stmt abstract syntax
-- to have a LabelStmt, so we can be more specific here
nonterminal LabelItem with sourceLocation;

-- Note that we unfortunately can't include a reference to the labeled statement here, since these
-- are function-scope defs, which need to be computed without the use of env to avoid a circular
-- dependancy.
abstract production labelItem
top::LabelItem ::= s::Decorated Stmt
top::LabelItem ::= sourceLocation::Location
{
top.sourceLocation = sourceLocation;
}

abstract production errorLabelItem
top::LabelItem ::=
{
top.sourceLocation = loc("nowhere", -1, -1, -1, -1, -1, -1);
}

2 changes: 1 addition & 1 deletion edu.umn.cs.melt.ableC/abstractsyntax/env/MiscItem.sv
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
grammar edu:umn:cs:melt:ableC:abstractsyntax:env;

nonterminal MiscItem;
closed nonterminal MiscItem;

{- Misc items are used to put various bits of information into the
environment such that it can be extracted later by, typically, some
Expand Down
2 changes: 1 addition & 1 deletion edu.umn.cs.melt.ableC/abstractsyntax/env/RefIdItem.sv
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ grammar edu:umn:cs:melt:ableC:abstractsyntax:env;
-
- This unfortunately complicates the types a bit, since
-}
nonterminal RefIdItem with moduleName, tagEnv;
closed nonterminal RefIdItem with moduleName, tagEnv;

{-- Name resolves to a full struct declaration -}
abstract production structRefIdItem
Expand Down
Loading