overflow in intersectionCountRunRun

This commit is contained in:
Todd Gruben 2017-08-03 14:30:37 -05:00
parent f6d63ddccb
commit fbdce18f70
2 changed files with 48 additions and 20 deletions

View file

@ -336,7 +336,7 @@ func (b *Bitmap) IntersectionCount(other *Bitmap) uint64 {
} else if ki > kj {
j++
} else {
n += intersectionCount(b.containers[i], other.containers[j])
n += uint64(intersectionCount(b.containers[i], other.containers[j]))
i, j = i+1, j+1
}
}
@ -1717,7 +1717,7 @@ type ContainerInfo struct {
Pointer unsafe.Pointer // offset within the mmap
}
func intersectionCount(a, b *container) uint64 {
func intersectionCount(a, b *container) int {
if a.isArray() {
if b.isArray() {
return intersectionCountArrayArray(a, b)
@ -1745,7 +1745,7 @@ func intersectionCount(a, b *container) uint64 {
}
}
func intersectionCountArrayArray(a, b *container) (n uint64) {
func intersectionCountArrayArray(a, b *container) (n int) {
na, nb := len(a.array), len(b.array)
for i, j := 0, 0; i < na && j < nb; {
va, vb := a.array[i], b.array[j]
@ -1761,7 +1761,7 @@ func intersectionCountArrayArray(a, b *container) (n uint64) {
return n
}
func intersectionCountArrayRun(a, b *container) (n uint64) {
func intersectionCountArrayRun(a, b *container) (n int) {
na, nb := len(a.array), len(b.runs)
for i, j := 0, 0; i < na && j < nb; {
va, vb := a.array[i], b.runs[j]
@ -1777,8 +1777,7 @@ func intersectionCountArrayRun(a, b *container) (n uint64) {
return n
}
func intersectionCountRunRun(a, b *container) uint64 {
var n uint16
func intersectionCountRunRun(a, b *container) (n int) {
na, nb := len(a.runs), len(b.runs)
for i, j := 0, 0; i < na && j < nb; {
va, vb := a.runs[i], b.runs[j]
@ -1790,28 +1789,28 @@ func intersectionCountRunRun(a, b *container) uint64 {
j++
} else if va.last > vb.last && va.start >= vb.start {
// |--vb-|-|-va--|
n += 1 + vb.last - va.start
n += 1 + int(vb.last-va.start)
j++
} else if va.last > vb.last && va.start < vb.start {
// |--va|--vb--|--|
n += 1 + vb.last - vb.start
n += 1 + int(vb.last-vb.start)
j++
} else if va.last <= vb.last && va.start >= vb.start {
// |--vb|--va--|--|
n += 1 + va.last - va.start
n += 1 + int(va.last-va.start)
i++
} else if va.last <= vb.last && va.start < vb.start {
// |--va-|-|-vb--|
n += 1 + va.last - vb.start
n += 1 + int(va.last-vb.start)
i++
}
}
return uint64(n)
return
}
func intersectionCountBitmapRun(a, b *container) (n uint64) {
func intersectionCountBitmapRun(a, b *container) (n int) {
for _, iv := range b.runs {
n += uint64(a.bitmapCountRange(int(iv.start), int(iv.last)+1))
n += a.bitmapCountRange(int(iv.start), int(iv.last)+1)
}
return n
}
@ -1858,20 +1857,20 @@ func intersectionCountArrayBitmapOld(a, b *container) (n uint64) {
return n
}
func intersectionCountArrayBitmap(a, b *container) (n uint64) {
func intersectionCountArrayBitmap(a, b *container) (n int) {
for _, val := range a.array {
i := val >> 6
if i >= uint16(len(b.bitmap)) {
break
}
off := val % 64
n += (b.bitmap[i] & (1 << off)) >> off
n += int((b.bitmap[i] & (1 << off)) >> off)
}
return n
}
func intersectionCountBitmapBitmap(a, b *container) (n uint64) {
return popcntAndSlice(a.bitmap, b.bitmap)
func intersectionCountBitmapBitmap(a, b *container) (n int) {
return int(popcntAndSlice(a.bitmap, b.bitmap))
}
func intersect(a, b *container) *container {

View file

@ -225,12 +225,39 @@ func TestBitmapCountRange(t *testing.T) {
}
}
func TestIntersectionCountArrayBitmap3(t *testing.T) {
a, b := &container{}, &container{}
a.container_type = ContainerBitmap
a.bitmap = getFullBitmap()
a.n = maxContainerVal + 1
b.container_type = ContainerBitmap
b.bitmap = getFullBitmap()
b.n = maxContainerVal + 1
res := intersectBitmapBitmap(a, b)
if res.n != res.count() || res.n != maxContainerVal+1 {
t.Fatalf("test #1 intersectCountBitmapBitmap fail orig: %v new: %v exp: %v", res.n, res.count(), maxContainerVal+1)
}
a.bitmapToRun()
res = intersectBitmapRun(b, a)
if res.n != res.count() || res.n != maxContainerVal+1 {
t.Fatalf("test #2 intersectCountBitmapRun fail orig: %v new: %v exp: %v", res.n, res.count(), maxContainerVal+1)
}
b.bitmapToRun()
res = intersectRunRun(a, b)
n := intersectionCountRunRun(a, b)
if res.n != res.count() || res.n != maxContainerVal+1 || res.n != int(n) {
t.Fatalf("test #3 intersectCountRunRun fail orig: %v new: %v exp: %v", res.n, res.count(), maxContainerVal+1)
}
}
func TestIntersectionCountArrayBitmap2(t *testing.T) {
a, b := &container{}, &container{}
tests := []struct {
array []uint16
bitmap []uint64
exp uint64
exp int
}{
{
array: []uint16{0},
@ -261,8 +288,10 @@ func TestIntersectionCountArrayBitmap2(t *testing.T) {
for i, test := range tests {
a.array = test.array
a.container_type = ContainerArray
b.bitmap = test.bitmap
ret1 := intersectionCountArrayBitmapOld(a, b)
b.container_type = ContainerBitmap
ret1 := int(intersectionCountArrayBitmapOld(a, b))
ret2 := intersectionCountArrayBitmap(a, b)
if ret1 != ret2 || ret2 != test.exp {
t.Fatalf("test #%v intersectCountArrayBitmap fail orig: %v new: %v exp: %v", i, ret1, ret2, test.exp)
@ -352,7 +381,7 @@ func TestIntersectionCountRunRun(t *testing.T) {
tests := []struct {
aruns []interval16
bruns []interval16
exp uint64
exp int
}{
{
aruns: []interval16{},