package delta
import (
"github.com/parquet-go/parquet-go/internal/unsafecast"
"golang.org/x/sys/cpu"
)
func init() {
if cpu .X86 .HasAVX2 {
encodeInt32 = encodeInt32AVX2
encodeInt64 = encodeInt64AVX2
}
}
func blockDeltaInt32AVX2(block *[blockSize ]int32 , lastValue int32 ) int32
func blockMinInt32AVX2(block *[blockSize ]int32 ) int32
func blockSubInt32AVX2(block *[blockSize ]int32 , value int32 )
func blockBitWidthsInt32AVX2(bitWidths *[numMiniBlocks ]byte , block *[blockSize ]int32 )
func encodeMiniBlockInt32Default(dst *byte , src *[miniBlockSize ]int32 , bitWidth uint )
func encodeMiniBlockInt32x1bitAVX2(dst *byte , src *[miniBlockSize ]int32 )
func encodeMiniBlockInt32x2bitsAVX2(dst *byte , src *[miniBlockSize ]int32 )
func encodeMiniBlockInt32x3to16bitsAVX2(dst *byte , src *[miniBlockSize ]int32 , bitWidth uint )
func encodeMiniBlockInt32x32bitsAVX2(dst *byte , src *[miniBlockSize ]int32 )
func encodeMiniBlockInt32(dst []byte , src *[miniBlockSize ]int32 , bitWidth uint ) {
encodeMiniBlockInt32Default (&dst [0 ], src , bitWidth )
}
func encodeMiniBlockInt32AVX2(dst *byte , src *[miniBlockSize ]int32 , bitWidth uint ) {
switch {
case bitWidth == 1 :
encodeMiniBlockInt32x1bitAVX2 (dst , src )
case bitWidth == 2 :
encodeMiniBlockInt32x2bitsAVX2 (dst , src )
case bitWidth == 32 :
encodeMiniBlockInt32x32bitsAVX2 (dst , src )
case bitWidth <= 16 :
encodeMiniBlockInt32x3to16bitsAVX2 (dst , src , bitWidth )
default :
encodeMiniBlockInt32Default (dst , src , bitWidth )
}
}
func encodeInt32AVX2(dst []byte , src []int32 ) []byte {
totalValues := len (src )
firstValue := int32 (0 )
if totalValues > 0 {
firstValue = src [0 ]
}
n := len (dst )
dst = resize (dst , n +maxHeaderLength32 )
dst = dst [:n +encodeBinaryPackedHeader (dst [n :], blockSize , numMiniBlocks , totalValues , int64 (firstValue ))]
if totalValues < 2 {
return dst
}
lastValue := firstValue
for i := 1 ; i < len (src ); i += blockSize {
block := [blockSize ]int32 {}
blockLength := copy (block [:], src [i :])
lastValue = blockDeltaInt32AVX2 (&block , lastValue )
minDelta := blockMinInt32AVX2 (&block )
blockSubInt32AVX2 (&block , minDelta )
blockClearInt32 (&block , blockLength )
bitWidths := [numMiniBlocks ]byte {}
blockBitWidthsInt32AVX2 (&bitWidths , &block )
n := len (dst )
dst = resize (dst , n +maxMiniBlockLength32 +16 )
n += encodeBlockHeader (dst [n :], int64 (minDelta ), bitWidths )
for i , bitWidth := range bitWidths {
if bitWidth != 0 {
miniBlock := (*[miniBlockSize ]int32 )(block [i *miniBlockSize :])
encodeMiniBlockInt32AVX2 (&dst [n ], miniBlock , uint (bitWidth ))
n += (miniBlockSize * int (bitWidth )) / 8
}
}
dst = dst [:n ]
}
return dst
}
func blockDeltaInt64AVX2(block *[blockSize ]int64 , lastValue int64 ) int64
func blockMinInt64AVX2(block *[blockSize ]int64 ) int64
func blockSubInt64AVX2(block *[blockSize ]int64 , value int64 )
func blockBitWidthsInt64AVX2(bitWidths *[numMiniBlocks ]byte , block *[blockSize ]int64 )
func encodeMiniBlockInt64Default(dst *byte , src *[miniBlockSize ]int64 , bitWidth uint )
func encodeMiniBlockInt64x1bitAVX2(dst *byte , src *[miniBlockSize ]int64 )
func encodeMiniBlockInt64x2bitsAVX2(dst *byte , src *[miniBlockSize ]int64 )
func encodeMiniBlockInt64x64bitsAVX2(dst *byte , src *[miniBlockSize ]int64 )
func encodeMiniBlockInt64(dst []byte , src *[miniBlockSize ]int64 , bitWidth uint ) {
encodeMiniBlockInt64Default (&dst [0 ], src , bitWidth )
}
func encodeMiniBlockInt64AVX2(dst *byte , src *[miniBlockSize ]int64 , bitWidth uint ) {
switch {
case bitWidth == 1 :
encodeMiniBlockInt64x1bitAVX2 (dst , src )
case bitWidth == 2 :
encodeMiniBlockInt64x2bitsAVX2 (dst , src )
case bitWidth == 64 :
encodeMiniBlockInt64x64bitsAVX2 (dst , src )
default :
encodeMiniBlockInt64Default (dst , src , bitWidth )
}
}
func encodeInt64AVX2(dst []byte , src []int64 ) []byte {
totalValues := len (src )
firstValue := int64 (0 )
if totalValues > 0 {
firstValue = src [0 ]
}
n := len (dst )
dst = resize (dst , n +maxHeaderLength64 )
dst = dst [:n +encodeBinaryPackedHeader (dst [n :], blockSize , numMiniBlocks , totalValues , int64 (firstValue ))]
if totalValues < 2 {
return dst
}
lastValue := firstValue
for i := 1 ; i < len (src ); i += blockSize {
block := [blockSize ]int64 {}
blockLength := copy (block [:], src [i :])
lastValue = blockDeltaInt64AVX2 (&block , lastValue )
minDelta := blockMinInt64AVX2 (&block )
blockSubInt64AVX2 (&block , minDelta )
blockClearInt64 (&block , blockLength )
bitWidths := [numMiniBlocks ]byte {}
blockBitWidthsInt64AVX2 (&bitWidths , &block )
n := len (dst )
dst = resize (dst , n +maxMiniBlockLength64 +16 )
n += encodeBlockHeader (dst [n :], int64 (minDelta ), bitWidths )
for i , bitWidth := range bitWidths {
if bitWidth != 0 {
miniBlock := (*[miniBlockSize ]int64 )(block [i *miniBlockSize :])
encodeMiniBlockInt64AVX2 (&dst [n ], miniBlock , uint (bitWidth ))
n += (miniBlockSize * int (bitWidth )) / 8
}
}
dst = dst [:n ]
}
return dst
}
func decodeBlockInt32Default(dst []int32 , minDelta , lastValue int32 ) int32
func decodeBlockInt32AVX2(dst []int32 , minDelta , lastValue int32 ) int32
func decodeBlockInt32(dst []int32 , minDelta , lastValue int32 ) int32 {
switch {
case cpu .X86 .HasAVX2 :
return decodeBlockInt32AVX2 (dst , minDelta , lastValue )
default :
return decodeBlockInt32Default (dst , minDelta , lastValue )
}
}
func decodeMiniBlockInt32Default(dst []int32 , src []uint32 , bitWidth uint )
func decodeMiniBlockInt32x1to16bitsAVX2(dst []int32 , src []uint32 , bitWidth uint )
func decodeMiniBlockInt32x17to26bitsAVX2(dst []int32 , src []uint32 , bitWidth uint )
func decodeMiniBlockInt32x27to31bitsAVX2(dst []int32 , src []uint32 , bitWidth uint )
func decodeMiniBlockInt32(dst []int32 , src []uint32 , bitWidth uint ) {
hasAVX2 := cpu .X86 .HasAVX2
switch {
case hasAVX2 && bitWidth <= 16 :
decodeMiniBlockInt32x1to16bitsAVX2 (dst , src , bitWidth )
case hasAVX2 && bitWidth <= 26 :
decodeMiniBlockInt32x17to26bitsAVX2 (dst , src , bitWidth )
case hasAVX2 && bitWidth <= 31 :
decodeMiniBlockInt32x27to31bitsAVX2 (dst , src , bitWidth )
case bitWidth == 32 :
copy (dst , unsafecast .Slice [int32 ](src ))
default :
decodeMiniBlockInt32Default (dst , src , bitWidth )
}
}
func decodeBlockInt64Default(dst []int64 , minDelta , lastValue int64 ) int64
func decodeBlockInt64(dst []int64 , minDelta , lastValue int64 ) int64 {
return decodeBlockInt64Default (dst , minDelta , lastValue )
}
func decodeMiniBlockInt64Default(dst []int64 , src []uint32 , bitWidth uint )
func decodeMiniBlockInt64(dst []int64 , src []uint32 , bitWidth uint ) {
switch {
case bitWidth == 64 :
copy (dst , unsafecast .Slice [int64 ](src ))
default :
decodeMiniBlockInt64Default (dst , src , bitWidth )
}
}
The pages are generated with Golds v0.8.4 . (GOOS=linux GOARCH=amd64)
Golds is a Go 101 project developed by Tapir Liu .
PR and bug reports are welcome and can be submitted to the issue list .
Please follow @zigo_101 (reachable from the left QR code) to get the latest news of Golds .