Skip to content

[Parser] Properly handle functions with * and / in the new parser #850

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

Merged
merged 4 commits into from
Jul 31, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
7 changes: 7 additions & 0 deletions src/lpython/parser/parser.yy
Original file line number Diff line number Diff line change
Expand Up @@ -615,6 +615,13 @@ parameter_list_starargs
| defparameter_list "," "/" "," defparameter_list "," "*" parameter
"," defparameter_list "," "**" parameter {
$$ = STAR_ARGS_20($1, $5, $8, $10, $13, @$); }
| defparameter_list "," "/" "," "*" "," defparameter_list {
$$ = STAR_ARGS_21($1, $7, @$); }
| defparameter_list "," "/" "," defparameter_list ","
"*" "," defparameter_list { $$ = STAR_ARGS_22($1, $5, $9, @$); }
| defparameter_list "," "*" "," defparameter_list {
$$ = STAR_ARGS_23($1, $5, @$); }
| "*" "," defparameter_list { $$ = STAR_ARGS_24($3, @$); }
;

parameter_list_opt
Expand Down
36 changes: 25 additions & 11 deletions src/lpython/parser/semantics.h
Original file line number Diff line number Diff line change
Expand Up @@ -376,14 +376,16 @@ Arg** ARG2LIST(Allocator &al, Arg *x) {
return v;
}

#define FUNC_ARGS_(x) \
#define FUNC_ARGS_(x, kw) \
Vec<arg_t> _m_##x; \
_m_##x.reserve(al, 4); \
if(n_##x > 0) { \
for(size_t i = 0; i < n_##x; i++) { \
_m_##x.push_back(al, m_##x[i]->_arg); \
if(m_##x[i]->default_value) { \
if(m_##x[i]->default_value && !kw) { \
defaults.push_back(al, m_##x[i]->defaults); \
} else if (m_##x[i]->default_value){ \
kw_defaults.push_back(al, m_##x[i]->defaults); \
} \
} \
}
Expand All @@ -397,12 +399,14 @@ static inline Args *FUNC_ARGS(Allocator &al, Location &l,
Args *r = al.allocate<Args>();
Vec<expr_t*> defaults;
defaults.reserve(al, 4);
Vec<expr_t*> kw_defaults;
kw_defaults.reserve(al, 4);

FUNC_ARGS_(posonlyargs);
FUNC_ARGS_(args);
FUNC_ARGS_(vararg);
FUNC_ARGS_(kwonlyargs);
FUNC_ARGS_(kwarg);
FUNC_ARGS_(posonlyargs, false);
FUNC_ARGS_(args, false);
FUNC_ARGS_(vararg, false);
FUNC_ARGS_(kwonlyargs, true);
FUNC_ARGS_(kwarg, true);

r->arguments.loc = l;
r->arguments.m_posonlyargs = _m_posonlyargs.p;
Expand All @@ -413,8 +417,8 @@ static inline Args *FUNC_ARGS(Allocator &al, Location &l,
r->arguments.n_vararg = _m_vararg.n;
r->arguments.m_kwonlyargs = _m_kwonlyargs.p;
r->arguments.n_kwonlyargs = _m_kwonlyargs.n;
r->arguments.m_kw_defaults = nullptr;
r->arguments.n_kw_defaults = 0;
r->arguments.m_kw_defaults = kw_defaults.p;
r->arguments.n_kw_defaults = kw_defaults.n;
r->arguments.m_kwarg = _m_kwarg.p;
r->arguments.n_kwarg = _m_kwarg.n;
r->arguments.m_defaults = defaults.p;
Expand Down Expand Up @@ -498,6 +502,16 @@ static inline void ADD_TYPE_COMMENT_(LFortran::Parser &p, Location l,
FUNC_ARGS(p.m_a, l, posonlyargs.p, posonlyargs.n, \
args.p, args.n, ARG2LIST(p.m_a, vararg), 1, \
kwonlyargs.p, kwonlyargs.n, ARG2LIST(p.m_a, kwarg), 1)
#define STAR_ARGS_21(posonlyargs, kwonlyargs, l) FUNC_ARGS(p.m_a, l, \
posonlyargs.p, posonlyargs.n, nullptr, 0, nullptr, 0, \
kwonlyargs.p, kwonlyargs.n, nullptr, 0)
#define STAR_ARGS_22(posonlyargs, args, kwonlyargs, l) FUNC_ARGS(p.m_a, l, \
posonlyargs.p, posonlyargs.n, args.p, args.n, nullptr, 0, \
kwonlyargs.p, kwonlyargs.n, nullptr, 0)
#define STAR_ARGS_23(args, kwonlyargs, l) FUNC_ARGS(p.m_a, l, nullptr, 0, \
args.p, args.n, nullptr, 0, kwonlyargs.p, kwonlyargs.n, nullptr, 0)
#define STAR_ARGS_24(kwonlyargs, l) FUNC_ARGS(p.m_a, l, nullptr, 0, \
nullptr, 0, nullptr, 0, kwonlyargs.p, kwonlyargs.n, nullptr, 0)

#define FUNC_ARG_LIST_01(args, l) FUNC_ARGS(p.m_a, l, nullptr, 0, \
args.p, args.n, nullptr, 0, nullptr, 0, nullptr, 0)
Expand Down Expand Up @@ -689,7 +703,7 @@ static inline ast_t *PREFIX_STRING(Allocator &al, Location &l, char *prefix, cha
for (size_t i = 0; i < strlen(prefix); i++) {
prefix[i] = tolower(prefix[i]);
}
if (strcmp(prefix, "f") == 0 || strcmp(prefix, "fr") == 0
if (strcmp(prefix, "f") == 0 || strcmp(prefix, "fr") == 0
|| strcmp(prefix, "rf") == 0) {
std::string str = std::string(s);
std::string s1 = "\"";
Expand Down Expand Up @@ -734,7 +748,7 @@ static inline ast_t *PREFIX_STRING(Allocator &al, Location &l, char *prefix, cha
}
}
tmp = make_JoinedStr_t(al, l, exprs.p, exprs.size());
} else if (strcmp(prefix, "b") == 0 || strcmp(prefix, "br") == 0
} else if (strcmp(prefix, "b") == 0 || strcmp(prefix, "br") == 0
|| strcmp(prefix, "rb") == 0) {
std::string str = std::string(s);
size_t start_pos = 0;
Expand Down
22 changes: 22 additions & 0 deletions tests/parser/function_def3.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,3 +47,25 @@ def test_01(a, # type:int
def test_02(a, # type:int
b):
pass

def quantiles(dist, /, *, n):
...

def quantiles(dist, /, *, n=4, method='exclusive'):
...

def func(self, param1, param2, /, param3, *, param4, param5):
...

def func(self, param1, param2, /, param3=7, *, param4, param5):
...

def func(self, param1, param2, /, param3, param3_1=2, *, param4, param5):
...


def add(a, b, *, c, d):
...

def func(*, param4, param5):
...
4 changes: 2 additions & 2 deletions tests/reference/ast_new-function_def3-f66064a.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,11 @@
"basename": "ast_new-function_def3-f66064a",
"cmd": "lpython --show-ast --new-parser --no-color {infile} -o {outfile}",
"infile": "tests/parser/function_def3.py",
"infile_hash": "92f1995802c2cf446ff865c20616ac65d9c3bd2c52357710d970db4f",
"infile_hash": "b5e4acc3d99fc5138d53737183c77f69cc9233435673ff1119cb21df",
"outfile": null,
"outfile_hash": null,
"stdout": "ast_new-function_def3-f66064a.stdout",
"stdout_hash": "05191d8dc81986b7c1eec58c9415d3a78e08543fc621fb873afbd6f1",
"stdout_hash": "45c49bce6580785f59584280023443fcd850c772c5fe6bd2ba414b7b",
"stderr": null,
"stderr_hash": null,
"returncode": 0
Expand Down
2 changes: 1 addition & 1 deletion tests/reference/ast_new-function_def3-f66064a.stdout
Original file line number Diff line number Diff line change
@@ -1 +1 @@
(Module [(FunctionDef main0 ([] [(i () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef example ([] [(text () ()) (width () ()) (fill_char () ())] [] [] [] [] [(ConstantInt 80 ()) (ConstantStr "-" ())]) [(Return ())] [] () "(...) -> str") (Expr (Call (Name example Load) [(Name text Load)] [(width (ConstantInt 80 ())) (fill_char (ConstantStr "-" ()))])) (FunctionDef test_1 ([] [(x () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef test_2 ([] [(y () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef func ([] [(a () "str") (b () "int") (c (Name str Load) "str")] [] [] [] [] [(ConstantInt 80 ()) (ConstantStr "-" ())]) [(Pass)] [] () ()) (FunctionDef abc ([] [(a () ()) (b () "int") (c () "list[str]")] [] [] [] [] [(List [(ConstantStr "-" ())] Load)]) [(Return ())] [] () "(...) -> str") (FunctionDef test_01 ([] [(a () "int") (b () ())] [] [] [] [] [(ConstantInt 0 ())]) [(Pass)] [] () ()) (FunctionDef test_02 ([] [(a () "int") (b () ())] [] [] [] [] []) [(Pass)] [] () ())] [(TypeIgnore 0 "[misc]") (TypeIgnore 0 "")])
(Module [(FunctionDef main0 ([] [(i () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef example ([] [(text () ()) (width () ()) (fill_char () ())] [] [] [] [] [(ConstantInt 80 ()) (ConstantStr "-" ())]) [(Return ())] [] () "(...) -> str") (Expr (Call (Name example Load) [(Name text Load)] [(width (ConstantInt 80 ())) (fill_char (ConstantStr "-" ()))])) (FunctionDef test_1 ([] [(x () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef test_2 ([] [(y () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef func ([] [(a () "str") (b () "int") (c (Name str Load) "str")] [] [] [] [] [(ConstantInt 80 ()) (ConstantStr "-" ())]) [(Pass)] [] () ()) (FunctionDef abc ([] [(a () ()) (b () "int") (c () "list[str]")] [] [] [] [] [(List [(ConstantStr "-" ())] Load)]) [(Return ())] [] () "(...) -> str") (FunctionDef test_01 ([] [(a () "int") (b () ())] [] [] [] [] [(ConstantInt 0 ())]) [(Pass)] [] () ()) (FunctionDef test_02 ([] [(a () "int") (b () ())] [] [] [] [] []) [(Pass)] [] () ()) (FunctionDef quantiles ([(dist () ())] [] [] [(n () ())] [] [] []) [(Expr (ConstantEllipsis ()))] [] () ()) (FunctionDef quantiles ([(dist () ())] [] [] [(n () ()) (method () ())] [(ConstantInt 4 ()) (ConstantStr "exclusive" ())] [] []) [(Expr (ConstantEllipsis ()))] [] () ()) (FunctionDef func ([(self () ()) (param1 () ()) (param2 () ())] [(param3 () ())] [] [(param4 () ()) (param5 () ())] [] [] []) [(Expr (ConstantEllipsis ()))] [] () ()) (FunctionDef func ([(self () ()) (param1 () ()) (param2 () ())] [(param3 () ())] [] [(param4 () ()) (param5 () ())] [] [] [(ConstantInt 7 ())]) [(Expr (ConstantEllipsis ()))] [] () ()) (FunctionDef func ([(self () ()) (param1 () ()) (param2 () ())] [(param3 () ()) (param3_1 () ())] [] [(param4 () ()) (param5 () ())] [] [] [(ConstantInt 2 ())]) [(Expr (ConstantEllipsis ()))] [] () ()) (FunctionDef add ([] [(a () ()) (b () ())] [] [(c () ()) (d () ())] [] [] []) [(Expr (ConstantEllipsis ()))] [] () ()) (FunctionDef func ([] [] [] [(param4 () ()) (param5 () ())] [] [] []) [(Expr (ConstantEllipsis ()))] [] () ())] [(TypeIgnore 0 "[misc]") (TypeIgnore 0 "")])