compiler.cpp 48 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234
  1. #include "pocketpy/compiler.h"
  2. namespace pkpy{
  3. NameScope Compiler::name_scope() const {
  4. auto s = contexts.size()>1 ? NAME_LOCAL : NAME_GLOBAL;
  5. if(unknown_global_scope && s == NAME_GLOBAL) s = NAME_GLOBAL_UNKNOWN;
  6. return s;
  7. }
  8. CodeObject_ Compiler::push_global_context(){
  9. CodeObject_ co = std::make_shared<CodeObject>(lexer->src, lexer->src->filename);
  10. co->start_line = i==0 ? 1 : prev().line;
  11. contexts.push(CodeEmitContext(vm, co, contexts.size()));
  12. return co;
  13. }
  14. FuncDecl_ Compiler::push_f_context(Str name){
  15. FuncDecl_ decl = std::make_shared<FuncDecl>();
  16. decl->code = std::make_shared<CodeObject>(lexer->src, name);
  17. decl->code->start_line = i==0 ? 1 : prev().line;
  18. decl->nested = name_scope() == NAME_LOCAL;
  19. contexts.push(CodeEmitContext(vm, decl->code, contexts.size()));
  20. contexts.top().func = decl;
  21. return decl;
  22. }
  23. void Compiler::pop_context(){
  24. if(!ctx()->s_expr.empty()){
  25. throw std::runtime_error("!ctx()->s_expr.empty()");
  26. }
  27. // add a `return None` in the end as a guard
  28. // previously, we only do this if the last opcode is not a return
  29. // however, this is buggy...since there may be a jump to the end (out of bound) even if the last opcode is a return
  30. ctx()->emit_(OP_RETURN_VALUE, 1, BC_KEEPLINE, true);
  31. // find the last valid token
  32. int j = i-1;
  33. while(tokens[j].type == TK("@eol") || tokens[j].type == TK("@dedent") || tokens[j].type == TK("@eof")) j--;
  34. ctx()->co->end_line = tokens[j].line;
  35. // some check here
  36. std::vector<Bytecode>& codes = ctx()->co->codes;
  37. if(ctx()->co->varnames.size() > PK_MAX_CO_VARNAMES){
  38. SyntaxError("maximum number of local variables exceeded");
  39. }
  40. if(ctx()->co->consts.size() > 65535){
  41. SyntaxError("maximum number of constants exceeded");
  42. }
  43. if(codes.size() > 65535 && ctx()->co->src->mode != JSON_MODE){
  44. // json mode does not contain jump instructions, so it is safe to ignore this check
  45. SyntaxError("maximum number of opcodes exceeded");
  46. }
  47. // pre-compute LOOP_BREAK and LOOP_CONTINUE and FOR_ITER
  48. for(int i=0; i<codes.size(); i++){
  49. Bytecode& bc = codes[i];
  50. if(bc.op == OP_LOOP_CONTINUE){
  51. bc.arg = ctx()->co->blocks[bc.arg].start;
  52. }else if(bc.op == OP_LOOP_BREAK){
  53. bc.arg = ctx()->co->blocks[bc.arg].get_break_end();
  54. }else if(bc.op == OP_FOR_ITER){
  55. bc.arg = ctx()->co->_get_block_codei(i).end;
  56. }
  57. }
  58. // pre-compute func->is_simple
  59. FuncDecl_ func = contexts.top().func;
  60. if(func){
  61. func->is_simple = true;
  62. if(func->code->is_generator) func->is_simple = false;
  63. if(func->kwargs.size() > 0) func->is_simple = false;
  64. if(func->starred_arg >= 0) func->is_simple = false;
  65. if(func->starred_kwarg >= 0) func->is_simple = false;
  66. }
  67. contexts.pop();
  68. }
  69. void Compiler::init_pratt_rules(){
  70. PK_LOCAL_STATIC unsigned int count = 0;
  71. if(count > 0) return;
  72. count += 1;
  73. // http://journal.stuffwithstuff.com/2011/03/19/pratt-parsers-expression-parsing-made-easy/
  74. #define PK_METHOD(name) &Compiler::name
  75. #define PK_NO_INFIX nullptr, PREC_LOWEST
  76. for(TokenIndex i=0; i<kTokenCount; i++) rules[i] = { nullptr, PK_NO_INFIX };
  77. rules[TK(".")] = { nullptr, PK_METHOD(exprAttrib), PREC_PRIMARY };
  78. rules[TK("(")] = { PK_METHOD(exprGroup), PK_METHOD(exprCall), PREC_PRIMARY };
  79. rules[TK("[")] = { PK_METHOD(exprList), PK_METHOD(exprSubscr), PREC_PRIMARY };
  80. rules[TK("{")] = { PK_METHOD(exprMap), PK_NO_INFIX };
  81. rules[TK("%")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_FACTOR };
  82. rules[TK("+")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_TERM };
  83. rules[TK("-")] = { PK_METHOD(exprUnaryOp), PK_METHOD(exprBinaryOp), PREC_TERM };
  84. rules[TK("*")] = { PK_METHOD(exprUnaryOp), PK_METHOD(exprBinaryOp), PREC_FACTOR };
  85. rules[TK("~")] = { PK_METHOD(exprUnaryOp), nullptr, PREC_UNARY };
  86. rules[TK("/")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_FACTOR };
  87. rules[TK("//")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_FACTOR };
  88. rules[TK("**")] = { PK_METHOD(exprUnaryOp), PK_METHOD(exprBinaryOp), PREC_EXPONENT };
  89. rules[TK(">")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  90. rules[TK("<")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  91. rules[TK("==")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  92. rules[TK("!=")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  93. rules[TK(">=")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  94. rules[TK("<=")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  95. rules[TK("in")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  96. rules[TK("is")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  97. rules[TK("<<")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_BITWISE_SHIFT };
  98. rules[TK(">>")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_BITWISE_SHIFT };
  99. rules[TK("&")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_BITWISE_AND };
  100. rules[TK("|")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_BITWISE_OR };
  101. rules[TK("^")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_BITWISE_XOR };
  102. rules[TK("@")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_FACTOR };
  103. rules[TK("if")] = { nullptr, PK_METHOD(exprTernary), PREC_TERNARY };
  104. rules[TK("not in")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  105. rules[TK("is not")] = { nullptr, PK_METHOD(exprBinaryOp), PREC_COMPARISION };
  106. rules[TK("and") ] = { nullptr, PK_METHOD(exprAnd), PREC_LOGICAL_AND };
  107. rules[TK("or")] = { nullptr, PK_METHOD(exprOr), PREC_LOGICAL_OR };
  108. rules[TK("not")] = { PK_METHOD(exprNot), nullptr, PREC_LOGICAL_NOT };
  109. rules[TK("True")] = { PK_METHOD(exprLiteral0), PK_NO_INFIX };
  110. rules[TK("False")] = { PK_METHOD(exprLiteral0), PK_NO_INFIX };
  111. rules[TK("None")] = { PK_METHOD(exprLiteral0), PK_NO_INFIX };
  112. rules[TK("...")] = { PK_METHOD(exprLiteral0), PK_NO_INFIX };
  113. rules[TK("lambda")] = { PK_METHOD(exprLambda), PK_NO_INFIX };
  114. rules[TK("@id")] = { PK_METHOD(exprName), PK_NO_INFIX };
  115. rules[TK("@num")] = { PK_METHOD(exprLiteral), PK_NO_INFIX };
  116. rules[TK("@str")] = { PK_METHOD(exprLiteral), PK_NO_INFIX };
  117. rules[TK("@fstr")] = { PK_METHOD(exprFString), PK_NO_INFIX };
  118. rules[TK("@long")] = { PK_METHOD(exprLong), PK_NO_INFIX };
  119. rules[TK("@imag")] = { PK_METHOD(exprImag), PK_NO_INFIX };
  120. rules[TK("@bytes")] = { PK_METHOD(exprBytes), PK_NO_INFIX };
  121. rules[TK(":")] = { PK_METHOD(exprSlice0), PK_METHOD(exprSlice1), PREC_PRIMARY };
  122. #undef PK_METHOD
  123. #undef PK_NO_INFIX
  124. }
  125. bool Compiler::match(TokenIndex expected) {
  126. if (curr().type != expected) return false;
  127. advance();
  128. return true;
  129. }
  130. void Compiler::consume(TokenIndex expected) {
  131. if (!match(expected)){
  132. SyntaxError(
  133. _S("expected '", TK_STR(expected), "', got '", TK_STR(curr().type), "'")
  134. );
  135. }
  136. }
  137. bool Compiler::match_newlines_repl(){
  138. return match_newlines(mode()==REPL_MODE);
  139. }
  140. bool Compiler::match_newlines(bool repl_throw) {
  141. bool consumed = false;
  142. if (curr().type == TK("@eol")) {
  143. while (curr().type == TK("@eol")) advance();
  144. consumed = true;
  145. }
  146. if (repl_throw && curr().type == TK("@eof")){
  147. throw NeedMoreLines(ctx()->is_compiling_class);
  148. }
  149. return consumed;
  150. }
  151. bool Compiler::match_end_stmt() {
  152. if (match(TK(";"))) { match_newlines(); return true; }
  153. if (match_newlines() || curr().type == TK("@eof")) return true;
  154. if (curr().type == TK("@dedent")) return true;
  155. return false;
  156. }
  157. void Compiler::consume_end_stmt() {
  158. if (!match_end_stmt()) SyntaxError("expected statement end");
  159. }
  160. void Compiler::EXPR() {
  161. parse_expression(PREC_LOWEST+1);
  162. }
  163. void Compiler::EXPR_TUPLE(bool allow_slice) {
  164. parse_expression(PREC_LOWEST+1, allow_slice);
  165. if(!match(TK(","))) return;
  166. // tuple expression
  167. std::vector<Expr_> items;
  168. items.push_back(ctx()->s_expr.popx());
  169. do {
  170. if(curr().brackets_level) match_newlines_repl();
  171. if(!is_expression(allow_slice)) break;
  172. parse_expression(PREC_LOWEST+1, allow_slice);
  173. items.push_back(ctx()->s_expr.popx());
  174. if(curr().brackets_level) match_newlines_repl();
  175. } while(match(TK(",")));
  176. ctx()->s_expr.push(make_expr<TupleExpr>(std::move(items)));
  177. }
  178. // special case for `for loop` and `comp`
  179. Expr_ Compiler::EXPR_VARS(){
  180. std::vector<Expr_> items;
  181. do {
  182. consume(TK("@id"));
  183. items.push_back(make_expr<NameExpr>(prev().str(), name_scope()));
  184. } while(match(TK(",")));
  185. if(items.size()==1) return std::move(items[0]);
  186. return make_expr<TupleExpr>(std::move(items));
  187. }
  188. void Compiler::exprLiteral(){
  189. ctx()->s_expr.push(make_expr<LiteralExpr>(prev().value));
  190. }
  191. void Compiler::exprLong(){
  192. ctx()->s_expr.push(make_expr<LongExpr>(prev().str()));
  193. }
  194. void Compiler::exprImag(){
  195. ctx()->s_expr.push(make_expr<ImagExpr>(std::get<f64>(prev().value)));
  196. }
  197. void Compiler::exprBytes(){
  198. ctx()->s_expr.push(make_expr<BytesExpr>(std::get<Str>(prev().value)));
  199. }
  200. void Compiler::exprFString(){
  201. ctx()->s_expr.push(make_expr<FStringExpr>(std::get<Str>(prev().value)));
  202. }
  203. void Compiler::exprLambda(){
  204. FuncDecl_ decl = push_f_context("<lambda>");
  205. auto e = make_expr<LambdaExpr>(decl);
  206. if(!match(TK(":"))){
  207. _compile_f_args(e->decl, false);
  208. consume(TK(":"));
  209. }
  210. // https://github.com/pocketpy/pocketpy/issues/37
  211. parse_expression(PREC_LAMBDA + 1);
  212. ctx()->emit_expr();
  213. ctx()->emit_(OP_RETURN_VALUE, BC_NOARG, BC_KEEPLINE);
  214. pop_context();
  215. ctx()->s_expr.push(std::move(e));
  216. }
  217. void Compiler::exprOr(){
  218. auto e = make_expr<OrExpr>();
  219. e->lhs = ctx()->s_expr.popx();
  220. parse_expression(PREC_LOGICAL_OR + 1);
  221. e->rhs = ctx()->s_expr.popx();
  222. ctx()->s_expr.push(std::move(e));
  223. }
  224. void Compiler::exprAnd(){
  225. auto e = make_expr<AndExpr>();
  226. e->lhs = ctx()->s_expr.popx();
  227. parse_expression(PREC_LOGICAL_AND + 1);
  228. e->rhs = ctx()->s_expr.popx();
  229. ctx()->s_expr.push(std::move(e));
  230. }
  231. void Compiler::exprTernary(){
  232. auto e = make_expr<TernaryExpr>();
  233. e->true_expr = ctx()->s_expr.popx();
  234. // cond
  235. parse_expression(PREC_TERNARY + 1);
  236. e->cond = ctx()->s_expr.popx();
  237. consume(TK("else"));
  238. // if false
  239. parse_expression(PREC_TERNARY + 1);
  240. e->false_expr = ctx()->s_expr.popx();
  241. ctx()->s_expr.push(std::move(e));
  242. }
  243. void Compiler::exprBinaryOp(){
  244. auto e = make_expr<BinaryExpr>();
  245. e->op = prev().type;
  246. e->lhs = ctx()->s_expr.popx();
  247. parse_expression(rules[e->op].precedence + 1);
  248. e->rhs = ctx()->s_expr.popx();
  249. ctx()->s_expr.push(std::move(e));
  250. }
  251. void Compiler::exprNot() {
  252. parse_expression(PREC_LOGICAL_NOT + 1);
  253. ctx()->s_expr.push(make_expr<NotExpr>(ctx()->s_expr.popx()));
  254. }
  255. void Compiler::exprUnaryOp(){
  256. TokenIndex op = prev().type;
  257. parse_expression(PREC_UNARY + 1);
  258. switch(op){
  259. case TK("-"):
  260. ctx()->s_expr.push(make_expr<NegatedExpr>(ctx()->s_expr.popx()));
  261. break;
  262. case TK("~"):
  263. ctx()->s_expr.push(make_expr<InvertExpr>(ctx()->s_expr.popx()));
  264. break;
  265. case TK("*"):
  266. ctx()->s_expr.push(make_expr<StarredExpr>(1, ctx()->s_expr.popx()));
  267. break;
  268. case TK("**"):
  269. ctx()->s_expr.push(make_expr<StarredExpr>(2, ctx()->s_expr.popx()));
  270. break;
  271. default: PK_FATAL_ERROR();
  272. }
  273. }
  274. void Compiler::exprGroup(){
  275. match_newlines_repl();
  276. EXPR_TUPLE(); // () is just for change precedence
  277. match_newlines_repl();
  278. consume(TK(")"));
  279. if(ctx()->s_expr.top()->is_tuple()) return;
  280. Expr_ g = make_expr<GroupedExpr>(ctx()->s_expr.popx());
  281. ctx()->s_expr.push(std::move(g));
  282. }
  283. void Compiler::exprList() {
  284. int line = prev().line;
  285. std::vector<Expr_> items;
  286. do {
  287. match_newlines_repl();
  288. if (curr().type == TK("]")) break;
  289. EXPR();
  290. items.push_back(ctx()->s_expr.popx());
  291. match_newlines_repl();
  292. if(items.size()==1 && match(TK("for"))){
  293. _consume_comp<ListCompExpr>(std::move(items[0]));
  294. consume(TK("]"));
  295. return;
  296. }
  297. match_newlines_repl();
  298. } while (match(TK(",")));
  299. consume(TK("]"));
  300. auto e = make_expr<ListExpr>(std::move(items));
  301. e->line = line; // override line
  302. ctx()->s_expr.push(std::move(e));
  303. }
  304. void Compiler::exprMap() {
  305. bool parsing_dict = false; // {...} may be dict or set
  306. std::vector<Expr_> items;
  307. do {
  308. match_newlines_repl();
  309. if (curr().type == TK("}")) break;
  310. EXPR();
  311. int star_level = ctx()->s_expr.top()->star_level();
  312. if(star_level==2 || curr().type == TK(":")){
  313. parsing_dict = true;
  314. }
  315. if(parsing_dict){
  316. auto dict_item = make_expr<DictItemExpr>();
  317. if(star_level == 2){
  318. dict_item->key = nullptr;
  319. dict_item->value = ctx()->s_expr.popx();
  320. }else{
  321. consume(TK(":"));
  322. EXPR();
  323. dict_item->key = ctx()->s_expr.popx();
  324. dict_item->value = ctx()->s_expr.popx();
  325. }
  326. items.push_back(std::move(dict_item));
  327. }else{
  328. items.push_back(ctx()->s_expr.popx());
  329. }
  330. match_newlines_repl();
  331. if(items.size()==1 && match(TK("for"))){
  332. if(parsing_dict) _consume_comp<DictCompExpr>(std::move(items[0]));
  333. else _consume_comp<SetCompExpr>(std::move(items[0]));
  334. consume(TK("}"));
  335. return;
  336. }
  337. match_newlines_repl();
  338. } while (match(TK(",")));
  339. consume(TK("}"));
  340. if(items.size()==0 || parsing_dict){
  341. auto e = make_expr<DictExpr>(std::move(items));
  342. ctx()->s_expr.push(std::move(e));
  343. }else{
  344. auto e = make_expr<SetExpr>(std::move(items));
  345. ctx()->s_expr.push(std::move(e));
  346. }
  347. }
  348. void Compiler::exprCall() {
  349. auto e = make_expr<CallExpr>();
  350. e->callable = ctx()->s_expr.popx();
  351. do {
  352. match_newlines_repl();
  353. if (curr().type==TK(")")) break;
  354. if(curr().type==TK("@id") && next().type==TK("=")) {
  355. consume(TK("@id"));
  356. Str key = prev().str();
  357. consume(TK("="));
  358. EXPR();
  359. e->kwargs.push_back({key, ctx()->s_expr.popx()});
  360. } else{
  361. EXPR();
  362. if(ctx()->s_expr.top()->star_level() == 2){
  363. // **kwargs
  364. e->kwargs.push_back({"**", ctx()->s_expr.popx()});
  365. }else{
  366. // positional argument
  367. if(!e->kwargs.empty()) SyntaxError("positional argument follows keyword argument");
  368. e->args.push_back(ctx()->s_expr.popx());
  369. }
  370. }
  371. match_newlines_repl();
  372. } while (match(TK(",")));
  373. consume(TK(")"));
  374. if(e->args.size() > 32767) SyntaxError("too many positional arguments");
  375. if(e->kwargs.size() > 32767) SyntaxError("too many keyword arguments");
  376. ctx()->s_expr.push(std::move(e));
  377. }
  378. void Compiler::exprName(){
  379. Str name = prev().str();
  380. NameScope scope = name_scope();
  381. if(ctx()->global_names.count(name)){
  382. scope = NAME_GLOBAL;
  383. }
  384. ctx()->s_expr.push(make_expr<NameExpr>(name, scope));
  385. }
  386. void Compiler::exprAttrib() {
  387. consume(TK("@id"));
  388. ctx()->s_expr.push(
  389. make_expr<AttribExpr>(ctx()->s_expr.popx(), StrName::get(prev().sv()))
  390. );
  391. }
  392. void Compiler::exprSlice0() {
  393. auto slice = make_expr<SliceExpr>();
  394. if(is_expression()){ // :<stop>
  395. EXPR();
  396. slice->stop = ctx()->s_expr.popx();
  397. // try optional step
  398. if(match(TK(":"))){ // :<stop>:<step>
  399. EXPR();
  400. slice->step = ctx()->s_expr.popx();
  401. }
  402. }else if(match(TK(":"))){
  403. if(is_expression()){ // ::<step>
  404. EXPR();
  405. slice->step = ctx()->s_expr.popx();
  406. } // else ::
  407. } // else :
  408. ctx()->s_expr.push(std::move(slice));
  409. }
  410. void Compiler::exprSlice1() {
  411. auto slice = make_expr<SliceExpr>();
  412. slice->start = ctx()->s_expr.popx();
  413. if(is_expression()){ // <start>:<stop>
  414. EXPR();
  415. slice->stop = ctx()->s_expr.popx();
  416. // try optional step
  417. if(match(TK(":"))){ // <start>:<stop>:<step>
  418. EXPR();
  419. slice->step = ctx()->s_expr.popx();
  420. }
  421. }else if(match(TK(":"))){ // <start>::<step>
  422. EXPR();
  423. slice->step = ctx()->s_expr.popx();
  424. } // else <start>:
  425. ctx()->s_expr.push(std::move(slice));
  426. }
  427. void Compiler::exprSubscr() {
  428. auto e = make_expr<SubscrExpr>();
  429. match_newlines_repl();
  430. e->a = ctx()->s_expr.popx(); // a
  431. EXPR_TUPLE(true);
  432. e->b = ctx()->s_expr.popx(); // a[<expr>]
  433. match_newlines_repl();
  434. consume(TK("]"));
  435. ctx()->s_expr.push(std::move(e));
  436. }
  437. void Compiler::exprLiteral0() {
  438. ctx()->s_expr.push(make_expr<Literal0Expr>(prev().type));
  439. }
  440. void Compiler::compile_block_body(void (Compiler::*callback)()) {
  441. if(callback == nullptr) callback = &Compiler::compile_stmt;
  442. consume(TK(":"));
  443. if(curr().type!=TK("@eol") && curr().type!=TK("@eof")){
  444. compile_stmt(); // inline block
  445. return;
  446. }
  447. if(!match_newlines(mode()==REPL_MODE)){
  448. SyntaxError("expected a new line after ':'");
  449. }
  450. consume(TK("@indent"));
  451. while (curr().type != TK("@dedent")) {
  452. match_newlines();
  453. (this->*callback)();
  454. match_newlines();
  455. }
  456. consume(TK("@dedent"));
  457. }
  458. // import a [as b]
  459. // import a [as b], c [as d]
  460. void Compiler::compile_normal_import() {
  461. do {
  462. consume(TK("@id"));
  463. Str name = prev().str();
  464. ctx()->emit_(OP_IMPORT_PATH, ctx()->add_const_string(name.sv()), prev().line);
  465. if (match(TK("as"))) {
  466. consume(TK("@id"));
  467. name = prev().str();
  468. }
  469. ctx()->emit_store_name(name_scope(), StrName(name), prev().line);
  470. } while (match(TK(",")));
  471. consume_end_stmt();
  472. }
  473. // from a import b [as c], d [as e]
  474. // from a.b import c [as d]
  475. // from . import a [as b]
  476. // from .a import b [as c]
  477. // from ..a import b [as c]
  478. // from .a.b import c [as d]
  479. // from xxx import *
  480. void Compiler::compile_from_import() {
  481. int dots = 0;
  482. while(true){
  483. switch(curr().type){
  484. case TK("."): dots+=1; break;
  485. case TK(".."): dots+=2; break;
  486. case TK("..."): dots+=3; break;
  487. default: goto __EAT_DOTS_END;
  488. }
  489. advance();
  490. }
  491. __EAT_DOTS_END:
  492. SStream ss;
  493. for(int i=0; i<dots; i++) ss << '.';
  494. if(dots > 0){
  495. // @id is optional if dots > 0
  496. if(match(TK("@id"))){
  497. ss << prev().sv();
  498. while (match(TK("."))) {
  499. consume(TK("@id"));
  500. ss << "." << prev().sv();
  501. }
  502. }
  503. }else{
  504. // @id is required if dots == 0
  505. consume(TK("@id"));
  506. ss << prev().sv();
  507. while (match(TK("."))) {
  508. consume(TK("@id"));
  509. ss << "." << prev().sv();
  510. }
  511. }
  512. ctx()->emit_(OP_IMPORT_PATH, ctx()->add_const_string(ss.str().sv()), prev().line);
  513. consume(TK("import"));
  514. if (match(TK("*"))) {
  515. if(name_scope() != NAME_GLOBAL) SyntaxError("from <module> import * can only be used in global scope");
  516. // pop the module and import __all__
  517. ctx()->emit_(OP_POP_IMPORT_STAR, BC_NOARG, prev().line);
  518. consume_end_stmt();
  519. return;
  520. }
  521. do {
  522. ctx()->emit_(OP_DUP_TOP, BC_NOARG, BC_KEEPLINE);
  523. consume(TK("@id"));
  524. Str name = prev().str();
  525. ctx()->emit_(OP_LOAD_ATTR, StrName(name).index, prev().line);
  526. if (match(TK("as"))) {
  527. consume(TK("@id"));
  528. name = prev().str();
  529. }
  530. ctx()->emit_store_name(name_scope(), StrName(name), prev().line);
  531. } while (match(TK(",")));
  532. ctx()->emit_(OP_POP_TOP, BC_NOARG, BC_KEEPLINE);
  533. consume_end_stmt();
  534. }
  535. bool Compiler::is_expression(bool allow_slice){
  536. PrattCallback prefix = rules[curr().type].prefix;
  537. return prefix != nullptr && (allow_slice || curr().type!=TK(":"));
  538. }
  539. void Compiler::parse_expression(int precedence, bool allow_slice) {
  540. PrattCallback prefix = rules[curr().type].prefix;
  541. if (prefix==nullptr || (curr().type==TK(":") && !allow_slice)){
  542. SyntaxError(Str("expected an expression, got ") + TK_STR(curr().type));
  543. }
  544. advance();
  545. (this->*prefix)();
  546. while (rules[curr().type].precedence >= precedence && (allow_slice || curr().type!=TK(":"))) {
  547. TokenIndex op = curr().type;
  548. advance();
  549. PrattCallback infix = rules[op].infix;
  550. PK_ASSERT(infix != nullptr);
  551. (this->*infix)();
  552. }
  553. }
  554. void Compiler::compile_if_stmt() {
  555. EXPR(); // condition
  556. ctx()->emit_expr();
  557. int patch = ctx()->emit_(OP_POP_JUMP_IF_FALSE, BC_NOARG, prev().line);
  558. compile_block_body();
  559. if (match(TK("elif"))) {
  560. int exit_patch = ctx()->emit_(OP_JUMP_ABSOLUTE, BC_NOARG, prev().line);
  561. ctx()->patch_jump(patch);
  562. compile_if_stmt();
  563. ctx()->patch_jump(exit_patch);
  564. } else if (match(TK("else"))) {
  565. int exit_patch = ctx()->emit_(OP_JUMP_ABSOLUTE, BC_NOARG, prev().line);
  566. ctx()->patch_jump(patch);
  567. compile_block_body();
  568. ctx()->patch_jump(exit_patch);
  569. } else {
  570. ctx()->patch_jump(patch);
  571. }
  572. }
  573. void Compiler::compile_while_loop() {
  574. CodeBlock* block = ctx()->enter_block(CodeBlockType::WHILE_LOOP);
  575. EXPR(); // condition
  576. ctx()->emit_expr();
  577. int patch = ctx()->emit_(OP_POP_JUMP_IF_FALSE, BC_NOARG, prev().line);
  578. compile_block_body();
  579. ctx()->emit_(OP_LOOP_CONTINUE, ctx()->get_loop(), BC_KEEPLINE, true);
  580. ctx()->patch_jump(patch);
  581. ctx()->exit_block();
  582. // optional else clause
  583. if (match(TK("else"))) {
  584. compile_block_body();
  585. block->end2 = ctx()->co->codes.size();
  586. }
  587. }
  588. void Compiler::compile_for_loop() {
  589. Expr_ vars = EXPR_VARS();
  590. consume(TK("in"));
  591. EXPR_TUPLE(); ctx()->emit_expr();
  592. ctx()->emit_(OP_GET_ITER, BC_NOARG, BC_KEEPLINE);
  593. CodeBlock* block = ctx()->enter_block(CodeBlockType::FOR_LOOP);
  594. ctx()->emit_(OP_FOR_ITER, BC_NOARG, BC_KEEPLINE);
  595. bool ok = vars->emit_store(ctx());
  596. if(!ok) SyntaxError(); // this error occurs in `vars` instead of this line, but...nevermind
  597. compile_block_body();
  598. ctx()->emit_(OP_LOOP_CONTINUE, ctx()->get_loop(), BC_KEEPLINE, true);
  599. ctx()->exit_block();
  600. // optional else clause
  601. if (match(TK("else"))) {
  602. compile_block_body();
  603. block->end2 = ctx()->co->codes.size();
  604. }
  605. }
  606. void Compiler::compile_try_except() {
  607. ctx()->enter_block(CodeBlockType::TRY_EXCEPT);
  608. compile_block_body();
  609. std::vector<int> patches = {
  610. ctx()->emit_(OP_JUMP_ABSOLUTE, BC_NOARG, BC_KEEPLINE)
  611. };
  612. ctx()->exit_block();
  613. int finally_entry = -1;
  614. if(curr().type != TK("finally")){
  615. do {
  616. StrName as_name;
  617. consume(TK("except"));
  618. if(is_expression()){
  619. EXPR(); // push assumed type on to the stack
  620. ctx()->emit_expr();
  621. ctx()->emit_(OP_EXCEPTION_MATCH, BC_NOARG, prev().line);
  622. if(match(TK("as"))){
  623. consume(TK("@id"));
  624. as_name = StrName(prev().sv());
  625. }
  626. }else{
  627. ctx()->emit_(OP_LOAD_TRUE, BC_NOARG, BC_KEEPLINE);
  628. }
  629. int patch = ctx()->emit_(OP_POP_JUMP_IF_FALSE, BC_NOARG, BC_KEEPLINE);
  630. // on match
  631. if(!as_name.empty()){
  632. ctx()->emit_(OP_DUP_TOP, BC_NOARG, BC_KEEPLINE);
  633. ctx()->emit_store_name(name_scope(), as_name, BC_KEEPLINE);
  634. }
  635. // pop the exception
  636. ctx()->emit_(OP_POP_EXCEPTION, BC_NOARG, BC_KEEPLINE);
  637. compile_block_body();
  638. patches.push_back(ctx()->emit_(OP_JUMP_ABSOLUTE, BC_NOARG, BC_KEEPLINE));
  639. ctx()->patch_jump(patch);
  640. }while(curr().type == TK("except"));
  641. }
  642. if(match(TK("finally"))){
  643. int patch = ctx()->emit_(OP_JUMP_ABSOLUTE, BC_NOARG, BC_KEEPLINE);
  644. finally_entry = ctx()->co->codes.size();
  645. compile_block_body();
  646. ctx()->emit_(OP_JUMP_ABSOLUTE_TOP, BC_NOARG, BC_KEEPLINE);
  647. ctx()->patch_jump(patch);
  648. }
  649. // no match, re-raise
  650. if(finally_entry != -1){
  651. ctx()->emit_(OP_LOAD_INTEGER, (uint16_t)ctx()->co->codes.size()+2, BC_KEEPLINE);
  652. ctx()->emit_(OP_JUMP_ABSOLUTE, finally_entry, BC_KEEPLINE);
  653. }
  654. ctx()->emit_(OP_RE_RAISE, BC_NOARG, BC_KEEPLINE);
  655. // no exception or no match, jump to the end
  656. for (int patch : patches) ctx()->patch_jump(patch);
  657. if(finally_entry != -1){
  658. ctx()->emit_(OP_LOAD_INTEGER, (uint16_t)ctx()->co->codes.size()+2, BC_KEEPLINE);
  659. ctx()->emit_(OP_JUMP_ABSOLUTE, finally_entry, BC_KEEPLINE);
  660. }
  661. }
  662. void Compiler::compile_decorated(){
  663. std::vector<Expr_> decorators;
  664. do{
  665. EXPR();
  666. decorators.push_back(ctx()->s_expr.popx());
  667. if(!match_newlines_repl()) SyntaxError();
  668. }while(match(TK("@")));
  669. if(match(TK("class"))){
  670. compile_class(decorators);
  671. }else{
  672. consume(TK("def"));
  673. compile_function(decorators);
  674. }
  675. }
  676. bool Compiler::try_compile_assignment(){
  677. switch (curr().type) {
  678. case TK("+="): case TK("-="): case TK("*="): case TK("/="): case TK("//="): case TK("%="):
  679. case TK("<<="): case TK(">>="): case TK("&="): case TK("|="): case TK("^="): {
  680. Expr* lhs_p = ctx()->s_expr.top().get();
  681. if(lhs_p->is_starred()) SyntaxError();
  682. if(ctx()->is_compiling_class) SyntaxError("can't use inplace operator in class definition");
  683. advance();
  684. auto e = make_expr<BinaryExpr>();
  685. e->op = prev().type - 1; // -1 to remove =
  686. e->lhs = ctx()->s_expr.popx();
  687. EXPR_TUPLE();
  688. e->rhs = ctx()->s_expr.popx();
  689. if(e->is_starred()) SyntaxError();
  690. e->emit_(ctx());
  691. bool ok = lhs_p->emit_store(ctx());
  692. if(!ok) SyntaxError();
  693. } return true;
  694. case TK("="): {
  695. int n = 0;
  696. while(match(TK("="))){
  697. EXPR_TUPLE();
  698. n += 1;
  699. }
  700. // stack size is n+1
  701. Expr_ val = ctx()->s_expr.popx();
  702. val->emit_(ctx());
  703. for(int j=1; j<n; j++) ctx()->emit_(OP_DUP_TOP, BC_NOARG, BC_KEEPLINE);
  704. for(int j=0; j<n; j++){
  705. auto e = ctx()->s_expr.popx();
  706. if(e->is_starred()) SyntaxError();
  707. bool ok = e->emit_store(ctx());
  708. if(!ok) SyntaxError();
  709. }
  710. } return true;
  711. default: return false;
  712. }
  713. }
  714. void Compiler::compile_stmt() {
  715. if(match(TK("class"))){
  716. compile_class();
  717. return;
  718. }
  719. advance();
  720. int kw_line = prev().line; // backup line number
  721. int curr_loop_block = ctx()->get_loop();
  722. switch(prev().type){
  723. case TK("break"):
  724. if (curr_loop_block < 0) SyntaxError("'break' outside loop");
  725. ctx()->emit_(OP_LOOP_BREAK, curr_loop_block, kw_line);
  726. consume_end_stmt();
  727. break;
  728. case TK("continue"):
  729. if (curr_loop_block < 0) SyntaxError("'continue' not properly in loop");
  730. ctx()->emit_(OP_LOOP_CONTINUE, curr_loop_block, kw_line);
  731. consume_end_stmt();
  732. break;
  733. case TK("yield"):
  734. if (contexts.size() <= 1) SyntaxError("'yield' outside function");
  735. EXPR_TUPLE(); ctx()->emit_expr();
  736. // if yield present, mark the function as generator
  737. ctx()->co->is_generator = true;
  738. ctx()->emit_(OP_YIELD_VALUE, BC_NOARG, kw_line);
  739. consume_end_stmt();
  740. break;
  741. case TK("yield from"):
  742. if (contexts.size() <= 1) SyntaxError("'yield from' outside function");
  743. EXPR_TUPLE(); ctx()->emit_expr();
  744. // if yield from present, mark the function as generator
  745. ctx()->co->is_generator = true;
  746. ctx()->emit_(OP_GET_ITER, BC_NOARG, kw_line);
  747. ctx()->enter_block(CodeBlockType::FOR_LOOP);
  748. ctx()->emit_(OP_FOR_ITER, BC_NOARG, kw_line);
  749. ctx()->emit_(OP_YIELD_VALUE, BC_NOARG, kw_line);
  750. ctx()->emit_(OP_LOOP_CONTINUE, ctx()->get_loop(), kw_line);
  751. ctx()->exit_block();
  752. consume_end_stmt();
  753. break;
  754. case TK("return"):
  755. if (contexts.size() <= 1) SyntaxError("'return' outside function");
  756. if(match_end_stmt()){
  757. ctx()->emit_(OP_RETURN_VALUE, 1, kw_line);
  758. }else{
  759. EXPR_TUPLE(); ctx()->emit_expr();
  760. // check if it is a generator
  761. if(ctx()->co->is_generator) SyntaxError("'return' with argument inside generator function");
  762. consume_end_stmt();
  763. ctx()->emit_(OP_RETURN_VALUE, BC_NOARG, kw_line);
  764. }
  765. break;
  766. /*************************************************/
  767. case TK("if"): compile_if_stmt(); break;
  768. case TK("while"): compile_while_loop(); break;
  769. case TK("for"): compile_for_loop(); break;
  770. case TK("import"): compile_normal_import(); break;
  771. case TK("from"): compile_from_import(); break;
  772. case TK("def"): compile_function(); break;
  773. case TK("@"): compile_decorated(); break;
  774. case TK("try"): compile_try_except(); break;
  775. case TK("pass"): consume_end_stmt(); break;
  776. /*************************************************/
  777. case TK("++"):{
  778. consume(TK("@id"));
  779. StrName name(prev().sv());
  780. NameScope scope = name_scope();
  781. bool is_global = ctx()->global_names.count(name.sv());
  782. if(is_global) scope = NAME_GLOBAL;
  783. switch(scope){
  784. case NAME_LOCAL:
  785. ctx()->emit_(OP_INC_FAST, ctx()->add_varname(name), prev().line);
  786. break;
  787. case NAME_GLOBAL:
  788. ctx()->emit_(OP_INC_GLOBAL, name.index, prev().line);
  789. break;
  790. default: SyntaxError(); break;
  791. }
  792. consume_end_stmt();
  793. break;
  794. }
  795. case TK("--"):{
  796. consume(TK("@id"));
  797. StrName name(prev().sv());
  798. switch(name_scope()){
  799. case NAME_LOCAL:
  800. ctx()->emit_(OP_DEC_FAST, ctx()->add_varname(name), prev().line);
  801. break;
  802. case NAME_GLOBAL:
  803. ctx()->emit_(OP_DEC_GLOBAL, name.index, prev().line);
  804. break;
  805. default: SyntaxError(); break;
  806. }
  807. consume_end_stmt();
  808. break;
  809. }
  810. case TK("assert"):{
  811. EXPR(); // condition
  812. ctx()->emit_expr();
  813. int index = ctx()->emit_(OP_POP_JUMP_IF_TRUE, BC_NOARG, kw_line);
  814. int has_msg = 0;
  815. if(match(TK(","))){
  816. EXPR(); // message
  817. ctx()->emit_expr();
  818. has_msg = 1;
  819. }
  820. ctx()->emit_(OP_RAISE_ASSERT, has_msg, kw_line);
  821. ctx()->patch_jump(index);
  822. consume_end_stmt();
  823. break;
  824. }
  825. case TK("global"):
  826. do {
  827. consume(TK("@id"));
  828. ctx()->global_names.insert(prev().str());
  829. } while (match(TK(",")));
  830. consume_end_stmt();
  831. break;
  832. case TK("raise"): {
  833. EXPR(); ctx()->emit_expr();
  834. ctx()->emit_(OP_RAISE, BC_NOARG, kw_line);
  835. consume_end_stmt();
  836. } break;
  837. case TK("del"): {
  838. EXPR_TUPLE();
  839. Expr_ e = ctx()->s_expr.popx();
  840. bool ok = e->emit_del(ctx());
  841. if(!ok) SyntaxError();
  842. consume_end_stmt();
  843. } break;
  844. case TK("with"): {
  845. EXPR(); // [ <expr> ]
  846. ctx()->emit_expr();
  847. ctx()->enter_block(CodeBlockType::CONTEXT_MANAGER);
  848. Expr_ as_name;
  849. if(match(TK("as"))){
  850. consume(TK("@id"));
  851. as_name = make_expr<NameExpr>(prev().str(), name_scope());
  852. }
  853. ctx()->emit_(OP_WITH_ENTER, BC_NOARG, prev().line);
  854. // [ <expr> <expr>.__enter__() ]
  855. if(as_name){
  856. bool ok = as_name->emit_store(ctx());
  857. if(!ok) SyntaxError();
  858. }else{
  859. ctx()->emit_(OP_POP_TOP, BC_NOARG, BC_KEEPLINE);
  860. }
  861. compile_block_body();
  862. ctx()->emit_(OP_WITH_EXIT, BC_NOARG, prev().line);
  863. ctx()->exit_block();
  864. } break;
  865. /*************************************************/
  866. case TK("=="): {
  867. consume(TK("@id"));
  868. if(mode()!=EXEC_MODE) SyntaxError("'label' is only available in EXEC_MODE");
  869. bool ok = ctx()->add_label(prev().str());
  870. consume(TK("=="));
  871. if(!ok) SyntaxError("label " + prev().str().escape() + " already exists");
  872. consume_end_stmt();
  873. } break;
  874. case TK("->"):
  875. consume(TK("@id"));
  876. if(mode()!=EXEC_MODE) SyntaxError("'goto' is only available in EXEC_MODE");
  877. ctx()->emit_(OP_GOTO, StrName(prev().sv()).index, prev().line);
  878. consume_end_stmt();
  879. break;
  880. /*************************************************/
  881. // handle dangling expression or assignment
  882. default: {
  883. advance(-1); // do revert since we have pre-called advance() at the beginning
  884. EXPR_TUPLE();
  885. bool is_typed_name = false; // e.g. x: int
  886. // eat variable's type hint if it is a single name
  887. if(ctx()->s_expr.top()->is_name()){
  888. if(match(TK(":"))){
  889. consume_type_hints();
  890. is_typed_name = true;
  891. if(ctx()->is_compiling_class){
  892. NameExpr* ne = static_cast<NameExpr*>(ctx()->s_expr.top().get());
  893. ctx()->emit_(OP_ADD_CLASS_ANNOTATION, ne->name.index, BC_KEEPLINE);
  894. }
  895. }
  896. }
  897. if(!try_compile_assignment()){
  898. if(!ctx()->s_expr.empty() && ctx()->s_expr.top()->is_starred()){
  899. SyntaxError();
  900. }
  901. if(!is_typed_name){
  902. ctx()->emit_expr();
  903. if((mode()==CELL_MODE || mode()==REPL_MODE) && name_scope()==NAME_GLOBAL){
  904. ctx()->emit_(OP_PRINT_EXPR, BC_NOARG, BC_KEEPLINE);
  905. }else{
  906. ctx()->emit_(OP_POP_TOP, BC_NOARG, BC_KEEPLINE);
  907. }
  908. }else{
  909. PK_ASSERT(ctx()->s_expr.size() == 1)
  910. ctx()->s_expr.pop();
  911. }
  912. }
  913. consume_end_stmt();
  914. }
  915. }
  916. }
  917. void Compiler::consume_type_hints(){
  918. EXPR();
  919. ctx()->s_expr.pop();
  920. }
  921. void Compiler::_add_decorators(const std::vector<Expr_>& decorators){
  922. // [obj]
  923. for(auto it=decorators.rbegin(); it!=decorators.rend(); ++it){
  924. (*it)->emit_(ctx()); // [obj, f]
  925. ctx()->emit_(OP_ROT_TWO, BC_NOARG, (*it)->line); // [f, obj]
  926. ctx()->emit_(OP_LOAD_NULL, BC_NOARG, BC_KEEPLINE); // [f, obj, NULL]
  927. ctx()->emit_(OP_ROT_TWO, BC_NOARG, BC_KEEPLINE); // [obj, NULL, f]
  928. ctx()->emit_(OP_CALL, 1, (*it)->line); // [obj]
  929. }
  930. }
  931. void Compiler::compile_class(const std::vector<Expr_>& decorators){
  932. consume(TK("@id"));
  933. int namei = StrName(prev().sv()).index;
  934. Expr_ base = nullptr;
  935. if(match(TK("("))){
  936. if(is_expression()){
  937. EXPR();
  938. base = ctx()->s_expr.popx();
  939. }
  940. consume(TK(")"));
  941. }
  942. if(base == nullptr){
  943. ctx()->emit_(OP_LOAD_NONE, BC_NOARG, prev().line);
  944. }else {
  945. base->emit_(ctx());
  946. }
  947. ctx()->emit_(OP_BEGIN_CLASS, namei, BC_KEEPLINE);
  948. for(auto& c: this->contexts.data()){
  949. if(c.is_compiling_class){
  950. SyntaxError("nested class is not allowed");
  951. }
  952. }
  953. ctx()->is_compiling_class = true;
  954. compile_block_body();
  955. ctx()->is_compiling_class = false;
  956. if(!decorators.empty()){
  957. ctx()->emit_(OP_BEGIN_CLASS_DECORATION, BC_NOARG, BC_KEEPLINE);
  958. _add_decorators(decorators);
  959. ctx()->emit_(OP_END_CLASS_DECORATION, BC_NOARG, BC_KEEPLINE);
  960. }
  961. ctx()->emit_(OP_END_CLASS, namei, BC_KEEPLINE);
  962. }
  963. void Compiler::_compile_f_args(FuncDecl_ decl, bool enable_type_hints){
  964. int state = 0; // 0 for args, 1 for *args, 2 for k=v, 3 for **kwargs
  965. do {
  966. if(state > 3) SyntaxError();
  967. if(state == 3) SyntaxError("**kwargs should be the last argument");
  968. match_newlines();
  969. if(match(TK("*"))){
  970. if(state < 1) state = 1;
  971. else SyntaxError("*args should be placed before **kwargs");
  972. }
  973. else if(match(TK("**"))){
  974. state = 3;
  975. }
  976. consume(TK("@id"));
  977. StrName name = prev().str();
  978. // check duplicate argument name
  979. for(int j: decl->args){
  980. if(decl->code->varnames[j] == name) {
  981. SyntaxError("duplicate argument name");
  982. }
  983. }
  984. for(auto& kv: decl->kwargs){
  985. if(decl->code->varnames[kv.index] == name){
  986. SyntaxError("duplicate argument name");
  987. }
  988. }
  989. if(decl->starred_arg!=-1 && decl->code->varnames[decl->starred_arg] == name){
  990. SyntaxError("duplicate argument name");
  991. }
  992. if(decl->starred_kwarg!=-1 && decl->code->varnames[decl->starred_kwarg] == name){
  993. SyntaxError("duplicate argument name");
  994. }
  995. // eat type hints
  996. if(enable_type_hints && match(TK(":"))) consume_type_hints();
  997. if(state == 0 && curr().type == TK("=")) state = 2;
  998. int index = ctx()->add_varname(name);
  999. switch (state)
  1000. {
  1001. case 0:
  1002. decl->args.push_back(index);
  1003. break;
  1004. case 1:
  1005. decl->starred_arg = index;
  1006. state+=1;
  1007. break;
  1008. case 2: {
  1009. consume(TK("="));
  1010. PyObject* value = read_literal();
  1011. if(value == nullptr){
  1012. SyntaxError(Str("default argument must be a literal"));
  1013. }
  1014. decl->add_kwarg(index, name, value);
  1015. } break;
  1016. case 3:
  1017. decl->starred_kwarg = index;
  1018. state+=1;
  1019. break;
  1020. }
  1021. } while (match(TK(",")));
  1022. }
  1023. void Compiler::compile_function(const std::vector<Expr_>& decorators){
  1024. const char* _start = curr().start;
  1025. consume(TK("@id"));
  1026. Str decl_name = prev().str();
  1027. FuncDecl_ decl = push_f_context(decl_name);
  1028. consume(TK("("));
  1029. if (!match(TK(")"))) {
  1030. _compile_f_args(decl, true);
  1031. consume(TK(")"));
  1032. }
  1033. if(match(TK("->"))) consume_type_hints();
  1034. const char* _end = curr().start;
  1035. decl->signature = Str(_start, _end-_start);
  1036. compile_block_body();
  1037. pop_context();
  1038. PyObject* docstring = nullptr;
  1039. if(decl->code->codes.size()>=2 && decl->code->codes[0].op == OP_LOAD_CONST && decl->code->codes[1].op == OP_POP_TOP){
  1040. PyObject* c = decl->code->consts[decl->code->codes[0].arg];
  1041. if(is_type(c, vm->tp_str)){
  1042. decl->code->codes[0].op = OP_NO_OP;
  1043. decl->code->codes[1].op = OP_NO_OP;
  1044. docstring = c;
  1045. }
  1046. }
  1047. if(docstring != nullptr){
  1048. decl->docstring = PK_OBJ_GET(Str, docstring);
  1049. }
  1050. ctx()->emit_(OP_LOAD_FUNCTION, ctx()->add_func_decl(decl), prev().line);
  1051. _add_decorators(decorators);
  1052. if(!ctx()->is_compiling_class){
  1053. auto e = make_expr<NameExpr>(decl_name, name_scope());
  1054. e->emit_store(ctx());
  1055. }else{
  1056. int index = StrName(decl_name).index;
  1057. ctx()->emit_(OP_STORE_CLASS_ATTR, index, prev().line);
  1058. }
  1059. }
  1060. PyObject* Compiler::to_object(const TokenValue& value){
  1061. PyObject* obj = nullptr;
  1062. if(std::holds_alternative<i64>(value)){
  1063. obj = VAR(std::get<i64>(value));
  1064. }
  1065. if(std::holds_alternative<f64>(value)){
  1066. obj = VAR(std::get<f64>(value));
  1067. }
  1068. if(std::holds_alternative<Str>(value)){
  1069. obj = VAR(std::get<Str>(value));
  1070. }
  1071. PK_ASSERT(obj != nullptr)
  1072. return obj;
  1073. }
  1074. PyObject* Compiler::read_literal(){
  1075. advance();
  1076. switch(prev().type){
  1077. case TK("-"): {
  1078. consume(TK("@num"));
  1079. PyObject* val = to_object(prev().value);
  1080. return vm->py_negate(val);
  1081. }
  1082. case TK("@num"): return to_object(prev().value);
  1083. case TK("@str"): return to_object(prev().value);
  1084. case TK("True"): return VAR(true);
  1085. case TK("False"): return VAR(false);
  1086. case TK("None"): return vm->None;
  1087. case TK("..."): return vm->Ellipsis;
  1088. case TK("("): {
  1089. List cpnts;
  1090. while(true) {
  1091. cpnts.push_back(read_literal());
  1092. if(curr().type == TK(")")) break;
  1093. consume(TK(","));
  1094. if(curr().type == TK(")")) break;
  1095. }
  1096. consume(TK(")"));
  1097. return VAR(Tuple(std::move(cpnts)));
  1098. }
  1099. default: break;
  1100. }
  1101. return nullptr;
  1102. }
  1103. Compiler::Compiler(VM* vm, std::string_view source, const Str& filename, CompileMode mode, bool unknown_global_scope){
  1104. this->vm = vm;
  1105. this->used = false;
  1106. this->unknown_global_scope = unknown_global_scope;
  1107. this->lexer = std::make_unique<Lexer>(
  1108. vm, std::make_shared<SourceData>(source, filename, mode)
  1109. );
  1110. init_pratt_rules();
  1111. }
  1112. CodeObject_ Compiler::compile(){
  1113. PK_ASSERT(!used)
  1114. used = true;
  1115. tokens = lexer->run();
  1116. CodeObject_ code = push_global_context();
  1117. advance(); // skip @sof, so prev() is always valid
  1118. match_newlines(); // skip possible leading '\n'
  1119. if(mode()==EVAL_MODE) {
  1120. EXPR_TUPLE(); ctx()->emit_expr();
  1121. consume(TK("@eof"));
  1122. ctx()->emit_(OP_RETURN_VALUE, BC_NOARG, BC_KEEPLINE);
  1123. pop_context();
  1124. return code;
  1125. }else if(mode()==JSON_MODE){
  1126. EXPR();
  1127. Expr_ e = ctx()->s_expr.popx();
  1128. if(!e->is_json_object()) SyntaxError("expect a JSON object, literal or array");
  1129. consume(TK("@eof"));
  1130. e->emit_(ctx());
  1131. ctx()->emit_(OP_RETURN_VALUE, BC_NOARG, BC_KEEPLINE);
  1132. pop_context();
  1133. return code;
  1134. }
  1135. while (!match(TK("@eof"))) {
  1136. compile_stmt();
  1137. match_newlines();
  1138. }
  1139. pop_context();
  1140. return code;
  1141. }
  1142. // TODO: refactor this
  1143. void Lexer::throw_err(StrName type, Str msg, int lineno, const char* cursor){
  1144. PyObject* e_obj = vm->call(vm->builtins->attr(type), VAR(msg));
  1145. Exception& e = PK_OBJ_GET(Exception, e_obj);
  1146. e.st_push(src, lineno, cursor, "");
  1147. throw e;
  1148. }
  1149. } // namespace pkpy