X-Git-Url: http://git.asbjorn.biz/?a=blobdiff_plain;f=lib%2Fq.c;h=3b9a62faddb43936fa9a813b3cae21f0665aec2f;hb=dc2f5b1a42742e40a1e5f9dfc6ecb63997e6cd09;hp=f7f79804bb7f530dfa994d18c15806650884dae9;hpb=b78c0fcd093d913860d445b1f8b28451711f7fa1;p=swftools.git diff --git a/lib/q.c b/lib/q.c index f7f7980..3b9a62f 100644 --- a/lib/q.c +++ b/lib/q.c @@ -318,10 +318,72 @@ string_t string_new2(const char*text) s.str = text; return s; } +string_t* string_new3(const char*text, int len) +{ + if(!text) { + string_t*s = malloc(sizeof(string_t)); + s->len = 0; + s->str = 0; + return s; + } else { + string_t*s = malloc(sizeof(string_t)+len+1); + s->len = len; + s->str = (const char*)(s+1); + memcpy((char*)s->str, text, len); + ((char*)s->str)[len]=0; + return s; + } +} +string_t* string_new4(const char*text) +{ + int l = strlen(text); + return string_new3(text, l); +} + +void string_free(string_t*s) +{ + if(!s) + return; + s->len = 0; + if((string_t*)(s->str) == s+1) { + s->str = 0; + rfx_free(s); + } else { + rfx_free((char*)(s->str)); + s->str = 0; + rfx_free(s); + } +} char* string_cstr(string_t*str) { return strdup_n(str->str, str->len); } +char* string_escape(string_t*str) +{ + int t; + int len = 0; + for(t=0;tlen;t++) { + if(str->str[t]<0x20) + len+=3; + else + len++; + } + char*s = malloc(len+1); + char*p=s; + for(t=0;tlen;t++) { + if(str->str[t]<0x20) { + *p++ ='\\'; + unsigned char c = str->str[t]; + *p++ = "0123456789abcdef"[c>>4]; + *p++ = "0123456789abcdef"[c&0x0f]; + } else { + *p++ = str->str[t]; + } + } + *p++ = 0; + assert(p == &s[len+1]); + return s; +} unsigned int crc32_add_byte(unsigned int checksum, unsigned char b) { @@ -567,6 +629,8 @@ void charptr_free(void*o) char stringstruct_equals(const void*o1, const void*o2) { + if(!o1 || !o2) + return o1==o2; string_t*s1 = (string_t*)o1; string_t*s2 = (string_t*)o2; int l = s1->lenlen?s1->len:s2->len; @@ -578,18 +642,29 @@ char stringstruct_equals(const void*o1, const void*o2) } unsigned int stringstruct_hash(const void*o) { + if(!o) return 0; return string_hash(o); } -void*stringstruct_dup(const void*o) +string_t*string_dup3(string_t*o) { - string_t*s = malloc(sizeof(string_t)); - string_set2(s, ((string_t*)o)->str, ((string_t*)o)->len); + if(!o) return 0; + if(!o->str) { + string_t*s = malloc(sizeof(string_t)); + s->str=0; + s->len=0; + return s; + } + string_t*s = rfx_alloc(sizeof(string_t)+o->len+1); + s->len = o->len; + s->str = (const char*)(s+1); + memcpy((char*)s->str, o->str, s->len); + ((char*)s->str)[s->len]=0; return s; } void stringstruct_free(void*o) { - rfx_free((void*)(((string_t*)o)->str)); - rfx_free((void*)o); + if(o) + string_free(o); } type_t ptr_type = { @@ -609,7 +684,7 @@ type_t charptr_type = { type_t stringstruct_type = { equals: stringstruct_equals, hash: stringstruct_hash, - dup: stringstruct_dup, + dup: (dup_func)string_dup3, free: stringstruct_free, }; @@ -725,10 +800,12 @@ int dict_count(dict_t*h) return h->num; } -void* dict_lookup(dict_t*h, const void*key) +void dict_do_lookup(dict_t*h, const void*key, void***match) { - if(!h->num) - return 0; + if(!h->num) { + *match = 0; + return; + } unsigned int ohash = h->key_type->hash(key); unsigned int hash = ohash % h->hashsize; @@ -736,7 +813,8 @@ void* dict_lookup(dict_t*h, const void*key) /* check first entry for match */ dictentry_t*e = h->slots[hash]; if(e && h->key_type->equals(e->key, key)) { - return e->data; + *match = &e->data; + return; } else if(e) { e = e->next; } @@ -757,12 +835,28 @@ void* dict_lookup(dict_t*h, const void*key) /* check subsequent entries for a match */ while(e) { if(h->key_type->equals(e->key, key)) { - return e->data; + *match = &e->data; + return; } e = e->next; } + *match = 0; +} +void* dict_lookup(dict_t*h, const void*key) +{ + void**data = 0; + dict_do_lookup(h, key, &data); + if(data) + return *data; return 0; } +char dict_contains(dict_t*h, const void*key) +{ + void**data = 0; + dict_do_lookup(h, key, &data); + return !!data; +} + char dict_del(dict_t*h, const void*key) { if(!h->num) @@ -1028,6 +1122,20 @@ int list_length_(void*_list) return 0; return l->info[0].size; } +void list_concat_(void*_l1, void*_l2) +{ + commonlist_t**l1 = (commonlist_t**)_l1; + commonlist_t**l2 = (commonlist_t**)_l2; + + if(!*l1) { + *l1 = *l2; + } else if(*l2) { + (*l1)->info[0].last->next = *l2; + (*l1)->info[0].last = (*l2)->info[0].last; + (*l1)->info[0].size += (*l2)->info[0].size; + } + *l2 = 0; +} void list_append_(void*_list, void*entry) { commonlist_t**list = (commonlist_t**)_list;