* Copyright (c) 2020 Huawei Technologies Co.,Ltd.
*
* openGauss is licensed under Mulan PSL v2.
* You can use this software according to the terms and conditions of the Mulan PSL v2.
* You may obtain a copy of Mulan PSL v2 at:
*
* http://license.coscl.org.cn/MulanPSL2
*
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
* EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
* MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
* See the Mulan PSL v2 for more details.
* ---------------------------------------------------------------------------------------
*
* vsonichashjoin.h
* Routines to handle vector sonic hashjoin nodes.
* Sonic Hash Join nodes are based on the column-based hash table.
*
* IDENTIFICATION
* src/include/vectorsonic/vsonichashjoin.h
*
* ---------------------------------------------------------------------------------------
*/
#ifndef SRC_INCLUDE_VECTORSONIC_VSONICHASHJOIN_H_
#define SRC_INCLUDE_VECTORSONIC_VSONICHASHJOIN_H_
#include "vectorsonic/vsonichash.h"
#include "vectorsonic/vsonicpartition.h"
* Max partition number when doing partition or repartition.
* Total partition number can be larger than this value.
*/
#define SONIC_PART_MAX_NUM 1024
typedef enum { reportTypeBuild = 1, reportTypeProbe, reportTypeRepartition } ReportType;
struct BatchPos {
uint32 partIdx;
int rowIdx;
};
class SonicHashJoin : public SonicHash {
public:
SonicHashJoin(int size, VecHashJoinState* node);
~SonicHashJoin(){};
void Build();
VectorBatch* Probe();
void closeAllFiles();
void ResetNecessary();
void freeMemoryContext();
private:
void setHashIndex(uint16* keyIndx, uint16* oKeyIndx, List* hashKeys);
void initMemoryControl();
void initHashTable(uint8 byteSize, uint32 curPartIdx);
void initHashFmgr();
template <bool complicateJoinKey>
void bindingFp();
template <bool complicateJoinKey>
void saveToMemory(VectorBatch* batch);
template <bool complicateJoinKey, bool optspill>
void saveToDisk(VectorBatch* batch);
template <bool complicateJoinKey>
void flushToDisk();
template <typename BucketType, bool complicateJoinKey, bool isSegHashTable>
void buildHashTable(uint32 curPartIdx);
uint64 calcHashSize(int64 nrows);
void prepareProbe();
VectorBatch* buildRes(VectorBatch* inBatch, VectorBatch* outBatch);
bool hasEnoughMem();
void judgeMemoryOverflow(uint64 hash_head_size);
void calcHashContextSize(MemoryContext ctx, uint64* allocateSize, uint64* freeSize);
void calcDatumArrayExpandSize();
VectorBatch* probeMemory();
VectorBatch* probeGrace();
template <typename T, bool complicateJoinKey, bool isSegHashTable>
VectorBatch* probeMemoryTable(SonicHashSource* probeP);
template <typename T, bool complicateJoinKey, bool isSegHashTable>
VectorBatch* probePartition(SonicHashSource* probeP = NULL);
template <typename bucketType, bool complicateJoinKey, bool isSegHashTable, bool isPartStatus>
VectorBatch* innerJoin(VectorBatch* batch);
void profile(bool writeLog, uint32 partIdx, uint8 bucketTypeSize);
template <typename BucketType, bool isSegHashTable>
void profileFunc(char* stats, uint32 partIdx);
void initMatchFunc(TupleDesc desc, uint16 keyNum);
void DispatchKeyInnerFunction(int KeyIndx);
template <typename innerType>
void DispatchKeyOuterFunction(int KeyIndx);
void CalcComplicateHashVal(VectorBatch* batch, List* hashKeys, bool inner);
template <bool matchPartComplicateKey>
void matchComplicateKey(VectorBatch* batch, SonicHashMemPartition* inPartition = NULL);
uint32 calcPartitionNum();
void calcPartIdx(uint32* hashVal, uint32 partNum, int nrows);
void calcRePartIdx(uint32* hashVal, uint32 partNum, uint32 rbit, int nrows);
bool preparePartition();
void initProbePartitions();
template <bool complicateJoinKey>
void rePartition(uint32 rePartIdx);
void recordPartitionInfo(bool buildside, int32 partIdx, uint32 istart, uint32 iend);
void analyzePartition(bool buildside, uint32 startPartIdx, uint32 endPartIdx, int64* totalFileNum,
long* totalFileSize, long* partSizeMin, long* partSizeMax, int* spillPartNum);
void reportSorthashinfo(ReportType reportType, uint32 totalPartNum, int32 rePartIdx = -1);
template <bool isInner>
void initPartition(SonicHashPartition* partition);
void loadInnerPartitions(uint64 memorySize);
void loadInnerPartition(uint32 partIdx);
void loadMultiInnerPartition(uint32 partIdx, SonicHashMemPartition* memPartition);
void quickSort(uint32* elements, const int start, const int end);
void sortPartitionSize(uint64 memorySize);
template <bool complicateJoinKey, bool optspill>
void saveProbePartition();
void pushDownFilterIfNeed();
void finishJoinPartition(uint32 partIdx);
void closePartFiles(uint32 partIdx);
void releaseAllFileHandlerBuffer(bool isInner);
void resetMemoryControl();
uint64 get_hash_head_size(int64 rows);
public:
double m_build_time;
double m_probe_time;
private:
VectorBatch* (SonicHashJoin::*m_probeFun[2])();
typedef VectorBatch* (SonicHashJoin::*probeTypeFun)(SonicHashSource* probeP);
void (SonicHashJoin::*m_saveProbePartition)();
void (SonicHashJoin::*m_funBuild[2])(VectorBatch* batch);
probeTypeFun m_probeTypeFun;
bool m_complicatekey;
SonicHashInputOpAttr m_probeOp;
bool* m_integertype;
VecHashJoinState* m_runtime;
char* m_next;
uint8 m_strategy;
VectorBatch* m_outRawBatch;
uint32 m_innerMatchLoc[2 * BatchMaxSize];
uint32 m_innerPartMatchLoc[2 * BatchMaxSize];
uint16 m_outerMatchLoc[2 * BatchMaxSize];
uint16 m_matchLocIndx;
uint32 m_partIdx[INIT_DATUM_ARRAY_SIZE];
uint32 m_probeIdx;
size_t m_arrayExpandSize;
SonicHashPartition** m_innerPartitions;
SonicHashPartition** m_outerPartitions;
* Get build side data from lower operator.
* Used for join without spilling.
*/
SonicHashOpSource* m_hashOpPartition;
uint8 m_probePartStatus;
* number of partitions.
* inner and outer should have the same number of partitions.
*/
uint32 m_partNum;
uint32* m_partSizeOrderedIdx;
int32 m_partLoadedOffset;
uint8* m_pLevel;
uint8 m_maxPLevel;
bool* m_isValid;
* the cjVector is only allocated and
* used when m_complicateJoinKey is true
*/
ScalarVector* m_cjVector;
VectorBatch* m_complicate_innerBatch;
VectorBatch* m_complicate_outerBatch;
bool m_nulleqmatch[BatchMaxSize];
* flag to show whether the build side partition is in memory.
* SONIC_PART_MAX_NUM is enough, because this array is not
* used after probePartition.
*/
bool m_memPartFlag[SONIC_PART_MAX_NUM];
BatchPos m_diskPartIdx[BatchMaxSize];
uint32 m_diskPartNum;
};
extern bool isSonicHashJoinEnable(HashJoin* hj);
#endif