From 785f8620fd889ba829ba9b2e0c974d3b7018bc26 Mon Sep 17 00:00:00 2001 From: Joe Groff Date: Tue, 6 Oct 2009 20:13:38 -0500 Subject: [PATCH] glue conversion intrinsics to instructions --- .../compiler/cfg/intrinsics/intrinsics.factor | 6 ++ .../tree/propagation/simd/simd.factor | 6 ++ .../math/vectors/simd/functor/functor.factor | 61 ++++++++++++++++++- .../vectors/simd/intrinsics/intrinsics.factor | 37 +++++++++-- basis/math/vectors/simd/simd-tests.factor | 3 + .../specialization/specialization.factor | 16 ++++- 6 files changed, 119 insertions(+), 10 deletions(-) diff --git a/basis/compiler/cfg/intrinsics/intrinsics.factor b/basis/compiler/cfg/intrinsics/intrinsics.factor index bf65b50897..0b6f5a94d5 100644 --- a/basis/compiler/cfg/intrinsics/intrinsics.factor +++ b/basis/compiler/cfg/intrinsics/intrinsics.factor @@ -196,6 +196,12 @@ IN: compiler.cfg.intrinsics { math.vectors.simd.intrinsics:(simd-vshuffle) [ emit-shuffle-vector ] } { math.vectors.simd.intrinsics:(simd-(vmerge-head)) [ [ ^^merge-vector-head ] emit-binary-vector-op ] } { math.vectors.simd.intrinsics:(simd-(vmerge-tail)) [ [ ^^merge-vector-tail ] emit-binary-vector-op ] } + { math.vectors.simd.intrinsics:(simd-(v>float)) [ [ ^^integer>float-vector ] emit-unary-vector-op ] } + { math.vectors.simd.intrinsics:(simd-(v>integer)) [ [ ^^float>integer-vector ] emit-unary-vector-op ] } + { math.vectors.simd.intrinsics:(simd-(vpack-signed)) [ [ ^^signed-pack-vector ] emit-binary-vector-op ] } + { math.vectors.simd.intrinsics:(simd-(vpack-unsigned)) [ [ ^^unsigned-pack-vector ] emit-binary-vector-op ] } + { math.vectors.simd.intrinsics:(simd-(vunpack-head)) [ [ ^^unpack-vector-head ] emit-unary-vector-op ] } + { math.vectors.simd.intrinsics:(simd-(vunpack-tail)) [ [ ^^unpack-vector-tail ] emit-unary-vector-op ] } { math.vectors.simd.intrinsics:(simd-select) [ emit-select-vector ] } { math.vectors.simd.intrinsics:(simd-sum) [ [ ^^horizontal-add-vector ] emit-unary-vector-op ] } { math.vectors.simd.intrinsics:alien-vector [ emit-alien-vector ] } diff --git a/basis/compiler/tree/propagation/simd/simd.factor b/basis/compiler/tree/propagation/simd/simd.factor index ba319d5f85..4e9734693b 100644 --- a/basis/compiler/tree/propagation/simd/simd.factor +++ b/basis/compiler/tree/propagation/simd/simd.factor @@ -33,6 +33,12 @@ IN: compiler.tree.propagation.simd (simd-vshuffle) (simd-(vmerge-head)) (simd-(vmerge-tail)) + (simd-(v>float)) + (simd-(v>integer)) + (simd-(vpack-signed)) + (simd-(vpack-unsigned)) + (simd-(vunpack-head)) + (simd-(vunpack-tail)) (simd-v<=) (simd-v<) (simd-v=) diff --git a/basis/math/vectors/simd/functor/functor.factor b/basis/math/vectors/simd/functor/functor.factor index 1c4c77133e..efdddc16e0 100644 --- a/basis/math/vectors/simd/functor/functor.factor +++ b/basis/math/vectors/simd/functor/functor.factor @@ -3,6 +3,7 @@ USING: accessors assocs byte-arrays classes classes.algebra effects fry functors generalizations kernel literals locals math math.functions math.vectors math.vectors.private math.vectors.simd.intrinsics +math.vectors.conversion math.vectors.conversion.private math.vectors.specialization parser prettyprint.custom sequences sequences.private strings words definitions macros cpu.architecture namespaces arrays quotations combinators combinators.short-circuit sets @@ -174,6 +175,8 @@ A-vn->v-op DEFINES-PRIVATE ${A}-vn->v-op A-vv->n-op DEFINES-PRIVATE ${A}-vv->n-op A-v->v-op DEFINES-PRIVATE ${A}-v->v-op A-v->n-op DEFINES-PRIVATE ${A}-v->n-op +A-v-conversion-op DEFINES-PRIVATE ${A}-v-conversion-op +A-vv-conversion-op DEFINES-PRIVATE ${A}-vv-conversion-op A-element-class [ A-rep rep-component-type c:c-type-boxed-class ] @@ -251,10 +254,29 @@ INSTANCE: A sequence : A-v->n-op ( v quot -- n ) [ underlying>> A-rep ] dip call ; inline +: A-v-conversion-op ( v1 to-type quot -- v2 ) + swap [ underlying>> A-rep ] [ call ] [ '[ _ boa ] call( u -- v ) ] tri* ; inline + +: A-vv-conversion-op ( v1 v2 to-type quot -- v2 ) + swap { + [ underlying>> ] + [ underlying>> A-rep ] + [ call ] + [ '[ _ boa ] call( u -- v ) ] + } spread ; inline + simd new \ A >>class \ A-with >>ctor \ A-rep >>rep + { + { (v>float) A-v-conversion-op } + { (v>integer) A-v-conversion-op } + { (vpack-signed) A-vv-conversion-op } + { (vpack-unsigned) A-vv-conversion-op } + { (vunpack-head) A-v-conversion-op } + { (vunpack-tail) A-v-conversion-op } + } >>special-wrappers { { { +vector+ +vector+ -> +vector+ } A-vv->v-op } { { +vector+ +scalar+ -> +vector+ } A-vn->v-op } @@ -327,6 +349,10 @@ A-vany-op DEFINES-PRIVATE ${A}-vany-op A-vall-op DEFINES-PRIVATE ${A}-vall-op A-vmerge-head-op DEFINES-PRIVATE ${A}-vmerge-head-op A-vmerge-tail-op DEFINES-PRIVATE ${A}-vmerge-tail-op +A-v-conversion-op DEFINES-PRIVATE ${A}-v-conversion-op +A-vpack-op DEFINES-PRIVATE ${A}-vpack-op +A-vunpack-head-op DEFINES-PRIVATE ${A}-vunpack-head-op +A-vunpack-tail-op DEFINES-PRIVATE ${A}-vunpack-tail-op WHERE @@ -426,14 +452,39 @@ INSTANCE: A sequence [ underlying1>> ] bi@ [ A-rep (simd-(vmerge-head)) ] [ A-rep (simd-(vmerge-tail)) ] 2bi - \ A boa ; + \ A boa ; inline : A-vmerge-tail-op ( v1 v2 quot -- v ) drop [ underlying2>> ] bi@ [ A-rep (simd-(vmerge-head)) ] [ A-rep (simd-(vmerge-tail)) ] 2bi - \ A boa ; + \ A boa ; inline + +: A-v-conversion-op ( v1 to-type quot -- v ) + swap [ + [ [ underlying1>> A-rep ] dip call ] + [ [ underlying2>> A-rep ] dip call ] 2bi + ] dip '[ _ boa ] call( u1 u2 -- v ) ; inline + +: A-vpack-op ( v1 v2 to-type quot -- v ) + swap [ + '[ [ underlying1>> ] [ underlying2>> ] bi A-rep @ ] bi* + ] dip '[ _ boa ] call( u1 u2 -- v ) ; inline + +: A-vunpack-head-op ( v1 to-type quot -- v ) + '[ + underlying1>> + [ A-rep @ ] + [ A-rep (simd-(vunpack-tail)) ] bi + ] dip '[ _ boa ] call( u1 u2 -- v ) ; inline + +: A-vunpack-tail-op ( v1 to-type quot -- v ) + '[ + underlying2>> + [ A-rep (simd-(vunpack-head)) ] + [ A-rep @ ] bi + ] dip '[ _ boa ] call( u1 u2 -- v ) ; inline simd new \ A >>class @@ -447,6 +498,12 @@ simd new { vall? A-vall-op } { (vmerge-head) A-vmerge-head-op } { (vmerge-tail) A-vmerge-tail-op } + { (v>integer) A-v-conversion-op } + { (v>float) A-v-conversion-op } + { (vpack-signed) A-vpack-op } + { (vpack-unsigned) A-vpack-op } + { (vunpack-head) A-vunpack-head-op } + { (vunpack-tail) A-vunpack-tail-op } } >>special-wrappers { { { +vector+ +vector+ -> +vector+ } A-vv->v-op } diff --git a/basis/math/vectors/simd/intrinsics/intrinsics.factor b/basis/math/vectors/simd/intrinsics/intrinsics.factor index 0fd0d13f84..6f0bea3b98 100644 --- a/basis/math/vectors/simd/intrinsics/intrinsics.factor +++ b/basis/math/vectors/simd/intrinsics/intrinsics.factor @@ -2,7 +2,9 @@ ! See http://factorcode.org/license.txt for BSD license. USING: alien alien.c-types alien.data assocs combinators cpu.architecture compiler.cfg.comparisons fry generalizations -kernel libc macros math sequences effects accessors namespaces +kernel libc macros math +math.vectors.conversion math.vectors.conversion.private +sequences effects accessors namespaces lexer parser vocabs.parser words arrays math.vectors ; IN: math.vectors.simd.intrinsics @@ -12,17 +14,27 @@ ERROR: bad-simd-call ; : simd-effect ( word -- effect ) stack-effect [ in>> "rep" suffix ] [ out>> ] bi ; +: simd-conversion-effect ( word -- effect ) + stack-effect [ in>> but-last "rep" suffix ] [ out>> ] bi ; SYMBOL: simd-ops V{ } clone simd-ops set-global -SYNTAX: SIMD-OP: - scan-word dup name>> "(simd-" ")" surround create-in - [ nip [ bad-simd-call ] define ] - [ [ simd-effect ] dip set-stack-effect ] +: (SIMD-OP:) ( accum quot -- accum ) + [ + scan-word dup name>> "(simd-" ")" surround create-in + [ nip [ bad-simd-call ] define ] + ] dip + '[ _ dip set-stack-effect ] [ 2array simd-ops get push ] - 2tri ; + 2tri ; inline + +SYNTAX: SIMD-OP: + [ simd-effect ] (SIMD-OP:) ; + +SYNTAX: SIMD-CONVERSION-OP: + [ simd-conversion-effect ] (SIMD-OP:) ; >> @@ -67,6 +79,13 @@ SIMD-OP: vany? SIMD-OP: vall? SIMD-OP: vnone? +SIMD-CONVERSION-OP: (v>float) +SIMD-CONVERSION-OP: (v>integer) +SIMD-CONVERSION-OP: (vpack-signed) +SIMD-CONVERSION-OP: (vpack-unsigned) +SIMD-CONVERSION-OP: (vunpack-head) +SIMD-CONVERSION-OP: (vunpack-tail) + : (simd-with) ( x rep -- v ) bad-simd-call ; : (simd-gather-2) ( a b rep -- v ) bad-simd-call ; : (simd-gather-4) ( a b c d rep -- v ) bad-simd-call ; @@ -151,6 +170,12 @@ M: vector-rep supported-simd-op? { \ (simd-vshuffle) [ %shuffle-vector-reps ] } { \ (simd-(vmerge-head)) [ %merge-vector-reps ] } { \ (simd-(vmerge-tail)) [ %merge-vector-reps ] } + { \ (simd-(v>float)) [ %integer>float-vector-reps ] } + { \ (simd-(v>integer)) [ %float>integer-vector-reps ] } + { \ (simd-(vpack-signed)) [ %signed-pack-vector-reps ] } + { \ (simd-(vpack-unsigned)) [ %unsigned-pack-vector-reps ] } + { \ (simd-(vunpack-head)) [ %unpack-vector-reps ] } + { \ (simd-(vunpack-tail)) [ %unpack-vector-reps ] } { \ (simd-v<=) [ cc<= %compare-vector-reps ] } { \ (simd-v<) [ cc< %compare-vector-reps ] } { \ (simd-v=) [ cc= %compare-vector-reps ] } diff --git a/basis/math/vectors/simd/simd-tests.factor b/basis/math/vectors/simd/simd-tests.factor index 88e5d5f1ea..8c2d523875 100644 --- a/basis/math/vectors/simd/simd-tests.factor +++ b/basis/math/vectors/simd/simd-tests.factor @@ -181,6 +181,9 @@ CONSTANT: simd-classes { hlshift hrshift vshuffle vbroadcast vany? vall? vnone? + (v>float) (v>integer) + (vpack-signed) (vpack-unsigned) + (vunpack-head) (vunpack-tail) } unique assoc-diff ; : ops-to-check ( elt-class -- alist ) diff --git a/basis/math/vectors/specialization/specialization.factor b/basis/math/vectors/specialization/specialization.factor index bed8a71f2c..fd76b005c6 100644 --- a/basis/math/vectors/specialization/specialization.factor +++ b/basis/math/vectors/specialization/specialization.factor @@ -2,6 +2,7 @@ ! See http://factorcode.org/license.txt for BSD license. USING: words kernel make sequences effects sets kernel.private accessors combinators math math.intervals math.vectors +math.vectors.conversion math.vectors.conversion.private namespaces assocs fry splitting classes.algebra generalizations locals compiler.tree.propagation.info ; IN: math.vectors.specialization @@ -100,6 +101,12 @@ H{ { vbroadcast { +vector+ +literal+ -> +vector+ } } { (vmerge-head) { +vector+ +vector+ -> +vector+ } } { (vmerge-tail) { +vector+ +vector+ -> +vector+ } } + { (v>float) { +vector+ +literal+ -> +vector+ } } + { (v>integer) { +vector+ +literal+ -> +vector+ } } + { (vpack-signed) { +vector+ +vector+ +literal+ -> +vector+ } } + { (vpack-unsigned) { +vector+ +vector+ +literal+ -> +vector+ } } + { (vunpack-head) { +vector+ +literal+ -> +vector+ } } + { (vunpack-tail) { +vector+ +literal+ -> +vector+ } } { v<= { +vector+ +vector+ -> +vector+ } } { v< { +vector+ +vector+ -> +vector+ } } { v= { +vector+ +vector+ -> +vector+ } } @@ -152,8 +159,13 @@ ERROR: bad-vector-word word ; { [ dup complex class<= ] [ vector-words keys { vsqrt } diff ] } [ { } ] } cond - ! Don't specialize horizontal shifts or shuffles at all, they're only for SIMD - { hlshift hrshift vshuffle vbroadcast } diff + ! Don't specialize horizontal shifts, shuffles, and conversions at all, they're only for SIMD + { + hlshift hrshift vshuffle vbroadcast + (v>integer) (v>float) + (vpack-signed) (vpack-unsigned) + (vunpack-head) (vunpack-tail) + } diff nip ; :: specialize-vector-words ( array-type elt-type simd -- )