• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

taosdata / TDengine / #4335

20 Jun 2025 05:45AM UTC coverage: 60.571% (-2.3%) from 62.916%
#4335

push

travis-ci

web-flow
fix: compatibility ci problems. (#31430)

149119 of 315107 branches covered (47.32%)

Branch coverage included in aggregate %.

231167 of 312731 relevant lines covered (73.92%)

6342953.77 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

58.82
/source/dnode/mnode/impl/src/mndUser.c
1
/*
2
 * Copyright (c) 2019 TAOS Data, Inc. <jhtao@taosdata.com>
3
 *
4
 * This program is free software: you can use, redistribute, and/or modify
5
 * it under the terms of the GNU Affero General Public License, version 3
6
 * or later ("AGPL"), as published by the Free Software Foundation.
7
 *
8
 * This program is distributed in the hope that it will be useful, but WITHOUT
9
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10
 * FITNESS FOR A PARTICULAR PURPOSE.
11
 *
12
 * You should have received a copy of the GNU Affero General Public License
13
 * along with this program. If not, see <http://www.gnu.org/licenses/>.
14
 */
15

16
#define _DEFAULT_SOURCE
17
// clang-format off
18
#ifndef TD_ASTRA
19
#include <uv.h>
20
#endif
21
#include "mndUser.h"
22
#include "audit.h"
23
#include "mndDb.h"
24
#include "mndPrivilege.h"
25
#include "mndShow.h"
26
#include "mndStb.h"
27
#include "mndTopic.h"
28
#include "mndTrans.h"
29
#include "tbase64.h"
30

31
// clang-format on
32

33
#define USER_VER_NUMBER                      7
34
#define USER_VER_SUPPORT_WHITELIST           5
35
#define USER_VER_SUPPORT_WHITELIT_DUAL_STACK 7
36
#define USER_RESERVE_SIZE                    64
37

38
#define BIT_FLAG_MASK(n)              (1 << n)
39
#define BIT_FLAG_SET_MASK(val, mask)  ((val) |= (mask))
40
#define BIT_FLAG_TEST_MASK(val, mask) (((val) & (mask)) != 0)
41

42
#define PRIVILEGE_TYPE_ALL       BIT_FLAG_MASK(0)
43
#define PRIVILEGE_TYPE_READ      BIT_FLAG_MASK(1)
44
#define PRIVILEGE_TYPE_WRITE     BIT_FLAG_MASK(2)
45
#define PRIVILEGE_TYPE_SUBSCRIBE BIT_FLAG_MASK(3)
46
#define PRIVILEGE_TYPE_ALTER     BIT_FLAG_MASK(4)
47

48
#define ALTER_USER_ADD_PRIVS(_type) ((_type) == TSDB_ALTER_USER_ADD_PRIVILEGES)
49
#define ALTER_USER_DEL_PRIVS(_type) ((_type) == TSDB_ALTER_USER_DEL_PRIVILEGES)
50

51
#define ALTER_USER_ALL_PRIV(_priv) (BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_ALL))
52
#define ALTER_USER_READ_PRIV(_priv) \
53
  (BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_READ) || BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_ALL))
54
#define ALTER_USER_WRITE_PRIV(_priv) \
55
  (BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_WRITE) || BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_ALL))
56
#define ALTER_USER_ALTER_PRIV(_priv) \
57
  (BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_ALTER) || BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_ALL))
58
#define ALTER_USER_SUBSCRIBE_PRIV(_priv) (BIT_FLAG_TEST_MASK((_priv), PRIVILEGE_TYPE_SUBSCRIBE))
59

60
#define ALTER_USER_TARGET_DB(_tbname) (0 == (_tbname)[0])
61
#define ALTER_USER_TARGET_TB(_tbname) (0 != (_tbname)[0])
62

63
#define ALTER_USER_ADD_READ_DB_PRIV(_type, _priv, _tbname) \
64
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_READ_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
65
#define ALTER_USER_DEL_READ_DB_PRIV(_type, _priv, _tbname) \
66
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_READ_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
67
#define ALTER_USER_ADD_WRITE_DB_PRIV(_type, _priv, _tbname) \
68
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_WRITE_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
69
#define ALTER_USER_DEL_WRITE_DB_PRIV(_type, _priv, _tbname) \
70
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_WRITE_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
71
#define ALTER_USER_ADD_ALTER_DB_PRIV(_type, _priv, _tbname) \
72
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_ALTER_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
73
#define ALTER_USER_DEL_ALTER_DB_PRIV(_type, _priv, _tbname) \
74
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_ALTER_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
75
#define ALTER_USER_ADD_ALL_DB_PRIV(_type, _priv, _tbname) \
76
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_ALL_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
77
#define ALTER_USER_DEL_ALL_DB_PRIV(_type, _priv, _tbname) \
78
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_ALL_PRIV(_priv) && ALTER_USER_TARGET_DB(_tbname))
79

80
#define ALTER_USER_ADD_READ_TB_PRIV(_type, _priv, _tbname) \
81
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_READ_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
82
#define ALTER_USER_DEL_READ_TB_PRIV(_type, _priv, _tbname) \
83
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_READ_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
84
#define ALTER_USER_ADD_WRITE_TB_PRIV(_type, _priv, _tbname) \
85
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_WRITE_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
86
#define ALTER_USER_DEL_WRITE_TB_PRIV(_type, _priv, _tbname) \
87
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_WRITE_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
88
#define ALTER_USER_ADD_ALTER_TB_PRIV(_type, _priv, _tbname) \
89
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_ALTER_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
90
#define ALTER_USER_DEL_ALTER_TB_PRIV(_type, _priv, _tbname) \
91
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_ALTER_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
92
#define ALTER_USER_ADD_ALL_TB_PRIV(_type, _priv, _tbname) \
93
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_ALL_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
94
#define ALTER_USER_DEL_ALL_TB_PRIV(_type, _priv, _tbname) \
95
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_ALL_PRIV(_priv) && ALTER_USER_TARGET_TB(_tbname))
96

97
#define ALTER_USER_ADD_SUBSCRIBE_TOPIC_PRIV(_type, _priv) \
98
  (ALTER_USER_ADD_PRIVS(_type) && ALTER_USER_SUBSCRIBE_PRIV(_priv))
99
#define ALTER_USER_DEL_SUBSCRIBE_TOPIC_PRIV(_type, _priv) \
100
  (ALTER_USER_DEL_PRIVS(_type) && ALTER_USER_SUBSCRIBE_PRIV(_priv))
101

102
static int32_t createDefaultIpWhiteList(SIpWhiteListDual **ppWhiteList);
103
static int32_t createIpWhiteList(void *buf, int32_t len, SIpWhiteListDual **ppWhiteList);
104

105
static bool isIpWhiteListEqual(SIpWhiteListDual *a, SIpWhiteListDual *b);
106
static bool isIpRangeEqual(SIpRange *a, SIpRange *b);
107

108
void destroyIpWhiteTab(SHashObj *pIpWhiteTab);
109

110
#define MND_MAX_USE_HOST (TSDB_PRIVILEDGE_HOST_LEN / 24)
111

112
static int32_t  mndCreateDefaultUsers(SMnode *pMnode);
113
static SSdbRow *mndUserActionDecode(SSdbRaw *pRaw);
114
static int32_t  mndUserActionInsert(SSdb *pSdb, SUserObj *pUser);
115
static int32_t  mndUserActionDelete(SSdb *pSdb, SUserObj *pUser);
116
static int32_t  mndUserActionUpdate(SSdb *pSdb, SUserObj *pOld, SUserObj *pNew);
117
static int32_t  mndCreateUser(SMnode *pMnode, char *acct, SCreateUserReq *pCreate, SRpcMsg *pReq);
118
static int32_t  mndProcessCreateUserReq(SRpcMsg *pReq);
119
static int32_t  mndProcessAlterUserReq(SRpcMsg *pReq);
120
static int32_t  mndProcessDropUserReq(SRpcMsg *pReq);
121
static int32_t  mndProcessGetUserAuthReq(SRpcMsg *pReq);
122
static int32_t  mndProcessGetUserWhiteListReq(SRpcMsg *pReq);
123
static int32_t  mndRetrieveUsers(SRpcMsg *pReq, SShowObj *pShow, SSDataBlock *pBlock, int32_t rows);
124
static int32_t  mndRetrieveUsersFull(SRpcMsg *pReq, SShowObj *pShow, SSDataBlock *pBlock, int32_t rows);
125
static void     mndCancelGetNextUser(SMnode *pMnode, void *pIter);
126
static int32_t  mndRetrievePrivileges(SRpcMsg *pReq, SShowObj *pShow, SSDataBlock *pBlock, int32_t rows);
127
static void     mndCancelGetNextPrivileges(SMnode *pMnode, void *pIter);
128
static int32_t  mndFetchAllIpWhite(SMnode *pMnode, SHashObj **ppIpWhiteTab);
129
static int32_t  mndProcesSRetrieveIpWhiteReq(SRpcMsg *pReq);
130
static int32_t  mndUpdateIpWhiteImpl(SHashObj *pIpWhiteTab, char *user, char *fqdn, int8_t type, bool *pUpdate);
131

132
static int32_t ipWhiteMgtUpdateAll(SMnode *pMnode);
133
static int32_t ipWhiteMgtRemove(char *user);
134

135
static int32_t createIpWhiteListFromOldVer(void *buf, int32_t len, SIpWhiteList **ppList);
136
static int32_t tDerializeIpWhileListFromOldVer(void *buf, int32_t len, SIpWhiteList *pList);
137
typedef struct {
138
  SHashObj      *pIpWhiteTab;
139
  int64_t        ver;
140
  TdThreadRwlock rw;
141
} SIpWhiteMgt;
142

143
static SIpWhiteMgt ipWhiteMgt;
144

145
const static SIpV4Range defaultIpRange = {.ip = 16777343, .mask = 32};
146

147
static int32_t ipWhiteMgtInit() {
2,223✔
148
  ipWhiteMgt.pIpWhiteTab = taosHashInit(8, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), 1, HASH_ENTRY_LOCK);
2,223✔
149
  if (ipWhiteMgt.pIpWhiteTab == NULL) {
2,223!
150
    TAOS_RETURN(terrno);
×
151
  }
152
  ipWhiteMgt.ver = 0;
2,223✔
153
  (void)taosThreadRwlockInit(&ipWhiteMgt.rw, NULL);
2,223✔
154
  TAOS_RETURN(0);
2,223✔
155
}
156
void ipWhiteMgtCleanup() {
2,221✔
157
  destroyIpWhiteTab(ipWhiteMgt.pIpWhiteTab);
2,221✔
158
  (void)taosThreadRwlockDestroy(&ipWhiteMgt.rw);
2,221✔
159
}
2,221✔
160

