asm/AJx86GPRegister.st
author Jan Vrany <jan.vrany@fit.cvut.cz>
Tue, 15 Dec 2015 23:18:02 +0000
changeset 3 483729eb4432
child 23 d2d9a2d4d6bf
permissions -rw-r--r--
Initial port ot Igor Stasenko's AsmJit

"{ Package: 'jv:dragonfly/asm' }"

"{ NameSpace: Smalltalk }"

AJRegister subclass:#AJx86GPRegister
	instanceVariableNames:''
	classVariableNames:''
	poolDictionaries:'AJx86Registers'
	category:'AsmJit-x86-Operands'
!

AJx86GPRegister comment:'A general purpose x86 & x64 registers'
!

!AJx86GPRegister methodsFor:'accessing'!

descriptionOn: s
    s nextPutAll: 'A '; print: self size * 8; nextPutAll: 'bit general purpose register'.
!

registerName 
    ^ name asString.
!

stackSize
    ^ self size
! !

!AJx86GPRegister methodsFor:'converting'!

as16
    ^ self isHighByte
        ifTrue: [ self asLowByte as16 ]
        ifFalse: [ 
            AJx86Registers
                generalPurposeWithIndex: self index
                size: 2
                requiresRex: self index > 7
                prohibitsRex: false ]
!

as32
    ^ self isHighByte
        ifTrue: [ self asLowByte as32 ]
        ifFalse: [ 
            AJx86Registers
                generalPurposeWithIndex: self index
                size: 4
                requiresRex: self index > 7
                prohibitsRex: false ]
!

as64
    ^ self isHighByte
        ifTrue: [ self asLowByte as64 ]
        ifFalse: [ 
            AJx86Registers
                generalPurposeWithIndex: self index
                size: 8
                requiresRex: self index > 7
                prohibitsRex: false ]
!

as8
    "8-bit low-byte registers require REX if they have a high index (>7), or if they are one of BPL, SIL, DIL, SPL (indices 4-7).
    The only way to get AH, BH, CH, or DH out of this method is to send it to one of those registers."

    ^ self is8
        ifTrue: [ self ]
        ifFalse: [ 
            AJx86Registers
                generalPurposeWithIndex: self index
                size: 1
                requiresRex: self index > 3
                prohibitsRex: false ]
!

asHighByte
    self isHighByte
        ifTrue: [ ^ self ].
    self isLowByte
        ifFalse: [ Error signal: 'Can only convert AH, BH, CH, or DH to high byte' ].
    ^ AJx86Registers
        generalPurposeWithIndex: self index + 2r100
        size: 1
        requiresRex: false
        prohibitsRex: true
!

asLowByte
    self isLowByte
        ifTrue: [ ^ self ].
    self isHighByte
        ifFalse: [ Error signal: 'Can only convert high byte 8bit register to low byte' ].
    ^ AJx86Registers
        generalPurposeWithIndex: self index - 2r100
        size: 1
        requiresRex: false
        prohibitsRex: false
!

ptr

    "turn receiver into a memory operand with receiver as base"
    
    ^ AJMem new base: self
! !

!AJx86GPRegister methodsFor:'emitting'!

emitModRM: emitter code: rCode immSize: immSize

    "Receiver is register, hence mod = 3 
    immSize is ignored"

    ^ emitter emitMod: 3 reg: rCode rm: self code
! !

!AJx86GPRegister methodsFor:'printing'!

printAsMemBaseOn: aStream

    aStream nextPutAll: self registerName 
!

printOn: aStream
    
    aStream nextPutAll: self registerName 
! !

!AJx86GPRegister methodsFor:'testing'!

isGeneralPurpose
    ^ true
!

isHighByte
    "return true for 8bit high-byte registers (AH - DH)"

    ^ self prohibitsRex
!

isLowByte
    "return true for 8bit low-byte register (AL - DL)"

    "Note that this does *not* answer true for all byte registers -- send #is8 for that."

    ^ self code <= 3
! !