first and last commit
This commit is contained in:
commit
c9e78fd810
381 changed files with 37141 additions and 0 deletions
239
str.h
Normal file
239
str.h
Normal file
|
@ -0,0 +1,239 @@
|
|||
|
||||
int str_time(char *str, ulong time) {
|
||||
ulong secs = (time /= 1000000ULL) % 60ULL;
|
||||
ulong mins = (time /= 60ULL) % 60ULL;
|
||||
ulong hrs = (time /= 60ULL) % 24ULL;
|
||||
time /= 24ULL;
|
||||
return time ? sprintf(str, "%dD+%02d:%02d:%02d", time, hrs, mins, secs) : sprintf(str, "%02d:%02d:%02d", hrs, mins, secs);
|
||||
}
|
||||
|
||||
int str_mtime(char *str, ulong time) {
|
||||
int pos = str_time(str, time);
|
||||
return pos + sprintf(str+pos, ".%03d", (time / 1000ULL) % 1000ULL);
|
||||
}
|
||||
|
||||
int str_utime(char *str, ulong time) {
|
||||
int pos = str_time(str, time);
|
||||
return pos + sprintf(str+pos, ".%03d+%03d", (time / 1000ULL) % 1000ULL, time % 1000ULL);
|
||||
}
|
||||
|
||||
int str_strip(const char *str, char *buf, int size, int len, char newl, char tab, char unk) {
|
||||
int off = 0;
|
||||
int pos = 0;
|
||||
char c;
|
||||
while(((len < 0) || (off < len)) && (c = str[off++]) && (pos < size - 1)) {
|
||||
if(c == '\n') {
|
||||
buf[pos++] = newl;
|
||||
if(!newl) {
|
||||
return pos - 1;
|
||||
}
|
||||
}
|
||||
else if((c == '\t') && tab) {
|
||||
for(int z = 0; (z < 4) && (pos < size - 1); z++)
|
||||
buf[pos++] = tab;
|
||||
}
|
||||
else if(c == CHR_UNK) {
|
||||
if(unk)
|
||||
buf[pos++] = unk;
|
||||
}
|
||||
else if((c < 0) || (c >= CHR_SPC)) {
|
||||
buf[pos++] = c;
|
||||
}
|
||||
}
|
||||
buf[pos] = 0;
|
||||
return pos;
|
||||
}
|
||||
|
||||
// void str_stripq(char *str) {
|
||||
// char c;
|
||||
// int pos = 0;
|
||||
// while(c = str[pos]) {
|
||||
// if((c >= 0) && (c < CHR_SPC)) {
|
||||
// str[pos] = '\x1f';
|
||||
// }
|
||||
// pos++;
|
||||
// }
|
||||
// }
|
||||
|
||||
uint utf_read(const char **ptr) {
|
||||
uint ch;
|
||||
byte utf;
|
||||
char c = *((*ptr)++);
|
||||
for(utf = 0; (utf < 6) && (c & (0x80 >> utf)); utf++) {
|
||||
;
|
||||
}
|
||||
if(utf == 1)
|
||||
return CHR_UNK;
|
||||
for(ch = ((!utf) || ((((uint)c) << 6) | (((**ptr) & 0x3f) & ~(0xff >> utf)))) ? (c & (0x7f >> utf)) : 0; utf > 1; utf--) {
|
||||
if(((c = **ptr) & 0xc0) == 0x80) {
|
||||
// if(ch) {
|
||||
ch <<= 6;
|
||||
ch |= c & 0x3f;
|
||||
// }
|
||||
}
|
||||
else {
|
||||
return c ? CHR_UNK : 0;
|
||||
}
|
||||
(*ptr)++;
|
||||
}
|
||||
// fprintf(stderr, "%d / %c\n", ch, ch);
|
||||
return (utf && !ch) ? CHR_UNK : ch;
|
||||
}
|
||||
|
||||
uint utf_readn(const char *ptr, int *pos) {
|
||||
const char *str = &ptr[*pos];
|
||||
uint ch = utf_read(&str);
|
||||
*pos = (int)(str-ptr);
|
||||
return ch;
|
||||
}
|
||||
|
||||
byte utf_write(char **ptr, int *len, uint ch) {
|
||||
uint test;
|
||||
uint mask = 0xffffff80;
|
||||
char utf;
|
||||
char c;
|
||||
if(ch & 0x80000000) {
|
||||
return 1;
|
||||
}
|
||||
for(utf = 0; ch & mask & ~(test = (0xffffffff << ((utf + 1) * 6 + (5 - utf)))); utf++) {
|
||||
mask &= test;
|
||||
}
|
||||
// fprintf(stderr, "%d\n", utf);
|
||||
if(utf + 1 >= (*len)) {
|
||||
return 0;
|
||||
}
|
||||
(*len) -= utf + 1;
|
||||
*((*ptr)++) = utf ? (~(0x7f >> utf) | (((uint)(ch >> (utf * 6))) & (0x3f >> utf))) : ch;
|
||||
for(--utf; utf >= 0; utf--) {
|
||||
*((*ptr)++) = 0x80 | (((uint)(ch >> (utf * 6))) & 0x3f);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
byte utf_rwriten(char *ptr, int *pos, int len, uint ch) {
|
||||
char *str = &ptr[*pos];
|
||||
len -= (*pos);
|
||||
byte res = utf_write(&str, &len, ch);
|
||||
*pos = (int)(str-ptr);
|
||||
return res;
|
||||
}
|
||||
|
||||
uint utf_rread(const char **ptr, const char *start) {
|
||||
const char *tp = *ptr;
|
||||
uint ch;
|
||||
char c;
|
||||
do {
|
||||
if(tp == start)
|
||||
return 0;
|
||||
tp--;
|
||||
} while(((c = (*tp)) & 0xc0) == 0x80);
|
||||
*ptr = tp;
|
||||
return (ch = utf_read(&tp)) ? ch : CHR_UNK;
|
||||
}
|
||||
|
||||
uint utf_rreadn(const char *ptr, int *pos) {
|
||||
const char *str = &ptr[*pos];
|
||||
uint ch = utf_rread(&str, ptr);
|
||||
*pos = (int)(str-ptr);
|
||||
return ch;
|
||||
}
|
||||
|
||||
int utf_len(const char *str) {
|
||||
int len;
|
||||
for(len = 0; utf_read(&str); len++) {
|
||||
;
|
||||
}
|
||||
return len;
|
||||
}
|
||||
|
||||
char str_lower(char c) {
|
||||
return ((c >= 'A') && (c <= 'Z')) ? (c + 32) : c;
|
||||
}
|
||||
|
||||
char str_upper(char c) {
|
||||
return ((c >= 'a') && (c <= 'z')) ? (c - 32) : c;
|
||||
}
|
||||
|
||||
byte str_eq_lower(const char *str1, const char *str2) {
|
||||
int pos = 0;
|
||||
char c;
|
||||
while(c = str_lower(str1[pos])) {
|
||||
if(str_lower(str2[pos++]) != c)
|
||||
return 0;
|
||||
}
|
||||
return str2[pos] ? 0 : 1;
|
||||
}
|
||||
|
||||
int str_cmp_lower(const char *str1, const char *str2) {
|
||||
int pos = 0;
|
||||
char c;
|
||||
while(c = str_lower(str2[pos])) {
|
||||
if(str_lower(str1[pos++]) != c)
|
||||
return 0;
|
||||
}
|
||||
return str1[pos] ? pos : 0x7fffffff;
|
||||
}
|
||||
|
||||
byte str_parse_int(const char *str, int *value, int base) {
|
||||
char c;
|
||||
byte tbase = 0;
|
||||
int pos = 0;
|
||||
int digits = 0;
|
||||
long v = 0;
|
||||
long nbase = base ? (base < 0 ? -base : base) : 10;
|
||||
long nsign = 1;
|
||||
while(c = str_lower(str[pos++])) {
|
||||
if(pos == 1 && ((c == '+') || ((c == '-') && (base >= 0))))
|
||||
nsign = (c == '+') ? 1 : -1;
|
||||
else if(pos == 1 && c == '0') {
|
||||
tbase = 1;
|
||||
digits++;
|
||||
}
|
||||
else if(tbase && pos == 2 && c == 'x') {
|
||||
nbase = 16;
|
||||
digits--;
|
||||
}
|
||||
else if(((nbase == 16) && (c >= 'a' && c <= 'f')) || (c >= '0' && c <= '9')) {
|
||||
v *= nbase;
|
||||
v += ((long)((c >= '0' && c <= '9') ? (c - '0') : (10 + (c - 'a'))));
|
||||
digits++;
|
||||
}
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
if(!digits)
|
||||
return 0;
|
||||
v *= nsign;
|
||||
// errno = 0;
|
||||
// long v = strtol(str, NULL, (base < 0) ? -base : base);
|
||||
if((base < 0) ? (v < 0LL || v > 0xffffffffLL) : (v < -0x80000000LL || v > 0x7fffffffLL)) {
|
||||
return 0;
|
||||
}
|
||||
*value = (int)((base < 0) ? (v & 0xffffffff) : (((v >> 32) & 0x80000000) | (v & 0x7fffffff)));
|
||||
return 1;
|
||||
}
|
||||
|
||||
byte str_parse_enum(const char *str, const char **names, int states, int *value) {
|
||||
int comp;
|
||||
int max = 0;
|
||||
int best = 0;
|
||||
if(str_parse_int(str, &comp, 0) && (comp >= 0) && (comp < states)) {
|
||||
*value = comp;
|
||||
return 1;
|
||||
}
|
||||
for(int z = 0; z < states; z++) {
|
||||
if((comp = str_cmp_lower(names[z], str)) > best) {
|
||||
max = comp;
|
||||
best = z;
|
||||
}
|
||||
}
|
||||
if(max) {
|
||||
*value = best;
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
// char char_to_dc32(char c) {
|
||||
//
|
||||
// }
|
Reference in a new issue