From 6bc6d1a3b8e144317d0b62ab6b948960a1520627 Mon Sep 17 00:00:00 2001 From: Shengliang Guan Date: Thu, 18 Jun 2020 07:41:51 +0000 Subject: [PATCH] [TD-466] add write auth for dnode --- src/dnode/src/dnodeMgmt.c | 6 +- src/inc/taoserror.h | 13 +-- src/inc/taosmsg.h | 1 + src/inc/vnode.h | 1 + src/mnode/inc/mnodeDef.h | 3 +- src/mnode/inc/mnodeVgroup.h | 2 +- src/mnode/src/mnodeAcct.c | 1 + src/mnode/src/mnodeDnode.c | 34 ++++---- src/mnode/src/mnodeVgroup.c | 2 + src/vnode/inc/vnodeInt.h | 1 + src/vnode/src/vnodeMain.c | 15 ++++ src/vnode/src/vnodeWrite.c | 4 + .../general/parser/limit1_tblocks100.sim | 1 + tests/script/unique/account/usage.sim | 86 +++++++++++++++++-- 14 files changed, 133 insertions(+), 37 deletions(-) diff --git a/src/dnode/src/dnodeMgmt.c b/src/dnode/src/dnodeMgmt.c index 30fdd21b99..d971e3ad6d 100644 --- a/src/dnode/src/dnodeMgmt.c +++ b/src/dnode/src/dnodeMgmt.c @@ -407,11 +407,7 @@ static void dnodeProcessStatusRsp(SRpcMsg *pMsg) { pMnodeInfo->nodeId = htonl(pMnodeInfo->nodeId); } - SDMVgroupAccess *pVgAcccess = pStatusRsp->vgAccess; - for (int32_t i = 0; i < pCfg->numOfVnodes; ++i) { - pVgAcccess[i].vgId = htonl(pVgAcccess[i].vgId); - } - + vnodeSetAccess(pStatusRsp->vgAccess, pCfg->numOfVnodes); dnodeProcessModuleStatus(pCfg->moduleStatus); dnodeUpdateDnodeCfg(pCfg); diff --git a/src/inc/taoserror.h b/src/inc/taoserror.h index ba95598646..562b9be854 100644 --- a/src/inc/taoserror.h +++ b/src/inc/taoserror.h @@ -113,12 +113,12 @@ TAOS_DEFINE_ERROR(TSDB_CODE_MND_INVALID_QUERY_ID, 0, 0x030C, "mnode inva TAOS_DEFINE_ERROR(TSDB_CODE_MND_INVALID_STREAM_ID, 0, 0x030D, "mnode invalid stream id") TAOS_DEFINE_ERROR(TSDB_CODE_MND_INVALID_CONN_ID, 0, 0x030E, "mnode invalid connection") -TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_OBJ_ALREADY_THERE, 0, 0x0320, "[sdb] object already there") -TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_ERROR, 0, 0x0321, "[sdb] app error") -TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_INVALID_TABLE_TYPE, 0, 0x0322, "[sdb] invalid table type") -TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_OBJ_NOT_THERE, 0, 0x0323, "[sdb] object not there") -TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_INVAID_META_ROW, 0, 0x0324, "[sdb] invalid meta row") -TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_INVAID_KEY_TYPE, 0, 0x0325, "[sdb] invalid key type") +TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_OBJ_ALREADY_THERE, 0, 0x0320, "sdb object already there") +TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_ERROR, 0, 0x0321, "sdb app error") +TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_INVALID_TABLE_TYPE, 0, 0x0322, "sdb invalid table type") +TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_OBJ_NOT_THERE, 0, 0x0323, "sdb object not there") +TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_INVAID_META_ROW, 0, 0x0324, "sdb invalid meta row") +TAOS_DEFINE_ERROR(TSDB_CODE_MND_SDB_INVAID_KEY_TYPE, 0, 0x0325, "sdb invalid key type") TAOS_DEFINE_ERROR(TSDB_CODE_MND_DNODE_ALREADY_EXIST, 0, 0x0330, "mnode dnode already exist") TAOS_DEFINE_ERROR(TSDB_CODE_MND_DNODE_NOT_EXIST, 0, 0x0331, "mnode dnode not exist") @@ -179,6 +179,7 @@ TAOS_DEFINE_ERROR(TSDB_CODE_VND_NO_DISK_PERMISSIONS, 0, 0x0506, "vnode no d TAOS_DEFINE_ERROR(TSDB_CODE_VND_NO_SUCH_FILE_OR_DIR, 0, 0x0507, "vnode no such file or directory") TAOS_DEFINE_ERROR(TSDB_CODE_VND_OUT_OF_MEMORY, 0, 0x0508, "vnode out of memory") TAOS_DEFINE_ERROR(TSDB_CODE_VND_APP_ERROR, 0, 0x0509, "vnode app error") +TAOS_DEFINE_ERROR(TSDB_CODE_VND_NO_WRITE_AUTH, 0, 0x0214, "vnode no write auth") // tsdb TAOS_DEFINE_ERROR(TSDB_CODE_TDB_INVALID_TABLE_ID, 0, 0x0600, "tsdb invalid table id") diff --git a/src/inc/taosmsg.h b/src/inc/taosmsg.h index fcb6d66422..78255a45d5 100644 --- a/src/inc/taosmsg.h +++ b/src/inc/taosmsg.h @@ -543,6 +543,7 @@ typedef struct { int32_t dnodeId; uint32_t moduleStatus; uint32_t numOfVnodes; + uint32_t reserved; } SDMDnodeCfg; typedef struct { diff --git a/src/inc/vnode.h b/src/inc/vnode.h index 0da1f51e27..9f0c8cc241 100644 --- a/src/inc/vnode.h +++ b/src/inc/vnode.h @@ -58,6 +58,7 @@ void* vnodeGetWal(void *pVnode); int32_t vnodeProcessWrite(void *pVnode, int qtype, void *pHead, void *item); void vnodeBuildStatusMsg(void * param); +void vnodeSetAccess(SDMVgroupAccess *pAccess, int32_t numOfVnodes); int32_t vnodeProcessRead(void *pVnode, SReadMsg *pReadMsg); diff --git a/src/mnode/inc/mnodeDef.h b/src/mnode/inc/mnodeDef.h index 2baf28f88f..80a638a21e 100644 --- a/src/mnode/inc/mnodeDef.h +++ b/src/mnode/inc/mnodeDef.h @@ -122,7 +122,8 @@ typedef struct SVgObj { int32_t lbDnodeId; int32_t lbTime; int8_t inUse; - int8_t reserved[13]; + int8_t accessState; + int8_t reserved[12]; int8_t updateEnd[1]; int32_t refCount; struct SVgObj *prev, *next; diff --git a/src/mnode/inc/mnodeVgroup.h b/src/mnode/inc/mnodeVgroup.h index d61145d9b8..683212998f 100644 --- a/src/mnode/inc/mnodeVgroup.h +++ b/src/mnode/inc/mnodeVgroup.h @@ -34,7 +34,7 @@ void mnodeUpdateAllDbVgroups(SDbObj *pAlterDb); void * mnodeGetNextVgroup(void *pIter, SVgObj **pVgroup); void mnodeUpdateVgroup(SVgObj *pVgroup); -void mnodeUpdateVgroupStatus(SVgObj *pVgroup, SDnodeObj *dnodeId, SVnodeLoad *pVload); +void mnodeUpdateVgroupStatus(SVgObj *pVgroup, SDnodeObj *pDnode, SVnodeLoad *pVload); int32_t mnodeCreateVgroup(struct SMnodeMsg *pMsg, SDbObj *pDb); void mnodeDropVgroup(SVgObj *pVgroup, void *ahandle); diff --git a/src/mnode/src/mnodeAcct.c b/src/mnode/src/mnodeAcct.c index 4c79564769..3fcb3849aa 100644 --- a/src/mnode/src/mnodeAcct.c +++ b/src/mnode/src/mnodeAcct.c @@ -39,6 +39,7 @@ static int32_t mnodeAcctActionDestroy(SSdbOper *pOper) { static int32_t mnodeAcctActionInsert(SSdbOper *pOper) { SAcctObj *pAcct = pOper->pObj; memset(&pAcct->acctInfo, 0, sizeof(SAcctInfo)); + pAcct->acctInfo.accessState = TSDB_VN_ALL_ACCCESS; pthread_mutex_init(&pAcct->mutex, NULL); return TSDB_CODE_SUCCESS; } diff --git a/src/mnode/src/mnodeDnode.c b/src/mnode/src/mnodeDnode.c index 35f4ea43d3..f7f4457a1c 100644 --- a/src/mnode/src/mnodeDnode.c +++ b/src/mnode/src/mnodeDnode.c @@ -335,6 +335,19 @@ static int32_t mnodeProcessDnodeStatusMsg(SMnodeMsg *pMsg) { } int32_t openVnodes = htons(pStatus->openVnodes); + int32_t contLen = sizeof(SDMStatusRsp) + openVnodes * sizeof(SDMVgroupAccess); + SDMStatusRsp *pRsp = rpcMallocCont(contLen); + if (pRsp == NULL) { + mnodeDecDnodeRef(pDnode); + return TSDB_CODE_MND_OUT_OF_MEMORY; + } + + pRsp->dnodeCfg.dnodeId = htonl(pDnode->dnodeId); + pRsp->dnodeCfg.moduleStatus = htonl((int32_t)pDnode->isMgmt); + pRsp->dnodeCfg.numOfVnodes = htonl(openVnodes); + mnodeGetMnodeInfos(&pRsp->mnodes); + SDMVgroupAccess *pAccess = (SDMVgroupAccess *)((char *)pRsp + sizeof(SDMStatusRsp)); + for (int32_t j = 0; j < openVnodes; ++j) { SVnodeLoad *pVload = &pStatus->load[j]; pVload->vgId = htonl(pVload->vgId); @@ -347,6 +360,8 @@ static int32_t mnodeProcessDnodeStatusMsg(SMnodeMsg *pMsg) { mnodeSendDropVnodeMsg(pVload->vgId, &ipSet, NULL); } else { mnodeUpdateVgroupStatus(pVgroup, pDnode, pVload); + pAccess->vgId = htonl(pVload->vgId); + pAccess->accessState = pVgroup->accessState; mnodeDecVgroupRef(pVgroup); } } @@ -366,26 +381,9 @@ static int32_t mnodeProcessDnodeStatusMsg(SMnodeMsg *pMsg) { balanceNotify(); } - mnodeDecDnodeRef(pDnode); - - int32_t contLen = sizeof(SDMStatusRsp) + TSDB_MAX_VNODES * sizeof(SDMVgroupAccess); - SDMStatusRsp *pRsp = rpcMallocCont(contLen); - if (pRsp == NULL) { - return TSDB_CODE_MND_OUT_OF_MEMORY; - } - pDnode->lastAccess = tsAccessSquence; + mnodeDecDnodeRef(pDnode); - mnodeGetMnodeInfos(&pRsp->mnodes); - - pRsp->dnodeCfg.dnodeId = htonl(pDnode->dnodeId); - pRsp->dnodeCfg.moduleStatus = htonl((int32_t)pDnode->isMgmt); - pRsp->dnodeCfg.numOfVnodes = 0; - - contLen = sizeof(SDMStatusRsp); - - //TODO: set vnode access - pMsg->rpcRsp.len = contLen; pMsg->rpcRsp.rsp = pRsp; diff --git a/src/mnode/src/mnodeVgroup.c b/src/mnode/src/mnodeVgroup.c index 10dfb2a28a..94753b970a 100644 --- a/src/mnode/src/mnodeVgroup.c +++ b/src/mnode/src/mnodeVgroup.c @@ -74,6 +74,7 @@ static int32_t mnodeVgroupActionInsert(SSdbOper *pOper) { pVgroup->pDb = pDb; pVgroup->prev = NULL; pVgroup->next = NULL; + pVgroup->accessState = TSDB_VN_ALL_ACCCESS; int32_t size = sizeof(SChildTableObj *) * pDb->cfg.maxTables; pVgroup->tableList = calloc(pDb->cfg.maxTables, sizeof(SChildTableObj *)); @@ -324,6 +325,7 @@ int32_t mnodeCreateVgroup(SMnodeMsg *pMsg, SDbObj *pDb) { strcpy(pVgroup->dbName, pDb->name); pVgroup->numOfVnodes = pDb->cfg.replications; pVgroup->createdTime = taosGetTimestampMs(); + pVgroup->accessState = TSDB_VN_ALL_ACCCESS; if (balanceAllocVnodes(pVgroup) != 0) { mError("db:%s, no enough dnode to alloc %d vnodes to vgroup", pDb->name, pVgroup->numOfVnodes); free(pVgroup); diff --git a/src/vnode/inc/vnodeInt.h b/src/vnode/inc/vnodeInt.h index ab74e329e6..d5a7dbfd2e 100644 --- a/src/vnode/inc/vnodeInt.h +++ b/src/vnode/inc/vnodeInt.h @@ -37,6 +37,7 @@ typedef struct { int32_t refCount; // reference count int status; int8_t role; + int8_t accessState; int64_t version; // current version int64_t fversion; // version on saved data file void *wqueue; diff --git a/src/vnode/src/vnodeMain.c b/src/vnode/src/vnodeMain.c index bada60b19b..1d88b2fff2 100644 --- a/src/vnode/src/vnodeMain.c +++ b/src/vnode/src/vnodeMain.c @@ -195,6 +195,7 @@ int32_t vnodeOpen(int32_t vnode, char *rootDir) { pVnode->version = 0; pVnode->tsdbCfg.tsdbId = pVnode->vgId; pVnode->rootDir = strdup(rootDir); + pVnode->accessState = TSDB_VN_ALL_ACCCESS; int32_t code = vnodeReadCfg(pVnode); if (code != TSDB_CODE_SUCCESS) { @@ -431,6 +432,20 @@ void vnodeBuildStatusMsg(void *param) { taosHashDestroyIter(pIter); } +void vnodeSetAccess(SDMVgroupAccess *pAccess, int32_t numOfVnodes) { + for (int32_t i = 0; i < numOfVnodes; ++i) { + pAccess[i].vgId = htonl(pAccess[i].vgId); + SVnodeObj *pVnode = vnodeAccquireVnode(pAccess[i].vgId); + if (pVnode != NULL) { + pVnode->accessState = pAccess[i].accessState; + if (pVnode->accessState != TSDB_VN_ALL_ACCCESS) { + vTrace("vgId:%d, access state is set to %d", pAccess[i].vgId) + } + } + vnodeRelease(pVnode); + } +} + static void vnodeCleanUp(SVnodeObj *pVnode) { // remove from hash, so new messages wont be consumed taosHashRemove(tsDnodeVnodesHash, (const char *)&pVnode->vgId, sizeof(int32_t)); diff --git a/src/vnode/src/vnodeWrite.c b/src/vnode/src/vnodeWrite.c index fa322757e2..a6a43a81aa 100644 --- a/src/vnode/src/vnodeWrite.c +++ b/src/vnode/src/vnodeWrite.c @@ -53,6 +53,10 @@ int32_t vnodeProcessWrite(void *param1, int qtype, void *param2, void *item) { if (vnodeProcessWriteMsgFp[pHead->msgType] == NULL) return TSDB_CODE_VND_MSG_NOT_PROCESSED; + if (!(pVnode->accessState & TSDB_VN_WRITE_ACCCESS)) { + return TSDB_CODE_VND_NO_WRITE_AUTH; + } + if (pHead->version == 0) { // from client or CQ if (pVnode->status != TAOS_VN_STATUS_READY) return TSDB_CODE_VND_INVALID_VGROUP_ID; // it may be in deleting or closing state diff --git a/tests/script/general/parser/limit1_tblocks100.sim b/tests/script/general/parser/limit1_tblocks100.sim index 2235e6b424..29b48bdd43 100644 --- a/tests/script/general/parser/limit1_tblocks100.sim +++ b/tests/script/general/parser/limit1_tblocks100.sim @@ -61,6 +61,7 @@ run general/parser/limit1_stb.sim print ================== restart server to commit data into disk system sh/exec.sh -n dnode1 -s stop -x SIGINT +sleep 5000 system sh/exec.sh -n dnode1 -s start print ================== server restart completed diff --git a/tests/script/unique/account/usage.sim b/tests/script/unique/account/usage.sim index c1c5d75728..3f12c46137 100644 --- a/tests/script/unique/account/usage.sim +++ b/tests/script/unique/account/usage.sim @@ -1,6 +1,8 @@ system sh/stop_dnodes.sh system sh/deploy.sh -n dnode1 -i 1 system sh/exec.sh -n dnode1 -s start +#system sh/exec.sh -n monitor -s 1 +system sh/exec.sh -n monitorInterval -s 1 sleep 3000 sql connect @@ -25,13 +27,16 @@ endi if $data05 != 0/10 then return -1 endi - +if $data06 != 0.000/unlimited then + return -1 +endi + print =============== check usage account -sql create database d1 -sql create database d2 -sql create database d3 -sql create database d4 -sql create database d5 +sql create database d1 wal 2 +sql create database d2 wal 2 +sql create database d3 wal 2 +sql create database d4 wal 2 +sql create database d5 wal 2 sql create table d1.t1 (ts timestamp, i int); sql create user u1 pass "u1" @@ -53,6 +58,75 @@ endi if $data05 != 0/10 then return -1 endi +if $data06 != 0.000/unlimited then + return -1 +endi + +print =============== step2 +sql alter account root pass "taosdata" tseries 10 storage 1073741824 streams 10 dbs 5 users 5 +sql show accounts +print $data00 $data01 $data02 $data03 $data04 $data05 $data06 +if $data00 != root then + return -1 +endi +if $data02 != 4/5 then + return -1 +endi +if $data03 != 5/5 then + return -1 +endi +if $data04 != 1/10 then + return -1 +endi +if $data05 != 0/10 then + return -1 +endi +if $data06 != 0.000/1.000 then + return -1 +endi + +print =============== step3 +sql alter account root pass "taosdata" tseries 10 storage 16 streams 10 dbs 5 users 5 +sql show accounts +print $data00 $data01 $data02 $data03 $data04 $data05 $data06 +if $data00 != root then + return -1 +endi +if $data02 != 4/5 then + return -1 +endi +if $data03 != 5/5 then + return -1 +endi +if $data04 != 1/10 then + return -1 +endi +if $data05 != 0/10 then + return -1 +endi +if $data06 != 0.000/0.000 then + return -1 +endi + +print =============== step4 +sql insert into d1.t1 values(now + 1s, 1) +sql insert into d1.t1 values(now + 2s, 2) + +# no write auth +sleep 3000 +sql_error insert into d1.t1 values(now + 3s, 2) +sql_error insert into d1.t1 values(now + 4s, 2) + +sql alter account root pass "taosdata" tseries 10 storage 36 streams 10 dbs 5 users 5 +sleep 3000 +sql insert into d1.t1 values(now + 5s, 1) +sql insert into d1.t1 values(now + 6s, 2) + +# no write auth +sleep 3000 +sql_error insert into d1.t1 values(now + 7s, 2) +sql_error insert into d1.t1 values(now + 8s, 2) + print =============== check grant sql_error create database d6 -- GitLab