obj.h 5.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216
  1. #pragma once
  2. #include "common.h"
  3. #include "namedict.h"
  4. #include "tuplelist.h"
  5. namespace pkpy {
  6. #if PK_ENABLE_STD_FUNCTION
  7. using NativeFuncC = std::function<PyVar(VM*, ArgsView)>;
  8. #else
  9. typedef PyVar (*NativeFuncC)(VM*, ArgsView);
  10. #endif
  11. enum class BindType{
  12. DEFAULT,
  13. STATICMETHOD,
  14. CLASSMETHOD,
  15. };
  16. struct BoundMethod {
  17. PyVar self;
  18. PyVar func;
  19. BoundMethod(PyVar self, PyVar func) : self(self), func(func) {}
  20. void _gc_mark(VM*) const;
  21. };
  22. struct StaticMethod{
  23. PyVar func;
  24. StaticMethod(PyVar func) : func(func) {}
  25. void _gc_mark(VM*) const;
  26. };
  27. struct ClassMethod{
  28. PyVar func;
  29. ClassMethod(PyVar func) : func(func) {}
  30. void _gc_mark(VM*) const;
  31. };
  32. struct Property{
  33. PyVar getter;
  34. PyVar setter;
  35. Property(PyVar getter, PyVar setter) : getter(getter), setter(setter) {}
  36. void _gc_mark(VM*) const;
  37. };
  38. struct Range {
  39. i64 start = 0;
  40. i64 stop = -1;
  41. i64 step = 1;
  42. };
  43. struct StarWrapper{
  44. int level; // either 1 or 2
  45. PyVar obj;
  46. StarWrapper(int level, PyVar obj) : level(level), obj(obj) {}
  47. void _gc_mark(VM*) const;
  48. };
  49. struct Bytes{
  50. unsigned char* _data;
  51. int _size;
  52. int size() const noexcept { return _size; }
  53. int operator[](int i) const noexcept { return (int)_data[i]; }
  54. const unsigned char* data() const noexcept { return _data; }
  55. bool operator==(const Bytes& rhs) const;
  56. bool operator!=(const Bytes& rhs) const;
  57. Str str() const noexcept { return Str((char*)_data, _size); }
  58. std::string_view sv() const noexcept { return std::string_view((char*)_data, _size); }
  59. Bytes() : _data(nullptr), _size(0) {}
  60. Bytes(unsigned char* p, int size): _data(p), _size(size) {}
  61. Bytes(const Str& str): Bytes(str.sv()) {}
  62. operator bool() const noexcept { return _data != nullptr; }
  63. Bytes(std::string_view sv);
  64. Bytes(const Bytes& rhs);
  65. Bytes(Bytes&& rhs) noexcept;
  66. Bytes& operator=(Bytes&& rhs) noexcept;
  67. Bytes& operator=(const Bytes& rhs) = delete;
  68. std::pair<unsigned char*, int> detach() noexcept;
  69. ~Bytes(){ delete[] _data;}
  70. };
  71. struct Super{
  72. PyVar first;
  73. Type second;
  74. Super(PyVar first, Type second) : first(first), second(second) {}
  75. void _gc_mark(VM*) const;
  76. };
  77. struct Slice {
  78. PyVar start;
  79. PyVar stop;
  80. PyVar step;
  81. Slice(PyVar start, PyVar stop, PyVar step) : start(start), stop(stop), step(step) {}
  82. void _gc_mark(VM*) const;
  83. };
  84. struct PyObject final{
  85. bool gc_marked; // whether this object is marked
  86. NameDict* _attr;
  87. bool is_attr_valid() const noexcept { return _attr != nullptr; }
  88. void* _value_ptr() noexcept { return 1 + &_attr; }
  89. NameDict& attr() {
  90. PK_DEBUG_ASSERT(is_attr_valid())
  91. return *_attr;
  92. }
  93. PyVar attr(StrName name) const {
  94. PK_DEBUG_ASSERT(is_attr_valid())
  95. return (*_attr)[name];
  96. }
  97. PyObject() : gc_marked(false), _attr(nullptr) {}
  98. template<typename T, typename ...Args>
  99. void placement_new(Args&&... args){
  100. static_assert(std::is_same_v<T, std::decay_t<T>>);
  101. new(_value_ptr()) T(std::forward<Args>(args)...);
  102. // backdoor for important builtin types
  103. if constexpr(std::is_same_v<T, DummyInstance>){
  104. _enable_instance_dict();
  105. }else if constexpr(std::is_same_v<T, Type>){
  106. _enable_instance_dict(PK_TYPE_ATTR_LOAD_FACTOR);
  107. }else if constexpr(std::is_same_v<T, DummyModule>){
  108. _enable_instance_dict(PK_TYPE_ATTR_LOAD_FACTOR);
  109. }
  110. }
  111. void _enable_instance_dict() {
  112. _attr = new(pool128_alloc<NameDict>()) NameDict();
  113. }
  114. void _enable_instance_dict(float lf){
  115. _attr = new(pool128_alloc<NameDict>()) NameDict(lf);
  116. }
  117. };
  118. template<typename T>
  119. inline constexpr int py_sizeof = sizeof(PyObject) + sizeof(T);
  120. static_assert(sizeof(PyObject) <= 16);
  121. const int kTpIntIndex = 3;
  122. const int kTpFloatIndex = 4;
  123. inline bool is_tagged(PyVar p) noexcept { return p.is_sso; }
  124. inline bool is_float(PyVar p) noexcept { return p.type.index == kTpFloatIndex; }
  125. inline bool is_int(PyVar p) noexcept { return p.type.index == kTpIntIndex; }
  126. inline bool is_type(PyVar obj, Type type) {
  127. PK_DEBUG_ASSERT(obj != nullptr)
  128. return obj.type == type;
  129. }
  130. template <typename, typename=void> struct has_gc_marker : std::false_type {};
  131. template <typename T> struct has_gc_marker<T, std::void_t<decltype(&T::_gc_mark)>> : std::true_type {};
  132. struct MappingProxy{
  133. PyVar obj;
  134. MappingProxy(PyVar obj) : obj(obj) {}
  135. NameDict& attr() { return obj->attr(); }
  136. void _gc_mark(VM*) const;
  137. };
  138. StrName _type_name(VM* vm, Type type);
  139. template<typename T> T to_void_p(VM*, PyVar);
  140. PyVar from_void_p(VM*, void*);
  141. template<typename T>
  142. obj_get_t<T> PyVar::obj_get(){
  143. if constexpr(is_sso_v<T>){
  144. return as<T>();
  145. }else{
  146. PK_DEBUG_ASSERT(!is_sso)
  147. void* v = ((PyObject*)_1)->_value_ptr();
  148. return *reinterpret_cast<T*>(v);
  149. }
  150. }
  151. #define PK_OBJ_GET(T, obj) (obj).obj_get<T>()
  152. #define PK_OBJ_MARK(obj) \
  153. if(!is_tagged(obj) && !(obj)->gc_marked) { \
  154. vm->__obj_gc_mark(obj); \
  155. }
  156. #define VAR(x) py_var(vm, x)
  157. #define CAST(T, x) py_cast<T>(vm, x)
  158. #define _CAST(T, x) _py_cast<T>(vm, x)
  159. #define CAST_F(x) py_cast<f64>(vm, x)
  160. #define CAST_DEFAULT(T, x, default_value) (x != vm->None) ? py_cast<T>(vm, x) : (default_value)
  161. /*****************************************************************/
  162. inline bool try_cast_int(PyVar obj, i64* val) noexcept {
  163. if(is_int(obj)){
  164. *val = obj.as<i64>();
  165. return true;
  166. }
  167. return false;
  168. }
  169. extern PyVar const PY_NULL;
  170. extern PyVar const PY_OP_CALL;
  171. extern PyVar const PY_OP_YIELD;
  172. } // namespace pkpy