Annotation of qemu/target-cris/op.c, revision 1.1

1.1     ! root        1: /*
        !             2:  *  CRIS emulation micro-operations for qemu.
        !             3:  *
        !             4:  *  Copyright (c) 2007 Edgar E. Iglesias, Axis Communications AB.
        !             5:  *
        !             6:  * This library is free software; you can redistribute it and/or
        !             7:  * modify it under the terms of the GNU Lesser General Public
        !             8:  * License as published by the Free Software Foundation; either
        !             9:  * version 2 of the License, or (at your option) any later version.
        !            10:  *
        !            11:  * This library is distributed in the hope that it will be useful,
        !            12:  * but WITHOUT ANY WARRANTY; without even the implied warranty of
        !            13:  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
        !            14:  * Lesser General Public License for more details.
        !            15:  *
        !            16:  * You should have received a copy of the GNU Lesser General Public
        !            17:  * License along with this library; if not, write to the Free Software
        !            18:  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
        !            19:  */
        !            20: #include "exec.h"
        !            21: #include "host-utils.h"
        !            22: 
        !            23: #define REGNAME r0
        !            24: #define REG (env->regs[0])
        !            25: #include "op_template.h"
        !            26: 
        !            27: #define REGNAME r1
        !            28: #define REG (env->regs[1])
        !            29: #include "op_template.h"
        !            30: 
        !            31: #define REGNAME r2
        !            32: #define REG (env->regs[2])
        !            33: #include "op_template.h"
        !            34: 
        !            35: #define REGNAME r3
        !            36: #define REG (env->regs[3])
        !            37: #include "op_template.h"
        !            38: 
        !            39: #define REGNAME r4
        !            40: #define REG (env->regs[4])
        !            41: #include "op_template.h"
        !            42: 
        !            43: #define REGNAME r5
        !            44: #define REG (env->regs[5])
        !            45: #include "op_template.h"
        !            46: 
        !            47: #define REGNAME r6
        !            48: #define REG (env->regs[6])
        !            49: #include "op_template.h"
        !            50: 
        !            51: #define REGNAME r7
        !            52: #define REG (env->regs[7])
        !            53: #include "op_template.h"
        !            54: 
        !            55: #define REGNAME r8
        !            56: #define REG (env->regs[8])
        !            57: #include "op_template.h"
        !            58: 
        !            59: #define REGNAME r9
        !            60: #define REG (env->regs[9])
        !            61: #include "op_template.h"
        !            62: 
        !            63: #define REGNAME r10
        !            64: #define REG (env->regs[10])
        !            65: #include "op_template.h"
        !            66: 
        !            67: #define REGNAME r11
        !            68: #define REG (env->regs[11])
        !            69: #include "op_template.h"
        !            70: 
        !            71: #define REGNAME r12
        !            72: #define REG (env->regs[12])
        !            73: #include "op_template.h"
        !            74: 
        !            75: #define REGNAME r13
        !            76: #define REG (env->regs[13])
        !            77: #include "op_template.h"
        !            78: 
        !            79: #define REGNAME r14
        !            80: #define REG (env->regs[14])
        !            81: #include "op_template.h"
        !            82: 
        !            83: #define REGNAME r15
        !            84: #define REG (env->regs[15])
        !            85: #include "op_template.h"
        !            86: 
        !            87: 
        !            88: #define REGNAME p0
        !            89: #define REG (env->pregs[0])
        !            90: #include "op_template.h"
        !            91: 
        !            92: #define REGNAME p1
        !            93: #define REG (env->pregs[1])
        !            94: #include "op_template.h"
        !            95: 
        !            96: #define REGNAME p2
        !            97: #define REG (env->pregs[2])
        !            98: #include "op_template.h"
        !            99: 
        !           100: #define REGNAME p3
        !           101: #define REG (env->pregs[3])
        !           102: #include "op_template.h"
        !           103: 
        !           104: #define REGNAME p4
        !           105: #define REG (env->pregs[4])
        !           106: #include "op_template.h"
        !           107: 
        !           108: #define REGNAME p5
        !           109: #define REG (env->pregs[5])
        !           110: #include "op_template.h"
        !           111: 
        !           112: #define REGNAME p6
        !           113: #define REG (env->pregs[6])
        !           114: #include "op_template.h"
        !           115: 
        !           116: #define REGNAME p7
        !           117: #define REG (env->pregs[7])
        !           118: #include "op_template.h"
        !           119: 
        !           120: #define REGNAME p8
        !           121: #define REG (env->pregs[8])
        !           122: #include "op_template.h"
        !           123: 
        !           124: #define REGNAME p9
        !           125: #define REG (env->pregs[9])
        !           126: #include "op_template.h"
        !           127: 
        !           128: #define REGNAME p10
        !           129: #define REG (env->pregs[10])
        !           130: #include "op_template.h"
        !           131: 
        !           132: #define REGNAME p11
        !           133: #define REG (env->pregs[11])
        !           134: #include "op_template.h"
        !           135: 
        !           136: #define REGNAME p12
        !           137: #define REG (env->pregs[12])
        !           138: #include "op_template.h"
        !           139: 
        !           140: #define REGNAME p13
        !           141: #define REG (env->pregs[13])
        !           142: #include "op_template.h"
        !           143: 
        !           144: #define REGNAME p14
        !           145: #define REG (env->pregs[14])
        !           146: #include "op_template.h"
        !           147: 
        !           148: #define REGNAME p15
        !           149: #define REG (env->pregs[15])
        !           150: #include "op_template.h"
        !           151: 
        !           152: /* Microcode.  */
        !           153: 
        !           154: void OPPROTO op_exit_tb (void)
        !           155: {
        !           156:        EXIT_TB();
        !           157: }
        !           158: 
        !           159: void OPPROTO op_goto_tb0 (void)
        !           160: {
        !           161:        GOTO_TB(op_goto_tb0, PARAM1, 0);
        !           162:        RETURN();
        !           163: }
        !           164: 
        !           165: void OPPROTO op_goto_tb1 (void)
        !           166: {
        !           167:        GOTO_TB(op_goto_tb1, PARAM1, 1);
        !           168:        RETURN();
        !           169: }
        !           170: 
        !           171: void OPPROTO op_break_im(void)
        !           172: {
        !           173:        env->trapnr = PARAM1;
        !           174:        env->exception_index = EXCP_BREAK;
        !           175:        cpu_loop_exit();
        !           176: }
        !           177: 
        !           178: void OPPROTO op_debug(void)
        !           179: {
        !           180:        env->exception_index = EXCP_DEBUG;
        !           181:        cpu_loop_exit();
        !           182: }
        !           183: 
        !           184: void OPPROTO op_exec_insn(void)
        !           185: {
        !           186:        env->stats.exec_insns++;
        !           187:        RETURN();
        !           188: }
        !           189: void OPPROTO op_exec_load(void)
        !           190: {
        !           191:        env->stats.exec_loads++;
        !           192:        RETURN();
        !           193: }
        !           194: void OPPROTO op_exec_store(void)
        !           195: {
        !           196:        env->stats.exec_stores++;
        !           197:        RETURN();
        !           198: }
        !           199: 
        !           200: void OPPROTO op_ccs_lshift (void)
        !           201: {
        !           202:        uint32_t ccs;
        !           203: 
        !           204:        /* Apply the ccs shift.  */
        !           205:        ccs = env->pregs[SR_CCS];
        !           206:        ccs = (ccs & 0xc0000000) | ((ccs << 12) >> 2);
        !           207:        env->pregs[SR_CCS] = ccs;
        !           208: }
        !           209: void OPPROTO op_ccs_rshift (void)
        !           210: {
        !           211:        uint32_t ccs;
        !           212: 
        !           213:        /* Apply the ccs shift.  */
        !           214:        ccs = env->pregs[SR_CCS];
        !           215:        ccs = (ccs & 0xc0000000) | (ccs >> 10);
        !           216:        env->pregs[SR_CCS] = ccs;
        !           217: }
        !           218: 
        !           219: void OPPROTO op_setf (void)
        !           220: {
        !           221:        env->pregs[SR_CCS] |= PARAM1;
        !           222:        RETURN();
        !           223: }
        !           224: 
        !           225: void OPPROTO op_clrf (void)
        !           226: {
        !           227:        env->pregs[SR_CCS] &= ~PARAM1;
        !           228:        RETURN();
        !           229: }
        !           230: 
        !           231: void OPPROTO op_movl_debug1_T0 (void)
        !           232: {
        !           233:        env->debug1 = T0;
        !           234:        RETURN();
        !           235: }
        !           236: 
        !           237: void OPPROTO op_movl_debug2_T0 (void)
        !           238: {
        !           239:        env->debug2 = T0;
        !           240:        RETURN();
        !           241: }
        !           242: 
        !           243: void OPPROTO op_movl_debug3_T0 (void)
        !           244: {
        !           245:        env->debug3 = T0;
        !           246:        RETURN();
        !           247: }
        !           248: void OPPROTO op_movl_debug1_T1 (void)
        !           249: {
        !           250:        env->debug1 = T1;
        !           251:        RETURN();
        !           252: }
        !           253: 
        !           254: void OPPROTO op_movl_debug2_T1 (void)
        !           255: {
        !           256:        env->debug2 = T1;
        !           257:        RETURN();
        !           258: }
        !           259: 
        !           260: void OPPROTO op_movl_debug3_T1 (void)
        !           261: {
        !           262:        env->debug3 = T1;
        !           263:        RETURN();
        !           264: }
        !           265: void OPPROTO op_movl_debug3_im (void)
        !           266: {
        !           267:        env->debug3 = PARAM1;
        !           268:        RETURN();
        !           269: }
        !           270: void OPPROTO op_movl_T0_flags (void)
        !           271: {
        !           272:        T0 = env->pregs[SR_CCS];
        !           273:        RETURN();
        !           274: }
        !           275: void OPPROTO op_movl_flags_T0 (void)
        !           276: {
        !           277:        env->pregs[SR_CCS] = T0;
        !           278:        RETURN();
        !           279: }
        !           280: 
        !           281: void OPPROTO op_movl_sreg_T0 (void)
        !           282: {
        !           283:        env->sregs[env->pregs[SR_SRS]][PARAM1] = T0;
        !           284:        RETURN();
        !           285: }
        !           286: 
        !           287: void OPPROTO op_movl_tlb_lo_T0 (void)
        !           288: {
        !           289:        int srs;
        !           290:        srs = env->pregs[SR_SRS];
        !           291:        if (srs == 1 || srs == 2)
        !           292:        {
        !           293:                int set;
        !           294:                int idx;
        !           295:                uint32_t lo, hi;
        !           296: 
        !           297:                idx = set = env->sregs[SFR_RW_MM_TLB_SEL];
        !           298:                set >>= 4;
        !           299:                set &= 3;
        !           300: 
        !           301:                idx &= 31;
        !           302:                /* We've just made a write to tlb_lo.  */
        !           303:                lo = env->sregs[SFR_RW_MM_TLB_LO];
        !           304:                hi = env->sregs[SFR_RW_MM_TLB_HI];
        !           305:                env->tlbsets[srs - 1][set][idx].lo = lo;
        !           306:                env->tlbsets[srs - 1][set][idx].hi = hi;
        !           307:        }
        !           308: 
        !           309:        RETURN();
        !           310: }
        !           311: 
        !           312: void OPPROTO op_movl_T0_sreg (void)
        !           313: {
        !           314:        T0 = env->sregs[env->pregs[SR_SRS]][PARAM1];
        !           315:        RETURN();
        !           316: }
        !           317: 
        !           318: void OPPROTO op_update_cc (void)
        !           319: {
        !           320:        env->cc_op = PARAM1;
        !           321:        env->cc_dest = PARAM2;
        !           322:        env->cc_src = PARAM3;
        !           323:        RETURN();
        !           324: }
        !           325: 
        !           326: void OPPROTO op_update_cc_op (void)
        !           327: {
        !           328:        env->cc_op = PARAM1;
        !           329:        RETURN();
        !           330: }
        !           331: 
        !           332: void OPPROTO op_update_cc_mask (void)
        !           333: {
        !           334:        env->cc_mask = PARAM1;
        !           335:        RETURN();
        !           336: }
        !           337: 
        !           338: void OPPROTO op_update_cc_dest_T0 (void)
        !           339: {
        !           340:        env->cc_dest = T0;
        !           341:        RETURN();
        !           342: }
        !           343: 
        !           344: void OPPROTO op_update_cc_result_T0 (void)
        !           345: {
        !           346:        env->cc_result = T0;
        !           347:        RETURN();
        !           348: }
        !           349: 
        !           350: void OPPROTO op_update_cc_size_im (void)
        !           351: {
        !           352:        env->cc_size = PARAM1;
        !           353:        RETURN();
        !           354: }
        !           355: 
        !           356: void OPPROTO op_update_cc_src_T1 (void)
        !           357: {
        !           358:        env->cc_src = T1;
        !           359:        RETURN();
        !           360: }
        !           361: void OPPROTO op_update_cc_x (void)
        !           362: {
        !           363:        env->cc_x_live = PARAM1;
        !           364:        env->cc_x = PARAM2;
        !           365:        RETURN();
        !           366: }
        !           367: 
        !           368: /* FIXME: is this allowed?  */
        !           369: extern inline void evaluate_flags_writeback(uint32_t flags)
        !           370: {
        !           371:        int x;
        !           372: 
        !           373:        /* Extended arithmetics, leave the z flag alone.  */
        !           374:        env->debug3 = env->pregs[SR_CCS];
        !           375: 
        !           376:        if (env->cc_x_live)
        !           377:                x = env->cc_x;
        !           378:        else
        !           379:                x = env->pregs[SR_CCS] & X_FLAG;
        !           380: 
        !           381:        if ((x || env->cc_op == CC_OP_ADDC)
        !           382:            && flags & Z_FLAG)
        !           383:                env->cc_mask &= ~Z_FLAG;
        !           384: 
        !           385:        /* all insn clear the x-flag except setf or clrf.  */
        !           386:        env->pregs[SR_CCS] &= ~(env->cc_mask | X_FLAG);
        !           387:        flags &= env->cc_mask;
        !           388:        env->pregs[SR_CCS] |= flags;
        !           389:        RETURN();
        !           390: }
        !           391: 
        !           392: void OPPROTO op_evaluate_flags_muls(void)
        !           393: {
        !           394:        uint32_t src;
        !           395:        uint32_t dst;
        !           396:        uint32_t res;
        !           397:        uint32_t flags = 0;
        !           398:        /* were gonna have to redo the muls.  */
        !           399:        int64_t tmp, t0 ,t1;
        !           400:        int32_t mof;
        !           401:        int dneg;
        !           402: 
        !           403:        src = env->cc_src;
        !           404:        dst = env->cc_dest;
        !           405:        res = env->cc_result;
        !           406: 
        !           407: 
        !           408:        /* cast into signed values to make GCC sign extend.  */
        !           409:        t0 = (int32_t)src;
        !           410:        t1 = (int32_t)dst;
        !           411:        dneg = ((int32_t)res) < 0;
        !           412: 
        !           413:        tmp = t0 * t1;
        !           414:        mof = tmp >> 32;
        !           415:        if (tmp == 0)
        !           416:                flags |= Z_FLAG;
        !           417:        else if (tmp < 0)
        !           418:                flags |= N_FLAG;
        !           419:        if ((dneg && mof != -1)
        !           420:            || (!dneg && mof != 0))
        !           421:                flags |= V_FLAG;
        !           422:        evaluate_flags_writeback(flags);
        !           423:        RETURN();
        !           424: }
        !           425: 
        !           426: void OPPROTO op_evaluate_flags_mulu(void)
        !           427: {
        !           428:        uint32_t src;
        !           429:        uint32_t dst;
        !           430:        uint32_t res;
        !           431:        uint32_t flags = 0;
        !           432:        /* were gonna have to redo the muls.  */
        !           433:        uint64_t tmp, t0 ,t1;
        !           434:        uint32_t mof;
        !           435: 
        !           436:        src = env->cc_src;
        !           437:        dst = env->cc_dest;
        !           438:        res = env->cc_result;
        !           439: 
        !           440: 
        !           441:        /* cast into signed values to make GCC sign extend.  */
        !           442:        t0 = src;
        !           443:        t1 = dst;
        !           444: 
        !           445:        tmp = t0 * t1;
        !           446:        mof = tmp >> 32;
        !           447:        if (tmp == 0)
        !           448:                flags |= Z_FLAG;
        !           449:        else if (tmp >> 63)
        !           450:                flags |= N_FLAG;
        !           451:        if (mof)
        !           452:                flags |= V_FLAG;
        !           453: 
        !           454:        evaluate_flags_writeback(flags);
        !           455:        RETURN();
        !           456: }
        !           457: 
        !           458: void OPPROTO op_evaluate_flags_mcp(void)
        !           459: {
        !           460:        uint32_t src;
        !           461:        uint32_t dst;
        !           462:        uint32_t res;
        !           463:        uint32_t flags = 0;
        !           464: 
        !           465:        src = env->cc_src;
        !           466:        dst = env->cc_dest;
        !           467:        res = env->cc_result;
        !           468: 
        !           469:        if ((res & 0x80000000L) != 0L)
        !           470:        {
        !           471:                flags |= N_FLAG;
        !           472:                if (((src & 0x80000000L) == 0L)
        !           473:                    && ((dst & 0x80000000L) == 0L))
        !           474:                {
        !           475:                        flags |= V_FLAG;
        !           476:                }
        !           477:                else if (((src & 0x80000000L) != 0L) &&
        !           478:                         ((dst & 0x80000000L) != 0L))
        !           479:                {
        !           480:                        flags |= R_FLAG;
        !           481:                }
        !           482:        }
        !           483:        else
        !           484:        {
        !           485:                if (res == 0L)
        !           486:                        flags |= Z_FLAG;
        !           487:                if (((src & 0x80000000L) != 0L)
        !           488:                    && ((dst & 0x80000000L) != 0L))
        !           489:                        flags |= V_FLAG;
        !           490:                if ((dst & 0x80000000L) != 0L
        !           491:                    || (src & 0x80000000L) != 0L)
        !           492:                        flags |= R_FLAG;
        !           493:        }
        !           494: 
        !           495:        evaluate_flags_writeback(flags);
        !           496:        RETURN();
        !           497: }
        !           498: 
        !           499: void OPPROTO op_evaluate_flags_alu_4(void)
        !           500: {
        !           501:        uint32_t src;
        !           502:        uint32_t dst;
        !           503:        uint32_t res;
        !           504:        uint32_t flags = 0;
        !           505: 
        !           506:        src = env->cc_src;
        !           507:        dst = env->cc_dest;
        !           508:        res = env->cc_result;
        !           509: 
        !           510:        if ((res & 0x80000000L) != 0L)
        !           511:        {
        !           512:                flags |= N_FLAG;
        !           513:                if (((src & 0x80000000L) == 0L)
        !           514:                    && ((dst & 0x80000000L) == 0L))
        !           515:                {
        !           516:                        flags |= V_FLAG;
        !           517:                }
        !           518:                else if (((src & 0x80000000L) != 0L) &&
        !           519:                         ((dst & 0x80000000L) != 0L))
        !           520:                {
        !           521:                        flags |= C_FLAG;
        !           522:                }
        !           523:        }
        !           524:        else
        !           525:        {
        !           526:                if (res == 0L)
        !           527:                        flags |= Z_FLAG;
        !           528:                if (((src & 0x80000000L) != 0L)
        !           529:                    && ((dst & 0x80000000L) != 0L))
        !           530:                        flags |= V_FLAG;
        !           531:                if ((dst & 0x80000000L) != 0L
        !           532:                    || (src & 0x80000000L) != 0L)
        !           533:                        flags |= C_FLAG;
        !           534:        }
        !           535: 
        !           536:        if (env->cc_op == CC_OP_SUB
        !           537:            || env->cc_op == CC_OP_CMP) {
        !           538:                flags ^= C_FLAG;
        !           539:        }
        !           540:        evaluate_flags_writeback(flags);
        !           541:        RETURN();
        !           542: }
        !           543: 
        !           544: void OPPROTO op_evaluate_flags_move_4 (void)
        !           545: {
        !           546:        uint32_t src;
        !           547:        uint32_t res;
        !           548:        uint32_t flags = 0;
        !           549: 
        !           550:        src = env->cc_src;
        !           551:        res = env->cc_result;
        !           552: 
        !           553:        if ((int32_t)res < 0)
        !           554:                flags |= N_FLAG;
        !           555:        else if (res == 0L)
        !           556:                flags |= Z_FLAG;
        !           557: 
        !           558:        evaluate_flags_writeback(flags);
        !           559:        RETURN();
        !           560: }
        !           561: void OPPROTO op_evaluate_flags_move_2 (void)
        !           562: {
        !           563:        uint32_t src;
        !           564:        uint32_t flags = 0;
        !           565:        uint16_t res;
        !           566: 
        !           567:        src = env->cc_src;
        !           568:        res = env->cc_result;
        !           569: 
        !           570:        if ((int16_t)res < 0L)
        !           571:                flags |= N_FLAG;
        !           572:        else if (res == 0)
        !           573:                flags |= Z_FLAG;
        !           574: 
        !           575:        evaluate_flags_writeback(flags);
        !           576:        RETURN();
        !           577: }
        !           578: 
        !           579: /* TODO: This is expensive. We could split things up and only evaluate part of
        !           580:    CCR on a need to know basis. For now, we simply re-evaluate everything.  */
        !           581: void OPPROTO op_evaluate_flags (void)
        !           582: {
        !           583:        uint32_t src;
        !           584:        uint32_t dst;
        !           585:        uint32_t res;
        !           586:        uint32_t flags = 0;
        !           587: 
        !           588:        src = env->cc_src;
        !           589:        dst = env->cc_dest;
        !           590:        res = env->cc_result;
        !           591: 
        !           592: 
        !           593:        /* Now, evaluate the flags. This stuff is based on
        !           594:           Per Zander's CRISv10 simulator.  */
        !           595:        switch (env->cc_size)
        !           596:        {
        !           597:                case 1:
        !           598:                        if ((res & 0x80L) != 0L)
        !           599:                        {
        !           600:                                flags |= N_FLAG;
        !           601:                                if (((src & 0x80L) == 0L)
        !           602:                                    && ((dst & 0x80L) == 0L))
        !           603:                                {
        !           604:                                        flags |= V_FLAG;
        !           605:                                }
        !           606:                                else if (((src & 0x80L) != 0L)
        !           607:                                         && ((dst & 0x80L) != 0L))
        !           608:                                {
        !           609:                                        flags |= C_FLAG;
        !           610:                                }
        !           611:                        }
        !           612:                        else
        !           613:                        {
        !           614:                                if ((res & 0xFFL) == 0L)
        !           615:                                {
        !           616:                                        flags |= Z_FLAG;
        !           617:                                }
        !           618:                                if (((src & 0x80L) != 0L)
        !           619:                                    && ((dst & 0x80L) != 0L))
        !           620:                                {
        !           621:                                        flags |= V_FLAG;
        !           622:                                }
        !           623:                                if ((dst & 0x80L) != 0L
        !           624:                                    || (src & 0x80L) != 0L)
        !           625:                                {
        !           626:                                        flags |= C_FLAG;
        !           627:                                }
        !           628:                        }
        !           629:                        break;
        !           630:                case 2:
        !           631:                        if ((res & 0x8000L) != 0L)
        !           632:                        {
        !           633:                                flags |= N_FLAG;
        !           634:                                if (((src & 0x8000L) == 0L)
        !           635:                                    && ((dst & 0x8000L) == 0L))
        !           636:                                {
        !           637:                                        flags |= V_FLAG;
        !           638:                                }
        !           639:                                else if (((src & 0x8000L) != 0L)
        !           640:                                         && ((dst & 0x8000L) != 0L))
        !           641:                                {
        !           642:                                        flags |= C_FLAG;
        !           643:                                }
        !           644:                        }
        !           645:                        else
        !           646:                        {
        !           647:                                if ((res & 0xFFFFL) == 0L)
        !           648:                                {
        !           649:                                        flags |= Z_FLAG;
        !           650:                                }
        !           651:                                if (((src & 0x8000L) != 0L)
        !           652:                                    && ((dst & 0x8000L) != 0L))
        !           653:                                {
        !           654:                                        flags |= V_FLAG;
        !           655:                                }
        !           656:                                if ((dst & 0x8000L) != 0L
        !           657:                                    || (src & 0x8000L) != 0L)
        !           658:                                {
        !           659:                                        flags |= C_FLAG;
        !           660:                                }
        !           661:                        }
        !           662:                        break;
        !           663:                case 4:
        !           664:                        if ((res & 0x80000000L) != 0L)
        !           665:                        {
        !           666:                                flags |= N_FLAG;
        !           667:                                if (((src & 0x80000000L) == 0L)
        !           668:                                    && ((dst & 0x80000000L) == 0L))
        !           669:                                {
        !           670:                                        flags |= V_FLAG;
        !           671:                                }
        !           672:                                else if (((src & 0x80000000L) != 0L) &&
        !           673:                                         ((dst & 0x80000000L) != 0L))
        !           674:                                {
        !           675:                                        flags |= C_FLAG;
        !           676:                                }
        !           677:                        }
        !           678:                        else
        !           679:                        {
        !           680:                                if (res == 0L)
        !           681:                                        flags |= Z_FLAG;
        !           682:                                if (((src & 0x80000000L) != 0L)
        !           683:                                    && ((dst & 0x80000000L) != 0L))
        !           684:                                        flags |= V_FLAG;
        !           685:                                if ((dst & 0x80000000L) != 0L
        !           686:                                    || (src & 0x80000000L) != 0L)
        !           687:                                        flags |= C_FLAG;
        !           688:                        }
        !           689:                        break;
        !           690:                default:
        !           691:                        break;
        !           692:        }
        !           693: 
        !           694:        if (env->cc_op == CC_OP_SUB
        !           695:            || env->cc_op == CC_OP_CMP) {
        !           696:                flags ^= C_FLAG;
        !           697:        }
        !           698:        evaluate_flags_writeback(flags);
        !           699:        RETURN();
        !           700: }
        !           701: 
        !           702: void OPPROTO op_extb_T0_T0 (void)
        !           703: {
        !           704:        T0 = ((int8_t)T0);
        !           705:        RETURN();
        !           706: }
        !           707: void OPPROTO op_extb_T1_T0 (void)
        !           708: {
        !           709:        T1 = ((int8_t)T0);
        !           710:        RETURN();
        !           711: }
        !           712: void OPPROTO op_extb_T1_T1 (void)
        !           713: {
        !           714:        T1 = ((int8_t)T1);
        !           715:        RETURN();
        !           716: }
        !           717: void OPPROTO op_zextb_T0_T0 (void)
        !           718: {
        !           719:        T0 = ((uint8_t)T0);
        !           720:        RETURN();
        !           721: }
        !           722: void OPPROTO op_zextb_T1_T0 (void)
        !           723: {
        !           724:        T1 = ((uint8_t)T0);
        !           725:        RETURN();
        !           726: }
        !           727: void OPPROTO op_zextb_T1_T1 (void)
        !           728: {
        !           729:        T1 = ((uint8_t)T1);
        !           730:        RETURN();
        !           731: }
        !           732: void OPPROTO op_extw_T0_T0 (void)
        !           733: {
        !           734:        T0 = ((int16_t)T0);
        !           735:        RETURN();
        !           736: }
        !           737: void OPPROTO op_extw_T1_T0 (void)
        !           738: {
        !           739:        T1 = ((int16_t)T0);
        !           740:        RETURN();
        !           741: }
        !           742: void OPPROTO op_extw_T1_T1 (void)
        !           743: {
        !           744:        T1 = ((int16_t)T1);
        !           745:        RETURN();
        !           746: }
        !           747: 
        !           748: void OPPROTO op_zextw_T0_T0 (void)
        !           749: {
        !           750:        T0 = ((uint16_t)T0);
        !           751:        RETURN();
        !           752: }
        !           753: void OPPROTO op_zextw_T1_T0 (void)
        !           754: {
        !           755:        T1 = ((uint16_t)T0);
        !           756:        RETURN();
        !           757: }
        !           758: 
        !           759: void OPPROTO op_zextw_T1_T1 (void)
        !           760: {
        !           761:        T1 = ((uint16_t)T1);
        !           762:        RETURN();
        !           763: }
        !           764: 
        !           765: void OPPROTO op_movl_T0_im (void)
        !           766: {
        !           767:        T0 = PARAM1;
        !           768:        RETURN();
        !           769: }
        !           770: void OPPROTO op_movl_T1_im (void)
        !           771: {
        !           772:        T1 = PARAM1;
        !           773:        RETURN();
        !           774: }
        !           775: 
        !           776: void OPPROTO op_addl_T0_im (void)
        !           777: {
        !           778:        T0 += PARAM1;
        !           779:        RETURN();
        !           780: }
        !           781: 
        !           782: void OPPROTO op_addl_T1_im (void)
        !           783: {
        !           784:        T1 += PARAM1;
        !           785:        RETURN();
        !           786: 
        !           787: }
        !           788: void OPPROTO op_subl_T0_im (void)
        !           789: {
        !           790:        T0 -= PARAM1;
        !           791:        RETURN();
        !           792: }
        !           793: 
        !           794: void OPPROTO op_addxl_T0_C (void)
        !           795: {
        !           796:        if (env->pregs[SR_CCS] & X_FLAG)
        !           797:                T0 += !!(env->pregs[SR_CCS] & C_FLAG);
        !           798:        RETURN();
        !           799: }
        !           800: void OPPROTO op_subxl_T0_C (void)
        !           801: {
        !           802:        if (env->pregs[SR_CCS] & X_FLAG)
        !           803:                T0 -= !!(env->pregs[SR_CCS] & C_FLAG);
        !           804:        RETURN();
        !           805: }
        !           806: void OPPROTO op_addl_T0_C (void)
        !           807: {
        !           808:        T0 += !!(env->pregs[SR_CCS] & C_FLAG);
        !           809:        RETURN();
        !           810: }
        !           811: void OPPROTO op_addl_T0_R (void)
        !           812: {
        !           813:        T0 += !!(env->pregs[SR_CCS] & R_FLAG);
        !           814:        RETURN();
        !           815: }
        !           816: 
        !           817: void OPPROTO op_clr_R (void)
        !           818: {
        !           819:        env->pregs[SR_CCS] &= ~R_FLAG;
        !           820:        RETURN();
        !           821: }
        !           822: 
        !           823: 
        !           824: void OPPROTO op_andl_T0_im (void)
        !           825: {
        !           826:        T0 &= PARAM1;
        !           827:        RETURN();
        !           828: }
        !           829: 
        !           830: void OPPROTO op_andl_T1_im (void)
        !           831: {
        !           832:        T1 &= PARAM1;
        !           833:        RETURN();
        !           834: }
        !           835: 
        !           836: void OPPROTO op_movl_T0_T1 (void)
        !           837: {
        !           838:        T0 = T1;
        !           839:        RETURN();
        !           840: }
        !           841: 
        !           842: void OPPROTO op_swp_T0_T1 (void)
        !           843: {
        !           844:        T0 ^= T1;
        !           845:        T1 ^= T0;
        !           846:        T0 ^= T1;
        !           847:        RETURN();
        !           848: }
        !           849: 
        !           850: void OPPROTO op_movl_T1_T0 (void)
        !           851: {
        !           852:        T1 = T0;
        !           853:        RETURN();
        !           854: }
        !           855: 
        !           856: void OPPROTO op_movl_pc_T0 (void)
        !           857: {
        !           858:        env->pc = T0;
        !           859:        RETURN();
        !           860: }
        !           861: 
        !           862: void OPPROTO op_movl_T0_0 (void)
        !           863: {
        !           864:        T0 = 0;
        !           865:        RETURN();
        !           866: }
        !           867: 
        !           868: void OPPROTO op_addl_T0_T1 (void)
        !           869: {
        !           870:        T0 += T1;
        !           871:        RETURN();
        !           872: }
        !           873: 
        !           874: void OPPROTO op_subl_T0_T1 (void)
        !           875: {
        !           876:        T0 -= T1;
        !           877:        RETURN();
        !           878: }
        !           879: 
        !           880: void OPPROTO op_absl_T1_T1 (void)
        !           881: {
        !           882:        int32_t st = T1;
        !           883: 
        !           884:        T1 = st < 0 ? -st : st;
        !           885:        RETURN();
        !           886: }
        !           887: 
        !           888: void OPPROTO op_muls_T0_T1 (void)
        !           889: {
        !           890:        int64_t tmp, t0 ,t1;
        !           891: 
        !           892:        /* cast into signed values to make GCC sign extend these babies.  */
        !           893:        t0 = (int32_t)T0;
        !           894:        t1 = (int32_t)T1;
        !           895: 
        !           896:        tmp = t0 * t1;
        !           897:        T0 = tmp & 0xffffffff;
        !           898:        env->pregs[REG_MOF] = tmp >> 32;
        !           899:        RETURN();
        !           900: }
        !           901: 
        !           902: void OPPROTO op_mulu_T0_T1 (void)
        !           903: {
        !           904:        uint64_t tmp, t0 ,t1;
        !           905:        t0 = T0;
        !           906:        t1 = T1;
        !           907: 
        !           908:        tmp = t0 * t1;
        !           909:        T0 = tmp & 0xffffffff;
        !           910:        env->pregs[REG_MOF] = tmp >> 32;
        !           911:        RETURN();
        !           912: }
        !           913: 
        !           914: void OPPROTO op_dstep_T0_T1 (void)
        !           915: {
        !           916:        T0 <<= 1;
        !           917:        if (T0 >= T1)
        !           918:                T0 -= T1;
        !           919:        RETURN();
        !           920: }
        !           921: 
        !           922: void OPPROTO op_orl_T0_T1 (void)
        !           923: {
        !           924:        T0 |= T1;
        !           925:        RETURN();
        !           926: }
        !           927: 
        !           928: void OPPROTO op_andl_T0_T1 (void)
        !           929: {
        !           930:        T0 &= T1;
        !           931:        RETURN();
        !           932: }
        !           933: 
        !           934: void OPPROTO op_xorl_T0_T1 (void)
        !           935: {
        !           936:        T0 ^= T1;
        !           937:        RETURN();
        !           938: }
        !           939: 
        !           940: void OPPROTO op_lsll_T0_T1 (void)
        !           941: {
        !           942:        int s = T1;
        !           943:        if (s > 31)
        !           944:                T0 = 0;
        !           945:        else
        !           946:                T0 <<= s;
        !           947:        RETURN();
        !           948: }
        !           949: 
        !           950: void OPPROTO op_lsll_T0_im (void)
        !           951: {
        !           952:        T0 <<= PARAM1;
        !           953:        RETURN();
        !           954: }
        !           955: 
        !           956: void OPPROTO op_lsrl_T0_T1 (void)
        !           957: {
        !           958:        int s = T1;
        !           959:        if (s > 31)
        !           960:                T0 = 0;
        !           961:        else
        !           962:                T0 >>= s;
        !           963:        RETURN();
        !           964: }
        !           965: 
        !           966: /* Rely on GCC emitting an arithmetic shift for signed right shifts.  */
        !           967: void OPPROTO op_asrl_T0_T1 (void)
        !           968: {
        !           969:        int s = T1;
        !           970:        if (s > 31)
        !           971:                T0 = T0 & 0x80000000 ? -1 : 0;
        !           972:        else
        !           973:                T0 = (int32_t)T0 >> s;
        !           974:        RETURN();
        !           975: }
        !           976: 
        !           977: void OPPROTO op_btst_T0_T1 (void)
        !           978: {
        !           979:        /* FIXME: clean this up.  */
        !           980: 
        !           981:        /* des ref:
        !           982:           The N flag is set according to the selected bit in the dest reg.
        !           983:           The Z flag is set if the selected bit and all bits to the right are
        !           984:           zero.
        !           985:           The destination reg is not affected.*/
        !           986:        unsigned int fz, sbit, bset, mask, masked_t0;
        !           987: 
        !           988:        sbit = T1 & 31;
        !           989:         bset = !!(T0 & (1 << sbit));
        !           990:        mask = sbit == 31 ? -1 : (1 << (sbit + 1)) - 1;
        !           991:        masked_t0 = T0 & mask;
        !           992:        fz = !(masked_t0 | bset);
        !           993:        /* Set the N and Z flags accordingly.  */
        !           994:        T0 = (bset << 3) | (fz << 2);
        !           995:        RETURN();
        !           996: }
        !           997: 
        !           998: void OPPROTO op_bound_T0_T1 (void)
        !           999: {
        !          1000:        if (T0 > T1)
        !          1001:                T0 = T1;
        !          1002:        RETURN();
        !          1003: }
        !          1004: 
        !          1005: void OPPROTO op_lz_T0_T1 (void)
        !          1006: {
        !          1007:        T0 = clz32(T1);
        !          1008:        RETURN();
        !          1009: }
        !          1010: 
        !          1011: void OPPROTO op_negl_T0_T1 (void)
        !          1012: {
        !          1013:        T0 = -T1;
        !          1014:        RETURN();
        !          1015: }
        !          1016: 
        !          1017: void OPPROTO op_negl_T1_T1 (void)
        !          1018: {
        !          1019:        T1 = -T1;
        !          1020:        RETURN();
        !          1021: }
        !          1022: 
        !          1023: void OPPROTO op_not_T0_T0 (void)
        !          1024: {
        !          1025:        T0 = ~(T0);
        !          1026:        RETURN();
        !          1027: }
        !          1028: void OPPROTO op_not_T1_T1 (void)
        !          1029: {
        !          1030:        T1 = ~(T1);
        !          1031:        RETURN();
        !          1032: }
        !          1033: 
        !          1034: void OPPROTO op_swapw_T0_T0 (void)
        !          1035: {
        !          1036:        T0 = (T0 << 16) | ((T0 >> 16));
        !          1037:        RETURN();
        !          1038: }
        !          1039: 
        !          1040: void OPPROTO op_swapb_T0_T0 (void)
        !          1041: {
        !          1042:        T0 = ((T0 << 8) & 0xff00ff00) | ((T0 >> 8) & 0x00ff00ff);
        !          1043:        RETURN();
        !          1044: }
        !          1045: 
        !          1046: void OPPROTO op_swapr_T0_T0 (void)
        !          1047: {
        !          1048:        T0 = (((T0 << 7) & 0x80808080) |
        !          1049:              ((T0 << 5) & 0x40404040) |
        !          1050:              ((T0 << 3) & 0x20202020) |
        !          1051:              ((T0 << 1) & 0x10101010) |
        !          1052:              ((T0 >> 1) & 0x08080808) |
        !          1053:              ((T0 >> 3) & 0x04040404) |
        !          1054:              ((T0 >> 5) & 0x02020202) |
        !          1055:              ((T0 >> 7) & 0x01010101));
        !          1056:        RETURN();
        !          1057: }
        !          1058: 
        !          1059: void OPPROTO op_tst_cc_eq (void) {
        !          1060:        uint32_t flags = env->pregs[SR_CCS];
        !          1061:        int z_set;
        !          1062: 
        !          1063:        z_set = !!(flags & Z_FLAG);
        !          1064:        T0 = z_set;
        !          1065:        RETURN();
        !          1066: }
        !          1067: 
        !          1068: void OPPROTO op_tst_cc_eq_fast (void) {
        !          1069:        T0 = !(env->cc_result);
        !          1070:        RETURN();
        !          1071: }
        !          1072: 
        !          1073: void OPPROTO op_tst_cc_ne (void) {
        !          1074:        uint32_t flags = env->pregs[SR_CCS];
        !          1075:        int z_set;
        !          1076: 
        !          1077:        z_set = !!(flags & Z_FLAG);
        !          1078:        T0 = !z_set;
        !          1079:        RETURN();
        !          1080: }
        !          1081: void OPPROTO op_tst_cc_ne_fast (void) {
        !          1082:        T0 = !!(env->cc_result);
        !          1083:        RETURN();
        !          1084: }
        !          1085: 
        !          1086: void OPPROTO op_tst_cc_cc (void) {
        !          1087:        uint32_t flags = env->pregs[SR_CCS];
        !          1088:        int c_set;
        !          1089: 
        !          1090:        c_set = !!(flags & C_FLAG);
        !          1091:        T0 = !c_set;
        !          1092:        RETURN();
        !          1093: }
        !          1094: void OPPROTO op_tst_cc_cs (void) {
        !          1095:        uint32_t flags = env->pregs[SR_CCS];
        !          1096:        int c_set;
        !          1097: 
        !          1098:        c_set = !!(flags & C_FLAG);
        !          1099:        T0 = c_set;
        !          1100:        RETURN();
        !          1101: }
        !          1102: 
        !          1103: void OPPROTO op_tst_cc_vc (void) {
        !          1104:        uint32_t flags = env->pregs[SR_CCS];
        !          1105:        int v_set;
        !          1106: 
        !          1107:        v_set = !!(flags & V_FLAG);
        !          1108:        T0 = !v_set;
        !          1109:        RETURN();
        !          1110: }
        !          1111: void OPPROTO op_tst_cc_vs (void) {
        !          1112:        uint32_t flags = env->pregs[SR_CCS];
        !          1113:        int v_set;
        !          1114: 
        !          1115:        v_set = !!(flags & V_FLAG);
        !          1116:        T0 = v_set;
        !          1117:        RETURN();
        !          1118: }
        !          1119: void OPPROTO op_tst_cc_pl (void) {
        !          1120:        uint32_t flags = env->pregs[SR_CCS];
        !          1121:        int n_set;
        !          1122: 
        !          1123:        n_set = !!(flags & N_FLAG);
        !          1124:        T0 = !n_set;
        !          1125:        RETURN();
        !          1126: }
        !          1127: void OPPROTO op_tst_cc_pl_fast (void) {
        !          1128:        T0 = ((int32_t)env->cc_result) >= 0;
        !          1129:        RETURN();
        !          1130: }
        !          1131: 
        !          1132: void OPPROTO op_tst_cc_mi (void) {
        !          1133:        uint32_t flags = env->pregs[SR_CCS];
        !          1134:        int n_set;
        !          1135: 
        !          1136:        n_set = !!(flags & N_FLAG);
        !          1137:        T0 = n_set;
        !          1138:        RETURN();
        !          1139: }
        !          1140: void OPPROTO op_tst_cc_mi_fast (void) {
        !          1141:        T0 = ((int32_t)env->cc_result) < 0;
        !          1142:        RETURN();
        !          1143: }
        !          1144: 
        !          1145: void OPPROTO op_tst_cc_ls (void) {
        !          1146:        uint32_t flags = env->pregs[SR_CCS];
        !          1147:        int c_set;
        !          1148:        int z_set;
        !          1149: 
        !          1150:        c_set = !!(flags & C_FLAG);
        !          1151:        z_set = !!(flags & Z_FLAG);
        !          1152:        T0 = c_set || z_set;
        !          1153:        RETURN();
        !          1154: }
        !          1155: void OPPROTO op_tst_cc_hi (void) {
        !          1156:        uint32_t flags = env->pregs[SR_CCS];
        !          1157:        int z_set;
        !          1158:        int c_set;
        !          1159: 
        !          1160:        z_set = !!(flags & Z_FLAG);
        !          1161:        c_set = !!(flags & C_FLAG);
        !          1162:        T0 = !c_set && !z_set;
        !          1163:        RETURN();
        !          1164: 
        !          1165: }
        !          1166: 
        !          1167: void OPPROTO op_tst_cc_ge (void) {
        !          1168:        uint32_t flags = env->pregs[SR_CCS];
        !          1169:        int n_set;
        !          1170:        int v_set;
        !          1171: 
        !          1172:        n_set = !!(flags & N_FLAG);
        !          1173:        v_set = !!(flags & V_FLAG);
        !          1174:        T0 = (n_set && v_set) || (!n_set && !v_set);
        !          1175:        RETURN();
        !          1176: }
        !          1177: 
        !          1178: void OPPROTO op_tst_cc_ge_fast (void) {
        !          1179:        T0 = ((int32_t)env->cc_src < (int32_t)env->cc_dest);
        !          1180:        RETURN();
        !          1181: }
        !          1182: 
        !          1183: void OPPROTO op_tst_cc_lt (void) {
        !          1184:        uint32_t flags = env->pregs[SR_CCS];
        !          1185:        int n_set;
        !          1186:        int v_set;
        !          1187: 
        !          1188:        n_set = !!(flags & N_FLAG);
        !          1189:        v_set = !!(flags & V_FLAG);
        !          1190:        T0 = (n_set && !v_set) || (!n_set && v_set);
        !          1191:        RETURN();
        !          1192: }
        !          1193: 
        !          1194: void OPPROTO op_tst_cc_gt (void) {
        !          1195:        uint32_t flags = env->pregs[SR_CCS];
        !          1196:        int n_set;
        !          1197:        int v_set;
        !          1198:        int z_set;
        !          1199: 
        !          1200:        n_set = !!(flags & N_FLAG);
        !          1201:        v_set = !!(flags & V_FLAG);
        !          1202:        z_set = !!(flags & Z_FLAG);
        !          1203:        T0 = (n_set && v_set && !z_set)
        !          1204:                || (!n_set && !v_set && !z_set);
        !          1205:        RETURN();
        !          1206: }
        !          1207: 
        !          1208: void OPPROTO op_tst_cc_le (void) {
        !          1209:        uint32_t flags = env->pregs[SR_CCS];
        !          1210:        int n_set;
        !          1211:        int v_set;
        !          1212:        int z_set;
        !          1213: 
        !          1214:        n_set = !!(flags & N_FLAG);
        !          1215:        v_set = !!(flags & V_FLAG);
        !          1216:        z_set = !!(flags & Z_FLAG);
        !          1217:        T0 = z_set || (n_set && !v_set) || (!n_set && v_set);
        !          1218:        RETURN();
        !          1219: }
        !          1220: 
        !          1221: void OPPROTO op_tst_cc_p (void) {
        !          1222:        uint32_t flags = env->pregs[SR_CCS];
        !          1223:        int p_set;
        !          1224: 
        !          1225:        p_set = !!(flags & P_FLAG);
        !          1226:        T0 = p_set;
        !          1227:        RETURN();
        !          1228: }
        !          1229: 
        !          1230: /* Evaluate the if the branch should be taken or not. Needs to be done in
        !          1231:    the original sequence. The acutal branch is rescheduled to right after the
        !          1232:    delay-slot.  */
        !          1233: void OPPROTO op_evaluate_bcc (void)
        !          1234: {
        !          1235:        env->btaken = T0;
        !          1236:        RETURN();
        !          1237: }
        !          1238: 
        !          1239: /* this one is used on every alu op, optimize it!.  */
        !          1240: void OPPROTO op_goto_if_not_x (void)
        !          1241: {
        !          1242:        if (env->pregs[SR_CCS] & X_FLAG)
        !          1243:                GOTO_LABEL_PARAM(1);
        !          1244:        RETURN();
        !          1245: }
        !          1246: 
        !          1247: void OPPROTO op_cc_jmp (void)
        !          1248: {
        !          1249:        if (env->btaken)
        !          1250:                env->pc = PARAM1;
        !          1251:        else
        !          1252:                env->pc = PARAM2;
        !          1253:        RETURN();
        !          1254: }
        !          1255: 
        !          1256: void OPPROTO op_cc_ngoto (void)
        !          1257: {
        !          1258:        if (!env->btaken)
        !          1259:                GOTO_LABEL_PARAM(1);
        !          1260:        RETURN();
        !          1261: }
        !          1262: 
        !          1263: void OPPROTO op_movl_btarget_T0 (void)
        !          1264: {
        !          1265:        env->btarget = T0;
        !          1266:        RETURN();
        !          1267: }
        !          1268: 
        !          1269: void OPPROTO op_jmp (void)
        !          1270: {
        !          1271:        env->pc = env->btarget;
        !          1272:        RETURN();
        !          1273: }
        !          1274: 
        !          1275: /* Load and store */
        !          1276: #define MEMSUFFIX _raw
        !          1277: #include "op_mem.c"
        !          1278: #undef MEMSUFFIX
        !          1279: #if !defined(CONFIG_USER_ONLY)
        !          1280: #define MEMSUFFIX _user
        !          1281: #include "op_mem.c"
        !          1282: #undef MEMSUFFIX
        !          1283: 
        !          1284: #define MEMSUFFIX _kernel
        !          1285: #include "op_mem.c"
        !          1286: #undef MEMSUFFIX
        !          1287: #endif

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.