161
int32_t ipWhiteMgtUpdate(SMnode *pMnode, char *user, SIpWhiteListDual *pNew) {
1,386✔
162
  int32_t code = 0;
1,386✔
163
  int32_t lino = 0;
1,386✔
164
  bool    update = true;
1,386✔
165
  SArray *fqdns = NULL;
1,386✔
166
  (void)taosThreadRwlockWrlock(&ipWhiteMgt.rw);
1,386✔
167
  SIpWhiteListDual **ppList = taosHashGet(ipWhiteMgt.pIpWhiteTab, user, strlen(user));
1,386✔
168

169
  if (ppList == NULL || *ppList == NULL) {
1,575!
170
    SIpWhiteListDual *p = cloneIpWhiteList(pNew);
189✔
171
    if (p == NULL) {
189!
172
      update = false;
×
173
      TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
174
    }
175
    if ((code = taosHashPut(ipWhiteMgt.pIpWhiteTab, user, strlen(user), &p, sizeof(void *))) != 0) {
189!
176
      update = false;
×
177
      taosMemoryFree(p);
×
178
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
179
    }
180
  } else {
181
    SIpWhiteListDual *pOld = *ppList;
1,197✔
182
    if (isIpWhiteListEqual(pOld, pNew)) {
1,197✔
183
      update = false;
1,172✔
184
    } else {
185
      taosMemoryFree(pOld);
25!
186
      SIpWhiteListDual *p = cloneIpWhiteList(pNew);
25✔
187
      if (p == NULL) {
25!
188
        update = false;
×
189
        TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
190
      }
191
      if ((code = taosHashPut(ipWhiteMgt.pIpWhiteTab, user, strlen(user), &p, sizeof(void *))) != 0) {
25!
192
        update = false;
×
193
        taosMemoryFree(p);
×
194
        TAOS_CHECK_GOTO(code, &lino, _OVER);
×
195
      }
196
    }
197
  }
198

199
  fqdns = mndGetAllDnodeFqdns(pMnode);  // TODO: update this line after refactor api
1,386✔
200
  if (fqdns == NULL) {
1,386!
201
    update = false;
×
202
    TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
203
  }
204

205
  for (int i = 0; i < taosArrayGetSize(fqdns); i++) {
2,983✔
206
    char *fqdn = taosArrayGetP(fqdns, i);
1,597✔
207
    bool  upd = false;
1,597✔
208
    TAOS_CHECK_GOTO(mndUpdateIpWhiteImpl(ipWhiteMgt.pIpWhiteTab, TSDB_DEFAULT_USER, fqdn, IP_WHITE_ADD, &upd), &lino,
1,597!
209
                    _OVER);
210
    update |= upd;
1,597✔
211
    TAOS_CHECK_GOTO(mndUpdateIpWhiteImpl(ipWhiteMgt.pIpWhiteTab, user, fqdn, IP_WHITE_ADD, &upd), &lino, _OVER);
1,597!
212
    update |= upd;
1,597✔
213
  }
214

215
  if (update) ipWhiteMgt.ver++;
1,386✔
216

217
_OVER:
1,172✔
218
  (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
1,386✔
219
  taosArrayDestroyP(fqdns, NULL);
1,386✔
220
  if (code < 0) {
1,386!
221
    mError("failed to update ip white list for user: %s at line %d since %s", user, lino, tstrerror(code));
×
222
  }
223
  TAOS_RETURN(code);
1,386✔
224
}
225
int32_t ipWhiteMgtRemove(char *user) {
75✔
226
  bool    update = true;
75✔
227
  int32_t code = 0;
75✔
228
  (void)taosThreadRwlockWrlock(&ipWhiteMgt.rw);
75✔
229
  SIpWhiteListDual **ppList = taosHashGet(ipWhiteMgt.pIpWhiteTab, user, strlen(user));
75✔
230
  if (ppList == NULL || *ppList == NULL) {
75!
231
    update = false;
×
232
  } else {
233
    taosMemoryFree(*ppList);
75!
234
    code = taosHashRemove(ipWhiteMgt.pIpWhiteTab, user, strlen(user));
75✔
235
    if (code != 0) {
75!
236
      update = false;
×
237
    }
238
  }
239

240
  if (update) ipWhiteMgt.ver++;
75!
241
  (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
75✔
242
  return 0;
75✔
243
}
244

245
bool isRangeInWhiteList(SIpWhiteListDual *pList, SIpRange *range) {
7,879✔
246
  for (int i = 0; i < pList->num; i++) {
11,035✔
247
    if (isIpRangeEqual(&pList->pIpRanges[i], range)) {
10,725✔
248
      return true;
7,569✔
249
    }
250
  }
251
  return false;
310✔
252
}
253

254
static int32_t ipWhiteMgtUpdateAll(SMnode *pMnode) {
2,547✔
255
  SHashObj *pNew = NULL;
2,547✔
256
  TAOS_CHECK_RETURN(mndFetchAllIpWhite(pMnode, &pNew));
2,547!
257

258
  SHashObj *pOld = ipWhiteMgt.pIpWhiteTab;
2,547✔
259

260
  ipWhiteMgt.pIpWhiteTab = pNew;
2,547✔
261
  ipWhiteMgt.ver++;
2,547✔
262

263
  destroyIpWhiteTab(pOld);
2,547✔
264
  TAOS_RETURN(0);
2,547✔
265
}
266

267
int64_t mndGetIpWhiteVer(SMnode *pMnode) {
93,471✔
268
  int64_t ver = 0;
93,471✔
269
  int32_t code = 0;
93,471✔
270
  (void)taosThreadRwlockWrlock(&ipWhiteMgt.rw);
93,471✔
271
  if (ipWhiteMgt.ver == 0) {
93,471!
272
    // get user and dnode ip white list
273
    if ((code = ipWhiteMgtUpdateAll(pMnode)) != 0) {
×
274
      (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
×
275
      mError("%s failed to update ip white list since %s", __func__, tstrerror(code));
×
276
      return ver;
×
277
    }
278
    ipWhiteMgt.ver = taosGetTimestampMs();
×
279
  }
280
  ver = ipWhiteMgt.ver;
93,471✔
281
  (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
93,471✔
282

283
  if (mndEnableIpWhiteList(pMnode) == 0 || tsEnableWhiteList == false) {
93,471!
284
    ver = 0;
93,446✔
285
  }
286
  mDebug("ip-white-list on mnode ver: %" PRId64, ver);
93,471✔
287
  return ver;
93,471✔
288
}
289

290
int32_t mndUpdateIpWhiteImpl(SHashObj *pIpWhiteTab, char *user, char *fqdn, int8_t type, bool *pUpdate) {
9,545✔
291
  int32_t lino = 0;
9,545✔
292
  bool    update = false;
9,545✔
293

294
  SIpRange range = {0};
9,545✔
295
  SIpAddr  addr = {0};
9,545✔
296
  int32_t  code = taosGetIpFromFqdn(tsEnableIpv6, fqdn, &addr);
9,545✔
297
  if (code) {
9,545!
298
    mError("failed to get ip from fqdn: %s at line %d since %s", fqdn, lino, tstrerror(code));
×
299
    TAOS_RETURN(TSDB_CODE_TSC_INVALID_FQDN);
×
300
  }
301

302
  code = tIpStrToUint(&addr, &range);
9,545✔
303
  if (code) {
9,545!
304
    TAOS_RETURN(code);
×
305
  }
306

307
  tIpRangeSetMask(&range, 32);
9,545✔
308

309
  mDebug("ip-white-list may update for user: %s, fqdn: %s", user, fqdn);
9,545✔
310
  SIpWhiteListDual **ppList = taosHashGet(pIpWhiteTab, user, strlen(user));
9,545✔
311
  SIpWhiteListDual  *pList = NULL;
9,545✔
312
  if (ppList != NULL && *ppList != NULL) {
9,545!
313
    pList = *ppList;
7,879✔
314
  }
315

316
  if (type == IP_WHITE_ADD) {
9,545!
317
    if (pList == NULL) {
9,545✔
318
      SIpWhiteListDual *pNewList = taosMemoryCalloc(1, sizeof(SIpWhiteListDual) + sizeof(SIpRange));
1,666!
319
      if (pNewList == NULL) {
1,666!
320
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
321
      }
322
      (void)memcpy(pNewList->pIpRanges, &range, sizeof(SIpRange));
1,666✔
323
      pNewList->num = 1;
1,666✔
324

325
      if ((code = taosHashPut(pIpWhiteTab, user, strlen(user), &pNewList, sizeof(void *))) != 0) {
1,666!
326
        taosMemoryFree(pNewList);
×
327
        TAOS_CHECK_GOTO(code, &lino, _OVER);
×
328
      }
329
      update = true;
1,666✔
330
    } else {
331
      if (!isRangeInWhiteList(pList, &range)) {
7,879✔
332
        int32_t           sz = sizeof(SIpWhiteListDual) + sizeof(SIpRange) * (pList->num + 1);
310✔
333
        SIpWhiteListDual *pNewList = taosMemoryCalloc(1, sz);
310!
334
        if (pNewList == NULL) {
310!
335
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
336
        }
337
        (void)memcpy(pNewList->pIpRanges, pList->pIpRanges, sizeof(SIpRange) * (pList->num));
310✔
338
        memcpy(&pNewList->pIpRanges[pList->num], &range, sizeof(SIpRange));
310✔
339

340
        pNewList->num = pList->num + 1;
310✔
341

342
        if ((code = taosHashPut(pIpWhiteTab, user, strlen(user), &pNewList, sizeof(void *))) != 0) {
310!
343
          taosMemoryFree(pNewList);
×
344
          TAOS_CHECK_GOTO(code, &lino, _OVER);
×
345
        }
346
        taosMemoryFree(pList);
310!
347
        update = true;
310✔
348
      }
349
    }
350
  } else if (type == IP_WHITE_DROP) {
×
351
    if (pList != NULL) {
×
352
      if (isRangeInWhiteList(pList, &range)) {
×
353
        if (pList->num == 1) {
×
354
          if (taosHashRemove(pIpWhiteTab, user, strlen(user)) < 0) {
×
355
            mError("failed to remove ip-white-list for user: %s at line %d", user, lino);
×
356
          }
357
          taosMemoryFree(pList);
×
358
        } else {
359
          int32_t           idx = 0;
×
360
          int32_t           sz = sizeof(SIpWhiteListDual) + sizeof(SIpRange) * (pList->num - 1);
×
361
          SIpWhiteListDual *pNewList = taosMemoryCalloc(1, sz);
×
362
          if (pNewList == NULL) {
×
363
            TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
364
          }
365
          for (int i = 0; i < pList->num; i++) {
×
366
            SIpRange *e = &pList->pIpRanges[i];
×
367
            if (!isIpRangeEqual(e, &range)) {
×
368
              memcpy(&pNewList->pIpRanges[idx], e, sizeof(SIpRange));
×
369
              idx++;
×
370
            }
371
          }
372
          pNewList->num = idx;
×
373
          if ((code = taosHashPut(pIpWhiteTab, user, strlen(user), &pNewList, sizeof(void *)) != 0)) {
×
374
            taosMemoryFree(pNewList);
×
375
            TAOS_CHECK_GOTO(code, &lino, _OVER);
×
376
          }
377
          taosMemoryFree(pList);
×
378
        }
379
        update = true;
×
380
      }
381
    }
382
  }
383
  if (update) {
9,545✔
384
    mDebug("ip-white-list update for user: %s, fqdn: %s", user, fqdn);
1,976✔
385
  }
386

387
_OVER:
7,638✔
388
  if (pUpdate) *pUpdate = update;
9,545✔
389
  if (code < 0) {
9,545!
390
    mError("failed to update ip-white-list for user: %s, fqdn: %s at line %d since %s", user, fqdn, lino,
×
391
           tstrerror(code));
392
  }
393
  TAOS_RETURN(code);
9,545✔
394
}
395

396
int32_t mndRefreshUserIpWhiteList(SMnode *pMnode) {
2,547✔
397
  int32_t code = 0;
2,547✔
398
  (void)taosThreadRwlockWrlock(&ipWhiteMgt.rw);
2,547✔
399

400
  if ((code = ipWhiteMgtUpdateAll(pMnode)) != 0) {
2,547!
401
    (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
×
402
    TAOS_RETURN(code);
×
403
  }
404
  ipWhiteMgt.ver = taosGetTimestampMs();
2,547✔
405
  (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
2,547✔
406

407
  TAOS_RETURN(code);
2,547✔
408
}
409

410
int32_t mndUpdateIpWhiteForAllUser(SMnode *pMnode, char *user, char *fqdn, int8_t type, int8_t lock) {
2,149✔
411
  int32_t code = 0;
2,149✔
412
  int32_t lino = 0;
2,149✔
413
  bool    update = false;
2,149✔
414

415
  if (lock) {
2,149!
416
    (void)taosThreadRwlockWrlock(&ipWhiteMgt.rw);
2,149✔
417
    if (ipWhiteMgt.ver == 0) {
2,149!
418
      TAOS_CHECK_GOTO(ipWhiteMgtUpdateAll(pMnode), &lino, _OVER);
×
419
      ipWhiteMgt.ver = taosGetTimestampMs();
×
420
      mInfo("update ip-white-list, user: %s, ver: %" PRId64, user, ipWhiteMgt.ver);
×
421
    }
422
  }
423

424
  TAOS_CHECK_GOTO(mndUpdateIpWhiteImpl(ipWhiteMgt.pIpWhiteTab, user, fqdn, type, &update), &lino, _OVER);
2,149!
425

426
  void *pIter = taosHashIterate(ipWhiteMgt.pIpWhiteTab, NULL);
2,149✔
427
  while (pIter) {
4,324✔
428
    size_t klen = 0;
2,175✔
429
    char  *key = taosHashGetKey(pIter, &klen);
2,175✔
430

431
    char *keyDup = taosMemoryCalloc(1, klen + 1);
2,175!
432
    if (keyDup == NULL) {
2,175!
433
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
434
    }
435
    (void)memcpy(keyDup, key, klen);
2,175✔
436
    bool upd = false;
2,175✔
437
    code = mndUpdateIpWhiteImpl(ipWhiteMgt.pIpWhiteTab, keyDup, fqdn, type, &upd);
2,175✔
438
    update |= upd;
2,175✔
439
    if (code < 0) {
2,175!
440
      taosMemoryFree(keyDup);
×
441
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
442
    }
443
    taosMemoryFree(keyDup);
2,175!
444

445
    pIter = taosHashIterate(ipWhiteMgt.pIpWhiteTab, pIter);
2,175✔
446
  }
447

448
_OVER:
2,149✔
449
  if (update) ipWhiteMgt.ver++;
2,149✔
450
  if (lock) (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
2,149!
451
  if (code < 0) {
2,149!
452
    mError("failed to update ip-white-list for user: %s, fqdn: %s at line %d since %s", user, fqdn, lino,
×
453
           tstrerror(code));
454
  }
455

456
  TAOS_RETURN(code);
2,149✔
457
}
458

459
static int64_t ipWhiteMgtFillMsg(SUpdateIpWhite *pUpdate) {
1✔
460
  int64_t ver = 0;
1✔
461
  (void)taosThreadRwlockWrlock(&ipWhiteMgt.rw);
1✔
462
  ver = ipWhiteMgt.ver;
1✔
463
  int32_t num = taosHashGetSize(ipWhiteMgt.pIpWhiteTab);
1✔
464

465
  pUpdate->pUserIpWhite = taosMemoryCalloc(1, num * sizeof(SUpdateUserIpWhite));
1!
466
  if (pUpdate->pUserIpWhite == NULL) {
1!
467
    (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
×
468
    TAOS_RETURN(terrno);
×
469
  }
470

471
  void   *pIter = taosHashIterate(ipWhiteMgt.pIpWhiteTab, NULL);
1✔
472
  int32_t i = 0;
1✔
473
  while (pIter) {
2✔
474
    SUpdateUserIpWhite *pUser = &pUpdate->pUserIpWhite[i];
1✔
475
    SIpWhiteListDual   *list = *(SIpWhiteListDual **)pIter;
1✔
476

477
    size_t klen;
478
    char  *key = taosHashGetKey(pIter, &klen);
1✔
479
    if (list->num != 0) {
1!
480
      pUser->ver = ver;
1✔
481
      (void)memcpy(pUser->user, key, klen);
1✔
482
      pUser->numOfRange = list->num;
1✔
483
      pUser->pIpRanges = taosMemoryCalloc(1, list->num * sizeof(SIpRange));
1!
484
      if (pUser->pIpRanges == NULL) {
1!
485
        (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
×
486
        TAOS_RETURN(terrno);
×
487
      }
488
      (void)memcpy(pUser->pIpRanges, list->pIpRanges, list->num * sizeof(SIpRange));
1✔
489
      i++;
1✔
490
    }
491
    pIter = taosHashIterate(ipWhiteMgt.pIpWhiteTab, pIter);
1✔
492
  }
493
  pUpdate->numOfUser = i;
1✔
494
  pUpdate->ver = ver;
1✔
495

496
  (void)taosThreadRwlockUnlock(&ipWhiteMgt.rw);
1✔
497
  TAOS_RETURN(0);
1✔
498
}
499

500
void destroyIpWhiteTab(SHashObj *pIpWhiteTab) {
4,768✔
501
  if (pIpWhiteTab == NULL) return;
4,768!
502

503
  void *pIter = taosHashIterate(pIpWhiteTab, NULL);
4,768✔
504
  while (pIter) {
7,354✔
505
    SIpWhiteListDual *list = *(SIpWhiteListDual **)pIter;
2,586✔
506
    taosMemoryFree(list);
2,586!
507
    pIter = taosHashIterate(pIpWhiteTab, pIter);
2,586✔
508
  }
509

510
  taosHashCleanup(pIpWhiteTab);
4,768✔
511
}
512
int32_t mndFetchAllIpWhite(SMnode *pMnode, SHashObj **ppIpWhiteTab) {
2,547✔
513
  int32_t   code = 0;
2,547✔
514
  int32_t   lino = 0;
2,547✔
515
  SSdb     *pSdb = pMnode->pSdb;
2,547✔
516
  void     *pIter = NULL;
2,547✔
517
  SHashObj *pIpWhiteTab = NULL;
2,547✔
518
  SArray   *pUserNames = NULL;
2,547✔
519
  SArray   *fqdns = NULL;
2,547✔
520

521
  pIpWhiteTab = taosHashInit(8, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), 1, HASH_ENTRY_LOCK);
2,547✔
522
  if (pIpWhiteTab == NULL) {
2,547!
523
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
524
  }
525
  pUserNames = taosArrayInit(8, sizeof(void *));
2,547✔
526
  if (pUserNames == NULL) {
2,547!
527
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
528
  }
529

530
  while (1) {
806✔
531
    SUserObj *pUser = NULL;
3,353✔
532
    pIter = sdbFetch(pSdb, SDB_USER, pIter, (void **)&pUser);
3,353✔
533
    if (pIter == NULL) break;
3,353✔
534

535
    SIpWhiteListDual *pWhiteList = cloneIpWhiteList(pUser->pIpWhiteListDual);
806✔
536
    if (pWhiteList == NULL) {
806!
537
      sdbRelease(pSdb, pUser);
×
538
      sdbCancelFetch(pSdb, pIter);
×
539
      TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
540
    }
541
    if ((code = taosHashPut(pIpWhiteTab, pUser->user, strlen(pUser->user), &pWhiteList, sizeof(void *))) != 0) {
806!
542
      taosMemoryFree(pWhiteList);
×
543
      sdbRelease(pSdb, pUser);
×
544
      sdbCancelFetch(pSdb, pIter);
×
545
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
546
    }
547

548
    char *name = taosStrdup(pUser->user);
806!
549
    if (name == NULL) {
806!
550
      sdbRelease(pSdb, pUser);
×
551
      sdbCancelFetch(pSdb, pIter);
×
552
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
553
    }
554
    if (taosArrayPush(pUserNames, &name) == NULL) {
806!
555
      taosMemoryFree(name);
×
556
      sdbRelease(pSdb, pUser);
×
557
      sdbCancelFetch(pSdb, pIter);
×
558
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
559
    }
560

561
    sdbRelease(pSdb, pUser);
806✔
562
  }
563

564
  bool found = false;
2,547✔
565
  for (int i = 0; i < taosArrayGetSize(pUserNames); i++) {
2,572✔
566
    char *name = taosArrayGetP(pUserNames, i);
802✔
567
    if (strlen(name) == strlen(TSDB_DEFAULT_USER) && strncmp(name, TSDB_DEFAULT_USER, strlen(TSDB_DEFAULT_USER)) == 0) {
802!
568
      found = true;
777✔
569
      break;
777✔
570
    }
571
  }
572
  if (found == false) {
2,547✔
573
    char *name = taosStrdup(TSDB_DEFAULT_USER);
1,770!
574
    if (name == NULL) {
1,770!
575
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
576
    }
577
    if (taosArrayPush(pUserNames, &name) == NULL) {
1,770!
578
      taosMemoryFree(name);
×
579
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
580
    }
581
  }
582

583
  fqdns = mndGetAllDnodeFqdns(pMnode);  // TODO: refactor this line after refactor api
2,547✔
584
  if (fqdns == NULL) {
2,547!
585
    TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
586
  }
587

588
  for (int i = 0; i < taosArrayGetSize(fqdns); i++) {
4,531✔
589
    char *fqdn = taosArrayGetP(fqdns, i);
1,984✔
590

591
    for (int j = 0; j < taosArrayGetSize(pUserNames); j++) {
4,011✔
592
      char *name = taosArrayGetP(pUserNames, j);
2,027✔
593
      TAOS_CHECK_GOTO(mndUpdateIpWhiteImpl(pIpWhiteTab, name, fqdn, IP_WHITE_ADD, NULL), &lino, _OVER);
2,027!
594
    }
595
  }
596

597
_OVER:
2,547✔
598
  taosArrayDestroyP(fqdns, NULL);
2,547✔
599
  taosArrayDestroyP(pUserNames, NULL);
2,547✔
600

601
  if (code < 0) {
2,547!
602
    mError("failed to fetch all ip white list at line %d since %s", lino, tstrerror(code));
×
603
    destroyIpWhiteTab(pIpWhiteTab);
×
604
    pIpWhiteTab = NULL;
×
605
  }
606
  *ppIpWhiteTab = pIpWhiteTab;
2,547✔
607
  TAOS_RETURN(code);
2,547✔
608
}
609

610
int32_t mndInitUser(SMnode *pMnode) {
2,223✔
611
  TAOS_CHECK_RETURN(ipWhiteMgtInit());
2,223!
612

613
  SSdbTable table = {
2,223✔
614
      .sdbType = SDB_USER,
615
      .keyType = SDB_KEY_BINARY,
616
      .deployFp = (SdbDeployFp)mndCreateDefaultUsers,
617
      .encodeFp = (SdbEncodeFp)mndUserActionEncode,
618
      .decodeFp = (SdbDecodeFp)mndUserActionDecode,
619
      .insertFp = (SdbInsertFp)mndUserActionInsert,
620
      .updateFp = (SdbUpdateFp)mndUserActionUpdate,
621
      .deleteFp = (SdbDeleteFp)mndUserActionDelete,
622
  };
623

624
  mndSetMsgHandle(pMnode, TDMT_MND_CREATE_USER, mndProcessCreateUserReq);
2,223✔
625
  mndSetMsgHandle(pMnode, TDMT_MND_ALTER_USER, mndProcessAlterUserReq);
2,223✔
626
  mndSetMsgHandle(pMnode, TDMT_MND_DROP_USER, mndProcessDropUserReq);
2,223✔
627
  mndSetMsgHandle(pMnode, TDMT_MND_GET_USER_AUTH, mndProcessGetUserAuthReq);
2,223✔
628
  mndSetMsgHandle(pMnode, TDMT_MND_GET_USER_WHITELIST, mndProcessGetUserWhiteListReq);
2,223✔
629
  mndSetMsgHandle(pMnode, TDMT_MND_GET_USER_WHITELIST_DUAL, mndProcessGetUserWhiteListReq);
2,223✔
630

631
  mndSetMsgHandle(pMnode, TDMT_MND_RETRIEVE_IP_WHITE, mndProcesSRetrieveIpWhiteReq);
2,223✔
632
  mndSetMsgHandle(pMnode, TDMT_MND_RETRIEVE_IP_WHITE_DUAL, mndProcesSRetrieveIpWhiteReq);
2,223✔
633

634
  mndAddShowRetrieveHandle(pMnode, TSDB_MGMT_TABLE_USER, mndRetrieveUsers);
2,223✔
635
  mndAddShowFreeIterHandle(pMnode, TSDB_MGMT_TABLE_USER, mndCancelGetNextUser);
2,223✔
636
  mndAddShowRetrieveHandle(pMnode, TSDB_MGMT_TABLE_USER_FULL, mndRetrieveUsersFull);
2,223✔
637
  mndAddShowFreeIterHandle(pMnode, TSDB_MGMT_TABLE_USER_FULL, mndCancelGetNextUser);
2,223✔
638
  mndAddShowRetrieveHandle(pMnode, TSDB_MGMT_TABLE_PRIVILEGES, mndRetrievePrivileges);
2,223✔
639
  mndAddShowFreeIterHandle(pMnode, TSDB_MGMT_TABLE_PRIVILEGES, mndCancelGetNextPrivileges);
2,223✔
640
  return sdbSetTable(pMnode->pSdb, table);
2,223✔
641
}
642

643
void mndCleanupUser(SMnode *pMnode) { ipWhiteMgtCleanup(); }
2,221✔
644

645
static bool isDefaultRange(SIpRange *pRange) {
2✔
646
  int32_t code = 0;
2✔
647
  int32_t lino = 0;
2✔
648

649
  SIpRange range4 = {0};
2✔
650
  SIpRange range6 = {0};
2✔
651

652
  code = createDefaultIp4Range(&range4);
2✔
653
  TSDB_CHECK_CODE(code, lino, _error);
2!
654

655
  code = createDefaultIp6Range(&range6);
2✔
656
  TSDB_CHECK_CODE(code, lino, _error);
2!
657

658
  if (isIpRangeEqual(pRange, &range4) || (isIpRangeEqual(pRange, &range6))) {
2!
659
    return true;
×
660
  }
661
_error:
2✔
662
  return false;
2✔
663
};
664

665
static int32_t ipRangeListToStr(SIpRange *range, int32_t num, char *buf, int64_t bufLen) {
150✔
666
  int32_t len = 0;
150✔
667
  for (int i = 0; i < num; i++) {
454✔
668
    SIpRange *pRange = &range[i];
304✔
669
    SIpAddr   addr = {0};
304✔
670
    tIpUintToStr(pRange, &addr);
304✔
671

672
    len += tsnprintf(buf + len, bufLen - len, "%s/%d,", IP_ADDR_STR(&addr), addr.mask);
304✔
673
  }
674
  if (len > 0) buf[len - 1] = 0;
150!
675
  return len;
150✔
676
}
677

678
static bool isIpRangeEqual(SIpRange *a, SIpRange *b) {
13,078✔
679
  // equal or not
680
  if (a->type != b->type) {
13,078✔
681
    return false;
1,580✔
682
  }
683
  if (a->type == 0) {
11,498✔
684
    SIpV4Range *aP4 = &a->ipV4;
10,326✔
685
    SIpV4Range *bP4 = &b->ipV4;
10,326✔
686
    if (aP4->ip != bP4->ip || aP4->mask != bP4->mask) {
10,326!
687
      return false;
1,585✔
688
    } else {
689
      return true;
8,741✔
690
    }
691
  } else {
692
    SIpV6Range *aP6 = &a->ipV6;
1,172✔
693
    SIpV6Range *bP6 = &b->ipV6;
1,172✔
694
    if (aP6->addr[0] != bP6->addr[0] || aP6->addr[1] != bP6->addr[1] || aP6->mask != bP6->mask) {
1,172!
695
      return false;
×
696
    } else {
697
      return true;
1,172✔
698
    }
699
  }
700

701
  return true;
702
}
703
static bool isRangeInIpWhiteList(SIpWhiteListDual *pList, SIpRange *tgt) {
1✔
704
  for (int i = 0; i < pList->num; i++) {
4✔
705
    if (isIpRangeEqual(&pList->pIpRanges[i], tgt)) return true;
3!
706
  }
707
  return false;
1✔
708
}
709
static bool isIpWhiteListEqual(SIpWhiteListDual *a, SIpWhiteListDual *b) {
1,197✔
710
  if (a->num != b->num) {
1,197✔
711
    return false;
25✔
712
  }
713
  for (int i = 0; i < a->num; i++) {
3,516✔
714
    if (!isIpRangeEqual(&a->pIpRanges[i], &b->pIpRanges[i])) {
2,344!
715
      return false;
×
716
    }
717
  }
718
  return true;
1,172✔
719
}
720
int32_t convertIpWhiteListToStr(SIpWhiteListDual *pList, char **buf) {
150✔
721
  if (pList->num == 0) {
150!
722
    *buf = NULL;
×
723
    return 0;
×
724
  }
725
  int64_t bufLen = pList->num * 256;
150✔
726
  *buf = taosMemoryCalloc(1, bufLen);
150!
727
  if (*buf == NULL) {
150!
728
    return 0;
×
729
  }
730

731
  int32_t len = ipRangeListToStr(pList->pIpRanges, pList->num, *buf, bufLen);
150✔
732
  if (len == 0) {
150!
733
    taosMemoryFreeClear(*buf);
×
734
    return 0;
×
735
  }
736
  return strlen(*buf);
150✔
737
}
738
int32_t tSerializeIpWhiteList(void *buf, int32_t len, SIpWhiteListDual *pList, uint32_t *pLen) {
7,398✔
739
  int32_t  code = 0;
7,398✔
740
  int32_t  lino = 0;
7,398✔
741
  int32_t  tlen = 0;
7,398✔
742
  SEncoder encoder = {0};
7,398✔
743
  tEncoderInit(&encoder, buf, len);
7,398✔
744

745
  TAOS_CHECK_GOTO(tStartEncode(&encoder), &lino, _OVER);
7,398!
746
  TAOS_CHECK_GOTO(tEncodeI32(&encoder, pList->num), &lino, _OVER);
14,796!
747

748
  for (int i = 0; i < pList->num; i++) {
22,199✔
749
    SIpRange *pRange = &(pList->pIpRanges[i]);
14,801✔
750
    TAOS_CHECK_GOTO(tSerializeIpRange(&encoder, pRange), &lino, _OVER);
14,801!
751
  }
752

753
  tEndEncode(&encoder);
7,398✔
754

755
  tlen = encoder.pos;
7,398✔
756
_OVER:
7,398✔
757
  tEncoderClear(&encoder);
7,398✔
758
  if (code < 0) {
7,398!
759
    mError("failed to serialize ip white list at line %d since %s", lino, tstrerror(code));
×
760
  }
761
  if (pLen) *pLen = tlen;
7,398!
762
  TAOS_RETURN(code);
7,398✔
763
}
764

765
int32_t tDerializeIpWhileList(void *buf, int32_t len, SIpWhiteListDual *pList) {
3,898✔
766
  int32_t  code = 0;
3,898✔
767
  int32_t  lino = 0;
3,898✔
768
  SDecoder decoder = {0};
3,898✔
769
  tDecoderInit(&decoder, buf, len);
3,898✔
770

771
  TAOS_CHECK_GOTO(tStartDecode(&decoder), &lino, _OVER);
3,898!
772
  TAOS_CHECK_GOTO(tDecodeI32(&decoder, &pList->num), &lino, _OVER);
7,796!
773

774
  for (int i = 0; i < pList->num; i++) {
11,697✔
775
    SIpRange *pRange = &(pList->pIpRanges[i]);
7,799✔
776
    TAOS_CHECK_GOTO(tDeserializeIpRange(&decoder, pRange), &lino, _OVER);
7,799!
777
  }
778

779
_OVER:
3,898✔
780
  tEndDecode(&decoder);
3,898✔
781
  tDecoderClear(&decoder);
3,898✔
782
  if (code < 0) {
3,898!
783
    mError("failed to deserialize ip white list at line %d since %s", lino, tstrerror(code));
×
784
  }
785
  TAOS_RETURN(code);
3,898✔
786
}
787

788
int32_t tDerializeIpWhileListFromOldVer(void *buf, int32_t len, SIpWhiteList *pList) {
×
789
  int32_t  code = 0;
×
790
  int32_t  lino = 0;
×
791
  SDecoder decoder = {0};
×
792
  tDecoderInit(&decoder, buf, len);
×
793

794
  TAOS_CHECK_GOTO(tStartDecode(&decoder), &lino, _OVER);
×
795
  TAOS_CHECK_GOTO(tDecodeI32(&decoder, &pList->num), &lino, _OVER);
×
796

797
  for (int i = 0; i < pList->num; i++) {
×
798
    SIpV4Range *pIp4 = &(pList->pIpRange[i]);
×
799
    TAOS_CHECK_GOTO(tDecodeU32(&decoder, &pIp4->ip), &lino, _OVER);
×
800
    TAOS_CHECK_GOTO(tDecodeU32(&decoder, &pIp4->mask), &lino, _OVER);
×
801
  }
802

803
_OVER:
×
804
  tEndDecode(&decoder);
×
805
  tDecoderClear(&decoder);
×
806
  if (code < 0) {
×
807
    mError("failed to deserialize ip white list at line %d since %s", lino, tstrerror(code));
×
808
  }
809
  TAOS_RETURN(code);
×
810
}
811

812
static int32_t createIpWhiteList(void *buf, int32_t len, SIpWhiteListDual **ppList) {
3,898✔
813
  int32_t           code = 0;
3,898✔
814
  int32_t           lino = 0;
3,898✔
815
  int32_t           num = 0;
3,898✔
816
  SIpWhiteListDual *p = NULL;
3,898✔
817
  SDecoder          decoder = {0};
3,898✔
818
  tDecoderInit(&decoder, buf, len);
3,898✔
819

820
  TAOS_CHECK_GOTO(tStartDecode(&decoder), &lino, _OVER);
3,898!
821
  TAOS_CHECK_GOTO(tDecodeI32(&decoder, &num), &lino, _OVER);
3,898!
822

823
  p = taosMemoryCalloc(1, sizeof(SIpWhiteListDual) + num * sizeof(SIpRange));
3,898!
824
  if (p == NULL) {
3,898!
825
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
826
  }
827
  TAOS_CHECK_GOTO(tDerializeIpWhileList(buf, len, p), &lino, _OVER);
3,898!
828

829
_OVER:
3,898✔
830
  tEndDecode(&decoder);
3,898✔
831
  tDecoderClear(&decoder);
3,898✔
832
  if (code < 0) {
3,898!
833
    taosMemoryFreeClear(p);
×
834
    mError("failed to create ip white list at line %d since %s", lino, tstrerror(code));
×
835
  }
836
  *ppList = p;
3,898✔
837
  TAOS_RETURN(code);
3,898✔
838
}
839

840
static int32_t createIpWhiteListFromOldVer(void *buf, int32_t len, SIpWhiteList **ppList) {
×
841
  int32_t       code = 0;
×
842
  int32_t       lino = 0;
×
843
  int32_t       num = 0;
×
844
  SIpWhiteList *p = NULL;
×
845
  SDecoder      decoder = {0};
×
846
  tDecoderInit(&decoder, buf, len);
×
847

848
  TAOS_CHECK_GOTO(tStartDecode(&decoder), &lino, _OVER);
×
849
  TAOS_CHECK_GOTO(tDecodeI32(&decoder, &num), &lino, _OVER);
×
850

851
  p = taosMemoryCalloc(1, sizeof(SIpWhiteList) + num * sizeof(SIpV4Range));
×
852
  if (p == NULL) {
×
853
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
854
  }
855
  TAOS_CHECK_GOTO(tDerializeIpWhileListFromOldVer(buf, len, p), &lino, _OVER);
×
856

857
_OVER:
×
858
  tEndDecode(&decoder);
×
859
  tDecoderClear(&decoder);
×
860
  if (code < 0) {
×
861
    taosMemoryFreeClear(p);
×
862
    mError("failed to create ip white list at line %d since %s", lino, tstrerror(code));
×
863
  }
864
  *ppList = p;
×
865
  TAOS_RETURN(code);
×
866
}
867

868
static int32_t createDefaultIpWhiteList(SIpWhiteListDual **ppWhiteList) {
1,852✔
869
  int32_t code = 0;
1,852✔
870
  int32_t lino = 0;
1,852✔
871
  *ppWhiteList = taosMemoryCalloc(1, sizeof(SIpWhiteListDual) + sizeof(SIpRange) * 2);
1,852!
872
  if (*ppWhiteList == NULL) {
1,852!
873
    TAOS_RETURN(terrno);
×
874
  }
875
  (*ppWhiteList)->num = 2;
1,852✔
876

877
  SIpRange v4 = {0};
1,852✔
878
  SIpRange v6 = {0};
1,852✔
879

880
#ifndef TD_ASTRA
881
  code = createDefaultIp4Range(&v4);
1,852✔
882
  TSDB_CHECK_CODE(code, lino, _error);
1,852!
883

884
  code = createDefaultIp6Range(&v6);
1,852✔
885
  TSDB_CHECK_CODE(code, lino, _error);
1,852!
886

887
#endif
888

889
_error:
1,852✔
890
  if (code != 0) {
1,852!
891
    taosMemoryFree(*ppWhiteList);
×
892
    *ppWhiteList = NULL;
×
893
    mError("failed to create default ip white list at line %d since %s", __LINE__, tstrerror(code));
×
894
  } else {
895
    memcpy(&(*ppWhiteList)->pIpRanges[0], &v4, sizeof(SIpRange));
1,852✔
896
    memcpy(&(*ppWhiteList)->pIpRanges[1], &v6, sizeof(SIpRange));
1,852✔
897
  }
898
  return 0;
1,852✔
899
}
900

901
static int32_t mndCreateDefaultUser(SMnode *pMnode, char *acct, char *user, char *pass) {
1,666✔
902
  int32_t  code = 0;
1,666✔
903
  int32_t  lino = 0;
1,666✔
904
  SUserObj userObj = {0};
1,666✔
905
  taosEncryptPass_c((uint8_t *)pass, strlen(pass), userObj.pass);
1,666✔
906
  tstrncpy(userObj.user, user, TSDB_USER_LEN);
1,666✔
907
  tstrncpy(userObj.acct, acct, TSDB_USER_LEN);
1,666✔
908
  userObj.createdTime = taosGetTimestampMs();
1,666✔
909
  userObj.updateTime = userObj.createdTime;
1,666✔
910
  userObj.sysInfo = 1;
1,666✔
911
  userObj.enable = 1;
1,666✔
912
  userObj.ipWhiteListVer = taosGetTimestampMs();
1,666✔
913
  TAOS_CHECK_RETURN(createDefaultIpWhiteList(&userObj.pIpWhiteListDual));
1,666!
914
  if (strcmp(user, TSDB_DEFAULT_USER) == 0) {
1,666!
915
    userObj.superUser = 1;
1,666✔
916
    userObj.createdb = 1;
1,666✔
917
  }
918

919
  SSdbRaw *pRaw = mndUserActionEncode(&userObj);
1,666✔
920
  if (pRaw == NULL) goto _ERROR;
1,666!
921
  TAOS_CHECK_GOTO(sdbSetRawStatus(pRaw, SDB_STATUS_READY), &lino, _ERROR);
1,666!
922

923
  mInfo("user:%s, will be created when deploying, raw:%p", userObj.user, pRaw);
1,666!
924

925
  STrans *pTrans = mndTransCreate(pMnode, TRN_POLICY_RETRY, TRN_CONFLICT_NOTHING, NULL, "create-user");
1,666✔
926
  if (pTrans == NULL) {
1,666!
927
    sdbFreeRaw(pRaw);
×
928
    mError("user:%s, failed to create since %s", userObj.user, terrstr());
×
929
    goto _ERROR;
×
930
  }
931
  mInfo("trans:%d, used to create user:%s", pTrans->id, userObj.user);
1,666!
932

933
  if (mndTransAppendCommitlog(pTrans, pRaw) != 0) {
1,666!
934
    mError("trans:%d, failed to commit redo log since %s", pTrans->id, terrstr());
×
935
    mndTransDrop(pTrans);
×
936
    goto _ERROR;
×
937
  }
938
  TAOS_CHECK_GOTO(sdbSetRawStatus(pRaw, SDB_STATUS_READY), &lino, _ERROR);
1,666!
939

940
  if (mndTransPrepare(pMnode, pTrans) != 0) {
1,666!
941
    mError("trans:%d, failed to prepare since %s", pTrans->id, terrstr());
×
942
    mndTransDrop(pTrans);
×
943
    goto _ERROR;
×
944
  }
945

946
  mndTransDrop(pTrans);
1,666✔
947
  taosMemoryFree(userObj.pIpWhiteListDual);
1,666!
948
  return 0;
1,666✔
949
_ERROR:
×
950
  taosMemoryFree(userObj.pIpWhiteListDual);
×
951
  TAOS_RETURN(terrno ? terrno : TSDB_CODE_APP_ERROR);
×
952
}
953

954
static int32_t mndCreateDefaultUsers(SMnode *pMnode) {
1,666✔
955
  return mndCreateDefaultUser(pMnode, TSDB_DEFAULT_USER, TSDB_DEFAULT_USER, TSDB_DEFAULT_PASS);
1,666✔
956
}
957

958
SSdbRaw *mndUserActionEncode(SUserObj *pUser) {
7,398✔
959
  int32_t code = 0;
7,398✔
960
  int32_t lino = 0;
7,398✔
961
  int32_t ipWhiteReserve =
×
962
      pUser->pIpWhiteListDual ? (sizeof(SIpRange) * pUser->pIpWhiteListDual->num + sizeof(SIpWhiteListDual) + 4) : 16;
7,398!
963
  int32_t numOfReadDbs = taosHashGetSize(pUser->readDbs);
7,398✔
964
  int32_t numOfWriteDbs = taosHashGetSize(pUser->writeDbs);
7,398✔
965
  int32_t numOfReadTbs = taosHashGetSize(pUser->readTbs);
7,398✔
966
  int32_t numOfWriteTbs = taosHashGetSize(pUser->writeTbs);
7,398✔
967
  int32_t numOfAlterTbs = taosHashGetSize(pUser->alterTbs);
7,398✔
968
  int32_t numOfReadViews = taosHashGetSize(pUser->readViews);
7,398✔
969
  int32_t numOfWriteViews = taosHashGetSize(pUser->writeViews);
7,398✔
970
  int32_t numOfAlterViews = taosHashGetSize(pUser->alterViews);
7,398✔
971
  int32_t numOfTopics = taosHashGetSize(pUser->topics);
7,398✔
972
  int32_t numOfUseDbs = taosHashGetSize(pUser->useDbs);
7,398✔
973
  int32_t size = sizeof(SUserObj) + USER_RESERVE_SIZE + (numOfReadDbs + numOfWriteDbs) * TSDB_DB_FNAME_LEN +
7,398✔
974
                 numOfTopics * TSDB_TOPIC_FNAME_LEN + ipWhiteReserve;
7,398✔
975
  char    *buf = NULL;
7,398✔
976
  SSdbRaw *pRaw = NULL;
7,398✔
977

978
  char *stb = taosHashIterate(pUser->readTbs, NULL);
7,398✔
979
  while (stb != NULL) {
170,839✔
980
    size_t keyLen = 0;
163,441✔
981
    void  *key = taosHashGetKey(stb, &keyLen);
163,441✔
982
    size += sizeof(int32_t);
163,441✔
983
    size += keyLen;
163,441✔
984

985
    size_t valueLen = 0;
163,441✔
986
    valueLen = strlen(stb) + 1;
163,441✔
987
    size += sizeof(int32_t);
163,441✔
988
    size += valueLen;
163,441✔
989
    stb = taosHashIterate(pUser->readTbs, stb);
163,441✔
990
  }
991

992
  stb = taosHashIterate(pUser->writeTbs, NULL);
7,398✔
993
  while (stb != NULL) {
170,438✔
994
    size_t keyLen = 0;
163,040✔
995
    void  *key = taosHashGetKey(stb, &keyLen);
163,040✔
996
    size += sizeof(int32_t);
163,040✔
997
    size += keyLen;
163,040✔
998

999
    size_t valueLen = 0;
163,040✔
1000
    valueLen = strlen(stb) + 1;
163,040✔
1001
    size += sizeof(int32_t);
163,040✔
1002
    size += valueLen;
163,040✔
1003
    stb = taosHashIterate(pUser->writeTbs, stb);
163,040✔
1004
  }
1005

1006
  stb = taosHashIterate(pUser->alterTbs, NULL);
7,398✔
1007
  while (stb != NULL) {
7,418✔
1008
    size_t keyLen = 0;
20✔
1009
    void  *key = taosHashGetKey(stb, &keyLen);
20✔
1010
    size += sizeof(int32_t);
20✔
1011
    size += keyLen;
20✔
1012

1013
    size_t valueLen = 0;
20✔
1014
    valueLen = strlen(stb) + 1;
20✔
1015
    size += sizeof(int32_t);
20✔
1016
    size += valueLen;
20✔
1017
    stb = taosHashIterate(pUser->alterTbs, stb);
20✔
1018
  }
1019

1020
  stb = taosHashIterate(pUser->readViews, NULL);
7,398✔
1021
  while (stb != NULL) {
7,516✔
1022
    size_t keyLen = 0;
118✔
1023
    void  *key = taosHashGetKey(stb, &keyLen);
118✔
1024
    size += sizeof(int32_t);
118✔
1025
    size += keyLen;
118✔
1026

1027
    size_t valueLen = 0;
118✔
1028
    valueLen = strlen(stb) + 1;
118✔
1029
    size += sizeof(int32_t);
118✔
1030
    size += valueLen;
118✔
1031
    stb = taosHashIterate(pUser->readViews, stb);
118✔
1032
  }
1033

1034
  stb = taosHashIterate(pUser->writeViews, NULL);
7,398✔
1035
  while (stb != NULL) {
7,495✔
1036
    size_t keyLen = 0;
97✔
1037
    void  *key = taosHashGetKey(stb, &keyLen);
97✔
1038
    size += sizeof(int32_t);
97✔
1039
    size += keyLen;
97✔
1040

1041
    size_t valueLen = 0;
97✔
1042
    valueLen = strlen(stb) + 1;
97✔
1043
    size += sizeof(int32_t);
97✔
1044
    size += valueLen;
97✔
1045
    stb = taosHashIterate(pUser->writeViews, stb);
97✔
1046
  }
1047

1048
  stb = taosHashIterate(pUser->alterViews, NULL);
7,398✔
1049
  while (stb != NULL) {
7,502✔
1050
    size_t keyLen = 0;
104✔
1051
    void  *key = taosHashGetKey(stb, &keyLen);
104✔
1052
    size += sizeof(int32_t);
104✔
1053
    size += keyLen;
104✔
1054

1055
    size_t valueLen = 0;
104✔
1056
    valueLen = strlen(stb) + 1;
104✔
1057
    size += sizeof(int32_t);
104✔
1058
    size += valueLen;
104✔
1059
    stb = taosHashIterate(pUser->alterViews, stb);
104✔
1060
  }
1061

1062
  int32_t *useDb = taosHashIterate(pUser->useDbs, NULL);
7,398✔
1063
  while (useDb != NULL) {
9,284✔
1064
    size_t keyLen = 0;
1,886✔
1065
    void  *key = taosHashGetKey(useDb, &keyLen);
1,886✔
1066
    size += sizeof(int32_t);
1,886✔
1067
    size += keyLen;
1,886✔
1068
    size += sizeof(int32_t);
1,886✔
1069
    useDb = taosHashIterate(pUser->useDbs, useDb);
1,886✔
1070
  }
1071

1072
  pRaw = sdbAllocRaw(SDB_USER, USER_VER_NUMBER, size);
7,398✔
1073
  if (pRaw == NULL) {
7,398!
1074
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1075
  }
1076

1077
  int32_t dataPos = 0;
7,398✔
1078
  SDB_SET_BINARY(pRaw, dataPos, pUser->user, TSDB_USER_LEN, _OVER)
7,398!
1079
  SDB_SET_BINARY(pRaw, dataPos, pUser->pass, TSDB_PASSWORD_LEN, _OVER)
7,398!
1080
  SDB_SET_BINARY(pRaw, dataPos, pUser->acct, TSDB_USER_LEN, _OVER)
7,398!
1081
  SDB_SET_INT64(pRaw, dataPos, pUser->createdTime, _OVER)
7,398!
1082
  SDB_SET_INT64(pRaw, dataPos, pUser->updateTime, _OVER)
7,398!
1083
  SDB_SET_INT8(pRaw, dataPos, pUser->superUser, _OVER)
7,398!
1084
  SDB_SET_INT8(pRaw, dataPos, pUser->sysInfo, _OVER)
7,398!
1085
  SDB_SET_INT8(pRaw, dataPos, pUser->enable, _OVER)
7,398!
1086
  SDB_SET_UINT8(pRaw, dataPos, pUser->flag, _OVER)
7,398!
1087
  SDB_SET_INT32(pRaw, dataPos, pUser->authVersion, _OVER)
7,398!
1088
  SDB_SET_INT32(pRaw, dataPos, pUser->passVersion, _OVER)
7,398!
1089
  SDB_SET_INT32(pRaw, dataPos, numOfReadDbs, _OVER)
7,398!
1090
  SDB_SET_INT32(pRaw, dataPos, numOfWriteDbs, _OVER)
7,398!
1091
  SDB_SET_INT32(pRaw, dataPos, numOfTopics, _OVER)
7,398!
1092

1093
  char *db = taosHashIterate(pUser->readDbs, NULL);
7,398✔
1094
  while (db != NULL) {
7,588✔
1095
    SDB_SET_BINARY(pRaw, dataPos, db, TSDB_DB_FNAME_LEN, _OVER);
190!
1096
    db = taosHashIterate(pUser->readDbs, db);
190✔
1097
  }
1098

1099
  db = taosHashIterate(pUser->writeDbs, NULL);
7,398✔
1100
  while (db != NULL) {
7,579✔
1101
    SDB_SET_BINARY(pRaw, dataPos, db, TSDB_DB_FNAME_LEN, _OVER);
181!
1102
    db = taosHashIterate(pUser->writeDbs, db);
181✔
1103
  }
1104

1105
  char *topic = taosHashIterate(pUser->topics, NULL);
7,398✔
1106
  while (topic != NULL) {
7,438✔
1107
    SDB_SET_BINARY(pRaw, dataPos, topic, TSDB_TOPIC_FNAME_LEN, _OVER);
40!
1108
    topic = taosHashIterate(pUser->topics, topic);
40✔
1109
  }
1110

1111
  SDB_SET_INT32(pRaw, dataPos, numOfReadTbs, _OVER)
7,398!
1112
  SDB_SET_INT32(pRaw, dataPos, numOfWriteTbs, _OVER)
7,398!
1113
  SDB_SET_INT32(pRaw, dataPos, numOfAlterTbs, _OVER)
7,398!
1114
  SDB_SET_INT32(pRaw, dataPos, numOfReadViews, _OVER)
7,398!
1115
  SDB_SET_INT32(pRaw, dataPos, numOfWriteViews, _OVER)
7,398!
1116
  SDB_SET_INT32(pRaw, dataPos, numOfAlterViews, _OVER)
7,398!
1117
  SDB_SET_INT32(pRaw, dataPos, numOfUseDbs, _OVER)
7,398!
1118

1119
  stb = taosHashIterate(pUser->readTbs, NULL);
7,398✔
1120
  while (stb != NULL) {
170,839✔
1121
    size_t keyLen = 0;
163,441✔
1122
    void  *key = taosHashGetKey(stb, &keyLen);
163,441✔
1123
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
163,441!
1124
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
163,441!
1125

1126
    size_t valueLen = 0;
163,441✔
1127
    valueLen = strlen(stb) + 1;
163,441✔
1128
    SDB_SET_INT32(pRaw, dataPos, valueLen, _OVER)
163,441!
1129
    SDB_SET_BINARY(pRaw, dataPos, stb, valueLen, _OVER);
163,441!
1130
    stb = taosHashIterate(pUser->readTbs, stb);
163,441✔
1131
  }
1132

1133
  stb = taosHashIterate(pUser->writeTbs, NULL);
7,398✔
1134
  while (stb != NULL) {
170,438✔
1135
    size_t keyLen = 0;
163,040✔
1136
    void  *key = taosHashGetKey(stb, &keyLen);
163,040✔
1137
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
163,040!
1138
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
163,040!
1139

1140
    size_t valueLen = 0;
163,040✔
1141
    valueLen = strlen(stb) + 1;
163,040✔
1142
    SDB_SET_INT32(pRaw, dataPos, valueLen, _OVER)
163,040!
1143
    SDB_SET_BINARY(pRaw, dataPos, stb, valueLen, _OVER);
163,040!
1144
    stb = taosHashIterate(pUser->writeTbs, stb);
163,040✔
1145
  }
1146

1147
  stb = taosHashIterate(pUser->alterTbs, NULL);
7,398✔
1148
  while (stb != NULL) {
7,418✔
1149
    size_t keyLen = 0;
20✔
1150
    void  *key = taosHashGetKey(stb, &keyLen);
20✔
1151
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
20!
1152
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
20!
1153

1154
    size_t valueLen = 0;
20✔
1155
    valueLen = strlen(stb) + 1;
20✔
1156
    SDB_SET_INT32(pRaw, dataPos, valueLen, _OVER)
20!
1157
    SDB_SET_BINARY(pRaw, dataPos, stb, valueLen, _OVER);
20!
1158
    stb = taosHashIterate(pUser->alterTbs, stb);
20✔
1159
  }
1160

1161
  stb = taosHashIterate(pUser->readViews, NULL);
7,398✔
1162
  while (stb != NULL) {
7,516✔
1163
    size_t keyLen = 0;
118✔
1164
    void  *key = taosHashGetKey(stb, &keyLen);
118✔
1165
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
118!
1166
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
118!
1167

1168
    size_t valueLen = 0;
118✔
1169
    valueLen = strlen(stb) + 1;
118✔
1170
    SDB_SET_INT32(pRaw, dataPos, valueLen, _OVER)
118!
1171
    SDB_SET_BINARY(pRaw, dataPos, stb, valueLen, _OVER);
118!
1172
    stb = taosHashIterate(pUser->readViews, stb);
118✔
1173
  }
1174

1175
  stb = taosHashIterate(pUser->writeViews, NULL);
7,398✔
1176
  while (stb != NULL) {
7,495✔
1177
    size_t keyLen = 0;
97✔
1178
    void  *key = taosHashGetKey(stb, &keyLen);
97✔
1179
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
97!
1180
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
97!
1181

1182
    size_t valueLen = 0;
97✔
1183
    valueLen = strlen(stb) + 1;
97✔
1184
    SDB_SET_INT32(pRaw, dataPos, valueLen, _OVER)
97!
1185
    SDB_SET_BINARY(pRaw, dataPos, stb, valueLen, _OVER);
97!
1186
    stb = taosHashIterate(pUser->writeViews, stb);
97✔
1187
  }
1188

1189
  stb = taosHashIterate(pUser->alterViews, NULL);
7,398✔
1190
  while (stb != NULL) {
7,502✔
1191
    size_t keyLen = 0;
104✔
1192
    void  *key = taosHashGetKey(stb, &keyLen);
104✔
1193
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
104!
1194
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
104!
1195

1196
    size_t valueLen = 0;
104✔
1197
    valueLen = strlen(stb) + 1;
104✔
1198
    SDB_SET_INT32(pRaw, dataPos, valueLen, _OVER)
104!
1199
    SDB_SET_BINARY(pRaw, dataPos, stb, valueLen, _OVER);
104!
1200
    stb = taosHashIterate(pUser->alterViews, stb);
104✔
1201
  }
1202

1203
  useDb = taosHashIterate(pUser->useDbs, NULL);
7,398✔
1204
  while (useDb != NULL) {
9,284✔
1205
    size_t keyLen = 0;
1,886✔
1206
    void  *key = taosHashGetKey(useDb, &keyLen);
1,886✔
1207
    SDB_SET_INT32(pRaw, dataPos, keyLen, _OVER)
1,886!
1208
    SDB_SET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
1,886!
1209

1210
    SDB_SET_INT32(pRaw, dataPos, *useDb, _OVER)
1,886!
1211
    useDb = taosHashIterate(pUser->useDbs, useDb);
1,886✔
1212
  }
1213

1214
  // save white list
1215
  int32_t num = pUser->pIpWhiteListDual->num;
7,398✔
1216
  int32_t tlen = sizeof(SIpWhiteListDual) + num * sizeof(SIpRange) + 4;
7,398✔
1217
  if ((buf = taosMemoryCalloc(1, tlen)) == NULL) {
7,398!
1218
    TAOS_CHECK_GOTO(terrno, NULL, _OVER);
×
1219
  }
1220
  int32_t len = 0;
7,398✔
1221
  TAOS_CHECK_GOTO(tSerializeIpWhiteList(buf, tlen, pUser->pIpWhiteListDual, &len), &lino, _OVER);
7,398!
1222

1223
  SDB_SET_INT32(pRaw, dataPos, len, _OVER);
7,398!
1224
  SDB_SET_BINARY(pRaw, dataPos, buf, len, _OVER);
7,398!
1225

1226
  SDB_SET_INT64(pRaw, dataPos, pUser->ipWhiteListVer, _OVER);
7,398!
1227

1228
  SDB_SET_RESERVE(pRaw, dataPos, USER_RESERVE_SIZE, _OVER)
7,398!
1229
  SDB_SET_DATALEN(pRaw, dataPos, _OVER)
7,398!
1230

1231
_OVER:
7,398✔
1232
  taosMemoryFree(buf);
7,398!
1233
  if (code < 0) {
7,398!
1234
    mError("user:%s, failed to encode user action to raw:%p at line %d since %s", pUser->user, pRaw, lino,
×
1235
           tstrerror(code));
1236
    sdbFreeRaw(pRaw);
×
1237
    pRaw = NULL;
×
1238
    terrno = code;
×
1239
  }
1240

1241
  mTrace("user:%s, encode user action to raw:%p, row:%p", pUser->user, pRaw, pUser);
7,398✔
1242
  return pRaw;
7,398✔
1243
}
1244

1245
static SSdbRow *mndUserActionDecode(SSdbRaw *pRaw) {
3,898✔
1246
  int32_t   code = 0;
3,898✔
1247
  int32_t   lino = 0;
3,898✔
1248
  SSdbRow  *pRow = NULL;
3,898✔
1249
  SUserObj *pUser = NULL;
3,898✔
1250
  char     *key = NULL;
3,898✔
1251
  char     *value = NULL;
3,898✔
1252

1253
  int8_t sver = 0;
3,898✔
1254
  if (sdbGetRawSoftVer(pRaw, &sver) != 0) {
3,898!
1255
    TAOS_CHECK_GOTO(TSDB_CODE_INVALID_PTR, &lino, _OVER);
×
1256
  }
1257

1258
  if (sver < 1 || sver > USER_VER_NUMBER) {
3,898!
1259
    TAOS_CHECK_GOTO(TSDB_CODE_SDB_INVALID_DATA_VER, &lino, _OVER);
×
1260
  }
1261

1262
  pRow = sdbAllocRow(sizeof(SUserObj));
3,898✔
1263
  if (pRow == NULL) {
3,898!
1264
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1265
  }
1266

1267
  pUser = sdbGetRowObj(pRow);
3,898✔
1268
  if (pUser == NULL) {
3,898!
1269
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1270
  }
1271

1272
  int32_t dataPos = 0;
3,898✔
1273
  SDB_GET_BINARY(pRaw, dataPos, pUser->user, TSDB_USER_LEN, _OVER)
3,898!
1274
  SDB_GET_BINARY(pRaw, dataPos, pUser->pass, TSDB_PASSWORD_LEN, _OVER)
3,898!
1275
  SDB_GET_BINARY(pRaw, dataPos, pUser->acct, TSDB_USER_LEN, _OVER)
3,898!
1276
  SDB_GET_INT64(pRaw, dataPos, &pUser->createdTime, _OVER)
3,898!
1277
  SDB_GET_INT64(pRaw, dataPos, &pUser->updateTime, _OVER)
3,898!
1278
  SDB_GET_INT8(pRaw, dataPos, &pUser->superUser, _OVER)
3,898!
1279
  SDB_GET_INT8(pRaw, dataPos, &pUser->sysInfo, _OVER)
3,898!
1280
  SDB_GET_INT8(pRaw, dataPos, &pUser->enable, _OVER)
3,898!
1281
  SDB_GET_UINT8(pRaw, dataPos, &pUser->flag, _OVER)
3,898!
1282
  if (pUser->superUser) pUser->createdb = 1;
3,898✔
1283
  SDB_GET_INT32(pRaw, dataPos, &pUser->authVersion, _OVER)
3,898!
1284
  if (sver >= 4) {
3,898!
1285
    SDB_GET_INT32(pRaw, dataPos, &pUser->passVersion, _OVER)
3,898!
1286
  }
1287

1288
  int32_t numOfReadDbs = 0;
3,898✔
1289
  int32_t numOfWriteDbs = 0;
3,898✔
1290
  int32_t numOfTopics = 0;
3,898✔
1291
  SDB_GET_INT32(pRaw, dataPos, &numOfReadDbs, _OVER)
3,898!
1292
  SDB_GET_INT32(pRaw, dataPos, &numOfWriteDbs, _OVER)
3,898!
1293
  if (sver >= 2) {
3,898!
1294
    SDB_GET_INT32(pRaw, dataPos, &numOfTopics, _OVER)
3,898!
1295
  }
1296

1297
  pUser->readDbs = taosHashInit(numOfReadDbs, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1298
  pUser->writeDbs =
3,898✔
1299
      taosHashInit(numOfWriteDbs, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1300
  pUser->topics = taosHashInit(numOfTopics, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1301
  if (pUser->readDbs == NULL || pUser->writeDbs == NULL || pUser->topics == NULL) {
3,898!
1302
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1303
    goto _OVER;
×
1304
  }
1305

1306
  for (int32_t i = 0; i < numOfReadDbs; ++i) {
4,066✔
1307
    char db[TSDB_DB_FNAME_LEN] = {0};
168✔
1308
    SDB_GET_BINARY(pRaw, dataPos, db, TSDB_DB_FNAME_LEN, _OVER)
168!
1309
    int32_t len = strlen(db) + 1;
168✔
1310
    TAOS_CHECK_GOTO(taosHashPut(pUser->readDbs, db, len, db, TSDB_DB_FNAME_LEN), &lino, _OVER);
168!
1311
  }
1312

1313
  for (int32_t i = 0; i < numOfWriteDbs; ++i) {
4,055✔
1314
    char db[TSDB_DB_FNAME_LEN] = {0};
157✔
1315
    SDB_GET_BINARY(pRaw, dataPos, db, TSDB_DB_FNAME_LEN, _OVER)
157!
1316
    int32_t len = strlen(db) + 1;
157✔
1317
    TAOS_CHECK_GOTO(taosHashPut(pUser->writeDbs, db, len, db, TSDB_DB_FNAME_LEN), &lino, _OVER);
157!
1318
  }
1319

1320
  if (sver >= 2) {
3,898!
1321
    for (int32_t i = 0; i < numOfTopics; ++i) {
3,934✔
1322
      char topic[TSDB_TOPIC_FNAME_LEN] = {0};
36✔
1323
      SDB_GET_BINARY(pRaw, dataPos, topic, TSDB_TOPIC_FNAME_LEN, _OVER)
36!
1324
      int32_t len = strlen(topic) + 1;
36✔
1325
      TAOS_CHECK_GOTO(taosHashPut(pUser->topics, topic, len, topic, TSDB_TOPIC_FNAME_LEN), &lino, _OVER);
36!
1326
    }
1327
  }
1328

1329
  if (sver >= 3) {
3,898!
1330
    int32_t numOfReadTbs = 0;
3,898✔
1331
    int32_t numOfWriteTbs = 0;
3,898✔
1332
    int32_t numOfAlterTbs = 0;
3,898✔
1333
    int32_t numOfReadViews = 0;
3,898✔
1334
    int32_t numOfWriteViews = 0;
3,898✔
1335
    int32_t numOfAlterViews = 0;
3,898✔
1336
    int32_t numOfUseDbs = 0;
3,898✔
1337
    SDB_GET_INT32(pRaw, dataPos, &numOfReadTbs, _OVER)
3,898!
1338
    SDB_GET_INT32(pRaw, dataPos, &numOfWriteTbs, _OVER)
3,898!
1339
    if (sver >= 6) {
3,898!
1340
      SDB_GET_INT32(pRaw, dataPos, &numOfAlterTbs, _OVER)
3,898!
1341
      SDB_GET_INT32(pRaw, dataPos, &numOfReadViews, _OVER)
3,898!
1342
      SDB_GET_INT32(pRaw, dataPos, &numOfWriteViews, _OVER)
3,898!
1343
      SDB_GET_INT32(pRaw, dataPos, &numOfAlterViews, _OVER)
3,898!
1344
    }
1345
    SDB_GET_INT32(pRaw, dataPos, &numOfUseDbs, _OVER)
3,898!
1346

1347
    pUser->readTbs =
3,898✔
1348
        taosHashInit(numOfReadTbs, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1349
    pUser->writeTbs =
3,898✔
1350
        taosHashInit(numOfWriteTbs, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1351
    pUser->alterTbs =
3,898✔
1352
        taosHashInit(numOfAlterTbs, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1353

1354
    pUser->readViews =
3,898✔
1355
        taosHashInit(numOfReadViews, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1356
    pUser->writeViews =
3,898✔
1357
        taosHashInit(numOfWriteViews, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1358
    pUser->alterViews =
3,898✔
1359
        taosHashInit(numOfAlterViews, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1360

1361
    pUser->useDbs = taosHashInit(numOfUseDbs, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
3,898✔
1362

1363
    if (pUser->readTbs == NULL || pUser->writeTbs == NULL || pUser->alterTbs == NULL || pUser->readViews == NULL ||
3,898!
1364
        pUser->writeViews == NULL || pUser->alterViews == NULL || pUser->useDbs == NULL) {
3,898!
1365
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1366
      goto _OVER;
×
1367
    }
1368

1369
    for (int32_t i = 0; i < numOfReadTbs; ++i) {
165,147✔
1370
      int32_t keyLen = 0;
161,249✔
1371
      SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
161,249!
1372

1373
      TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
161,249!
1374
      if (key == NULL) {
161,249!
1375
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1376
      }
1377
      (void)memset(key, 0, keyLen);
161,249✔
1378
      SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
161,249!
1379

1380
      int32_t valuelen = 0;
161,249✔
1381
      SDB_GET_INT32(pRaw, dataPos, &valuelen, _OVER);
161,249!
1382
      TAOS_MEMORY_REALLOC(value, valuelen * sizeof(char));
161,249!
1383
      if (value == NULL) {
161,249!
1384
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1385
      }
1386
      (void)memset(value, 0, valuelen);
161,249✔
1387
      SDB_GET_BINARY(pRaw, dataPos, value, valuelen, _OVER)
161,249!
1388

1389
      TAOS_CHECK_GOTO(taosHashPut(pUser->readTbs, key, keyLen, value, valuelen), &lino, _OVER);
161,249!
1390
    }
1391

1392
    for (int32_t i = 0; i < numOfWriteTbs; ++i) {
164,748✔
1393
      int32_t keyLen = 0;
160,850✔
1394
      SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
160,850!
1395

1396
      TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
160,850!
1397
      if (key == NULL) {
160,850!
1398
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1399
      }
1400
      (void)memset(key, 0, keyLen);
160,850✔
1401
      SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
160,850!
1402

1403
      int32_t valuelen = 0;
160,850✔
1404
      SDB_GET_INT32(pRaw, dataPos, &valuelen, _OVER);
160,850!
1405
      TAOS_MEMORY_REALLOC(value, valuelen * sizeof(char));
160,850!
1406
      if (value == NULL) {
160,850!
1407
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1408
      }
1409
      (void)memset(value, 0, valuelen);
160,850✔
1410
      SDB_GET_BINARY(pRaw, dataPos, value, valuelen, _OVER)
160,850!
1411

1412
      TAOS_CHECK_GOTO(taosHashPut(pUser->writeTbs, key, keyLen, value, valuelen), &lino, _OVER);
160,850!
1413
    }
1414

1415
    if (sver >= 6) {
3,898!
1416
      for (int32_t i = 0; i < numOfAlterTbs; ++i) {
3,917✔
1417
        int32_t keyLen = 0;
19✔
1418
        SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
19!
1419

1420
        TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
19!
1421
        if (key == NULL) {
19!
1422
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1423
        }
1424
        (void)memset(key, 0, keyLen);
19✔
1425
        SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
19!
1426

1427
        int32_t valuelen = 0;
19✔
1428
        SDB_GET_INT32(pRaw, dataPos, &valuelen, _OVER);
19!
1429
        TAOS_MEMORY_REALLOC(value, valuelen * sizeof(char));
19!
1430
        if (value == NULL) {
19!
1431
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1432
        }
1433
        (void)memset(value, 0, valuelen);
19✔
1434
        SDB_GET_BINARY(pRaw, dataPos, value, valuelen, _OVER)
19!
1435

1436
        TAOS_CHECK_GOTO(taosHashPut(pUser->alterTbs, key, keyLen, value, valuelen), &lino, _OVER);
19!
1437
      }
1438

1439
      for (int32_t i = 0; i < numOfReadViews; ++i) {
4,013✔
1440
        int32_t keyLen = 0;
115✔
1441
        SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
115!
1442

1443
        TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
115!
1444
        if (key == NULL) {
115!
1445
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1446
        }
1447
        (void)memset(key, 0, keyLen);
115✔
1448
        SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
115!
1449

1450
        int32_t valuelen = 0;
115✔
1451
        SDB_GET_INT32(pRaw, dataPos, &valuelen, _OVER);
115!
1452
        TAOS_MEMORY_REALLOC(value, valuelen * sizeof(char));
115!
1453
        if (value == NULL) {
115!
1454
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1455
        }
1456
        (void)memset(value, 0, valuelen);
115✔
1457
        SDB_GET_BINARY(pRaw, dataPos, value, valuelen, _OVER)
115!
1458

1459
        TAOS_CHECK_GOTO(taosHashPut(pUser->readViews, key, keyLen, value, valuelen), &lino, _OVER);
115!
1460
      }
1461

1462
      for (int32_t i = 0; i < numOfWriteViews; ++i) {
3,992✔
1463
        int32_t keyLen = 0;
94✔
1464
        SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
94!
1465

1466
        TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
94!
1467
        if (key == NULL) {
94!
1468
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1469
        }
1470
        (void)memset(key, 0, keyLen);
94✔
1471
        SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
94!
1472

1473
        int32_t valuelen = 0;
94✔
1474
        SDB_GET_INT32(pRaw, dataPos, &valuelen, _OVER);
94!
1475
        TAOS_MEMORY_REALLOC(value, valuelen * sizeof(char));
94!
1476
        if (value == NULL) {
94!
1477
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1478
        }
1479
        (void)memset(value, 0, valuelen);
94✔
1480
        SDB_GET_BINARY(pRaw, dataPos, value, valuelen, _OVER)
94!
1481

1482
        TAOS_CHECK_GOTO(taosHashPut(pUser->writeViews, key, keyLen, value, valuelen), &lino, _OVER);
94!
1483
      }
1484

1485
      for (int32_t i = 0; i < numOfAlterViews; ++i) {
3,998✔
1486
        int32_t keyLen = 0;
100✔
1487
        SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
100!
1488

1489
        TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
100!
1490
        if (key == NULL) {
100!
1491
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1492
        }
1493
        (void)memset(key, 0, keyLen);
100✔
1494
        SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
100!
1495

1496
        int32_t valuelen = 0;
100✔
1497
        SDB_GET_INT32(pRaw, dataPos, &valuelen, _OVER);
100!
1498
        TAOS_MEMORY_REALLOC(value, valuelen * sizeof(char));
100!
1499
        if (value == NULL) {
100!
1500
          TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1501
        }
1502
        (void)memset(value, 0, valuelen);
100✔
1503
        SDB_GET_BINARY(pRaw, dataPos, value, valuelen, _OVER)
100!
1504

1505
        TAOS_CHECK_GOTO(taosHashPut(pUser->alterViews, key, keyLen, value, valuelen), &lino, _OVER);
100!
1506
      }
1507
    }
1508

1509
    for (int32_t i = 0; i < numOfUseDbs; ++i) {
5,712✔
1510
      int32_t keyLen = 0;
1,814✔
1511
      SDB_GET_INT32(pRaw, dataPos, &keyLen, _OVER);
1,814!
1512

1513
      TAOS_MEMORY_REALLOC(key, keyLen * sizeof(char));
1,814!
1514
      if (key == NULL) {
1,814!
1515
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1516
      }
1517
      (void)memset(key, 0, keyLen);
1,814✔
1518
      SDB_GET_BINARY(pRaw, dataPos, key, keyLen, _OVER);
1,814!
1519

1520
      int32_t ref = 0;
1,814✔
1521
      SDB_GET_INT32(pRaw, dataPos, &ref, _OVER);
1,814!
1522

1523
      TAOS_CHECK_GOTO(taosHashPut(pUser->useDbs, key, keyLen, &ref, sizeof(ref)), &lino, _OVER);
1,814!
1524
    }
1525
  }
1526
  // decoder white list
1527
  if (sver >= USER_VER_SUPPORT_WHITELIST) {
3,898!
1528
    if (sver < USER_VER_SUPPORT_WHITELIT_DUAL_STACK) {
3,898!
1529
      int32_t len = 0;
×
1530
      SDB_GET_INT32(pRaw, dataPos, &len, _OVER);
×
1531

1532
      TAOS_MEMORY_REALLOC(key, len);
×
1533
      if (key == NULL) {
×
1534
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1535
      }
1536
      SDB_GET_BINARY(pRaw, dataPos, key, len, _OVER);
×
1537

1538
      SIpWhiteList *pIpWhiteList = NULL;
×
1539
      TAOS_CHECK_GOTO(createIpWhiteListFromOldVer(key, len, &pIpWhiteList), &lino, _OVER);
×
1540

1541
      SDB_GET_INT64(pRaw, dataPos, &pUser->ipWhiteListVer, _OVER);
×
1542

1543
      code = cvtIpWhiteListToDual(pIpWhiteList, &pUser->pIpWhiteListDual);
×
1544
      if (code != 0) {
×
1545
        taosMemoryFreeClear(pIpWhiteList);
×
1546
      }
1547
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
1548

1549
      taosMemoryFreeClear(pIpWhiteList);
×
1550

1551
    } else if (sver >= USER_VER_SUPPORT_WHITELIT_DUAL_STACK) {
3,898!
1552
      int32_t len = 0;
3,898✔
1553
      SDB_GET_INT32(pRaw, dataPos, &len, _OVER);
3,898!
1554

1555
      TAOS_MEMORY_REALLOC(key, len);
3,898!
1556
      if (key == NULL) {
3,898!
1557
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1558
      }
1559
      SDB_GET_BINARY(pRaw, dataPos, key, len, _OVER);
3,898!
1560

1561
      TAOS_CHECK_GOTO(createIpWhiteList(key, len, &pUser->pIpWhiteListDual), &lino, _OVER);
3,898!
1562
      SDB_GET_INT64(pRaw, dataPos, &pUser->ipWhiteListVer, _OVER);
3,898!
1563
    }
1564
  }
1565

1566
  if (pUser->pIpWhiteListDual == NULL) {
3,898!
1567
    TAOS_CHECK_GOTO(createDefaultIpWhiteList(&pUser->pIpWhiteListDual), &lino, _OVER);
×
1568
    pUser->ipWhiteListVer = taosGetTimestampMs();
×
1569
  }
1570

1571
  SDB_GET_RESERVE(pRaw, dataPos, USER_RESERVE_SIZE, _OVER)
3,898!
1572
  taosInitRWLatch(&pUser->lock);
3,898✔
1573

1574
_OVER:
3,898✔
1575
  taosMemoryFree(key);
3,898!
1576
  taosMemoryFree(value);
3,898!
1577
  if (code < 0) {
3,898!
1578
    terrno = code;
×
1579
    mError("user:%s, failed to decode at line %d from raw:%p since %s", pUser == NULL ? "null" : pUser->user, lino,
×
1580
           pRaw, tstrerror(code));
1581
    if (pUser != NULL) {
×
1582
      taosHashCleanup(pUser->readDbs);
×
1583
      taosHashCleanup(pUser->writeDbs);
×
1584
      taosHashCleanup(pUser->topics);
×
1585
      taosHashCleanup(pUser->readTbs);
×
1586
      taosHashCleanup(pUser->writeTbs);
×
1587
      taosHashCleanup(pUser->alterTbs);
×
1588
      taosHashCleanup(pUser->readViews);
×
1589
      taosHashCleanup(pUser->writeViews);
×
1590
      taosHashCleanup(pUser->alterViews);
×
1591
      taosHashCleanup(pUser->useDbs);
×
1592
      taosMemoryFreeClear(pUser->pIpWhiteListDual);
×
1593
    }
1594
    taosMemoryFreeClear(pRow);
×
1595
    return NULL;
×
1596
  }
1597

1598
  mTrace("user:%s, decode from raw:%p, row:%p", pUser->user, pRaw, pUser);
3,898✔
1599
  return pRow;
3,898✔
1600
}
1601

1602
static int32_t mndUserActionInsert(SSdb *pSdb, SUserObj *pUser) {
2,490✔
1603
  mTrace("user:%s, perform insert action, row:%p", pUser->user, pUser);
2,490✔
1604

1605
  SAcctObj *pAcct = sdbAcquire(pSdb, SDB_ACCT, pUser->acct);
2,490✔
1606
  if (pAcct == NULL) {
2,490!
1607
    terrno = TSDB_CODE_MND_ACCT_NOT_EXIST;
×
1608
    mError("user:%s, failed to perform insert action since %s", pUser->user, terrstr());
×
1609
    TAOS_RETURN(terrno);
×
1610
  }
1611
  pUser->acctId = pAcct->acctId;
2,490✔
1612
  sdbRelease(pSdb, pAcct);
2,490✔
1613

1614
  return 0;
2,490✔
1615
}
1616

1617
int32_t mndDupTableHash(SHashObj *pOld, SHashObj **ppNew) {
222,040✔
1618
  int32_t code = 0;
222,040✔
1619
  *ppNew =
222,040✔
1620
      taosHashInit(taosHashGetSize(pOld), taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
222,040✔
1621
  if (*ppNew == NULL) {
222,040!
1622
    TAOS_RETURN(terrno);
×
1623
  }
1624

1625
  char *tb = taosHashIterate(pOld, NULL);
222,040✔
1626
  while (tb != NULL) {
545,998✔
1627
    size_t keyLen = 0;
323,958✔
1628
    char  *key = taosHashGetKey(tb, &keyLen);
323,958✔
1629

1630
    int32_t valueLen = strlen(tb) + 1;
323,958✔
1631
    if ((code = taosHashPut(*ppNew, key, keyLen, tb, valueLen)) != 0) {
323,958!
1632
      taosHashCancelIterate(pOld, tb);
×
1633
      taosHashCleanup(*ppNew);
×
1634
      TAOS_RETURN(code);
×
1635
    }
1636
    tb = taosHashIterate(pOld, tb);
323,958✔
1637
  }
1638

1639
  TAOS_RETURN(code);
222,040✔
1640
}
1641

1642
int32_t mndDupUseDbHash(SHashObj *pOld, SHashObj **ppNew) {
7,735✔
1643
  int32_t code = 0;
7,735✔
1644
  *ppNew =
7,735✔
1645
      taosHashInit(taosHashGetSize(pOld), taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
7,735✔
1646
  if (*ppNew == NULL) {
7,735!
1647
    TAOS_RETURN(terrno);
×
1648
  }
1649

1650
  int32_t *db = taosHashIterate(pOld, NULL);
7,735✔
1651
  while (db != NULL) {
9,751✔
1652
    size_t keyLen = 0;
2,016✔
1653
    char  *key = taosHashGetKey(db, &keyLen);
2,016✔
1654

1655
    if ((code = taosHashPut(*ppNew, key, keyLen, db, sizeof(*db))) != 0) {
2,016!
1656
      taosHashCancelIterate(pOld, db);
×
1657
      taosHashCleanup(*ppNew);
×
1658
      TAOS_RETURN(code);
×
1659
    }
1660
    db = taosHashIterate(pOld, db);
2,016✔
1661
  }
1662

1663
  TAOS_RETURN(code);
7,735✔
1664
}
1665

1666
int32_t mndUserDupObj(SUserObj *pUser, SUserObj *pNew) {
7,735✔
1667
  int32_t code = 0;
7,735✔
1668
  (void)memcpy(pNew, pUser, sizeof(SUserObj));
7,735✔
1669
  pNew->authVersion++;
7,735✔
1670
  pNew->updateTime = taosGetTimestampMs();
7,735✔
1671

1672
  taosRLockLatch(&pUser->lock);
7,735✔
1673
  TAOS_CHECK_GOTO(mndDupDbHash(pUser->readDbs, &pNew->readDbs), NULL, _OVER);
7,735!
1674
  TAOS_CHECK_GOTO(mndDupDbHash(pUser->writeDbs, &pNew->writeDbs), NULL, _OVER);
7,735!
1675
  TAOS_CHECK_GOTO(mndDupTableHash(pUser->readTbs, &pNew->readTbs), NULL, _OVER);
7,735!
1676
  TAOS_CHECK_GOTO(mndDupTableHash(pUser->writeTbs, &pNew->writeTbs), NULL, _OVER);
7,735!
1677
  TAOS_CHECK_GOTO(mndDupTableHash(pUser->alterTbs, &pNew->alterTbs), NULL, _OVER);
7,735!
1678
  TAOS_CHECK_GOTO(mndDupTableHash(pUser->readViews, &pNew->readViews), NULL, _OVER);
7,735!
1679
  TAOS_CHECK_GOTO(mndDupTableHash(pUser->writeViews, &pNew->writeViews), NULL, _OVER);
7,735!
1680
  TAOS_CHECK_GOTO(mndDupTableHash(pUser->alterViews, &pNew->alterViews), NULL, _OVER);
7,735!
1681
  TAOS_CHECK_GOTO(mndDupTopicHash(pUser->topics, &pNew->topics), NULL, _OVER);
7,735!
1682
  TAOS_CHECK_GOTO(mndDupUseDbHash(pUser->useDbs, &pNew->useDbs), NULL, _OVER);
7,735!
1683
  pNew->pIpWhiteListDual = cloneIpWhiteList(pUser->pIpWhiteListDual);
7,735✔
1684
  if (pNew->pIpWhiteListDual == NULL) {
7,735!
1685
    code = TSDB_CODE_OUT_OF_MEMORY;
×
1686
  }
1687

1688
_OVER:
7,735✔
1689
  taosRUnLockLatch(&pUser->lock);
7,735✔
1690
  TAOS_RETURN(code);
7,735✔
1691
}
1692

1693
void mndUserFreeObj(SUserObj *pUser) {
22,676✔
1694
  taosHashCleanup(pUser->readDbs);
22,676✔
1695
  taosHashCleanup(pUser->writeDbs);
22,676✔
1696
  taosHashCleanup(pUser->topics);
22,676✔
1697
  taosHashCleanup(pUser->readTbs);
22,676✔
1698
  taosHashCleanup(pUser->writeTbs);
22,676✔
1699
  taosHashCleanup(pUser->alterTbs);
22,676✔
1700
  taosHashCleanup(pUser->readViews);
22,676✔
1701
  taosHashCleanup(pUser->writeViews);
22,676✔
1702
  taosHashCleanup(pUser->alterViews);
22,676✔
1703
  taosHashCleanup(pUser->useDbs);
22,676✔
1704
  taosMemoryFreeClear(pUser->pIpWhiteListDual);
22,676!
1705
  pUser->readDbs = NULL;
22,676✔
1706
  pUser->writeDbs = NULL;
22,676✔
1707
  pUser->topics = NULL;
22,676✔
1708
  pUser->readTbs = NULL;
22,676✔
1709
  pUser->writeTbs = NULL;
22,676✔
1710
  pUser->alterTbs = NULL;
22,676✔
1711
  pUser->readViews = NULL;
22,676✔
1712
  pUser->writeViews = NULL;
22,676✔
1713
  pUser->alterViews = NULL;
22,676✔
1714
  pUser->useDbs = NULL;
22,676✔
1715
}
22,676✔
1716

1717
static int32_t mndUserActionDelete(SSdb *pSdb, SUserObj *pUser) {
3,885✔
1718
  mTrace("user:%s, perform delete action, row:%p", pUser->user, pUser);
3,885✔
1719
  mndUserFreeObj(pUser);
3,885✔
1720
  return 0;
3,885✔
1721
}
1722

1723
static int32_t mndUserActionUpdate(SSdb *pSdb, SUserObj *pOld, SUserObj *pNew) {
1,293✔
1724
  mTrace("user:%s, perform update action, old row:%p new row:%p", pOld->user, pOld, pNew);
1,293✔
1725
  taosWLockLatch(&pOld->lock);
1,293✔
1726
  pOld->updateTime = pNew->updateTime;
1,293✔
1727
  pOld->authVersion = pNew->authVersion;
1,293✔
1728
  pOld->passVersion = pNew->passVersion;
1,293✔
1729
  pOld->sysInfo = pNew->sysInfo;
1,293✔
1730
  pOld->enable = pNew->enable;
1,293✔
1731
  pOld->flag = pNew->flag;
1,293✔
1732
  (void)memcpy(pOld->pass, pNew->pass, TSDB_PASSWORD_LEN);
1,293✔
1733
  TSWAP(pOld->readDbs, pNew->readDbs);
1,293✔
1734
  TSWAP(pOld->writeDbs, pNew->writeDbs);
1,293✔
1735
  TSWAP(pOld->topics, pNew->topics);
1,293✔
1736
  TSWAP(pOld->readTbs, pNew->readTbs);
1,293✔
1737
  TSWAP(pOld->writeTbs, pNew->writeTbs);
1,293✔
1738
  TSWAP(pOld->alterTbs, pNew->alterTbs);
1,293✔
1739
  TSWAP(pOld->readViews, pNew->readViews);
1,293✔
1740
  TSWAP(pOld->writeViews, pNew->writeViews);
1,293✔
1741
  TSWAP(pOld->alterViews, pNew->alterViews);
1,293✔
1742
  TSWAP(pOld->useDbs, pNew->useDbs);
1,293✔
1743

1744
  int32_t sz = sizeof(SIpWhiteListDual) + pNew->pIpWhiteListDual->num * sizeof(SIpRange);
1,293✔
1745
  TAOS_MEMORY_REALLOC(pOld->pIpWhiteListDual, sz);
1,293!
1746
  if (pOld->pIpWhiteListDual == NULL) {
1,293!
1747
    taosWUnLockLatch(&pOld->lock);
×
1748
    return terrno;
×
1749
  }
1750
  (void)memcpy(pOld->pIpWhiteListDual, pNew->pIpWhiteListDual, sz);
1,293✔
1751
  pOld->ipWhiteListVer = pNew->ipWhiteListVer;
1,293✔
1752

1753
  taosWUnLockLatch(&pOld->lock);
1,293✔
1754

1755
  return 0;
1,293✔
1756
}
1757

1758
int32_t mndAcquireUser(SMnode *pMnode, const char *userName, SUserObj **ppUser) {
313,378✔
1759
  int32_t code = 0;
313,378✔
1760
  SSdb   *pSdb = pMnode->pSdb;
313,378✔
1761

1762
  *ppUser = sdbAcquire(pSdb, SDB_USER, userName);
313,378✔
1763
  if (*ppUser == NULL) {
313,381✔
1764
    if (terrno == TSDB_CODE_SDB_OBJ_NOT_THERE) {
245!
1765
      code = TSDB_CODE_MND_USER_NOT_EXIST;
245✔
1766
    } else {
1767
      code = TSDB_CODE_MND_USER_NOT_AVAILABLE;
×
1768
    }
1769
  }
1770
  TAOS_RETURN(code);
313,381✔
1771
}
1772

1773
void mndReleaseUser(SMnode *pMnode, SUserObj *pUser) {
313,795✔
1774
  SSdb *pSdb = pMnode->pSdb;
313,795✔
1775
  sdbRelease(pSdb, pUser);
313,795✔
1776
}
313,799✔
1777

1778
static int32_t addDefaultIpToTable(int8_t enableIpv6, SHashObj *pUniqueTab) {
3✔
1779
  int32_t code = 0;
3✔
1780
  int32_t lino = 0;
3✔
1781
  int32_t dummpy = 0;
3✔
1782

1783
  SIpRange ipv4 = {0}, ipv6 = {0};
3✔
1784
  code = createDefaultIp4Range(&ipv4);
3✔
1785
  TSDB_CHECK_CODE(code, lino, _error);
3!
1786

1787
  code = taosHashPut(pUniqueTab, &ipv4, sizeof(ipv4), &dummpy, sizeof(dummpy));
3✔
1788
  TSDB_CHECK_CODE(code, lino, _error);
3!
1789

1790
  if (enableIpv6) {
3!
1791
    code = createDefaultIp6Range(&ipv6);
×
1792
    TSDB_CHECK_CODE(code, lino, _error);
×
1793

1794
    code = taosHashPut(pUniqueTab, &ipv6, sizeof(ipv6), &dummpy, sizeof(dummpy));
×
1795
    TSDB_CHECK_CODE(code, lino, _error);
×
1796
  }
1797
_error:
3✔
1798
  if (code != 0) {
3!
1799
    mError("failed to add default ip range to table since %s", tstrerror(code));
×
1800
  }
1801
  return code;
3✔
1802
}
1803
static int32_t mndCreateUser(SMnode *pMnode, char *acct, SCreateUserReq *pCreate, SRpcMsg *pReq) {
189✔
1804
  int32_t  code = 0;
189✔
1805
  int32_t  lino = 0;
189✔
1806
  SUserObj userObj = {0};
189✔
1807

1808
  if (pCreate->passIsMd5 == 1) {
189!
1809
    memcpy(userObj.pass, pCreate->pass, TSDB_PASSWORD_LEN);
189✔
1810
  } else {
1811
    if (pCreate->isImport != 1) {
×
1812
      taosEncryptPass_c((uint8_t *)pCreate->pass, strlen(pCreate->pass), userObj.pass);
×
1813
    } else {
1814
      // mInfo("pCreate->pass:%s", pCreate->eass)
1815
      memcpy(userObj.pass, pCreate->pass, TSDB_PASSWORD_LEN);
×
1816
    }
1817
  }
1818

1819
  tstrncpy(userObj.user, pCreate->user, TSDB_USER_LEN);
189✔
1820
  tstrncpy(userObj.acct, acct, TSDB_USER_LEN);
189✔
1821
  userObj.createdTime = taosGetTimestampMs();
189✔
1822
  userObj.updateTime = userObj.createdTime;
189✔
1823
  userObj.superUser = 0;  // pCreate->superUser;
189✔
1824
  userObj.sysInfo = pCreate->sysInfo;
189✔
1825
  userObj.enable = pCreate->enable;
189✔
1826
  userObj.createdb = pCreate->createDb;
189✔
1827

1828
  if (pCreate->numIpRanges == 0) {
189✔
1829
    TAOS_CHECK_RETURN(createDefaultIpWhiteList(&userObj.pIpWhiteListDual));
186!
1830
  } else {
1831
    SHashObj *pUniqueTab = taosHashInit(64, MurmurHash3_32, true, HASH_NO_LOCK);
3✔
1832
    if (pUniqueTab == NULL) {
3!
1833
      TAOS_RETURN(terrno);
×
1834
    }
1835
    int32_t dummpy = 0;
3✔
1836
    for (int i = 0; i < pCreate->numIpRanges; i++) {
8✔
1837
      SIpRange range = {0};
5✔
1838
      if (pCreate->pIpDualRanges == NULL) {
5!
1839
        range.type = 0;
×
1840
        memcpy(&range.ipV4, &(pCreate->pIpRanges[i]), sizeof(SIpV4Range));
×
1841
      } else {
1842
        memcpy(&range, pCreate->pIpDualRanges + i, sizeof(SIpRange));
5✔
1843
      }
1844

1845
      if ((code = taosHashPut(pUniqueTab, &range, sizeof(range), &dummpy, sizeof(dummpy))) != 0) {
5!
1846
        taosHashCleanup(pUniqueTab);
×
1847
        TAOS_RETURN(code);
×
1848
      }
1849
    }
1850
    code = addDefaultIpToTable(tsEnableIpv6, pUniqueTab);
3✔
1851
    if (code != 0) {
3!
1852
      taosHashCleanup(pUniqueTab);
×
1853
      TAOS_RETURN(code);
×
1854
    }
1855

1856
    if (taosHashGetSize(pUniqueTab) > MND_MAX_USE_HOST) {
3!
1857
      taosHashCleanup(pUniqueTab);
×
1858
      TAOS_RETURN(TSDB_CODE_MND_TOO_MANY_USER_HOST);
×
1859
    }
1860

1861
    int32_t           numOfRanges = taosHashGetSize(pUniqueTab);
3✔
1862
    SIpWhiteListDual *p = taosMemoryCalloc(1, sizeof(SIpWhiteListDual) + numOfRanges * sizeof(SIpRange));
3!
1863
    if (p == NULL) {
3!
1864
      taosHashCleanup(pUniqueTab);
×
1865
      TAOS_RETURN(terrno);
×
1866
    }
1867
    void   *pIter = taosHashIterate(pUniqueTab, NULL);
3✔
1868
    int32_t i = 0;
3✔
1869
    while (pIter) {
10✔
1870
      size_t    len = 0;
7✔
1871
      SIpRange *key = taosHashGetKey(pIter, &len);
7✔
1872
      memcpy(p->pIpRanges + i, key, sizeof(SIpRange));
7✔
1873
      pIter = taosHashIterate(pUniqueTab, pIter);
7✔
1874
      i++;
7✔
1875
    }
1876

1877
    taosHashCleanup(pUniqueTab);
3✔
1878
    p->num = numOfRanges;
3✔
1879
    userObj.pIpWhiteListDual = p;
3✔
1880
  }
1881

1882
  userObj.ipWhiteListVer = taosGetTimestampMs();
189✔
1883

1884
  STrans *pTrans = mndTransCreate(pMnode, TRN_POLICY_ROLLBACK, TRN_CONFLICT_NOTHING, pReq, "create-user");
189✔
1885
  if (pTrans == NULL) {
189!
1886
    mError("user:%s, failed to create since %s", pCreate->user, terrstr());
×
1887
    taosMemoryFree(userObj.pIpWhiteListDual);
×
1888
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1889
  }
1890
  mInfo("trans:%d, used to create user:%s", pTrans->id, pCreate->user);
189!
1891

1892
  SSdbRaw *pCommitRaw = mndUserActionEncode(&userObj);
189✔
1893
  if (pCommitRaw == NULL || mndTransAppendCommitlog(pTrans, pCommitRaw) != 0) {
189!
1894
    mError("trans:%d, failed to commit redo log since %s", pTrans->id, terrstr());
×
1895
    mndTransDrop(pTrans);
×
1896
    TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
1897
  }
1898
  TAOS_CHECK_GOTO(sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY), &lino, _OVER);
189!
1899

1900
  if (mndTransPrepare(pMnode, pTrans) != 0) {
189!
1901
    mError("trans:%d, failed to prepare since %s", pTrans->id, terrstr());
×
1902
    mndTransDrop(pTrans);
×
1903
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
1904
  }
1905
  if ((code = ipWhiteMgtUpdate(pMnode, userObj.user, userObj.pIpWhiteListDual)) != 0) {
189!
1906
    mndTransDrop(pTrans);
×
1907
    TAOS_CHECK_GOTO(code, &lino, _OVER);
×
1908
  }
1909

1910
  taosMemoryFree(userObj.pIpWhiteListDual);
189!
1911
  mndTransDrop(pTrans);
189✔
1912
  return 0;
189✔
1913
_OVER:
×
1914
  taosMemoryFree(userObj.pIpWhiteListDual);
×
1915

1916
  TAOS_RETURN(code);
×
1917
}
1918

1919
static int32_t mndCheckPasswordMinLen(const char *pwd, int32_t len) {
×
1920
  if (len < TSDB_PASSWORD_MIN_LEN) {
×
1921
    return -1;
×
1922
  }
1923
  return 0;
×
1924
}
1925

1926
static int32_t mndCheckPasswordMaxLen(const char *pwd, int32_t len) {
×
1927
  if (len > TSDB_PASSWORD_MAX_LEN) {
×
1928
    return -1;
×
1929
  }
1930
  return 0;
×
1931
}
1932

1933
static int32_t mndCheckPasswordFmt(const char *pwd, int32_t len) {
×
1934
  if (strcmp(pwd, "taosdata") == 0) {
×
1935
    return 0;
×
1936
  }
1937

1938
  bool charTypes[4] = {0};
×
1939
  for (int32_t i = 0; i < len; ++i) {
×
1940
    if (taosIsBigChar(pwd[i])) {
×
1941
      charTypes[0] = true;
×
1942
    } else if (taosIsSmallChar(pwd[i])) {
×
1943
      charTypes[1] = true;
×
1944
    } else if (taosIsNumberChar(pwd[i])) {
×
1945
      charTypes[2] = true;
×
1946
    } else if (taosIsSpecialChar(pwd[i])) {
×
1947
      charTypes[3] = true;
×
1948
    } else {
1949
      return -1;
×
1950
    }
1951
  }
1952

1953
  int32_t numOfTypes = 0;
×
1954
  for (int32_t i = 0; i < 4; ++i) {
×
1955
    numOfTypes += charTypes[i];
×
1956
  }
1957

1958
  if (numOfTypes < 3) {
×
1959
    return -1;
×
1960
  }
1961

1962
  return 0;
×
1963
}
1964

1965
static int32_t mndProcessCreateUserReq(SRpcMsg *pReq) {
191✔
1966
  SMnode        *pMnode = pReq->info.node;
191✔
1967
  int32_t        code = 0;
191✔
1968
  int32_t        lino = 0;
191✔
1969
  SUserObj      *pUser = NULL;
191✔
1970
  SUserObj      *pOperUser = NULL;
191✔
1971
  SCreateUserReq createReq = {0};
191✔
1972

1973
  if (tDeserializeSCreateUserReq(pReq->pCont, pReq->contLen, &createReq) != 0) {
191!
1974
    TAOS_CHECK_GOTO(TSDB_CODE_INVALID_MSG, &lino, _OVER);
×
1975
  }
1976

1977
  mInfo("user:%s, start to create, createdb:%d, is_import:%d", createReq.user, createReq.createDb, createReq.isImport);
191!
1978

1979
#ifndef TD_ENTERPRISE
1980
  if (createReq.isImport == 1) {
1981
    TAOS_CHECK_GOTO(TSDB_CODE_OPS_NOT_SUPPORT, &lino, _OVER);  // enterprise feature
1982
  }
1983
#endif
1984

1985
  if (createReq.isImport != 1) {
191✔
1986
    TAOS_CHECK_GOTO(mndCheckOperPrivilege(pMnode, pReq->info.conn.user, MND_OPER_CREATE_USER), &lino, _OVER);
190!
1987
  } else {
1988
    if (strcmp(pReq->info.conn.user, "root") != 0) {
1!
1989
      mError("The operation is not permitted, user:%s", pReq->info.conn.user);
×
1990
      TAOS_CHECK_GOTO(TSDB_CODE_MND_NO_RIGHTS, &lino, _OVER);
×
1991
    }
1992
  }
1993

1994
  if (createReq.user[0] == 0) {
191!
1995
    TAOS_CHECK_GOTO(TSDB_CODE_MND_INVALID_USER_FORMAT, &lino, _OVER);
×
1996
  }
1997

1998
  if (createReq.passIsMd5 == 0) {
191!
1999
    int32_t len = strlen(createReq.pass);
×
2000
    if (createReq.isImport != 1) {
×
2001
      if (mndCheckPasswordMinLen(createReq.pass, len) != 0) {
×
2002
        TAOS_CHECK_GOTO(TSDB_CODE_PAR_PASSWD_TOO_SHORT_OR_EMPTY, &lino, _OVER);
×
2003
      }
2004
      if (mndCheckPasswordMaxLen(createReq.pass, len) != 0) {
×
2005
        TAOS_CHECK_GOTO(TSDB_CODE_PAR_NAME_OR_PASSWD_TOO_LONG, &lino, _OVER);
×
2006
      }
2007
      if (mndCheckPasswordFmt(createReq.pass, len) != 0) {
×
2008
        TAOS_CHECK_GOTO(TSDB_CODE_MND_INVALID_PASS_FORMAT, &lino, _OVER);
×
2009
      }
2010
    }
2011
  }
2012

2013
  code = mndAcquireUser(pMnode, createReq.user, &pUser);
191✔
2014
  if (pUser != NULL) {
191✔
2015
    TAOS_CHECK_GOTO(TSDB_CODE_MND_USER_ALREADY_EXIST, &lino, _OVER);
2!
2016
  }
2017

2018
  code = mndAcquireUser(pMnode, pReq->info.conn.user, &pOperUser);
189✔
2019
  if (pOperUser == NULL) {
189!
2020
    TAOS_CHECK_GOTO(TSDB_CODE_MND_NO_USER_FROM_CONN, &lino, _OVER);
×
2021
  }
2022

2023
  TAOS_CHECK_GOTO(grantCheck(TSDB_GRANT_USER), &lino, _OVER);
189!
2024

2025
  code = mndCreateUser(pMnode, pOperUser->acct, &createReq, pReq);
189✔
2026
  if (code == 0) code = TSDB_CODE_ACTION_IN_PROGRESS;
189!
2027

2028
  char detail[1000] = {0};
189✔
2029
  (void)tsnprintf(detail, sizeof(detail), "enable:%d, superUser:%d, sysInfo:%d, password:xxx", createReq.enable,
189✔
2030
                  createReq.superUser, createReq.sysInfo);
189✔
2031
  char operation[15] = {0};
189✔
2032
  if (createReq.isImport == 1) {
189✔
2033
    tstrncpy(operation, "importUser", sizeof(operation));
1✔
2034
  } else {
2035
    tstrncpy(operation, "createUser", sizeof(operation));
188✔
2036
  }
2037

2038
  auditRecord(pReq, pMnode->clusterId, operation, "", createReq.user, detail, strlen(detail));
189✔
2039

2040
_OVER:
191✔
2041
  if (code < 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
191!
2042
    mError("user:%s, failed to create at line %d since %s", createReq.user, lino, tstrerror(code));
2!
2043
  }
2044

2045
  mndReleaseUser(pMnode, pUser);
191✔
2046
  mndReleaseUser(pMnode, pOperUser);
191✔
2047
  tFreeSCreateUserReq(&createReq);
191✔
2048

2049
  TAOS_RETURN(code);
191✔
2050
}
2051

2052
int32_t mndProcessGetUserWhiteListReq(SRpcMsg *pReq) {
221✔
2053
  SMnode              *pMnode = pReq->info.node;
221✔
2054
  int32_t              code = 0;
221✔
2055
  int32_t              lino = 0;
221✔
2056
  int32_t              contLen = 0;
221✔
2057
  void                *pRsp = NULL;
221✔
2058
  SUserObj            *pUser = NULL;
221✔
2059
  SGetUserWhiteListReq wlReq = {0};
221✔
2060
  SGetUserWhiteListRsp wlRsp = {0};
221✔
2061

2062
  int32_t (*serialFn)(void *, int32_t, SGetUserWhiteListRsp *) = NULL;
221✔
2063
  int32_t (*setRspFn)(SMnode * pMnode, SUserObj * pUser, SGetUserWhiteListRsp * pRsp) = NULL;
221✔
2064

2065
  if (pReq->msgType == TDMT_MND_GET_USER_WHITELIST_DUAL) {
221!
2066
    serialFn = tSerializeSGetUserWhiteListDualRsp;
×
2067
    setRspFn = mndSetUserWhiteListDualRsp;
×
2068
  } else {
2069
    serialFn = tSerializeSGetUserWhiteListRsp;
221✔
2070
    setRspFn = mndSetUserWhiteListRsp;
221✔
2071
  }
2072
  if (tDeserializeSGetUserWhiteListReq(pReq->pCont, pReq->contLen, &wlReq) != 0) {
221!
2073
    TAOS_CHECK_GOTO(TSDB_CODE_INVALID_MSG, &lino, _OVER);
×
2074
  }
2075
  mTrace("user: %s, start to get whitelist", wlReq.user);
221✔
2076

2077
  code = mndAcquireUser(pMnode, wlReq.user, &pUser);
221✔
2078
  if (pUser == NULL) {
221!
2079
    TAOS_CHECK_GOTO(TSDB_CODE_MND_USER_NOT_EXIST, &lino, _OVER);
×
2080
  }
2081

2082
  TAOS_CHECK_GOTO(setRspFn(pMnode, pUser, &wlRsp), &lino, _OVER);
221!
2083
  contLen = serialFn(NULL, 0, &wlRsp);
221✔
2084
  if (contLen < 0) {
221!
2085
    TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
2086
  }
2087
  pRsp = rpcMallocCont(contLen);
221✔
2088
  if (pRsp == NULL) {
221!
2089
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
2090
  }
2091

2092
  contLen = serialFn(pRsp, contLen, &wlRsp);
221✔
2093
  if (contLen < 0) {
221!
2094
    TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _OVER);
×
2095
  }
2096

2097
_OVER:
221✔
2098
  mndReleaseUser(pMnode, pUser);
221✔
2099
  tFreeSGetUserWhiteListDualRsp(&wlRsp);
221✔
2100
  if (code < 0) {
221!
2101
    mError("user:%s, failed to get whitelist at line %d since %s", wlReq.user, lino, tstrerror(code));
×
2102
    rpcFreeCont(pRsp);
×
2103
    pRsp = NULL;
×
2104
    contLen = 0;
×
2105
  }
2106
  pReq->code = code;
221✔
2107
  pReq->info.rsp = pRsp;
221✔
2108
  pReq->info.rspLen = contLen;
221✔
2109

2110
  TAOS_RETURN(code);
221✔
2111
}
2112

2113
int32_t mndProcesSRetrieveIpWhiteReq(SRpcMsg *pReq) {
1✔
2114
  int32_t        code = 0;
1✔
2115
  int32_t        lino = 0;
1✔
2116
  int32_t        len = 0;
1✔
2117
  void          *pRsp = NULL;
1✔
2118
  SUpdateIpWhite ipWhite = {0};
1✔
2119

2120
  // impl later
2121
  SRetrieveIpWhiteReq req = {0};
1✔
2122
  if (tDeserializeRetrieveIpWhite(pReq->pCont, pReq->contLen, &req) != 0) {
1!
2123
    code = TSDB_CODE_INVALID_MSG;
×
2124
    TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2125
  }
2126

2127
  int32_t (*fn)(void *, int32_t, SUpdateIpWhite *) = NULL;
1✔
2128
  if (pReq->msgType == TDMT_MND_RETRIEVE_IP_WHITE) {
1!
2129
    fn = tSerializeSUpdateIpWhite;
×
2130
  } else if (pReq->msgType == TDMT_MND_RETRIEVE_IP_WHITE_DUAL) {
1!
2131
    fn = tSerializeSUpdateIpWhiteDual;
1✔
2132
  }
2133

2134
  TAOS_CHECK_GOTO(ipWhiteMgtFillMsg(&ipWhite), &lino, _OVER);
1!
2135

2136
  len = fn(NULL, 0, &ipWhite);
1✔
2137
  if (len < 0) {
1!
2138
    TAOS_CHECK_GOTO(len, &lino, _OVER);
×
2139
  }
2140

2141
  pRsp = rpcMallocCont(len);
1✔
2142
  if (!pRsp) {
1!
2143
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
2144
  }
2145
  len = fn(pRsp, len, &ipWhite);
1✔
2146
  if (len < 0) {
1!
2147
    TAOS_CHECK_GOTO(len, &lino, _OVER);
×
2148
  }
2149

2150
_OVER:
1✔
2151
  if (code < 0) {
1!
2152
    mError("failed to process retrieve ip white request at line %d since %s", lino, tstrerror(code));
×
2153
    rpcFreeCont(pRsp);
×
2154
    pRsp = NULL;
×
2155
    len = 0;
×
2156
  }
2157
  pReq->code = code;
1✔
2158
  pReq->info.rsp = pRsp;
1✔
2159
  pReq->info.rspLen = len;
1✔
2160

2161
  tFreeSUpdateIpWhiteReq(&ipWhite);
1✔
2162
  TAOS_RETURN(code);
1✔
2163
}
2164

2165
static int32_t mndAlterUser(SMnode *pMnode, SUserObj *pOld, SUserObj *pNew, SRpcMsg *pReq) {
1,197✔
2166
  int32_t code = 0;
1,197✔
2167
  STrans *pTrans = mndTransCreate(pMnode, TRN_POLICY_ROLLBACK, TRN_CONFLICT_NOTHING, pReq, "alter-user");
1,197✔
2168
  if (pTrans == NULL) {
1,197!
2169
    mError("user:%s, failed to alter since %s", pOld->user, terrstr());
×
2170
    TAOS_RETURN(terrno);
×
2171
  }
2172
  mInfo("trans:%d, used to alter user:%s", pTrans->id, pOld->user);
1,197!
2173

2174
  SSdbRaw *pCommitRaw = mndUserActionEncode(pNew);
1,197✔
2175
  if (pCommitRaw == NULL || mndTransAppendCommitlog(pTrans, pCommitRaw) != 0) {
1,197!
2176
    mError("trans:%d, failed to append commit log since %s", pTrans->id, terrstr());
×
2177
    mndTransDrop(pTrans);
×
2178
    TAOS_RETURN(terrno);
×
2179
  }
2180
  code = sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY);
1,197✔
2181
  if (code < 0) {
1,197!
2182
    mndTransDrop(pTrans);
×
2183
    TAOS_RETURN(code);
×
2184
  }
2185

2186
  if (mndTransPrepare(pMnode, pTrans) != 0) {
1,197!
2187
    mError("trans:%d, failed to prepare since %s", pTrans->id, terrstr());
×
2188
    mndTransDrop(pTrans);
×
2189
    TAOS_RETURN(terrno);
×
2190
  }
2191
  if ((code = ipWhiteMgtUpdate(pMnode, pNew->user, pNew->pIpWhiteListDual)) != 0) {
1,197!
2192
    mndTransDrop(pTrans);
×
2193
    TAOS_RETURN(code);
×
2194
  }
2195
  mndTransDrop(pTrans);
1,197✔
2196
  return 0;
1,197✔
2197
}
2198

2199
static int32_t mndDupObjHash(SHashObj *pOld, int32_t dataLen, SHashObj **ppNew) {
73,385✔
2200
  int32_t code = 0;
73,385✔
2201

2202
  *ppNew =
73,385✔
2203
      taosHashInit(taosHashGetSize(pOld), taosGetDefaultHashFunction(TSDB_DATA_TYPE_BINARY), true, HASH_ENTRY_LOCK);
73,385✔
2204
  if (*ppNew == NULL) {
73,385!
2205
    code = terrno ? terrno : TSDB_CODE_OUT_OF_MEMORY;
×
2206
    TAOS_RETURN(code);
×
2207
  }
2208

2209
  char *db = taosHashIterate(pOld, NULL);
73,385✔
2210
  while (db != NULL) {
74,183✔
2211
    int32_t len = strlen(db) + 1;
798✔
2212
    if ((code = taosHashPut(*ppNew, db, len, db, dataLen)) != 0) {
798!
2213
      taosHashCancelIterate(pOld, db);
×
2214
      taosHashCleanup(*ppNew);
×
2215
      TAOS_RETURN(code);
×
2216
    }
2217
    db = taosHashIterate(pOld, db);
798✔
2218
  }
2219

2220
  TAOS_RETURN(code);
73,385✔
2221
}
2222

2223
int32_t mndDupDbHash(SHashObj *pOld, SHashObj **ppNew) { return mndDupObjHash(pOld, TSDB_DB_FNAME_LEN, ppNew); }
65,650✔
2224

2225
int32_t mndDupTopicHash(SHashObj *pOld, SHashObj **ppNew) { return mndDupObjHash(pOld, TSDB_TOPIC_FNAME_LEN, ppNew); }
7,735✔
2226

2227
static int32_t mndTablePriviledge(SMnode *pMnode, SHashObj *hash, SHashObj *useDbHash, SAlterUserReq *alterReq,
929✔
2228
                                  SSdb *pSdb) {
2229
  void *pIter = NULL;
929✔
2230
  char  tbFName[TSDB_TABLE_FNAME_LEN] = {0};
929✔
2231

2232
  (void)snprintf(tbFName, sizeof(tbFName), "%s.%s", alterReq->objname, alterReq->tabName);
929✔
2233
  int32_t len = strlen(tbFName) + 1;
929✔
2234

2235
  if (alterReq->tagCond != NULL && alterReq->tagCondLen != 0) {
962!
2236
    char *value = taosHashGet(hash, tbFName, len);
33✔
2237
    if (value != NULL) {
33!
2238
      TAOS_RETURN(TSDB_CODE_MND_PRIVILEDGE_EXIST);
×
2239
    }
2240

2241
    int32_t condLen = alterReq->tagCondLen;
33✔
2242
    TAOS_CHECK_RETURN(taosHashPut(hash, tbFName, len, alterReq->tagCond, condLen));
33!
2243
  } else {
2244
    TAOS_CHECK_RETURN(taosHashPut(hash, tbFName, len, alterReq->isView ? "v" : "t", 2));
896!
2245
  }
2246

2247
  int32_t  dbKeyLen = strlen(alterReq->objname) + 1;
929✔
2248
  int32_t  ref = 1;
929✔
2249
  int32_t *currRef = taosHashGet(useDbHash, alterReq->objname, dbKeyLen);
929✔
2250
  if (NULL != currRef) {
929✔
2251
    ref = (*currRef) + 1;
848✔
2252
  }
2253
  TAOS_CHECK_RETURN(taosHashPut(useDbHash, alterReq->objname, dbKeyLen, &ref, sizeof(ref)));
929!
2254

2255
  TAOS_RETURN(0);
929✔
2256
}
2257

2258
static int32_t mndRemoveTablePriviledge(SMnode *pMnode, SHashObj *hash, SHashObj *useDbHash, SAlterUserReq *alterReq,
36✔
2259
                                        SSdb *pSdb) {
2260
  void *pIter = NULL;
36✔
2261
  char  tbFName[TSDB_TABLE_FNAME_LEN] = {0};
36✔
2262
  (void)snprintf(tbFName, sizeof(tbFName), "%s.%s", alterReq->objname, alterReq->tabName);
36✔
2263
  int32_t len = strlen(tbFName) + 1;
36✔
2264

2265
  if (taosHashRemove(hash, tbFName, len) != 0) {
36✔
2266
    TAOS_RETURN(0);  // not found
4✔
2267
  }
2268

2269
  int32_t  dbKeyLen = strlen(alterReq->objname) + 1;
32✔
2270
  int32_t *currRef = taosHashGet(useDbHash, alterReq->objname, dbKeyLen);
32✔
2271
  if (NULL == currRef) {
32!
2272
    return 0;
×
2273
  }
2274

2275
  if (1 == *currRef) {
32✔
2276
    if (taosHashRemove(useDbHash, alterReq->objname, dbKeyLen) != 0) {
25!
2277
      TAOS_RETURN(0);  // not found
×
2278
    }
2279
    return 0;
25✔
2280
  }
2281
  int32_t ref = (*currRef) - 1;
7✔
2282
  TAOS_CHECK_RETURN(taosHashPut(useDbHash, alterReq->objname, dbKeyLen, &ref, sizeof(ref)));
7!
2283

2284
  return 0;
7✔
2285
}
2286

2287
static char *mndUserAuditTypeStr(int32_t type) {
42✔
2288
  if (type == TSDB_ALTER_USER_PASSWD) {
42!
2289
    return "changePassword";
42✔
2290
  }
2291
  if (type == TSDB_ALTER_USER_SUPERUSER) {
×
2292
    return "changeSuperUser";
×
2293
  }
2294
  if (type == TSDB_ALTER_USER_ENABLE) {
×
2295
    return "enableUser";
×
2296
  }
2297
  if (type == TSDB_ALTER_USER_SYSINFO) {
×
2298
    return "userSysInfo";
×
2299
  }
2300
  if (type == TSDB_ALTER_USER_CREATEDB) {
×
2301
    return "userCreateDB";
×
2302
  }
2303
  return "error";
×
2304
}
2305

2306
static int32_t mndProcessAlterUserPrivilegesReq(SAlterUserReq *pAlterReq, SMnode *pMnode, SUserObj *pNewUser) {
1,115✔
2307
  SSdb   *pSdb = pMnode->pSdb;
1,115✔
2308
  void   *pIter = NULL;
1,115✔
2309
  int32_t code = 0;
1,115✔
2310
  int32_t lino = 0;
1,115✔
2311

2312
  if (ALTER_USER_ADD_READ_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,115✔
2313
      ALTER_USER_ADD_ALL_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,039!
2314
    if (strcmp(pAlterReq->objname, "1.*") != 0) {
76✔
2315
      int32_t len = strlen(pAlterReq->objname) + 1;
66✔
2316
      SDbObj *pDb = mndAcquireDb(pMnode, pAlterReq->objname);
66✔
2317
      if (pDb == NULL) {
66✔
2318
        mndReleaseDb(pMnode, pDb);
8✔
2319
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);  // TODO: refactor the terrno to code
8!
2320
      }
2321
      if ((code = taosHashPut(pNewUser->readDbs, pAlterReq->objname, len, pAlterReq->objname, TSDB_DB_FNAME_LEN)) !=
58!
2322
          0) {
2323
        mndReleaseDb(pMnode, pDb);
×
2324
        TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2325
      }
2326
      mndReleaseDb(pMnode, pDb);
58✔
2327
    } else {
2328
      while (1) {
16✔
2329
        SDbObj *pDb = NULL;
26✔
2330
        pIter = sdbFetch(pSdb, SDB_DB, pIter, (void **)&pDb);
26✔
2331
        if (pIter == NULL) break;
26✔
2332
        int32_t len = strlen(pDb->name) + 1;
16✔
2333
        if ((code = taosHashPut(pNewUser->readDbs, pDb->name, len, pDb->name, TSDB_DB_FNAME_LEN)) != 0) {
16!
2334
          sdbRelease(pSdb, pDb);
×
2335
          sdbCancelFetch(pSdb, pIter);
×
2336
          TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2337
        }
2338
        sdbRelease(pSdb, pDb);
16✔
2339
      }
2340
    }
2341
  }
2342

2343
  if (ALTER_USER_ADD_WRITE_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,107✔
2344
      ALTER_USER_ADD_ALL_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,042!
2345
    if (strcmp(pAlterReq->objname, "1.*") != 0) {
65✔
2346
      int32_t len = strlen(pAlterReq->objname) + 1;
56✔
2347
      SDbObj *pDb = mndAcquireDb(pMnode, pAlterReq->objname);
56✔
2348
      if (pDb == NULL) {
56✔
2349
        mndReleaseDb(pMnode, pDb);
1✔
2350
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);  // TODO: refactor the terrno to code
1!
2351
      }
2352
      if ((code = taosHashPut(pNewUser->writeDbs, pAlterReq->objname, len, pAlterReq->objname, TSDB_DB_FNAME_LEN)) !=
55!
2353
          0) {
2354
        mndReleaseDb(pMnode, pDb);
×
2355
        TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2356
      }
2357
      mndReleaseDb(pMnode, pDb);
55✔
2358
    } else {
2359
      while (1) {
15✔
2360
        SDbObj *pDb = NULL;
24✔
2361
        pIter = sdbFetch(pSdb, SDB_DB, pIter, (void **)&pDb);
24✔
2362
        if (pIter == NULL) break;
24✔
2363
        int32_t len = strlen(pDb->name) + 1;
15✔
2364
        if ((code = taosHashPut(pNewUser->writeDbs, pDb->name, len, pDb->name, TSDB_DB_FNAME_LEN)) != 0) {
15!
2365
          sdbRelease(pSdb, pDb);
×
2366
          sdbCancelFetch(pSdb, pIter);
×
2367
          TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2368
        }
2369
        sdbRelease(pSdb, pDb);
15✔
2370
      }
2371
    }
2372
  }
2373

2374
  if (ALTER_USER_DEL_READ_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,106✔
2375
      ALTER_USER_DEL_ALL_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,057!
2376
    if (strcmp(pAlterReq->objname, "1.*") != 0) {
49✔
2377
      int32_t len = strlen(pAlterReq->objname) + 1;
39✔
2378
      SDbObj *pDb = mndAcquireDb(pMnode, pAlterReq->objname);
39✔
2379
      if (pDb == NULL) {
39✔
2380
        mndReleaseDb(pMnode, pDb);
1✔
2381
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);  // TODO: refactor the terrno to code
1!
2382
      }
2383
      code = taosHashRemove(pNewUser->readDbs, pAlterReq->objname, len);
38✔
2384
      if (code < 0) {
38!
2385
        mError("read db:%s, failed to remove db:%s since %s", pNewUser->user, pAlterReq->objname, terrstr());
×
2386
      }
2387
      mndReleaseDb(pMnode, pDb);
38✔
2388
    } else {
2389
      taosHashClear(pNewUser->readDbs);
10✔
2390
    }
2391
  }
2392

2393
  if (ALTER_USER_DEL_WRITE_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105✔
2394
      ALTER_USER_DEL_ALL_DB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,060!
2395
    if (strcmp(pAlterReq->objname, "1.*") != 0) {
45✔
2396
      int32_t len = strlen(pAlterReq->objname) + 1;
34✔
2397
      SDbObj *pDb = mndAcquireDb(pMnode, pAlterReq->objname);
34✔
2398
      if (pDb == NULL) {
34!
2399
        mndReleaseDb(pMnode, pDb);
×
2400
        TAOS_CHECK_GOTO(terrno, &lino, _OVER);  // TODO: refactor the terrno to code
×
2401
      }
2402
      code = taosHashRemove(pNewUser->writeDbs, pAlterReq->objname, len);
34✔
2403
      if (code < 0) {
34!
2404
        mError("user:%s, failed to remove db:%s since %s", pNewUser->user, pAlterReq->objname, terrstr());
×
2405
      }
2406
      mndReleaseDb(pMnode, pDb);
34✔
2407
    } else {
2408
      taosHashClear(pNewUser->writeDbs);
11✔
2409
    }
2410
  }
2411

2412
  SHashObj *pReadTbs = pNewUser->readTbs;
1,105✔
2413
  SHashObj *pWriteTbs = pNewUser->writeTbs;
1,105✔
2414
  SHashObj *pAlterTbs = pNewUser->alterTbs;
1,105✔
2415

2416
#ifdef TD_ENTERPRISE
2417
  if (pAlterReq->isView) {
1,105✔
2418
    pReadTbs = pNewUser->readViews;
31✔
2419
    pWriteTbs = pNewUser->writeViews;
31✔
2420
    pAlterTbs = pNewUser->alterViews;
31✔
2421
  }
2422
#endif
2423

2424
  if (ALTER_USER_ADD_READ_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105✔
2425
      ALTER_USER_ADD_ALL_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
650!
2426
    TAOS_CHECK_GOTO(mndTablePriviledge(pMnode, pReadTbs, pNewUser->useDbs, pAlterReq, pSdb), &lino, _OVER);
455!
2427
  }
2428

2429
  if (ALTER_USER_ADD_WRITE_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105✔
2430
      ALTER_USER_ADD_ALL_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
657!
2431
    TAOS_CHECK_GOTO(mndTablePriviledge(pMnode, pWriteTbs, pNewUser->useDbs, pAlterReq, pSdb), &lino, _OVER);
448!
2432
  }
2433

2434
  if (ALTER_USER_ADD_ALTER_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105✔
2435
      ALTER_USER_ADD_ALL_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,079!
2436
    TAOS_CHECK_GOTO(mndTablePriviledge(pMnode, pAlterTbs, pNewUser->useDbs, pAlterReq, pSdb), &lino, _OVER);
26!
2437
  }
2438

2439
  if (ALTER_USER_DEL_READ_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105✔
2440
      ALTER_USER_DEL_ALL_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,086!
2441
    TAOS_CHECK_GOTO(mndRemoveTablePriviledge(pMnode, pReadTbs, pNewUser->useDbs, pAlterReq, pSdb), &lino, _OVER);
19!
2442
  }
2443

2444
  if (ALTER_USER_DEL_WRITE_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105✔
2445
      ALTER_USER_DEL_ALL_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,092!
2446
    TAOS_CHECK_GOTO(mndRemoveTablePriviledge(pMnode, pWriteTbs, pNewUser->useDbs, pAlterReq, pSdb), &lino, _OVER);
13!
2447
  }
2448

2449
  if (ALTER_USER_DEL_ALTER_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName) ||
1,105!
2450
      ALTER_USER_DEL_ALL_TB_PRIV(pAlterReq->alterType, pAlterReq->privileges, pAlterReq->tabName)) {
1,101!
2451
    TAOS_CHECK_GOTO(mndRemoveTablePriviledge(pMnode, pAlterTbs, pNewUser->useDbs, pAlterReq, pSdb), &lino, _OVER);
4!
2452
  }
2453

2454
#ifdef USE_TOPIC
2455
  if (ALTER_USER_ADD_SUBSCRIBE_TOPIC_PRIV(pAlterReq->alterType, pAlterReq->privileges)) {
1,105✔
2456
    int32_t      len = strlen(pAlterReq->objname) + 1;
17✔
2457
    SMqTopicObj *pTopic = NULL;
17✔
2458
    if ((code = mndAcquireTopic(pMnode, pAlterReq->objname, &pTopic)) != 0) {
17!
2459
      mndReleaseTopic(pMnode, pTopic);
×
2460
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2461
    }
2462
    if ((code = taosHashPut(pNewUser->topics, pTopic->name, len, pTopic->name, TSDB_TOPIC_FNAME_LEN)) != 0) {
17!
2463
      mndReleaseTopic(pMnode, pTopic);
×
2464
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
2465
    }
2466
    mndReleaseTopic(pMnode, pTopic);
17✔
2467
  }
2468

2469
  if (ALTER_USER_DEL_SUBSCRIBE_TOPIC_PRIV(pAlterReq->alterType, pAlterReq->privileges)) {
1,105✔
2470
    int32_t      len = strlen(pAlterReq->objname) + 1;
12✔
2471
    SMqTopicObj *pTopic = NULL;
12✔
2472
    if ((code = mndAcquireTopic(pMnode, pAlterReq->objname, &pTopic)) != 0) {
12✔
2473
      mndReleaseTopic(pMnode, pTopic);
1✔
2474
      TAOS_CHECK_GOTO(code, &lino, _OVER);
1!
2475
    }
2476
    code = taosHashRemove(pNewUser->topics, pAlterReq->objname, len);
11✔
2477
    if (code < 0) {
11!
2478
      mError("user:%s, failed to remove topic:%s since %s", pNewUser->user, pAlterReq->objname, tstrerror(code));
×
2479
    }
2480
    mndReleaseTopic(pMnode, pTopic);
11✔
2481
  }
2482
#endif
2483
_OVER:
1,093✔
2484
  if (code < 0) {
1,115✔
2485
    mError("user:%s, failed to alter user privileges at line %d since %s", pAlterReq->user, lino, tstrerror(code));
11!
2486
  }
2487
  TAOS_RETURN(code);
1,115✔
2488
}
2489

2490
static int32_t mndProcessAlterUserReq(SRpcMsg *pReq) {
1,304✔
2491
  SMnode       *pMnode = pReq->info.node;
1,304✔
2492
  SSdb         *pSdb = pMnode->pSdb;
1,304✔
2493
  void         *pIter = NULL;
1,304✔
2494
  int32_t       code = 0;
1,304✔
2495
  int32_t       lino = 0;
1,304✔
2496
  SUserObj     *pUser = NULL;
1,304✔
2497
  SUserObj     *pOperUser = NULL;
1,304✔
2498
  SUserObj      newUser = {0};
1,304✔
2499
  SAlterUserReq alterReq = {0};
1,304✔
2500

2501
  TAOS_CHECK_GOTO(tDeserializeSAlterUserReq(pReq->pCont, pReq->contLen, &alterReq), &lino, _OVER);
1,304!
2502

2503
  mInfo("user:%s, start to alter", alterReq.user);
1,304!
2504

2505
  if (alterReq.user[0] == 0) {
1,304!
2506
    TAOS_CHECK_GOTO(TSDB_CODE_MND_INVALID_USER_FORMAT, &lino, _OVER);
×
2507
  }
2508
  if (alterReq.passIsMd5 == 0) {
1,304✔
2509
    if (TSDB_ALTER_USER_PASSWD == alterReq.alterType) {
1,259!
2510
      int32_t len = strlen(alterReq.pass);
×
2511
      if (mndCheckPasswordMinLen(alterReq.pass, len) != 0) {
×
2512
        TAOS_CHECK_GOTO(TSDB_CODE_PAR_PASSWD_TOO_SHORT_OR_EMPTY, &lino, _OVER);
×
2513
      }
2514
      if (mndCheckPasswordMaxLen(alterReq.pass, len) != 0) {
×
2515
        TAOS_CHECK_GOTO(TSDB_CODE_PAR_NAME_OR_PASSWD_TOO_LONG, &lino, _OVER);
×
2516
      }
2517
      if (mndCheckPasswordFmt(alterReq.pass, len) != 0) {
×
2518
        TAOS_CHECK_GOTO(TSDB_CODE_MND_INVALID_PASS_FORMAT, &lino, _OVER);
×
2519
      }
2520
    }
2521
  }
2522

2523
  TAOS_CHECK_GOTO(mndAcquireUser(pMnode, alterReq.user, &pUser), &lino, _OVER);
1,304✔
2524

2525
  (void)mndAcquireUser(pMnode, pReq->info.conn.user, &pOperUser);
1,281✔
2526
  if (pOperUser == NULL) {
1,281!
2527
    TAOS_CHECK_GOTO(TSDB_CODE_MND_NO_USER_FROM_CONN, &lino, _OVER);
×
2528
  }
2529

2530
  TAOS_CHECK_GOTO(mndCheckAlterUserPrivilege(pOperUser, pUser, &alterReq), &lino, _OVER);
1,281✔
2531

2532
  TAOS_CHECK_GOTO(mndUserDupObj(pUser, &newUser), &lino, _OVER);
1,209!
2533

2534
  if (alterReq.alterType == TSDB_ALTER_USER_PASSWD) {
1,209✔
2535
    if (alterReq.passIsMd5 == 1) {
42!
2536
      (void)memcpy(newUser.pass, alterReq.pass, TSDB_PASSWORD_LEN);
42✔
2537
    } else {
2538
      taosEncryptPass_c((uint8_t *)alterReq.pass, strlen(alterReq.pass), newUser.pass);
×
2539
    }
2540

2541
    if (0 != strncmp(pUser->pass, newUser.pass, TSDB_PASSWORD_LEN)) {
42✔
2542
      ++newUser.passVersion;
37✔
2543
    }
2544
  }
2545

2546
  if (alterReq.alterType == TSDB_ALTER_USER_SUPERUSER) {
1,209!
2547
    newUser.superUser = alterReq.superUser;
×
2548
  }
2549

2550
  if (alterReq.alterType == TSDB_ALTER_USER_ENABLE) {
1,209✔
2551
    newUser.enable = alterReq.enable;
11✔
2552
  }
2553

2554
  if (alterReq.alterType == TSDB_ALTER_USER_SYSINFO) {
1,209✔
2555
    newUser.sysInfo = alterReq.sysInfo;
20✔
2556
  }
2557

2558
  if (alterReq.alterType == TSDB_ALTER_USER_CREATEDB) {
1,209✔
2559
    newUser.createdb = alterReq.createdb;
19✔
2560
  }
2561

2562
  if (ALTER_USER_ADD_PRIVS(alterReq.alterType) || ALTER_USER_DEL_PRIVS(alterReq.alterType)) {
1,209✔
2563
    TAOS_CHECK_GOTO(mndProcessAlterUserPrivilegesReq(&alterReq, pMnode, &newUser), &lino, _OVER);
1,115✔
2564
  }
2565

2566
  if (alterReq.alterType == TSDB_ALTER_USER_ADD_WHITE_LIST) {
1,198✔
2567
    taosMemoryFreeClear(newUser.pIpWhiteListDual);
1!
2568

2569
    int32_t           num = pUser->pIpWhiteListDual->num + alterReq.numIpRanges;
1✔
2570
    int32_t           idx = pUser->pIpWhiteListDual->num;
1✔
2571
    SIpWhiteListDual *pNew = taosMemoryCalloc(1, sizeof(SIpWhiteListDual) + sizeof(SIpRange) * num);
1!
2572

2573
    if (pNew == NULL) {
1!
2574
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
2575
    }
2576

2577
    bool exist = false;
1✔
2578
    (void)memcpy(pNew->pIpRanges, pUser->pIpWhiteListDual->pIpRanges, sizeof(SIpRange) * idx);
1✔
2579
    for (int i = 0; i < alterReq.numIpRanges; i++) {
2✔
2580
      SIpRange range = {0};
1✔
2581
      if (alterReq.pIpDualRanges == NULL) {
1!
2582
        range.type = 0;
×
2583
        memcpy(&range.ipV4, &alterReq.pIpRanges[i], sizeof(SIpV4Range));
×
2584
      } else {
2585
        memcpy(&range, &alterReq.pIpDualRanges[i], sizeof(SIpRange));
1✔
2586
        range = alterReq.pIpDualRanges[i];
1✔
2587
      }
2588
      if (!isRangeInIpWhiteList(pUser->pIpWhiteListDual, &range)) {
1!
2589
        // already exist, just ignore;
2590
        (void)memcpy(&pNew->pIpRanges[idx], &range, sizeof(SIpRange));
1✔
2591
        idx++;
1✔
2592
        continue;
1✔
2593
      } else {
2594
        exist = true;
×
2595
      }
2596
    }
2597
    if (exist) {
1!
2598
      taosMemoryFree(pNew);
×
2599
      TAOS_CHECK_GOTO(TSDB_CODE_MND_USER_HOST_EXIST, &lino, _OVER);
×
2600
    }
2601
    pNew->num = idx;
1✔
2602
    newUser.pIpWhiteListDual = pNew;
1✔
2603
    newUser.ipWhiteListVer = pUser->ipWhiteListVer + 1;
1✔
2604

2605
    if (pNew->num > MND_MAX_USE_HOST) {
1!
2606
      TAOS_CHECK_GOTO(TSDB_CODE_MND_TOO_MANY_USER_HOST, &lino, _OVER);
×
2607
    }
2608
  }
2609
  if (alterReq.alterType == TSDB_ALTER_USER_DROP_WHITE_LIST) {
1,198✔
2610
    taosMemoryFreeClear(newUser.pIpWhiteListDual);
1!
2611

2612
    int32_t           num = pUser->pIpWhiteListDual->num;
1✔
2613
    bool              noexist = true;
1✔
2614
    bool              localHost = false;
1✔
2615
    SIpWhiteListDual *pNew = taosMemoryCalloc(1, sizeof(SIpWhiteListDual) + sizeof(SIpRange) * num);
1!
2616

2617
    if (pNew == NULL) {
1!
2618
      TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
2619
    }
2620

2621
    if (pUser->pIpWhiteListDual->num > 0) {
1!
2622
      int idx = 0;
1✔
2623
      for (int i = 0; i < pUser->pIpWhiteListDual->num; i++) {
3✔
2624
        SIpRange *oldRange = &pUser->pIpWhiteListDual->pIpRanges[i];
2✔
2625

2626
        bool found = false;
2✔
2627
        for (int j = 0; j < alterReq.numIpRanges; j++) {
4✔
2628
          SIpRange range = {0};
2✔
2629
          if (alterReq.pIpDualRanges == NULL) {
2!
2630
            SIpV4Range *trange = &alterReq.pIpRanges[j];
×
2631
            memcpy(&range.ipV4, trange, sizeof(SIpV4Range));
×
2632
          } else {
2633
            memcpy(&range, &alterReq.pIpDualRanges[j], sizeof(SIpRange));
2✔
2634
          }
2635

2636
          if (isDefaultRange(&range)) {
2!
2637
            localHost = true;
×
2638
            break;
×
2639
          }
2640
          if (isIpRangeEqual(oldRange, &range)) {
2!
2641
            found = true;
×
2642
            break;
×
2643
          }
2644
        }
2645
        if (localHost) break;
2!
2646

2647
        if (found == false) {
2!
2648
          (void)memcpy(&pNew->pIpRanges[idx], oldRange, sizeof(SIpRange));
2✔
2649
          idx++;
2✔
2650
        } else {
2651
          noexist = false;
×
2652
        }
2653
      }
2654
      pNew->num = idx;
1✔
2655
      newUser.pIpWhiteListDual = pNew;
1✔
2656
      newUser.ipWhiteListVer = pUser->ipWhiteListVer + 1;
1✔
2657

2658
    } else {
2659
      pNew->num = 0;
×
2660
      newUser.pIpWhiteListDual = pNew;
×
2661
      newUser.ipWhiteListVer = pUser->ipWhiteListVer + 1;
×
2662
    }
2663

2664
    if (localHost) {
1!
2665
      TAOS_CHECK_GOTO(TSDB_CODE_MND_USER_LOCAL_HOST_NOT_DROP, &lino, _OVER);
×
2666
    }
2667
    if (noexist) {
1!
2668
      TAOS_CHECK_GOTO(TSDB_CODE_MND_USER_HOST_NOT_EXIST, &lino, _OVER);
1!
2669
    }
2670
  }
2671

2672
  code = mndAlterUser(pMnode, pUser, &newUser, pReq);
1,197✔
2673
  if (code == 0) code = TSDB_CODE_ACTION_IN_PROGRESS;
1,197!
2674

2675
  if (alterReq.alterType == TSDB_ALTER_USER_PASSWD) {
1,197✔
2676
    char detail[1000] = {0};
42✔
2677
    (void)tsnprintf(detail, sizeof(detail),
42✔
2678
                    "alterType:%s, enable:%d, superUser:%d, sysInfo:%d, createdb:%d, tabName:%s, password:xxx",
2679
                    mndUserAuditTypeStr(alterReq.alterType), alterReq.enable, alterReq.superUser, alterReq.sysInfo,
42✔
2680
                    alterReq.createdb ? 1 : 0, alterReq.tabName);
42✔
2681
    auditRecord(pReq, pMnode->clusterId, "alterUser", "", alterReq.user, detail, strlen(detail));
42✔
2682
  } else if (alterReq.alterType == TSDB_ALTER_USER_SUPERUSER || alterReq.alterType == TSDB_ALTER_USER_ENABLE ||
1,155!
2683
             alterReq.alterType == TSDB_ALTER_USER_SYSINFO || alterReq.alterType == TSDB_ALTER_USER_CREATEDB) {
1,144✔
2684
    auditRecord(pReq, pMnode->clusterId, "alterUser", "", alterReq.user, alterReq.sql, alterReq.sqlLen);
50✔
2685
  } else if (ALTER_USER_ADD_READ_DB_PRIV(alterReq.alterType, alterReq.privileges, alterReq.tabName) ||
1,105✔
2686
             ALTER_USER_ADD_WRITE_DB_PRIV(alterReq.alterType, alterReq.privileges, alterReq.tabName) ||
1,037✔
2687
             ALTER_USER_ADD_ALL_DB_PRIV(alterReq.alterType, alterReq.privileges, alterReq.tabName) ||
1,010!
2688
             ALTER_USER_ADD_READ_TB_PRIV(alterReq.alterType, alterReq.privileges, alterReq.tabName) ||
1,010!
2689
             ALTER_USER_ADD_WRITE_TB_PRIV(alterReq.alterType, alterReq.privileges, alterReq.tabName) ||
555!
2690
             ALTER_USER_ADD_ALL_TB_PRIV(alterReq.alterType, alterReq.privileges, alterReq.tabName)) {
127!
2691
    if (strcmp(alterReq.objname, "1.*") != 0) {
978✔
2692
      SName name = {0};
964✔
2693
      TAOS_CHECK_GOTO(tNameFromString(&name, alterReq.objname, T_NAME_ACCT | T_NAME_DB), &lino, _OVER);
964!
2694
      auditRecord(pReq, pMnode->clusterId, "GrantPrivileges", name.dbname, alterReq.user, alterReq.sql,
964✔
2695
                  alterReq.sqlLen);
2696
    } else {
2697
      auditRecord(pReq, pMnode->clusterId, "GrantPrivileges", "", alterReq.user, alterReq.sql, alterReq.sqlLen);
14✔
2698
    }
2699
  } else if (ALTER_USER_ADD_SUBSCRIBE_TOPIC_PRIV(alterReq.alterType, alterReq.privileges)) {
127✔
2700
    auditRecord(pReq, pMnode->clusterId, "GrantPrivileges", alterReq.objname, alterReq.user, alterReq.sql,
17✔
2701
                alterReq.sqlLen);
2702
  } else if (ALTER_USER_DEL_SUBSCRIBE_TOPIC_PRIV(alterReq.alterType, alterReq.privileges)) {
110✔
2703
    auditRecord(pReq, pMnode->clusterId, "RevokePrivileges", alterReq.objname, alterReq.user, alterReq.sql,
11✔
2704
                alterReq.sqlLen);
2705
  } else {
2706
    if (strcmp(alterReq.objname, "1.*") != 0) {
99✔
2707
      SName name = {0};
83✔
2708
      TAOS_CHECK_GOTO(tNameFromString(&name, alterReq.objname, T_NAME_ACCT | T_NAME_DB), &lino, _OVER);
83✔
2709
      auditRecord(pReq, pMnode->clusterId, "RevokePrivileges", name.dbname, alterReq.user, alterReq.sql,
82✔
2710
                  alterReq.sqlLen);
2711
    } else {
2712
      auditRecord(pReq, pMnode->clusterId, "RevokePrivileges", "", alterReq.user, alterReq.sql, alterReq.sqlLen);
16✔
2713
    }
2714
  }
2715

2716
_OVER:
1,304✔
2717
  if (code < 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
1,304✔
2718
    mError("user:%s, failed to alter at line %d since %s", alterReq.user, lino, tstrerror(code));
108!
2719
  }
2720

2721
  tFreeSAlterUserReq(&alterReq);
1,304✔
2722
  mndReleaseUser(pMnode, pOperUser);
1,304✔
2723
  mndReleaseUser(pMnode, pUser);
1,304✔
2724
  mndUserFreeObj(&newUser);
1,304✔
2725

2726
  TAOS_RETURN(code);
1,304✔
2727
}
2728

2729
static int32_t mndDropUser(SMnode *pMnode, SRpcMsg *pReq, SUserObj *pUser) {
75✔
2730
  STrans *pTrans = mndTransCreate(pMnode, TRN_POLICY_ROLLBACK, TRN_CONFLICT_NOTHING, pReq, "drop-user");
75✔
2731
  if (pTrans == NULL) {
75!
2732
    mError("user:%s, failed to drop since %s", pUser->user, terrstr());
×
2733
    TAOS_RETURN(terrno);
×
2734
  }
2735
  mInfo("trans:%d, used to drop user:%s", pTrans->id, pUser->user);
75!
2736

2737
  SSdbRaw *pCommitRaw = mndUserActionEncode(pUser);
75✔
2738
  if (pCommitRaw == NULL || mndTransAppendCommitlog(pTrans, pCommitRaw) != 0) {
75!
2739
    mError("trans:%d, failed to append commit log since %s", pTrans->id, terrstr());
×
2740
    mndTransDrop(pTrans);
×
2741
    TAOS_RETURN(terrno);
×
2742
  }
2743
  if (sdbSetRawStatus(pCommitRaw, SDB_STATUS_DROPPED) < 0) {
75!
2744
    mndTransDrop(pTrans);
×
2745
    TAOS_RETURN(terrno);
×
2746
  }
2747

2748
  if (mndTransPrepare(pMnode, pTrans) != 0) {
75!
2749
    mError("trans:%d, failed to prepare since %s", pTrans->id, terrstr());
×
2750
    mndTransDrop(pTrans);
×
2751
    TAOS_RETURN(terrno);
×
2752
  }
2753
  (void)ipWhiteMgtRemove(pUser->user);
75✔
2754

2755
  mndTransDrop(pTrans);
75✔
2756
  TAOS_RETURN(0);
75✔
2757
}
2758

2759
static int32_t mndProcessDropUserReq(SRpcMsg *pReq) {
76✔
2760
  SMnode      *pMnode = pReq->info.node;
76✔
2761
  int32_t      code = 0;
76✔
2762
  int32_t      lino = 0;
76✔
2763
  SUserObj    *pUser = NULL;
76✔
2764
  SDropUserReq dropReq = {0};
76✔
2765

2766
  TAOS_CHECK_GOTO(tDeserializeSDropUserReq(pReq->pCont, pReq->contLen, &dropReq), &lino, _OVER);
76!
2767

2768
  mInfo("user:%s, start to drop", dropReq.user);
76!
2769
  TAOS_CHECK_GOTO(mndCheckOperPrivilege(pMnode, pReq->info.conn.user, MND_OPER_DROP_USER), &lino, _OVER);
76!
2770

2771
  if (dropReq.user[0] == 0) {
76!
2772
    TAOS_CHECK_GOTO(TSDB_CODE_MND_INVALID_USER_FORMAT, &lino, _OVER);
×
2773
  }
2774

2775
  TAOS_CHECK_GOTO(mndAcquireUser(pMnode, dropReq.user, &pUser), &lino, _OVER);
76✔
2776

2777
  TAOS_CHECK_GOTO(mndDropUser(pMnode, pReq, pUser), &lino, _OVER);
75!
2778
  if (code == 0) code = TSDB_CODE_ACTION_IN_PROGRESS;
75!
2779

2780
  auditRecord(pReq, pMnode->clusterId, "dropUser", "", dropReq.user, dropReq.sql, dropReq.sqlLen);
75✔
2781

2782
_OVER:
76✔
2783
  if (code < 0 && code != TSDB_CODE_ACTION_IN_PROGRESS) {
76!
2784
    mError("user:%s, failed to drop at line %d since %s", dropReq.user, lino, tstrerror(code));
1!
2785
  }
2786

2787
  mndReleaseUser(pMnode, pUser);
76✔
2788
  tFreeSDropUserReq(&dropReq);
76✔
2789
  TAOS_RETURN(code);
76✔
2790
}
2791

2792
static int32_t mndProcessGetUserAuthReq(SRpcMsg *pReq) {
21,957✔
2793
  SMnode         *pMnode = pReq->info.node;
21,957✔
2794
  int32_t         code = 0;
21,957✔
2795
  int32_t         lino = 0;
21,957✔
2796
  int32_t         contLen = 0;
21,957✔
2797
  void           *pRsp = NULL;
21,957✔
2798
  SUserObj       *pUser = NULL;
21,957✔
2799
  SGetUserAuthReq authReq = {0};
21,957✔
2800
  SGetUserAuthRsp authRsp = {0};
21,957✔
2801

2802
  TAOS_CHECK_EXIT(tDeserializeSGetUserAuthReq(pReq->pCont, pReq->contLen, &authReq));
21,957!
2803
  mTrace("user:%s, start to get auth", authReq.user);
21,957✔
2804

2805
  TAOS_CHECK_EXIT(mndAcquireUser(pMnode, authReq.user, &pUser));
21,957✔
2806

2807
  TAOS_CHECK_EXIT(mndSetUserAuthRsp(pMnode, pUser, &authRsp));
21,953!
2808

2809
  contLen = tSerializeSGetUserAuthRsp(NULL, 0, &authRsp);
21,953✔
2810
  if (contLen < 0) {
21,953!
2811
    TAOS_CHECK_EXIT(contLen);
×
2812
  }
2813
  pRsp = rpcMallocCont(contLen);
21,953✔
2814
  if (pRsp == NULL) {
21,953!
2815
    TAOS_CHECK_EXIT(terrno);
×
2816
  }
2817

2818
  contLen = tSerializeSGetUserAuthRsp(pRsp, contLen, &authRsp);
21,953✔
2819
  if (contLen < 0) {
21,953!
2820
    TAOS_CHECK_EXIT(contLen);
×
2821
  }
2822

2823
_exit:
21,953✔
2824
  mndReleaseUser(pMnode, pUser);
21,957✔
2825
  tFreeSGetUserAuthRsp(&authRsp);
21,957✔
2826
  if (code < 0) {
21,957✔
2827
    mError("user:%s, failed to get auth at line %d since %s", authReq.user, lino, tstrerror(code));
4!
2828
    rpcFreeCont(pRsp);
4✔
2829
    pRsp = NULL;
4✔
2830
    contLen = 0;
4✔
2831
  }
2832
  pReq->info.rsp = pRsp;
21,957✔
2833
  pReq->info.rspLen = contLen;
21,957✔
2834
  pReq->code = code;
21,957✔
2835

2836
  TAOS_RETURN(code);
21,957✔
2837
}
2838

2839
static int32_t mndRetrieveUsers(SRpcMsg *pReq, SShowObj *pShow, SSDataBlock *pBlock, int32_t rows) {
60✔
2840
  SMnode   *pMnode = pReq->info.node;
60✔
2841
  SSdb     *pSdb = pMnode->pSdb;
60✔
2842
  int32_t   code = 0;
60✔
2843
  int32_t   lino = 0;
60✔
2844
  int32_t   numOfRows = 0;
60✔
2845
  SUserObj *pUser = NULL;
60✔
2846
  int32_t   cols = 0;
60✔
2847
  int8_t    flag = 0;
60✔
2848
  char     *pWrite = NULL;
60✔
2849
  char     *buf = NULL;
60✔
2850
  char     *varstr = NULL;
60✔
2851

2852
  while (numOfRows < rows) {
210!
2853
    pShow->pIter = sdbFetch(pSdb, SDB_USER, pShow->pIter, (void **)&pUser);
210✔
2854
    if (pShow->pIter == NULL) break;
210✔
2855

2856
    cols = 0;
150✔
2857
    SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2858
    char             name[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
150✔
2859
    STR_WITH_MAXSIZE_TO_VARSTR(name, pUser->user, pShow->pMeta->pSchemas[cols].bytes);
150✔
2860
    COL_DATA_SET_VAL_GOTO((const char *)name, false, pUser, _exit);
150!
2861

2862
    cols++;
150✔
2863
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2864
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->superUser, false, pUser, _exit);
150!
2865

2866
    cols++;
150✔
2867
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2868
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->enable, false, pUser, _exit);
150!
2869

2870
    cols++;
150✔
2871
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2872
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->sysInfo, false, pUser, _exit);
150!
2873

2874
    cols++;
150✔
2875
    flag = pUser->createdb ? 1 : 0;
150✔
2876
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2877
    COL_DATA_SET_VAL_GOTO((const char *)&flag, false, pUser, _exit);
150!
2878

2879
    cols++;
150✔
2880
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2881
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->createdTime, false, pUser, _exit);
150!
2882

2883
    cols++;
150✔
2884

2885
    int32_t tlen = convertIpWhiteListToStr(pUser->pIpWhiteListDual, &buf);
150✔
2886
    if (tlen != 0) {
150!
2887
      TAOS_MEMORY_REALLOC(varstr, VARSTR_HEADER_SIZE + tlen);
150!
2888
      if (varstr == NULL) {
150!
2889
        sdbRelease(pSdb, pUser);
×
2890
        TAOS_CHECK_GOTO(terrno, &lino, _exit);
×
2891
      }
2892
      varDataSetLen(varstr, tlen);
150✔
2893
      (void)memcpy(varDataVal(varstr), buf, tlen);
150✔
2894

2895
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
150✔
2896
      COL_DATA_SET_VAL_GOTO((const char *)varstr, false, pUser, _exit);
150!
2897

2898
      taosMemoryFreeClear(buf);
150!
2899
    } else {
2900
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2901
      COL_DATA_SET_VAL_GOTO((const char *)NULL, true, pUser, _exit);
×
2902
    }
2903

2904
    numOfRows++;
150✔
2905
    sdbRelease(pSdb, pUser);
150✔
2906
  }
2907

2908
  pShow->numOfRows += numOfRows;
60✔
2909
_exit:
60✔
2910
  taosMemoryFreeClear(buf);
60!
2911
  taosMemoryFreeClear(varstr);
60!
2912
  if (code < 0) {
60!
2913
    uError("%s failed at line %d since %s", __func__, lino, tstrerror(code));
×
2914
    TAOS_RETURN(code);
×
2915
  }
2916
  return numOfRows;
60✔
2917
}
2918

2919
static int32_t mndRetrieveUsersFull(SRpcMsg *pReq, SShowObj *pShow, SSDataBlock *pBlock, int32_t rows) {
×
2920
  int32_t numOfRows = 0;
×
2921
#ifdef TD_ENTERPRISE
2922
  SMnode   *pMnode = pReq->info.node;
×
2923
  SSdb     *pSdb = pMnode->pSdb;
×
2924
  SUserObj *pUser = NULL;
×
2925
  int32_t   code = 0;
×
2926
  int32_t   lino = 0;
×
2927
  int32_t   cols = 0;
×
2928
  int8_t    flag = 0;
×
2929
  char     *pWrite = NULL;
×
2930
  char     *buf = NULL;
×
2931
  char     *varstr = NULL;
×
2932

2933
  while (numOfRows < rows) {
×
2934
    pShow->pIter = sdbFetch(pSdb, SDB_USER, pShow->pIter, (void **)&pUser);
×
2935
    if (pShow->pIter == NULL) break;
×
2936

2937
    cols = 0;
×
2938
    SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2939
    char             name[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
×
2940
    STR_WITH_MAXSIZE_TO_VARSTR(name, pUser->user, pShow->pMeta->pSchemas[cols].bytes);
×
2941
    COL_DATA_SET_VAL_GOTO((const char *)name, false, pUser, _exit);
×
2942

2943
    cols++;
×
2944
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2945
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->superUser, false, pUser, _exit);
×
2946

2947
    cols++;
×
2948
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2949
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->enable, false, pUser, _exit);
×
2950

2951
    cols++;
×
2952
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2953
    COL_DATA_SET_VAL_GOTO((const char *)&pUser->sysInfo, false, pUser, _exit);
×
2954

2955
    cols++;
×
2956
    flag = pUser->createdb ? 1 : 0;
×
2957
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2958
    COL_DATA_SET_VAL_GOTO((const char *)&flag, false, pUser, _exit);
×
2959

2960
    // mInfo("pUser->pass:%s", pUser->pass);
2961
    cols++;
×
2962
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2963
    char pass[TSDB_PASSWORD_LEN + VARSTR_HEADER_SIZE] = {0};
×
2964
    STR_WITH_MAXSIZE_TO_VARSTR(pass, pUser->pass, pShow->pMeta->pSchemas[cols].bytes);
×
2965
    COL_DATA_SET_VAL_GOTO((const char *)pass, false, pUser, _exit);
×
2966

2967
    cols++;
×
2968

2969
    int32_t tlen = convertIpWhiteListToStr(pUser->pIpWhiteListDual, &buf);
×
2970
    if (tlen != 0) {
×
2971
      TAOS_MEMORY_REALLOC(varstr, VARSTR_HEADER_SIZE + tlen);
×
2972
      if (varstr == NULL) {
×
2973
        sdbRelease(pSdb, pUser);
×
2974
        TAOS_CHECK_GOTO(TSDB_CODE_OUT_OF_MEMORY, &lino, _exit);
×
2975
      }
2976
      varDataSetLen(varstr, tlen);
×
2977
      (void)memcpy(varDataVal(varstr), buf, tlen);
×
2978

2979
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2980
      COL_DATA_SET_VAL_GOTO((const char *)varstr, false, pUser, _exit);
×
2981

2982
      taosMemoryFreeClear(buf);
×
2983
    } else {
2984
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols);
×
2985
      COL_DATA_SET_VAL_GOTO((const char *)NULL, true, pUser, _exit);
×
2986
    }
2987

2988
    numOfRows++;
×
2989
    sdbRelease(pSdb, pUser);
×
2990
  }
2991

2992
  pShow->numOfRows += numOfRows;
×
2993
_exit:
×
2994
  taosMemoryFreeClear(buf);
×
2995
  taosMemoryFreeClear(varstr);
×
2996
  if (code < 0) {
×
2997
    uError("%s failed at line %d since %s", __func__, lino, tstrerror(code));
×
2998
    TAOS_RETURN(code);
×
2999
  }
3000
#endif
3001
  return numOfRows;
×
3002
}
3003

3004
static void mndCancelGetNextUser(SMnode *pMnode, void *pIter) {
×
3005
  SSdb *pSdb = pMnode->pSdb;
×
3006
  sdbCancelFetchByType(pSdb, pIter, SDB_USER);
×
3007
}
×
3008

3009
static int32_t mndLoopHash(SHashObj *hash, char *priType, SSDataBlock *pBlock, int32_t *pNumOfRows, SSdb *pSdb,
882✔
3010
                           SUserObj *pUser, SShowObj *pShow, char **condition, char **sql) {
3011
  char   *value = taosHashIterate(hash, NULL);
882✔
3012
  char   *user = pUser->user;
882✔
3013
  int32_t code = 0;
882✔
3014
  int32_t lino = 0;
882✔
3015
  int32_t cols = 0;
882✔
3016
  int32_t numOfRows = *pNumOfRows;
882✔
3017

3018
  while (value != NULL) {
914✔
3019
    cols = 0;
32✔
3020
    char userName[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
32✔
3021
    STR_WITH_MAXSIZE_TO_VARSTR(userName, user, pShow->pMeta->pSchemas[cols].bytes);
32✔
3022
    SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
32✔
3023
    COL_DATA_SET_VAL_GOTO((const char *)userName, false, NULL, _exit);
32!
3024

3025
    char privilege[20] = {0};
32✔
3026
    STR_WITH_MAXSIZE_TO_VARSTR(privilege, priType, pShow->pMeta->pSchemas[cols].bytes);
32✔
3027
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
32✔
3028
    COL_DATA_SET_VAL_GOTO((const char *)privilege, false, NULL, _exit);
32!
3029

3030
    size_t keyLen = 0;
32✔
3031
    void  *key = taosHashGetKey(value, &keyLen);
32✔
3032

3033
    char dbName[TSDB_DB_NAME_LEN] = {0};
32✔
3034
    (void)mndExtractShortDbNameFromStbFullName(key, dbName);
32✔
3035
    char dbNameContent[TSDB_DB_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
32✔
3036
    STR_WITH_MAXSIZE_TO_VARSTR(dbNameContent, dbName, pShow->pMeta->pSchemas[cols].bytes);
32✔
3037
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
32✔
3038
    COL_DATA_SET_VAL_GOTO((const char *)dbNameContent, false, NULL, _exit);
32!
3039

3040
    char tableName[TSDB_TABLE_NAME_LEN] = {0};
32✔
3041
    mndExtractTbNameFromStbFullName(key, tableName, TSDB_TABLE_NAME_LEN);
32✔
3042
    char tableNameContent[TSDB_TABLE_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
32✔
3043
    STR_WITH_MAXSIZE_TO_VARSTR(tableNameContent, tableName, pShow->pMeta->pSchemas[cols].bytes);
32✔
3044
    pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
32✔
3045
    COL_DATA_SET_VAL_GOTO((const char *)tableNameContent, false, NULL, _exit);
32!
3046

3047
    if (strcmp("t", value) != 0 && strcmp("v", value) != 0) {
40✔
3048
      SNode  *pAst = NULL;
8✔
3049
      int32_t sqlLen = 0;
8✔
3050
      size_t  bufSz = strlen(value) + 1;
8✔
3051
      if (bufSz < 6) bufSz = 6;
8!
3052
      TAOS_MEMORY_REALLOC(*sql, bufSz);
8!
3053
      if (*sql == NULL) {
8!
3054
        code = terrno;
×
3055
        goto _exit;
×
3056
      }
3057
      TAOS_MEMORY_REALLOC(*condition, TSDB_PRIVILEDGE_CONDITION_LEN + VARSTR_HEADER_SIZE);
8!
3058
      if ((*condition) == NULL) {
8!
3059
        code = terrno;
×
3060
        goto _exit;
×
3061
      }
3062

3063
      if (nodesStringToNode(value, &pAst) == 0) {
8!
3064
        if (nodesNodeToSQLFormat(pAst, *sql, bufSz, &sqlLen, true) != 0) {
8!
3065
          sqlLen = tsnprintf(*sql, bufSz, "error");
×
3066
        }
3067
        nodesDestroyNode(pAst);
8✔
3068
      }
3069

3070
      if (sqlLen == 0) {
8!
3071
        sqlLen = tsnprintf(*sql, bufSz, "error");
×
3072
      }
3073

3074
      STR_WITH_MAXSIZE_TO_VARSTR((*condition), (*sql), pShow->pMeta->pSchemas[cols].bytes);
8✔
3075

3076
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
8✔
3077
      COL_DATA_SET_VAL_GOTO((const char *)(*condition), false, NULL, _exit);
8!
3078

3079
      char notes[2] = {0};
8✔
3080
      STR_WITH_MAXSIZE_TO_VARSTR(notes, "", sizeof(notes));
8✔
3081
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
8✔
3082
      COL_DATA_SET_VAL_GOTO((const char *)notes, false, NULL, _exit);
8!
3083
    } else {
3084
      TAOS_MEMORY_REALLOC(*condition, TSDB_PRIVILEDGE_CONDITION_LEN + VARSTR_HEADER_SIZE);
24!
3085
      if ((*condition) == NULL) {
24!
3086
        code = terrno;
×
3087
        goto _exit;
×
3088
      }
3089
      STR_WITH_MAXSIZE_TO_VARSTR((*condition), "", pShow->pMeta->pSchemas[cols].bytes);
24✔
3090
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
24✔
3091
      COL_DATA_SET_VAL_GOTO((const char *)(*condition), false, NULL, _exit);
24!
3092

3093
      char notes[64 + VARSTR_HEADER_SIZE] = {0};
24✔
3094
      STR_WITH_MAXSIZE_TO_VARSTR(notes, value[0] == 'v' ? "view" : "", sizeof(notes));
24✔
3095
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
24✔
3096
      COL_DATA_SET_VAL_GOTO((const char *)notes, false, NULL, _exit);
24!
3097
    }
3098

3099
    numOfRows++;
32✔
3100
    value = taosHashIterate(hash, value);
32✔
3101
  }
3102
  *pNumOfRows = numOfRows;
882✔
3103
_exit:
882✔
3104
  if (code < 0) {
882!
3105
    uError("%s failed at line %d since %s", __func__, lino, tstrerror(code));
×
3106
    sdbRelease(pSdb, pUser);
×
3107
  }
3108
  TAOS_RETURN(code);
882✔
3109
}
3110

3111
static int32_t mndRetrievePrivileges(SRpcMsg *pReq, SShowObj *pShow, SSDataBlock *pBlock, int32_t rows) {
49✔
3112
  int32_t   code = 0;
49✔
3113
  int32_t   lino = 0;
49✔
3114
  SMnode   *pMnode = pReq->info.node;
49✔
3115
  SSdb     *pSdb = pMnode->pSdb;
49✔
3116
  int32_t   numOfRows = 0;
49✔
3117
  SUserObj *pUser = NULL;
49✔
3118
  int32_t   cols = 0;
49✔
3119
  char     *pWrite = NULL;
49✔
3120
  char     *condition = NULL;
49✔
3121
  char     *sql = NULL;
49✔
3122

3123
  bool fetchNextUser = pShow->restore ? false : true;
49✔
3124
  pShow->restore = false;
49✔
3125

3126
  while (numOfRows < rows) {
196!
3127
    if (fetchNextUser) {
196!
3128
      pShow->pIter = sdbFetch(pSdb, SDB_USER, pShow->pIter, (void **)&pUser);
196✔
3129
      if (pShow->pIter == NULL) break;
196✔
3130
    } else {
3131
      fetchNextUser = true;
×
3132
      void *pKey = taosHashGetKey(pShow->pIter, NULL);
×
3133
      pUser = sdbAcquire(pSdb, SDB_USER, pKey);
×
3134
      if (!pUser) {
×
3135
        continue;
×
3136
      }
3137
    }
3138

3139
    int32_t numOfReadDbs = taosHashGetSize(pUser->readDbs);
147✔
3140
    int32_t numOfWriteDbs = taosHashGetSize(pUser->writeDbs);
147✔
3141
    int32_t numOfTopics = taosHashGetSize(pUser->topics);
147✔
3142
    int32_t numOfReadTbs = taosHashGetSize(pUser->readTbs);
147✔
3143
    int32_t numOfWriteTbs = taosHashGetSize(pUser->writeTbs);
147✔
3144
    int32_t numOfAlterTbs = taosHashGetSize(pUser->alterTbs);
147✔
3145
    int32_t numOfReadViews = taosHashGetSize(pUser->readViews);
147✔
3146
    int32_t numOfWriteViews = taosHashGetSize(pUser->writeViews);
147✔
3147
    int32_t numOfAlterViews = taosHashGetSize(pUser->alterViews);
147✔
3148
    if (numOfRows + numOfReadDbs + numOfWriteDbs + numOfTopics + numOfReadTbs + numOfWriteTbs + numOfAlterTbs +
147✔
3149
            numOfReadViews + numOfWriteViews + numOfAlterViews >=
147!
3150
        rows) {
3151
      mInfo(
×
3152
          "will restore. current num of rows: %d, read dbs %d, write dbs %d, topics %d, read tables %d, write tables "
3153
          "%d, alter tables %d, read views %d, write views %d, alter views %d",
3154
          numOfRows, numOfReadDbs, numOfWriteDbs, numOfTopics, numOfReadTbs, numOfWriteTbs, numOfAlterTbs,
3155
          numOfReadViews, numOfWriteViews, numOfAlterViews);
3156
      pShow->restore = true;
×
3157
      sdbRelease(pSdb, pUser);
×
3158
      break;
×
3159
    }
3160

3161
    if (pUser->superUser) {
147✔
3162
      cols = 0;
49✔
3163
      char userName[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
49✔
3164
      STR_WITH_MAXSIZE_TO_VARSTR(userName, pUser->user, pShow->pMeta->pSchemas[cols].bytes);
49✔
3165
      SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
49✔
3166
      COL_DATA_SET_VAL_GOTO((const char *)userName, false, pUser, _exit);
49!
3167

3168
      char privilege[20] = {0};
49✔
3169
      STR_WITH_MAXSIZE_TO_VARSTR(privilege, "all", pShow->pMeta->pSchemas[cols].bytes);
49✔
3170
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
49✔
3171
      COL_DATA_SET_VAL_GOTO((const char *)privilege, false, pUser, _exit);
49!
3172

3173
      char objName[TSDB_DB_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
49✔
3174
      STR_WITH_MAXSIZE_TO_VARSTR(objName, "all", pShow->pMeta->pSchemas[cols].bytes);
49✔
3175
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
49✔
3176
      COL_DATA_SET_VAL_GOTO((const char *)objName, false, pUser, _exit);
49!
3177

3178
      char tableName[TSDB_TABLE_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
49✔
3179
      STR_WITH_MAXSIZE_TO_VARSTR(tableName, "", pShow->pMeta->pSchemas[cols].bytes);
49✔
3180
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
49✔
3181
      COL_DATA_SET_VAL_GOTO((const char *)tableName, false, pUser, _exit);
49!
3182

3183
      TAOS_MEMORY_REALLOC(condition, TSDB_PRIVILEDGE_CONDITION_LEN + VARSTR_HEADER_SIZE);
49!
3184
      if (condition == NULL) {
49!
3185
        sdbRelease(pSdb, pUser);
×
3186
        TAOS_CHECK_GOTO(terrno, &lino, _exit);
×
3187
      }
3188
      STR_WITH_MAXSIZE_TO_VARSTR(condition, "", pShow->pMeta->pSchemas[cols].bytes);
49✔
3189
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
49✔
3190
      COL_DATA_SET_VAL_GOTO((const char *)condition, false, pUser, _exit);
49!
3191

3192
      char notes[2] = {0};
49✔
3193
      STR_WITH_MAXSIZE_TO_VARSTR(notes, "", sizeof(notes));
49✔
3194
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
49✔
3195
      COL_DATA_SET_VAL_GOTO((const char *)notes, false, pUser, _exit);
49!
3196

3197
      numOfRows++;
49✔
3198
    }
3199

3200
    char *db = taosHashIterate(pUser->readDbs, NULL);
147✔
3201
    while (db != NULL) {
175✔
3202
      cols = 0;
28✔
3203
      char userName[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
28✔
3204
      STR_WITH_MAXSIZE_TO_VARSTR(userName, pUser->user, pShow->pMeta->pSchemas[cols].bytes);
28✔
3205
      SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3206
      COL_DATA_SET_VAL_GOTO((const char *)userName, false, pUser, _exit);
28!
3207

3208
      char privilege[20] = {0};
28✔
3209
      STR_WITH_MAXSIZE_TO_VARSTR(privilege, "read", pShow->pMeta->pSchemas[cols].bytes);
28✔
3210
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3211
      COL_DATA_SET_VAL_GOTO((const char *)privilege, false, pUser, _exit);
28!
3212

3213
      SName name = {0};
28✔
3214
      char  objName[TSDB_DB_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
28✔
3215
      code = tNameFromString(&name, db, T_NAME_ACCT | T_NAME_DB);
28✔
3216
      if (code < 0) {
28!
3217
        sdbRelease(pSdb, pUser);
×
3218
        TAOS_CHECK_GOTO(code, &lino, _exit);
×
3219
      }
3220
      (void)tNameGetDbName(&name, varDataVal(objName));
28✔
3221
      varDataSetLen(objName, strlen(varDataVal(objName)));
28✔
3222
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3223
      COL_DATA_SET_VAL_GOTO((const char *)objName, false, pUser, _exit);
28!
3224

3225
      char tableName[TSDB_TABLE_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
28✔
3226
      STR_WITH_MAXSIZE_TO_VARSTR(tableName, "", pShow->pMeta->pSchemas[cols].bytes);
28✔
3227
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3228
      COL_DATA_SET_VAL_GOTO((const char *)tableName, false, pUser, _exit);
28!
3229

3230
      TAOS_MEMORY_REALLOC(condition, TSDB_PRIVILEDGE_CONDITION_LEN + VARSTR_HEADER_SIZE);
28!
3231
      if (condition == NULL) {
28!
3232
        sdbRelease(pSdb, pUser);
×
3233
        TAOS_CHECK_GOTO(terrno, &lino, _exit);
×
3234
      }
3235
      STR_WITH_MAXSIZE_TO_VARSTR(condition, "", pShow->pMeta->pSchemas[cols].bytes);
28✔
3236
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3237
      COL_DATA_SET_VAL_GOTO((const char *)condition, false, pUser, _exit);
28!
3238

3239
      char notes[2] = {0};
28✔
3240
      STR_WITH_MAXSIZE_TO_VARSTR(notes, "", sizeof(notes));
28✔
3241
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3242
      COL_DATA_SET_VAL_GOTO((const char *)notes, false, pUser, _exit);
28!
3243

3244
      numOfRows++;
28✔
3245
      db = taosHashIterate(pUser->readDbs, db);
28✔
3246
    }
3247

3248
    db = taosHashIterate(pUser->writeDbs, NULL);
147✔
3249
    while (db != NULL) {
175✔
3250
      cols = 0;
28✔
3251
      char userName[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
28✔
3252
      STR_WITH_MAXSIZE_TO_VARSTR(userName, pUser->user, pShow->pMeta->pSchemas[cols].bytes);
28✔
3253
      SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3254
      COL_DATA_SET_VAL_GOTO((const char *)userName, false, pUser, _exit);
28!
3255

3256
      char privilege[20] = {0};
28✔
3257
      STR_WITH_MAXSIZE_TO_VARSTR(privilege, "write", pShow->pMeta->pSchemas[cols].bytes);
28✔
3258
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3259
      COL_DATA_SET_VAL_GOTO((const char *)privilege, false, pUser, _exit);
28!
3260

3261
      SName name = {0};
28✔
3262
      char  objName[TSDB_DB_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
28✔
3263
      code = tNameFromString(&name, db, T_NAME_ACCT | T_NAME_DB);
28✔
3264
      if (code < 0) {
28!
3265
        sdbRelease(pSdb, pUser);
×
3266
        TAOS_CHECK_GOTO(code, &lino, _exit);
×
3267
      }
3268
      (void)tNameGetDbName(&name, varDataVal(objName));
28✔
3269
      varDataSetLen(objName, strlen(varDataVal(objName)));
28✔
3270
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3271
      COL_DATA_SET_VAL_GOTO((const char *)objName, false, pUser, _exit);
28!
3272

3273
      char tableName[TSDB_TABLE_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
28✔
3274
      STR_WITH_MAXSIZE_TO_VARSTR(tableName, "", pShow->pMeta->pSchemas[cols].bytes);
28✔
3275
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3276
      COL_DATA_SET_VAL_GOTO((const char *)tableName, false, pUser, _exit);
28!
3277

3278
      TAOS_MEMORY_REALLOC(condition, TSDB_PRIVILEDGE_CONDITION_LEN + VARSTR_HEADER_SIZE);
28!
3279
      if (condition == NULL) {
28!
3280
        sdbRelease(pSdb, pUser);
×
3281
        TAOS_CHECK_GOTO(terrno, &lino, _exit);
×
3282
      }
3283
      STR_WITH_MAXSIZE_TO_VARSTR(condition, "", pShow->pMeta->pSchemas[cols].bytes);
28✔
3284
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3285
      COL_DATA_SET_VAL_GOTO((const char *)condition, false, pUser, _exit);
28!
3286

3287
      char notes[2] = {0};
28✔
3288
      STR_WITH_MAXSIZE_TO_VARSTR(notes, "", sizeof(notes));
28✔
3289
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
28✔
3290
      COL_DATA_SET_VAL_GOTO((const char *)notes, false, pUser, _exit);
28!
3291

3292
      numOfRows++;
28✔
3293
      db = taosHashIterate(pUser->writeDbs, db);
28✔
3294
    }
3295

3296
    TAOS_CHECK_EXIT(mndLoopHash(pUser->readTbs, "read", pBlock, &numOfRows, pSdb, pUser, pShow, &condition, &sql));
147!
3297

3298
    TAOS_CHECK_EXIT(mndLoopHash(pUser->writeTbs, "write", pBlock, &numOfRows, pSdb, pUser, pShow, &condition, &sql));
147!
3299

3300
    TAOS_CHECK_EXIT(mndLoopHash(pUser->alterTbs, "alter", pBlock, &numOfRows, pSdb, pUser, pShow, &condition, &sql));
147!
3301

3302
    TAOS_CHECK_EXIT(mndLoopHash(pUser->readViews, "read", pBlock, &numOfRows, pSdb, pUser, pShow, &condition, &sql));
147!
3303

3304
    TAOS_CHECK_EXIT(mndLoopHash(pUser->writeViews, "write", pBlock, &numOfRows, pSdb, pUser, pShow, &condition, &sql));
147!
3305

3306
    TAOS_CHECK_EXIT(mndLoopHash(pUser->alterViews, "alter", pBlock, &numOfRows, pSdb, pUser, pShow, &condition, &sql));
147!
3307

3308
    char *topic = taosHashIterate(pUser->topics, NULL);
147✔
3309
    while (topic != NULL) {
156✔
3310
      cols = 0;
9✔
3311
      char userName[TSDB_USER_LEN + VARSTR_HEADER_SIZE] = {0};
9✔
3312
      STR_WITH_MAXSIZE_TO_VARSTR(userName, pUser->user, pShow->pMeta->pSchemas[cols].bytes);
9✔
3313
      SColumnInfoData *pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
9✔
3314
      COL_DATA_SET_VAL_GOTO((const char *)userName, false, pUser, _exit);
9!
3315

3316
      char privilege[20] = {0};
9✔
3317
      STR_WITH_MAXSIZE_TO_VARSTR(privilege, "subscribe", pShow->pMeta->pSchemas[cols].bytes);
9✔
3318
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
9✔
3319
      COL_DATA_SET_VAL_GOTO((const char *)privilege, false, pUser, _exit);
9!
3320

3321
      char topicName[TSDB_TOPIC_NAME_LEN + VARSTR_HEADER_SIZE + 5] = {0};
9✔
3322
      tstrncpy(varDataVal(topicName), mndGetDbStr(topic), TSDB_TOPIC_NAME_LEN - 2);
9✔
3323
      varDataSetLen(topicName, strlen(varDataVal(topicName)));
9✔
3324
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
9✔
3325
      COL_DATA_SET_VAL_GOTO((const char *)topicName, false, pUser, _exit);
9!
3326

3327
      char tableName[TSDB_TABLE_NAME_LEN + VARSTR_HEADER_SIZE] = {0};
9✔
3328
      STR_WITH_MAXSIZE_TO_VARSTR(tableName, "", pShow->pMeta->pSchemas[cols].bytes);
9✔
3329
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
9✔
3330
      COL_DATA_SET_VAL_GOTO((const char *)tableName, false, pUser, _exit);
9!
3331

3332
      TAOS_MEMORY_REALLOC(condition, TSDB_PRIVILEDGE_CONDITION_LEN + VARSTR_HEADER_SIZE);
9!
3333
      if (condition == NULL) {
9!
3334
        sdbRelease(pSdb, pUser);
×
3335
        TAOS_CHECK_GOTO(terrno, &lino, _exit);
×
3336
      }
3337
      STR_WITH_MAXSIZE_TO_VARSTR(condition, "", pShow->pMeta->pSchemas[cols].bytes);
9✔
3338
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
9✔
3339
      COL_DATA_SET_VAL_GOTO((const char *)condition, false, pUser, _exit);
9!
3340

3341
      char notes[2] = {0};
9✔
3342
      STR_WITH_MAXSIZE_TO_VARSTR(notes, "", sizeof(notes));
9✔
3343
      pColInfo = taosArrayGet(pBlock->pDataBlock, cols++);
9✔
3344
      COL_DATA_SET_VAL_GOTO((const char *)notes, false, pUser, _exit);
9!
3345

3346
      numOfRows++;
9✔
3347
      topic = taosHashIterate(pUser->topics, topic);
9✔
3348
    }
3349

3350
    sdbRelease(pSdb, pUser);
147✔
3351
  }
3352

3353
  pShow->numOfRows += numOfRows;
49✔
3354
_exit:
49✔
3355
  taosMemoryFreeClear(condition);
49!
3356
  taosMemoryFreeClear(sql);
49!
3357
  if (code < 0) {
49!
3358
    uError("%s failed at line %d since %s", __func__, lino, tstrerror(code));
×
3359
    TAOS_RETURN(code);
×
3360
  }
3361
  return numOfRows;
49✔
3362
}
3363

3364
static void mndCancelGetNextPrivileges(SMnode *pMnode, void *pIter) {
×
3365
  SSdb *pSdb = pMnode->pSdb;
×
3366
  sdbCancelFetchByType(pSdb, pIter, SDB_USER);
×
3367
}
×
3368

3369
int32_t mndValidateUserAuthInfo(SMnode *pMnode, SUserAuthVersion *pUsers, int32_t numOfUses, void **ppRsp,
36,978✔
3370
                                int32_t *pRspLen, int64_t ipWhiteListVer) {
3371
  int32_t           code = 0;
36,978✔
3372
  int32_t           lino = 0;
36,978✔
3373
  int32_t           rspLen = 0;
36,978✔
3374
  void             *pRsp = NULL;
36,978✔
3375
  SUserAuthBatchRsp batchRsp = {0};
36,978✔
3376

3377
  batchRsp.pArray = taosArrayInit(numOfUses, sizeof(SGetUserAuthRsp));
36,978✔
3378
  if (batchRsp.pArray == NULL) {
36,979!
3379
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
3380
  }
3381

3382
  for (int32_t i = 0; i < numOfUses; ++i) {
74,935✔
3383
    SUserObj *pUser = NULL;
37,956✔
3384
    code = mndAcquireUser(pMnode, pUsers[i].user, &pUser);
37,956✔
3385
    if (pUser == NULL) {
37,956✔
3386
      if (TSDB_CODE_MND_USER_NOT_EXIST == code) {
28!
3387
        SGetUserAuthRsp rsp = {.dropped = 1};
28✔
3388
        (void)memcpy(rsp.user, pUsers[i].user, TSDB_USER_LEN);
28✔
3389
        TSDB_CHECK_NULL(taosArrayPush(batchRsp.pArray, &rsp), code, lino, _OVER, TSDB_CODE_OUT_OF_MEMORY);
56!
3390
      }
3391
      mError("user:%s, failed to auth user since %s", pUsers[i].user, tstrerror(code));
28!
3392
      code = 0;
28✔
3393
      continue;
34,819✔
3394
    }
3395

3396
    pUsers[i].version = ntohl(pUsers[i].version);
37,928✔
3397
    if (pUser->authVersion <= pUsers[i].version && ipWhiteListVer == pMnode->ipWhiteVer) {
37,928✔
3398
      mndReleaseUser(pMnode, pUser);
34,791✔
3399
      continue;
34,791✔
3400
    }
3401

3402
    SGetUserAuthRsp rsp = {0};
3,137✔
3403
    code = mndSetUserAuthRsp(pMnode, pUser, &rsp);
3,137✔
3404
    if (code) {
3,137!
3405
      mndReleaseUser(pMnode, pUser);
×
3406
      tFreeSGetUserAuthRsp(&rsp);
×
3407
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
3408
    }
3409

3410
    if (!(taosArrayPush(batchRsp.pArray, &rsp))) {
6,274!
3411
      code = terrno;
×
3412
      mndReleaseUser(pMnode, pUser);
×
3413
      tFreeSGetUserAuthRsp(&rsp);
×
3414
      TAOS_CHECK_GOTO(code, &lino, _OVER);
×
3415
    }
3416
    mndReleaseUser(pMnode, pUser);
3,137✔
3417
  }
3418

3419
  if (taosArrayGetSize(batchRsp.pArray) <= 0) {
36,979✔
3420
    *ppRsp = NULL;
34,023✔
3421
    *pRspLen = 0;
34,023✔
3422

3423
    tFreeSUserAuthBatchRsp(&batchRsp);
34,023✔
3424
    return 0;
34,023✔
3425
  }
3426

3427
  rspLen = tSerializeSUserAuthBatchRsp(NULL, 0, &batchRsp);
2,956✔
3428
  if (rspLen < 0) {
2,956!
3429
    TAOS_CHECK_GOTO(rspLen, &lino, _OVER);
×
3430
  }
3431
  pRsp = taosMemoryMalloc(rspLen);
2,956!
3432
  if (pRsp == NULL) {
2,956!
3433
    TAOS_CHECK_GOTO(terrno, &lino, _OVER);
×
3434
  }
3435
  rspLen = tSerializeSUserAuthBatchRsp(pRsp, rspLen, &batchRsp);
2,956✔
3436
  if (rspLen < 0) {
2,956!
3437
    TAOS_CHECK_GOTO(rspLen, &lino, _OVER);
×
3438
  }
3439
_OVER:
2,956✔
3440
  tFreeSUserAuthBatchRsp(&batchRsp);
2,956✔
3441
  if (code < 0) {
2,956!
3442
    uError("%s failed at line %d since %s", __func__, lino, tstrerror(code));
×
3443
    taosMemoryFreeClear(pRsp);
×
3444
    rspLen = 0;
×
3445
  }
3446
  *ppRsp = pRsp;
2,956✔
3447
  *pRspLen = rspLen;
2,956✔
3448

3449
  TAOS_RETURN(code);
2,956✔
3450
}
3451

3452
int32_t mndUserRemoveDb(SMnode *pMnode, STrans *pTrans, char *db) {
1,885✔
3453
  int32_t   code = 0;
1,885✔
3454
  int32_t   lino = 0;
1,885✔
3455
  SSdb     *pSdb = pMnode->pSdb;
1,885✔
3456
  int32_t   len = strlen(db) + 1;
1,885✔
3457
  void     *pIter = NULL;
1,885✔
3458
  SUserObj *pUser = NULL;
1,885✔
3459
  SUserObj  newUser = {0};
1,885✔
3460

3461
  while (1) {
2,092✔
3462
    pIter = sdbFetch(pSdb, SDB_USER, pIter, (void **)&pUser);
3,977✔
3463
    if (pIter == NULL) break;
3,977✔
3464

3465
    if ((code = mndUserDupObj(pUser, &newUser)) != 0) {
2,092!
3466
      break;
×
3467
    }
3468

3469
    bool inRead = (taosHashGet(newUser.readDbs, db, len) != NULL);
2,092✔
3470
    bool inWrite = (taosHashGet(newUser.writeDbs, db, len) != NULL);
2,092✔
3471
    if (inRead || inWrite) {
2,092!
3472
      code = taosHashRemove(newUser.readDbs, db, len);
3✔
3473
      if (code < 0) {
3!
3474
        mError("failed to remove readDbs:%s from user:%s", db, pUser->user);
×
3475
      }
3476
      code = taosHashRemove(newUser.writeDbs, db, len);
3✔
3477
      if (code < 0) {
3!
3478
        mError("failed to remove writeDbs:%s from user:%s", db, pUser->user);
×
3479
      }
3480

3481
      SSdbRaw *pCommitRaw = mndUserActionEncode(&newUser);
3✔
3482
      if (pCommitRaw == NULL || (code = mndTransAppendCommitlog(pTrans, pCommitRaw)) != 0) {
3!
3483
        code = TSDB_CODE_OUT_OF_MEMORY;
×
3484
        break;
×
3485
      }
3486
      TAOS_CHECK_GOTO(sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY), &lino, _OVER);
3!
3487
    }
3488

3489
    mndUserFreeObj(&newUser);
2,092✔
3490
    sdbRelease(pSdb, pUser);
2,092✔
3491
  }
3492

3493
_OVER:
1,885✔
3494
  if (pUser != NULL) sdbRelease(pSdb, pUser);
1,885!
3495
  if (pIter != NULL) sdbCancelFetch(pSdb, pIter);
1,885!
3496
  mndUserFreeObj(&newUser);
1,885✔
3497
  TAOS_RETURN(code);
1,885✔
3498
}
3499

3500
int32_t mndUserRemoveStb(SMnode *pMnode, STrans *pTrans, char *stb) {
3,367✔
3501
  int32_t   code = 0;
3,367✔
3502
  SSdb     *pSdb = pMnode->pSdb;
3,367✔
3503
  int32_t   len = strlen(stb) + 1;
3,367✔
3504
  void     *pIter = NULL;
3,367✔
3505
  SUserObj *pUser = NULL;
3,367✔
3506
  SUserObj  newUser = {0};
3,367✔
3507

3508
  while (1) {
3,562✔
3509
    pIter = sdbFetch(pSdb, SDB_USER, pIter, (void **)&pUser);
6,929✔
3510
    if (pIter == NULL) break;
6,929✔
3511

3512
    if ((code = mndUserDupObj(pUser, &newUser)) != 0) {
3,562!
3513
      break;
×
3514
    }
3515

3516
    bool inRead = (taosHashGet(newUser.readTbs, stb, len) != NULL);
3,562✔
3517
    bool inWrite = (taosHashGet(newUser.writeTbs, stb, len) != NULL);
3,562✔
3518
    bool inAlter = (taosHashGet(newUser.alterTbs, stb, len) != NULL);
3,562✔
3519
    if (inRead || inWrite || inAlter) {
3,562!
3520
      code = taosHashRemove(newUser.readTbs, stb, len);
×
3521
      if (code < 0) {
×
3522
        mError("failed to remove readTbs:%s from user:%s", stb, pUser->user);
×
3523
      }
3524
      code = taosHashRemove(newUser.writeTbs, stb, len);
×
3525
      if (code < 0) {
×
3526
        mError("failed to remove writeTbs:%s from user:%s", stb, pUser->user);
×
3527
      }
3528
      code = taosHashRemove(newUser.alterTbs, stb, len);
×
3529
      if (code < 0) {
×
3530
        mError("failed to remove alterTbs:%s from user:%s", stb, pUser->user);
×
3531
      }
3532

3533
      SSdbRaw *pCommitRaw = mndUserActionEncode(&newUser);
×
3534
      if (pCommitRaw == NULL || (code = mndTransAppendCommitlog(pTrans, pCommitRaw)) != 0) {
×
3535
        code = TSDB_CODE_OUT_OF_MEMORY;
×
3536
        break;
×
3537
      }
3538
      code = sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY);
×
3539
      if (code != 0) {
×
3540
        mndUserFreeObj(&newUser);
×
3541
        sdbRelease(pSdb, pUser);
×
3542
        TAOS_RETURN(code);
×
3543
      }
3544
    }
3545

3546
    mndUserFreeObj(&newUser);
3,562✔
3547
    sdbRelease(pSdb, pUser);
3,562✔
3548
  }
3549

3550
  if (pUser != NULL) sdbRelease(pSdb, pUser);
3,367!
3551
  if (pIter != NULL) sdbCancelFetch(pSdb, pIter);
3,367!
3552
  mndUserFreeObj(&newUser);
3,367✔
3553
  TAOS_RETURN(code);
3,367✔
3554
}
3555

3556
int32_t mndUserRemoveView(SMnode *pMnode, STrans *pTrans, char *view) {
451✔
3557
  int32_t   code = 0;
451✔
3558
  SSdb     *pSdb = pMnode->pSdb;
451✔
3559
  int32_t   len = strlen(view) + 1;
451✔
3560
  void     *pIter = NULL;
451✔
3561
  SUserObj *pUser = NULL;
451✔
3562
  SUserObj  newUser = {0};
451✔
3563

3564
  while (1) {
470✔
3565
    pIter = sdbFetch(pSdb, SDB_USER, pIter, (void **)&pUser);
921✔
3566
    if (pIter == NULL) break;
921✔
3567

3568
    if ((code = mndUserDupObj(pUser, &newUser)) != 0) {
470!
3569
      break;
×
3570
    }
3571

3572
    bool inRead = (taosHashGet(newUser.readViews, view, len) != NULL);
470✔
3573
    bool inWrite = (taosHashGet(newUser.writeViews, view, len) != NULL);
470✔
3574
    bool inAlter = (taosHashGet(newUser.alterViews, view, len) != NULL);
470✔
3575
    if (inRead || inWrite || inAlter) {
470!
3576
      code = taosHashRemove(newUser.readViews, view, len);
11✔
3577
      if (code < 0) {
11✔
3578
        mError("failed to remove readViews:%s from user:%s", view, pUser->user);
2!
3579
      }
3580
      code = taosHashRemove(newUser.writeViews, view, len);
11✔
3581
      if (code < 0) {
11✔
3582
        mError("failed to remove writeViews:%s from user:%s", view, pUser->user);
6!
3583
      }
3584
      code = taosHashRemove(newUser.alterViews, view, len);
11✔
3585
      if (code < 0) {
11✔
3586
        mError("failed to remove alterViews:%s from user:%s", view, pUser->user);
4!
3587
      }
3588

3589
      SSdbRaw *pCommitRaw = mndUserActionEncode(&newUser);
11✔
3590
      if (pCommitRaw == NULL || (code = mndTransAppendCommitlog(pTrans, pCommitRaw)) != 0) {
11!
3591
        code = TSDB_CODE_OUT_OF_MEMORY;
×
3592
        break;
×
3593
      }
3594
      code = sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY);
11✔
3595
      if (code < 0) {
11!
3596
        mndUserFreeObj(&newUser);
×
3597
        sdbRelease(pSdb, pUser);
×
3598
        TAOS_RETURN(code);
×
3599
      }
3600
    }
3601

3602
    mndUserFreeObj(&newUser);
470✔
3603
    sdbRelease(pSdb, pUser);
470✔
3604
  }
3605

3606
  if (pUser != NULL) sdbRelease(pSdb, pUser);
451!
3607
  if (pIter != NULL) sdbCancelFetch(pSdb, pIter);
451!
3608
  mndUserFreeObj(&newUser);
451✔
3609
  TAOS_RETURN(code);
451✔
3610
}
3611

3612
int32_t mndUserRemoveTopic(SMnode *pMnode, STrans *pTrans, char *topic) {
336✔
3613
  int32_t   code = 0;
336✔
3614
  SSdb     *pSdb = pMnode->pSdb;
336✔
3615
  int32_t   len = strlen(topic) + 1;
336✔
3616
  void     *pIter = NULL;
336✔
3617
  SUserObj *pUser = NULL;
336✔
3618
  SUserObj  newUser = {0};
336✔
3619

3620
  while (1) {
371✔
3621
    pIter = sdbFetch(pSdb, SDB_USER, pIter, (void **)&pUser);
707✔
3622
    if (pIter == NULL) {
707✔
3623
      break;
336✔
3624
    }
3625

3626
    if ((code = mndUserDupObj(pUser, &newUser)) != 0) {
371!
3627
      break;
×
3628
    }
3629

3630
    bool inTopic = (taosHashGet(newUser.topics, topic, len) != NULL);
371✔
3631
    if (inTopic) {
371!
3632
      code = taosHashRemove(newUser.topics, topic, len);
×
3633
      if (code < 0) {
×
3634
        mError("failed to remove topic:%s from user:%s", topic, pUser->user);
×
3635
      }
3636
      SSdbRaw *pCommitRaw = mndUserActionEncode(&newUser);
×
3637
      if (pCommitRaw == NULL || (code = mndTransAppendCommitlog(pTrans, pCommitRaw)) != 0) {
×
3638
        code = TSDB_CODE_OUT_OF_MEMORY;
×
3639
        break;
×
3640
      }
3641
      code = sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY);
×
3642
      if (code < 0) {
×
3643
        mndUserFreeObj(&newUser);
×
3644
        sdbRelease(pSdb, pUser);
×
3645
        TAOS_RETURN(code);
×
3646
      }
3647
    }
3648

3649
    mndUserFreeObj(&newUser);
371✔
3650
    sdbRelease(pSdb, pUser);
371✔
3651
  }
3652

3653
  if (pUser != NULL) sdbRelease(pSdb, pUser);
336!
3654
  if (pIter != NULL) sdbCancelFetch(pSdb, pIter);
336!
3655
  mndUserFreeObj(&newUser);
336✔
3656
  TAOS_RETURN(code);
336✔
3657
}
3658

3659
int64_t mndGetUserIpWhiteListVer(SMnode *pMnode, SUserObj *pUser) {
×
3660
  // ver = 0, disable ip white list
3661
  // ver > 0, enable ip white list
3662
  return tsEnableWhiteList ? pUser->ipWhiteListVer : 0;
×
3663
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc