mirror of
https://gitee.com/Lyon1998/pikapython.git
synced 2025-01-29 17:22:56 +08:00
961 lines
32 KiB
C
961 lines
32 KiB
C
/*
|
|
* This file is part of the PikaPython project.
|
|
* http://github.com/pikastech/pikapython
|
|
*
|
|
* MIT License
|
|
*
|
|
* Copyright (c) 2021 lyon liang6516@outlook.com
|
|
* Copyright (c) 2023 Gorgon Meducer embedded_zhuroan@hotmail.com
|
|
*
|
|
* Permission is hereby granted, free of charge, to any person obtaining a
|
|
* copy of this software and associated documentation files (the "Software"),
|
|
* to deal in the Software without restriction, including without limitation
|
|
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
|
* and/or sell copies of the Software, and to permit persons to whom the
|
|
* Software is furnished to do so, subject to the following conditions:
|
|
*
|
|
* The above copyright notice and this permission notice shall be included in
|
|
* all copies or substantial portions of the Software.
|
|
*
|
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
|
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
|
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
|
* DEALINGS IN THE SOFTWARE.
|
|
*/
|
|
#include <stdint.h>
|
|
#ifdef __cplusplus
|
|
extern "C" {
|
|
#endif
|
|
|
|
#ifndef _Process__H
|
|
#define _Process__H
|
|
|
|
#include "dataArgs.h"
|
|
#include "dataLink.h"
|
|
#include "dataMemory.h"
|
|
#include "dataQueue.h"
|
|
#include "dataStack.h"
|
|
#include "dataStrs.h"
|
|
|
|
typedef struct InstructUnit InstructUnit;
|
|
struct InstructUnit {
|
|
uint8_t deepth;
|
|
uint8_t isNewLine_instruct;
|
|
uint16_t const_pool_index;
|
|
};
|
|
|
|
typedef struct ConstPool ConstPool;
|
|
struct ConstPool {
|
|
Arg* arg_buff;
|
|
uint32_t content_offset_now;
|
|
uint32_t size;
|
|
void* content_start;
|
|
void (*output_redirect_fun)(ConstPool* self, char* content);
|
|
FILE* output_f;
|
|
};
|
|
|
|
typedef struct InstructArray InstructArray;
|
|
struct InstructArray {
|
|
Arg* arg_buff;
|
|
uint32_t content_offset_now;
|
|
uint32_t size;
|
|
void* content_start;
|
|
void (*output_redirect_fun)(InstructArray* self, InstructUnit* ins_unit);
|
|
FILE* output_f;
|
|
};
|
|
|
|
typedef struct ByteCodeFrame ByteCodeFrame;
|
|
struct ByteCodeFrame {
|
|
char* name;
|
|
Hash name_hash;
|
|
ConstPool const_pool;
|
|
InstructArray instruct_array;
|
|
int32_t label_pc;
|
|
};
|
|
|
|
typedef struct NativeProperty NativeProperty;
|
|
struct NativeProperty {
|
|
const NativeProperty* super;
|
|
const Arg* methodGroup;
|
|
uint32_t methodGroupCount;
|
|
};
|
|
|
|
enum InstructIndex {
|
|
#define __INS_ENUM
|
|
#include "__instruction_table.h"
|
|
__INSTRUCTION_CNT,
|
|
__INSTRUCTION_INDEX_MAX = 0xFFFF,
|
|
__INSTRUCTION_UNKNOWN = 0xFFFF,
|
|
};
|
|
|
|
typedef enum {
|
|
VM_JMP_EXIT = -999,
|
|
VM_JMP_CONTINUE = -997,
|
|
VM_JMP_BREAK = -998,
|
|
VM_JMP_RAISE = -996,
|
|
} VM_JMP;
|
|
|
|
#define VM_PC_EXIT (-99999)
|
|
|
|
typedef enum {
|
|
TRY_STATE_NONE = 0,
|
|
TRY_STATE_INNER,
|
|
} TRY_STATE;
|
|
|
|
typedef enum {
|
|
TRY_RESULT_NONE = 0,
|
|
TRY_RESULT_RAISE,
|
|
} TRY_RESULT;
|
|
|
|
typedef struct PikaThreadState PikaVMThread;
|
|
struct PikaThreadState {
|
|
TRY_STATE try_state;
|
|
TRY_RESULT try_result;
|
|
int8_t error_code;
|
|
uint8_t line_error_code;
|
|
uint8_t try_error_code;
|
|
};
|
|
|
|
typedef PikaObj VMParameters;
|
|
typedef struct PikaVMFrame PikaVMFrame;
|
|
struct PikaVMFrame {
|
|
VMParameters* locals;
|
|
VMParameters* globals;
|
|
Stack stack;
|
|
int32_t jmp;
|
|
int32_t pc;
|
|
ByteCodeFrame* bytecode_frame;
|
|
uint8_t loop_deepth;
|
|
uint32_t ins_cnt;
|
|
pika_bool in_super;
|
|
uint8_t super_invoke_deepth;
|
|
PikaVMThread* vm_thread;
|
|
pika_bool ireg[PIKA_REGIST_SIZE];
|
|
PikaObj* oreg[16];
|
|
pika_bool in_repl;
|
|
};
|
|
|
|
struct PikaObj {
|
|
Args* list;
|
|
void* constructor;
|
|
#if PIKA_GC_MARK_SWEEP_ENABLE
|
|
PikaObj* gcNext;
|
|
#endif
|
|
#if PIKA_KERNAL_DEBUG_ENABLE
|
|
char* name;
|
|
Arg* aName;
|
|
PikaObj* parent;
|
|
pika_bool isAlive;
|
|
pika_bool isGCRoot;
|
|
#endif
|
|
#if PIKA_GC_MARK_SWEEP_ENABLE && PIKA_KERNAL_DEBUG_ENABLE
|
|
PikaObj* gcRoot;
|
|
#endif
|
|
uint8_t refcnt;
|
|
uint16_t flag;
|
|
PikaVMFrame* vmFrame;
|
|
};
|
|
|
|
typedef struct PikaGC PikaGC;
|
|
typedef int (*pikaGC_hook)(PikaGC* gc);
|
|
struct PikaGC {
|
|
uint32_t markDeepth;
|
|
pikaGC_hook onMarkObj;
|
|
PikaObj* oThis;
|
|
};
|
|
|
|
typedef struct RangeData RangeData;
|
|
struct RangeData {
|
|
int64_t start;
|
|
int64_t end;
|
|
int64_t step;
|
|
int64_t i;
|
|
};
|
|
|
|
typedef struct PikaObjState PikaObjState;
|
|
struct PikaObjState {
|
|
Arg* helpModulesCmodule;
|
|
pika_bool inRootObj;
|
|
#if PIKA_GC_MARK_SWEEP_ENABLE
|
|
PikaObj* gcChain;
|
|
uint32_t objCnt;
|
|
uint32_t objCntMax;
|
|
uint32_t objCntLastGC;
|
|
uint32_t markSweepBusy;
|
|
#endif
|
|
};
|
|
|
|
#define OBJ_FLAG_PROXY_GETATTRIBUTE 1 << 0
|
|
#define OBJ_FLAG_PROXY_GETATTR 1 << 1
|
|
#define OBJ_FLAG_PROXY_SETATTR 1 << 2
|
|
#define OBJ_FLAG_ALREADY_INIT 1 << 3
|
|
#define OBJ_FLAG_RUN_AS 1 << 4
|
|
#define OBJ_FLAG_GLOBALS 1 << 5
|
|
#define OBJ_FLAG_GC_MARKED 1 << 6
|
|
#define OBJ_FLAG_GC_ROOT 1 << 7
|
|
#define OBJ_FLAG_PROXY_METHOD 1 << 8
|
|
#define OBJ_FLAG_IN_DEL 1 << 9
|
|
|
|
#define PIKA_KEY_UP 0x41
|
|
#define PIKA_KEY_DOWN 0x42
|
|
#define PIKA_KEY_RIGHT 0x43
|
|
#define PIKA_KEY_LEFT 0x44
|
|
|
|
static inline uint8_t obj_getFlag(PikaObj* self, uint16_t flag) {
|
|
pika_assert(self);
|
|
return (self->flag & flag) == flag;
|
|
}
|
|
|
|
static inline void obj_setFlag(PikaObj* self, uint16_t flag) {
|
|
pika_assert(self);
|
|
self->flag |= flag;
|
|
#if PIKA_KERNAL_DEBUG_ENABLE
|
|
if (flag == OBJ_FLAG_GC_ROOT) {
|
|
self->isGCRoot = pika_true;
|
|
}
|
|
#endif
|
|
}
|
|
|
|
static inline void obj_clearFlag(PikaObj* self, uint16_t flag) {
|
|
self->flag &= ~flag;
|
|
#if PIKA_KERNAL_DEBUG_ENABLE
|
|
if (flag == OBJ_FLAG_GC_ROOT) {
|
|
self->isGCRoot = pika_false;
|
|
}
|
|
#endif
|
|
}
|
|
|
|
typedef PikaObj* (*NewFun)(Args* args);
|
|
typedef PikaObj* (*InitFun)(PikaObj* self, Args* args);
|
|
typedef void (*Method)(PikaObj* self, Args* args);
|
|
|
|
typedef struct MethodInfo MethodInfo;
|
|
struct MethodInfo {
|
|
char* name;
|
|
char* dec;
|
|
char* ptr;
|
|
char* typelist;
|
|
PikaObj* def_context;
|
|
ArgType type;
|
|
ByteCodeFrame* bytecode_frame;
|
|
};
|
|
|
|
typedef struct MethodProp {
|
|
void* ptr;
|
|
char* type_list;
|
|
char* name;
|
|
ByteCodeFrame* bytecode_frame;
|
|
PikaObj* def_context;
|
|
PikaObj* host_obj;
|
|
char* declareation;
|
|
} MethodProp;
|
|
|
|
typedef struct MethodPropNative {
|
|
void* ptr;
|
|
char* type_list;
|
|
#if !PIKA_NANO_ENABLE
|
|
char* name;
|
|
#endif
|
|
} MethodPropNative;
|
|
|
|
typedef PikaObj LibObj;
|
|
typedef PikaObj PikaMaker;
|
|
|
|
/* operation */
|
|
int32_t obj_deinit(PikaObj* self);
|
|
int obj_GC(PikaObj* self);
|
|
int32_t obj_init(PikaObj* self, Args* args);
|
|
int32_t obj_update(PikaObj* self);
|
|
int32_t obj_enable(PikaObj* self);
|
|
int32_t obj_disable(PikaObj* self);
|
|
|
|
// arg type operations
|
|
PIKA_RES obj_setInt(PikaObj* self, char* argPath, int64_t val);
|
|
PIKA_RES obj_setObj(PikaObj* self, char* argPath, PikaObj* obj);
|
|
PIKA_RES obj_setRef(PikaObj* self, char* argPath, PikaObj* pointer);
|
|
PIKA_RES obj_setPtr(PikaObj* self, char* argPath, void* pointer);
|
|
PIKA_RES obj_setFloat(PikaObj* self, char* argPath, pika_float value);
|
|
PIKA_RES obj_setStr(PikaObj* self, char* argPath, char* str);
|
|
PIKA_RES obj_setNone(PikaObj* self, char* argPath);
|
|
PIKA_RES obj_setArg(PikaObj* self, char* argPath, Arg* arg);
|
|
PIKA_RES obj_setArg_noCopy(PikaObj* self, char* argPath, Arg* arg);
|
|
PIKA_RES obj_setBytes(PikaObj* self, char* argPath, uint8_t* src, size_t size);
|
|
|
|
void* obj_getPtr(PikaObj* self, char* argPath);
|
|
PikaObj* obj_getBuiltins(void);
|
|
pika_float obj_getFloat(PikaObj* self, char* argPath);
|
|
char* obj_getStr(PikaObj* self, char* argPath);
|
|
int64_t obj_getInt(PikaObj* self, char* argPath);
|
|
int64_t obj_getSize(PikaObj* arg_obj);
|
|
pika_bool obj_getBool(PikaObj* self, char* argPath);
|
|
Arg* obj_getArg(PikaObj* self, char* argPath);
|
|
uint8_t* obj_getBytes(PikaObj* self, char* argPath);
|
|
size_t obj_getBytesSize(PikaObj* self, char* argPath);
|
|
size_t obj_loadBytes(PikaObj* self, char* argPath, uint8_t* out_buff);
|
|
|
|
char* obj_print(PikaObj* self, char* name);
|
|
|
|
// args operations
|
|
int32_t obj_load(PikaObj* self, Args* args, char* name);
|
|
|
|
// subObject
|
|
int32_t obj_addOther(PikaObj* self, char* subObjectName, void* new_projcetFun);
|
|
PikaObj* obj_getObj(PikaObj* self, char* objPath);
|
|
PikaObj* obj_getHostObj(PikaObj* self, char* objPath);
|
|
PikaObj* obj_getHostObjWithIsTemp(PikaObj* self,
|
|
char* objPath,
|
|
pika_bool* pIsClass);
|
|
|
|
// subProcess
|
|
int32_t obj_freeObj(PikaObj* self, char* subObjectName);
|
|
|
|
/* method */
|
|
int32_t class_defineMethod(PikaObj* self,
|
|
char* name,
|
|
char* typelist,
|
|
Method methodPtr);
|
|
|
|
int32_t class_defineObjectMethod(PikaObj* self,
|
|
char* declareation,
|
|
Method methodPtr,
|
|
PikaObj* def_context,
|
|
ByteCodeFrame* bytecode_frame);
|
|
|
|
int32_t class_defineStaticMethod(PikaObj* self,
|
|
char* declareation,
|
|
Method methodPtr,
|
|
PikaObj* def_context,
|
|
ByteCodeFrame* bytecode_frame);
|
|
|
|
int32_t class_defineConstructor(PikaObj* self,
|
|
char* name,
|
|
char* typelist,
|
|
Method methodPtr);
|
|
|
|
int32_t class_defineRunTimeConstructor(PikaObj* self,
|
|
char* declareation,
|
|
Method methodPtr,
|
|
PikaObj* def_context,
|
|
ByteCodeFrame* bytecode_frame);
|
|
|
|
int32_t obj_removeArg(PikaObj* self, char* argPath);
|
|
pika_bool obj_isArgExist(PikaObj* self, char* argPath);
|
|
pika_bool obj_isMethodExist(PikaObj* self, char* method);
|
|
PikaObj* obj_newObjFromConstructor(PikaObj* self,
|
|
char* name,
|
|
NewFun newClassFun);
|
|
PikaObj* newRootObj(char* name, NewFun newObjFun);
|
|
PikaObj* obj_getClassObj(PikaObj* obj);
|
|
Arg* obj_getMethodArg(PikaObj* obj, char* methodName);
|
|
Arg* obj_getMethodArg_noalloc(PikaObj* obj, char* methodName, Arg* arg_reg);
|
|
Arg* obj_getMethodArgWithFullPath(PikaObj* obj, char* methodPath);
|
|
Arg* obj_getMethodArgWithFullPath_noalloc(PikaObj* obj,
|
|
char* methodPath,
|
|
Arg* arg_reg);
|
|
|
|
void obj_setErrorCode(PikaObj* self, int32_t errCode);
|
|
|
|
void obj_setSysOut(PikaObj* self, char* fmt, ...);
|
|
|
|
uint8_t obj_getAnyArg(PikaObj* self,
|
|
char* targetArgName,
|
|
char* sourceArgPath,
|
|
Args* targetArgs);
|
|
|
|
void method_returnStr(Args* args, char* val);
|
|
void method_returnInt(Args* args, int64_t val);
|
|
void method_returnBool(Args* args, pika_bool val);
|
|
void method_returnFloat(Args* args, pika_float val);
|
|
void method_returnPtr(Args* args, void* val);
|
|
void method_returnObj(Args* args, void* val);
|
|
int64_t method_getInt(Args* args, char* argName);
|
|
pika_float method_getFloat(Args* args, char* argName);
|
|
char* method_getStr(Args* args, char* argName);
|
|
void method_returnArg(Args* args, Arg* arg);
|
|
MethodProp* methodArg_getProp(Arg* method_arg);
|
|
char* methodArg_getDec(Arg* method_arg);
|
|
char* methodArg_getTypeList(Arg* method_arg, char* buffs, size_t size);
|
|
char* methodArg_getName(Arg* method_arg, char* buffs, size_t size);
|
|
Arg* methodArg_setHostObj(Arg* method_arg, PikaObj* host_obj);
|
|
Arg* methodArg_super(Arg* aThis, NativeProperty** p_prop);
|
|
PikaObj* methodArg_getHostObj(Arg* method_arg);
|
|
ByteCodeFrame* methodArg_getBytecodeFrame(Arg* method_arg);
|
|
Method methodArg_getPtr(Arg* method_arg);
|
|
|
|
VMParameters* obj_run(PikaObj* self, char* cmd);
|
|
Arg* pika_runFunction0(Arg* functionArg);
|
|
Arg* pika_runFunction1(Arg* methodArg, Arg* arg1);
|
|
Arg* obj_runMethodArg0(PikaObj* self, Arg* methodArg);
|
|
Arg* obj_runMethodArg1(PikaObj* self, Arg* methodArg, Arg* arg1);
|
|
Arg* obj_runMethod0(PikaObj* self, char* methodName);
|
|
Arg* obj_runMethod1(PikaObj* self, char* methodName, Arg* arg1);
|
|
PikaObj* New_PikaObj(void);
|
|
PikaObj* New_PikaObj_noGC(void);
|
|
|
|
/* tools */
|
|
int64_t fast_atoi(char* src);
|
|
PIKA_RES fast_atoi_safe(char* src, int64_t* out);
|
|
char* fast_itoa(char* buf, uint32_t val);
|
|
|
|
/* shell */
|
|
void pikaPythonShell(PikaObj* self);
|
|
void pikaShellSetEcho(pika_bool enable_echo);
|
|
enum shellCTRL { SHELL_CTRL_CONTINUE, SHELL_CTRL_EXIT };
|
|
|
|
typedef struct ShellConfig ShellConfig;
|
|
typedef enum shellCTRL (*sh_handler)(PikaObj*, char*, ShellConfig*);
|
|
typedef char (*sh_getchar)(void);
|
|
|
|
int shConfig_deinit(ShellConfig* self);
|
|
|
|
#if PIKA_SHELL_FILTER_ENABLE
|
|
typedef struct FilterFIFO {
|
|
ByteQueue queue;
|
|
uint8_t ignore_mask;
|
|
uint8_t buffer[PIKA_SHELL_FILTER_FIFO_SIZE];
|
|
} FilterFIFO;
|
|
|
|
typedef struct FilterItem FilterItem;
|
|
|
|
typedef pika_bool FilterMessageHandler(FilterItem* msg,
|
|
PikaObj* self,
|
|
ShellConfig* shell);
|
|
|
|
struct FilterItem {
|
|
FilterMessageHandler* handler;
|
|
const uint8_t* message;
|
|
uint16_t size;
|
|
uint8_t is_visible : 1;
|
|
uint8_t is_case_insensitive : 1;
|
|
uint8_t : 6;
|
|
uint8_t ignore_mask;
|
|
uintptr_t target;
|
|
};
|
|
|
|
#endif
|
|
|
|
typedef struct {
|
|
int max_size;
|
|
int current;
|
|
int count;
|
|
int last_offset;
|
|
char** history;
|
|
int cached_current;
|
|
} ShellHistory;
|
|
|
|
struct ShellConfig {
|
|
#if PIKA_SHELL_FILTER_ENABLE
|
|
FilterFIFO filter_fifo;
|
|
FilterItem* messages;
|
|
uint16_t message_count;
|
|
uint16_t : 16; /* padding to suppress warning*/
|
|
#endif
|
|
char* prefix;
|
|
sh_handler handler;
|
|
void* context;
|
|
char lineBuff[PIKA_LINE_BUFF_SIZE];
|
|
size_t line_position;
|
|
size_t line_curpos;
|
|
char* blockBuffName;
|
|
pika_bool inBlock;
|
|
char lastChar;
|
|
sh_getchar fn_getchar;
|
|
uint8_t stat;
|
|
#if PIKA_SHELL_HISTORY_ENABLE
|
|
ShellHistory* history;
|
|
#endif
|
|
pika_bool no_echo;
|
|
PikaObj* locals;
|
|
PikaObj* globals;
|
|
};
|
|
|
|
#if PIKA_SHELL_HISTORY_ENABLE
|
|
ShellHistory* shHistory_create(int max_size);
|
|
void shHistory_destroy(ShellHistory* self);
|
|
void shHistory_add(ShellHistory* self, char* command);
|
|
void shHistory_setMaxSize(ShellHistory* self, int max_size);
|
|
char* shHistory_get(ShellHistory* self, int index);
|
|
char* shHistory_getPrev(ShellHistory* self);
|
|
char* shHistory_getNext(ShellHistory* self);
|
|
#endif
|
|
|
|
void _do_pikaScriptShell(PikaObj* self, ShellConfig* cfg);
|
|
|
|
void _temp__do_pikaScriptShell(PikaObj* self, ShellConfig* cfg);
|
|
|
|
/*
|
|
need implament :
|
|
pika_platform_fopen()
|
|
pika_platform_fwrite()
|
|
pika_platform_fclose()
|
|
*/
|
|
Method obj_getNativeMethod(PikaObj* self, char* method_name);
|
|
PIKA_RES obj_runNativeMethod(PikaObj* self, char* method_name, Args* args);
|
|
Arg* obj_newObjInPackage(NewFun newObjFun);
|
|
|
|
/* A helper function to create a new tuple PikaObj and append the given
|
|
* arguments (of type Arg*) to it. */
|
|
PikaObj* _pika_tuple_new(int num_args, ...);
|
|
|
|
/* A helper function to create a new list PikaObj and append the given
|
|
* arguments (of type Arg*) to it. */
|
|
PikaObj* _pika_list_new(int num_args, ...);
|
|
PikaObj* _pika_dict_new(int num_args, ...);
|
|
|
|
/* Macro to create a new tuple PikaObj with the given arguments (of type Arg*).
|
|
*/
|
|
#define New_PikaTupleFromVarArgs(...) \
|
|
_pika_tuple_new(sizeof((Arg*[]){__VA_ARGS__}) / sizeof(Arg*), __VA_ARGS__)
|
|
|
|
/* Macro to create a new list PikaObj with the given arguments (of type Arg*).
|
|
*/
|
|
#define New_PikaListFromVarArgs(...) \
|
|
_pika_list_new(sizeof((Arg*[]){__VA_ARGS__}) / sizeof(Arg*), __VA_ARGS__)
|
|
|
|
/* Macro to create a new dict PikaObj with the given arguments (of type
|
|
* Arg*).
|
|
*/
|
|
|
|
#define New_PikaDictFromVarArgs(...) \
|
|
_pika_dict_new(sizeof((Arg*[]){__VA_ARGS__, NULL}) / sizeof(Arg*) - 1, \
|
|
__VA_ARGS__)
|
|
|
|
PikaObj* newNormalObj(NewFun newObjFun);
|
|
Arg* arg_setRef(Arg* self, char* name, PikaObj* obj);
|
|
Arg* arg_setObj(Arg* self, char* name, PikaObj* obj);
|
|
Arg* arg_setWeakRef(Arg* self, char* name, PikaObj* obj);
|
|
|
|
PikaObj* arg_getObj(Arg* self);
|
|
pika_bool arg_isList(Arg* arg);
|
|
pika_bool arg_isDict(Arg* arg);
|
|
pika_bool arg_isTuple(Arg* arg);
|
|
|
|
static inline void arg_setObjFlag(Arg* self, uint8_t flag) {
|
|
if (!arg_isObject(self)) {
|
|
return;
|
|
}
|
|
obj_setFlag((PikaObj*)arg_getPtr(self), flag);
|
|
}
|
|
|
|
static inline void arg_clearObjFlag(Arg* self, uint8_t flag) {
|
|
if (!arg_isObject(self)) {
|
|
return;
|
|
}
|
|
obj_clearFlag((PikaObj*)arg_getPtr(self), flag);
|
|
}
|
|
|
|
static inline Arg* arg_newObj(PikaObj* obj) {
|
|
return arg_setObj(NULL, (char*)"", (obj));
|
|
}
|
|
|
|
static inline Arg* arg_newRef(PikaObj* obj) {
|
|
return arg_setRef(NULL, (char*)"", (obj));
|
|
}
|
|
|
|
uint8_t* pika_getByteCodeFromModule(char* module_name);
|
|
LibObj* pika_getLibObj(void);
|
|
|
|
PikaObj* obj_importModuleWithByteCodeFrame(PikaObj* self,
|
|
char* name,
|
|
ByteCodeFrame* bytecode_frame);
|
|
PikaObj* obj_importModuleWithByteCode(PikaObj* self,
|
|
char* name,
|
|
uint8_t* byteCode);
|
|
|
|
int32_t obj_newObj(PikaObj* self,
|
|
char* objName,
|
|
char* className,
|
|
NewFun newFunPtr);
|
|
|
|
Arg* arg_newMetaObj(NewFun objPtr);
|
|
PikaObj* obj_linkLibObj(PikaObj* self, LibObj* library);
|
|
PikaObj* obj_linkLibrary(PikaObj* self, uint8_t* library_bytes);
|
|
int obj_importModule(PikaObj* self, char* module_name);
|
|
int32_t obj_newMetaObj(PikaObj* self, char* objName, NewFun newFunPtr);
|
|
int32_t obj_newDirectObj(PikaObj* self, char* objName, NewFun newFunPtr);
|
|
int32_t obj_newHostObj(PikaObj* self, char* objName);
|
|
int obj_runModule(PikaObj* self, char* module_name);
|
|
PikaObj* obj_runFile(PikaObj* self, char* file_name);
|
|
PikaObj* obj_runSingleFile(PikaObj* self, char* file_name);
|
|
char* obj_toStr(PikaObj* self);
|
|
Arg* arg_newDirectObj(NewFun new_obj_fun);
|
|
enum shellCTRL obj_runChar(PikaObj* self, char inputChar);
|
|
|
|
#define PIKA_PYTHON_BEGIN
|
|
#define PIKA_PYTHON(x)
|
|
#define PIKA_PYTHON_END
|
|
|
|
typedef PikaObj PikaEventListener;
|
|
|
|
void pika_eventListener_registEventHandler(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
PikaObj* eventHandleObj);
|
|
|
|
void pika_eventListener_registEventCallback(PikaEventListener* listener_p,
|
|
uintptr_t eventId,
|
|
Arg* eventCallback);
|
|
|
|
void pika_eventListener_removeEvent(PikaEventListener* self, uintptr_t eventId);
|
|
|
|
PIKA_RES _do_pika_eventListener_send(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
Arg* eventData,
|
|
int eventSignal,
|
|
pika_bool pickupWhenNoVM);
|
|
|
|
PIKA_RES pika_eventListener_sendSignal(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
int eventSignal);
|
|
|
|
Arg* pika_eventListener_sendSignalAwaitResult(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
int eventSignal);
|
|
|
|
PIKA_RES pika_eventListener_send(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
Arg* eventData);
|
|
|
|
Arg* pika_eventListener_syncSendAwaitResult(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
Arg* eventData);
|
|
|
|
PIKA_RES pika_eventListener_syncSend(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
Arg* eventData);
|
|
|
|
PIKA_RES pika_eventListener_syncSendSignal(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
int eventSignal);
|
|
|
|
Arg* pika_eventListener_syncSendSignalAwaitResult(PikaEventListener* self,
|
|
uintptr_t eventId,
|
|
int eventSignal);
|
|
|
|
void pika_eventListener_init(PikaEventListener** p_self);
|
|
void pika_eventListener_deinit(PikaEventListener** p_self);
|
|
PikaObj* methodArg_getDefContext(Arg* method_arg);
|
|
int obj_linkLibraryFile(PikaObj* self, char* input_file_name);
|
|
NewFun obj_getClass(PikaObj* obj);
|
|
|
|
void pika_printVersion(void);
|
|
void pika_getVersion(char* buff);
|
|
void* obj_getStruct(PikaObj* self, char* name);
|
|
|
|
static inline void obj_refcntDec(PikaObj* self) {
|
|
self->refcnt--;
|
|
}
|
|
|
|
static inline void obj_refcntInc(PikaObj* self) {
|
|
self->refcnt++;
|
|
}
|
|
|
|
static inline uint8_t obj_refcntNow(PikaObj* self) {
|
|
return self->refcnt;
|
|
}
|
|
|
|
#define obj_setStruct(PikaObj_p_self, char_p_name, struct_) \
|
|
args_setStruct(((PikaObj_p_self)->list), char_p_name, struct_)
|
|
|
|
#define PIKA_ERR_STRING_SYNTAX_ERROR \
|
|
ANSI_COLOR_RED "SyntaxError: invalid syntax" ANSI_COLOR_RESET
|
|
|
|
#define ABSTRACT_METHOD_NEED_OVERRIDE_ERROR(_) \
|
|
obj_setErrorCode(self, 1); \
|
|
obj_setSysOut( \
|
|
self, \
|
|
ANSI_COLOR_RED \
|
|
"Error: abstract method `%s()` need override." ANSI_COLOR_RESET, \
|
|
__FUNCTION__)
|
|
|
|
char* obj_cacheStr(PikaObj* self, char* str);
|
|
PikaObj* _arg_to_obj(Arg* self, pika_bool* pIsTemp);
|
|
Arg* arg_toStrArg(Arg* arg);
|
|
|
|
#define PIKASCRIPT_VERSION_TO_NUM(majer, minor, micro) \
|
|
majer * 100 * 100 + minor * 100 + micro
|
|
|
|
#define PIKASCRIPT_VERSION_NUM \
|
|
PIKASCRIPT_VERSION_TO_NUM(PIKA_VERSION_MAJOR, PIKA_VERSION_MINOR, \
|
|
PIKA_VERSION_MICRO)
|
|
|
|
#define PIKASCRIPT_VERSION_REQUIRE_MINIMUN(majer, minor, micro) \
|
|
(PIKASCRIPT_VERSION_NUM >= PIKASCRIPT_VERSION_TO_NUM(majer, minor, micro))
|
|
|
|
/* [example]
|
|
const MethodProp floatMethod = {
|
|
.ptr = (void*)builtins_floatMethod,
|
|
.bytecode_frame = NULL,
|
|
.def_context = NULL,
|
|
.declareation = "float(arg)",
|
|
.type_list = "arg",
|
|
.name = "float",
|
|
};
|
|
*/
|
|
|
|
#if !PIKA_NANO_ENABLE
|
|
#define method_typedef(_method, _name, _typelist) \
|
|
const MethodPropNative _method##Prop = { \
|
|
.ptr = (void*)_method##Method, \
|
|
.type_list = _typelist, \
|
|
.name = _name, \
|
|
};
|
|
#else
|
|
#define method_typedef(_method, _name, _typelist) \
|
|
const MethodPropNative _method##Prop = { \
|
|
.ptr = (void*)_method##Method, \
|
|
.type_list = _typelist, \
|
|
};
|
|
#endif
|
|
|
|
#if PIKA_ARG_CACHE_ENABLE
|
|
#define _ARG_HEAP_SIZE_DEF() .heap_size = 0,
|
|
#else
|
|
#define _ARG_HEAP_SIZE_DEF()
|
|
#endif
|
|
|
|
#if PIKA_KERNAL_DEBUG_ENABLE
|
|
#define _ARG_VALUE_DEF(_method) \
|
|
.name = (char*)&_method##Prop, .value = (_arg_value*)&_method##Prop, \
|
|
.str = (char*)&_method##Prop, .bytes = (uint8_t*)&_method##Prop, \
|
|
._name_buff = ""
|
|
#else
|
|
#define _ARG_VALUE_DEF(_method)
|
|
#endif
|
|
|
|
/* clang-format off */
|
|
#define _method_def(_method, _hash, _type) \
|
|
{ \
|
|
._ = \
|
|
{ \
|
|
.buffer = (uint8_t*)&_method##Prop \
|
|
}, \
|
|
.size = sizeof(MethodPropNative), \
|
|
_ARG_HEAP_SIZE_DEF() \
|
|
.type = _type, \
|
|
.flag = 0, \
|
|
.name_hash = _hash, \
|
|
_ARG_VALUE_DEF(_method) \
|
|
}
|
|
|
|
|
|
#if defined(_WIN32) || \
|
|
(defined(__ARMCC_VERSION) && (__ARMCC_VERSION < 6000000))
|
|
#define __BEFORE_MOETHOD_DEF \
|
|
{ \
|
|
._ = \
|
|
{ \
|
|
.buffer = NULL \
|
|
}, \
|
|
.size = 0, \
|
|
.type = ARG_TYPE_NONE, \
|
|
.flag = 0, \
|
|
.name_hash = 0 \
|
|
},
|
|
#else
|
|
#define __BEFORE_MOETHOD_DEF
|
|
#endif
|
|
/* clang-format on */
|
|
|
|
#define method_def(_method, _hash) \
|
|
_method_def(_method, _hash, ARG_TYPE_METHOD_NATIVE)
|
|
#define constructor_def(_method, _hash) \
|
|
_method_def(_method, _hash, ARG_TYPE_METHOD_NATIVE_CONSTRUCTOR)
|
|
#define class_def(_class) const ConstArg _class##Collect[] =
|
|
|
|
#define class_inhert(_class, _super) \
|
|
extern const NativeProperty _super##NativeProp; \
|
|
const NativeProperty _class##NativeProp = { \
|
|
.super = &_super##NativeProp, \
|
|
.methodGroup = (Arg*)_class##Collect, \
|
|
.methodGroupCount = \
|
|
sizeof(_class##Collect) / sizeof(_class##Collect[0]), \
|
|
}
|
|
|
|
#define pika_class(_method) _method##NativeProp
|
|
|
|
void _obj_updateProxyFlag(PikaObj* self);
|
|
#define obj_setClass(_self, _method) \
|
|
obj_setPtr((_self), "@p", (void*)&pika_class(_method)); \
|
|
_obj_updateProxyFlag((_self))
|
|
|
|
Arg* _obj_getPropArg(PikaObj* obj, char* name);
|
|
|
|
Arg* __eventListener_runEvent(PikaEventListener* lisener,
|
|
uintptr_t eventId,
|
|
Arg* eventData);
|
|
|
|
void obj_printModules(PikaObj* self);
|
|
#if PIKA_DEBUG_ENABLE
|
|
#define pika_debug(fmt, ...) \
|
|
pika_platform_printf(ANSI_COLOR_GREEN "[PikaDBG] " fmt \
|
|
"\r\n" ANSI_COLOR_RESET, \
|
|
##__VA_ARGS__)
|
|
#else
|
|
#define pika_debug(...) \
|
|
do { \
|
|
} while (0)
|
|
#endif
|
|
|
|
#define pika_assert_arg_alive(__arg) \
|
|
do { \
|
|
if (NULL != (__arg)) { \
|
|
if (arg_isObject((__arg))) { \
|
|
pika_assert(obj_checkAlive(arg_getPtr((__arg)))); \
|
|
} \
|
|
} \
|
|
} while (0)
|
|
|
|
#define pika_assert_obj_alive(__obj) \
|
|
do { \
|
|
pika_assert(obj_checkAlive((__obj))); \
|
|
} while (0)
|
|
|
|
void obj_appendGcChain(PikaObj* self);
|
|
void obj_removeGcChain(PikaObj* self);
|
|
void obj_enableGC(PikaObj* self);
|
|
pika_bool obj_checkAlive(PikaObj* self);
|
|
void obj_setName(PikaObj* self, char* name);
|
|
|
|
void pikaGC_mark(void);
|
|
void pikaGC_markDump(void);
|
|
void pikaGC_lock(void);
|
|
void pikaGC_unlock(void);
|
|
pika_bool pikaGC_islock(void);
|
|
uint32_t pikaGC_count(void);
|
|
uint32_t pikaGC_countMarked(void);
|
|
uint32_t pikaGC_markSweep(void);
|
|
uint32_t pikaGC_printFreeList(void);
|
|
|
|
int pika_GIL_EXIT(void);
|
|
int pika_GIL_ENTER(void);
|
|
|
|
int32_t pika_debug_find_break_point_pc(char* pyFile, uint32_t pyLine);
|
|
|
|
typedef PikaObj PikaList;
|
|
typedef PikaObj PikaTuple;
|
|
typedef PikaObj PikaDict;
|
|
|
|
pika_bool pika_GIL_isInit(void);
|
|
int pika_GIL_deinit(void);
|
|
|
|
pika_bool _bytes_contains(Arg* self, Arg* others);
|
|
|
|
/* builtins */
|
|
PikaObj* New_builtins(Args* args);
|
|
|
|
void pika_sleep_ms(uint32_t ms);
|
|
PIKA_RES _transeBool(Arg* arg, pika_bool* res);
|
|
|
|
#define _OBJ2LIST(_obj) ((Args*)obj_getPtr((_obj), "list"))
|
|
#define _OBJ2DICT(_obj) ((Args*)obj_getPtr((_obj), "dict"))
|
|
#define _OBJ2KEYS(_obj) ((Args*)obj_getPtr((_obj), "_keys"))
|
|
|
|
/* list api */
|
|
PikaList* New_PikaList(void);
|
|
#define New_PikaListFrom New_PikaListFromVarArgs
|
|
PIKA_RES pikaList_append(PikaList* self, Arg* arg);
|
|
PIKA_RES pikaList_set(PikaList* self, int index, Arg* arg);
|
|
void pikaList_init(PikaObj* self);
|
|
int pikaList_getInt(PikaList* self, int index);
|
|
pika_bool pikaList_getBool(PikaList* self, int index);
|
|
pika_bool pikaTuple_getBool(PikaTuple* self, int index);
|
|
pika_float pikaList_getFloat(PikaList* self, int index);
|
|
char* pikaList_getStr(PikaList* self, int index);
|
|
void* pikaList_getPtr(PikaList* self, int index);
|
|
Arg* pikaList_get(PikaList* self, int index);
|
|
#define pikaList_getArg pikaList_get
|
|
size_t pikaList_getSize(PikaList* self);
|
|
void pikaList_reverse(PikaList* self);
|
|
PIKA_RES pikaList_insert(PikaList* self, int index, Arg* arg);
|
|
Arg* pikaList_pop(PikaList* list);
|
|
Arg* pikaList_pop_withIndex(PikaList* list, int index);
|
|
PIKA_RES pikaList_remove(PikaList* list, Arg* arg);
|
|
void pikaList_deinit(PikaList* self);
|
|
ArgType pikaList_getType(PikaList* self, int index);
|
|
int32_t pikaList_forEach(PikaObj* self,
|
|
int32_t (*eachHandle)(PikaObj* self,
|
|
int itemIndex,
|
|
Arg* itemEach,
|
|
void* context),
|
|
void* context);
|
|
|
|
/* tuple api */
|
|
PikaTuple* New_PikaTuple(void);
|
|
#define New_PikaTupleFrom New_PikaTupleFromVarArgs
|
|
#define pikaTuple_forEach pikaList_forEach
|
|
void pikaTuple_deinit(PikaTuple* self);
|
|
Arg* pikaTuple_getArg(PikaTuple* self, int index);
|
|
#define pikaTuple_get pikaTuple_getArg
|
|
size_t pikaTuple_getSize(PikaTuple* self);
|
|
int64_t pikaTuple_getInt(PikaTuple* self, int index);
|
|
pika_float pikaTuple_getFloat(PikaTuple* self, int index);
|
|
char* pikaTuple_getStr(PikaTuple* self, int index);
|
|
void* pikaTuple_getPtr(PikaTuple* self, int index);
|
|
ArgType pikaTuple_getType(PikaTuple* self, int index);
|
|
|
|
/* dict api */
|
|
PikaDict* New_PikaDict(void);
|
|
#define New_PikaDictFrom New_PikaDictFromVarArgs
|
|
PIKA_RES _pikaDict_setVal(PikaDict* self, Arg* val);
|
|
PIKA_RES pikaDict_setInt(PikaDict* self, char* name, int64_t val);
|
|
pika_bool pikaDict_setBool(PikaDict* self, char* name, pika_bool val);
|
|
PIKA_RES pikaDict_setFloat(PikaDict* self, char* name, pika_float val);
|
|
PIKA_RES pikaDict_setStr(PikaDict* self, char* name, char* val);
|
|
PIKA_RES pikaDict_setPtr(PikaDict* self, char* name, void* val);
|
|
PIKA_RES pikaDict_set(PikaDict* self, char* name, Arg* val);
|
|
#define pikaDict_setArg pikaDict_set
|
|
PIKA_RES pikaDict_removeArg(PikaDict* self, Arg* val);
|
|
PIKA_RES pikaDict_reverse(PikaDict* self);
|
|
PIKA_RES pikaDict_setBytes(PikaDict* self,
|
|
char* name,
|
|
uint8_t* val,
|
|
size_t size);
|
|
int64_t pikaDict_getInt(PikaDict* self, char* name);
|
|
pika_bool pikaDict_getBool(PikaDict* self, char* name);
|
|
pika_float pikaDict_getFloat(PikaDict* self, char* name);
|
|
char* pikaDict_getStr(PikaDict* self, char* name);
|
|
void* pikaDict_getPtr(PikaDict* self, char* name);
|
|
int pikaDict_getSize(PikaDict* self);
|
|
Arg* pikaDict_getArgByidex(PikaDict* self, int index);
|
|
Arg* pikaDict_get(PikaDict* self, char* name);
|
|
#define pikaDict_getArg pikaDict_get
|
|
int32_t pikaDict_isArgExist(PikaDict* self, char* name);
|
|
uint8_t* pikaDict_getBytes(PikaDict* self, char* name);
|
|
ArgType pikaDict_getType(PikaDict* self, char* name);
|
|
size_t pikaDict_getBytesSize(PikaDict* self, char* name);
|
|
int32_t pikaDict_forEach(PikaObj* self,
|
|
int32_t (*eachHandle)(PikaObj* self,
|
|
Arg* keyEach,
|
|
Arg* valEach,
|
|
void* context),
|
|
void* context);
|
|
void pikaDict_init(PikaObj* self);
|
|
void pikaDict_deinit(PikaDict* self);
|
|
|
|
PikaTuple* args_getTuple(Args* self, char* name);
|
|
PikaDict* args_getDict(Args* self, char* name);
|
|
char* strsFormatList(Args* out_buffs, char* fmt, PikaList* list);
|
|
PIKA_RES obj_setEventCallback(PikaObj* self,
|
|
uintptr_t eventId,
|
|
Arg* eventCallback,
|
|
PikaEventListener* eventListener);
|
|
|
|
#if 1
|
|
#define _RETURN_WHEN_NOT_ZERO(_stmt_, _ret_) \
|
|
do { \
|
|
if (0 != (_stmt_)) { \
|
|
return _ret_; \
|
|
} \
|
|
} while (0)
|
|
#else
|
|
#define _RETURN_WHEN_NOT_ZERO(_stmt_, _ret_) (_stmt_)
|
|
#endif
|
|
|
|
#endif
|
|
#ifdef __cplusplus
|
|
}
|
|
#endif
|