add c11_vector__foreach

This commit is contained in:
blueloveTH 2024-06-22 15:26:20 +08:00
parent 841be061e0
commit 58c5bb1d35
4 changed files with 20 additions and 12 deletions

View File

@ -88,6 +88,9 @@ void* c11_vector__emplace(c11_vector* self);
} \ } \
}while(0) }while(0)
#define c11_vector__foreach(T, self, it) \
for(T* it = (T*)(self)->data; it != (T*)(self)->data + (self)->count; it++)
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

View File

@ -62,6 +62,7 @@ struct CodeObject {
}; };
struct FuncDecl { struct FuncDecl {
PK_ALWAYS_PASS_BY_POINTER(FuncDecl)
struct KwArg { struct KwArg {
int index; // index in co->varnames int index; // index in co->varnames
StrName key; // name of this argument StrName key; // name of this argument
@ -70,8 +71,8 @@ struct FuncDecl {
CodeObject_ code; // code object of this function CodeObject_ code; // code object of this function
small_vector_2<int, 8> args; // indices in co->varnames small_vector_2<int, 8> args; // indices in co->varnames
small_vector_2<KwArg, 6> kwargs; // indices in co->varnames c11_vector/*T=KwArg*/ kwargs; // indices in co->varnames
int starred_arg = -1; // index in co->varnames, -1 if no *arg int starred_arg = -1; // index in co->varnames, -1 if no *arg
int starred_kwarg = -1; // index in co->varnames, -1 if no **kwarg int starred_kwarg = -1; // index in co->varnames, -1 if no **kwarg
@ -84,16 +85,18 @@ struct FuncDecl {
void add_kwarg(int index, StrName key, PyVar value) { void add_kwarg(int index, StrName key, PyVar value) {
c11_smallmap_n2i__set(&kw_to_index, key.index, index); c11_smallmap_n2i__set(&kw_to_index, key.index, index);
kwargs.push_back(KwArg{index, key, value}); c11_vector__push(KwArg, &kwargs, (KwArg{index, key.index, value}));
} }
void _gc_mark(VM*) const; void _gc_mark(VM*) const;
FuncDecl(){ FuncDecl(){
c11_vector__ctor(&kwargs, sizeof(KwArg));
c11_smallmap_n2i__ctor(&kw_to_index); c11_smallmap_n2i__ctor(&kw_to_index);
} }
~FuncDecl(){ ~FuncDecl(){
c11_vector__dtor(&kwargs);
c11_smallmap_n2i__dtor(&kw_to_index); c11_smallmap_n2i__dtor(&kw_to_index);
} }
}; };

View File

@ -84,7 +84,7 @@ Error* Compiler::pop_context() noexcept{
} }
if(func->type == FuncType_UNSET) { if(func->type == FuncType_UNSET) {
bool is_simple = true; bool is_simple = true;
if(func->kwargs.size() > 0) is_simple = false; if(func->kwargs.count > 0) is_simple = false;
if(func->starred_arg >= 0) is_simple = false; if(func->starred_arg >= 0) is_simple = false;
if(func->starred_kwarg >= 0) is_simple = false; if(func->starred_kwarg >= 0) is_simple = false;
@ -1165,8 +1165,8 @@ Error* Compiler::_compile_f_args(FuncDecl_ decl, bool enable_type_hints) noexcep
for(int j: decl->args) { for(int j: decl->args) {
if(decl->code->varnames[j] == name) return SyntaxError("duplicate argument name"); if(decl->code->varnames[j] == name) return SyntaxError("duplicate argument name");
} }
for(auto& kv: decl->kwargs) { c11_vector__foreach(FuncDecl::KwArg, &decl->kwargs, kv) {
if(decl->code->varnames[kv.index] == name) return SyntaxError("duplicate argument name"); if(decl->code->varnames[kv->index] == name) return SyntaxError("duplicate argument name");
} }
if(decl->starred_arg != -1 && decl->code->varnames[decl->starred_arg] == name) { if(decl->starred_arg != -1 && decl->code->varnames[decl->starred_arg] == name) {
return SyntaxError("duplicate argument name"); return SyntaxError("duplicate argument name");

View File

@ -996,8 +996,9 @@ void VM::__prepare_py_call(PyVar* buffer, ArgsView args, ArgsView kwargs, const
for(int index: decl->args) for(int index: decl->args)
buffer[index] = args[i++]; buffer[index] = args[i++];
// prepare kwdefaults // prepare kwdefaults
for(auto& kv: decl->kwargs) c11_vector__foreach(FuncDecl::KwArg, &decl->kwargs, kv) {
buffer[kv.index] = kv.value; buffer[kv->index] = kv->value;
}
// handle *args // handle *args
if(decl->starred_arg != -1) { if(decl->starred_arg != -1) {
@ -1006,9 +1007,9 @@ void VM::__prepare_py_call(PyVar* buffer, ArgsView args, ArgsView kwargs, const
i += vargs.size(); i += vargs.size();
} else { } else {
// kwdefaults override // kwdefaults override
for(auto& kv: decl->kwargs) { c11_vector__foreach(FuncDecl::KwArg, &decl->kwargs, kv) {
if(i >= args.size()) break; if(i >= args.size()) break;
buffer[kv.index] = args[i++]; buffer[kv->index] = args[i++];
} }
if(i < args.size()) TypeError(_S("too many arguments", " (", decl->code->name, ')')); if(i < args.size()) TypeError(_S("too many arguments", " (", decl->code->name, ')'));
} }
@ -1830,8 +1831,9 @@ void NativeFunc::_gc_mark(VM* vm) const {
void FuncDecl::_gc_mark(VM* vm) const { void FuncDecl::_gc_mark(VM* vm) const {
code->_gc_mark(vm); code->_gc_mark(vm);
for(int i = 0; i < kwargs.size(); i++) c11_vector__foreach(FuncDecl::KwArg, &kwargs, kv) {
vm->obj_gc_mark(kwargs[i].value); vm->obj_gc_mark(kv->value);
}
} }
void List::_gc_mark(VM* vm) const { void List::_gc_mark(VM* vm) const {