USING: accessors alien arrays byte-arrays classes combinators
-cpu.architecture effects fry functors generalizations generic
-generic.parser kernel lexer literals locals macros math math.functions
-math.vectors math.vectors.private math.vectors.simd.intrinsics
-namespaces parser prettyprint.custom quotations sequences
-sequences.generalizations sequences.private vocabs vocabs.loader
-words ;
+cpu.architecture effects functors generalizations kernel lexer
+literals math math.bitwise math.vectors
+math.vectors.simd.intrinsics parser prettyprint.custom
+quotations sequences sequences.generalizations sequences.private
+vocabs.loader words ;
QUALIFIED-WITH: alien.c-types c
IN: math.vectors.simd
ERROR: bad-simd-length got expected ;
-
ERROR: bad-simd-vector obj ;
<<
: v->v-op ( a rep quot: ( (a) rep -- (c) ) fallback-quot -- c )
drop [ simd-unbox ] 2dip 2curry make-underlying ; inline
-: vn->v-op ( a n rep quot: ( (a) n rep -- (c) ) fallback-quot -- c )
+: vx->v-op ( a obj rep quot: ( (a) obj rep -- (c) ) fallback-quot -- c )
drop [ simd-unbox ] 3dip 3curry make-underlying ; inline
-: vn->n-op ( a n rep quot: ( (a) n rep -- n ) fallback-quot -- n )
+: vn->v-op ( a n rep quot: ( (a) n rep -- (c) ) fallback-quot -- c )
+ drop [ [ simd-unbox ] [ >fixnum ] bi* ] 2dip 3curry make-underlying ; inline
+
+: vx->x-op ( a obj rep quot: ( (a) obj rep -- obj ) fallback-quot -- obj )
drop [ underlying>> ] 3dip call ; inline
-: v->n-op ( a rep quot: ( (a) rep -- n ) fallback-quot -- n )
+: v->x-op ( a rep quot: ( (a) rep -- obj ) fallback-quot -- obj )
drop [ underlying>> ] 2dip call ; inline
: (vv->v-op) ( a b rep quot: ( (a) (b) rep -- (c) ) -- c )
[ [ simd-unbox ] [ underlying>> ] bi* ] 2dip 3curry make-underlying ; inline
-: (vv->n-op) ( a b rep quot: ( (a) (b) rep -- n ) -- n )
+
+: (vv->x-op) ( a b rep quot: ( (a) (b) rep -- n ) -- n )
[ [ underlying>> ] bi@ ] 2dip 3curry call ; inline
-: (vvn->v-op) ( a b n rep quot: ( (a) (b) n rep -- (c) ) -- c )
+
+: (vvx->v-op) ( a b obj rep quot: ( (a) (b) obj rep -- (c) ) -- c )
[ [ simd-unbox ] [ underlying>> ] bi* ] 3dip 2curry 2curry make-underlying ; inline
-
+
: vv->v-op ( a b rep quot: ( (a) (b) rep -- (c) ) fallback-quot -- c )
[ '[ _ (vv->v-op) ] ] [ '[ drop @ ] ] bi* if-both-vectors-match ; inline
-:: vvn->v-op ( a b n rep quot: ( (a) (b) n rep -- (c) ) fallback-quot -- c )
+:: vvx->v-op ( a b obj rep quot: ( (a) (b) obj rep -- (c) ) fallback-quot -- c )
a b rep
- [ n swap quot (vvn->v-op) ]
- [ drop n fallback-quot call ] if-both-vectors-match ; inline
+ [ obj swap quot (vvx->v-op) ]
+ [ drop obj fallback-quot call ] if-both-vectors-match ; inline
: vv'->v-op ( a b rep quot: ( (a) (b) rep -- (c) ) fallback-quot -- c )
[ '[ _ (vv->v-op) ] ] [ '[ drop @ ] ] bi* if-both-vectors ; inline
-: vv->n-op ( a b rep quot: ( (a) (b) rep -- n ) fallback-quot -- n )
- [ '[ _ (vv->n-op) ] ] [ '[ drop @ ] ] bi* if-both-vectors-match ; inline
+: vv->x-op ( a b rep quot: ( (a) (b) rep -- obj ) fallback-quot -- obj )
+ [ '[ _ (vv->x-op) ] ] [ '[ drop @ ] ] bi* if-both-vectors-match ; inline
+
+: mask>count ( n rep -- n' )
+ [ bit-count ] dip {
+ { float-4-rep [ ] }
+ { double-2-rep [ -1 shift ] }
+ { uchar-16-rep [ ] }
+ { char-16-rep [ ] }
+ { ushort-8-rep [ -1 shift ] }
+ { short-8-rep [ -1 shift ] }
+ { ushort-8-rep [ -1 shift ] }
+ { int-4-rep [ -2 shift ] }
+ { uint-4-rep [ -2 shift ] }
+ { longlong-2-rep [ -3 shift ] }
+ { ulonglong-2-rep [ -3 shift ] }
+ } case ; inline
PRIVATE>
>>
! SIMD primitive operations
M: simd-128 v+
- dup simd-rep [ (simd-v+) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v+) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v-
- dup simd-rep [ (simd-v-) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v-) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vneg
- dup simd-rep [ (simd-vneg) ] [ call-next-method ] v->v-op ; inline
+ dup simd-rep [ (simd-vneg) ] [ call-next-method ] v->v-op ; inline
M: simd-128 v+-
- dup simd-rep [ (simd-v+-) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v+-) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vs+
- dup simd-rep [ (simd-vs+) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vs+) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vs-
- dup simd-rep [ (simd-vs-) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vs-) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vs*
- dup simd-rep [ (simd-vs*) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vs*) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v*
- dup simd-rep [ (simd-v*) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v*) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v*high
- dup simd-rep [ (simd-v*high) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v*high) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v/
- dup simd-rep [ (simd-v/) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v/) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vavg
- dup simd-rep [ (simd-vavg) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vavg) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vmin
- dup simd-rep [ (simd-vmin) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vmin) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vmax
- dup simd-rep [ (simd-vmax) ] [ call-next-method ] vv->v-op ; inline
-M: simd-128 v.
- dup simd-rep [ (simd-v.) ] [ call-next-method ] vv->n-op ; inline
+ dup simd-rep [ (simd-vmax) ] [ call-next-method ] vv->v-op ; inline
+M: simd-128 vdot
+ dup simd-rep [ (simd-vdot) ] [ call-next-method ] vv->x-op ; inline
M: simd-128 vsad
- dup simd-rep [ (simd-vsad) ] [ call-next-method ] vv->n-op ; inline
+ dup simd-rep [ (simd-vsad) ] [ call-next-method ] vv->x-op ; inline
M: simd-128 vsqrt
- dup simd-rep [ (simd-vsqrt) ] [ call-next-method ] v->v-op ; inline
+ dup simd-rep [ (simd-vsqrt) ] [ call-next-method ] v->v-op ; inline
M: simd-128 sum
- dup simd-rep [ (simd-sum) ] [ call-next-method ] v->n-op ; inline
+ dup simd-rep [ (simd-sum) ] [ call-next-method ] v->x-op ; inline
M: simd-128 vabs
- dup simd-rep [ (simd-vabs) ] [ call-next-method ] v->v-op ; inline
+ dup simd-rep [ (simd-vabs) ] [ call-next-method ] v->v-op ; inline
M: simd-128 vbitand
- dup simd-rep [ (simd-vbitand) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vbitand) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vbitandn
- dup simd-rep [ (simd-vbitandn) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vbitandn) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vbitor
- dup simd-rep [ (simd-vbitor) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vbitor) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vbitxor
- dup simd-rep [ (simd-vbitxor) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vbitxor) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vbitnot
- dup simd-rep [ (simd-vbitnot) ] [ call-next-method ] v->v-op ; inline
+ dup simd-rep [ (simd-vbitnot) ] [ call-next-method ] v->v-op ; inline
M: simd-128 vand
- dup simd-rep [ (simd-vand) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vand) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vandn
- dup simd-rep [ (simd-vandn) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vandn) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vor
- dup simd-rep [ (simd-vor) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vor) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vxor
- dup simd-rep [ (simd-vxor) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vxor) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vnot
- dup simd-rep [ (simd-vnot) ] [ call-next-method ] v->v-op ; inline
+ dup simd-rep [ (simd-vnot) ] [ call-next-method ] v->v-op ; inline
M: simd-128 vlshift
- over simd-rep [ (simd-vlshift) ] [ call-next-method ] vn->v-op ; inline
+ over simd-rep [ (simd-vlshift) ] [ call-next-method ] vn->v-op ; inline
M: simd-128 vrshift
- over simd-rep [ (simd-vrshift) ] [ call-next-method ] vn->v-op ; inline
+ over simd-rep [ (simd-vrshift) ] [ call-next-method ] vn->v-op ; inline
M: simd-128 hlshift
- over simd-rep [ (simd-hlshift) ] [ call-next-method ] vn->v-op ; inline
+ over simd-rep [ (simd-hlshift) ] [ call-next-method ] vn->v-op ; inline
M: simd-128 hrshift
- over simd-rep [ (simd-hrshift) ] [ call-next-method ] vn->v-op ; inline
+ over simd-rep [ (simd-hrshift) ] [ call-next-method ] vn->v-op ; inline
M: simd-128 vshuffle-elements
- over simd-rep [ (simd-vshuffle-elements) ] [ call-next-method ] vn->v-op ; inline
+ over simd-rep [ (simd-vshuffle-elements) ] [ call-next-method ] vx->v-op ; inline
M: simd-128 vshuffle2-elements
- over simd-rep [ (simd-vshuffle2-elements) ] [ call-next-method ] vvn->v-op ; inline
+ over simd-rep [ (simd-vshuffle2-elements) ] [ call-next-method ] vvx->v-op ; inline
M: simd-128 vshuffle-bytes
- dup simd-rep [ (simd-vshuffle-bytes) ] [ call-next-method ] vv'->v-op ; inline
+ dup simd-rep [ (simd-vshuffle-bytes) ] [ call-next-method ] vv'->v-op ; inline
M: simd-128 (vmerge-head)
- dup simd-rep [ (simd-vmerge-head) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vmerge-head) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 (vmerge-tail)
- dup simd-rep [ (simd-vmerge-tail) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vmerge-tail) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v<=
- dup simd-rep [ (simd-v<=) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v<=) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v<
- dup simd-rep [ (simd-v<) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v<) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v=
- dup simd-rep [ (simd-v=) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v=) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v>
- dup simd-rep [ (simd-v>) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v>) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 v>=
- dup simd-rep [ (simd-v>=) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-v>=) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vunordered?
- dup simd-rep [ (simd-vunordered?) ] [ call-next-method ] vv->v-op ; inline
+ dup simd-rep [ (simd-vunordered?) ] [ call-next-method ] vv->v-op ; inline
M: simd-128 vany?
- dup simd-rep [ (simd-vany?) ] [ call-next-method ] v->n-op ; inline
+ dup simd-rep [ (simd-vany?) ] [ call-next-method ] v->x-op ; inline
M: simd-128 vall?
- dup simd-rep [ (simd-vall?) ] [ call-next-method ] v->n-op ; inline
+ dup simd-rep [ (simd-vall?) ] [ call-next-method ] v->x-op ; inline
M: simd-128 vnone?
- dup simd-rep [ (simd-vnone?) ] [ call-next-method ] v->n-op ; inline
+ dup simd-rep [ (simd-vnone?) ] [ call-next-method ] v->x-op ; inline
+M: simd-128 vcount
+ dup simd-rep
+ [ [ (simd-vgetmask) assert-positive ] [ call-next-method ] v->x-op ]
+ [ mask>count ] bi ; inline
! SIMD high-level specializations
M: simd-128 v-n over simd-with v- ; inline
M: simd-128 v*n over simd-with v* ; inline
M: simd-128 v/n over simd-with v/ ; inline
-M: simd-128 norm-sq dup v. assert-positive ; inline
+M: simd-128 norm-sq dup vdot assert-positive ; inline
M: simd-128 distance v- norm ; inline
M: simd-128 >pprint-sequence ;
! SIMD concrete type functor
-FUNCTOR: define-simd-128 ( T -- )
+<FUNCTOR: define-simd-128 ( T -- )
A DEFINES-CLASS ${T}
A-rep IS ${T}-rep
M: A simd-with drop A-with ; inline
M: A nth-unsafe
- swap \ A-rep [ (simd-select) ] [ call-next-method ] vn->n-op ; inline
+ swap \ A-rep [ (simd-select) ] [ call-next-method ] vx->x-op ; inline
M: A set-nth-unsafe
[ ELT boolean>element ] 2dip
underlying>> ELT c:set-alien-element ; inline
A-rep >>rep
\ A c:typedef
-;FUNCTOR
+;FUNCTOR>
SYNTAX: SIMD-128:
- scan define-simd-128 ;
+ scan-token define-simd-128 ;
PRIVATE>
! misc
-M: simd-128 vshuffle ( u perm -- v )
+M: simd-128 vshuffle
vshuffle-bytes ; inline
M: uchar-16 v*hs+