Skip to content

roaring64: honor copy-on-write in Bitmap.Or#525

Open
ostafen wants to merge 1 commit into
RoaringBitmap:masterfrom
authzed:fix-roaring64-or-cow
Open

roaring64: honor copy-on-write in Bitmap.Or#525
ostafen wants to merge 1 commit into
RoaringBitmap:masterfrom
authzed:fix-roaring64-or-cow

Conversation

@ostafen
Copy link
Copy Markdown

@ostafen ostafen commented May 21, 2026

Description

When two bitmaps share a container key, the in-place Or was calling getContainerAtIndex, which returns the raw container without consulting needCopyOnWrite. If rb's container at that index was shared with another bitmap (e.g. produced by Clone() on a CoW-enabled bitmap), the Or would mutate the shared container in place and silently corrupt the other bitmap.

Type of Change

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Performance improvement
  • Code refactoring
  • Documentation update
  • Test improvements
  • Build/CI changes

Changes Made

Switch to getWritableContainerAtIndex, which clones the container first when needCopyOnWrite is set. This matches what the sibling AndNot/And methods in the same file already do, and what the 32-bit Bitmap.Or does via getUnionedWritableContainer.

Testing

Added a unit test reproducing the issue that fails without the fix.

You must run

go test

Formatting

Please run

go fmt

Fuzzing

Please run our fuzzer on your changes.

  1. Generate initial smat corpus:
go test -tags=gofuzz -run=TestGenerateSmatCorpus

You should see a directory workdir created with initial corpus files.

  1. Run the fuzz test:
go test -run='^$' -fuzz=FuzzSmat -fuzztime=300s -timeout=60s

Adjust -fuzztime as needed for longer or shorter runs. If crashes are found,
check the test output and the reproducer files in the workdir directory.
You may copy the reproducers to roaring_tests.go

Performance Impact

If applicable, describe any performance implications of these changes and include benchmark results.

Running Benchmarks

This project includes comprehensive benchmarks. Please run relevant benchmarks before and after your changes:

Basic Benchmarks

# Run all benchmarks
go test -bench=. -run=^$

# Run with memory allocation statistics
go test -bench=. -benchmem -run=^$

# Run specific benchmark
go test -bench=BenchmarkIteratorAlloc -run=^$

Parallel Benchmarks

# Run parallel processing benchmarks
go test -bench=BenchmarkIntersectionLargeParallel -run=^$

Real Data Benchmarks

# Requires real-roaring-datasets (run: go get github.com/RoaringBitmap/real-roaring-datasets)
BENCH_REAL_DATA=1 go test -bench=BenchmarkRealData -run=^$

Benchmark Results Format

Please include before/after results in the following format:

BenchmarkName-8    1000000    1234 ns/op    567 B/op    12 allocs/op

Performance Analysis

  • Compare benchmark results before and after changes
  • Note any significant improvements or regressions
  • Include memory usage changes if relevant
  • Mention any trade-offs (e.g., memory vs speed)

Breaking Changes

If this PR introduces breaking changes, please describe them and the migration path:

Related Issues

Fixes # (issue number)
Related to # (issue number)

Additional Notes

Any additional information or context about this pull request.

When two bitmaps share a container key, the in-place Or was calling
getContainerAtIndex, which returns the raw container without consulting
needCopyOnWrite. If rb's container at that index was shared with another
bitmap (e.g. produced by Clone() on a CoW-enabled bitmap), the Or would
mutate the shared container in place and silently corrupt the other
bitmap.

Switch to getWritableContainerAtIndex, which clones the container first
when needCopyOnWrite is set. This matches what the sibling AndNot/And
methods in the same file already do, and what the 32-bit Bitmap.Or does
via getUnionedWritableContainer.
@lemire
Copy link
Copy Markdown
Member

lemire commented May 21, 2026

Running tests.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants