mirror of
https://github.com/pocketpy/pocketpy
synced 2025-10-25 22:10:17 +00:00
some fix
This commit is contained in:
parent
4bdb268d93
commit
9e426d3291
@ -25,19 +25,18 @@ _Str pad(const _Str& s, const int n){
|
|||||||
return s + _Str(n - s.size(), ' ');
|
return s + _Str(n - s.size(), ' ');
|
||||||
}
|
}
|
||||||
|
|
||||||
class CodeObject {
|
struct CodeObject {
|
||||||
public:
|
|
||||||
std::vector<ByteCode> co_code;
|
std::vector<ByteCode> co_code;
|
||||||
_Str co_filename;
|
_Str co_filename;
|
||||||
_Str co_name;
|
_Str co_name;
|
||||||
|
|
||||||
PyVarList co_consts;
|
PyVarList co_consts;
|
||||||
std::vector<NamePointer> co_names;
|
std::vector<std::shared_ptr<NamePointer>> co_names;
|
||||||
|
|
||||||
int addName(const _Str& name, NameScope scope){
|
int addName(const _Str& name, NameScope scope){
|
||||||
auto p = NamePointer(name, scope);
|
auto p = std::make_shared<NamePointer>(name, scope);
|
||||||
for(int i=0; i<co_names.size(); i++){
|
for(int i=0; i<co_names.size(); i++){
|
||||||
if(co_names[i] == p) return i;
|
if(*co_names[i] == *p) return i;
|
||||||
}
|
}
|
||||||
co_names.push_back(p);
|
co_names.push_back(p);
|
||||||
return co_names.size() - 1;
|
return co_names.size() - 1;
|
||||||
@ -74,7 +73,7 @@ public:
|
|||||||
_StrStream names;
|
_StrStream names;
|
||||||
names << "co_names: ";
|
names << "co_names: ";
|
||||||
for(int i=0; i<co_names.size(); i++){
|
for(int i=0; i<co_names.size(); i++){
|
||||||
names << co_names[i].name;
|
names << co_names[i]->name;
|
||||||
if(i != co_names.size() - 1) names << ", ";
|
if(i != co_names.size() - 1) names << ", ";
|
||||||
}
|
}
|
||||||
ss << '\n' << consts.str() << '\n' << names.str() << '\n';
|
ss << '\n' << consts.str() << '\n' << names.str() << '\n';
|
||||||
@ -108,6 +107,10 @@ public:
|
|||||||
return code->co_code[ip].line;
|
return code->co_code[ip].line;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int stackSize() const {
|
||||||
|
return s_data.size();
|
||||||
|
}
|
||||||
|
|
||||||
inline bool isEnd() const {
|
inline bool isEnd() const {
|
||||||
return ip >= code->co_code.size();
|
return ip >= code->co_code.size();
|
||||||
}
|
}
|
||||||
@ -119,7 +122,6 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
inline PyVar __deref_pointer(VM*, PyVar);
|
inline PyVar __deref_pointer(VM*, PyVar);
|
||||||
inline _Pointer popPtr(VM*);
|
|
||||||
|
|
||||||
inline PyVar popValue(VM* vm){
|
inline PyVar popValue(VM* vm){
|
||||||
return __deref_pointer(vm, __pop());
|
return __deref_pointer(vm, __pop());
|
||||||
|
|||||||
@ -105,12 +105,12 @@ public:
|
|||||||
rules[TK("@id")] = { METHOD(exprName), NO_INFIX };
|
rules[TK("@id")] = { METHOD(exprName), NO_INFIX };
|
||||||
rules[TK("@num")] = { METHOD(exprLiteral), NO_INFIX };
|
rules[TK("@num")] = { METHOD(exprLiteral), NO_INFIX };
|
||||||
rules[TK("@str")] = { METHOD(exprLiteral), NO_INFIX };
|
rules[TK("@str")] = { METHOD(exprLiteral), NO_INFIX };
|
||||||
rules[TK("=")] = { nullptr, METHOD(exprAssign), PREC_ASSIGNMENT };
|
rules[TK("=")] = { nullptr, METHOD(exprAssign), PREC_LOWEST };
|
||||||
rules[TK("+=")] = { nullptr, METHOD(exprAssign), PREC_ASSIGNMENT };
|
rules[TK("+=")] = { nullptr, METHOD(exprAssign), PREC_LOWEST };
|
||||||
rules[TK("-=")] = { nullptr, METHOD(exprAssign), PREC_ASSIGNMENT };
|
rules[TK("-=")] = { nullptr, METHOD(exprAssign), PREC_LOWEST };
|
||||||
rules[TK("*=")] = { nullptr, METHOD(exprAssign), PREC_ASSIGNMENT };
|
rules[TK("*=")] = { nullptr, METHOD(exprAssign), PREC_LOWEST };
|
||||||
rules[TK("/=")] = { nullptr, METHOD(exprAssign), PREC_ASSIGNMENT };
|
rules[TK("/=")] = { nullptr, METHOD(exprAssign), PREC_LOWEST };
|
||||||
rules[TK("//=")] = { nullptr, METHOD(exprAssign), PREC_ASSIGNMENT };
|
rules[TK("//=")] = { nullptr, METHOD(exprAssign), PREC_LOWEST };
|
||||||
#undef METHOD
|
#undef METHOD
|
||||||
#undef NO_INFIX
|
#undef NO_INFIX
|
||||||
}
|
}
|
||||||
@ -301,12 +301,12 @@ public:
|
|||||||
void exprAssign(){
|
void exprAssign(){
|
||||||
_TokenType op = parser->previous.type;
|
_TokenType op = parser->previous.type;
|
||||||
if(op == TK("=")) { // a = (expr)
|
if(op == TK("=")) { // a = (expr)
|
||||||
parsePrecedence((Precedence)(rules[op].precedence + 1));
|
compileExpressionTuple();
|
||||||
emitCode(OP_STORE_PTR);
|
emitCode(OP_STORE_PTR);
|
||||||
}else{ // a += (expr) -> a = a + (expr)
|
}else{ // a += (expr) -> a = a + (expr)
|
||||||
// TODO: optimization is needed for inplace operators
|
// TODO: optimization is needed for inplace operators
|
||||||
emitCode(OP_DUP_TOP);
|
emitCode(OP_DUP_TOP);
|
||||||
parsePrecedence((Precedence)(rules[op].precedence + 1));
|
compileExpression();
|
||||||
switch (op) {
|
switch (op) {
|
||||||
case TK("+="): emitCode(OP_BINARY_OP, 0); break;
|
case TK("+="): emitCode(OP_BINARY_OP, 0); break;
|
||||||
case TK("-="): emitCode(OP_BINARY_OP, 1); break;
|
case TK("-="): emitCode(OP_BINARY_OP, 1); break;
|
||||||
|
|||||||
@ -66,7 +66,6 @@ struct Token{
|
|||||||
enum Precedence {
|
enum Precedence {
|
||||||
PREC_NONE,
|
PREC_NONE,
|
||||||
PREC_LOWEST,
|
PREC_LOWEST,
|
||||||
PREC_ASSIGNMENT, // =
|
|
||||||
PREC_LOGICAL_OR, // or
|
PREC_LOGICAL_OR, // or
|
||||||
PREC_LOGICAL_AND, // and
|
PREC_LOGICAL_AND, // and
|
||||||
PREC_EQUALITY, // == !=
|
PREC_EQUALITY, // == !=
|
||||||
|
|||||||
@ -434,8 +434,8 @@ extern "C" {
|
|||||||
VM* createVM(PrintFn printFn){
|
VM* createVM(PrintFn printFn){
|
||||||
VM* vm = new VM();
|
VM* vm = new VM();
|
||||||
__initializeBuiltinFunctions(vm);
|
__initializeBuiltinFunctions(vm);
|
||||||
//__runCodeBuiltins(vm, __BUILTINS_CODE);
|
__runCodeBuiltins(vm, __BUILTINS_CODE);
|
||||||
//__addModuleRandom(vm);
|
__addModuleRandom(vm);
|
||||||
vm->printFn = printFn;
|
vm->printFn = printFn;
|
||||||
return vm;
|
return vm;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -29,18 +29,18 @@ struct NamePointer : BasePointer {
|
|||||||
};
|
};
|
||||||
|
|
||||||
struct AttrPointer : BasePointer {
|
struct AttrPointer : BasePointer {
|
||||||
const _Pointer root;
|
mutable PyVar obj;
|
||||||
const NamePointer* attr;
|
const NamePointer* attr;
|
||||||
AttrPointer(const _Pointer& root, const NamePointer* attr) : root(root), attr(attr) {}
|
AttrPointer(PyVar obj, const NamePointer* attr) : obj(obj), attr(attr) {}
|
||||||
|
|
||||||
PyVar get(VM* vm, Frame* frame) const;
|
PyVar get(VM* vm, Frame* frame) const;
|
||||||
void set(VM* vm, Frame* frame, PyVar val) const;
|
void set(VM* vm, Frame* frame, PyVar val) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct IndexPointer : BasePointer {
|
struct IndexPointer : BasePointer {
|
||||||
const _Pointer root;
|
mutable PyVar obj;
|
||||||
const PyVar index;
|
const PyVar index;
|
||||||
IndexPointer(_Pointer root, PyVar index) : root(root), index(index) {}
|
IndexPointer(PyVar obj, PyVar index) : obj(obj), index(index) {}
|
||||||
|
|
||||||
PyVar get(VM* vm, Frame* frame) const;
|
PyVar get(VM* vm, Frame* frame) const;
|
||||||
void set(VM* vm, Frame* frame, PyVar val) const;
|
void set(VM* vm, Frame* frame, PyVar val) const;
|
||||||
|
|||||||
41
src/vm.h
41
src/vm.h
@ -132,32 +132,31 @@ public:
|
|||||||
callstack.push(frame);
|
callstack.push(frame);
|
||||||
while(!frame->isEnd()){
|
while(!frame->isEnd()){
|
||||||
const ByteCode& byte = frame->readCode();
|
const ByteCode& byte = frame->readCode();
|
||||||
printf("%s (%d)\n", OP_NAMES[byte.op], byte.arg);
|
printf("%s (%d) stack_size: %d\n", OP_NAMES[byte.op], byte.arg, frame->stackSize());
|
||||||
|
|
||||||
switch (byte.op)
|
switch (byte.op)
|
||||||
{
|
{
|
||||||
case OP_LOAD_CONST: frame->push(frame->code->co_consts[byte.arg]); break;
|
case OP_LOAD_CONST: frame->push(frame->code->co_consts[byte.arg]); break;
|
||||||
case OP_LOAD_NAME_PTR: {
|
case OP_LOAD_NAME_PTR: {
|
||||||
const NamePointer* p = &frame->code->co_names[byte.arg];
|
frame->push(PyPointer(frame->code->co_names[byte.arg]));
|
||||||
frame->push(PyPointer(_Pointer(p)));
|
|
||||||
} break;
|
} break;
|
||||||
case OP_STORE_NAME_PTR: {
|
case OP_STORE_NAME_PTR: {
|
||||||
const NamePointer& p = frame->code->co_names[byte.arg];
|
const auto& p = frame->code->co_names[byte.arg];
|
||||||
p.set(this, frame.get(), frame->popValue(this));
|
p->set(this, frame.get(), frame->popValue(this));
|
||||||
} break;
|
} break;
|
||||||
case OP_BUILD_ATTR_PTR: {
|
case OP_BUILD_ATTR_PTR: {
|
||||||
const NamePointer* attr = &frame->code->co_names[byte.arg];
|
const auto& attr = frame->code->co_names[byte.arg];
|
||||||
_Pointer root = frame->popPtr(this);
|
PyVar obj = frame->popValue(this);
|
||||||
frame->push(PyPointer(std::make_shared<AttrPointer>(root, attr)));
|
frame->push(PyPointer(std::make_shared<AttrPointer>(obj, attr.get())));
|
||||||
} break;
|
} break;
|
||||||
case OP_BUILD_INDEX_PTR: {
|
case OP_BUILD_INDEX_PTR: {
|
||||||
PyVar index = frame->popValue(this);
|
PyVar index = frame->popValue(this);
|
||||||
_Pointer root = frame->popPtr(this);
|
PyVar obj = frame->popValue(this);
|
||||||
frame->push(PyPointer(std::make_shared<IndexPointer>(root, index)));
|
frame->push(PyPointer(std::make_shared<IndexPointer>(obj, index)));
|
||||||
} break;
|
} break;
|
||||||
case OP_STORE_PTR: {
|
case OP_STORE_PTR: {
|
||||||
PyVar obj = frame->popValue(this);
|
PyVar obj = frame->popValue(this);
|
||||||
_Pointer p = frame->popPtr(this);
|
_Pointer p = PyPointer_AS_C(frame->__pop());
|
||||||
p->set(this, frame.get(), obj);
|
p->set(this, frame.get(), obj);
|
||||||
} break;
|
} break;
|
||||||
case OP_STORE_FUNCTION:
|
case OP_STORE_FUNCTION:
|
||||||
@ -168,7 +167,7 @@ public:
|
|||||||
} break;
|
} break;
|
||||||
case OP_BUILD_CLASS:
|
case OP_BUILD_CLASS:
|
||||||
{
|
{
|
||||||
const _Str& clsName = frame->code->co_names[byte.arg].name;
|
const _Str& clsName = frame->code->co_names[byte.arg]->name;
|
||||||
PyVar clsBase = frame->popValue(this);
|
PyVar clsBase = frame->popValue(this);
|
||||||
if(clsBase == None) clsBase = _tp_object;
|
if(clsBase == None) clsBase = _tp_object;
|
||||||
__checkType(clsBase, _tp_type);
|
__checkType(clsBase, _tp_type);
|
||||||
@ -321,7 +320,7 @@ public:
|
|||||||
} break;
|
} break;
|
||||||
case OP_IMPORT_NAME:
|
case OP_IMPORT_NAME:
|
||||||
{
|
{
|
||||||
const _Str& name = frame->code->co_names[byte.arg].name;
|
const _Str& name = frame->code->co_names[byte.arg]->name;
|
||||||
auto it = _modules.find(name);
|
auto it = _modules.find(name);
|
||||||
if(it == _modules.end()){
|
if(it == _modules.end()){
|
||||||
_error("ImportError", "module '" + name + "' not found");
|
_error("ImportError", "module '" + name + "' not found");
|
||||||
@ -578,33 +577,29 @@ void NamePointer::set(VM* vm, Frame* frame, PyVar val) const{
|
|||||||
case NAME_LOCAL: frame->f_locals[name] = val; break;
|
case NAME_LOCAL: frame->f_locals[name] = val; break;
|
||||||
case NAME_GLOBAL:
|
case NAME_GLOBAL:
|
||||||
{
|
{
|
||||||
if(frame->f_locals.find(name) != frame->f_locals.end()){
|
if(frame->f_locals.count(name) > 0){
|
||||||
frame->f_locals[name] = frame->popValue(vm);
|
frame->f_locals[name] = val;
|
||||||
}else{
|
}else{
|
||||||
frame->f_globals->operator[](name) = frame->popValue(vm);
|
frame->f_globals->operator[](name) = val;
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
|
default: UNREACHABLE();
|
||||||
}
|
}
|
||||||
UNREACHABLE();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
PyVar AttrPointer::get(VM* vm, Frame* frame) const{
|
PyVar AttrPointer::get(VM* vm, Frame* frame) const{
|
||||||
PyVar obj = root->get(vm, frame);
|
|
||||||
return vm->getAttr(obj, attr->name);
|
return vm->getAttr(obj, attr->name);
|
||||||
}
|
}
|
||||||
|
|
||||||
void AttrPointer::set(VM* vm, Frame* frame, PyVar val) const{
|
void AttrPointer::set(VM* vm, Frame* frame, PyVar val) const{
|
||||||
PyVar obj = root->get(vm, frame);
|
|
||||||
vm->setAttr(obj, attr->name, val);
|
vm->setAttr(obj, attr->name, val);
|
||||||
}
|
}
|
||||||
|
|
||||||
PyVar IndexPointer::get(VM* vm, Frame* frame) const{
|
PyVar IndexPointer::get(VM* vm, Frame* frame) const{
|
||||||
PyVar obj = root->get(vm, frame);
|
|
||||||
return vm->call(obj, __getitem__, {index});
|
return vm->call(obj, __getitem__, {index});
|
||||||
}
|
}
|
||||||
|
|
||||||
void IndexPointer::set(VM* vm, Frame* frame, PyVar val) const{
|
void IndexPointer::set(VM* vm, Frame* frame, PyVar val) const{
|
||||||
PyVar obj = root->get(vm, frame);
|
|
||||||
vm->call(obj, __setitem__, {index, val});
|
vm->call(obj, __setitem__, {index, val});
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -612,8 +607,4 @@ void IndexPointer::set(VM* vm, Frame* frame, PyVar val) const{
|
|||||||
inline PyVar Frame::__deref_pointer(VM* vm, PyVar v){
|
inline PyVar Frame::__deref_pointer(VM* vm, PyVar v){
|
||||||
if(v->isType(vm->_tp_pointer)) v = vm->PyPointer_AS_C(v)->get(vm, this);
|
if(v->isType(vm->_tp_pointer)) v = vm->PyPointer_AS_C(v)->get(vm, this);
|
||||||
return v;
|
return v;
|
||||||
}
|
|
||||||
|
|
||||||
inline _Pointer Frame::popPtr(VM* vm){
|
|
||||||
return vm->PyPointer_AS_C(__pop());
|
|
||||||
}
|
}
|
||||||
Loading…
x
Reference in New Issue
Block a user