# Rules to optimize BCC assembler output for 386 # Many of these rules are very broken, ho hum. # Rules for loading a long constant xor ax,ax xor %[bx|si|di]1,%[bx|si|di]1 = xor eax,eax xor eax,eax mov %[ebx|ecx|edx]1,eax = xor %1,%1 xor ax,ax mov %[bx|si|di]*,%[*|#]0%1 = mov eax,%0%1<<16 mov ax,%[*|#]0%1 xor %[bx|si|di]2,%[bx|si|di]2 = mov eax,%0%1 & $0000FFFF mov ax,%0[%1] xor %[bx|si|di]2,%[bx|si|di]2 = movzx eax,word ptr %0[%1] mov ax,%[si|di]1 xor bx,bx = movzx eax,%1 %[movzx|movsx]5 eax,%1 mov %[ebx|ecx|edx]2,eax = %5 %2,%1 %[movzx|movsx]5 %[ebx|ecx|edx]1,%2 mov eax,%[#|*]0%3 %[add|and|xor|or]4 eax,%[ebx|ecx|edx]1 = %5 eax,%2 %4 eax,%0%3 mov ax,%0[%1] cwde = movsx eax,word ptr %0[%1] mov ax,%[si|di]1 cwde = movsx eax,%1 mov ax,%[#|*]3%1 mov %[bx|si|di]*,%[#|*]4%2 = mov eax,%4%2<<16 + %1 # Rules for pushing variables and constants onto the stack push %![dword ptr]%1[%[bx|si|di|bp]3] push %![dword ptr]%(%1-2)[%[bx|si|di|bp]3] = push dword ptr %(%1-2)[%3] push [%1+2] push [%1] = push dword ptr [%1] push %[bx|si|di]* push ax = push eax mov eax,%[#|*]0%1 push eax = push dword %0%1 mov %1,%[eax|ebx|ecx|edx]2 push dword ptr %1 = mov %1,%2 push %2 # Rules for loading long variables mov ax,[%1] mov %[bx|si|di]*,[%1+2] = mov eax,[%1] mov ax,%1[%[bx|si|di|bp]3] mov %[bx|si|di]*,%(%1+2)[%[bx|si|di|bp]3] = mov eax,%1[%3] mov ax,#%1[bx] mov %[bx|si|di]*,#%1+2[bx] = mov eax,#%1[bx] mov [%1],ax mov [%1+2],%[bx|si|di]* = mov [%1],eax mov [%1+%3],ax mov [%1+%(%3+2)],%[bx|si|di]* = mov [%1+%3],eax mov %1[%[si|di|bp]3],ax mov %(%1+2)[%[si|di|bp]3],%[bx|si|di]* = mov %1[%3],eax mov #%1[bx],ax mov #%1+2[bx],%[bx|si|di]* = mov #%1[bx],eax mov eax,%[#|*]0%1 mov %![dword ptr]%3[%2],eax = mov dword ptr %3[%2],%0%1 xor ax,ax xor %[bx|si|di]3,%[bx|si|di]3 mov %1[%[bx|bp]4],ax mov %(%1+2)[%[bx|bp]4],%[bx|si|di]3 = mov dword ptr %1[%4],#0 mov ax,%1 mov %[bx|si|di]5,%2 mov %3[%[bx|bp]6],ax mov %(%3+2)[%[bx|bp]6],%[bx|si|di]5 = mov eax,dword ptr %1 mov dword ptr %3[%6],eax # Long return values are in EAX, so we can skip dx mov dx,bx add sp,*%1 = add sp,*%1 # Rules for manipulating long values call %1 mov bx,dx = call %1 call l%[tstu|tst]*l = test eax,eax call l%[comu|com]*l = not eax mov eax,eax %1 = %1 mov %2,%[eax|ebx|ecx|edx]1 mov %[eax|ebx|ecx|edx]1,%2 = mov %2,%1 cwd mov bx,dx = cwde mov %[ebx|ecx|edx]0,%1 mov eax,%2 %3 eax,%[ebc|ecx|edx]0 = mov eax,%2 %3 eax,%1 %[movzx|movsx|mov]0 %[eax|ebx|ecx|edx]2,%4 %[add|and|xor|sub|or]1 %[eax|ebx|ecx|edx]2,%6 mov %6,%[eax|ebx|ecx|edx]2 = %0 %2,%4 %1 %6,%2 mov eax,%[#|*]0%1 cmp eax,%2 %[jbe |jae |jne |jge |jle ]3 %4 = cmp dword ptr %2,%0%1 %=[jbe |jae |jne |jge |jle ][jae |jbe |jne |jle |jge ]3 %4 mov eax,%[#|*]0%1 cmp eax,%2 %[jb |ja |je |jg |jl ]3 %4 = cmp dword ptr %2,%0%1 %=[jb |ja |je |jg |jl ][ja |jb |je |jl |jg ]3 %4 mov eax,%1[%3] cmp eax,dword %[#|*]0%2 = cmp dword ptr %1[%3],%0%2 # Rules for calling the bcc library routines. push %1 push %2 mov eax,%3[bp] %4 eax,%(%3-4)[bp] add sp,*8 = mov edx,%2 mov eax,%1 %4 eax,edx push %1 mov eax,%2 push eax mov eax,%3[bp] %4 eax,%(%3-4)[bp] add sp,*8 = mov edx,%2 mov eax,%1 %4 eax,edx push %1 xor eax,eax push eax mov eax,%2[bp] %3 eax,%(%2-4)[bp] add sp,*8 = mov eax,%1 %3 eax,#0 push %1 mov eax,%2 %3 eax,%4[bp] add sp,*4 = mov edx,%1 mov eax,%2 %3 eax,edx push %1 mov eax,%2 %3 eax,%4[bp] mov %2,eax add sp,*4 = mov edx,%1 %3 %2,edx push %1 push %2 mov eax,%3[bp] %4 eax,%(%3-4)[bp] lea sp,%(%3+4)[bp] = mov edx,%2 mov eax,%1 %4 eax,edx push %1 mov eax,%2 push eax mov eax,%3[bp] %4 eax,%(%3-4)[bp] lea sp,%(%3+4)[bp] = mov edx,%2 mov eax,%1 %4 eax,edx push %1 xor eax,eax push eax mov eax,%2[bp] %3 eax,%(%2-4)[bp] lea sp,%(%2+4)[bp] = mov eax,%1 %3 eax,#0 push %1 mov eax,%2 %3 eax,%4[bp] lea sp,%(%4+4)[bp] = mov edx,%1 mov eax,%2 %3 eax,edx # Rules for calling the basic bcc library routines. mov di,#%2 call l%3%[ul|l]* = %3 eax,[%2] mov di,*%2 call lsll = lsl eax,*%2 lea di,%2 call l%3%[ul|l]* = %3 eax,%2 mov di,%[si|di]1 call l%3%[ul|l]* = %3 eax,[%1] mov di,%[ax|bx|cx|dx]1 call l%3%[ul|l]* = mov di,%[ax|bx|cx|dx]1 %3 eax,[di] # Rules for pushing short values mov %[ax|bx|cx|dx|si|di]2,%0[%1] push %[ax|bx|cx|dx|si|di]2 = push word ptr %0[%1] mov %[ax|bx|cx|dx|si|di]2,%[#|*]0%1 push %[ax|bx|cx|dx|si|di]2 = push %0%1 # Shifting rules %[shl|shr]2 %1,*1 %[shl|shr]2 %1,*1 = %2 %1,*2 mov cl,*%1 %[shl|shr]2 %3,cl = %2 %3,*%1 mov dx,ax shl ax,*%1 add ax,dx shl ax,*%2 = mov dx,ax imul ax,*%(1<%1+1<%2) mov dx,ax imul ax,*%1 add ax,dx = mov dx,ax imul ax,*%(%1+1) mov dx,ax imul ax,*%1 shl ax,*%2 = mov dx,ax imul ax,*%(%1<%2) mov ax,%![#|*]%4 mov dx,ax imul ax,*%1 %[add|and|xor|sub|or]2 ax,%![dx]%3 = imul ax,%4,*%1 %2 ax,%3 mov ax,%![#|*]%4 mov dx,ax imul ax,*%1 push ax = imul ax,%4,*%1 push ax imul ax,%2,%[#|*]0%1 add ax,%3 mov bx,ax = imul bx,%2,%0%1 add bx,%3 # Different rules %1 dword ptr %[eax|ebx|ecx|edx]3,*%2 = %1 %3,*%2 %1 dword ptr %[eax|ebx|ecx|edx]3,#%2 = %1 %3,#%2 eor %1,%2 = xor %1,%2 com %1 = not %1 xor bx,bx = and eax,#$0000FFFF