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

📄 nasm.c

📁 是用C语言写的NASM汇编源码 是用C语言写的NASM汇编源码 是用C语言写的NASM汇编源码 是用C语言写的NASM汇编源码
💻 C
📖 第 1 页 / 共 5 页
字号:
                            if (!nasm_stricmp(value, suppressed_names[i]))
                                break;
                        if (i <= ERR_WARN_MAX)
                            suppressed[i] = validid;
                        else
                            report_error(ERR_NONFATAL,
                                         "invalid warning id in WARNING directive");
                    }
                    break;
                case 9:        /* cpu */
                    cpu = get_cpu(value);
                    break;
                case 10:       /* fbk 9/2/00 *//* [LIST {+|-}] */
                    while (*value && isspace(*value))
                        value++;

                    if (*value == '+') {
                        user_nolist = 0;
                    } else {
                        if (*value == '-') {
                            user_nolist = 1;
                        } else {
                            report_error(ERR_NONFATAL,
                                         "invalid parameter to \"list\" directive");
                        }
                    }
                    break;
                default:
                    if (!ofmt->directive(directive, value, pass2))
                        report_error(pass1 == 1 ? ERR_NONFATAL : ERR_PANIC,
                                     "unrecognised directive [%s]",
                                     directive);
                }
            } else {            /* it isn't a directive */

                parse_line(pass1, line, &output_ins,
                           report_error, evaluate, def_label);

                if (!(optimizing > 0) && pass == 2) {
                    if (forwref != NULL && globallineno == forwref->lineno) {
                        output_ins.forw_ref = TRUE;
                        do {
                            output_ins.oprs[forwref->operand].opflags |=
                                OPFLAG_FORWARD;
                            forwref = saa_rstruct(forwrefs);
                        } while (forwref != NULL
                                 && forwref->lineno == globallineno);
                    } else
                        output_ins.forw_ref = FALSE;
                }

                if (!(optimizing > 0) && output_ins.forw_ref) {
                    if (pass == 1) {
                        for (i = 0; i < output_ins.operands; i++) {
                            if (output_ins.oprs[i].
                                opflags & OPFLAG_FORWARD) {
                                struct forwrefinfo *fwinf =
                                    (struct forwrefinfo *)
                                    saa_wstruct(forwrefs);
                                fwinf->lineno = globallineno;
                                fwinf->operand = i;
                            }
                        }
                    } else {    /* pass == 2 */
                        /*
                         * Hack to prevent phase error in the code
                         *   rol ax,x
                         *   x equ 1
                         *
                         * If the second operand is a forward reference,
                         * the UNITY property of the number 1 in that
                         * operand is cancelled. Otherwise the above
                         * sequence will cause a phase error.
                         *
                         * This hack means that the above code will
                         * generate 286+ code.
                         *
                         * The forward reference will mean that the
                         * operand will not have the UNITY property on
                         * the first pass, so the pass behaviours will
                         * be consistent.
                         */

                        if (output_ins.operands >= 2 &&
                            (output_ins.oprs[1].opflags & OPFLAG_FORWARD))
                        {
                            output_ins.oprs[1].type &=
                                ~(ONENESS | BYTENESS);
                        }

                    }           /* pass == 2 */

                }

                /*  forw_ref */
                if (output_ins.opcode == I_EQU) {
                    if (pass1 == 1) {
                        /*
                         * Special `..' EQUs get processed in pass two,
                         * except `..@' macro-processor EQUs which are done
                         * in the normal place.
                         */
                        if (!output_ins.label)
                            report_error(ERR_NONFATAL,
                                         "EQU not preceded by label");

                        else if (output_ins.label[0] != '.' ||
                                 output_ins.label[1] != '.' ||
                                 output_ins.label[2] == '@') {
                            if (output_ins.operands == 1 &&
                                (output_ins.oprs[0].type & IMMEDIATE) &&
                                output_ins.oprs[0].wrt == NO_SEG) {
                                int isext =
                                    output_ins.oprs[0].
                                    opflags & OPFLAG_EXTERN;
                                def_label(output_ins.label,
                                          output_ins.oprs[0].segment,
                                          output_ins.oprs[0].offset, NULL,
                                          FALSE, isext, ofmt,
                                          report_error);
                            } else if (output_ins.operands == 2
                                       && (output_ins.oprs[0].
                                           type & IMMEDIATE)
                                       && (output_ins.oprs[0].type & COLON)
                                       && output_ins.oprs[0].segment ==
                                       NO_SEG
                                       && output_ins.oprs[0].wrt == NO_SEG
                                       && (output_ins.oprs[1].
                                           type & IMMEDIATE)
                                       && output_ins.oprs[1].segment ==
                                       NO_SEG
                                       && output_ins.oprs[1].wrt ==
                                       NO_SEG) {
                                def_label(output_ins.label,
                                          output_ins.oprs[0].
                                          offset | SEG_ABS,
                                          output_ins.oprs[1].offset, NULL,
                                          FALSE, FALSE, ofmt,
                                          report_error);
                            } else
                                report_error(ERR_NONFATAL,
                                             "bad syntax for EQU");
                        }
                    } else {    /* pass == 2 */
                        /*
                         * Special `..' EQUs get processed here, except
                         * `..@' macro processor EQUs which are done above.
                         */
                        if (output_ins.label[0] == '.' &&
                            output_ins.label[1] == '.' &&
                            output_ins.label[2] != '@') {
                            if (output_ins.operands == 1 &&
                                (output_ins.oprs[0].type & IMMEDIATE)) {
                                define_label(output_ins.label,
                                             output_ins.oprs[0].segment,
                                             output_ins.oprs[0].offset,
                                             NULL, FALSE, FALSE, ofmt,
                                             report_error);
                            } else if (output_ins.operands == 2
                                       && (output_ins.oprs[0].
                                           type & IMMEDIATE)
                                       && (output_ins.oprs[0].type & COLON)
                                       && output_ins.oprs[0].segment ==
                                       NO_SEG
                                       && (output_ins.oprs[1].
                                           type & IMMEDIATE)
                                       && output_ins.oprs[1].segment ==
                                       NO_SEG) {
                                define_label(output_ins.label,
                                             output_ins.oprs[0].
                                             offset | SEG_ABS,
                                             output_ins.oprs[1].offset,
                                             NULL, FALSE, FALSE, ofmt,
                                             report_error);
                            } else
                                report_error(ERR_NONFATAL,
                                             "bad syntax for EQU");
                        }
                    }           /* pass == 2 */
                } else {        /* instruction isn't an EQU */

                    if (pass1 == 1) {

                        long l = insn_size(location.segment, offs, sb, cpu,
                                           &output_ins, report_error);

                        /* if (using_debug_info)  && output_ins.opcode != -1) */
                        if (using_debug_info)
                        {       /* fbk 03/25/01 */
                            /* this is done here so we can do debug type info */
                            long typeinfo =
                                TYS_ELEMENTS(output_ins.operands);
                            switch (output_ins.opcode) {
                            case I_RESB:
                                typeinfo =
                                    TYS_ELEMENTS(output_ins.oprs[0].
                                                 offset) | TY_BYTE;
                                break;
                            case I_RESW:
                                typeinfo =
                                    TYS_ELEMENTS(output_ins.oprs[0].
                                                 offset) | TY_WORD;
                                break;
                            case I_RESD:
                                typeinfo =
                                    TYS_ELEMENTS(output_ins.oprs[0].
                                                 offset) | TY_DWORD;
                                break;
                            case I_RESQ:
                                typeinfo =
                                    TYS_ELEMENTS(output_ins.oprs[0].
                                                 offset) | TY_QWORD;
                                break;
                            case I_REST:
                                typeinfo =
                                    TYS_ELEMENTS(output_ins.oprs[0].
                                                 offset) | TY_TBYTE;
                                break;
                            case I_DB:
                                typeinfo |= TY_BYTE;
                                break;
                            case I_DW:
                                typeinfo |= TY_WORD;
                                break;
                            case I_DD:
                                if (output_ins.eops_float)
                                    typeinfo |= TY_FLOAT;
                                else
                                    typeinfo |= TY_DWORD;
                                break;
                            case I_DQ:
                                typeinfo |= TY_QWORD;
                                break;
                            case I_DT:
                                typeinfo |= TY_TBYTE;
                                break;
                            default:
                                typeinfo = TY_LABEL;

                            }

                            ofmt->current_dfmt->debug_typevalue(typeinfo);

                        }
                        if (l != -1) {
                            offs += l;
                            SET_CURR_OFFS(offs);
                        }
                        /*
                         * else l == -1 => invalid instruction, which will be
                         * flagged as an error on pass 2
                         */

                    } else {    /* pass == 2 */
                        offs += assemble(location.segment, offs, sb, cpu,
                                         &output_ins, ofmt, report_error,
                                         &nasmlist);
                        SET_CURR_OFFS(offs);

                    }
                }               /* not an EQU */
                cleanup_insn(&output_ins);
            }
            nasm_free(line);
            location.offset = offs = GET_CURR_OFFS;
        }                       /* end while (line = preproc->getline... */

        if (pass1 == 2 && global_offset_changed)
            report_error(ERR_NONFATAL,
                         "phase error detected at end of assembly.");

        if (pass1 == 1)
            preproc->cleanup(1);

        if (pass1 == 1 && terminate_after_phase) {
            fclose(ofile);
            remove(outname);
            if (want_usage)
                usage();
            exit(1);
        }
        pass_cnt++;
        if (pass > 1 && !global_offset_changed) {
            pass0++;
            if (pass0 == 2)
                pass = pass_max - 1;
        } else if (!(optimizing > 0))
            pass0++;

    }                           /* for (pass=1; pass<=2; pass++) */

    preproc->cleanup(0);
    nasmlist.cleanup();
#if 1
    if (optimizing > 0 && opt_verbose_info)     /*  -On and -Ov switches */
        fprintf(stdout,
                "info:: assembly required 1+%d+1 passes\n", pass_cnt - 2);
#endif
}                               /* exit from assemble_file (...) */

static int getkw(char **directive, char **value)
{
    char *p, *q, *buf;

    buf = *directive;

    /*  allow leading spaces or tabs */
    while (*buf == ' ' || *buf == '\t')
        buf++;

    if (*buf != '[')
        return 0;

    p = buf;

    while (*p && *p != ']')
        p++;

    if (!*p)
        return 0;

    q = p++;

    while (*p && *p != ';') {
        if (!isspace(*p))
            return 0;
        p++;
    }
    q[1] = '\0';

    *directive = p = buf + 1;
    while (*buf && *buf != ' ' && *buf != ']' && *buf != '\t')
        buf++;
    if (*buf == ']') {
        *buf = '\0';
        *value = buf;
    } else {
        *buf++ = '\0';
        while (isspace(*buf))
            buf++;              /* beppu - skip leading whitespace */
        *value = buf;
        while (*buf != ']')
            buf++;
        *buf++ = '\0';
    }

⌨️ 快捷键说明

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