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

taosdata / TDengine / #3910

23 Apr 2025 02:47AM UTC coverage: 62.362% (-0.7%) from 63.063%
#3910

push

travis-ci

web-flow
docs(datain): add missing health status types (#30828)

155061 of 317305 branches covered (48.87%)

Branch coverage included in aggregate %.

240172 of 316469 relevant lines covered (75.89%)

6269478.46 hits per line

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

58.03
/source/dnode/mnode/impl/src/mndConfig.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
#include "audit.h"
18
#include "mndConfig.h"
19
#include "mndDnode.h"
20
#include "mndMnode.h"
21
#include "mndPrivilege.h"
22
#include "mndSync.h"
23
#include "mndTrans.h"
24
#include "mndUser.h"
25
#include "tutil.h"
26
#include "tcompare.h"
27

28
#define CFG_VER_NUMBER    1
29
#define CFG_RESERVE_SIZE  63
30
#define CFG_ALTER_TIMEOUT 3 * 1000
31

32
static int32_t mndMCfgGetValInt32(SMCfgDnodeReq *pInMCfgReq, int32_t optLen, int32_t *pOutValue);
33
static int32_t mndProcessShowVariablesReq(SRpcMsg *pReq);
34
static int32_t mndProcessConfigDnodeReq(SRpcMsg *pReq);
35
static int32_t mndProcessConfigDnodeRsp(SRpcMsg *pRsp);
36
static int32_t mndProcessConfigReq(SRpcMsg *pReq);
37
static int32_t mndInitWriteCfg(SMnode *pMnode);
38
static int32_t mndSendRebuildReq(SMnode *pMnode);
39
static int32_t mndTryRebuildConfigSdbRsp(SRpcMsg *pRsp);
40
static int32_t initConfigArrayFromSdb(SMnode *pMnode, SArray *array);
41
static int32_t mndTryRebuildConfigSdb(SRpcMsg *pReq);
42
static void    cfgArrayCleanUp(SArray *array);
43
static void    cfgObjArrayCleanUp(SArray *array);
44
int32_t        compareSConfigItemArrays(SMnode *pMnode, const SArray *dArray, SArray *diffArray);
45

46
static int32_t mndConfigUpdateTrans(SMnode *pMnode, const char *name, char *pValue, ECfgDataType dtype,
47
                                    int32_t tsmmConfigVersion);
48

49
int32_t mndSetCreateConfigCommitLogs(STrans *pTrans, SConfigObj *obj);
50

51
int32_t mndInitConfig(SMnode *pMnode) {
1,978✔
52
  int32_t   code = 0;
1,978✔
53
  SSdbTable table = {.sdbType = SDB_CFG,
1,978✔
54
                     .keyType = SDB_KEY_BINARY,
55
                     .encodeFp = (SdbEncodeFp)mnCfgActionEncode,
56
                     .decodeFp = (SdbDecodeFp)mndCfgActionDecode,
57
                     .insertFp = (SdbInsertFp)mndCfgActionInsert,
58
                     .updateFp = (SdbUpdateFp)mndCfgActionUpdate,
59
                     .deleteFp = (SdbDeleteFp)mndCfgActionDelete,
60
                     .deployFp = (SdbDeployFp)mndCfgActionDeploy,
61
                     .afterRestoredFp = (SdbAfterRestoredFp)mndCfgActionAfterRestored};
62

63
  mndSetMsgHandle(pMnode, TDMT_MND_CONFIG, mndProcessConfigReq);
1,978✔
64
  mndSetMsgHandle(pMnode, TDMT_MND_CONFIG_DNODE, mndProcessConfigDnodeReq);
1,978✔
65
  mndSetMsgHandle(pMnode, TDMT_DND_CONFIG_DNODE_RSP, mndProcessConfigDnodeRsp);
1,978✔
66
  mndSetMsgHandle(pMnode, TDMT_MND_SHOW_VARIABLES, mndProcessShowVariablesReq);
1,978✔
67
  mndSetMsgHandle(pMnode, TDMT_MND_CONFIG_SDB, mndTryRebuildConfigSdb);
1,978✔
68
  mndSetMsgHandle(pMnode, TDMT_MND_CONFIG_SDB_RSP, mndTryRebuildConfigSdbRsp);
1,978✔
69

70
  return sdbSetTable(pMnode->pSdb, table);
1,978✔
71
}
72

73
SSdbRaw *mnCfgActionEncode(SConfigObj *obj) {
449,404✔
74
  int32_t  code = 0;
449,404✔
75
  int32_t  lino = 0;
449,404✔
76
  void    *buf = NULL;
449,404✔
77
  SSdbRaw *pRaw = NULL;
449,404✔
78

79
  SEncoder encoder;
80
  tEncoderInit(&encoder, NULL, 0);
449,404✔
81
  if ((code = tEncodeSConfigObj(&encoder, obj)) < 0) {
449,404!
82
    tEncoderClear(&encoder);
×
83
    TSDB_CHECK_CODE(code, lino, _over);
×
84
  }
85

86
  int32_t tlen = encoder.pos;
449,404✔
87
  tEncoderClear(&encoder);
449,404✔
88

89
  int32_t size = sizeof(int32_t) + tlen;
449,404✔
90
  pRaw = sdbAllocRaw(SDB_CFG, CFG_VER_NUMBER, size);
449,404✔
91
  TSDB_CHECK_NULL(pRaw, code, lino, _over, terrno);
449,404!
92

93
  buf = taosMemoryMalloc(tlen);
449,404!
94
  TSDB_CHECK_NULL(buf, code, lino, _over, terrno);
449,404!
95

96
  tEncoderInit(&encoder, buf, tlen);
449,404✔
97
  if ((code = tEncodeSConfigObj(&encoder, obj)) < 0) {
449,404!
98
    tEncoderClear(&encoder);
×
99
    TSDB_CHECK_CODE(code, lino, _over);
×
100
  }
101

102
  tEncoderClear(&encoder);
449,404✔
103

104
  int32_t dataPos = 0;
449,404✔
105
  SDB_SET_INT32(pRaw, dataPos, tlen, _over);
449,404!
106
  SDB_SET_BINARY(pRaw, dataPos, buf, tlen, _over);
449,404!
107
  SDB_SET_DATALEN(pRaw, dataPos, _over);
449,404!
108

109
_over:
449,404✔
110
  taosMemoryFreeClear(buf);
449,404!
111
  if (code != TSDB_CODE_SUCCESS) {
449,404!
112
    mError("cfg:%s, failed to encode to raw:%p at line:%d since %s", obj->name, pRaw, lino, tstrerror(code));
×
113
    sdbFreeRaw(pRaw);
×
114
    terrno = code;
×
115
    return NULL;
×
116
  }
117

118
  terrno = 0;
449,404✔
119
  mTrace("cfg:%s, encode to raw:%p, row:%p", obj->name, pRaw, obj);
449,404✔
120
  return pRaw;
449,404✔
121
}
122

123
SSdbRow *mndCfgActionDecode(SSdbRaw *pRaw) {
177,852✔
124
  int32_t     code = 0;
177,852✔
125
  int32_t     lino = 0;
177,852✔
126
  SSdbRow    *pRow = NULL;
177,852✔
127
  SConfigObj *pObj = NULL;
177,852✔
128
  void       *buf = NULL;
177,852✔
129
  int8_t      sver = 0;
177,852✔
130
  int32_t     tlen;
131
  int32_t     dataPos = 0;
177,852✔
132

133
  code = sdbGetRawSoftVer(pRaw, &sver);
177,852✔
134
  TSDB_CHECK_CODE(code, lino, _over);
177,852!
135

136
  if (sver != CFG_VER_NUMBER) {
177,852!
137
    terrno = TSDB_CODE_SDB_INVALID_DATA_VER;
×
138
    goto _over;
×
139
  }
140

141
  pRow = sdbAllocRow(sizeof(SConfigObj));
177,852✔
142
  TSDB_CHECK_NULL(pRow, code, lino, _over, terrno);
177,852!
143

144
  pObj = sdbGetRowObj(pRow);
177,852✔
145
  TSDB_CHECK_NULL(pObj, code, lino, _over, terrno);
177,852!
146

147
  SDB_GET_INT32(pRaw, dataPos, &tlen, _over);
177,852!
148

149
  buf = taosMemoryMalloc(tlen + 1);
177,852!
150
  TSDB_CHECK_NULL(buf, code, lino, _over, terrno);
177,852!
151

152
  SDB_GET_BINARY(pRaw, dataPos, buf, tlen, _over);
177,852!
153

154
  SDecoder decoder;
155
  tDecoderInit(&decoder, buf, tlen + 1);
177,852✔
156
  code = tDecodeSConfigObj(&decoder, pObj);
177,852✔
157
  tDecoderClear(&decoder);
177,852✔
158

159
  if (code < 0) {
177,852!
160
    tFreeSConfigObj(pObj);
×
161
  }
162

163
_over:
177,852✔
164
  taosMemoryFreeClear(buf);
177,852!
165

166
  if (code != TSDB_CODE_SUCCESS) {
177,852!
167
    mError("cfg:%s, failed to decode from raw:%p since %s at:%d", pObj->name, pRaw, tstrerror(code), lino);
×
168
    taosMemoryFreeClear(pRow);
×
169
    terrno = code;
×
170
    return NULL;
×
171
  } else {
172
    mTrace("config:%s, decode from raw:%p, row:%p", pObj->name, pRaw, pObj);
177,852✔
173
    terrno = 0;
177,852✔
174
    return pRow;
177,852✔
175
  }
176
}
177

178
static int32_t mndCfgActionInsert(SSdb *pSdb, SConfigObj *obj) {
177,308✔
179
  mTrace("cfg:%s, perform insert action, row:%p", obj->name, obj);
177,308✔
180
  return 0;
177,308✔
181
}
182

183
static int32_t mndCfgActionDelete(SSdb *pSdb, SConfigObj *obj) {
177,762✔
184
  mTrace("cfg:%s, perform delete action, row:%p", obj->name, obj);
177,762✔
185
  tFreeSConfigObj(obj);
177,762✔
186
  return 0;
177,762✔
187
}
188

189
static int32_t mndCfgActionUpdate(SSdb *pSdb, SConfigObj *pOld, SConfigObj *pNew) {
544✔
190
  mTrace("cfg:%s, perform update action, old row:%p new row:%p", pOld->name, pOld, pNew);
544!
191
  switch (pNew->dtype) {
544!
192
    case CFG_DTYPE_NONE:
×
193
      break;
×
194
    case CFG_DTYPE_BOOL:
64✔
195
      pOld->bval = pNew->bval;
64✔
196
      break;
64✔
197
    case CFG_DTYPE_INT32:
438✔
198
      pOld->i32 = pNew->i32;
438✔
199
      break;
438✔
200
    case CFG_DTYPE_INT64:
22✔
201
      pOld->i64 = pNew->i64;
22✔
202
      break;
22✔
203
    case CFG_DTYPE_FLOAT:
8✔
204
    case CFG_DTYPE_DOUBLE:
205
      pOld->fval = pNew->fval;
8✔
206
      break;
8✔
207
    case CFG_DTYPE_STRING:
12✔
208
    case CFG_DTYPE_DIR:
209
    case CFG_DTYPE_LOCALE:
210
    case CFG_DTYPE_CHARSET:
211
    case CFG_DTYPE_TIMEZONE:
212
      taosMemoryFree(pOld->str);
12!
213
      pOld->str = taosStrdup(pNew->str);
12!
214
      if (pOld->str == NULL) {
12!
215
        return terrno;
×
216
      }
217
      break;
12✔
218
  }
219
  return TSDB_CODE_SUCCESS;
544✔
220
}
221

222
static int32_t mndCfgActionDeploy(SMnode *pMnode) { return mndInitWriteCfg(pMnode); }
1,486✔
223

224
static int32_t mndCfgActionAfterRestored(SMnode *pMnode) { return mndSendRebuildReq(pMnode); }
734✔
225

226
static int32_t mndProcessConfigReq(SRpcMsg *pReq) {
2,365✔
227
  SMnode    *pMnode = pReq->info.node;
2,365✔
228
  SConfigReq configReq = {0};
2,365✔
229
  int32_t    code = TSDB_CODE_SUCCESS;
2,365✔
230
  SArray    *array = NULL;
2,365✔
231
  bool       needFree = false;
2,365✔
232
  code = tDeserializeSConfigReq(pReq->pCont, pReq->contLen, &configReq);
2,365✔
233
  if (code != 0) {
2,365!
234
    mError("failed to deserialize config req, since %s", terrstr());
×
235
    goto _OVER;
×
236
  }
237

238
  SConfigObj *vObj = sdbAcquire(pMnode->pSdb, SDB_CFG, "tsmmConfigVersion");
2,365✔
239
  if (vObj == NULL) {
2,365!
240
    mInfo("failed to acquire mnd config version, since %s", terrstr());
×
241
    goto _OVER;
×
242
  }
243

244
  array = taosArrayInit(16, sizeof(SConfigItem));
2,365✔
245
  if (array == NULL) {
2,365!
246
    code = TSDB_CODE_OUT_OF_MEMORY;
×
247
    goto _OVER;
×
248
  }
249
  SConfigRsp configRsp = {0};
2,365✔
250
  configRsp.cver = vObj->i32;
2,365✔
251

252
  if (configReq.cver == vObj->i32) {
2,365✔
253
    configRsp.isVersionVerified = 1;
422✔
254
  } else {
255
    code = initConfigArrayFromSdb(pMnode, array);
1,943✔
256
    if (code != 0) {
1,943!
257
      mError("failed to init config array from sdb, since %s", tstrerror(code));
×
258
      goto _OVER;
×
259
    }
260
    configRsp.array = array;
1,943✔
261
  }
262

263
  int32_t contLen = tSerializeSConfigRsp(NULL, 0, &configRsp);
2,365✔
264
  if (contLen < 0) {
2,365!
265
    code = contLen;
×
266
    goto _OVER;
×
267
  }
268
  void *pHead = rpcMallocCont(contLen);
2,365✔
269
  if (pHead == NULL) {
2,365!
270
    code = TSDB_CODE_OUT_OF_MEMORY;
×
271
    goto _OVER;
×
272
  }
273
  contLen = tSerializeSConfigRsp(pHead, contLen, &configRsp);
2,365✔
274
  if (contLen < 0) {
2,365!
275
    rpcFreeCont(pHead);
×
276
    code = contLen;
×
277
    goto _OVER;
×
278
  }
279
  pReq->info.rspLen = contLen;
2,365✔
280
  pReq->info.rsp = pHead;
2,365✔
281

282
_OVER:
2,365✔
283
  if (code != 0) {
2,365!
284
    mError("failed to process config req, since %s", tstrerror(code));
×
285
  }
286
  sdbRelease(pMnode->pSdb, vObj);
2,365✔
287
  cfgArrayCleanUp(array);
2,365✔
288
  tFreeSConfigReq(&configReq);
2,365✔
289
  return code;
2,365✔
290
}
291

292
int32_t mndInitWriteCfg(SMnode *pMnode) {
1,486✔
293
  int    code = 0;
1,486✔
294
  size_t sz = 0;
1,486✔
295

296
  mInfo("init write cfg to sdb");
1,486!
297
  STrans *pTrans = mndTransCreate(pMnode, TRN_POLICY_RETRY, TRN_CONFLICT_NOTHING, NULL, "init-write-config");
1,486✔
298
  if (pTrans == NULL) {
1,486!
299
    mError("failed to init write cfg in create trans, since %s", terrstr());
×
300
    goto _OVER;
×
301
  }
302

303
  // encode mnd config version
304
  SConfigObj versionObj = mndInitConfigVersion();
1,486✔
305
  if ((code = mndSetCreateConfigCommitLogs(pTrans, &versionObj)) != 0) {
1,486!
306
    mError("failed to init mnd config version, since %s", tstrerror(code));
×
307
    tFreeSConfigObj(&versionObj);
×
308
    goto _OVER;
×
309
  }
310
  tFreeSConfigObj(&versionObj);
1,486✔
311
  sz = taosArrayGetSize(taosGetGlobalCfg(tsCfg));
1,486✔
312

313
  for (int i = 0; i < sz; ++i) {
133,028✔
314
    SConfigItem *item = taosArrayGet(taosGetGlobalCfg(tsCfg), i);
131,542✔
315
    SConfigObj   obj;
316
    if ((code = mndInitConfigObj(item, &obj)) != 0) {
131,542!
317
      goto _OVER;
×
318
    }
319
    if ((code = mndSetCreateConfigCommitLogs(pTrans, &obj)) != 0) {
131,542!
320
      mError("failed to init mnd config:%s, since %s", item->name, tstrerror(code));
×
321
      tFreeSConfigObj(&obj);
×
322
      goto _OVER;
×
323
    }
324
    tFreeSConfigObj(&obj);
131,542✔
325
  }
326
  if ((code = mndTransPrepare(pMnode, pTrans)) != 0) goto _OVER;
1,486!
327

328
_OVER:
1,486✔
329
  if (code != 0) {
1,486!
330
    mError("failed to init write cfg, since %s", tstrerror(code));
×
331
  }
332
  mndTransDrop(pTrans);
1,486✔
333
  return code;
1,486✔
334
}
335

336
int32_t mndSendRebuildReq(SMnode *pMnode) {
734✔
337
  int32_t code = 0;
734✔
338

339
  SRpcMsg rpcMsg = {.pCont = NULL,
734✔
340
                    .contLen = 0,
341
                    .msgType = TDMT_MND_CONFIG_SDB,
342
                    .info.ahandle = 0,
343
                    .info.notFreeAhandle = 1,
344
                    .info.refId = 0,
345
                    .info.noResp = 0,
346
                    .info.handle = 0};
347
  SEpSet  epSet = {0};
734✔
348

349
  mndGetMnodeEpSet(pMnode, &epSet);
734✔
350

351
  code = tmsgSendReq(&epSet, &rpcMsg);
734✔
352
  if (code != 0) {
734!
353
    mError("failed to send rebuild config req, since %s", tstrerror(code));
×
354
  }
355
  return code;
734✔
356
}
357

358
static int32_t mndTryRebuildConfigSdb(SRpcMsg *pReq) {
729✔
359
  SMnode *pMnode = pReq->info.node;
729✔
360
  if (!mndIsLeader(pMnode)) {
729!
361
    return TSDB_CODE_SUCCESS;
×
362
  }
363
  int32_t     code = 0;
729✔
364
  int32_t     sz = -1;
729✔
365
  STrans     *pTrans = NULL;
729✔
366
  SConfigObj *vObj = NULL;
729✔
367
  SArray     *addArray = NULL;
729✔
368

369
  vObj = sdbAcquire(pMnode->pSdb, SDB_CFG, "tsmmConfigVersion");
729✔
370
  if (vObj == NULL) {
729!
371
    if ((code = mndInitWriteCfg(pMnode)) < 0) goto _exit;
×
372
    mInfo("failed to acquire mnd config version, try to rebuild config in sdb.");
×
373
  } else {
374
    sz = taosArrayGetSize(taosGetGlobalCfg(tsCfg));
729✔
375
    addArray = taosArrayInit(4, sizeof(SConfigObj));
729✔
376
    for (int i = 0; i < sz; ++i) {
65,610✔
377
      SConfigItem *item = taosArrayGet(taosGetGlobalCfg(tsCfg), i);
64,881✔
378
      SConfigObj  *obj = sdbAcquire(pMnode->pSdb, SDB_CFG, item->name);
64,881✔
379
      if (obj == NULL) {
64,881!
380
        mInfo("config:%s, not exist in sdb, try to add it", item->name);
×
381
        SConfigObj newObj;
382
        if ((code = mndInitConfigObj(item, &newObj)) != 0) goto _exit;
×
383
        if (NULL == taosArrayPush(addArray, &newObj)) {
×
384
          code = terrno;
×
385
          goto _exit;
×
386
        }
387
      } else {
388
        sdbRelease(pMnode->pSdb, obj);
64,881✔
389
      }
390
    }
391
    int32_t addSize = taosArrayGetSize(addArray);
729✔
392
    if (addSize > 0) {
729!
393
      pTrans = mndTransCreate(pMnode, TRN_POLICY_RETRY, TRN_CONFLICT_NOTHING, NULL, "add-config");
×
394
      if (pTrans == NULL) {
×
395
        code = terrno;
×
396
        goto _exit;
×
397
      }
398
      for (int i = 0; i < addSize; ++i) {
×
399
        SConfigObj *AddObj = taosArrayGet(addArray, i);
×
400
        if ((code = mndSetCreateConfigCommitLogs(pTrans, AddObj)) != 0) goto _exit;
×
401
      }
402
      if ((code = mndTransPrepare(pMnode, pTrans)) != 0) goto _exit;
×
403
      mInfo("add new config to sdb, nums:%d", addSize);
×
404
    }
405
  }
406
_exit:
729✔
407
  if (code != 0) {
729!
408
    mError("failed to try rebuild config in sdb, since %s", tstrerror(code));
×
409
  }
410
  sdbRelease(pMnode->pSdb, vObj);
729✔
411
  cfgObjArrayCleanUp(addArray);
729✔
412
  mndTransDrop(pTrans);
729✔
413
  TAOS_RETURN(code);
729✔
414
}
415

416
int32_t mndSetCreateConfigCommitLogs(STrans *pTrans, SConfigObj *item) {
133,308✔
417
  int32_t  code = 0;
133,308✔
418
  SSdbRaw *pCommitRaw = mnCfgActionEncode(item);
133,308✔
419
  if (pCommitRaw == NULL) {
133,308!
420
    code = terrno;
×
421
    TAOS_RETURN(code);
×
422
  }
423
  if ((code = mndTransAppendCommitlog(pTrans, pCommitRaw) != 0)) TAOS_RETURN(code);
133,308!
424
  if ((code = sdbSetRawStatus(pCommitRaw, SDB_STATUS_READY)) != 0) TAOS_RETURN(code);
133,308!
425
  return TSDB_CODE_SUCCESS;
133,308✔
426
}
427

428
static int32_t mndMCfg2DCfg(SMCfgDnodeReq *pMCfgReq, SDCfgDnodeReq *pDCfgReq) {
258✔
429
  int32_t code = 0;
258✔
430
  char   *p = pMCfgReq->config;
258✔
431
  while (*p) {
3,734✔
432
    if (*p == ' ') {
3,665✔
433
      break;
189✔
434
    }
435
    p++;
3,476✔
436
  }
437

438
  size_t optLen = p - pMCfgReq->config;
258✔
439
  tstrncpy(pDCfgReq->config, pMCfgReq->config, sizeof(pDCfgReq->config));
258✔
440
  pDCfgReq->config[optLen] = 0;
258✔
441

442
  if (' ' == pMCfgReq->config[optLen]) {
258✔
443
    // 'key value'
444
    if (strlen(pMCfgReq->value) != 0) goto _err;
189!
445
    tstrncpy(pDCfgReq->value, p + 1, sizeof(pDCfgReq->value));
189✔
446
  } else {
447
    // 'key' 'value'
448
    if (strlen(pMCfgReq->value) == 0) goto _err;
69✔
449
    tstrncpy(pDCfgReq->value, pMCfgReq->value, sizeof(pDCfgReq->value));
65✔
450
  }
451

452
  TAOS_RETURN(code);
254✔
453

454
_err:
4✔
455
  mError("dnode:%d, failed to config since invalid conf:%s", pMCfgReq->dnodeId, pMCfgReq->config);
4!
456
  code = TSDB_CODE_INVALID_CFG;
4✔
457
  TAOS_RETURN(code);
4✔
458
}
459

460
static int32_t mndSendCfgDnodeReq(SMnode *pMnode, int32_t dnodeId, SDCfgDnodeReq *pDcfgReq) {
219✔
461
  int32_t code = -1;
219✔
462
  SSdb   *pSdb = pMnode->pSdb;
219✔
463
  void   *pIter = NULL;
219✔
464

465
  int64_t curMs = taosGetTimestampMs();
219✔
466

467
  while (1) {
540✔
468
    SDnodeObj *pDnode = NULL;
759✔
469
    pIter = sdbFetch(pSdb, SDB_DNODE, pIter, (void **)&pDnode);
759✔
470
    if (pIter == NULL) break;
759✔
471

472
    if (pDnode->id == dnodeId || dnodeId == -1 || dnodeId == 0) {
540!
473
      bool online = mndIsDnodeOnline(pDnode, curMs);
519✔
474
      if (!online) {
519✔
475
        mWarn("dnode:%d, is offline, skip to send config req", pDnode->id);
1!
476
        continue;
1✔
477
      }
478
      SEpSet  epSet = mndGetDnodeEpset(pDnode);
518✔
479
      int32_t bufLen = tSerializeSDCfgDnodeReq(NULL, 0, pDcfgReq);
518✔
480
      void   *pBuf = rpcMallocCont(bufLen);
518✔
481

482
      if (pBuf == NULL) {
518!
483
        sdbCancelFetch(pMnode->pSdb, pIter);
×
484
        sdbRelease(pMnode->pSdb, pDnode);
×
485
        code = TSDB_CODE_OUT_OF_MEMORY;
×
486
        return code;
×
487
      }
488

489
      if ((bufLen = tSerializeSDCfgDnodeReq(pBuf, bufLen, pDcfgReq)) <= 0) {
518!
490
        sdbCancelFetch(pMnode->pSdb, pIter);
×
491
        sdbRelease(pMnode->pSdb, pDnode);
×
492
        code = bufLen;
×
493
        rpcFreeCont(pBuf);
×
494
        return code;
×
495
      }
496

497
      mInfo("dnode:%d, send config req to dnode, config:%s value:%s", pDnode->id, pDcfgReq->config, pDcfgReq->value);
518!
498
      SRpcMsg rpcMsg = {.msgType = TDMT_DND_CONFIG_DNODE, .pCont = pBuf, .contLen = bufLen};
518✔
499
      SRpcMsg rpcRsp = {0};
518✔
500

501
      code = rpcSendRecvWithTimeout(pMnode->msgCb.statusRpc, &epSet, &rpcMsg, &rpcRsp, NULL, CFG_ALTER_TIMEOUT);
518✔
502
      if (code != 0) {
518!
503
        mError("failed to send config req to dnode:%d, since %s", pDnode->id, tstrerror(code));
×
504
        sdbCancelFetch(pMnode->pSdb, pIter);
×
505
        sdbRelease(pMnode->pSdb, pDnode);
×
506
        return code;
×
507
      }
508

509
      code = rpcRsp.code;
518✔
510
      if (code != 0) {
518!
511
        mError("failed to alter config %s,on dnode:%d, since %s", pDcfgReq->config, pDnode->id, tstrerror(code));
×
512
        sdbCancelFetch(pMnode->pSdb, pIter);
×
513
        sdbRelease(pMnode->pSdb, pDnode);
×
514
        return code;
×
515
      }
516
      rpcFreeCont(rpcRsp.pCont);
518✔
517
    }
518
    sdbRelease(pSdb, pDnode);
539✔
519
  }
520

521
  if (code == -1) {
219✔
522
    code = TSDB_CODE_MND_DNODE_NOT_EXIST;
5✔
523
  }
524
  TAOS_RETURN(code);
219✔
525
}
526

527
static int32_t mndProcessConfigDnodeReq(SRpcMsg *pReq) {
267✔
528
  int32_t       code = 0;
267✔
529
  int32_t       lino = -1;
267✔
530
  SMnode       *pMnode = pReq->info.node;
267✔
531
  SMCfgDnodeReq cfgReq = {0};
267✔
532
  SConfigObj   *vObj = sdbAcquire(pMnode->pSdb, SDB_CFG, "tsmmConfigVersion");
267✔
533
  if (vObj == NULL) {
267!
534
    code = TSDB_CODE_SDB_OBJ_NOT_THERE;
×
535
    mInfo("failed to acquire mnd config version, since %s", tstrerror(code));
×
536
    goto _err_out;
×
537
  }
538

539
  TAOS_CHECK_RETURN(tDeserializeSMCfgDnodeReq(pReq->pCont, pReq->contLen, &cfgReq));
267!
540
  int8_t updateIpWhiteList = 0;
267✔
541
  mInfo("dnode:%d, start to config, option:%s, value:%s", cfgReq.dnodeId, cfgReq.config, cfgReq.value);
267!
542
  if ((code = mndCheckOperPrivilege(pMnode, pReq->info.conn.user, MND_OPER_CONFIG_DNODE)) != 0) {
267✔
543
    goto _err_out;
7✔
544
  }
545

546
  SDCfgDnodeReq dcfgReq = {0};
260✔
547
  if (strcasecmp(cfgReq.config, "resetlog") == 0) {
260✔
548
    tstrncpy(dcfgReq.config, "resetlog", 9);
2✔
549
    goto _send_req;
2✔
550
#ifdef TD_ENTERPRISE
551
  } else if (strncasecmp(cfgReq.config, "s3blocksize", 12) == 0) {
258!
552
    int32_t optLen = strlen("s3blocksize");
×
553
    int32_t flag = -1;
×
554
    int32_t code = mndMCfgGetValInt32(&cfgReq, optLen, &flag);
×
555
    if (code < 0) {
×
556
      goto _err_out;
×
557
    }
558

559
    if (flag > 1024 * 1024 || (flag > -1 && flag < 1024) || flag < -1) {
×
560
      mError("dnode:%d, failed to config s3blocksize since value:%d. Valid range: -1 or [1024, 1024 * 1024]",
×
561
             cfgReq.dnodeId, flag);
562
      code = TSDB_CODE_INVALID_CFG;
×
563
      goto _err_out;
×
564
    }
565

566
    tstrncpy(dcfgReq.config, "s3blocksize", 12);
×
567
    snprintf(dcfgReq.value, TSDB_DNODE_VALUE_LEN, "%d", flag);
×
568
#endif
569
  } else {
570
    TAOS_CHECK_GOTO(mndMCfg2DCfg(&cfgReq, &dcfgReq), &lino, _err_out);
258✔
571
    if (strlen(dcfgReq.config) > TSDB_DNODE_CONFIG_LEN) {
254!
572
      mError("dnode:%d, failed to config since config is too long", cfgReq.dnodeId);
×
573
      code = TSDB_CODE_INVALID_CFG;
×
574
      goto _err_out;
×
575
    }
576
    if (strncasecmp(dcfgReq.config, "enableWhiteList", strlen("enableWhiteList")) == 0) {
254✔
577
      updateIpWhiteList = 1;
2✔
578
    }
579

580
    CfgAlterType alterType = (cfgReq.dnodeId == 0 || cfgReq.dnodeId == -1) ? CFG_ALTER_ALL_DNODES : CFG_ALTER_DNODE;
254!
581
    TAOS_CHECK_GOTO(cfgCheckRangeForDynUpdate(taosGetCfg(), dcfgReq.config, dcfgReq.value, true, alterType), &lino,
254✔
582
                    _err_out);
583
  }
584
  SConfigItem *pItem = cfgGetItem(taosGetCfg(), dcfgReq.config);
217✔
585
  // Update config in sdb.
586
  if (pItem == NULL) {
217!
587
    mError("failed to find config:%s while process config dnode req", cfgReq.config);
×
588
    code = TSDB_CODE_CFG_NOT_FOUND;
×
589
    goto _err_out;
×
590
  }
591
  if (pItem->category == CFG_CATEGORY_GLOBAL) {
217✔
592
    TAOS_CHECK_GOTO(mndConfigUpdateTrans(pMnode, dcfgReq.config, dcfgReq.value, pItem->dtype, ++vObj->i32), &lino,
140!
593
                    _err_out);
594
  }
595
_send_req :
217✔
596

597
{  // audit
598
  char obj[50] = {0};
219✔
599
  (void)tsnprintf(obj, sizeof(obj), "%d", cfgReq.dnodeId);
219✔
600

601
  auditRecord(pReq, pMnode->clusterId, "alterDnode", obj, "", cfgReq.sql, cfgReq.sqlLen);
219✔
602
}
603
  dcfgReq.version = vObj->i32;
219✔
604
  code = mndSendCfgDnodeReq(pMnode, cfgReq.dnodeId, &dcfgReq);
219✔
605
  if (code != 0) {
219✔
606
    mError("failed to send config req to dnode:%d, since %s", cfgReq.dnodeId, tstrerror(code));
5!
607
    goto _err_out;
5✔
608
  }
609
  // dont care suss or succ;
610
  if (updateIpWhiteList) mndRefreshUserIpWhiteList(pMnode);
214✔
611
  tFreeSMCfgDnodeReq(&cfgReq);
214✔
612
  sdbRelease(pMnode->pSdb, vObj);
214✔
613
  TAOS_RETURN(code);
214✔
614

615
_err_out:
53✔
616
  mError("failed to process config dnode req, since %s", tstrerror(code));
53!
617
  tFreeSMCfgDnodeReq(&cfgReq);
53✔
618
  sdbRelease(pMnode->pSdb, vObj);
53✔
619
  TAOS_RETURN(code);
53✔
620
}
621

622
static int32_t mndProcessConfigDnodeRsp(SRpcMsg *pRsp) {
×
623
  mInfo("config rsp from dnode");
×
624
  return 0;
×
625
}
626

627
static int32_t mndTryRebuildConfigSdbRsp(SRpcMsg *pRsp) {
734✔
628
  mInfo("rebuild config sdb rsp");
734!
629
  return 0;
734✔
630
}
631

632
// get int32_t value from 'SMCfgDnodeReq'
633
static int32_t mndMCfgGetValInt32(SMCfgDnodeReq *pMCfgReq, int32_t optLen, int32_t *pOutValue) {
×
634
  int32_t code = 0;
×
635
  if (' ' != pMCfgReq->config[optLen] && 0 != pMCfgReq->config[optLen]) {
×
636
    goto _err;
×
637
  }
638

639
  if (' ' == pMCfgReq->config[optLen]) {
×
640
    // 'key value'
641
    if (strlen(pMCfgReq->value) != 0) goto _err;
×
642
    *pOutValue = taosStr2Int32(pMCfgReq->config + optLen + 1, NULL, 10);
×
643
  } else {
644
    // 'key' 'value'
645
    if (strlen(pMCfgReq->value) == 0) goto _err;
×
646
    *pOutValue = taosStr2Int32(pMCfgReq->value, NULL, 10);
×
647
  }
648

649
  TAOS_RETURN(code);
×
650

651
_err:
×
652
  mError(" failed to set config since:%s", tstrerror(code));
×
653
  TAOS_RETURN(code);
×
654
}
655

656
static int32_t mndConfigUpdateTrans(SMnode *pMnode, const char *name, char *pValue, ECfgDataType dtype,
140✔
657
                                    int32_t tsmmConfigVersion) {
658
  int32_t     code = -1;
140✔
659
  int32_t     lino = -1;
140✔
660
  SConfigObj *pVersion = taosMemoryMalloc(sizeof(SConfigObj)), *pObj = taosMemoryMalloc(sizeof(SConfigObj));
140!
661
  if (pVersion == NULL || pObj == NULL) {
140!
662
    code = terrno;
×
663
    goto _OVER;
×
664
  }
665
  tstrncpy(pVersion->name, "tsmmConfigVersion", CFG_NAME_MAX_LEN);
140✔
666
  pVersion->dtype = CFG_DTYPE_INT32;
140✔
667
  pVersion->i32 = tsmmConfigVersion;
140✔
668

669
  pObj->dtype = dtype;
140✔
670
  tstrncpy(pObj->name, name, CFG_NAME_MAX_LEN);
140✔
671

672
  TAOS_CHECK_GOTO(mndUpdateObj(pObj, name, pValue), &lino, _OVER);
140!
673
  STrans *pTrans = mndTransCreate(pMnode, TRN_POLICY_ROLLBACK, TRN_CONFLICT_NOTHING, NULL, "update-config");
140✔
674
  if (pTrans == NULL) {
140!
675
    code = terrno;
×
676
    goto _OVER;
×
677
  }
678
  mInfo("trans:%d, used to update config:%s to value:%s", pTrans->id, name, pValue);
140!
679
  TAOS_CHECK_GOTO(mndSetCreateConfigCommitLogs(pTrans, pVersion), &lino, _OVER);
140!
680
  TAOS_CHECK_GOTO(mndSetCreateConfigCommitLogs(pTrans, pObj), &lino, _OVER);
140!
681
  if ((code = mndTransPrepare(pMnode, pTrans)) != 0) goto _OVER;
140!
682
  code = 0;
140✔
683
_OVER:
140✔
684
  if (code != 0) {
140!
685
    mError("failed to update config:%s to value:%s, since %s", name, pValue, tstrerror(code));
×
686
  }
687
  mndTransDrop(pTrans);
140✔
688
  tFreeSConfigObj(pVersion);
140✔
689
  taosMemoryFree(pVersion);
140!
690
  tFreeSConfigObj(pObj);
140✔
691
  taosMemoryFree(pObj);
140!
692
  return code;
140✔
693
}
694

695
static int32_t initConfigArrayFromSdb(SMnode *pMnode, SArray *array) {
1,943✔
696
  int32_t     code = 0;
1,943✔
697
  SSdb       *pSdb = pMnode->pSdb;
1,943✔
698
  void       *pIter = NULL;
1,943✔
699
  SConfigObj *obj = NULL;
1,943✔
700

701
  while (1) {
173,179✔
702
    pIter = sdbFetch(pSdb, SDB_CFG, pIter, (void **)&obj);
175,122✔
703
    if (pIter == NULL) break;
175,122✔
704
    if (obj == NULL) {
173,179!
705
      code = TSDB_CODE_OUT_OF_MEMORY;
×
706
      goto _exit;
×
707
    }
708
    if (strcasecmp(obj->name, "tsmmConfigVersion") == 0) {
173,179✔
709
      sdbRelease(pSdb, obj);
1,943✔
710
      continue;
1,943✔
711
    }
712
    SConfigItem item = {0};
171,236✔
713
    item.dtype = obj->dtype;
171,236✔
714
    item.name = taosStrdup(obj->name);
171,236!
715
    if (item.name == NULL) {
171,236!
716
      code = terrno;
×
717
      sdbCancelFetch(pSdb, pIter);
×
718
      sdbRelease(pSdb, obj);
×
719
      goto _exit;
×
720
    }
721
    switch (obj->dtype) {
171,236!
722
      case CFG_DTYPE_NONE:
×
723
        break;
×
724
      case CFG_DTYPE_BOOL:
36,556✔
725
        item.bval = obj->bval;
36,556✔
726
        break;
36,556✔
727
      case CFG_DTYPE_INT32:
88,504✔
728
        item.i32 = obj->i32;
88,504✔
729
        break;
88,504✔
730
      case CFG_DTYPE_INT64:
15,392✔
731
        item.i64 = obj->i64;
15,392✔
732
        break;
15,392✔
733
      case CFG_DTYPE_FLOAT:
5,772✔
734
      case CFG_DTYPE_DOUBLE:
735
        item.fval = obj->fval;
5,772✔
736
        break;
5,772✔
737
      case CFG_DTYPE_STRING:
25,012✔
738
      case CFG_DTYPE_DIR:
739
      case CFG_DTYPE_LOCALE:
740
      case CFG_DTYPE_CHARSET:
741
      case CFG_DTYPE_TIMEZONE:
742
        item.str = taosStrdup(obj->str);
25,012!
743
        if (item.str == NULL) {
25,012!
744
          sdbCancelFetch(pSdb, pIter);
×
745
          sdbRelease(pSdb, obj);
×
746
          code = terrno;
×
747
          goto _exit;
×
748
        }
749
        break;
25,012✔
750
    }
751
    if (taosArrayPush(array, &item) == NULL) {
171,236!
752
      sdbCancelFetch(pSdb, pIter);
×
753
      sdbRelease(pSdb, obj);
×
754
      code = TSDB_CODE_OUT_OF_MEMORY;
×
755
      goto _exit;
×
756
      break;
757
    }
758
    sdbRelease(pSdb, obj);
171,236✔
759
  }
760
_exit:
1,943✔
761
  if (code != 0) {
1,943!
762
    mError("failed to init config array from sdb, since %s", tstrerror(code));
×
763
  }
764
  return code;
1,943✔
765
}
766

767
static void cfgArrayCleanUp(SArray *array) {
2,365✔
768
  if (array == NULL) {
2,365!
769
    return;
×
770
  }
771

772
  int32_t sz = taosArrayGetSize(array);
2,365✔
773
  for (int32_t i = 0; i < sz; ++i) {
173,601✔
774
    SConfigItem *item = taosArrayGet(array, i);
171,236✔
775
    if (item->dtype == CFG_DTYPE_STRING || item->dtype == CFG_DTYPE_DIR || item->dtype == CFG_DTYPE_LOCALE ||
171,236!
776
        item->dtype == CFG_DTYPE_CHARSET || item->dtype == CFG_DTYPE_TIMEZONE) {
150,072✔
777
      taosMemoryFreeClear(item->str);
25,012!
778
    }
779
    taosMemoryFreeClear(item->name);
171,236!
780
  }
781

782
  taosArrayDestroy(array);
2,365✔
783
}
784

785
static void cfgObjArrayCleanUp(SArray *array) {
729✔
786
  if (array == NULL) {
729!
787
    return;
×
788
  }
789
  int32_t sz = taosArrayGetSize(array);
729✔
790
  for (int32_t i = 0; i < sz; ++i) {
729!
791
    SConfigObj *obj = taosArrayGet(array, i);
×
792
    tFreeSConfigObj(obj);
×
793
  }
794
  taosArrayDestroy(array);
729✔
795
}
796

797
static SArray *initVariablesFromItems(SArray *pItems, const char* likePattern) {
36✔
798
  if (pItems == NULL) {
36!
799
    return NULL;
×
800
  }
801

802
  int32_t sz = taosArrayGetSize(pItems);
36✔
803

804
  SArray *pInfos = taosArrayInit(sz, sizeof(SVariablesInfo));
36✔
805
  if (pInfos == NULL) {
36!
806
    mError("failed to init array while init variables from items, since %s", tstrerror(terrno));
×
807
    return NULL;
×
808
  }
809
  for (int32_t i = 0; i < sz; ++i) {
3,240✔
810
    SConfigItem   *pItem = taosArrayGet(pItems, i);
3,204✔
811
    SVariablesInfo info = {0};
3,204✔
812
    tstrncpy(info.name, pItem->name, sizeof(info.name));
3,204✔
813
    if (likePattern != NULL && rawStrPatternMatch(pItem->name, likePattern) != TSDB_PATTERN_MATCH) {
3,204✔
814
      continue;
1,724✔
815
    }
816

817
    // init info value
818
    switch (pItem->dtype) {
1,480!
819
      case CFG_DTYPE_NONE:
×
820
        break;
×
821
      case CFG_DTYPE_BOOL:
312✔
822
        tsnprintf(info.value, sizeof(info.value), "%d", pItem->bval);
312✔
823
        break;
312✔
824
      case CFG_DTYPE_INT32:
776✔
825
        tsnprintf(info.value, sizeof(info.value), "%d", pItem->i32);
776✔
826
        break;
776✔
827
      case CFG_DTYPE_INT64:
128✔
828
        tsnprintf(info.value, sizeof(info.value), "%" PRId64, pItem->i64);
128✔
829
        break;
128✔
830
      case CFG_DTYPE_FLOAT:
48✔
831
      case CFG_DTYPE_DOUBLE:
832
        tsnprintf(info.value, sizeof(info.value), "%f", pItem->fval);
48✔
833
        break;
48✔
834
      case CFG_DTYPE_STRING:
216✔
835
      case CFG_DTYPE_DIR:
836
      case CFG_DTYPE_LOCALE:
837
      case CFG_DTYPE_CHARSET:
838
      case CFG_DTYPE_TIMEZONE:
839
        tsnprintf(info.value, sizeof(info.value), "%s", pItem->str);
216✔
840
        break;
216✔
841
    }
842

843
    // init info scope
844
    switch (pItem->scope) {
1,480!
845
      case CFG_SCOPE_SERVER:
1,240✔
846
        tstrncpy(info.scope, "server", sizeof(info.scope));
1,240✔
847
        break;
1,240✔
848
      case CFG_SCOPE_CLIENT:
×
849
        tstrncpy(info.scope, "client", sizeof(info.scope));
×
850
        break;
×
851
      case CFG_SCOPE_BOTH:
240✔
852
        tstrncpy(info.scope, "both", sizeof(info.scope));
240✔
853
        break;
240✔
854
      default:
×
855
        tstrncpy(info.scope, "unknown", sizeof(info.scope));
×
856
        break;
×
857
    }
858
    // init info category
859
    switch (pItem->category) {
1,480!
860
      case CFG_CATEGORY_GLOBAL:
1,480✔
861
        tstrncpy(info.category, "global", sizeof(info.category));
1,480✔
862
        break;
1,480✔
863
      case CFG_CATEGORY_LOCAL:
×
864
        tstrncpy(info.category, "local", sizeof(info.category));
×
865
        break;
×
866
      default:
×
867
        tstrncpy(info.category, "unknown", sizeof(info.category));
×
868
        break;
×
869
    }
870
    if (NULL == taosArrayPush(pInfos, &info)) {
1,480!
871
      mError("failed to push info to array while init variables from items,since %s", tstrerror(terrno));
×
872
      taosArrayDestroy(pInfos);
×
873
      return NULL;
×
874
    }
875
  }
876

877
  return pInfos;
36✔
878
}
879

880
static int32_t mndProcessShowVariablesReq(SRpcMsg *pReq) {
36✔
881
  SShowVariablesRsp rsp = {0};
36✔
882
  int32_t           code = TSDB_CODE_SUCCESS;
36✔
883
  SShowVariablesReq req = {0};
36✔
884
  SArray           *array = NULL;
36✔
885

886
  code = tDeserializeSShowVariablesReq(pReq->pCont, pReq->contLen, &req);
36✔
887
  if (code != 0) {
36!
888
    mError("failed to deserialize config req, since %s", terrstr());
×
889
    goto _OVER;
×
890
  }
891

892
  if ((code = mndCheckOperPrivilege(pReq->info.node, pReq->info.conn.user, MND_OPER_SHOW_VARIABLES)) != 0) {
36!
893
    goto _OVER;
×
894
  }
895

896
  SVariablesInfo info = {0};
36✔
897
  char          *likePattern = req.opType == OP_TYPE_LIKE ? req.val : NULL;
36✔
898
  rsp.variables = initVariablesFromItems(taosGetGlobalCfg(tsCfg), likePattern);
36✔
899
  if (rsp.variables == NULL) {
36!
900
    code = terrno;
×
901
    goto _OVER;
×
902
  }
903
  int32_t rspLen = tSerializeSShowVariablesRsp(NULL, 0, &rsp);
36✔
904
  void   *pRsp = rpcMallocCont(rspLen);
36✔
905
  if (pRsp == NULL) {
36!
906
    code = terrno;
×
907
    goto _OVER;
×
908
  }
909

910
  if ((rspLen = tSerializeSShowVariablesRsp(pRsp, rspLen, &rsp)) <= 0) {
36!
911
    rpcFreeCont(pRsp);
×
912
    code = rspLen;
×
913
    goto _OVER;
×
914
  }
915

916
  pReq->info.rspLen = rspLen;
36✔
917
  pReq->info.rsp = pRsp;
36✔
918
  code = 0;
36✔
919

920
_OVER:
36✔
921

922
  if (code != 0) {
36!
923
    mError("failed to get show variables info since %s", tstrerror(code));
×
924
  }
925
  tFreeSShowVariablesReq(&req);
36✔
926
  tFreeSShowVariablesRsp(&rsp);
36✔
927
  TAOS_RETURN(code);
36✔
928
}
929

930
int32_t compareSConfigItem(const SConfigObj *item1, SConfigItem *item2, bool *compare) {
×
931
  *compare = true;
×
932
  switch (item1->dtype) {
×
933
    case CFG_DTYPE_BOOL:
×
934
      if (item1->bval != item2->bval) {
×
935
        item2->bval = item1->bval;
×
936
        *compare = false;
×
937
      }
938
      break;
×
939
    case CFG_DTYPE_FLOAT:
×
940
      if (item1->fval != item2->fval) {
×
941
        item2->fval = item1->fval;
×
942
        *compare = false;
×
943
      }
944
      break;
×
945
    case CFG_DTYPE_INT32:
×
946
      if (item1->i32 != item2->i32) {
×
947
        item2->i32 = item1->i32;
×
948
        *compare = false;
×
949
      }
950
      break;
×
951
    case CFG_DTYPE_INT64:
×
952
      if (item1->i64 != item2->i64) {
×
953
        item2->i64 = item1->i64;
×
954
        *compare = false;
×
955
      }
956
      break;
×
957
    case CFG_DTYPE_STRING:
×
958
    case CFG_DTYPE_DIR:
959
    case CFG_DTYPE_LOCALE:
960
    case CFG_DTYPE_CHARSET:
961
    case CFG_DTYPE_TIMEZONE:
962
      if (strcmp(item1->str, item2->str) != 0) {
×
963
        item2->str = taosStrdup(item1->str);
×
964
        if (item2->str == NULL) {
×
965
          return TSDB_CODE_OUT_OF_MEMORY;
×
966
        }
967
        *compare = false;
×
968
      }
969
      break;
×
970
    default:
×
971
      *compare = false;
×
972
      return TSDB_CODE_INVALID_CFG;
×
973
  }
974
  return TSDB_CODE_SUCCESS;
×
975
}
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