Note: This website is archived. For up-to-date information about D projects and development, please visit wiki.dlang.org.

Changeset 619

Show
Ignore:
Timestamp:
08/17/10 19:39:11 (14 years ago)
Author:
walter
Message:

more 64 bits

Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • branches/dmd-1.x/src/backend/cgcod.c

    r618 r619  
    124124 
    125125    //printf("codgen('%s')\n",funcsym_p->Sident); 
    126126 
    127127    cgreg_init(); 
    128128    csmax = 64; 
    129129    csextab = (struct CSE *) util_calloc(sizeof(struct CSE),csmax); 
    130130    functy = tybasic(funcsym_p->ty()); 
    131131#if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_SOLARIS 
    132132    if (0 && config.flags3 & CFG3pic) 
    133133    { 
    134134        ALLREGS = ALLREGS_INIT_PIC; 
    135135        BYTEREGS = BYTEREGS_INIT_PIC; 
    136136    } 
    137137    else 
    138138    { 
    139139        regm_t value = BYTEREGS_INIT; 
    140140        ALLREGS = ALLREGS_INIT; 
    141141        BYTEREGS = value; 
    142142    } 
    143143    if (I64) 
    144         ALLREGS = mAX|mBX|mCX|mDX|mSI|mDI| mR8|mR9|mR10|mR11|mR12|mR13|mR14|mR15; 
     144    {   ALLREGS = mAX|mBX|mCX|mDX|mSI|mDI| mR8|mR9|mR10|mR11|mR12|mR13|mR14|mR15; 
     145        BYTEREGS = ALLREGS; 
     146    } 
    145147#endif 
    146148    allregs = ALLREGS; 
    147149    if (0 && config.flags3 & CFG3pic) 
    148150        allregs &= ~mBX; 
    149151    pass = PASSinit; 
    150152 
    151153tryagain: 
    152154    #ifdef DEBUG 
    153155    if (debugr) 
    154156        printf("------------------ PASS%s -----------------\n", 
    155157            (pass == PASSinit) ? "init" : ((pass == PASSreg) ? "reg" : "final")); 
    156158    #endif 
    157159    lastretregs = last2retregs = last3retregs = last4retregs = last5retregs = 0; 
    158160 
    159161    // if no parameters, assume we don't need a stack frame 
    160162    needframe = 0; 
    161163    usedalloca = 0; 
    162164    gotref = 0; 
    163165    stackchanged = 0; 
    164166    stackpush = 0; 
     
    22782280                regcon.immed.mval | regcon.params | mfuncreg); 
    22792281    } 
    22802282    return scratch; 
    22812283} 
    22822284 
    22832285 
    22842286/****************************** 
    22852287 * Evaluate an elem that is a common subexp that has been encountered 
    22862288 * before. 
    22872289 * Look first to see if it is already in a register. 
    22882290 */ 
    22892291 
    22902292STATIC code * comsub(elem *e,regm_t *pretregs) 
    22912293{   tym_t tym; 
    22922294    regm_t regm,emask,csemask; 
    22932295    unsigned reg,i,byte,sz; 
    22942296    code *c; 
    22952297    int forcc;                  // !=0 if we evaluate for condition codes 
    22962298    int forregs;                // !=0 if we evaluate into registers 
    22972299 
    2298     //printf("comsub(e = %p, *pretregs = x%x)\n",e,*pretregs); 
     2300    //printf("comsub(e = %p, *pretregs = %s)\n",e,regm_str(*pretregs)); 
    22992301    elem_debug(e); 
    23002302#ifdef DEBUG 
    23012303    if (e->Ecomsub > e->Ecount) 
    23022304        elem_print(e); 
    23032305#endif 
    23042306    assert(e->Ecomsub <= e->Ecount); 
    23052307 
    23062308  c = CNIL; 
    23072309  if (*pretregs == 0) goto done;        /* no possible side effects anyway */ 
    23082310 
    23092311    if (tyfloating(e->Ety) && config.inline8087) 
    23102312        return comsub87(e,pretregs); 
    23112313 
    23122314  /* First construct a mask, emask, of all the registers that   */ 
    23132315  /* have the right contents.                                   */ 
    23142316 
    23152317  emask = 0; 
    23162318  for (i = 0; i < arraysize(regcon.cse.value); i++) 
    23172319  { 
    23182320        //dbg_printf("regcon.cse.value[%d] = %p\n",i,regcon.cse.value[i]); 
     
    25662568 *                      Note:   longs are in AX,BX or CX,DX or SI,DI 
    25672569 *                              doubles are AX,BX,CX,DX only 
    25682570 *      constflag       TRUE if user of result will not modify the 
    25692571 *                      registers returned in *pretregs. 
    25702572 * Output: 
    25712573 *      *pretregs       mask of registers result is returned in 
    25722574 * Returns: 
    25732575 *      pointer to code sequence generated 
    25742576 */ 
    25752577 
    25762578#include "cdxxx.c"                      /* jump table                   */ 
    25772579 
    25782580code *codelem(elem *e,regm_t *pretregs,bool constflag) 
    25792581{ code *c; 
    25802582  Symbol *s; 
    25812583  tym_t tym; 
    25822584  unsigned op; 
    25832585 
    25842586#ifdef DEBUG 
    25852587  if (debugw) 
    2586   {     printf("+codelem(e=%p,*pretregs=x%x) ",e,*pretregs); 
     2588  {     printf("+codelem(e=%p,*pretregs=%s) ",e,regm_str(*pretregs)); 
    25872589        WROP(e->Eoper); 
    25882590        printf("msavereg=x%x regcon.cse.mval=x%x regcon.cse.mops=x%x\n", 
    25892591                msavereg,regcon.cse.mval,regcon.cse.mops); 
    25902592        printf("Ecount = %d, Ecomsub = %d\n", e->Ecount, e->Ecomsub); 
    25912593  } 
    25922594#endif 
    25932595  assert(e); 
    25942596  elem_debug(e); 
    25952597  if ((regcon.cse.mops & regcon.cse.mval) != regcon.cse.mops) 
    25962598  { 
    25972599#ifdef DEBUG 
    25982600        printf("+codelem(e=%p,*pretregs=x%x) ",e,*pretregs); 
    25992601        elem_print(e); 
    26002602        printf("msavereg=x%x regcon.cse.mval=x%x regcon.cse.mops=x%x\n", 
    26012603                msavereg,regcon.cse.mval,regcon.cse.mops); 
    26022604        printf("Ecount = %d, Ecomsub = %d\n", e->Ecount, e->Ecomsub); 
    26032605#endif 
    26042606        assert(0); 
    26052607  } 
    26062608 
  • branches/dmd-1.x/src/backend/cod1.c

    r618 r619  
    596596        } 
    597597        for (unsigned i = 0; rm; i++) 
    598598        {       if (mask[i] & rm) 
    599599                {       if (regcon.cse.value[i] == e && // if register has elem 
    600600                            /* watch out for a CWD destroying DX        */ 
    601601                            !(i == DX && op == 0xF7 && desmsk & mDX)) 
    602602                        { 
    603603                                /* if ES, then it can only be a load    */ 
    604604                                if (i == ES) 
    605605                                {       if (op != 0x8B) 
    606606                                            goto L1;    /* not a load   */ 
    607607                                        cs->Iop = 0x8C; /* MOV reg,ES   */ 
    608608                                        cs->Irm = modregrm(3,0,reg & 7); 
    609609                                        if (reg & 8) 
    610610                                            code_orrex(cs, REX_B); 
    611611                                } 
    612612                                else    // XXX reg,i 
    613613                                { 
    614614                                    cs->Irm = modregrm(3,reg & 7,i & 7); 
    615615                                    if (reg & 8) 
    616                                         code_orrex(cs, REX_R)
     616                                        cs->Irex |= REX_R
    617617                                    if (i & 8) 
    618                                         code_orrex(cs, REX_B)
     618                                        cs->Irex |= REX_B
    619619                                } 
    620620                                c = CNIL; 
    621621                                goto L2; 
    622622                        } 
    623623                        rm &= ~mask[i]; 
    624624                } 
    625625        } 
    626626  } 
    627627 
    628628L1: 
    629629  c = getlvalue(cs,e,keepmsk); 
    630630  if (offset == REGSIZE) 
    631631        getlvalue_msw(cs); 
    632632  else 
    633633        cs->IEVoffset1 += offset; 
    634634  code_newreg(cs, reg);                         // OR in reg field 
    635635  if (!I16) 
    636636  { 
    637637      if (reg == 6 && op == 0xFF ||             /* don't PUSH a word    */ 
    638638          op == 0x0FB7 || op == 0x0FBF ||       /* MOVZX/MOVSX          */ 
     
    11081107                break; 
    11091108            case TYsptr:                        /* if pointer to stack  */ 
    11101109                if (config.wflags & WFssneds)   // if SS != DS 
    11111110                    pcs->Iflags |= CFss;        /* then need SS: override */ 
    11121111                break; 
    11131112            case TYcptr:                        /* if pointer to code   */ 
    11141113                pcs->Iflags |= CFcs;            /* then need CS: override */ 
    11151114                break; 
    11161115        } 
    11171116#endif 
    11181117        pcs->IFL1 = FLoffset; 
    11191118        pcs->IEV1.Vuns = 0; 
    11201119 
    11211120        /* see if we can replace *(e+c) with 
    11221121         *      MOV     idxreg,e 
    11231122         *      [MOV    ES,segment] 
    11241123         *      EA =    [ES:]c[idxreg] 
    11251124         */ 
    11261125 
    11271126        if (e1isadd && e12->Eoper == OPconst && 
    1128             tysize(e12->Ety) == REGSIZE && 
     1127            (tysize(e12->Ety) == REGSIZE || (I64 && tysize(e12->Ety) == 4)) && 
    11291128            (!e1->Ecount || !e1free) 
    11301129           ) 
    11311130        {   int ss; 
    11321131 
    11331132            pcs->IEV1.Vuns = e12->EV.Vuns; 
    11341133            freenode(e12); 
    11351134            if (e1free) freenode(e1); 
    1136             if (I32 && e11->Eoper == OPadd && !e11->Ecount && 
     1135            if (!I16 && e11->Eoper == OPadd && !e11->Ecount && 
    11371136                tysize(e11->Ety) == REGSIZE) 
    11381137            { 
    11391138                e12 = e11->E2; 
    11401139                e11 = e11->E1; 
    11411140                e1 = e1->E1; 
    11421141                e1free = TRUE; 
    11431142                goto L4; 
    11441143            } 
    11451144            if (!I16 && (ss = isscaledindex(e11)) != 0) 
    11461145            {   // (v * scale) + const 
    11471146                c = cdisscaledindex(e11,&idxregs,keepmsk); 
    11481147                reg = findreg(idxregs); 
    11491148                pcs->Irm = modregrm(0,0,4); 
    11501149                pcs->Isib = modregrm(ss,reg & 7,5); 
    11511150                if (reg & 8) 
    11521151                    pcs->Irex |= REX_X; 
    11531152            } 
    11541153            else 
    11551154            { 
    11561155                c = scodelem(e11,&idxregs,keepmsk,TRUE); // load index reg 
     
    14091408} 
    14101409 
    14111410/******************************* 
    14121411 * Same as codelem(), but do not destroy the registers in keepmsk. 
    14131412 * Use scratch registers as much as possible, then use stack. 
    14141413 * Input: 
    14151414 *      constflag       TRUE if user of result will not modify the 
    14161415 *                      registers returned in *pretregs. 
    14171416 */ 
    14181417 
    14191418code *scodelem(elem *e,regm_t *pretregs,regm_t keepmsk,bool constflag) 
    14201419{ code *c,*cs1,*cs2,*cs3; 
    14211420  unsigned i,j; 
    14221421  regm_t oldmfuncreg,oldregcon,oldregimmed,overlap,tosave,touse; 
    14231422  int adjesp; 
    14241423  unsigned stackpushsave; 
    14251424  char calledafuncsave; 
    14261425 
    14271426#ifdef DEBUG 
    14281427  if (debugw) 
    1429         printf("+scodelem(e=%p *pretregs=x%x keepmsk=x%x constflag=%d\n", 
    1430                 e,*pretregs,keepmsk,constflag); 
     1428        printf("+scodelem(e=%p *pretregs=%s keepmsk=%s constflag=%d\n", 
     1429                e,regm_str(*pretregs),regm_str(keepmsk),constflag); 
    14311430#endif 
    14321431  elem_debug(e); 
    14331432  if (constflag) 
    14341433  {     regm_t regm; 
    14351434        unsigned reg; 
    14361435 
    14371436        if (isregvar(e,&regm,&reg) &&           // if e is a register variable 
    14381437            (regm & *pretregs) == regm &&       // in one of the right regs 
    14391438            e->EV.sp.Voffset == 0 
    14401439           ) 
    1441         {       unsigned sz1,sz2; 
    1442  
    1443                 sz1 = tysize(e->Ety); 
    1444                 sz2 = tysize(e->EV.sp.Vsym->Stype->Tty); 
     1440        { 
     1441                unsigned sz1 = tysize(e->Ety); 
     1442                unsigned sz2 = tysize(e->EV.sp.Vsym->Stype->Tty); 
    14451443                if (sz1 <= REGSIZE && sz2 > REGSIZE) 
    14461444                    regm &= mLSW; 
    14471445                c = fixresult(e,regm,pretregs); 
    14481446                cssave(e,regm,0); 
    14491447                freenode(e); 
    14501448#ifdef DEBUG 
    14511449                if (debugw) 
    14521450                    printf("-scodelem(e=%p *pretregs=x%x keepmsk=x%x constflag=%d\n", 
    14531451                            e,*pretregs,keepmsk,constflag); 
    14541452#endif 
    14551453                return c; 
    14561454        } 
    14571455  } 
    14581456  overlap = msavereg & keepmsk; 
    14591457  msavereg |= keepmsk;          /* add to mask of regs to save          */ 
    14601458  oldregcon = regcon.cse.mval; 
    14611459  oldregimmed = regcon.immed.mval; 
    14621460  oldmfuncreg = mfuncreg;       /* remember old one                     */ 
    14631461  mfuncreg = (mBP | mES | ALLREGS) & ~regcon.mvar; 
    14641462  stackpushsave = stackpush; 
  • branches/dmd-1.x/src/backend/cod3.c

    r606 r619  
    36453645        // If the instruction has a second operand that is not an 8 bit, 
    36463646        // and the operand size prefix is present, then fix the size computation 
    36473647        // because the operand size will be different. 
    36483648        // Walter, I had problems with this bit at the end.  There can still be 
    36493649        // an ADDRSIZE prefix for these and it does indeed change the operand size. 
    36503650 
    36513651        if (iflags & (CFopsize | CFaddrsize)) 
    36523652        { 
    36533653            if ((ins & (T|E)) == T) 
    36543654            { 
    36553655                if ((op & 0xAC) == 0xA0) 
    36563656                { 
    36573657                    if (iflags & CFaddrsize && !I64) 
    36583658                    {   if (I32) 
    36593659                            size -= 2; 
    36603660                        else 
    36613661                            size += 2; 
    36623662                    } 
    36633663                } 
    36643664                else if (iflags & CFopsize) 
    3665                 {   if (I32) 
     3665                {   if (I16) 
     3666                        size += 2; 
     3667                    else 
    36663668                        size -= 2; 
    3667                     else 
    3668                         size += 2; 
    36693669                } 
    36703670            } 
    36713671            if (iflags & CFaddrsize) 
    36723672            {   if (!I64) 
    36733673                    a32 ^= 1; 
    36743674                size++; 
    36753675            } 
    36763676            if (iflags & CFopsize) 
    36773677                size++;                         /* +1 for OPSIZE prefix         */ 
    36783678        } 
    36793679    } 
    36803680 
    36813681    if ((op & ~0x0F) == 0x70) 
    36823682    {   if (iflags & CFjmp16)           // if long branch 
    36833683            size += I16 ? 3 : 4;        // + 3(4) bytes for JMP 
    36843684    } 
    36853685    else if (ins & M)                   // if modregrm byte 
    36863686    { 
    36873687        rm = c->Irm; 
    36883688        mod = rm & 0xC0; 
     
    50025002        ; 
    50035003        pc = &code_next(c); 
    50045004    } 
    50055005} 
    50065006#endif 
    50075007 
    50085008 
    50095009/*************************** 
    50105010 * Debug code to dump code stucture. 
    50115011 */ 
    50125012 
    50135013#if DEBUG 
    50145014 
    50155015void WRcodlst(code *c) 
    50165016{ for (; c; c = code_next(c)) 
    50175017        c->print(); 
    50185018} 
    50195019 
    50205020void code::print() 
    50215021{ 
    5022   unsigned op,rm; 
    5023   unsigned char ins; 
    5024   code *c = this; 
    5025  
    5026   if (c == CNIL) 
    5027   {     printf("code 0\n"); 
     5022    unsigned char ins; 
     5023    code *c = this; 
     5024 
     5025    if (c == CNIL) 
     5026    {   printf("code 0\n"); 
    50285027        return; 
    5029  
    5030   op = c->Iop; 
    5031  
     5028   
     5029 
     5030    unsigned op = c->Iop; 
    50325031    if ((c->Iop & 0xFF00) == 0x0F00) 
    50335032        ins = inssize2[op & 0xFF]; 
    50345033    else 
    50355034        ins = inssize[op & 0xFF]; 
    50365035 
    5037   printf("code %p: nxt=%p op=%02x",c,code_next(c),op); 
     5036    printf("code %p: nxt=%p ",c,code_next(c)); 
     5037    if (c->Irex) 
     5038        printf("rex=%x ", c->Irex); 
     5039    printf("op=%02x",op); 
     5040 
    50385041  if ((op & 0xFF) == ESCAPE) 
    50395042  {     if ((op & 0xFF00) == ESClinnum) 
    50405043        {   printf(" linnum = %d\n",c->IEV2.Vsrcpos.Slinnum); 
    50415044            return; 
    50425045        } 
    50435046        printf(" ESCAPE %d",c->Iop >> 8); 
    50445047  } 
    50455048  if (c->Iflags) 
    50465049        printf(" flg=%x",c->Iflags); 
    50475050  if (ins & M) 
    5048   {     rm = c->Irm; 
     5051  {     unsigned rm = c->Irm; 
    50495052        printf(" rm=%02x=%d,%d,%d",rm,(rm>>6)&3,(rm>>3)&7,rm&7); 
    50505053        if (I32 && issib(rm)) 
    50515054        {   unsigned char sib = c->Isib; 
    50525055            printf(" sib=%02x=%d,%d,%d",sib,(sib>>6)&3,(sib>>3)&7,sib&7); 
    50535056        } 
    50545057        if ((rm & 0xC7) == BPRM || (rm & 0xC0) == 0x80 || (rm & 0xC0) == 0x40) 
    50555058        { 
    50565059            switch (c->IFL1) 
    50575060            { 
    50585061                case FLconst: 
    50595062                case FLoffset: 
    50605063                    printf(" int = %4d",c->IEV1.Vuns); 
    50615064                    break; 
    50625065                case FLblock: 
    50635066                    printf(" block = %p",c->IEV1.Vblock); 
    50645067                    break; 
    50655068                case FLswitch: 
    50665069                case FLblockoff: 
    50675070                case FLlocalsize: 
    50685071                case FLframehandler: 
  • branches/dmd-1.x/src/backend/ptrntab.c

    r618 r619  
    809809}; 
    810810PTRNTAB2  aptb2CMPS[] = /* CMPS */ { 
    811811        { 0xa6, _modsidi,               _m8,    _m8 }, 
    812812        { 0xa7, _modsidi,       _m16,   _m16 }, 
    813813        { 0xa7, _modsidi,       _m32,   _m32 }, 
    814814        { ASM_END, 0, 0, 0 } 
    815815}; 
    816816PTRNTAB2  aptb2CMPXCHG[] = /* CMPXCHG */ { 
    817817        { 0xfb0, _I386 | _cb|_mod2,     _rm8,   _r8 }, 
    818818                                                // This is really a 486 only 
    819819                                                // instruction 
    820820        { 0xfb1, _I386 | _cw | _16_bit|_mod2,   _rm16,  _r16 }, 
    821821        { 0xfb1, _I386 | _cd | _32_bit|_mod2,   _rm32,  _r32 }, 
    822822        { 0xfb1, _I386 | _cq | _64_bit|_mod2,   _rm64,  _r64 }, 
    823823        { ASM_END, 0, 0, 0 } 
    824824}; 
    825825PTRNTAB2  aptb2DIV[] = /* DIV */ { 
    826826        { 0xf6, _6,                     _al,            _rm8 }, 
    827827        { 0xf7, _6 | _16_bit | _moddx,          _ax,            _rm16 }, 
    828828        { 0xf7, _6 | _32_bit | _moddx,          _eax,           _rm32 }, 
     829        { 0xf7, _6 | _64_bit | _moddx,          _rax,           _rm64 }, 
    829830        { 0xf6, _6 | _modax,                    _rm8,           0 }, 
    830         { 0xf7, _6 | _16_bit | _modaxdx,                _rm16,          0 }, 
    831         { 0xf7, _6 | _32_bit | _modaxdx,                _rm32,          0 }, 
     831        { 0xf7, _6 | _16_bit | _modaxdx,        _rm16,          0 }, 
     832        { 0xf7, _6 | _32_bit | _modaxdx,        _rm32,          0 }, 
     833        { 0xf7, _6 | _64_bit | _modaxdx,        _rm64,          0 }, 
    832834        { ASM_END, 0, 0, 0 } 
    833835}; 
    834836PTRNTAB2  aptb2ENTER[] = /* ENTER */ { 
    835837        { 0xc8, _iw|_ib,        _imm16, _imm8 }, 
    836838        { ASM_END, 0, 0, 0 } 
    837839}; 
    838840PTRNTAB2  aptb2IDIV[] = /* IDIV */ { 
    839841        { 0xf6, _7,                     _al,            _rm8 }, 
    840         { 0xf7, _7|_16_bit|_moddx,              _ax,            _rm16 }, 
    841         { 0xf7, _7|_32_bit|_moddx,              _eax,           _rm32 }, 
    842         { 0xf6, _7 | _modax,                    _rm8,           0 }, 
     842        { 0xf7, _7|_16_bit|_moddx,      _ax,            _rm16 }, 
     843        { 0xf7, _7|_32_bit|_moddx,      _eax,           _rm32 }, 
     844        { 0xf7, _7|_64_bit|_moddx,      _rax,           _rm64 }, 
     845        { 0xf6, _7 | _modax,            _rm8,           0 }, 
    843846        { 0xf7, _7|_16_bit|_modaxdx,    _rm16,          0 }, 
    844847        { 0xf7, _7|_32_bit|_modaxdx,    _rm32,          0 }, 
     848        { 0xf7, _7|_64_bit|_modaxdx,    _rm64,          0 }, 
    845849        { ASM_END, 0, 0, 0 } 
    846850}; 
    847851PTRNTAB2  aptb2IN[] = /* IN */ { 
    848852        { 0xe4, _ib,        _al,                _imm8 }, 
    849853        { 0xe5, _ib|_16_bit,_ax,                _imm8 }, 
    850854        { 0xe5, _ib|_32_bit,_eax,       _imm8 }, 
    851855        { 0xec, 0,          _al,                _dx }, 
    852856        { 0xed, _16_bit,    _ax,                _dx }, 
    853857        { 0xed, _32_bit,    _eax,       _dx }, 
    854858        { ASM_END, 0, 0, 0 } 
    855859}; 
    856860PTRNTAB2  aptb2INS[] = /* INS */ { 
    857861        { 0x6c, _modsi, _rm8, _dx }, 
    858862        { 0x6d, _modsi|_16_bit, _rm16, _dx }, 
    859863        { 0x6d, _32_bit|_modsi, _rm32, _dx }, 
    860864        { ASM_END, 0, 0, 0 } 
    861865}; 
    862866 
    863867PTRNTAB2  aptb2LAR[] = /* LAR */ { 
    864868        { 0x0f02,       _r|_16_bit,                     _r16,   _rm16 }, 
     
    958962#else 
    959963        { 0x0fbf,       _r,                     _r32,   _rm16 }, 
    960964#endif 
    961965        { ASM_END, 0, 0, 0 } 
    962966}; 
    963967PTRNTAB2  aptb2MOVZX[] = /* MOVZX */ { 
    964968        { 0x0fb6,       _r|_16_bit,                     _r16,   _rm8 }, 
    965969        { 0x0fb6,       _r|_32_bit,                     _r32,   _rm8 }, 
    966970#if 1 
    967971        { 0x0fb7,       _r|_16_bit,             _r16,   _rm16 }, 
    968972        { 0x0fb7,       _r|_32_bit,             _r32,   _rm16 }, 
    969973#else 
    970974        { 0x0fb7,       _r,                     _r32,   _rm16 }, 
    971975#endif 
    972976        { ASM_END, 0, 0, 0 } 
    973977}; 
    974978PTRNTAB2  aptb2MUL[] = /* MUL */ { 
    975979        { 0xf6, _4,                     _al,    _rm8 }, 
    976980        { 0xf7, _4|_16_bit|_moddx,      _ax,    _rm16 }, 
    977981        { 0xf7, _4|_32_bit|_moddx,      _eax,   _rm32 }, 
     982        { 0xf7, _4|_64_bit|_moddx,      _rax,   _rm64 }, 
    978983        { 0xf6, _4|_modax,              _rm8,   0 }, 
    979984        { 0xf7, _4|_16_bit|_modaxdx,    _rm16,  0 }, 
    980985        { 0xf7, _4|_32_bit|_modaxdx,    _rm32,  0 }, 
     986        { 0xf7, _4|_64_bit|_modaxdx,    _rm64,  0 }, 
    981987        { ASM_END, 0, 0, 0 } 
    982988}; 
    983989PTRNTAB2  aptb2OR[] = /* OR */ { 
    984990        { 0x0c, _ib,            _al,    _imm8 }, 
    985991        { 0x83, _1|_ib|_16_bit,         _rm16,  _imm8 }, 
    986992        { 0x0d, _iw|_16_bit,            _ax,    _imm16 }, 
    987993        { 0x83, _1|_ib|_32_bit,         _rm32,  _imm8 }, 
    988994        { 0x0d, _id|_32_bit,            _eax,   _imm32 }, 
    989995        { 0x80, _1|_ib,         _rm8,   _imm8 }, 
    990996        { 0x81, _1|_iw|_16_bit,         _rm16,  _imm16 }, 
    991997        { 0x81, _1|_id|_32_bit,         _rm32,  _imm32 }, 
    992998        { 0x08, _r,                     _rm8,   _r8 }, 
    993999        { 0x09, _r|_16_bit,                     _rm16,  _r16 }, 
    9941000        { 0x09, _r|_32_bit,                     _rm32,  _r32 }, 
    9951001        { 0x0a, _r,                     _r8,    _rm8 }, 
    9961002        { 0x0b, _r|_16_bit,                     _r16,   _rm16 }, 
    9971003        { 0x0b, _r|_32_bit,                     _r32,   _rm32 }, 
    9981004        { ASM_END, 0, 0, 0 } 
    9991005}; 
    10001006PTRNTAB2  aptb2OUT[] = { 
     
    12631269}; 
    12641270PTRNTAB2  aptb2CMOVNL[] = { 
    12651271        { 0x0F4D, _r|_16_bit,   _r16,   _rm16 }, 
    12661272        { 0x0F4D, _r|_32_bit,   _r32,   _rm32 }, 
    12671273        { ASM_END, 0, 0, 0 } 
    12681274}; 
    12691275PTRNTAB2  aptb2CMOVLE[] = { 
    12701276        { 0x0F4E, _r|_16_bit,   _r16,   _rm16 }, 
    12711277        { 0x0F4E, _r|_32_bit,   _r32,   _rm32 }, 
    12721278        { ASM_END, 0, 0, 0 } 
    12731279}; 
    12741280PTRNTAB2  aptb2CMOVNLE[] = { 
    12751281        { 0x0F4F, _r|_16_bit,   _r16,   _rm16 }, 
    12761282        { 0x0F4F, _r|_32_bit,   _r32,   _rm32 }, 
    12771283        { ASM_END, 0, 0, 0 } 
    12781284}; 
    12791285 
    12801286PTRNTAB3  aptb3IMUL[] = /* IMUL */ { 
    12811287        { 0x0faf,       _r|_16_bit,             _r16,   _rm16, 0 }, 
    12821288        { 0x0faf,       _r|_32_bit,             _r32,   _rm32, 0 }, 
     1289        { 0x0faf,       _r|_64_bit,             _r64,   _rm64, 0 }, 
    12831290        { 0xf6, _5|_modax,                      _rm8,   0, 0 }, 
    12841291        { 0xf7, _5|_16_bit|_modaxdx,            _rm16,  0, 0 }, 
    12851292        { 0xf7, _5|_32_bit|_modaxdx,            _rm32,  0, 0 }, 
     1293        { 0xf7, _5|_64_bit|_modaxdx,            _rm64,  0, 0 }, 
    12861294        { 0x6b, _r|_ib|_16_bit,         _r16,   _imm8, 0 }, 
    12871295        { 0x6b, _r|_ib|_32_bit,         _r32,   _imm8, 0 }, 
    12881296        { 0x69, _r|_iw|_16_bit,         _r16,   _imm16, 0 }, 
    12891297        { 0x69, _r|_id|_32_bit,         _r32,   _imm32, 0 }, 
     1298        { 0x69, _r|_id|_64_bit,         _r64,   _imm32, 0 }, 
    12901299        { 0x6b, _r|_ib|_16_bit,         _r16,   _rm16,  _imm8 }, 
    12911300        { 0x6b, _r|_ib|_32_bit,         _r32,   _rm32,  _imm8 }, 
     1301        { 0x6b, _r|_ib|_64_bit,         _r64,   _rm64,  _imm8 }, 
    12921302        { 0x69, _r|_iw|_16_bit,         _r16,   _rm16,  _imm16 }, 
    12931303        { 0x69, _r|_id|_32_bit,         _r32,   _rm32,  _imm32 }, 
     1304        { 0x69, _r|_id|_64_bit,         _r64,   _rm64,  _imm32 }, 
    12941305        { ASM_END, 0, 0, 0 } 
    12951306}; 
    12961307PTRNTAB3  aptb3SHLD[] = /* SHLD */ { 
    12971308        { 0x0fa4,       _cw|_16_bit, _rm16, _r16, _imm8 }, 
    12981309        { 0x0fa4,       _cd|_32_bit, _rm32, _r32, _imm8 }, 
    12991310        { 0x0fa5,       _cw|_16_bit, _rm16, _r16, _cl }, 
    13001311        { 0x0fa5,       _cd|_32_bit, _rm32, _r32, _cl }, 
    13011312        { ASM_END, 0, 0, 0 } 
    13021313}; 
    13031314PTRNTAB3  aptb3SHRD[] = /* SHRD */ { 
    13041315        { 0x0fac,       _cw|_16_bit, _rm16, _r16, _imm8 }, 
    13051316        { 0x0fac,       _cd|_32_bit, _rm32, _r32, _imm8 }, 
    13061317        { 0x0fad,       _cw|_16_bit, _rm16, _r16, _cl }, 
    13071318        { 0x0fad,       _cd|_32_bit, _rm32, _r32, _cl }, 
    13081319        { ASM_END, 0, 0, 0 } 
    13091320}; 
    13101321// 
    13111322// Floating point instructions which have entirely different flag 
    13121323// interpretations 
    13131324// 
  • branches/dmd-1.x/src/mtype.c

    r604 r619  
    31053105        t = this; 
    31063106    else 
    31073107        t = new TypeDelegate(t); 
    31083108    return t; 
    31093109} 
    31103110 
    31113111Type *TypeDelegate::semantic(Loc loc, Scope *sc) 
    31123112{ 
    31133113    if (deco)                   // if semantic() already run 
    31143114    { 
    31153115        //printf("already done\n"); 
    31163116        return this; 
    31173117    } 
    31183118    next = next->semantic(loc,sc); 
    31193119    return merge(); 
    31203120} 
    31213121 
    31223122d_uns64 TypeDelegate::size(Loc loc) 
    31233123{ 
    31243124    return PTRSIZE * 2; 
     3125} 
     3126 
     3127unsigned TypeDelegate::alignsize() 
     3128{ 
     3129    // See Bugzilla 942 for discussion 
     3130#if 0 
     3131    return PTRSIZE; 
     3132#else 
     3133    return PTRSIZE * 2; 
     3134#endif 
    31253135} 
    31263136 
    31273137void TypeDelegate::toCBuffer2(OutBuffer *buf, HdrGenState *hgs, int mod) 
    31283138{ 
    31293139    if (mod != this->mod) 
    31303140    {   toCBuffer3(buf, hgs, mod); 
    31313141        return; 
    31323142    } 
    31333143    TypeFunction *tf = (TypeFunction *)next; 
    31343144 
    31353145    tf->next->toCBuffer2(buf, hgs, 0); 
    31363146    buf->writestring(" delegate"); 
    31373147    Parameter::argsToCBuffer(buf, hgs, tf->parameters, tf->varargs); 
    31383148} 
    31393149 
    31403150Expression *TypeDelegate::defaultInit(Loc loc) 
    31413151{ 
    31423152#if LOGDEFAULTINIT 
    31433153    printf("TypeDelegate::defaultInit() '%s'\n", toChars()); 
    31443154#endif 
  • branches/dmd-1.x/src/mtype.h

    r523 r619  
    465465    void toDecoBuffer(OutBuffer *buf); 
    466466    void toCBuffer(OutBuffer *buf, Identifier *ident, HdrGenState *hgs); 
    467467    void toCBuffer2(OutBuffer *buf, HdrGenState *hgs, int mod); 
    468468    MATCH deduceType(Scope *sc, Type *tparam, TemplateParameters *parameters, Objects *dedtypes); 
    469469    TypeInfoDeclaration *getTypeInfoDeclaration(); 
    470470    Type *reliesOnTident(); 
    471471 
    472472    int callMatch(Expressions *toargs); 
    473473    type *toCtype(); 
    474474    enum RET retStyle(); 
    475475 
    476476    unsigned totym(); 
    477477}; 
    478478 
    479479struct TypeDelegate : Type 
    480480{ 
    481481    TypeDelegate(Type *t); 
    482482    Type *syntaxCopy(); 
    483483    Type *semantic(Loc loc, Scope *sc); 
    484484    d_uns64 size(Loc loc); 
     485    unsigned alignsize(); 
    485486    void toCBuffer2(OutBuffer *buf, HdrGenState *hgs, int mod); 
    486487    Expression *defaultInit(Loc loc); 
    487488    int isZeroInit(Loc loc); 
    488489    int checkBoolean(); 
    489490    TypeInfoDeclaration *getTypeInfoDeclaration(); 
    490491    Expression *dotExp(Scope *sc, Expression *e, Identifier *ident); 
    491492    int hasPointers(); 
    492493 
    493494    type *toCtype(); 
    494495}; 
    495496 
    496497struct TypeQualified : Type 
    497498{ 
    498499    Loc loc; 
    499500    Array idents;       // array of Identifier's representing ident.ident.ident etc. 
    500501 
    501502    TypeQualified(TY ty, Loc loc); 
    502503    void syntaxCopyHelper(TypeQualified *t); 
    503504    void addIdent(Identifier *ident); 
    504505    void toCBuffer2Helper(OutBuffer *buf, HdrGenState *hgs); 
  • trunk/src/backend/cgcod.c

    r618 r619  
    124124 
    125125    //printf("codgen('%s')\n",funcsym_p->Sident); 
    126126 
    127127    cgreg_init(); 
    128128    csmax = 64; 
    129129    csextab = (struct CSE *) util_calloc(sizeof(struct CSE),csmax); 
    130130    functy = tybasic(funcsym_p->ty()); 
    131131#if TARGET_LINUX || TARGET_OSX || TARGET_FREEBSD || TARGET_SOLARIS 
    132132    if (0 && config.flags3 & CFG3pic) 
    133133    { 
    134134        ALLREGS = ALLREGS_INIT_PIC; 
    135135        BYTEREGS = BYTEREGS_INIT_PIC; 
    136136    } 
    137137    else 
    138138    { 
    139139        regm_t value = BYTEREGS_INIT; 
    140140        ALLREGS = ALLREGS_INIT; 
    141141        BYTEREGS = value; 
    142142    } 
    143143    if (I64) 
    144         ALLREGS = mAX|mBX|mCX|mDX|mSI|mDI| mR8|mR9|mR10|mR11|mR12|mR13|mR14|mR15; 
     144    {   ALLREGS = mAX|mBX|mCX|mDX|mSI|mDI| mR8|mR9|mR10|mR11|mR12|mR13|mR14|mR15; 
     145        BYTEREGS = ALLREGS; 
     146    } 
    145147#endif 
    146148    allregs = ALLREGS; 
    147149    if (0 && config.flags3 & CFG3pic) 
    148150        allregs &= ~mBX; 
    149151    pass = PASSinit; 
    150152 
    151153tryagain: 
    152154    #ifdef DEBUG 
    153155    if (debugr) 
    154156        printf("------------------ PASS%s -----------------\n", 
    155157            (pass == PASSinit) ? "init" : ((pass == PASSreg) ? "reg" : "final")); 
    156158    #endif 
    157159    lastretregs = last2retregs = last3retregs = last4retregs = last5retregs = 0; 
    158160 
    159161    // if no parameters, assume we don't need a stack frame 
    160162    needframe = 0; 
    161163    usedalloca = 0; 
    162164    gotref = 0; 
    163165    stackchanged = 0; 
    164166    stackpush = 0; 
     
    22782280                regcon.immed.mval | regcon.params | mfuncreg); 
    22792281    } 
    22802282    return scratch; 
    22812283} 
    22822284 
    22832285 
    22842286/****************************** 
    22852287 * Evaluate an elem that is a common subexp that has been encountered 
    22862288 * before. 
    22872289 * Look first to see if it is already in a register. 
    22882290 */ 
    22892291 
    22902292STATIC code * comsub(elem *e,regm_t *pretregs) 
    22912293{   tym_t tym; 
    22922294    regm_t regm,emask,csemask; 
    22932295    unsigned reg,i,byte,sz; 
    22942296    code *c; 
    22952297    int forcc;                  // !=0 if we evaluate for condition codes 
    22962298    int forregs;                // !=0 if we evaluate into registers 
    22972299 
    2298     //printf("comsub(e = %p, *pretregs = x%x)\n",e,*pretregs); 
     2300    //printf("comsub(e = %p, *pretregs = %s)\n",e,regm_str(*pretregs)); 
    22992301    elem_debug(e); 
    23002302#ifdef DEBUG 
    23012303    if (e->Ecomsub > e->Ecount) 
    23022304        elem_print(e); 
    23032305#endif 
    23042306    assert(e->Ecomsub <= e->Ecount); 
    23052307 
    23062308  c = CNIL; 
    23072309  if (*pretregs == 0) goto done;        /* no possible side effects anyway */ 
    23082310 
    23092311    if (tyfloating(e->Ety) && config.inline8087) 
    23102312        return comsub87(e,pretregs); 
    23112313 
    23122314  /* First construct a mask, emask, of all the registers that   */ 
    23132315  /* have the right contents.                                   */ 
    23142316 
    23152317  emask = 0; 
    23162318  for (i = 0; i < arraysize(regcon.cse.value); i++) 
    23172319  { 
    23182320        //dbg_printf("regcon.cse.value[%d] = %p\n",i,regcon.cse.value[i]); 
     
    25662568 *                      Note:   longs are in AX,BX or CX,DX or SI,DI 
    25672569 *                              doubles are AX,BX,CX,DX only 
    25682570 *      constflag       TRUE if user of result will not modify the 
    25692571 *                      registers returned in *pretregs. 
    25702572 * Output: 
    25712573 *      *pretregs       mask of registers result is returned in 
    25722574 * Returns: 
    25732575 *      pointer to code sequence generated 
    25742576 */ 
    25752577 
    25762578#include "cdxxx.c"                      /* jump table                   */ 
    25772579 
    25782580code *codelem(elem *e,regm_t *pretregs,bool constflag) 
    25792581{ code *c; 
    25802582  Symbol *s; 
    25812583  tym_t tym; 
    25822584  unsigned op; 
    25832585 
    25842586#ifdef DEBUG 
    25852587  if (debugw) 
    2586   {     printf("+codelem(e=%p,*pretregs=x%x) ",e,*pretregs); 
     2588  {     printf("+codelem(e=%p,*pretregs=%s) ",e,regm_str(*pretregs)); 
    25872589        WROP(e->Eoper); 
    25882590        printf("msavereg=x%x regcon.cse.mval=x%x regcon.cse.mops=x%x\n", 
    25892591                msavereg,regcon.cse.mval,regcon.cse.mops); 
    25902592        printf("Ecount = %d, Ecomsub = %d\n", e->Ecount, e->Ecomsub); 
    25912593  } 
    25922594#endif 
    25932595  assert(e); 
    25942596  elem_debug(e); 
    25952597  if ((regcon.cse.mops & regcon.cse.mval) != regcon.cse.mops) 
    25962598  { 
    25972599#ifdef DEBUG 
    25982600        printf("+codelem(e=%p,*pretregs=x%x) ",e,*pretregs); 
    25992601        elem_print(e); 
    26002602        printf("msavereg=x%x regcon.cse.mval=x%x regcon.cse.mops=x%x\n", 
    26012603                msavereg,regcon.cse.mval,regcon.cse.mops); 
    26022604        printf("Ecount = %d, Ecomsub = %d\n", e->Ecount, e->Ecomsub); 
    26032605#endif 
    26042606        assert(0); 
    26052607  } 
    26062608 
  • trunk/src/backend/cod1.c

    r618 r619  
    596596        } 
    597597        for (unsigned i = 0; rm; i++) 
    598598        {       if (mask[i] & rm) 
    599599                {       if (regcon.cse.value[i] == e && // if register has elem 
    600600                            /* watch out for a CWD destroying DX        */ 
    601601                            !(i == DX && op == 0xF7 && desmsk & mDX)) 
    602602                        { 
    603603                                /* if ES, then it can only be a load    */ 
    604604                                if (i == ES) 
    605605                                {       if (op != 0x8B) 
    606606                                            goto L1;    /* not a load   */ 
    607607                                        cs->Iop = 0x8C; /* MOV reg,ES   */ 
    608608                                        cs->Irm = modregrm(3,0,reg & 7); 
    609609                                        if (reg & 8) 
    610610                                            code_orrex(cs, REX_B); 
    611611                                } 
    612612                                else    // XXX reg,i 
    613613                                { 
    614614                                    cs->Irm = modregrm(3,reg & 7,i & 7); 
    615615                                    if (reg & 8) 
    616                                         code_orrex(cs, REX_R)
     616                                        cs->Irex |= REX_R
    617617                                    if (i & 8) 
    618                                         code_orrex(cs, REX_B)
     618                                        cs->Irex |= REX_B
    619619                                } 
    620620                                c = CNIL; 
    621621                                goto L2; 
    622622                        } 
    623623                        rm &= ~mask[i]; 
    624624                } 
    625625        } 
    626626  } 
    627627 
    628628L1: 
    629629  c = getlvalue(cs,e,keepmsk); 
    630630  if (offset == REGSIZE) 
    631631        getlvalue_msw(cs); 
    632632  else 
    633633        cs->IEVoffset1 += offset; 
    634634  code_newreg(cs, reg);                         // OR in reg field 
    635635  if (!I16) 
    636636  { 
    637637      if (reg == 6 && op == 0xFF ||             /* don't PUSH a word    */ 
    638638          op == 0x0FB7 || op == 0x0FBF ||       /* MOVZX/MOVSX          */ 
     
    11081107                break; 
    11091108            case TYsptr:                        /* if pointer to stack  */ 
    11101109                if (config.wflags & WFssneds)   // if SS != DS 
    11111110                    pcs->Iflags |= CFss;        /* then need SS: override */ 
    11121111                break; 
    11131112            case TYcptr:                        /* if pointer to code   */ 
    11141113                pcs->Iflags |= CFcs;            /* then need CS: override */ 
    11151114                break; 
    11161115        } 
    11171116#endif 
    11181117        pcs->IFL1 = FLoffset; 
    11191118        pcs->IEV1.Vuns = 0; 
    11201119 
    11211120        /* see if we can replace *(e+c) with 
    11221121         *      MOV     idxreg,e 
    11231122         *      [MOV    ES,segment] 
    11241123         *      EA =    [ES:]c[idxreg] 
    11251124         */ 
    11261125 
    11271126        if (e1isadd && e12->Eoper == OPconst && 
    1128             tysize(e12->Ety) == REGSIZE && 
     1127            (tysize(e12->Ety) == REGSIZE || (I64 && tysize(e12->Ety) == 4)) && 
    11291128            (!e1->Ecount || !e1free) 
    11301129           ) 
    11311130        {   int ss; 
    11321131 
    11331132            pcs->IEV1.Vuns = e12->EV.Vuns; 
    11341133            freenode(e12); 
    11351134            if (e1free) freenode(e1); 
    1136             if (I32 && e11->Eoper == OPadd && !e11->Ecount && 
     1135            if (!I16 && e11->Eoper == OPadd && !e11->Ecount && 
    11371136                tysize(e11->Ety) == REGSIZE) 
    11381137            { 
    11391138                e12 = e11->E2; 
    11401139                e11 = e11->E1; 
    11411140                e1 = e1->E1; 
    11421141                e1free = TRUE; 
    11431142                goto L4; 
    11441143            } 
    11451144            if (!I16 && (ss = isscaledindex(e11)) != 0) 
    11461145            {   // (v * scale) + const 
    11471146                c = cdisscaledindex(e11,&idxregs,keepmsk); 
    11481147                reg = findreg(idxregs); 
    11491148                pcs->Irm = modregrm(0,0,4); 
    11501149                pcs->Isib = modregrm(ss,reg & 7,5); 
    11511150                if (reg & 8) 
    11521151                    pcs->Irex |= REX_X; 
    11531152            } 
    11541153            else 
    11551154            { 
    11561155                c = scodelem(e11,&idxregs,keepmsk,TRUE); // load index reg 
     
    14091408} 
    14101409 
    14111410/******************************* 
    14121411 * Same as codelem(), but do not destroy the registers in keepmsk. 
    14131412 * Use scratch registers as much as possible, then use stack. 
    14141413 * Input: 
    14151414 *      constflag       TRUE if user of result will not modify the 
    14161415 *                      registers returned in *pretregs. 
    14171416 */ 
    14181417 
    14191418code *scodelem(elem *e,regm_t *pretregs,regm_t keepmsk,bool constflag) 
    14201419{ code *c,*cs1,*cs2,*cs3; 
    14211420  unsigned i,j; 
    14221421  regm_t oldmfuncreg,oldregcon,oldregimmed,overlap,tosave,touse; 
    14231422  int adjesp; 
    14241423  unsigned stackpushsave; 
    14251424  char calledafuncsave; 
    14261425 
    14271426#ifdef DEBUG 
    14281427  if (debugw) 
    1429         printf("+scodelem(e=%p *pretregs=x%x keepmsk=x%x constflag=%d\n", 
    1430                 e,*pretregs,keepmsk,constflag); 
     1428        printf("+scodelem(e=%p *pretregs=%s keepmsk=%s constflag=%d\n", 
     1429                e,regm_str(*pretregs),regm_str(keepmsk),constflag); 
    14311430#endif 
    14321431  elem_debug(e); 
    14331432  if (constflag) 
    14341433  {     regm_t regm; 
    14351434        unsigned reg; 
    14361435 
    14371436        if (isregvar(e,&regm,&reg) &&           // if e is a register variable 
    14381437            (regm & *pretregs) == regm &&       // in one of the right regs 
    14391438            e->EV.sp.Voffset == 0 
    14401439           ) 
    1441         {       unsigned sz1,sz2; 
    1442  
    1443                 sz1 = tysize(e->Ety); 
    1444                 sz2 = tysize(e->EV.sp.Vsym->Stype->Tty); 
     1440        { 
     1441                unsigned sz1 = tysize(e->Ety); 
     1442                unsigned sz2 = tysize(e->EV.sp.Vsym->Stype->Tty); 
    14451443                if (sz1 <= REGSIZE && sz2 > REGSIZE) 
    14461444                    regm &= mLSW; 
    14471445                c = fixresult(e,regm,pretregs); 
    14481446                cssave(e,regm,0); 
    14491447                freenode(e); 
    14501448#ifdef DEBUG 
    14511449                if (debugw) 
    14521450                    printf("-scodelem(e=%p *pretregs=x%x keepmsk=x%x constflag=%d\n", 
    14531451                            e,*pretregs,keepmsk,constflag); 
    14541452#endif 
    14551453                return c; 
    14561454        } 
    14571455  } 
    14581456  overlap = msavereg & keepmsk; 
    14591457  msavereg |= keepmsk;          /* add to mask of regs to save          */ 
    14601458  oldregcon = regcon.cse.mval; 
    14611459  oldregimmed = regcon.immed.mval; 
    14621460  oldmfuncreg = mfuncreg;       /* remember old one                     */ 
    14631461  mfuncreg = (mBP | mES | ALLREGS) & ~regcon.mvar; 
    14641462  stackpushsave = stackpush; 
  • trunk/src/backend/cod3.c

    r605 r619  
    36453645        // If the instruction has a second operand that is not an 8 bit, 
    36463646        // and the operand size prefix is present, then fix the size computation 
    36473647        // because the operand size will be different. 
    36483648        // Walter, I had problems with this bit at the end.  There can still be 
    36493649        // an ADDRSIZE prefix for these and it does indeed change the operand size. 
    36503650 
    36513651        if (iflags & (CFopsize | CFaddrsize)) 
    36523652        { 
    36533653            if ((ins & (T|E)) == T) 
    36543654            { 
    36553655                if ((op & 0xAC) == 0xA0) 
    36563656                { 
    36573657                    if (iflags & CFaddrsize && !I64) 
    36583658                    {   if (I32) 
    36593659                            size -= 2; 
    36603660                        else 
    36613661                            size += 2; 
    36623662                    } 
    36633663                } 
    36643664                else if (iflags & CFopsize) 
    3665                 {   if (I32) 
     3665                {   if (I16) 
     3666                        size += 2; 
     3667                    else 
    36663668                        size -= 2; 
    3667                     else 
    3668                         size += 2; 
    36693669                } 
    36703670            } 
    36713671            if (iflags & CFaddrsize) 
    36723672            {   if (!I64) 
    36733673                    a32 ^= 1; 
    36743674                size++; 
    36753675            } 
    36763676            if (iflags & CFopsize) 
    36773677                size++;                         /* +1 for OPSIZE prefix         */ 
    36783678        } 
    36793679    } 
    36803680 
    36813681    if ((op & ~0x0F) == 0x70) 
    36823682    {   if (iflags & CFjmp16)           // if long branch 
    36833683            size += I16 ? 3 : 4;        // + 3(4) bytes for JMP 
    36843684    } 
    36853685    else if (ins & M)                   // if modregrm byte 
    36863686    { 
    36873687        rm = c->Irm; 
    36883688        mod = rm & 0xC0; 
     
    50025002        ; 
    50035003        pc = &code_next(c); 
    50045004    } 
    50055005} 
    50065006#endif 
    50075007 
    50085008 
    50095009/*************************** 
    50105010 * Debug code to dump code stucture. 
    50115011 */ 
    50125012 
    50135013#if DEBUG 
    50145014 
    50155015void WRcodlst(code *c) 
    50165016{ for (; c; c = code_next(c)) 
    50175017        c->print(); 
    50185018} 
    50195019 
    50205020void code::print() 
    50215021{ 
    5022   unsigned op,rm; 
    5023   unsigned char ins; 
    5024   code *c = this; 
    5025  
    5026   if (c == CNIL) 
    5027   {     printf("code 0\n"); 
     5022    unsigned char ins; 
     5023    code *c = this; 
     5024 
     5025    if (c == CNIL) 
     5026    {   printf("code 0\n"); 
    50285027        return; 
    5029  
    5030   op = c->Iop; 
    5031  
     5028   
     5029 
     5030    unsigned op = c->Iop; 
    50325031    if ((c->Iop & 0xFF00) == 0x0F00) 
    50335032        ins = inssize2[op & 0xFF]; 
    50345033    else 
    50355034        ins = inssize[op & 0xFF]; 
    50365035 
    5037   printf("code %p: nxt=%p op=%02x",c,code_next(c),op); 
     5036    printf("code %p: nxt=%p ",c,code_next(c)); 
     5037    if (c->Irex) 
     5038        printf("rex=%x ", c->Irex); 
     5039    printf("op=%02x",op); 
     5040 
    50385041  if ((op & 0xFF) == ESCAPE) 
    50395042  {     if ((op & 0xFF00) == ESClinnum) 
    50405043        {   printf(" linnum = %d\n",c->IEV2.Vsrcpos.Slinnum); 
    50415044            return; 
    50425045        } 
    50435046        printf(" ESCAPE %d",c->Iop >> 8); 
    50445047  } 
    50455048  if (c->Iflags) 
    50465049        printf(" flg=%x",c->Iflags); 
    50475050  if (ins & M) 
    5048   {     rm = c->Irm; 
     5051  {     unsigned rm = c->Irm; 
    50495052        printf(" rm=%02x=%d,%d,%d",rm,(rm>>6)&3,(rm>>3)&7,rm&7); 
    50505053        if (I32 && issib(rm)) 
    50515054        {   unsigned char sib = c->Isib; 
    50525055            printf(" sib=%02x=%d,%d,%d",sib,(sib>>6)&3,(sib>>3)&7,sib&7); 
    50535056        } 
    50545057        if ((rm & 0xC7) == BPRM || (rm & 0xC0) == 0x80 || (rm & 0xC0) == 0x40) 
    50555058        { 
    50565059            switch (c->IFL1) 
    50575060            { 
    50585061                case FLconst: 
    50595062                case FLoffset: 
    50605063                    printf(" int = %4d",c->IEV1.Vuns); 
    50615064                    break; 
    50625065                case FLblock: 
    50635066                    printf(" block = %p",c->IEV1.Vblock); 
    50645067                    break; 
    50655068                case FLswitch: 
    50665069                case FLblockoff: 
    50675070                case FLlocalsize: 
    50685071                case FLframehandler: 
  • trunk/src/backend/ptrntab.c

    r618 r619  
    809809}; 
    810810PTRNTAB2  aptb2CMPS[] = /* CMPS */ { 
    811811        { 0xa6, _modsidi,               _m8,    _m8 }, 
    812812        { 0xa7, _modsidi,       _m16,   _m16 }, 
    813813        { 0xa7, _modsidi,       _m32,   _m32 }, 
    814814        { ASM_END, 0, 0, 0 } 
    815815}; 
    816816PTRNTAB2  aptb2CMPXCHG[] = /* CMPXCHG */ { 
    817817        { 0xfb0, _I386 | _cb|_mod2,     _rm8,   _r8 }, 
    818818                                                // This is really a 486 only 
    819819                                                // instruction 
    820820        { 0xfb1, _I386 | _cw | _16_bit|_mod2,   _rm16,  _r16 }, 
    821821        { 0xfb1, _I386 | _cd | _32_bit|_mod2,   _rm32,  _r32 }, 
    822822        { 0xfb1, _I386 | _cq | _64_bit|_mod2,   _rm64,  _r64 }, 
    823823        { ASM_END, 0, 0, 0 } 
    824824}; 
    825825PTRNTAB2  aptb2DIV[] = /* DIV */ { 
    826826        { 0xf6, _6,                     _al,            _rm8 }, 
    827827        { 0xf7, _6 | _16_bit | _moddx,          _ax,            _rm16 }, 
    828828        { 0xf7, _6 | _32_bit | _moddx,          _eax,           _rm32 }, 
     829        { 0xf7, _6 | _64_bit | _moddx,          _rax,           _rm64 }, 
    829830        { 0xf6, _6 | _modax,                    _rm8,           0 }, 
    830         { 0xf7, _6 | _16_bit | _modaxdx,                _rm16,          0 }, 
    831         { 0xf7, _6 | _32_bit | _modaxdx,                _rm32,          0 }, 
     831        { 0xf7, _6 | _16_bit | _modaxdx,        _rm16,          0 }, 
     832        { 0xf7, _6 | _32_bit | _modaxdx,        _rm32,          0 }, 
     833        { 0xf7, _6 | _64_bit | _modaxdx,        _rm64,          0 }, 
    832834        { ASM_END, 0, 0, 0 } 
    833835}; 
    834836PTRNTAB2  aptb2ENTER[] = /* ENTER */ { 
    835837        { 0xc8, _iw|_ib,        _imm16, _imm8 }, 
    836838        { ASM_END, 0, 0, 0 } 
    837839}; 
    838840PTRNTAB2  aptb2IDIV[] = /* IDIV */ { 
    839841        { 0xf6, _7,                     _al,            _rm8 }, 
    840         { 0xf7, _7|_16_bit|_moddx,              _ax,            _rm16 }, 
    841         { 0xf7, _7|_32_bit|_moddx,              _eax,           _rm32 }, 
    842         { 0xf6, _7 | _modax,                    _rm8,           0 }, 
     842        { 0xf7, _7|_16_bit|_moddx,      _ax,            _rm16 }, 
     843        { 0xf7, _7|_32_bit|_moddx,      _eax,           _rm32 }, 
     844        { 0xf7, _7|_64_bit|_moddx,      _rax,           _rm64 }, 
     845        { 0xf6, _7 | _modax,            _rm8,           0 }, 
    843846        { 0xf7, _7|_16_bit|_modaxdx,    _rm16,          0 }, 
    844847        { 0xf7, _7|_32_bit|_modaxdx,    _rm32,          0 }, 
     848        { 0xf7, _7|_64_bit|_modaxdx,    _rm64,          0 }, 
    845849        { ASM_END, 0, 0, 0 } 
    846850}; 
    847851PTRNTAB2  aptb2IN[] = /* IN */ { 
    848852        { 0xe4, _ib,        _al,                _imm8 }, 
    849853        { 0xe5, _ib|_16_bit,_ax,                _imm8 }, 
    850854        { 0xe5, _ib|_32_bit,_eax,       _imm8 }, 
    851855        { 0xec, 0,          _al,                _dx }, 
    852856        { 0xed, _16_bit,    _ax,                _dx }, 
    853857        { 0xed, _32_bit,    _eax,       _dx }, 
    854858        { ASM_END, 0, 0, 0 } 
    855859}; 
    856860PTRNTAB2  aptb2INS[] = /* INS */ { 
    857861        { 0x6c, _modsi, _rm8, _dx }, 
    858862        { 0x6d, _modsi|_16_bit, _rm16, _dx }, 
    859863        { 0x6d, _32_bit|_modsi, _rm32, _dx }, 
    860864        { ASM_END, 0, 0, 0 } 
    861865}; 
    862866 
    863867PTRNTAB2  aptb2LAR[] = /* LAR */ { 
    864868        { 0x0f02,       _r|_16_bit,                     _r16,   _rm16 }, 
     
    958962#else 
    959963        { 0x0fbf,       _r,                     _r32,   _rm16 }, 
    960964#endif 
    961965        { ASM_END, 0, 0, 0 } 
    962966}; 
    963967PTRNTAB2  aptb2MOVZX[] = /* MOVZX */ { 
    964968        { 0x0fb6,       _r|_16_bit,                     _r16,   _rm8 }, 
    965969        { 0x0fb6,       _r|_32_bit,                     _r32,   _rm8 }, 
    966970#if 1 
    967971        { 0x0fb7,       _r|_16_bit,             _r16,   _rm16 }, 
    968972        { 0x0fb7,       _r|_32_bit,             _r32,   _rm16 }, 
    969973#else 
    970974        { 0x0fb7,       _r,                     _r32,   _rm16 }, 
    971975#endif 
    972976        { ASM_END, 0, 0, 0 } 
    973977}; 
    974978PTRNTAB2  aptb2MUL[] = /* MUL */ { 
    975979        { 0xf6, _4,                     _al,    _rm8 }, 
    976980        { 0xf7, _4|_16_bit|_moddx,      _ax,    _rm16 }, 
    977981        { 0xf7, _4|_32_bit|_moddx,      _eax,   _rm32 }, 
     982        { 0xf7, _4|_64_bit|_moddx,      _rax,   _rm64 }, 
    978983        { 0xf6, _4|_modax,              _rm8,   0 }, 
    979984        { 0xf7, _4|_16_bit|_modaxdx,    _rm16,  0 }, 
    980985        { 0xf7, _4|_32_bit|_modaxdx,    _rm32,  0 }, 
     986        { 0xf7, _4|_64_bit|_modaxdx,    _rm64,  0 }, 
    981987        { ASM_END, 0, 0, 0 } 
    982988}; 
    983989PTRNTAB2  aptb2OR[] = /* OR */ { 
    984990        { 0x0c, _ib,            _al,    _imm8 }, 
    985991        { 0x83, _1|_ib|_16_bit,         _rm16,  _imm8 }, 
    986992        { 0x0d, _iw|_16_bit,            _ax,    _imm16 }, 
    987993        { 0x83, _1|_ib|_32_bit,         _rm32,  _imm8 }, 
    988994        { 0x0d, _id|_32_bit,            _eax,   _imm32 }, 
    989995        { 0x80, _1|_ib,         _rm8,   _imm8 }, 
    990996        { 0x81, _1|_iw|_16_bit,         _rm16,  _imm16 }, 
    991997        { 0x81, _1|_id|_32_bit,         _rm32,  _imm32 }, 
    992998        { 0x08, _r,                     _rm8,   _r8 }, 
    993999        { 0x09, _r|_16_bit,                     _rm16,  _r16 }, 
    9941000        { 0x09, _r|_32_bit,                     _rm32,  _r32 }, 
    9951001        { 0x0a, _r,                     _r8,    _rm8 }, 
    9961002        { 0x0b, _r|_16_bit,                     _r16,   _rm16 }, 
    9971003        { 0x0b, _r|_32_bit,                     _r32,   _rm32 }, 
    9981004        { ASM_END, 0, 0, 0 } 
    9991005}; 
    10001006PTRNTAB2  aptb2OUT[] = { 
     
    12631269}; 
    12641270PTRNTAB2  aptb2CMOVNL[] = { 
    12651271        { 0x0F4D, _r|_16_bit,   _r16,   _rm16 }, 
    12661272        { 0x0F4D, _r|_32_bit,   _r32,   _rm32 }, 
    12671273        { ASM_END, 0, 0, 0 } 
    12681274}; 
    12691275PTRNTAB2  aptb2CMOVLE[] = { 
    12701276        { 0x0F4E, _r|_16_bit,   _r16,   _rm16 }, 
    12711277        { 0x0F4E, _r|_32_bit,   _r32,   _rm32 }, 
    12721278        { ASM_END, 0, 0, 0 } 
    12731279}; 
    12741280PTRNTAB2  aptb2CMOVNLE[] = { 
    12751281        { 0x0F4F, _r|_16_bit,   _r16,   _rm16 }, 
    12761282        { 0x0F4F, _r|_32_bit,   _r32,   _rm32 }, 
    12771283        { ASM_END, 0, 0, 0 } 
    12781284}; 
    12791285 
    12801286PTRNTAB3  aptb3IMUL[] = /* IMUL */ { 
    12811287        { 0x0faf,       _r|_16_bit,             _r16,   _rm16, 0 }, 
    12821288        { 0x0faf,       _r|_32_bit,             _r32,   _rm32, 0 }, 
     1289        { 0x0faf,       _r|_64_bit,             _r64,   _rm64, 0 }, 
    12831290        { 0xf6, _5|_modax,                      _rm8,   0, 0 }, 
    12841291        { 0xf7, _5|_16_bit|_modaxdx,            _rm16,  0, 0 }, 
    12851292        { 0xf7, _5|_32_bit|_modaxdx,            _rm32,  0, 0 }, 
     1293        { 0xf7, _5|_64_bit|_modaxdx,            _rm64,  0, 0 }, 
    12861294        { 0x6b, _r|_ib|_16_bit,         _r16,   _imm8, 0 }, 
    12871295        { 0x6b, _r|_ib|_32_bit,         _r32,   _imm8, 0 }, 
    12881296        { 0x69, _r|_iw|_16_bit,         _r16,   _imm16, 0 }, 
    12891297        { 0x69, _r|_id|_32_bit,         _r32,   _imm32, 0 }, 
     1298        { 0x69, _r|_id|_64_bit,         _r64,   _imm32, 0 }, 
    12901299        { 0x6b, _r|_ib|_16_bit,         _r16,   _rm16,  _imm8 }, 
    12911300        { 0x6b, _r|_ib|_32_bit,         _r32,   _rm32,  _imm8 }, 
     1301        { 0x6b, _r|_ib|_64_bit,         _r64,   _rm64,  _imm8 }, 
    12921302        { 0x69, _r|_iw|_16_bit,         _r16,   _rm16,  _imm16 }, 
    12931303        { 0x69, _r|_id|_32_bit,         _r32,   _rm32,  _imm32 }, 
     1304        { 0x69, _r|_id|_64_bit,         _r64,   _rm64,  _imm32 }, 
    12941305        { ASM_END, 0, 0, 0 } 
    12951306}; 
    12961307PTRNTAB3  aptb3SHLD[] = /* SHLD */ { 
    12971308        { 0x0fa4,       _cw|_16_bit, _rm16, _r16, _imm8 }, 
    12981309        { 0x0fa4,       _cd|_32_bit, _rm32, _r32, _imm8 }, 
    12991310        { 0x0fa5,       _cw|_16_bit, _rm16, _r16, _cl }, 
    13001311        { 0x0fa5,       _cd|_32_bit, _rm32, _r32, _cl }, 
    13011312        { ASM_END, 0, 0, 0 } 
    13021313}; 
    13031314PTRNTAB3  aptb3SHRD[] = /* SHRD */ { 
    13041315        { 0x0fac,       _cw|_16_bit, _rm16, _r16, _imm8 }, 
    13051316        { 0x0fac,       _cd|_32_bit, _rm32, _r32, _imm8 }, 
    13061317        { 0x0fad,       _cw|_16_bit, _rm16, _r16, _cl }, 
    13071318        { 0x0fad,       _cd|_32_bit, _rm32, _r32, _cl }, 
    13081319        { ASM_END, 0, 0, 0 } 
    13091320}; 
    13101321// 
    13111322// Floating point instructions which have entirely different flag 
    13121323// interpretations 
    13131324// 
  • trunk/src/mtype.c

    r605 r619  
    52415241    } 
    52425242    return t; 
    52435243} 
    52445244 
    52455245Type *TypeDelegate::semantic(Loc loc, Scope *sc) 
    52465246{ 
    52475247    if (deco)                   // if semantic() already run 
    52485248    { 
    52495249        //printf("already done\n"); 
    52505250        return this; 
    52515251    } 
    52525252    next = next->semantic(loc,sc); 
    52535253    return merge(); 
    52545254} 
    52555255 
    52565256d_uns64 TypeDelegate::size(Loc loc) 
    52575257{ 
    52585258    return PTRSIZE * 2; 
    52595259} 
    52605260 
     5261unsigned TypeDelegate::alignsize() 
     5262{ 
     5263    // See Bugzilla 942 for discussion 
     5264#if 0 
     5265    return PTRSIZE; 
     5266#else 
     5267    return PTRSIZE * 2; 
     5268#endif 
     5269} 
     5270 
    52615271MATCH TypeDelegate::implicitConvTo(Type *to) 
    52625272{ 
    52635273    //printf("TypeDelegate::implicitConvTo(this=%p, to=%p)\n", this, to); 
    52645274    //printf("from: %s\n", toChars()); 
    52655275    //printf("to  : %s\n", to->toChars()); 
    52665276    if (this == to) 
    52675277        return MATCHexact; 
    52685278#if 0 // not allowing covariant conversions because it interferes with overriding 
    52695279    if (to->ty == Tdelegate && this->nextOf()->covariant(to->nextOf()) == 1) 
    52705280        return MATCHconvert; 
    52715281#endif 
    52725282    return MATCHnomatch; 
    52735283} 
    52745284 
    52755285void TypeDelegate::toCBuffer2(OutBuffer *buf, HdrGenState *hgs, int mod) 
    52765286{ 
    52775287    if (mod != this->mod) 
    52785288    {   toCBuffer3(buf, hgs, mod); 
    52795289        return; 
    52805290    } 
  • trunk/src/mtype.h

    r578 r619  
    575575#if CPP_MANGLE 
    576576    void toCppMangle(OutBuffer *buf, CppMangleState *cms); 
    577577#endif 
    578578    bool parameterEscapes(Parameter *p); 
    579579 
    580580    int callMatch(Expression *ethis, Expressions *toargs, int flag = 0); 
    581581    type *toCtype(); 
    582582    enum RET retStyle(); 
    583583 
    584584    unsigned totym(); 
    585585}; 
    586586 
    587587struct TypeDelegate : TypeNext 
    588588{ 
    589589    // .next is a TypeFunction 
    590590 
    591591    TypeDelegate(Type *t); 
    592592    Type *syntaxCopy(); 
    593593    Type *semantic(Loc loc, Scope *sc); 
    594594    d_uns64 size(Loc loc); 
     595    unsigned alignsize(); 
    595596    MATCH implicitConvTo(Type *to); 
    596597    void toCBuffer2(OutBuffer *buf, HdrGenState *hgs, int mod); 
    597598    Expression *defaultInit(Loc loc); 
    598599    int isZeroInit(Loc loc); 
    599600    int checkBoolean(); 
    600601    TypeInfoDeclaration *getTypeInfoDeclaration(); 
    601602    Expression *dotExp(Scope *sc, Expression *e, Identifier *ident); 
    602603    int hasPointers(); 
    603604#if CPP_MANGLE 
    604605    void toCppMangle(OutBuffer *buf, CppMangleState *cms); 
    605606#endif 
    606607 
    607608    type *toCtype(); 
    608609}; 
    609610 
    610611struct TypeQualified : Type 
    611612{ 
    612613    Loc loc; 
    613614    Array idents;       // array of Identifier's representing ident.ident.ident etc. 
    614615