Advertisement
Guest User

Untitled

a guest
Jun 22nd, 2019
193
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 72.44 KB | None | 0 0
  1. // Generated by V
  2. #define linux (1)
  3. #include <pthread.h>
  4.  
  5. #include <stdio.h> // TODO remove all these includes, define all function signatures and types manually
  6. #include <stdlib.h>
  7. #include <signal.h>
  8. #include <stdarg.h> // for va_list
  9. #include <inttypes.h> // int64_t etc
  10.  
  11. //================================== TYPEDEFS ================================*/
  12.  
  13. typedef unsigned char byte;
  14. typedef unsigned int uint;
  15. typedef int64_t i64;
  16. typedef int32_t i32;
  17. typedef int16_t i16;
  18. typedef int8_t i8;
  19. typedef uint64_t u64;
  20. typedef uint32_t u32;
  21. typedef uint16_t u16;
  22. typedef uint8_t u8;
  23. typedef uint32_t rune;
  24. typedef float f32;
  25. typedef double f64;
  26. typedef unsigned char* byteptr;
  27. typedef int* intptr;
  28. typedef void* voidptr;
  29. typedef struct array array;
  30. typedef struct map map;
  31. typedef array array_string;
  32. typedef array array_int;
  33. typedef array array_byte;
  34. typedef array array_uint;
  35. typedef array array_float;
  36. typedef map map_int;
  37. typedef map map_string;
  38. #ifndef bool
  39. typedef int bool;
  40. #define true 1
  41. #define false 0
  42. #endif
  43.  
  44. //============================== HELPER C MACROS =============================*/
  45.  
  46. #define _PUSH(arr, val, tmp, tmp_typ) {tmp_typ tmp = (val); array__push(arr, &tmp);}
  47. #define _IN(typ, val, arr) array_##typ##_contains(arr, val)
  48. #define ALLOC_INIT(type, ...) (type *)memdup((type[]){ __VA_ARGS__ }, sizeof(type))
  49. #define UTF8_CHAR_LEN( byte ) (( 0xE5000000 >> (( byte >> 3 ) & 0x1e )) & 3 ) + 1
  50.  
  51. //================================== GLOBALS =================================*/
  52. //int V_ZERO = 0;
  53. byteptr g_str_buf;
  54. int load_so(byteptr);
  55. void reload_so();
  56. void init_consts();
  57. i64 total_m = 0; // For counting total RAM allocated
  58. int g_test_ok = 1;
  59. /*================================== FNS =================================*/
  60. #include <sys/stat.h>
  61. #include <execinfo.h>
  62. #include <signal.h>
  63. #include <unistd.h>
  64. #include <dirent.h>
  65. #include <errno.h>
  66. #define MAX 1000
  67. #define MAX 5000
  68. typedef struct array array;
  69. typedef array array_int;
  70. typedef array array_string;
  71. typedef struct string string;
  72. typedef struct ustring ustring;
  73. typedef array array_byte;
  74. typedef struct map map;
  75. typedef array array_Entry;
  76. typedef struct Entry Entry;
  77. typedef struct Entry2 Entry2;
  78. typedef struct smap smap;
  79. typedef array array_Entry2;
  80. typedef struct Option Option;
  81. typedef struct StringBuilder StringBuilder;
  82. typedef struct os__FILE os__FILE;
  83. typedef struct os__File os__File;
  84. typedef array array_ustring;
  85. typedef struct os__Reader os__Reader;
  86. typedef struct os__FileInfo os__FileInfo;
  87. struct array {
  88. void* data;
  89. int len;
  90. int cap;
  91. int element_size;
  92. };
  93. struct string {
  94. byte* str;
  95. int len;
  96. };
  97. struct ustring {
  98. string s;
  99. array_int runes;
  100. int len;
  101. };
  102. struct map {
  103. int element_size;
  104. array_Entry entries;
  105. bool is_sorted;
  106. };
  107. struct Entry {
  108. string key;
  109. void* val;
  110. };
  111. struct Entry2 {
  112. string key;
  113. string val;
  114. };
  115. struct smap {
  116. array_Entry2 entries;
  117. bool is_sorted;
  118. };
  119. struct Option {
  120. void* data;
  121. string error;
  122. bool ok;
  123. };
  124. struct StringBuilder {
  125. array_byte buf;
  126. int len;
  127. };
  128. struct os__FILE {
  129. };
  130. struct os__File {
  131. os__FILE* cfile;
  132. };
  133. struct os__Reader {
  134. os__FILE* fp;
  135. };
  136. struct os__FileInfo {
  137. string name;
  138. int size;
  139. };
  140.  
  141. string _STR(const char*, ...);
  142.  
  143.  
  144. string _STR_TMP(const char*, ...);
  145.  
  146. array new_array(int mylen, int cap, int elm_size);
  147. array new_array_from_c_array(int len, int cap, int elm_size, void* c_array);
  148. array new_array_from_c_array_no_alloc(int len, int cap, int elm_size, void* c_array);
  149. array array_repeat(void* val, int nr_repeats, int elm_size);
  150. void array_append_array(array* a, array b);
  151. void array_sort_with_compare(array* a, void* compare);
  152. void array_insert(array* a, int i, void* val);
  153. void array_prepend(array* a, void* val);
  154. void array_delete(array* a, int idx);
  155. void* array__get(array a, int i);
  156. void* array_first(array a);
  157. void* array_last(array a);
  158. array array_left(array s, int n);
  159. array array_right(array s, int n);
  160. array array_slice(array s, int start, int _end);
  161. void array_set(array* a, int idx, void* val);
  162. void array__push(array* arr, void* val);
  163. void array__push_many(array* arr, void* val, int size);
  164. string array_int_str(array_int a);
  165. void v_array_int_free(array_int a);
  166. string array_string_str(array_string a);
  167. void v_free(void* a);
  168. string tos_clone(byte* s);
  169. string tos2(byte* s);
  170. string tos_no_len(byte* s);
  171. string string_clone(string a);
  172. byte* string_cstr(string s);
  173. string string_replace(string s, string rep, string with);
  174. int string_to_i(string s);
  175. float string_to_float(string s);
  176. bool string_eq(string s, string a);
  177. bool string_ne(string s, string a);
  178. bool string_ge(string s, string a);
  179. bool string_le(string s, string a);
  180. bool string_lt(string s, string a);
  181. bool string_gt(string s, string a);
  182. string string_add(string s, string a);
  183. array_string string_split(string s, string delim);
  184. array_string string_split_single(string s, byte delim);
  185. array_string string_split_into_lines(string s);
  186. string string_left(string s, int n);
  187. string string_right(string s, int n);
  188. string string_substr(string s, int start, int end);
  189. int string_index(string s, string p);
  190. int string_last_index(string s, string p);
  191. int string_index_after(string s, string p, int start);
  192. bool string_contains(string s, string p);
  193. bool string_starts_with(string s, string p);
  194. bool string_ends_with(string s, string p);
  195. string string_to_lower(string s);
  196. string string_to_upper(string s);
  197. string string_find_between(string s, string start, string end);
  198. bool array_string_contains(array_string ar, string val);
  199. bool array_int_contains(array_int ar, int val);
  200. void* array_string_to_c(array_string a);
  201. bool is_space(byte c);
  202. bool byte_is_space(byte c);
  203. string string_trim_space(string s);
  204. string string_trim(string s, byte c);
  205. string string_trim_left(string s, string cutset);
  206. string string_trim_right(string s, string cutset);
  207. int compare_strings(string* a, string* b);
  208. int compare_strings_by_len(string* a, string* b);
  209. int compare_lower_strings(string* a, string* b);
  210. void array_string_sort(array_string* s);
  211. void array_string_sort_ignore_case(array_string* s);
  212. void array_string_sort_by_len(array_string* s);
  213. ustring string_ustring(string s);
  214. ustring string_ustring_tmp(string s);
  215. string ustring_substr(ustring u, int start, int end);
  216. string ustring_left(ustring u, int pos);
  217. string ustring_right(ustring u, int pos);
  218. byte string_at(string s, int idx);
  219. string ustring_at(ustring u, int idx);
  220. void v_ustring_free(ustring u);
  221. int abs(int a);
  222. bool byte_is_digit(byte c);
  223. bool byte_is_letter(byte c);
  224. void v_string_free(string s);
  225. void v_array_string_free(array_string arr);
  226. string string_all_before(string s, string dot);
  227. string string_all_before_last(string s, string dot);
  228. string string_all_after(string s, string dot);
  229. string array_string_join(array_string a, string del);
  230. string array_string_join_lines(array_string s);
  231. string string_limit(string s, int max);
  232. bool byte_is_white(byte c);
  233. string repeat_char(byte c, int n);
  234. int string_hash(string s);
  235. void v_exit(string reason);
  236. bool isnil(void* v);
  237. void on_panic(int (*f)( int /*FFF*/ ));
  238. void print_backtrace();
  239. void v_panic(string s);
  240. void println(string s);
  241. void eprintln(string s);
  242. void v_print(string s);
  243. void println2(string s);
  244. byte* v_malloc(int n);
  245. byte* v_calloc(int n);
  246. int _strlen(byte* s);
  247. Option opt_ok(void* data);
  248. void* memdup(void* src, int sz);
  249. Option v_error(string s);
  250. array_int range_int(int start, int end);
  251. string double_str(double d);
  252. string float_str(float d);
  253. string f64_str(f64 d);
  254. string f32_str(f32 d);
  255. string ptr_str(void* ptr);
  256. string int_str(int nn);
  257. string u8_str(u8 nn);
  258. string i64_str(i64 nn);
  259. string bool_str(bool b);
  260. string int_hex(int n);
  261. string i64_hex(i64 n);
  262. bool array_byte_contains(array_byte a, byte val);
  263. string byte_str(byte c);
  264. int string_is_utf8(string s);
  265. string utf32_to_str(u32 code);
  266. string utf32_to_str_no_malloc(u32 code, void* buf);
  267. int string_utf32_code(string _rune);
  268. map new_map(int cap, int elm_size);
  269. Entry map_new_entry(map* m, string key, void* val);
  270. void map__set(map* m, string key, void* val);
  271. int volt_abs(int n);
  272. void map_bs(map m, string query, int start, int end, void* out);
  273. int compare_map(Entry* a, Entry* b);
  274. void map_sort(map* m);
  275. bool map_get(map m, string key, void* out);
  276. void v_map_print(map m);
  277. void v_map_free(map m);
  278. string map_string_str(map_string m);
  279. smap new_smap();
  280. void smap_set(smap* m, string key, string val);
  281. string smap_get(smap m, string key);
  282. string smap_bs(smap m, string query, int start, int end);
  283. int compare_smap(Entry2* a, Entry2* b);
  284. void smap_sort(smap* m);
  285. void v_smap_free(smap m);
  286. string smap_str(smap m);
  287. StringBuilder new_string_builder(int initial_size);
  288. void StringBuilder_write(StringBuilder* b, string s);
  289. void StringBuilder_writeln(StringBuilder* b, string s);
  290. string StringBuilder_str(StringBuilder b);
  291. void StringBuilder_cut(StringBuilder b, int n);
  292. array_string os__init_os_args(int argc, void* c);
  293. void os__parse_windows_cmd_line(byte* cmd);
  294. string os__read_file(string path);
  295. string os__File_read_rune(os__File f);
  296. int os__file_size(string path);
  297. int os__file_last_mod_unix(string path);
  298. array_string os__read_lines(string path);
  299. array_string os__read_file_into_lines(string path);
  300. array_ustring os__read_file_into_ulines(string path);
  301. array_string os__read_file_lines(string path);
  302. void os__append_to_file(string file, string s);
  303. os__File os__open(string path);
  304. os__File os__open_file(string file);
  305. os__File os__create(string path);
  306. os__File os__open_append(string path);
  307. os__File os__create_file(string file);
  308. os__File os__create_file_a(string file);
  309. os__File os__open_file_a(string file);
  310. os__File os__create_file2(string file, string mode);
  311. void os__File_append(os__File f, string s);
  312. void os__File_write(os__File f, void* data, int size);
  313. void os__File_write_at(os__File f, void* data, int size, int pos);
  314. void os__File_appendln(os__File f, string s);
  315. void os__File_close(os__File f);
  316. void os__close_file(os__FILE* fp);
  317. int os__system2(string cmd);
  318. os__FILE* os__popen(string path);
  319. string os__system(string cmd);
  320. array_string os__system_into_lines(string s);
  321. string os__getenv(string key);
  322. void os__exit(string reason);
  323. void os__exit1(string reason);
  324. bool os__file_exists(string path);
  325. void os__mkdir(string path);
  326. void os__rm(string path);
  327. void os__rmdir(string path, string guard);
  328. void os__unzip(string path, string out);
  329. void os__print_c_errno();
  330. string os__basedir(string path);
  331. string os__filename(string path);
  332. string os__get_line();
  333. string os__user_os();
  334. string os__home_dir();
  335. void os__write_file(string path, string text);
  336. void os__on_segfault(void* f);
  337. void os__log(string s);
  338. bool os__is_dir(string path);
  339. void os__chdir(string path);
  340. string os__getwd();
  341. array_string os__ls(string path);
  342. void os__print_backtrace();
  343. string filter_word(string word);
  344. bool is_letter(byte c);
  345. array_string os__args;
  346. #define os__BUF_SIZE 5000
  347.  
  348.  
  349. array new_array(int mylen, int cap, int elm_size) {
  350.  
  351. array arr= /* S INIT */ (array){ .len = mylen , .cap = cap , .element_size = elm_size , .data = v_malloc ( cap * elm_size ) } ;
  352.  
  353.  
  354. return arr ;
  355.  
  356.  
  357. }
  358. array new_array_from_c_array(int len, int cap, int elm_size, void* c_array) {
  359.  
  360. array arr= /* S INIT */ (array){ .len = len , .cap = cap , .element_size = elm_size , .data = v_malloc ( cap * elm_size ) } ;
  361.  
  362. memcpy ( arr .data , c_array , len * elm_size ) ;
  363.  
  364.  
  365. return arr ;
  366.  
  367.  
  368. }
  369. array new_array_from_c_array_no_alloc(int len, int cap, int elm_size, void* c_array) {
  370.  
  371. array arr= /* S INIT */ (array){ .len = len , .cap = cap , .element_size = elm_size , .data = c_array } ;
  372.  
  373.  
  374. return arr ;
  375.  
  376.  
  377. }
  378. array array_repeat(void* val, int nr_repeats, int elm_size) {
  379.  
  380. array arr= /* S INIT */ (array){ .len = nr_repeats , .cap = nr_repeats , .element_size = elm_size , .data = v_malloc ( nr_repeats * elm_size ) } ;
  381.  
  382. for (
  383. int i= 0 ; i < nr_repeats ; i ++ ) {
  384.  
  385. memcpy ( arr .data + i * elm_size , val , elm_size ) ;
  386.  
  387. }
  388. ;
  389.  
  390.  
  391. return arr ;
  392.  
  393.  
  394. }
  395. void array_append_array(array* a, array b) {
  396.  
  397. for (
  398. int i= 0 ; i < b .len ; i ++ ) {
  399.  
  400. void* val= ( *(void**) array__get( b , i) ) ;
  401.  
  402. array__push( a , val ) ;
  403.  
  404. }
  405. ;
  406.  
  407.  
  408. }
  409. void array_sort_with_compare(array* a, void* compare) {
  410.  
  411. qsort ( a ->data , a ->len , a ->element_size , compare ) ;
  412.  
  413.  
  414. }
  415. void array_insert(array* a, int i, void* val) {
  416.  
  417. if ( i >= a ->len ) {
  418. /*if*/
  419.  
  420. v_panic ( tos2("array.insert: index larger than length") ) ;
  421.  
  422.  
  423. return ;
  424.  
  425. }
  426. ;
  427.  
  428. array__push( a , val ) ;
  429.  
  430. int size= a ->element_size ;
  431.  
  432. memmove ( a ->data + (/*lpar*/ i + 1 ) * size , a ->data + i * size , (/*lpar*/ a ->len - i ) * size ) ;
  433.  
  434. array_set( a , i , val ) ;
  435.  
  436.  
  437. }
  438. void array_prepend(array* a, void* val) {
  439.  
  440. array_insert( a , 0 , val ) ;
  441.  
  442.  
  443. }
  444. void array_delete(array* a, int idx) {
  445.  
  446. int size= a ->element_size ;
  447.  
  448. memmove ( a ->data + idx * size , a ->data + (/*lpar*/ idx + 1 ) * size , (/*lpar*/ a ->len - idx ) * size ) ;
  449.  
  450. a ->len -- ;
  451.  
  452. a ->cap -- ;
  453.  
  454.  
  455. }
  456. void* array__get(array a, int i) {
  457.  
  458. if ( i < 0 || i >= a .len ) {
  459. /*if*/
  460.  
  461. v_panic ( _STR("array index out of range: %d/%d", i, a .len) ) ;
  462.  
  463. }
  464. ;
  465.  
  466.  
  467. return a .data + i * a .element_size ;
  468.  
  469.  
  470. }
  471. void* array_first(array a) {
  472.  
  473. if ( a .len == 0 ) {
  474. /*if*/
  475.  
  476. v_panic ( tos2("array.first: empty array") ) ;
  477.  
  478. }
  479. ;
  480.  
  481.  
  482. return a .data + 0 ;
  483.  
  484.  
  485. }
  486. void* array_last(array a) {
  487.  
  488. if ( a .len == 0 ) {
  489. /*if*/
  490.  
  491. v_panic ( tos2("array.last: empty array") ) ;
  492.  
  493. }
  494. ;
  495.  
  496.  
  497. return a .data + (/*lpar*/ a .len - 1 ) * a .element_size ;
  498.  
  499.  
  500. }
  501. array array_left(array s, int n) {
  502.  
  503. if ( n >= s .len ) {
  504. /*if*/
  505.  
  506.  
  507. return s ;
  508.  
  509. }
  510. ;
  511.  
  512.  
  513. return array_slice( s , 0 , n ) ;
  514.  
  515.  
  516. }
  517. array array_right(array s, int n) {
  518.  
  519. if ( n >= s .len ) {
  520. /*if*/
  521.  
  522.  
  523. return s ;
  524.  
  525. }
  526. ;
  527.  
  528.  
  529. return array_slice( s , n , s .len ) ;
  530.  
  531.  
  532. }
  533. array array_slice(array s, int start, int _end) {
  534.  
  535. int end= _end ;
  536.  
  537. if ( start > end ) {
  538. /*if*/
  539.  
  540. v_panic ( _STR("invalid slice index: %d > %d", start, end) ) ;
  541.  
  542. }
  543. ;
  544.  
  545. if ( end >= s .len ) {
  546. /*if*/
  547.  
  548. end = s .len ;
  549.  
  550. }
  551. ;
  552.  
  553. int l= end - start ;
  554.  
  555. array res= /* S INIT */ (array){ .element_size = s .element_size , .data = s .data + start * s .element_size , .len = l , .cap = l } ;
  556.  
  557.  
  558. return res ;
  559.  
  560.  
  561. }
  562. void array_set(array* a, int idx, void* val) {
  563.  
  564. if ( idx < 0 || idx >= a ->len ) {
  565. /*if*/
  566.  
  567. v_panic ( _STR("array index out of range: %d / %d", idx, a ->len) ) ;
  568.  
  569. }
  570. ;
  571.  
  572. memcpy ( a ->data + a ->element_size * idx , val , a ->element_size ) ;
  573.  
  574.  
  575. }
  576. void array__push(array* arr, void* val) {
  577.  
  578. if ( arr ->len >= arr ->cap - 1 ) {
  579. /*if*/
  580.  
  581. int cap= (/*lpar*/ arr ->len + 1 ) * 2 ;
  582.  
  583. if ( arr ->cap == 0 ) {
  584. /*if*/
  585.  
  586. arr ->data = v_malloc ( cap * arr ->element_size ) ;
  587.  
  588. }
  589. else {
  590. /*else if*/
  591.  
  592. arr ->data = realloc ( arr ->data , cap * arr ->element_size ) ;
  593.  
  594. }
  595. ;
  596.  
  597. arr ->cap = cap ;
  598.  
  599. }
  600. ;
  601.  
  602. memcpy ( arr ->data + arr ->element_size * arr ->len , val , arr ->element_size ) ;
  603.  
  604. arr ->len ++ ;
  605.  
  606.  
  607. }
  608. void array__push_many(array* arr, void* val, int size) {
  609.  
  610. if ( arr ->len >= arr ->cap - size ) {
  611. /*if*/
  612.  
  613. int cap= (/*lpar*/ arr ->len + size ) * 2 ;
  614.  
  615. if ( arr ->cap == 0 ) {
  616. /*if*/
  617.  
  618. arr ->data = v_malloc ( cap * arr ->element_size ) ;
  619.  
  620. }
  621. else {
  622. /*else if*/
  623.  
  624. arr ->data = realloc ( arr ->data , cap * arr ->element_size ) ;
  625.  
  626. }
  627. ;
  628.  
  629. arr ->cap = cap ;
  630.  
  631. }
  632. ;
  633.  
  634. memcpy ( arr ->data + arr ->element_size * arr ->len , val , arr ->element_size * size ) ;
  635.  
  636. arr ->len += size ;
  637.  
  638.  
  639. }
  640. string array_int_str(array_int a) {
  641.  
  642. string res= tos2("[") ;
  643.  
  644. for (
  645. int i= 0 ; i < a .len ; i ++ ) {
  646.  
  647. int val= ( *(int*) array__get( a , i) ) ;
  648.  
  649. res = string_add(res, _STR("%d", val) ) ;
  650.  
  651. if ( i < a .len - 1 ) {
  652. /*if*/
  653.  
  654. res = string_add(res, tos2(", ") ) ;
  655.  
  656. }
  657. ;
  658.  
  659. }
  660. ;
  661.  
  662. res = string_add(res, tos2("]") ) ;
  663.  
  664.  
  665. return res ;
  666.  
  667.  
  668. }
  669. void v_array_int_free(array_int a) {
  670.  
  671. free ( a .data ) ;
  672.  
  673.  
  674. }
  675. string array_string_str(array_string a) {
  676.  
  677. string res= tos2("[") ;
  678.  
  679. for (
  680. int i= 0 ; i < a .len ; i ++ ) {
  681.  
  682. string val= ( *(string*) array__get( a , i) ) ;
  683.  
  684. res = string_add(res, _STR("\"%.*s\"", val.len, val.str) ) ;
  685.  
  686. if ( i < a .len - 1 ) {
  687. /*if*/
  688.  
  689. res = string_add(res, tos2(", ") ) ;
  690.  
  691. }
  692. ;
  693.  
  694. }
  695. ;
  696.  
  697. res = string_add(res, tos2("]") ) ;
  698.  
  699.  
  700. return res ;
  701.  
  702.  
  703. }
  704. void v_free(void* a) {
  705.  
  706. free ( a ) ;
  707.  
  708.  
  709. }
  710. string tos(byte* s, int len) {
  711.  
  712. if ( isnil ( s ) ) {
  713. /*if*/
  714.  
  715. v_panic ( tos2("tos(): nil string") ) ;
  716.  
  717. }
  718. ;
  719.  
  720.  
  721. return /* S INIT */ (string){ .str = s , .len = len } ;
  722.  
  723.  
  724. }
  725. string tos_clone(byte* s) {
  726.  
  727. if ( isnil ( s ) ) {
  728. /*if*/
  729.  
  730. v_panic ( tos2("tos: nil string") ) ;
  731.  
  732.  
  733. return /* S INIT */ (string){ .str = 0 , .len = 0 } ;
  734.  
  735. }
  736. ;
  737.  
  738. int len= strlen ( s ) ;
  739.  
  740. string res= tos ( s , len ) ;
  741.  
  742.  
  743. return string_clone( res ) ;
  744.  
  745.  
  746. }
  747. string tos2(byte* s) {
  748.  
  749. if ( isnil ( s ) ) {
  750. /*if*/
  751.  
  752. v_panic ( tos2("tos2: nil string") ) ;
  753.  
  754.  
  755. return /* S INIT */ (string){ .str = 0 , .len = 0 } ;
  756.  
  757. }
  758. ;
  759.  
  760. int len= strlen ( s ) ;
  761.  
  762. string res= tos ( s , len ) ;
  763.  
  764.  
  765. return res ;
  766.  
  767.  
  768. }
  769. string tos_no_len(byte* s) {
  770.  
  771.  
  772. return tos2 ( s ) ;
  773.  
  774.  
  775. }
  776. string string_clone(string a) {
  777.  
  778. string b= /* S INIT */ (string){ .len = a .len , .str = v_malloc ( a .len + 1 ) } ;
  779.  
  780. for (
  781. int i= 0 ; i < a .len ; i ++ ) {
  782.  
  783. b .str[ i ]/*rbyte 1*/ = a .str[ i ]/*rbyte 0*/ ;
  784.  
  785. }
  786. ;
  787.  
  788. b .str[ a .len ]/*rbyte 1*/ = '\0' ;
  789.  
  790.  
  791. return b ;
  792.  
  793.  
  794. }
  795. byte* string_cstr(string s) {
  796.  
  797. string clone= string_clone( s ) ;
  798.  
  799.  
  800. return clone .str ;
  801.  
  802.  
  803. }
  804. string string_replace(string s, string rep, string with) {
  805.  
  806. if ( s .len == 0 || rep .len == 0 ) {
  807. /*if*/
  808.  
  809.  
  810. return tos2("") ;
  811.  
  812. }
  813. ;
  814.  
  815. if ( ! string_contains( s , rep ) ) {
  816. /*if*/
  817.  
  818.  
  819. return s ;
  820.  
  821. }
  822. ;
  823.  
  824. array_int idxs=/*0*/ new_array_from_c_array(0, 0, sizeof(int), (int[]) { }) ;
  825.  
  826. {
  827.  
  828. }
  829.  
  830. for (
  831. int i= 0 ; i < s .len ; i ++ ) {
  832.  
  833. int rep_i= 0 ;
  834.  
  835. int j= i ;
  836.  
  837. while ( rep_i < rep .len && j < s .len && s .str[ j ]/*rbyte 0*/ == rep .str[ rep_i ]/*rbyte 0*/ ) {
  838.  
  839. rep_i ++ ;
  840.  
  841. j ++ ;
  842.  
  843. }
  844. ;
  845.  
  846. if ( rep_i == rep .len ) {
  847. /*if*/
  848.  
  849. _PUSH(& idxs , ( i ), tmp12, int) ;
  850.  
  851. }
  852. ;
  853.  
  854. }
  855. ;
  856.  
  857. if ( idxs .len == 0 ) {
  858. /*if*/
  859.  
  860.  
  861. return s ;
  862.  
  863. }
  864. ;
  865.  
  866. int new_len= s .len + idxs .len * (/*lpar*/ with .len - rep .len ) ;
  867.  
  868. byte* b= v_malloc ( new_len + 1 ) ;
  869.  
  870. int idx_pos= 0 ;
  871.  
  872. int cur_idx= ( *(int*) array__get( idxs , idx_pos) ) ;
  873.  
  874. int b_i= 0 ;
  875.  
  876. for (
  877. int i= 0 ; i < s .len ; i ++ ) {
  878.  
  879. if ( i == cur_idx ) {
  880. /*if*/
  881.  
  882. for (
  883. int j= 0 ; j < with .len ; j ++ ) {
  884.  
  885. b [/*ptr*/ b_i ]/*rbyte 1*/ = with .str[ j ]/*rbyte 0*/ ;
  886.  
  887. b_i ++ ;
  888.  
  889. }
  890. ;
  891.  
  892. i += rep .len - 1 ;
  893.  
  894. idx_pos ++ ;
  895.  
  896. if ( idx_pos < idxs .len ) {
  897. /*if*/
  898.  
  899. cur_idx = ( *(int*) array__get( idxs , idx_pos) ) ;
  900.  
  901. }
  902. ;
  903.  
  904. }
  905. else {
  906. /*else if*/
  907.  
  908. b [/*ptr*/ b_i ]/*rbyte 1*/ = s .str[ i ]/*rbyte 0*/ ;
  909.  
  910. b_i ++ ;
  911.  
  912. }
  913. ;
  914.  
  915. }
  916. ;
  917.  
  918. b [/*ptr*/ new_len ]/*rbyte 1*/ = '\0' ;
  919.  
  920.  
  921. return tos ( b , new_len ) ;
  922.  
  923.  
  924. }
  925. int string_to_i(string s) {
  926.  
  927.  
  928. return atoi ( s .str ) ;
  929.  
  930.  
  931. }
  932. float string_to_float(string s) {
  933.  
  934.  
  935. return atof ( s .str ) ;
  936.  
  937.  
  938. }
  939. bool string_eq(string s, string a) {
  940.  
  941. if ( isnil ( s .str ) ) {
  942. /*if*/
  943.  
  944. v_panic ( tos2("string.eq(): nil string") ) ;
  945.  
  946. }
  947. ;
  948.  
  949. if ( s .len != a .len ) {
  950. /*if*/
  951.  
  952.  
  953. return 0 ;
  954.  
  955. }
  956. ;
  957.  
  958. for (
  959. int i= 0 ; i < s .len ; i ++ ) {
  960.  
  961. if ( s .str[ i ]/*rbyte 0*/ != a .str[ i ]/*rbyte 0*/ ) {
  962. /*if*/
  963.  
  964.  
  965. return 0 ;
  966.  
  967. }
  968. ;
  969.  
  970. }
  971. ;
  972.  
  973.  
  974. return 1 ;
  975.  
  976.  
  977. }
  978. bool string_ne(string s, string a) {
  979.  
  980.  
  981. return ! string_eq( s , a ) ;
  982.  
  983.  
  984. }
  985. bool string_ge(string s, string a) {
  986.  
  987. int j= 0 ;
  988.  
  989. for (
  990. int i= 0 ; i < s .len ; i ++ ) {
  991.  
  992. if ( i >= a .len ) {
  993. /*if*/
  994.  
  995.  
  996. return 1 ;
  997.  
  998. }
  999. ;
  1000.  
  1001. if ( (/*casttt*/ (int)( /*77*/ s .str[ i ]/*rbyte 0*/ ) ) < (/*casttt*/ (int)( /*77*/ a .str[ j ]/*rbyte 0*/ ) ) ) {
  1002. /*if*/
  1003.  
  1004.  
  1005. return 0 ;
  1006.  
  1007. }
  1008. else if ( (/*casttt*/ (int)( /*77*/ s .str[ i ]/*rbyte 0*/ ) ) > (/*casttt*/ (int)( /*77*/ a .str[ j ]/*rbyte 0*/ ) ) ) {
  1009. /*if*/
  1010.  
  1011.  
  1012. return 1 ;
  1013.  
  1014. }
  1015. ;
  1016.  
  1017. j ++ ;
  1018.  
  1019. }
  1020. ;
  1021.  
  1022.  
  1023. return 1 ;
  1024.  
  1025.  
  1026. }
  1027. bool string_le(string s, string a) {
  1028.  
  1029.  
  1030. return ! string_ge( s , a ) || string_eq( s , a )/*8*/ ;
  1031.  
  1032.  
  1033. }
  1034. bool string_lt(string s, string a) {
  1035.  
  1036.  
  1037. return string_le( s , a ) && string_ne( s , a )/*8*/ ;
  1038.  
  1039.  
  1040. }
  1041. bool string_gt(string s, string a) {
  1042.  
  1043.  
  1044. return string_ge( s , a ) && string_ne( s , a )/*8*/ ;
  1045.  
  1046.  
  1047. }
  1048. string string_add(string s, string a) {
  1049.  
  1050. int new_len= a .len + s .len ;
  1051.  
  1052. string res= /* S INIT */ (string){ .len = new_len , .str = v_malloc ( new_len + 1 ) } ;
  1053.  
  1054. for (
  1055. int j= 0 ; j < s .len ; j ++ ) {
  1056.  
  1057. res .str[ j ]/*rbyte 1*/ = s .str[ j ]/*rbyte 0*/ ;
  1058.  
  1059. }
  1060. ;
  1061.  
  1062. for (
  1063. int j= 0 ; j < a .len ; j ++ ) {
  1064.  
  1065. res .str[ s .len + j ]/*rbyte 1*/ = a .str[ j ]/*rbyte 0*/ ;
  1066.  
  1067. }
  1068. ;
  1069.  
  1070. res .str[ new_len ]/*rbyte 1*/ = '\0' ;
  1071.  
  1072.  
  1073. return res ;
  1074.  
  1075.  
  1076. }
  1077. array_string string_split(string s, string delim) {
  1078.  
  1079. array_string res=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  1080.  
  1081. if ( delim .len == 0 ) {
  1082. /*if*/
  1083.  
  1084. _PUSH(& res , ( s ), tmp32, string) ;
  1085.  
  1086.  
  1087. return res ;
  1088.  
  1089. }
  1090. ;
  1091.  
  1092. if ( delim .len == 1 ) {
  1093. /*if*/
  1094.  
  1095.  
  1096. return string_split_single( s , delim .str[ 0 ]/*rbyte 0*/ ) ;
  1097.  
  1098. }
  1099. ;
  1100.  
  1101. int i= 0 ;
  1102.  
  1103. int start= 0 ;
  1104.  
  1105. while ( i < s .len ) {
  1106.  
  1107. bool a= s .str[ i ]/*rbyte 0*/ == delim .str[ 0 ]/*rbyte 0*/ ;
  1108.  
  1109. int j= 1 ;
  1110.  
  1111. while ( j < delim .len && a ) {
  1112.  
  1113. a = a && s .str[ i + j ]/*rbyte 0*/ == delim .str[ j ]/*rbyte 0*/ ;
  1114.  
  1115. j ++ ;
  1116.  
  1117. }
  1118. ;
  1119.  
  1120. bool last= i == s .len - 1 ;
  1121.  
  1122. if ( a || last ) {
  1123. /*if*/
  1124.  
  1125. if ( last ) {
  1126. /*if*/
  1127.  
  1128. i ++ ;
  1129.  
  1130. }
  1131. ;
  1132.  
  1133. string val= string_substr( s , start , i ) ;
  1134.  
  1135. if ( val .len > 0 ) {
  1136. /*if*/
  1137.  
  1138. if ( string_starts_with( val , delim ) ) {
  1139. /*if*/
  1140.  
  1141. val = string_right( val , delim .len ) ;
  1142.  
  1143. }
  1144. ;
  1145.  
  1146. _PUSH(& res , ( string_trim_space( val ) ), tmp39, string) ;
  1147.  
  1148. }
  1149. ;
  1150.  
  1151. start = i ;
  1152.  
  1153. }
  1154. ;
  1155.  
  1156. i ++ ;
  1157.  
  1158. }
  1159. ;
  1160.  
  1161.  
  1162. return res ;
  1163.  
  1164.  
  1165. }
  1166. array_string string_split_single(string s, byte delim) {
  1167.  
  1168. array_string res=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  1169.  
  1170. if ( (/*casttt*/ (int)( /*77*/ delim ) ) == 0 ) {
  1171. /*if*/
  1172.  
  1173. _PUSH(& res , ( s ), tmp41, string) ;
  1174.  
  1175.  
  1176. return res ;
  1177.  
  1178. }
  1179. ;
  1180.  
  1181. int i= 0 ;
  1182.  
  1183. int start= 0 ;
  1184.  
  1185. while ( i < s .len ) {
  1186.  
  1187. bool a= s .str[ i ]/*rbyte 0*/ == delim ;
  1188.  
  1189. bool b= i == s .len - 1 ;
  1190.  
  1191. if ( a || b ) {
  1192. /*if*/
  1193.  
  1194. if ( i == s .len - 1 ) {
  1195. /*if*/
  1196.  
  1197. i ++ ;
  1198.  
  1199. }
  1200. ;
  1201.  
  1202. string val= string_substr( s , start , i ) ;
  1203.  
  1204. if ( val .len > 0 ) {
  1205. /*if*/
  1206.  
  1207. _PUSH(& res , ( string_trim_space( val ) ), tmp47, string) ;
  1208.  
  1209. }
  1210. ;
  1211.  
  1212. start = i + 1 ;
  1213.  
  1214. }
  1215. ;
  1216.  
  1217. i ++ ;
  1218.  
  1219. }
  1220. ;
  1221.  
  1222.  
  1223. return res ;
  1224.  
  1225.  
  1226. }
  1227. array_string string_split_into_lines(string s) {
  1228.  
  1229. array_string res=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  1230.  
  1231. if ( s .len == 0 ) {
  1232. /*if*/
  1233.  
  1234.  
  1235. return res ;
  1236.  
  1237. }
  1238. ;
  1239.  
  1240. int start= 0 ;
  1241.  
  1242. for (
  1243. int i= 0 ; i < s .len ; i ++ ) {
  1244.  
  1245. bool last= i == s .len - 1 ;
  1246.  
  1247. if ( (/*casttt*/ (int)( /*77*/ s .str[ i ]/*rbyte 0*/ ) ) == 10 || last ) {
  1248. /*if*/
  1249.  
  1250. if ( last ) {
  1251. /*if*/
  1252.  
  1253. i ++ ;
  1254.  
  1255. }
  1256. ;
  1257.  
  1258. string line= string_substr( s , start , i ) ;
  1259.  
  1260. _PUSH(& res , ( line ), tmp53, string) ;
  1261.  
  1262. start = i + 1 ;
  1263.  
  1264. }
  1265. ;
  1266.  
  1267. }
  1268. ;
  1269.  
  1270.  
  1271. return res ;
  1272.  
  1273.  
  1274. }
  1275. string string_left(string s, int n) {
  1276.  
  1277. if ( n >= s .len ) {
  1278. /*if*/
  1279.  
  1280.  
  1281. return s ;
  1282.  
  1283. }
  1284. ;
  1285.  
  1286.  
  1287. return string_substr( s , 0 , n ) ;
  1288.  
  1289.  
  1290. }
  1291. string string_right(string s, int n) {
  1292.  
  1293. if ( n >= s .len ) {
  1294. /*if*/
  1295.  
  1296.  
  1297. return tos2("") ;
  1298.  
  1299. }
  1300. ;
  1301.  
  1302.  
  1303. return string_substr( s , n , s .len ) ;
  1304.  
  1305.  
  1306. }
  1307. string string_substr(string s, int start, int end) {
  1308.  
  1309. if ( start >= s .len ) {
  1310. /*if*/
  1311.  
  1312.  
  1313. return tos2("") ;
  1314.  
  1315. }
  1316. ;
  1317.  
  1318. int len= end - start ;
  1319.  
  1320. string res= /* S INIT */ (string){ .str = s .str + start , .len = len } ;
  1321.  
  1322.  
  1323. return res ;
  1324.  
  1325.  
  1326. }
  1327. int string_index(string s, string p) {
  1328.  
  1329. if ( p .len > s .len ) {
  1330. /*if*/
  1331.  
  1332.  
  1333. return - 1 ;
  1334.  
  1335. }
  1336. ;
  1337.  
  1338. int i= 0 ;
  1339.  
  1340. while ( i < s .len ) {
  1341.  
  1342. int j= 0 ;
  1343.  
  1344. int ii= i ;
  1345.  
  1346. while ( j < p .len && s .str[ ii ]/*rbyte 0*/ == p .str[ j ]/*rbyte 0*/ ) {
  1347.  
  1348. j ++ ;
  1349.  
  1350. ii ++ ;
  1351.  
  1352. }
  1353. ;
  1354.  
  1355. if ( j == p .len ) {
  1356. /*if*/
  1357.  
  1358.  
  1359. return i ;
  1360.  
  1361. }
  1362. ;
  1363.  
  1364. i ++ ;
  1365.  
  1366. }
  1367. ;
  1368.  
  1369.  
  1370. return - 1 ;
  1371.  
  1372.  
  1373. }
  1374. int string_last_index(string s, string p) {
  1375.  
  1376. if ( p .len > s .len ) {
  1377. /*if*/
  1378.  
  1379.  
  1380. return - 1 ;
  1381.  
  1382. }
  1383. ;
  1384.  
  1385. int i= s .len - p .len ;
  1386.  
  1387. while ( i >= 0 ) {
  1388.  
  1389. int j= 0 ;
  1390.  
  1391. while ( j < p .len && s .str[ i + j ]/*rbyte 0*/ == p .str[ j ]/*rbyte 0*/ ) {
  1392.  
  1393. j ++ ;
  1394.  
  1395. }
  1396. ;
  1397.  
  1398. if ( j == p .len ) {
  1399. /*if*/
  1400.  
  1401.  
  1402. return i ;
  1403.  
  1404. }
  1405. ;
  1406.  
  1407. i -- ;
  1408.  
  1409. }
  1410. ;
  1411.  
  1412.  
  1413. return - 1 ;
  1414.  
  1415.  
  1416. }
  1417. int string_index_after(string s, string p, int start) {
  1418.  
  1419. if ( p .len > s .len ) {
  1420. /*if*/
  1421.  
  1422.  
  1423. return - 1 ;
  1424.  
  1425. }
  1426. ;
  1427.  
  1428. int strt= start ;
  1429.  
  1430. if ( start < 0 ) {
  1431. /*if*/
  1432.  
  1433. strt = 0 ;
  1434.  
  1435. }
  1436. ;
  1437.  
  1438. if ( start >= s .len ) {
  1439. /*if*/
  1440.  
  1441.  
  1442. return - 1 ;
  1443.  
  1444. }
  1445. ;
  1446.  
  1447. int i= strt ;
  1448.  
  1449. while ( i < s .len ) {
  1450.  
  1451. int j= 0 ;
  1452.  
  1453. int ii= i ;
  1454.  
  1455. while ( j < p .len && s .str[ ii ]/*rbyte 0*/ == p .str[ j ]/*rbyte 0*/ ) {
  1456.  
  1457. j ++ ;
  1458.  
  1459. ii ++ ;
  1460.  
  1461. }
  1462. ;
  1463.  
  1464. if ( j == p .len ) {
  1465. /*if*/
  1466.  
  1467.  
  1468. return i ;
  1469.  
  1470. }
  1471. ;
  1472.  
  1473. i ++ ;
  1474.  
  1475. }
  1476. ;
  1477.  
  1478.  
  1479. return - 1 ;
  1480.  
  1481.  
  1482. }
  1483. bool string_contains(string s, string p) {
  1484.  
  1485. bool res= string_index( s , p ) > 0 - 1 ;
  1486.  
  1487.  
  1488. return res ;
  1489.  
  1490.  
  1491. }
  1492. bool string_starts_with(string s, string p) {
  1493.  
  1494. bool res= string_index( s , p ) == 0 ;
  1495.  
  1496.  
  1497. return res ;
  1498.  
  1499.  
  1500. }
  1501. bool string_ends_with(string s, string p) {
  1502.  
  1503. if ( p .len > s .len ) {
  1504. /*if*/
  1505.  
  1506.  
  1507. return 0 ;
  1508.  
  1509. }
  1510. ;
  1511.  
  1512. bool res= string_last_index( s , p ) == s .len - p .len ;
  1513.  
  1514.  
  1515. return res ;
  1516.  
  1517.  
  1518. }
  1519. string string_to_lower(string s) {
  1520.  
  1521. byte* b= v_malloc ( s .len ) ;
  1522.  
  1523. for (
  1524. int i= 0 ; i < s .len ; i ++ ) {
  1525.  
  1526. b [/*ptr*/ i ]/*rbyte 1*/ = tolower ( s .str [/*ptr*/ i ]/*rbyte 0*/ ) ;
  1527.  
  1528. }
  1529. ;
  1530.  
  1531.  
  1532. return tos ( b , s .len ) ;
  1533.  
  1534.  
  1535. }
  1536. string string_to_upper(string s) {
  1537.  
  1538. byte* b= v_malloc ( s .len ) ;
  1539.  
  1540. for (
  1541. int i= 0 ; i < s .len ; i ++ ) {
  1542.  
  1543. b [/*ptr*/ i ]/*rbyte 1*/ = toupper ( s .str [/*ptr*/ i ]/*rbyte 0*/ ) ;
  1544.  
  1545. }
  1546. ;
  1547.  
  1548.  
  1549. return tos ( b , s .len ) ;
  1550.  
  1551.  
  1552. }
  1553. string string_find_between(string s, string start, string end) {
  1554.  
  1555. int start_pos= string_index( s , start ) ;
  1556.  
  1557. if ( start_pos == - 1 ) {
  1558. /*if*/
  1559.  
  1560.  
  1561. return tos2("") ;
  1562.  
  1563. }
  1564. ;
  1565.  
  1566. string val= string_right( s , start_pos + start .len ) ;
  1567.  
  1568. int end_pos= string_index( val , end ) ;
  1569.  
  1570. if ( end_pos == - 1 ) {
  1571. /*if*/
  1572.  
  1573.  
  1574. return val ;
  1575.  
  1576. }
  1577. ;
  1578.  
  1579.  
  1580. return string_left( val , end_pos ) ;
  1581.  
  1582.  
  1583. }
  1584. bool array_string_contains(array_string ar, string val) {
  1585.  
  1586. array_string tmp75 = ar;
  1587. ;
  1588. for (int tmp76 = 0; tmp76 < tmp75 .len; tmp76 ++) {
  1589. string s = ((string *) tmp75.data)[tmp76];
  1590.  
  1591. if (string_eq( s , val )/*8*/ ) {
  1592. /*if*/
  1593.  
  1594.  
  1595. return 1 ;
  1596.  
  1597. }
  1598. ;
  1599.  
  1600. }
  1601. ;
  1602.  
  1603.  
  1604. return 0 ;
  1605.  
  1606.  
  1607. }
  1608. bool array_int_contains(array_int ar, int val) {
  1609.  
  1610. array_int tmp77 = ar ;
  1611. ;
  1612. for (int i = 0; i < tmp77 .len; i ++) {
  1613. int s = ((int *) tmp77 . data)[i];
  1614.  
  1615. if ( s == val ) {
  1616. /*if*/
  1617.  
  1618.  
  1619. return 1 ;
  1620.  
  1621. }
  1622. ;
  1623.  
  1624. }
  1625. ;
  1626.  
  1627.  
  1628. return 0 ;
  1629.  
  1630.  
  1631. }
  1632. void* array_string_to_c(array_string a) {
  1633.  
  1634. char ** res = malloc(sizeof(char*) * a.len);
  1635.  
  1636. for (
  1637. int i= 0 ; i < a .len ; i ++ ) {
  1638.  
  1639. string val= ( *(string*) array__get( a , i) ) ;
  1640.  
  1641. res[i] = val.str;
  1642.  
  1643. }
  1644. ;
  1645.  
  1646. return res;
  1647.  
  1648.  
  1649. return 0 ;
  1650.  
  1651.  
  1652. }
  1653. bool is_space(byte c) {
  1654.  
  1655.  
  1656. return isspace ( c ) ;
  1657.  
  1658.  
  1659. }
  1660. bool byte_is_space(byte c) {
  1661.  
  1662.  
  1663. return is_space ( c ) ;
  1664.  
  1665.  
  1666. }
  1667. string string_trim_space(string s) {
  1668.  
  1669. if (string_eq( s , tos2("") )/*8*/ ) {
  1670. /*if*/
  1671.  
  1672.  
  1673. return tos2("") ;
  1674.  
  1675. }
  1676. ;
  1677.  
  1678. int i= 0 ;
  1679.  
  1680. while ( i < s .len && is_space ( s .str[ i ]/*rbyte 0*/ ) ) {
  1681.  
  1682. i ++ ;
  1683.  
  1684. }
  1685. ;
  1686.  
  1687. string res= string_right( s , i ) ;
  1688.  
  1689. int end= res .len - 1 ;
  1690.  
  1691. while ( end >= 0 && is_space ( res .str[ end ]/*rbyte 1*/ ) ) {
  1692.  
  1693. end -- ;
  1694.  
  1695. }
  1696. ;
  1697.  
  1698. res = string_left( res , end + 1 ) ;
  1699.  
  1700.  
  1701. return res ;
  1702.  
  1703.  
  1704. }
  1705. string string_trim(string s, byte c) {
  1706.  
  1707. if (string_eq( s , tos2("") )/*8*/ ) {
  1708. /*if*/
  1709.  
  1710.  
  1711. return tos2("") ;
  1712.  
  1713. }
  1714. ;
  1715.  
  1716. int i= 0 ;
  1717.  
  1718. while ( i < s .len && c == s .str[ i ]/*rbyte 0*/ ) {
  1719.  
  1720. i ++ ;
  1721.  
  1722. }
  1723. ;
  1724.  
  1725. string res= string_right( s , i ) ;
  1726.  
  1727. int end= res .len - 1 ;
  1728.  
  1729. while ( end >= 0 && c == res .str[ end ]/*rbyte 1*/ ) {
  1730.  
  1731. end -- ;
  1732.  
  1733. }
  1734. ;
  1735.  
  1736. res = string_left( res , end + 1 ) ;
  1737.  
  1738.  
  1739. return res ;
  1740.  
  1741.  
  1742. }
  1743. string string_trim_left(string s, string cutset) {
  1744.  
  1745. int start= string_index( s , cutset ) ;
  1746.  
  1747. if ( start != 0 ) {
  1748. /*if*/
  1749.  
  1750.  
  1751. return s ;
  1752.  
  1753. }
  1754. ;
  1755.  
  1756. while ( start < s .len - 1 && s .str[ start ]/*rbyte 0*/ == cutset .str[ 0 ]/*rbyte 0*/ ) {
  1757.  
  1758. start ++ ;
  1759.  
  1760. }
  1761. ;
  1762.  
  1763.  
  1764. return string_right( s , start ) ;
  1765.  
  1766.  
  1767. }
  1768. string string_trim_right(string s, string cutset) {
  1769.  
  1770.  
  1771. return s ;
  1772.  
  1773. int pos= string_last_index( s , cutset ) ;
  1774.  
  1775. if ( pos == - 1 ) {
  1776. /*if*/
  1777.  
  1778.  
  1779. return s ;
  1780.  
  1781. }
  1782. ;
  1783.  
  1784.  
  1785. return string_left( s , pos ) ;
  1786.  
  1787.  
  1788. }
  1789. int compare_strings(string* a, string* b) {
  1790.  
  1791. if ( string_le(* a ,* b ) ) {
  1792. /*if*/
  1793.  
  1794.  
  1795. return - 1 ;
  1796.  
  1797. }
  1798. ;
  1799.  
  1800. if ( string_ge(* a ,* b ) ) {
  1801. /*if*/
  1802.  
  1803.  
  1804. return 1 ;
  1805.  
  1806. }
  1807. ;
  1808.  
  1809.  
  1810. return 0 ;
  1811.  
  1812.  
  1813. }
  1814. int compare_strings_by_len(string* a, string* b) {
  1815.  
  1816. if ( a ->len < b ->len ) {
  1817. /*if*/
  1818.  
  1819.  
  1820. return - 1 ;
  1821.  
  1822. }
  1823. ;
  1824.  
  1825. if ( a ->len > b ->len ) {
  1826. /*if*/
  1827.  
  1828.  
  1829. return 1 ;
  1830.  
  1831. }
  1832. ;
  1833.  
  1834.  
  1835. return 0 ;
  1836.  
  1837.  
  1838. }
  1839. int compare_lower_strings(string* a, string* b) {
  1840.  
  1841. string aa= string_to_lower(* a ) ;
  1842.  
  1843. string bb= string_to_lower(* a ) ;
  1844.  
  1845.  
  1846. return compare_strings (& /*11 EXP:"string*" GOT:"string" */ aa ,& /*11 EXP:"string*" GOT:"string" */ bb ) ;
  1847.  
  1848.  
  1849. }
  1850. void array_string_sort(array_string* s) {
  1851.  
  1852. array_sort_with_compare( s , compare_strings ) ;
  1853.  
  1854.  
  1855. }
  1856. void array_string_sort_ignore_case(array_string* s) {
  1857.  
  1858. array_sort_with_compare( s , compare_lower_strings ) ;
  1859.  
  1860.  
  1861. }
  1862. void array_string_sort_by_len(array_string* s) {
  1863.  
  1864. array_sort_with_compare( s , compare_strings_by_len ) ;
  1865.  
  1866.  
  1867. }
  1868. ustring string_ustring(string s) {
  1869.  
  1870. ustring res= /* S INIT */ (ustring){ .s = s , .runes = new_array ( 0 , s .len , sizeof( int) ) , .len = 0 } ;
  1871.  
  1872. for (
  1873. int i= 0 ; i < s .len ; i ++ ) {
  1874.  
  1875. int char_len= 0 ;
  1876.  
  1877. char_len =UTF8_CHAR_LEN(s.str[i]);
  1878.  
  1879. _PUSH(& res .runes , ( i ), tmp95, int) ;
  1880.  
  1881. i += char_len - 1 ;
  1882.  
  1883. res .len ++ ;
  1884.  
  1885. }
  1886. ;
  1887.  
  1888.  
  1889. return res ;
  1890.  
  1891.  
  1892. }
  1893. array_int g_ustring_runes;
  1894. ustring string_ustring_tmp(string s) {
  1895.  
  1896. ustring res= /* S INIT */ (ustring){ .s = s , .runes = 0 , .len = 0 } ;
  1897.  
  1898. res.runes = g_ustring_runes ;
  1899.  
  1900. res.runes.len = s.len ;
  1901.  
  1902. int j= 0 ;
  1903.  
  1904. for (
  1905. int i= 0 ; i < s .len ; i ++ ) {
  1906.  
  1907. int char_len= 0 ;
  1908.  
  1909. char_len =UTF8_CHAR_LEN(s.str[i]);
  1910. int tmp100 = i;
  1911.  
  1912. array_set(&/*q*/ res .runes , j , & tmp100) ;
  1913.  
  1914. j ++ ;
  1915.  
  1916. i += char_len - 1 ;
  1917.  
  1918. res .len ++ ;
  1919.  
  1920. }
  1921. ;
  1922.  
  1923.  
  1924. return res ;
  1925.  
  1926.  
  1927. }
  1928. string ustring_substr(ustring u, int start, int end) {
  1929.  
  1930. start = ( *(int*) array__get( u .runes , start) ) ;
  1931.  
  1932. if ( end >= u .runes .len ) {
  1933. /*if*/
  1934.  
  1935. end = u .s .len ;
  1936.  
  1937. }
  1938. else {
  1939. /*else if*/
  1940.  
  1941. end = ( *(int*) array__get( u .runes , end) ) ;
  1942.  
  1943. }
  1944. ;
  1945.  
  1946.  
  1947. return string_substr( u .s , start , end ) ;
  1948.  
  1949.  
  1950. }
  1951. string ustring_left(ustring u, int pos) {
  1952.  
  1953.  
  1954. return ustring_substr( u , 0 , pos ) ;
  1955.  
  1956.  
  1957. }
  1958. string ustring_right(ustring u, int pos) {
  1959.  
  1960.  
  1961. return ustring_substr( u , pos , u .len ) ;
  1962.  
  1963.  
  1964. }
  1965. byte string_at(string s, int idx) {
  1966.  
  1967. if ( idx < 0 || idx >= s .len ) {
  1968. /*if*/
  1969.  
  1970. v_panic ( _STR("string index out of range: %d / %d", idx, s .len) ) ;
  1971.  
  1972. }
  1973. ;
  1974.  
  1975.  
  1976. return s .str [/*ptr*/ idx ]/*rbyte 0*/ ;
  1977.  
  1978.  
  1979. }
  1980. string ustring_at(ustring u, int idx) {
  1981.  
  1982.  
  1983. return ustring_substr( u , idx , idx + 1 ) ;
  1984.  
  1985.  
  1986. }
  1987. void v_ustring_free(ustring u) {
  1988.  
  1989. v_array_int_free( u .runes ) ;
  1990.  
  1991.  
  1992. }
  1993. int abs(int a) {
  1994.  
  1995. if ( a >= 0 ) {
  1996. /*if*/
  1997.  
  1998.  
  1999. return a ;
  2000.  
  2001. }
  2002. ;
  2003.  
  2004.  
  2005. return - a ;
  2006.  
  2007.  
  2008. }
  2009. bool byte_is_digit(byte c) {
  2010.  
  2011.  
  2012. return c >= '0' && c <= '9' ;
  2013.  
  2014.  
  2015. }
  2016. bool byte_is_letter(byte c) {
  2017.  
  2018.  
  2019. return (/*lpar*/ c >= 'a' && c <= 'z' ) || (/*lpar*/ c >= 'A' && c <= 'Z' ) ;
  2020.  
  2021.  
  2022. }
  2023. void v_string_free(string s) {
  2024.  
  2025. free ( s .str ) ;
  2026.  
  2027.  
  2028. }
  2029. void v_array_string_free(array_string arr) {
  2030.  
  2031. array_string tmp105 = arr;
  2032. ;
  2033. for (int tmp106 = 0; tmp106 < tmp105 .len; tmp106 ++) {
  2034. string s = ((string *) tmp105.data)[tmp106];
  2035.  
  2036. v_string_free( s ) ;
  2037.  
  2038. }
  2039. ;
  2040.  
  2041. free ( arr .data ) ;
  2042.  
  2043.  
  2044. }
  2045. string string_all_before(string s, string dot) {
  2046.  
  2047. int pos= string_index( s , dot ) ;
  2048.  
  2049. if ( pos == - 1 ) {
  2050. /*if*/
  2051.  
  2052.  
  2053. return s ;
  2054.  
  2055. }
  2056. ;
  2057.  
  2058.  
  2059. return string_left( s , pos ) ;
  2060.  
  2061.  
  2062. }
  2063. string string_all_before_last(string s, string dot) {
  2064.  
  2065. int pos= string_last_index( s , dot ) ;
  2066.  
  2067. if ( pos == - 1 ) {
  2068. /*if*/
  2069.  
  2070.  
  2071. return s ;
  2072.  
  2073. }
  2074. ;
  2075.  
  2076.  
  2077. return string_left( s , pos ) ;
  2078.  
  2079.  
  2080. }
  2081. string string_all_after(string s, string dot) {
  2082.  
  2083. int pos= string_last_index( s , dot ) ;
  2084.  
  2085. if ( pos == - 1 ) {
  2086. /*if*/
  2087.  
  2088.  
  2089. return s ;
  2090.  
  2091. }
  2092. ;
  2093.  
  2094.  
  2095. return string_right( s , pos + dot .len ) ;
  2096.  
  2097.  
  2098. }
  2099. string array_string_join(array_string a, string del) {
  2100.  
  2101. if ( a .len == 0 ) {
  2102. /*if*/
  2103.  
  2104.  
  2105. return tos2("") ;
  2106.  
  2107. }
  2108. ;
  2109.  
  2110. int len= 0 ;
  2111.  
  2112. array_string tmp111 = a ;
  2113. ;
  2114. for (int i = 0; i < tmp111 .len; i ++) {
  2115. string val = ((string *) tmp111 . data)[i];
  2116.  
  2117. len += val .len + del .len ;
  2118.  
  2119. }
  2120. ;
  2121.  
  2122. len -= del .len ;
  2123.  
  2124. string res= tos2("") ;
  2125.  
  2126. res .len = len ;
  2127.  
  2128. res .str = v_malloc ( res .len + 1 ) ;
  2129.  
  2130. int idx= 0 ;
  2131.  
  2132. array_string tmp114 = a ;
  2133. ;
  2134. for (int i = 0; i < tmp114 .len; i ++) {
  2135. string val = ((string *) tmp114 . data)[i];
  2136.  
  2137. for (
  2138. int j= 0 ; j < val .len ; j ++ ) {
  2139.  
  2140. byte c= val .str[ j ]/*rbyte 0*/ ;
  2141.  
  2142. res .str [/*ptr*/ idx ]/*rbyte 1*/ = val .str [/*ptr*/ j ]/*rbyte 0*/ ;
  2143.  
  2144. idx ++ ;
  2145.  
  2146. }
  2147. ;
  2148.  
  2149. if ( i != a .len - 1 ) {
  2150. /*if*/
  2151.  
  2152. for (
  2153. int k= 0 ; k < del .len ; k ++ ) {
  2154.  
  2155. res .str [/*ptr*/ idx ]/*rbyte 1*/ = del .str [/*ptr*/ k ]/*rbyte 0*/ ;
  2156.  
  2157. idx ++ ;
  2158.  
  2159. }
  2160. ;
  2161.  
  2162. }
  2163. ;
  2164.  
  2165. }
  2166. ;
  2167.  
  2168. res .str [/*ptr*/ res .len ]/*rbyte 1*/ = '\0' ;
  2169.  
  2170.  
  2171. return res ;
  2172.  
  2173.  
  2174. }
  2175. string array_string_join_lines(array_string s) {
  2176.  
  2177.  
  2178. return array_string_join( s , tos2("\n") ) ;
  2179.  
  2180.  
  2181. }
  2182. string string_limit(string s, int max) {
  2183.  
  2184. ustring u= string_ustring( s ) ;
  2185.  
  2186. if ( u .len <= max ) {
  2187. /*if*/
  2188.  
  2189.  
  2190. return s ;
  2191.  
  2192. }
  2193. ;
  2194.  
  2195.  
  2196. return ustring_substr( u , 0 , max ) ;
  2197.  
  2198.  
  2199. }
  2200. bool byte_is_white(byte c) {
  2201.  
  2202. int i= (/*casttt*/ (int)( /*77*/ c ) ) ;
  2203.  
  2204.  
  2205. return i == 10 || i == 32 || i == 9 || i == 13 || c == '\r' ;
  2206.  
  2207.  
  2208. }
  2209. string repeat_char(byte c, int n) {
  2210.  
  2211. if ( n <= 0 ) {
  2212. /*if*/
  2213.  
  2214.  
  2215. return tos2("") ;
  2216.  
  2217. }
  2218. ;
  2219.  
  2220. byte* arr= v_malloc ( n + 1 ) ;
  2221.  
  2222. for (
  2223. int i= 0 ; i < n ; i ++ ) {
  2224.  
  2225. arr [/*ptr*/ i ]/*rbyte 1*/ = c ;
  2226.  
  2227. }
  2228. ;
  2229.  
  2230. arr [/*ptr*/ n ]/*rbyte 1*/ = '\0' ;
  2231.  
  2232.  
  2233. return tos ( arr , n ) ;
  2234.  
  2235.  
  2236. }
  2237. int string_hash(string s) {
  2238.  
  2239. int hash= (/*casttt*/ (int)( /*77*/ 0 ) ) ;
  2240.  
  2241. for (
  2242. int i= 0 ; i < s .len ; i ++ ) {
  2243.  
  2244. hash = hash * (/*casttt*/ (int)( /*77*/ 31 ) ) + (/*casttt*/ (int)( /*77*/ s .str [/*ptr*/ i ]/*rbyte 0*/ ) ) ;
  2245.  
  2246. }
  2247. ;
  2248.  
  2249.  
  2250. return hash ;
  2251.  
  2252.  
  2253. }
  2254. void v_exit(string reason) {
  2255.  
  2256. if (string_eq( reason , tos2("") )/*8*/ ) {
  2257. /*if*/
  2258.  
  2259. v_panic ( tos2("exit empty reason") ) ;
  2260.  
  2261. }
  2262. ;
  2263.  
  2264. println2 ( _STR("exit(): %.*s", reason.len, reason.str) ) ;
  2265.  
  2266. exit ( 0 ) ;
  2267.  
  2268.  
  2269. }
  2270. bool isnil(void* v) {
  2271.  
  2272.  
  2273. return v == 0 ;
  2274.  
  2275.  
  2276. }
  2277. void on_panic(int (*f)( int /*FFF*/ )) {
  2278.  
  2279.  
  2280. }
  2281. void print_backtrace() {
  2282.  
  2283.  
  2284. return ;
  2285.  
  2286. #ifdef mac
  2287.  
  2288. voidptr buffer [100 ]= {} /* arkek init*/ ;
  2289.  
  2290. void* nr_ptrs= backtrace ( buffer , 100 ) ;
  2291.  
  2292. backtrace_symbols_fd ( buffer , nr_ptrs , 1 ) ;
  2293.  
  2294. #endif
  2295. ;
  2296.  
  2297.  
  2298. }
  2299. void v_panic(string s) {
  2300.  
  2301. println2 ( _STR("V panic: %.*s", s.len, s.str) ) ;
  2302.  
  2303. print_backtrace ( ) ;
  2304.  
  2305. exit ( 1 ) ;
  2306.  
  2307.  
  2308. }
  2309. void println(string s) {
  2310.  
  2311. if ( isnil ( s .str ) ) {
  2312. /*if*/
  2313.  
  2314. v_panic ( tos2("println(NIL)") ) ;
  2315.  
  2316. }
  2317. ;
  2318.  
  2319. printf ( "%.*s\n" , s .len , s .str ) ;
  2320.  
  2321.  
  2322. }
  2323. void eprintln(string s) {
  2324.  
  2325. if ( isnil ( s .str ) ) {
  2326. /*if*/
  2327.  
  2328. v_panic ( tos2("eprintln(NIL)") ) ;
  2329.  
  2330. }
  2331. ;
  2332.  
  2333. #ifdef mac
  2334.  
  2335. fprintf ( stderr , "%.*s\n" , s .len , s .str ) ;
  2336.  
  2337. ;
  2338.  
  2339. #else
  2340.  
  2341. println2 ( s ) ;
  2342.  
  2343. #endif
  2344. ;
  2345.  
  2346.  
  2347. }
  2348. void v_print(string s) {
  2349.  
  2350. printf ( "%.*s" , s .len , s .str ) ;
  2351.  
  2352.  
  2353. }
  2354. void println2(string s) {
  2355.  
  2356. printf ( "%.*s\n" , s .len , s .str ) ;
  2357.  
  2358.  
  2359. }
  2360. byte* v_malloc(int n) {
  2361.  
  2362. if ( n < 0 ) {
  2363. /*if*/
  2364.  
  2365. v_panic ( tos2("malloc(<0)") ) ;
  2366.  
  2367. }
  2368. ;
  2369.  
  2370. #ifdef VPLAY
  2371.  
  2372. if ( n > 10000 ) {
  2373. /*if*/
  2374.  
  2375. v_panic ( tos2("allocating more than 10 KB is not allowed in the playground") ) ;
  2376.  
  2377. }
  2378. ;
  2379.  
  2380. #endif
  2381.  
  2382. #ifdef DEBUG_ALLOC
  2383.  
  2384. i64 total= (/*casttt*/ (i64)( /*77*/ 0 ) ) ;
  2385.  
  2386. total_m += n;
  2387.  
  2388. total = total_m;
  2389.  
  2390. println2 ( _STR("\n\n\nmalloc(%d) total=%lld", n, total) ) ;
  2391.  
  2392. print_backtrace ( ) ;
  2393.  
  2394. #endif
  2395.  
  2396. byte* ptr= malloc ( n ) ;
  2397.  
  2398. if ( isnil ( ptr ) ) {
  2399. /*if*/
  2400.  
  2401. v_panic ( _STR("malloc(%d) failed", n) ) ;
  2402.  
  2403. }
  2404. ;
  2405.  
  2406.  
  2407. return ptr ;
  2408.  
  2409.  
  2410. }
  2411. byte* v_calloc(int n) {
  2412.  
  2413. if ( n < 0 ) {
  2414. /*if*/
  2415.  
  2416. v_panic ( tos2("calloc(<0)") ) ;
  2417.  
  2418. }
  2419. ;
  2420.  
  2421.  
  2422. return calloc ( sizeof( float) * n , sizeof( float) ) ;
  2423.  
  2424.  
  2425. }
  2426. int _strlen(byte* s) {
  2427.  
  2428.  
  2429. return strlen ( s ) ;
  2430.  
  2431.  
  2432. }
  2433. Option opt_ok(void* data) {
  2434.  
  2435.  
  2436. return /* S INIT */ (Option){ .data = data , .ok = 1 , .error = tos("", 0) , } ;
  2437.  
  2438.  
  2439. }
  2440. void* memdup(void* src, int sz) {
  2441.  
  2442. byte* mem= v_malloc ( sz ) ;
  2443.  
  2444.  
  2445. return memcpy ( mem , src , sz ) ;
  2446.  
  2447.  
  2448. }
  2449. Option v_error(string s) {
  2450.  
  2451.  
  2452. return /* S INIT */ (Option){ .error = s , .data = 0 , .ok = 0 } ;
  2453.  
  2454.  
  2455. }
  2456. array_int range_int(int start, int end) {
  2457.  
  2458. int len= end - start ;
  2459. /* arr init tmp*/ int tmp7 = 0;
  2460.  
  2461. array_int res= array_repeat(&tmp7, len , sizeof(int) ) ;
  2462.  
  2463. for (
  2464. int i= 0 ; i < len ; i ++ ) {
  2465. int tmp10 = start + i;
  2466.  
  2467. array_set(&/*q*/ res , i , & tmp10) ;
  2468.  
  2469. }
  2470. ;
  2471.  
  2472.  
  2473. return res ;
  2474.  
  2475.  
  2476. }
  2477. string double_str(double d) {
  2478.  
  2479. byte* buf= v_malloc ( sizeof( double) * 5 + 1 ) ;
  2480.  
  2481. sprintf ( buf , "%f" , d ) ;
  2482.  
  2483.  
  2484. return tos ( buf , _strlen ( buf ) ) ;
  2485.  
  2486.  
  2487. }
  2488. string float_str(float d) {
  2489.  
  2490. byte* buf= v_malloc ( sizeof( double) * 5 + 1 ) ;
  2491.  
  2492. sprintf ( buf , "%f" , d ) ;
  2493.  
  2494.  
  2495. return tos ( buf , _strlen ( buf ) ) ;
  2496.  
  2497.  
  2498. }
  2499. string f64_str(f64 d) {
  2500.  
  2501. byte* buf= v_malloc ( sizeof( double) * 5 + 1 ) ;
  2502.  
  2503. sprintf ( buf , "%f" , d ) ;
  2504.  
  2505.  
  2506. return tos ( buf , _strlen ( buf ) ) ;
  2507.  
  2508.  
  2509. }
  2510. string f32_str(f32 d) {
  2511.  
  2512. byte* buf= v_malloc ( sizeof( double) * 5 + 1 ) ;
  2513.  
  2514. sprintf ( buf , "%f" , d ) ;
  2515.  
  2516.  
  2517. return tos ( buf , _strlen ( buf ) ) ;
  2518.  
  2519.  
  2520. }
  2521. string ptr_str(void* ptr) {
  2522.  
  2523. byte* buf= v_malloc ( sizeof( double) * 5 + 1 ) ;
  2524.  
  2525. sprintf ( buf , "%p" , ptr ) ;
  2526.  
  2527.  
  2528. return tos ( buf , _strlen ( buf ) ) ;
  2529.  
  2530.  
  2531. }
  2532. string int_str(int nn) {
  2533.  
  2534. int n= nn ;
  2535.  
  2536. if ( n == 0 ) {
  2537. /*if*/
  2538.  
  2539.  
  2540. return tos2("0") ;
  2541.  
  2542. }
  2543. ;
  2544.  
  2545. int max= 16 ;
  2546.  
  2547. byte* buf= v_malloc ( max ) ;
  2548.  
  2549. int len= 0 ;
  2550.  
  2551. bool is_neg= 0 ;
  2552.  
  2553. if ( n < 0 ) {
  2554. /*if*/
  2555.  
  2556. n = - n ;
  2557.  
  2558. is_neg = 1 ;
  2559.  
  2560. }
  2561. ;
  2562.  
  2563. while ( n > 0 ) {
  2564.  
  2565. int d= n % 10 ;
  2566.  
  2567. buf [/*ptr*/ max - len - 1 ]/*rbyte 1*/ = d + (/*casttt*/ (int)( /*77*/ '0' ) ) ;
  2568.  
  2569. len ++ ;
  2570.  
  2571. n = n / 10 ;
  2572.  
  2573. }
  2574. ;
  2575.  
  2576. if ( is_neg ) {
  2577. /*if*/
  2578.  
  2579. buf [/*ptr*/ max - len - 1 ]/*rbyte 1*/ = '-' ;
  2580.  
  2581. len ++ ;
  2582.  
  2583. }
  2584. ;
  2585.  
  2586.  
  2587. return tos ( buf + max - len , len ) ;
  2588.  
  2589.  
  2590. }
  2591. string u8_str(u8 nn) {
  2592.  
  2593. u8 n= nn ;
  2594.  
  2595. if ( n == (/*casttt*/ (u8)( /*77*/ 0 ) ) ) {
  2596. /*if*/
  2597.  
  2598.  
  2599. return tos2("0") ;
  2600.  
  2601. }
  2602. ;
  2603.  
  2604. int max= 5 ;
  2605.  
  2606. byte* buf= v_malloc ( max ) ;
  2607.  
  2608. int len= 0 ;
  2609.  
  2610. bool is_neg= 0 ;
  2611.  
  2612. if ( n < (/*casttt*/ (u8)( /*77*/ 0 ) ) ) {
  2613. /*if*/
  2614.  
  2615. n = - n ;
  2616.  
  2617. is_neg = 1 ;
  2618.  
  2619. }
  2620. ;
  2621.  
  2622. while ( n > (/*casttt*/ (u8)( /*77*/ 0 ) ) ) {
  2623.  
  2624. u8 d= n % (/*casttt*/ (u8)( /*77*/ 10 ) ) ;
  2625.  
  2626. buf [/*ptr*/ max - len - 1 ]/*rbyte 1*/ = d + (/*casttt*/ (u8)( /*77*/ '0' ) ) ;
  2627.  
  2628. len ++ ;
  2629.  
  2630. n = n / (/*casttt*/ (u8)( /*77*/ 10 ) ) ;
  2631.  
  2632. }
  2633. ;
  2634.  
  2635. if ( is_neg ) {
  2636. /*if*/
  2637.  
  2638. buf [/*ptr*/ max - len - 1 ]/*rbyte 1*/ = '-' ;
  2639.  
  2640. len ++ ;
  2641.  
  2642. }
  2643. ;
  2644.  
  2645.  
  2646. return tos ( buf + max - len , len ) ;
  2647.  
  2648.  
  2649. }
  2650. string i64_str(i64 nn) {
  2651.  
  2652. i64 n= nn ;
  2653.  
  2654. if ( n == (/*casttt*/ (i64)( /*77*/ 0 ) ) ) {
  2655. /*if*/
  2656.  
  2657.  
  2658. return tos2("0") ;
  2659.  
  2660. }
  2661. ;
  2662.  
  2663. int max= 32 ;
  2664.  
  2665. byte* buf= v_malloc ( max ) ;
  2666.  
  2667. int len= 0 ;
  2668.  
  2669. bool is_neg= 0 ;
  2670.  
  2671. if ( n < (/*casttt*/ (i64)( /*77*/ 0 ) ) ) {
  2672. /*if*/
  2673.  
  2674. n = - n ;
  2675.  
  2676. is_neg = 1 ;
  2677.  
  2678. }
  2679. ;
  2680.  
  2681. while ( n > (/*casttt*/ (i64)( /*77*/ 0 ) ) ) {
  2682.  
  2683. int d= (/*casttt*/ (int)( /*77*/ n % (/*casttt*/ (i64)( /*77*/ 10 ) ) ) ) ;
  2684.  
  2685. buf [/*ptr*/ max - len - 1 ]/*rbyte 1*/ = d + (/*casttt*/ (int)( /*77*/ '0' ) ) ;
  2686.  
  2687. len ++ ;
  2688.  
  2689. n = n / (/*casttt*/ (i64)( /*77*/ 10 ) ) ;
  2690.  
  2691. }
  2692. ;
  2693.  
  2694. if ( is_neg ) {
  2695. /*if*/
  2696.  
  2697. buf [/*ptr*/ max - len - 1 ]/*rbyte 1*/ = '-' ;
  2698.  
  2699. len ++ ;
  2700.  
  2701. }
  2702. ;
  2703.  
  2704.  
  2705. return tos ( buf + max - len , len ) ;
  2706.  
  2707.  
  2708. }
  2709. string bool_str(bool b) {
  2710.  
  2711. if ( b ) {
  2712. /*if*/
  2713.  
  2714.  
  2715. return tos2("true") ;
  2716.  
  2717. }
  2718. ;
  2719.  
  2720.  
  2721. return tos2("false") ;
  2722.  
  2723.  
  2724. }
  2725. string int_hex(int n) {
  2726.  
  2727. string s= int_str( n ) ;
  2728.  
  2729. byte* hex= v_malloc ( s .len + 2 ) ;
  2730.  
  2731. sprintf ( hex , "0x%x" , n ) ;
  2732.  
  2733.  
  2734. return tos ( hex , s .len + 2 ) ;
  2735.  
  2736.  
  2737. }
  2738. string i64_hex(i64 n) {
  2739.  
  2740. string s= i64_str( n ) ;
  2741.  
  2742. byte* hex= v_malloc ( s .len + 2 ) ;
  2743.  
  2744. sprintf ( hex , "0x%x" , n ) ;
  2745.  
  2746.  
  2747. return tos ( hex , s .len + 2 ) ;
  2748.  
  2749.  
  2750. }
  2751. bool array_byte_contains(array_byte a, byte val) {
  2752.  
  2753. array_byte tmp28 = a;
  2754. ;
  2755. for (int tmp29 = 0; tmp29 < tmp28 .len; tmp29 ++) {
  2756. byte aa = ((byte *) tmp28.data)[tmp29];
  2757.  
  2758. if ( aa == val ) {
  2759. /*if*/
  2760.  
  2761.  
  2762. return 1 ;
  2763.  
  2764. }
  2765. ;
  2766.  
  2767. }
  2768. ;
  2769.  
  2770.  
  2771. return 0 ;
  2772.  
  2773.  
  2774. }
  2775. string byte_str(byte c) {
  2776.  
  2777. string str= /* S INIT */ (string){ .len = 1 , .str = v_malloc ( 2 ) } ;
  2778.  
  2779. str .str [/*ptr*/ 0 ]/*rbyte 1*/ = c ;
  2780.  
  2781. str .str [/*ptr*/ 1 ]/*rbyte 1*/ = '\0' ;
  2782.  
  2783.  
  2784. return str ;
  2785.  
  2786.  
  2787. }
  2788. int string_is_utf8(string s) {
  2789.  
  2790. int faulty_bytes= 0 ;
  2791.  
  2792. int len= s .len ;
  2793.  
  2794. int i= 0 ;
  2795.  
  2796. byte * str = s.str;
  2797.  
  2798.  
  2799.  
  2800. while (i < len) {
  2801.  
  2802. if (str[i] <= 0x7F) /* 00..7F */ {
  2803.  
  2804. i += 1;
  2805.  
  2806. }
  2807.  
  2808. else if (str[i] >= 0xC2 && str[i] <= 0xDF) /* C2..DF 80..BF */ {
  2809.  
  2810. if (i + 1 < len) /* Expect a 2nd byte */ {
  2811.  
  2812. if (str[i + 1] < 0x80 || str[i + 1] > 0xBF) {
  2813.  
  2814. printf( "After a first byte between C2 and DF, expecting a 2nd byte between 80 and BF");
  2815.  
  2816. faulty_bytes = 2;
  2817.  
  2818. goto end;
  2819.  
  2820. }
  2821.  
  2822. }
  2823.  
  2824. else {
  2825.  
  2826. printf( "After a first byte between C2 and DF, expecting a 2nd byte.");
  2827.  
  2828. faulty_bytes = 1;
  2829.  
  2830. goto end;
  2831.  
  2832. }
  2833.  
  2834. i += 2;
  2835.  
  2836. }
  2837.  
  2838. else if (str[i] == 0xE0) /* E0 A0..BF 80..BF */ {
  2839.  
  2840. if (i + 2 < len) /* Expect a 2nd and 3rd byte */ {
  2841.  
  2842. if (str[i + 1] < 0xA0 || str[i + 1] > 0xBF) {
  2843.  
  2844. printf( "After a first byte of E0, expecting a 2nd byte between A0 and BF.");
  2845.  
  2846. faulty_bytes = 2;
  2847.  
  2848. goto end;
  2849.  
  2850. }
  2851.  
  2852. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  2853.  
  2854. printf( "After a first byte of E0, expecting a 3nd byte between 80 and BF.");
  2855.  
  2856. faulty_bytes = 3;
  2857.  
  2858. goto end;
  2859.  
  2860. }
  2861.  
  2862. }
  2863.  
  2864. else {
  2865.  
  2866. printf( "After a first byte of E0, expecting two following bytes.");
  2867.  
  2868. faulty_bytes = 1;
  2869.  
  2870. goto end;
  2871.  
  2872. }
  2873.  
  2874. i += 3;
  2875.  
  2876. }
  2877.  
  2878. else if (str[i] >= 0xE1 && str[i] <= 0xEC) /* E1..EC 80..BF 80..BF */ {
  2879.  
  2880. if (i + 2 < len) /* Expect a 2nd and 3rd byte */ {
  2881.  
  2882. if (str[i + 1] < 0x80 || str[i + 1] > 0xBF) {
  2883.  
  2884. printf( "After a first byte between E1 and EC, expecting the 2nd byte between 80 and BF.");
  2885.  
  2886. faulty_bytes = 2;
  2887.  
  2888. goto end;
  2889.  
  2890. }
  2891.  
  2892. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  2893.  
  2894. printf( "After a first byte between E1 and EC, expecting the 3rd byte between 80 and BF.");
  2895.  
  2896. faulty_bytes = 3;
  2897.  
  2898. goto end;
  2899.  
  2900. }
  2901.  
  2902. }
  2903.  
  2904. else {
  2905.  
  2906. printf( "After a first byte between E1 and EC, expecting two following bytes.");
  2907.  
  2908. faulty_bytes = 1;
  2909.  
  2910. goto end;
  2911.  
  2912. }
  2913.  
  2914. i += 3;
  2915.  
  2916. }
  2917.  
  2918. else if (str[i] == 0xED) /* ED 80..9F 80..BF */ {
  2919.  
  2920. if (i + 2 < len) /* Expect a 2nd and 3rd byte */ {
  2921.  
  2922. if (str[i + 1] < 0x80 || str[i + 1] > 0x9F) {
  2923.  
  2924. printf( "After a first byte of ED, expecting 2nd byte between 80 and 9F.");
  2925.  
  2926. faulty_bytes = 2;
  2927.  
  2928. goto end;
  2929.  
  2930. }
  2931.  
  2932. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  2933.  
  2934. printf( "After a first byte of ED, expecting 3rd byte between 80 and BF.");
  2935.  
  2936. faulty_bytes = 3;
  2937.  
  2938. goto end;
  2939.  
  2940. }
  2941.  
  2942. }
  2943.  
  2944. else {
  2945.  
  2946. printf( "After a first byte of ED, expecting two following bytes.");
  2947.  
  2948. faulty_bytes = 1;
  2949.  
  2950. goto end;
  2951.  
  2952. }
  2953.  
  2954. i += 3;
  2955.  
  2956. }
  2957.  
  2958. else if (str[i] >= 0xEE && str[i] <= 0xEF) /* EE..EF 80..BF 80..BF */ {
  2959.  
  2960. if (i + 2 < len) /* Expect a 2nd and 3rd byte */ {
  2961.  
  2962. if (str[i + 1] < 0x80 || str[i + 1] > 0xBF) {
  2963.  
  2964. printf( "After a first byte between EE and EF, expecting 2nd byte between 80 and BF.");
  2965.  
  2966. faulty_bytes = 2;
  2967.  
  2968. goto end;
  2969.  
  2970. }
  2971.  
  2972. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  2973.  
  2974. printf( "After a first byte between EE and EF, expecting 3rd byte between 80 and BF.");
  2975.  
  2976. faulty_bytes = 3;
  2977.  
  2978. goto end;
  2979.  
  2980. }
  2981.  
  2982. }
  2983.  
  2984. else {
  2985.  
  2986. printf( "After a first byte between EE and EF, two following bytes.");
  2987.  
  2988. faulty_bytes = 1;
  2989.  
  2990. goto end;
  2991.  
  2992. }
  2993.  
  2994. i += 3;
  2995.  
  2996. }
  2997.  
  2998. else if (str[i] == 0xF0) /* F0 90..BF 80..BF 80..BF */ {
  2999.  
  3000. if (i + 3 < len) /* Expect a 2nd, 3rd 3th byte */ {
  3001.  
  3002. if (str[i + 1] < 0x90 || str[i + 1] > 0xBF) {
  3003.  
  3004. printf( "After a first byte of F0, expecting 2nd byte between 90 and BF.");
  3005.  
  3006. faulty_bytes = 2;
  3007.  
  3008. goto end;
  3009.  
  3010. }
  3011.  
  3012. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  3013.  
  3014. printf( "After a first byte of F0, expecting 3rd byte between 80 and BF.");
  3015.  
  3016. faulty_bytes = 3;
  3017.  
  3018. goto end;
  3019.  
  3020. }
  3021.  
  3022. if (str[i + 3] < 0x80 || str[i + 3] > 0xBF) {
  3023.  
  3024. printf( "After a first byte of F0, expecting 4th byte between 80 and BF.");
  3025.  
  3026. faulty_bytes = 4;
  3027.  
  3028. goto end;
  3029.  
  3030. }
  3031.  
  3032. }
  3033.  
  3034. else {
  3035.  
  3036. printf( "After a first byte of F0, expecting three following bytes.");
  3037.  
  3038. faulty_bytes = 1;
  3039.  
  3040. goto end;
  3041.  
  3042. }
  3043.  
  3044. i += 4;
  3045.  
  3046. }
  3047.  
  3048. else if (str[i] >= 0xF1 && str[i] <= 0xF3) /* F1..F3 80..BF 80..BF 80..BF */ {
  3049.  
  3050. if (i + 3 < len) /* Expect a 2nd, 3rd 3th byte */ {
  3051.  
  3052. if (str[i + 1] < 0x80 || str[i + 1] > 0xBF) {
  3053.  
  3054. printf( "After a first byte of F1, F2, or F3, expecting a 2nd byte between 80 and BF.");
  3055.  
  3056. faulty_bytes = 2;
  3057.  
  3058. goto end;
  3059.  
  3060. }
  3061.  
  3062. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  3063.  
  3064. printf( "After a first byte of F1, F2, or F3, expecting a 3rd byte between 80 and BF.");
  3065.  
  3066. faulty_bytes = 3;
  3067.  
  3068. goto end;
  3069.  
  3070. }
  3071.  
  3072. if (str[i + 3] < 0x80 || str[i + 3] > 0xBF) {
  3073.  
  3074. printf( "After a first byte of F1, F2, or F3, expecting a 4th byte between 80 and BF.");
  3075.  
  3076. faulty_bytes = 4;
  3077.  
  3078. goto end;
  3079.  
  3080. }
  3081.  
  3082. }
  3083.  
  3084. else {
  3085.  
  3086. printf( "After a first byte of F1, F2, or F3, expecting three following bytes.");
  3087.  
  3088. faulty_bytes = 1;
  3089.  
  3090. goto end;
  3091.  
  3092. }
  3093.  
  3094. i += 4;
  3095.  
  3096. }
  3097.  
  3098. else if (str[i] == 0xF4) /* F4 80..8F 80..BF 80..BF */ {
  3099.  
  3100. if (i + 3 < len) /* Expect a 2nd, 3rd 3th byte */ {
  3101.  
  3102. if (str[i + 1] < 0x80 || str[i + 1] > 0x8F) {
  3103.  
  3104. printf( "After a first byte of F4, expecting 2nd byte between 80 and 8F.");
  3105.  
  3106. faulty_bytes = 2;
  3107.  
  3108. goto end;
  3109.  
  3110. }
  3111.  
  3112. if (str[i + 2] < 0x80 || str[i + 2] > 0xBF) {
  3113.  
  3114. printf( "After a first byte of F4, expecting 3rd byte between 80 and BF.");
  3115.  
  3116. faulty_bytes = 3;
  3117.  
  3118. goto end;
  3119.  
  3120. }
  3121.  
  3122. if (str[i + 3] < 0x80 || str[i + 3] > 0xBF) {
  3123.  
  3124. printf( "After a first byte of F4, expecting 4th byte between 80 and BF.");
  3125.  
  3126. faulty_bytes = 4;
  3127.  
  3128. goto end;
  3129.  
  3130. }
  3131.  
  3132. }
  3133.  
  3134. else {
  3135.  
  3136. printf( "After a first byte of F4, expecting three following bytes.");
  3137.  
  3138. faulty_bytes = 1;
  3139.  
  3140. goto end;
  3141.  
  3142. }
  3143.  
  3144. i += 4;
  3145.  
  3146. }
  3147.  
  3148. else {
  3149.  
  3150. printf( "i=%d Expecting bytes in the following ranges: 00..7F C2..F4.",
  3151.  
  3152. i);
  3153.  
  3154. faulty_bytes = 1;
  3155.  
  3156. goto end;
  3157.  
  3158. }
  3159.  
  3160. }
  3161.  
  3162.  
  3163.  
  3164. end: ;
  3165.  
  3166. bool ok= faulty_bytes == 0 ;
  3167.  
  3168. if ( ok ) {
  3169. /*if*/
  3170.  
  3171.  
  3172. return - 1 ;
  3173.  
  3174. }
  3175. ;
  3176.  
  3177. if ( ! ok ) {
  3178. /*if*/
  3179.  
  3180. println2 ( _STR("utf is bad dalen=%d KEK %.*s sdf", len, s.len, s.str) ) ;
  3181.  
  3182. }
  3183. ;
  3184.  
  3185.  
  3186. return i ;
  3187.  
  3188.  
  3189. }
  3190. string utf32_to_str(u32 code) {
  3191.  
  3192. byte* buffer= v_malloc ( 5 ) ;
  3193.  
  3194. if (code <= 0x7F) {
  3195.  
  3196. buffer[0] = code;
  3197.  
  3198. return tos(buffer, 1);
  3199.  
  3200. }
  3201.  
  3202. if (code <= 0x7FF) {
  3203.  
  3204. buffer[0] = 0xC0 | (code >> 6); /* 110xxxxx */
  3205.  
  3206. buffer[1] = 0x80 | (code & 0x3F); /* 10xxxxxx */
  3207.  
  3208. return tos(buffer, 2);
  3209.  
  3210. }
  3211.  
  3212. if (code <= 0xFFFF) {
  3213.  
  3214. buffer[0] = 0xE0 | (code >> 12); /* 1110xxxx */
  3215.  
  3216. buffer[1] = 0x80 | ((code >> 6) & 0x3F); /* 10xxxxxx */
  3217.  
  3218. buffer[2] = 0x80 | (code & 0x3F); /* 10xxxxxx */
  3219.  
  3220. return tos(buffer, 3);
  3221.  
  3222. }
  3223.  
  3224. if (code <= 0x10FFFF) {
  3225.  
  3226. buffer[0] = 0xF0 | (code >> 18); /* 11110xxx */
  3227.  
  3228. buffer[1] = 0x80 | ((code >> 12) & 0x3F); /* 10xxxxxx */
  3229.  
  3230. buffer[2] = 0x80 | ((code >> 6) & 0x3F); /* 10xxxxxx */
  3231.  
  3232. buffer[3] = 0x80 | (code & 0x3F); /* 10xxxxxx */
  3233.  
  3234. return tos(buffer, 4);
  3235.  
  3236. }
  3237.  
  3238.  
  3239. return tos2("") ;
  3240.  
  3241.  
  3242. }
  3243. string utf32_to_str_no_malloc(u32 code, void* buf) {
  3244.  
  3245. char* buffer = buf;
  3246.  
  3247. if (code <= 0x7F) {
  3248.  
  3249. buffer[0] = code;
  3250.  
  3251. return tos(buffer, 1);
  3252.  
  3253. }
  3254.  
  3255. if (code <= 0x7FF) {
  3256.  
  3257. buffer[0] = 0xC0 | (code >> 6); /* 110xxxxx */
  3258.  
  3259. buffer[1] = 0x80 | (code & 0x3F); /* 10xxxxxx */
  3260.  
  3261. return tos(buffer, 2);
  3262.  
  3263. }
  3264.  
  3265. if (code <= 0xFFFF) {
  3266.  
  3267. buffer[0] = 0xE0 | (code >> 12); /* 1110xxxx */
  3268.  
  3269. buffer[1] = 0x80 | ((code >> 6) & 0x3F); /* 10xxxxxx */
  3270.  
  3271. buffer[2] = 0x80 | (code & 0x3F); /* 10xxxxxx */
  3272.  
  3273. return tos(buffer, 3);
  3274.  
  3275. }
  3276.  
  3277. if (code <= 0x10FFFF) {
  3278.  
  3279. buffer[0] = 0xF0 | (code >> 18); /* 11110xxx */
  3280.  
  3281. buffer[1] = 0x80 | ((code >> 12) & 0x3F); /* 10xxxxxx */
  3282.  
  3283. buffer[2] = 0x80 | ((code >> 6) & 0x3F); /* 10xxxxxx */
  3284.  
  3285. buffer[3] = 0x80 | (code & 0x3F); /* 10xxxxxx */
  3286.  
  3287. return tos(buffer, 4);
  3288.  
  3289. }
  3290.  
  3291.  
  3292. return tos2("") ;
  3293.  
  3294.  
  3295. }
  3296. int string_utf32_code(string _rune) {
  3297.  
  3298. if ( _rune .len == 0 ) {
  3299. /*if*/
  3300.  
  3301.  
  3302. return 0 ;
  3303.  
  3304. }
  3305. ;
  3306.  
  3307. if ( _rune .len == 1 ) {
  3308. /*if*/
  3309.  
  3310.  
  3311. return (/*casttt*/ (int)( /*77*/ _rune .str[ 0 ]/*rbyte 0*/ ) ) ;
  3312.  
  3313. }
  3314. ;
  3315.  
  3316. byte b= (/*casttt*/ (byte)( /*77*/ (/*casttt*/ (int)( /*77*/ _rune .str[ 0 ]/*rbyte 0*/ ) ) ) ) ;
  3317.  
  3318. b <<= _rune.len;
  3319.  
  3320. int res= (/*casttt*/ (int)( /*77*/ b ) ) ;
  3321.  
  3322. int shift= 6 - _rune .len ;
  3323.  
  3324. for (
  3325. int i= 1 ; i < _rune .len ; i ++ ) {
  3326.  
  3327. int c= (/*casttt*/ (int)( /*77*/ _rune .str[ i ]/*rbyte 0*/ ) ) ;
  3328.  
  3329. res <<= shift;
  3330.  
  3331. res |= c & 0x3f;
  3332.  
  3333. shift = 6 ;
  3334.  
  3335. }
  3336. ;
  3337.  
  3338.  
  3339. return res ;
  3340.  
  3341.  
  3342. }
  3343. map new_map(int cap, int elm_size) {
  3344.  
  3345. map res= /* S INIT */ (map){ .element_size = elm_size , .entries = new_array(0, 1, sizeof(Entry)) , .is_sorted = 0 } ;
  3346.  
  3347.  
  3348. return res ;
  3349.  
  3350.  
  3351. }
  3352. Entry map_new_entry(map* m, string key, void* val) {
  3353.  
  3354. Entry new_e= /* S INIT */ (Entry){ .key = key , .val = v_malloc ( m ->element_size ) } ;
  3355.  
  3356. memcpy ( new_e .val , val , m ->element_size ) ;
  3357.  
  3358.  
  3359. return new_e ;
  3360.  
  3361.  
  3362. }
  3363. void map__set(map* m, string key, void* val) {
  3364.  
  3365. Entry e= map_new_entry(& /* ? */* m , key , val ) ;
  3366.  
  3367. for (
  3368. int i= 0 ; i < m ->entries .len ; i ++ ) {
  3369.  
  3370. Entry entry= ( *(Entry*) array__get( m ->entries , i) ) ;
  3371.  
  3372. if (string_eq( entry .key , key )/*8*/ ) {
  3373. /*if*/
  3374. Entry tmp8 = e;
  3375.  
  3376. array_set(&/*q*/ m ->entries , i , & tmp8) ;
  3377.  
  3378.  
  3379. return ;
  3380.  
  3381. }
  3382. ;
  3383.  
  3384. }
  3385. ;
  3386.  
  3387. _PUSH(& m ->entries , ( e ), tmp9, Entry) ;
  3388.  
  3389. m ->is_sorted = 0 ;
  3390.  
  3391.  
  3392. }
  3393. int volt_abs(int n) {
  3394.  
  3395. if ( n < 0 ) {
  3396. /*if*/
  3397.  
  3398.  
  3399. return - n ;
  3400.  
  3401. }
  3402. ;
  3403.  
  3404.  
  3405. return n ;
  3406.  
  3407.  
  3408. }
  3409. void map_bs(map m, string query, int start, int end, void* out) {
  3410.  
  3411. int mid= start + (/*lpar*/ (/*lpar*/ end - start ) / 2 ) ;
  3412.  
  3413. if ( end - start == 0 ) {
  3414. /*if*/
  3415.  
  3416. Entry last= ( *(Entry*) array__get( m .entries , end) ) ;
  3417.  
  3418. memcpy ( out , last .val , m .element_size ) ;
  3419.  
  3420.  
  3421. return ;
  3422.  
  3423. }
  3424. ;
  3425.  
  3426. if ( end - start == 1 ) {
  3427. /*if*/
  3428.  
  3429. Entry first= ( *(Entry*) array__get( m .entries , start) ) ;
  3430.  
  3431. memcpy ( out , first .val , m .element_size ) ;
  3432.  
  3433.  
  3434. return ;
  3435.  
  3436. }
  3437. ;
  3438.  
  3439. if ( mid >= m .entries .len ) {
  3440. /*if*/
  3441.  
  3442.  
  3443. return ;
  3444.  
  3445. }
  3446. ;
  3447.  
  3448. Entry mid_msg= ( *(Entry*) array__get( m .entries , mid) ) ;
  3449.  
  3450. if (string_lt( query , mid_msg .key )/*8*/ ) {
  3451. /*if*/
  3452.  
  3453. map_bs( m , query , start , mid , out ) ;
  3454.  
  3455.  
  3456. return ;
  3457.  
  3458. }
  3459. ;
  3460.  
  3461. map_bs( m , query , mid , end , out ) ;
  3462.  
  3463.  
  3464. }
  3465. int compare_map(Entry* a, Entry* b) {
  3466.  
  3467. if (string_lt( a ->key , b ->key )/*8*/ ) {
  3468. /*if*/
  3469.  
  3470.  
  3471. return - 1 ;
  3472.  
  3473. }
  3474. ;
  3475.  
  3476. if (string_gt( a ->key , b ->key )/*8*/ ) {
  3477. /*if*/
  3478.  
  3479.  
  3480. return 1 ;
  3481.  
  3482. }
  3483. ;
  3484.  
  3485.  
  3486. return 0 ;
  3487.  
  3488.  
  3489. }
  3490. void map_sort(map* m) {
  3491.  
  3492. array_sort_with_compare(& /* ? */ m ->entries , compare_map ) ;
  3493.  
  3494. m ->is_sorted = 1 ;
  3495.  
  3496.  
  3497. }
  3498. bool map_get(map m, string key, void* out) {
  3499.  
  3500. if ( m .is_sorted ) {
  3501. /*if*/
  3502.  
  3503. map_bs( m , key , 0 , m .entries .len , out ) ;
  3504.  
  3505.  
  3506. return 1 ;
  3507.  
  3508. }
  3509. ;
  3510.  
  3511. for (
  3512. int i= 0 ; i < m .entries .len ; i ++ ) {
  3513.  
  3514. Entry entry= ( *(Entry*) array__get( m .entries , i) ) ;
  3515.  
  3516. if (string_eq( entry .key , key )/*8*/ ) {
  3517. /*if*/
  3518.  
  3519. memcpy ( out , entry .val , m .element_size ) ;
  3520.  
  3521.  
  3522. return 1 ;
  3523.  
  3524. }
  3525. ;
  3526.  
  3527. }
  3528. ;
  3529.  
  3530.  
  3531. return 0 ;
  3532.  
  3533.  
  3534. }
  3535. void v_map_print(map m) {
  3536.  
  3537. println ( tos2("<<<<<<<<") ) ;
  3538.  
  3539. for (
  3540. int i= 0 ; i < m .entries .len ; i ++ ) {
  3541.  
  3542. }
  3543. ;
  3544.  
  3545. println ( tos2(">>>>>>>>>>") ) ;
  3546.  
  3547.  
  3548. }
  3549. void v_map_free(map m) {
  3550.  
  3551.  
  3552. }
  3553. string map_string_str(map_string m) {
  3554.  
  3555. if ( m .entries .len == 0 ) {
  3556. /*if*/
  3557.  
  3558.  
  3559. return tos2("{}") ;
  3560.  
  3561. }
  3562. ;
  3563.  
  3564. string s= tos2("{\n") ;
  3565.  
  3566. array_Entry tmp26 = m .entries;
  3567. ;
  3568. for (int tmp27 = 0; tmp27 < tmp26 .len; tmp27 ++) {
  3569. Entry entry = ((Entry *) tmp26.data)[tmp27];
  3570. string tmp28 = tos("", 0); bool tmp29 = map_get( m , entry .key, & tmp28);
  3571. if (!tmp29) tmp28 = tos("", 0);
  3572.  
  3573. string val= tmp28 ;
  3574.  
  3575. s = string_add(s, _STR(" \"%.*s\" => \"%.*s\"\n", entry .key.len, entry .key.str, val.len, val.str) ) ;
  3576.  
  3577. }
  3578. ;
  3579.  
  3580. s = string_add(s, tos2("}") ) ;
  3581.  
  3582.  
  3583. return s ;
  3584.  
  3585.  
  3586. }
  3587. smap new_smap() {
  3588.  
  3589. smap res= /* S INIT */ (smap){ .entries = new_array(0, 1, sizeof(Entry2)) , .is_sorted = 0 } ;
  3590.  
  3591.  
  3592. return res ;
  3593.  
  3594.  
  3595. }
  3596. void smap_set(smap* m, string key, string val) {
  3597.  
  3598. Entry2 e= /* S INIT */ (Entry2){ .key = key , .val = val } ;
  3599.  
  3600. _PUSH(& m ->entries , ( e ), tmp3, Entry2) ;
  3601.  
  3602.  
  3603. }
  3604. string smap_get(smap m, string key) {
  3605.  
  3606. if ( m .is_sorted ) {
  3607. /*if*/
  3608.  
  3609.  
  3610. return smap_bs( m , key , 0 , m .entries .len ) ;
  3611.  
  3612. }
  3613. ;
  3614.  
  3615. for (
  3616. int i= 0 ; i < m .entries .len ; i ++ ) {
  3617.  
  3618. Entry2 entry= ( *(Entry2*) array__get( m .entries , i) ) ;
  3619.  
  3620. if (string_eq( entry .key , key )/*8*/ ) {
  3621. /*if*/
  3622.  
  3623.  
  3624. return entry .val ;
  3625.  
  3626. }
  3627. ;
  3628.  
  3629. }
  3630. ;
  3631.  
  3632.  
  3633. return tos2("") ;
  3634.  
  3635.  
  3636. }
  3637. string smap_bs(smap m, string query, int start, int end) {
  3638.  
  3639. int mid= start + (/*lpar*/ (/*lpar*/ end - start ) / 2 ) ;
  3640.  
  3641. if ( end - start == 0 ) {
  3642. /*if*/
  3643.  
  3644. Entry2 last= ( *(Entry2*) array__get( m .entries , end) ) ;
  3645.  
  3646.  
  3647. return last .val ;
  3648.  
  3649. }
  3650. ;
  3651.  
  3652. if ( end - start == 1 ) {
  3653. /*if*/
  3654.  
  3655. Entry2 first= ( *(Entry2*) array__get( m .entries , start) ) ;
  3656.  
  3657.  
  3658. return first .val ;
  3659.  
  3660. }
  3661. ;
  3662.  
  3663. if ( mid >= m .entries .len ) {
  3664. /*if*/
  3665.  
  3666.  
  3667. return tos2("") ;
  3668.  
  3669. }
  3670. ;
  3671.  
  3672. Entry2 mid_msg= ( *(Entry2*) array__get( m .entries , mid) ) ;
  3673.  
  3674. if (string_lt( query , mid_msg .key )/*8*/ ) {
  3675. /*if*/
  3676.  
  3677.  
  3678. return smap_bs( m , query , start , mid ) ;
  3679.  
  3680. }
  3681. ;
  3682.  
  3683.  
  3684. return smap_bs( m , query , mid , end ) ;
  3685.  
  3686.  
  3687. }
  3688. int compare_smap(Entry2* a, Entry2* b) {
  3689.  
  3690. if (string_lt( a ->key , b ->key )/*8*/ ) {
  3691. /*if*/
  3692.  
  3693.  
  3694. return - 1 ;
  3695.  
  3696. }
  3697. ;
  3698.  
  3699. if (string_gt( a ->key , b ->key )/*8*/ ) {
  3700. /*if*/
  3701.  
  3702.  
  3703. return 1 ;
  3704.  
  3705. }
  3706. ;
  3707.  
  3708.  
  3709. return 0 ;
  3710.  
  3711.  
  3712. }
  3713. void smap_sort(smap* m) {
  3714.  
  3715. array_sort_with_compare(& /* ? */ m ->entries , compare_smap ) ;
  3716.  
  3717. m ->is_sorted = 1 ;
  3718.  
  3719.  
  3720. }
  3721. void v_smap_free(smap m) {
  3722.  
  3723.  
  3724. }
  3725. string smap_str(smap m) {
  3726.  
  3727. if ( m .entries .len == 0 ) {
  3728. /*if*/
  3729.  
  3730.  
  3731. return tos2("{}") ;
  3732.  
  3733. }
  3734. ;
  3735.  
  3736. string s= tos2("{\n") ;
  3737.  
  3738. array_Entry2 tmp19 = m .entries;
  3739. ;
  3740. for (int tmp20 = 0; tmp20 < tmp19 .len; tmp20 ++) {
  3741. Entry2 entry = ((Entry2 *) tmp19.data)[tmp20];
  3742.  
  3743. s = string_add(s, _STR(" \"%.*s\" => \"%.*s\"\n", entry .key.len, entry .key.str, entry .val.len, entry .val.str) ) ;
  3744.  
  3745. }
  3746. ;
  3747.  
  3748. s = string_add(s, tos2("}") ) ;
  3749.  
  3750.  
  3751. return s ;
  3752.  
  3753.  
  3754. }
  3755. StringBuilder new_string_builder(int initial_size) {
  3756.  
  3757.  
  3758. return /* S INIT */ (StringBuilder){ .buf = new_array ( 0 , initial_size , sizeof( byte) ) , .len = 0 } ;
  3759.  
  3760.  
  3761. }
  3762. void StringBuilder_write(StringBuilder* b, string s) {
  3763.  
  3764. array__push_many(& /* ? */ b ->buf , s .str , s .len ) ;
  3765.  
  3766. b ->len += s .len ;
  3767.  
  3768.  
  3769. }
  3770. void StringBuilder_writeln(StringBuilder* b, string s) {
  3771.  
  3772. array__push_many(& /* ? */ b ->buf , s .str , s .len ) ;
  3773.  
  3774. _PUSH(& b ->buf , ( '\n' ), tmp1, byte) ;
  3775.  
  3776. b ->len += s .len + 1 ;
  3777.  
  3778.  
  3779. }
  3780. string StringBuilder_str(StringBuilder b) {
  3781.  
  3782.  
  3783. return tos ( b .buf .data , b .len ) ;
  3784.  
  3785.  
  3786. }
  3787. void StringBuilder_cut(StringBuilder b, int n) {
  3788.  
  3789. b .len -= n ;
  3790.  
  3791.  
  3792. }
  3793. array_string os__init_os_args(int argc, void* c) {
  3794.  
  3795. array_string args=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  3796.  
  3797. char** argv = (char**) c;
  3798.  
  3799. for (
  3800. int i= 0 ; i < argc ; i ++ ) {
  3801.  
  3802. string arg= tos2("") ;
  3803.  
  3804. arg = tos(argv[i], strlen(argv[i]));
  3805.  
  3806. _PUSH(& args , ( arg ), tmp4, string) ;
  3807.  
  3808. }
  3809. ;
  3810.  
  3811. os__args = args;
  3812.  
  3813.  
  3814. return args ;
  3815.  
  3816.  
  3817. }
  3818. void os__parse_windows_cmd_line(byte* cmd) {
  3819.  
  3820. string s= tos2 ( cmd ) ;
  3821.  
  3822. array_string vals= string_split( s , tos2(" ") ) ;
  3823.  
  3824. println (array_string_str( vals ) ) ;
  3825.  
  3826. os__args = vals;
  3827.  
  3828.  
  3829. }
  3830. string os__read_file(string path) {
  3831.  
  3832. string res= tos2("") ;
  3833.  
  3834. FILE *f = fopen(path.str, "r");
  3835.  
  3836. if (!f) return tos("", 0);
  3837.  
  3838. fseek(f, 0, SEEK_END);
  3839.  
  3840. long fsize = ftell(f);
  3841.  
  3842. rewind(f);
  3843.  
  3844. char *string = malloc(fsize + 1);
  3845.  
  3846. fread(string, fsize, 1, f);
  3847.  
  3848. fclose(f);
  3849.  
  3850. string[fsize] = 0;
  3851.  
  3852. res = tos(string, fsize);
  3853.  
  3854.  
  3855. return res ;
  3856.  
  3857.  
  3858. }
  3859. string os__File_read_rune(os__File f) {
  3860.  
  3861. if (!f.cfile) return tos("", 0);
  3862.  
  3863. byte* c= v_malloc ( 1 ) ;
  3864.  
  3865. fread ( c , 1 , 1 , f .cfile ) ;
  3866.  
  3867.  
  3868. return tos ( c , 1 ) ;
  3869.  
  3870.  
  3871. }
  3872. int os__file_size(string path) {
  3873.  
  3874. struct stat s;
  3875.  
  3876. stat(path.str, &s);
  3877.  
  3878. return s.st_size;
  3879.  
  3880. FILE *f = fopen(path.str, "r");
  3881.  
  3882. if (!f) return 0;
  3883.  
  3884. fseek(f, 0, SEEK_END);
  3885.  
  3886. long fsize = ftell(f);
  3887.  
  3888. rewind(f);
  3889.  
  3890. return fsize;
  3891.  
  3892.  
  3893. return 0 ;
  3894.  
  3895.  
  3896. }
  3897. int os__file_last_mod_unix(string path) {
  3898.  
  3899. struct stat attr;
  3900.  
  3901. stat(path.str, &attr);
  3902.  
  3903. return attr.st_mtime ;
  3904.  
  3905.  
  3906. return 0 ;
  3907.  
  3908.  
  3909. }
  3910. array_string os__read_lines(string path) {
  3911.  
  3912.  
  3913. return os__read_file_lines ( path ) ;
  3914.  
  3915.  
  3916. }
  3917. array_string os__read_file_into_lines(string path) {
  3918.  
  3919.  
  3920. return os__read_file_lines ( path ) ;
  3921.  
  3922.  
  3923. }
  3924. array_ustring os__read_file_into_ulines(string path) {
  3925.  
  3926. array_string lines= os__read_file_into_lines ( path ) ;
  3927.  
  3928. array_ustring ulines=/*0*/ new_array_from_c_array(0, 0, sizeof(ustring), (ustring[]) { }) ;
  3929.  
  3930. array_string tmp11 = lines;
  3931. ;
  3932. for (int tmp12 = 0; tmp12 < tmp11 .len; tmp12 ++) {
  3933. string myline = ((string *) tmp11.data)[tmp12];
  3934.  
  3935. _PUSH(& ulines , ( string_ustring( myline ) ), tmp13, ustring) ;
  3936.  
  3937. }
  3938. ;
  3939.  
  3940.  
  3941. return ulines ;
  3942.  
  3943.  
  3944. }
  3945. array_string os__read_file_lines(string path) {
  3946.  
  3947. array_string res=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  3948.  
  3949. char buf[os__BUF_SIZE];
  3950.  
  3951. FILE *fp = fopen(path.str, "rb");
  3952.  
  3953. if (!fp)
  3954.  
  3955. {
  3956.  
  3957. println ( _STR("failed to open file \"%.*s\"", path.len, path.str) ) ;
  3958.  
  3959.  
  3960. return res ;
  3961.  
  3962. }
  3963.  
  3964. while (fgets(buf, os__BUF_SIZE, fp) != NULL)
  3965.  
  3966. {
  3967.  
  3968. string val= tos2("") ;
  3969.  
  3970. buf[strlen(buf) - 1] = '\0'; // eat the newline fgets() stores
  3971.  
  3972. #ifdef windows
  3973.  
  3974. if (buf[strlen(buf)-2] == 13)
  3975.  
  3976. buf[strlen(buf) - 2] = '\0'; // eat the newline fgets() stores
  3977.  
  3978. #endif
  3979.  
  3980. val=tos_clone(buf) ;
  3981.  
  3982. #ifdef windows
  3983.  
  3984. if ( string_at( val , val .len - 1) == 13 ) {
  3985. /*if*/
  3986.  
  3987. }
  3988. ;
  3989.  
  3990. #endif
  3991.  
  3992. _PUSH(& res , ( val ), tmp18, string) ;
  3993.  
  3994. }
  3995.  
  3996. fclose(fp);
  3997.  
  3998.  
  3999. return res ;
  4000.  
  4001.  
  4002. }
  4003. void os__append_to_file(string file, string s) {
  4004.  
  4005. FILE* fp = fopen(file.str, "a");
  4006.  
  4007. fputs(s.str, fp);
  4008.  
  4009. fputs("\n", fp);
  4010.  
  4011. fclose(fp);
  4012.  
  4013.  
  4014. }
  4015. os__File os__open(string path) {
  4016.  
  4017.  
  4018. return os__open_file ( path ) ;
  4019.  
  4020.  
  4021. }
  4022. os__File os__open_file(string file) {
  4023.  
  4024.  
  4025. return os__create_file2 ( file , tos2("r") ) ;
  4026.  
  4027.  
  4028. }
  4029. os__File os__create(string path) {
  4030.  
  4031.  
  4032. return os__create_file ( path ) ;
  4033.  
  4034.  
  4035. }
  4036. os__File os__open_append(string path) {
  4037.  
  4038.  
  4039. return os__create_file ( path ) ;
  4040.  
  4041.  
  4042. }
  4043. os__File os__create_file(string file) {
  4044.  
  4045.  
  4046. return os__create_file2 ( file , tos2("w") ) ;
  4047.  
  4048.  
  4049. }
  4050. os__File os__create_file_a(string file) {
  4051.  
  4052.  
  4053. return os__create_file2 ( file , tos2("a") ) ;
  4054.  
  4055.  
  4056. }
  4057. os__File os__open_file_a(string file) {
  4058.  
  4059.  
  4060. return os__create_file2 ( file , tos2("a") ) ;
  4061.  
  4062.  
  4063. }
  4064. os__File os__create_file2(string file, string mode) {
  4065.  
  4066. os__File res= /* S INIT */ (os__File){ .cfile = fopen ( string_cstr( file ) , string_cstr( mode ) ) } ;
  4067.  
  4068. if ( isnil ( res .cfile ) ) {
  4069. /*if*/
  4070.  
  4071. println ( _STR("coudlnt create file \"%.*s\"", file.len, file.str) ) ;
  4072.  
  4073. }
  4074. ;
  4075.  
  4076.  
  4077. return res ;
  4078.  
  4079.  
  4080. }
  4081. void os__File_append(os__File f, string s) {
  4082.  
  4083. string ss= string_clone( s ) ;
  4084.  
  4085. fputs ( string_cstr( ss ) , f .cfile ) ;
  4086.  
  4087.  
  4088. }
  4089. void os__File_write(os__File f, void* data, int size) {
  4090.  
  4091. fwrite ( data , 1 , size , f .cfile ) ;
  4092.  
  4093.  
  4094. }
  4095. void os__File_write_at(os__File f, void* data, int size, int pos) {
  4096.  
  4097. fseek ( f .cfile , pos , SEEK_SET ) ;
  4098.  
  4099. fwrite ( data , 1 , size , f .cfile ) ;
  4100.  
  4101. fseek ( f .cfile , 0 , SEEK_END ) ;
  4102.  
  4103.  
  4104. }
  4105. void os__File_appendln(os__File f, string s) {
  4106.  
  4107. fputs ( string_cstr( s ) , f .cfile ) ;
  4108.  
  4109. fputs ( "\n" , f .cfile ) ;
  4110.  
  4111.  
  4112. }
  4113. void os__File_close(os__File f) {
  4114.  
  4115. fclose ( f .cfile ) ;
  4116.  
  4117.  
  4118. }
  4119. void os__close_file(os__FILE* fp) {
  4120.  
  4121. #ifdef windows
  4122.  
  4123. #endif
  4124. ;
  4125.  
  4126. if (fp)
  4127.  
  4128. fclose ( fp ) ;
  4129.  
  4130.  
  4131. }
  4132. int os__system2(string cmd) {
  4133.  
  4134. string cstr= string_clone( cmd ) ;
  4135.  
  4136. int ret= (/*casttt*/ (int)( /*77*/ system ( string_cstr( cstr ) ) ) ) ;
  4137.  
  4138. if ( ret == - 1 ) {
  4139. /*if*/
  4140.  
  4141. os__print_c_errno ( ) ;
  4142.  
  4143. }
  4144. ;
  4145.  
  4146.  
  4147. return ret ;
  4148.  
  4149.  
  4150. }
  4151. os__FILE* os__popen(string path) {
  4152.  
  4153. byte* cpath= string_cstr( path ) ;
  4154.  
  4155. #ifdef windows
  4156.  
  4157.  
  4158. return _popen ( cpath , "r" ) ;
  4159.  
  4160. ;
  4161.  
  4162. #else
  4163.  
  4164.  
  4165. return popen ( cpath , "r" ) ;
  4166.  
  4167. #endif
  4168. ;
  4169.  
  4170.  
  4171. }
  4172. string os__system(string cmd) {
  4173.  
  4174. string res= tos2("") ;
  4175.  
  4176. string ss= _STR("%.*s 2>&1", cmd.len, cmd.str) ;
  4177.  
  4178. int _= 0 ;
  4179.  
  4180. os__FILE* f= os__popen ( ss ) ;
  4181.  
  4182. if ( isnil ( f ) ) {
  4183. /*if*/
  4184.  
  4185. println ( _STR("popen %.*s failed", cmd.len, cmd.str) ) ;
  4186.  
  4187. }
  4188. ;
  4189.  
  4190.  
  4191. char buf[MAX];
  4192.  
  4193. while (fgets(buf, MAX, f) != NULL) {
  4194.  
  4195. res = string_add(res, tos(buf, strlen(buf)));
  4196.  
  4197. }
  4198.  
  4199.  
  4200. return string_trim_space( res ) ;
  4201.  
  4202.  
  4203. }
  4204. array_string os__system_into_lines(string s) {
  4205.  
  4206. array_string res=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  4207.  
  4208. string cmd= _STR("%.*s 2>&1", s.len, s.str) ;
  4209.  
  4210. #ifdef windows
  4211.  
  4212. FILE* f = _popen(cmd.str, "r");
  4213.  
  4214. #else
  4215.  
  4216. FILE* f = popen(cmd.str, "r");
  4217.  
  4218. #endif
  4219.  
  4220.  
  4221. char * buf = malloc(sizeof(char) * MAX);
  4222.  
  4223. while (fgets(buf, MAX, f) != NULL)
  4224.  
  4225. {
  4226.  
  4227. string val= tos2("") ;
  4228.  
  4229. buf[strlen(buf) - 1] = '\0'; // eat the newline fgets() stores
  4230.  
  4231. val=tos_clone(buf);
  4232.  
  4233. _PUSH(& res , ( val ), tmp31, string) ;
  4234.  
  4235. }
  4236.  
  4237.  
  4238. return res ;
  4239.  
  4240.  
  4241. }
  4242. string os__getenv(string key) {
  4243.  
  4244. void* s= getenv ( string_cstr( key ) ) ;
  4245.  
  4246. if ( isnil ( s ) ) {
  4247. /*if*/
  4248.  
  4249.  
  4250. return tos2("") ;
  4251.  
  4252. }
  4253. ;
  4254.  
  4255.  
  4256. return tos2 ( s ) ;
  4257.  
  4258.  
  4259. }
  4260. void os__exit(string reason) {
  4261.  
  4262. println2 ( _STR("exit(): %.*s", reason.len, reason.str) ) ;
  4263.  
  4264. os__log ( reason ) ;
  4265.  
  4266. exit ( 0 ) ;
  4267.  
  4268.  
  4269. }
  4270. void os__exit1(string reason) {
  4271.  
  4272. println2 ( _STR("exit(): %.*s", reason.len, reason.str) ) ;
  4273.  
  4274. exit ( 1 ) ;
  4275.  
  4276.  
  4277. }
  4278. bool os__file_exists(string path) {
  4279.  
  4280. bool res= 0 ;
  4281.  
  4282. #ifdef windows
  4283.  
  4284. res = _access( path.str, 0 ) != -1 ;
  4285.  
  4286. #else
  4287.  
  4288. res = access( path.str, 0 ) != -1 ;
  4289.  
  4290. #endif
  4291.  
  4292.  
  4293. return res ;
  4294.  
  4295.  
  4296. }
  4297. void os__mkdir(string path) {
  4298.  
  4299. #ifdef windows
  4300.  
  4301. path = string_replace( path , tos2("/") , tos2("\\") ) ;
  4302.  
  4303. CreateDirectory ( string_cstr( path ) , 0 ) ;
  4304.  
  4305. ;
  4306.  
  4307. #else
  4308.  
  4309. println ( _STR("AAAAAAAA $$ \"%.*s\"", path.len, path.str) ) ;
  4310.  
  4311. mkdir ( string_cstr( path ) , 511 ) ;
  4312.  
  4313. #endif
  4314. ;
  4315.  
  4316.  
  4317. }
  4318. void os__rm(string path) {
  4319.  
  4320. #ifdef windows
  4321.  
  4322. ;
  4323.  
  4324. #else
  4325.  
  4326. remove ( string_cstr( path ) ) ;
  4327.  
  4328. #endif
  4329. ;
  4330.  
  4331.  
  4332. }
  4333. void os__rmdir(string path, string guard) {
  4334.  
  4335. if ( ! string_contains( path , guard ) ) {
  4336. /*if*/
  4337.  
  4338. println ( _STR("rmdir canceled because the path doesnt contain %.*s", guard.len, guard.str) ) ;
  4339.  
  4340.  
  4341. return ;
  4342.  
  4343. }
  4344. ;
  4345.  
  4346. println2 ( _STR("rmdir \"%.*s\"", path.len, path.str) ) ;
  4347.  
  4348. #ifndef windows
  4349.  
  4350. os__system ( _STR("rm -rf \"%.*s\"", path.len, path.str) ) ;
  4351.  
  4352. #else
  4353.  
  4354. os__system ( _STR("rmdir /s /q \"%.*s\"", path.len, path.str) ) ;
  4355.  
  4356. #endif
  4357.  
  4358.  
  4359. }
  4360. void os__unzip(string path, string out) {
  4361.  
  4362. #ifdef windows
  4363.  
  4364. char *s="powershell.exe -nologo -noprofile -command \"& { Add-Type -A 'System.IO.Compression.FileSystem'; [IO.Compression.ZipFile]::ExtractToDirectory('PATH', 'OUT'); }\" ";
  4365.  
  4366. string cmd= tos2("") ;
  4367.  
  4368. cmd = tos(s, strlen(s));
  4369.  
  4370. cmd = string_replace( cmd , tos2("PATH") , path ) ;
  4371.  
  4372. cmd = string_replace( cmd , tos2("OUT") , out ) ;
  4373.  
  4374. os__system ( cmd ) ;
  4375.  
  4376. ;
  4377.  
  4378. #else
  4379.  
  4380. os__system ( _STR("unzip -o -d \"%.*s\" \"%.*s\"", out.len, out.str, path.len, path.str) ) ;
  4381.  
  4382. #endif
  4383. ;
  4384.  
  4385.  
  4386. }
  4387. void os__print_c_errno() {
  4388.  
  4389. printf("errno=%d err='%s'\n", errno, strerror(errno));
  4390.  
  4391.  
  4392. }
  4393. string os__basedir(string path) {
  4394.  
  4395. int pos= string_last_index( path , tos2("/") ) ;
  4396.  
  4397. if ( pos == - 1 ) {
  4398. /*if*/
  4399.  
  4400.  
  4401. return path ;
  4402.  
  4403. }
  4404. ;
  4405.  
  4406.  
  4407. return string_left( path , pos + 1 ) ;
  4408.  
  4409.  
  4410. }
  4411. string os__filename(string path) {
  4412.  
  4413.  
  4414. return string_all_after( path , tos2("/") ) ;
  4415.  
  4416.  
  4417. }
  4418. string os__get_line() {
  4419.  
  4420. int max= 256 ;
  4421.  
  4422. byte* buf= v_malloc ( max ) ;
  4423.  
  4424. int nr_chars= getline ( & /*vvar*/ buf , & /*vvar*/ max , stdin ) ;
  4425.  
  4426. if ( nr_chars == 0 ) {
  4427. /*if*/
  4428.  
  4429.  
  4430. return tos2("") ;
  4431.  
  4432. }
  4433. ;
  4434.  
  4435.  
  4436. return tos ( buf , nr_chars - 1 ) ;
  4437.  
  4438.  
  4439. }
  4440. string os__user_os() {
  4441.  
  4442. #ifdef linux
  4443.  
  4444.  
  4445. return tos2("linux") ;
  4446.  
  4447. #endif
  4448. ;
  4449.  
  4450. #ifdef mac
  4451.  
  4452.  
  4453. return tos2("mac") ;
  4454.  
  4455. #endif
  4456. ;
  4457.  
  4458. #ifdef windows
  4459.  
  4460.  
  4461. return tos2("windows") ;
  4462.  
  4463. #endif
  4464. ;
  4465.  
  4466.  
  4467. return tos2("unknown") ;
  4468.  
  4469.  
  4470. }
  4471. string os__home_dir() {
  4472.  
  4473. string home= os__getenv ( tos2("HOME") ) ;
  4474.  
  4475. #ifdef windows
  4476.  
  4477. home = os__getenv ( tos2("HOMEDRIVE") ) ;
  4478.  
  4479. home = string_add(home, os__getenv ( tos2("HOMEPATH") ) ) ;
  4480.  
  4481. #endif
  4482. ;
  4483.  
  4484. home = string_add(home, tos2("/") ) ;
  4485.  
  4486.  
  4487. return home ;
  4488.  
  4489.  
  4490. }
  4491. void os__write_file(string path, string text) {
  4492.  
  4493. os__File f= os__create ( path ) ;
  4494.  
  4495. os__File_appendln( f , text ) ;
  4496.  
  4497. os__File_close( f ) ;
  4498.  
  4499.  
  4500. }
  4501. void os__on_segfault(void* f) {
  4502.  
  4503. #ifdef windows
  4504.  
  4505.  
  4506. return ;
  4507.  
  4508. #endif
  4509.  
  4510. #ifdef mac
  4511.  
  4512. struct sigaction sa;
  4513.  
  4514. memset(&sa, 0, sizeof(struct sigaction));
  4515.  
  4516. sigemptyset(&sa.sa_mask);
  4517.  
  4518. sa.sa_sigaction = f;
  4519.  
  4520. sa.sa_flags = SA_SIGINFO;
  4521.  
  4522. sigaction(SIGSEGV, &sa, 0);
  4523.  
  4524. #endif
  4525.  
  4526.  
  4527. }
  4528. void os__log(string s) {
  4529.  
  4530.  
  4531. }
  4532. bool os__is_dir(string path) {
  4533.  
  4534. struct stat statbuf;
  4535.  
  4536. byte* cstr= string_cstr( path ) ;
  4537.  
  4538. if (stat(cstr, &statbuf) != 0)
  4539.  
  4540. {
  4541.  
  4542.  
  4543. return 0 ;
  4544.  
  4545. }
  4546.  
  4547. return S_ISDIR(statbuf.st_mode);
  4548.  
  4549.  
  4550. return 0 ;
  4551.  
  4552.  
  4553. }
  4554. void os__chdir(string path) {
  4555.  
  4556. chdir ( string_cstr( path ) ) ;
  4557.  
  4558.  
  4559. }
  4560. string os__getwd() {
  4561.  
  4562. byte* cwd= v_malloc ( 1024 ) ;
  4563.  
  4564. if (getcwd(cwd, 1024)) return tos2(cwd);
  4565.  
  4566.  
  4567. return tos2("") ;
  4568.  
  4569.  
  4570. }
  4571. array_string os__ls(string path) {
  4572.  
  4573. array_string res=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  4574.  
  4575. DIR *dir;
  4576.  
  4577. struct dirent *ent;
  4578.  
  4579. if ((dir = opendir (path.str)) == NULL)
  4580.  
  4581. {
  4582.  
  4583. println ( _STR("ls() couldnt open dir \"%.*s\"", path.len, path.str) ) ;
  4584.  
  4585. os__print_c_errno ( ) ;
  4586.  
  4587.  
  4588. return res ;
  4589.  
  4590. }
  4591.  
  4592. while ((ent = readdir (dir)) != NULL) {
  4593.  
  4594. string name= tos2("") ;
  4595.  
  4596. name = tos_clone(ent->d_name);//, strlen(ent->d_name));
  4597.  
  4598. if (string_ne( name , tos2(".") )/*8*/ && string_ne( name , tos2("..") )/*8*/ && string_ne( name , tos2("") )/*8*/ ) {
  4599. /*if*/
  4600.  
  4601. _PUSH(& res , ( name ), tmp5, string) ;
  4602.  
  4603. }
  4604. ;
  4605.  
  4606. }
  4607.  
  4608. closedir (dir);
  4609.  
  4610.  
  4611. return res ;
  4612.  
  4613.  
  4614. }
  4615. void os__print_backtrace() {
  4616.  
  4617. void *buffer[100];
  4618.  
  4619. int nptrs= 0 ;
  4620.  
  4621. nptrs = backtrace(buffer, 100);
  4622.  
  4623. printf("%d!!\n", nptrs);
  4624.  
  4625. backtrace_symbols_fd(buffer, nptrs, STDOUT_FILENO) ;
  4626.  
  4627.  
  4628. }
  4629. int main(int argc, char** argv) {
  4630. init_consts();
  4631. os__init_os_args(argc, argv);
  4632.  
  4633. string path= tos2("cinderella.txt") ;
  4634.  
  4635. if ( os__args .len != 2 ) {
  4636. /*if*/
  4637.  
  4638. println ( tos2("usage: word_counter [text_file]") ) ;
  4639.  
  4640. println ( _STR("using %.*s", path.len, path.str) ) ;
  4641.  
  4642. }
  4643. else {
  4644. /*else if*/
  4645.  
  4646. path = ( *(string*) array__get( os__args , 1) ) ;
  4647.  
  4648. }
  4649. ;
  4650.  
  4651. array_string lines= os__read_file_lines ( string_trim_space( path ) ) ;
  4652.  
  4653. map_int m= new_map(1, sizeof(int)) ;
  4654.  
  4655. array_string tmp6 = lines;
  4656. ;
  4657. for (int tmp7 = 0; tmp7 < tmp6 .len; tmp7 ++) {
  4658. string line = ((string *) tmp6.data)[tmp7];
  4659.  
  4660. array_string words= string_split( string_to_lower( line ) , tos2(" ") ) ;
  4661.  
  4662. array_string tmp9 = words;
  4663. ;
  4664. for (int tmp10 = 0; tmp10 < tmp9 .len; tmp10 ++) {
  4665. string word = ((string *) tmp9.data)[tmp10];
  4666.  
  4667. string key= filter_word ( word ) ;
  4668.  
  4669. if (string_eq( key , tos2("") )/*8*/ ) {
  4670. /*if*/
  4671.  
  4672. continue
  4673. ;
  4674.  
  4675. }
  4676. ;
  4677. int tmp12 = 0; bool tmp13 = map_get( m , key, & tmp12);
  4678. int tmp14 = tmp12 + 1;
  4679.  
  4680. map__set(& m , key , & tmp14) ;
  4681.  
  4682. }
  4683. ;
  4684.  
  4685. }
  4686. ;
  4687.  
  4688. array_string keys=/*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }) ;
  4689.  
  4690. array_Entry tmp16 = m .entries;
  4691. ;
  4692. for (int tmp17 = 0; tmp17 < tmp16 .len; tmp17 ++) {
  4693. Entry e = ((Entry *) tmp16.data)[tmp17];
  4694.  
  4695. _PUSH(& keys , ( e .key ), tmp18, string) ;
  4696.  
  4697. }
  4698. ;
  4699.  
  4700. array_string_sort(& /* ? */ keys ) ;
  4701.  
  4702. array_string tmp19 = keys;
  4703. ;
  4704. for (int tmp20 = 0; tmp20 < tmp19 .len; tmp20 ++) {
  4705. string key = ((string *) tmp19.data)[tmp20];
  4706. int tmp21 = 0; bool tmp22 = map_get( m , key, & tmp21);
  4707.  
  4708. int val= tmp21 ;
  4709.  
  4710. println ( _STR("%.*s => %d", key.len, key.str, val) ) ;
  4711.  
  4712. }
  4713. ;
  4714.  
  4715.  
  4716. }
  4717. string filter_word(string word) {
  4718.  
  4719. if (string_eq( word , tos2("") )/*8*/ || string_eq( word , tos2(" ") )/*8*/ ) {
  4720. /*if*/
  4721.  
  4722.  
  4723. return tos2("") ;
  4724.  
  4725. }
  4726. ;
  4727.  
  4728. int i= 0 ;
  4729.  
  4730. while ( i < word .len && ! is_letter ( string_at( word , i) ) ) {
  4731.  
  4732. i ++ ;
  4733.  
  4734. }
  4735. ;
  4736.  
  4737. int start= i ;
  4738.  
  4739. while ( i < word .len && is_letter ( string_at( word , i) ) ) {
  4740.  
  4741. i ++ ;
  4742.  
  4743. }
  4744. ;
  4745.  
  4746. int end= i ;
  4747.  
  4748.  
  4749. return string_substr( word , start , end ) ;
  4750.  
  4751.  
  4752. }
  4753. bool is_letter(byte c) {
  4754.  
  4755.  
  4756. return byte_is_letter( c ) ;
  4757.  
  4758.  
  4759. }
  4760. void init_consts() { g_str_buf=malloc(1000); os__args = /*0*/ new_array_from_c_array(0, 0, sizeof(string), (string[]) { }); }
  4761.  
  4762. string _STR(const char *fmt, ...) {
  4763. va_list argptr;
  4764. va_start(argptr, fmt);
  4765. size_t len = vsnprintf(0, 0, fmt, argptr) + 1;
  4766. va_end(argptr);
  4767. byte* buf = malloc(len);
  4768. va_start(argptr, fmt);
  4769. vsprintf(buf, fmt, argptr);
  4770. va_end(argptr);
  4771. #ifdef DEBUG_ALLOC
  4772. puts("_STR:");
  4773. puts(buf);
  4774. #endif
  4775. return tos2(buf);
  4776. }
  4777.  
  4778. string _STR_TMP(const char *fmt, ...) {
  4779. va_list argptr;
  4780. va_start(argptr, fmt);
  4781. size_t len = vsnprintf(0, 0, fmt, argptr) + 1;
  4782. va_end(argptr);
  4783. va_start(argptr, fmt);
  4784. vsprintf(g_str_buf, fmt, argptr);
  4785. va_end(argptr);
  4786. #ifdef DEBUG_ALLOC
  4787. //puts("_STR_TMP:");
  4788. //puts(g_str_buf);
  4789. #endif
  4790. return tos2(g_str_buf);
  4791. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement