blueloveTH 2024-02-01 11:57:18 +08:00
parent 5e55df9b97
commit 7a5ec84d14
6 changed files with 65 additions and 83 deletions

View File

@ -30,7 +30,7 @@ SRC=$(find src/ -name "*.cpp")
echo "> Compiling and linking source files... "
FLAGS="-std=c++17 -s -O1 -stdlib=libc++ -Wfatal-errors -Iinclude"
FLAGS="-std=c++17 -O1 -stdlib=libc++ -Wfatal-errors -Iinclude"
if [[ "$OSTYPE" == "darwin"* ]]; then
LIB_EXTENSION=".dylib"
@ -46,7 +46,7 @@ clang++ $FLAGS -o libpocketpy$LIB_EXTENSION $SRC -fPIC -shared
# compile main.cpp and link to libpocketpy.so
echo "> Compiling main.cpp and linking to libpocketpy$LIB_EXTENSION..."
clang++ $FLAGS -o main -s -O1 src2/main.cpp -L. -lpocketpy $LINK_FLAGS
clang++ $FLAGS -o main -O1 src2/main.cpp -L. -lpocketpy $LINK_FLAGS
if [ $? -eq 0 ]; then
echo "Build completed. Type \"./main\" to enter REPL."

View File

@ -16,11 +16,7 @@ typedef void (*pkpy_COutputHandler)(const char*, int);
typedef unsigned char* (*pkpy_CImportHandler)(const char*, int, int*);
typedef int pkpy_CName;
typedef int pkpy_CType;
typedef struct{
const char* data;
int size;
}pkpy_CString;
typedef const char* pkpy_CString;
/* Basic Functions */
PK_EXPORT pkpy_vm* pkpy_new_vm(bool enable_os);

View File

@ -13,25 +13,20 @@ struct Str{
int size;
bool is_ascii;
char* data;
char _inlined[16];
mutable const char* _cached_c_str = nullptr;
char _inlined[24];
bool is_inlined() const { return data == _inlined; }
Str(): size(0), is_ascii(true), data(_inlined) {}
Str();
Str(int size, bool is_ascii);
Str(const std::string& s);
Str(std::string_view s);
Str(std::nullptr_t) { PK_FATAL_ERROR(); }
Str(const char* s);
Str(const char* s, int len);
Str(std::pair<char *, int>);
Str(const Str& other);
Str(Str&& other);
void _alloc();
const char* begin() const { return data; }
const char* end() const { return data + size; }
char operator[](int idx) const { return data[idx]; }
@ -41,29 +36,30 @@ struct Str{
Str& operator=(const Str& other);
Str operator+(const Str& other) const;
friend Str operator+(const char* p, const Str& str);
Str operator+(const char* p) const;
bool operator==(const std::string_view other) const;
bool operator!=(const std::string_view other) const;
bool operator<(const std::string_view other) const;
friend bool operator<(const std::string_view other, const Str& str);
bool operator==(const char* p) const;
bool operator!=(const char* p) const;
bool operator==(const Str& other) const;
bool operator!=(const Str& other) const;
bool operator==(const std::string_view other) const;
bool operator!=(const std::string_view other) const;
bool operator==(const char* p) const;
bool operator!=(const char* p) const;
bool operator<(const Str& other) const;
bool operator>(const Str& other) const;
bool operator<=(const Str& other) const;
bool operator>=(const Str& other) const;
bool operator<(const std::string_view other) const;
~Str();
friend Str operator+(const char* p, const Str& str);
friend std::ostream& operator<<(std::ostream& os, const Str& str);
friend bool operator<(const std::string_view other, const Str& str);
Str substr(int start, int len) const;
Str substr(int start) const;
char* c_str_dup() const;
const char* c_str() const;
std::string_view sv() const;
std::string str() const;
@ -95,6 +91,7 @@ struct StrName {
StrName(const char* s);
StrName(const Str& s);
std::string_view sv() const;
const char* c_str() const;
bool empty() const { return index == 0; }
friend std::ostream& operator<<(std::ostream& os, const StrName& sn);

View File

@ -231,7 +231,7 @@ bool pkpy_to_bool(pkpy_vm* vm_handle, int i, bool* out){
bool pkpy_push_string(pkpy_vm* vm_handle, pkpy_CString value) {
VM* vm = (VM*) vm_handle;
PK_ASSERT_NO_ERROR()
PyObject* res = py_var(vm, std::string_view(value.data, value.size));
PyObject* res = py_var(vm, value);
vm->s_data.push(res);
return true;
}
@ -251,8 +251,7 @@ bool pkpy_to_string(pkpy_vm* vm_handle, int i, pkpy_CString* out){
PK_PROTECTED(
PyObject* item = stack_item(vm, i);
const Str& s = py_cast<Str&>(vm, item);
out->data = s.data;
out->size = s.size;
*out = s.c_str();
)
return true;
}
@ -503,7 +502,7 @@ bool pkpy_error(pkpy_vm* vm_handle, const char* name, pkpy_CString message) {
std::cerr << "[warning] pkpy_error(): " << Str(name).escape() << " not found, fallback to 'Exception'" << std::endl;
}
}
vm->_c.error = vm->call(e_t, VAR(std::string_view(message.data, message.size)));
vm->_c.error = vm->call(e_t, VAR(message));
return false;
}
@ -518,7 +517,7 @@ bool pkpy_clear_error(pkpy_vm* vm_handle, char** message) {
if (vm->_c.error == nullptr) return false;
Exception& e = PK_OBJ_GET(Exception, vm->_c.error);
if (message != nullptr)
*message = e.summary().c_str_dup();
*message = strdup(e.summary().c_str());
else
std::cout << e.summary() << std::endl;
vm->_c.error = nullptr;
@ -548,10 +547,7 @@ void pkpy_free(void* p){
}
pkpy_CString pkpy_string(const char* value){
pkpy_CString s;
s.data = value;
s.size = strlen(value);
return s;
return value;
}
pkpy_CName pkpy_name(const char* name){
@ -559,11 +555,7 @@ pkpy_CName pkpy_name(const char* name){
}
pkpy_CString pkpy_name_to_string(pkpy_CName name){
std::string_view sv = StrName(name).sv();
pkpy_CString s;
s.data = sv.data();
s.size = sv.size();
return s;
return StrName(name).c_str();
}
void pkpy_set_output_handler(pkpy_vm* vm_handle, pkpy_COutputHandler handler){

View File

@ -13,51 +13,58 @@ int utf8len(unsigned char c, bool suppress){
return 0;
}
Str::Str(int size, bool is_ascii): size(size), is_ascii(is_ascii) {
_alloc();
}
#define STR_INIT() \
_alloc(); \
for(int i=0; i<size; i++){ \
data[i] = s[i]; \
if(!isascii(s[i])) is_ascii = false; \
#define PK_STR_ALLOCATE() \
if(this->size < sizeof(this->_inlined)){ \
this->data = this->_inlined; \
}else{ \
this->data = (char*)pool64_alloc(this->size); \
}
#define PK_STR_COPY_INIT(__s) \
for(int i=0; i<this->size; i++){ \
this->data[i] = __s[i]; \
if(!isascii(__s[i])) is_ascii = false; \
}
Str::Str(): size(0), is_ascii(true), data(_inlined) {
_inlined[0] = '\0';
}
Str::Str(int size, bool is_ascii): size(size), is_ascii(is_ascii) {
PK_STR_ALLOCATE()
}
Str::Str(const std::string& s): size(s.size()), is_ascii(true) {
STR_INIT()
PK_STR_ALLOCATE()
PK_STR_COPY_INIT(s)
}
Str::Str(std::string_view s): size(s.size()), is_ascii(true) {
STR_INIT()
PK_STR_ALLOCATE()
PK_STR_COPY_INIT(s)
}
Str::Str(const char* s): size(strlen(s)), is_ascii(true) {
STR_INIT()
PK_STR_ALLOCATE()
PK_STR_COPY_INIT(s)
}
Str::Str(const char* s, int len): size(len), is_ascii(true) {
STR_INIT()
PK_STR_ALLOCATE()
PK_STR_COPY_INIT(s)
}
#undef STR_INIT
Str::Str(std::pair<char *, int> detached) {
this->size = detached.second;
Str::Str(std::pair<char *, int> detached): size(detached.second), is_ascii(true) {
this->data = detached.first;
this->is_ascii = true;
// check is_ascii
for(int i=0; i<size; i++){
if(!isascii(data[i])){
is_ascii = false;
break;
}
if(!isascii(data[i])){ is_ascii = false; break; }
}
}
Str::Str(const Str& other): size(other.size), is_ascii(other.is_ascii) {
_alloc();
PK_STR_ALLOCATE()
memcpy(data, other.data, size);
data[size] = '\0';
}
Str::Str(Str&& other): size(other.size), is_ascii(other.is_ascii) {
@ -66,7 +73,9 @@ int utf8len(unsigned char c, bool suppress){
for(int i=0; i<size; i++) _inlined[i] = other._inlined[i];
}else{
data = other.data;
// zero out `other`
other.data = other._inlined;
other.data[0] = '\0';
other.size = 0;
}
}
@ -84,20 +93,11 @@ int utf8len(unsigned char c, bool suppress){
return other < str.sv();
}
void Str::_alloc(){
if(size <= 16){
this->data = _inlined;
}else{
this->data = (char*)pool64_alloc(size);
}
}
Str& Str::operator=(const Str& other){
if(!is_inlined()) pool64_dealloc(data);
size = other.size;
is_ascii = other.is_ascii;
_cached_c_str = nullptr;
_alloc();
PK_STR_ALLOCATE()
memcpy(data, other.data, size);
return *this;
}
@ -164,7 +164,6 @@ int utf8len(unsigned char c, bool suppress){
Str::~Str(){
if(!is_inlined()) pool64_dealloc(data);
if(_cached_c_str != nullptr) free((void*)_cached_c_str);
}
Str Str::substr(int start, int len) const {
@ -177,18 +176,8 @@ int utf8len(unsigned char c, bool suppress){
return substr(start, size - start);
}
char* Str::c_str_dup() const {
char* p = (char*)malloc(size + 1);
memcpy(p, data, size);
p[size] = 0;
return p;
}
const char* Str::c_str() const{
if(_cached_c_str == nullptr){
_cached_c_str = c_str_dup();
}
return _cached_c_str;
return data;
}
std::string_view Str::sv() const {
@ -435,6 +424,11 @@ int utf8len(unsigned char c, bool suppress){
return std::string_view(str);
}
const char* StrName::c_str() const{
const std::string& str = _r_interned()[index];
return str.c_str();
}
Str SStream::str(){
// after this call, the buffer is no longer valid
return Str(buffer.detach());
@ -545,4 +539,7 @@ int utf8len(unsigned char c, bool suppress){
}
}
#undef PK_STR_ALLOCATE
#undef PK_STR_COPY_INIT
} // namespace pkpy

View File

@ -53,7 +53,7 @@ static int f_input(pkpy_vm* vm){
pkpy_CString prompt;
bool ok = pkpy_to_string(vm, -1, &prompt);
if(!ok) return 0;
std::cout << std::string_view(prompt.data, prompt.size) << std::flush;
std::cout << prompt << std::flush;
}
bool eof;
std::string output = pkpy_platform_getline(&eof);