vm.cpp 66 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924
  1. #include "pocketpy/interpreter/vm.hpp"
  2. #include "pocketpy/common/memorypool.h"
  3. #include "pocketpy/objects/base.h"
  4. #include "pocketpy/objects/public.h"
  5. #include <cstddef>
  6. #include <iostream>
  7. #include <cmath>
  8. #include <stdexcept>
  9. #if PK_DEBUG_CEVAL_STEP
  10. #include <map>
  11. #endif
  12. const static char* OP_NAMES[] = {
  13. #define OPCODE(name) #name,
  14. #include "pocketpy/xmacros/opcodes.h"
  15. #undef OPCODE
  16. };
  17. namespace pkpy {
  18. struct JsonSerializer {
  19. VM* vm;
  20. PyVar root;
  21. SStream ss;
  22. JsonSerializer(VM* vm, PyVar root) : vm(vm), root(root) {}
  23. template <typename T>
  24. void write_array(T& arr) {
  25. ss << '[';
  26. for(int i = 0; i < arr.size(); i++) {
  27. if(i != 0) ss << ", ";
  28. write_object(arr[i]);
  29. }
  30. ss << ']';
  31. }
  32. void write_dict(Dict& dict) {
  33. ss << '{';
  34. bool first = true;
  35. dict.apply([&](PyVar k, PyVar v) {
  36. if(!first) ss << ", ";
  37. first = false;
  38. if(!is_type(k, VM::tp_str)) {
  39. vm->TypeError(_S("json keys must be string, got ", _type_name(vm, vm->_tp(k))));
  40. }
  41. ss << _CAST(Str&, k).escape('"') << ": ";
  42. write_object(v);
  43. });
  44. ss << '}';
  45. }
  46. void write_object(PyVar obj) {
  47. Type obj_t = vm->_tp(obj);
  48. if(is_none(obj)) {
  49. ss << "null";
  50. } else if(obj_t == vm->tp_int) {
  51. ss << _CAST(i64, obj);
  52. } else if(obj_t == vm->tp_float) {
  53. f64 val = _CAST(f64, obj);
  54. if(std::isinf(val) || std::isnan(val)) vm->ValueError("cannot jsonify 'nan' or 'inf'");
  55. ss << val;
  56. } else if(obj_t == vm->tp_bool) {
  57. ss << (obj.extra ? "true" : "false");
  58. } else if(obj_t == vm->tp_str) {
  59. ss << _CAST(Str&, obj).escape('"');
  60. } else if(obj_t == vm->tp_list) {
  61. write_array<List>(_CAST(List&, obj));
  62. } else if(obj_t == vm->tp_tuple) {
  63. write_array<Tuple>(_CAST(Tuple&, obj));
  64. } else if(obj_t == vm->tp_dict) {
  65. write_dict(_CAST(Dict&, obj));
  66. } else {
  67. vm->TypeError(_S("unrecognized type ", _type_name(vm, obj_t).escape()));
  68. }
  69. }
  70. Str serialize() {
  71. auto _lock = vm->gc_scope_lock();
  72. write_object(root);
  73. return ss.str();
  74. }
  75. };
  76. VM::VM(bool enable_os) : enable_os(enable_os) {
  77. pkpy_g.vm = (pkpy_VM*)this; // setup the current VM
  78. Pools_initialize();
  79. pkpy_StrName__initialize();
  80. pk_ManagedHeap__ctor(&heap, (pkpy_VM*)this);
  81. static ::PyObject __true_obj = {tp_bool, false, false, NULL};
  82. static ::PyObject __false_obj = {tp_bool, false, false, NULL};
  83. static ::PyObject __none_obj = {tp_none_type, false, false, NULL};
  84. static ::PyObject __not_implemented_obj = {tp_not_implemented_type, false, false, NULL};
  85. static ::PyObject __ellipsis_obj = {tp_ellipsis, false, false, NULL};
  86. /* Must be heap objects to support `==` and `is` and `is not` */
  87. True.type = tp_bool; True.is_ptr = true; True.extra = 1; True._obj = &__true_obj;
  88. False.type = tp_bool; False.is_ptr = true; False.extra = 0; False._obj = &__false_obj;
  89. None.type = tp_none_type; None.is_ptr = true; None._obj = &__none_obj;
  90. NotImplemented.type = tp_not_implemented_type; NotImplemented.is_ptr = true; NotImplemented._obj = &__not_implemented_obj;
  91. Ellipsis.type = tp_ellipsis; Ellipsis.is_ptr = true; Ellipsis._obj = &__ellipsis_obj;
  92. this->vm = this;
  93. this->__c.error = nullptr;
  94. _ceval_on_step = nullptr;
  95. _stdout = [](const char* buf, int size) {
  96. std::cout.write(buf, size);
  97. };
  98. _stderr = [](const char* buf, int size) {
  99. std::cerr.write(buf, size);
  100. };
  101. builtins = nullptr;
  102. _main = nullptr;
  103. __last_exception = nullptr;
  104. _import_handler = [](const char* name, int* out_size) -> unsigned char* {
  105. return nullptr;
  106. };
  107. __init_builtin_types();
  108. }
  109. Str VM::py_str(PyVar obj) {
  110. const PyTypeInfo* ti = _tp_info(obj);
  111. if(ti->m__str__) return ti->m__str__(this, obj);
  112. PyVar self;
  113. PyVar f = get_unbound_method(obj, __str__, &self, false);
  114. if(self) {
  115. PyVar retval = call_method(self, f);
  116. if(!is_type(retval, tp_str)) { throw std::runtime_error("object.__str__ must return str"); }
  117. return PK_OBJ_GET(Str, retval);
  118. }
  119. return py_repr(obj);
  120. }
  121. Str VM::py_repr(PyVar obj) {
  122. const PyTypeInfo* ti = _tp_info(obj);
  123. if(ti->m__repr__) return ti->m__repr__(this, obj);
  124. PyVar retval = call_method(obj, __repr__);
  125. if(!is_type(retval, tp_str)) { throw std::runtime_error("object.__repr__ must return str"); }
  126. return PK_OBJ_GET(Str, retval);
  127. }
  128. Str VM::py_json(PyVar obj) {
  129. JsonSerializer j(this, obj);
  130. return j.serialize();
  131. }
  132. PyVar VM::py_iter(PyVar obj) {
  133. const PyTypeInfo* ti = _tp_info(obj);
  134. if(ti->m__iter__) return ti->m__iter__(this, obj);
  135. PyVar self;
  136. PyVar iter_f = get_unbound_method(obj, __iter__, &self, false);
  137. if(self) return call_method(self, iter_f);
  138. TypeError(_type_name(vm, _tp(obj)).escape() + " object is not iterable");
  139. return nullptr;
  140. }
  141. ArgsView VM::cast_array_view(PyVar obj) {
  142. if(is_type(obj, VM::tp_list)) {
  143. List& list = PK_OBJ_GET(List, obj);
  144. return ArgsView(list.begin(), list.end());
  145. } else if(is_type(obj, VM::tp_tuple)) {
  146. Tuple& tuple = PK_OBJ_GET(Tuple, obj);
  147. return ArgsView(tuple.begin(), tuple.end());
  148. }
  149. TypeError(_S("expected list or tuple, got ", _type_name(this, _tp(obj)).escape()));
  150. }
  151. void VM::set_main_argv(int argc, char** argv) {
  152. PyVar mod = vm->_modules["sys"];
  153. List argv_(argc);
  154. for(int i = 0; i < argc; i++)
  155. argv_[i] = VAR(std::string_view(argv[i]));
  156. mod->attr().set("argv", VAR(std::move(argv_)));
  157. }
  158. PyVar* VM::find_name_in_mro(Type cls, StrName name) {
  159. PyVar* val;
  160. do {
  161. val = _t(cls)->attr().try_get_2(name);
  162. if(val != nullptr) return val;
  163. cls = _all_types[cls].base;
  164. if(!cls) break;
  165. } while(true);
  166. return nullptr;
  167. }
  168. bool VM::isinstance(PyVar obj, Type base) { return issubclass(_tp(obj), base); }
  169. bool VM::issubclass(Type cls, Type base) {
  170. do {
  171. if(cls == base) return true;
  172. Type next = _all_types[cls].base;
  173. if(!next) break;
  174. cls = next;
  175. } while(true);
  176. return false;
  177. }
  178. PyVar VM::exec(std::string_view source, Str filename, CompileMode mode, PyObject* _module) {
  179. if(_module == nullptr) _module = _main;
  180. try {
  181. #if PK_DEBUG_PRECOMPILED_EXEC == 1
  182. Str precompiled = vm->precompile(source, filename, mode);
  183. source = precompiled.sv();
  184. #endif
  185. CodeObject_ code = compile(source, filename, mode);
  186. return _exec(code, _module);
  187. } catch(TopLevelException e) {
  188. stderr_write(e.summary() + "\n");
  189. } catch(const std::exception& e) {
  190. Str msg = "An std::exception occurred! It could be a bug.\n";
  191. msg = msg + e.what() + "\n";
  192. stderr_write(msg);
  193. } catch(NeedMoreLines) { throw; } catch(...) {
  194. Str msg = "An unknown exception occurred! It could be a bug. Please report it to @blueloveTH on GitHub.\n";
  195. stderr_write(msg);
  196. }
  197. callstack.clear();
  198. s_data.clear();
  199. return nullptr;
  200. }
  201. PyVar VM::exec(std::string_view source) { return exec(source, "main.py", EXEC_MODE); }
  202. PyVar VM::eval(std::string_view source) { return exec(source, "<eval>", EVAL_MODE); }
  203. PyObject* VM::new_type_object(PyObject* mod, StrName name, Type base, bool subclass_enabled, PyTypeInfo::Vt vt) {
  204. PyObject* obj = new_object_no_gc<Type>(tp_type, Type(_all_types.size())).get();
  205. const PyTypeInfo& base_info = _all_types[base];
  206. if(!base_info.subclass_enabled) {
  207. Str error = _S("type ", base_info.name.escape(), " is not `subclass_enabled`");
  208. throw std::runtime_error(error.c_str());
  209. }
  210. if(base_info.vt) {
  211. if(vt) {
  212. Str error = _S("type ", base_info.name.escape(), " has a custom vtable, cannot override");
  213. throw std::runtime_error(error.c_str());
  214. } else {
  215. // promote base vt to its subclass
  216. vt = base_info.vt;
  217. }
  218. }
  219. _all_types.emplace_back(obj, base, mod, name, subclass_enabled, vt);
  220. return obj;
  221. }
  222. bool VM::py_eq(PyVar lhs, PyVar rhs) {
  223. if(is_int(lhs) && is_int(rhs)) return lhs._i64 == rhs._i64;
  224. const PyTypeInfo* ti = _tp_info(lhs);
  225. PyVar res;
  226. if(ti->m__eq__) {
  227. res = ti->m__eq__(this, lhs, rhs);
  228. if(!is_not_implemented(res)) return res.extra;
  229. }
  230. res = call_method(lhs, __eq__, rhs);
  231. if(!is_not_implemented(res)) return res.extra;
  232. ti = _tp_info(rhs);
  233. if(ti->m__eq__) {
  234. res = ti->m__eq__(this, rhs, lhs);
  235. if(!is_not_implemented(res)) return res.extra;
  236. }
  237. res = call_method(rhs, __eq__, lhs);
  238. if(!is_not_implemented(res)) return res.extra;
  239. return false;
  240. }
  241. PyVar VM::py_op(std::string_view name) {
  242. // TODO: cache the result
  243. return py_import("operator")->attr()[StrName::get(name)];
  244. }
  245. i64 VM::normalized_index(i64 index, int size) {
  246. if(index < 0) index += size;
  247. if(index < 0 || index >= size) { IndexError(std::to_string(index) + " not in [0, " + std::to_string(size) + ")"); }
  248. return index;
  249. }
  250. PyVar VM::_py_next(const PyTypeInfo* ti, PyVar obj) {
  251. if(ti->op__next__) {
  252. unsigned n = ti->op__next__(this, obj);
  253. return __pack_next_retval(n);
  254. }
  255. return call_method(obj, __next__);
  256. }
  257. PyVar VM::py_next(PyVar obj) {
  258. const PyTypeInfo* ti = _tp_info(obj);
  259. return _py_next(ti, obj);
  260. }
  261. bool VM::py_callable(PyVar obj) {
  262. Type cls = vm->_tp(obj);
  263. switch(cls) {
  264. case VM::tp_function: return true;
  265. case VM::tp_native_func: return true;
  266. case VM::tp_bound_method: return true;
  267. case VM::tp_type: return true;
  268. }
  269. return vm->find_name_in_mro(cls, __call__) != nullptr;
  270. }
  271. PyVar VM::__minmax_reduce(bool (VM::*op)(PyVar, PyVar), PyVar args, PyVar key) {
  272. auto _lock = gc_scope_lock();
  273. const Tuple& args_tuple = PK_OBJ_GET(Tuple, args); // from *args, it must be a tuple
  274. if(is_none(key) && args_tuple.size() == 2) {
  275. // fast path
  276. PyVar a = args_tuple[0];
  277. PyVar b = args_tuple[1];
  278. return (this->*op)(a, b) ? a : b;
  279. }
  280. if(args_tuple.size() == 0) TypeError("expected at least 1 argument, got 0");
  281. ArgsView view(nullptr, nullptr);
  282. if(args_tuple.size() == 1) {
  283. view = cast_array_view(args_tuple[0]);
  284. } else {
  285. view = ArgsView(args_tuple);
  286. }
  287. if(view.empty()) ValueError("arg is an empty sequence");
  288. PyVar res = view[0];
  289. if(is_none(key)) {
  290. for(int i = 1; i < view.size(); i++) {
  291. if((this->*op)(view[i], res)) res = view[i];
  292. }
  293. } else {
  294. auto _lock = gc_scope_lock();
  295. for(int i = 1; i < view.size(); i++) {
  296. PyVar a = call(key, view[i]);
  297. PyVar b = call(key, res);
  298. if((this->*op)(a, b)) res = view[i];
  299. }
  300. }
  301. return res;
  302. }
  303. PyObject* VM::py_import(Str path, bool throw_err) {
  304. if(path.empty()) vm->ValueError("empty module name");
  305. static auto f_join = [](const vector<std::string_view>& cpnts) {
  306. SStream ss;
  307. for(int i = 0; i < cpnts.size(); i++) {
  308. if(i != 0) ss << ".";
  309. ss << cpnts[i];
  310. }
  311. return ss.str();
  312. };
  313. if(path[0] == '.') {
  314. if(__import_context.pending.empty()) { ImportError("relative import outside of package"); }
  315. Str curr_path = __import_context.pending.back();
  316. bool curr_is_init = __import_context.pending_is_init.back();
  317. // convert relative path to absolute path
  318. vector<std::string_view> cpnts = curr_path.split('.');
  319. int prefix = 0; // how many dots in the prefix
  320. for(int i = 0; i < path.length(); i++) {
  321. if(path[i] == '.')
  322. prefix++;
  323. else
  324. break;
  325. }
  326. if(prefix > cpnts.size()) ImportError("attempted relative import beyond top-level package");
  327. path = path.substr(prefix); // remove prefix
  328. for(int i = (int)curr_is_init; i < prefix; i++)
  329. cpnts.pop_back();
  330. if(!path.empty()) cpnts.push_back(path.sv());
  331. path = f_join(cpnts);
  332. }
  333. assert(path.begin()[0] != '.' && path.end()[-1] != '.');
  334. // check existing module
  335. StrName name(path);
  336. PyVar ext_mod = _modules.try_get(name);
  337. if(ext_mod) return ext_mod.get();
  338. vector<std::string_view> path_cpnts = path.split('.');
  339. // check circular import
  340. if(__import_context.pending.size() > 128) { ImportError("maximum recursion depth exceeded while importing"); }
  341. // try import
  342. Str filename = path.replace('.', PK_PLATFORM_SEP) + ".py";
  343. Str source;
  344. bool is_init = false;
  345. auto it = _lazy_modules.try_get(name);
  346. if(it == nullptr) {
  347. int out_size;
  348. unsigned char* out = _import_handler(filename.c_str(), &out_size);
  349. if(out == nullptr) {
  350. filename = path.replace('.', PK_PLATFORM_SEP).str() + PK_PLATFORM_SEP + "__init__.py";
  351. is_init = true;
  352. out = _import_handler(filename.c_str(), &out_size);
  353. }
  354. if(out == nullptr) {
  355. if(throw_err)
  356. ImportError(_S("module ", path.escape(), " not found"));
  357. else
  358. return nullptr;
  359. }
  360. assert(out_size >= 0);
  361. source = Str(std::string_view((char*)out, out_size));
  362. std::free(out);
  363. } else {
  364. source = *it;
  365. // _lazy_modules.erase(it); // no need to erase
  366. }
  367. auto _ = __import_context.scope(path, is_init);
  368. CodeObject_ code = compile(source, filename, EXEC_MODE);
  369. Str name_cpnt = path_cpnts.back();
  370. path_cpnts.pop_back();
  371. PyObject* new_mod = new_module(name_cpnt, f_join(path_cpnts));
  372. _exec(code, new_mod);
  373. return new_mod;
  374. }
  375. VM::~VM() {
  376. // destroy all objects
  377. pk_ManagedHeap__dtor(&heap);
  378. // clear everything
  379. callstack.clear();
  380. s_data.clear();
  381. _all_types.clear();
  382. _modules.clear();
  383. _lazy_modules.clear();
  384. }
  385. PyVar VM::py_negate(PyVar obj) {
  386. const PyTypeInfo* ti = _tp_info(obj);
  387. if(ti->m__neg__) return ti->m__neg__(this, obj);
  388. return call_method(obj, __neg__);
  389. }
  390. bool VM::__py_bool_non_trivial(PyVar obj) {
  391. if(is_none(obj)) return false;
  392. if(is_int(obj)) return _CAST(i64, obj) != 0;
  393. if(is_float(obj)) return _CAST(f64, obj) != 0.0;
  394. PyVar self;
  395. PyVar len_f = get_unbound_method(obj, __len__, &self, false);
  396. if(self) {
  397. PyVar ret = call_method(self, len_f);
  398. return CAST(i64, ret) != 0;
  399. }
  400. return true;
  401. }
  402. void VM::__obj_gc_mark(PyObject* obj) {
  403. if(obj->gc_marked) return;
  404. obj->gc_marked = true;
  405. const PyTypeInfo* ti = _tp_info(obj->type);
  406. if(ti->vt._gc_mark) ti->vt._gc_mark(obj->_value_ptr(), this);
  407. if(obj->is_attr_valid()) {
  408. obj->attr().apply([](StrName _, PyVar obj, void* userdata) {
  409. VM* vm = (VM*)userdata;
  410. if(obj.is_ptr) vm->__obj_gc_mark((obj).get());
  411. }, vm);
  412. }
  413. }
  414. void VM::__stack_gc_mark(PyVar* begin, PyVar* end) {
  415. for(PyVar* it = begin; it != end; it++) {
  416. if(it->is_ptr) {
  417. __obj_gc_mark(it->get());
  418. }
  419. }
  420. }
  421. List VM::py_list(PyVar it) {
  422. auto _lock = gc_scope_lock();
  423. it = py_iter(it);
  424. List list;
  425. const PyTypeInfo* info = _tp_info(it);
  426. PyVar obj = _py_next(info, it);
  427. while(obj != StopIteration) {
  428. list.push_back(obj);
  429. obj = _py_next(info, it);
  430. }
  431. return list;
  432. }
  433. void VM::parse_int_slice(const Slice& s, int length, int& start, int& stop, int& step) {
  434. auto clip = [](int value, int min, int max) {
  435. if(value < min) return min;
  436. if(value > max) return max;
  437. return value;
  438. };
  439. if(is_none(s.step))
  440. step = 1;
  441. else
  442. step = CAST(int, s.step);
  443. if(step == 0) ValueError("slice step cannot be zero");
  444. if(step > 0) {
  445. if(is_none(s.start)) {
  446. start = 0;
  447. } else {
  448. start = CAST(int, s.start);
  449. if(start < 0) start += length;
  450. start = clip(start, 0, length);
  451. }
  452. if(is_none(s.stop)) {
  453. stop = length;
  454. } else {
  455. stop = CAST(int, s.stop);
  456. if(stop < 0) stop += length;
  457. stop = clip(stop, 0, length);
  458. }
  459. } else {
  460. if(is_none(s.start)) {
  461. start = length - 1;
  462. } else {
  463. start = CAST(int, s.start);
  464. if(start < 0) start += length;
  465. start = clip(start, -1, length - 1);
  466. }
  467. if(is_none(s.stop)) {
  468. stop = -1;
  469. } else {
  470. stop = CAST(int, s.stop);
  471. if(stop < 0) stop += length;
  472. stop = clip(stop, -1, length - 1);
  473. }
  474. }
  475. }
  476. i64 VM::py_hash(PyVar obj) {
  477. // https://docs.python.org/3.10/reference/datamodel.html#object.__hash__
  478. const PyTypeInfo* ti = _tp_info(obj);
  479. if(ti->m__hash__) return ti->m__hash__(this, obj);
  480. PyVar self;
  481. PyVar f = get_unbound_method(obj, __hash__, &self, false);
  482. if(f) {
  483. PyVar ret = call_method(self, f);
  484. return CAST(i64, ret);
  485. }
  486. // if it is trivial `object`, return PK_BITS
  487. if(ti == &_all_types[tp_object]) return obj.hash();
  488. // otherwise, we check if it has a custom __eq__ other than object.__eq__
  489. bool has_custom_eq = false;
  490. if(ti->m__eq__)
  491. has_custom_eq = true;
  492. else {
  493. f = get_unbound_method(obj, __eq__, &self, false);
  494. PyVar base_eq = _t(tp_object)->attr()[__eq__];
  495. has_custom_eq = !PyVar__IS_OP(&f, &base_eq);
  496. }
  497. if(has_custom_eq) {
  498. TypeError(_S("unhashable type: ", ti->name.escape()));
  499. } else {
  500. return obj.hash();
  501. }
  502. }
  503. PyVar VM::__py_exec_internal(const CodeObject_& code, PyVar globals, PyVar locals) {
  504. Frame* frame = nullptr;
  505. if(!callstack.empty()) frame = &callstack.top();
  506. // fast path
  507. if(frame && is_none(globals) && is_none(locals)) {
  508. return vm->_exec(code.get(), frame->_module, frame->_callable, frame->_locals);
  509. }
  510. auto _lock = gc_scope_lock(); // for safety
  511. PyObject* globals_obj = nullptr;
  512. Dict* globals_dict = nullptr;
  513. NameDict* locals_closure = nullptr;
  514. Dict* locals_dict = nullptr;
  515. if(is_none(globals)){
  516. globals_obj = frame ? frame->_module: _main;
  517. } else {
  518. if(is_type(globals, VM::tp_mappingproxy)) {
  519. globals_obj = PK_OBJ_GET(MappingProxy, globals).obj;
  520. } else {
  521. check_compatible_type(globals, VM::tp_dict);
  522. // make a temporary object and copy globals into it
  523. globals_obj = new_object<DummyInstance>(VM::tp_object).get();
  524. globals_dict = &PK_OBJ_GET(Dict, globals);
  525. globals_dict->apply([&](PyVar k, PyVar v) {
  526. globals_obj->attr().set(CAST(Str&, k), v);
  527. });
  528. }
  529. }
  530. PyVar retval = nullptr;
  531. if(is_none(locals)) {
  532. retval = vm->_exec(code, globals_obj); // only globals
  533. } else {
  534. check_compatible_type(locals, VM::tp_dict);
  535. locals_dict = &PK_OBJ_GET(Dict, locals);
  536. locals_closure = new NameDict();
  537. locals_dict->apply([&](PyVar k, PyVar v) {
  538. locals_closure->set(CAST(Str&, k), v);
  539. });
  540. PyObject* _callable =
  541. new_object<Function>(tp_function, __dynamic_func_decl, globals_obj, nullptr, locals_closure).get();
  542. retval = vm->_exec(code.get(), globals_obj, _callable, vm->s_data._sp);
  543. }
  544. if(globals_dict) {
  545. globals_dict->clear();
  546. for(auto [k, v]: globals_obj->attr().items()){
  547. globals_dict->set(vm, VAR(k.sv()), v);
  548. }
  549. }
  550. if(locals_dict) {
  551. locals_dict->clear();
  552. for(auto [k, v]: locals_closure->items()){
  553. locals_dict->set(vm, VAR(k.sv()), v);
  554. }
  555. }
  556. return retval;
  557. }
  558. void VM::py_exec(std::string_view source, PyVar globals, PyVar locals) {
  559. CodeObject_ code = vm->compile(source, "<exec>", EXEC_MODE, true);
  560. __py_exec_internal(code, globals, locals);
  561. }
  562. PyVar VM::py_eval(std::string_view source, PyVar globals, PyVar locals) {
  563. CodeObject_ code = vm->compile(source, "<eval>", EVAL_MODE, true);
  564. return __py_exec_internal(code, globals, locals);
  565. }
  566. PyVar VM::__format_object(PyVar obj, Str spec) {
  567. if(spec.empty()) return VAR(py_str(obj));
  568. char type;
  569. switch(spec.end()[-1]) {
  570. case 'f':
  571. case 'd':
  572. case 's':
  573. type = spec.end()[-1];
  574. spec = spec.slice(0, spec.length() - 1);
  575. break;
  576. default: type = ' '; break;
  577. }
  578. char pad_c = ' ';
  579. for(char c: std::string_view("0-=*#@!~")) {
  580. if(spec[0] == c) {
  581. pad_c = c;
  582. spec = spec.substr(1);
  583. break;
  584. }
  585. }
  586. char align;
  587. if(spec[0] == '^') {
  588. align = '^';
  589. spec = spec.substr(1);
  590. } else if(spec[0] == '>') {
  591. align = '>';
  592. spec = spec.substr(1);
  593. } else if(spec[0] == '<') {
  594. align = '<';
  595. spec = spec.substr(1);
  596. } else {
  597. if(is_int(obj) || is_float(obj))
  598. align = '>';
  599. else
  600. align = '<';
  601. }
  602. int dot = spec.index(".");
  603. int width, precision;
  604. try {
  605. if(dot >= 0) {
  606. if(dot == 0) {
  607. width = -1;
  608. } else {
  609. width = std::stoi(spec.slice(0, dot).str());
  610. }
  611. precision = std::stoi(spec.slice(dot + 1).str());
  612. } else {
  613. width = std::stoi(spec.str());
  614. precision = -1;
  615. }
  616. } catch(...) { ValueError("invalid format specifer"); }
  617. if(type != 'f' && dot >= 0) ValueError("precision not allowed in the format specifier");
  618. Str ret;
  619. if(type == 'f') {
  620. f64 val = CAST(f64, obj);
  621. if(precision < 0) precision = 6;
  622. SStream ss;
  623. ss.setprecision(precision);
  624. ss << val;
  625. ret = ss.str();
  626. } else if(type == 'd') {
  627. ret = std::to_string(CAST(i64, obj));
  628. } else if(type == 's') {
  629. ret = CAST(Str&, obj);
  630. } else {
  631. ret = py_str(obj);
  632. }
  633. if(width != -1 && width > ret.length()) {
  634. int pad = width - ret.length();
  635. if(align == '>' || align == '<') {
  636. std::string padding(pad, pad_c);
  637. if(align == '>')
  638. ret = padding.c_str() + ret;
  639. else
  640. ret = ret + padding.c_str();
  641. } else { // ^
  642. int pad_left = pad / 2;
  643. int pad_right = pad - pad_left;
  644. std::string padding_left(pad_left, pad_c);
  645. std::string padding_right(pad_right, pad_c);
  646. ret = padding_left.c_str() + ret + padding_right.c_str();
  647. }
  648. }
  649. return VAR(ret);
  650. }
  651. PyObject* VM::new_module(Str name, Str package) {
  652. PyObject* obj = new_object_no_gc<DummyModule>(tp_module).get();
  653. obj->attr().set(__name__, VAR(name));
  654. obj->attr().set(__package__, VAR(package));
  655. // convert to fullname
  656. if(!package.empty()) name = package + "." + name;
  657. obj->attr().set(__path__, VAR(name));
  658. // we do not allow override in order to avoid memory leak
  659. // it is because Module objects are not garbage collected
  660. if(_modules.contains(name)) { throw std::runtime_error(_S("module ", name.escape(), " already exists").str()); }
  661. // set it into _modules
  662. _modules.set(name, obj);
  663. return obj;
  664. }
  665. static std::string _opcode_argstr(VM* vm, int i, Bytecode byte, const CodeObject* co) {
  666. SStream ss;
  667. if(byte.is_forward_jump()) {
  668. std::string argStr = std::to_string((int16_t)byte.arg);
  669. ss << (i64)(int16_t)byte.arg;
  670. ss << " (to " << (i64)((int16_t)byte.arg + i) << ")";
  671. return ss.str().str();
  672. }
  673. ss << (i64)byte.arg;
  674. switch(byte.op) {
  675. case OP_LOAD_CONST:
  676. case OP_FORMAT_STRING:
  677. case OP_IMPORT_PATH:
  678. if(vm != nullptr) ss << " (" << vm->py_repr(co->consts[byte.arg]) << ")";
  679. break;
  680. case OP_LOAD_NAME:
  681. case OP_LOAD_GLOBAL:
  682. case OP_LOAD_NONLOCAL:
  683. case OP_STORE_GLOBAL:
  684. case OP_LOAD_ATTR:
  685. case OP_LOAD_METHOD:
  686. case OP_STORE_ATTR:
  687. case OP_DELETE_ATTR:
  688. case OP_BEGIN_CLASS:
  689. case OP_GOTO:
  690. case OP_DELETE_GLOBAL:
  691. case OP_STORE_CLASS_ATTR:
  692. case OP_FOR_ITER_STORE_GLOBAL: ss << " (" << StrName(byte.arg).sv() << ")"; break;
  693. case OP_LOAD_FAST:
  694. case OP_STORE_FAST:
  695. case OP_DELETE_FAST:
  696. case OP_FOR_ITER_STORE_FAST:
  697. case OP_LOAD_SUBSCR_FAST:
  698. case OP_STORE_SUBSCR_FAST: ss << " (" << co->varnames[byte.arg].sv() << ")"; break;
  699. case OP_LOAD_FUNCTION: ss << " (" << co->func_decls[byte.arg]->code->name << ")"; break;
  700. }
  701. return ss.str().str();
  702. }
  703. Str VM::disassemble(CodeObject_ co) {
  704. auto pad = [](const Str& s, const int n) {
  705. if(s.length() >= n) return s.slice(0, n);
  706. return s + std::string(n - s.length(), ' ');
  707. };
  708. vector<int> jumpTargets;
  709. for(int i = 0; i < co->codes.size(); i++) {
  710. Bytecode byte = co->codes[i];
  711. if(byte.is_forward_jump()) { jumpTargets.push_back((int16_t)byte.arg + i); }
  712. }
  713. SStream ss;
  714. int prev_line = -1;
  715. for(int i = 0; i < co->codes.size(); i++) {
  716. const Bytecode& byte = co->codes[i];
  717. Str line = std::to_string(co->lines[i].lineno);
  718. if(co->lines[i].lineno == prev_line)
  719. line = "";
  720. else {
  721. if(prev_line != -1) ss << "\n";
  722. prev_line = co->lines[i].lineno;
  723. }
  724. std::string pointer;
  725. if(jumpTargets.contains(i)) {
  726. pointer = "-> ";
  727. } else {
  728. pointer = " ";
  729. }
  730. ss << pad(line, 8) << pointer << pad(std::to_string(i), 3);
  731. std::string bc_name(OP_NAMES[byte.op]);
  732. if(co->lines[i].is_virtual) bc_name += '*';
  733. ss << " " << pad(bc_name, 25) << " ";
  734. std::string argStr = _opcode_argstr(this, i, byte, co.get());
  735. ss << argStr;
  736. if(i != co->codes.size() - 1) ss << '\n';
  737. }
  738. for(auto& decl: co->func_decls) {
  739. ss << "\n\n"
  740. << "Disassembly of " << decl->code->name << ":\n";
  741. ss << disassemble(decl->code);
  742. }
  743. ss << "\n";
  744. return Str(ss.str());
  745. }
  746. #if PK_DEBUG_CEVAL_STEP
  747. void VM::__log_s_data(const char* title) {
  748. if(_main == nullptr) return;
  749. if(callstack.empty()) return;
  750. SStream ss;
  751. if(title) ss << title << " | ";
  752. std::map<PyVar*, int> sp_bases;
  753. callstack.apply([&](Frame& f) {
  754. assert(f._sp_base != nullptr);
  755. sp_bases[f._sp_base] += 1;
  756. });
  757. Frame* frame = &callstack.top();
  758. int line = frame->curr_lineno();
  759. ss << frame->co->name << ":" << line << " [";
  760. for(PyVar* p = s_data.begin(); p != s_data.end(); p++) {
  761. ss << std::string(sp_bases[p], '|');
  762. if(sp_bases[p] > 0) ss << " ";
  763. if(!(*p))
  764. ss << "NULL";
  765. else {
  766. switch(p->type) {
  767. case tp_none_type: ss << "None"; break;
  768. case tp_int: ss << _CAST(i64, *p); break;
  769. case tp_float: ss << _CAST(f64, *p); break;
  770. case tp_bool: ss << (p->_bool ? "True" : "False"); break;
  771. case tp_str: ss << _CAST(Str, *p).escape(); break;
  772. case tp_function: ss << p->obj_get<Function>().decl->code->name << "()"; break;
  773. case tp_type: ss << "<class " + _type_name(this, p->obj_get<Type>()).escape() + ">"; break;
  774. case tp_list: ss << "list(size=" << p->obj_get<List>().size() << ")"; break;
  775. case tp_tuple: ss << "tuple(size=" << p->obj_get<Tuple>().size() << ")"; break;
  776. default: ss << "(" << _type_name(this, p->type) << ")"; break;
  777. }
  778. }
  779. ss << ", ";
  780. }
  781. std::string output = ss.str().str();
  782. if(!s_data.empty()) {
  783. output.pop_back();
  784. output.pop_back();
  785. }
  786. output.push_back(']');
  787. Bytecode byte = *frame->_ip;
  788. std::cout << output << " " << OP_NAMES[byte.op] << " " << _opcode_argstr(nullptr, frame->ip(), byte, frame->co)
  789. << std::endl;
  790. }
  791. #endif
  792. void VM::__init_builtin_types() {
  793. _all_types.emplace_back(nullptr, Type(), nullptr, "", false); // 0 is not used
  794. _all_types.emplace_back(new_object_no_gc<Type>(tp_type, tp_object).get(), Type(), nullptr, "object", true);
  795. _all_types.emplace_back(new_object_no_gc<Type>(tp_type, tp_type).get(), tp_object, nullptr, "type", false);
  796. auto validate = [](Type type, PyObject* ret) {
  797. Type ret_t = ret->as<Type>();
  798. if(ret_t != type) exit(-3);
  799. };
  800. validate(tp_int, new_type_object(nullptr, "int", tp_object, false));
  801. validate(tp_float, new_type_object(nullptr, "float", tp_object, false));
  802. validate(tp_bool, new_type_object(nullptr, "bool", tp_object, false));
  803. validate(tp_str, new_type_object<Str>(nullptr, "str", tp_object, false));
  804. validate(tp_list, new_type_object<List>(nullptr, "list", tp_object, false));
  805. validate(tp_tuple, new_type_object<Tuple>(nullptr, "tuple", tp_object, false));
  806. validate(tp_slice, new_type_object<Slice>(nullptr, "slice", tp_object, false));
  807. validate(tp_range, new_type_object<Range>(nullptr, "range", tp_object, false));
  808. validate(tp_module, new_type_object<DummyModule>(nullptr, "module", tp_object, false));
  809. validate(tp_function, new_type_object<Function>(nullptr, "function", tp_object, false));
  810. validate(tp_native_func, new_type_object<NativeFunc>(nullptr, "native_func", tp_object, false));
  811. validate(tp_bound_method, new_type_object<BoundMethod>(nullptr, "bound_method", tp_object, false));
  812. validate(tp_super, new_type_object<Super>(nullptr, "super", tp_object, false));
  813. validate(tp_exception, new_type_object<Exception>(nullptr, "Exception", tp_object, true));
  814. validate(tp_bytes, new_type_object<Bytes>(nullptr, "bytes", tp_object, false));
  815. validate(tp_mappingproxy, new_type_object<MappingProxy>(nullptr, "mappingproxy", tp_object, false));
  816. validate(tp_dict, new_type_object<Dict>(nullptr, "dict", tp_object, true));
  817. validate(tp_property, new_type_object<Property>(nullptr, "property", tp_object, false));
  818. validate(tp_star_wrapper, new_type_object<StarWrapper>(nullptr, "_star_wrapper", tp_object, false));
  819. validate(tp_staticmethod, new_type_object<StaticMethod>(nullptr, "staticmethod", tp_object, false));
  820. validate(tp_classmethod, new_type_object<ClassMethod>(nullptr, "classmethod", tp_object, false));
  821. validate(tp_none_type, new_type_object(nullptr, "NoneType", tp_object, false));
  822. validate(tp_not_implemented_type, new_type_object(nullptr, "NotImplementedType", tp_object, false));
  823. validate(tp_ellipsis, new_type_object(nullptr, "ellipsis", tp_object, false));
  824. validate(::tp_op_call, new_type_object(nullptr, "__op_call", tp_object, false));
  825. validate(::tp_op_yield, new_type_object(nullptr, "__op_yield", tp_object, false));
  826. // SyntaxError and IndentationError must be created here
  827. PyObject* SyntaxError = new_type_object(nullptr, "SyntaxError", tp_exception, true);
  828. PyObject* IndentationError = new_type_object(nullptr, "IndentationError", SyntaxError->as<Type>(), true);
  829. this->StopIteration = new_type_object(nullptr, "StopIteration", tp_exception, true);
  830. this->builtins = new_module("builtins");
  831. // setup public types
  832. builtins->attr().set("type", _t(tp_type));
  833. builtins->attr().set("object", _t(tp_object));
  834. builtins->attr().set("bool", _t(tp_bool));
  835. builtins->attr().set("int", _t(tp_int));
  836. builtins->attr().set("float", _t(tp_float));
  837. builtins->attr().set("str", _t(tp_str));
  838. builtins->attr().set("list", _t(tp_list));
  839. builtins->attr().set("tuple", _t(tp_tuple));
  840. builtins->attr().set("range", _t(tp_range));
  841. builtins->attr().set("bytes", _t(tp_bytes));
  842. builtins->attr().set("dict", _t(tp_dict));
  843. builtins->attr().set("property", _t(tp_property));
  844. builtins->attr().set("StopIteration", StopIteration);
  845. builtins->attr().set("NotImplemented", NotImplemented);
  846. builtins->attr().set("slice", _t(tp_slice));
  847. builtins->attr().set("Exception", _t(tp_exception));
  848. builtins->attr().set("SyntaxError", SyntaxError);
  849. builtins->attr().set("IndentationError", IndentationError);
  850. __post_init_builtin_types();
  851. this->_main = new_module("__main__");
  852. }
  853. void VM::__unpack_as_list(ArgsView args, List& list) {
  854. auto _lock = gc_scope_lock();
  855. for(PyVar obj: args) {
  856. if(is_type(obj, tp_star_wrapper)) {
  857. const StarWrapper& w = _CAST(StarWrapper&, obj);
  858. // maybe this check should be done in the compile time
  859. if(w.level != 1) TypeError("expected level 1 star wrapper");
  860. PyVar _0 = py_iter(w.obj);
  861. const PyTypeInfo* info = _tp_info(_0);
  862. PyVar _1 = _py_next(info, _0);
  863. while(_1 != StopIteration) {
  864. list.push_back(_1);
  865. _1 = _py_next(info, _0);
  866. }
  867. } else {
  868. list.push_back(obj);
  869. }
  870. }
  871. }
  872. void VM::__unpack_as_dict(ArgsView args, Dict& dict) {
  873. auto _lock = gc_scope_lock();
  874. for(PyVar obj: args) {
  875. if(is_type(obj, tp_star_wrapper)) {
  876. const StarWrapper& w = _CAST(StarWrapper&, obj);
  877. // maybe this check should be done in the compile time
  878. if(w.level != 2) TypeError("expected level 2 star wrapper");
  879. const Dict& other = CAST(Dict&, w.obj);
  880. dict.update(this, other);
  881. } else {
  882. const Tuple& t = CAST(Tuple&, obj);
  883. if(t.size() != 2) TypeError("expected tuple of length 2");
  884. dict.set(this, t[0], t[1]);
  885. }
  886. }
  887. }
  888. void VM::__prepare_py_call(PyVar* buffer, ArgsView args, ArgsView kwargs, const FuncDecl_& decl) {
  889. const CodeObject* co = decl->code.get();
  890. int decl_argc = decl->args.size();
  891. if(args.size() < decl_argc) {
  892. vm->TypeError(_S(co->name, "() takes ", decl_argc, " positional arguments but ", args.size(), " were given"));
  893. }
  894. int i = 0;
  895. // prepare args
  896. std::memset(buffer, 0, co->nlocals * sizeof(PyVar));
  897. for(int index: decl->args)
  898. buffer[index] = args[i++];
  899. // prepare kwdefaults
  900. for(auto& kv: decl->kwargs)
  901. buffer[kv.index] = kv.value;
  902. // handle *args
  903. if(decl->starred_arg != -1) {
  904. ArgsView vargs(args.begin() + i, args.end());
  905. buffer[decl->starred_arg] = VAR(vargs.to_tuple());
  906. i += vargs.size();
  907. } else {
  908. // kwdefaults override
  909. for(auto& kv: decl->kwargs) {
  910. if(i >= args.size()) break;
  911. buffer[kv.index] = args[i++];
  912. }
  913. if(i < args.size()) TypeError(_S("too many arguments", " (", decl->code->name, ')'));
  914. }
  915. PyVar vkwargs;
  916. if(decl->starred_kwarg != -1) {
  917. vkwargs = VAR(Dict());
  918. buffer[decl->starred_kwarg] = vkwargs;
  919. } else {
  920. vkwargs = nullptr;
  921. }
  922. for(int j = 0; j < kwargs.size(); j += 2) {
  923. StrName key(_CAST(uint16_t, kwargs[j]));
  924. int index = c11_smallmap_n2i__get(&decl->kw_to_index, key.index, -1);
  925. // if key is an explicit key, set as local variable
  926. if(index >= 0) {
  927. buffer[index] = kwargs[j + 1];
  928. } else {
  929. // otherwise, set as **kwargs if possible
  930. if(!vkwargs) {
  931. TypeError(_S(key.escape(), " is an invalid keyword argument for ", co->name, "()"));
  932. } else {
  933. Dict& dict = _CAST(Dict&, vkwargs);
  934. dict.set(this, VAR(key.sv()), kwargs[j + 1]);
  935. }
  936. }
  937. }
  938. }
  939. PyVar VM::vectorcall(int ARGC, int KWARGC, bool op_call) {
  940. PyVar* p1 = s_data._sp - KWARGC * 2;
  941. PyVar* p0 = p1 - ARGC - 2;
  942. // [callable, <self>, args..., kwargs...]
  943. // ^p0 ^p1 ^_sp
  944. PyVar callable = p1[-ARGC - 2];
  945. Type callable_t = _tp(callable);
  946. // handle boundmethod, do a patch
  947. if(callable_t == tp_bound_method) {
  948. assert(!p0[1]);
  949. BoundMethod& bm = PK_OBJ_GET(BoundMethod, callable);
  950. callable = bm.func; // get unbound method
  951. callable_t = _tp(callable);
  952. p1[-(ARGC + 2)] = bm.func;
  953. p1[-(ARGC + 1)] = bm.self;
  954. // [unbound, self, args..., kwargs...]
  955. }
  956. ArgsView args((!p0[1]) ? (p0 + 2) : (p0 + 1), p1);
  957. ArgsView kwargs(p1, s_data._sp);
  958. PyVar* _base = args.begin();
  959. if(callable_t == tp_function) {
  960. /*****************_py_call*****************/
  961. // check stack overflow
  962. if(s_data.is_overflow()) StackOverflowError();
  963. const Function& fn = PK_OBJ_GET(Function, callable);
  964. const CodeObject* co = fn.decl->code.get();
  965. switch(fn.decl->type) {
  966. case FuncType::NORMAL:
  967. __prepare_py_call(__vectorcall_buffer, args, kwargs, fn.decl);
  968. // copy buffer back to stack
  969. s_data.reset(_base + co->nlocals);
  970. for(int j = 0; j < co->nlocals; j++)
  971. _base[j] = __vectorcall_buffer[j];
  972. break;
  973. case FuncType::SIMPLE:
  974. if(args.size() != fn.decl->args.size())
  975. TypeError(_S(co->name,
  976. "() takes ",
  977. fn.decl->args.size(),
  978. " positional arguments but ",
  979. args.size(),
  980. " were given"));
  981. if(!kwargs.empty()) TypeError(_S(co->name, "() takes no keyword arguments"));
  982. // [callable, <self>, args..., local_vars...]
  983. // ^p0 ^p1 ^_sp
  984. s_data.reset(_base + co->nlocals);
  985. // initialize local variables to PY_NULL
  986. std::memset(p1, 0, (char*)s_data._sp - (char*)p1);
  987. break;
  988. case FuncType::EMPTY:
  989. if(args.size() != fn.decl->args.size())
  990. TypeError(_S(co->name,
  991. "() takes ",
  992. fn.decl->args.size(),
  993. " positional arguments but ",
  994. args.size(),
  995. " were given"));
  996. if(!kwargs.empty()) TypeError(_S(co->name, "() takes no keyword arguments"));
  997. s_data.reset(p0);
  998. return None;
  999. case FuncType::GENERATOR:
  1000. __prepare_py_call(__vectorcall_buffer, args, kwargs, fn.decl);
  1001. s_data.reset(p0);
  1002. callstack.emplace(nullptr, co, fn._module, callable.get(), nullptr);
  1003. return __py_generator(callstack.popx(),
  1004. ArgsView(__vectorcall_buffer, __vectorcall_buffer + co->nlocals));
  1005. default: PK_UNREACHABLE()
  1006. };
  1007. // simple or normal
  1008. callstack.emplace(p0, co, fn._module, callable.get(), args.begin());
  1009. if(op_call) return pkpy_OP_CALL;
  1010. return __run_top_frame();
  1011. /*****************_py_call*****************/
  1012. }
  1013. if(callable_t == tp_native_func) {
  1014. const auto& f = PK_OBJ_GET(NativeFunc, callable);
  1015. PyVar ret;
  1016. if(f.decl != nullptr) {
  1017. int co_nlocals = f.decl->code->nlocals;
  1018. __prepare_py_call(__vectorcall_buffer, args, kwargs, f.decl);
  1019. // copy buffer back to stack
  1020. s_data.reset(_base + co_nlocals);
  1021. for(int j = 0; j < co_nlocals; j++)
  1022. _base[j] = __vectorcall_buffer[j];
  1023. ret = f.call(vm, ArgsView(s_data._sp - co_nlocals, s_data._sp));
  1024. } else {
  1025. if(f.argc != -1) {
  1026. if(KWARGC != 0)
  1027. TypeError(
  1028. "old-style native_func does not accept keyword arguments. If you want to skip this check, specify `argc` to -1");
  1029. if(args.size() != f.argc) { vm->TypeError(_S("expected ", f.argc, " arguments, got ", args.size())); }
  1030. }
  1031. ret = f.call(this, args);
  1032. }
  1033. s_data.reset(p0);
  1034. return ret;
  1035. }
  1036. if(callable_t == tp_type) {
  1037. // [type, NULL, args..., kwargs...]
  1038. PyVar new_f = *find_name_in_mro(PK_OBJ_GET(Type, callable), __new__);
  1039. PyVar obj;
  1040. assert(new_f && (!p0[1]));
  1041. if(PyVar__IS_OP(&new_f, &__cached_object_new)) {
  1042. // fast path for object.__new__
  1043. obj = vm->new_object<DummyInstance>(PK_OBJ_GET(Type, callable));
  1044. } else {
  1045. PUSH(new_f);
  1046. PUSH(PY_NULL);
  1047. PUSH(callable); // cls
  1048. for(PyVar o: args)
  1049. PUSH(o);
  1050. for(PyVar o: kwargs)
  1051. PUSH(o);
  1052. // if obj is not an instance of `cls`, the behavior is undefined
  1053. obj = vectorcall(ARGC + 1, KWARGC);
  1054. }
  1055. // __init__
  1056. PyVar self;
  1057. callable = get_unbound_method(obj, __init__, &self, false);
  1058. if(callable) {
  1059. callable_t = _tp(callable);
  1060. // replace `NULL` with `self`
  1061. p1[-(ARGC + 2)] = callable;
  1062. p1[-(ARGC + 1)] = self;
  1063. // [init_f, self, args..., kwargs...]
  1064. vectorcall(ARGC, KWARGC);
  1065. // We just discard the return value of `__init__`
  1066. // in cpython it raises a TypeError if the return value is not None
  1067. } else {
  1068. // manually reset the stack
  1069. s_data.reset(p0);
  1070. }
  1071. return obj;
  1072. }
  1073. // handle `__call__` overload
  1074. PyVar self;
  1075. PyVar call_f = get_unbound_method(callable, __call__, &self, false);
  1076. if(self) {
  1077. p1[-(ARGC + 2)] = call_f;
  1078. p1[-(ARGC + 1)] = self;
  1079. // [call_f, self, args..., kwargs...]
  1080. return vectorcall(ARGC, KWARGC, op_call);
  1081. }
  1082. TypeError(_type_name(vm, callable_t).escape() + " object is not callable");
  1083. }
  1084. void VM::delattr(PyVar _0, StrName _name) {
  1085. const PyTypeInfo* ti = _tp_info(_0);
  1086. if(ti->m__delattr__ && ti->m__delattr__(this, _0, _name)) return;
  1087. if(is_tagged(_0) || !_0->is_attr_valid()) TypeError("cannot delete attribute");
  1088. if(!_0->attr().del(_name)) AttributeError(_0, _name);
  1089. }
  1090. // https://docs.python.org/3/howto/descriptor.html#invocation-from-an-instance
  1091. PyVar VM::getattr(PyVar obj, StrName name, bool throw_err) {
  1092. Type objtype(0);
  1093. // handle super() proxy
  1094. if(is_type(obj, tp_super)) {
  1095. const Super& super = PK_OBJ_GET(Super, obj);
  1096. obj = super.first;
  1097. objtype = super.second;
  1098. } else {
  1099. objtype = _tp(obj);
  1100. }
  1101. PyVar* cls_var = find_name_in_mro(objtype, name);
  1102. if(cls_var != nullptr) {
  1103. // handle descriptor
  1104. if(is_type(*cls_var, tp_property)) {
  1105. const Property& prop = PK_OBJ_GET(Property, *cls_var);
  1106. return call(prop.getter, obj);
  1107. }
  1108. }
  1109. // handle instance __dict__
  1110. if(!is_tagged(obj) && obj->is_attr_valid()) {
  1111. PyVar* val;
  1112. if(obj.type == tp_type) {
  1113. val = find_name_in_mro(PK_OBJ_GET(Type, obj), name);
  1114. if(val != nullptr) {
  1115. if(is_tagged(*val)) return *val;
  1116. if(val->type == tp_staticmethod) return PK_OBJ_GET(StaticMethod, *val).func;
  1117. if(val->type == tp_classmethod) return VAR(BoundMethod(obj, PK_OBJ_GET(ClassMethod, *val).func));
  1118. return *val;
  1119. }
  1120. } else {
  1121. val = obj->attr().try_get_2_likely_found(name);
  1122. if(val != nullptr) return *val;
  1123. }
  1124. }
  1125. if(cls_var != nullptr) {
  1126. // bound method is non-data descriptor
  1127. if(!is_tagged(*cls_var)) {
  1128. switch(cls_var->type) {
  1129. case tp_function: return VAR(BoundMethod(obj, *cls_var));
  1130. case tp_native_func: return VAR(BoundMethod(obj, *cls_var));
  1131. case tp_staticmethod: return PK_OBJ_GET(StaticMethod, *cls_var).func;
  1132. case tp_classmethod: return VAR(BoundMethod(_t(objtype), PK_OBJ_GET(ClassMethod, *cls_var).func));
  1133. }
  1134. }
  1135. return *cls_var;
  1136. }
  1137. const PyTypeInfo* ti = &_all_types[objtype];
  1138. if(ti->m__getattr__) {
  1139. PyVar ret = ti->m__getattr__(this, obj, name);
  1140. if(ret) return ret;
  1141. }
  1142. if(throw_err) AttributeError(obj, name);
  1143. return nullptr;
  1144. }
  1145. // used by OP_LOAD_METHOD
  1146. // try to load a unbound method (fallback to `getattr` if not found)
  1147. PyVar VM::get_unbound_method(PyVar obj, StrName name, PyVar* self, bool throw_err, bool fallback) {
  1148. self->set_null();
  1149. Type objtype(0);
  1150. // handle super() proxy
  1151. if(is_type(obj, tp_super)) {
  1152. const Super& super = PK_OBJ_GET(Super, obj);
  1153. obj = super.first;
  1154. objtype = super.second;
  1155. } else {
  1156. objtype = _tp(obj);
  1157. }
  1158. PyVar* cls_var = find_name_in_mro(objtype, name);
  1159. if(fallback) {
  1160. if(cls_var != nullptr) {
  1161. // handle descriptor
  1162. if(is_type(*cls_var, tp_property)) {
  1163. const Property& prop = PK_OBJ_GET(Property, *cls_var);
  1164. return call(prop.getter, obj);
  1165. }
  1166. }
  1167. // handle instance __dict__
  1168. if(!is_tagged(obj) && obj->is_attr_valid()) {
  1169. PyVar* val;
  1170. if(obj.type == tp_type) {
  1171. val = find_name_in_mro(PK_OBJ_GET(Type, obj), name);
  1172. if(val != nullptr) {
  1173. if(is_tagged(*val)) return *val;
  1174. if(val->type == tp_staticmethod) return PK_OBJ_GET(StaticMethod, *val).func;
  1175. if(val->type == tp_classmethod) return VAR(BoundMethod(obj, PK_OBJ_GET(ClassMethod, *val).func));
  1176. return *val;
  1177. }
  1178. } else {
  1179. val = obj->attr().try_get_2_likely_found(name);
  1180. if(val != nullptr) return *val;
  1181. }
  1182. }
  1183. }
  1184. if(cls_var != nullptr) {
  1185. if(!is_tagged(*cls_var)) {
  1186. switch(cls_var->type) {
  1187. case tp_function: *self = obj; break;
  1188. case tp_native_func: *self = obj; break;
  1189. case tp_staticmethod: self->set_null(); return PK_OBJ_GET(StaticMethod, *cls_var).func;
  1190. case tp_classmethod: *self = _t(objtype); return PK_OBJ_GET(ClassMethod, *cls_var).func;
  1191. }
  1192. }
  1193. return *cls_var;
  1194. }
  1195. const PyTypeInfo* ti = &_all_types[objtype];
  1196. if(fallback && ti->m__getattr__) {
  1197. PyVar ret = ti->m__getattr__(this, obj, name);
  1198. if(ret) return ret;
  1199. }
  1200. if(throw_err) AttributeError(obj, name);
  1201. return nullptr;
  1202. }
  1203. void VM::setattr(PyVar obj, StrName name, PyVar value) {
  1204. Type objtype(0);
  1205. // handle super() proxy
  1206. if(is_type(obj, tp_super)) {
  1207. Super& super = PK_OBJ_GET(Super, obj);
  1208. obj = super.first;
  1209. objtype = super.second;
  1210. } else {
  1211. objtype = _tp(obj);
  1212. }
  1213. PyVar* cls_var = find_name_in_mro(objtype, name);
  1214. if(cls_var != nullptr) {
  1215. // handle descriptor
  1216. if(is_type(*cls_var, tp_property)) {
  1217. const Property& prop = _CAST(Property&, *cls_var);
  1218. if(!is_none(prop.setter)) {
  1219. call(prop.setter, obj, value);
  1220. } else {
  1221. TypeError(_S("readonly attribute: ", name.escape()));
  1222. }
  1223. return;
  1224. }
  1225. }
  1226. const PyTypeInfo* ti = &_all_types[objtype];
  1227. if(ti->m__setattr__) {
  1228. ti->m__setattr__(this, obj, name, value);
  1229. return;
  1230. }
  1231. // handle instance __dict__
  1232. if(is_tagged(obj) || !obj->is_attr_valid()) TypeError("cannot set attribute");
  1233. obj->attr().set(name, value);
  1234. }
  1235. PyObject* VM::bind_func(PyObject* obj, StrName name, int argc, NativeFuncC fn, any userdata, BindType bt) {
  1236. PyObject* nf = new_object<NativeFunc>(tp_native_func, fn, argc, std::move(userdata)).get();
  1237. switch(bt) {
  1238. case BindType::DEFAULT: break;
  1239. case BindType::STATICMETHOD: nf = new_object<StaticMethod>(tp_staticmethod, nf).get(); break;
  1240. case BindType::CLASSMETHOD: nf = new_object<ClassMethod>(tp_classmethod, nf).get(); break;
  1241. }
  1242. if(obj != nullptr) obj->attr().set(name, nf);
  1243. return nf;
  1244. }
  1245. PyObject* VM::bind(PyObject* obj, const char* sig, NativeFuncC fn, any userdata, BindType bt) {
  1246. return bind(obj, sig, nullptr, fn, std::move(userdata), bt);
  1247. }
  1248. PyObject* VM::bind(PyObject* obj, const char* sig, const char* docstring, NativeFuncC fn, any userdata, BindType bt) {
  1249. char buffer[256];
  1250. int length = snprintf(buffer, sizeof(buffer), "def %s : pass", sig);
  1251. std::string_view source(buffer, length);
  1252. // fn(a, b, *c, d=1) -> None
  1253. CodeObject_ co = compile(source, "<bind>", EXEC_MODE);
  1254. assert(co->func_decls.size() == 1);
  1255. FuncDecl_ decl = co->func_decls[0];
  1256. decl->docstring = docstring;
  1257. PyObject* f_obj = new_object<NativeFunc>(tp_native_func, fn, decl, std::move(userdata)).get();
  1258. switch(bt) {
  1259. case BindType::STATICMETHOD: f_obj = new_object<StaticMethod>(tp_staticmethod, f_obj).get(); break;
  1260. case BindType::CLASSMETHOD: f_obj = new_object<ClassMethod>(tp_classmethod, f_obj).get(); break;
  1261. case BindType::DEFAULT: break;
  1262. }
  1263. if(obj != nullptr) obj->attr().set(decl->code->name, f_obj);
  1264. return f_obj;
  1265. }
  1266. PyObject* VM::bind_property(PyObject* obj, const char* name, NativeFuncC fget, NativeFuncC fset) {
  1267. assert(is_type(obj, tp_type));
  1268. std::string_view name_sv(name);
  1269. int pos = name_sv.find(':');
  1270. if(pos > 0) name_sv = name_sv.substr(0, pos);
  1271. PyVar _0 = new_object<NativeFunc>(tp_native_func, fget, 1);
  1272. PyVar _1 = vm->None;
  1273. if(fset != nullptr) _1 = new_object<NativeFunc>(tp_native_func, fset, 2);
  1274. PyObject* prop = new_object<Property>(tp_property, _0, _1).get();
  1275. obj->attr().set(StrName(name_sv), prop);
  1276. return prop;
  1277. }
  1278. void VM::__builtin_error(StrName type) { _error(call(builtins->attr()[type])); }
  1279. void VM::__builtin_error(StrName type, PyVar arg) { _error(call(builtins->attr()[type], arg)); }
  1280. void VM::__builtin_error(StrName type, const Str& msg) { __builtin_error(type, VAR(msg)); }
  1281. void VM::BinaryOptError(const char* op, PyVar _0, PyVar _1) {
  1282. StrName name_0 = _type_name(vm, _tp(_0));
  1283. StrName name_1 = _type_name(vm, _tp(_1));
  1284. TypeError(_S("unsupported operand type(s) for ", op, ": ", name_0.escape(), " and ", name_1.escape()));
  1285. }
  1286. void VM::AttributeError(PyVar obj, StrName name) {
  1287. if(isinstance(obj, vm->tp_type)) {
  1288. __builtin_error(
  1289. "AttributeError",
  1290. _S("type object ", _type_name(vm, PK_OBJ_GET(Type, obj)).escape(), " has no attribute ", name.escape()));
  1291. } else {
  1292. __builtin_error("AttributeError",
  1293. _S(_type_name(vm, _tp(obj)).escape(), " object has no attribute ", name.escape()));
  1294. }
  1295. }
  1296. void VM::_error(PyVar e_obj) {
  1297. assert(isinstance(e_obj, tp_exception));
  1298. Exception& e = PK_OBJ_GET(Exception, e_obj);
  1299. if(callstack.empty()) {
  1300. e.is_re = false;
  1301. __last_exception = e_obj.get();
  1302. throw TopLevelException(this, &e);
  1303. }
  1304. PUSH(e_obj);
  1305. __raise_exc();
  1306. }
  1307. void VM::__raise_exc(bool re_raise) {
  1308. Frame* frame = &callstack.top();
  1309. Exception& e = PK_OBJ_GET(Exception, s_data.top());
  1310. if(!re_raise) {
  1311. e._ip_on_error = frame->ip();
  1312. e._code_on_error = (void*)frame->co;
  1313. }
  1314. int next_ip = frame->prepare_jump_exception_handler(&s_data);
  1315. int actual_ip = frame->ip();
  1316. if(e._ip_on_error >= 0 && e._code_on_error == (void*)frame->co) actual_ip = e._ip_on_error;
  1317. int current_line = frame->co->lines[actual_ip].lineno; // current line
  1318. const char* current_f_name = frame->co->name.c_str(); // current function name
  1319. if(frame->_callable == nullptr) current_f_name = ""; // not in a function
  1320. e.stpush(frame->co->src, current_line, nullptr, current_f_name);
  1321. if(next_ip >= 0) {
  1322. throw InternalException(InternalExceptionType::Handled, next_ip);
  1323. } else {
  1324. throw InternalException(InternalExceptionType::Unhandled);
  1325. }
  1326. }
  1327. StrName _type_name(VM* vm, Type type) { return vm->_all_types[type].name; }
  1328. void VM::bind__getitem__(Type type, PyVar (*f)(VM*, PyVar, PyVar)) {
  1329. _all_types[type].m__getitem__ = f;
  1330. bind_func(
  1331. type,
  1332. __getitem__,
  1333. 2,
  1334. [](VM* vm, ArgsView args) {
  1335. return lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0], args[1]);
  1336. },
  1337. f);
  1338. }
  1339. void VM::bind__setitem__(Type type, void (*f)(VM*, PyVar, PyVar, PyVar)) {
  1340. _all_types[type].m__setitem__ = f;
  1341. bind_func(
  1342. type,
  1343. __setitem__,
  1344. 3,
  1345. [](VM* vm, ArgsView args) {
  1346. lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0], args[1], args[2]);
  1347. return vm->None;
  1348. },
  1349. f);
  1350. }
  1351. void VM::bind__delitem__(Type type, void (*f)(VM*, PyVar, PyVar)) {
  1352. _all_types[type].m__delitem__ = f;
  1353. bind_func(
  1354. type,
  1355. __delitem__,
  1356. 2,
  1357. [](VM* vm, ArgsView args) {
  1358. lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0], args[1]);
  1359. return vm->None;
  1360. },
  1361. f);
  1362. }
  1363. PyVar VM::__pack_next_retval(unsigned n) {
  1364. if(n == 0) return StopIteration;
  1365. if(n == 1) return s_data.popx();
  1366. PyVar retval = VAR(s_data.view(n).to_tuple());
  1367. s_data._sp -= n;
  1368. return retval;
  1369. }
  1370. void VM::bind__next__(Type type, unsigned (*f)(VM*, PyVar)) {
  1371. _all_types[type].op__next__ = f;
  1372. bind_func(
  1373. type,
  1374. __next__,
  1375. 1,
  1376. [](VM* vm, ArgsView args) {
  1377. int n = lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0]);
  1378. return vm->__pack_next_retval(n);
  1379. },
  1380. f);
  1381. }
  1382. void VM::bind__next__(Type type, PyVar (*f)(VM*, PyVar)) {
  1383. bind_func(
  1384. type,
  1385. __next__,
  1386. 1,
  1387. [](VM* vm, ArgsView args) {
  1388. auto f = lambda_get_userdata<PyVar (*)(VM*, PyVar)>(args.begin());
  1389. return f(vm, args[0]);
  1390. },
  1391. f);
  1392. }
  1393. #define BIND_UNARY_SPECIAL(name) \
  1394. void VM::bind##name(Type type, PyVar (*f)(VM*, PyVar)) { \
  1395. _all_types[type].m##name = f; \
  1396. bind_func( \
  1397. type, \
  1398. name, \
  1399. 1, \
  1400. [](VM* vm, ArgsView args) { \
  1401. return lambda_get_userdata<PyVar (*)(VM*, PyVar)>(args.begin())(vm, args[0]); \
  1402. }, \
  1403. f); \
  1404. }
  1405. BIND_UNARY_SPECIAL(__iter__)
  1406. BIND_UNARY_SPECIAL(__neg__)
  1407. BIND_UNARY_SPECIAL(__invert__)
  1408. #undef BIND_UNARY_SPECIAL
  1409. void VM::bind__str__(Type type, Str (*f)(VM*, PyVar)) {
  1410. _all_types[type].m__str__ = f;
  1411. bind_func(
  1412. type,
  1413. __str__,
  1414. 1,
  1415. [](VM* vm, ArgsView args) {
  1416. Str s = lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0]);
  1417. return VAR(s);
  1418. },
  1419. f);
  1420. }
  1421. void VM::bind__repr__(Type type, Str (*f)(VM*, PyVar)) {
  1422. _all_types[type].m__repr__ = f;
  1423. bind_func(
  1424. type,
  1425. __repr__,
  1426. 1,
  1427. [](VM* vm, ArgsView args) {
  1428. Str s = lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0]);
  1429. return VAR(s);
  1430. },
  1431. f);
  1432. }
  1433. void VM::bind__hash__(Type type, i64 (*f)(VM*, PyVar)) {
  1434. _all_types[type].m__hash__ = f;
  1435. bind_func(
  1436. type,
  1437. __hash__,
  1438. 1,
  1439. [](VM* vm, ArgsView args) {
  1440. i64 ret = lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0]);
  1441. return VAR(ret);
  1442. },
  1443. f);
  1444. }
  1445. void VM::bind__len__(Type type, i64 (*f)(VM*, PyVar)) {
  1446. _all_types[type].m__len__ = f;
  1447. bind_func(
  1448. type,
  1449. __len__,
  1450. 1,
  1451. [](VM* vm, ArgsView args) {
  1452. i64 ret = lambda_get_userdata<decltype(f)>(args.begin())(vm, args[0]);
  1453. return VAR(ret);
  1454. },
  1455. f);
  1456. }
  1457. #define BIND_BINARY_SPECIAL(name) \
  1458. void VM::bind##name(Type type, BinaryFuncC f) { \
  1459. _all_types[type].m##name = f; \
  1460. bind_func( \
  1461. type, \
  1462. name, \
  1463. 2, \
  1464. [](VM* vm, ArgsView args) { \
  1465. return lambda_get_userdata<BinaryFuncC>(args.begin())(vm, args[0], args[1]); \
  1466. }, \
  1467. f); \
  1468. }
  1469. BIND_BINARY_SPECIAL(__eq__)
  1470. BIND_BINARY_SPECIAL(__lt__)
  1471. BIND_BINARY_SPECIAL(__le__)
  1472. BIND_BINARY_SPECIAL(__gt__)
  1473. BIND_BINARY_SPECIAL(__ge__)
  1474. BIND_BINARY_SPECIAL(__contains__)
  1475. BIND_BINARY_SPECIAL(__add__)
  1476. BIND_BINARY_SPECIAL(__sub__)
  1477. BIND_BINARY_SPECIAL(__mul__)
  1478. BIND_BINARY_SPECIAL(__truediv__)
  1479. BIND_BINARY_SPECIAL(__floordiv__)
  1480. BIND_BINARY_SPECIAL(__mod__)
  1481. BIND_BINARY_SPECIAL(__pow__)
  1482. BIND_BINARY_SPECIAL(__matmul__)
  1483. BIND_BINARY_SPECIAL(__lshift__)
  1484. BIND_BINARY_SPECIAL(__rshift__)
  1485. BIND_BINARY_SPECIAL(__and__)
  1486. BIND_BINARY_SPECIAL(__or__)
  1487. BIND_BINARY_SPECIAL(__xor__)
  1488. #undef BIND_BINARY_SPECIAL
  1489. #if PK_ENABLE_PROFILER
  1490. void NextBreakpoint::_step(VM* vm) {
  1491. int curr_callstack_size = vm->callstack.size();
  1492. int curr_lineno = vm->callstack.top().curr_lineno();
  1493. if(should_step_into) {
  1494. if(curr_callstack_size != callstack_size || curr_lineno != lineno) { vm->__breakpoint(); }
  1495. } else {
  1496. if(curr_callstack_size == callstack_size) {
  1497. if(curr_lineno != lineno) vm->__breakpoint();
  1498. } else if(curr_callstack_size < callstack_size) {
  1499. // returning
  1500. vm->__breakpoint();
  1501. }
  1502. }
  1503. }
  1504. #endif
  1505. void VM::__pop_frame() {
  1506. s_data.reset(callstack.top()._sp_base);
  1507. callstack.pop();
  1508. #if PK_ENABLE_PROFILER
  1509. if(!_next_breakpoint.empty() && callstack.size() < _next_breakpoint.callstack_size) {
  1510. _next_breakpoint = NextBreakpoint();
  1511. }
  1512. #endif
  1513. }
  1514. void VM::__breakpoint() {
  1515. #if PK_ENABLE_PROFILER
  1516. _next_breakpoint = NextBreakpoint();
  1517. bool show_where = false;
  1518. bool show_headers = true;
  1519. while(true) {
  1520. vector<LinkedFrame*> frames;
  1521. LinkedFrame* lf = callstack._tail;
  1522. while(lf != nullptr) {
  1523. frames.push_back(lf);
  1524. lf = lf->f_back;
  1525. if(frames.size() >= 4) break;
  1526. }
  1527. if(show_headers) {
  1528. for(int i = frames.size() - 1; i >= 0; i--) {
  1529. if(!show_where && i != 0) continue;
  1530. SStream ss;
  1531. Frame* frame = &frames[i]->frame;
  1532. int lineno = frame->curr_lineno();
  1533. ss << "File \"" << frame->co->src.filename() << "\", line " << lineno;
  1534. if(frame->_callable) {
  1535. ss << ", in ";
  1536. ss << frame->_callable->as<Function>().decl->code->name;
  1537. }
  1538. ss << '\n';
  1539. ss << "-> " << frame->co->src->get_line(lineno) << '\n';
  1540. stdout_write(ss.str());
  1541. }
  1542. show_headers = false;
  1543. }
  1544. vm->stdout_write("(Pdb) ");
  1545. Frame* frame_0 = &frames[0]->frame;
  1546. std::string line;
  1547. if(!std::getline(std::cin, line)) {
  1548. stdout_write("--KeyboardInterrupt--\n");
  1549. continue;
  1550. }
  1551. if(line == "h" || line == "help") {
  1552. stdout_write("h, help: show this help message\n");
  1553. stdout_write("q, quit: exit the debugger\n");
  1554. stdout_write("n, next: execute next line\n");
  1555. stdout_write("s, step: step into\n");
  1556. stdout_write("w, where: show current stack frame\n");
  1557. stdout_write("c, continue: continue execution\n");
  1558. stdout_write("a, args: show local variables\n");
  1559. stdout_write("p, print <expr>: evaluate expression\n");
  1560. stdout_write("l, list: show lines around current line\n");
  1561. stderr_write("ll, longlist: show all lines\n");
  1562. stdout_write("!: execute statement\n");
  1563. continue;
  1564. }
  1565. if(line == "q" || line == "quit") { vm->RuntimeError("pdb quit"); }
  1566. if(line == "n" || line == "next") {
  1567. vm->_next_breakpoint = NextBreakpoint(vm->callstack.size(), frame_0->curr_lineno(), false);
  1568. break;
  1569. }
  1570. if(line == "s" || line == "step") {
  1571. vm->_next_breakpoint = NextBreakpoint(vm->callstack.size(), frame_0->curr_lineno(), true);
  1572. break;
  1573. }
  1574. if(line == "w" || line == "where") {
  1575. show_where = !show_where;
  1576. show_headers = true;
  1577. continue;
  1578. }
  1579. if(line == "c" || line == "continue") break;
  1580. if(line == "a" || line == "args") {
  1581. int i = 0;
  1582. for(PyVar obj: frame_0->_locals) {
  1583. if(obj == PY_NULL) continue;
  1584. StrName name = frame_0->co->varnames[i++];
  1585. stdout_write(_S(name.sv(), " = ", vm->py_repr(obj), '\n'));
  1586. }
  1587. continue;
  1588. }
  1589. bool is_list = line == "l" || line == "list";
  1590. bool is_longlist = line == "ll" || line == "longlist";
  1591. if(is_list || is_longlist) {
  1592. if(frame_0->co->src->is_precompiled) continue;
  1593. int lineno = frame_0->curr_lineno();
  1594. int start, end;
  1595. if(is_list) {
  1596. int max_line = frame_0->co->src->line_starts.size() + 1;
  1597. start = (std::max)(1, lineno - 5);
  1598. end = (std::min)(max_line, lineno + 5);
  1599. } else {
  1600. start = frame_0->co->start_line;
  1601. end = frame_0->co->end_line;
  1602. if(start == -1 || end == -1) continue;
  1603. }
  1604. SStream ss;
  1605. int max_width = std::to_string(end).size();
  1606. for(int i = start; i <= end; i++) {
  1607. int spaces = max_width - std::to_string(i).size();
  1608. ss << std::string(spaces, ' ') << std::to_string(i);
  1609. if(i == lineno)
  1610. ss << " -> ";
  1611. else
  1612. ss << " ";
  1613. ss << frame_0->co->src->get_line(i) << '\n';
  1614. }
  1615. stdout_write(ss.str());
  1616. continue;
  1617. }
  1618. int space = line.find_first_of(' ');
  1619. if(space != -1) {
  1620. std::string cmd = line.substr(0, space);
  1621. std::string arg = line.substr(space + 1);
  1622. if(arg.empty()) continue; // ignore empty command
  1623. if(cmd == "p" || cmd == "print") {
  1624. CodeObject_ code = compile(arg, "<stdin>", EVAL_MODE, true);
  1625. PyVar retval = vm->_exec(code.get(), frame_0->_module, frame_0->_callable, frame_0->_locals);
  1626. stdout_write(vm->py_repr(retval));
  1627. stdout_write("\n");
  1628. } else if(cmd == "!") {
  1629. CodeObject_ code = compile(arg, "<stdin>", EXEC_MODE, true);
  1630. vm->_exec(code.get(), frame_0->_module, frame_0->_callable, frame_0->_locals);
  1631. }
  1632. continue;
  1633. }
  1634. }
  1635. #endif
  1636. }
  1637. PyVar PyObject::attr(StrName name) const{
  1638. return attr()[name];
  1639. }
  1640. /**************************************************************************/
  1641. void Function::_gc_mark(VM* vm) const {
  1642. decl->_gc_mark(vm);
  1643. if(_closure) {
  1644. _closure->apply([](StrName _, PyVar obj, void* userdata) {
  1645. VM* vm = (VM*)userdata;
  1646. vm->obj_gc_mark(obj);
  1647. }, vm);
  1648. }
  1649. }
  1650. void NativeFunc::_gc_mark(VM* vm) const {
  1651. if(decl) decl->_gc_mark(vm);
  1652. }
  1653. void FuncDecl::_gc_mark(VM* vm) const {
  1654. code->_gc_mark(vm);
  1655. for(int i = 0; i < kwargs.size(); i++)
  1656. vm->obj_gc_mark(kwargs[i].value);
  1657. }
  1658. void List::_gc_mark(VM* vm) const {
  1659. for(PyVar obj: *this)
  1660. vm->obj_gc_mark(obj);
  1661. }
  1662. void Tuple::_gc_mark(VM* vm) const {
  1663. for(PyVar obj: *this)
  1664. vm->obj_gc_mark(obj);
  1665. }
  1666. void MappingProxy::_gc_mark(VM* vm) const { vm->__obj_gc_mark(obj); }
  1667. void BoundMethod::_gc_mark(VM* vm) const {
  1668. vm->obj_gc_mark(func);
  1669. vm->obj_gc_mark(self);
  1670. }
  1671. void StarWrapper::_gc_mark(VM* vm) const { vm->obj_gc_mark(obj); }
  1672. void StaticMethod::_gc_mark(VM* vm) const { vm->obj_gc_mark(func); }
  1673. void ClassMethod::_gc_mark(VM* vm) const { vm->obj_gc_mark(func); }
  1674. void Property::_gc_mark(VM* vm) const {
  1675. vm->obj_gc_mark(getter);
  1676. vm->obj_gc_mark(setter);
  1677. }
  1678. void Slice::_gc_mark(VM* vm) const {
  1679. vm->obj_gc_mark(start);
  1680. vm->obj_gc_mark(stop);
  1681. vm->obj_gc_mark(step);
  1682. }
  1683. void Super::_gc_mark(VM* vm) const { vm->obj_gc_mark(first); }
  1684. void Frame::_gc_mark(VM* vm) const {
  1685. vm->obj_gc_mark(_module);
  1686. co->_gc_mark(vm);
  1687. // Frame could be stored in a generator, so mark _callable for safety
  1688. vm->obj_gc_mark(_callable);
  1689. }
  1690. extern "C"{
  1691. void pk_ManagedHeap__mark(pk_ManagedHeap* self){
  1692. VM* vm = (VM*)self->vm;
  1693. for(int i=0; i<self->no_gc.count; i++){
  1694. PyObject* obj = c11__getitem(PyObject*, &self->no_gc, i);
  1695. vm->__obj_gc_mark(obj);
  1696. }
  1697. vm->callstack.apply([vm](Frame& frame) {
  1698. frame._gc_mark(vm);
  1699. });
  1700. vm->obj_gc_mark(vm->__last_exception);
  1701. vm->obj_gc_mark(vm->__curr_class);
  1702. vm->obj_gc_mark(vm->__c.error);
  1703. vm->__stack_gc_mark(vm->s_data.begin(), vm->s_data.end());
  1704. if(self->_gc_marker_ex) self->_gc_marker_ex((pkpy_VM*)vm);
  1705. }
  1706. void pk_ManagedHeap__delete_obj(pk_ManagedHeap* self, ::PyObject* __obj){
  1707. PyObject* obj = (PyObject*)__obj;
  1708. const PyTypeInfo* ti = ((VM*)(self->vm))->_tp_info(obj->type);
  1709. if(ti->vt._dtor) ti->vt._dtor(obj->_value_ptr());
  1710. if (obj->_attr)
  1711. c11_vector__dtor(obj->_attr);
  1712. delete obj->_attr; // delete __dict__ if exists
  1713. if(obj->gc_is_large){
  1714. std::free(obj);
  1715. }else{
  1716. PoolObject_dealloc(obj);
  1717. }
  1718. }
  1719. }
  1720. void Dict::_gc_mark(VM* vm) const {
  1721. apply([vm](PyVar k, PyVar v) {
  1722. vm->obj_gc_mark(k);
  1723. vm->obj_gc_mark(v);
  1724. });
  1725. }
  1726. void CodeObject::_gc_mark(VM* vm) const {
  1727. for(PyVar v: consts)
  1728. vm->obj_gc_mark(v);
  1729. for(auto& decl: func_decls)
  1730. decl->_gc_mark(vm);
  1731. }
  1732. } // namespace pkpy