aboutsummaryrefslogtreecommitdiffstats
path: root/searchlib/src/vespa/searchlib/queryeval/multibitvectoriterator.h
blob: 855ecfae60c55f48f4f92c073c6dff8f4cf3189b (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root.

#pragma once

#include "multisearch.h"
#include "unpackinfo.h"
#include <vespa/searchlib/common/bitword.h>

namespace vespalib::hwaccelrated { class IAccelrated; }

namespace search::queryeval {

class MultiBitVectorBase {
public:
    using Meta = std::pair<const void *, bool>;
    MultiBitVectorBase(size_t reserved);
    using Word = BitWord::Word;
    void reset() {
        _lastMaxDocIdLimit = 0;
        _lastMaxDocIdLimitRequireFetch = 0;
    }
    bool isAtEnd(uint32_t docId) const noexcept { return docId >= _numDocs; }
    void addBitVector(Meta bv, uint32_t docIdLimit);
protected:
    uint32_t            _numDocs;
    uint32_t            _lastMaxDocIdLimit; // next documentid requiring recomputation.
    uint32_t            _lastMaxDocIdLimitRequireFetch;
    Word                _lastValue; // Last value computed
    std::vector<Meta>   _bvs;
};

template <typename Update>
class MultiBitVector : public MultiBitVectorBase {
public:
    explicit MultiBitVector(size_t reserved);
    uint32_t strictSeek(uint32_t docId) noexcept;
    bool seek(uint32_t docId) noexcept;
    bool acceptExtraFilter() const noexcept { return Update::isAnd(); }
private:
    bool updateLastValue(uint32_t docId) noexcept;
    using IAccelrated = vespalib::hwaccelrated::IAccelrated;

    Update              _update;
    const IAccelrated & _accel;
    alignas(64) Word    _lastWords[8];
    static constexpr size_t NumWordsInBatch = sizeof(_lastWords) / sizeof(Word);
};

class MultiBitVectorIteratorBase : public MultiSearch
{
public:
    ~MultiBitVectorIteratorBase() override;
    void initRange(uint32_t beginId, uint32_t endId) override;
    void addUnpackIndex(size_t index) { _unpackInfo.add(index); }
    /**
     * Will steal and optimize bitvectoriterators if it can
     * Might return itself or a new structure.
     */
    static SearchIterator::UP optimize(SearchIterator::UP parent);
protected:
    explicit MultiBitVectorIteratorBase(Children children);
private:
    virtual bool acceptExtraFilter() const noexcept = 0;
    void doUnpack(uint32_t docid) override;
    static SearchIterator::UP optimizeMultiSearch(SearchIterator::UP parent);

    UnpackInfo  _unpackInfo;
};

}