remove old dnode files
This commit is contained in:
parent
676819f31f
commit
a0aa00b51d
|
@ -1,6 +0,0 @@
|
|||
aux_source_directory(source DNODE_SRC)
|
||||
add_executable(taosd ${DNODE_SRC})
|
||||
target_link_libraries(
|
||||
taosd
|
||||
PRIVATE os
|
||||
)
|
|
@ -1,63 +0,0 @@
|
|||
CMAKE_MINIMUM_REQUIRED(VERSION 2.8...3.20)
|
||||
PROJECT(TDengine)
|
||||
|
||||
INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/query/inc)
|
||||
INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/mnode/inc)
|
||||
INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/tsdb/inc)
|
||||
INCLUDE_DIRECTORIES(${TD_COMMUNITY_DIR}/src/sync/inc)
|
||||
INCLUDE_DIRECTORIES(${TD_ENTERPRISE_DIR}/src/inc)
|
||||
|
||||
INCLUDE_DIRECTORIES(inc)
|
||||
AUX_SOURCE_DIRECTORY(src SRC)
|
||||
|
||||
IF (TD_LINUX_64 AND JEMALLOC_ENABLED)
|
||||
ADD_DEFINITIONS(-DTD_JEMALLOC_ENABLED -I${CMAKE_BINARY_DIR}/build/include -L${CMAKE_BINARY_DIR}/build/lib -Wl,-rpath,${CMAKE_BINARY_DIR}/build/lib -ljemalloc)
|
||||
SET(LINK_JEMALLOC "-L${CMAKE_BINARY_DIR}/build/lib -ljemalloc")
|
||||
ELSE ()
|
||||
SET(LINK_JEMALLOC "")
|
||||
ENDIF ()
|
||||
|
||||
ADD_EXECUTABLE(taosd ${SRC})
|
||||
TARGET_LINK_LIBRARIES(taosd mnode monitor http tsdb twal vnode cJson lua lz4 balance sync ${LINK_JEMALLOC})
|
||||
|
||||
IF (TD_SOMODE_STATIC)
|
||||
TARGET_LINK_LIBRARIES(taosd taos_static)
|
||||
ELSE ()
|
||||
TARGET_LINK_LIBRARIES(taosd taos)
|
||||
ENDIF ()
|
||||
|
||||
IF (TD_ACCOUNT)
|
||||
TARGET_LINK_LIBRARIES(taosd account)
|
||||
ENDIF ()
|
||||
|
||||
IF (TD_GRANT)
|
||||
TARGET_LINK_LIBRARIES(taosd grant)
|
||||
ENDIF ()
|
||||
|
||||
IF (TD_MQTT)
|
||||
TARGET_LINK_LIBRARIES(taosd mqtt)
|
||||
ENDIF ()
|
||||
|
||||
IF (TD_TOPIC)
|
||||
TARGET_LINK_LIBRARIES(taosd topic)
|
||||
ENDIF ()
|
||||
|
||||
IF (TD_MODULE AND TD_LINUX)
|
||||
TARGET_LINK_LIBRARIES(taosd module dl)
|
||||
ENDIF ()
|
||||
|
||||
SET(PREPARE_ENV_CMD "prepare_env_cmd")
|
||||
SET(PREPARE_ENV_TARGET "prepare_env_target")
|
||||
ADD_CUSTOM_COMMAND(OUTPUT ${PREPARE_ENV_CMD}
|
||||
POST_BUILD
|
||||
COMMAND echo "make test directory"
|
||||
DEPENDS taosd
|
||||
COMMAND ${CMAKE_COMMAND} -E make_directory ${TD_TESTS_OUTPUT_DIR}/cfg/
|
||||
COMMAND ${CMAKE_COMMAND} -E make_directory ${TD_TESTS_OUTPUT_DIR}/log/
|
||||
COMMAND ${CMAKE_COMMAND} -E make_directory ${TD_TESTS_OUTPUT_DIR}/data/
|
||||
COMMAND ${CMAKE_COMMAND} -E echo dataDir ${TD_TESTS_OUTPUT_DIR}/data > ${TD_TESTS_OUTPUT_DIR}/cfg/taos.cfg
|
||||
COMMAND ${CMAKE_COMMAND} -E echo logDir ${TD_TESTS_OUTPUT_DIR}/log >> ${TD_TESTS_OUTPUT_DIR}/cfg/taos.cfg
|
||||
COMMAND ${CMAKE_COMMAND} -E echo charset UTF-8 >> ${TD_TESTS_OUTPUT_DIR}/cfg/taos.cfg
|
||||
COMMAND ${CMAKE_COMMAND} -E echo monitor 0 >> ${TD_TESTS_OUTPUT_DIR}/cfg/taos.cfg
|
||||
COMMENT "prepare taosd environment")
|
||||
ADD_CUSTOM_TARGET(${PREPARE_ENV_TARGET} ALL WORKING_DIRECTORY ${TD_EXECUTABLE_OUTPUT_PATH} DEPENDS ${PREPARE_ENV_CMD})
|
|
@ -1,36 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_CFG_H
|
||||
#define TDENGINE_DNODE_CFG_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitCfg();
|
||||
void dnodeCleanupCfg();
|
||||
void dnodeUpdateCfg(SDnodeCfg *cfg);
|
||||
int32_t dnodeGetDnodeId();
|
||||
void dnodeGetClusterId(char *clusterId);
|
||||
void dnodeGetCfg(int32_t *dnodeId, char *clusterId);
|
||||
void dnodeSetDropped();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,31 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_CHECK_H
|
||||
#define TDENGINE_DNODE_CHECK_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitCheck();
|
||||
void dnodeCleanupCheck();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,34 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_EP_H
|
||||
#define TDENGINE_DNODE_EP_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitEps();
|
||||
void dnodeCleanupEps();
|
||||
void dnodeUpdateEps(SDnodeEps *eps);
|
||||
void dnodeUpdateEp(int32_t dnodeId, char *epstr, char *fqdn, uint16_t *port);
|
||||
bool dnodeCheckEpChanged(int32_t dnodeId, char *epstr);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,51 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_LOG_H
|
||||
#define TDENGINE_DNODE_LOG_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "taoserror.h"
|
||||
#include "taosmsg.h"
|
||||
#include "tlog.h"
|
||||
#include "trpc.h"
|
||||
#include "tglobal.h"
|
||||
#include "dnode.h"
|
||||
#include "vnode.h"
|
||||
|
||||
extern int32_t dDebugFlag;
|
||||
|
||||
#define dFatal(...) { if (dDebugFlag & DEBUG_FATAL) { taosPrintLog("DND FATAL ", 255, __VA_ARGS__); }}
|
||||
#define dError(...) { if (dDebugFlag & DEBUG_ERROR) { taosPrintLog("DND ERROR ", 255, __VA_ARGS__); }}
|
||||
#define dWarn(...) { if (dDebugFlag & DEBUG_WARN) { taosPrintLog("DND WARN ", 255, __VA_ARGS__); }}
|
||||
#define dInfo(...) { if (dDebugFlag & DEBUG_INFO) { taosPrintLog("DND ", 255, __VA_ARGS__); }}
|
||||
#define dDebug(...) { if (dDebugFlag & DEBUG_DEBUG) { taosPrintLog("DND ", dDebugFlag, __VA_ARGS__); }}
|
||||
#define dTrace(...) { if (dDebugFlag & DEBUG_TRACE) { taosPrintLog("DND ", dDebugFlag, __VA_ARGS__); }}
|
||||
|
||||
typedef enum {
|
||||
TSDB_RUN_STATUS_INITIALIZE,
|
||||
TSDB_RUN_STATUS_RUNING,
|
||||
TSDB_RUN_STATUS_STOPPED
|
||||
} SRunStatus;
|
||||
|
||||
SRunStatus dnodeGetRunStatus();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,39 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_MINFOS_H
|
||||
#define TDENGINE_DNODE_MINFOS_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitMInfos();
|
||||
void dnodeCleanupMInfos();
|
||||
void dnodeUpdateMInfos(SMInfos *pMinfos);
|
||||
void dnodeUpdateEpSetForPeer(SRpcEpSet *pEpSet);
|
||||
void dnodeGetMInfos(SMInfos *pMinfos);
|
||||
bool dnodeIsMasterEp(char *ep);
|
||||
|
||||
void dnodeSendRedirectMsg(SRpcMsg *rpcMsg, bool forShell);
|
||||
void dnodeGetEpSetForPeer(SRpcEpSet *epSet);
|
||||
void dnodeGetEpSetForShell(SRpcEpSet *epSet);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,34 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_MPEER_H
|
||||
#define TDENGINE_DNODE_MPEER_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitMPeer();
|
||||
void dnodeCleanupMPeer();
|
||||
int32_t dnodeAllocateMPeerQueue();
|
||||
void dnodeFreeMPeerQueue();
|
||||
void dnodeDispatchToMPeerQueue(SRpcMsg *pMsg);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,34 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_MREAD_H
|
||||
#define TDENGINE_DNODE_MREAD_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitMRead();
|
||||
void dnodeCleanupMRead();
|
||||
int32_t dnodeAllocMReadQueue();
|
||||
void dnodeFreeMReadQueue();
|
||||
void dnodeDispatchToMReadQueue(SRpcMsg *rpcMsg);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,34 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_MWRITE_H
|
||||
#define TDENGINE_DNODE_MWRITE_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitMWrite();
|
||||
void dnodeCleanupMWrite();
|
||||
int32_t dnodeAllocMWritequeue();
|
||||
void dnodeFreeMWritequeue();
|
||||
void dnodeDispatchToMWriteQueue(SRpcMsg *pMsg);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,31 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_MAIN_H
|
||||
#define TDENGINE_DNODE_MAIN_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitSystem();
|
||||
void dnodeCleanUpSystem();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,32 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_MODULE_H
|
||||
#define TDENGINE_DNODE_MODULE_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitModules();
|
||||
void dnodeCleanupModules();
|
||||
int32_t dnodeStartMnode(SMInfos *pMinfos);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,33 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_PEER_H
|
||||
#define TDENGINE_DNODE_PEER_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitServer();
|
||||
void dnodeCleanupServer();
|
||||
int32_t dnodeInitClient();
|
||||
void dnodeCleanupClient();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,31 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_SHELL_H
|
||||
#define TDENGINE_DNODE_SHELL_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitShell();
|
||||
void dnodeCleanupShell();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,33 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_STEP_H
|
||||
#define TDENGINE_DNODE_STEP_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeStepInit(SStep *pSteps, int32_t stepSize);
|
||||
void dnodeStepCleanup(SStep *pSteps, int32_t stepSize);
|
||||
void dnodeReportStep(char *name, char *desc, int8_t finished);
|
||||
void dnodeSendStartupStep(SRpcMsg *pMsg);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,31 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2020 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_TELEMETRY_H
|
||||
#define TDENGINE_DNODE_TELEMETRY_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitTelemetry();
|
||||
void dnodeCleanupTelemetry();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,32 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_VMGMT_H
|
||||
#define TDENGINE_DNODE_VMGMT_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitVMgmt();
|
||||
void dnodeCleanupVMgmt();
|
||||
void dnodeDispatchToVMgmtQueue(SRpcMsg *rpcMsg);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,36 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_VREAD_H
|
||||
#define TDENGINE_DNODE_VREAD_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitVRead();
|
||||
void dnodeCleanupVRead();
|
||||
void dnodeDispatchToVReadQueue(SRpcMsg *pMsg);
|
||||
void * dnodeAllocVQueryQueue(void *pVnode);
|
||||
void * dnodeAllocVFetchQueue(void *pVnode);
|
||||
void dnodeFreeVQueryQueue(void *pQqueue);
|
||||
void dnodeFreeVFetchQueue(void *pFqueue);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,35 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_VWRITE_H
|
||||
#define TDENGINE_DNODE_VWRITE_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitVWrite();
|
||||
void dnodeCleanupVWrite();
|
||||
void dnodeDispatchToVWriteQueue(SRpcMsg *pMsg);
|
||||
void * dnodeAllocVWriteQueue(void *pVnode);
|
||||
void dnodeFreeVWriteQueue(void *pWqueue);
|
||||
void dnodeSendRpcVWriteRsp(void *pVnode, void *pWrite, int32_t code);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,34 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef TDENGINE_DNODE_VNODES_H
|
||||
#define TDENGINE_DNODE_VNODES_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include "dnodeInt.h"
|
||||
|
||||
int32_t dnodeInitVnodes();
|
||||
void dnodeCleanupVnodes();
|
||||
int32_t dnodeInitStatusTimer();
|
||||
void dnodeCleanupStatusTimer();
|
||||
void dnodeSendStatusMsgToMnode();
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
|
@ -1,20 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#include "os.h"
|
||||
|
||||
int main(int argc, char const *argv[]) {
|
||||
printf("Hello world!\n");
|
||||
return 0;
|
||||
}
|
|
@ -1,190 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "cJSON.h"
|
||||
#include "dnodeCfg.h"
|
||||
#include "tglobal.h"
|
||||
|
||||
static SDnodeCfg tsCfg = {0};
|
||||
static pthread_mutex_t tsCfgMutex;
|
||||
static int32_t tsDnodeDropped;
|
||||
|
||||
static int32_t dnodeReadCfg();
|
||||
static int32_t dnodeWriteCfg();
|
||||
static void dnodeResetCfg(SDnodeCfg *cfg);
|
||||
static void dnodePrintCfg(SDnodeCfg *cfg);
|
||||
|
||||
int32_t dnodeInitCfg() {
|
||||
pthread_mutex_init(&tsCfgMutex, NULL);
|
||||
dnodeResetCfg(NULL);
|
||||
int32_t ret = dnodeReadCfg();
|
||||
if (ret == 0) {
|
||||
dInfo("dnode cfg is initialized");
|
||||
}
|
||||
if (tsDnodeDropped) {
|
||||
dInfo("dnode is dropped, exiting");
|
||||
return -1;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
void dnodeCleanupCfg() { pthread_mutex_destroy(&tsCfgMutex); }
|
||||
|
||||
void dnodeUpdateCfg(SDnodeCfg *cfg) {
|
||||
if (tsCfg.dnodeId != 0) return;
|
||||
dnodeResetCfg(cfg);
|
||||
}
|
||||
|
||||
void dnodeSetDropped() {
|
||||
pthread_mutex_lock(&tsCfgMutex);
|
||||
tsDnodeDropped = 1;
|
||||
|
||||
dnodeWriteCfg();
|
||||
pthread_mutex_unlock(&tsCfgMutex);
|
||||
}
|
||||
|
||||
int32_t dnodeGetDnodeId() {
|
||||
int32_t dnodeId = 0;
|
||||
pthread_mutex_lock(&tsCfgMutex);
|
||||
dnodeId = tsCfg.dnodeId;
|
||||
pthread_mutex_unlock(&tsCfgMutex);
|
||||
return dnodeId;
|
||||
}
|
||||
|
||||
void dnodeGetClusterId(char *clusterId) {
|
||||
pthread_mutex_lock(&tsCfgMutex);
|
||||
tstrncpy(clusterId, tsCfg.clusterId, TSDB_CLUSTER_ID_LEN);
|
||||
pthread_mutex_unlock(&tsCfgMutex);
|
||||
}
|
||||
|
||||
void dnodeGetCfg(int32_t *dnodeId, char *clusterId) {
|
||||
pthread_mutex_lock(&tsCfgMutex);
|
||||
*dnodeId = tsCfg.dnodeId;
|
||||
tstrncpy(clusterId, tsCfg.clusterId, TSDB_CLUSTER_ID_LEN);
|
||||
pthread_mutex_unlock(&tsCfgMutex);
|
||||
}
|
||||
|
||||
static void dnodeResetCfg(SDnodeCfg *cfg) {
|
||||
if (cfg == NULL) return;
|
||||
if (cfg->dnodeId == 0) return;
|
||||
|
||||
pthread_mutex_lock(&tsCfgMutex);
|
||||
tsCfg.dnodeId = cfg->dnodeId;
|
||||
tsDnodeId = cfg->dnodeId;
|
||||
tstrncpy(tsCfg.clusterId, cfg->clusterId, TSDB_CLUSTER_ID_LEN);
|
||||
dnodePrintCfg(cfg);
|
||||
dnodeWriteCfg();
|
||||
pthread_mutex_unlock(&tsCfgMutex);
|
||||
}
|
||||
|
||||
static void dnodePrintCfg(SDnodeCfg *cfg) {
|
||||
dInfo("dnodeId is set to %d, clusterId is set to %s", cfg->dnodeId, cfg->clusterId);
|
||||
}
|
||||
|
||||
static int32_t dnodeReadCfg() {
|
||||
int32_t len = 0;
|
||||
int32_t maxLen = 200;
|
||||
char * content = calloc(1, maxLen + 1);
|
||||
cJSON * root = NULL;
|
||||
FILE * fp = NULL;
|
||||
SDnodeCfg cfg = {0};
|
||||
|
||||
char file[TSDB_FILENAME_LEN + 20] = {0};
|
||||
sprintf(file, "%s/dnodeCfg.json", tsDnodeDir);
|
||||
|
||||
fp = fopen(file, "r");
|
||||
if (!fp) {
|
||||
dDebug("failed to read %s, file not exist", file);
|
||||
goto PARSE_CFG_OVER;
|
||||
}
|
||||
|
||||
len = (int32_t)fread(content, 1, maxLen, fp);
|
||||
if (len <= 0) {
|
||||
dError("failed to read %s, content is null", file);
|
||||
goto PARSE_CFG_OVER;
|
||||
}
|
||||
|
||||
content[len] = 0;
|
||||
root = cJSON_Parse(content);
|
||||
if (root == NULL) {
|
||||
dError("failed to read %s, invalid json format", file);
|
||||
goto PARSE_CFG_OVER;
|
||||
}
|
||||
|
||||
cJSON *dnodeId = cJSON_GetObjectItem(root, "dnodeId");
|
||||
if (!dnodeId || dnodeId->type != cJSON_Number) {
|
||||
dError("failed to read %s, dnodeId not found", file);
|
||||
goto PARSE_CFG_OVER;
|
||||
}
|
||||
cfg.dnodeId = (int32_t)dnodeId->valueint;
|
||||
|
||||
cJSON *dnodeDropped = cJSON_GetObjectItem(root, "dnodeDropped");
|
||||
if (!dnodeDropped || dnodeDropped->type != cJSON_Number) {
|
||||
dError("failed to read %s, dnodeDropped not found", file);
|
||||
//goto PARSE_CFG_OVER;
|
||||
} else {
|
||||
tsDnodeDropped = (int32_t)dnodeDropped->valueint;
|
||||
}
|
||||
|
||||
cJSON *clusterId = cJSON_GetObjectItem(root, "clusterId");
|
||||
if (!clusterId || clusterId->type != cJSON_String) {
|
||||
dError("failed to read %s, clusterId not found", file);
|
||||
goto PARSE_CFG_OVER;
|
||||
}
|
||||
tstrncpy(cfg.clusterId, clusterId->valuestring, TSDB_CLUSTER_ID_LEN);
|
||||
|
||||
dInfo("read file %s successed", file);
|
||||
|
||||
PARSE_CFG_OVER:
|
||||
if (content != NULL) free(content);
|
||||
if (root != NULL) cJSON_Delete(root);
|
||||
if (fp != NULL) fclose(fp);
|
||||
terrno = 0;
|
||||
|
||||
dnodeResetCfg(&cfg);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeWriteCfg() {
|
||||
char file[TSDB_FILENAME_LEN + 20] = {0};
|
||||
sprintf(file, "%s/dnodeCfg.json", tsDnodeDir);
|
||||
|
||||
FILE *fp = fopen(file, "w");
|
||||
if (!fp) {
|
||||
dError("failed to write %s, reason:%s", file, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
int32_t len = 0;
|
||||
int32_t maxLen = 200;
|
||||
char * content = calloc(1, maxLen + 1);
|
||||
|
||||
len += snprintf(content + len, maxLen - len, "{\n");
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodeId\": %d,\n", tsCfg.dnodeId);
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodeDropped\": %d,\n", tsDnodeDropped);
|
||||
len += snprintf(content + len, maxLen - len, " \"clusterId\": \"%s\"\n", tsCfg.clusterId);
|
||||
len += snprintf(content + len, maxLen - len, "}\n");
|
||||
|
||||
fwrite(content, 1, len, fp);
|
||||
taosFsync(fileno(fp));
|
||||
fclose(fp);
|
||||
free(content);
|
||||
terrno = 0;
|
||||
|
||||
dInfo("successed to write %s", file);
|
||||
return 0;
|
||||
}
|
|
@ -1,265 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "dnodeCheck.h"
|
||||
|
||||
typedef struct {
|
||||
bool enable;
|
||||
char * name;
|
||||
int32_t (*initFp)();
|
||||
int32_t (*startFp)();
|
||||
void (*cleanUpFp)();
|
||||
void (*stopFp)();
|
||||
} SCheckItem;
|
||||
|
||||
static SCheckItem tsCheckItem[TSDB_CHECK_ITEM_MAX] = {{0}};
|
||||
int64_t tsMinFreeMemSizeForStart = 0;
|
||||
|
||||
static int32_t bindTcpPort(uint16_t port) {
|
||||
SOCKET serverSocket;
|
||||
struct sockaddr_in server_addr;
|
||||
|
||||
if ((serverSocket = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0) {
|
||||
dError("socket() fail: %s", strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
bzero(&server_addr, sizeof(server_addr));
|
||||
server_addr.sin_family = AF_INET;
|
||||
server_addr.sin_port = htons(port);
|
||||
server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
|
||||
|
||||
if (bind(serverSocket, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) {
|
||||
dError("port:%d tcp bind() fail: %s", port, strerror(errno));
|
||||
taosCloseSocket(serverSocket);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (listen(serverSocket, 5) < 0) {
|
||||
dError("port:%d listen() fail: %s", port, strerror(errno));
|
||||
taosCloseSocket(serverSocket);
|
||||
return -1;
|
||||
}
|
||||
|
||||
taosCloseSocket(serverSocket);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t bindUdpPort(int16_t port) {
|
||||
SOCKET serverSocket;
|
||||
struct sockaddr_in server_addr;
|
||||
|
||||
if ((serverSocket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP)) < 0) {
|
||||
dError("socket() fail: %s", strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
bzero(&server_addr, sizeof(server_addr));
|
||||
server_addr.sin_family = AF_INET;
|
||||
server_addr.sin_port = htons(port);
|
||||
server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
|
||||
|
||||
if (bind(serverSocket, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0) {
|
||||
dError("port:%d udp bind() fail: %s", port, strerror(errno));
|
||||
taosCloseSocket(serverSocket);
|
||||
return -1;
|
||||
}
|
||||
|
||||
taosCloseSocket(serverSocket);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckNetwork() {
|
||||
int32_t ret;
|
||||
uint16_t startPort = tsServerPort;
|
||||
|
||||
for (uint16_t port = startPort; port < startPort + 12; port++) {
|
||||
ret = bindTcpPort(port);
|
||||
if (0 != ret) {
|
||||
dError("failed to tcp bind port %d, quit", port);
|
||||
return -1;
|
||||
}
|
||||
ret = bindUdpPort(port);
|
||||
if (0 != ret) {
|
||||
dError("failed to udp bind port %d, quit", port);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckMem() {
|
||||
float memoryUsedMB;
|
||||
float memoryAvailMB;
|
||||
if (true != taosGetSysMemory(&memoryUsedMB)) {
|
||||
dError("failed to get system mem infomation, errno:%u, reason:%s", errno, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
memoryAvailMB = (float)tsTotalMemoryMB - memoryUsedMB;
|
||||
|
||||
if (memoryAvailMB < tsMinFreeMemSizeForStart) {
|
||||
dError("free mem %f too little, quit", memoryAvailMB);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckCpu() {
|
||||
// TODO:
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckDisk() {
|
||||
taosGetDisk();
|
||||
|
||||
if (tsAvailDataDirGB < tsMinimalDataDirGB) {
|
||||
dError("free disk size: %f GB, too little, quit", tsAvailDataDirGB);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (tsAvailLogDirGB < tsMinimalLogDirGB) {
|
||||
dError("free disk size: %f GB, too little, quit", tsAvailLogDirGB);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (tsAvailTmpDirectorySpace < tsReservedTmpDirectorySpace) {
|
||||
dError("free disk size: %f GB, too little, quit", tsAvailTmpDirectorySpace);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckOs() {
|
||||
// TODO:
|
||||
|
||||
return 0;
|
||||
}
|
||||
static int32_t dnodeCheckAccess() {
|
||||
// TODO:
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckVersion() {
|
||||
// TODO:
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeCheckDatafile() {
|
||||
// TODO:
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void dnodeAllocCheckItem() {
|
||||
tsCheckItem[TSDB_CHECK_ITEM_NETWORK].enable = false;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_NETWORK].name = "network";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_NETWORK].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_NETWORK].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_NETWORK].startFp = dnodeCheckNetwork;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_NETWORK].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_MEM].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_MEM].name = "mem";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_MEM].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_MEM].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_MEM].startFp = dnodeCheckMem;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_MEM].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_CPU].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_CPU].name = "cpu";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_CPU].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_CPU].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_CPU].startFp = dnodeCheckCpu;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_CPU].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DISK].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DISK].name = "disk";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DISK].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DISK].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DISK].startFp = dnodeCheckDisk;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DISK].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_OS].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_OS].name = "os";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_OS].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_OS].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_OS].startFp = dnodeCheckOs;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_OS].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_ACCESS].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_ACCESS].name = "access";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_ACCESS].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_ACCESS].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_ACCESS].startFp = dnodeCheckAccess;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_ACCESS].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_VERSION].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_VERSION].name = "version";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_VERSION].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_VERSION].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_VERSION].startFp = dnodeCheckVersion;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_VERSION].stopFp = NULL;
|
||||
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DATAFILE].enable = true;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DATAFILE].name = "datafile";
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DATAFILE].initFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DATAFILE].cleanUpFp = NULL;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DATAFILE].startFp = dnodeCheckDatafile;
|
||||
tsCheckItem[TSDB_CHECK_ITEM_DATAFILE].stopFp = NULL;
|
||||
}
|
||||
|
||||
void dnodeCleanupCheck() {
|
||||
for (ECheckItemType index = 0; index < TSDB_CHECK_ITEM_MAX; ++index) {
|
||||
if (tsCheckItem[index].enable && tsCheckItem[index].stopFp) {
|
||||
(*tsCheckItem[index].stopFp)();
|
||||
}
|
||||
if (tsCheckItem[index].cleanUpFp) {
|
||||
(*tsCheckItem[index].cleanUpFp)();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int32_t dnodeInitCheck() {
|
||||
dnodeAllocCheckItem();
|
||||
|
||||
for (ECheckItemType index = 0; index < TSDB_CHECK_ITEM_MAX; ++index) {
|
||||
if (tsCheckItem[index].initFp) {
|
||||
if ((*tsCheckItem[index].initFp)() != 0) {
|
||||
dError("failed to init check item:%s", tsCheckItem[index].name);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (ECheckItemType index = 0; index < TSDB_CHECK_ITEM_MAX; ++index) {
|
||||
if (tsCheckItem[index].enable && tsCheckItem[index].startFp) {
|
||||
if ((*tsCheckItem[index].startFp)() != 0) {
|
||||
dError("failed to check item:%s", tsCheckItem[index].name);
|
||||
exit(-1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dInfo("dnode check is initialized");
|
||||
return 0;
|
||||
}
|
|
@ -1,287 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "cJSON.h"
|
||||
#include "hash.h"
|
||||
#include "dnodeEps.h"
|
||||
|
||||
static SDnodeEps *tsEps = NULL;
|
||||
static SHashObj * tsEpsHash = NULL;
|
||||
static pthread_mutex_t tsEpsMutex;
|
||||
|
||||
static int32_t dnodeReadEps();
|
||||
static int32_t dnodeWriteEps();
|
||||
static void dnodeResetEps(SDnodeEps *eps);
|
||||
static void dnodePrintEps(SDnodeEps *eps);
|
||||
|
||||
int32_t dnodeInitEps() {
|
||||
pthread_mutex_init(&tsEpsMutex, NULL);
|
||||
tsEpsHash = taosHashInit(4, taosGetDefaultHashFunction(TSDB_DATA_TYPE_INT), true, HASH_ENTRY_LOCK);
|
||||
dnodeResetEps(NULL);
|
||||
int32_t ret = dnodeReadEps();
|
||||
if (ret == 0) {
|
||||
dInfo("dnode eps is initialized");
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
void dnodeCleanupEps() {
|
||||
pthread_mutex_lock(&tsEpsMutex);
|
||||
if (tsEps) {
|
||||
free(tsEps);
|
||||
tsEps = NULL;
|
||||
}
|
||||
if (tsEpsHash) {
|
||||
taosHashCleanup(tsEpsHash);
|
||||
tsEpsHash = NULL;
|
||||
}
|
||||
pthread_mutex_unlock(&tsEpsMutex);
|
||||
pthread_mutex_destroy(&tsEpsMutex);
|
||||
}
|
||||
|
||||
void dnodeUpdateEps(SDnodeEps *eps) {
|
||||
if (eps == NULL) return;
|
||||
|
||||
eps->dnodeNum = htonl(eps->dnodeNum);
|
||||
for (int32_t i = 0; i < eps->dnodeNum; ++i) {
|
||||
eps->dnodeEps[i].dnodeId = htonl(eps->dnodeEps[i].dnodeId);
|
||||
eps->dnodeEps[i].dnodePort = htons(eps->dnodeEps[i].dnodePort);
|
||||
}
|
||||
|
||||
pthread_mutex_lock(&tsEpsMutex);
|
||||
if (eps->dnodeNum != tsEps->dnodeNum) {
|
||||
dnodeResetEps(eps);
|
||||
dnodeWriteEps();
|
||||
} else {
|
||||
int32_t size = sizeof(SDnodeEps) + eps->dnodeNum * sizeof(SDnodeEp);
|
||||
if (memcmp(eps, tsEps, size) != 0) {
|
||||
dnodeResetEps(eps);
|
||||
dnodeWriteEps();
|
||||
}
|
||||
}
|
||||
pthread_mutex_unlock(&tsEpsMutex);
|
||||
}
|
||||
|
||||
bool dnodeCheckEpChanged(int32_t dnodeId, char *epstr) {
|
||||
bool changed = false;
|
||||
pthread_mutex_lock(&tsEpsMutex);
|
||||
SDnodeEp *ep = taosHashGet(tsEpsHash, &dnodeId, sizeof(int32_t));
|
||||
if (ep != NULL) {
|
||||
char epSaved[TSDB_EP_LEN + 1];
|
||||
snprintf(epSaved, TSDB_EP_LEN, "%s:%u", ep->dnodeFqdn, ep->dnodePort);
|
||||
changed = strcmp(epstr, epSaved) != 0;
|
||||
tstrncpy(epstr, epSaved, TSDB_EP_LEN);
|
||||
}
|
||||
pthread_mutex_unlock(&tsEpsMutex);
|
||||
return changed;
|
||||
}
|
||||
|
||||
void dnodeUpdateEp(int32_t dnodeId, char *epstr, char *fqdn, uint16_t *port) {
|
||||
pthread_mutex_lock(&tsEpsMutex);
|
||||
SDnodeEp *ep = taosHashGet(tsEpsHash, &dnodeId, sizeof(int32_t));
|
||||
if (ep != NULL) {
|
||||
if (port) *port = ep->dnodePort;
|
||||
if (fqdn) tstrncpy(fqdn, ep->dnodeFqdn, TSDB_FQDN_LEN);
|
||||
if (epstr) snprintf(epstr, TSDB_EP_LEN, "%s:%u", ep->dnodeFqdn, ep->dnodePort);
|
||||
}
|
||||
pthread_mutex_unlock(&tsEpsMutex);
|
||||
}
|
||||
|
||||
static void dnodeResetEps(SDnodeEps *eps) {
|
||||
if (eps == NULL) {
|
||||
int32_t size = sizeof(SDnodeEps) + sizeof(SDnodeEp);
|
||||
if (tsEps == NULL) {
|
||||
tsEps = calloc(1, size);
|
||||
} else {
|
||||
tsEps->dnodeNum = 0;
|
||||
}
|
||||
} else {
|
||||
assert(tsEps);
|
||||
|
||||
int32_t size = sizeof(SDnodeEps) + sizeof(SDnodeEp) * eps->dnodeNum;
|
||||
if (eps->dnodeNum > tsEps->dnodeNum) {
|
||||
tsEps = realloc(tsEps, size);
|
||||
}
|
||||
memcpy(tsEps, eps, size);
|
||||
dnodePrintEps(eps);
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < tsEps->dnodeNum; ++i) {
|
||||
SDnodeEp *ep = &tsEps->dnodeEps[i];
|
||||
taosHashPut(tsEpsHash, &ep->dnodeId, sizeof(int32_t), ep, sizeof(SDnodeEp));
|
||||
}
|
||||
}
|
||||
|
||||
static void dnodePrintEps(SDnodeEps *eps) {
|
||||
dDebug("print dnodeEp, dnodeNum:%d", eps->dnodeNum);
|
||||
for (int32_t i = 0; i < eps->dnodeNum; i++) {
|
||||
SDnodeEp *ep = &eps->dnodeEps[i];
|
||||
dDebug("dnode:%d, dnodeFqdn:%s dnodePort:%u", ep->dnodeId, ep->dnodeFqdn, ep->dnodePort);
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeReadEps() {
|
||||
int32_t ret = -1;
|
||||
int32_t len = 0;
|
||||
int32_t maxLen = 30000;
|
||||
char * content = calloc(1, maxLen + 1);
|
||||
cJSON * root = NULL;
|
||||
FILE * fp = NULL;
|
||||
SDnodeEps *eps = NULL;
|
||||
|
||||
char file[TSDB_FILENAME_LEN + 20] = {0};
|
||||
sprintf(file, "%s/dnodeEps.json", tsDnodeDir);
|
||||
|
||||
fp = fopen(file, "r");
|
||||
if (!fp) {
|
||||
dDebug("failed to read %s, file not exist", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
|
||||
len = (int32_t)fread(content, 1, maxLen, fp);
|
||||
if (len <= 0) {
|
||||
dError("failed to read %s, content is null", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
|
||||
content[len] = 0;
|
||||
root = cJSON_Parse(content);
|
||||
if (root == NULL) {
|
||||
dError("failed to read %s, invalid json format", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
|
||||
cJSON *dnodeNum = cJSON_GetObjectItem(root, "dnodeNum");
|
||||
if (!dnodeNum || dnodeNum->type != cJSON_Number) {
|
||||
dError("failed to read %s, dnodeNum not found", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
|
||||
cJSON *dnodeInfos = cJSON_GetObjectItem(root, "dnodeInfos");
|
||||
if (!dnodeInfos || dnodeInfos->type != cJSON_Array) {
|
||||
dError("failed to read %s, dnodeInfos not found", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
|
||||
int32_t dnodeInfosSize = cJSON_GetArraySize(dnodeInfos);
|
||||
if (dnodeInfosSize != dnodeNum->valueint) {
|
||||
dError("failed to read %s, dnodeInfos size:%d not matched dnodeNum:%d", file, dnodeInfosSize,
|
||||
(int32_t)dnodeNum->valueint);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
|
||||
int32_t epsSize = sizeof(SDnodeEps) + dnodeInfosSize * sizeof(SDnodeEp);
|
||||
eps = calloc(1, epsSize);
|
||||
eps->dnodeNum = dnodeInfosSize;
|
||||
|
||||
for (int32_t i = 0; i < dnodeInfosSize; ++i) {
|
||||
cJSON *dnodeInfo = cJSON_GetArrayItem(dnodeInfos, i);
|
||||
if (dnodeInfo == NULL) break;
|
||||
|
||||
SDnodeEp *ep = &eps->dnodeEps[i];
|
||||
|
||||
cJSON *dnodeId = cJSON_GetObjectItem(dnodeInfo, "dnodeId");
|
||||
if (!dnodeId || dnodeId->type != cJSON_Number) {
|
||||
dError("failed to read %s, dnodeId not found", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
ep->dnodeId = (int32_t)dnodeId->valueint;
|
||||
|
||||
cJSON *dnodeFqdn = cJSON_GetObjectItem(dnodeInfo, "dnodeFqdn");
|
||||
if (!dnodeFqdn || dnodeFqdn->type != cJSON_String || dnodeFqdn->valuestring == NULL) {
|
||||
dError("failed to read %s, dnodeFqdn not found", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
strncpy(ep->dnodeFqdn, dnodeFqdn->valuestring, TSDB_FQDN_LEN);
|
||||
|
||||
cJSON *dnodePort = cJSON_GetObjectItem(dnodeInfo, "dnodePort");
|
||||
if (!dnodePort || dnodePort->type != cJSON_Number) {
|
||||
dError("failed to read %s, dnodePort not found", file);
|
||||
goto PRASE_EPS_OVER;
|
||||
}
|
||||
ep->dnodePort = (uint16_t)dnodePort->valueint;
|
||||
}
|
||||
|
||||
ret = 0;
|
||||
|
||||
dInfo("read file %s successed", file);
|
||||
dnodePrintEps(eps);
|
||||
|
||||
PRASE_EPS_OVER:
|
||||
if (content != NULL) free(content);
|
||||
if (root != NULL) cJSON_Delete(root);
|
||||
if (fp != NULL) fclose(fp);
|
||||
if (ret != 0) {
|
||||
if (eps) free(eps);
|
||||
eps = NULL;
|
||||
}
|
||||
|
||||
dnodeResetEps(eps);
|
||||
if (eps) free(eps);
|
||||
|
||||
#if 0
|
||||
dnodeUpdateEp(dnodeGetDnodeId(), tsLocalEp, tsLocalFqdn, &tsServerPort);
|
||||
#else
|
||||
if (dnodeCheckEpChanged(dnodeGetDnodeId(), tsLocalEp)) {
|
||||
dError("dnode:%d, localEp is different from %s in dnodeEps.json and need reconfigured", dnodeGetDnodeId(), tsLocalEp);
|
||||
return -1;
|
||||
}
|
||||
#endif
|
||||
|
||||
terrno = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeWriteEps() {
|
||||
char file[TSDB_FILENAME_LEN + 20] = {0};
|
||||
sprintf(file, "%s/dnodeEps.json", tsDnodeDir);
|
||||
|
||||
FILE *fp = fopen(file, "w");
|
||||
if (!fp) {
|
||||
dError("failed to write %s, reason:%s", file, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
int32_t len = 0;
|
||||
int32_t maxLen = 30000;
|
||||
char * content = calloc(1, maxLen + 1);
|
||||
|
||||
len += snprintf(content + len, maxLen - len, "{\n");
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodeNum\": %d,\n", tsEps->dnodeNum);
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodeInfos\": [{\n");
|
||||
for (int32_t i = 0; i < tsEps->dnodeNum; ++i) {
|
||||
SDnodeEp *ep = &tsEps->dnodeEps[i];
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodeId\": %d,\n", ep->dnodeId);
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodeFqdn\": \"%s\",\n", ep->dnodeFqdn);
|
||||
len += snprintf(content + len, maxLen - len, " \"dnodePort\": %u\n", ep->dnodePort);
|
||||
if (i < tsEps->dnodeNum - 1) {
|
||||
len += snprintf(content + len, maxLen - len, " },{\n");
|
||||
} else {
|
||||
len += snprintf(content + len, maxLen - len, " }]\n");
|
||||
}
|
||||
}
|
||||
len += snprintf(content + len, maxLen - len, "}\n");
|
||||
|
||||
fwrite(content, 1, len, fp);
|
||||
taosFsync(fileno(fp));
|
||||
fclose(fp);
|
||||
free(content);
|
||||
terrno = 0;
|
||||
|
||||
dInfo("successed to write %s", file);
|
||||
return 0;
|
||||
}
|
|
@ -1,326 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "cJSON.h"
|
||||
#include "mnode.h"
|
||||
#include "dnodeMInfos.h"
|
||||
|
||||
static SMInfos tsMInfos;
|
||||
static SRpcEpSet tsMEpSet;
|
||||
static pthread_mutex_t tsMInfosMutex;
|
||||
|
||||
static void dnodeResetMInfos(SMInfos *minfos);
|
||||
static void dnodePrintMInfos(SMInfos *minfos);
|
||||
static int32_t dnodeReadMInfos();
|
||||
static int32_t dnodeWriteMInfos();
|
||||
|
||||
int32_t dnodeInitMInfos() {
|
||||
pthread_mutex_init(&tsMInfosMutex, NULL);
|
||||
dnodeResetMInfos(NULL);
|
||||
int32_t ret = dnodeReadMInfos();
|
||||
if (ret == 0) {
|
||||
dInfo("dnode minfos is initialized");
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
void dnodeCleanupMInfos() { pthread_mutex_destroy(&tsMInfosMutex); }
|
||||
|
||||
void dnodeUpdateMInfos(SMInfos *pMinfos) {
|
||||
if (pMinfos->mnodeNum <= 0 || pMinfos->mnodeNum > 3) {
|
||||
dError("invalid mnode infos, mnodeNum:%d", pMinfos->mnodeNum);
|
||||
return;
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < pMinfos->mnodeNum; ++i) {
|
||||
SMInfo *minfo = &pMinfos->mnodeInfos[i];
|
||||
minfo->mnodeId = htonl(minfo->mnodeId);
|
||||
if (minfo->mnodeId <= 0 || strlen(minfo->mnodeEp) <= 5) {
|
||||
dError("invalid mnode info:%d, mnodeId:%d mnodeEp:%s", i, minfo->mnodeId, minfo->mnodeEp);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
pthread_mutex_lock(&tsMInfosMutex);
|
||||
if (pMinfos->mnodeNum != tsMInfos.mnodeNum) {
|
||||
dnodeResetMInfos(pMinfos);
|
||||
dnodeWriteMInfos();
|
||||
sdbUpdateAsync();
|
||||
} else {
|
||||
int32_t size = sizeof(SMInfos);
|
||||
if (memcmp(pMinfos, &tsMInfos, size) != 0) {
|
||||
dnodeResetMInfos(pMinfos);
|
||||
dnodeWriteMInfos();
|
||||
sdbUpdateAsync();
|
||||
}
|
||||
}
|
||||
pthread_mutex_unlock(&tsMInfosMutex);
|
||||
}
|
||||
|
||||
void dnodeUpdateEpSetForPeer(SRpcEpSet *ep) {
|
||||
if (ep->numOfEps <= 0) {
|
||||
dError("minfos is changed, but content is invalid, discard it");
|
||||
return;
|
||||
}
|
||||
|
||||
pthread_mutex_lock(&tsMInfosMutex);
|
||||
dInfo("minfos is changed, numOfEps:%d inUse:%d", ep->numOfEps, ep->inUse);
|
||||
for (int32_t i = 0; i < ep->numOfEps; ++i) {
|
||||
ep->port[i] -= TSDB_PORT_DNODEDNODE;
|
||||
dInfo("minfo:%d %s:%u", i, ep->fqdn[i], ep->port[i]);
|
||||
}
|
||||
tsMEpSet = *ep;
|
||||
pthread_mutex_unlock(&tsMInfosMutex);
|
||||
}
|
||||
|
||||
bool dnodeIsMasterEp(char *ep) {
|
||||
pthread_mutex_lock(&tsMInfosMutex);
|
||||
bool isMaster = strcmp(ep, tsMInfos.mnodeInfos[tsMEpSet.inUse].mnodeEp) == 0;
|
||||
pthread_mutex_unlock(&tsMInfosMutex);
|
||||
|
||||
return isMaster;
|
||||
}
|
||||
|
||||
void dnodeGetMInfos(SMInfos *pMinfos) {
|
||||
pthread_mutex_lock(&tsMInfosMutex);
|
||||
memcpy(pMinfos, &tsMInfos, sizeof(SMInfos));
|
||||
for (int32_t i = 0; i < tsMInfos.mnodeNum; ++i) {
|
||||
pMinfos->mnodeInfos[i].mnodeId = htonl(tsMInfos.mnodeInfos[i].mnodeId);
|
||||
}
|
||||
pthread_mutex_unlock(&tsMInfosMutex);
|
||||
}
|
||||
|
||||
void dnodeGetEpSetForPeer(SRpcEpSet *epSet) {
|
||||
pthread_mutex_lock(&tsMInfosMutex);
|
||||
*epSet = tsMEpSet;
|
||||
for (int32_t i = 0; i < epSet->numOfEps; ++i) {
|
||||
epSet->port[i] += TSDB_PORT_DNODEDNODE;
|
||||
}
|
||||
pthread_mutex_unlock(&tsMInfosMutex);
|
||||
}
|
||||
|
||||
void dnodeGetEpSetForShell(SRpcEpSet *epSet) {
|
||||
pthread_mutex_lock(&tsMInfosMutex);
|
||||
*epSet = tsMEpSet;
|
||||
pthread_mutex_unlock(&tsMInfosMutex);
|
||||
}
|
||||
|
||||
static void dnodePrintMInfos(SMInfos *pMinfos) {
|
||||
dInfo("print minfos, mnodeNum:%d inUse:%d", pMinfos->mnodeNum, pMinfos->inUse);
|
||||
for (int32_t i = 0; i < pMinfos->mnodeNum; i++) {
|
||||
dInfo("mnode index:%d, %s", pMinfos->mnodeInfos[i].mnodeId, pMinfos->mnodeInfos[i].mnodeEp);
|
||||
}
|
||||
}
|
||||
|
||||
static void dnodeResetMInfos(SMInfos *pMinfos) {
|
||||
if (pMinfos == NULL) {
|
||||
tsMEpSet.numOfEps = 1;
|
||||
taosGetFqdnPortFromEp(tsFirst, tsMEpSet.fqdn[0], &tsMEpSet.port[0]);
|
||||
|
||||
if (strcmp(tsSecond, tsFirst) != 0) {
|
||||
tsMEpSet.numOfEps = 2;
|
||||
taosGetFqdnPortFromEp(tsSecond, tsMEpSet.fqdn[1], &tsMEpSet.port[1]);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (pMinfos->mnodeNum == 0) return;
|
||||
|
||||
int32_t size = sizeof(SMInfos);
|
||||
memcpy(&tsMInfos, pMinfos, size);
|
||||
|
||||
tsMEpSet.inUse = tsMInfos.inUse;
|
||||
tsMEpSet.numOfEps = tsMInfos.mnodeNum;
|
||||
for (int32_t i = 0; i < tsMInfos.mnodeNum; i++) {
|
||||
taosGetFqdnPortFromEp(tsMInfos.mnodeInfos[i].mnodeEp, tsMEpSet.fqdn[i], &tsMEpSet.port[i]);
|
||||
}
|
||||
|
||||
dnodePrintMInfos(pMinfos);
|
||||
}
|
||||
|
||||
static int32_t dnodeReadMInfos() {
|
||||
int32_t len = 0;
|
||||
int32_t maxLen = 2000;
|
||||
char * content = calloc(1, maxLen + 1);
|
||||
cJSON * root = NULL;
|
||||
FILE * fp = NULL;
|
||||
SMInfos minfos = {0};
|
||||
bool nodeChanged = false;
|
||||
|
||||
char file[TSDB_FILENAME_LEN + 20] = {0};
|
||||
sprintf(file, "%s/mnodeEpSet.json", tsDnodeDir);
|
||||
|
||||
fp = fopen(file, "r");
|
||||
if (!fp) {
|
||||
dDebug("failed to read %s, file not exist", file);
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
len = (int32_t)fread(content, 1, maxLen, fp);
|
||||
if (len <= 0) {
|
||||
dError("failed to read %s, content is null", file);
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
content[len] = 0;
|
||||
root = cJSON_Parse(content);
|
||||
if (root == NULL) {
|
||||
dError("failed to read %s, invalid json format", file);
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
cJSON *inUse = cJSON_GetObjectItem(root, "inUse");
|
||||
if (!inUse || inUse->type != cJSON_Number) {
|
||||
dError("failed to read mnodeEpSet.json, inUse not found");
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
tsMInfos.inUse = (int8_t)inUse->valueint;
|
||||
|
||||
cJSON *nodeNum = cJSON_GetObjectItem(root, "nodeNum");
|
||||
if (!nodeNum || nodeNum->type != cJSON_Number) {
|
||||
dError("failed to read mnodeEpSet.json, nodeNum not found");
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
minfos.mnodeNum = (int8_t)nodeNum->valueint;
|
||||
|
||||
cJSON *nodeInfos = cJSON_GetObjectItem(root, "nodeInfos");
|
||||
if (!nodeInfos || nodeInfos->type != cJSON_Array) {
|
||||
dError("failed to read mnodeEpSet.json, nodeInfos not found");
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
int32_t size = cJSON_GetArraySize(nodeInfos);
|
||||
if (size != minfos.mnodeNum) {
|
||||
dError("failed to read mnodeEpSet.json, nodeInfos size not matched");
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < size; ++i) {
|
||||
cJSON *nodeInfo = cJSON_GetArrayItem(nodeInfos, i);
|
||||
if (nodeInfo == NULL) continue;
|
||||
|
||||
cJSON *nodeId = cJSON_GetObjectItem(nodeInfo, "nodeId");
|
||||
if (!nodeId || nodeId->type != cJSON_Number) {
|
||||
dError("failed to read mnodeEpSet.json, nodeId not found");
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
cJSON *nodeEp = cJSON_GetObjectItem(nodeInfo, "nodeEp");
|
||||
if (!nodeEp || nodeEp->type != cJSON_String || nodeEp->valuestring == NULL) {
|
||||
dError("failed to read mnodeEpSet.json, nodeName not found");
|
||||
goto PARSE_MINFOS_OVER;
|
||||
}
|
||||
|
||||
SMInfo *pMinfo = &minfos.mnodeInfos[i];
|
||||
pMinfo->mnodeId = (int32_t)nodeId->valueint;
|
||||
tstrncpy(pMinfo->mnodeEp, nodeEp->valuestring, TSDB_EP_LEN);
|
||||
|
||||
bool changed = dnodeCheckEpChanged(pMinfo->mnodeId, pMinfo->mnodeEp);
|
||||
if (changed) nodeChanged = changed;
|
||||
}
|
||||
|
||||
dInfo("read file %s successed", file);
|
||||
dnodePrintMInfos(&minfos);
|
||||
|
||||
PARSE_MINFOS_OVER:
|
||||
if (content != NULL) free(content);
|
||||
if (root != NULL) cJSON_Delete(root);
|
||||
if (fp != NULL) fclose(fp);
|
||||
terrno = 0;
|
||||
|
||||
for (int32_t i = 0; i < minfos.mnodeNum; ++i) {
|
||||
SMInfo *mInfo = &minfos.mnodeInfos[i];
|
||||
dnodeUpdateEp(mInfo->mnodeId, mInfo->mnodeEp, NULL, NULL);
|
||||
}
|
||||
dnodeResetMInfos(&minfos);
|
||||
|
||||
if (nodeChanged) {
|
||||
dnodeWriteMInfos();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeWriteMInfos() {
|
||||
char file[TSDB_FILENAME_LEN + 20] = {0};
|
||||
sprintf(file, "%s/mnodeEpSet.json", tsDnodeDir);
|
||||
|
||||
FILE *fp = fopen(file, "w");
|
||||
if (!fp) {
|
||||
dError("failed to write %s, reason:%s", file, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
int32_t len = 0;
|
||||
int32_t maxLen = 2000;
|
||||
char * content = calloc(1, maxLen + 1);
|
||||
|
||||
len += snprintf(content + len, maxLen - len, "{\n");
|
||||
len += snprintf(content + len, maxLen - len, " \"inUse\": %d,\n", tsMInfos.inUse);
|
||||
len += snprintf(content + len, maxLen - len, " \"nodeNum\": %d,\n", tsMInfos.mnodeNum);
|
||||
len += snprintf(content + len, maxLen - len, " \"nodeInfos\": [{\n");
|
||||
for (int32_t i = 0; i < tsMInfos.mnodeNum; i++) {
|
||||
len += snprintf(content + len, maxLen - len, " \"nodeId\": %d,\n", tsMInfos.mnodeInfos[i].mnodeId);
|
||||
len += snprintf(content + len, maxLen - len, " \"nodeEp\": \"%s\"\n", tsMInfos.mnodeInfos[i].mnodeEp);
|
||||
if (i < tsMInfos.mnodeNum - 1) {
|
||||
len += snprintf(content + len, maxLen - len, " },{\n");
|
||||
} else {
|
||||
len += snprintf(content + len, maxLen - len, " }]\n");
|
||||
}
|
||||
}
|
||||
len += snprintf(content + len, maxLen - len, "}\n");
|
||||
|
||||
fwrite(content, 1, len, fp);
|
||||
taosFsync(fileno(fp));
|
||||
fclose(fp);
|
||||
free(content);
|
||||
terrno = 0;
|
||||
|
||||
dInfo("successed to write %s", file);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeSendRedirectMsg(SRpcMsg *rpcMsg, bool forShell) {
|
||||
SRpcConnInfo connInfo = {0};
|
||||
rpcGetConnInfo(rpcMsg->handle, &connInfo);
|
||||
|
||||
SRpcEpSet epSet = {0};
|
||||
if (forShell) {
|
||||
dnodeGetEpSetForShell(&epSet);
|
||||
} else {
|
||||
dnodeGetEpSetForPeer(&epSet);
|
||||
}
|
||||
|
||||
dDebug("msg:%s will be redirected, dnodeIp:%s user:%s, numOfEps:%d inUse:%d", taosMsg[rpcMsg->msgType],
|
||||
taosIpStr(connInfo.clientIp), connInfo.user, epSet.numOfEps, epSet.inUse);
|
||||
|
||||
for (int32_t i = 0; i < epSet.numOfEps; ++i) {
|
||||
dDebug("mnode index:%d %s:%d", i, epSet.fqdn[i], epSet.port[i]);
|
||||
if (strcmp(epSet.fqdn[i], tsLocalFqdn) == 0) {
|
||||
if ((epSet.port[i] == tsServerPort + TSDB_PORT_DNODEDNODE && !forShell) ||
|
||||
(epSet.port[i] == tsServerPort && forShell)) {
|
||||
epSet.inUse = (i + 1) % epSet.numOfEps;
|
||||
dDebug("mnode index:%d %s:%d set inUse to %d", i, epSet.fqdn[i], epSet.port[i], epSet.inUse);
|
||||
}
|
||||
}
|
||||
|
||||
epSet.port[i] = htons(epSet.port[i]);
|
||||
}
|
||||
|
||||
rpcSendRedirectRsp(rpcMsg->handle, &epSet);
|
||||
}
|
|
@ -1,168 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "tqueue.h"
|
||||
#include "twal.h"
|
||||
#include "mnode.h"
|
||||
#include "dnodeVMgmt.h"
|
||||
#include "dnodeMInfos.h"
|
||||
#include "dnodeMWrite.h"
|
||||
|
||||
typedef struct {
|
||||
pthread_t thread;
|
||||
int32_t workerId;
|
||||
} SMPeerWorker;
|
||||
|
||||
typedef struct {
|
||||
int32_t curNum;
|
||||
int32_t maxNum;
|
||||
SMPeerWorker *worker;
|
||||
} SMPeerWorkerPool;
|
||||
|
||||
static SMPeerWorkerPool tsMPeerWP;
|
||||
static taos_qset tsMPeerQset;
|
||||
static taos_queue tsMPeerQueue;
|
||||
|
||||
static void *dnodeProcessMPeerQueue(void *param);
|
||||
|
||||
int32_t dnodeInitMPeer() {
|
||||
tsMPeerQset = taosOpenQset();
|
||||
|
||||
tsMPeerWP.maxNum = 1;
|
||||
tsMPeerWP.curNum = 0;
|
||||
tsMPeerWP.worker = (SMPeerWorker *)calloc(sizeof(SMPeerWorker), tsMPeerWP.maxNum);
|
||||
|
||||
if (tsMPeerWP.worker == NULL) return -1;
|
||||
for (int32_t i = 0; i < tsMPeerWP.maxNum; ++i) {
|
||||
SMPeerWorker *pWorker = tsMPeerWP.worker + i;
|
||||
pWorker->workerId = i;
|
||||
dDebug("dnode mpeer worker:%d is created", i);
|
||||
}
|
||||
|
||||
dDebug("dnode mpeer is initialized, workers:%d qset:%p", tsMPeerWP.maxNum, tsMPeerQset);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupMPeer() {
|
||||
for (int32_t i = 0; i < tsMPeerWP.maxNum; ++i) {
|
||||
SMPeerWorker *pWorker = tsMPeerWP.worker + i;
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
taosQsetThreadResume(tsMPeerQset);
|
||||
}
|
||||
dDebug("dnode mpeer worker:%d is closed", i);
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < tsMPeerWP.maxNum; ++i) {
|
||||
SMPeerWorker *pWorker = tsMPeerWP.worker + i;
|
||||
dDebug("dnode mpeer worker:%d start to join", i);
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
pthread_join(pWorker->thread, NULL);
|
||||
}
|
||||
dDebug("dnode mpeer worker:%d join success", i);
|
||||
}
|
||||
|
||||
dDebug("dnode mpeer is closed, qset:%p", tsMPeerQset);
|
||||
|
||||
taosCloseQset(tsMPeerQset);
|
||||
tsMPeerQset = NULL;
|
||||
tfree(tsMPeerWP.worker);
|
||||
}
|
||||
|
||||
int32_t dnodeAllocateMPeerQueue() {
|
||||
tsMPeerQueue = taosOpenQueue();
|
||||
if (tsMPeerQueue == NULL) return TSDB_CODE_DND_OUT_OF_MEMORY;
|
||||
|
||||
taosAddIntoQset(tsMPeerQset, tsMPeerQueue, NULL);
|
||||
|
||||
for (int32_t i = tsMPeerWP.curNum; i < tsMPeerWP.maxNum; ++i) {
|
||||
SMPeerWorker *pWorker = tsMPeerWP.worker + i;
|
||||
pWorker->workerId = i;
|
||||
|
||||
pthread_attr_t thAttr;
|
||||
pthread_attr_init(&thAttr);
|
||||
pthread_attr_setdetachstate(&thAttr, PTHREAD_CREATE_JOINABLE);
|
||||
|
||||
if (pthread_create(&pWorker->thread, &thAttr, dnodeProcessMPeerQueue, pWorker) != 0) {
|
||||
dError("failed to create thread to process mpeer queue, reason:%s", strerror(errno));
|
||||
}
|
||||
|
||||
pthread_attr_destroy(&thAttr);
|
||||
|
||||
tsMPeerWP.curNum = i + 1;
|
||||
dDebug("dnode mpeer worker:%d is launched, total:%d", pWorker->workerId, tsMPeerWP.maxNum);
|
||||
}
|
||||
|
||||
dDebug("dnode mpeer queue:%p is allocated", tsMPeerQueue);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeFreeMPeerQueue() {
|
||||
dDebug("dnode mpeer queue:%p is freed", tsMPeerQueue);
|
||||
taosCloseQueue(tsMPeerQueue);
|
||||
tsMPeerQueue = NULL;
|
||||
}
|
||||
|
||||
void dnodeDispatchToMPeerQueue(SRpcMsg *pMsg) {
|
||||
if (!mnodeIsRunning() || tsMPeerQueue == NULL) {
|
||||
dnodeSendRedirectMsg(pMsg, false);
|
||||
} else {
|
||||
SMnodeMsg *pPeer = mnodeCreateMsg(pMsg);
|
||||
taosWriteQitem(tsMPeerQueue, TAOS_QTYPE_RPC, pPeer);
|
||||
}
|
||||
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
static void dnodeFreeMPeerMsg(SMnodeMsg *pPeer) {
|
||||
mnodeCleanupMsg(pPeer);
|
||||
taosFreeQitem(pPeer);
|
||||
}
|
||||
|
||||
static void dnodeSendRpcMPeerRsp(SMnodeMsg *pPeer, int32_t code) {
|
||||
if (code == TSDB_CODE_MND_ACTION_IN_PROGRESS) return;
|
||||
|
||||
SRpcMsg rpcRsp = {
|
||||
.handle = pPeer->rpcMsg.handle,
|
||||
.pCont = pPeer->rpcRsp.rsp,
|
||||
.contLen = pPeer->rpcRsp.len,
|
||||
.code = code,
|
||||
};
|
||||
|
||||
rpcSendResponse(&rpcRsp);
|
||||
dnodeFreeMPeerMsg(pPeer);
|
||||
}
|
||||
|
||||
static void *dnodeProcessMPeerQueue(void *param) {
|
||||
SMnodeMsg *pPeerMsg;
|
||||
int32_t type;
|
||||
void * unUsed;
|
||||
|
||||
setThreadName("dnodeMPeerQ");
|
||||
|
||||
while (1) {
|
||||
if (taosReadQitemFromQset(tsMPeerQset, &type, (void **)&pPeerMsg, &unUsed) == 0) {
|
||||
dDebug("qset:%p, mnode peer got no message from qset, exiting", tsMPeerQset);
|
||||
break;
|
||||
}
|
||||
|
||||
dTrace("msg:%s will be processed in mpeer queue", taosMsg[pPeerMsg->rpcMsg.msgType]);
|
||||
int32_t code = mnodeProcessPeerReq(pPeerMsg);
|
||||
dnodeSendRpcMPeerRsp(pPeerMsg, code);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
|
@ -1,173 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "tqueue.h"
|
||||
#include "mnode.h"
|
||||
#include "dnodeMInfos.h"
|
||||
#include "dnodeMRead.h"
|
||||
|
||||
typedef struct {
|
||||
pthread_t thread;
|
||||
int32_t workerId;
|
||||
} SMReadWorker;
|
||||
|
||||
typedef struct {
|
||||
int32_t curNum;
|
||||
int32_t maxNum;
|
||||
SMReadWorker *worker;
|
||||
} SMReadWorkerPool;
|
||||
|
||||
static SMReadWorkerPool tsMReadWP;
|
||||
static taos_qset tsMReadQset;
|
||||
static taos_queue tsMReadQueue;
|
||||
|
||||
static void *dnodeProcessMReadQueue(void *param);
|
||||
|
||||
int32_t dnodeInitMRead() {
|
||||
tsMReadQset = taosOpenQset();
|
||||
|
||||
tsMReadWP.maxNum = (int32_t)(tsNumOfCores * tsNumOfThreadsPerCore / 2);
|
||||
tsMReadWP.maxNum = MAX(2, tsMReadWP.maxNum);
|
||||
tsMReadWP.maxNum = MIN(4, tsMReadWP.maxNum);
|
||||
tsMReadWP.curNum = 0;
|
||||
tsMReadWP.worker = (SMReadWorker *)calloc(sizeof(SMReadWorker), tsMReadWP.maxNum);
|
||||
|
||||
if (tsMReadWP.worker == NULL) return -1;
|
||||
for (int32_t i = 0; i < tsMReadWP.maxNum; ++i) {
|
||||
SMReadWorker *pWorker = tsMReadWP.worker + i;
|
||||
pWorker->workerId = i;
|
||||
dDebug("dnode mread worker:%d is created", i);
|
||||
}
|
||||
|
||||
dDebug("dnode mread is initialized, workers:%d qset:%p", tsMReadWP.maxNum, tsMReadQset);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupMRead() {
|
||||
for (int32_t i = 0; i < tsMReadWP.maxNum; ++i) {
|
||||
SMReadWorker *pWorker = tsMReadWP.worker + i;
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
taosQsetThreadResume(tsMReadQset);
|
||||
}
|
||||
dDebug("dnode mread worker:%d is closed", i);
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < tsMReadWP.maxNum; ++i) {
|
||||
SMReadWorker *pWorker = tsMReadWP.worker + i;
|
||||
dDebug("dnode mread worker:%d start to join", i);
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
pthread_join(pWorker->thread, NULL);
|
||||
}
|
||||
dDebug("dnode mread worker:%d start to join", i);
|
||||
}
|
||||
|
||||
dDebug("dnode mread is closed, qset:%p", tsMReadQset);
|
||||
|
||||
taosCloseQset(tsMReadQset);
|
||||
tsMReadQset = NULL;
|
||||
free(tsMReadWP.worker);
|
||||
}
|
||||
|
||||
int32_t dnodeAllocMReadQueue() {
|
||||
tsMReadQueue = taosOpenQueue();
|
||||
if (tsMReadQueue == NULL) return TSDB_CODE_DND_OUT_OF_MEMORY;
|
||||
|
||||
taosAddIntoQset(tsMReadQset, tsMReadQueue, NULL);
|
||||
|
||||
for (int32_t i = tsMReadWP.curNum; i < tsMReadWP.maxNum; ++i) {
|
||||
SMReadWorker *pWorker = tsMReadWP.worker + i;
|
||||
pWorker->workerId = i;
|
||||
|
||||
pthread_attr_t thAttr;
|
||||
pthread_attr_init(&thAttr);
|
||||
pthread_attr_setdetachstate(&thAttr, PTHREAD_CREATE_JOINABLE);
|
||||
|
||||
if (pthread_create(&pWorker->thread, &thAttr, dnodeProcessMReadQueue, pWorker) != 0) {
|
||||
dError("failed to create thread to process mread queue, reason:%s", strerror(errno));
|
||||
}
|
||||
|
||||
pthread_attr_destroy(&thAttr);
|
||||
tsMReadWP.curNum = i + 1;
|
||||
dDebug("dnode mread worker:%d is launched, total:%d", pWorker->workerId, tsMReadWP.maxNum);
|
||||
}
|
||||
|
||||
dDebug("dnode mread queue:%p is allocated", tsMReadQueue);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeFreeMReadQueue() {
|
||||
dDebug("dnode mread queue:%p is freed", tsMReadQueue);
|
||||
taosCloseQueue(tsMReadQueue);
|
||||
tsMReadQueue = NULL;
|
||||
}
|
||||
|
||||
void dnodeDispatchToMReadQueue(SRpcMsg *pMsg) {
|
||||
if (!mnodeIsRunning() || tsMReadQueue == NULL) {
|
||||
dnodeSendRedirectMsg(pMsg, true);
|
||||
} else {
|
||||
SMnodeMsg *pRead = mnodeCreateMsg(pMsg);
|
||||
taosWriteQitem(tsMReadQueue, TAOS_QTYPE_RPC, pRead);
|
||||
}
|
||||
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
static void dnodeFreeMReadMsg(SMnodeMsg *pRead) {
|
||||
mnodeCleanupMsg(pRead);
|
||||
taosFreeQitem(pRead);
|
||||
}
|
||||
|
||||
static void dnodeSendRpcMReadRsp(SMnodeMsg *pRead, int32_t code) {
|
||||
if (code == TSDB_CODE_MND_ACTION_IN_PROGRESS) return;
|
||||
if (code == TSDB_CODE_MND_ACTION_NEED_REPROCESSED) {
|
||||
// may be a auto create req, should put into write queue
|
||||
dnodeReprocessMWriteMsg(pRead);
|
||||
return;
|
||||
}
|
||||
|
||||
SRpcMsg rpcRsp = {
|
||||
.handle = pRead->rpcMsg.handle,
|
||||
.pCont = pRead->rpcRsp.rsp,
|
||||
.contLen = pRead->rpcRsp.len,
|
||||
.code = code,
|
||||
};
|
||||
|
||||
rpcSendResponse(&rpcRsp);
|
||||
dnodeFreeMReadMsg(pRead);
|
||||
}
|
||||
|
||||
static void *dnodeProcessMReadQueue(void *param) {
|
||||
SMnodeMsg *pRead;
|
||||
int32_t type;
|
||||
void * unUsed;
|
||||
|
||||
setThreadName("dnodeMReadQ");
|
||||
|
||||
while (1) {
|
||||
if (taosReadQitemFromQset(tsMReadQset, &type, (void **)&pRead, &unUsed) == 0) {
|
||||
dDebug("qset:%p, mnode read got no message from qset, exiting", tsMReadQset);
|
||||
break;
|
||||
}
|
||||
|
||||
dTrace("msg:%p, app:%p type:%s will be processed in mread queue", pRead->rpcMsg.ahandle, pRead,
|
||||
taosMsg[pRead->rpcMsg.msgType]);
|
||||
int32_t code = mnodeProcessRead(pRead);
|
||||
dnodeSendRpcMReadRsp(pRead, code);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
|
@ -1,227 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "ttimer.h"
|
||||
#include "tqueue.h"
|
||||
#include "mnode.h"
|
||||
#include "dnodeMInfos.h"
|
||||
#include "dnodeMWrite.h"
|
||||
|
||||
typedef struct {
|
||||
pthread_t thread;
|
||||
int32_t workerId;
|
||||
} SMWriteWorker;
|
||||
|
||||
typedef struct {
|
||||
int32_t curNum;
|
||||
int32_t maxNum;
|
||||
SMWriteWorker *worker;
|
||||
} SMWriteWorkerPool;
|
||||
|
||||
static SMWriteWorkerPool tsMWriteWP;
|
||||
static taos_qset tsMWriteQset;
|
||||
static taos_queue tsMWriteQueue;
|
||||
extern void * tsDnodeTmr;
|
||||
|
||||
static void *dnodeProcessMWriteQueue(void *param);
|
||||
|
||||
int32_t dnodeInitMWrite() {
|
||||
tsMWriteQset = taosOpenQset();
|
||||
|
||||
tsMWriteWP.maxNum = 1;
|
||||
tsMWriteWP.curNum = 0;
|
||||
tsMWriteWP.worker = (SMWriteWorker *)calloc(sizeof(SMWriteWorker), tsMWriteWP.maxNum);
|
||||
|
||||
if (tsMWriteWP.worker == NULL) return -1;
|
||||
for (int32_t i = 0; i < tsMWriteWP.maxNum; ++i) {
|
||||
SMWriteWorker *pWorker = tsMWriteWP.worker + i;
|
||||
pWorker->workerId = i;
|
||||
dDebug("dnode mwrite worker:%d is created", i);
|
||||
}
|
||||
|
||||
dDebug("dnode mwrite is initialized, workers:%d qset:%p", tsMWriteWP.maxNum, tsMWriteQset);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupMWrite() {
|
||||
for (int32_t i = 0; i < tsMWriteWP.maxNum; ++i) {
|
||||
SMWriteWorker *pWorker = tsMWriteWP.worker + i;
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
taosQsetThreadResume(tsMWriteQset);
|
||||
}
|
||||
dDebug("dnode mwrite worker:%d is closed", i);
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < tsMWriteWP.maxNum; ++i) {
|
||||
SMWriteWorker *pWorker = tsMWriteWP.worker + i;
|
||||
dDebug("dnode mwrite worker:%d start to join", i);
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
pthread_join(pWorker->thread, NULL);
|
||||
}
|
||||
dDebug("dnode mwrite worker:%d join success", i);
|
||||
}
|
||||
|
||||
dDebug("dnode mwrite is closed, qset:%p", tsMWriteQset);
|
||||
|
||||
taosCloseQset(tsMWriteQset);
|
||||
tsMWriteQset = NULL;
|
||||
tfree(tsMWriteWP.worker);
|
||||
}
|
||||
|
||||
int32_t dnodeAllocMWritequeue() {
|
||||
tsMWriteQueue = taosOpenQueue();
|
||||
if (tsMWriteQueue == NULL) return TSDB_CODE_DND_OUT_OF_MEMORY;
|
||||
|
||||
taosAddIntoQset(tsMWriteQset, tsMWriteQueue, NULL);
|
||||
|
||||
for (int32_t i = tsMWriteWP.curNum; i < tsMWriteWP.maxNum; ++i) {
|
||||
SMWriteWorker *pWorker = tsMWriteWP.worker + i;
|
||||
pWorker->workerId = i;
|
||||
|
||||
pthread_attr_t thAttr;
|
||||
pthread_attr_init(&thAttr);
|
||||
pthread_attr_setdetachstate(&thAttr, PTHREAD_CREATE_JOINABLE);
|
||||
|
||||
if (pthread_create(&pWorker->thread, &thAttr, dnodeProcessMWriteQueue, pWorker) != 0) {
|
||||
dError("failed to create thread to process mwrite queue, reason:%s", strerror(errno));
|
||||
}
|
||||
|
||||
pthread_attr_destroy(&thAttr);
|
||||
tsMWriteWP.curNum = i + 1;
|
||||
dDebug("dnode mwrite worker:%d is launched, total:%d", pWorker->workerId, tsMWriteWP.maxNum);
|
||||
}
|
||||
|
||||
dDebug("dnode mwrite queue:%p is allocated", tsMWriteQueue);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeFreeMWritequeue() {
|
||||
dDebug("dnode mwrite queue:%p is freed", tsMWriteQueue);
|
||||
taosCloseQueue(tsMWriteQueue);
|
||||
tsMWriteQueue = NULL;
|
||||
}
|
||||
|
||||
void dnodeDispatchToMWriteQueue(SRpcMsg *pMsg) {
|
||||
if (!mnodeIsRunning() || tsMWriteQueue == NULL) {
|
||||
dnodeSendRedirectMsg(pMsg, true);
|
||||
} else {
|
||||
SMnodeMsg *pWrite = mnodeCreateMsg(pMsg);
|
||||
dTrace("msg:%p, app:%p type:%s is put into mwrite queue:%p", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType], tsMWriteQueue);
|
||||
taosWriteQitem(tsMWriteQueue, TAOS_QTYPE_RPC, pWrite);
|
||||
}
|
||||
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
static void dnodeFreeMWriteMsg(SMnodeMsg *pWrite) {
|
||||
dTrace("msg:%p, app:%p type:%s is freed from mwrite queue:%p", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType], tsMWriteQueue);
|
||||
|
||||
mnodeCleanupMsg(pWrite);
|
||||
taosFreeQitem(pWrite);
|
||||
}
|
||||
|
||||
void dnodeSendRpcMWriteRsp(void *pMsg, int32_t code) {
|
||||
SMnodeMsg *pWrite = pMsg;
|
||||
if (pWrite == NULL) return;
|
||||
if (code == TSDB_CODE_MND_ACTION_IN_PROGRESS) return;
|
||||
if (code == TSDB_CODE_MND_ACTION_NEED_REPROCESSED) {
|
||||
dnodeReprocessMWriteMsg(pWrite);
|
||||
return;
|
||||
}
|
||||
|
||||
dTrace("msg:%p, app:%p type:%s master:%p will be responsed", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType], pWrite->pBatchMasterMsg);
|
||||
if (pWrite->pBatchMasterMsg && pWrite != pWrite->pBatchMasterMsg) {
|
||||
dError("msg:%p, app:%p type:%s master:%p sub message should not response!", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType], pWrite->pBatchMasterMsg);
|
||||
return;
|
||||
}
|
||||
|
||||
SRpcMsg rpcRsp = {
|
||||
.handle = pWrite->rpcMsg.handle,
|
||||
.pCont = pWrite->rpcRsp.rsp,
|
||||
.contLen = pWrite->rpcRsp.len,
|
||||
.code = code,
|
||||
};
|
||||
|
||||
rpcSendResponse(&rpcRsp);
|
||||
dnodeFreeMWriteMsg(pWrite);
|
||||
}
|
||||
|
||||
static void *dnodeProcessMWriteQueue(void *param) {
|
||||
SMnodeMsg *pWrite;
|
||||
int32_t type;
|
||||
void * unUsed;
|
||||
|
||||
setThreadName("dnodeMWriteQ");
|
||||
|
||||
while (1) {
|
||||
if (taosReadQitemFromQset(tsMWriteQset, &type, (void **)&pWrite, &unUsed) == 0) {
|
||||
dDebug("qset:%p, mnode write got no message from qset, exiting", tsMWriteQset);
|
||||
break;
|
||||
}
|
||||
|
||||
dTrace("msg:%p, app:%p type:%s will be processed in mwrite queue", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType]);
|
||||
|
||||
int32_t code = mnodeProcessWrite(pWrite);
|
||||
dnodeSendRpcMWriteRsp(pWrite, code);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void dnodeReprocessMWriteMsg(void *pMsg) {
|
||||
SMnodeMsg *pWrite = pMsg;
|
||||
|
||||
if (!mnodeIsRunning() || tsMWriteQueue == NULL) {
|
||||
dDebug("msg:%p, app:%p type:%s is redirected for mnode not running, retry times:%d", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType], pWrite->retry);
|
||||
|
||||
if (pWrite->pBatchMasterMsg) {
|
||||
++pWrite->pBatchMasterMsg->received;
|
||||
if (pWrite->pBatchMasterMsg->successed + pWrite->pBatchMasterMsg->received
|
||||
>= pWrite->pBatchMasterMsg->expected) {
|
||||
dnodeSendRedirectMsg(&pWrite->pBatchMasterMsg->rpcMsg, true);
|
||||
dnodeFreeMWriteMsg(pWrite->pBatchMasterMsg);
|
||||
}
|
||||
|
||||
mnodeDestroySubMsg(pWrite);
|
||||
|
||||
return;
|
||||
}
|
||||
dnodeSendRedirectMsg(&pWrite->rpcMsg, true);
|
||||
dnodeFreeMWriteMsg(pWrite);
|
||||
} else {
|
||||
dDebug("msg:%p, app:%p type:%s is reput into mwrite queue:%p, retry times:%d", pWrite, pWrite->rpcMsg.ahandle,
|
||||
taosMsg[pWrite->rpcMsg.msgType], tsMWriteQueue, pWrite->retry);
|
||||
|
||||
taosWriteQitem(tsMWriteQueue, TAOS_QTYPE_RPC, pWrite);
|
||||
}
|
||||
}
|
||||
|
||||
static void dnodeDoDelayReprocessMWriteMsg(void *param, void *tmrId) {
|
||||
dnodeReprocessMWriteMsg(param);
|
||||
}
|
||||
|
||||
void dnodeDelayReprocessMWriteMsg(void *pMsg) {
|
||||
SMnodeMsg *mnodeMsg = pMsg;
|
||||
void *unUsed = NULL;
|
||||
taosTmrReset(dnodeDoDelayReprocessMWriteMsg, 300, mnodeMsg, tsDnodeTmr, &unUsed);
|
||||
}
|
|
@ -1,337 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "taos.h"
|
||||
#include "tnote.h"
|
||||
#include "ttimer.h"
|
||||
#include "tconfig.h"
|
||||
#include "tfile.h"
|
||||
#include "twal.h"
|
||||
#include "tfs.h"
|
||||
#include "tsync.h"
|
||||
#include "dnodeStep.h"
|
||||
#include "dnodePeer.h"
|
||||
#include "dnodeModule.h"
|
||||
#include "dnodeEps.h"
|
||||
#include "dnodeMInfos.h"
|
||||
#include "dnodeCfg.h"
|
||||
#include "dnodeCheck.h"
|
||||
#include "dnodeVRead.h"
|
||||
#include "dnodeVWrite.h"
|
||||
#include "dnodeVMgmt.h"
|
||||
#include "dnodeVnodes.h"
|
||||
#include "dnodeMRead.h"
|
||||
#include "dnodeMWrite.h"
|
||||
#include "dnodeMPeer.h"
|
||||
#include "dnodeShell.h"
|
||||
#include "dnodeTelemetry.h"
|
||||
#include "module.h"
|
||||
#include "mnode.h"
|
||||
#include "qScript.h"
|
||||
#include "tcache.h"
|
||||
#include "tscompression.h"
|
||||
|
||||
#if !defined(_MODULE) || !defined(_TD_LINUX)
|
||||
int32_t moduleStart() { return 0; }
|
||||
void moduleStop() {}
|
||||
#endif
|
||||
|
||||
|
||||
void *tsDnodeTmr = NULL;
|
||||
static SRunStatus tsRunStatus = TSDB_RUN_STATUS_STOPPED;
|
||||
|
||||
static int32_t dnodeInitStorage();
|
||||
static void dnodeCleanupStorage();
|
||||
static void dnodeSetRunStatus(SRunStatus status);
|
||||
static void dnodeCheckDataDirOpenned(char *dir);
|
||||
static int dnodeCreateDir(const char *dir);
|
||||
|
||||
static SStep tsDnodeSteps[] = {
|
||||
{"dnode-tfile", tfInit, tfCleanup},
|
||||
{"dnode-rpc", rpcInit, rpcCleanup},
|
||||
{"dnode-globalcfg", taosCheckGlobalCfg, NULL},
|
||||
{"dnode-storage", dnodeInitStorage, dnodeCleanupStorage},
|
||||
{"dnode-cfg", dnodeInitCfg, dnodeCleanupCfg},
|
||||
{"dnode-eps", dnodeInitEps, dnodeCleanupEps},
|
||||
{"dnode-minfos", dnodeInitMInfos, dnodeCleanupMInfos},
|
||||
{"dnode-wal", walInit, walCleanUp},
|
||||
{"dnode-sync", syncInit, syncCleanUp},
|
||||
{"dnode-check", dnodeInitCheck, dnodeCleanupCheck}, // NOTES: dnodeInitCheck must be behind the dnodeinitStorage component !!!
|
||||
{"dnode-vread", dnodeInitVRead, dnodeCleanupVRead},
|
||||
{"dnode-vwrite", dnodeInitVWrite, dnodeCleanupVWrite},
|
||||
{"dnode-vmgmt", dnodeInitVMgmt, dnodeCleanupVMgmt},
|
||||
{"dnode-mread", dnodeInitMRead, NULL},
|
||||
{"dnode-mwrite", dnodeInitMWrite, NULL},
|
||||
{"dnode-mpeer", dnodeInitMPeer, NULL},
|
||||
{"dnode-client", dnodeInitClient, dnodeCleanupClient},
|
||||
{"dnode-server", dnodeInitServer, dnodeCleanupServer},
|
||||
{"dnode-vnodes", dnodeInitVnodes, dnodeCleanupVnodes},
|
||||
{"dnode-modules", dnodeInitModules, dnodeCleanupModules},
|
||||
{"dnode-mread", NULL, dnodeCleanupMRead},
|
||||
{"dnode-mwrite", NULL, dnodeCleanupMWrite},
|
||||
{"dnode-mpeer", NULL, dnodeCleanupMPeer},
|
||||
{"dnode-shell", dnodeInitShell, dnodeCleanupShell},
|
||||
{"dnode-statustmr", dnodeInitStatusTimer,dnodeCleanupStatusTimer},
|
||||
{"dnode-telemetry", dnodeInitTelemetry, dnodeCleanupTelemetry},
|
||||
{"dnode-script", scriptEnvPoolInit, scriptEnvPoolCleanup},
|
||||
};
|
||||
|
||||
static SStep tsDnodeCompactSteps[] = {
|
||||
{"dnode-tfile", tfInit, tfCleanup},
|
||||
{"dnode-globalcfg", taosCheckGlobalCfg, NULL},
|
||||
{"dnode-storage", dnodeInitStorage, dnodeCleanupStorage},
|
||||
{"dnode-cfg", dnodeInitCfg, dnodeCleanupCfg},
|
||||
{"dnode-eps", dnodeInitEps, dnodeCleanupEps},
|
||||
{"dnode-minfos", dnodeInitMInfos, dnodeCleanupMInfos},
|
||||
{"dnode-wal", walInit, walCleanUp},
|
||||
{"dnode-sync", syncInit, syncCleanUp},
|
||||
{"dnode-vread", dnodeInitVRead, dnodeCleanupVRead},
|
||||
{"dnode-vwrite", dnodeInitVWrite, dnodeCleanupVWrite},
|
||||
{"dnode-vmgmt", dnodeInitVMgmt, dnodeCleanupVMgmt},
|
||||
{"dnode-mread", dnodeInitMRead, NULL},
|
||||
{"dnode-mwrite", dnodeInitMWrite, NULL},
|
||||
{"dnode-mpeer", dnodeInitMPeer, NULL},
|
||||
{"dnode-vnodes", dnodeInitVnodes, dnodeCleanupVnodes},
|
||||
{"dnode-modules", dnodeInitModules, dnodeCleanupModules},
|
||||
{"dnode-mread", NULL, dnodeCleanupMRead},
|
||||
{"dnode-mwrite", NULL, dnodeCleanupMWrite},
|
||||
{"dnode-mpeer", NULL, dnodeCleanupMPeer},
|
||||
};
|
||||
|
||||
static int dnodeCreateDir(const char *dir) {
|
||||
if (mkdir(dir, 0755) != 0 && errno != EEXIST) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void dnodeCleanupComponents() {
|
||||
if (!tsCompactMnodeWal) {
|
||||
int32_t stepSize = sizeof(tsDnodeSteps) / sizeof(SStep);
|
||||
dnodeStepCleanup(tsDnodeSteps, stepSize);
|
||||
} else {
|
||||
int32_t stepSize = sizeof(tsDnodeCompactSteps) / sizeof(SStep);
|
||||
dnodeStepCleanup(tsDnodeCompactSteps, stepSize);
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeInitComponents() {
|
||||
if (!tsCompactMnodeWal) {
|
||||
int32_t stepSize = sizeof(tsDnodeSteps) / sizeof(SStep);
|
||||
return dnodeStepInit(tsDnodeSteps, stepSize);
|
||||
} else {
|
||||
int32_t stepSize = sizeof(tsDnodeCompactSteps) / sizeof(SStep);
|
||||
return dnodeStepInit(tsDnodeCompactSteps, stepSize);
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeInitTmr() {
|
||||
tsDnodeTmr = taosTmrInit(100, 200, 60000, "DND-DM");
|
||||
if (tsDnodeTmr == NULL) {
|
||||
dError("failed to init dnode timer");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void dnodeCleanupTmr() {
|
||||
if (tsDnodeTmr != NULL) {
|
||||
taosTmrCleanUp(tsDnodeTmr);
|
||||
tsDnodeTmr = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
int32_t dnodeInitSystem() {
|
||||
dnodeSetRunStatus(TSDB_RUN_STATUS_INITIALIZE);
|
||||
tscEmbedded = 1;
|
||||
taosIgnSIGPIPE();
|
||||
taosBlockSIGPIPE();
|
||||
taosResolveCRC();
|
||||
taosInitGlobalCfg();
|
||||
taosReadGlobalLogCfg();
|
||||
taosSetCoreDump();
|
||||
dnodeInitTmr();
|
||||
|
||||
if (dnodeCreateDir(tsLogDir) < 0) {
|
||||
printf("failed to create dir: %s, reason: %s\n", tsLogDir, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
char temp[TSDB_FILENAME_LEN];
|
||||
sprintf(temp, "%s/taosdlog", tsLogDir);
|
||||
if (taosInitLog(temp, tsNumOfLogLines, 1) < 0) {
|
||||
printf("failed to init log file\n");
|
||||
}
|
||||
|
||||
if (!taosReadGlobalCfg()) {
|
||||
taosPrintGlobalCfg();
|
||||
dError("TDengine read global config failed");
|
||||
return -1;
|
||||
}
|
||||
|
||||
dInfo("start to initialize TDengine");
|
||||
|
||||
taosInitNotes();
|
||||
|
||||
if (dnodeInitComponents() != 0) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
dnodeSetRunStatus(TSDB_RUN_STATUS_RUNING);
|
||||
moduleStart();
|
||||
|
||||
tsDnodeStartTime = taosGetTimestampMs();
|
||||
dnodeReportStep("TDengine", "initialized successfully", 1);
|
||||
dInfo("TDengine is initialized successfully");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanUpSystem() {
|
||||
if (dnodeGetRunStatus() != TSDB_RUN_STATUS_STOPPED) {
|
||||
moduleStop();
|
||||
dnodeSetRunStatus(TSDB_RUN_STATUS_STOPPED);
|
||||
dnodeCleanupTmr();
|
||||
dnodeCleanupComponents();
|
||||
taos_cleanup();
|
||||
taosCloseLog();
|
||||
taosStopCacheRefreshWorker();
|
||||
}
|
||||
}
|
||||
|
||||
SRunStatus dnodeGetRunStatus() {
|
||||
return tsRunStatus;
|
||||
}
|
||||
|
||||
static void dnodeSetRunStatus(SRunStatus status) {
|
||||
tsRunStatus = status;
|
||||
}
|
||||
|
||||
static void dnodeCheckDataDirOpenned(char *dir) {
|
||||
char filepath[256] = {0};
|
||||
sprintf(filepath, "%s/.running", dir);
|
||||
|
||||
int fd = open(filepath, O_WRONLY | O_CREAT | O_TRUNC, S_IRWXU | S_IRWXG | S_IRWXO);
|
||||
if (fd < 0) {
|
||||
dError("failed to open lock file:%s, reason: %s, quit", filepath, strerror(errno));
|
||||
exit(0);
|
||||
}
|
||||
int32_t ret = flock(fd, LOCK_EX | LOCK_NB);
|
||||
if (ret != 0) {
|
||||
dError("failed to lock file:%s ret:%d[%s], database may be running, quit", filepath, ret, strerror(errno));
|
||||
close(fd);
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeInitStorage() {
|
||||
#ifdef TD_TSZ
|
||||
// compress module init
|
||||
tsCompressInit();
|
||||
#endif
|
||||
|
||||
// storage module init
|
||||
if (tsDiskCfgNum == 1 && dnodeCreateDir(tsDataDir) < 0) {
|
||||
dError("failed to create dir: %s, reason: %s", tsDataDir, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (tfsInit(tsDiskCfg, tsDiskCfgNum) < 0) {
|
||||
dError("failed to init TFS since %s", tstrerror(terrno));
|
||||
return -1;
|
||||
}
|
||||
strncpy(tsDataDir, TFS_PRIMARY_PATH(), TSDB_FILENAME_LEN);
|
||||
sprintf(tsMnodeDir, "%s/mnode", tsDataDir);
|
||||
sprintf(tsVnodeDir, "%s/vnode", tsDataDir);
|
||||
sprintf(tsDnodeDir, "%s/dnode", tsDataDir);
|
||||
// sprintf(tsVnodeBakDir, "%s/vnode_bak", tsDataDir);
|
||||
|
||||
if (tsCompactMnodeWal == 1) {
|
||||
sprintf(tsMnodeTmpDir, "%s/mnode_tmp", tsDataDir);
|
||||
if (taosDirExist(tsMnodeTmpDir)) {
|
||||
dError("mnode_tmp dir already exist in %s,quit compact job", tsMnodeTmpDir);
|
||||
return -1;
|
||||
}
|
||||
if (dnodeCreateDir(tsMnodeTmpDir) < 0) {
|
||||
dError("failed to create dir: %s, reason: %s", tsMnodeTmpDir, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
sprintf(tsMnodeBakDir, "%s/mnode_bak", tsDataDir);
|
||||
if (taosDirExist(tsMnodeBakDir)) {
|
||||
dError("mnode_bak dir already exist in %s,quit compact job", tsMnodeBakDir);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
//TODO(dengyihao): no need to init here
|
||||
if (dnodeCreateDir(tsMnodeDir) < 0) {
|
||||
dError("failed to create dir: %s, reason: %s", tsMnodeDir, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (dnodeCreateDir(tsDnodeDir) < 0) {
|
||||
dError("failed to create dir: %s, reason: %s", tsDnodeDir, strerror(errno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (tfsMkdir("vnode") < 0) {
|
||||
dError("failed to create vnode dir since %s", tstrerror(terrno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (tfsMkdir("vnode_bak") < 0) {
|
||||
dError("failed to create vnode_bak dir since %s", tstrerror(terrno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
TDIR *tdir = tfsOpendir("vnode_bak/.staging");
|
||||
bool stagingNotEmpty = tfsReaddir(tdir) != NULL;
|
||||
tfsClosedir(tdir);
|
||||
|
||||
if (stagingNotEmpty) {
|
||||
dError("vnode_bak/.staging dir not empty, fix it first.");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (tfsMkdir("vnode_bak/.staging") < 0) {
|
||||
dError("failed to create vnode_bak/.staging dir since %s", tstrerror(terrno));
|
||||
return -1;
|
||||
}
|
||||
|
||||
dnodeCheckDataDirOpenned(tsDnodeDir);
|
||||
|
||||
taosGetDisk();
|
||||
taosPrintDiskInfo();
|
||||
dInfo("dnode storage is initialized at %s", tsDnodeDir);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void dnodeCleanupStorage() {
|
||||
// storage destroy
|
||||
tfsDestroy();
|
||||
|
||||
#ifdef TD_TSZ
|
||||
// compress destroy
|
||||
tsCompressExit();
|
||||
#endif
|
||||
}
|
||||
|
||||
bool dnodeIsFirstDeploy() {
|
||||
return strcmp(tsFirst, tsLocalEp) == 0;
|
||||
}
|
|
@ -1,174 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "mnode.h"
|
||||
#include "http.h"
|
||||
#include "tmqtt.h"
|
||||
#include "monitor.h"
|
||||
#include "dnodeModule.h"
|
||||
|
||||
typedef struct {
|
||||
bool enable;
|
||||
char * name;
|
||||
int32_t (*initFp)();
|
||||
int32_t (*startFp)();
|
||||
void (*cleanUpFp)();
|
||||
void (*stopFp)();
|
||||
} SModule;
|
||||
|
||||
static SModule tsModule[TSDB_MOD_MAX] = {{0}};
|
||||
static uint32_t tsModuleStatus = 0;
|
||||
|
||||
static void dnodeSetModuleStatus(int32_t module) {
|
||||
tsModuleStatus |= (1 << module);
|
||||
}
|
||||
|
||||
static void dnodeUnSetModuleStatus(int32_t module) {
|
||||
tsModuleStatus &= ~(1 << module);
|
||||
}
|
||||
|
||||
static void dnodeAllocModules() {
|
||||
tsModule[TSDB_MOD_MNODE].enable = false;
|
||||
tsModule[TSDB_MOD_MNODE].name = "mnode";
|
||||
tsModule[TSDB_MOD_MNODE].initFp = mnodeInitSystem;
|
||||
tsModule[TSDB_MOD_MNODE].cleanUpFp = mnodeCleanupSystem;
|
||||
tsModule[TSDB_MOD_MNODE].startFp = mnodeStartSystem;
|
||||
tsModule[TSDB_MOD_MNODE].stopFp = mnodeStopSystem;
|
||||
|
||||
tsModule[TSDB_MOD_HTTP].enable = (tsEnableHttpModule == 1);
|
||||
tsModule[TSDB_MOD_HTTP].name = "http";
|
||||
tsModule[TSDB_MOD_HTTP].initFp = httpInitSystem;
|
||||
tsModule[TSDB_MOD_HTTP].cleanUpFp = httpCleanUpSystem;
|
||||
tsModule[TSDB_MOD_HTTP].startFp = httpStartSystem;
|
||||
tsModule[TSDB_MOD_HTTP].stopFp = httpStopSystem;
|
||||
if (tsEnableHttpModule) {
|
||||
dnodeSetModuleStatus(TSDB_MOD_HTTP);
|
||||
}
|
||||
|
||||
#ifdef _MQTT
|
||||
tsModule[TSDB_MOD_MQTT].enable = (tsEnableMqttModule == 1);
|
||||
tsModule[TSDB_MOD_MQTT].name = "mqtt";
|
||||
tsModule[TSDB_MOD_MQTT].initFp = mqttInitSystem;
|
||||
tsModule[TSDB_MOD_MQTT].cleanUpFp = mqttCleanUpSystem;
|
||||
tsModule[TSDB_MOD_MQTT].startFp = mqttStartSystem;
|
||||
tsModule[TSDB_MOD_MQTT].stopFp = mqttStopSystem;
|
||||
if (tsEnableMqttModule) {
|
||||
dnodeSetModuleStatus(TSDB_MOD_MQTT);
|
||||
}
|
||||
#endif
|
||||
|
||||
tsModule[TSDB_MOD_MONITOR].enable = (tsEnableMonitorModule == 1);
|
||||
tsModule[TSDB_MOD_MONITOR].name = "monitor";
|
||||
tsModule[TSDB_MOD_MONITOR].initFp = monInitSystem;
|
||||
tsModule[TSDB_MOD_MONITOR].cleanUpFp = monCleanupSystem;
|
||||
tsModule[TSDB_MOD_MONITOR].startFp = monStartSystem;
|
||||
tsModule[TSDB_MOD_MONITOR].stopFp = monStopSystem;
|
||||
if (tsEnableMonitorModule) {
|
||||
dnodeSetModuleStatus(TSDB_MOD_MONITOR);
|
||||
}
|
||||
}
|
||||
|
||||
void dnodeCleanupModules() {
|
||||
for (EModuleType module = 1; module < TSDB_MOD_MAX; ++module) {
|
||||
if (tsModule[module].enable && tsModule[module].stopFp) {
|
||||
(*tsModule[module].stopFp)();
|
||||
}
|
||||
if (tsModule[module].cleanUpFp) {
|
||||
(*tsModule[module].cleanUpFp)();
|
||||
}
|
||||
}
|
||||
|
||||
if (tsModule[TSDB_MOD_MNODE].cleanUpFp) {
|
||||
(*tsModule[TSDB_MOD_MNODE].cleanUpFp)();
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeStartModules() {
|
||||
for (EModuleType module = 1; module < TSDB_MOD_MAX; ++module) {
|
||||
if (tsModule[module].enable && tsModule[module].startFp) {
|
||||
int32_t code = (*tsModule[module].startFp)();
|
||||
if (code != 0) {
|
||||
dError("failed to start module:%s, code:%d", tsModule[module].name, code);
|
||||
return code;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int32_t dnodeInitModules() {
|
||||
dnodeAllocModules();
|
||||
|
||||
for (EModuleType module = 0; module < TSDB_MOD_MAX; ++module) {
|
||||
if (tsModule[module].initFp) {
|
||||
if ((*tsModule[module].initFp)() != 0) {
|
||||
dError("failed to init module:%s", tsModule[module].name);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dInfo("dnode modules is initialized");
|
||||
return dnodeStartModules();
|
||||
}
|
||||
|
||||
int32_t dnodeProcessModuleStatus(uint32_t moduleStatus) {
|
||||
int32_t code = 0;
|
||||
|
||||
for (int32_t module = TSDB_MOD_MNODE; module < TSDB_MOD_HTTP; ++module) {
|
||||
bool enableModule = moduleStatus & (1 << module);
|
||||
if (!tsModule[module].enable && enableModule) {
|
||||
dInfo("module status:%u is set, start %s module", moduleStatus, tsModule[module].name);
|
||||
tsModule[module].enable = true;
|
||||
dnodeSetModuleStatus(module);
|
||||
code = (*tsModule[module].startFp)();
|
||||
}
|
||||
|
||||
if (tsModule[module].enable && !enableModule) {
|
||||
dInfo("module status:%u is set, stop %s module", moduleStatus, tsModule[module].name);
|
||||
tsModule[module].enable = false;
|
||||
dnodeUnSetModuleStatus(module);
|
||||
(*tsModule[module].stopFp)();
|
||||
}
|
||||
}
|
||||
|
||||
return code;
|
||||
}
|
||||
|
||||
int32_t dnodeStartMnode(SMInfos *pMinfos) {
|
||||
if (tsModuleStatus & (1 << TSDB_MOD_MNODE)) {
|
||||
dDebug("mnode module is already started, module status:%d", tsModuleStatus);
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint32_t moduleStatus = tsModuleStatus | (1 << TSDB_MOD_MNODE);
|
||||
dInfo("start mnode module, module status:%d, new status:%d", tsModuleStatus, moduleStatus);
|
||||
|
||||
int32_t code = dnodeProcessModuleStatus(moduleStatus);
|
||||
if (code == 0) {
|
||||
code = sdbUpdateSync(pMinfos);
|
||||
}
|
||||
|
||||
if (code != 0) {
|
||||
dError("failed to start mnode module since %s", tstrerror(code));
|
||||
moduleStatus = tsModuleStatus & ~(1 << TSDB_MOD_MNODE);
|
||||
dnodeProcessModuleStatus(moduleStatus);
|
||||
}
|
||||
|
||||
return code;
|
||||
}
|
|
@ -1,195 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
/* this file is mainly responsible for the communication between DNODEs. Each
|
||||
* dnode works as both server and client. Dnode may send status, grant, config
|
||||
* messages to mnode, mnode may send create/alter/drop table/vnode messages
|
||||
* to dnode. All theses messages are handled from here
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "mnode.h"
|
||||
#include "dnodeVMgmt.h"
|
||||
#include "dnodeVWrite.h"
|
||||
#include "dnodeMPeer.h"
|
||||
#include "dnodeMInfos.h"
|
||||
#include "dnodeStep.h"
|
||||
|
||||
static void (*dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MAX])(SRpcMsg *);
|
||||
static void dnodeProcessReqMsgFromDnode(SRpcMsg *pMsg, SRpcEpSet *);
|
||||
static void (*dnodeProcessRspMsgFp[TSDB_MSG_TYPE_MAX])(SRpcMsg *rpcMsg);
|
||||
static void dnodeProcessRspFromDnode(SRpcMsg *pMsg, SRpcEpSet *pEpSet);
|
||||
static void *tsServerRpc = NULL;
|
||||
static void *tsClientRpc = NULL;
|
||||
|
||||
int32_t dnodeInitServer() {
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_CREATE_TABLE] = dnodeDispatchToVWriteQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_DROP_TABLE] = dnodeDispatchToVWriteQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_ALTER_TABLE] = dnodeDispatchToVWriteQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_DROP_STABLE] = dnodeDispatchToVWriteQueue;
|
||||
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_CREATE_VNODE] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_ALTER_VNODE] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_SYNC_VNODE] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_DROP_VNODE] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_ALTER_STREAM] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_CONFIG_DNODE] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_CREATE_MNODE] = dnodeDispatchToVMgmtQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_MD_COMPACT_VNODE] = dnodeDispatchToVMgmtQueue;
|
||||
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_DM_CONFIG_TABLE] = dnodeDispatchToMPeerQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_DM_CONFIG_VNODE] = dnodeDispatchToMPeerQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_DM_AUTH] = dnodeDispatchToMPeerQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_DM_GRANT] = dnodeDispatchToMPeerQueue;
|
||||
dnodeProcessReqMsgFp[TSDB_MSG_TYPE_DM_STATUS] = dnodeDispatchToMPeerQueue;
|
||||
|
||||
SRpcInit rpcInit;
|
||||
memset(&rpcInit, 0, sizeof(rpcInit));
|
||||
rpcInit.localPort = tsDnodeDnodePort;
|
||||
rpcInit.label = "DND-S";
|
||||
rpcInit.numOfThreads = 1;
|
||||
rpcInit.cfp = dnodeProcessReqMsgFromDnode;
|
||||
rpcInit.sessions = TSDB_MAX_VNODES << 4;
|
||||
rpcInit.connType = TAOS_CONN_SERVER;
|
||||
rpcInit.idleTime = tsShellActivityTimer * 1000;
|
||||
|
||||
tsServerRpc = rpcOpen(&rpcInit);
|
||||
if (tsServerRpc == NULL) {
|
||||
dError("failed to init inter-dnodes RPC server");
|
||||
return -1;
|
||||
}
|
||||
|
||||
dInfo("dnode inter-dnodes RPC server is initialized");
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupServer() {
|
||||
if (tsServerRpc) {
|
||||
rpcClose(tsServerRpc);
|
||||
tsServerRpc = NULL;
|
||||
dInfo("inter-dnodes RPC server is closed");
|
||||
}
|
||||
}
|
||||
|
||||
static void dnodeProcessReqMsgFromDnode(SRpcMsg *pMsg, SRpcEpSet *pEpSet) {
|
||||
SRpcMsg rspMsg = {
|
||||
.handle = pMsg->handle,
|
||||
.pCont = NULL,
|
||||
.contLen = 0
|
||||
};
|
||||
|
||||
if (pMsg->pCont == NULL) return;
|
||||
if (pMsg->msgType == TSDB_MSG_TYPE_NETWORK_TEST) {
|
||||
dnodeSendStartupStep(pMsg);
|
||||
return;
|
||||
}
|
||||
|
||||
if (dnodeGetRunStatus() != TSDB_RUN_STATUS_RUNING) {
|
||||
rspMsg.code = TSDB_CODE_APP_NOT_READY;
|
||||
rpcSendResponse(&rspMsg);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
dTrace("RPC %p, msg:%s is ignored since dnode not running", pMsg->handle, taosMsg[pMsg->msgType]);
|
||||
return;
|
||||
}
|
||||
|
||||
if (pMsg->pCont == NULL) {
|
||||
rspMsg.code = TSDB_CODE_DND_INVALID_MSG_LEN;
|
||||
rpcSendResponse(&rspMsg);
|
||||
return;
|
||||
}
|
||||
|
||||
if (dnodeProcessReqMsgFp[pMsg->msgType]) {
|
||||
(*dnodeProcessReqMsgFp[pMsg->msgType])(pMsg);
|
||||
} else {
|
||||
dDebug("RPC %p, message:%s not processed", pMsg->handle, taosMsg[pMsg->msgType]);
|
||||
rspMsg.code = TSDB_CODE_DND_MSG_NOT_PROCESSED;
|
||||
rpcSendResponse(&rspMsg);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
}
|
||||
|
||||
int32_t dnodeInitClient() {
|
||||
char secret[TSDB_KEY_LEN] = "secret";
|
||||
SRpcInit rpcInit;
|
||||
memset(&rpcInit, 0, sizeof(rpcInit));
|
||||
rpcInit.label = "DND-C";
|
||||
rpcInit.numOfThreads = 1;
|
||||
rpcInit.cfp = dnodeProcessRspFromDnode;
|
||||
rpcInit.sessions = TSDB_MAX_VNODES << 4;
|
||||
rpcInit.connType = TAOS_CONN_CLIENT;
|
||||
rpcInit.idleTime = tsShellActivityTimer * 1000;
|
||||
rpcInit.user = "t";
|
||||
rpcInit.ckey = "key";
|
||||
rpcInit.secret = secret;
|
||||
|
||||
tsClientRpc = rpcOpen(&rpcInit);
|
||||
if (tsClientRpc == NULL) {
|
||||
dError("failed to init mnode rpc client");
|
||||
return -1;
|
||||
}
|
||||
|
||||
dInfo("dnode inter-dnodes rpc client is initialized");
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupClient() {
|
||||
if (tsClientRpc) {
|
||||
rpcClose(tsClientRpc);
|
||||
tsClientRpc = NULL;
|
||||
dInfo("dnode inter-dnodes rpc client is closed");
|
||||
}
|
||||
}
|
||||
|
||||
static void dnodeProcessRspFromDnode(SRpcMsg *pMsg, SRpcEpSet *pEpSet) {
|
||||
if (dnodeGetRunStatus() == TSDB_RUN_STATUS_STOPPED) {
|
||||
if (pMsg == NULL || pMsg->pCont == NULL) return;
|
||||
dTrace("msg:%p is ignored since dnode is stopping", pMsg);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
return;
|
||||
}
|
||||
|
||||
if (pMsg->msgType == TSDB_MSG_TYPE_DM_STATUS_RSP && pEpSet) {
|
||||
dnodeUpdateEpSetForPeer(pEpSet);
|
||||
}
|
||||
|
||||
if (dnodeProcessRspMsgFp[pMsg->msgType]) {
|
||||
(*dnodeProcessRspMsgFp[pMsg->msgType])(pMsg);
|
||||
} else {
|
||||
mnodeProcessPeerRsp(pMsg);
|
||||
}
|
||||
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
void dnodeAddClientRspHandle(uint8_t msgType, void (*fp)(SRpcMsg *rpcMsg)) {
|
||||
dnodeProcessRspMsgFp[msgType] = fp;
|
||||
}
|
||||
|
||||
void dnodeSendMsgToDnode(SRpcEpSet *epSet, SRpcMsg *rpcMsg) {
|
||||
rpcSendRequest(tsClientRpc, epSet, rpcMsg, NULL);
|
||||
}
|
||||
|
||||
void dnodeSendMsgToMnodeRecv(SRpcMsg *rpcMsg, SRpcMsg *rpcRsp) {
|
||||
SRpcEpSet epSet = {0};
|
||||
dnodeGetEpSetForPeer(&epSet);
|
||||
|
||||
assert(tsClientRpc != 0);
|
||||
rpcSendRecv(tsClientRpc, &epSet, rpcMsg, rpcRsp);
|
||||
}
|
||||
|
||||
void dnodeSendMsgToDnodeRecv(SRpcMsg *rpcMsg, SRpcMsg *rpcRsp, SRpcEpSet *epSet) {
|
||||
rpcSendRecv(tsClientRpc, epSet, rpcMsg, rpcRsp);
|
||||
}
|
|
@ -1,249 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "http.h"
|
||||
#include "mnode.h"
|
||||
#include "dnodeVRead.h"
|
||||
#include "dnodeVWrite.h"
|
||||
#include "dnodeMRead.h"
|
||||
#include "dnodeMWrite.h"
|
||||
#include "dnodeShell.h"
|
||||
#include "dnodeStep.h"
|
||||
|
||||
static void (*dnodeProcessShellMsgFp[TSDB_MSG_TYPE_MAX])(SRpcMsg *);
|
||||
static void dnodeProcessMsgFromShell(SRpcMsg *pMsg, SRpcEpSet *);
|
||||
static int dnodeRetrieveUserAuthInfo(char *user, char *spi, char *encrypt, char *secret, char *ckey);
|
||||
static void * tsShellRpc = NULL;
|
||||
static int32_t tsQueryReqNum = 0;
|
||||
static int32_t tsSubmitReqNum = 0;
|
||||
|
||||
int32_t dnodeInitShell() {
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_SUBMIT] = dnodeDispatchToVWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_QUERY] = dnodeDispatchToVReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_FETCH] = dnodeDispatchToVReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_UPDATE_TAG_VAL] = dnodeDispatchToVWriteQueue;
|
||||
|
||||
// the following message shall be treated as mnode write
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_ACCT] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_ALTER_ACCT] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_ACCT] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_USER] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_ALTER_USER] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_USER] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_DNODE]= dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_DNODE] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_DB] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_TP] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_FUNCTION] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_DB] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_SYNC_DB] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_TP] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_FUNCTION] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_ALTER_DB] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_ALTER_TP] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CREATE_TABLE]= dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_DROP_TABLE] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_ALTER_TABLE] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_ALTER_STREAM]= dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_KILL_QUERY] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_KILL_STREAM] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_KILL_CONN] = dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CONFIG_DNODE]= dnodeDispatchToMWriteQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_COMPACT_VNODE]= dnodeDispatchToMWriteQueue;
|
||||
|
||||
// the following message shall be treated as mnode query
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_HEARTBEAT] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_CONNECT] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_USE_DB] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_TABLE_META] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_STABLE_VGROUP]= dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_TABLES_META] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_SHOW] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_RETRIEVE] = dnodeDispatchToMReadQueue;
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_CM_RETRIEVE_FUNC] = dnodeDispatchToMReadQueue;
|
||||
|
||||
dnodeProcessShellMsgFp[TSDB_MSG_TYPE_NETWORK_TEST] = dnodeSendStartupStep;
|
||||
|
||||
int32_t numOfThreads = (int32_t)((tsNumOfCores * tsNumOfThreadsPerCore) / 2.0);
|
||||
if (numOfThreads < 1) {
|
||||
numOfThreads = 1;
|
||||
}
|
||||
|
||||
SRpcInit rpcInit;
|
||||
memset(&rpcInit, 0, sizeof(rpcInit));
|
||||
rpcInit.localPort = tsDnodeShellPort;
|
||||
rpcInit.label = "SHELL";
|
||||
rpcInit.numOfThreads = numOfThreads;
|
||||
rpcInit.cfp = dnodeProcessMsgFromShell;
|
||||
rpcInit.sessions = tsMaxShellConns;
|
||||
rpcInit.connType = TAOS_CONN_SERVER;
|
||||
rpcInit.idleTime = tsShellActivityTimer * 1000;
|
||||
rpcInit.afp = dnodeRetrieveUserAuthInfo;
|
||||
|
||||
tsShellRpc = rpcOpen(&rpcInit);
|
||||
if (tsShellRpc == NULL) {
|
||||
dError("failed to init shell rpc server");
|
||||
return -1;
|
||||
}
|
||||
|
||||
dInfo("dnode shell rpc server is initialized");
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupShell() {
|
||||
if (tsShellRpc) {
|
||||
rpcClose(tsShellRpc);
|
||||
tsShellRpc = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static void dnodeProcessMsgFromShell(SRpcMsg *pMsg, SRpcEpSet *pEpSet) {
|
||||
SRpcMsg rpcMsg = {
|
||||
.handle = pMsg->handle,
|
||||
.pCont = NULL,
|
||||
.contLen = 0
|
||||
};
|
||||
|
||||
if (pMsg->pCont == NULL) return;
|
||||
|
||||
SRunStatus dnodeStatus = dnodeGetRunStatus();
|
||||
if (dnodeStatus == TSDB_RUN_STATUS_STOPPED) {
|
||||
dError("RPC %p, shell msg:%s is ignored since dnode exiting", pMsg->handle, taosMsg[pMsg->msgType]);
|
||||
rpcMsg.code = TSDB_CODE_DND_EXITING;
|
||||
rpcSendResponse(&rpcMsg);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
return;
|
||||
} else if (dnodeStatus != TSDB_RUN_STATUS_RUNING) {
|
||||
dError("RPC %p, shell msg:%s is ignored since dnode not running", pMsg->handle, taosMsg[pMsg->msgType]);
|
||||
rpcMsg.code = TSDB_CODE_APP_NOT_READY;
|
||||
rpcSendResponse(&rpcMsg);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
return;
|
||||
}
|
||||
|
||||
if (pMsg->msgType == TSDB_MSG_TYPE_QUERY) {
|
||||
atomic_fetch_add_32(&tsQueryReqNum, 1);
|
||||
} else if (pMsg->msgType == TSDB_MSG_TYPE_SUBMIT) {
|
||||
atomic_fetch_add_32(&tsSubmitReqNum, 1);
|
||||
} else {}
|
||||
|
||||
if ( dnodeProcessShellMsgFp[pMsg->msgType] ) {
|
||||
(*dnodeProcessShellMsgFp[pMsg->msgType])(pMsg);
|
||||
} else {
|
||||
dError("RPC %p, shell msg:%s is not processed", pMsg->handle, taosMsg[pMsg->msgType]);
|
||||
rpcMsg.code = TSDB_CODE_DND_MSG_NOT_PROCESSED;
|
||||
rpcSendResponse(&rpcMsg);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeAuthNettestUser(char *user, char *spi, char *encrypt, char *secret, char *ckey) {
|
||||
if (strcmp(user, "nettestinternal") == 0) {
|
||||
char pass[32] = {0};
|
||||
taosEncryptPass((uint8_t *)user, strlen(user), pass);
|
||||
*spi = 0;
|
||||
*encrypt = 0;
|
||||
*ckey = 0;
|
||||
memcpy(secret, pass, TSDB_KEY_LEN);
|
||||
dTrace("nettest user is authorized");
|
||||
return 0;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
static int dnodeRetrieveUserAuthInfo(char *user, char *spi, char *encrypt, char *secret, char *ckey) {
|
||||
if (dnodeAuthNettestUser(user, spi, encrypt, secret, ckey) == 0) return 0;
|
||||
int code = mnodeRetriveAuth(user, spi, encrypt, secret, ckey);
|
||||
if (code != TSDB_CODE_APP_NOT_READY) return code;
|
||||
|
||||
SAuthMsg *pMsg = rpcMallocCont(sizeof(SAuthMsg));
|
||||
tstrncpy(pMsg->user, user, sizeof(pMsg->user));
|
||||
|
||||
SRpcMsg rpcMsg = {0};
|
||||
rpcMsg.pCont = pMsg;
|
||||
rpcMsg.contLen = sizeof(SAuthMsg);
|
||||
rpcMsg.msgType = TSDB_MSG_TYPE_DM_AUTH;
|
||||
|
||||
dDebug("user:%s, send auth msg to mnodes", user);
|
||||
SRpcMsg rpcRsp = {0};
|
||||
dnodeSendMsgToMnodeRecv(&rpcMsg, &rpcRsp);
|
||||
|
||||
if (rpcRsp.code != 0) {
|
||||
dError("user:%s, auth msg received from mnodes, error:%s", user, tstrerror(rpcRsp.code));
|
||||
} else {
|
||||
SAuthRsp *pRsp = rpcRsp.pCont;
|
||||
dDebug("user:%s, auth msg received from mnodes", user);
|
||||
memcpy(secret, pRsp->secret, TSDB_KEY_LEN);
|
||||
memcpy(ckey, pRsp->ckey, TSDB_KEY_LEN);
|
||||
*spi = pRsp->spi;
|
||||
*encrypt = pRsp->encrypt;
|
||||
}
|
||||
|
||||
rpcFreeCont(rpcRsp.pCont);
|
||||
return rpcRsp.code;
|
||||
}
|
||||
|
||||
void *dnodeSendCfgTableToRecv(int32_t vgId, int32_t tid) {
|
||||
dDebug("vgId:%d, tid:%d send config table msg to mnode", vgId, tid);
|
||||
|
||||
int32_t contLen = sizeof(SConfigTableMsg);
|
||||
SConfigTableMsg *pMsg = rpcMallocCont(contLen);
|
||||
|
||||
pMsg->dnodeId = htonl(dnodeGetDnodeId());
|
||||
pMsg->vgId = htonl(vgId);
|
||||
pMsg->tid = htonl(tid);
|
||||
|
||||
SRpcMsg rpcMsg = {0};
|
||||
rpcMsg.pCont = pMsg;
|
||||
rpcMsg.contLen = contLen;
|
||||
rpcMsg.msgType = TSDB_MSG_TYPE_DM_CONFIG_TABLE;
|
||||
|
||||
SRpcMsg rpcRsp = {0};
|
||||
dnodeSendMsgToMnodeRecv(&rpcMsg, &rpcRsp);
|
||||
terrno = rpcRsp.code;
|
||||
|
||||
if (rpcRsp.code != 0) {
|
||||
rpcFreeCont(rpcRsp.pCont);
|
||||
dError("vgId:%d, tid:%d failed to config table from mnode", vgId, tid);
|
||||
return NULL;
|
||||
} else {
|
||||
dInfo("vgId:%d, tid:%d config table msg is received", vgId, tid);
|
||||
|
||||
// delete this after debug finished
|
||||
SMDCreateTableMsg *pTable = rpcRsp.pCont;
|
||||
int16_t numOfColumns = htons(pTable->numOfColumns);
|
||||
int16_t numOfTags = htons(pTable->numOfTags);
|
||||
int32_t tableId = htonl(pTable->tid);
|
||||
uint64_t uid = htobe64(pTable->uid);
|
||||
dInfo("table:%s, numOfColumns:%d numOfTags:%d tid:%d uid:%" PRIu64, pTable->tableFname, numOfColumns, numOfTags, tableId, uid);
|
||||
|
||||
return rpcRsp.pCont;
|
||||
}
|
||||
}
|
||||
|
||||
SStatisInfo dnodeGetStatisInfo() {
|
||||
SStatisInfo info = {0};
|
||||
if (dnodeGetRunStatus() == TSDB_RUN_STATUS_RUNING) {
|
||||
info.httpReqNum = httpGetReqCount();
|
||||
info.queryReqNum = atomic_exchange_32(&tsQueryReqNum, 0);
|
||||
info.submitReqNum = atomic_exchange_32(&tsSubmitReqNum, 0);
|
||||
}
|
||||
|
||||
return info;
|
||||
}
|
|
@ -1,74 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "dnodeStep.h"
|
||||
|
||||
static SStartupStep tsStartupStep;
|
||||
|
||||
void dnodeReportStep(char *name, char *desc, int8_t finished) {
|
||||
tstrncpy(tsStartupStep.name, name, sizeof(tsStartupStep.name));
|
||||
tstrncpy(tsStartupStep.desc, desc, sizeof(tsStartupStep.desc));
|
||||
tsStartupStep.finished = finished;
|
||||
}
|
||||
|
||||
void dnodeSendStartupStep(SRpcMsg *pMsg) {
|
||||
dInfo("nettest msg is received, cont:%s", (char *)pMsg->pCont);
|
||||
|
||||
SStartupStep *pStep = rpcMallocCont(sizeof(SStartupStep));
|
||||
memcpy(pStep, &tsStartupStep, sizeof(SStartupStep));
|
||||
|
||||
dDebug("startup msg is sent, step:%s desc:%s finished:%d", pStep->name, pStep->desc, pStep->finished);
|
||||
|
||||
SRpcMsg rpcRsp = {.handle = pMsg->handle, .pCont = pStep, .contLen = sizeof(SStartupStep)};
|
||||
rpcSendResponse(&rpcRsp);
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
void taosStepCleanupImp(SStep *pSteps, int32_t stepId) {
|
||||
for (int32_t step = stepId; step >= 0; step--) {
|
||||
SStep *pStep = pSteps + step;
|
||||
dDebug("step:%s will cleanup", pStep->name);
|
||||
if (pStep->cleanupFp != NULL) {
|
||||
(*pStep->cleanupFp)();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int32_t dnodeStepInit(SStep *pSteps, int32_t stepSize) {
|
||||
for (int32_t step = 0; step < stepSize; step++) {
|
||||
SStep *pStep = pSteps + step;
|
||||
if (pStep->initFp == NULL) continue;
|
||||
|
||||
dnodeReportStep(pStep->name, "Start initialization", 0);
|
||||
|
||||
int32_t code = (*pStep->initFp)();
|
||||
if (code != 0) {
|
||||
dDebug("step:%s will cleanup", pStep->name);
|
||||
taosStepCleanupImp(pSteps, step);
|
||||
return code;
|
||||
}
|
||||
dInfo("step:%s is initialized", pStep->name);
|
||||
|
||||
dnodeReportStep(pStep->name, "Initialization complete", 0);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeStepCleanup(SStep *pSteps, int32_t stepSize) {
|
||||
taosStepCleanupImp(pSteps, stepSize - 1);
|
||||
}
|
|
@ -1,188 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "tgrant.h"
|
||||
#include "tconfig.h"
|
||||
#include "dnodeMain.h"
|
||||
|
||||
static tsem_t exitSem;
|
||||
static void siguser1Handler(int32_t signum, void *sigInfo, void *context);
|
||||
static void siguser2Handler(int32_t signum, void *sigInfo, void *context);
|
||||
static void sigintHandler(int32_t signum, void *sigInfo, void *context);
|
||||
|
||||
int32_t main(int32_t argc, char *argv[]) {
|
||||
int dump_config = 0;
|
||||
|
||||
// Set global configuration file
|
||||
for (int32_t i = 1; i < argc; ++i) {
|
||||
if (strcmp(argv[i], "-c") == 0) {
|
||||
if (i < argc - 1) {
|
||||
if (strlen(argv[++i]) >= TSDB_FILENAME_LEN) {
|
||||
printf("config file path overflow");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
tstrncpy(configDir, argv[i], TSDB_FILENAME_LEN);
|
||||
} else {
|
||||
printf("'-c' requires a parameter, default:%s\n", configDir);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
} else if (strcmp(argv[i], "-C") == 0) {
|
||||
dump_config = 1;
|
||||
} else if (strcmp(argv[i], "--force-keep-file") == 0) {
|
||||
tsdbForceKeepFile = true;
|
||||
} else if (strcmp(argv[i], "--compact-mnode-wal") == 0) {
|
||||
tsCompactMnodeWal = 1;
|
||||
} else if (strcmp(argv[i], "-V") == 0) {
|
||||
#ifdef _ACCT
|
||||
char *versionStr = "enterprise";
|
||||
#else
|
||||
char *versionStr = "community";
|
||||
#endif
|
||||
printf("%s version: %s compatible_version: %s\n", versionStr, version, compatible_version);
|
||||
printf("gitinfo: %s\n", gitinfo);
|
||||
printf("gitinfoI: %s\n", gitinfoOfInternal);
|
||||
printf("buildinfo: %s\n", buildinfo);
|
||||
exit(EXIT_SUCCESS);
|
||||
} else if (strcmp(argv[i], "-k") == 0) {
|
||||
grantParseParameter();
|
||||
exit(EXIT_SUCCESS);
|
||||
} else if (strcmp(argv[i], "-A") == 0) {
|
||||
tsPrintAuth = 1;
|
||||
}
|
||||
#ifdef TAOS_MEM_CHECK
|
||||
else if (strcmp(argv[i], "--alloc-random-fail") == 0) {
|
||||
if ((i < argc - 1) && (argv[i + 1][0] != '-')) {
|
||||
taosSetAllocMode(TAOS_ALLOC_MODE_RANDOM_FAIL, argv[++i], true);
|
||||
} else {
|
||||
taosSetAllocMode(TAOS_ALLOC_MODE_RANDOM_FAIL, NULL, true);
|
||||
}
|
||||
} else if (strcmp(argv[i], "--detect-mem-leak") == 0) {
|
||||
if ((i < argc - 1) && (argv[i + 1][0] != '-')) {
|
||||
taosSetAllocMode(TAOS_ALLOC_MODE_DETECT_LEAK, argv[++i], true);
|
||||
} else {
|
||||
taosSetAllocMode(TAOS_ALLOC_MODE_DETECT_LEAK, NULL, true);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#ifdef TAOS_RANDOM_FILE_FAIL
|
||||
else if (strcmp(argv[i], "--random-file-fail-output") == 0) {
|
||||
if ((i < argc - 1) && (argv[i + 1][0] != '-')) {
|
||||
taosSetRandomFileFailOutput(argv[++i]);
|
||||
} else {
|
||||
taosSetRandomFileFailOutput(NULL);
|
||||
}
|
||||
} else if (strcmp(argv[i], "--random-file-fail-factor") == 0) {
|
||||
if ((i + 1) < argc) {
|
||||
int factor = atoi(argv[i + 1]);
|
||||
printf("The factor of random failure is %d\n", factor);
|
||||
taosSetRandomFileFailFactor(factor);
|
||||
} else {
|
||||
printf("Please specify a number for random failure factor!");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
if (0 != dump_config) {
|
||||
tscEmbedded = 1;
|
||||
taosInitGlobalCfg();
|
||||
taosReadGlobalLogCfg();
|
||||
|
||||
if (!taosReadGlobalCfg()) {
|
||||
printf("TDengine read global config failed");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
taosDumpGlobalCfg();
|
||||
exit(EXIT_SUCCESS);
|
||||
}
|
||||
|
||||
if (tsem_init(&exitSem, 0, 0) != 0) {
|
||||
printf("failed to create exit semphore\n");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
/* Set termination handler. */
|
||||
taosSetSignal(SIGUSR1, siguser1Handler);
|
||||
taosSetSignal(SIGUSR2, siguser2Handler);
|
||||
taosSetSignal(SIGTERM, sigintHandler);
|
||||
taosSetSignal(SIGHUP, sigintHandler);
|
||||
taosSetSignal(SIGINT, sigintHandler);
|
||||
taosSetSignal(SIGABRT, sigintHandler);
|
||||
taosSetSignal(SIGBREAK, sigintHandler);
|
||||
|
||||
// Open /var/log/syslog file to record information.
|
||||
openlog("TDengine:", LOG_PID | LOG_CONS | LOG_NDELAY, LOG_LOCAL1);
|
||||
syslog(LOG_INFO, "Starting TDengine service...");
|
||||
|
||||
// Initialize the system
|
||||
if (dnodeInitSystem() < 0) {
|
||||
syslog(LOG_ERR, "Error initialize TDengine system");
|
||||
dInfo("Failed to start TDengine, please check the log at:%s", tsLogDir);
|
||||
closelog();
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
syslog(LOG_INFO, "Started TDengine service successfully.");
|
||||
|
||||
if (tsem_wait(&exitSem) != 0) {
|
||||
syslog(LOG_ERR, "failed to wait exit semphore: %s", strerror(errno));
|
||||
}
|
||||
|
||||
dnodeCleanUpSystem();
|
||||
// close the syslog
|
||||
syslog(LOG_INFO, "Shut down TDengine service successfully");
|
||||
dInfo("TDengine is shut down!");
|
||||
closelog();
|
||||
|
||||
#ifdef WINDOWS
|
||||
tsem_post(&exitSem);
|
||||
#endif
|
||||
return EXIT_SUCCESS;
|
||||
}
|
||||
|
||||
static void siguser1Handler(int32_t signum, void *sigInfo, void *context) { taosCfgDynamicOptions("debugFlag 143"); }
|
||||
|
||||
static void siguser2Handler(int32_t signum, void *sigInfo, void *context) { taosCfgDynamicOptions("resetlog"); }
|
||||
|
||||
static void sigintHandler(int32_t signum, void *sigInfo, void *context) {
|
||||
// protect the application from receive another signal
|
||||
taosIgnSignal(SIGUSR1);
|
||||
taosIgnSignal(SIGUSR2);
|
||||
taosIgnSignal(SIGTERM);
|
||||
taosIgnSignal(SIGHUP);
|
||||
taosIgnSignal(SIGINT);
|
||||
taosIgnSignal(SIGABRT);
|
||||
taosIgnSignal(SIGBREAK);
|
||||
|
||||
// clean the system.
|
||||
dInfo("shut down signal is %d", signum);
|
||||
|
||||
#ifndef WINDOWS
|
||||
dInfo("sender PID:%d cmdline:%s", ((siginfo_t *)sigInfo)->si_pid, taosGetCmdlineByPID(((siginfo_t *)sigInfo)->si_pid));
|
||||
#endif
|
||||
|
||||
syslog(LOG_INFO, "Shut down signal is %d", signum);
|
||||
syslog(LOG_INFO, "Shutting down TDengine service...");
|
||||
|
||||
// inform main thread to exit
|
||||
tsem_post(&exitSem);
|
||||
#ifdef WINDOWS
|
||||
tsem_wait(&exitSem);
|
||||
#endif
|
||||
}
|
|
@ -1,315 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2020 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "osTime.h"
|
||||
#include "tsocket.h"
|
||||
#include "tbuffer.h"
|
||||
#include "mnode.h"
|
||||
#include "mnodeDef.h"
|
||||
#include "mnodeDb.h"
|
||||
#include "mnodeDnode.h"
|
||||
#include "mnodeCluster.h"
|
||||
#include "mnodeDnode.h"
|
||||
#include "mnodeVgroup.h"
|
||||
#include "mnodeMnode.h"
|
||||
#include "mnodeTable.h"
|
||||
#include "mnodeSdb.h"
|
||||
#include "mnodeAcct.h"
|
||||
#include "dnodeTelemetry.h"
|
||||
|
||||
// sem_timedwait is NOT implemented on MacOSX
|
||||
// thus, we use pthread_mutex_t/pthread_cond_t to simulate
|
||||
static pthread_mutex_t tsExitLock = PTHREAD_MUTEX_INITIALIZER;
|
||||
static pthread_cond_t tsExitCond = PTHREAD_COND_INITIALIZER;
|
||||
static volatile int tsExit = 0;
|
||||
static pthread_t tsTelemetryThread;
|
||||
|
||||
#define TELEMETRY_SERVER "telemetry.taosdata.com"
|
||||
#define TELEMETRY_PORT 80
|
||||
#define REPORT_INTERVAL 86400
|
||||
|
||||
static void beginObject(SBufferWriter* bw) {
|
||||
tbufWriteChar(bw, '{');
|
||||
}
|
||||
|
||||
static void closeObject(SBufferWriter* bw) {
|
||||
size_t len = tbufTell(bw);
|
||||
if (tbufGetData(bw, false)[len - 1] == ',') {
|
||||
tbufWriteCharAt(bw, len - 1, '}');
|
||||
} else {
|
||||
tbufWriteChar(bw, '}');
|
||||
}
|
||||
tbufWriteChar(bw, ',');
|
||||
}
|
||||
|
||||
#if 0
|
||||
static void beginArray(SBufferWriter* bw) {
|
||||
tbufWriteChar(bw, '[');
|
||||
}
|
||||
|
||||
static void closeArray(SBufferWriter* bw) {
|
||||
size_t len = tbufTell(bw);
|
||||
if (tbufGetData(bw, false)[len - 1] == ',') {
|
||||
tbufWriteCharAt(bw, len - 1, ']');
|
||||
} else {
|
||||
tbufWriteChar(bw, ']');
|
||||
}
|
||||
tbufWriteChar(bw, ',');
|
||||
}
|
||||
#endif
|
||||
|
||||
static void writeString(SBufferWriter* bw, const char* str) {
|
||||
tbufWriteChar(bw, '"');
|
||||
tbufWrite(bw, str, strlen(str));
|
||||
tbufWriteChar(bw, '"');
|
||||
}
|
||||
|
||||
static void addIntField(SBufferWriter* bw, const char* k, int64_t v) {
|
||||
writeString(bw, k);
|
||||
tbufWriteChar(bw, ':');
|
||||
char buf[32];
|
||||
sprintf(buf, "%" PRId64, v);
|
||||
tbufWrite(bw, buf, strlen(buf));
|
||||
tbufWriteChar(bw, ',');
|
||||
}
|
||||
|
||||
static void addStringField(SBufferWriter* bw, const char* k, const char* v) {
|
||||
writeString(bw, k);
|
||||
tbufWriteChar(bw, ':');
|
||||
writeString(bw, v);
|
||||
tbufWriteChar(bw, ',');
|
||||
}
|
||||
|
||||
static void addCpuInfo(SBufferWriter* bw) {
|
||||
char * line = NULL;
|
||||
size_t size = 0;
|
||||
int32_t done = 0;
|
||||
|
||||
FILE* fp = fopen("/proc/cpuinfo", "r");
|
||||
if (fp == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
while (done != 3 && (size = tgetline(&line, &size, fp)) != -1) {
|
||||
line[size - 1] = '\0';
|
||||
if (((done&1) == 0) && strncmp(line, "model name", 10) == 0) {
|
||||
const char* v = strchr(line, ':') + 2;
|
||||
addStringField(bw, "cpuModel", v);
|
||||
done |= 1;
|
||||
} else if (((done&2)==0) && strncmp(line, "cpu cores", 9) == 0) {
|
||||
const char* v = strchr(line, ':') + 2;
|
||||
writeString(bw, "numOfCpu");
|
||||
tbufWriteChar(bw, ':');
|
||||
tbufWrite(bw, v, strlen(v));
|
||||
tbufWriteChar(bw, ',');
|
||||
done |= 2;
|
||||
}
|
||||
}
|
||||
|
||||
free(line);
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
static void addOsInfo(SBufferWriter* bw) {
|
||||
char * line = NULL;
|
||||
size_t size = 0;
|
||||
|
||||
FILE* fp = fopen("/etc/os-release", "r");
|
||||
if (fp == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
while ((size = tgetline(&line, &size, fp)) != -1) {
|
||||
line[size - 1] = '\0';
|
||||
if (strncmp(line, "PRETTY_NAME", 11) == 0) {
|
||||
const char* p = strchr(line, '=') + 1;
|
||||
if (*p == '"') {
|
||||
p++;
|
||||
line[size - 2] = 0;
|
||||
}
|
||||
addStringField(bw, "os", p);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
free(line);
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
static void addMemoryInfo(SBufferWriter* bw) {
|
||||
char * line = NULL;
|
||||
size_t size = 0;
|
||||
|
||||
FILE* fp = fopen("/proc/meminfo", "r");
|
||||
if (fp == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
while ((size = tgetline(&line, &size, fp)) != -1) {
|
||||
line[size - 1] = '\0';
|
||||
if (strncmp(line, "MemTotal", 8) == 0) {
|
||||
const char* p = strchr(line, ':') + 1;
|
||||
while (*p == ' ') p++;
|
||||
addStringField(bw, "memory", p);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
free(line);
|
||||
fclose(fp);
|
||||
}
|
||||
|
||||
static void addVersionInfo(SBufferWriter* bw) {
|
||||
addStringField(bw, "version", version);
|
||||
addStringField(bw, "buildInfo", buildinfo);
|
||||
addStringField(bw, "gitInfo", gitinfo);
|
||||
addStringField(bw, "email", tsEmail);
|
||||
}
|
||||
|
||||
static void addRuntimeInfo(SBufferWriter* bw) {
|
||||
addIntField(bw, "numOfDnode", mnodeGetDnodesNum());
|
||||
addIntField(bw, "numOfMnode", mnodeGetMnodesNum());
|
||||
addIntField(bw, "numOfVgroup", mnodeGetVgroupNum());
|
||||
addIntField(bw, "numOfDatabase", mnodeGetDbNum());
|
||||
addIntField(bw, "numOfSuperTable", mnodeGetSuperTableNum());
|
||||
addIntField(bw, "numOfChildTable", mnodeGetChildTableNum());
|
||||
|
||||
SAcctInfo info;
|
||||
mnodeGetStatOfAllAcct(&info);
|
||||
addIntField(bw, "numOfColumn", info.numOfTimeSeries);
|
||||
addIntField(bw, "numOfPoint", info.totalPoints);
|
||||
addIntField(bw, "totalStorage", info.totalStorage);
|
||||
addIntField(bw, "compStorage", info.compStorage);
|
||||
// addStringField(bw, "installTime", "2020-08-01T00:00:00Z");
|
||||
}
|
||||
|
||||
static void sendTelemetryReport() {
|
||||
char buf[128];
|
||||
uint32_t ip = taosGetIpv4FromFqdn(TELEMETRY_SERVER);
|
||||
if (ip == 0xffffffff) {
|
||||
dTrace("failed to get IP address of " TELEMETRY_SERVER ", reason:%s", strerror(errno));
|
||||
return;
|
||||
}
|
||||
SOCKET fd = taosOpenTcpClientSocket(ip, TELEMETRY_PORT, 0);
|
||||
if (fd < 0) {
|
||||
dTrace("failed to create socket for telemetry, reason:%s", strerror(errno));
|
||||
return;
|
||||
}
|
||||
|
||||
SBufferWriter bw = tbufInitWriter(NULL, false);
|
||||
beginObject(&bw);
|
||||
addStringField(&bw, "instanceId", mnodeGetClusterId());
|
||||
addIntField(&bw, "reportVersion", 1);
|
||||
addOsInfo(&bw);
|
||||
addCpuInfo(&bw);
|
||||
addMemoryInfo(&bw);
|
||||
addVersionInfo(&bw);
|
||||
addRuntimeInfo(&bw);
|
||||
closeObject(&bw);
|
||||
|
||||
const char* header = "POST /report HTTP/1.1\n"
|
||||
"Host: " TELEMETRY_SERVER "\n"
|
||||
"Content-Type: application/json\n"
|
||||
"Content-Length: ";
|
||||
|
||||
taosWriteSocket(fd, header, (int32_t)strlen(header));
|
||||
int32_t contLen = (int32_t)(tbufTell(&bw) - 1);
|
||||
sprintf(buf, "%d\n\n", contLen);
|
||||
taosWriteSocket(fd, buf, (int32_t)strlen(buf));
|
||||
taosWriteSocket(fd, tbufGetData(&bw, false), contLen);
|
||||
tbufCloseWriter(&bw);
|
||||
|
||||
// read something to avoid nginx error 499
|
||||
if (taosReadSocket(fd, buf, 10) < 0) {
|
||||
dTrace("failed to receive response, reason:%s", strerror(errno));
|
||||
}
|
||||
taosCloseSocket(fd);
|
||||
}
|
||||
|
||||
static void* telemetryThread(void* param) {
|
||||
struct timespec end = {0};
|
||||
clock_gettime(CLOCK_REALTIME, &end);
|
||||
end.tv_sec += 300; // wait 5 minutes before send first report
|
||||
|
||||
setThreadName("telemetry");
|
||||
|
||||
while (!tsExit) {
|
||||
int r = 0;
|
||||
struct timespec ts = end;
|
||||
pthread_mutex_lock(&tsExitLock);
|
||||
r = pthread_cond_timedwait(&tsExitCond, &tsExitLock, &ts);
|
||||
pthread_mutex_unlock(&tsExitLock);
|
||||
if (r==0) break;
|
||||
if (r!=ETIMEDOUT) continue;
|
||||
|
||||
if (sdbIsMaster()) {
|
||||
sendTelemetryReport();
|
||||
}
|
||||
end.tv_sec += REPORT_INTERVAL;
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void dnodeGetEmail(char* filepath) {
|
||||
int32_t fd = open(filepath, O_RDONLY);
|
||||
if (fd < 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (taosRead(fd, (void *)tsEmail, TSDB_FQDN_LEN) < 0) {
|
||||
dError("failed to read %d bytes from file %s since %s", TSDB_FQDN_LEN, filepath, strerror(errno));
|
||||
}
|
||||
|
||||
taosClose(fd);
|
||||
}
|
||||
|
||||
int32_t dnodeInitTelemetry() {
|
||||
if (!tsEnableTelemetryReporting) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
dnodeGetEmail("/usr/local/taos/email");
|
||||
|
||||
pthread_attr_t attr;
|
||||
pthread_attr_init(&attr);
|
||||
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
|
||||
|
||||
int32_t code = pthread_create(&tsTelemetryThread, &attr, telemetryThread, NULL);
|
||||
pthread_attr_destroy(&attr);
|
||||
if (code != 0) {
|
||||
dTrace("failed to create telemetry thread, reason:%s", strerror(code));
|
||||
}
|
||||
|
||||
dInfo("dnode telemetry is initialized");
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupTelemetry() {
|
||||
if (!tsEnableTelemetryReporting) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (taosCheckPthreadValid(tsTelemetryThread)) {
|
||||
pthread_mutex_lock(&tsExitLock);
|
||||
tsExit = 1;
|
||||
pthread_cond_signal(&tsExitCond);
|
||||
pthread_mutex_unlock(&tsExitLock);
|
||||
|
||||
pthread_join(tsTelemetryThread, NULL);
|
||||
}
|
||||
}
|
|
@ -1,236 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "tqueue.h"
|
||||
#include "tworker.h"
|
||||
#include "dnodeVMgmt.h"
|
||||
|
||||
typedef struct {
|
||||
SRpcMsg rpcMsg;
|
||||
char pCont[];
|
||||
} SMgmtMsg;
|
||||
|
||||
static SWorkerPool tsVMgmtWP;
|
||||
static taos_queue tsVMgmtQueue = NULL;
|
||||
|
||||
static void * dnodeProcessMgmtQueue(void *param);
|
||||
static int32_t dnodeProcessCreateVnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessAlterVnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessSyncVnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessCompactVnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessDropVnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessAlterStreamMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessConfigDnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t dnodeProcessCreateMnodeMsg(SRpcMsg *pMsg);
|
||||
static int32_t (*dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MAX])(SRpcMsg *pMsg);
|
||||
|
||||
int32_t dnodeInitVMgmt() {
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_CREATE_VNODE] = dnodeProcessCreateVnodeMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_ALTER_VNODE] = dnodeProcessAlterVnodeMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_SYNC_VNODE] = dnodeProcessSyncVnodeMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_COMPACT_VNODE]= dnodeProcessCompactVnodeMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_DROP_VNODE] = dnodeProcessDropVnodeMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_ALTER_STREAM] = dnodeProcessAlterStreamMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_CONFIG_DNODE] = dnodeProcessConfigDnodeMsg;
|
||||
dnodeProcessMgmtMsgFp[TSDB_MSG_TYPE_MD_CREATE_MNODE] = dnodeProcessCreateMnodeMsg;
|
||||
|
||||
int32_t code = vnodeInitMgmt();
|
||||
if (code != TSDB_CODE_SUCCESS) return -1;
|
||||
|
||||
tsVMgmtWP.name = "vmgmt";
|
||||
tsVMgmtWP.workerFp = dnodeProcessMgmtQueue;
|
||||
tsVMgmtWP.min = 1;
|
||||
tsVMgmtWP.max = 1;
|
||||
if (tWorkerInit(&tsVMgmtWP) != 0) return -1;
|
||||
|
||||
tsVMgmtQueue = tWorkerAllocQueue(&tsVMgmtWP, NULL);
|
||||
|
||||
dInfo("dnode vmgmt is initialized");
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeCleanupVMgmt() {
|
||||
tWorkerFreeQueue(&tsVMgmtWP, tsVMgmtQueue);
|
||||
tWorkerCleanup(&tsVMgmtWP);
|
||||
|
||||
tsVMgmtQueue = NULL;
|
||||
vnodeCleanupMgmt();
|
||||
}
|
||||
|
||||
static int32_t dnodeWriteToMgmtQueue(SRpcMsg *pMsg) {
|
||||
int32_t size = sizeof(SMgmtMsg) + pMsg->contLen;
|
||||
SMgmtMsg *pMgmt = taosAllocateQitem(size);
|
||||
if (pMgmt == NULL) return TSDB_CODE_DND_OUT_OF_MEMORY;
|
||||
|
||||
pMgmt->rpcMsg = *pMsg;
|
||||
pMgmt->rpcMsg.pCont = pMgmt->pCont;
|
||||
memcpy(pMgmt->pCont, pMsg->pCont, pMsg->contLen);
|
||||
taosWriteQitem(tsVMgmtQueue, TAOS_QTYPE_RPC, pMgmt);
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeDispatchToVMgmtQueue(SRpcMsg *pMsg) {
|
||||
int32_t code = dnodeWriteToMgmtQueue(pMsg);
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
SRpcMsg rsp = {.handle = pMsg->handle, .code = code};
|
||||
rpcSendResponse(&rsp);
|
||||
}
|
||||
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
static void *dnodeProcessMgmtQueue(void *wparam) {
|
||||
SWorker * pWorker = wparam;
|
||||
SWorkerPool *pPool = pWorker->pPool;
|
||||
SMgmtMsg * pMgmt;
|
||||
SRpcMsg * pMsg;
|
||||
SRpcMsg rsp = {0};
|
||||
int32_t qtype;
|
||||
void * handle;
|
||||
|
||||
setThreadName("dnodeMgmtQ");
|
||||
|
||||
while (1) {
|
||||
if (taosReadQitemFromQset(pPool->qset, &qtype, (void **)&pMgmt, &handle) == 0) {
|
||||
dDebug("qdnode mgmt got no message from qset:%p, , exit", pPool->qset);
|
||||
break;
|
||||
}
|
||||
|
||||
pMsg = &pMgmt->rpcMsg;
|
||||
dTrace("msg:%p, ahandle:%p type:%s will be processed", pMgmt, pMsg->ahandle, taosMsg[pMsg->msgType]);
|
||||
if (dnodeProcessMgmtMsgFp[pMsg->msgType]) {
|
||||
rsp.code = (*dnodeProcessMgmtMsgFp[pMsg->msgType])(pMsg);
|
||||
} else {
|
||||
rsp.code = TSDB_CODE_DND_MSG_NOT_PROCESSED;
|
||||
}
|
||||
|
||||
dTrace("msg:%p, is processed, code:0x%x", pMgmt, rsp.code);
|
||||
if (rsp.code != TSDB_CODE_DND_ACTION_IN_PROGRESS) {
|
||||
rsp.handle = pMsg->handle;
|
||||
rsp.pCont = NULL;
|
||||
rpcSendResponse(&rsp);
|
||||
}
|
||||
|
||||
taosFreeQitem(pMsg);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static SCreateVnodeMsg* dnodeParseVnodeMsg(SRpcMsg *rpcMsg) {
|
||||
SCreateVnodeMsg *pCreate = rpcMsg->pCont;
|
||||
pCreate->cfg.vgId = htonl(pCreate->cfg.vgId);
|
||||
pCreate->cfg.dbCfgVersion = htonl(pCreate->cfg.dbCfgVersion);
|
||||
pCreate->cfg.vgCfgVersion = htonl(pCreate->cfg.vgCfgVersion);
|
||||
pCreate->cfg.maxTables = htonl(pCreate->cfg.maxTables);
|
||||
pCreate->cfg.cacheBlockSize = htonl(pCreate->cfg.cacheBlockSize);
|
||||
pCreate->cfg.totalBlocks = htonl(pCreate->cfg.totalBlocks);
|
||||
pCreate->cfg.daysPerFile = htonl(pCreate->cfg.daysPerFile);
|
||||
pCreate->cfg.daysToKeep1 = htonl(pCreate->cfg.daysToKeep1);
|
||||
pCreate->cfg.daysToKeep2 = htonl(pCreate->cfg.daysToKeep2);
|
||||
pCreate->cfg.daysToKeep = htonl(pCreate->cfg.daysToKeep);
|
||||
pCreate->cfg.minRowsPerFileBlock = htonl(pCreate->cfg.minRowsPerFileBlock);
|
||||
pCreate->cfg.maxRowsPerFileBlock = htonl(pCreate->cfg.maxRowsPerFileBlock);
|
||||
pCreate->cfg.fsyncPeriod = htonl(pCreate->cfg.fsyncPeriod);
|
||||
pCreate->cfg.commitTime = htonl(pCreate->cfg.commitTime);
|
||||
|
||||
for (int32_t j = 0; j < pCreate->cfg.vgReplica; ++j) {
|
||||
pCreate->nodes[j].nodeId = htonl(pCreate->nodes[j].nodeId);
|
||||
}
|
||||
|
||||
return pCreate;
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessCreateVnodeMsg(SRpcMsg *rpcMsg) {
|
||||
SCreateVnodeMsg *pCreate = dnodeParseVnodeMsg(rpcMsg);
|
||||
void *pVnode = vnodeAcquire(pCreate->cfg.vgId);
|
||||
if (pVnode != NULL) {
|
||||
dDebug("vgId:%d, already exist, return success", pCreate->cfg.vgId);
|
||||
vnodeRelease(pVnode);
|
||||
return TSDB_CODE_SUCCESS;
|
||||
} else {
|
||||
dDebug("vgId:%d, create vnode msg is received", pCreate->cfg.vgId);
|
||||
return vnodeCreate(pCreate);
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessAlterVnodeMsg(SRpcMsg *rpcMsg) {
|
||||
SAlterVnodeMsg *pAlter = dnodeParseVnodeMsg(rpcMsg);
|
||||
|
||||
void *pVnode = vnodeAcquireNotClose(pAlter->cfg.vgId);
|
||||
if (pVnode != NULL) {
|
||||
dDebug("vgId:%d, alter vnode msg is received", pAlter->cfg.vgId);
|
||||
int32_t code = vnodeAlter(pVnode, pAlter);
|
||||
vnodeRelease(pVnode);
|
||||
return code;
|
||||
} else {
|
||||
dInfo("vgId:%d, vnode not exist, can't alter it", pAlter->cfg.vgId);
|
||||
return TSDB_CODE_VND_INVALID_VGROUP_ID;
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessSyncVnodeMsg(SRpcMsg *rpcMsg) {
|
||||
SSyncVnodeMsg *pSyncVnode = rpcMsg->pCont;
|
||||
pSyncVnode->vgId = htonl(pSyncVnode->vgId);
|
||||
|
||||
return vnodeSync(pSyncVnode->vgId);
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessCompactVnodeMsg(SRpcMsg *rpcMsg) {
|
||||
SCompactVnodeMsg *pCompactVnode = rpcMsg->pCont;
|
||||
pCompactVnode->vgId = htonl(pCompactVnode->vgId);
|
||||
return vnodeCompact(pCompactVnode->vgId);
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessDropVnodeMsg(SRpcMsg *rpcMsg) {
|
||||
SDropVnodeMsg *pDrop = rpcMsg->pCont;
|
||||
pDrop->vgId = htonl(pDrop->vgId);
|
||||
|
||||
return vnodeDrop(pDrop->vgId);
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessAlterStreamMsg(SRpcMsg *pMsg) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessConfigDnodeMsg(SRpcMsg *pMsg) {
|
||||
SCfgDnodeMsg *pCfg = pMsg->pCont;
|
||||
return taosCfgDynamicOptions(pCfg->config);
|
||||
}
|
||||
|
||||
static int32_t dnodeProcessCreateMnodeMsg(SRpcMsg *pMsg) {
|
||||
SCreateMnodeMsg *pCfg = pMsg->pCont;
|
||||
pCfg->dnodeId = htonl(pCfg->dnodeId);
|
||||
if (pCfg->dnodeId != dnodeGetDnodeId()) {
|
||||
dDebug("dnode:%d, in create mnode msg is not equal with saved dnodeId:%d", pCfg->dnodeId, dnodeGetDnodeId());
|
||||
return TSDB_CODE_MND_DNODE_ID_NOT_CONFIGURED;
|
||||
}
|
||||
|
||||
if (strcmp(pCfg->dnodeEp, tsLocalEp) != 0) {
|
||||
dDebug("dnodeEp:%s, in create mnode msg is not equal with saved dnodeEp:%s", pCfg->dnodeEp, tsLocalEp);
|
||||
return TSDB_CODE_MND_DNODE_EP_NOT_CONFIGURED;
|
||||
}
|
||||
|
||||
dDebug("dnode:%d, create mnode msg is received from mnodes, numOfMnodes:%d", pCfg->dnodeId, pCfg->mnodes.mnodeNum);
|
||||
for (int i = 0; i < pCfg->mnodes.mnodeNum; ++i) {
|
||||
pCfg->mnodes.mnodeInfos[i].mnodeId = htonl(pCfg->mnodes.mnodeInfos[i].mnodeId);
|
||||
dDebug("mnode index:%d, mnode:%d:%s", i, pCfg->mnodes.mnodeInfos[i].mnodeId, pCfg->mnodes.mnodeInfos[i].mnodeEp);
|
||||
}
|
||||
|
||||
return dnodeStartMnode(&pCfg->mnodes);
|
||||
}
|
|
@ -1,154 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "tqueue.h"
|
||||
#include "tworker.h"
|
||||
#include "dnodeVRead.h"
|
||||
|
||||
static void *dnodeProcessReadQueue(void *pWorker);
|
||||
|
||||
// module global variable
|
||||
static SWorkerPool tsVQueryWP;
|
||||
static SWorkerPool tsVFetchWP;
|
||||
|
||||
int32_t dnodeInitVRead() {
|
||||
const int32_t maxFetchThreads = 4;
|
||||
|
||||
// calculate the available query thread
|
||||
float threadsForQuery = MAX(tsNumOfCores * tsRatioOfQueryCores, 1);
|
||||
|
||||
tsVQueryWP.name = "vquery";
|
||||
tsVQueryWP.workerFp = dnodeProcessReadQueue;
|
||||
tsVQueryWP.min = (int32_t) threadsForQuery;
|
||||
tsVQueryWP.max = tsVQueryWP.min;
|
||||
if (tWorkerInit(&tsVQueryWP) != 0) return -1;
|
||||
|
||||
tsVFetchWP.name = "vfetch";
|
||||
tsVFetchWP.workerFp = dnodeProcessReadQueue;
|
||||
tsVFetchWP.min = MIN(maxFetchThreads, tsNumOfCores);
|
||||
tsVFetchWP.max = tsVFetchWP.min;
|
||||
if (tWorkerInit(&tsVFetchWP) != 0) return -1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupVRead() {
|
||||
tWorkerCleanup(&tsVFetchWP);
|
||||
tWorkerCleanup(&tsVQueryWP);
|
||||
}
|
||||
|
||||
void dnodeDispatchToVReadQueue(SRpcMsg *pMsg) {
|
||||
int32_t queuedMsgNum = 0;
|
||||
int32_t leftLen = pMsg->contLen;
|
||||
int32_t code = TSDB_CODE_VND_INVALID_VGROUP_ID;
|
||||
char * pCont = pMsg->pCont;
|
||||
|
||||
while (leftLen > 0) {
|
||||
SMsgHead *pHead = (SMsgHead *)pCont;
|
||||
pHead->vgId = htonl(pHead->vgId);
|
||||
pHead->contLen = htonl(pHead->contLen);
|
||||
|
||||
assert(pHead->contLen > 0);
|
||||
void *pVnode = vnodeAcquireNotClose(pHead->vgId);
|
||||
if (pVnode != NULL) {
|
||||
code = vnodeWriteToRQueue(pVnode, pCont, pHead->contLen, TAOS_QTYPE_RPC, pMsg);
|
||||
if (code == TSDB_CODE_SUCCESS) queuedMsgNum++;
|
||||
vnodeRelease(pVnode);
|
||||
}
|
||||
|
||||
leftLen -= pHead->contLen;
|
||||
pCont -= pHead->contLen;
|
||||
}
|
||||
|
||||
if (queuedMsgNum == 0) {
|
||||
SRpcMsg rpcRsp = {.handle = pMsg->handle, .code = code};
|
||||
rpcSendResponse(&rpcRsp);
|
||||
}
|
||||
|
||||
rpcFreeCont(pMsg->pCont);
|
||||
}
|
||||
|
||||
void *dnodeAllocVQueryQueue(void *pVnode) {
|
||||
return tWorkerAllocQueue(&tsVQueryWP, pVnode);
|
||||
}
|
||||
|
||||
void *dnodeAllocVFetchQueue(void *pVnode) {
|
||||
return tWorkerAllocQueue(&tsVFetchWP, pVnode);
|
||||
}
|
||||
|
||||
void dnodeFreeVQueryQueue(void *pQqueue) {
|
||||
tWorkerFreeQueue(&tsVQueryWP, pQqueue);
|
||||
}
|
||||
|
||||
void dnodeFreeVFetchQueue(void *pFqueue) {
|
||||
tWorkerFreeQueue(&tsVFetchWP, pFqueue);
|
||||
}
|
||||
|
||||
void dnodeSendRpcVReadRsp(void *pVnode, SVReadMsg *pRead, int32_t code) {
|
||||
SRpcMsg rpcRsp = {
|
||||
.handle = pRead->rpcHandle,
|
||||
.pCont = pRead->rspRet.rsp,
|
||||
.contLen = pRead->rspRet.len,
|
||||
.code = code,
|
||||
};
|
||||
|
||||
rpcSendResponse(&rpcRsp);
|
||||
}
|
||||
|
||||
void dnodeDispatchNonRspMsg(void *pVnode, SVReadMsg *pRead, int32_t code) {
|
||||
}
|
||||
|
||||
static void *dnodeProcessReadQueue(void *wparam) {
|
||||
SWorker * pWorker = wparam;
|
||||
SWorkerPool *pPool = pWorker->pPool;
|
||||
SVReadMsg * pRead;
|
||||
int32_t qtype;
|
||||
void * pVnode;
|
||||
|
||||
char* threadname = strcmp(pPool->name, "vquery") == 0? "dnodeQueryQ":"dnodeFetchQ";
|
||||
|
||||
char name[16] = {0};
|
||||
snprintf(name, tListLen(name), "%s", threadname);
|
||||
setThreadName(name);
|
||||
|
||||
while (1) {
|
||||
if (taosReadQitemFromQset(pPool->qset, &qtype, (void **)&pRead, &pVnode) == 0) {
|
||||
dDebug("dnode vquery got no message from qset:%p, exiting", pPool->qset);
|
||||
break;
|
||||
}
|
||||
|
||||
dTrace("msg:%p, app:%p type:%s will be processed in vquery queue, qtype:%d", pRead, pRead->rpcAhandle,
|
||||
taosMsg[pRead->msgType], qtype);
|
||||
|
||||
int32_t code = vnodeProcessRead(pVnode, pRead);
|
||||
|
||||
if (qtype == TAOS_QTYPE_RPC && code != TSDB_CODE_QRY_NOT_READY) {
|
||||
dnodeSendRpcVReadRsp(pVnode, pRead, code);
|
||||
} else {
|
||||
if (code == TSDB_CODE_QRY_HAS_RSP) {
|
||||
dnodeSendRpcVReadRsp(pVnode, pRead, pRead->code);
|
||||
} else { // code == TSDB_CODE_QRY_NOT_READY, do not return msg to client
|
||||
assert(pRead->rpcHandle == NULL || (pRead->rpcHandle != NULL && pRead->msgType == 5));
|
||||
dnodeDispatchNonRspMsg(pVnode, pRead, code);
|
||||
}
|
||||
}
|
||||
|
||||
vnodeFreeFromRQueue(pVnode, pRead);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
|
@ -1,238 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "tqueue.h"
|
||||
#include "dnodeVWrite.h"
|
||||
|
||||
typedef struct {
|
||||
taos_qall qall;
|
||||
taos_qset qset; // queue set
|
||||
int32_t workerId; // worker ID
|
||||
pthread_t thread; // thread
|
||||
} SVWriteWorker;
|
||||
|
||||
typedef struct {
|
||||
int32_t max; // max number of workers
|
||||
int32_t nextId; // from 0 to max-1, cyclic
|
||||
SVWriteWorker * worker;
|
||||
pthread_mutex_t mutex;
|
||||
} SVWriteWorkerPool;
|
||||
|
||||
static SVWriteWorkerPool tsVWriteWP;
|
||||
static void *dnodeProcessVWriteQueue(void *pWorker);
|
||||
|
||||
int32_t dnodeInitVWrite() {
|
||||
tsVWriteWP.max = tsNumOfCores;
|
||||
tsVWriteWP.worker = tcalloc(sizeof(SVWriteWorker), tsVWriteWP.max);
|
||||
if (tsVWriteWP.worker == NULL) return -1;
|
||||
pthread_mutex_init(&tsVWriteWP.mutex, NULL);
|
||||
|
||||
for (int32_t i = 0; i < tsVWriteWP.max; ++i) {
|
||||
tsVWriteWP.worker[i].workerId = i;
|
||||
}
|
||||
|
||||
dInfo("dnode vwrite is initialized, max worker %d", tsVWriteWP.max);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void dnodeCleanupVWrite() {
|
||||
for (int32_t i = 0; i < tsVWriteWP.max; ++i) {
|
||||
SVWriteWorker *pWorker = tsVWriteWP.worker + i;
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
if (pWorker->qset) taosQsetThreadResume(pWorker->qset);
|
||||
}
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < tsVWriteWP.max; ++i) {
|
||||
SVWriteWorker *pWorker = tsVWriteWP.worker + i;
|
||||
if (taosCheckPthreadValid(pWorker->thread)) {
|
||||
pthread_join(pWorker->thread, NULL);
|
||||
taosFreeQall(pWorker->qall);
|
||||
taosCloseQset(pWorker->qset);
|
||||
}
|
||||
}
|
||||
|
||||
pthread_mutex_destroy(&tsVWriteWP.mutex);
|
||||
tfree(tsVWriteWP.worker);
|
||||
dInfo("dnode vwrite is closed");
|
||||
}
|
||||
|
||||
void dnodeDispatchToVWriteQueue(SRpcMsg *pRpcMsg) {
|
||||
int32_t code;
|
||||
char *pCont = pRpcMsg->pCont;
|
||||
|
||||
if (pRpcMsg->msgType == TSDB_MSG_TYPE_SUBMIT) {
|
||||
SMsgDesc *pDesc = (SMsgDesc *)pCont;
|
||||
pDesc->numOfVnodes = htonl(pDesc->numOfVnodes);
|
||||
pCont += sizeof(SMsgDesc);
|
||||
}
|
||||
|
||||
SMsgHead *pMsg = (SMsgHead *)pCont;
|
||||
pMsg->vgId = htonl(pMsg->vgId);
|
||||
pMsg->contLen = htonl(pMsg->contLen);
|
||||
|
||||
void *pVnode = vnodeAcquireNotClose(pMsg->vgId);
|
||||
if (pVnode == NULL) {
|
||||
code = TSDB_CODE_VND_INVALID_VGROUP_ID;
|
||||
} else {
|
||||
SWalHead *pHead = (SWalHead *)(pCont - sizeof(SWalHead));
|
||||
pHead->msgType = pRpcMsg->msgType;
|
||||
pHead->version = 0;
|
||||
pHead->len = pMsg->contLen;
|
||||
code = vnodeWriteToWQueue(pVnode, pHead, TAOS_QTYPE_RPC, pRpcMsg);
|
||||
}
|
||||
|
||||
if (code != TSDB_CODE_SUCCESS) {
|
||||
SRpcMsg rpcRsp = {.handle = pRpcMsg->handle, .code = code};
|
||||
rpcSendResponse(&rpcRsp);
|
||||
}
|
||||
|
||||
vnodeRelease(pVnode);
|
||||
rpcFreeCont(pRpcMsg->pCont);
|
||||
}
|
||||
|
||||
void *dnodeAllocVWriteQueue(void *pVnode) {
|
||||
pthread_mutex_lock(&tsVWriteWP.mutex);
|
||||
SVWriteWorker *pWorker = tsVWriteWP.worker + tsVWriteWP.nextId;
|
||||
taos_queue *queue = taosOpenQueue();
|
||||
if (queue == NULL) {
|
||||
pthread_mutex_unlock(&tsVWriteWP.mutex);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (pWorker->qset == NULL) {
|
||||
pWorker->qset = taosOpenQset();
|
||||
if (pWorker->qset == NULL) {
|
||||
taosCloseQueue(queue);
|
||||
pthread_mutex_unlock(&tsVWriteWP.mutex);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
taosAddIntoQset(pWorker->qset, queue, pVnode);
|
||||
pWorker->qall = taosAllocateQall();
|
||||
if (pWorker->qall == NULL) {
|
||||
taosCloseQset(pWorker->qset);
|
||||
taosCloseQueue(queue);
|
||||
pthread_mutex_unlock(&tsVWriteWP.mutex);
|
||||
return NULL;
|
||||
}
|
||||
pthread_attr_t thAttr;
|
||||
pthread_attr_init(&thAttr);
|
||||
pthread_attr_setdetachstate(&thAttr, PTHREAD_CREATE_JOINABLE);
|
||||
|
||||
if (pthread_create(&pWorker->thread, &thAttr, dnodeProcessVWriteQueue, pWorker) != 0) {
|
||||
dError("failed to create thread to process vwrite queue since %s", strerror(errno));
|
||||
taosFreeQall(pWorker->qall);
|
||||
taosCloseQset(pWorker->qset);
|
||||
taosCloseQueue(queue);
|
||||
queue = NULL;
|
||||
} else {
|
||||
dDebug("dnode vwrite worker:%d is launched", pWorker->workerId);
|
||||
tsVWriteWP.nextId = (tsVWriteWP.nextId + 1) % tsVWriteWP.max;
|
||||
}
|
||||
|
||||
pthread_attr_destroy(&thAttr);
|
||||
} else {
|
||||
taosAddIntoQset(pWorker->qset, queue, pVnode);
|
||||
tsVWriteWP.nextId = (tsVWriteWP.nextId + 1) % tsVWriteWP.max;
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&tsVWriteWP.mutex);
|
||||
dDebug("pVnode:%p, dnode vwrite queue:%p is allocated", pVnode, queue);
|
||||
|
||||
return queue;
|
||||
}
|
||||
|
||||
void dnodeFreeVWriteQueue(void *pWqueue) {
|
||||
taosCloseQueue(pWqueue);
|
||||
}
|
||||
|
||||
void dnodeSendRpcVWriteRsp(void *pVnode, void *wparam, int32_t code) {
|
||||
if (wparam == NULL) return;
|
||||
SVWriteMsg *pWrite = wparam;
|
||||
|
||||
if (code < 0) pWrite->code = code;
|
||||
int32_t count = atomic_add_fetch_32(&pWrite->processedCount, 1);
|
||||
|
||||
if (count <= 1) return;
|
||||
|
||||
SRpcMsg rpcRsp = {
|
||||
.handle = pWrite->rpcMsg.handle,
|
||||
.pCont = pWrite->rspRet.rsp,
|
||||
.contLen = pWrite->rspRet.len,
|
||||
.code = pWrite->code,
|
||||
};
|
||||
|
||||
rpcSendResponse(&rpcRsp);
|
||||
vnodeFreeFromWQueue(pVnode, pWrite);
|
||||
}
|
||||
|
||||
static void *dnodeProcessVWriteQueue(void *wparam) {
|
||||
SVWriteWorker *pWorker = wparam;
|
||||
SVWriteMsg * pWrite;
|
||||
void * pVnode;
|
||||
int32_t numOfMsgs;
|
||||
int32_t qtype;
|
||||
|
||||
taosBlockSIGPIPE();
|
||||
dDebug("dnode vwrite worker:%d is running", pWorker->workerId);
|
||||
|
||||
setThreadName("dnodeWriteQ");
|
||||
|
||||
while (1) {
|
||||
numOfMsgs = taosReadAllQitemsFromQset(pWorker->qset, pWorker->qall, &pVnode);
|
||||
if (numOfMsgs == 0) {
|
||||
dDebug("qset:%p, dnode vwrite got no message from qset, exiting", pWorker->qset);
|
||||
break;
|
||||
}
|
||||
|
||||
bool forceFsync = false;
|
||||
for (int32_t i = 0; i < numOfMsgs; ++i) {
|
||||
taosGetQitem(pWorker->qall, &qtype, (void **)&pWrite);
|
||||
dTrace("msg:%p, app:%p type:%s will be processed in vwrite queue, qtype:%s hver:%" PRIu64, pWrite,
|
||||
pWrite->rpcMsg.ahandle, taosMsg[pWrite->walHead.msgType], qtypeStr[qtype], pWrite->walHead.version);
|
||||
|
||||
pWrite->code = vnodeProcessWrite(pVnode, &pWrite->walHead, qtype, pWrite);
|
||||
if (pWrite->code <= 0) atomic_add_fetch_32(&pWrite->processedCount, 1);
|
||||
if (pWrite->code > 0) pWrite->code = 0;
|
||||
if (pWrite->code == 0 && pWrite->walHead.msgType != TSDB_MSG_TYPE_SUBMIT) forceFsync = true;
|
||||
|
||||
dTrace("msg:%p is processed in vwrite queue, code:0x%x", pWrite, pWrite->code);
|
||||
}
|
||||
|
||||
walFsync(vnodeGetWal(pVnode), forceFsync);
|
||||
|
||||
// browse all items, and process them one by one
|
||||
taosResetQitems(pWorker->qall);
|
||||
for (int32_t i = 0; i < numOfMsgs; ++i) {
|
||||
taosGetQitem(pWorker->qall, &qtype, (void **)&pWrite);
|
||||
if (qtype == TAOS_QTYPE_RPC) {
|
||||
dnodeSendRpcVWriteRsp(pVnode, pWrite, pWrite->code);
|
||||
} else {
|
||||
if (qtype == TAOS_QTYPE_FWD) {
|
||||
vnodeConfirmForward(pVnode, pWrite->walHead.version, pWrite->code, pWrite->walHead.msgType != TSDB_MSG_TYPE_SUBMIT);
|
||||
}
|
||||
if (pWrite->rspRet.rsp) {
|
||||
rpcFreeCont(pWrite->rspRet.rsp);
|
||||
}
|
||||
vnodeFreeFromWQueue(pVnode, pWrite);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
|
@ -1,303 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
|
||||
*
|
||||
* This program is free software: you can use, redistribute, and/or modify
|
||||
* it under the terms of the GNU Affero General Public License, version 3
|
||||
* or later ("AGPL"), as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE
|
||||
#include "os.h"
|
||||
#include "ttimer.h"
|
||||
#include "dnodeEps.h"
|
||||
#include "dnodeCfg.h"
|
||||
#include "dnodeMInfos.h"
|
||||
#include "dnodeVnodes.h"
|
||||
|
||||
typedef struct {
|
||||
pthread_t thread;
|
||||
int32_t threadIndex;
|
||||
int32_t failed;
|
||||
int32_t opened;
|
||||
int32_t vnodeNum;
|
||||
int32_t * vnodeList;
|
||||
} SOpenVnodeThread;
|
||||
|
||||
extern void * tsDnodeTmr;
|
||||
static void * tsStatusTimer = NULL;
|
||||
static uint32_t tsRebootTime = 0;
|
||||
static int32_t tsOpenVnodes = 0;
|
||||
static int32_t tsTotalVnodes = 0;
|
||||
|
||||
static void dnodeSendStatusMsg(void *handle, void *tmrId);
|
||||
static void dnodeProcessStatusRsp(SRpcMsg *pMsg);
|
||||
|
||||
int32_t dnodeInitStatusTimer() {
|
||||
dnodeAddClientRspHandle(TSDB_MSG_TYPE_DM_STATUS_RSP, dnodeProcessStatusRsp);
|
||||
|
||||
tsRebootTime = taosGetTimestampSec();
|
||||
taosTmrReset(dnodeSendStatusMsg, 500, NULL, tsDnodeTmr, &tsStatusTimer);
|
||||
|
||||
dInfo("dnode status timer is initialized");
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeCleanupStatusTimer() {
|
||||
if (tsStatusTimer != NULL) {
|
||||
taosTmrStopA(&tsStatusTimer);
|
||||
tsStatusTimer = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static int32_t dnodeGetVnodeList(int32_t vnodeList[], int32_t *numOfVnodes) {
|
||||
DIR *dir = opendir(tsVnodeDir);
|
||||
if (dir == NULL) return TSDB_CODE_DND_NO_WRITE_ACCESS;
|
||||
|
||||
*numOfVnodes = 0;
|
||||
struct dirent *de = NULL;
|
||||
while ((de = readdir(dir)) != NULL) {
|
||||
if (strcmp(de->d_name, ".") == 0 || strcmp(de->d_name, "..") == 0) continue;
|
||||
if (de->d_type & DT_DIR) {
|
||||
if (strncmp("vnode", de->d_name, 5) != 0) continue;
|
||||
int32_t vnode = atoi(de->d_name + 5);
|
||||
if (vnode == 0) continue;
|
||||
|
||||
(*numOfVnodes)++;
|
||||
|
||||
if (*numOfVnodes >= TSDB_MAX_VNODES) {
|
||||
dError("vgId:%d, too many vnode directory in disk, exist:%d max:%d", vnode, *numOfVnodes, TSDB_MAX_VNODES);
|
||||
closedir(dir);
|
||||
return TSDB_CODE_DND_TOO_MANY_VNODES;
|
||||
} else {
|
||||
vnodeList[*numOfVnodes - 1] = vnode;
|
||||
}
|
||||
}
|
||||
}
|
||||
closedir(dir);
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
static void *dnodeOpenVnode(void *param) {
|
||||
SOpenVnodeThread *pThread = param;
|
||||
char stepDesc[TSDB_STEP_DESC_LEN] = {0};
|
||||
|
||||
dDebug("thread:%d, start to open %d vnodes", pThread->threadIndex, pThread->vnodeNum);
|
||||
setThreadName("dnodeOpenVnode");
|
||||
|
||||
for (int32_t v = 0; v < pThread->vnodeNum; ++v) {
|
||||
int32_t vgId = pThread->vnodeList[v];
|
||||
snprintf(stepDesc, TSDB_STEP_DESC_LEN, "vgId:%d, start to restore, %d of %d have been opened", vgId, tsOpenVnodes, tsTotalVnodes);
|
||||
dnodeReportStep("open-vnodes", stepDesc, 0);
|
||||
|
||||
if (vnodeOpen(vgId) < 0) {
|
||||
dError("vgId:%d, failed to open vnode by thread:%d", vgId, pThread->threadIndex);
|
||||
pThread->failed++;
|
||||
} else {
|
||||
dDebug("vgId:%d, is opened by thread:%d", vgId, pThread->threadIndex);
|
||||
pThread->opened++;
|
||||
}
|
||||
|
||||
atomic_add_fetch_32(&tsOpenVnodes, 1);
|
||||
}
|
||||
|
||||
dDebug("thread:%d, total vnodes:%d, opened:%d failed:%d", pThread->threadIndex, pThread->vnodeNum, pThread->opened,
|
||||
pThread->failed);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int32_t dnodeInitVnodes() {
|
||||
int32_t vnodeList[TSDB_MAX_VNODES] = {0};
|
||||
int32_t numOfVnodes = 0;
|
||||
int32_t status = dnodeGetVnodeList(vnodeList, &numOfVnodes);
|
||||
tsTotalVnodes = numOfVnodes;
|
||||
|
||||
if (status != TSDB_CODE_SUCCESS) {
|
||||
dInfo("get dnode list failed");
|
||||
return status;
|
||||
}
|
||||
|
||||
int32_t threadNum = tsNumOfCores;
|
||||
int32_t vnodesPerThread = numOfVnodes / threadNum + 1;
|
||||
SOpenVnodeThread *threads = calloc(threadNum, sizeof(SOpenVnodeThread));
|
||||
for (int32_t t = 0; t < threadNum; ++t) {
|
||||
threads[t].threadIndex = t;
|
||||
threads[t].vnodeList = calloc(vnodesPerThread, sizeof(int32_t));
|
||||
}
|
||||
|
||||
for (int32_t v = 0; v < numOfVnodes; ++v) {
|
||||
int32_t t = v % threadNum;
|
||||
SOpenVnodeThread *pThread = &threads[t];
|
||||
pThread->vnodeList[pThread->vnodeNum++] = vnodeList[v];
|
||||
}
|
||||
|
||||
dInfo("start %d threads to open %d vnodes", threadNum, numOfVnodes);
|
||||
|
||||
for (int32_t t = 0; t < threadNum; ++t) {
|
||||
SOpenVnodeThread *pThread = &threads[t];
|
||||
if (pThread->vnodeNum == 0) continue;
|
||||
|
||||
pthread_attr_t thAttr;
|
||||
pthread_attr_init(&thAttr);
|
||||
pthread_attr_setdetachstate(&thAttr, PTHREAD_CREATE_JOINABLE);
|
||||
if (pthread_create(&pThread->thread, &thAttr, dnodeOpenVnode, pThread) != 0) {
|
||||
dError("thread:%d, failed to create thread to open vnode, reason:%s", pThread->threadIndex, strerror(errno));
|
||||
}
|
||||
|
||||
pthread_attr_destroy(&thAttr);
|
||||
}
|
||||
|
||||
int32_t openVnodes = 0;
|
||||
int32_t failedVnodes = 0;
|
||||
for (int32_t t = 0; t < threadNum; ++t) {
|
||||
SOpenVnodeThread *pThread = &threads[t];
|
||||
if (pThread->vnodeNum > 0 && taosCheckPthreadValid(pThread->thread)) {
|
||||
pthread_join(pThread->thread, NULL);
|
||||
}
|
||||
openVnodes += pThread->opened;
|
||||
failedVnodes += pThread->failed;
|
||||
free(pThread->vnodeList);
|
||||
}
|
||||
|
||||
free(threads);
|
||||
dInfo("there are total vnodes:%d, opened:%d", numOfVnodes, openVnodes);
|
||||
|
||||
if (failedVnodes != 0) {
|
||||
dError("there are total vnodes:%d, failed:%d", numOfVnodes, failedVnodes);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return TSDB_CODE_SUCCESS;
|
||||
}
|
||||
|
||||
void dnodeCleanupVnodes() {
|
||||
int32_t vnodeList[TSDB_MAX_VNODES]= {0};
|
||||
int32_t numOfVnodes = 0;
|
||||
int32_t status;
|
||||
|
||||
status = vnodeGetVnodeList(vnodeList, &numOfVnodes);
|
||||
|
||||
if (status != TSDB_CODE_SUCCESS) {
|
||||
dInfo("get dnode list failed");
|
||||
return;
|
||||
}
|
||||
|
||||
for (int32_t i = 0; i < numOfVnodes; ++i) {
|
||||
vnodeClose(vnodeList[i]);
|
||||
}
|
||||
|
||||
dInfo("total vnodes:%d are all closed", numOfVnodes);
|
||||
}
|
||||
|
||||
static void dnodeProcessStatusRsp(SRpcMsg *pMsg) {
|
||||
if (pMsg->code != TSDB_CODE_SUCCESS) {
|
||||
dError("status rsp is received, error:%s", tstrerror(pMsg->code));
|
||||
if (pMsg->code == TSDB_CODE_MND_DNODE_NOT_EXIST) {
|
||||
char clusterId[TSDB_CLUSTER_ID_LEN];
|
||||
dnodeGetClusterId(clusterId);
|
||||
if (clusterId[0] != '\0') {
|
||||
dnodeSetDropped();
|
||||
dError("exit zombie dropped dnode");
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
taosTmrReset(dnodeSendStatusMsg, tsStatusInterval * 1000, NULL, tsDnodeTmr, &tsStatusTimer);
|
||||
return;
|
||||
}
|
||||
|
||||
SStatusRsp *pStatusRsp = pMsg->pCont;
|
||||
SMInfos *minfos = &pStatusRsp->mnodes;
|
||||
dnodeUpdateMInfos(minfos);
|
||||
|
||||
SDnodeCfg *pCfg = &pStatusRsp->dnodeCfg;
|
||||
pCfg->numOfVnodes = htonl(pCfg->numOfVnodes);
|
||||
pCfg->moduleStatus = htonl(pCfg->moduleStatus);
|
||||
pCfg->dnodeId = htonl(pCfg->dnodeId);
|
||||
dnodeUpdateCfg(pCfg);
|
||||
|
||||
vnodeSetAccess(pStatusRsp->vgAccess, pCfg->numOfVnodes);
|
||||
|
||||
SDnodeEps *pEps = (SDnodeEps *)((char *)pStatusRsp->vgAccess + pCfg->numOfVnodes * sizeof(SVgroupAccess));
|
||||
dnodeUpdateEps(pEps);
|
||||
|
||||
taosTmrReset(dnodeSendStatusMsg, tsStatusInterval * 1000, NULL, tsDnodeTmr, &tsStatusTimer);
|
||||
}
|
||||
|
||||
static void dnodeSendStatusMsg(void *handle, void *tmrId) {
|
||||
if (tsDnodeTmr == NULL) {
|
||||
dError("dnode timer is already released");
|
||||
return;
|
||||
}
|
||||
|
||||
if (tsStatusTimer == NULL) {
|
||||
taosTmrReset(dnodeSendStatusMsg, tsStatusInterval * 1000, NULL, tsDnodeTmr, &tsStatusTimer);
|
||||
dError("failed to start status timer");
|
||||
return;
|
||||
}
|
||||
|
||||
int32_t contLen = sizeof(SStatusMsg) + TSDB_MAX_VNODES * sizeof(SVnodeLoad);
|
||||
SStatusMsg *pStatus = rpcMallocCont(contLen);
|
||||
if (pStatus == NULL) {
|
||||
taosTmrReset(dnodeSendStatusMsg, tsStatusInterval * 1000, NULL, tsDnodeTmr, &tsStatusTimer);
|
||||
dError("failed to malloc status message");
|
||||
return;
|
||||
}
|
||||
|
||||
dnodeGetCfg(&pStatus->dnodeId, pStatus->clusterId);
|
||||
pStatus->dnodeId = htonl(dnodeGetDnodeId());
|
||||
pStatus->version = htonl(tsVersion);
|
||||
pStatus->lastReboot = htonl(tsRebootTime);
|
||||
pStatus->numOfCores = htons((uint16_t) tsNumOfCores);
|
||||
pStatus->diskAvailable = tsAvailDataDirGB;
|
||||
pStatus->alternativeRole = tsAlternativeRole;
|
||||
tstrncpy(pStatus->dnodeEp, tsLocalEp, TSDB_EP_LEN);
|
||||
|
||||
// fill cluster cfg parameters
|
||||
pStatus->clusterCfg.numOfMnodes = htonl(tsNumOfMnodes);
|
||||
pStatus->clusterCfg.mnodeEqualVnodeNum = htonl(tsMnodeEqualVnodeNum);
|
||||
pStatus->clusterCfg.offlineThreshold = htonl(tsOfflineThreshold);
|
||||
pStatus->clusterCfg.statusInterval = htonl(tsStatusInterval);
|
||||
pStatus->clusterCfg.maxtablesPerVnode = htonl(tsMaxTablePerVnode);
|
||||
pStatus->clusterCfg.maxVgroupsPerDb = htonl(tsMaxVgroupsPerDb);
|
||||
tstrncpy(pStatus->clusterCfg.arbitrator, tsArbitrator, TSDB_EP_LEN);
|
||||
tstrncpy(pStatus->clusterCfg.timezone, tsTimezone, 64);
|
||||
pStatus->clusterCfg.checkTime = 0;
|
||||
char timestr[32] = "1970-01-01 00:00:00.00";
|
||||
(void)taosParseTime(timestr, &pStatus->clusterCfg.checkTime, (int32_t)strlen(timestr), TSDB_TIME_PRECISION_MILLI, 0);
|
||||
tstrncpy(pStatus->clusterCfg.locale, tsLocale, TSDB_LOCALE_LEN);
|
||||
tstrncpy(pStatus->clusterCfg.charset, tsCharset, TSDB_LOCALE_LEN);
|
||||
|
||||
pStatus->clusterCfg.enableBalance = tsEnableBalance;
|
||||
pStatus->clusterCfg.flowCtrl = tsEnableFlowCtrl;
|
||||
pStatus->clusterCfg.slaveQuery = tsEnableSlaveQuery;
|
||||
pStatus->clusterCfg.adjustMaster = tsEnableAdjustMaster;
|
||||
|
||||
vnodeBuildStatusMsg(pStatus);
|
||||
contLen = sizeof(SStatusMsg) + pStatus->openVnodes * sizeof(SVnodeLoad);
|
||||
pStatus->openVnodes = htons(pStatus->openVnodes);
|
||||
|
||||
SRpcMsg rpcMsg = {
|
||||
.pCont = pStatus,
|
||||
.contLen = contLen,
|
||||
.msgType = TSDB_MSG_TYPE_DM_STATUS
|
||||
};
|
||||
|
||||
SRpcEpSet epSet;
|
||||
dnodeGetEpSetForPeer(&epSet);
|
||||
dnodeSendMsgToDnode(&epSet, &rpcMsg);
|
||||
}
|
||||
|
||||
void dnodeSendStatusMsgToMnode() {
|
||||
if (tsDnodeTmr != NULL && tsStatusTimer != NULL) {
|
||||
dInfo("force send status msg to mnode");
|
||||
taosTmrReset(dnodeSendStatusMsg, 3, NULL, tsDnodeTmr, &tsStatusTimer);
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue