diff --git a/include/common/tmsgcb.h b/include/common/tmsgcb.h
index 4002db06ea..b6c96bb2d1 100644
--- a/include/common/tmsgcb.h
+++ b/include/common/tmsgcb.h
@@ -57,6 +57,7 @@ typedef struct {
RegisterBrokenLinkArgFp registerBrokenLinkArgFp;
ReleaseHandleFp releaseHandleFp;
ReportStartup reportStartupFp;
+ void* clientRpc;
} SMsgCb;
void tmsgSetDefaultMsgCb(const SMsgCb* pMsgCb);
diff --git a/include/common/tname.h b/include/common/tname.h
index ffa4f8f253..ae2dc32335 100644
--- a/include/common/tname.h
+++ b/include/common/tname.h
@@ -17,6 +17,7 @@
#define _TD_COMMON_NAME_H_
#include "tdef.h"
+#include "tarray.h"
#ifdef __cplusplus
extern "C" {
@@ -62,6 +63,18 @@ int32_t tNameSetAcctId(SName* dst, int32_t acctId);
bool tNameDBNameEqual(SName* left, SName* right);
+typedef struct {
+ // input
+ SArray *tags; // element is SSmlKV
+ const char *sTableName; // super table name
+ uint8_t sTableNameLen; // the length of super table name
+
+ // output
+ char *childTableName; // must have size of TSDB_TABLE_NAME_LEN;
+ uint64_t uid; // child table uid, may be useful
+} RandTableName;
+
+void buildChildTableName(RandTableName *rName);
#ifdef __cplusplus
}
diff --git a/include/libs/executor/executor.h b/include/libs/executor/executor.h
index e0fce2aa6a..162b6fb2ed 100644
--- a/include/libs/executor/executor.h
+++ b/include/libs/executor/executor.h
@@ -22,6 +22,7 @@ extern "C" {
#include "query.h"
#include "tcommon.h"
+#include "tmsgcb.h"
typedef void* qTaskInfo_t;
typedef void* DataSinkHandle;
@@ -29,11 +30,12 @@ struct SRpcMsg;
struct SSubplan;
typedef struct SReadHandle {
- void* reader;
- void* meta;
- void* config;
- void* vnode;
- void* mnd;
+ void* reader;
+ void* meta;
+ void* config;
+ void* vnode;
+ void* mnd;
+ SMsgCb* pMsgCb;
} SReadHandle;
#define STREAM_DATA_TYPE_SUBMIT_BLOCK 0x1
diff --git a/include/libs/function/functionMgt.h b/include/libs/function/functionMgt.h
index 4a37283ee5..40f8a9e383 100644
--- a/include/libs/function/functionMgt.h
+++ b/include/libs/function/functionMgt.h
@@ -154,6 +154,7 @@ bool fmIsWindowClauseFunc(int32_t funcId);
bool fmIsSpecialDataRequiredFunc(int32_t funcId);
bool fmIsDynamicScanOptimizedFunc(int32_t funcId);
bool fmIsMultiResFunc(int32_t funcId);
+bool fmIsRepeatScanFunc(int32_t funcId);
bool fmIsUserDefinedFunc(int32_t funcId);
typedef enum EFuncDataRequired {
@@ -170,7 +171,7 @@ int32_t fmGetScalarFuncExecFuncs(int32_t funcId, SScalarFuncExecFuncs* pFpSet);
int32_t fmGetUdafExecFuncs(int32_t funcId, SFuncExecFuncs* pFpSet);
int32_t fmSetInvertFunc(int32_t funcId, SFuncExecFuncs* pFpSet);
int32_t fmSetNormalFunc(int32_t funcId, SFuncExecFuncs* pFpSet);
-bool fmIsInvertible(int32_t funcId);
+bool fmIsInvertible(int32_t funcId);
#ifdef __cplusplus
}
diff --git a/include/libs/nodes/nodes.h b/include/libs/nodes/nodes.h
index ad8a472d08..702dd50df5 100644
--- a/include/libs/nodes/nodes.h
+++ b/include/libs/nodes/nodes.h
@@ -206,6 +206,7 @@ typedef enum ENodeType {
QUERY_NODE_PHYSICAL_PLAN_EXCHANGE,
QUERY_NODE_PHYSICAL_PLAN_SORT,
QUERY_NODE_PHYSICAL_PLAN_INTERVAL,
+ QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL,
QUERY_NODE_PHYSICAL_PLAN_FILL,
QUERY_NODE_PHYSICAL_PLAN_SESSION_WINDOW,
QUERY_NODE_PHYSICAL_PLAN_STATE_WINDOW,
diff --git a/include/libs/nodes/plannodes.h b/include/libs/nodes/plannodes.h
index a756217c7a..d0d10b2761 100644
--- a/include/libs/nodes/plannodes.h
+++ b/include/libs/nodes/plannodes.h
@@ -274,6 +274,8 @@ typedef struct SIntervalPhysiNode {
int8_t slidingUnit;
} SIntervalPhysiNode;
+typedef SIntervalPhysiNode SStreamIntervalPhysiNode;
+
typedef struct SFillPhysiNode {
SPhysiNode node;
EFillMode mode;
diff --git a/include/libs/nodes/querynodes.h b/include/libs/nodes/querynodes.h
index 91c80f6cf5..0a835dae83 100644
--- a/include/libs/nodes/querynodes.h
+++ b/include/libs/nodes/querynodes.h
@@ -233,6 +233,7 @@ typedef struct SSelectStmt {
uint8_t precision;
bool isEmptyResult;
bool hasAggFuncs;
+ bool hasRepeatScanFuncs;
bool isTimeOrderQuery;
} SSelectStmt;
diff --git a/include/libs/qcom/query.h b/include/libs/qcom/query.h
index c1e53fa805..cac60c33bb 100644
--- a/include/libs/qcom/query.h
+++ b/include/libs/qcom/query.h
@@ -24,6 +24,7 @@ extern "C" {
#include "thash.h"
#include "tlog.h"
#include "tmsg.h"
+#include "tmsgcb.h"
typedef enum {
JOB_TASK_STATUS_NULL = 0,
@@ -149,7 +150,8 @@ int32_t cleanupTaskQueue();
*/
int32_t taosAsyncExec(__async_exec_fn_t execFn, void* execParam, int32_t* code);
-int32_t asyncSendMsgToServerExt(void* pTransporter, SEpSet* epSet, int64_t* pTransporterId, const SMsgSendInfo* pInfo, bool persistHandle, void *ctx);
+int32_t asyncSendMsgToServerExt(void* pTransporter, SEpSet* epSet, int64_t* pTransporterId, const SMsgSendInfo* pInfo,
+ bool persistHandle, void* ctx);
/**
* Asynchronously send message to server, after the response received, the callback will be incured.
diff --git a/source/client/src/clientSml.c b/source/client/src/clientSml.c
index 2a0e85092b..15d1500860 100644
--- a/source/client/src/clientSml.c
+++ b/source/client/src/clientSml.c
@@ -15,6 +15,7 @@
#include "tcommon.h"
#include "catalog.h"
#include "clientInt.h"
+#include "tname.h"
//=================================================================================================
#define SPACE ' '
@@ -97,6 +98,21 @@ typedef struct {
char *buf;
} SSmlMsgBuf;
+typedef struct {
+ int32_t code;
+ int32_t lineNum;
+
+ int32_t numOfSTables;
+ int32_t numOfCTables;
+ int32_t numOfCreateSTables;
+
+ int64_t parseTime;
+ int64_t schemaTime;
+ int64_t insertBindTime;
+ int64_t insertRpcTime;
+ int64_t endTime;
+} SSmlCostInfo;
+
typedef struct {
uint64_t id;
@@ -114,6 +130,7 @@ typedef struct {
SRequestObj *pRequest;
SQuery *pQuery;
+ SSmlCostInfo cost;
int32_t affectedRows;
SSmlMsgBuf msgBuf;
SHashObj *dumplicateKey; // for dumplicate key
@@ -147,45 +164,6 @@ static int32_t smlBuildInvalidDataMsg(SSmlMsgBuf* pBuf, const char *msg1, const
return TSDB_CODE_SML_INVALID_DATA;
}
-static int smlCompareKv(const void* p1, const void* p2) {
- SSmlKv* kv1 = *(SSmlKv**)p1;
- SSmlKv* kv2 = *(SSmlKv**)p2;
- int32_t kvLen1 = kv1->keyLen;
- int32_t kvLen2 = kv2->keyLen;
- int32_t res = strncasecmp(kv1->key, kv2->key, TMIN(kvLen1, kvLen2));
- if (res != 0) {
- return res;
- } else {
- return kvLen1-kvLen2;
- }
-}
-
-static void smlBuildChildTableName(SSmlTableInfo *tags) {
- int32_t size = taosArrayGetSize(tags->tags);
- ASSERT(size > 0);
- taosArraySort(tags->tags, smlCompareKv);
-
- SStringBuilder sb = {0};
- taosStringBuilderAppendStringLen(&sb, tags->sTableName, tags->sTableNameLen);
- for (int j = 0; j < size; ++j) {
- SSmlKv *tagKv = taosArrayGetP(tags->tags, j);
- taosStringBuilderAppendStringLen(&sb, tagKv->key, tagKv->keyLen);
- taosStringBuilderAppendStringLen(&sb, tagKv->value, tagKv->valueLen);
- }
- size_t len = 0;
- char* keyJoined = taosStringBuilderGetResult(&sb, &len);
- T_MD5_CTX context;
- tMD5Init(&context);
- tMD5Update(&context, (uint8_t *)keyJoined, (uint32_t)len);
- tMD5Final(&context);
- uint64_t digest1 = *(uint64_t*)(context.digest);
- //uint64_t digest2 = *(uint64_t*)(context.digest + 8);
- //snprintf(tags->childTableName, TSDB_TABLE_NAME_LEN, "t_%016"PRIx64"%016"PRIx64, digest1, digest2);
- snprintf(tags->childTableName, TSDB_TABLE_NAME_LEN, "t_%016"PRIx64, digest1);
- taosStringBuilderDestroy(&sb);
- tags->uid = digest1;
-}
-
static int32_t smlGenerateSchemaAction(SSchema* pointColField, SHashObj* dbAttrHash, SArray* dbAttrArray, bool isTag, char sTableName[],
SSchemaAction* action, bool* actionNeeded, SSmlHandle* info) {
// char fieldName[TSDB_COL_NAME_LEN] = {0};
@@ -444,6 +422,7 @@ static int32_t smlModifyDBSchemas(SSmlHandle* info) {
uError("SML:0x%"PRIx64" catalogGetSTableMeta failed. super table name %s", info->id, schemaAction.createSTable.sTableName);
return code;
}
+ info->cost.numOfCreateSTables++;
}else if (code == TSDB_CODE_SUCCESS) {
} else {
uError("SML:0x%"PRIx64" load table meta error: %s", info->id, tstrerror(code));
@@ -926,20 +905,6 @@ static bool smlParseValue(SSmlKv *pVal, SSmlMsgBuf *msg) {
return false;
}
-static bool checkDuplicateKey(char *key, SHashObj *pHash, SSmlHandle* info) {
- char *val = NULL;
- val = taosHashGet(pHash, key, strlen(key));
- if (val) {
- uError("SML:0x%"PRIx64" Duplicate key detected:%s", info->id, key);
- return true;
- }
-
- uint8_t dummy_val = 0;
- taosHashPut(pHash, key, strlen(key), &dummy_val, sizeof(uint8_t));
-
- return false;
-}
-
static int32_t smlParseString(const char* sql, SSmlLineInfo *elements, SSmlMsgBuf *msg){
if(!sql) return TSDB_CODE_SML_INVALID_DATA;
while (*sql != '\0') { // jump the space at the begining
@@ -1546,8 +1511,10 @@ static int32_t smlParseLine(SSmlHandle* info, const char* sql) {
tinfo->sTableName = elements.measure;
tinfo->sTableNameLen = elements.measureLen;
- smlBuildChildTableName(tinfo);
- uDebug("SML:0x%"PRIx64" child table name: %s", info->id, tinfo->childTableName);
+ RandTableName rName = {.tags=tinfo->tags, .sTableName=tinfo->sTableName, .sTableNameLen=tinfo->sTableNameLen,
+ .childTableName=tinfo->childTableName};
+ buildChildTableName(&rName);
+ tinfo->uid = rName.uid;
SSmlSTableMeta** tableMeta = taosHashGet(info->superTables, elements.measure, elements.measureLen);
if(tableMeta){ // update meta
@@ -1604,7 +1571,7 @@ static void smlDestroyInfo(SSmlHandle* info){
static SSmlHandle* smlBuildSmlInfo(TAOS* taos, SRequestObj* request, SMLProtocolType protocol, int8_t precision, bool dataFormat){
int32_t code = TSDB_CODE_SUCCESS;
- SSmlHandle* info = taosMemoryMalloc(sizeof(SSmlHandle));
+ SSmlHandle* info = taosMemoryCalloc(1, sizeof(SSmlHandle));
if (NULL == info) {
return NULL;
}
@@ -1699,12 +1666,23 @@ static int32_t smlInsertData(SSmlHandle* info) {
}
smlBuildOutput(info->exec, info->pVgHash);
+ info->cost.insertRpcTime = taosGetTimestampUs();
+
launchQueryImpl(info->pRequest, info->pQuery, TSDB_CODE_SUCCESS, true);
info->affectedRows = taos_affected_rows(info->pRequest);
return info->pRequest->code;
}
+static void smlPrintStatisticInfo(SSmlHandle *info){
+ uError("SML:0x%"PRIx64" smlInsertLines result, code:%d,lineNum:%d,stable num:%d,ctable num:%d,create stable num:%d \
+ parse cost:%"PRId64",schema cost:%"PRId64",bind cost:%"PRId64",rpc cost:%"PRId64",total cost:%"PRId64"", info->id, info->cost.code,
+ info->cost.lineNum, info->cost.numOfSTables, info->cost.numOfCTables, info->cost.numOfCreateSTables,
+ info->cost.schemaTime-info->cost.parseTime, info->cost.insertBindTime-info->cost.schemaTime,
+ info->cost.insertRpcTime-info->cost.insertBindTime, info->cost.endTime-info->cost.insertRpcTime,
+ info->cost.endTime-info->cost.parseTime);
+}
+
static int smlInsertLines(SSmlHandle *info, char* lines[], int numLines) {
int32_t code = TSDB_CODE_SUCCESS;
@@ -1714,6 +1692,7 @@ static int smlInsertLines(SSmlHandle *info, char* lines[], int numLines) {
goto cleanup;
}
+ info->cost.parseTime = taosGetTimestampUs();
for (int32_t i = 0; i < numLines; ++i) {
code = smlParseLine(info, lines[i]);
if (code != TSDB_CODE_SUCCESS) {
@@ -1721,24 +1700,29 @@ static int smlInsertLines(SSmlHandle *info, char* lines[], int numLines) {
goto cleanup;
}
}
- uDebug("SML:0x%"PRIx64" smlInsertLines parse success. tables %d", info->id, taosHashGetSize(info->childTables));
- uDebug("SML:0x%"PRIx64" smlInsertLines parse success. super tables %d", info->id, taosHashGetSize(info->superTables));
+ info->cost.lineNum = numLines;
+ info->cost.numOfSTables = taosHashGetSize(info->superTables);
+ info->cost.numOfCTables = taosHashGetSize(info->childTables);
+
+ info->cost.schemaTime = taosGetTimestampUs();
code = smlModifyDBSchemas(info);
if (code != 0) {
uError("SML:0x%"PRIx64" smlModifyDBSchemas error : %s", info->id, tstrerror(code));
goto cleanup;
}
+ info->cost.insertBindTime = taosGetTimestampUs();
code = smlInsertData(info);
if (code != 0) {
uError("SML:0x%"PRIx64" smlInsertData error : %s", info->id, tstrerror(code));
goto cleanup;
}
-
- uDebug("SML:0x%"PRIx64" smlInsertLines finish inserting %d lines.", info->id, numLines);
+ info->cost.endTime = taosGetTimestampUs();
cleanup:
+ info->cost.code = code;
+ smlPrintStatisticInfo(info);
return code;
}
@@ -1790,7 +1774,6 @@ TAOS_RES* taos_schemaless_insert(TAOS* taos, char* lines[], int numLines, int pr
}
smlDestroyInfo(info);
-end:
return (TAOS_RES*)request;
}
diff --git a/source/common/src/tname.c b/source/common/src/tname.c
index f4755f5b5e..62ba4bfb79 100644
--- a/source/common/src/tname.c
+++ b/source/common/src/tname.c
@@ -15,6 +15,8 @@
#define _DEFAULT_SOURCE
#include "tname.h"
+#include "tcommon.h"
+#include "tstrbuild.h"
#define VALID_NAME_TYPE(x) ((x) == TSDB_DB_NAME_T || (x) == TSDB_TABLE_NAME_T)
@@ -294,4 +296,43 @@ int32_t tNameFromString(SName* dst, const char* str, uint32_t type) {
return 0;
}
+static int compareKv(const void* p1, const void* p2) {
+ SSmlKv* kv1 = *(SSmlKv**)p1;
+ SSmlKv* kv2 = *(SSmlKv**)p2;
+ int32_t kvLen1 = kv1->keyLen;
+ int32_t kvLen2 = kv2->keyLen;
+ int32_t res = strncasecmp(kv1->key, kv2->key, TMIN(kvLen1, kvLen2));
+ if (res != 0) {
+ return res;
+ } else {
+ return kvLen1-kvLen2;
+ }
+}
+/*
+ * use stable name and tags to grearate child table name
+ */
+void buildChildTableName(RandTableName *rName) {
+ int32_t size = taosArrayGetSize(rName->tags);
+ ASSERT(size > 0);
+ taosArraySort(rName->tags, compareKv);
+
+ SStringBuilder sb = {0};
+ taosStringBuilderAppendStringLen(&sb, rName->sTableName, rName->sTableNameLen);
+ for (int j = 0; j < size; ++j) {
+ SSmlKv *tagKv = taosArrayGetP(rName->tags, j);
+ taosStringBuilderAppendStringLen(&sb, tagKv->key, tagKv->keyLen);
+ taosStringBuilderAppendStringLen(&sb, tagKv->value, tagKv->valueLen);
+ }
+ size_t len = 0;
+ char* keyJoined = taosStringBuilderGetResult(&sb, &len);
+ T_MD5_CTX context;
+ tMD5Init(&context);
+ tMD5Update(&context, (uint8_t *)keyJoined, (uint32_t)len);
+ tMD5Final(&context);
+ uint64_t digest1 = *(uint64_t*)(context.digest);
+ uint64_t digest2 = *(uint64_t*)(context.digest + 8);
+ snprintf(rName->childTableName, TSDB_TABLE_NAME_LEN, "t_%016"PRIx64"%016"PRIx64, digest1, digest2);
+ taosStringBuilderDestroy(&sb);
+ rName->uid = digest1;
+}
diff --git a/source/dnode/mgmt/implement/inc/dmImp.h b/source/dnode/mgmt/implement/inc/dmImp.h
index 32869aee9e..8a1a116ab3 100644
--- a/source/dnode/mgmt/implement/inc/dmImp.h
+++ b/source/dnode/mgmt/implement/inc/dmImp.h
@@ -26,8 +26,10 @@ int32_t dmOpenNode(SMgmtWrapper *pWrapper);
void dmCloseNode(SMgmtWrapper *pWrapper);
// dmTransport.c
-int32_t dmInitTrans(SDnode *pDnode);
-void dmCleanupTrans(SDnode *pDnode);
+int32_t dmInitServer(SDnode *pDnode);
+void dmCleanupServer(SDnode *pDnode);
+int32_t dmInitClient(SDnode *pDnode);
+void dmCleanupClient(SDnode *pDnode);
SProcCfg dmGenProcCfg(SMgmtWrapper *pWrapper);
SMsgCb dmGetMsgcb(SMgmtWrapper *pWrapper);
int32_t dmInitMsgHandle(SDnode *pDnode);
diff --git a/source/dnode/mgmt/implement/src/dmExec.c b/source/dnode/mgmt/implement/src/dmExec.c
index 06001028b5..6999cee037 100644
--- a/source/dnode/mgmt/implement/src/dmExec.c
+++ b/source/dnode/mgmt/implement/src/dmExec.c
@@ -213,10 +213,12 @@ static int32_t dmOpenNodes(SDnode *pDnode) {
}
pWrapper->procType = DND_PROC_CHILD;
+ if (dmInitClient(pDnode) != 0) {
+ return -1;
+ }
- SMsgCb msgCb = pDnode->data.msgCb;
- msgCb.pWrapper = pWrapper;
- tmsgSetDefaultMsgCb(&msgCb);
+ pDnode->data.msgCb = dmGetMsgcb(pWrapper);
+ tmsgSetDefaultMsgCb(&pDnode->data.msgCb);
if (dmOpenNode(pWrapper) != 0) {
dError("node:%s, failed to open since %s", pWrapper->name, terrstr());
@@ -234,6 +236,15 @@ static int32_t dmOpenNodes(SDnode *pDnode) {
pWrapper->procType = DND_PROC_SINGLE;
}
+ if (n == DNODE) {
+ if (dmInitClient(pDnode) != 0) {
+ return -1;
+ }
+
+ pDnode->data.msgCb = dmGetMsgcb(pWrapper);
+ tmsgSetDefaultMsgCb(&pDnode->data.msgCb);
+ }
+
if (dmOpenNode(pWrapper) != 0) {
dError("node:%s, failed to open since %s", pWrapper->name, terrstr());
return -1;
@@ -281,21 +292,21 @@ static void dmProcessProcHandle(void *handle) {
}
static void dmWatchNodes(SDnode *pDnode) {
- taosThreadMutexLock(&pDnode->mutex);
- if (pDnode->ptype == DND_PROC_PARENT) {
- for (EDndNodeType n = DNODE + 1; n < NODE_END; ++n) {
- SMgmtWrapper *pWrapper = &pDnode->wrappers[n];
- if (!pWrapper->required) continue;
- if (pWrapper->procType != DND_PROC_PARENT) continue;
- if (pDnode->ntype == NODE_END) continue;
+ if (pDnode->ptype != DND_PROC_PARENT) return;
+ if (pDnode->ntype == NODE_END) return;
- if (pWrapper->procId <= 0 || !taosProcExist(pWrapper->procId)) {
- dWarn("node:%s, process:%d is killed and needs to be restarted", pWrapper->name, pWrapper->procId);
- if (pWrapper->procObj) {
- taosProcCloseHandles(pWrapper->procObj, dmProcessProcHandle);
- }
- dmNewNodeProc(pWrapper, n);
+ taosThreadMutexLock(&pDnode->mutex);
+ for (EDndNodeType n = DNODE + 1; n < NODE_END; ++n) {
+ SMgmtWrapper *pWrapper = &pDnode->wrappers[n];
+ if (!pWrapper->required) continue;
+ if (pWrapper->procType != DND_PROC_PARENT) continue;
+
+ if (pWrapper->procId <= 0 || !taosProcExist(pWrapper->procId)) {
+ dWarn("node:%s, process:%d is killed and needs to be restarted", pWrapper->name, pWrapper->procId);
+ if (pWrapper->procObj) {
+ taosProcCloseHandles(pWrapper->procObj, dmProcessProcHandle);
}
+ dmNewNodeProc(pWrapper, n);
}
}
taosThreadMutexUnlock(&pDnode->mutex);
diff --git a/source/dnode/mgmt/implement/src/dmHandle.c b/source/dnode/mgmt/implement/src/dmHandle.c
index 129d41061e..097d18679b 100644
--- a/source/dnode/mgmt/implement/src/dmHandle.c
+++ b/source/dnode/mgmt/implement/src/dmHandle.c
@@ -242,7 +242,7 @@ static int32_t dmInitMgmt(SMgmtWrapper *pWrapper) {
return -1;
}
- if (dmInitTrans(pDnode) != 0) {
+ if (dmInitServer(pDnode) != 0) {
dError("failed to init transport since %s", terrstr());
return -1;
}
@@ -275,7 +275,8 @@ static void dmCleanupMgmt(SMgmtWrapper *pWrapper) {
}
taosWUnLockLatch(&pDnode->data.latch);
- dmCleanupTrans(pDnode);
+ dmCleanupClient(pDnode);
+ dmCleanupServer(pDnode);
dInfo("dnode-mgmt is cleaned up");
}
diff --git a/source/dnode/mgmt/implement/src/dmObj.c b/source/dnode/mgmt/implement/src/dmObj.c
index 66bfb27016..a43439d465 100644
--- a/source/dnode/mgmt/implement/src/dmObj.c
+++ b/source/dnode/mgmt/implement/src/dmObj.c
@@ -124,9 +124,6 @@ SDnode *dmCreate(const SDnodeOpt *pOption) {
goto _OVER;
}
- pDnode->data.msgCb = dmGetMsgcb(&pDnode->wrappers[DNODE]);
- tmsgSetDefaultMsgCb(&pDnode->data.msgCb);
-
dInfo("dnode is created, data:%p", pDnode);
code = 0;
diff --git a/source/dnode/mgmt/implement/src/dmTransport.c b/source/dnode/mgmt/implement/src/dmTransport.c
index 114d7b6dfc..a58999bf2d 100644
--- a/source/dnode/mgmt/implement/src/dmTransport.c
+++ b/source/dnode/mgmt/implement/src/dmTransport.c
@@ -16,6 +16,8 @@
#define _DEFAULT_SOURCE
#include "dmImp.h"
+#include "qworker.h"
+
#define INTERNAL_USER "_dnd"
#define INTERNAL_CKEY "_key"
#define INTERNAL_SECRET "_pwd"
@@ -85,17 +87,14 @@ static void dmProcessRpcMsg(SMgmtWrapper *pWrapper, SRpcMsg *pRpc, SEpSet *pEpSe
if ((pMsg = taosAllocateQitem(sizeof(SNodeMsg))) == NULL) goto _OVER;
if (dmBuildMsg(pMsg, pRpc) != 0) goto _OVER;
- if (pWrapper->procType == DND_PROC_SINGLE) {
+ if (pWrapper->procType != DND_PROC_PARENT) {
dTrace("msg:%p, created, type:%s handle:%p user:%s", pMsg, TMSG_INFO(msgType), pRpc->handle, pMsg->user);
code = (*msgFp)(pWrapper, pMsg);
- } else if (pWrapper->procType == DND_PROC_PARENT) {
+ } else {
dTrace("msg:%p, created and put into child queue, type:%s handle:%p code:0x%04x user:%s contLen:%d", pMsg,
TMSG_INFO(msgType), pRpc->handle, pMsg->rpcMsg.code & 0XFFFF, pMsg->user, pRpc->contLen);
code = taosProcPutToChildQ(pWrapper->procObj, pMsg, sizeof(SNodeMsg), pRpc->pCont, pRpc->contLen,
(isReq && (pMsg->rpcMsg.code == 0)) ? pRpc->handle : NULL, pRpc->refId, PROC_FUNC_REQ);
- } else {
- dTrace("msg:%p, should not processed in child process, handle:%p user:%s", pMsg, pRpc->handle, pMsg->user);
- ASSERT(1);
}
_OVER:
@@ -108,7 +107,7 @@ _OVER:
} else {
dError("msg:%p, type:%s handle:%p failed to process since 0x%04x:%s", pMsg, TMSG_INFO(msgType), pRpc->handle,
code & 0XFFFF, terrstr());
- if (msgType & 1U) {
+ if (isReq) {
if (terrno != 0) code = terrno;
if (code == TSDB_CODE_NODE_NOT_DEPLOYED || code == TSDB_CODE_NODE_OFFLINE) {
if (msgType > TDMT_MND_MSG && msgType < TDMT_VND_MSG) {
@@ -130,22 +129,27 @@ _OVER:
}
static void dmProcessMsg(SDnode *pDnode, SRpcMsg *pMsg, SEpSet *pEpSet) {
- SDnodeTrans * pTrans = &pDnode->trans;
+ SDnodeTrans *pTrans = &pDnode->trans;
tmsg_t msgType = pMsg->msgType;
bool isReq = msgType & 1u;
- SMsgHandle * pHandle = &pTrans->msgHandles[TMSG_INDEX(msgType)];
+ SMsgHandle *pHandle = &pTrans->msgHandles[TMSG_INDEX(msgType)];
SMgmtWrapper *pWrapper = pHandle->pNdWrapper;
- if (msgType == TDMT_DND_SERVER_STATUS) {
- dTrace("server status req will be processed, handle:%p, app:%p", pMsg->handle, pMsg->ahandle);
- dmProcessServerStatusReq(pDnode, pMsg);
- return;
- }
-
- if (msgType == TDMT_DND_NET_TEST) {
- dTrace("net test req will be processed, handle:%p, app:%p", pMsg->handle, pMsg->ahandle);
- dmProcessServerStatusReq(pDnode, pMsg);
- return;
+ switch (msgType) {
+ case TDMT_DND_SERVER_STATUS:
+ dTrace("server status req will be processed, handle:%p, app:%p", pMsg->handle, pMsg->ahandle);
+ dmProcessServerStatusReq(pDnode, pMsg);
+ return;
+ case TDMT_DND_NET_TEST:
+ dTrace("net test req will be processed, handle:%p, app:%p", pMsg->handle, pMsg->ahandle);
+ dmProcessNetTestReq(pDnode, pMsg);
+ return;
+ case TDMT_MND_SYSTABLE_RETRIEVE_RSP:
+ case TDMT_VND_FETCH_RSP:
+ dTrace("retrieve rsp is received");
+ qWorkerProcessFetchRsp(NULL, NULL, pMsg);
+ pMsg->pCont = NULL; // already freed in qworker
+ return;
}
if (pDnode->status != DND_STAT_RUNNING) {
@@ -233,16 +237,6 @@ int32_t dmInitMsgHandle(SDnode *pDnode) {
return 0;
}
-static inline int32_t dmSendRpcReq(SDnode *pDnode, const SEpSet *pEpSet, SRpcMsg *pReq) {
- if (pDnode->trans.clientRpc == NULL) {
- terrno = TSDB_CODE_NODE_OFFLINE;
- return -1;
- }
-
- rpcSendRequest(pDnode->trans.clientRpc, pEpSet, pReq, NULL);
- return 0;
-}
-
static void dmSendRpcRedirectRsp(SDnode *pDnode, const SRpcMsg *pReq) {
SEpSet epSet = {0};
dmGetMnodeEpSet(pDnode, &epSet);
@@ -288,28 +282,20 @@ void dmSendToMnodeRecv(SDnode *pDnode, SRpcMsg *pReq, SRpcMsg *pRsp) {
}
static inline int32_t dmSendReq(SMgmtWrapper *pWrapper, const SEpSet *pEpSet, SRpcMsg *pReq) {
- if (pWrapper->pDnode->status != DND_STAT_RUNNING) {
+ SDnode *pDnode = pWrapper->pDnode;
+ if (pDnode->status != DND_STAT_RUNNING) {
terrno = TSDB_CODE_NODE_OFFLINE;
dError("failed to send rpc msg since %s, handle:%p", terrstr(), pReq->handle);
return -1;
}
- if (pWrapper->procType != DND_PROC_CHILD) {
- return dmSendRpcReq(pWrapper->pDnode, pEpSet, pReq);
- } else {
- char *pHead = taosMemoryMalloc(sizeof(SRpcMsg) + sizeof(SEpSet));
- if (pHead == NULL) {
- terrno = TSDB_CODE_OUT_OF_MEMORY;
- return -1;
- }
-
- memcpy(pHead, pReq, sizeof(SRpcMsg));
- memcpy(pHead + sizeof(SRpcMsg), pEpSet, sizeof(SEpSet));
- taosProcPutToParentQ(pWrapper->procObj, pHead, sizeof(SRpcMsg) + sizeof(SEpSet), pReq->pCont, pReq->contLen,
- PROC_FUNC_REQ);
- taosMemoryFree(pHead);
- return 0;
+ if (pDnode->trans.clientRpc == NULL) {
+ terrno = TSDB_CODE_NODE_OFFLINE;
+ return -1;
}
+
+ rpcSendRequest(pDnode->trans.clientRpc, pEpSet, pReq, NULL);
+ return 0;
}
static inline void dmSendRsp(SMgmtWrapper *pWrapper, const SRpcMsg *pRsp) {
@@ -396,9 +382,10 @@ static void dmConsumeParentQueue(SMgmtWrapper *pWrapper, SRpcMsg *pMsg, int16_t
pMsg->pCont = pCont;
if (ftype == PROC_FUNC_REQ) {
+ ASSERT(1);
dTrace("msg:%p, get from parent queue, send req:%s handle:%p code:0x%04x, app:%p", pMsg, TMSG_INFO(pMsg->msgType),
pMsg->handle, code, pMsg->ahandle);
- dmSendRpcReq(pWrapper->pDnode, (SEpSet *)((char *)pMsg + sizeof(SRpcMsg)), pMsg);
+ dmSendReq(pWrapper, (SEpSet *)((char *)pMsg + sizeof(SRpcMsg)), pMsg);
} else if (ftype == PROC_FUNC_RSP) {
dTrace("msg:%p, get from parent queue, rsp handle:%p code:0x%04x, app:%p", pMsg, pMsg->handle, code, pMsg->ahandle);
pMsg->refId = taosProcRemoveHandle(pWrapper->procObj, pMsg->handle);
@@ -421,23 +408,25 @@ static void dmConsumeParentQueue(SMgmtWrapper *pWrapper, SRpcMsg *pMsg, int16_t
}
SProcCfg dmGenProcCfg(SMgmtWrapper *pWrapper) {
- SProcCfg cfg = {.childConsumeFp = (ProcConsumeFp)dmConsumeChildQueue,
- .childMallocHeadFp = (ProcMallocFp)taosAllocateQitem,
- .childFreeHeadFp = (ProcFreeFp)taosFreeQitem,
- .childMallocBodyFp = (ProcMallocFp)rpcMallocCont,
- .childFreeBodyFp = (ProcFreeFp)rpcFreeCont,
- .parentConsumeFp = (ProcConsumeFp)dmConsumeParentQueue,
- .parentMallocHeadFp = (ProcMallocFp)taosMemoryMalloc,
- .parentFreeHeadFp = (ProcFreeFp)taosMemoryFree,
- .parentMallocBodyFp = (ProcMallocFp)rpcMallocCont,
- .parentFreeBodyFp = (ProcFreeFp)rpcFreeCont,
- .shm = pWrapper->procShm,
- .parent = pWrapper,
- .name = pWrapper->name};
+ SProcCfg cfg = {
+ .childConsumeFp = (ProcConsumeFp)dmConsumeChildQueue,
+ .childMallocHeadFp = (ProcMallocFp)taosAllocateQitem,
+ .childFreeHeadFp = (ProcFreeFp)taosFreeQitem,
+ .childMallocBodyFp = (ProcMallocFp)rpcMallocCont,
+ .childFreeBodyFp = (ProcFreeFp)rpcFreeCont,
+ .parentConsumeFp = (ProcConsumeFp)dmConsumeParentQueue,
+ .parentMallocHeadFp = (ProcMallocFp)taosMemoryMalloc,
+ .parentFreeHeadFp = (ProcFreeFp)taosMemoryFree,
+ .parentMallocBodyFp = (ProcMallocFp)rpcMallocCont,
+ .parentFreeBodyFp = (ProcFreeFp)rpcFreeCont,
+ .shm = pWrapper->procShm,
+ .parent = pWrapper,
+ .name = pWrapper->name,
+ };
return cfg;
}
-bool rpcRfp(int32_t code) {
+static bool rpcRfp(int32_t code) {
if (code == TSDB_CODE_RPC_REDIRECT) {
return true;
} else {
@@ -445,7 +434,7 @@ bool rpcRfp(int32_t code) {
}
}
-static int32_t dmInitClient(SDnode *pDnode) {
+int32_t dmInitClient(SDnode *pDnode) {
SDnodeTrans *pTrans = &pDnode->trans;
SRpcInit rpcInit = {0};
@@ -471,11 +460,15 @@ static int32_t dmInitClient(SDnode *pDnode) {
return -1;
}
+ pDnode->data.msgCb = dmGetMsgcb(&pDnode->wrappers[DNODE]);
+ tmsgSetDefaultMsgCb(&pDnode->data.msgCb);
+
dDebug("dnode rpc client is initialized");
+
return 0;
}
-static void dmCleanupClient(SDnode *pDnode) {
+void dmCleanupClient(SDnode *pDnode) {
SDnodeTrans *pTrans = &pDnode->trans;
if (pTrans->clientRpc) {
rpcClose(pTrans->clientRpc);
@@ -517,7 +510,7 @@ static inline int32_t dmRetrieveUserAuthInfo(SDnode *pDnode, char *user, char *s
SAuthReq authReq = {0};
tstrncpy(authReq.user, user, TSDB_USER_LEN);
int32_t contLen = tSerializeSAuthReq(NULL, 0, &authReq);
- void * pReq = rpcMallocCont(contLen);
+ void *pReq = rpcMallocCont(contLen);
tSerializeSAuthReq(pReq, contLen, &authReq);
SRpcMsg rpcMsg = {.pCont = pReq, .contLen = contLen, .msgType = TDMT_MND_AUTH, .ahandle = (void *)9528};
@@ -543,7 +536,7 @@ static inline int32_t dmRetrieveUserAuthInfo(SDnode *pDnode, char *user, char *s
return rpcRsp.code;
}
-static int32_t dmInitServer(SDnode *pDnode) {
+int32_t dmInitServer(SDnode *pDnode) {
SDnodeTrans *pTrans = &pDnode->trans;
SRpcInit rpcInit = {0};
@@ -569,7 +562,7 @@ static int32_t dmInitServer(SDnode *pDnode) {
return 0;
}
-static void dmCleanupServer(SDnode *pDnode) {
+void dmCleanupServer(SDnode *pDnode) {
SDnodeTrans *pTrans = &pDnode->trans;
if (pTrans->serverRpc) {
rpcClose(pTrans->serverRpc);
@@ -578,17 +571,6 @@ static void dmCleanupServer(SDnode *pDnode) {
}
}
-int32_t dmInitTrans(SDnode *pDnode) {
- if (dmInitServer(pDnode) != 0) return -1;
- if (dmInitClient(pDnode) != 0) return -1;
- return 0;
-}
-
-void dmCleanupTrans(SDnode *pDnode) {
- dmCleanupServer(pDnode);
- dmCleanupClient(pDnode);
-}
-
SMsgCb dmGetMsgcb(SMgmtWrapper *pWrapper) {
SMsgCb msgCb = {
.sendReqFp = dmSendReq,
@@ -598,6 +580,7 @@ SMsgCb dmGetMsgcb(SMgmtWrapper *pWrapper) {
.releaseHandleFp = dmReleaseHandle,
.reportStartupFp = dmReportStartupByWrapper,
.pWrapper = pWrapper,
+ .clientRpc = pWrapper->pDnode->trans.clientRpc,
};
return msgCb;
}
diff --git a/source/dnode/mgmt/interface/inc/dmInt.h b/source/dnode/mgmt/interface/inc/dmInt.h
index 63bfaf5ad2..b56edd2630 100644
--- a/source/dnode/mgmt/interface/inc/dmInt.h
+++ b/source/dnode/mgmt/interface/inc/dmInt.h
@@ -37,7 +37,7 @@ void dmSetMsgHandle(SMgmtWrapper *pWrapper, tmsg_t msgType, NodeMsgFp nodeMsgF
void dmReportStartup(SDnode *pDnode, const char *pName, const char *pDesc);
void dmReportStartupByWrapper(SMgmtWrapper *pWrapper, const char *pName, const char *pDesc);
void dmProcessServerStatusReq(SDnode *pDnode, SRpcMsg *pMsg);
-void dmProcessNettestReq(SDnode *pDnode, SRpcMsg *pMsg);
+void dmProcessNetTestReq(SDnode *pDnode, SRpcMsg *pMsg);
void dmGetMonitorSysInfo(SMonSysInfo *pInfo);
// dmFile.c
diff --git a/source/dnode/mgmt/interface/src/dmInt.c b/source/dnode/mgmt/interface/src/dmInt.c
index 2d15a7a008..f8e23ad262 100644
--- a/source/dnode/mgmt/interface/src/dmInt.c
+++ b/source/dnode/mgmt/interface/src/dmInt.c
@@ -171,16 +171,17 @@ static void dmGetServerStatus(SDnode *pDnode, SServerStatusRsp *pStatus) {
}
}
-void dmProcessNettestReq(SDnode *pDnode, SRpcMsg *pRpc) {
+void dmProcessNetTestReq(SDnode *pDnode, SRpcMsg *pReq) {
dDebug("net test req is received");
- SRpcMsg rsp = {.handle = pRpc->handle, .refId = pRpc->refId, .ahandle = pRpc->ahandle, .code = 0};
- rsp.pCont = rpcMallocCont(pRpc->contLen);
+ SRpcMsg rsp = {.handle = pReq->handle, .refId = pReq->refId, .ahandle = pReq->ahandle, .code = 0};
+ rsp.pCont = rpcMallocCont(pReq->contLen);
if (rsp.pCont == NULL) {
rsp.code = TSDB_CODE_OUT_OF_MEMORY;
} else {
- rsp.contLen = pRpc->contLen;
+ rsp.contLen = pReq->contLen;
}
rpcSendResponse(&rsp);
+ rpcFreeCont(pReq->pCont);
}
void dmProcessServerStatusReq(SDnode *pDnode, SRpcMsg *pReq) {
@@ -208,6 +209,7 @@ void dmProcessServerStatusReq(SDnode *pDnode, SRpcMsg *pReq) {
_OVER:
rpcSendResponse(&rspMsg);
+ rpcFreeCont(pReq->pCont);
}
void dmGetMonitorSysInfo(SMonSysInfo *pInfo) {
diff --git a/source/dnode/mgmt/mgmt_vnode/src/vmHandle.c b/source/dnode/mgmt/mgmt_vnode/src/vmHandle.c
index b19602f3ff..c5919e06b6 100644
--- a/source/dnode/mgmt/mgmt_vnode/src/vmHandle.c
+++ b/source/dnode/mgmt/mgmt_vnode/src/vmHandle.c
@@ -289,7 +289,6 @@ void vmInitMsgHandle(SMgmtWrapper *pWrapper) {
dmSetMsgHandle(pWrapper, TDMT_VND_QUERY, vmProcessQueryMsg, DEFAULT_HANDLE);
dmSetMsgHandle(pWrapper, TDMT_VND_QUERY_CONTINUE, vmProcessQueryMsg, DEFAULT_HANDLE);
dmSetMsgHandle(pWrapper, TDMT_VND_FETCH, vmProcessFetchMsg, DEFAULT_HANDLE);
- dmSetMsgHandle(pWrapper, TDMT_VND_FETCH_RSP, vmProcessFetchMsg, DEFAULT_HANDLE);
dmSetMsgHandle(pWrapper, TDMT_VND_ALTER_TABLE, vmProcessWriteMsg, DEFAULT_HANDLE);
dmSetMsgHandle(pWrapper, TDMT_VND_UPDATE_TAG_VAL, vmProcessWriteMsg, DEFAULT_HANDLE);
dmSetMsgHandle(pWrapper, TDMT_VND_TABLE_META, vmProcessFetchMsg, DEFAULT_HANDLE);
diff --git a/source/dnode/mnode/impl/src/mndQuery.c b/source/dnode/mnode/impl/src/mndQuery.c
index 7aa55e2109..36cde396fa 100644
--- a/source/dnode/mnode/impl/src/mndQuery.c
+++ b/source/dnode/mnode/impl/src/mndQuery.c
@@ -20,7 +20,7 @@
int32_t mndProcessQueryMsg(SNodeMsg *pReq) {
SMnode *pMnode = pReq->pNode;
- SReadHandle handle = {.mnd = pMnode};
+ SReadHandle handle = {.mnd = pMnode, .pMsgCb = &pMnode->msgCb};
mTrace("msg:%p, in query queue is processing", pReq);
switch (pReq->rpcMsg.msgType) {
diff --git a/source/dnode/qnode/src/qnode.c b/source/dnode/qnode/src/qnode.c
index b21141001a..54b29f546c 100644
--- a/source/dnode/qnode/src/qnode.c
+++ b/source/dnode/qnode/src/qnode.c
@@ -51,7 +51,7 @@ int32_t qndGetLoad(SQnode *pQnode, SQnodeLoad *pLoad) { return 0; }
int32_t qndProcessQueryMsg(SQnode *pQnode, SRpcMsg *pMsg) {
qTrace("message in qnode query queue is processing");
- SReadHandle handle = {0};
+ SReadHandle handle = {.pMsgCb = &pQnode->msgCb};
switch (pMsg->msgType) {
case TDMT_VND_QUERY: {
diff --git a/source/dnode/vnode/src/inc/vnodeInt.h b/source/dnode/vnode/src/inc/vnodeInt.h
index a7617291b0..986b2740f3 100644
--- a/source/dnode/vnode/src/inc/vnodeInt.h
+++ b/source/dnode/vnode/src/inc/vnodeInt.h
@@ -34,6 +34,7 @@
#include "tlockfree.h"
#include "tlosertree.h"
#include "tmallocator.h"
+#include "tmsgcb.h"
#include "tskiplist.h"
#include "tstream.h"
#include "ttime.h"
@@ -121,7 +122,7 @@ int32_t tqProcessPollReq(STQ* pTq, SRpcMsg* pMsg, int32_t workerId);
// sma
-int32_t tsdbRegisterRSma(STsdb* pTsdb, SMeta* pMeta, SVCreateStbReq* pReq);
+int32_t tsdbRegisterRSma(STsdb* pTsdb, SMeta* pMeta, SVCreateStbReq* pReq, SMsgCb* pMsgCb);
int32_t tsdbFetchTbUidList(STsdb* pTsdb, STbUidStore** ppStore, tb_uid_t suid, tb_uid_t uid);
int32_t tsdbUpdateTbUidList(STsdb* pTsdb, STbUidStore* pUidStore);
void tsdbUidStoreDestory(STbUidStore* pStore);
diff --git a/source/dnode/vnode/src/tq/tq.c b/source/dnode/vnode/src/tq/tq.c
index b8d6e84b1c..f607e0367e 100644
--- a/source/dnode/vnode/src/tq/tq.c
+++ b/source/dnode/vnode/src/tq/tq.c
@@ -378,6 +378,7 @@ int32_t tqDeserializeConsumer(STQ* pTq, const STqSerializedHead* pHead, STqConsu
SReadHandle handle = {
.reader = pReadHandle,
.meta = pTq->pVnode->pMeta,
+ .pMsgCb = &pTq->pVnode->msgCb,
};
pTopic->buffer.output[j].pReadHandle = pReadHandle;
pTopic->buffer.output[j].task = qCreateStreamExecTaskInfo(pTopic->qmsg, &handle);
@@ -857,6 +858,7 @@ int32_t tqProcessVgChangeReq(STQ* pTq, char* msg, int32_t msgLen) {
SReadHandle handle = {
.reader = pExec->pExecReader[i],
.meta = pTq->pVnode->pMeta,
+ .pMsgCb = &pTq->pVnode->msgCb,
};
pExec->task[i] = qCreateStreamExecTaskInfo(pExec->qmsg, &handle);
ASSERT(pExec->task[i]);
@@ -914,6 +916,7 @@ int32_t tqExpandTask(STQ* pTq, SStreamTask* pTask, int32_t parallel) {
SReadHandle handle = {
.reader = pStreamReader,
.meta = pTq->pVnode->pMeta,
+ .pMsgCb = &pTq->pVnode->msgCb,
};
pTask->exec.runners[i].inputHandle = pStreamReader;
pTask->exec.runners[i].executor = qCreateStreamExecTaskInfo(pTask->exec.qmsg, &handle);
diff --git a/source/dnode/vnode/src/tsdb/tsdbSma.c b/source/dnode/vnode/src/tsdb/tsdbSma.c
index 615018a9ea..32051c2de4 100644
--- a/source/dnode/vnode/src/tsdb/tsdbSma.c
+++ b/source/dnode/vnode/src/tsdb/tsdbSma.c
@@ -1698,7 +1698,7 @@ int32_t tsdbDropTSma(STsdb *pTsdb, char *pMsg) {
* @param pReq
* @return int32_t
*/
-int32_t tsdbRegisterRSma(STsdb *pTsdb, SMeta *pMeta, SVCreateStbReq *pReq) {
+int32_t tsdbRegisterRSma(STsdb *pTsdb, SMeta *pMeta, SVCreateStbReq *pReq, SMsgCb *pMsgCb) {
if (!pReq->rollup) {
tsdbDebug("vgId:%d return directly since no rollup for stable %s %" PRIi64, REPO_ID(pTsdb), pReq->name, pReq->suid);
return TSDB_CODE_SUCCESS;
@@ -1742,6 +1742,7 @@ int32_t tsdbRegisterRSma(STsdb *pTsdb, SMeta *pMeta, SVCreateStbReq *pReq) {
SReadHandle handle = {
.reader = pReadHandle,
.meta = pMeta,
+ .pMsgCb = pMsgCb,
};
if (param->qmsg1) {
diff --git a/source/dnode/vnode/src/vnd/vnodeSvr.c b/source/dnode/vnode/src/vnd/vnodeSvr.c
index ee6bdc1a59..c1e0a202a8 100644
--- a/source/dnode/vnode/src/vnd/vnodeSvr.c
+++ b/source/dnode/vnode/src/vnd/vnodeSvr.c
@@ -142,9 +142,9 @@ _err:
int vnodeProcessQueryMsg(SVnode *pVnode, SRpcMsg *pMsg) {
vTrace("message in vnode query queue is processing");
#if 0
- SReadHandle handle = {.reader = pVnode->pTsdb, .meta = pVnode->pMeta, .config = &pVnode->config, .vnode = pVnode};
+ SReadHandle handle = {.reader = pVnode->pTsdb, .meta = pVnode->pMeta, .config = &pVnode->config, .vnode = pVnode, .pMsgCb = &pVnode->msgCb};
#endif
- SReadHandle handle = {.meta = pVnode->pMeta, .config = &pVnode->config, .vnode = pVnode};
+ SReadHandle handle = {.meta = pVnode->pMeta, .config = &pVnode->config, .vnode = pVnode, .pMsgCb = &pVnode->msgCb};
switch (pMsg->msgType) {
case TDMT_VND_QUERY:
return qWorkerProcessQueryMsg(&handle, pVnode->pQuery, pMsg);
@@ -305,7 +305,7 @@ static int vnodeProcessCreateStbReq(SVnode *pVnode, int64_t version, void *pReq,
goto _err;
}
- tsdbRegisterRSma(pVnode->pTsdb, pVnode->pMeta, &req);
+ tsdbRegisterRSma(pVnode->pTsdb, pVnode->pMeta, &req, &pVnode->msgCb);
tDecoderClear(&coder);
return 0;
diff --git a/source/libs/executor/inc/executorimpl.h b/source/libs/executor/inc/executorimpl.h
index 5cfe796a29..98559f974d 100644
--- a/source/libs/executor/inc/executorimpl.h
+++ b/source/libs/executor/inc/executorimpl.h
@@ -392,10 +392,7 @@ typedef struct SStreamBlockScanInfo {
} SStreamBlockScanInfo;
typedef struct SSysTableScanInfo {
- union {
- void* pTransporter;
- SReadHandle readHandle;
- };
+ SReadHandle readHandle;
SRetrieveMetaTableRsp* pRsp;
SRetrieveTableReq req;
@@ -663,8 +660,6 @@ SResultRow* doSetResultOutBufByKey(SDiskbasedBuf* pResultBuf, SResultRowInfo* pR
char* pData, int16_t bytes, bool masterscan, uint64_t groupId,
SExecTaskInfo* pTaskInfo, bool isIntervalQuery, SAggSupporter* pSup);
-SOperatorInfo* createExchangeOperatorInfo(const SNodeList* pSources, SSDataBlock* pBlock, SExecTaskInfo* pTaskInfo);
-
SOperatorInfo* createTableScanOperatorInfo(void* pDataReader, SQueryTableDataCond* pCond, int32_t numOfOutput, int32_t dataLoadFlag, const uint8_t* scanInfo,
SArray* pColMatchInfo, SSDataBlock* pResBlock, SNode* pCondition, SInterval* pInterval, double sampleRatio, SExecTaskInfo* pTaskInfo);
diff --git a/source/libs/executor/src/executorimpl.c b/source/libs/executor/src/executorimpl.c
index 1327ddb48e..99cad87e5a 100644
--- a/source/libs/executor/src/executorimpl.c
+++ b/source/libs/executor/src/executorimpl.c
@@ -13,6 +13,7 @@
* along with this program. If not, see .
*/
+#include
#include "filter.h"
#include "function.h"
#include "functionMgt.h"
@@ -203,9 +204,9 @@ SSDataBlock* createResDataBlock(SDataBlockDescNode* pNode) {
for (int32_t i = 0; i < numOfCols; ++i) {
SColumnInfoData idata = {{0}};
SSlotDescNode* pDescNode = nodesListGetNode(pNode->pSlots, i);
-// if (!pDescNode->output) { // todo disable it temporarily
-// continue;
-// }
+ // if (!pDescNode->output) { // todo disable it temporarily
+ // continue;
+ // }
idata.info.type = pDescNode->dataType.type;
idata.info.bytes = pDescNode->dataType.bytes;
@@ -803,7 +804,8 @@ static void doAggregateImpl(SOperatorInfo* pOperator, TSKEY startTs, SqlFunction
for (int32_t k = 0; k < pOperator->numOfExprs; ++k) {
if (functionNeedToExecute(&pCtx[k])) {
pCtx[k].startTs = startTs; // this can be set during create the struct
- pCtx[k].fpSet.process(&pCtx[k]);
+ if (pCtx[k].fpSet.process != NULL)
+ pCtx[k].fpSet.process(&pCtx[k]);
}
}
}
@@ -833,7 +835,8 @@ int32_t projectApplyFunctions(SExprInfo* pExpr, SSDataBlock* pResult, SSDataBloc
if (pExpr[k].pExpr->nodeType == QUERY_NODE_COLUMN) { // it is a project query
SColumnInfoData* pColInfoData = taosArrayGet(pResult->pDataBlock, outputSlotId);
if (pResult->info.rows > 0 && !createNewColModel) {
- colDataMergeCol(pColInfoData, pResult->info.rows, &pResult->info.capacity, pfCtx->input.pData[0], pfCtx->input.numOfRows);
+ colDataMergeCol(pColInfoData, pResult->info.rows, &pResult->info.capacity, pfCtx->input.pData[0],
+ pfCtx->input.numOfRows);
} else {
colDataAssign(pColInfoData, pfCtx->input.pData[0], pfCtx->input.numOfRows);
}
@@ -1074,35 +1077,36 @@ void setBlockStatisInfo(SqlFunctionCtx* pCtx, SExprInfo* pExprInfo, SSDataBlock*
// set the output buffer for the selectivity + tag query
static int32_t setCtxTagColumnInfo(SqlFunctionCtx* pCtx, int32_t numOfOutput) {
int32_t num = 0;
- int16_t tagLen = 0;
SqlFunctionCtx* p = NULL;
- SqlFunctionCtx** pTagCtx = taosMemoryCalloc(numOfOutput, POINTER_BYTES);
- if (pTagCtx == NULL) {
+ SqlFunctionCtx** pValCtx = taosMemoryCalloc(numOfOutput, POINTER_BYTES);
+ if (pValCtx == NULL) {
return TSDB_CODE_QRY_OUT_OF_MEMORY;
}
for (int32_t i = 0; i < numOfOutput; ++i) {
- int32_t functionId = pCtx[i].functionId;
-
- if (functionId == FUNCTION_TAG_DUMMY || functionId == FUNCTION_TS_DUMMY) {
- tagLen += pCtx[i].resDataInfo.bytes;
- pTagCtx[num++] = &pCtx[i];
- } else if (1 /*(aAggs[functionId].status & FUNCSTATE_SELECTIVITY) != 0*/) {
- p = &pCtx[i];
- } else if (functionId == FUNCTION_TS || functionId == FUNCTION_TAG) {
- // tag function may be the group by tag column
- // ts may be the required primary timestamp column
- continue;
+ if (strcmp(pCtx[i].pExpr->pExpr->_function.functionName, "_select_value") == 0) {
+ pValCtx[num++] = &pCtx[i];
} else {
- // the column may be the normal column, group by normal_column, the functionId is FUNCTION_PRJ
+ p = &pCtx[i];
}
+// if (functionId == FUNCTION_TAG_DUMMY || functionId == FUNCTION_TS_DUMMY) {
+// tagLen += pCtx[i].resDataInfo.bytes;
+// pTagCtx[num++] = &pCtx[i];
+// } else if (functionId == FUNCTION_TS || functionId == FUNCTION_TAG) {
+// // tag function may be the group by tag column
+// // ts may be the required primary timestamp column
+// continue;
+// } else {
+// // the column may be the normal column, group by normal_column, the functionId is FUNCTION_PRJ
+// }
}
+
if (p != NULL) {
- p->subsidiaries.pCtx = pTagCtx;
+ p->subsidiaries.pCtx = pValCtx;
p->subsidiaries.num = num;
} else {
- taosMemoryFreeClear(pTagCtx);
+ taosMemoryFreeClear(pValCtx);
}
return TSDB_CODE_SUCCESS;
@@ -1873,7 +1877,7 @@ static void updateTableQueryInfoForReverseScan(STableQueryInfo* pTableQueryInfo)
}
void initResultRow(SResultRow* pResultRow) {
-// pResultRow->pEntryInfo = (struct SResultRowEntryInfo*)((char*)pResultRow + sizeof(SResultRow));
+ // pResultRow->pEntryInfo = (struct SResultRowEntryInfo*)((char*)pResultRow + sizeof(SResultRow));
}
/*
@@ -1885,7 +1889,8 @@ void initResultRow(SResultRow* pResultRow) {
* offset[0] offset[1] offset[2]
*/
// TODO refactor: some function move away
-void setFunctionResultOutput(SOptrBasicInfo* pInfo, SAggSupporter* pSup, int32_t stage, int32_t numOfExprs, SExecTaskInfo* pTaskInfo) {
+void setFunctionResultOutput(SOptrBasicInfo* pInfo, SAggSupporter* pSup, int32_t stage, int32_t numOfExprs,
+ SExecTaskInfo* pTaskInfo) {
SqlFunctionCtx* pCtx = pInfo->pCtx;
SSDataBlock* pDataBlock = pInfo->pRes;
int32_t* rowCellInfoOffset = pInfo->rowCellInfoOffset;
@@ -2219,6 +2224,8 @@ int32_t doCopyToSDataBlock(SSDataBlock* pBlock, SExprInfo* pExprInfo, SDiskbased
pCtx[j].resultInfo = getResultCell(pRow, j, rowCellOffset);
if (pCtx[j].fpSet.process) {
pCtx[j].fpSet.finalize(&pCtx[j], pBlock);
+ } else if (strcmp(pCtx[j].pExpr->pExpr->_function.functionName, "_select_value") == 0) {
+ // do nothing, todo refactor
} else {
SColumnInfoData* pColInfoData = taosArrayGet(pBlock->pDataBlock, slotId);
@@ -2240,12 +2247,13 @@ int32_t doCopyToSDataBlock(SSDataBlock* pBlock, SExprInfo* pExprInfo, SDiskbased
return 0;
}
-void doBuildResultDatablock(SOptrBasicInfo *pbInfo, SGroupResInfo* pGroupResInfo, SExprInfo* pExprInfo, SDiskbasedBuf* pBuf) {
+void doBuildResultDatablock(SOptrBasicInfo* pbInfo, SGroupResInfo* pGroupResInfo, SExprInfo* pExprInfo,
+ SDiskbasedBuf* pBuf) {
assert(pGroupResInfo->currentGroup <= pGroupResInfo->totalGroup);
- int32_t* rowCellOffset = pbInfo->rowCellInfoOffset;
- SSDataBlock* pBlock = pbInfo->pRes;
- SqlFunctionCtx* pCtx = pbInfo->pCtx;
+ int32_t* rowCellOffset = pbInfo->rowCellInfoOffset;
+ SSDataBlock* pBlock = pbInfo->pRes;
+ SqlFunctionCtx* pCtx = pbInfo->pCtx;
blockDataCleanup(pBlock);
if (!hasRemainDataInCurrentGroup(pGroupResInfo)) {
@@ -2419,7 +2427,8 @@ void queryCostStatis(SExecTaskInfo* pTaskInfo) {
SFileBlockLoadRecorder* pRecorder = pSummary->pRecoder;
if (pSummary->pRecoder != NULL) {
- qDebug("%s :cost summary: elapsed time:%" PRId64 " us, first merge:%" PRId64 " us, total blocks:%d, "
+ qDebug("%s :cost summary: elapsed time:%" PRId64 " us, first merge:%" PRId64
+ " us, total blocks:%d, "
"load block statis:%d, load data block:%d, total rows:%" PRId64 ", check rows:%" PRId64,
GET_TASKID(pTaskInfo), pSummary->elapsedTime, pSummary->firstStageMergeTime, pRecorder->totalBlocks,
pRecorder->loadBlockStatis, pRecorder->loadBlocks, pRecorder->totalRows, pRecorder->totalCheckedRows);
@@ -2954,7 +2963,7 @@ int32_t setSDataBlockFromFetchRsp(SSDataBlock* pRes, SLoadRemoteDataInfo* pLoadI
relocateColumnData(pRes, pColList, pBlock->pDataBlock);
taosArrayDestroy(pBlock->pDataBlock);
taosMemoryFree(pBlock);
-// blockDataDestroy(pBlock);
+ // blockDataDestroy(pBlock);
}
pRes->info.rows = numOfRows;
@@ -3259,7 +3268,8 @@ static int32_t initDataSource(int32_t numOfSources, SExchangeInfo* pInfo) {
return TSDB_CODE_SUCCESS;
}
-SOperatorInfo* createExchangeOperatorInfo(const SNodeList* pSources, SSDataBlock* pBlock, SExecTaskInfo* pTaskInfo) {
+SOperatorInfo* createExchangeOperatorInfo(void *pTransporter, const SNodeList* pSources, SSDataBlock* pBlock,
+ SExecTaskInfo* pTaskInfo) {
SExchangeInfo* pInfo = taosMemoryCalloc(1, sizeof(SExchangeInfo));
SOperatorInfo* pOperator = taosMemoryCalloc(1, sizeof(SOperatorInfo));
@@ -3302,29 +3312,7 @@ SOperatorInfo* createExchangeOperatorInfo(const SNodeList* pSources, SSDataBlock
pOperator->fpSet = createOperatorFpSet(prepareLoadRemoteData, doLoadRemoteData, NULL, NULL,
destroyExchangeOperatorInfo, NULL, NULL, NULL);
-
-#if 1
- { // todo refactor
- SRpcInit rpcInit;
- memset(&rpcInit, 0, sizeof(rpcInit));
- rpcInit.localPort = 0;
- rpcInit.label = "EX";
- rpcInit.numOfThreads = 1;
- rpcInit.cfp = qProcessFetchRsp;
- rpcInit.sessions = tsMaxConnections;
- rpcInit.connType = TAOS_CONN_CLIENT;
- rpcInit.user = (char*)"root";
- rpcInit.idleTime = tsShellActivityTimer * 1000;
- rpcInit.ckey = "key";
- rpcInit.spi = 1;
- rpcInit.secret = (char*)"dcc5bed04851fec854c035b2e40263b6";
-
- pInfo->pTransporter = rpcOpen(&rpcInit);
- if (pInfo->pTransporter == NULL) {
- return NULL; // todo
- }
- }
-#endif
+ pInfo->pTransporter = pTransporter;
return pOperator;
@@ -3974,6 +3962,7 @@ static SSDataBlock* doProjectOperation(SOperatorInfo* pOperator) {
SSDataBlock* pRes = pInfo->pRes;
blockDataCleanup(pRes);
+ SExecTaskInfo* pTaskInfo = pOperator->pTaskInfo;
if (pOperator->status == OP_EXEC_DONE) {
return NULL;
}
@@ -4037,9 +4026,13 @@ static SSDataBlock* doProjectOperation(SOperatorInfo* pOperator) {
setInputDataBlock(pOperator, pInfo->pCtx, pBlock, order, false);
blockDataEnsureCapacity(pInfo->pRes, pInfo->pRes->info.rows + pBlock->info.rows);
- projectApplyFunctions(pOperator->pExpr, pInfo->pRes, pBlock, pInfo->pCtx, pOperator->numOfExprs,
+ pTaskInfo->code = projectApplyFunctions(pOperator->pExpr, pInfo->pRes, pBlock, pInfo->pCtx, pOperator->numOfExprs,
pProjectInfo->pPseudoColInfo);
+ if (pTaskInfo->code != TSDB_CODE_SUCCESS) {
+ longjmp(pTaskInfo->env, pTaskInfo->code);
+ }
+
int32_t status = handleLimitOffset(pOperator, pBlock);
if (status == PROJECT_RETRIEVE_CONTINUE) {
continue;
@@ -4099,8 +4092,8 @@ static SSDataBlock* doFill(SOperatorInfo* pOperator) {
}
// todo handle different group data interpolation
- bool n = false;
- bool *newgroup = &n;
+ bool n = false;
+ bool* newgroup = &n;
doHandleRemainBlockFromNewGroup(pInfo, pResultInfo, newgroup, pTaskInfo);
if (pResBlock->info.rows > pResultInfo->threshold || (!pInfo->multigroupResult && pResBlock->info.rows > 0)) {
return pResBlock;
@@ -4224,7 +4217,7 @@ int32_t doInitAggInfoSup(SAggSupporter* pAggSup, SqlFunctionCtx* pCtx, int32_t n
}
uint32_t defaultPgsz = 4096;
- while(defaultPgsz < pAggSup->resultRowSize*4) {
+ while (defaultPgsz < pAggSup->resultRowSize * 4) {
defaultPgsz <<= 1u;
}
@@ -4375,7 +4368,7 @@ void destroyBasicOperatorInfo(void* param, int32_t numOfOutput) {
}
void destroyMergeJoinOperator(void* param, int32_t numOfOutput) {
- SJoinOperatorInfo* pJoinOperator = (SJoinOperatorInfo*) param;
+ SJoinOperatorInfo* pJoinOperator = (SJoinOperatorInfo*)param;
}
void destroyAggOperatorInfo(void* param, int32_t numOfOutput) {
@@ -4487,8 +4480,9 @@ static int32_t initFillInfo(SFillOperatorInfo* pInfo, SExprInfo* pExpr, int32_t
}
SOperatorInfo* createFillOperatorInfo(SOperatorInfo* downstream, SExprInfo* pExpr, int32_t numOfCols,
- SInterval* pInterval, STimeWindow* pWindow, SSDataBlock* pResBlock, int32_t fillType, SNodeListNode* pValueNode,
- bool multigroupResult, SExecTaskInfo* pTaskInfo) {
+ SInterval* pInterval, STimeWindow* pWindow, SSDataBlock* pResBlock,
+ int32_t fillType, SNodeListNode* pValueNode, bool multigroupResult,
+ SExecTaskInfo* pTaskInfo) {
SFillOperatorInfo* pInfo = taosMemoryCalloc(1, sizeof(SFillOperatorInfo));
SOperatorInfo* pOperator = taosMemoryCalloc(1, sizeof(SOperatorInfo));
@@ -4522,8 +4516,8 @@ SOperatorInfo* createFillOperatorInfo(SOperatorInfo* downstream, SExprInfo* pExp
SResultInfo* pResultInfo = &pOperator->resultInfo;
initResultSizeInfo(pOperator, 4096);
- int32_t code = initFillInfo(pInfo, pExpr, numOfCols, pValueNode, *pWindow, pResultInfo->capacity,
- pTaskInfo->id.str, pInterval, type);
+ int32_t code = initFillInfo(pInfo, pExpr, numOfCols, pValueNode, *pWindow, pResultInfo->capacity, pTaskInfo->id.str,
+ pInterval, type);
if (code != TSDB_CODE_SUCCESS) {
goto _error;
}
@@ -4736,7 +4730,8 @@ static int32_t doCreateTableGroup(void* metaHandle, int32_t tableType, uint64_t
uint64_t queryId, uint64_t taskId);
static SArray* extractTableIdList(const STableGroupInfo* pTableGroupInfo);
static SArray* extractColumnInfo(SNodeList* pNodeList);
-static SArray* extractColMatchInfo(SNodeList* pNodeList, SDataBlockDescNode* pOutputNodeList, int32_t* numOfOutputCols, int32_t type);
+static SArray* extractColMatchInfo(SNodeList* pNodeList, SDataBlockDescNode* pOutputNodeList, int32_t* numOfOutputCols,
+ int32_t type);
static SArray* createSortInfo(SNodeList* pNodeList);
static SArray* extractPartitionColInfo(SNodeList* pNodeList);
@@ -4776,33 +4771,34 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo
SSDataBlock* pResBlock = createResDataBlock(pDescNode);
SQueryTableDataCond cond = {0};
- int32_t code = initQueryTableDataCond(&cond, pTableScanNode);
+ int32_t code = initQueryTableDataCond(&cond, pTableScanNode);
if (code != TSDB_CODE_SUCCESS) {
return NULL;
}
- SInterval interval = extractIntervalInfo(pTableScanNode);
- SOperatorInfo* pOperator = createTableScanOperatorInfo(pDataReader, &cond, numOfCols, pTableScanNode->dataRequired,
- pTableScanNode->scanSeq, pColList, pResBlock, pScanPhyNode->node.pConditions,
- &interval, pTableScanNode->ratio, pTaskInfo);
+ SInterval interval = extractIntervalInfo(pTableScanNode);
+ SOperatorInfo* pOperator = createTableScanOperatorInfo(
+ pDataReader, &cond, numOfCols, pTableScanNode->dataRequired, pTableScanNode->scanSeq, pColList, pResBlock,
+ pScanPhyNode->node.pConditions, &interval, pTableScanNode->ratio, pTaskInfo);
STableScanInfo* pScanInfo = pOperator->info;
pTaskInfo->cost.pRecoder = &pScanInfo->readRecorder;
return pOperator;
} else if (QUERY_NODE_PHYSICAL_PLAN_EXCHANGE == type) {
SExchangePhysiNode* pExchange = (SExchangePhysiNode*)pPhyNode;
SSDataBlock* pResBlock = createResDataBlock(pExchange->node.pOutputDataBlockDesc);
- return createExchangeOperatorInfo(pExchange->pSrcEndPoints, pResBlock, pTaskInfo);
+ return createExchangeOperatorInfo(pHandle->pMsgCb->clientRpc, pExchange->pSrcEndPoints, pResBlock, pTaskInfo);
} else if (QUERY_NODE_PHYSICAL_PLAN_STREAM_SCAN == type) {
SScanPhysiNode* pScanPhyNode = (SScanPhysiNode*)pPhyNode; // simple child table.
- int32_t code = doCreateTableGroup(pHandle->meta, pScanPhyNode->tableType, pScanPhyNode->uid, pTableGroupInfo, queryId, taskId);
+ int32_t code = doCreateTableGroup(pHandle->meta, pScanPhyNode->tableType, pScanPhyNode->uid, pTableGroupInfo,
+ queryId, taskId);
SArray* tableIdList = extractTableIdList(pTableGroupInfo);
SDataBlockDescNode* pDescNode = pScanPhyNode->node.pOutputDataBlockDesc;
- SSDataBlock* pResBlock = createResDataBlock(pDescNode);
+ SSDataBlock* pResBlock = createResDataBlock(pDescNode);
- int32_t numOfCols = 0;
- SArray* pCols = extractColMatchInfo(pScanPhyNode->pScanCols, pDescNode, &numOfCols, COL_MATCH_FROM_COL_ID);
+ int32_t numOfCols = 0;
+ SArray* pCols = extractColMatchInfo(pScanPhyNode->pScanCols, pDescNode, &numOfCols, COL_MATCH_FROM_COL_ID);
SOperatorInfo* pOperator = createStreamScanOperatorInfo(pHandle->reader, pResBlock, pCols, tableIdList, pTaskInfo,
pScanPhyNode->node.pConditions);
taosArrayDestroy(tableIdList);
@@ -4822,25 +4818,27 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo
pTaskInfo, pSysScanPhyNode->showRewrite, pSysScanPhyNode->accountId);
return pOperator;
} else if (QUERY_NODE_PHYSICAL_PLAN_TAG_SCAN == type) {
- STagScanPhysiNode* pScanPhyNode = (STagScanPhysiNode*) pPhyNode;
+ STagScanPhysiNode* pScanPhyNode = (STagScanPhysiNode*)pPhyNode;
SDataBlockDescNode* pDescNode = pScanPhyNode->node.pOutputDataBlockDesc;
SSDataBlock* pResBlock = createResDataBlock(pDescNode);
- int32_t code =
- doCreateTableGroup(pHandle->meta, pScanPhyNode->tableType, pScanPhyNode->uid, pTableGroupInfo, queryId, taskId);
+ int32_t code = doCreateTableGroup(pHandle->meta, pScanPhyNode->tableType, pScanPhyNode->uid, pTableGroupInfo,
+ queryId, taskId);
if (code != TSDB_CODE_SUCCESS) {
return NULL;
}
- int32_t num = 0;
+ int32_t num = 0;
SExprInfo* pExprInfo = createExprInfo(pScanPhyNode->pScanPseudoCols, NULL, &num);
int32_t numOfOutputCols = 0;
- SArray* colList = extractColMatchInfo(pScanPhyNode->pScanPseudoCols, pDescNode, &numOfOutputCols, COL_MATCH_FROM_COL_ID);
+ SArray* colList =
+ extractColMatchInfo(pScanPhyNode->pScanPseudoCols, pDescNode, &numOfOutputCols, COL_MATCH_FROM_COL_ID);
- SOperatorInfo* pOperator = createTagScanOperatorInfo(pHandle, pExprInfo, num, pResBlock, colList, pTableGroupInfo, pTaskInfo);
+ SOperatorInfo* pOperator =
+ createTagScanOperatorInfo(pHandle, pExprInfo, num, pResBlock, colList, pTableGroupInfo, pTaskInfo);
return pOperator;
} else {
ASSERT(0);
@@ -4887,7 +4885,7 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo
pOptr = createAggregateOperatorInfo(ops[0], pExprInfo, num, pResBlock, pScalarExprInfo, numOfScalarExpr,
pTaskInfo, pTableGroupInfo);
}
- } else if (QUERY_NODE_PHYSICAL_PLAN_INTERVAL == type) {
+ } else if (QUERY_NODE_PHYSICAL_PLAN_INTERVAL == type || QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL == type) {
SIntervalPhysiNode* pIntervalPhyNode = (SIntervalPhysiNode*)pPhyNode;
SExprInfo* pExprInfo = createExprInfo(pIntervalPhyNode->window.pFuncs, NULL, &num);
@@ -4925,13 +4923,15 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo
} else if (QUERY_NODE_PHYSICAL_PLAN_SESSION_WINDOW == type) {
SSessionWinodwPhysiNode* pSessionNode = (SSessionWinodwPhysiNode*)pPhyNode;
- STimeWindowAggSupp as = {.waterMark = pSessionNode->window.watermark, .calTrigger = pSessionNode->window.triggerType};
+ STimeWindowAggSupp as = {.waterMark = pSessionNode->window.watermark,
+ .calTrigger = pSessionNode->window.triggerType};
SExprInfo* pExprInfo = createExprInfo(pSessionNode->window.pFuncs, NULL, &num);
SSDataBlock* pResBlock = createResDataBlock(pPhyNode->pOutputDataBlockDesc);
int32_t tsSlotId = ((SColumnNode*)pSessionNode->window.pTspk)->slotId;
- pOptr = createSessionAggOperatorInfo(ops[0], pExprInfo, num, pResBlock, pSessionNode->gap, tsSlotId, &as, pTaskInfo);
+ pOptr =
+ createSessionAggOperatorInfo(ops[0], pExprInfo, num, pResBlock, pSessionNode->gap, tsSlotId, &as, pTaskInfo);
} else if (QUERY_NODE_PHYSICAL_PLAN_PARTITION == type) {
SPartitionPhysiNode* pPartNode = (SPartitionPhysiNode*)pPhyNode;
SArray* pColList = extractPartitionColInfo(pPartNode->pPartitionKeys);
@@ -4957,11 +4957,12 @@ SOperatorInfo* createOperatorTree(SPhysiNode* pPhyNode, SExecTaskInfo* pTaskInfo
pOptr = createMergeJoinOperatorInfo(ops, size, pExprInfo, num, pResBlock, pJoinNode->pOnConditions, pTaskInfo);
} else if (QUERY_NODE_PHYSICAL_PLAN_FILL == type) {
SFillPhysiNode* pFillNode = (SFillPhysiNode*)pPhyNode;
- SSDataBlock* pResBlock = createResDataBlock(pPhyNode->pOutputDataBlockDesc);
- SExprInfo* pExprInfo = createExprInfo(pFillNode->pTargets, NULL, &num);
+ SSDataBlock* pResBlock = createResDataBlock(pPhyNode->pOutputDataBlockDesc);
+ SExprInfo* pExprInfo = createExprInfo(pFillNode->pTargets, NULL, &num);
SInterval* pInterval = &((SIntervalAggOperatorInfo*)ops[0]->info)->interval;
- pOptr = createFillOperatorInfo(ops[0], pExprInfo, num, pInterval, &pFillNode->timeRange, pResBlock, pFillNode->mode, (SNodeListNode*)pFillNode->pValues, false, pTaskInfo);
+ pOptr = createFillOperatorInfo(ops[0], pExprInfo, num, pInterval, &pFillNode->timeRange, pResBlock, pFillNode->mode,
+ (SNodeListNode*)pFillNode->pValues, false, pTaskInfo);
} else {
ASSERT(0);
}
@@ -5101,7 +5102,8 @@ SArray* createSortInfo(SNodeList* pNodeList) {
return pList;
}
-SArray* extractColMatchInfo(SNodeList* pNodeList, SDataBlockDescNode* pOutputNodeList, int32_t* numOfOutputCols, int32_t type) {
+SArray* extractColMatchInfo(SNodeList* pNodeList, SDataBlockDescNode* pOutputNodeList, int32_t* numOfOutputCols,
+ int32_t type) {
size_t numOfCols = LIST_LENGTH(pNodeList);
SArray* pList = taosArrayInit(numOfCols, sizeof(SColMatchInfo));
if (pList == NULL) {
@@ -5114,10 +5116,10 @@ SArray* extractColMatchInfo(SNodeList* pNodeList, SDataBlockDescNode* pOutputNod
SColumnNode* pColNode = (SColumnNode*)pNode->pExpr;
SColMatchInfo c = {0};
- c.output = true;
- c.colId = pColNode->colId;
- c.srcSlotId = pColNode->slotId;
- c.matchType = type;
+ c.output = true;
+ c.colId = pColNode->colId;
+ c.srcSlotId = pColNode->slotId;
+ c.matchType = type;
c.targetSlotId = pNode->slotId;
taosArrayPush(pList, &c);
}
@@ -5527,8 +5529,8 @@ static SSDataBlock* doMergeJoin(struct SOperatorInfo* pOperator) {
}
SOperatorInfo* createMergeJoinOperatorInfo(SOperatorInfo** pDownstream, int32_t numOfDownstream, SExprInfo* pExprInfo,
- int32_t numOfCols, SSDataBlock* pResBlock, SNode* pOnCondition,
- SExecTaskInfo* pTaskInfo) {
+ int32_t numOfCols, SSDataBlock* pResBlock, SNode* pOnCondition,
+ SExecTaskInfo* pTaskInfo) {
SJoinOperatorInfo* pInfo = taosMemoryCalloc(1, sizeof(SJoinOperatorInfo));
SOperatorInfo* pOperator = taosMemoryCalloc(1, sizeof(SOperatorInfo));
if (pOperator == NULL || pInfo == NULL) {
@@ -5537,14 +5539,14 @@ SOperatorInfo* createMergeJoinOperatorInfo(SOperatorInfo** pDownstream, int32_t
initResultSizeInfo(pOperator, 4096);
- pInfo->pRes = pResBlock;
- pOperator->name = "MergeJoinOperator";
+ pInfo->pRes = pResBlock;
+ pOperator->name = "MergeJoinOperator";
pOperator->operatorType = QUERY_NODE_PHYSICAL_PLAN_JOIN;
- pOperator->blocking = false;
- pOperator->status = OP_NOT_OPENED;
- pOperator->pExpr = pExprInfo;
+ pOperator->blocking = false;
+ pOperator->status = OP_NOT_OPENED;
+ pOperator->pExpr = pExprInfo;
pOperator->numOfExprs = numOfCols;
- pOperator->info = pInfo;
+ pOperator->info = pInfo;
pOperator->pTaskInfo = pTaskInfo;
SOperatorNode* pNode = (SOperatorNode*)pOnCondition;
@@ -5568,9 +5570,9 @@ _error:
}
void setJoinColumnInfo(SColumnInfo* pColumn, const SColumnNode* pColumnNode) {
- pColumn->slotId = pColumnNode->slotId;
- pColumn->type = pColumnNode->node.resType.type;
- pColumn->bytes = pColumnNode->node.resType.bytes;
+ pColumn->slotId = pColumnNode->slotId;
+ pColumn->type = pColumnNode->node.resType.type;
+ pColumn->bytes = pColumnNode->node.resType.bytes;
pColumn->precision = pColumnNode->node.resType.precision;
- pColumn->scale = pColumnNode->node.resType.scale;
+ pColumn->scale = pColumnNode->node.resType.scale;
}
diff --git a/source/libs/executor/src/groupoperator.c b/source/libs/executor/src/groupoperator.c
index 183cb9dbe6..2ba3e257b2 100644
--- a/source/libs/executor/src/groupoperator.c
+++ b/source/libs/executor/src/groupoperator.c
@@ -262,6 +262,8 @@ static SSDataBlock* hashGroupbyAggregate(SOperatorInfo* pOperator) {
return NULL;
}
+ SExecTaskInfo* pTaskInfo = pOperator->pTaskInfo;
+
SGroupbyOperatorInfo* pInfo = pOperator->info;
SSDataBlock* pRes = pInfo->binfo.pRes;
@@ -289,7 +291,10 @@ static SSDataBlock* hashGroupbyAggregate(SOperatorInfo* pOperator) {
// there is an scalar expression that needs to be calculated right before apply the group aggregation.
if (pInfo->pScalarExprInfo != NULL) {
- projectApplyFunctions(pInfo->pScalarExprInfo, pBlock, pBlock, pInfo->pScalarFuncCtx, pInfo->numOfScalarExpr, NULL);
+ pTaskInfo->code = projectApplyFunctions(pInfo->pScalarExprInfo, pBlock, pBlock, pInfo->pScalarFuncCtx, pInfo->numOfScalarExpr, NULL);
+ if (pTaskInfo->code != TSDB_CODE_SUCCESS) {
+ longjmp(pTaskInfo->env, pTaskInfo->code);
+ }
}
// setTagValue(pOperator, pRuntimeEnv->current->pTable, pInfo->binfo.pCtx, pOperator->numOfExprs);
diff --git a/source/libs/executor/src/scanoperator.c b/source/libs/executor/src/scanoperator.c
index c1aee5ba35..eaacb561d5 100644
--- a/source/libs/executor/src/scanoperator.c
+++ b/source/libs/executor/src/scanoperator.c
@@ -1057,7 +1057,8 @@ static SSDataBlock* doSysTableScan(SOperatorInfo* pOperator) {
pMsgSendInfo->fp = loadSysTableCallback;
int64_t transporterId = 0;
- int32_t code = asyncSendMsgToServer(pInfo->pTransporter, &pInfo->epSet, &transporterId, pMsgSendInfo);
+ int32_t code =
+ asyncSendMsgToServer(pInfo->readHandle.pMsgCb->clientRpc, &pInfo->epSet, &transporterId, pMsgSendInfo);
tsem_wait(&pInfo->ready);
if (pTaskInfo->code) {
@@ -1182,29 +1183,7 @@ SOperatorInfo* createSysTableScanOperatorInfo(void* readHandle, SSDataBlock* pRe
} else {
tsem_init(&pInfo->ready, 0, 0);
pInfo->epSet = epset;
-
-#if 1
- { // todo refactor
- SRpcInit rpcInit;
- memset(&rpcInit, 0, sizeof(rpcInit));
- rpcInit.localPort = 0;
- rpcInit.label = "DB-META";
- rpcInit.numOfThreads = 1;
- rpcInit.cfp = qProcessFetchRsp;
- rpcInit.sessions = tsMaxConnections;
- rpcInit.connType = TAOS_CONN_CLIENT;
- rpcInit.user = (char*)"root";
- rpcInit.idleTime = tsShellActivityTimer * 1000;
- rpcInit.ckey = "key";
- rpcInit.spi = 1;
- rpcInit.secret = (char*)"dcc5bed04851fec854c035b2e40263b6";
-
- pInfo->pTransporter = rpcOpen(&rpcInit);
- if (pInfo->pTransporter == NULL) {
- return NULL; // todo
- }
- }
-#endif
+ pInfo->readHandle = *(SReadHandle*)readHandle;
}
pOperator->name = "SysTableScanOperator";
diff --git a/source/libs/executor/src/sortoperator.c b/source/libs/executor/src/sortoperator.c
index a654876513..990dc0f200 100644
--- a/source/libs/executor/src/sortoperator.c
+++ b/source/libs/executor/src/sortoperator.c
@@ -114,7 +114,10 @@ void applyScalarFunction(SSDataBlock* pBlock, void* param) {
SOperatorInfo* pOperator = param;
SSortOperatorInfo* pSort = pOperator->info;
if (pOperator->pExpr != NULL) {
- projectApplyFunctions(pOperator->pExpr, pBlock, pBlock, pSort->binfo.pCtx, pOperator->numOfExprs, NULL);
+ int32_t code = projectApplyFunctions(pOperator->pExpr, pBlock, pBlock, pSort->binfo.pCtx, pOperator->numOfExprs, NULL);
+ if (code != TSDB_CODE_SUCCESS) {
+ longjmp(pOperator->pTaskInfo->env, code);
+ }
}
}
diff --git a/source/libs/function/inc/builtinsimpl.h b/source/libs/function/inc/builtinsimpl.h
index 1f2ad0797d..ce2f0b0651 100644
--- a/source/libs/function/inc/builtinsimpl.h
+++ b/source/libs/function/inc/builtinsimpl.h
@@ -37,11 +37,11 @@ bool getSumFuncEnv(struct SFunctionNode* pFunc, SFuncExecEnv* pEnv);
int32_t sumFunction(SqlFunctionCtx *pCtx);
int32_t sumInvertFunction(SqlFunctionCtx *pCtx);
-bool minFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo);
-bool maxFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo);
+bool minmaxFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo);
bool getMinmaxFuncEnv(struct SFunctionNode* pFunc, SFuncExecEnv* pEnv);
int32_t minFunction(SqlFunctionCtx* pCtx);
int32_t maxFunction(SqlFunctionCtx *pCtx);
+int32_t minmaxFunctionFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock);
bool getAvgFuncEnv(struct SFunctionNode* pFunc, SFuncExecEnv* pEnv);
bool avgFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultInfo);
@@ -70,6 +70,7 @@ int32_t lastFunction(SqlFunctionCtx *pCtx);
bool getTopBotFuncEnv(SFunctionNode* UNUSED_PARAM(pFunc), SFuncExecEnv* pEnv);
int32_t topFunction(SqlFunctionCtx *pCtx);
+int32_t bottomFunction(SqlFunctionCtx *pCtx);
int32_t topBotFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock);
bool getSpreadFuncEnv(struct SFunctionNode* pFunc, SFuncExecEnv* pEnv);
@@ -82,6 +83,8 @@ bool histogramFunctionSetup(SqlFunctionCtx *pCtx, SResultRowEntryInfo* pResultIn
int32_t histogramFunction(SqlFunctionCtx* pCtx);
int32_t histogramFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock);
+bool getSelectivityFuncEnv(SFunctionNode* pFunc, SFuncExecEnv* pEnv);
+
#ifdef __cplusplus
}
#endif
diff --git a/source/libs/function/inc/functionMgtInt.h b/source/libs/function/inc/functionMgtInt.h
index 3869a5d7b2..4d45eb91ce 100644
--- a/source/libs/function/inc/functionMgtInt.h
+++ b/source/libs/function/inc/functionMgtInt.h
@@ -40,6 +40,7 @@ extern "C" {
#define FUNC_MGT_MULTI_RES_FUNC FUNC_MGT_FUNC_CLASSIFICATION_MASK(11)
#define FUNC_MGT_SCAN_PC_FUNC FUNC_MGT_FUNC_CLASSIFICATION_MASK(12)
#define FUNC_MGT_SELECT_FUNC FUNC_MGT_FUNC_CLASSIFICATION_MASK(13)
+#define FUNC_MGT_REPEAT_SCAN_FUNC FUNC_MGT_FUNC_CLASSIFICATION_MASK(14)
#define FUNC_MGT_TEST_MASK(val, mask) (((val) & (mask)) != 0)
diff --git a/source/libs/function/src/builtins.c b/source/libs/function/src/builtins.c
index 5aa1b63c79..b7bd023581 100644
--- a/source/libs/function/src/builtins.c
+++ b/source/libs/function/src/builtins.c
@@ -207,7 +207,8 @@ static int32_t translateTop(SFunctionNode* pFunc, char* pErrBuf, int32_t len) {
}
static int32_t translateBottom(SFunctionNode* pFunc, char* pErrBuf, int32_t len) {
- // todo
+ SDataType* pType = &((SExprNode*)nodesListGetNode(pFunc->pParameterList, 0))->resType;
+ pFunc->node.resType = (SDataType){.bytes = pType->bytes, .type = pType->type};
return TSDB_CODE_SUCCESS;
}
@@ -241,7 +242,7 @@ static int32_t translateHistogram(SFunctionNode* pFunc, char* pErrBuf, int32_t l
return invaildFuncParaTypeErrMsg(pErrBuf, len, pFunc->functionName);
}
- pFunc->node.resType = (SDataType) { .bytes = 512, .type = TSDB_DATA_TYPE_BINARY };
+ pFunc->node.resType = (SDataType){.bytes = 512, .type = TSDB_DATA_TYPE_BINARY};
return TSDB_CODE_SUCCESS;
}
@@ -273,7 +274,8 @@ static int32_t translateDiff(SFunctionNode* pFunc, char* pErrBuf, int32_t len) {
}
SExprNode* p1 = (SExprNode*)nodesListGetNode(pFunc->pParameterList, 0);
- if (!IS_NUMERIC_TYPE(p1->resType.type)) {
+ if (!IS_SIGNED_NUMERIC_TYPE(p1->resType.type) && !IS_FLOAT_TYPE(p1->resType.type) &&
+ TSDB_DATA_TYPE_BOOL != p1->resType.type) {
return invaildFuncParaTypeErrMsg(pErrBuf, len, pFunc->functionName);
}
pFunc->node.resType = p1->resType;
@@ -509,9 +511,9 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
.translateFunc = translateInOutNum,
.dataRequiredFunc = statisDataRequired,
.getEnvFunc = getMinmaxFuncEnv,
- .initFunc = minFunctionSetup,
+ .initFunc = minmaxFunctionSetup,
.processFunc = minFunction,
- .finalizeFunc = functionFinalize
+ .finalizeFunc = minmaxFunctionFinalize
},
{
.name = "max",
@@ -520,9 +522,9 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
.translateFunc = translateInOutNum,
.dataRequiredFunc = statisDataRequired,
.getEnvFunc = getMinmaxFuncEnv,
- .initFunc = maxFunctionSetup,
+ .initFunc = minmaxFunctionSetup,
.processFunc = maxFunction,
- .finalizeFunc = functionFinalize
+ .finalizeFunc = minmaxFunctionFinalize
},
{
.name = "stddev",
@@ -549,7 +551,7 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
{
.name = "percentile",
.type = FUNCTION_TYPE_PERCENTILE,
- .classification = FUNC_MGT_AGG_FUNC,
+ .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_REPEAT_SCAN_FUNC,
.translateFunc = translatePercentile,
.getEnvFunc = getPercentileFuncEnv,
.initFunc = percentileFunctionSetup,
@@ -562,14 +564,14 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
.classification = FUNC_MGT_AGG_FUNC,
.translateFunc = translateApercentile,
.getEnvFunc = getMinmaxFuncEnv,
- .initFunc = maxFunctionSetup,
+ .initFunc = minmaxFunctionSetup,
.processFunc = maxFunction,
.finalizeFunc = functionFinalize
},
{
.name = "top",
.type = FUNCTION_TYPE_TOP,
- .classification = FUNC_MGT_AGG_FUNC,
+ .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC,
.translateFunc = translateTop,
.getEnvFunc = getTopBotFuncEnv,
.initFunc = functionSetup,
@@ -579,12 +581,12 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
{
.name = "bottom",
.type = FUNCTION_TYPE_BOTTOM,
- .classification = FUNC_MGT_AGG_FUNC,
+ .classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC,
.translateFunc = translateBottom,
- .getEnvFunc = getMinmaxFuncEnv,
- .initFunc = maxFunctionSetup,
- .processFunc = maxFunction,
- .finalizeFunc = functionFinalize
+ .getEnvFunc = getTopBotFuncEnv,
+ .initFunc = functionSetup,
+ .processFunc = bottomFunction,
+ .finalizeFunc = topBotFinalize
},
{
.name = "spread",
@@ -603,7 +605,7 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
.classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_MULTI_RES_FUNC,
.translateFunc = translateLastRow,
.getEnvFunc = getMinmaxFuncEnv,
- .initFunc = maxFunctionSetup,
+ .initFunc = minmaxFunctionSetup,
.processFunc = maxFunction,
.finalizeFunc = functionFinalize
},
@@ -1032,8 +1034,8 @@ const SBuiltinFuncDefinition funcMgtBuiltins[] = {
.type = FUNCTION_TYPE_SELECT_VALUE,
.classification = FUNC_MGT_AGG_FUNC | FUNC_MGT_SELECT_FUNC,
.translateFunc = translateSelectValue,
- .getEnvFunc = NULL,
- .initFunc = NULL,
+ .getEnvFunc = getSelectivityFuncEnv, // todo remove this function later.
+ .initFunc = functionSetup,
.sprocessFunc = NULL,
.finalizeFunc = NULL
}
diff --git a/source/libs/function/src/builtinsimpl.c b/source/libs/function/src/builtinsimpl.c
index 9c1601b61a..1cb47a0bf1 100644
--- a/source/libs/function/src/builtinsimpl.c
+++ b/source/libs/function/src/builtinsimpl.c
@@ -37,13 +37,15 @@ typedef struct SAvgRes {
int64_t count;
} SAvgRes;
+typedef struct STuplePos {
+ int32_t pageId;
+ int32_t offset;
+} STuplePos;
+
typedef struct STopBotResItem {
- SVariant v;
- uint64_t uid; // it is a table uid, used to extract tag data during building of the final result for the tag data
- struct {
- int32_t pageId;
- int32_t offset;
- } tuplePos; // tuple data of this chosen row
+ SVariant v;
+ uint64_t uid; // it is a table uid, used to extract tag data during building of the final result for the tag data
+ STuplePos tuplePos; // tuple data of this chosen row
} STopBotResItem;
typedef struct STopBotRes {
@@ -616,101 +618,25 @@ EFuncDataRequired statisDataRequired(SFunctionNode* pFunc, STimeWindow* pTimeWin
return FUNC_DATA_REQUIRED_STATIS_LOAD;
}
-bool maxFunctionSetup(SqlFunctionCtx* pCtx, SResultRowEntryInfo* pResultInfo) {
- if (!functionSetup(pCtx, pResultInfo)) {
- return false;
- }
+typedef struct SMinmaxResInfo {
+ bool assign; // assign the first value or not
+ int64_t v;
+ STuplePos tuplePos;
+} SMinmaxResInfo;
- char* buf = GET_ROWCELL_INTERBUF(pResultInfo);
- switch (pCtx->resDataInfo.type) {
- case TSDB_DATA_TYPE_INT:
- *((int32_t*)buf) = INT32_MIN;
- break;
- case TSDB_DATA_TYPE_UINT:
- *((uint32_t*)buf) = 0;
- break;
- case TSDB_DATA_TYPE_FLOAT:
- *((float*)buf) = -FLT_MAX;
- break;
- case TSDB_DATA_TYPE_DOUBLE:
- SET_DOUBLE_VAL(((double*)buf), -DBL_MAX);
- break;
- case TSDB_DATA_TYPE_BIGINT:
- *((int64_t*)buf) = INT64_MIN;
- break;
- case TSDB_DATA_TYPE_UBIGINT:
- *((uint64_t*)buf) = 0;
- break;
- case TSDB_DATA_TYPE_SMALLINT:
- *((int16_t*)buf) = INT16_MIN;
- break;
- case TSDB_DATA_TYPE_USMALLINT:
- *((uint16_t*)buf) = 0;
- break;
- case TSDB_DATA_TYPE_TINYINT:
- *((int8_t*)buf) = INT8_MIN;
- break;
- case TSDB_DATA_TYPE_UTINYINT:
- *((uint8_t*)buf) = 0;
- break;
- case TSDB_DATA_TYPE_BOOL:
- *((int8_t*)buf) = 0;
- break;
- default:
- assert(0);
- }
- return true;
-}
-
-bool minFunctionSetup(SqlFunctionCtx* pCtx, SResultRowEntryInfo* pResultInfo) {
+bool minmaxFunctionSetup(SqlFunctionCtx* pCtx, SResultRowEntryInfo* pResultInfo) {
if (!functionSetup(pCtx, pResultInfo)) {
return false; // not initialized since it has been initialized
}
- char* buf = GET_ROWCELL_INTERBUF(pResultInfo);
- switch (pCtx->resDataInfo.type) {
- case TSDB_DATA_TYPE_TINYINT:
- *((int8_t*)buf) = INT8_MAX;
- break;
- case TSDB_DATA_TYPE_UTINYINT:
- *(uint8_t*)buf = UINT8_MAX;
- break;
- case TSDB_DATA_TYPE_SMALLINT:
- *((int16_t*)buf) = INT16_MAX;
- break;
- case TSDB_DATA_TYPE_USMALLINT:
- *((uint16_t*)buf) = UINT16_MAX;
- break;
- case TSDB_DATA_TYPE_INT:
- *((int32_t*)buf) = INT32_MAX;
- break;
- case TSDB_DATA_TYPE_UINT:
- *((uint32_t*)buf) = UINT32_MAX;
- break;
- case TSDB_DATA_TYPE_BIGINT:
- *((int64_t*)buf) = INT64_MAX;
- break;
- case TSDB_DATA_TYPE_UBIGINT:
- *((uint64_t*)buf) = UINT64_MAX;
- break;
- case TSDB_DATA_TYPE_FLOAT:
- *((float*)buf) = FLT_MAX;
- break;
- case TSDB_DATA_TYPE_DOUBLE:
- SET_DOUBLE_VAL(((double*)buf), DBL_MAX);
- break;
- case TSDB_DATA_TYPE_BOOL:
- *((int8_t*)buf) = 1;
- break;
- default:
- assert(0);
- }
-
+ SMinmaxResInfo* buf = GET_ROWCELL_INTERBUF(pResultInfo);
+ buf->assign = false;
+ buf->tuplePos.pageId = -1;
return true;
}
bool getMinmaxFuncEnv(SFunctionNode* UNUSED_PARAM(pFunc), SFuncExecEnv* pEnv) {
- pEnv->calcMemSize = sizeof(int64_t);
+ pEnv->calcMemSize = sizeof(SMinmaxResInfo);
return true;
}
@@ -758,6 +684,9 @@ bool getMinmaxFuncEnv(SFunctionNode* UNUSED_PARAM(pFunc), SFuncExecEnv* pEnv) {
} \
} while (0)
+static void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STuplePos* pPos);
+static void copyTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STuplePos* pPos);
+
int32_t doMinMaxHelper(SqlFunctionCtx* pCtx, int32_t isMinFunc) {
int32_t numOfElems = 0;
@@ -768,13 +697,12 @@ int32_t doMinMaxHelper(SqlFunctionCtx* pCtx, int32_t isMinFunc) {
int32_t type = pCol->info.type;
SResultRowEntryInfo* pResInfo = GET_RES_INFO(pCtx);
- char* buf = GET_ROWCELL_INTERBUF(pResInfo);
+ SMinmaxResInfo *pBuf = GET_ROWCELL_INTERBUF(pResInfo);
// data in current data block are qualified to the query
if (pInput->colDataAggIsSet) {
numOfElems = pInput->numOfRows - pAgg->numOfNull;
ASSERT(pInput->numOfRows == pInput->totalRows && numOfElems >= 0);
-
if (numOfElems == 0) {
return numOfElems;
}
@@ -793,48 +721,82 @@ int32_t doMinMaxHelper(SqlFunctionCtx* pCtx, int32_t isMinFunc) {
// the index is the original position, not the relative position
TSKEY key = (pCtx->ptsList != NULL) ? pCtx->ptsList[index] : TSKEY_INITIAL_VAL;
- if (IS_SIGNED_NUMERIC_TYPE(type)) {
- int64_t prev = 0;
- GET_TYPED_DATA(prev, int64_t, type, buf);
+ if (!pBuf->assign) {
+ pBuf->v = *(int64_t*)tval;
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, index, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ } else {
+ if (IS_SIGNED_NUMERIC_TYPE(type)) {
+ int64_t prev = 0;
+ GET_TYPED_DATA(prev, int64_t, type, &pBuf->v);
- int64_t val = GET_INT64_VAL(tval);
- if ((prev < val) ^ isMinFunc) {
- *(int64_t*)buf = val;
- for (int32_t i = 0; i < (pCtx)->subsidiaries.num; ++i) {
- SqlFunctionCtx* __ctx = pCtx->subsidiaries.pCtx[i];
- if (__ctx->functionId == FUNCTION_TS_DUMMY) { // TODO refactor
- __ctx->tag.i = key;
- __ctx->tag.nType = TSDB_DATA_TYPE_BIGINT;
+ int64_t val = GET_INT64_VAL(tval);
+ if ((prev < val) ^ isMinFunc) {
+ pBuf->v = val;
+ // for (int32_t i = 0; i < (pCtx)->subsidiaries.num; ++i) {
+ // SqlFunctionCtx* __ctx = pCtx->subsidiaries.pCtx[i];
+ // if (__ctx->functionId == FUNCTION_TS_DUMMY) { // TODO refactor
+ // __ctx->tag.i = key;
+ // __ctx->tag.nType = TSDB_DATA_TYPE_BIGINT;
+ // }
+ //
+ // __ctx->fpSet.process(__ctx);
+ // }
+
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, index, pCtx->pSrcBlock, &pBuf->tuplePos);
}
+ }
- __ctx->fpSet.process(__ctx);
+ } else if (IS_UNSIGNED_NUMERIC_TYPE(type)) {
+ uint64_t prev = 0;
+ GET_TYPED_DATA(prev, uint64_t, type, &pBuf->v);
+
+ uint64_t val = GET_UINT64_VAL(tval);
+ if ((prev < val) ^ isMinFunc) {
+ pBuf->v = val;
+ // for (int32_t i = 0; i < (pCtx)->subsidiaries.num; ++i) {
+ // SqlFunctionCtx* __ctx = pCtx->subsidiaries.pCtx[i];
+ // if (__ctx->functionId == FUNCTION_TS_DUMMY) { // TODO refactor
+ // __ctx->tag.i = key;
+ // __ctx->tag.nType = TSDB_DATA_TYPE_BIGINT;
+ // }
+ //
+ // __ctx->fpSet.process(__ctx);
+ // }
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, index, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ } else if (type == TSDB_DATA_TYPE_DOUBLE) {
+ double prev = 0;
+ GET_TYPED_DATA(prev, int64_t, type, &pBuf->v);
+
+ double val = GET_DOUBLE_VAL(tval);
+ if ((prev < val) ^ isMinFunc) {
+ pBuf->v = val;
+
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, index, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ } else if (type == TSDB_DATA_TYPE_FLOAT) {
+ double prev = 0;
+ GET_TYPED_DATA(prev, int64_t, type, &pBuf->v);
+
+ double val = GET_DOUBLE_VAL(tval);
+ if ((prev < val) ^ isMinFunc) {
+ pBuf->v = val;
+ }
+
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, index, pCtx->pSrcBlock, &pBuf->tuplePos);
}
}
- } else if (IS_UNSIGNED_NUMERIC_TYPE(type)) {
- uint64_t prev = 0;
- GET_TYPED_DATA(prev, uint64_t, type, buf);
-
- uint64_t val = GET_UINT64_VAL(tval);
- if ((prev < val) ^ isMinFunc) {
- *(uint64_t*)buf = val;
- for (int32_t i = 0; i < (pCtx)->subsidiaries.num; ++i) {
- SqlFunctionCtx* __ctx = pCtx->subsidiaries.pCtx[i];
- if (__ctx->functionId == FUNCTION_TS_DUMMY) { // TODO refactor
- __ctx->tag.i = key;
- __ctx->tag.nType = TSDB_DATA_TYPE_BIGINT;
- }
-
- __ctx->fpSet.process(__ctx);
- }
- }
- } else if (type == TSDB_DATA_TYPE_DOUBLE) {
- double val = GET_DOUBLE_VAL(tval);
- UPDATE_DATA(pCtx, *(double*)buf, val, numOfElems, isMinFunc, key);
- } else if (type == TSDB_DATA_TYPE_FLOAT) {
- double val = GET_DOUBLE_VAL(tval);
- UPDATE_DATA(pCtx, *(float*)buf, val, numOfElems, isMinFunc, key);
}
+ pBuf->assign = true;
return numOfElems;
}
@@ -843,47 +805,318 @@ int32_t doMinMaxHelper(SqlFunctionCtx* pCtx, int32_t isMinFunc) {
if (IS_SIGNED_NUMERIC_TYPE(type) || type == TSDB_DATA_TYPE_BOOL) {
if (type == TSDB_DATA_TYPE_TINYINT || type == TSDB_DATA_TYPE_BOOL) {
- LOOPCHECK_N(*(int8_t*)buf, pCol, pCtx, int8_t, numOfRows, start, isMinFunc, numOfElems);
- } else if (type == TSDB_DATA_TYPE_SMALLINT) {
- LOOPCHECK_N(*(int16_t*)buf, pCol, pCtx, int16_t, numOfRows, start, isMinFunc, numOfElems);
- } else if (type == TSDB_DATA_TYPE_INT) {
- int32_t* pData = (int32_t*)pCol->pData;
- int32_t* val = (int32_t*)buf;
+ int8_t* pData = (int8_t*)pCol->pData;
+ int8_t* val = (int8_t*)&pBuf->v;
for (int32_t i = start; i < start + numOfRows; ++i) {
if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
continue;
}
- if ((*val < pData[i]) ^ isMinFunc) {
+ if (!pBuf->assign) {
*val = pData[i];
- TSKEY ts = (pCtx->ptsList != NULL) ? GET_TS_DATA(pCtx, i) : 0;
- DO_UPDATE_SUBSID_RES(pCtx, ts);
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
}
numOfElems += 1;
}
+ } else if (type == TSDB_DATA_TYPE_SMALLINT) {
+ int16_t* pData = (int16_t*)pCol->pData;
+ int16_t* val = (int16_t*)&pBuf->v;
-#if defined(_DEBUG_VIEW)
- qDebug("max value updated:%d", *retVal);
-#endif
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
+ } else if (type == TSDB_DATA_TYPE_INT) {
+ int32_t* pData = (int32_t*)pCol->pData;
+ int32_t* val = (int32_t*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
} else if (type == TSDB_DATA_TYPE_BIGINT) {
- LOOPCHECK_N(*(int64_t*)buf, pCol, pCtx, int64_t, numOfRows, start, isMinFunc, numOfElems);
+ int64_t* pData = (int64_t*)pCol->pData;
+ int64_t* val = (int64_t*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
}
} else if (IS_UNSIGNED_NUMERIC_TYPE(type)) {
if (type == TSDB_DATA_TYPE_UTINYINT) {
- LOOPCHECK_N(*(uint8_t*)buf, pCol, pCtx, uint8_t, numOfRows, start, isMinFunc, numOfElems);
+ uint8_t* pData = (uint8_t*)pCol->pData;
+ uint8_t* val = (uint8_t*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
} else if (type == TSDB_DATA_TYPE_USMALLINT) {
- LOOPCHECK_N(*(uint16_t*)buf, pCol, pCtx, uint16_t, numOfRows, start, isMinFunc, numOfElems);
+ uint16_t* pData = (uint16_t*)pCol->pData;
+ uint16_t* val = (uint16_t*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
} else if (type == TSDB_DATA_TYPE_UINT) {
- LOOPCHECK_N(*(uint32_t*)buf, pCol, pCtx, uint32_t, numOfRows, start, isMinFunc, numOfElems);
+ uint32_t* pData = (uint32_t*)pCol->pData;
+ uint32_t* val = (uint32_t*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
} else if (type == TSDB_DATA_TYPE_UBIGINT) {
- LOOPCHECK_N(*(uint64_t*)buf, pCol, pCtx, uint64_t, numOfRows, start, isMinFunc, numOfElems);
+ uint64_t* pData = (uint64_t*)pCol->pData;
+ uint64_t* val = (uint64_t*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
}
} else if (type == TSDB_DATA_TYPE_DOUBLE) {
- LOOPCHECK_N(*(double*)buf, pCol, pCtx, double, numOfRows, start, isMinFunc, numOfElems);
+ double* pData = (double*)pCol->pData;
+ double* val = (double*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
} else if (type == TSDB_DATA_TYPE_FLOAT) {
- LOOPCHECK_N(*(float*)buf, pCol, pCtx, float, numOfRows, start, isMinFunc, numOfElems);
+ float* pData = (float*)pCol->pData;
+ double* val = (double*)&pBuf->v;
+
+ for (int32_t i = start; i < start + numOfRows; ++i) {
+ if ((pCol->hasNull) && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ if (!pBuf->assign) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ saveTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ pBuf->assign = true;
+ } else {
+ // ignore the equivalent data value
+ if ((*val) == pData[i]) {
+ continue;
+ }
+
+ if ((*val < pData[i]) ^ isMinFunc) {
+ *val = pData[i];
+ if (pCtx->subsidiaries.num > 0) {
+ copyTupleData(pCtx, i, pCtx->pSrcBlock, &pBuf->tuplePos);
+ }
+ }
+ }
+
+ numOfElems += 1;
+ }
}
return numOfElems;
@@ -901,6 +1134,65 @@ int32_t maxFunction(SqlFunctionCtx* pCtx) {
return TSDB_CODE_SUCCESS;
}
+static void setSelectivityValue(SqlFunctionCtx* pCtx, SSDataBlock* pBlock, const STuplePos *pTuplePos, int32_t rowIndex);
+
+int32_t minmaxFunctionFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock) {
+ SResultRowEntryInfo* pEntryInfo = GET_RES_INFO(pCtx);
+
+ SMinmaxResInfo* pRes = GET_ROWCELL_INTERBUF(pEntryInfo);
+
+ int32_t type = pCtx->input.pData[0]->info.type;
+ int32_t slotId = pCtx->pExpr->base.resSchema.slotId;
+
+ SColumnInfoData* pCol = taosArrayGet(pBlock->pDataBlock, slotId);
+
+ // todo assign the tag value
+ int32_t currentRow = pBlock->info.rows;
+
+ if (pCol->info.type == TSDB_DATA_TYPE_FLOAT) {
+ float v = *(double*) &pRes->v;
+ colDataAppend(pCol, currentRow, (const char*)&v, false);
+ } else {
+ colDataAppend(pCol, currentRow, (const char*)&pRes->v, false);
+ }
+
+ setSelectivityValue(pCtx, pBlock, &pRes->tuplePos, currentRow);
+ return pEntryInfo->numOfRes;
+}
+
+void setSelectivityValue(SqlFunctionCtx* pCtx, SSDataBlock* pBlock, const STuplePos *pTuplePos, int32_t rowIndex) {
+ int32_t pageId = pTuplePos->pageId;
+ int32_t offset = pTuplePos->offset;
+ if (pTuplePos->pageId != -1) {
+ SFilePage* pPage = getBufPage(pCtx->pBuf, pageId);
+
+ bool* nullList = (bool*)((char*)pPage + offset);
+ char* pStart = (char*)(nullList + pCtx->pSrcBlock->info.numOfCols * sizeof(bool));
+
+ // todo set the offset value to optimize the performance.
+ for (int32_t j = 0; j < pCtx->subsidiaries.num; ++j) {
+ SqlFunctionCtx* pc = pCtx->subsidiaries.pCtx[j];
+
+ SFunctParam* pFuncParam = &pc->pExpr->base.pParam[0];
+ int32_t srcSlotId = pFuncParam->pCol->slotId;
+ int32_t dstSlotId = pc->pExpr->base.resSchema.slotId;
+
+ int32_t ps = 0;
+ for (int32_t k = 0; k < srcSlotId; ++k) {
+ SColumnInfoData* pSrcCol = taosArrayGet(pCtx->pSrcBlock->pDataBlock, k);
+ ps += pSrcCol->info.bytes;
+ }
+
+ SColumnInfoData* pDstCol = taosArrayGet(pBlock->pDataBlock, dstSlotId);
+ if (nullList[srcSlotId]) {
+ colDataAppendNULL(pDstCol, rowIndex);
+ } else {
+ colDataAppend(pDstCol, rowIndex, (pStart + ps), false);
+ }
+ }
+ }
+}
+
bool getStddevFuncEnv(SFunctionNode* pFunc, SFuncExecEnv* pEnv) {
pEnv->calcMemSize = sizeof(SStddevRes);
return true;
@@ -1244,6 +1536,14 @@ bool getFirstLastFuncEnv(SFunctionNode* pFunc, SFuncExecEnv* pEnv) {
return true;
}
+bool getSelectivityFuncEnv(SFunctionNode* pFunc, SFuncExecEnv* pEnv) {
+ SColumnNode* pNode = nodesListGetNode(pFunc->pParameterList, 0);
+ pEnv->calcMemSize = pNode->node.resType.bytes;
+ return true;
+}
+
+
+
static FORCE_INLINE TSKEY getRowPTs(SColumnInfoData* pTsColInfo, int32_t rowIndex) {
if (pTsColInfo == NULL) {
return 0;
@@ -1622,35 +1922,49 @@ static STopBotRes* getTopBotOutputInfo(SqlFunctionCtx* pCtx) {
}
static void doAddIntoResult(SqlFunctionCtx* pCtx, void* pData, int32_t rowIndex, SSDataBlock* pSrcBlock, uint16_t type,
- uint64_t uid, SResultRowEntryInfo* pEntryInfo);
-
-static void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STopBotResItem* pItem);
-static void copyTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STopBotResItem* pItem);
+ uint64_t uid, SResultRowEntryInfo* pEntryInfo, bool isTopQuery);
int32_t topFunction(SqlFunctionCtx* pCtx) {
int32_t numOfElems = 0;
SResultRowEntryInfo* pResInfo = GET_RES_INFO(pCtx);
- // if ((void *)pRes->res[0] != (void *)((char *)pRes + sizeof(STopBotRes) + POINTER_BYTES * pCtx->param[0].i)) {
- // buildTopBotStruct(pRes, pCtx);
- // }
-
SInputColumnInfoData* pInput = &pCtx->input;
SColumnInfoData* pCol = pInput->pData[0];
int32_t type = pInput->pData[0]->info.type;
int32_t start = pInput->startRowIndex;
- int32_t numOfRows = pInput->numOfRows;
-
- for (int32_t i = start; i < numOfRows + start; ++i) {
+ for (int32_t i = start; i < pInput->numOfRows + start; ++i) {
if (pCol->hasNull && colDataIsNull_f(pCol->nullbitmap, i)) {
continue;
}
- numOfElems++;
+ numOfElems++;
char* data = colDataGetData(pCol, i);
- doAddIntoResult(pCtx, data, i, pCtx->pSrcBlock, type, pInput->uid, pResInfo);
+ doAddIntoResult(pCtx, data, i, pCtx->pSrcBlock, type, pInput->uid, pResInfo, true);
+ }
+
+ return TSDB_CODE_SUCCESS;
+}
+
+int32_t bottomFunction(SqlFunctionCtx* pCtx) {
+ int32_t numOfElems = 0;
+ SResultRowEntryInfo* pResInfo = GET_RES_INFO(pCtx);
+
+ SInputColumnInfoData* pInput = &pCtx->input;
+ SColumnInfoData* pCol = pInput->pData[0];
+
+ int32_t type = pInput->pData[0]->info.type;
+
+ int32_t start = pInput->startRowIndex;
+ for (int32_t i = start; i < pInput->numOfRows + start; ++i) {
+ if (pCol->hasNull && colDataIsNull_f(pCol->nullbitmap, i)) {
+ continue;
+ }
+
+ numOfElems++;
+ char* data = colDataGetData(pCol, i);
+ doAddIntoResult(pCtx, data, i, pCtx->pSrcBlock, type, pInput->uid, pResInfo, false);
}
return TSDB_CODE_SUCCESS;
@@ -1684,7 +1998,7 @@ static int32_t topBotResComparFn(const void* p1, const void* p2, const void* par
}
void doAddIntoResult(SqlFunctionCtx* pCtx, void* pData, int32_t rowIndex, SSDataBlock* pSrcBlock, uint16_t type,
- uint64_t uid, SResultRowEntryInfo* pEntryInfo) {
+ uint64_t uid, SResultRowEntryInfo* pEntryInfo, bool isTopQuery) {
STopBotRes* pRes = getTopBotOutputInfo(pCtx);
int32_t maxSize = pCtx->param[1].param.i;
@@ -1701,30 +2015,36 @@ void doAddIntoResult(SqlFunctionCtx* pCtx, void* pData, int32_t rowIndex, SSData
pItem->uid = uid;
// save the data of this tuple
- saveTupleData(pCtx, rowIndex, pSrcBlock, pItem);
+ saveTupleData(pCtx, rowIndex, pSrcBlock, &pItem->tuplePos);
// allocate the buffer and keep the data of this row into the new allocated buffer
pEntryInfo->numOfRes++;
taosheapsort((void*)pItems, sizeof(STopBotResItem), pEntryInfo->numOfRes, (const void*)&type, topBotResComparFn,
- false);
+ !isTopQuery);
} else { // replace the minimum value in the result
- if ((IS_SIGNED_NUMERIC_TYPE(type) && val.i > pItems[0].v.i) ||
- (IS_UNSIGNED_NUMERIC_TYPE(type) && val.u > pItems[0].v.u) || (IS_FLOAT_TYPE(type) && val.d > pItems[0].v.d)) {
+ if ((isTopQuery && (
+ (IS_SIGNED_NUMERIC_TYPE(type) && val.i > pItems[0].v.i) ||
+ (IS_UNSIGNED_NUMERIC_TYPE(type) && val.u > pItems[0].v.u) ||
+ (IS_FLOAT_TYPE(type) && val.d > pItems[0].v.d)))
+ || (!isTopQuery && (
+ (IS_SIGNED_NUMERIC_TYPE(type) && val.i < pItems[0].v.i) ||
+ (IS_UNSIGNED_NUMERIC_TYPE(type) && val.u < pItems[0].v.u) ||
+ (IS_FLOAT_TYPE(type) && val.d < pItems[0].v.d))
+ )) {
// replace the old data and the coresponding tuple data
STopBotResItem* pItem = &pItems[0];
pItem->v = val;
pItem->uid = uid;
// save the data of this tuple by over writing the old data
- copyTupleData(pCtx, rowIndex, pSrcBlock, pItem);
-
+ copyTupleData(pCtx, rowIndex, pSrcBlock, &pItem->tuplePos);
taosheapadjust((void*)pItems, sizeof(STopBotResItem), 0, pEntryInfo->numOfRes - 1, (const void*)&type,
- topBotResComparFn, NULL, false);
+ topBotResComparFn, NULL, !isTopQuery);
}
}
}
-void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STopBotResItem* pItem) {
+void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STuplePos* pPos) {
SFilePage* pPage = NULL;
int32_t completeRowSize = pSrcBlock->info.rowSize + pSrcBlock->info.numOfCols * sizeof(bool);
@@ -1740,7 +2060,7 @@ void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pS
}
}
- pItem->tuplePos.pageId = pCtx->curBufPage;
+ pPos->pageId = pCtx->curBufPage;
// keep the current row data, extract method
int32_t offset = 0;
@@ -1751,6 +2071,7 @@ void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pS
bool isNull = colDataIsNull_s(pCol, rowIndex);
if (isNull) {
nullList[i] = true;
+ offset += pCol->info.bytes;
continue;
}
@@ -1764,17 +2085,17 @@ void saveTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pS
offset += pCol->info.bytes;
}
- pItem->tuplePos.offset = pPage->num;
+ pPos->offset = pPage->num;
pPage->num += completeRowSize;
setBufPageDirty(pPage, true);
releaseBufPage(pCtx->pBuf, pPage);
}
-void copyTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STopBotResItem* pItem) {
- SFilePage* pPage = getBufPage(pCtx->pBuf, pItem->tuplePos.pageId);
+void copyTupleData(SqlFunctionCtx* pCtx, int32_t rowIndex, const SSDataBlock* pSrcBlock, STuplePos* pPos) {
+ SFilePage* pPage = getBufPage(pCtx->pBuf, pPos->pageId);
- bool* nullList = (bool*)((char*)pPage + pItem->tuplePos.offset);
+ bool* nullList = (bool*)((char*)pPage + pPos->offset);
char* pStart = (char*)(nullList + pSrcBlock->info.numOfCols * sizeof(bool));
int32_t offset = 0;
@@ -1803,54 +2124,24 @@ int32_t topBotFinalize(SqlFunctionCtx* pCtx, SSDataBlock* pBlock) {
STopBotRes* pRes = GET_ROWCELL_INTERBUF(pEntryInfo);
pEntryInfo->complete = true;
- int32_t type = pCtx->input.pData[0]->info.type;
- int32_t slotId = pCtx->pExpr->base.resSchema.slotId;
+ int32_t type = pCtx->input.pData[0]->info.type;
+ int32_t slotId = pCtx->pExpr->base.resSchema.slotId;
+
SColumnInfoData* pCol = taosArrayGet(pBlock->pDataBlock, slotId);
// todo assign the tag value and the corresponding row data
int32_t currentRow = pBlock->info.rows;
- switch (type) {
- case TSDB_DATA_TYPE_INT: {
- for (int32_t i = 0; i < pEntryInfo->numOfRes; ++i) {
- STopBotResItem* pItem = &pRes->pItems[i];
- colDataAppendInt32(pCol, currentRow, (int32_t*)&pItem->v.i);
-
- int32_t pageId = pItem->tuplePos.pageId;
- int32_t offset = pItem->tuplePos.offset;
- if (pItem->tuplePos.pageId != -1) {
- SFilePage* pPage = getBufPage(pCtx->pBuf, pageId);
-
- bool* nullList = (bool*)((char*)pPage + offset);
- char* pStart = (char*)(nullList + pCtx->pSrcBlock->info.numOfCols * sizeof(bool));
-
- // todo set the offset value to optimize the performance.
- for (int32_t j = 0; j < pCtx->subsidiaries.num; ++j) {
- SqlFunctionCtx* pc = pCtx->subsidiaries.pCtx[j];
-
- SFunctParam* pFuncParam = &pc->pExpr->base.pParam[0];
- int32_t srcSlotId = pFuncParam->pCol->slotId;
- int32_t dstSlotId = pCtx->pExpr->base.resSchema.slotId;
-
- int32_t ps = 0;
- for (int32_t k = 0; k < srcSlotId; ++k) {
- SColumnInfoData* pSrcCol = taosArrayGet(pCtx->pSrcBlock->pDataBlock, k);
- ps += pSrcCol->info.bytes;
- }
-
- SColumnInfoData* pDstCol = taosArrayGet(pBlock->pDataBlock, dstSlotId);
- if (nullList[srcSlotId]) {
- colDataAppendNULL(pDstCol, currentRow);
- } else {
- colDataAppend(pDstCol, currentRow, (pStart + ps), false);
- }
- }
- }
-
- currentRow += 1;
- }
-
- break;
+ for (int32_t i = 0; i < pEntryInfo->numOfRes; ++i) {
+ STopBotResItem* pItem = &pRes->pItems[i];
+ if (type == TSDB_DATA_TYPE_FLOAT) {
+ float v = pItem->v.d;
+ colDataAppend(pCol, currentRow, (const char*)&v, false);
+ } else {
+ colDataAppend(pCol, currentRow, (const char*)&pItem->v.i, false);
}
+
+ setSelectivityValue(pCtx, pBlock, &pRes->pItems[i].tuplePos, currentRow);
+ currentRow += 1;
}
return pEntryInfo->numOfRes;
diff --git a/source/libs/function/src/functionMgt.c b/source/libs/function/src/functionMgt.c
index 46bbb33aa7..73ec7f510b 100644
--- a/source/libs/function/src/functionMgt.c
+++ b/source/libs/function/src/functionMgt.c
@@ -169,6 +169,8 @@ bool fmIsDynamicScanOptimizedFunc(int32_t funcId) {
bool fmIsMultiResFunc(int32_t funcId) { return isSpecificClassifyFunc(funcId, FUNC_MGT_MULTI_RES_FUNC); }
+bool fmIsRepeatScanFunc(int32_t funcId) { return isSpecificClassifyFunc(funcId, FUNC_MGT_REPEAT_SCAN_FUNC); }
+
bool fmIsUserDefinedFunc(int32_t funcId) { return funcId > FUNC_UDF_ID_START; }
void fmFuncMgtDestroy() {
@@ -197,15 +199,14 @@ int32_t fmSetNormalFunc(int32_t funcId, SFuncExecFuncs* pFpSet) {
bool fmIsInvertible(int32_t funcId) {
bool res = false;
switch (funcMgtBuiltins[funcId].type) {
- case FUNCTION_TYPE_COUNT:
- case FUNCTION_TYPE_SUM:
- case FUNCTION_TYPE_STDDEV:
- case FUNCTION_TYPE_AVG:
- res = true;
- break;
- default:
- break;
+ case FUNCTION_TYPE_COUNT:
+ case FUNCTION_TYPE_SUM:
+ case FUNCTION_TYPE_STDDEV:
+ case FUNCTION_TYPE_AVG:
+ res = true;
+ break;
+ default:
+ break;
}
return res;
}
-
diff --git a/source/libs/nodes/src/nodesCodeFuncs.c b/source/libs/nodes/src/nodesCodeFuncs.c
index 507cd79411..a625fc0d0c 100644
--- a/source/libs/nodes/src/nodesCodeFuncs.c
+++ b/source/libs/nodes/src/nodesCodeFuncs.c
@@ -222,6 +222,8 @@ const char* nodesNodeName(ENodeType type) {
return "PhysiSort";
case QUERY_NODE_PHYSICAL_PLAN_INTERVAL:
return "PhysiInterval";
+ case QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL:
+ return "PhysiStreamInterval";
case QUERY_NODE_PHYSICAL_PLAN_FILL:
return "PhysiFill";
case QUERY_NODE_PHYSICAL_PLAN_SESSION_WINDOW:
@@ -2893,6 +2895,7 @@ static int32_t specificNodeToJson(const void* pObj, SJson* pJson) {
case QUERY_NODE_PHYSICAL_PLAN_SORT:
return physiSortNodeToJson(pObj, pJson);
case QUERY_NODE_PHYSICAL_PLAN_INTERVAL:
+ case QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL:
return physiIntervalNodeToJson(pObj, pJson);
case QUERY_NODE_PHYSICAL_PLAN_FILL:
return physiFillNodeToJson(pObj, pJson);
@@ -2983,6 +2986,7 @@ static int32_t jsonToSpecificNode(const SJson* pJson, void* pObj) {
case QUERY_NODE_PHYSICAL_PLAN_SORT:
return jsonToPhysiSortNode(pJson, pObj);
case QUERY_NODE_PHYSICAL_PLAN_INTERVAL:
+ case QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL:
return jsonToPhysiIntervalNode(pJson, pObj);
case QUERY_NODE_PHYSICAL_PLAN_FILL:
return jsonToPhysiFillNode(pJson, pObj);
@@ -3099,6 +3103,7 @@ int32_t nodesStringToNode(const char* pStr, SNode** pNode) {
return TSDB_CODE_FAILED;
}
int32_t code = makeNodeByJson(pJson, pNode);
+ tjsonDelete(pJson);
if (TSDB_CODE_SUCCESS != code) {
nodesDestroyNode(*pNode);
*pNode = NULL;
diff --git a/source/libs/nodes/src/nodesTraverseFuncs.c b/source/libs/nodes/src/nodesTraverseFuncs.c
index f2c043b9ea..e8274c3c8e 100644
--- a/source/libs/nodes/src/nodesTraverseFuncs.c
+++ b/source/libs/nodes/src/nodesTraverseFuncs.c
@@ -513,6 +513,7 @@ static EDealRes dispatchPhysiPlan(SNode* pNode, ETraversalOrder order, FNodeWalk
break;
}
case QUERY_NODE_PHYSICAL_PLAN_INTERVAL:
+ case QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL:
res = walkWindowPhysi((SWinodwPhysiNode*)pNode, order, walker, pContext);
break;
case QUERY_NODE_PHYSICAL_PLAN_SESSION_WINDOW:
diff --git a/source/libs/nodes/src/nodesUtilFuncs.c b/source/libs/nodes/src/nodesUtilFuncs.c
index eeb069383f..af7ebf5d10 100644
--- a/source/libs/nodes/src/nodesUtilFuncs.c
+++ b/source/libs/nodes/src/nodesUtilFuncs.c
@@ -252,6 +252,8 @@ SNodeptr nodesMakeNode(ENodeType type) {
return makeNode(type, sizeof(SSortPhysiNode));
case QUERY_NODE_PHYSICAL_PLAN_INTERVAL:
return makeNode(type, sizeof(SIntervalPhysiNode));
+ case QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL:
+ return makeNode(type, sizeof(SStreamIntervalPhysiNode));
case QUERY_NODE_PHYSICAL_PLAN_FILL:
return makeNode(type, sizeof(SFillPhysiNode));
case QUERY_NODE_PHYSICAL_PLAN_SESSION_WINDOW:
@@ -644,6 +646,7 @@ void nodesDestroyNode(SNodeptr pNode) {
break;
}
case QUERY_NODE_PHYSICAL_PLAN_INTERVAL:
+ case QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL:
destroyWinodwPhysiNode((SWinodwPhysiNode*)pNode);
break;
case QUERY_NODE_PHYSICAL_PLAN_SESSION_WINDOW:
diff --git a/source/libs/parser/src/parAstParser.c b/source/libs/parser/src/parAstParser.c
index ee1a92d8b3..ebc8281f56 100644
--- a/source/libs/parser/src/parAstParser.c
+++ b/source/libs/parser/src/parAstParser.c
@@ -64,8 +64,8 @@ int32_t parse(SParseContext* pParseCxt, SQuery** pQuery) {
goto abort_parse;
}
default:
- Parse(pParser, t0.type, t0, &cxt);
// ParseTrace(stdout, "");
+ Parse(pParser, t0.type, t0, &cxt);
if (TSDB_CODE_SUCCESS != cxt.errCode) {
goto abort_parse;
}
diff --git a/source/libs/parser/src/parTokenizer.c b/source/libs/parser/src/parTokenizer.c
index 54a0fce3e7..01327c08ef 100644
--- a/source/libs/parser/src/parTokenizer.c
+++ b/source/libs/parser/src/parTokenizer.c
@@ -590,6 +590,8 @@ uint32_t tGetToken(const char* z, uint32_t* tokenId) {
if (seg == 4) { // ip address
*tokenId = TK_NK_IPTOKEN;
return i;
+ } else if (seg > 2) {
+ break;
}
if ((z[i] == 'e' || z[i] == 'E') &&
diff --git a/source/libs/parser/src/parTranslater.c b/source/libs/parser/src/parTranslater.c
index 1bd7e28c74..d40da8a629 100644
--- a/source/libs/parser/src/parTranslater.c
+++ b/source/libs/parser/src/parTranslater.c
@@ -699,6 +699,10 @@ static EDealRes translateFunction(STranslateContext* pCxt, SFunctionNode* pFunc)
if (isCountStar(pFunc)) {
pCxt->errCode = rewriteCountStar(pCxt, pFunc);
}
+
+ if (fmIsRepeatScanFunc(pFunc->funcId)) {
+ pCxt->pCurrStmt->hasRepeatScanFuncs = true;
+ }
}
return TSDB_CODE_SUCCESS == pCxt->errCode ? DEAL_RES_CONTINUE : DEAL_RES_ERROR;
}
@@ -2255,8 +2259,8 @@ static int32_t checkTableColsSchema(STranslateContext* pCxt, SHashObj* pHash, SN
code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_DUPLICATED_COLUMN);
}
if (TSDB_CODE_SUCCESS == code) {
- if ((TSDB_DATA_TYPE_VARCHAR == pCol->dataType.type && pCol->dataType.bytes > TSDB_MAX_BINARY_LEN) ||
- (TSDB_DATA_TYPE_NCHAR == pCol->dataType.type && pCol->dataType.bytes > TSDB_MAX_NCHAR_LEN)) {
+ if ((TSDB_DATA_TYPE_VARCHAR == pCol->dataType.type && calcTypeBytes(pCol->dataType) > TSDB_MAX_BINARY_LEN) ||
+ (TSDB_DATA_TYPE_NCHAR == pCol->dataType.type && calcTypeBytes(pCol->dataType) > TSDB_MAX_NCHAR_LEN)) {
code = code = generateSyntaxErrMsg(&pCxt->msgBuf, TSDB_CODE_PAR_INVALID_VAR_COLUMN_LEN);
}
}
diff --git a/source/libs/planner/src/planLogicCreater.c b/source/libs/planner/src/planLogicCreater.c
index 3e19ccbd82..d4b9f5b292 100644
--- a/source/libs/planner/src/planLogicCreater.c
+++ b/source/libs/planner/src/planLogicCreater.c
@@ -54,6 +54,9 @@ static EDealRes doRewriteExpr(SNode** pNode, void* pContext) {
pCol->node.resType = pToBeRewrittenExpr->resType;
strcpy(pCol->node.aliasName, pToBeRewrittenExpr->aliasName);
strcpy(pCol->colName, ((SExprNode*)pExpr)->aliasName);
+ if (QUERY_NODE_FUNCTION == nodeType(pExpr) && FUNCTION_TYPE_WSTARTTS == ((SFunctionNode*)pExpr)->funcType) {
+ pCol->colId = PRIMARYKEY_TIMESTAMP_COL_ID;
+ }
nodesDestroyNode(*pNode);
*pNode = (SNode*)pCol;
return DEAL_RES_IGNORE_CHILD;
@@ -253,7 +256,7 @@ static int32_t createScanLogicNode(SLogicPlanContext* pCxt, SSelectStmt* pSelect
TSWAP(pScan->pMeta, pRealTable->pMeta);
TSWAP(pScan->pVgroupList, pRealTable->pVgroupList);
- pScan->scanSeq[0] = 1;
+ pScan->scanSeq[0] = pSelect->hasRepeatScanFuncs ? 2 : 1;
pScan->scanSeq[1] = 0;
pScan->scanRange = TSWINDOW_INITIALIZER;
pScan->tableName.type = TSDB_TABLE_NAME_T;
diff --git a/source/libs/planner/src/planOptimizer.c b/source/libs/planner/src/planOptimizer.c
index dbce9abf36..30f6f03a6c 100644
--- a/source/libs/planner/src/planOptimizer.c
+++ b/source/libs/planner/src/planOptimizer.c
@@ -754,10 +754,7 @@ static int32_t opkDoOptimized(SOptimizeContext* pCxt, SSortLogicNode* pSort, SNo
EOrder order = opkGetPrimaryKeyOrder(pSort);
if (ORDER_DESC == order) {
SNode* pScan = NULL;
- FOREACH(pScan, pScanNodes) {
- ((SScanLogicNode*)pScan)->scanSeq[0] = 0;
- ((SScanLogicNode*)pScan)->scanSeq[1] = 1;
- }
+ FOREACH(pScan, pScanNodes) { TSWAP(((SScanLogicNode*)pScan)->scanSeq[0], ((SScanLogicNode*)pScan)->scanSeq[1]); }
}
if (NULL == pSort->node.pParent) {
diff --git a/source/libs/planner/src/planPhysiCreater.c b/source/libs/planner/src/planPhysiCreater.c
index 18fa5b93dd..835d607099 100644
--- a/source/libs/planner/src/planPhysiCreater.c
+++ b/source/libs/planner/src/planPhysiCreater.c
@@ -869,7 +869,8 @@ static int32_t createWindowPhysiNodeFinalize(SPhysiPlanContext* pCxt, SNodeList*
static int32_t createIntervalPhysiNode(SPhysiPlanContext* pCxt, SNodeList* pChildren,
SWindowLogicNode* pWindowLogicNode, SPhysiNode** pPhyNode) {
SIntervalPhysiNode* pInterval = (SIntervalPhysiNode*)makePhysiNode(
- pCxt, getPrecision(pChildren), (SLogicNode*)pWindowLogicNode, QUERY_NODE_PHYSICAL_PLAN_INTERVAL);
+ pCxt, getPrecision(pChildren), (SLogicNode*)pWindowLogicNode,
+ (pCxt->pPlanCxt->streamQuery ? QUERY_NODE_PHYSICAL_PLAN_STREAM_INTERVAL : QUERY_NODE_PHYSICAL_PLAN_INTERVAL));
if (NULL == pInterval) {
return TSDB_CODE_OUT_OF_MEMORY;
}
diff --git a/source/libs/planner/test/planBasicTest.cpp b/source/libs/planner/test/planBasicTest.cpp
index 639af2875e..a17d8cd850 100644
--- a/source/libs/planner/test/planBasicTest.cpp
+++ b/source/libs/planner/test/planBasicTest.cpp
@@ -48,4 +48,6 @@ TEST_F(PlanBasicTest, func) {
useDb("root", "test");
run("SELECT DIFF(c1) FROM t1");
+
+ run("SELECT PERCENTILE(c1, 60) FROM t1");
}
diff --git a/source/libs/planner/test/planOptimizeTest.cpp b/source/libs/planner/test/planOptimizeTest.cpp
index 4938618db6..6c7b1d0a0e 100644
--- a/source/libs/planner/test/planOptimizeTest.cpp
+++ b/source/libs/planner/test/planOptimizeTest.cpp
@@ -37,4 +37,6 @@ TEST_F(PlanOptimizeTest, orderByPrimaryKey) {
run("SELECT * FROM t1 ORDER BY ts DESC");
run("SELECT c1 FROM t1 ORDER BY ts");
run("SELECT c1 FROM t1 ORDER BY ts DESC");
+
+ run("SELECT COUNT(*) FROM t1 INTERVAL(10S) ORDER BY _WSTARTTS DESC");
}
diff --git a/source/libs/qcom/src/queryUtil.c b/source/libs/qcom/src/queryUtil.c
index 288d2e5f76..3e3e393f5f 100644
--- a/source/libs/qcom/src/queryUtil.c
+++ b/source/libs/qcom/src/queryUtil.c
@@ -136,7 +136,8 @@ int32_t taosAsyncExec(__async_exec_fn_t execFn, void* execParam, int32_t* code)
return 0;
}
-int32_t asyncSendMsgToServerExt(void* pTransporter, SEpSet* epSet, int64_t* pTransporterId, const SMsgSendInfo* pInfo, bool persistHandle, void *rpcCtx) {
+int32_t asyncSendMsgToServerExt(void* pTransporter, SEpSet* epSet, int64_t* pTransporterId, const SMsgSendInfo* pInfo,
+ bool persistHandle, void* rpcCtx) {
char* pMsg = rpcMallocCont(pInfo->msgInfo.len);
if (NULL == pMsg) {
qError("0x%" PRIx64 " msg:%s malloc failed", pInfo->requestId, TMSG_INFO(pInfo->msgType));
diff --git a/source/libs/sync/src/syncMain.c b/source/libs/sync/src/syncMain.c
index 9a8dcc57d9..911d8384f0 100644
--- a/source/libs/sync/src/syncMain.c
+++ b/source/libs/sync/src/syncMain.c
@@ -522,6 +522,7 @@ void syncNodeClose(SSyncNode* pSyncNode) {
ret = raftStoreClose(pSyncNode->pRaftStore);
assert(ret == 0);
+ syncRespMgrDestroy(pSyncNode->pSyncRespMgr);
voteGrantedDestroy(pSyncNode->pVotesGranted);
votesRespondDestory(pSyncNode->pVotesRespond);
syncIndexMgrDestroy(pSyncNode->pNextIndex);
@@ -1138,6 +1139,7 @@ static int32_t syncNodeAppendNoop(SSyncNode* ths) {
syncNodeReplicate(ths);
}
+ syncEntryDestory(pEntry);
return ret;
}
diff --git a/source/util/test/encodeTest.cpp b/source/util/test/encodeTest.cpp
index 00e12a4fe8..974677d26c 100644
--- a/source/util/test/encodeTest.cpp
+++ b/source/util/test/encodeTest.cpp
@@ -440,6 +440,7 @@ TEST(td_encode_test, compound_struct_encode_test) {
tCoderClear(&decoder);
}
#endif
+
#pragma GCC diagnostic pop
#endif
diff --git a/tests/script/sh/exec.sh b/tests/script/sh/exec.sh
index 1310cf2656..74015eebd6 100755
--- a/tests/script/sh/exec.sh
+++ b/tests/script/sh/exec.sh
@@ -101,8 +101,8 @@ if [ "$EXEC_OPTON" = "start" ]; then
if [ "$VALGRIND_OPTION" = "true" ]; then
TT=`date +%s`
#mkdir ${LOG_DIR}/${TT}
- echo "nohup valgrind --log-file=${LOG_DIR}/valgrind-taosd-${NODE_NAME}-${TT}.log --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes $EXE_DIR/taosd -c $CFG_DIR > /dev/null 2>&1 &"
- nohup valgrind --log-file=${LOG_DIR}/valgrind-taosd-${NODE_NAME}-${TT}.log --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes $EXE_DIR/taosd -c $CFG_DIR > /dev/null 2>&1 &
+ echo "nohup valgrind --log-file=${LOG_DIR}/valgrind-taosd-${NODE_NAME}-${TT}.log --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all --num-callers=20 -v -v --workaround-gcc296-bugs=yes $EXE_DIR/taosd -c $CFG_DIR > /dev/null 2>&1 &"
+ nohup valgrind --log-file=${LOG_DIR}/valgrind-taosd-${NODE_NAME}-${TT}.log --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --show-leak-kinds=all --num-callers=20 -v -v --workaround-gcc296-bugs=yes $EXE_DIR/taosd -c $CFG_DIR > /dev/null 2>&1 &
else
echo "nohup $EXE_DIR/taosd -c $CFG_DIR > /dev/null 2>&1 &"
nohup $EXE_DIR/taosd -c $CFG_DIR > /dev/null 2>&1 &
diff --git a/tests/script/test.sh b/tests/script/test.sh
index e4191da0a9..1cfe8dd6f5 100755
--- a/tests/script/test.sh
+++ b/tests/script/test.sh
@@ -131,8 +131,8 @@ if [ -n "$FILE_NAME" ]; then
FLAG="-v"
fi
- echo valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --child-silent-after-fork=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes --log-file=${LOG_DIR}/valgrind-tsim.log $PROGRAM -c $CFG_DIR -f $FILE_NAME $FLAG
- valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --child-silent-after-fork=yes --show-leak-kinds=all -v --workaround-gcc296-bugs=yes --log-file=${LOG_DIR}/valgrind-tsim.log $PROGRAM -c $CFG_DIR -f $FILE_NAME $FLAG
+ echo valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --child-silent-after-fork=yes --show-leak-kinds=all --num-callers=20 -v --workaround-gcc296-bugs=yes --log-file=${LOG_DIR}/valgrind-tsim.log $PROGRAM -c $CFG_DIR -f $FILE_NAME $FLAG
+ valgrind --tool=memcheck --leak-check=full --show-reachable=no --track-origins=yes --child-silent-after-fork=yes --show-leak-kinds=all --num-callers=20 -v --workaround-gcc296-bugs=yes --log-file=${LOG_DIR}/valgrind-tsim.log $PROGRAM -c $CFG_DIR -f $FILE_NAME $FLAG
else
if [[ $MULTIPROCESS -eq 1 ]];then
echo "ExcuteCmd(multiprocess):" $PROGRAM -m -c $CFG_DIR -f $FILE_NAME
diff --git a/tests/script/tsim/insert/basic0.sim b/tests/script/tsim/insert/basic0.sim
index 94bd0f1ecf..d8dde20e4e 100644
--- a/tests/script/tsim/insert/basic0.sim
+++ b/tests/script/tsim/insert/basic0.sim
@@ -140,7 +140,8 @@ endi
if $data00 != -13 then
return -1
endi
-if $data01 != -2.30000 then
+if $data01 != -2.30000 then
+ print expect -2.30000, actual: $data01
return -1
endi
if $data02 != -3.300000000 then
diff --git a/tests/system-test/2-query/diff.py b/tests/system-test/2-query/diff.py
index 82c450771f..1a6a2e7cf1 100644
--- a/tests/system-test/2-query/diff.py
+++ b/tests/system-test/2-query/diff.py
@@ -1,3 +1,4 @@
+from wsgiref.headers import tspecials
from util.log import *
from util.cases import *
from util.sql import *
@@ -27,6 +28,36 @@ class TDTestCase:
def run(self):
tdSql.prepare()
+ tdSql.execute("create table ntb(ts timestamp,c1 int,c2 double,c3 float)")
+ tdSql.execute("insert into ntb values(now,1,1.0,10.5)(now+1s,10,-100.0,5.1)(now+10s,-1,15.1,5.0)")
+
+ tdSql.query("select diff(c1,0) from ntb")
+ tdSql.checkRows(2)
+ tdSql.checkData(0,0,9)
+ tdSql.checkData(1,0,-11)
+ tdSql.query("select diff(c1,1) from ntb")
+ tdSql.checkRows(2)
+ tdSql.checkData(0,0,9)
+ tdSql.checkData(1,0,None)
+
+ tdSql.query("select diff(c2,0) from ntb")
+ tdSql.checkRows(2)
+ tdSql.checkData(0,0,-101)
+ tdSql.checkData(1,0,115.1)
+ tdSql.query("select diff(c2,1) from ntb")
+ tdSql.checkRows(2)
+ tdSql.checkData(0,0,None)
+ tdSql.checkData(1,0,115.1)
+
+ tdSql.query("select diff(c3,0) from ntb")
+ tdSql.checkRows(2)
+ tdSql.checkData(0,0,-5.4)
+ tdSql.checkData(1,0,-0.1)
+ tdSql.query("select diff(c3,1) from ntb")
+ tdSql.checkRows(2)
+ tdSql.checkData(0,0,None)
+ tdSql.checkData(1,0,None)
+
tdSql.execute('''create table stb(ts timestamp, col1 tinyint, col2 smallint, col3 int, col4 bigint, col5 float, col6 double,
col7 bool, col8 binary(20), col9 nchar(20), col11 tinyint unsigned, col12 smallint unsigned, col13 int unsigned, col14 bigint unsigned) tags(loc nchar(20))''')
@@ -58,12 +89,6 @@ class TDTestCase:
tdSql.error("select diff(ts) from stb")
tdSql.error("select diff(ts) from stb_1")
- tdSql.error("select diff(col1) from stb")
- tdSql.error("select diff(col2) from stb")
- tdSql.error("select diff(col3) from stb")
- tdSql.error("select diff(col4) from stb")
- tdSql.error("select diff(col5) from stb")
- tdSql.error("select diff(col6) from stb")
tdSql.error("select diff(col7) from stb")
tdSql.error("select diff(col7) from stb_1")
tdSql.error("select diff(col8) from stb")
@@ -74,10 +99,6 @@ class TDTestCase:
tdSql.error("select diff(col12) from stb_1")
tdSql.error("select diff(col13) from stb_1")
tdSql.error("select diff(col14) from stb_1")
- tdSql.error("select diff(col11) from stb")
- tdSql.error("select diff(col12) from stb")
- tdSql.error("select diff(col13) from stb")
- tdSql.error("select diff(col14) from stb")
tdSql.query("select ts,diff(col1),ts from stb_1")
tdSql.checkRows(10)
@@ -88,14 +109,14 @@ class TDTestCase:
tdSql.checkData(9, 1, "2018-09-17 09:00:00.009")
tdSql.checkData(9, 3, "2018-09-17 09:00:00.009")
- tdSql.query("select ts,diff(col1),ts from stb group by tbname")
- tdSql.checkRows(10)
- tdSql.checkData(0, 0, "2018-09-17 09:00:00.000")
- tdSql.checkData(0, 1, "2018-09-17 09:00:00.000")
- tdSql.checkData(0, 3, "2018-09-17 09:00:00.000")
- tdSql.checkData(9, 0, "2018-09-17 09:00:00.009")
- tdSql.checkData(9, 1, "2018-09-17 09:00:00.009")
- tdSql.checkData(9, 3, "2018-09-17 09:00:00.009")
+ # tdSql.query("select ts,diff(col1),ts from stb group by tbname")
+ # tdSql.checkRows(10)
+ # tdSql.checkData(0, 0, "2018-09-17 09:00:00.000")
+ # tdSql.checkData(0, 1, "2018-09-17 09:00:00.000")
+ # tdSql.checkData(0, 3, "2018-09-17 09:00:00.000")
+ # tdSql.checkData(9, 0, "2018-09-17 09:00:00.009")
+ # tdSql.checkData(9, 1, "2018-09-17 09:00:00.009")
+ # tdSql.checkData(9, 3, "2018-09-17 09:00:00.009")
tdSql.query("select ts,diff(col1),ts from stb_1")
tdSql.checkRows(10)
@@ -106,14 +127,14 @@ class TDTestCase:
tdSql.checkData(9, 1, "2018-09-17 09:00:00.009")
tdSql.checkData(9, 3, "2018-09-17 09:00:00.009")
- tdSql.query("select ts,diff(col1),ts from stb group by tbname")
- tdSql.checkRows(10)
- tdSql.checkData(0, 0, "2018-09-17 09:00:00.000")
- tdSql.checkData(0, 1, "2018-09-17 09:00:00.000")
- tdSql.checkData(0, 3, "2018-09-17 09:00:00.000")
- tdSql.checkData(9, 0, "2018-09-17 09:00:00.009")
- tdSql.checkData(9, 1, "2018-09-17 09:00:00.009")
- tdSql.checkData(9, 3, "2018-09-17 09:00:00.009")
+ # tdSql.query("select ts,diff(col1),ts from stb group by tbname")
+ # tdSql.checkRows(10)
+ # tdSql.checkData(0, 0, "2018-09-17 09:00:00.000")
+ # tdSql.checkData(0, 1, "2018-09-17 09:00:00.000")
+ # tdSql.checkData(0, 3, "2018-09-17 09:00:00.000")
+ # tdSql.checkData(9, 0, "2018-09-17 09:00:00.009")
+ # tdSql.checkData(9, 1, "2018-09-17 09:00:00.009")
+ # tdSql.checkData(9, 3, "2018-09-17 09:00:00.009")
tdSql.query("select diff(col1) from stb_1")
tdSql.checkRows(10)
diff --git a/tests/system-test/fulltest.sh b/tests/system-test/fulltest.sh
index f713f707cb..4009f10d70 100755
--- a/tests/system-test/fulltest.sh
+++ b/tests/system-test/fulltest.sh
@@ -31,8 +31,8 @@ python3 ./test.py -f 2-query/last.py
#python3 ./test.py -f 2-query/To_iso8601.py
python3 ./test.py -f 2-query/To_unixtimestamp.py
python3 ./test.py -f 2-query/timetruncate.py
-
-# python3 ./test.py -f 2-query/Timediff.py
+# python3 ./test.py -f 2-query/diff.py
+python3 ./test.py -f 2-query/Timediff.py
#python3 ./test.py -f 2-query/cast.py
diff --git a/tools/taos-tools b/tools/taos-tools
index 2f3dfddd4d..0ae9f872c2 160000
--- a/tools/taos-tools
+++ b/tools/taos-tools
@@ -1 +1 @@
-Subproject commit 2f3dfddd4d9a869e706ba3cf98fb6d769404cd7c
+Subproject commit 0ae9f872c26d5da8cb61aa9eb00b5c7aeba10ec4