1 /* 2 * ***************************************************************************** 3 * 4 * Copyright (c) 2018-2019 Gavin D. Howard and contributors. 5 * 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions are met: 10 * 11 * * Redistributions of source code must retain the above copyright notice, this 12 * list of conditions and the following disclaimer. 13 * 14 * * Redistributions in binary form must reproduce the above copyright notice, 15 * this list of conditions and the following disclaimer in the documentation 16 * and/or other materials provided with the distribution. 17 * 18 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 19 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 21 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE 22 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 23 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 24 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 25 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 26 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 27 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 28 * POSSIBILITY OF SUCH DAMAGE. 29 * 30 * ***************************************************************************** 31 * 32 * Definitions for bc programs. 33 * 34 */ 35 36 #ifndef BC_PROGRAM_H 37 #define BC_PROGRAM_H 38 39 #include <stddef.h> 40 41 #include <status.h> 42 #include <parse.h> 43 #include <lang.h> 44 #include <num.h> 45 46 #define BC_PROG_GLOBALS_IBASE (0) 47 #define BC_PROG_GLOBALS_OBASE (1) 48 #define BC_PROG_GLOBALS_SCALE (2) 49 #define BC_PROG_GLOBALS_LEN (3) 50 51 #define BC_PROG_ONE_CAP (1) 52 53 typedef struct BcProgram { 54 55 BcBigDig globals[BC_PROG_GLOBALS_LEN]; 56 BcVec globals_v[BC_PROG_GLOBALS_LEN]; 57 58 BcVec results; 59 BcVec stack; 60 61 BcVec fns; 62 #if BC_ENABLED 63 BcVec fn_map; 64 #endif // BC_ENABLED 65 66 BcVec vars; 67 BcVec var_map; 68 69 BcVec arrs; 70 BcVec arr_map; 71 72 #if DC_ENABLED 73 BcVec tail_calls; 74 75 BcBigDig strm; 76 BcNum strmb; 77 #endif // DC_ENABLED 78 79 BcNum one; 80 81 #if BC_ENABLED 82 BcNum last; 83 #endif // BC_ENABLED 84 85 #if DC_ENABLED 86 // This uses BC_NUM_LONG_LOG10 because it is used in bc_num_ulong2num(), 87 // which attempts to realloc, unless it is big enough. This is big enough. 88 BcDig strmb_num[BC_NUM_BIGDIG_LOG10]; 89 #endif // DC_ENABLED 90 91 BcDig one_num[BC_PROG_ONE_CAP]; 92 93 } BcProgram; 94 95 #define BC_PROG_STACK(s, n) ((s)->len >= ((size_t) (n))) 96 97 #define BC_PROG_GLOBAL_PTR(v) (bc_vec_top(v)) 98 #define BC_PROG_GLOBAL(v) (*((BcBigDig*) BC_PROG_GLOBAL_PTR(v))) 99 100 #define BC_PROG_IBASE(p) ((p)->globals[BC_PROG_GLOBALS_IBASE]) 101 #define BC_PROG_OBASE(p) ((p)->globals[BC_PROG_GLOBALS_OBASE]) 102 #define BC_PROG_SCALE(p) ((p)->globals[BC_PROG_GLOBALS_SCALE]) 103 104 #define BC_PROG_MAIN (0) 105 #define BC_PROG_READ (1) 106 107 #if DC_ENABLED 108 #define BC_PROG_REQ_FUNCS (2) 109 #if !BC_ENABLED 110 // For dc only, last is always true. 111 #define bc_program_copyToVar(p, name, t, last) \ 112 bc_program_copyToVar(p, name, t) 113 #endif // !BC_ENABLED 114 #else // DC_ENABLED 115 // For bc, 'pop' and 'copy' are always false. 116 #define bc_program_pushVar(p, code, bgn, pop, copy) \ 117 bc_program_pushVar(p, code, bgn) 118 #ifdef NDEBUG 119 #define BC_PROG_NO_STACK_CHECK 120 #endif // NDEBUG 121 #endif // DC_ENABLED 122 123 #define BC_PROG_STR(n) ((n)->num == NULL && !(n)->cap) 124 #if BC_ENABLED 125 #define BC_PROG_NUM(r, n) \ 126 ((r)->t != BC_RESULT_ARRAY && (r)->t != BC_RESULT_STR && !BC_PROG_STR(n)) 127 #else // BC_ENABLED 128 #define BC_PROG_NUM(r, n) ((r)->t != BC_RESULT_STR && !BC_PROG_STR(n)) 129 // For dc, inst is always BC_INST_ARRAY_ELEM. 130 #define bc_program_pushArray(p, code, bgn, inst) \ 131 bc_program_pushArray(p, code, bgn) 132 #endif // BC_ENABLED 133 134 typedef void (*BcProgramUnary)(BcResult*, BcNum*); 135 136 void bc_program_init(BcProgram *p); 137 void bc_program_free(BcProgram *p); 138 139 #if BC_DEBUG_CODE 140 #if BC_ENABLED && DC_ENABLED 141 void bc_program_code(const BcProgram *p); 142 void bc_program_printInst(const BcProgram *p, const char *code, 143 size_t *restrict bgn); 144 BcStatus bc_program_printStackDebug(BcProgram* p); 145 #endif // BC_ENABLED && DC_ENABLED 146 #endif // BC_DEBUG_CODE 147 148 size_t bc_program_search(BcProgram *p, char* id, bool var); 149 void bc_program_addFunc(BcProgram *p, BcFunc *f, const char* name); 150 size_t bc_program_insertFunc(BcProgram *p, char *name); 151 BcStatus bc_program_reset(BcProgram *p, BcStatus s); 152 BcStatus bc_program_exec(BcProgram *p); 153 154 void bc_program_negate(BcResult *r, BcNum *n); 155 void bc_program_not(BcResult *r, BcNum *n); 156 #if BC_ENABLE_EXTRA_MATH 157 void bc_program_trunc(BcResult *r, BcNum *n); 158 #endif // BC_ENABLE_EXTRA_MATH 159 160 extern const BcNumBinaryOp bc_program_ops[]; 161 extern const BcNumBinaryOpReq bc_program_opReqs[]; 162 extern const BcProgramUnary bc_program_unarys[]; 163 extern const char bc_program_exprs_name[]; 164 extern const char bc_program_stdin_name[]; 165 #if BC_ENABLE_SIGNALS 166 extern const char bc_program_ready_msg[]; 167 extern const size_t bc_program_ready_msg_len; 168 #endif // BC_ENABLE_SIGNALS 169 extern const char bc_program_esc_chars[]; 170 extern const char bc_program_esc_seqs[]; 171 172 #endif // BC_PROGRAM_H 173