optimize symbol->string
This commit is contained in:
parent
3e4abf8949
commit
fd248d31bd
|
@ -117,7 +117,7 @@ analyzer_scope_destroy(pic_state *pic, analyze_scope *scope)
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool
|
static bool
|
||||||
search_scope(analyze_scope *scope, pic_sym *sym)
|
search_scope(pic_state *pic, analyze_scope *scope, pic_sym *sym)
|
||||||
{
|
{
|
||||||
return kh_get(a, &scope->args, sym) != kh_end(&scope->args) || kh_get(a, &scope->locals, sym) != kh_end(&scope->locals) || scope->depth == 0;
|
return kh_get(a, &scope->args, sym) != kh_end(&scope->args) || kh_get(a, &scope->locals, sym) != kh_end(&scope->locals) || scope->depth == 0;
|
||||||
}
|
}
|
||||||
|
@ -128,7 +128,7 @@ find_var(pic_state *pic, analyze_scope *scope, pic_sym *sym)
|
||||||
int depth = 0, ret;
|
int depth = 0, ret;
|
||||||
|
|
||||||
while (scope) {
|
while (scope) {
|
||||||
if (search_scope(scope, sym)) {
|
if (search_scope(pic, scope, sym)) {
|
||||||
if (depth > 0) {
|
if (depth > 0) {
|
||||||
kh_put(a, &scope->captures, sym, &ret); /* capture! */
|
kh_put(a, &scope->captures, sym, &ret); /* capture! */
|
||||||
}
|
}
|
||||||
|
@ -145,7 +145,7 @@ define_var(pic_state *pic, analyze_scope *scope, pic_sym *sym)
|
||||||
{
|
{
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
if (search_scope(scope, sym)) {
|
if (search_scope(pic, scope, sym)) {
|
||||||
if (scope->depth > 0 || pic_reg_has(pic, pic->globals, sym)) {
|
if (scope->depth > 0 || pic_reg_has(pic, pic->globals, sym)) {
|
||||||
pic_warnf(pic, "redefining variable: ~s", pic_obj_value(sym));
|
pic_warnf(pic, "redefining variable: ~s", pic_obj_value(sym));
|
||||||
}
|
}
|
||||||
|
|
|
@ -384,6 +384,7 @@ gc_mark_object(pic_state *pic, struct pic_object *obj)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PIC_TT_SYMBOL: {
|
case PIC_TT_SYMBOL: {
|
||||||
|
LOOP(obj->u.sym.str);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PIC_TT_REG: {
|
case PIC_TT_REG: {
|
||||||
|
@ -559,7 +560,7 @@ gc_finalize_object(pic_state *pic, struct pic_object *obj)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PIC_TT_SYMBOL: {
|
case PIC_TT_SYMBOL: {
|
||||||
pic_free(pic, (void *)obj->u.sym.cstr);
|
/* TODO: remove this symbol's entry from pic->syms immediately */
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case PIC_TT_REG: {
|
case PIC_TT_REG: {
|
||||||
|
|
|
@ -45,7 +45,7 @@ typedef struct pic_state pic_state;
|
||||||
#include "picrin/read.h"
|
#include "picrin/read.h"
|
||||||
#include "picrin/gc.h"
|
#include "picrin/gc.h"
|
||||||
|
|
||||||
KHASH_DECLARE(s, const char *, pic_sym *)
|
KHASH_DECLARE(s, pic_str *, pic_sym *)
|
||||||
|
|
||||||
typedef struct pic_checkpoint {
|
typedef struct pic_checkpoint {
|
||||||
PIC_OBJECT_HEADER
|
PIC_OBJECT_HEADER
|
||||||
|
|
|
@ -27,6 +27,8 @@
|
||||||
#ifndef AC_KHASH_H
|
#ifndef AC_KHASH_H
|
||||||
#define AC_KHASH_H
|
#define AC_KHASH_H
|
||||||
|
|
||||||
|
#include <stddef.h>
|
||||||
|
|
||||||
typedef int khint_t;
|
typedef int khint_t;
|
||||||
typedef khint_t khiter_t;
|
typedef khint_t khiter_t;
|
||||||
|
|
||||||
|
@ -41,23 +43,6 @@ typedef khint_t khiter_t;
|
||||||
#define ac_roundup32(x) \
|
#define ac_roundup32(x) \
|
||||||
(--(x), (x)|=(x)>>1, (x)|=(x)>>2, (x)|=(x)>>4, (x)|=(x)>>8, (x)|=(x)>>16, ++(x))
|
(--(x), (x)|=(x)>>1, (x)|=(x)>>2, (x)|=(x)>>4, (x)|=(x)>>8, (x)|=(x)>>16, ++(x))
|
||||||
|
|
||||||
PIC_INLINE khint_t ac_X31_hash_string(const char *s)
|
|
||||||
{
|
|
||||||
khint_t h = (khint_t)*s;
|
|
||||||
if (h) for (++s ; *s; ++s) h = (h << 5) - h + (khint_t)*s;
|
|
||||||
return h;
|
|
||||||
}
|
|
||||||
PIC_INLINE khint_t ac_Wang_hash(khint_t key)
|
|
||||||
{
|
|
||||||
key += ~(key << 15);
|
|
||||||
key ^= (key >> 10);
|
|
||||||
key += (key << 3);
|
|
||||||
key ^= (key >> 6);
|
|
||||||
key += ~(key << 11);
|
|
||||||
key ^= (key >> 16);
|
|
||||||
return key;
|
|
||||||
}
|
|
||||||
|
|
||||||
#define ac_fsize(m) ((m) < 16? 1 : (m)>>4)
|
#define ac_fsize(m) ((m) < 16? 1 : (m)>>4)
|
||||||
#define ac_hash_upper(x) ((((x) * 2) * 77 / 100 + 1) / 2)
|
#define ac_hash_upper(x) ((((x) * 2) * 77 / 100 + 1) / 2)
|
||||||
|
|
||||||
|
@ -71,7 +56,7 @@ PIC_INLINE khint_t ac_Wang_hash(khint_t key)
|
||||||
void kh_init_##name(kh_##name##_t *h); \
|
void kh_init_##name(kh_##name##_t *h); \
|
||||||
void kh_destroy_##name(pic_state *, kh_##name##_t *h); \
|
void kh_destroy_##name(pic_state *, kh_##name##_t *h); \
|
||||||
void kh_clear_##name(kh_##name##_t *h); \
|
void kh_clear_##name(kh_##name##_t *h); \
|
||||||
khint_t kh_get_##name(const kh_##name##_t *h, khkey_t key); \
|
khint_t kh_get_##name(pic_state *, const kh_##name##_t *h, khkey_t key); \
|
||||||
void kh_resize_##name(pic_state *, kh_##name##_t *h, khint_t new_n_buckets); \
|
void kh_resize_##name(pic_state *, kh_##name##_t *h, khint_t new_n_buckets); \
|
||||||
khint_t kh_put_##name(pic_state *, kh_##name##_t *h, khkey_t key, int *ret); \
|
khint_t kh_put_##name(pic_state *, kh_##name##_t *h, khkey_t key, int *ret); \
|
||||||
void kh_del_##name(kh_##name##_t *h, khint_t x);
|
void kh_del_##name(kh_##name##_t *h, khint_t x);
|
||||||
|
@ -95,8 +80,9 @@ PIC_INLINE khint_t ac_Wang_hash(khint_t key)
|
||||||
h->size = h->n_occupied = 0; \
|
h->size = h->n_occupied = 0; \
|
||||||
} \
|
} \
|
||||||
} \
|
} \
|
||||||
khint_t kh_get_##name(const kh_##name##_t *h, khkey_t key) \
|
khint_t kh_get_##name(pic_state *pic, const kh_##name##_t *h, khkey_t key) \
|
||||||
{ \
|
{ \
|
||||||
|
(void)pic; \
|
||||||
if (h->n_buckets) { \
|
if (h->n_buckets) { \
|
||||||
khint_t k, i, last, mask, step = 0; \
|
khint_t k, i, last, mask, step = 0; \
|
||||||
mask = h->n_buckets - 1; \
|
mask = h->n_buckets - 1; \
|
||||||
|
@ -220,9 +206,6 @@ PIC_INLINE khint_t ac_Wang_hash(khint_t key)
|
||||||
#define kh_ptr_hash_equal(a, b) ((a) == (b))
|
#define kh_ptr_hash_equal(a, b) ((a) == (b))
|
||||||
#define kh_int_hash_func(key) (int)(key)
|
#define kh_int_hash_func(key) (int)(key)
|
||||||
#define kh_int_hash_equal(a, b) ((a) == (b))
|
#define kh_int_hash_equal(a, b) ((a) == (b))
|
||||||
#define kh_str_hash_func(key) ac_X31_hash_string(key)
|
|
||||||
#define kh_str_hash_equal(a, b) (strcmp(a, b) == 0)
|
|
||||||
#define kh_int_hash_func2(k) ac_Wang_hash((khint_t)key)
|
|
||||||
|
|
||||||
/* --- END OF HASH FUNCTIONS --- */
|
/* --- END OF HASH FUNCTIONS --- */
|
||||||
|
|
||||||
|
@ -232,7 +215,7 @@ PIC_INLINE khint_t ac_Wang_hash(khint_t key)
|
||||||
#define kh_clear(name, h) kh_clear_##name(h)
|
#define kh_clear(name, h) kh_clear_##name(h)
|
||||||
#define kh_resize(name, h, s) kh_resize_##name(pic, h, s)
|
#define kh_resize(name, h, s) kh_resize_##name(pic, h, s)
|
||||||
#define kh_put(name, h, k, r) kh_put_##name(pic, h, k, r)
|
#define kh_put(name, h, k, r) kh_put_##name(pic, h, k, r)
|
||||||
#define kh_get(name, h, k) kh_get_##name(h, k)
|
#define kh_get(name, h, k) kh_get_##name(pic, h, k)
|
||||||
#define kh_del(name, h, k) kh_del_##name(h, k)
|
#define kh_del(name, h, k) kh_del_##name(h, k)
|
||||||
|
|
||||||
#define kh_exist(h, x) (!ac_iseither((h)->flags, (x)))
|
#define kh_exist(h, x) (!ac_iseither((h)->flags, (x)))
|
||||||
|
|
|
@ -29,6 +29,7 @@ int pic_str_len(pic_str *);
|
||||||
pic_str *pic_str_cat(pic_state *, pic_str *, pic_str *);
|
pic_str *pic_str_cat(pic_state *, pic_str *, pic_str *);
|
||||||
pic_str *pic_str_sub(pic_state *, pic_str *, int, int);
|
pic_str *pic_str_sub(pic_state *, pic_str *, int, int);
|
||||||
int pic_str_cmp(pic_state *, pic_str *, pic_str *);
|
int pic_str_cmp(pic_state *, pic_str *, pic_str *);
|
||||||
|
int pic_str_hash(pic_state *, pic_str *);
|
||||||
const char *pic_str_cstr(pic_state *, pic_str *);
|
const char *pic_str_cstr(pic_state *, pic_str *);
|
||||||
|
|
||||||
pic_str *pic_format(pic_state *, const char *, ...);
|
pic_str *pic_format(pic_state *, const char *, ...);
|
||||||
|
|
|
@ -13,7 +13,7 @@ struct pic_id {
|
||||||
union {
|
union {
|
||||||
struct pic_symbol {
|
struct pic_symbol {
|
||||||
PIC_OBJECT_HEADER
|
PIC_OBJECT_HEADER
|
||||||
const char *cstr;
|
pic_str *str;
|
||||||
} sym;
|
} sym;
|
||||||
struct {
|
struct {
|
||||||
PIC_OBJECT_HEADER
|
PIC_OBJECT_HEADER
|
||||||
|
|
|
@ -288,6 +288,19 @@ pic_str_cmp(pic_state *pic, pic_str *str1, pic_str *str2)
|
||||||
return strcmp(pic_str_cstr(pic, str1), pic_str_cstr(pic, str2));
|
return strcmp(pic_str_cstr(pic, str1), pic_str_cstr(pic, str2));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
pic_str_hash(pic_state *pic, pic_str *str)
|
||||||
|
{
|
||||||
|
const char *s;
|
||||||
|
int h = 0;
|
||||||
|
|
||||||
|
s = pic_str_cstr(pic, str);
|
||||||
|
while (*s) {
|
||||||
|
h = (h << 5) - h + *s++;
|
||||||
|
}
|
||||||
|
return h;
|
||||||
|
}
|
||||||
|
|
||||||
const char *
|
const char *
|
||||||
pic_str_cstr(pic_state *pic, pic_str *str)
|
pic_str_cstr(pic_state *pic, pic_str *str)
|
||||||
{
|
{
|
||||||
|
|
|
@ -4,43 +4,39 @@
|
||||||
|
|
||||||
#include "picrin.h"
|
#include "picrin.h"
|
||||||
|
|
||||||
KHASH_DEFINE(s, const char *, pic_sym *, kh_str_hash_func, kh_str_hash_equal)
|
#define kh_pic_str_hash(a) (pic_str_hash(pic, (a)))
|
||||||
|
#define kh_pic_str_cmp(a, b) (pic_str_cmp(pic, (a), (b)) == 0)
|
||||||
|
|
||||||
|
KHASH_DEFINE(s, pic_str *, pic_sym *, kh_pic_str_hash, kh_pic_str_cmp)
|
||||||
|
|
||||||
pic_sym *
|
pic_sym *
|
||||||
pic_intern_str(pic_state *pic, pic_str *str)
|
pic_intern_str(pic_state *pic, pic_str *str)
|
||||||
{
|
|
||||||
return pic_intern(pic, pic_str_cstr(pic, str));
|
|
||||||
}
|
|
||||||
|
|
||||||
pic_sym *
|
|
||||||
pic_intern(pic_state *pic, const char *cstr)
|
|
||||||
{
|
{
|
||||||
khash_t(s) *h = &pic->syms;
|
khash_t(s) *h = &pic->syms;
|
||||||
pic_sym *sym;
|
pic_sym *sym;
|
||||||
khiter_t it;
|
khiter_t it;
|
||||||
int ret;
|
int ret;
|
||||||
char *copy;
|
|
||||||
|
|
||||||
it = kh_put(s, h, cstr, &ret);
|
it = kh_put(s, h, str, &ret);
|
||||||
if (ret == 0) { /* if exists */
|
if (ret == 0) { /* if exists */
|
||||||
sym = kh_val(h, it);
|
sym = kh_val(h, it);
|
||||||
pic_gc_protect(pic, pic_obj_value(sym));
|
pic_gc_protect(pic, pic_obj_value(sym));
|
||||||
return sym;
|
return sym;
|
||||||
}
|
}
|
||||||
|
|
||||||
copy = pic_malloc(pic, strlen(cstr) + 1);
|
|
||||||
strcpy(copy, cstr);
|
|
||||||
kh_key(h, it) = copy;
|
|
||||||
|
|
||||||
kh_val(h, it) = pic->sQUOTE; /* insert dummy */
|
|
||||||
|
|
||||||
sym = (pic_sym *)pic_obj_alloc(pic, sizeof(pic_sym), PIC_TT_SYMBOL);
|
sym = (pic_sym *)pic_obj_alloc(pic, sizeof(pic_sym), PIC_TT_SYMBOL);
|
||||||
sym->cstr = copy;
|
sym->str = str;
|
||||||
kh_val(h, it) = sym;
|
kh_val(h, it) = sym;
|
||||||
|
|
||||||
return sym;
|
return sym;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pic_sym *
|
||||||
|
pic_intern(pic_state *pic, const char *cstr)
|
||||||
|
{
|
||||||
|
return pic_intern_str(pic, pic_make_cstr(pic, cstr));
|
||||||
|
}
|
||||||
|
|
||||||
pic_id *
|
pic_id *
|
||||||
pic_make_identifier(pic_state *pic, pic_id *id, struct pic_env *env)
|
pic_make_identifier(pic_state *pic, pic_id *id, struct pic_env *env)
|
||||||
{
|
{
|
||||||
|
@ -53,9 +49,9 @@ pic_make_identifier(pic_state *pic, pic_id *id, struct pic_env *env)
|
||||||
}
|
}
|
||||||
|
|
||||||
const char *
|
const char *
|
||||||
pic_symbol_name(pic_state PIC_UNUSED(*pic), pic_sym *sym)
|
pic_symbol_name(pic_state *pic, pic_sym *sym)
|
||||||
{
|
{
|
||||||
return sym->cstr;
|
return pic_str_cstr(pic, sym->str);
|
||||||
}
|
}
|
||||||
|
|
||||||
const char *
|
const char *
|
||||||
|
@ -104,7 +100,7 @@ pic_symbol_symbol_to_string(pic_state *pic)
|
||||||
|
|
||||||
pic_get_args(pic, "m", &sym);
|
pic_get_args(pic, "m", &sym);
|
||||||
|
|
||||||
return pic_obj_value(pic_make_cstr(pic, sym->cstr));
|
return pic_obj_value(sym->str);
|
||||||
}
|
}
|
||||||
|
|
||||||
static pic_value
|
static pic_value
|
||||||
|
|
Loading…
Reference in New Issue