⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tcc.c

📁 tcc
💻 C
📖 第 1 页 / 共 5 页
字号:
#define VT_TYPE    (~(VT_STORAGE))/* token values *//* warning: the following compare tokens depend on i386 asm code */#define TOK_ULT 0x92#define TOK_UGE 0x93#define TOK_EQ  0x94#define TOK_NE  0x95#define TOK_ULE 0x96#define TOK_UGT 0x97#define TOK_LT  0x9c#define TOK_GE  0x9d#define TOK_LE  0x9e#define TOK_GT  0x9f#define TOK_LAND  0xa0#define TOK_LOR   0xa1#define TOK_DEC   0xa2#define TOK_MID   0xa3 /* inc/dec, to void constant */#define TOK_INC   0xa4#define TOK_UDIV  0xb0 /* unsigned division */#define TOK_UMOD  0xb1 /* unsigned modulo */#define TOK_PDIV  0xb2 /* fast division with undefined rounding for pointers */#define TOK_CINT   0xb3 /* number in tokc */#define TOK_CCHAR 0xb4 /* char constant in tokc */#define TOK_STR   0xb5 /* pointer to string in tokc */#define TOK_TWOSHARPS 0xb6 /* ## preprocessing token */#define TOK_LCHAR    0xb7#define TOK_LSTR     0xb8#define TOK_CFLOAT   0xb9 /* float constant */#define TOK_LINENUM  0xba /* line number info */#define TOK_CDOUBLE  0xc0 /* double constant */#define TOK_CLDOUBLE 0xc1 /* long double constant */#define TOK_UMULL    0xc2 /* unsigned 32x32 -> 64 mul */#define TOK_ADDC1    0xc3 /* add with carry generation */#define TOK_ADDC2    0xc4 /* add with carry use */#define TOK_SUBC1    0xc5 /* add with carry generation */#define TOK_SUBC2    0xc6 /* add with carry use */#define TOK_CUINT    0xc8 /* unsigned int constant */#define TOK_CLLONG   0xc9 /* long long constant */#define TOK_CULLONG  0xca /* unsigned long long constant */#define TOK_ARROW    0xcb#define TOK_DOTS     0xcc /* three dots */#define TOK_SHR      0xcd /* unsigned shift right */#define TOK_PPNUM    0xce /* preprocessor number */#define TOK_SHL   0x01 /* shift left */#define TOK_SAR   0x02 /* signed shift right */  /* assignement operators : normal operator or 0x80 */#define TOK_A_MOD 0xa5#define TOK_A_AND 0xa6#define TOK_A_MUL 0xaa#define TOK_A_ADD 0xab#define TOK_A_SUB 0xad#define TOK_A_DIV 0xaf#define TOK_A_XOR 0xde#define TOK_A_OR  0xfc#define TOK_A_SHL 0x81#define TOK_A_SAR 0x82#ifndef offsetof#define offsetof(type, field) ((size_t) &((type *)0)->field)#endif#ifndef countof#define countof(tab) (sizeof(tab) / sizeof((tab)[0]))#endif/* WARNING: the content of this string encodes token numbers */static char tok_two_chars[] = "<=\236>=\235!=\225&&\240||\241++\244--\242==\224<<\1>>\2+=\253-=\255*=\252/=\257%=\245&=\246^=\336|=\374->\313..\250##\266";#define TOK_EOF       (-1)  /* end of file */#define TOK_LINEFEED  10    /* line feed *//* all identificators and strings have token above that */#define TOK_IDENT 256/* only used for i386 asm opcodes definitions */#define DEF_ASM(x) DEF(TOK_ASM_ ## x, #x)#define DEF_BWL(x) \ DEF(TOK_ASM_ ## x ## b, #x "b") \ DEF(TOK_ASM_ ## x ## w, #x "w") \ DEF(TOK_ASM_ ## x ## l, #x "l") \ DEF(TOK_ASM_ ## x, #x)#define DEF_WL(x) \ DEF(TOK_ASM_ ## x ## w, #x "w") \ DEF(TOK_ASM_ ## x ## l, #x "l") \ DEF(TOK_ASM_ ## x, #x)#define DEF_FP1(x) \ DEF(TOK_ASM_ ## f ## x ## s, "f" #x "s") \ DEF(TOK_ASM_ ## fi ## x ## l, "fi" #x "l") \ DEF(TOK_ASM_ ## f ## x ## l, "f" #x "l") \ DEF(TOK_ASM_ ## fi ## x ## s, "fi" #x "s")#define DEF_FP(x) \ DEF(TOK_ASM_ ## f ## x, "f" #x ) \ DEF(TOK_ASM_ ## f ## x ## p, "f" #x "p") \ DEF_FP1(x)#define DEF_ASMTEST(x) \ DEF_ASM(x ## o) \ DEF_ASM(x ## no) \ DEF_ASM(x ## b) \ DEF_ASM(x ## c) \ DEF_ASM(x ## nae) \ DEF_ASM(x ## nb) \ DEF_ASM(x ## nc) \ DEF_ASM(x ## ae) \ DEF_ASM(x ## e) \ DEF_ASM(x ## z) \ DEF_ASM(x ## ne) \ DEF_ASM(x ## nz) \ DEF_ASM(x ## be) \ DEF_ASM(x ## na) \ DEF_ASM(x ## nbe) \ DEF_ASM(x ## a) \ DEF_ASM(x ## s) \ DEF_ASM(x ## ns) \ DEF_ASM(x ## p) \ DEF_ASM(x ## pe) \ DEF_ASM(x ## np) \ DEF_ASM(x ## po) \ DEF_ASM(x ## l) \ DEF_ASM(x ## nge) \ DEF_ASM(x ## nl) \ DEF_ASM(x ## ge) \ DEF_ASM(x ## le) \ DEF_ASM(x ## ng) \ DEF_ASM(x ## nle) \ DEF_ASM(x ## g)#define TOK_ASM_int TOK_INTenum {    TOK_LAST = TOK_IDENT - 1,#define DEF(id, str) id,#include "tcctok.h"#undef DEF};static const char tcc_keywords[] = #define DEF(id, str) str "\0"#include "tcctok.h"#undef DEF;#define TOK_UIDENT TOK_DEFINE#ifdef WIN32#define snprintf _snprintf#define vsnprintf _vsnprintf#endif#if defined(WIN32) || defined(TCC_UCLIBC) || defined(__FreeBSD__)/* currently incorrect */long double strtold(const char *nptr, char **endptr){    return (long double)strtod(nptr, endptr);}float strtof(const char *nptr, char **endptr){    return (float)strtod(nptr, endptr);}#else/* XXX: need to define this to use them in non ISOC99 context */extern float strtof (const char *__nptr, char **__endptr);extern long double strtold (const char *__nptr, char **__endptr);#endifstatic char *pstrcpy(char *buf, int buf_size, const char *s);static char *pstrcat(char *buf, int buf_size, const char *s);static void next(void);static void next_nomacro(void);static void parse_expr_type(CType *type);static void expr_type(CType *type);static void unary_type(CType *type);static void block(int *bsym, int *csym, int *case_sym, int *def_sym,                   int case_reg, int is_expr);static int expr_const(void);static void expr_eq(void);static void gexpr(void);static void decl(int l);static void decl_initializer(CType *type, Section *sec, unsigned long c,                              int first, int size_only);static void decl_initializer_alloc(CType *type, AttributeDef *ad, int r,                                    int has_init, int v, int scope);int gv(int rc);void gv2(int rc1, int rc2);void move_reg(int r, int s);void save_regs(int n);void save_reg(int r);void vpop(void);void vswap(void);void vdup(void);int get_reg(int rc);static void macro_subst(TokenString *tok_str, Sym **nested_list,                         const int *macro_str, int can_read_stream);int save_reg_forced(int r);void gen_op(int op);void force_charshort_cast(int t);static void gen_cast(CType *type);void vstore(void);static Sym *sym_find(int v);static Sym *sym_push(int v, CType *type, int r, int c);/* type handling */static int type_size(CType *type, int *a);static inline CType *pointed_type(CType *type);static int pointed_size(CType *type);static int lvalue_type(int t);static int parse_btype(CType *type, AttributeDef *ad);static void type_decl(CType *type, AttributeDef *ad, int *v, int td);static int is_compatible_types(CType *type1, CType *type2);void error(const char *fmt, ...);void vpushi(int v);void vset(CType *type, int r, int v);void type_to_str(char *buf, int buf_size,                  CType *type, const char *varstr);char *get_tok_str(int v, CValue *cv);static Sym *get_sym_ref(CType *type, Section *sec,                         unsigned long offset, unsigned long size);static Sym *external_global_sym(int v, CType *type, int r);/* section generation */static void section_realloc(Section *sec, unsigned long new_size);static void *section_ptr_add(Section *sec, unsigned long size);static void put_extern_sym(Sym *sym, Section *section,                            unsigned long value, unsigned long size);static void greloc(Section *s, Sym *sym, unsigned long addr, int type);static int put_elf_str(Section *s, const char *sym);static int put_elf_sym(Section *s,                        unsigned long value, unsigned long size,                       int info, int other, int shndx, const char *name);static int add_elf_sym(Section *s, unsigned long value, unsigned long size,                       int info, int sh_num, const char *name);static void put_elf_reloc(Section *symtab, Section *s, unsigned long offset,                          int type, int symbol);static void put_stabs(const char *str, int type, int other, int desc,                       unsigned long value);static void put_stabs_r(const char *str, int type, int other, int desc,                         unsigned long value, Section *sec, int sym_index);static void put_stabn(int type, int other, int desc, int value);static void put_stabd(int type, int other, int desc);static int tcc_add_dll(TCCState *s, const char *filename, int flags);#define AFF_PRINT_ERROR     0x0001 /* print error if file not found */#define AFF_REFERENCED_DLL  0x0002 /* load a referenced dll from another dll */static int tcc_add_file_internal(TCCState *s, const char *filename, int flags);/* tccasm.c */#ifdef CONFIG_TCC_ASMtypedef struct ExprValue {    uint32_t v;    Sym *sym;} ExprValue;#define MAX_ASM_OPERANDS 30typedef struct ASMOperand {    int id; /* GCC 3 optionnal identifier (0 if number only supported */    char *constraint;    char asm_str[16]; /* computed asm string for operand */    SValue *vt; /* C value of the expression */    int ref_index; /* if >= 0, gives reference to a output constraint */    int priority; /* priority, used to assign registers */    int reg; /* if >= 0, register number used for this operand */    int is_llong; /* true if double register value */} ASMOperand;static void asm_expr(TCCState *s1, ExprValue *pe);static int asm_int_expr(TCCState *s1);static int find_constraint(ASMOperand *operands, int nb_operands,                            const char *name, const char **pp);static int tcc_assemble(TCCState *s1, int do_preprocess);#endifstatic void asm_instr(void);/* true if float/double/long double type */static inline int is_float(int t){    int bt;    bt = t & VT_BTYPE;    return bt == VT_LDOUBLE || bt == VT_DOUBLE || bt == VT_FLOAT;}#ifdef TCC_TARGET_I386#include "i386-gen.c"#endif#ifdef CONFIG_TCC_STATIC#define RTLD_LAZY       0x001#define RTLD_NOW        0x002#define RTLD_GLOBAL     0x100#define RTLD_DEFAULT    NULL/* dummy function for profiling */void *dlopen(const char *filename, int flag){    return NULL;}const char *dlerror(void){    return "error";}typedef struct TCCSyms {    char *str;    void *ptr;} TCCSyms;#define TCCSYM(a) { #a, &a, },/* add the symbol you want here if no dynamic linking is done */static TCCSyms tcc_syms[] = {    TCCSYM(printf)    TCCSYM(fprintf)    TCCSYM(fopen)    TCCSYM(fclose)    { NULL, NULL },};void *dlsym(void *handle, const char *symbol){    TCCSyms *p;    p = tcc_syms;    while (p->str != NULL) {        if (!strcmp(p->str, symbol))            return p->ptr;        p++;    }    return NULL;}#endif/********************************************************//* we use our own 'finite' function to avoid potential problems with   non standard math libs *//* XXX: endianness dependent */int ieee_finite(double d){    int *p = (int *)&d;    return ((unsigned)((p[1] | 0x800fffff) + 1)) >> 31;}/* copy a string and truncate it. */static char *pstrcpy(char *buf, int buf_size, const char *s){    char *q, *q_end;    int c;    if (buf_size > 0) {        q = buf;        q_end = buf + buf_size - 1;        while (q < q_end) {            c = *s++;            if (c == '\0')                break;            *q++ = c;        }        *q = '\0';    }    return buf;}/* strcat and truncate. */static char *pstrcat(char *buf, int buf_size, const char *s){    int len;    len = strlen(buf);    if (len < buf_size)         pstrcpy(buf + len, buf_size - len, s);    return buf;}/* memory management */#ifdef MEM_DEBUGint mem_cur_size;int mem_max_size;#endifstatic inline void tcc_free(void *ptr){#ifdef MEM_DEBUG    mem_cur_size -= malloc_usable_size(ptr);#endif    free(ptr);}static void *tcc_malloc(unsigned long size){    void *ptr;    ptr = malloc(size);    if (!ptr && size)        error("memory full");#ifdef MEM_DEBUG    mem_cur_size += malloc_usable_size(ptr);    if (mem_cur_size > mem_max_size)        mem_max_size = mem_cur_size;#endif    return ptr;}static void *tcc_mallocz(unsigned long size){    void *ptr;    ptr = tcc_malloc(size);    memset(ptr, 0, size);    return ptr;}static inline void *tcc_realloc(void *ptr, unsigned long size){    void *ptr1;#ifdef MEM_DEBUG    mem_cur_size -= malloc_usable_size(ptr);#endif    ptr1 = realloc(ptr, size);#ifdef MEM_DEBUG    /* NOTE: count not correct if alloc error, but not critical */    mem_cur_size += malloc_usable_size(ptr1);    if (mem_cur_size > mem_max_size)        mem_max_size = mem_cur_size;#endif    return ptr1;}static char *tcc_strdup(const char *str){    char *ptr;    ptr = tcc_malloc(strlen(str) + 1);    strcpy(ptr, str);    return ptr;}#define free(p) use_tcc_free(p)#define malloc(s) use_tcc_malloc(s)#define realloc(p, s) use_tcc_realloc(p, s)static void dynarray_add(void ***ptab, int *nb_ptr, void *data){    int nb, nb_alloc;    void **pp;        nb = *nb_ptr;    pp = *ptab;    /* every power of two we double array size */    if ((nb & (nb - 1)) == 0) {        if (!nb)            nb_alloc = 1;        else            nb_alloc = nb * 2;        pp = tcc_realloc(pp, nb_alloc * sizeof(void *));        if (!pp)            error("memory full");        *ptab = pp;    }    pp[nb++] = data;    *nb_ptr = nb;}Section *new_section(TCCState *s1, const char *name, int sh_type, int sh_flags){    Section *sec;    sec = tcc_mallocz(sizeof(Section) + strlen(name));    strcpy(sec->name, name);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -