diff options
author | Denys Vlasenko <vda.linux@googlemail.com> | 2018-12-20 20:34:09 +0100 |
---|---|---|
committer | Denys Vlasenko <vda.linux@googlemail.com> | 2018-12-20 20:34:09 +0100 |
commit | 44a99ca61716f9846756c3d0cd434bfe8192339e (patch) | |
tree | 4e39c7c272aea2ac92620d8759a8bd98635b0cf8 /miscutils | |
parent | 5acd14ba5b911aff28cb259cabdb84c5f8233e55 (diff) | |
download | busybox-w32-44a99ca61716f9846756c3d0cd434bfe8192339e.tar.gz busybox-w32-44a99ca61716f9846756c3d0cd434bfe8192339e.tar.bz2 busybox-w32-44a99ca61716f9846756c3d0cd434bfe8192339e.zip |
bc: "dc only" config does not need G.prog.fn_map
function old new delta
bc_program_add_fn - 43 +43
bc_vm_init 655 675 +20
bc_program_addFunc 138 118 -20
zdc_parse_expr 658 635 -23
zdc_program_asciify 447 407 -40
------------------------------------------------------------------------------
(add/remove: 1/0 grow/shrink: 1/3 up/down: 63/-83) Total: -20 bytes
text data bss dec hex filename
984739 489 7312 992540 f251c busybox_old
984712 489 7312 992513 f2501 busybox_unstripped
Signed-off-by: Denys Vlasenko <vda.linux@googlemail.com>
Diffstat (limited to 'miscutils')
-rw-r--r-- | miscutils/bc.c | 92 |
1 files changed, 56 insertions, 36 deletions
diff --git a/miscutils/bc.c b/miscutils/bc.c index 1e2ca8b83..e05191717 100644 --- a/miscutils/bc.c +++ b/miscutils/bc.c | |||
@@ -686,7 +686,7 @@ typedef struct BcProgram { | |||
686 | BcVec exestack; | 686 | BcVec exestack; |
687 | 687 | ||
688 | BcVec fns; | 688 | BcVec fns; |
689 | BcVec fn_map; //TODO: dc does not need this, its 'functions' are anonynomous (have no names) | 689 | IF_BC(BcVec fn_map;) |
690 | 690 | ||
691 | BcVec vars; | 691 | BcVec vars; |
692 | BcVec var_map; | 692 | BcVec var_map; |
@@ -3606,12 +3606,23 @@ static void bc_parse_create(BcParse *p, size_t fidx) | |||
3606 | p->func = bc_program_func(fidx); | 3606 | p->func = bc_program_func(fidx); |
3607 | } | 3607 | } |
3608 | 3608 | ||
3609 | static size_t bc_program_add_fn(void) | ||
3610 | { | ||
3611 | size_t idx; | ||
3612 | BcFunc f; | ||
3613 | bc_func_init(&f); | ||
3614 | idx = G.prog.fns.len; | ||
3615 | bc_vec_push(&G.prog.fns, &f); | ||
3616 | return idx; | ||
3617 | } | ||
3618 | |||
3619 | #if ENABLE_BC | ||
3620 | |||
3609 | // Note: takes ownership of 'name' (must be malloced) | 3621 | // Note: takes ownership of 'name' (must be malloced) |
3610 | static size_t bc_program_addFunc(char *name) | 3622 | static size_t bc_program_addFunc(char *name) |
3611 | { | 3623 | { |
3612 | size_t idx; | 3624 | size_t idx; |
3613 | BcId entry, *entry_ptr; | 3625 | BcId entry, *entry_ptr; |
3614 | BcFunc f; | ||
3615 | int inserted; | 3626 | int inserted; |
3616 | 3627 | ||
3617 | entry.name = name; | 3628 | entry.name = name; |
@@ -3630,15 +3641,12 @@ static size_t bc_program_addFunc(char *name) | |||
3630 | bc_func_free(func); | 3641 | bc_func_free(func); |
3631 | bc_func_init(func); | 3642 | bc_func_init(func); |
3632 | } else { | 3643 | } else { |
3633 | bc_func_init(&f); | 3644 | bc_program_add_fn(); |
3634 | bc_vec_push(&G.prog.fns, &f); | ||
3635 | } | 3645 | } |
3636 | 3646 | ||
3637 | return idx; | 3647 | return idx; |
3638 | } | 3648 | } |
3639 | 3649 | ||
3640 | #if ENABLE_BC | ||
3641 | |||
3642 | #define BC_PARSE_TOP_OP(p) (*((BcLexType *) bc_vec_top(&(p)->ops))) | 3650 | #define BC_PARSE_TOP_OP(p) (*((BcLexType *) bc_vec_top(&(p)->ops))) |
3643 | #define BC_PARSE_LEAF(p, rparen) \ | 3651 | #define BC_PARSE_LEAF(p, rparen) \ |
3644 | (((p) >= BC_INST_NUM && (p) <= BC_INST_SQRT) || (rparen) || \ | 3652 | (((p) >= BC_INST_NUM && (p) <= BC_INST_SQRT) || (rparen) || \ |
@@ -4776,19 +4784,22 @@ static BC_STATUS zdc_parse_register(BcParse *p) | |||
4776 | 4784 | ||
4777 | static BC_STATUS zdc_parse_string(BcParse *p) | 4785 | static BC_STATUS zdc_parse_string(BcParse *p) |
4778 | { | 4786 | { |
4779 | char *str, *name; | 4787 | char *str; |
4780 | size_t len = G.prog.strs.len; | 4788 | size_t len = G.prog.strs.len; |
4781 | 4789 | ||
4782 | //why pad to 32 zeros?? | 4790 | dbg_lex_enter("%s:%d entered", __func__, __LINE__); |
4783 | name = xasprintf("%032lu", (unsigned long)len); | ||
4784 | 4791 | ||
4785 | str = xstrdup(p->l.t.v.v); | 4792 | str = xstrdup(p->l.t.v.v); |
4786 | bc_parse_push(p, BC_INST_STR); | 4793 | bc_parse_push(p, BC_INST_STR); |
4787 | bc_parse_pushIndex(p, len); | 4794 | bc_parse_pushIndex(p, len); |
4788 | bc_vec_push(&G.prog.strs, &str); | 4795 | bc_vec_push(&G.prog.strs, &str); |
4789 | bc_program_addFunc(name); | 4796 | |
4797 | // Explanation needed here | ||
4798 | bc_program_add_fn(); | ||
4790 | p->func = bc_program_func(p->fidx); | 4799 | p->func = bc_program_func(p->fidx); |
4791 | 4800 | ||
4801 | dbg_lex_done("%s:%d done", __func__, __LINE__); | ||
4802 | |||
4792 | RETURN_STATUS(zbc_lex_next(&p->l)); | 4803 | RETURN_STATUS(zbc_lex_next(&p->l)); |
4793 | } | 4804 | } |
4794 | #define zdc_parse_string(...) (zdc_parse_string(__VA_ARGS__) COMMA_SUCCESS) | 4805 | #define zdc_parse_string(...) (zdc_parse_string(__VA_ARGS__) COMMA_SUCCESS) |
@@ -4843,6 +4854,7 @@ static BC_STATUS zdc_parse_token(BcParse *p, BcLexType t, uint8_t flags) | |||
4843 | uint8_t inst; | 4854 | uint8_t inst; |
4844 | bool assign, get_token = false; | 4855 | bool assign, get_token = false; |
4845 | 4856 | ||
4857 | dbg_lex_enter("%s:%d entered", __func__, __LINE__); | ||
4846 | switch (t) { | 4858 | switch (t) { |
4847 | case BC_LEX_OP_REL_EQ: | 4859 | case BC_LEX_OP_REL_EQ: |
4848 | case BC_LEX_OP_REL_LE: | 4860 | case BC_LEX_OP_REL_LE: |
@@ -4857,10 +4869,12 @@ static BC_STATUS zdc_parse_token(BcParse *p, BcLexType t, uint8_t flags) | |||
4857 | s = zdc_parse_mem(p, BC_INST_ARRAY_ELEM, true, t == BC_LEX_COLON); | 4869 | s = zdc_parse_mem(p, BC_INST_ARRAY_ELEM, true, t == BC_LEX_COLON); |
4858 | break; | 4870 | break; |
4859 | case BC_LEX_STR: | 4871 | case BC_LEX_STR: |
4872 | dbg_lex("%s:%d LEX_STR", __func__, __LINE__); | ||
4860 | s = zdc_parse_string(p); | 4873 | s = zdc_parse_string(p); |
4861 | break; | 4874 | break; |
4862 | case BC_LEX_NEG: | 4875 | case BC_LEX_NEG: |
4863 | case BC_LEX_NUMBER: | 4876 | case BC_LEX_NUMBER: |
4877 | dbg_lex("%s:%d LEX_NEG/NUMBER", __func__, __LINE__); | ||
4864 | if (t == BC_LEX_NEG) { | 4878 | if (t == BC_LEX_NEG) { |
4865 | s = zbc_lex_next(&p->l); | 4879 | s = zbc_lex_next(&p->l); |
4866 | if (s) RETURN_STATUS(s); | 4880 | if (s) RETURN_STATUS(s); |
@@ -4903,6 +4917,7 @@ static BC_STATUS zdc_parse_token(BcParse *p, BcLexType t, uint8_t flags) | |||
4903 | 4917 | ||
4904 | if (!s && get_token) s = zbc_lex_next(&p->l); | 4918 | if (!s && get_token) s = zbc_lex_next(&p->l); |
4905 | 4919 | ||
4920 | dbg_lex_done("%s:%d done", __func__, __LINE__); | ||
4906 | RETURN_STATUS(s); | 4921 | RETURN_STATUS(s); |
4907 | } | 4922 | } |
4908 | #define zdc_parse_token(...) (zdc_parse_token(__VA_ARGS__) COMMA_SUCCESS) | 4923 | #define zdc_parse_token(...) (zdc_parse_token(__VA_ARGS__) COMMA_SUCCESS) |
@@ -4911,6 +4926,7 @@ static BC_STATUS zdc_parse_expr(BcParse *p, uint8_t flags) | |||
4911 | { | 4926 | { |
4912 | BcLexType t; | 4927 | BcLexType t; |
4913 | 4928 | ||
4929 | dbg_lex_enter("%s:%d entered G.prs.l.t.t:%d", __func__, __LINE__, G.prs.l.t.t); | ||
4914 | for (;;) { | 4930 | for (;;) { |
4915 | BcInst inst; | 4931 | BcInst inst; |
4916 | BcStatus s; | 4932 | BcStatus s; |
@@ -4920,9 +4936,11 @@ static BC_STATUS zdc_parse_expr(BcParse *p, uint8_t flags) | |||
4920 | 4936 | ||
4921 | inst = dc_parse_insts[t]; | 4937 | inst = dc_parse_insts[t]; |
4922 | if (inst != BC_INST_INVALID) { | 4938 | if (inst != BC_INST_INVALID) { |
4939 | dbg_lex("%s:%d", __func__, __LINE__); | ||
4923 | bc_parse_push(p, inst); | 4940 | bc_parse_push(p, inst); |
4924 | s = zbc_lex_next(&p->l); | 4941 | s = zbc_lex_next(&p->l); |
4925 | } else { | 4942 | } else { |
4943 | dbg_lex("%s:%d", __func__, __LINE__); | ||
4926 | s = zdc_parse_token(p, t, flags); | 4944 | s = zdc_parse_token(p, t, flags); |
4927 | } | 4945 | } |
4928 | if (s) RETURN_STATUS(s); | 4946 | if (s) RETURN_STATUS(s); |
@@ -4931,6 +4949,7 @@ static BC_STATUS zdc_parse_expr(BcParse *p, uint8_t flags) | |||
4931 | if (flags & BC_PARSE_NOCALL) | 4949 | if (flags & BC_PARSE_NOCALL) |
4932 | bc_parse_push(p, BC_INST_POP_EXEC); | 4950 | bc_parse_push(p, BC_INST_POP_EXEC); |
4933 | 4951 | ||
4952 | dbg_lex_done("%s:%d done", __func__, __LINE__); | ||
4934 | RETURN_STATUS(BC_STATUS_SUCCESS); | 4953 | RETURN_STATUS(BC_STATUS_SUCCESS); |
4935 | } | 4954 | } |
4936 | #define zdc_parse_expr(...) (zdc_parse_expr(__VA_ARGS__) COMMA_SUCCESS) | 4955 | #define zdc_parse_expr(...) (zdc_parse_expr(__VA_ARGS__) COMMA_SUCCESS) |
@@ -6122,8 +6141,10 @@ static BC_STATUS zdc_program_asciify(void) | |||
6122 | BcStatus s; | 6141 | BcStatus s; |
6123 | BcResult *r, res; | 6142 | BcResult *r, res; |
6124 | BcNum *num, n; | 6143 | BcNum *num, n; |
6125 | char *str, *str2, c; | 6144 | char **strs; |
6126 | size_t len = G.prog.strs.len, idx; | 6145 | char *str; |
6146 | char c; | ||
6147 | size_t idx; | ||
6127 | unsigned long val; | 6148 | unsigned long val; |
6128 | 6149 | ||
6129 | if (!STACK_HAS_MORE_THAN(&G.prog.results, 0)) | 6150 | if (!STACK_HAS_MORE_THAN(&G.prog.results, 0)) |
@@ -6155,31 +6176,25 @@ static BC_STATUS zdc_program_asciify(void) | |||
6155 | 6176 | ||
6156 | bc_num_free(&n); | 6177 | bc_num_free(&n); |
6157 | } else { | 6178 | } else { |
6179 | char *sp; | ||
6158 | idx = (r->t == BC_RESULT_STR) ? r->d.id.idx : num->rdx; | 6180 | idx = (r->t == BC_RESULT_STR) ? r->d.id.idx : num->rdx; |
6159 | str2 = *bc_program_str(idx); | 6181 | sp = *bc_program_str(idx); |
6160 | c = str2[0]; | 6182 | c = sp[0]; |
6161 | } | 6183 | } |
6162 | 6184 | ||
6185 | strs = (void*)G.prog.strs.v; | ||
6186 | for (idx = 0; idx < G.prog.strs.len; idx++) { | ||
6187 | if (strs[idx][0] == c && strs[idx][1] == '\0') { | ||
6188 | goto dup; | ||
6189 | } | ||
6190 | } | ||
6163 | str = xzalloc(2); | 6191 | str = xzalloc(2); |
6164 | str[0] = c; | 6192 | str[0] = c; |
6165 | //str[1] = '\0'; - already is | 6193 | //str[1] = '\0'; - already is |
6166 | 6194 | bc_vec_push(&G.prog.strs, &str); | |
6167 | str2 = xstrdup(str); | 6195 | dup: |
6168 | idx = bc_program_addFunc(str2); | ||
6169 | |||
6170 | if (idx != len + BC_PROG_REQ_FUNCS) { | ||
6171 | for (idx = 0; idx < G.prog.strs.len; ++idx) { | ||
6172 | if (strcmp(*bc_program_str(idx), str) == 0) { | ||
6173 | len = idx; | ||
6174 | break; | ||
6175 | } | ||
6176 | } | ||
6177 | free(str); | ||
6178 | } else | ||
6179 | bc_vec_push(&G.prog.strs, &str); | ||
6180 | |||
6181 | res.t = BC_RESULT_STR; | 6196 | res.t = BC_RESULT_STR; |
6182 | res.d.id.idx = len; | 6197 | res.d.id.idx = idx; |
6183 | bc_vec_pop(&G.prog.results); | 6198 | bc_vec_pop(&G.prog.results); |
6184 | bc_vec_push(&G.prog.results, &res); | 6199 | bc_vec_push(&G.prog.results, &res); |
6185 | 6200 | ||
@@ -6973,7 +6988,7 @@ static BC_STATUS zbc_vm_exec(void) | |||
6973 | static void bc_program_free(void) | 6988 | static void bc_program_free(void) |
6974 | { | 6989 | { |
6975 | bc_vec_free(&G.prog.fns); | 6990 | bc_vec_free(&G.prog.fns); |
6976 | bc_vec_free(&G.prog.fn_map); | 6991 | IF_BC(bc_vec_free(&G.prog.fn_map);) |
6977 | bc_vec_free(&G.prog.vars); | 6992 | bc_vec_free(&G.prog.vars); |
6978 | bc_vec_free(&G.prog.var_map); | 6993 | bc_vec_free(&G.prog.var_map); |
6979 | bc_vec_free(&G.prog.arrs); | 6994 | bc_vec_free(&G.prog.arrs); |
@@ -6982,8 +6997,8 @@ static void bc_program_free(void) | |||
6982 | bc_vec_free(&G.prog.consts); | 6997 | bc_vec_free(&G.prog.consts); |
6983 | bc_vec_free(&G.prog.results); | 6998 | bc_vec_free(&G.prog.results); |
6984 | bc_vec_free(&G.prog.exestack); | 6999 | bc_vec_free(&G.prog.exestack); |
6985 | bc_num_free(&G.prog.last); | 7000 | IF_BC(bc_num_free(&G.prog.last);) |
6986 | bc_num_free(&G.prog.zero); | 7001 | IF_BC(bc_num_free(&G.prog.zero);) |
6987 | IF_BC(bc_num_free(&G.prog.one);) | 7002 | IF_BC(bc_num_free(&G.prog.one);) |
6988 | bc_vec_free(&G.input_buffer); | 7003 | bc_vec_free(&G.input_buffer); |
6989 | } | 7004 | } |
@@ -7018,11 +7033,16 @@ static void bc_program_init(void) | |||
7018 | IF_BC(bc_num_one(&G.prog.one);) | 7033 | IF_BC(bc_num_one(&G.prog.one);) |
7019 | 7034 | ||
7020 | bc_vec_init(&G.prog.fns, sizeof(BcFunc), bc_func_free); | 7035 | bc_vec_init(&G.prog.fns, sizeof(BcFunc), bc_func_free); |
7021 | bc_vec_init(&G.prog.fn_map, sizeof(BcId), bc_id_free); | 7036 | IF_BC(bc_vec_init(&G.prog.fn_map, sizeof(BcId), bc_id_free);) |
7022 | 7037 | ||
7023 | //TODO: with "", dc_strings.dc enters infinite loop, ??! | 7038 | //TODO: with "", dc_strings.dc enters infinite loop, ??! |
7024 | bc_program_addFunc(xstrdup("(m)")); // func #0: main | 7039 | if (IS_BC) { |
7025 | bc_program_addFunc(xstrdup("(r)")); // func #1: for read() | 7040 | IF_BC(bc_program_addFunc(xstrdup("(m)"))); // func #0: main |
7041 | IF_BC(bc_program_addFunc(xstrdup("(r)"))); // func #1: for read() | ||
7042 | } else { | ||
7043 | bc_program_add_fn(); | ||
7044 | bc_program_add_fn(); | ||
7045 | } | ||
7026 | 7046 | ||
7027 | bc_vec_init(&G.prog.vars, sizeof(BcVec), bc_vec_free); | 7047 | bc_vec_init(&G.prog.vars, sizeof(BcVec), bc_vec_free); |
7028 | bc_vec_init(&G.prog.var_map, sizeof(BcId), bc_id_free); | 7048 | bc_vec_init(&G.prog.var_map, sizeof(BcId), bc_id_free); |