codeobject.cpp 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169
  1. #include "pocketpy/codeobject.h"
  2. namespace pkpy{
  3. CodeObject::CodeObject(shared_ptr<SourceData> src, const Str& name):
  4. src(src), name(name) {}
  5. void CodeObject::_gc_mark() const {
  6. for(PyObject* v : consts) PK_OBJ_MARK(v);
  7. for(auto& decl: func_decls) decl->_gc_mark();
  8. }
  9. void CodeObject::write(VM* vm, CodeObjectSerializer& ss) const{
  10. ss.write_begin_mark(); // [
  11. ss.write_str(src->filename); // src->filename
  12. ss.write_int(src->mode); // src->mode
  13. ss.write_end_mark(); // ]
  14. ss.write_str(name); // name
  15. ss.write_bool(is_generator); // is_generator
  16. ss.write_begin_mark(); // [
  17. for(Bytecode bc: codes){
  18. if(StrName::is_valid(bc.arg)) ss.names.insert(StrName(bc.arg));
  19. ss.write_bytes(bc);
  20. }
  21. ss.write_end_mark(); // ]
  22. ss.write_begin_mark(); // [
  23. for(int line: lines){
  24. ss.write_int(line); // line
  25. }
  26. ss.write_end_mark(); // ]
  27. ss.write_begin_mark(); // [
  28. for(PyObject* o: consts){
  29. ss.write_object(vm, o);
  30. }
  31. ss.write_end_mark(); // ]
  32. ss.write_begin_mark(); // [
  33. for(StrName vn: varnames){
  34. ss.write_name(vn); // name
  35. }
  36. ss.write_end_mark(); // ]
  37. ss.write_begin_mark(); // [
  38. for(CodeBlock block: blocks){
  39. ss.write_bytes(block); // block
  40. }
  41. ss.write_end_mark(); // ]
  42. ss.write_begin_mark(); // [
  43. for(auto& label: labels.items()){
  44. ss.write_name(label.first); // label.first
  45. ss.write_int(label.second); // label.second
  46. }
  47. ss.write_end_mark(); // ]
  48. ss.write_begin_mark(); // [
  49. for(auto& decl: func_decls){
  50. ss.write_code(vm, decl->code.get()); // decl->code
  51. ss.write_begin_mark(); // [
  52. for(int arg: decl->args) ss.write_int(arg);
  53. ss.write_end_mark(); // ]
  54. ss.write_begin_mark(); // [
  55. for(auto kw: decl->kwargs){
  56. ss.write_int(kw.key); // kw.key
  57. ss.write_object(vm, kw.value); // kw.value
  58. }
  59. ss.write_end_mark(); // ]
  60. ss.write_int(decl->starred_arg);
  61. ss.write_int(decl->starred_kwarg);
  62. ss.write_bool(decl->nested);
  63. }
  64. ss.write_end_mark(); // ]
  65. }
  66. Str CodeObject::serialize(VM* vm) const{
  67. CodeObjectSerializer ss;
  68. ss.write_code(vm, this);
  69. return ss.str();
  70. }
  71. void CodeObjectSerializer::write_int(i64 v){
  72. buffer += 'i';
  73. buffer += std::to_string(v);
  74. buffer += END;
  75. }
  76. void CodeObjectSerializer::write_float(f64 v){
  77. buffer += 'f';
  78. buffer += std::to_string(v);
  79. buffer += END;
  80. }
  81. void CodeObjectSerializer::write_str(const Str& v){
  82. buffer += 's';
  83. buffer += v.escape(false).str();
  84. buffer += END;
  85. }
  86. void CodeObjectSerializer::write_none(){
  87. buffer += 'N';
  88. buffer += END;
  89. }
  90. void CodeObjectSerializer::write_ellipsis(){
  91. buffer += 'E';
  92. buffer += END;
  93. }
  94. void CodeObjectSerializer::write_bool(bool v){
  95. buffer += 'b';
  96. buffer += v ? '1' : '0';
  97. buffer += END;
  98. }
  99. void CodeObjectSerializer::write_begin_mark(){
  100. buffer += '[';
  101. buffer += END;
  102. depth++;
  103. }
  104. void CodeObjectSerializer::write_name(StrName name){
  105. PK_ASSERT(StrName::is_valid(name.index));
  106. buffer += 'n';
  107. buffer += std::to_string(name.index);
  108. buffer += END;
  109. names.insert(name);
  110. }
  111. void CodeObjectSerializer::write_end_mark(){
  112. buffer += ']';
  113. buffer += END;
  114. depth--;
  115. PK_ASSERT(depth >= 0);
  116. }
  117. std::string CodeObjectSerializer::str(){
  118. PK_ASSERT(depth == 0);
  119. for(auto name: names){
  120. PK_ASSERT(StrName::is_valid(name.index));
  121. write_name(name);
  122. write_str(name.sv());
  123. }
  124. return std::move(buffer);
  125. }
  126. CodeObjectSerializer::CodeObjectSerializer(){
  127. write_str(PK_VERSION);
  128. }
  129. void CodeObjectSerializer::write_code(VM* vm, const CodeObject* co){
  130. buffer += '(';
  131. buffer += END;
  132. co->write(vm, *this);
  133. buffer += ')';
  134. buffer += END;
  135. }
  136. NativeFunc::NativeFunc(NativeFuncC f, int argc, bool method){
  137. this->f = f;
  138. this->argc = argc;
  139. if(argc != -1) this->argc += (int)method;
  140. }
  141. NativeFunc::NativeFunc(NativeFuncC f, FuncDecl_ decl){
  142. this->f = f;
  143. this->argc = -1;
  144. this->decl = decl;
  145. }
  146. } // namespace pkpy