[Vm-dev] VM Maker: VMMaker.oscog-nice.1711.mcz

Eliot Miranda eliot.miranda at gmail.com
Sat Mar 5 01:27:26 UTC 2016


Thanks Nicolas!  And great that you found slips.  The more eyes the merrier.

On Fri, Mar 4, 2016 at 5:24 PM, <commits at source.squeak.org> wrote:

>
> Nicolas Cellier uploaded a new version of VMMaker to project VM Maker:
> http://source.squeak.org/VMMaker/VMMaker.oscog-nice.1711.mcz
>
> ==================== Summary ====================
>
> Name: VMMaker.oscog-nice.1711
> Author: nice
> Time: 5 March 2016, 2:14:57.11 am
> UUID: 9e7ba417-b6ed-4263-82f2-27ec641d8f30
> Ancestors: VMMaker.oscog-eem.1709
>
> 3 minor fixes for type inference:
> 1) remove unecessary block argument assignment
> 2) infer type of allMask:
> 3) infer type of rem: instead of mod: (mod: does not exist)
>
> Don't use cCode: pointer aliasing for storing/fetching float/double in FFI
> primitives.
> Replace with a call to mem:cp:y:
> - the first one is dangerous with modern C compilers
> - while the second is optimized away (no call to memcpy)
>
> =============== Diff against VMMaker.oscog-eem.1709 ===============
>
> Item was changed:
>   ----- Method: FFIPlugin>>primitiveFFIDoubleAt (in category 'primitives')
> -----
>   primitiveFFIDoubleAt
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #double>
> -       <var: #floatValue type:'double '>
>         byteOffset := interpreterProxy stackIntegerValue: 0.
>         rcvr := interpreterProxy stackObjectValue: 1.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 8.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: (self addressOf: floatValue) cp: addr y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)(&floatValue))[0] = ((int*)addr)[0]'.
> -       self cCode:'((int*)(&floatValue))[1] = ((int*)addr)[1]'.
>         interpreterProxy pop: 2.
>         ^interpreterProxy pushFloat: floatValue
>   !
>
> Item was changed:
>   ----- Method: FFIPlugin>>primitiveFFIDoubleAtPut (in category
> 'primitives') -----
>   primitiveFFIDoubleAtPut
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue floatOop |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #double>
> -       <var: #floatValue type:'double '>
>         floatOop := interpreterProxy stackValue: 0.
>         (interpreterProxy isIntegerObject: floatOop)
>                 ifTrue:[floatValue := self cCoerce: (interpreterProxy
> integerValueOf: floatOop) to:'double']
>                 ifFalse:[floatValue := self cCoerce: (interpreterProxy
> floatValueOf: floatOop) to:'double'].
>         byteOffset := interpreterProxy stackIntegerValue: 1.
>         rcvr := interpreterProxy stackObjectValue: 2.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 8.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: addr cp: (self addressOf: floatValue) y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)addr)[0] = ((int*)(&floatValue))[0]'.
> -       self cCode:'((int*)addr)[1] = ((int*)(&floatValue))[1]'.
>         interpreterProxy pop: 3.
>         ^interpreterProxy push: floatOop!
>
> Item was changed:
>   ----- Method: FFIPlugin>>primitiveFFIFloatAt (in category 'primitives')
> -----
>   primitiveFFIFloatAt
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #float>
> -       <var: #floatValue type:'float '>
>         byteOffset := interpreterProxy stackIntegerValue: 0.
>         rcvr := interpreterProxy stackObjectValue: 1.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 4.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: (self addressOf: floatValue) cp: addr y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)(&floatValue))[0] = ((int*)addr)[0]'.
>         interpreterProxy pop: 2.
>         ^interpreterProxy pushFloat: floatValue!
>
> Item was changed:
>   ----- Method: FFIPlugin>>primitiveFFIFloatAtPut (in category
> 'primitives') -----
>   primitiveFFIFloatAtPut
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue floatOop |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #float>
> -       <var: #floatValue type:'float '>
>         floatOop := interpreterProxy stackValue: 0.
>         (interpreterProxy isIntegerObject: floatOop)
>                 ifTrue:[floatValue := self cCoerce: (interpreterProxy
> integerValueOf: floatOop) to:'float']
>                 ifFalse:[floatValue := self cCoerce: (interpreterProxy
> floatValueOf: floatOop) to:'float'].
>         byteOffset := interpreterProxy stackIntegerValue: 1.
>         rcvr := interpreterProxy stackObjectValue: 2.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 4.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: addr cp: (self addressOf: floatValue) y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)addr)[0] = ((int*)(&floatValue))[0]'.
>         interpreterProxy pop: 3.
>         ^interpreterProxy push: floatOop!
>
> Item was changed:
>   ----- Method: IA32ABIPlugin>>primDoubleAt (in category
> 'primitives-accessing') -----
>   primDoubleAt
>         "Answer the 64-bit double starting at the given byte offset
> (little endian)."
>         "<Alien> doubleAt: index <Integer> ^<Float>
>                 <primitive: 'primDoubleAt' error: errorCode module:
> 'IA32ABI'>"
>         | byteOffset rcvr startAddr addr floatValue |
>         <export: true>
> +       <var: #floatValue type: #double>
> -       <var: #floatValue type:'double '>
>
>         byteOffset := (interpreterProxy stackPositiveMachineIntegerValue:
> 0) - 1.
>         rcvr := interpreterProxy stackObjectValue: 1.
>         interpreterProxy failed ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadArgument].
>         (self index: byteOffset length: 8 inRange: rcvr) ifFalse:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadIndex].
>         (startAddr := self startOfData: rcvr) = 0 ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadReceiver].
>         addr := startAddr + byteOffset.
> +       self mem: (self addressOf: floatValue) cp: addr y: (self sizeof:
> floatValue).
> -       self cCode:'((long *)(&floatValue))[0] = ((long *)addr)[0]; ((long
> *)(&floatValue))[1] = ((long *)addr)[1]'
> -               inSmalltalk: [floatValue := rcvr doubleAt: byteOffset].
>         interpreterProxy pop: 2.
>         ^interpreterProxy pushFloat: floatValue!
>
> Item was changed:
>   ----- Method: IA32ABIPlugin>>primDoubleAtPut (in category
> 'primitives-accessing') -----
>   primDoubleAtPut
>         "Store a double into 64 bits starting at the given byte offset
> (little endian)."
>         "<Alien> doubleAt: index <Integer> put: value <Float | Integer>
> ^<Float | Integer>
>                 <primitive: 'primDoubleAtPut' error: errorCode module:
> 'IA32ABI'>"
>         | byteOffset rcvr startAddr addr valueOop floatValue |
>         <export: true>
>         <var: #floatValue type: #double>
>
>         valueOop := interpreterProxy stackValue: 0.
>         (interpreterProxy isIntegerObject: valueOop)
>                 ifTrue:[floatValue := self cCoerce: (interpreterProxy
> integerValueOf: valueOop) to: #double]
>                 ifFalse:[floatValue := self cCoerce: (interpreterProxy
> floatValueOf: valueOop) to: #double].
>         byteOffset := (interpreterProxy stackPositiveMachineIntegerValue:
> 1) - 1.
>         rcvr := interpreterProxy stackObjectValue: 2.
>         interpreterProxy failed ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadArgument].
>         (self index: byteOffset length: 8 inRange: rcvr) ifFalse:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadIndex].
>         (interpreterProxy isOopImmutable: rcvr) ifTrue:
>                 [^interpreterProxy primitiveFailFor:
> PrimErrNoModification].
>         (startAddr := self startOfData: rcvr) = 0 ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadReceiver].
>         addr := startAddr + byteOffset.
> +       self mem: addr cp: (self addressOf: floatValue) y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)addr)[0] = ((int*)(&floatValue))[0]'.
> -       self cCode:'((int*)addr)[1] = ((int*)(&floatValue))[1]'.
>         interpreterProxy methodReturnValue: valueOop!
>
> Item was changed:
>   ----- Method: IA32ABIPlugin>>primFloatAt (in category
> 'primitives-accessing') -----
>   primFloatAt
>         "Answer the 32-bit float starting at the given byte offset (little
> endian)."
>         "<Alien> floatAt: index <Integer> ^<Float>
>                 <primitive: 'primFloatAt' error: errorCode module:
> 'IA32ABI'>"
>         | byteOffset rcvr startAddr addr floatValue |
>         <export: true>
> +       <var: #floatValue type: #float>
> -       <var: #floatValue type: 'float '>
>
>         byteOffset := (interpreterProxy stackPositiveMachineIntegerValue:
> 0) - 1.
>         rcvr := interpreterProxy stackObjectValue: 1.
>         interpreterProxy failed ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadArgument].
>         (self index: byteOffset length: 4 inRange: rcvr) ifFalse:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadIndex].
>         (startAddr := self startOfData: rcvr) = 0 ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadReceiver].
>         addr := startAddr + byteOffset.
> +       self mem: (self addressOf: floatValue) cp: addr y: (self sizeof:
> floatValue).
> -       self cCode:'((long *)(&floatValue))[0] = ((long *)addr)[0]'
> -               inSmalltalk: [floatValue := rcvr floatAt: byteOffset].
>         interpreterProxy pop: 2.
>         ^interpreterProxy pushFloat: floatValue!
>
> Item was changed:
>   ----- Method: IA32ABIPlugin>>primFloatAtPut (in category
> 'primitives-accessing') -----
>   primFloatAtPut
>         "Store a float into 32 bits starting at the given byte offset
> (little endian)."
>         "<Alien> floatAt: index <Integer> put: value <Float | Integer>
> ^<Float | Integer>
>                 <primitive: 'primFloatAtPut' error: errorCode module:
> 'IA32ABI'>"
>         | byteOffset rcvr startAddr addr valueOop floatValue |
>         <export: true>
>         <var: #floatValue type: #float>
>
>         valueOop := interpreterProxy stackValue: 0.
>         (interpreterProxy isIntegerObject: valueOop)
>                 ifTrue:[floatValue := self cCoerce: (interpreterProxy
> integerValueOf: valueOop) to: #double]
>                 ifFalse:[floatValue := self cCoerce: (interpreterProxy
> floatValueOf: valueOop) to: #double].
>         byteOffset := (interpreterProxy stackPositiveMachineIntegerValue:
> 1) - 1.
>         rcvr := interpreterProxy stackObjectValue: 2.
>         interpreterProxy failed ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadArgument].
>         (self index: byteOffset length: 4 inRange: rcvr) ifFalse:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadIndex].
>         (interpreterProxy isOopImmutable: rcvr) ifTrue:
>                 [^interpreterProxy primitiveFailFor:
> PrimErrNoModification].
>         (startAddr := self startOfData: rcvr) = 0 ifTrue:
>                 [^interpreterProxy primitiveFailFor: PrimErrBadReceiver].
>         addr := startAddr + byteOffset.
> +       self mem: addr cp: (self addressOf: floatValue) y: (self sizeof:
> floatValue).
> -       self cCode:'((long *)addr)[0] = ((long *)(&floatValue))[0]'.
>         interpreterProxy methodReturnValue: valueOop!
>
> Item was changed:
>   ----- Method: TMethod>>addTypesFor:to:in: (in category 'type inference')
> -----
>   addTypesFor: node to: typeSet in: aCodeGen
>         "Add the value tupes for the node to typeSet.
>          Answer if any type was derived from an as-yet-untyped method,
> which allows us to abort
>          inferReturnTypeFromReturnsIn: if the return type depends on a
> yet-to-be-typed method."
>         | expr |
>         expr := node.
>         [expr isAssignment or: [expr isStmtList]] whileTrue:
>                 [expr isAssignment ifTrue:
>                         [expr := expr variable].
>                  expr isStmtList ifTrue:
>                         [expr := expr statements last]].
>         expr isSend ifTrue:
>                 [(#(ifTrue: ifFalse: ifTrue:ifFalse: ifFalse:ifTrue:)
> includes: expr selector) ifTrue:
>                         [^expr args
>                                 inject: false
>                                 into: [:asYetUntyped :block|
> +                                       asYetUntyped | (self addTypesFor:
> block to: typeSet in: aCodeGen)]].
> +                (#(= ~= == ~~ < > <= >= anyMask: allMask: noMask:)
> includes: expr selector) ifTrue:
> -                                       asYetUntyped := asYetUntyped |
> (self addTypesFor: block to: typeSet in: aCodeGen)]].
> -                (#(= ~= == ~~ < > <= >= anyMask: noMask:) includes: expr
> selector) ifTrue:
>                         [typeSet add: #sqInt. ^false].
> +                (#(+ - * / // \\ rem: quo: bitAnd: bitClear: bitOr:
> bitXor: bitShift:) includes: expr selector) ifTrue:
> -                (#(+ - * / // \\ mod: quo: bitAnd: bitClear: bitOr:
> bitXor: bitShift:) includes: expr selector) ifTrue:
>                         [| types |
>                          types := Set new.
>                          self addTypesFor: expr receiver to: types in:
> aCodeGen.
>                          (types size = 1 and: [types anyOne last = $*])
> ifTrue: "pointer arithmetic"
>                                 [typeSet add: types anyOne. ^false].
>                          self addTypesFor: expr args first to: types in:
> aCodeGen.
>                          types := aCodeGen harmonizeReturnTypesIn: types.
>                          types size = 2 ifTrue:
>                                 [(types includes: #double) ifTrue:
>                                         [typeSet add: #double. ^false].
>                                  (types includes: #float) ifTrue:
>                                         [typeSet add: #float. ^false].
>                                 ^false]. "don't know; leave unspecified."
>                         types notEmpty ifTrue:
>                                 [typeSet add: types anyOne].
>                         ^false].
>                 "Abort only for untyped methods that will be typed, but
> don't be phased by recursion."
>                  ^(aCodeGen returnTypeForSend: expr in: self)
>                         ifNotNil: [:type| typeSet add: type. false]
>                         ifNil: [(aCodeGen methodNamed: expr selector)
> notNil and: [expr selector ~~ selector]]].
>         expr isVariable ifTrue:
>                 [(aCodeGen typeOfVariable: expr name)
>                         ifNotNil: [:type| typeSet add: type]
>                         ifNil: [typeSet add: (expr name = 'self'
>
>       ifTrue: [#void]
>
>       ifFalse: [#sqInt])]].
>         expr isConstant ifTrue:
>                 [| val |
>                  val := expr value.
>                  val isInteger ifTrue:
>                         [typeSet add: ((val >= 0 ifTrue: [val] ifFalse:
> [-1 - val]) highBit <= 32
>
> ifTrue: [#sqInt]
>
> ifFalse: [#sqLong])].
>                  (#(nil true false) includes: val) ifTrue:
>                         [typeSet add: #sqInt].
>                  val isFloat ifTrue:
>                         [typeSet add: #float]].
>         ^false!
>
> Item was changed:
>   ----- Method: ThreadedFFIPlugin>>primitiveFFIDoubleAt (in category
> 'primitives') -----
>   primitiveFFIDoubleAt
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #double>
> -       <var: #floatValue type:'double '>
>         byteOffset := interpreterProxy stackIntegerValue: 0.
>         rcvr := interpreterProxy stackObjectValue: 1.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 8.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: (self addressOf: floatValue) cp: addr y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)(&floatValue))[0] = ((int*)addr)[0]'.
> -       self cCode:'((int*)(&floatValue))[1] = ((int*)addr)[1]'.
>         interpreterProxy pop: 2.
>         ^interpreterProxy pushFloat: floatValue
>   !
>
> Item was changed:
>   ----- Method: ThreadedFFIPlugin>>primitiveFFIDoubleAtPut (in category
> 'primitives') -----
>   primitiveFFIDoubleAtPut
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue floatOop |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #double>
> -       <var: #floatValue type:'double '>
>         floatOop := interpreterProxy stackValue: 0.
>         (interpreterProxy isIntegerObject: floatOop)
>                 ifTrue:[floatValue := self cCoerce: (interpreterProxy
> integerValueOf: floatOop) to:'double']
>                 ifFalse:[floatValue := self cCoerce: (interpreterProxy
> floatValueOf: floatOop) to:'double'].
>         byteOffset := interpreterProxy stackIntegerValue: 1.
>         rcvr := interpreterProxy stackObjectValue: 2.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 8.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: addr cp: (self addressOf: floatValue) y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)addr)[0] = ((int*)(&floatValue))[0]'.
> -       self cCode:'((int*)addr)[1] = ((int*)(&floatValue))[1]'.
>         ^interpreterProxy pop: 3 thenPush: floatOop!
>
> Item was changed:
>   ----- Method: ThreadedFFIPlugin>>primitiveFFIFloatAt (in category
> 'primitives') -----
>   primitiveFFIFloatAt
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #float>
> -       <var: #floatValue type:'float '>
>         byteOffset := interpreterProxy stackIntegerValue: 0.
>         rcvr := interpreterProxy stackObjectValue: 1.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 4.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: (self addressOf: floatValue) cp: addr y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)(&floatValue))[0] = ((int*)addr)[0]'.
>         interpreterProxy pop: 2.
>         ^interpreterProxy pushFloat: floatValue!
>
> Item was changed:
>   ----- Method: ThreadedFFIPlugin>>primitiveFFIFloatAtPut (in category
> 'primitives') -----
>   primitiveFFIFloatAtPut
>         "Return a (signed or unsigned) n byte integer from the given byte
> offset."
>         | byteOffset rcvr addr floatValue floatOop |
>         <export: true>
>         <inline: false>
> +       <var: #floatValue type: #float>
> -       <var: #floatValue type:'float '>
>         floatOop := interpreterProxy stackValue: 0.
>         (interpreterProxy isIntegerObject: floatOop)
>                 ifTrue:[floatValue := self cCoerce: (interpreterProxy
> integerValueOf: floatOop) to:'float']
>                 ifFalse:[floatValue := self cCoerce: (interpreterProxy
> floatValueOf: floatOop) to:'float'].
>         byteOffset := interpreterProxy stackIntegerValue: 1.
>         rcvr := interpreterProxy stackObjectValue: 2.
>         interpreterProxy failed ifTrue:[^0].
>         addr := self ffiAddressOf: rcvr startingAt: byteOffset size: 4.
>         interpreterProxy failed ifTrue:[^0].
> +       self mem: addr cp: (self addressOf: floatValue) y: (self sizeof:
> floatValue).
> -       self cCode:'((int*)addr)[0] = ((int*)(&floatValue))[0]'.
>         ^interpreterProxy pop: 3 thenPush: floatOop!
>
>


-- 
_,,,^..^,,,_
best, Eliot
-------------- next part --------------
An HTML attachment was scrubbed...
URL: http://lists.squeakfoundation.org/pipermail/vm-dev/attachments/20160304/ee808409/attachment-0001.htm


More information about the Vm-dev mailing list