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

[Relay][Parser] Improve Relay parser and pretty printing, including CMAKE #2377

Merged
merged 16 commits into from
Jan 17, 2019

Conversation

jroesch
Copy link
Member

@jroesch jroesch commented Jan 7, 2019

As per a conversation between @tqchen from last week we decided to split up my new work on error reporting into a couple different pieces. This is the first pieces which includes some fixes and improvements to the parser and text format.

I also fixed the CMAKE formula to correctly build locally on Macbooks which have set up ANTLR via Homebrew.

cc @tqchen @wweic @joshpoll

@@ -1,7 +1,9 @@
if(USE_ANTLR)
if(EXISTS /usr/local/lib/antlr-4.7.1-complete.jar)
set(ANTLR4 "/usr/local/lib/antlr-4.7.1-complete.jar")
file(GLOB_RECURSE ANTLR4
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Won't this find a list of all matching files? What if there are multiple jars?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed. see below

DEPENDS ${RELAY_PARSER_DIR}/Relay.g4
WORKING_DIRECTORY ${RELAY_PARSER_DIR})

add_custom_target(relay_parser ALL DEPENDS ${RELAY_PARSER})
else()
message(FATAL_ERROR "Can't find ANTLR4!")
message(FATAL_ERROR "Can't find ANTLR4: ANTLR4=" ${ANTLR4})
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What could ANTLR4 be set to if it's not defined?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

When we were using exists the variable would be set, but then not work, good to just print it out.

@@ -76,21 +78,35 @@ def lookup(scopes, name):
return val
return None

def spanify(f):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could you add a docstring?

@@ -410,6 +440,14 @@ def visitFuncType(self, ctx):

return ty.FuncType(arg_types, ret_type, [], None)

def visitGraphExpr(self, ctx):
graph_nid = int(ctx.LOCAL_VAR().getText()[1:])
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this will fail with an internal python message if the user accidentally uses a CNAME

@@ -20,7 +20,7 @@ NE: '!=' ;

opIdent: CNAME ;
GLOBAL_VAR: '@' CNAME ;
LOCAL_VAR: '%' CNAME ;
LOCAL_VAR: '%' (CNAME | INT);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

imo LOCAL_VAR and GRAPH_VAR should be separated at the lexing stage. This will simplify code paths in _parser.py.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to have a GRAPH_VAR definition. It would be clearer to write and read the parser code.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For sure, I was just hacking to try and get errors working.

@@ -83,8 +83,9 @@ expr

| ident # identExpr
| scalar # scalarExpr
// | expr '.' INT # project
// | 'debug' # debug
| LOCAL_VAR '=' expr ';' expr # graphExpr
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
| LOCAL_VAR '=' expr ';' expr # graphExpr
| var '=' expr ';' expr # seq

LOCAL_VAR/GRAPH_VAR should be enforced in _parser.py. Also I think this case should be added to visitSeq, since it shares a lot of code with the other sequencing cases.

@@ -131,7 +132,7 @@ identType: CNAME ;
// Float16, Float32, Float64
// Bool

body: '{' expr '}' ;
body: '{' expr ';' '}' ;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This syntax change my deserve a bit of discussion. We could add it, have it be optional, or not add it at all. There original justification for not having it is that ; was a logical replacement for in for let expressions, separating it from the imperative use of semicolons. To me, imperative uses of semicolons serve to separate individual statements, whereas the functional use here indicates chaining. It also opens up the question of whether to require/allow/forbid semicolons between global definitions.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm a fan of using semi-colons everywhere because it makes parsing simpler. The text format should be relatively straight forward to parse.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think it should go in this PR. It needs to be added in several places and test cases need to be updated. Could you open an issue?

@tqchen
Copy link
Member

tqchen commented Jan 7, 2019

@@ -410,6 +440,14 @@ def visitFuncType(self, ctx):

return ty.FuncType(arg_types, ret_type, [], None)

def visitGraphExpr(self, ctx):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To be consistent with other visit* functions, add the function's type as a comment.

if isinstance(source_name, str):
source_name = SourceName(source_name)

import pdb; pdb.set_trace()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

remove debug statement?

@@ -20,7 +20,7 @@ NE: '!=' ;

opIdent: CNAME ;
GLOBAL_VAR: '@' CNAME ;
LOCAL_VAR: '%' CNAME ;
LOCAL_VAR: '%' (CNAME | INT);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

+1 to have a GRAPH_VAR definition. It would be clearer to write and read the parser code.

@jroesch
Copy link
Member Author

jroesch commented Jan 11, 2019

@joshpoll what else is required for this?

@tqchen
Copy link
Member

tqchen commented Jan 12, 2019

Please do fix the lint errors, ping reviewers to do another round of review and when things get approved, let us merge it in

@joshpoll
Copy link
Contributor

@jroesch you should add a doc comment for spanify and we need to fix some erroring tests I think. that's it.

@joshpoll
Copy link
Contributor

also the changes to text_printer.cc should be reverted since ; changes are being punted

@jroesch jroesch changed the title Improve Relay parser and pretty printing, including CMAKE [Relay][Parser] Improve Relay parser and pretty printing, including CMAKE Jan 12, 2019
@jroesch
Copy link
Member Author

jroesch commented Jan 12, 2019

don't we need semi-colon to parse? the whole point of this is to move towards round-tripping

@joshpoll
Copy link
Contributor

joshpoll commented Jan 13, 2019

I'm not super familiar with how the text printer works now, but it should only be necessary to print semicolons between the two expressions in a let node and after an interstitial temp var.

@tqchen
Copy link
Member

tqchen commented Jan 15, 2019

@joshpoll can we remove the semicolon for now and try to make CI green?

@jroesch
Copy link
Member Author

jroesch commented Jan 15, 2019

@joshpoll Can you open an issue about getting round-tripping working? maybe you, @wweic and I can work on a solution.

@@ -172,6 +205,7 @@ def visitTerminal(self, node):
raise ParseError("Unrecognized BOOL_LIT: `{}`".format(node_text))

else:
print(node_text)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove

@@ -48,6 +49,11 @@
"float16x4",
}

def parses_as(code, expr):
# type: (str, relay.Expr) -> bool
print(relay.fromtext(SEMVER + "\n" + code))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove

@@ -420,6 +499,14 @@ def visitFuncType(self, ctx):

return ty.FuncType(arg_types, ret_type, [], None)

def visitGraphExpr(self, ctx):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it doesn't seem like antlr will generate this function.

@tqchen
Copy link
Member

tqchen commented Jan 16, 2019

Copy link
Contributor

@wweic wweic left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. Contingent on successful integration tests pass.

@tqchen tqchen merged commit d274e4b into apache:master Jan 17, 2019
@tqchen
Copy link
Member

tqchen commented Jan 17, 2019

Thanks to @wweic @jroesch @joshpoll , this is now merged

Anthony-Mai pushed a commit to Anthony-Mai/tvm that referenced this pull request Jan 20, 2019
Anthony-Mai pushed a commit to Anthony-Mai/tvm that referenced this pull request Jan 20, 2019
@jroesch jroesch deleted the relay-parser-pp branch February 11, 2019 00:01
wweic pushed a commit to neo-ai/tvm that referenced this pull request Feb 20, 2019
wweic pushed a commit to neo-ai/tvm that referenced this pull request Feb 20, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants