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

taosdata / TDengine / #3533

20 Nov 2024 07:11AM UTC coverage: 58.848% (-1.9%) from 60.78%
#3533

push

travis-ci

web-flow
Merge pull request #28823 from taosdata/fix/3.0/TD-32587

fix:[TD-32587]fix stmt segmentation fault

115578 of 252434 branches covered (45.79%)

Branch coverage included in aggregate %.

1 of 4 new or added lines in 1 file covered. (25.0%)

8038 existing lines in 233 files now uncovered.

194926 of 275199 relevant lines covered (70.83%)

1494459.59 hits per line

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

58.41
/source/dnode/vnode/src/meta/metaTable.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
#include "meta.h"
17

18
extern SDmNotifyHandle dmNotifyHdl;
19

20
static int  metaSaveJsonVarToIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry, const SSchema *pSchema);
21
static int  metaDelJsonVarFromIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry, const SSchema *pSchema);
22
static int  metaSaveToTbDb(SMeta *pMeta, const SMetaEntry *pME);
23
static int  metaUpdateUidIdx(SMeta *pMeta, const SMetaEntry *pME);
24
static int  metaUpdateNameIdx(SMeta *pMeta, const SMetaEntry *pME);
25
static void metaUpdateTtl(SMeta *pMeta, const SMetaEntry *pME);
26
static int  metaUpdateChangeTime(SMeta *pMeta, tb_uid_t uid, int64_t changeTimeMs);
27
static int  metaSaveToSkmDb(SMeta *pMeta, const SMetaEntry *pME);
28
static int  metaUpdateCtbIdx(SMeta *pMeta, const SMetaEntry *pME);
29
static int  metaUpdateSuidIdx(SMeta *pMeta, const SMetaEntry *pME);
30
static int  metaUpdateTagIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry);
31
static int  metaDropTableByUid(SMeta *pMeta, tb_uid_t uid, int *type, tb_uid_t *pSuid, int8_t *pSysTbl);
32
static void metaDestroyTagIdxKey(STagIdxKey *pTagIdxKey);
33
// opt ins_tables query
34
static int metaUpdateBtimeIdx(SMeta *pMeta, const SMetaEntry *pME);
35
static int metaDeleteBtimeIdx(SMeta *pMeta, const SMetaEntry *pME);
36
static int metaUpdateNcolIdx(SMeta *pMeta, const SMetaEntry *pME);
37
static int metaDeleteNcolIdx(SMeta *pMeta, const SMetaEntry *pME);
38

39
static int32_t updataTableColCmpr(SColCmprWrapper *pWp, SSchema *pSchema, int8_t add, uint32_t compress) {
129✔
40
  int32_t nCols = pWp->nCols;
129✔
41
  int32_t ver = pWp->version;
129✔
42
  if (add) {
129✔
43
    SColCmpr *p = taosMemoryCalloc(1, sizeof(SColCmpr) * (nCols + 1));
70✔
44
    if (p == NULL) {
70!
45
      return terrno;
×
46
    }
47

48
    memcpy(p, pWp->pColCmpr, sizeof(SColCmpr) * nCols);
70✔
49

50
    SColCmpr *pCol = p + nCols;
70✔
51
    pCol->id = pSchema->colId;
70✔
52
    pCol->alg = compress;
70✔
53
    pWp->nCols = nCols + 1;
70✔
54
    pWp->version = ver;
70✔
55
    pWp->pColCmpr = p;
70✔
56
  } else {
57
    for (int32_t i = 0; i < nCols; i++) {
8,497!
58
      SColCmpr *pOCmpr = &pWp->pColCmpr[i];
8,497✔
59
      if (pOCmpr->id == pSchema->colId) {
8,497✔
60
        int32_t left = (nCols - i - 1) * sizeof(SColCmpr);
59✔
61
        if (left) {
59✔
62
          memmove(pWp->pColCmpr + i, pWp->pColCmpr + i + 1, left);
35✔
63
        }
64
        nCols--;
59✔
65
        break;
59✔
66
      }
67
    }
68
    pWp->nCols = nCols;
59✔
69
    pWp->version = ver;
59✔
70
  }
71
  return 0;
129✔
72
}
73
static void metaGetEntryInfo(const SMetaEntry *pEntry, SMetaInfo *pInfo) {
44,759✔
74
  pInfo->uid = pEntry->uid;
44,759✔
75
  pInfo->version = pEntry->version;
44,759✔
76
  if (pEntry->type == TSDB_SUPER_TABLE) {
44,759✔
77
    pInfo->suid = pEntry->uid;
13,358✔
78
    pInfo->skmVer = pEntry->stbEntry.schemaRow.version;
13,358✔
79
  } else if (pEntry->type == TSDB_CHILD_TABLE) {
31,401✔
80
    pInfo->suid = pEntry->ctbEntry.suid;
29,063✔
81
    pInfo->skmVer = 0;
29,063✔
82
  } else if (pEntry->type == TSDB_NORMAL_TABLE) {
2,338!
83
    pInfo->suid = 0;
2,641✔
84
    pInfo->skmVer = pEntry->ntbEntry.schemaRow.version;
2,641✔
85
  } else {
86
    metaError("meta/table: invalide table type: %" PRId8 " get entry info failed.", pEntry->type);
×
87
  }
88
}
44,759✔
89

90
static int metaUpdateMetaRsp(tb_uid_t uid, char *tbName, SSchemaWrapper *pSchema, STableMetaRsp *pMetaRsp) {
2,598✔
91
  pMetaRsp->pSchemas = taosMemoryMalloc(pSchema->nCols * sizeof(SSchema));
2,598✔
92
  if (NULL == pMetaRsp->pSchemas) {
2,598!
93
    return terrno;
×
94
  }
95

96
  pMetaRsp->pSchemaExt = taosMemoryMalloc(pSchema->nCols * sizeof(SSchemaExt));
2,598✔
97
  if (pMetaRsp->pSchemaExt == NULL) {
2,598!
98
    taosMemoryFree(pMetaRsp->pSchemas);
×
99
    return terrno;
×
100
  }
101

102
  tstrncpy(pMetaRsp->tbName, tbName, TSDB_TABLE_NAME_LEN);
2,598✔
103
  pMetaRsp->numOfColumns = pSchema->nCols;
2,598✔
104
  pMetaRsp->tableType = TSDB_NORMAL_TABLE;
2,598✔
105
  pMetaRsp->sversion = pSchema->version;
2,598✔
106
  pMetaRsp->tuid = uid;
2,598✔
107

108
  memcpy(pMetaRsp->pSchemas, pSchema->pSchema, pSchema->nCols * sizeof(SSchema));
2,598✔
109

110
  return 0;
2,598✔
111
}
112

113
static int metaSaveJsonVarToIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry, const SSchema *pSchema) {
169✔
114
  int32_t code = 0;
169✔
115

116
#ifdef USE_INVERTED_INDEX
117
  if (pMeta->pTagIvtIdx == NULL || pCtbEntry == NULL) {
169!
118
    return TSDB_CODE_INVALID_PARA;
×
119
  }
120
  void       *data = pCtbEntry->ctbEntry.pTags;
169✔
121
  const char *tagName = pSchema->name;
169✔
122

123
  tb_uid_t    suid = pCtbEntry->ctbEntry.suid;
169✔
124
  tb_uid_t    tuid = pCtbEntry->uid;
169✔
125
  const void *pTagData = pCtbEntry->ctbEntry.pTags;
169✔
126
  int32_t     nTagData = 0;
169✔
127

128
  SArray *pTagVals = NULL;
169✔
129
  code = tTagToValArray((const STag *)data, &pTagVals);
169✔
130
  if (code) {
169!
131
    return code;
×
132
  }
133

134
  SIndexMultiTerm *terms = indexMultiTermCreate();
169✔
135
  if (terms == NULL) {
169!
136
    return terrno;
×
137
  }
138

139
  int16_t nCols = taosArrayGetSize(pTagVals);
169✔
140
  for (int i = 0; i < nCols; i++) {
360✔
141
    STagVal *pTagVal = (STagVal *)taosArrayGet(pTagVals, i);
191✔
142
    char     type = pTagVal->type;
191✔
143

144
    char   *key = pTagVal->pKey;
191✔
145
    int32_t nKey = strlen(key);
191✔
146

147
    SIndexTerm *term = NULL;
191✔
148
    if (type == TSDB_DATA_TYPE_NULL) {
191✔
149
      term = indexTermCreate(suid, ADD_VALUE, TSDB_DATA_TYPE_VARCHAR, key, nKey, NULL, 0);
18✔
150
    } else if (type == TSDB_DATA_TYPE_NCHAR) {
173✔
151
      if (pTagVal->nData > 0) {
91✔
152
        char *val = taosMemoryCalloc(1, pTagVal->nData + VARSTR_HEADER_SIZE);
79✔
153
        if (val == NULL) {
79!
154
          TAOS_CHECK_GOTO(terrno, NULL, _exception);
×
155
        }
156
        int32_t len = taosUcs4ToMbs((TdUcs4 *)pTagVal->pData, pTagVal->nData, val + VARSTR_HEADER_SIZE);
79✔
157
        if (len < 0) {
79!
158
          TAOS_CHECK_GOTO(len, NULL, _exception);
×
159
        }
160
        memcpy(val, (uint16_t *)&len, VARSTR_HEADER_SIZE);
79✔
161
        type = TSDB_DATA_TYPE_VARCHAR;
79✔
162
        term = indexTermCreate(suid, ADD_VALUE, type, key, nKey, val, len);
79✔
163
        taosMemoryFree(val);
79✔
164
      } else if (pTagVal->nData == 0) {
12!
165
        term = indexTermCreate(suid, ADD_VALUE, TSDB_DATA_TYPE_VARCHAR, key, nKey, pTagVal->pData, 0);
12✔
166
      }
167
    } else if (type == TSDB_DATA_TYPE_DOUBLE) {
82✔
168
      double val = *(double *)(&pTagVal->i64);
64✔
169
      int    len = sizeof(val);
64✔
170
      term = indexTermCreate(suid, ADD_VALUE, type, key, nKey, (const char *)&val, len);
64✔
171
    } else if (type == TSDB_DATA_TYPE_BOOL) {
18!
172
      int val = *(int *)(&pTagVal->i64);
18✔
173
      int len = sizeof(val);
18✔
174
      term = indexTermCreate(suid, ADD_VALUE, TSDB_DATA_TYPE_BOOL, key, nKey, (const char *)&val, len);
18✔
175
    }
176

177
    if (term != NULL) {
191!
178
      int32_t ret = indexMultiTermAdd(terms, term);
191✔
179
      if (ret < 0) {
191!
180
        metaError("vgId:%d, failed to add term to multi term, uid: %" PRId64 ", key: %s, type: %d, ret: %d",
×
181
                  TD_VID(pMeta->pVnode), tuid, key, type, ret);
182
      }
183
    } else {
184
      code = terrno;
×
185
      goto _exception;
×
186
    }
187
  }
188
  code = indexJsonPut(pMeta->pTagIvtIdx, terms, tuid);
169✔
189
  indexMultiTermDestroy(terms);
169✔
190

191
  taosArrayDestroy(pTagVals);
169✔
192
#endif
193
  return code;
169✔
194
_exception:
×
195
  indexMultiTermDestroy(terms);
×
196
  taosArrayDestroy(pTagVals);
×
197
  return code;
×
198
}
199
int metaDelJsonVarFromIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry, const SSchema *pSchema) {
6✔
200
#ifdef USE_INVERTED_INDEX
201
  if (pMeta->pTagIvtIdx == NULL || pCtbEntry == NULL) {
6!
202
    return TSDB_CODE_INVALID_PARA;
×
203
  }
204
  void       *data = pCtbEntry->ctbEntry.pTags;
6✔
205
  const char *tagName = pSchema->name;
6✔
206

207
  tb_uid_t    suid = pCtbEntry->ctbEntry.suid;
6✔
208
  tb_uid_t    tuid = pCtbEntry->uid;
6✔
209
  const void *pTagData = pCtbEntry->ctbEntry.pTags;
6✔
210
  int32_t     nTagData = 0;
6✔
211

212
  SArray *pTagVals = NULL;
6✔
213
  int32_t code = tTagToValArray((const STag *)data, &pTagVals);
6✔
214
  if (code) {
6!
215
    return code;
×
216
  }
217

218
  SIndexMultiTerm *terms = indexMultiTermCreate();
6✔
219
  if (terms == NULL) {
6!
220
    return terrno;
×
221
  }
222

223
  int16_t nCols = taosArrayGetSize(pTagVals);
6✔
224
  for (int i = 0; i < nCols; i++) {
12✔
225
    STagVal *pTagVal = (STagVal *)taosArrayGet(pTagVals, i);
6✔
226
    char     type = pTagVal->type;
6✔
227

228
    char   *key = pTagVal->pKey;
6✔
229
    int32_t nKey = strlen(key);
6✔
230

231
    SIndexTerm *term = NULL;
6✔
232
    if (type == TSDB_DATA_TYPE_NULL) {
6!
233
      term = indexTermCreate(suid, DEL_VALUE, TSDB_DATA_TYPE_VARCHAR, key, nKey, NULL, 0);
×
234
    } else if (type == TSDB_DATA_TYPE_NCHAR) {
6✔
235
      if (pTagVal->nData > 0) {
3!
236
        char *val = taosMemoryCalloc(1, pTagVal->nData + VARSTR_HEADER_SIZE);
3✔
237
        if (val == NULL) {
3!
238
          TAOS_CHECK_GOTO(terrno, NULL, _exception);
×
239
        }
240
        int32_t len = taosUcs4ToMbs((TdUcs4 *)pTagVal->pData, pTagVal->nData, val + VARSTR_HEADER_SIZE);
3✔
241
        if (len < 0) {
3!
242
          TAOS_CHECK_GOTO(len, NULL, _exception);
×
243
        }
244
        memcpy(val, (uint16_t *)&len, VARSTR_HEADER_SIZE);
3✔
245
        type = TSDB_DATA_TYPE_VARCHAR;
3✔
246
        term = indexTermCreate(suid, DEL_VALUE, type, key, nKey, val, len);
3✔
247
        taosMemoryFree(val);
3✔
248
      } else if (pTagVal->nData == 0) {
×
249
        term = indexTermCreate(suid, DEL_VALUE, TSDB_DATA_TYPE_VARCHAR, key, nKey, pTagVal->pData, 0);
×
250
      }
251
    } else if (type == TSDB_DATA_TYPE_DOUBLE) {
3!
252
      double val = *(double *)(&pTagVal->i64);
3✔
253
      int    len = sizeof(val);
3✔
254
      term = indexTermCreate(suid, DEL_VALUE, type, key, nKey, (const char *)&val, len);
3✔
255
    } else if (type == TSDB_DATA_TYPE_BOOL) {
×
256
      int val = *(int *)(&pTagVal->i64);
×
257
      int len = sizeof(val);
×
258
      term = indexTermCreate(suid, DEL_VALUE, TSDB_DATA_TYPE_BOOL, key, nKey, (const char *)&val, len);
×
259
    }
260
    if (term != NULL) {
6!
261
      int32_t ret = indexMultiTermAdd(terms, term);
6✔
262
      if (ret < 0) {
6!
263
        metaError("vgId:%d, failed to add term to multi term, uid: %" PRId64 ", key: %s, type: %d, ret: %d",
×
264
                  TD_VID(pMeta->pVnode), tuid, key, type, ret);
265
      }
266
    } else {
267
      code = terrno;
×
268
      goto _exception;
×
269
    }
270
  }
271
  code = indexJsonPut(pMeta->pTagIvtIdx, terms, tuid);
6✔
272
  indexMultiTermDestroy(terms);
6✔
273
  taosArrayDestroy(pTagVals);
6✔
274
#endif
275
  return code;
6✔
276
_exception:
×
277
  indexMultiTermDestroy(terms);
×
278
  taosArrayDestroy(pTagVals);
×
279
  return code;
×
280
}
281

282
static inline void metaTimeSeriesNotifyCheck(SMeta *pMeta) {
30,249✔
283
#if defined(TD_ENTERPRISE)
284
  int64_t nTimeSeries = metaGetTimeSeriesNum(pMeta, 0);
30,249✔
285
  int64_t deltaTS = nTimeSeries - pMeta->pVnode->config.vndStats.numOfReportedTimeSeries;
30,249✔
286
  if (deltaTS > tsTimeSeriesThreshold) {
30,249✔
287
    if (0 == atomic_val_compare_exchange_8(&dmNotifyHdl.state, 1, 2)) {
15,109✔
288
      if (tsem_post(&dmNotifyHdl.sem) != 0) {
15,110!
289
        metaError("vgId:%d, failed to post semaphore, errno:%d", TD_VID(pMeta->pVnode), errno);
×
290
      }
291
    }
292
  }
293
#endif
294
}
30,254✔
295

296
int metaCreateSTable(SMeta *pMeta, int64_t version, SVCreateStbReq *pReq) {
11,874✔
297
  SMetaEntry  me = {0};
11,874✔
298
  int         kLen = 0;
11,874✔
299
  int         vLen = 0;
11,874✔
300
  const void *pKey = NULL;
11,874✔
301
  const void *pVal = NULL;
11,874✔
302
  void       *pBuf = NULL;
11,874✔
303
  int32_t     szBuf = 0;
11,874✔
304
  void       *p = NULL;
11,874✔
305
  int32_t     code = 0;
11,874✔
306

307
  // validate req
308
  void *pData = NULL;
11,874✔
309
  int   nData = 0;
11,874✔
310
  if (tdbTbGet(pMeta->pNameIdx, pReq->name, strlen(pReq->name) + 1, &pData, &nData) == 0) {
11,874✔
311
    tb_uid_t uid = *(tb_uid_t *)pData;
6✔
312
    tdbFree(pData);
6✔
313
    SMetaInfo info;
314
    if (metaGetInfo(pMeta, uid, &info, NULL) == TSDB_CODE_NOT_FOUND) {
6!
315
      return terrno = TSDB_CODE_PAR_TABLE_NOT_EXIST;
×
316
    }
317
    if (info.uid == info.suid) {
6✔
318
      return 0;
3✔
319
    } else {
320
      return terrno = TSDB_CODE_TDB_TABLE_ALREADY_EXIST;
3✔
321
    }
322
  }
323

324
  // set structs
325
  me.version = version;
11,962✔
326
  me.type = TSDB_SUPER_TABLE;
11,962✔
327
  me.uid = pReq->suid;
11,962✔
328
  me.name = pReq->name;
11,962✔
329
  me.stbEntry.schemaRow = pReq->schemaRow;
11,962✔
330
  me.stbEntry.schemaTag = pReq->schemaTag;
11,962✔
331
  if (pReq->rollup) {
11,962✔
332
    TABLE_SET_ROLLUP(me.flags);
7✔
333
    me.stbEntry.rsmaParam = pReq->rsmaParam;
7✔
334
  }
335
  if (pReq->colCmpred) {
11,962✔
336
    TABLE_SET_COL_COMPRESSED(me.flags);
11,942✔
337
    me.colCmpr = pReq->colCmpr;
11,942✔
338
  }
339

340
  code = metaHandleEntry(pMeta, &me);
11,962✔
341
  if (code) goto _err;
11,988!
342

343
  ++pMeta->pVnode->config.vndStats.numOfSTables;
11,988✔
344

345
  pMeta->changed = true;
11,988✔
346
  metaDebug("vgId:%d, stb:%s is created, suid:%" PRId64, TD_VID(pMeta->pVnode), pReq->name, pReq->suid);
11,988✔
347

348
  return 0;
11,992✔
349

350
_err:
×
351
  metaError("vgId:%d, failed to create stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
×
352
            tstrerror(terrno));
353
  return code;
×
354
}
355

356
int metaDropSTable(SMeta *pMeta, int64_t verison, SVDropStbReq *pReq, SArray *tbUidList) {
308✔
357
  void   *pKey = NULL;
308✔
358
  int     nKey = 0;
308✔
359
  void   *pData = NULL;
308✔
360
  int     nData = 0;
308✔
361
  int     c = 0;
308✔
362
  int     rc = 0;
308✔
363
  int32_t lino;
364
  int32_t ret;
365

366
  // check if super table exists
367
  rc = tdbTbGet(pMeta->pNameIdx, pReq->name, strlen(pReq->name) + 1, &pData, &nData);
308✔
368
  if (rc < 0 || *(tb_uid_t *)pData != pReq->suid) {
309✔
369
    tdbFree(pData);
13✔
370
    return terrno = TSDB_CODE_TDB_STB_NOT_EXIST;
13✔
371
  }
372

373
  // drop all child tables
374
  TBC *pCtbIdxc = NULL;
296✔
375

376
  rc = tdbTbcOpen(pMeta->pCtbIdx, &pCtbIdxc, NULL);
296✔
377
  if (rc) {
296!
378
    return (terrno = rc);
×
379
  }
380

381
  rc = tdbTbcMoveTo(pCtbIdxc, &(SCtbIdxKey){.suid = pReq->suid, .uid = INT64_MIN}, sizeof(SCtbIdxKey), &c);
296✔
382
  if (rc < 0) {
297!
383
    tdbTbcClose(pCtbIdxc);
×
384
    metaWLock(pMeta);
×
385
    goto _drop_super_table;
×
386
  }
387

388
  for (;;) {
389
    rc = tdbTbcNext(pCtbIdxc, &pKey, &nKey, NULL, NULL);
684✔
390
    if (rc < 0) break;
679✔
391

392
    if (((SCtbIdxKey *)pKey)->suid < pReq->suid) {
392✔
393
      continue;
20✔
394
    } else if (((SCtbIdxKey *)pKey)->suid > pReq->suid) {
372✔
395
      break;
8✔
396
    }
397

398
    if (taosArrayPush(tbUidList, &(((SCtbIdxKey *)pKey)->uid)) == NULL) {
731!
399
      tdbFree(pKey);
×
400
      tdbTbcClose(pCtbIdxc);
×
401
      return terrno;
×
402
    }
403
  }
404

405
  tdbTbcClose(pCtbIdxc);
295✔
406

407
  ret = tsdbCacheDropSubTables(pMeta->pVnode->pTsdb, tbUidList, pReq->suid);
295✔
408
  if (ret < 0) {
297!
409
    metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
×
410
              tstrerror(terrno));
411
  }
412

413
  metaWLock(pMeta);
297✔
414

415
  for (int32_t iChild = 0; iChild < taosArrayGetSize(tbUidList); iChild++) {
665✔
416
    tb_uid_t uid = *(tb_uid_t *)taosArrayGet(tbUidList, iChild);
370✔
417
    ret = metaDropTableByUid(pMeta, uid, NULL, NULL, NULL);
370✔
418
    if (ret < 0) {
370!
419
      metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
420
                pReq->suid, tstrerror(terrno));
421
    }
422
  }
423

424
  // drop super table
425
_drop_super_table:
295✔
426
  tdbTbGet(pMeta->pUidIdx, &pReq->suid, sizeof(tb_uid_t), &pData, &nData);
295✔
427
  ret = tdbTbDelete(pMeta->pTbDb, &(STbDbKey){.version = ((SUidIdxVal *)pData)[0].version, .uid = pReq->suid},
297✔
428
                    sizeof(STbDbKey), pMeta->txn);
429
  if (ret < 0) {
296!
430
    metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
×
431
              tstrerror(terrno));
432
  }
433

434
  ret = tdbTbDelete(pMeta->pNameIdx, pReq->name, strlen(pReq->name) + 1, pMeta->txn);
296✔
435
  if (ret < 0) {
297!
436
    metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
×
437
              tstrerror(terrno));
438
  }
439

440
  ret = tdbTbDelete(pMeta->pUidIdx, &pReq->suid, sizeof(tb_uid_t), pMeta->txn);
297✔
441
  if (ret < 0) {
297!
442
    metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
×
443
              tstrerror(terrno));
444
  }
445

446
  ret = tdbTbDelete(pMeta->pSuidIdx, &pReq->suid, sizeof(tb_uid_t), pMeta->txn);
297✔
447
  if (ret < 0) {
297!
448
    metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
×
449
              tstrerror(terrno));
450
  }
451

452
  ret = metaStatsCacheDrop(pMeta, pReq->suid);
297✔
453
  if (ret < 0) {
294✔
454
    metaError("vgId:%d, failed to drop stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, pReq->suid,
100!
455
              tstrerror(terrno));
456
  }
457

458
  metaULock(pMeta);
294✔
459

460
  metaUpdTimeSeriesNum(pMeta);
297✔
461

462
  pMeta->changed = true;
297✔
463

464
_exit:
297✔
465
  tdbFree(pKey);
297✔
466
  tdbFree(pData);
297✔
467
  metaDebug("vgId:%d, super table %s uid:%" PRId64 " is dropped", TD_VID(pMeta->pVnode), pReq->name, pReq->suid);
297✔
468
  return 0;
297✔
469
}
470

UNCOV
471
static int32_t metaGetSubtables(SMeta *pMeta, int64_t suid, SArray *uids) {
×
UNCOV
472
  if (!uids) return TSDB_CODE_INVALID_PARA;
×
473

UNCOV
474
  int   c = 0;
×
UNCOV
475
  void *pKey = NULL;
×
UNCOV
476
  int   nKey = 0;
×
UNCOV
477
  TBC  *pCtbIdxc = NULL;
×
478

UNCOV
479
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pCtbIdx, &pCtbIdxc, NULL));
×
UNCOV
480
  int rc = tdbTbcMoveTo(pCtbIdxc, &(SCtbIdxKey){.suid = suid, .uid = INT64_MIN}, sizeof(SCtbIdxKey), &c);
×
UNCOV
481
  if (rc < 0) {
×
482
    tdbTbcClose(pCtbIdxc);
×
483
    metaWLock(pMeta);
×
484
    return 0;
×
485
  }
486

487
  for (;;) {
UNCOV
488
    rc = tdbTbcNext(pCtbIdxc, &pKey, &nKey, NULL, NULL);
×
UNCOV
489
    if (rc < 0) break;
×
490

UNCOV
491
    if (((SCtbIdxKey *)pKey)->suid < suid) {
×
492
      continue;
×
UNCOV
493
    } else if (((SCtbIdxKey *)pKey)->suid > suid) {
×
494
      break;
×
495
    }
496

UNCOV
497
    if (taosArrayPush(uids, &(((SCtbIdxKey *)pKey)->uid)) == NULL) {
×
498
      tdbFree(pKey);
×
499
      tdbTbcClose(pCtbIdxc);
×
500
      return terrno;
×
501
    }
502
  }
503

UNCOV
504
  tdbFree(pKey);
×
505

UNCOV
506
  tdbTbcClose(pCtbIdxc);
×
UNCOV
507
  return 0;
×
508
}
509

510
int metaAlterSTable(SMeta *pMeta, int64_t version, SVCreateStbReq *pReq) {
1,256✔
511
  SMetaEntry  oStbEntry = {0};
1,256✔
512
  SMetaEntry  nStbEntry = {0};
1,256✔
513
  TBC        *pUidIdxc = NULL;
1,256✔
514
  TBC        *pTbDbc = NULL;
1,256✔
515
  const void *pData;
516
  int         nData;
517
  int64_t     oversion;
518
  SDecoder    dc = {0};
1,256✔
519
  int32_t     ret;
520
  int32_t     c = -2;
1,256✔
521

522
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pUidIdx, &pUidIdxc, NULL));
1,256!
523
  ret = tdbTbcMoveTo(pUidIdxc, &pReq->suid, sizeof(tb_uid_t), &c);
1,258✔
524
  if (ret < 0 || c) {
1,254!
525
    tdbTbcClose(pUidIdxc);
×
526

527
    return terrno = TSDB_CODE_TDB_STB_NOT_EXIST;
×
528
  }
529

530
  ret = tdbTbcGet(pUidIdxc, NULL, NULL, &pData, &nData);
1,255✔
531
  if (ret < 0) {
1,254!
532
    tdbTbcClose(pUidIdxc);
×
533

534
    return terrno = TSDB_CODE_TDB_STB_NOT_EXIST;
×
535
  }
536

537
  oversion = ((SUidIdxVal *)pData)[0].version;
1,254✔
538

539
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pTbDb, &pTbDbc, NULL));
1,254!
540
  ret = tdbTbcMoveTo(pTbDbc, &((STbDbKey){.uid = pReq->suid, .version = oversion}), sizeof(STbDbKey), &c);
1,259✔
541
  if (!(ret == 0 && c == 0)) {
1,259!
542
    tdbTbcClose(pUidIdxc);
1✔
543
    tdbTbcClose(pTbDbc);
×
544

545
    metaError("meta/table: invalide ret: %" PRId32 " or c: %" PRId32 "alter stb failed.", ret, c);
×
546
    return terrno = TSDB_CODE_TDB_STB_NOT_EXIST;
×
547
  }
548

549
  ret = tdbTbcGet(pTbDbc, NULL, NULL, &pData, &nData);
1,258✔
550
  if (ret < 0) {
1,258!
551
    tdbTbcClose(pUidIdxc);
×
552
    tdbTbcClose(pTbDbc);
×
553

554
    return terrno = TSDB_CODE_TDB_STB_NOT_EXIST;
×
555
  }
556

557
  if ((oStbEntry.pBuf = taosMemoryMalloc(nData)) == NULL) {
1,258!
558
    tdbTbcClose(pTbDbc);
×
559
    tdbTbcClose(pUidIdxc);
×
560
    return terrno;
×
561
  }
562
  memcpy(oStbEntry.pBuf, pData, nData);
1,259✔
563
  tDecoderInit(&dc, oStbEntry.pBuf, nData);
1,259✔
564
  ret = metaDecodeEntry(&dc, &oStbEntry);
1,256✔
565
  if (ret < 0) {
1,252!
566
    metaError("vgId:%d, failed to decode stb:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
567
              pReq->suid, tstrerror(ret));
568
    tDecoderClear(&dc);
×
569
    tdbTbcClose(pTbDbc);
×
570
    tdbTbcClose(pUidIdxc);
×
571
    return terrno;
×
572
  }
573

574
  nStbEntry.version = version;
1,252✔
575
  nStbEntry.type = TSDB_SUPER_TABLE;
1,252✔
576
  nStbEntry.uid = pReq->suid;
1,252✔
577
  nStbEntry.name = pReq->name;
1,252✔
578
  nStbEntry.stbEntry.schemaRow = pReq->schemaRow;
1,252✔
579
  nStbEntry.stbEntry.schemaTag = pReq->schemaTag;
1,252✔
580
  nStbEntry.colCmpr = pReq->colCmpr;
1,252✔
581
  TABLE_SET_COL_COMPRESSED(nStbEntry.flags);
1,252✔
582

583
  int     nCols = pReq->schemaRow.nCols;
1,252✔
584
  int     onCols = oStbEntry.stbEntry.schemaRow.nCols;
1,252✔
585
  int32_t deltaCol = nCols - onCols;
1,252✔
586
  bool    updStat = deltaCol != 0 && !metaTbInFilterCache(pMeta, pReq->name, 1);
1,252!
587

588
  if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
1,254!
UNCOV
589
    STsdb  *pTsdb = pMeta->pVnode->pTsdb;
×
UNCOV
590
    SArray *uids = taosArrayInit(8, sizeof(int64_t));
×
UNCOV
591
    if (uids == NULL) {
×
592
      if (oStbEntry.pBuf) taosMemoryFree(oStbEntry.pBuf);
×
593
      tDecoderClear(&dc);
×
594
      tdbTbcClose(pTbDbc);
×
595
      tdbTbcClose(pUidIdxc);
×
596
      return terrno;
×
597
    }
UNCOV
598
    if (deltaCol == 1) {
×
UNCOV
599
      int16_t cid = pReq->schemaRow.pSchema[nCols - 1].colId;
×
UNCOV
600
      int8_t  col_type = pReq->schemaRow.pSchema[nCols - 1].type;
×
601

UNCOV
602
      TAOS_CHECK_RETURN(metaGetSubtables(pMeta, pReq->suid, uids));
×
UNCOV
603
      TAOS_CHECK_RETURN(tsdbCacheNewSTableColumn(pTsdb, uids, cid, col_type));
×
UNCOV
604
    } else if (deltaCol == -1) {
×
UNCOV
605
      int16_t cid = -1;
×
UNCOV
606
      bool    hasPrimaryKey = false;
×
UNCOV
607
      if (onCols >= 2) {
×
UNCOV
608
        hasPrimaryKey = (oStbEntry.stbEntry.schemaRow.pSchema[1].flags & COL_IS_KEY) ? true : false;
×
609
      }
UNCOV
610
      for (int i = 0, j = 0; i < nCols && j < onCols; ++i, ++j) {
×
UNCOV
611
        if (pReq->schemaRow.pSchema[i].colId != oStbEntry.stbEntry.schemaRow.pSchema[j].colId) {
×
UNCOV
612
          cid = oStbEntry.stbEntry.schemaRow.pSchema[j].colId;
×
UNCOV
613
          break;
×
614
        }
615
      }
616

UNCOV
617
      if (cid != -1) {
×
UNCOV
618
        TAOS_CHECK_RETURN(metaGetSubtables(pMeta, pReq->suid, uids));
×
UNCOV
619
        TAOS_CHECK_RETURN(tsdbCacheDropSTableColumn(pTsdb, uids, cid, hasPrimaryKey));
×
620
      }
621
    }
UNCOV
622
    if (uids) taosArrayDestroy(uids);
×
623

UNCOV
624
    tsdbCacheInvalidateSchema(pTsdb, pReq->suid, -1, pReq->schemaRow.version);
×
625
  }
626

627
  metaWLock(pMeta);
1,254✔
628
  // compare two entry
629
  if (oStbEntry.stbEntry.schemaRow.version != pReq->schemaRow.version) {
1,255✔
630
    ret = metaSaveToSkmDb(pMeta, &nStbEntry);
619✔
631
    if (ret < 0) {
617!
632
      metaError("vgId:%d, failed to save skm db:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
633
                pReq->suid, tstrerror(ret));
634
    }
635
  }
636

637
  // update table.db
638
  ret = metaSaveToTbDb(pMeta, &nStbEntry);
1,253✔
639
  if (ret < 0) {
1,255!
640
    metaError("vgId:%d, failed to save tb db:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
641
              pReq->suid, tstrerror(ret));
642
  }
643

644
  // update uid index
645
  ret = metaUpdateUidIdx(pMeta, &nStbEntry);
1,255✔
646
  if (ret < 0) {
1,254!
647
    metaError("vgId:%d, failed to update uid idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
648
              pReq->suid, tstrerror(ret));
649
  }
650

651
  // metaStatsCacheDrop(pMeta, nStbEntry.uid);
652

653
  if (updStat) {
1,255✔
654
    metaUpdateStbStats(pMeta, pReq->suid, 0, deltaCol);
524✔
655
  }
656
  metaULock(pMeta);
1,256✔
657

658
  if (updStat) {
1,260✔
659
    int64_t ctbNum;
660
    ret = metaGetStbStats(pMeta->pVnode, pReq->suid, &ctbNum, NULL);
531✔
661
    if (ret < 0) {
524!
662
      metaError("vgId:%d, failed to get stb stats:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
663
                pReq->suid, tstrerror(ret));
664
    }
665
    pMeta->pVnode->config.vndStats.numOfTimeSeries += (ctbNum * deltaCol);
524✔
666
    metaTimeSeriesNotifyCheck(pMeta);
524✔
667
  }
668

669
  pMeta->changed = true;
1,255✔
670

671
_exit:
1,255✔
672
  if (oStbEntry.pBuf) taosMemoryFree(oStbEntry.pBuf);
1,255!
673
  tDecoderClear(&dc);
1,256✔
674
  tdbTbcClose(pTbDbc);
1,256✔
675
  tdbTbcClose(pUidIdxc);
1,260✔
676
  return 0;
1,259✔
677
}
678
int metaAddIndexToSTable(SMeta *pMeta, int64_t version, SVCreateStbReq *pReq) {
49✔
679
  SMetaEntry oStbEntry = {0};
49✔
680
  SMetaEntry nStbEntry = {0};
49✔
681
  STbDbKey   tbDbKey = {0};
49✔
682

683
  TBC     *pUidIdxc = NULL;
49✔
684
  TBC     *pTbDbc = NULL;
49✔
685
  void    *pData = NULL;
49✔
686
  int      nData = 0;
49✔
687
  int64_t  oversion;
688
  SDecoder dc = {0};
49✔
689
  int32_t  ret;
690
  int32_t  c = -2;
49✔
691
  tb_uid_t suid = pReq->suid;
49✔
692
  int32_t  code = 0;
49✔
693

694
  // get super table
695
  if ((code = tdbTbGet(pMeta->pUidIdx, &suid, sizeof(tb_uid_t), &pData, &nData)) != 0) {
49!
696
    goto _err;
×
697
  }
698

699
  tbDbKey.uid = suid;
49✔
700
  tbDbKey.version = ((SUidIdxVal *)pData)[0].version;
49✔
701
  if ((code = tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &pData, &nData)) != 0) {
49!
702
    goto _err;
×
703
  }
704

705
  tDecoderInit(&dc, pData, nData);
49✔
706
  code = metaDecodeEntry(&dc, &oStbEntry);
49✔
707
  if (code < 0) {
49!
708
    goto _err;
×
709
  }
710

711
  if (oStbEntry.stbEntry.schemaTag.pSchema == NULL || oStbEntry.stbEntry.schemaTag.pSchema == NULL) {
49!
712
    code = TSDB_CODE_INVALID_PARA;
×
713
    goto _err;
×
714
  }
715

716
  if (oStbEntry.stbEntry.schemaTag.version == pReq->schemaTag.version) {
49!
717
    code = TSDB_CODE_INVALID_PARA;
×
718
    goto _err;
×
719
  }
720

721
  if (oStbEntry.stbEntry.schemaTag.nCols != pReq->schemaTag.nCols) {
49!
722
    code = TSDB_CODE_INVALID_PARA;
×
723
    goto _err;
×
724
  }
725

726
  int diffIdx = -1;
49✔
727
  for (int i = 0; i < pReq->schemaTag.nCols; i++) {
258!
728
    SSchema *pNew = pReq->schemaTag.pSchema + i;
258✔
729
    SSchema *pOld = oStbEntry.stbEntry.schemaTag.pSchema + i;
258✔
730
    if (pNew->type != pOld->type || pNew->colId != pOld->colId || pNew->bytes != pOld->bytes ||
258!
731
        strncmp(pOld->name, pNew->name, sizeof(pNew->name))) {
258!
732
      code = TSDB_CODE_INVALID_PARA;
×
733
      goto _err;
×
734
    }
735
    if (IS_IDX_ON(pNew) && !IS_IDX_ON(pOld)) {
258✔
736
      // if (diffIdx != -1) goto _err;
737
      diffIdx = i;
49✔
738
      break;
49✔
739
    }
740
  }
741

742
  if (diffIdx == -1) {
49!
743
    code = TSDB_CODE_INVALID_PARA;
×
744
    goto _err;
×
745
  }
746

747
  // Get target schema info
748
  SSchemaWrapper *pTagSchema = &pReq->schemaTag;
49✔
749
  if (pTagSchema->nCols == 1 && pTagSchema->pSchema[0].type == TSDB_DATA_TYPE_JSON) {
49!
750
    code = TSDB_CODE_INVALID_PARA;
×
751
    goto _err;
×
752
  }
753
  SSchema *pCol = pTagSchema->pSchema + diffIdx;
49✔
754

755
  /*
756
   * iterator all pTdDbc by uid and version
757
   */
758
  TBC *pCtbIdxc = NULL;
49✔
759
  code = tdbTbcOpen(pMeta->pCtbIdx, &pCtbIdxc, NULL);
49✔
760
  if (code != 0) {
49!
761
    goto _err;
×
762
  }
763

764
  code = tdbTbcMoveTo(pCtbIdxc, &(SCtbIdxKey){.suid = suid, .uid = INT64_MIN}, sizeof(SCtbIdxKey), &c);
49✔
765
  if (code < 0) {
49!
766
    tdbTbcClose(pCtbIdxc);
×
767
    goto _err;
×
768
  }
769
  for (;;) {
13,587✔
770
    void *pKey = NULL, *pVal = NULL;
13,636✔
771
    int   nKey = 0, nVal = 0;
13,636✔
772
    code = tdbTbcNext(pCtbIdxc, &pKey, &nKey, &pVal, &nVal);
13,636✔
773
    if (code < 0) {
13,636✔
774
      tdbFree(pKey);
49✔
775
      tdbFree(pVal);
49✔
776
      tdbTbcClose(pCtbIdxc);
49✔
777
      pCtbIdxc = NULL;
49✔
778
      break;
49✔
779
    }
780
    if (((SCtbIdxKey *)pKey)->suid != suid) {
13,587!
UNCOV
781
      tdbFree(pKey);
×
UNCOV
782
      tdbFree(pVal);
×
UNCOV
783
      continue;
×
784
    }
785
    STagIdxKey *pTagIdxKey = NULL;
13,587✔
786
    int32_t     nTagIdxKey;
787

788
    const void *pTagData = NULL;
13,587✔
789
    int32_t     nTagData = 0;
13,587✔
790

791
    SCtbIdxKey *table = (SCtbIdxKey *)pKey;
13,587✔
792
    STagVal     tagVal = {.cid = pCol->colId};
13,587✔
793
    if (tTagGet((const STag *)pVal, &tagVal)) {
13,587!
794
      if (IS_VAR_DATA_TYPE(pCol->type)) {
13,587!
795
        pTagData = tagVal.pData;
2,000✔
796
        nTagData = (int32_t)tagVal.nData;
2,000✔
797
      } else {
798
        pTagData = &(tagVal.i64);
11,587✔
799
        nTagData = tDataTypes[pCol->type].bytes;
11,587✔
800
      }
801
    } else {
802
      if (!IS_VAR_DATA_TYPE(pCol->type)) {
×
803
        nTagData = tDataTypes[pCol->type].bytes;
×
804
      }
805
    }
806
    code = metaCreateTagIdxKey(suid, pCol->colId, pTagData, nTagData, pCol->type, table->uid, &pTagIdxKey, &nTagIdxKey);
13,587✔
807
    tdbFree(pKey);
13,587✔
808
    tdbFree(pVal);
13,587✔
809
    if (code < 0) {
13,587!
810
      metaDestroyTagIdxKey(pTagIdxKey);
×
811
      tdbTbcClose(pCtbIdxc);
×
812
      goto _err;
×
813
    }
814

815
    metaWLock(pMeta);
13,587✔
816
    ret = tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
13,587✔
817
    if (ret < 0) {
13,587!
818
      metaError("vgId:%d, failed to upsert tag idx key:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
819
                pReq->suid, tstrerror(ret));
820
    }
821
    metaULock(pMeta);
13,587✔
822

823
    metaDestroyTagIdxKey(pTagIdxKey);
13,587✔
824
    pTagIdxKey = NULL;
13,587✔
825
  }
826

827
  nStbEntry.version = version;
49✔
828
  nStbEntry.type = TSDB_SUPER_TABLE;
49✔
829
  nStbEntry.uid = pReq->suid;
49✔
830
  nStbEntry.name = pReq->name;
49✔
831
  nStbEntry.stbEntry.schemaRow = pReq->schemaRow;
49✔
832
  nStbEntry.stbEntry.schemaTag = pReq->schemaTag;
49✔
833
  nStbEntry.colCmpr = pReq->colCmpr;
49✔
834

835
  metaWLock(pMeta);
49✔
836
  // update table.db
837
  ret = metaSaveToTbDb(pMeta, &nStbEntry);
49✔
838
  if (ret < 0) {
49!
839
    metaError("vgId:%d, failed to save tb db:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
840
              pReq->suid, tstrerror(ret));
841
  }
842
  // update uid index
843
  ret = metaUpdateUidIdx(pMeta, &nStbEntry);
49✔
844
  if (ret < 0) {
49!
845
    metaError("vgId:%d, failed to update uid idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
846
              pReq->suid, tstrerror(ret));
847
  }
848
  metaULock(pMeta);
49✔
849

850
  if (oStbEntry.pBuf) taosMemoryFree(oStbEntry.pBuf);
49!
851
  tDecoderClear(&dc);
49✔
852
  tdbFree(pData);
49✔
853

854
  tdbTbcClose(pCtbIdxc);
49✔
855
  return TSDB_CODE_SUCCESS;
49✔
856
_err:
×
857
  if (oStbEntry.pBuf) taosMemoryFree(oStbEntry.pBuf);
×
858
  tDecoderClear(&dc);
×
859
  tdbFree(pData);
×
860

861
  return code;
×
862
}
863
int metaDropIndexFromSTable(SMeta *pMeta, int64_t version, SDropIndexReq *pReq) {
32✔
864
  int32_t    code = 0;
32✔
865
  SMetaEntry oStbEntry = {0};
32✔
866
  SMetaEntry nStbEntry = {0};
32✔
867

868
  STbDbKey tbDbKey = {0};
32✔
869
  TBC     *pUidIdxc = NULL;
32✔
870
  TBC     *pTbDbc = NULL;
32✔
871
  int      ret = 0;
32✔
872
  int      c = -2;
32✔
873
  void    *pData = NULL;
32✔
874
  int      nData = 0;
32✔
875
  int64_t  oversion;
876
  SDecoder dc = {0};
32✔
877

878
  tb_uid_t suid = pReq->stbUid;
32✔
879

880
  if ((code = tdbTbGet(pMeta->pUidIdx, &suid, sizeof(tb_uid_t), &pData, &nData)) != 0) {
32!
881
    goto _err;
×
882
  }
883

884
  tbDbKey.uid = suid;
32✔
885
  tbDbKey.version = ((SUidIdxVal *)pData)[0].version;
32✔
886
  if ((code = tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &pData, &nData)) != 0) {
32!
887
    goto _err;
×
888
  }
889

890
  tDecoderInit(&dc, pData, nData);
32✔
891
  code = metaDecodeEntry(&dc, &oStbEntry);
32✔
892
  if (code != 0) {
32!
893
    goto _err;
×
894
  }
895

896
  SSchema *pCol = NULL;
32✔
897
  int32_t  colId = -1;
32✔
898
  for (int i = 0; i < oStbEntry.stbEntry.schemaTag.nCols; i++) {
220!
899
    SSchema *schema = oStbEntry.stbEntry.schemaTag.pSchema + i;
220✔
900
    if (0 == strncmp(schema->name, pReq->colName, sizeof(pReq->colName))) {
220✔
901
      if (IS_IDX_ON(schema)) {
32!
902
        pCol = schema;
32✔
903
      }
904
      break;
32✔
905
    }
906
  }
907

908
  if (pCol == NULL) {
32!
909
    metaError("vgId:%d, failed to drop index on %s.%s,since %s", TD_VID(pMeta->pVnode), pReq->stb, pReq->colName,
×
910
              tstrerror(TSDB_CODE_VND_COL_NOT_EXISTS));
911
    code = 0;
×
912

913
    goto _err;
×
914
  }
915

916
  /*
917
   * iterator all pTdDbc by uid and version
918
   */
919
  TBC *pCtbIdxc = NULL;
32✔
920
  code = tdbTbcOpen(pMeta->pCtbIdx, &pCtbIdxc, NULL);
32✔
921
  if (code != 0) {
32!
922
    goto _err;
×
923
  }
924

925
  code = tdbTbcMoveTo(pCtbIdxc, &(SCtbIdxKey){.suid = suid, .uid = INT64_MIN}, sizeof(SCtbIdxKey), &c);
32✔
926
  if (code < 0) {
32!
927
    tdbTbcClose(pCtbIdxc);
×
928
    goto _err;
×
929
  }
930
  for (;;) {
8,051✔
931
    void *pKey = NULL, *pVal = NULL;
8,083✔
932
    int   nKey = 0, nVal = 0;
8,083✔
933

934
    code = tdbTbcNext(pCtbIdxc, &pKey, &nKey, &pVal, &nVal);
8,083✔
935
    if (code < 0) {
8,083✔
936
      tdbFree(pKey);
32✔
937
      tdbFree(pVal);
32✔
938
      tdbTbcClose(pCtbIdxc);
32✔
939
      pCtbIdxc = NULL;
32✔
940
      break;
32✔
941
    }
942
    if (((SCtbIdxKey *)pKey)->suid != suid) {
8,051!
UNCOV
943
      tdbFree(pKey);
×
UNCOV
944
      tdbFree(pVal);
×
UNCOV
945
      continue;
×
946
    }
947
    STagIdxKey *pTagIdxKey = NULL;
8,051✔
948
    int32_t     nTagIdxKey;
949

950
    const void *pTagData = NULL;
8,051✔
951
    int32_t     nTagData = 0;
8,051✔
952

953
    SCtbIdxKey *table = (SCtbIdxKey *)pKey;
8,051✔
954
    STagVal     tagVal = {.cid = pCol->colId};
8,051✔
955
    if (tTagGet((const STag *)pVal, &tagVal)) {
8,051!
956
      if (IS_VAR_DATA_TYPE(pCol->type)) {
8,051!
957
        pTagData = tagVal.pData;
1,150✔
958
        nTagData = (int32_t)tagVal.nData;
1,150✔
959
      } else {
960
        pTagData = &(tagVal.i64);
6,901✔
961
        nTagData = tDataTypes[pCol->type].bytes;
6,901✔
962
      }
963
    } else {
964
      if (!IS_VAR_DATA_TYPE(pCol->type)) {
×
965
        nTagData = tDataTypes[pCol->type].bytes;
×
966
      }
967
    }
968

969
    code = metaCreateTagIdxKey(suid, pCol->colId, pTagData, nTagData, pCol->type, table->uid, &pTagIdxKey, &nTagIdxKey);
8,051✔
970
    tdbFree(pKey);
8,051✔
971
    tdbFree(pVal);
8,051✔
972
    if (code < 0) {
8,051!
973
      metaDestroyTagIdxKey(pTagIdxKey);
×
974
      tdbTbcClose(pCtbIdxc);
×
975
      goto _err;
×
976
    }
977

978
    metaWLock(pMeta);
8,051✔
979
    ret = tdbTbDelete(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, pMeta->txn);
8,051✔
980
    if (ret < 0) {
8,051!
981
      metaError("vgId:%d, failed to delete tag idx key:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->stb,
×
982
                pReq->stbUid, tstrerror(ret));
983
    }
984
    metaULock(pMeta);
8,051✔
985
    metaDestroyTagIdxKey(pTagIdxKey);
8,051✔
986
    pTagIdxKey = NULL;
8,051✔
987
  }
988

989
  // clear idx flag
990
  SSCHMEA_SET_IDX_OFF(pCol);
32✔
991

992
  nStbEntry.version = version;
32✔
993
  nStbEntry.type = TSDB_SUPER_TABLE;
32✔
994
  nStbEntry.uid = oStbEntry.uid;
32✔
995
  nStbEntry.name = oStbEntry.name;
32!
996

997
  SSchemaWrapper  *row = tCloneSSchemaWrapper(&oStbEntry.stbEntry.schemaRow);
32!
998
  SSchemaWrapper  *tag = tCloneSSchemaWrapper(&oStbEntry.stbEntry.schemaTag);
32!
999
  SColCmprWrapper *cmpr = tCloneSColCmprWrapper(&oStbEntry.colCmpr);
32✔
1000
  if (row == NULL || tag == NULL || cmpr == NULL) {
32!
1001
    tDeleteSchemaWrapper(row);
1002
    tDeleteSchemaWrapper(tag);
1003
    tDeleteSColCmprWrapper(cmpr);
1004
    code = TSDB_CODE_OUT_OF_MEMORY;
×
1005

1006
    tdbTbcClose(pCtbIdxc);
×
1007
    goto _err;
×
1008
  }
1009

1010
  nStbEntry.stbEntry.schemaRow = *row;
32✔
1011
  nStbEntry.stbEntry.schemaTag = *tag;
32✔
1012
  nStbEntry.stbEntry.rsmaParam = oStbEntry.stbEntry.rsmaParam;
32✔
1013
  nStbEntry.colCmpr = *cmpr;
32✔
1014

1015
  nStbEntry.colCmpr = oStbEntry.colCmpr;
32✔
1016

1017
  metaWLock(pMeta);
32✔
1018
  // update table.db
1019
  ret = metaSaveToTbDb(pMeta, &nStbEntry);
32✔
1020
  if (ret < 0) {
32!
1021
    metaError("vgId:%d, failed to save tb db:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->stb,
×
1022
              pReq->stbUid, tstrerror(ret));
1023
  }
1024
  // update uid index
1025
  ret = metaUpdateUidIdx(pMeta, &nStbEntry);
32✔
1026
  if (ret < 0) {
32!
1027
    metaError("vgId:%d, failed to update uid idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->stb,
×
1028
              pReq->stbUid, tstrerror(ret));
1029
  }
1030
  metaULock(pMeta);
32✔
1031

1032
  tDeleteSchemaWrapper(tag);
1033
  tDeleteSchemaWrapper(row);
1034
  tDeleteSColCmprWrapper(cmpr);
1035

1036
  if (oStbEntry.pBuf) taosMemoryFree(oStbEntry.pBuf);
32!
1037
  tDecoderClear(&dc);
32✔
1038
  tdbFree(pData);
32✔
1039

1040
  tdbTbcClose(pCtbIdxc);
32✔
1041
  return TSDB_CODE_SUCCESS;
32✔
1042
_err:
×
1043
  if (oStbEntry.pBuf) taosMemoryFree(oStbEntry.pBuf);
×
1044
  tDecoderClear(&dc);
×
1045
  tdbFree(pData);
×
1046

1047
  return code;
×
1048
}
1049

1050
int metaCreateTable(SMeta *pMeta, int64_t ver, SVCreateTbReq *pReq, STableMetaRsp **pMetaRsp) {
47,068✔
1051
  SMetaEntry  me = {0};
47,068✔
1052
  SMetaReader mr = {0};
47,068✔
1053
  int32_t     ret;
1054

1055
  // validate message
1056
  if (pReq->type != TSDB_CHILD_TABLE && pReq->type != TSDB_NORMAL_TABLE) {
47,068!
1057
    terrno = TSDB_CODE_INVALID_MSG;
×
1058
    goto _err;
×
1059
  }
1060

1061
  if (pReq->type == TSDB_CHILD_TABLE) {
47,068✔
1062
    tb_uid_t suid = metaGetTableEntryUidByName(pMeta, pReq->ctb.stbName);
44,655✔
1063
    if (suid != pReq->ctb.suid) {
44,649!
1064
      return terrno = TSDB_CODE_PAR_TABLE_NOT_EXIST;
×
1065
    }
1066
  }
1067

1068
  // validate req
1069
  metaReaderDoInit(&mr, pMeta, META_READER_LOCK);
47,062✔
1070
  if (metaGetTableEntryByName(&mr, pReq->name) == 0) {
47,060✔
1071
    if (pReq->type == TSDB_CHILD_TABLE && pReq->ctb.suid != mr.me.ctbEntry.suid) {
17,405✔
1072
      metaReaderClear(&mr);
9✔
1073
      return terrno = TSDB_CODE_TDB_TABLE_IN_OTHER_STABLE;
9✔
1074
    }
1075
    pReq->uid = mr.me.uid;
17,396✔
1076
    if (pReq->type == TSDB_CHILD_TABLE) {
17,396✔
1077
      pReq->ctb.suid = mr.me.ctbEntry.suid;
17,390✔
1078
    }
1079
    metaReaderClear(&mr);
17,396✔
1080
    return terrno = TSDB_CODE_TDB_TABLE_ALREADY_EXIST;
17,396✔
1081
  } else if (terrno == TSDB_CODE_PAR_TABLE_NOT_EXIST) {
29,656!
1082
    terrno = TSDB_CODE_SUCCESS;
29,656✔
1083
  }
1084
  metaReaderClear(&mr);
29,656✔
1085

1086
  bool sysTbl = (pReq->type == TSDB_CHILD_TABLE) && metaTbInFilterCache(pMeta, pReq->ctb.stbName, 1);
29,663!
1087

1088
  if (!sysTbl && ((terrno = grantCheck(TSDB_GRANT_TIMESERIES)) < 0)) goto _err;
29,662!
1089

1090
  // build SMetaEntry
1091
  SVnodeStats *pStats = &pMeta->pVnode->config.vndStats;
29,659✔
1092
  me.version = ver;
29,659✔
1093
  me.type = pReq->type;
29,659✔
1094
  me.uid = pReq->uid;
29,659✔
1095
  me.name = pReq->name;
29,659✔
1096
  if (me.type == TSDB_CHILD_TABLE) {
29,659✔
1097
    me.ctbEntry.btime = pReq->btime;
27,248✔
1098
    me.ctbEntry.ttlDays = pReq->ttl;
27,248✔
1099
    me.ctbEntry.commentLen = pReq->commentLen;
27,248✔
1100
    me.ctbEntry.comment = pReq->comment;
27,248✔
1101
    me.ctbEntry.suid = pReq->ctb.suid;
27,248✔
1102
    me.ctbEntry.pTags = pReq->ctb.pTag;
27,248✔
1103

1104
#ifdef TAG_FILTER_DEBUG
1105
    SArray *pTagVals = NULL;
1106
    int32_t code = tTagToValArray((STag *)pReq->ctb.pTag, &pTagVals);
1107
    for (int i = 0; i < taosArrayGetSize(pTagVals); i++) {
1108
      STagVal *pTagVal = (STagVal *)taosArrayGet(pTagVals, i);
1109

1110
      if (IS_VAR_DATA_TYPE(pTagVal->type)) {
1111
        char *buf = taosMemoryCalloc(pTagVal->nData + 1, 1);
1112
        memcpy(buf, pTagVal->pData, pTagVal->nData);
1113
        metaDebug("metaTag table:%s varchar index:%d cid:%d type:%d value:%s", pReq->name, i, pTagVal->cid,
1114
                  pTagVal->type, buf);
1115
        taosMemoryFree(buf);
1116
      } else {
1117
        double val = 0;
1118
        GET_TYPED_DATA(val, double, pTagVal->type, &pTagVal->i64);
1119
        metaDebug("metaTag table:%s number index:%d cid:%d type:%d value:%f", pReq->name, i, pTagVal->cid,
1120
                  pTagVal->type, val);
1121
      }
1122
    }
1123
#endif
1124

1125
    ++pStats->numOfCTables;
27,248✔
1126

1127
    if (!sysTbl) {
27,248!
1128
      int32_t nCols = 0;
27,249✔
1129
      ret = metaGetStbStats(pMeta->pVnode, me.ctbEntry.suid, 0, &nCols);
27,249✔
1130
      if (ret < 0) {
27,255!
1131
        metaError("vgId:%d, failed to get stb stats:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
1132
                  pReq->ctb.suid, tstrerror(ret));
1133
      }
1134
      pStats->numOfTimeSeries += nCols - 1;
27,254✔
1135
    }
1136

1137
    metaWLock(pMeta);
27,253✔
1138
    metaUpdateStbStats(pMeta, me.ctbEntry.suid, 1, 0);
27,253✔
1139
    ret = metaUidCacheClear(pMeta, me.ctbEntry.suid);
27,250✔
1140
    if (ret < 0) {
27,251!
1141
      metaError("vgId:%d, failed to clear uid cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
1142
                pReq->ctb.suid, tstrerror(ret));
1143
    }
1144
    ret = metaTbGroupCacheClear(pMeta, me.ctbEntry.suid);
27,251✔
1145
    if (ret < 0) {
27,252!
1146
      metaError("vgId:%d, failed to clear group cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name,
×
1147
                pReq->ctb.suid, tstrerror(ret));
1148
    }
1149
    metaULock(pMeta);
27,252✔
1150

1151
    if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
27,255✔
1152
      ret = tsdbCacheNewTable(pMeta->pVnode->pTsdb, me.uid, me.ctbEntry.suid, NULL);
88✔
1153
      if (ret < 0) {
88!
1154
        metaError("vgId:%d, failed to create table:%s since %s", TD_VID(pMeta->pVnode), pReq->name, tstrerror(ret));
×
1155
        goto _err;
×
1156
      }
1157
    }
1158
  } else {
1159
    me.ntbEntry.btime = pReq->btime;
2,411✔
1160
    me.ntbEntry.ttlDays = pReq->ttl;
2,411✔
1161
    me.ntbEntry.commentLen = pReq->commentLen;
2,411✔
1162
    me.ntbEntry.comment = pReq->comment;
2,411✔
1163
    me.ntbEntry.schemaRow = pReq->ntb.schemaRow;
2,411✔
1164
    me.ntbEntry.ncid = me.ntbEntry.schemaRow.pSchema[me.ntbEntry.schemaRow.nCols - 1].colId + 1;
2,411✔
1165
    me.colCmpr = pReq->colCmpr;
2,411✔
1166
    TABLE_SET_COL_COMPRESSED(me.flags);
2,411✔
1167

1168
    ++pStats->numOfNTables;
2,411✔
1169
    pStats->numOfNTimeSeries += me.ntbEntry.schemaRow.nCols - 1;
2,411✔
1170

1171
    if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
2,411✔
1172
      ret = tsdbCacheNewTable(pMeta->pVnode->pTsdb, me.uid, -1, &me.ntbEntry.schemaRow);
6✔
1173
      if (ret < 0) {
6!
1174
        metaError("vgId:%d, failed to create table:%s since %s", TD_VID(pMeta->pVnode), pReq->name, tstrerror(ret));
×
1175
        goto _err;
×
1176
      }
1177
    }
1178
  }
1179

1180
  if (metaHandleEntry(pMeta, &me) < 0) goto _err;
29,666!
1181

1182
  metaTimeSeriesNotifyCheck(pMeta);
29,655✔
1183

1184
  if (pMetaRsp) {
29,657!
1185
    *pMetaRsp = taosMemoryCalloc(1, sizeof(STableMetaRsp));
29,659✔
1186

1187
    if (*pMetaRsp) {
29,656!
1188
      if (me.type == TSDB_CHILD_TABLE) {
29,657✔
1189
        (*pMetaRsp)->tableType = TSDB_CHILD_TABLE;
27,246✔
1190
        (*pMetaRsp)->tuid = pReq->uid;
27,246✔
1191
        (*pMetaRsp)->suid = pReq->ctb.suid;
27,246✔
1192
        strcpy((*pMetaRsp)->tbName, pReq->name);
27,246✔
1193
      } else {
1194
        ret = metaUpdateMetaRsp(pReq->uid, pReq->name, &pReq->ntb.schemaRow, *pMetaRsp);
2,411✔
1195
        if (ret < 0) {
2,411!
1196
          metaError("vgId:%d, failed to update meta rsp:%s since %s", TD_VID(pMeta->pVnode), pReq->name,
×
1197
                    tstrerror(ret));
1198
        }
1199
        for (int32_t i = 0; i < pReq->colCmpr.nCols; i++) {
75,294✔
1200
          SColCmpr *p = &pReq->colCmpr.pColCmpr[i];
72,883✔
1201
          (*pMetaRsp)->pSchemaExt[i].colId = p->id;
72,883✔
1202
          (*pMetaRsp)->pSchemaExt[i].compress = p->alg;
72,883✔
1203
        }
1204
      }
1205
    }
1206
  }
1207

1208
  pMeta->changed = true;
29,654✔
1209
  metaDebug("vgId:%d, table:%s uid %" PRId64 " is created, type:%" PRId8, TD_VID(pMeta->pVnode), pReq->name, pReq->uid,
29,654✔
1210
            pReq->type);
1211
  return 0;
29,658✔
1212

1213
_err:
×
1214
  metaError("vgId:%d, failed to create table:%s type:%s since %s", TD_VID(pMeta->pVnode), pReq->name,
×
1215
            pReq->type == TSDB_CHILD_TABLE ? "child table" : "normal table", tstrerror(terrno));
1216
  return TSDB_CODE_FAILED;
×
1217
}
1218

1219
int metaDropTable(SMeta *pMeta, int64_t version, SVDropTbReq *pReq, SArray *tbUids, tb_uid_t *tbUid) {
1,018✔
1220
  void    *pData = NULL;
1,018✔
1221
  int      nData = 0;
1,018✔
1222
  int      rc = 0;
1,018✔
1223
  tb_uid_t uid = 0;
1,018✔
1224
  tb_uid_t suid = 0;
1,018✔
1225
  int8_t   sysTbl = 0;
1,018✔
1226
  int      type;
1227

1228
  rc = tdbTbGet(pMeta->pNameIdx, pReq->name, strlen(pReq->name) + 1, &pData, &nData);
1,018✔
1229
  if (rc < 0) {
1,018!
1230
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
1231
  }
1232
  uid = *(tb_uid_t *)pData;
1,018✔
1233

1234
  metaWLock(pMeta);
1,018✔
1235
  rc = metaDropTableByUid(pMeta, uid, &type, &suid, &sysTbl);
1,018✔
1236
  metaULock(pMeta);
1,018✔
1237

1238
  if (rc < 0) goto _exit;
1,018!
1239

1240
  if (!sysTbl && type == TSDB_CHILD_TABLE) {
1,018!
1241
    int32_t      nCols = 0;
604✔
1242
    SVnodeStats *pStats = &pMeta->pVnode->config.vndStats;
604✔
1243
    if (metaGetStbStats(pMeta->pVnode, suid, NULL, &nCols) == 0) {
604!
1244
      pStats->numOfTimeSeries -= nCols - 1;
604✔
1245
    }
1246
  }
1247

1248
  if ((type == TSDB_CHILD_TABLE || type == TSDB_NORMAL_TABLE) && tbUids) {
1,018!
1249
    if (taosArrayPush(tbUids, &uid) == NULL) {
1,018!
1250
      rc = terrno;
×
1251
      goto _exit;
×
1252
    }
1253

1254
    if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
1,018✔
1255
      int32_t ret = tsdbCacheDropTable(pMeta->pVnode->pTsdb, uid, suid, NULL);
51✔
1256
      if (ret < 0) {
51!
1257
        metaError("vgId:%d, failed to drop table:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pReq->name, uid,
×
1258
                  tstrerror(ret));
1259
      }
1260
    }
1261
  }
1262

1263
  if ((type == TSDB_CHILD_TABLE) && tbUid) {
1,018!
1264
    *tbUid = uid;
604✔
1265
  }
1266

1267
  pMeta->changed = true;
1,018✔
1268
_exit:
1,018✔
1269
  tdbFree(pData);
1,018✔
1270
  return rc;
1,018✔
1271
}
1272

1273
int32_t metaDropTables(SMeta *pMeta, SArray *tbUids) {
12✔
1274
  int32_t code = 0;
12✔
1275
  if (taosArrayGetSize(tbUids) == 0) return TSDB_CODE_SUCCESS;
12!
1276

1277
  int64_t    nCtbDropped = 0;
12✔
1278
  SSHashObj *suidHash = tSimpleHashInit(16, taosGetDefaultHashFunction(TSDB_DATA_TYPE_BIGINT));
12✔
1279
  if (suidHash == NULL) {
12!
1280
    return terrno;
×
1281
  }
1282

1283
  metaWLock(pMeta);
12✔
1284
  for (int i = 0; i < taosArrayGetSize(tbUids); ++i) {
117✔
1285
    tb_uid_t uid = *(tb_uid_t *)taosArrayGet(tbUids, i);
105✔
1286
    tb_uid_t suid = 0;
105✔
1287
    int8_t   sysTbl = 0;
105✔
1288
    int      type;
1289
    code = metaDropTableByUid(pMeta, uid, &type, &suid, &sysTbl);
105✔
1290
    if (code) return code;
105!
1291
    if (!sysTbl && type == TSDB_CHILD_TABLE && suid != 0 && suidHash) {
105!
1292
      int64_t *pVal = tSimpleHashGet(suidHash, &suid, sizeof(tb_uid_t));
105✔
1293
      if (pVal) {
105✔
1294
        nCtbDropped = *pVal + 1;
93✔
1295
      } else {
1296
        nCtbDropped = 1;
12✔
1297
      }
1298
      code = tSimpleHashPut(suidHash, &suid, sizeof(tb_uid_t), &nCtbDropped, sizeof(int64_t));
105✔
1299
      if (code) return code;
105!
1300
    }
1301
    /*
1302
    if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
1303
      tsdbCacheDropTable(pMeta->pVnode->pTsdb, uid, suid, NULL);
1304
    }
1305
    */
1306
    metaDebug("batch drop table:%" PRId64, uid);
105✔
1307
  }
1308
  metaULock(pMeta);
12✔
1309

1310
  // update timeseries
1311
  void   *pCtbDropped = NULL;
12✔
1312
  int32_t iter = 0;
12✔
1313
  while ((pCtbDropped = tSimpleHashIterate(suidHash, pCtbDropped, &iter))) {
24✔
1314
    tb_uid_t    *pSuid = tSimpleHashGetKey(pCtbDropped, NULL);
12✔
1315
    int32_t      nCols = 0;
12✔
1316
    SVnodeStats *pStats = &pMeta->pVnode->config.vndStats;
12✔
1317
    if (metaGetStbStats(pMeta->pVnode, *pSuid, NULL, &nCols) == 0) {
12!
1318
      pStats->numOfTimeSeries -= *(int64_t *)pCtbDropped * (nCols - 1);
12✔
1319
    }
1320
  }
1321
  tSimpleHashCleanup(suidHash);
12✔
1322

1323
  pMeta->changed = true;
12✔
1324
  return 0;
12✔
1325
}
1326

1327
static int32_t metaFilterTableByHash(SMeta *pMeta, SArray *uidList) {
12✔
1328
  int32_t code = 0;
12✔
1329
  // 1, tranverse table's
1330
  // 2, validate table name using vnodeValidateTableHash
1331
  // 3, push invalidated table's uid into uidList
1332

1333
  TBC *pCur;
1334
  code = tdbTbcOpen(pMeta->pTbDb, &pCur, NULL);
12✔
1335
  if (code < 0) {
12!
1336
    return code;
×
1337
  }
1338

1339
  code = tdbTbcMoveToFirst(pCur);
12✔
1340
  if (code) {
12!
1341
    tdbTbcClose(pCur);
×
1342
    return code;
×
1343
  }
1344

1345
  void *pData = NULL, *pKey = NULL;
12✔
1346
  int   nData = 0, nKey = 0;
12✔
1347

1348
  while (1) {
222✔
1349
    int32_t ret = tdbTbcNext(pCur, &pKey, &nKey, &pData, &nData);
234✔
1350
    if (ret < 0) {
234✔
1351
      break;
12✔
1352
    }
1353

1354
    SMetaEntry me = {0};
222✔
1355
    SDecoder   dc = {0};
222✔
1356
    tDecoderInit(&dc, pData, nData);
222✔
1357
    code = metaDecodeEntry(&dc, &me);
222✔
1358
    if (code < 0) {
222!
1359
      tDecoderClear(&dc);
×
1360
      return code;
×
1361
    }
1362

1363
    if (me.type != TSDB_SUPER_TABLE) {
222✔
1364
      char tbFName[TSDB_TABLE_FNAME_LEN + 1];
1365
      snprintf(tbFName, sizeof(tbFName), "%s.%s", pMeta->pVnode->config.dbname, me.name);
210✔
1366
      tbFName[TSDB_TABLE_FNAME_LEN] = '\0';
210✔
1367
      int32_t ret = vnodeValidateTableHash(pMeta->pVnode, tbFName);
210✔
1368
      if (ret < 0 && terrno == TSDB_CODE_VND_HASH_MISMATCH) {
210!
1369
        if (taosArrayPush(uidList, &me.uid) == NULL) {
105!
1370
          code = terrno;
×
1371
          break;
×
1372
        }
1373
      }
1374
    }
1375
    tDecoderClear(&dc);
222✔
1376
  }
1377
  tdbFree(pData);
12✔
1378
  tdbFree(pKey);
12✔
1379
  tdbTbcClose(pCur);
12✔
1380

1381
  return 0;
12✔
1382
}
1383

1384
int32_t metaTrimTables(SMeta *pMeta) {
12✔
1385
  int32_t code = 0;
12✔
1386

1387
  SArray *tbUids = taosArrayInit(8, sizeof(int64_t));
12✔
1388
  if (tbUids == NULL) {
12!
1389
    return terrno;
×
1390
  }
1391

1392
  code = metaFilterTableByHash(pMeta, tbUids);
12✔
1393
  if (code != 0) {
12!
1394
    goto end;
×
1395
  }
1396
  if (TARRAY_SIZE(tbUids) == 0) {
12!
UNCOV
1397
    goto end;
×
1398
  }
1399

1400
  metaInfo("vgId:%d, trim %ld tables", TD_VID(pMeta->pVnode), taosArrayGetSize(tbUids));
12!
1401
  code = metaDropTables(pMeta, tbUids);
12✔
1402
  if (code) goto end;
12!
1403

1404
end:
12✔
1405
  taosArrayDestroy(tbUids);
12✔
1406

1407
  return code;
12✔
1408
}
1409

1410
int metaTtlFindExpired(SMeta *pMeta, int64_t timePointMs, SArray *tbUids, int32_t ttlDropMaxCount) {
8,589✔
1411
  metaRLock(pMeta);
8,589✔
1412

1413
  int ret = ttlMgrFindExpired(pMeta->pTtlMgr, timePointMs, tbUids, ttlDropMaxCount);
8,603✔
1414

1415
  metaULock(pMeta);
8,585✔
1416

1417
  if (ret != 0) {
8,605!
1418
    metaError("ttl failed to find expired table, ret:%d", ret);
×
1419
  }
1420

1421
  return ret;
8,606✔
1422
}
1423

1424
static int metaBuildBtimeIdxKey(SBtimeIdxKey *btimeKey, const SMetaEntry *pME) {
44,340✔
1425
  int64_t btime;
1426
  if (pME->type == TSDB_CHILD_TABLE) {
44,340✔
1427
    btime = pME->ctbEntry.btime;
29,511✔
1428
  } else if (pME->type == TSDB_NORMAL_TABLE) {
14,829✔
1429
    btime = pME->ntbEntry.btime;
2,825✔
1430
  } else {
1431
    return TSDB_CODE_FAILED;
12,004✔
1432
  }
1433

1434
  btimeKey->btime = btime;
32,336✔
1435
  btimeKey->uid = pME->uid;
32,336✔
1436
  return 0;
32,336✔
1437
}
1438

1439
static int metaBuildNColIdxKey(SNcolIdxKey *ncolKey, const SMetaEntry *pME) {
3,199✔
1440
  if (pME->type == TSDB_NORMAL_TABLE) {
3,199!
1441
    ncolKey->ncol = pME->ntbEntry.schemaRow.nCols;
3,199✔
1442
    ncolKey->uid = pME->uid;
3,199✔
1443
  } else {
1444
    return TSDB_CODE_FAILED;
×
1445
  }
1446
  return 0;
3,199✔
1447
}
1448

1449
static void metaDeleteTtl(SMeta *pMeta, const SMetaEntry *pME) {
1,521✔
1450
  if (pME->type != TSDB_CHILD_TABLE && pME->type != TSDB_NORMAL_TABLE) return;
1,521!
1451

1452
  STtlDelTtlCtx ctx = {.uid = pME->uid, .pTxn = pMeta->txn};
1,521✔
1453
  if (pME->type == TSDB_CHILD_TABLE) {
1,521✔
1454
    ctx.ttlDays = pME->ctbEntry.ttlDays;
1,092✔
1455
  } else {
1456
    ctx.ttlDays = pME->ntbEntry.ttlDays;
429✔
1457
  }
1458

1459
  int32_t ret = ttlMgrDeleteTtl(pMeta->pTtlMgr, &ctx);
1,521✔
1460
  if (ret < 0) {
1,521!
1461
    metaError("vgId:%d, failed to delete ttl for table:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), pME->name,
×
1462
              pME->uid, tstrerror(ret));
1463
  }
1464
  return;
1,521✔
1465
}
1466

1467
static int metaDropTableByUid(SMeta *pMeta, tb_uid_t uid, int *type, tb_uid_t *pSuid, int8_t *pSysTbl) {
1,492✔
1468
  void      *pData = NULL;
1,492✔
1469
  int        nData = 0;
1,492✔
1470
  int        rc = 0;
1,492✔
1471
  SMetaEntry e = {0};
1,492✔
1472
  SDecoder   dc = {0};
1,492✔
1473
  int32_t    ret = 0;
1,492✔
1474

1475
  rc = tdbTbGet(pMeta->pUidIdx, &uid, sizeof(uid), &pData, &nData);
1,492✔
1476
  if (rc < 0) {
1,493!
1477
    return rc;
×
1478
  }
1479
  int64_t version = ((SUidIdxVal *)pData)[0].version;
1,493✔
1480

1481
  rc = tdbTbGet(pMeta->pTbDb, &(STbDbKey){.version = version, .uid = uid}, sizeof(STbDbKey), &pData, &nData);
1,493✔
1482
  if (rc < 0) {
1,493!
1483
    tdbFree(pData);
×
1484
    return rc;
×
1485
  }
1486

1487
  tDecoderInit(&dc, pData, nData);
1,493✔
1488
  rc = metaDecodeEntry(&dc, &e);
1,493✔
1489
  if (rc < 0) {
1,493!
1490
    tDecoderClear(&dc);
×
1491
    return rc;
×
1492
  }
1493

1494
  if (type) *type = e.type;
1,493✔
1495

1496
  if (e.type == TSDB_CHILD_TABLE) {
1,493✔
1497
    if (pSuid) *pSuid = e.ctbEntry.suid;
1,079✔
1498
    void *tData = NULL;
1,079✔
1499
    int   tLen = 0;
1,079✔
1500

1501
    if (tdbTbGet(pMeta->pUidIdx, &e.ctbEntry.suid, sizeof(tb_uid_t), &tData, &tLen) == 0) {
1,079!
1502
      STbDbKey tbDbKey = {.uid = e.ctbEntry.suid, .version = ((SUidIdxVal *)tData)[0].version};
1,079✔
1503
      if (tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &tData, &tLen) == 0) {
1,079!
1504
        SDecoder   tdc = {0};
1,078✔
1505
        SMetaEntry stbEntry = {0};
1,078✔
1506

1507
        tDecoderInit(&tdc, tData, tLen);
1,078✔
1508
        int32_t ret = metaDecodeEntry(&tdc, &stbEntry);
1,078✔
1509
        if (ret < 0) {
1,079!
1510
          tDecoderClear(&tdc);
×
1511
          metaError("vgId:%d, failed to decode child table:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name,
×
1512
                    e.ctbEntry.suid, tstrerror(ret));
1513
          return ret;
×
1514
        }
1515

1516
        if (pSysTbl) *pSysTbl = metaTbInFilterCache(pMeta, stbEntry.name, 1) ? 1 : 0;
1,079✔
1517

1518
        SSchema        *pTagColumn = NULL;
1,079✔
1519
        SSchemaWrapper *pTagSchema = &stbEntry.stbEntry.schemaTag;
1,079✔
1520
        if (pTagSchema->nCols == 1 && pTagSchema->pSchema[0].type == TSDB_DATA_TYPE_JSON) {
1,079✔
1521
          pTagColumn = &stbEntry.stbEntry.schemaTag.pSchema[0];
6✔
1522
          ret = metaDelJsonVarFromIdx(pMeta, &e, pTagColumn);
6✔
1523
          if (ret < 0) {
6!
1524
            metaError("vgId:%d, failed to delete json var from idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode),
×
1525
                      e.name, e.uid, tstrerror(ret));
1526
          }
1527
        } else {
1528
          for (int i = 0; i < pTagSchema->nCols; i++) {
8,291✔
1529
            pTagColumn = &stbEntry.stbEntry.schemaTag.pSchema[i];
7,218✔
1530
            if (!IS_IDX_ON(pTagColumn)) continue;
7,218✔
1531
            STagIdxKey *pTagIdxKey = NULL;
6,590✔
1532
            int32_t     nTagIdxKey;
1533

1534
            const void *pTagData = NULL;
6,590✔
1535
            int32_t     nTagData = 0;
6,590✔
1536

1537
            STagVal tagVal = {.cid = pTagColumn->colId};
6,590✔
1538
            if (tTagGet((const STag *)e.ctbEntry.pTags, &tagVal)) {
6,590✔
1539
              if (IS_VAR_DATA_TYPE(pTagColumn->type)) {
6,586!
1540
                pTagData = tagVal.pData;
867✔
1541
                nTagData = (int32_t)tagVal.nData;
867✔
1542
              } else {
1543
                pTagData = &(tagVal.i64);
5,719✔
1544
                nTagData = tDataTypes[pTagColumn->type].bytes;
5,719✔
1545
              }
1546
            } else {
1547
              if (!IS_VAR_DATA_TYPE(pTagColumn->type)) {
4!
1548
                nTagData = tDataTypes[pTagColumn->type].bytes;
4✔
1549
              }
1550
            }
1551

1552
            if (metaCreateTagIdxKey(e.ctbEntry.suid, pTagColumn->colId, pTagData, nTagData, pTagColumn->type, uid,
6,590!
1553
                                    &pTagIdxKey, &nTagIdxKey) == 0) {
1554
              ret = tdbTbDelete(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, pMeta->txn);
6,590✔
1555
              if (ret < 0) {
6,590!
1556
                metaError("vgId:%d, failed to delete tag idx key:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode),
×
1557
                          e.name, e.uid, tstrerror(ret));
1558
              }
1559
            }
1560
            metaDestroyTagIdxKey(pTagIdxKey);
6,590✔
1561
            pTagIdxKey = NULL;
6,590✔
1562
          }
1563
        }
1564
        tDecoderClear(&tdc);
1,079✔
1565
      }
1566
      tdbFree(tData);
1,079✔
1567
    }
1568
  }
1569

1570
  ret = tdbTbDelete(pMeta->pTbDb, &(STbDbKey){.version = version, .uid = uid}, sizeof(STbDbKey), pMeta->txn);
1,493✔
1571
  if (ret < 0) {
1,493!
1572
    metaError("vgId:%d, failed to delete table:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1573
              tstrerror(ret));
1574
  }
1575
  ret = tdbTbDelete(pMeta->pNameIdx, e.name, strlen(e.name) + 1, pMeta->txn);
1,493✔
1576
  if (ret < 0) {
1,493!
1577
    metaError("vgId:%d, failed to delete name idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1578
              tstrerror(ret));
1579
  }
1580
  ret = tdbTbDelete(pMeta->pUidIdx, &uid, sizeof(uid), pMeta->txn);
1,493✔
1581
  if (ret < 0) {
1,493!
1582
    metaError("vgId:%d, failed to delete uid idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1583
              tstrerror(ret));
1584
  }
1585

1586
  if (e.type == TSDB_CHILD_TABLE || e.type == TSDB_NORMAL_TABLE) metaDeleteBtimeIdx(pMeta, &e);
1,493!
1587
  if (e.type == TSDB_NORMAL_TABLE) metaDeleteNcolIdx(pMeta, &e);
1,493✔
1588

1589
  if (e.type != TSDB_SUPER_TABLE) metaDeleteTtl(pMeta, &e);
1,493!
1590

1591
  if (e.type == TSDB_CHILD_TABLE) {
1,493✔
1592
    ret =
1593
        tdbTbDelete(pMeta->pCtbIdx, &(SCtbIdxKey){.suid = e.ctbEntry.suid, .uid = uid}, sizeof(SCtbIdxKey), pMeta->txn);
1,079✔
1594
    if (ret < 0) {
1,079!
1595
      metaError("vgId:%d, failed to delete ctb idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1596
                tstrerror(ret));
1597
    }
1598

1599
    --pMeta->pVnode->config.vndStats.numOfCTables;
1,079✔
1600
    metaUpdateStbStats(pMeta, e.ctbEntry.suid, -1, 0);
1,079✔
1601
    ret = metaUidCacheClear(pMeta, e.ctbEntry.suid);
1,079✔
1602
    if (ret < 0) {
1,079!
1603
      metaError("vgId:%d, failed to clear uid cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name,
×
1604
                e.ctbEntry.suid, tstrerror(ret));
1605
    }
1606
    ret = metaTbGroupCacheClear(pMeta, e.ctbEntry.suid);
1,079✔
1607
    if (ret < 0) {
1,079!
1608
      metaError("vgId:%d, failed to clear group cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name,
×
1609
                e.ctbEntry.suid, tstrerror(ret));
1610
    }
1611
    /*
1612
    if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
1613
      tsdbCacheDropTable(pMeta->pVnode->pTsdb, e.uid, e.ctbEntry.suid, NULL);
1614
    }
1615
    */
1616
  } else if (e.type == TSDB_NORMAL_TABLE) {
414!
1617
    // drop schema.db (todo)
1618

1619
    --pMeta->pVnode->config.vndStats.numOfNTables;
414✔
1620
    pMeta->pVnode->config.vndStats.numOfNTimeSeries -= e.ntbEntry.schemaRow.nCols - 1;
414✔
1621

1622
    /*
1623
    if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
1624
      tsdbCacheDropTable(pMeta->pVnode->pTsdb, e.uid, -1, &e.ntbEntry.schemaRow);
1625
    }
1626
    */
1627
  } else if (e.type == TSDB_SUPER_TABLE) {
×
1628
    ret = tdbTbDelete(pMeta->pSuidIdx, &e.uid, sizeof(tb_uid_t), pMeta->txn);
×
1629
    if (ret < 0) {
×
1630
      metaError("vgId:%d, failed to delete suid idx:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1631
                tstrerror(ret));
1632
    }
1633
    // drop schema.db (todo)
1634

1635
    ret = metaStatsCacheDrop(pMeta, uid);
×
1636
    if (ret < 0) {
×
1637
      metaError("vgId:%d, failed to drop stats cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1638
                tstrerror(ret));
1639
    }
1640
    ret = metaUidCacheClear(pMeta, uid);
×
1641
    if (ret < 0) {
×
1642
      metaError("vgId:%d, failed to clear uid cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
×
1643
                tstrerror(ret));
1644
    }
1645
    ret = metaTbGroupCacheClear(pMeta, uid);
×
1646
    if (ret < 0) {
×
1647
      metaError("vgId:%d, failed to clear group cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name,
×
1648
                e.uid, tstrerror(ret));
1649
    }
1650
    --pMeta->pVnode->config.vndStats.numOfSTables;
×
1651
  }
1652

1653
  ret = metaCacheDrop(pMeta, uid);
1,493✔
1654
  if (ret < 0) {
1,493✔
1655
    metaError("vgId:%d, failed to drop cache:%s uid:%" PRId64 " since %s", TD_VID(pMeta->pVnode), e.name, e.uid,
108!
1656
              tstrerror(ret));
1657
  }
1658

1659
  tDecoderClear(&dc);
1,493✔
1660
  tdbFree(pData);
1,493✔
1661

1662
  return 0;
1,493✔
1663
}
1664
// opt ins_tables
1665
int metaUpdateBtimeIdx(SMeta *pMeta, const SMetaEntry *pME) {
42,666✔
1666
  SBtimeIdxKey btimeKey = {0};
42,666✔
1667
  if (metaBuildBtimeIdxKey(&btimeKey, pME) < 0) {
42,666✔
1668
    return 0;
12,014✔
1669
  }
1670
  metaTrace("vgId:%d, start to save version:%" PRId64 " uid:%" PRId64 " btime:%" PRId64, TD_VID(pMeta->pVnode),
30,835✔
1671
            pME->version, pME->uid, btimeKey.btime);
1672

1673
  return tdbTbUpsert(pMeta->pBtimeIdx, &btimeKey, sizeof(btimeKey), NULL, 0, pMeta->txn);
30,835✔
1674
}
1675

1676
int metaDeleteBtimeIdx(SMeta *pMeta, const SMetaEntry *pME) {
1,493✔
1677
  SBtimeIdxKey btimeKey = {0};
1,493✔
1678
  if (metaBuildBtimeIdxKey(&btimeKey, pME) < 0) {
1,493!
1679
    return 0;
×
1680
  }
1681
  return tdbTbDelete(pMeta->pBtimeIdx, &btimeKey, sizeof(btimeKey), pMeta->txn);
1,493✔
1682
}
1683
int metaUpdateNcolIdx(SMeta *pMeta, const SMetaEntry *pME) {
2,598✔
1684
  SNcolIdxKey ncolKey = {0};
2,598✔
1685
  if (metaBuildNColIdxKey(&ncolKey, pME) < 0) {
2,598!
1686
    return 0;
×
1687
  }
1688
  return tdbTbUpsert(pMeta->pNcolIdx, &ncolKey, sizeof(ncolKey), NULL, 0, pMeta->txn);
2,598✔
1689
}
1690

1691
int metaDeleteNcolIdx(SMeta *pMeta, const SMetaEntry *pME) {
601✔
1692
  SNcolIdxKey ncolKey = {0};
601✔
1693
  if (metaBuildNColIdxKey(&ncolKey, pME) < 0) {
601!
1694
    return 0;
×
1695
  }
1696
  return tdbTbDelete(pMeta->pNcolIdx, &ncolKey, sizeof(ncolKey), pMeta->txn);
601✔
1697
}
1698

1699
static int metaAlterTableColumn(SMeta *pMeta, int64_t version, SVAlterTbReq *pAlterTbReq, STableMetaRsp *pMetaRsp) {
230✔
1700
  void           *pVal = NULL;
230✔
1701
  int             nVal = 0;
230✔
1702
  const void     *pData = NULL;
230✔
1703
  int             nData = 0;
230✔
1704
  int             ret = 0;
230✔
1705
  tb_uid_t        uid;
1706
  int64_t         oversion;
1707
  SSchema        *pColumn = NULL;
230✔
1708
  SMetaEntry      entry = {0};
230✔
1709
  SSchemaWrapper *pSchema;
1710
  int             c;
1711
  bool            freeColCmpr = false;
230✔
1712
  if (pAlterTbReq->colName == NULL) {
230!
1713
    metaError("meta/table: null pAlterTbReq->colName");
×
1714
    return terrno = TSDB_CODE_INVALID_MSG;
×
1715
  }
1716

1717
  // search name index
1718
  ret = tdbTbGet(pMeta->pNameIdx, pAlterTbReq->tbName, strlen(pAlterTbReq->tbName) + 1, &pVal, &nVal);
230✔
1719
  if (ret < 0) {
230!
1720
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
1721
  }
1722

1723
  uid = *(tb_uid_t *)pVal;
230✔
1724
  tdbFree(pVal);
230✔
1725
  pVal = NULL;
230✔
1726

1727
  // search uid index
1728
  TBC *pUidIdxc = NULL;
230✔
1729

1730
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pUidIdx, &pUidIdxc, NULL));
230!
1731
  ret = tdbTbcMoveTo(pUidIdxc, &uid, sizeof(uid), &c);
230✔
1732
  if (c != 0) {
230!
1733
    tdbTbcClose(pUidIdxc);
×
1734
    metaError("meta/table: invalide c: %" PRId32 " alt tb column failed.", c);
×
1735
    return TSDB_CODE_FAILED;
×
1736
  }
1737

1738
  ret = tdbTbcGet(pUidIdxc, NULL, NULL, &pData, &nData);
230✔
1739
  oversion = ((SUidIdxVal *)pData)[0].version;
230✔
1740

1741
  // search table.db
1742
  TBC *pTbDbc = NULL;
230✔
1743

1744
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pTbDb, &pTbDbc, NULL));
230!
1745
  ret = tdbTbcMoveTo(pTbDbc, &((STbDbKey){.uid = uid, .version = oversion}), sizeof(STbDbKey), &c);
230✔
1746
  if (c != 0) {
230!
1747
    tdbTbcClose(pUidIdxc);
×
1748
    tdbTbcClose(pTbDbc);
×
1749
    metaError("meta/table: invalide c: %" PRId32 " alt tb column failed.", c);
×
1750
    return TSDB_CODE_FAILED;
×
1751
  }
1752

1753
  ret = tdbTbcGet(pTbDbc, NULL, NULL, &pData, &nData);
230✔
1754

1755
  // get table entry
1756
  SDecoder dc = {0};
230✔
1757
  if ((entry.pBuf = taosMemoryMalloc(nData)) == NULL) {
230!
1758
    tdbTbcClose(pUidIdxc);
×
1759
    tdbTbcClose(pTbDbc);
×
1760
    return terrno;
×
1761
  }
1762
  memcpy(entry.pBuf, pData, nData);
230✔
1763
  tDecoderInit(&dc, entry.pBuf, nData);
230✔
1764
  ret = metaDecodeEntry(&dc, &entry);
230✔
1765
  if (ret != 0) {
230!
1766
    tdbTbcClose(pUidIdxc);
×
1767
    tdbTbcClose(pTbDbc);
×
1768
    tDecoderClear(&dc);
×
1769
    metaError("meta/table: invalide ret: %" PRId32 " alt tb column failed.", ret);
×
1770
    return ret;
×
1771
  }
1772

1773
  if (entry.type != TSDB_NORMAL_TABLE) {
230✔
1774
    terrno = TSDB_CODE_VND_INVALID_TABLE_ACTION;
14✔
1775
    goto _err;
14✔
1776
  }
1777
  // search the column to add/drop/update
1778
  pSchema = &entry.ntbEntry.schemaRow;
216✔
1779

1780
  // save old entry
1781
  SMetaEntry oldEntry = {.type = TSDB_NORMAL_TABLE, .uid = entry.uid};
216✔
1782
  oldEntry.ntbEntry.schemaRow.nCols = pSchema->nCols;
216✔
1783

1784
  int32_t rowLen = -1;
216✔
1785
  if (pAlterTbReq->action == TSDB_ALTER_TABLE_ADD_COLUMN ||
216✔
1786
      pAlterTbReq->action == TSDB_ALTER_TABLE_UPDATE_COLUMN_BYTES) {
146✔
1787
    rowLen = 0;
103✔
1788
  }
1789

1790
  int32_t  iCol = 0, jCol = 0;
216✔
1791
  SSchema *qColumn = NULL;
216✔
1792
  for (;;) {
1793
    qColumn = NULL;
17,933✔
1794

1795
    if (jCol >= pSchema->nCols) break;
17,933✔
1796
    qColumn = &pSchema->pSchema[jCol];
17,718✔
1797

1798
    if (!pColumn && (strcmp(qColumn->name, pAlterTbReq->colName) == 0)) {
17,718✔
1799
      pColumn = qColumn;
146✔
1800
      iCol = jCol;
146✔
1801
      if (rowLen < 0) break;
146✔
1802
    }
1803
    rowLen += qColumn->bytes;
17,717✔
1804
    ++jCol;
17,717✔
1805
  }
1806

1807
  entry.version = version;
216✔
1808
  int      tlen;
1809
  SSchema *pNewSchema = NULL;
216✔
1810
  SSchema  tScheam;
1811
  switch (pAlterTbReq->action) {
216!
1812
    case TSDB_ALTER_TABLE_ADD_COLUMN:
70✔
1813
    case TSDB_ALTER_TABLE_ADD_COLUMN_WITH_COMPRESS_OPTION:
1814
      if (pColumn) {
70!
UNCOV
1815
        terrno = TSDB_CODE_VND_COL_ALREADY_EXISTS;
×
UNCOV
1816
        goto _err;
×
1817
      }
1818
      if ((terrno = grantCheck(TSDB_GRANT_TIMESERIES)) < 0) {
70!
1819
        goto _err;
×
1820
      }
1821
      if (rowLen + pAlterTbReq->bytes > TSDB_MAX_BYTES_PER_ROW) {
70!
UNCOV
1822
        terrno = TSDB_CODE_PAR_INVALID_ROW_LENGTH;
×
UNCOV
1823
        goto _err;
×
1824
      }
1825
      pSchema->version++;
70✔
1826
      pSchema->nCols++;
70✔
1827
      pNewSchema = taosMemoryMalloc(sizeof(SSchema) * pSchema->nCols);
70✔
1828
      if (pNewSchema == NULL) {
70!
1829
        goto _err;
×
1830
      }
1831
      memcpy(pNewSchema, pSchema->pSchema, sizeof(SSchema) * (pSchema->nCols - 1));
70✔
1832
      pSchema->pSchema = pNewSchema;
70✔
1833
      pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].bytes = pAlterTbReq->bytes;
70✔
1834
      pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].type = pAlterTbReq->type;
70✔
1835
      pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].flags = pAlterTbReq->flags;
70✔
1836
      pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].colId = entry.ntbEntry.ncid++;
70✔
1837
      strcpy(pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].name, pAlterTbReq->colName);
70✔
1838

1839
      ++pMeta->pVnode->config.vndStats.numOfNTimeSeries;
70✔
1840
      metaTimeSeriesNotifyCheck(pMeta);
70✔
1841

1842
      if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
70✔
1843
        int16_t cid = pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].colId;
3✔
1844
        int8_t  col_type = pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1].type;
3✔
1845
        int32_t ret = tsdbCacheNewNTableColumn(pMeta->pVnode->pTsdb, entry.uid, cid, col_type);
3✔
1846
        if (ret < 0) {
3!
1847
          terrno = ret;
×
1848
          goto _err;
×
1849
        }
1850
      }
1851
      SSchema *pCol = &pSchema->pSchema[entry.ntbEntry.schemaRow.nCols - 1];
70✔
1852
      uint32_t compress = pAlterTbReq->action == TSDB_ALTER_TABLE_ADD_COLUMN ? createDefaultColCmprByType(pCol->type)
70✔
1853
                                                                             : pAlterTbReq->compress;
70!
1854
      if (updataTableColCmpr(&entry.colCmpr, pCol, 1, compress) != 0) {
70!
1855
        metaError("vgId:%d, failed to update table col cmpr:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name,
×
1856
                  entry.uid);
1857
      }
1858
      freeColCmpr = true;
70✔
1859
      if (entry.colCmpr.nCols != pSchema->nCols) {
70!
1860
        if (pNewSchema) taosMemoryFree(pNewSchema);
×
1861
        if (freeColCmpr) taosMemoryFree(entry.colCmpr.pColCmpr);
×
1862
        terrno = TSDB_CODE_VND_INVALID_TABLE_ACTION;
×
1863
        goto _err;
×
1864
      }
1865
      break;
70✔
1866
    case TSDB_ALTER_TABLE_DROP_COLUMN:
70✔
1867
      if (pColumn == NULL) {
70!
1868
        terrno = TSDB_CODE_VND_COL_NOT_EXISTS;
×
1869
        goto _err;
×
1870
      }
1871
      if (pColumn->colId == 0) {
70!
1872
        terrno = TSDB_CODE_VND_INVALID_TABLE_ACTION;
×
1873
        goto _err;
×
1874
      }
1875
      if (tqCheckColModifiable(pMeta->pVnode->pTq, uid, pColumn->colId) != 0) {
70✔
1876
        terrno = TSDB_CODE_VND_COL_SUBSCRIBED;
11✔
1877
        goto _err;
11✔
1878
      }
1879
      bool hasPrimayKey = false;
59✔
1880
      if (pSchema->nCols >= 2) {
59!
1881
        hasPrimayKey = pSchema->pSchema[1].flags & COL_IS_KEY ? true : false;
59✔
1882
      }
1883

1884
      memcpy(&tScheam, pColumn, sizeof(SSchema));
59✔
1885
      pSchema->version++;
59✔
1886
      tlen = (pSchema->nCols - iCol - 1) * sizeof(SSchema);
59✔
1887
      if (tlen) {
59✔
1888
        memmove(pColumn, pColumn + 1, tlen);
35✔
1889
      }
1890
      pSchema->nCols--;
59✔
1891

1892
      --pMeta->pVnode->config.vndStats.numOfNTimeSeries;
59✔
1893

1894
      if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
59✔
1895
        int16_t cid = pColumn->colId;
3✔
1896

1897
        if (tsdbCacheDropNTableColumn(pMeta->pVnode->pTsdb, entry.uid, cid, hasPrimayKey) != 0) {
3!
1898
          metaError("vgId:%d, failed to drop ntable column:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name,
×
1899
                    entry.uid);
1900
        }
1901
      }
1902

1903
      if (updataTableColCmpr(&entry.colCmpr, &tScheam, 0, 0) != 0) {
59!
1904
        metaError("vgId:%d, failed to update table col cmpr:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name,
×
1905
                  entry.uid);
1906
      }
1907
      if (entry.colCmpr.nCols != pSchema->nCols) {
59!
1908
        terrno = TSDB_CODE_VND_INVALID_TABLE_ACTION;
×
1909
        goto _err;
×
1910
      }
1911
      break;
59✔
1912
    case TSDB_ALTER_TABLE_UPDATE_COLUMN_BYTES:
33✔
1913
      if (pColumn == NULL) {
33!
1914
        terrno = TSDB_CODE_VND_COL_NOT_EXISTS;
×
1915
        goto _err;
×
1916
      }
1917
      if (!IS_VAR_DATA_TYPE(pColumn->type) || pColumn->bytes >= pAlterTbReq->colModBytes) {
33!
UNCOV
1918
        terrno = TSDB_CODE_VND_INVALID_TABLE_ACTION;
×
UNCOV
1919
        goto _err;
×
1920
      }
1921
      if (rowLen + pAlterTbReq->colModBytes - pColumn->bytes > TSDB_MAX_BYTES_PER_ROW) {
33!
UNCOV
1922
        terrno = TSDB_CODE_PAR_INVALID_ROW_LENGTH;
×
UNCOV
1923
        goto _err;
×
1924
      }
1925
      if (tqCheckColModifiable(pMeta->pVnode->pTq, uid, pColumn->colId) != 0) {
33✔
1926
        terrno = TSDB_CODE_VND_COL_SUBSCRIBED;
7✔
1927
        goto _err;
7✔
1928
      }
1929
      pSchema->version++;
26✔
1930
      pColumn->bytes = pAlterTbReq->colModBytes;
26✔
1931
      break;
26✔
1932
    case TSDB_ALTER_TABLE_UPDATE_COLUMN_NAME:
43✔
1933
      if (pAlterTbReq->colNewName == NULL) {
43!
1934
        terrno = TSDB_CODE_INVALID_MSG;
×
1935
        goto _err;
×
1936
      }
1937
      if (pColumn == NULL) {
43!
1938
        terrno = TSDB_CODE_VND_COL_NOT_EXISTS;
×
1939
        goto _err;
×
1940
      }
1941
      if (tqCheckColModifiable(pMeta->pVnode->pTq, uid, pColumn->colId) != 0) {
43✔
1942
        terrno = TSDB_CODE_VND_COL_SUBSCRIBED;
11✔
1943
        goto _err;
11✔
1944
      }
1945
      pSchema->version++;
32✔
1946
      strcpy(pColumn->name, pAlterTbReq->colNewName);
32✔
1947
      break;
32✔
1948
  }
1949

1950
  if (!TSDB_CACHE_NO(pMeta->pVnode->config)) {
187✔
1951
    tsdbCacheInvalidateSchema(pMeta->pVnode->pTsdb, 0, entry.uid, pSchema->version);
6✔
1952
  }
1953

1954
  entry.version = version;
187✔
1955

1956
  // do actual write
1957
  metaWLock(pMeta);
187✔
1958

1959
  if (metaDeleteNcolIdx(pMeta, &oldEntry) < 0) {
187!
1960
    metaError("vgId:%d, failed to delete ncol idx:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1961
  }
1962

1963
  if (metaUpdateNcolIdx(pMeta, &entry) < 0) {
187!
1964
    metaError("vgId:%d, failed to update ncol idx:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1965
  }
1966

1967
  // save to table db
1968
  if (metaSaveToTbDb(pMeta, &entry) < 0) {
187!
1969
    metaError("vgId:%d, failed to save to tb db:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1970
  }
1971

1972
  if (metaUpdateUidIdx(pMeta, &entry) < 0) {
187!
1973
    metaError("vgId:%d, failed to update uid idx:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1974
  }
1975

1976
  if (metaSaveToSkmDb(pMeta, &entry) < 0) {
187!
1977
    metaError("vgId:%d, failed to save to skm db:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1978
  }
1979

1980
  if (metaUpdateChangeTime(pMeta, entry.uid, pAlterTbReq->ctimeMs) < 0) {
187!
1981
    metaError("vgId:%d, failed to update change time:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1982
  }
1983

1984
  metaULock(pMeta);
187✔
1985

1986
  if (metaUpdateMetaRsp(uid, pAlterTbReq->tbName, pSchema, pMetaRsp) < 0) {
187!
1987
    metaError("vgId:%d, failed to update meta rsp:%s uid:%" PRId64, TD_VID(pMeta->pVnode), entry.name, entry.uid);
×
1988
  }
1989
  for (int32_t i = 0; i < entry.colCmpr.nCols; i++) {
17,759✔
1990
    SColCmpr *p = &entry.colCmpr.pColCmpr[i];
17,572✔
1991
    pMetaRsp->pSchemaExt[i].colId = p->id;
17,572✔
1992
    pMetaRsp->pSchemaExt[i].compress = p->alg;
17,572✔
1993
  }
1994

1995
  if (entry.pBuf) taosMemoryFree(entry.pBuf);
187!
1996
  if (pNewSchema) taosMemoryFree(pNewSchema);
187✔
1997
  if (freeColCmpr) taosMemoryFree(entry.colCmpr.pColCmpr);
187✔
1998

1999
  tdbTbcClose(pTbDbc);
187✔
2000
  tdbTbcClose(pUidIdxc);
187✔
2001
  tDecoderClear(&dc);
187✔
2002

2003
  return 0;
187✔
2004

2005
_err:
43✔
2006
  if (entry.pBuf) taosMemoryFree(entry.pBuf);
43!
2007
  tdbTbcClose(pTbDbc);
43✔
2008
  tdbTbcClose(pUidIdxc);
43✔
2009
  tDecoderClear(&dc);
43✔
2010

2011
  return terrno != 0 ? terrno : TSDB_CODE_FAILED;
43!
2012
}
2013

2014
static int metaUpdateTableTagVal(SMeta *pMeta, int64_t version, SVAlterTbReq *pAlterTbReq) {
591✔
2015
  SMetaEntry  ctbEntry = {0};
591✔
2016
  SMetaEntry  stbEntry = {0};
591✔
2017
  void       *pVal = NULL;
591✔
2018
  int         nVal = 0;
591✔
2019
  int         ret;
2020
  int         c;
2021
  tb_uid_t    uid;
2022
  int64_t     oversion;
2023
  const void *pData = NULL;
591✔
2024
  int         nData = 0;
591✔
2025

2026
  if (pAlterTbReq->tagName == NULL) {
591!
2027
    return terrno = TSDB_CODE_INVALID_MSG;
×
2028
  }
2029

2030
  // search name index
2031
  ret = tdbTbGet(pMeta->pNameIdx, pAlterTbReq->tbName, strlen(pAlterTbReq->tbName) + 1, &pVal, &nVal);
591✔
2032
  if (ret < 0) {
591✔
2033
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
1✔
2034
  }
2035

2036
  uid = *(tb_uid_t *)pVal;
590✔
2037
  tdbFree(pVal);
590✔
2038
  pVal = NULL;
590✔
2039

2040
  // search uid index
2041
  TBC *pUidIdxc = NULL;
590✔
2042

2043
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pUidIdx, &pUidIdxc, NULL));
590!
2044
  if (tdbTbcMoveTo(pUidIdxc, &uid, sizeof(uid), &c) < 0) {
590!
2045
    metaTrace("meta/table: failed to move to uid index, uid:%" PRId64, uid);
×
2046
  }
2047
  if (c != 0) {
590!
2048
    tdbTbcClose(pUidIdxc);
×
2049
    metaError("meta/table: invalide c: %" PRId32 " update tb tag val failed.", c);
×
2050
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
2051
  }
2052

2053
  if (tdbTbcGet(pUidIdxc, NULL, NULL, &pData, &nData) != 0) {
590!
2054
    metaError("meta/table: failed to get uid index, uid:%" PRId64, uid);
×
2055
  }
2056
  oversion = ((SUidIdxVal *)pData)[0].version;
590✔
2057

2058
  // search table.db
2059
  TBC     *pTbDbc = NULL;
590✔
2060
  SDecoder dc1 = {0};
590✔
2061
  SDecoder dc2 = {0};
590✔
2062

2063
  /* get ctbEntry */
2064
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pTbDb, &pTbDbc, NULL));
590!
2065
  if (tdbTbcMoveTo(pTbDbc, &((STbDbKey){.uid = uid, .version = oversion}), sizeof(STbDbKey), &c) != 0) {
590!
2066
    metaError("meta/table: failed to move to tb db, uid:%" PRId64, uid);
×
2067
  }
2068
  if (c != 0) {
590!
2069
    tdbTbcClose(pUidIdxc);
×
2070
    tdbTbcClose(pTbDbc);
×
2071
    metaError("meta/table: invalide c: %" PRId32 " update tb tag val failed.", c);
×
2072
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
2073
  }
2074

2075
  if (tdbTbcGet(pTbDbc, NULL, NULL, &pData, &nData) != 0) {
590!
2076
    metaError("meta/table: failed to get tb db, uid:%" PRId64, uid);
×
2077
  }
2078

2079
  if ((ctbEntry.pBuf = taosMemoryMalloc(nData)) == NULL) {
590!
2080
    tdbTbcClose(pUidIdxc);
×
2081
    tdbTbcClose(pTbDbc);
×
2082
    return terrno;
×
2083
  }
2084
  memcpy(ctbEntry.pBuf, pData, nData);
590✔
2085
  tDecoderInit(&dc1, ctbEntry.pBuf, nData);
590✔
2086
  ret = metaDecodeEntry(&dc1, &ctbEntry);
590✔
2087
  if (ret < 0) {
590!
2088
    terrno = ret;
×
2089
    goto _err;
×
2090
  }
2091

2092
  /* get stbEntry*/
2093
  if (tdbTbGet(pMeta->pUidIdx, &ctbEntry.ctbEntry.suid, sizeof(tb_uid_t), &pVal, &nVal) != 0) {
590!
2094
    metaError("meta/table: failed to get uid index, uid:%" PRId64, ctbEntry.ctbEntry.suid);
×
2095
  }
2096
  if (!pVal) {
590!
2097
    terrno = TSDB_CODE_INVALID_MSG;
×
2098
    goto _err;
×
2099
  }
2100

2101
  if (tdbTbGet(pMeta->pTbDb, &((STbDbKey){.uid = ctbEntry.ctbEntry.suid, .version = ((SUidIdxVal *)pVal)[0].version}),
590!
2102
               sizeof(STbDbKey), (void **)&stbEntry.pBuf, &nVal) != 0) {
2103
    metaError("meta/table: failed to get tb db, uid:%" PRId64, ctbEntry.ctbEntry.suid);
×
2104
  }
2105
  tdbFree(pVal);
590✔
2106
  tDecoderInit(&dc2, stbEntry.pBuf, nVal);
590✔
2107
  ret = metaDecodeEntry(&dc2, &stbEntry);
590✔
2108
  if (ret < 0) {
590!
2109
    terrno = ret;
×
2110
    goto _err;
×
2111
  }
2112

2113
  SSchemaWrapper *pTagSchema = &stbEntry.stbEntry.schemaTag;
590✔
2114
  SSchema        *pColumn = NULL;
590✔
2115
  int32_t         iCol = 0;
590✔
2116
  for (;;) {
2117
    pColumn = NULL;
1,546✔
2118

2119
    if (iCol >= pTagSchema->nCols) break;
1,546!
2120
    pColumn = &pTagSchema->pSchema[iCol];
1,546✔
2121

2122
    if (strcmp(pColumn->name, pAlterTbReq->tagName) == 0) break;
1,546✔
2123
    iCol++;
956✔
2124
  }
2125

2126
  if (pColumn == NULL) {
590!
2127
    terrno = TSDB_CODE_VND_COL_NOT_EXISTS;
×
2128
    goto _err;
×
2129
  }
2130

2131
  ctbEntry.version = version;
590✔
2132
  if (pTagSchema->nCols == 1 && pTagSchema->pSchema[0].type == TSDB_DATA_TYPE_JSON) {
590✔
2133
    ctbEntry.ctbEntry.pTags = taosMemoryMalloc(pAlterTbReq->nTagVal);
15✔
2134
    if (ctbEntry.ctbEntry.pTags == NULL) {
15!
2135
      terrno = TSDB_CODE_OUT_OF_MEMORY;
×
2136
      goto _err;
×
2137
    }
2138
    memcpy((void *)ctbEntry.ctbEntry.pTags, pAlterTbReq->pTagVal, pAlterTbReq->nTagVal);
15✔
2139
  } else {
2140
    const STag *pOldTag = (const STag *)ctbEntry.ctbEntry.pTags;
575✔
2141
    STag       *pNewTag = NULL;
575✔
2142
    SArray     *pTagArray = taosArrayInit(pTagSchema->nCols, sizeof(STagVal));
575✔
2143
    if (!pTagArray) {
575!
2144
      terrno = TSDB_CODE_OUT_OF_MEMORY;
×
2145
      goto _err;
×
2146
    }
2147
    for (int32_t i = 0; i < pTagSchema->nCols; i++) {
2,696✔
2148
      SSchema *pCol = &pTagSchema->pSchema[i];
2,121✔
2149
      if (iCol == i) {
2,121✔
2150
        if (pAlterTbReq->isNull) {
575✔
2151
          continue;
50✔
2152
        }
2153
        STagVal val = {0};
525✔
2154
        val.type = pCol->type;
525✔
2155
        val.cid = pCol->colId;
525✔
2156
        if (IS_VAR_DATA_TYPE(pCol->type)) {
525!
2157
          val.pData = pAlterTbReq->pTagVal;
190✔
2158
          val.nData = pAlterTbReq->nTagVal;
190✔
2159
        } else {
2160
          memcpy(&val.i64, pAlterTbReq->pTagVal, pAlterTbReq->nTagVal);
335✔
2161
        }
2162
        if (taosArrayPush(pTagArray, &val) == NULL) {
525!
2163
          terrno = TSDB_CODE_OUT_OF_MEMORY;
×
2164
          taosArrayDestroy(pTagArray);
×
2165
          goto _err;
×
2166
        }
2167
      } else {
2168
        STagVal val = {.cid = pCol->colId};
1,546✔
2169
        if (tTagGet(pOldTag, &val)) {
1,546✔
2170
          if (taosArrayPush(pTagArray, &val) == NULL) {
1,134!
2171
            terrno = TSDB_CODE_OUT_OF_MEMORY;
×
2172
            taosArrayDestroy(pTagArray);
×
2173
            goto _err;
×
2174
          }
2175
        }
2176
      }
2177
    }
2178
    if ((terrno = tTagNew(pTagArray, pTagSchema->version, false, &pNewTag)) < 0) {
575!
2179
      taosArrayDestroy(pTagArray);
×
2180
      goto _err;
×
2181
    }
2182
    ctbEntry.ctbEntry.pTags = (uint8_t *)pNewTag;
575✔
2183
    taosArrayDestroy(pTagArray);
575✔
2184
  }
2185

2186
  metaWLock(pMeta);
590✔
2187

2188
  // save to table.db
2189
  if (metaSaveToTbDb(pMeta, &ctbEntry) < 0) {
590!
2190
    metaError("meta/table: failed to save to tb db:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2191
  }
2192

2193
  // save to uid.idx
2194
  if (metaUpdateUidIdx(pMeta, &ctbEntry) < 0) {
590!
2195
    metaError("meta/table: failed to update uid idx:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2196
  }
2197

2198
  if (metaUpdateTagIdx(pMeta, &ctbEntry) < 0) {
590!
2199
    metaError("meta/table: failed to update tag idx:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2200
  }
2201

2202
  if (NULL == ctbEntry.ctbEntry.pTags) {
590!
2203
    metaError("meta/table: null tags, update tag val failed.");
×
2204
    goto _err;
×
2205
  }
2206

2207
  SCtbIdxKey ctbIdxKey = {.suid = ctbEntry.ctbEntry.suid, .uid = uid};
590✔
2208
  if (tdbTbUpsert(pMeta->pCtbIdx, &ctbIdxKey, sizeof(ctbIdxKey), ctbEntry.ctbEntry.pTags,
590!
2209
                  ((STag *)(ctbEntry.ctbEntry.pTags))->len, pMeta->txn) < 0) {
590✔
2210
    metaError("meta/table: failed to upsert ctb idx:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2211
  }
2212

2213
  if (metaUidCacheClear(pMeta, ctbEntry.ctbEntry.suid) < 0) {
590!
2214
    metaError("meta/table: failed to clear uid cache:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2215
  }
2216

2217
  if (metaTbGroupCacheClear(pMeta, ctbEntry.ctbEntry.suid) < 0) {
590!
2218
    metaError("meta/table: failed to clear group cache:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2219
  }
2220

2221
  if (metaUpdateChangeTime(pMeta, ctbEntry.uid, pAlterTbReq->ctimeMs) < 0) {
590!
2222
    metaError("meta/table: failed to update change time:%s uid:%" PRId64, ctbEntry.name, ctbEntry.uid);
×
2223
  }
2224

2225
  metaULock(pMeta);
590✔
2226

2227
  tDecoderClear(&dc1);
590✔
2228
  tDecoderClear(&dc2);
590✔
2229
  taosMemoryFree((void *)ctbEntry.ctbEntry.pTags);
590✔
2230
  if (ctbEntry.pBuf) taosMemoryFree(ctbEntry.pBuf);
590!
2231
  if (stbEntry.pBuf) tdbFree(stbEntry.pBuf);
590!
2232
  tdbTbcClose(pTbDbc);
590✔
2233
  tdbTbcClose(pUidIdxc);
590✔
2234
  return 0;
590✔
2235

2236
_err:
×
2237
  tDecoderClear(&dc1);
×
2238
  tDecoderClear(&dc2);
×
2239
  if (ctbEntry.pBuf) taosMemoryFree(ctbEntry.pBuf);
×
2240
  if (stbEntry.pBuf) tdbFree(stbEntry.pBuf);
×
2241
  tdbTbcClose(pTbDbc);
×
2242
  tdbTbcClose(pUidIdxc);
×
2243
  return -1;
×
2244
}
2245

2246
static int metaUpdateTableOptions(SMeta *pMeta, int64_t version, SVAlterTbReq *pAlterTbReq) {
82✔
2247
  void       *pVal = NULL;
82✔
2248
  int         nVal = 0;
82✔
2249
  const void *pData = NULL;
82✔
2250
  int         nData = 0;
82✔
2251
  int         ret = 0;
82✔
2252
  tb_uid_t    uid;
2253
  int64_t     oversion;
2254
  SMetaEntry  entry = {0};
82✔
2255
  int         c = 0;
82✔
2256

2257
  // search name index
2258
  ret = tdbTbGet(pMeta->pNameIdx, pAlterTbReq->tbName, strlen(pAlterTbReq->tbName) + 1, &pVal, &nVal);
82✔
2259
  if (ret < 0) {
82!
2260
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
2261
  }
2262

2263
  uid = *(tb_uid_t *)pVal;
82✔
2264
  tdbFree(pVal);
82✔
2265
  pVal = NULL;
82✔
2266

2267
  // search uid index
2268
  TBC *pUidIdxc = NULL;
82✔
2269

2270
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pUidIdx, &pUidIdxc, NULL));
82!
2271
  if (tdbTbcMoveTo(pUidIdxc, &uid, sizeof(uid), &c) < 0) {
82!
2272
    metaError("meta/table: failed to move to uid index, uid:%" PRId64, uid);
×
2273
  }
2274
  if (c != 0) {
82!
2275
    tdbTbcClose(pUidIdxc);
×
2276
    metaError("meta/table: invalide c: %" PRId32 " update tb options failed.", c);
×
2277
    return TSDB_CODE_FAILED;
×
2278
  }
2279

2280
  if (tdbTbcGet(pUidIdxc, NULL, NULL, &pData, &nData) < 0) {
82!
2281
    metaError("meta/table: failed to get uid index, uid:%" PRId64, uid);
×
2282
  }
2283
  oversion = ((SUidIdxVal *)pData)[0].version;
82✔
2284

2285
  // search table.db
2286
  TBC *pTbDbc = NULL;
82✔
2287

2288
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pTbDb, &pTbDbc, NULL));
82!
2289
  if (tdbTbcMoveTo(pTbDbc, &((STbDbKey){.uid = uid, .version = oversion}), sizeof(STbDbKey), &c) < 0) {
82!
2290
    metaError("meta/table: failed to move to tb db, uid:%" PRId64, uid);
×
2291
  }
2292
  if (c != 0) {
82!
2293
    tdbTbcClose(pUidIdxc);
×
2294
    tdbTbcClose(pTbDbc);
×
2295
    metaError("meta/table: invalide c: %" PRId32 " update tb options failed.", c);
×
2296
    return TSDB_CODE_FAILED;
×
2297
  }
2298

2299
  if (tdbTbcGet(pTbDbc, NULL, NULL, &pData, &nData) < 0) {
82!
2300
    metaError("meta/table: failed to get tb db, uid:%" PRId64, uid);
×
2301
  }
2302

2303
  // get table entry
2304
  SDecoder dc = {0};
82✔
2305
  if ((entry.pBuf = taosMemoryMalloc(nData)) == NULL) {
82!
2306
    tdbTbcClose(pUidIdxc);
×
2307
    tdbTbcClose(pTbDbc);
×
2308
    return terrno;
×
2309
  }
2310
  memcpy(entry.pBuf, pData, nData);
82✔
2311
  tDecoderInit(&dc, entry.pBuf, nData);
82✔
2312
  ret = metaDecodeEntry(&dc, &entry);
82✔
2313
  if (ret != 0) {
82!
2314
    tDecoderClear(&dc);
×
2315
    tdbTbcClose(pUidIdxc);
×
2316
    tdbTbcClose(pTbDbc);
×
2317
    metaError("meta/table: invalide ret: %" PRId32 " alt tb options failed.", ret);
×
2318
    return TSDB_CODE_FAILED;
×
2319
  }
2320

2321
  entry.version = version;
82✔
2322
  metaWLock(pMeta);
82✔
2323
  // build SMetaEntry
2324
  if (entry.type == TSDB_CHILD_TABLE) {
82✔
2325
    if (pAlterTbReq->updateTTL) {
39✔
2326
      metaDeleteTtl(pMeta, &entry);
13✔
2327
      entry.ctbEntry.ttlDays = pAlterTbReq->newTTL;
13✔
2328
      metaUpdateTtl(pMeta, &entry);
13✔
2329
    }
2330
    if (pAlterTbReq->newCommentLen >= 0) {
39✔
2331
      entry.ctbEntry.commentLen = pAlterTbReq->newCommentLen;
26✔
2332
      entry.ctbEntry.comment = pAlterTbReq->newComment;
26✔
2333
    }
2334
  } else {
2335
    if (pAlterTbReq->updateTTL) {
43✔
2336
      metaDeleteTtl(pMeta, &entry);
15✔
2337
      entry.ntbEntry.ttlDays = pAlterTbReq->newTTL;
15✔
2338
      metaUpdateTtl(pMeta, &entry);
15✔
2339
    }
2340
    if (pAlterTbReq->newCommentLen >= 0) {
43✔
2341
      entry.ntbEntry.commentLen = pAlterTbReq->newCommentLen;
28✔
2342
      entry.ntbEntry.comment = pAlterTbReq->newComment;
28✔
2343
    }
2344
  }
2345

2346
  // save to table db
2347
  if (metaSaveToTbDb(pMeta, &entry) < 0) {
82!
2348
    metaError("meta/table: failed to save to tb db:%s uid:%" PRId64, entry.name, entry.uid);
×
2349
  }
2350

2351
  if (metaUpdateUidIdx(pMeta, &entry) < 0) {
82!
2352
    metaError("meta/table: failed to update uid idx:%s uid:%" PRId64, entry.name, entry.uid);
×
2353
  }
2354

2355
  if (metaUpdateChangeTime(pMeta, entry.uid, pAlterTbReq->ctimeMs) < 0) {
82!
2356
    metaError("meta/table: failed to update change time:%s uid:%" PRId64, entry.name, entry.uid);
×
2357
  }
2358

2359
  metaULock(pMeta);
82✔
2360

2361
  tdbTbcClose(pTbDbc);
82✔
2362
  tdbTbcClose(pUidIdxc);
82✔
2363
  tDecoderClear(&dc);
82✔
2364
  if (entry.pBuf) taosMemoryFree(entry.pBuf);
82!
2365
  return 0;
82✔
2366
}
2367

2368
static int metaAddTagIndex(SMeta *pMeta, int64_t version, SVAlterTbReq *pAlterTbReq) {
×
2369
  SMetaEntry  stbEntry = {0};
×
2370
  void       *pVal = NULL;
×
2371
  int         nVal = 0;
×
2372
  int         ret;
2373
  int         c;
2374
  tb_uid_t    uid, suid;
2375
  int64_t     oversion;
2376
  const void *pData = NULL;
×
2377
  int         nData = 0;
×
2378
  SDecoder    dc = {0};
×
2379

2380
  if (pAlterTbReq->tagName == NULL) {
×
2381
    return terrno = TSDB_CODE_INVALID_MSG;
×
2382
  }
2383

2384
  // search name index
2385
  ret = tdbTbGet(pMeta->pNameIdx, pAlterTbReq->tbName, strlen(pAlterTbReq->tbName) + 1, &pVal, &nVal);
×
2386
  if (ret < 0) {
×
2387
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
2388
  } else {
2389
    uid = *(tb_uid_t *)pVal;
×
2390
    tdbFree(pVal);
×
2391
    pVal = NULL;
×
2392
  }
2393

2394
  if (tdbTbGet(pMeta->pUidIdx, &uid, sizeof(tb_uid_t), &pVal, &nVal) == -1) {
×
2395
    ret = -1;
×
2396
    goto _err;
×
2397
  }
2398
  suid = ((SUidIdxVal *)pVal)[0].suid;
×
2399

2400
  STbDbKey tbDbKey = {0};
×
2401
  tbDbKey.uid = suid;
×
2402
  tbDbKey.version = ((SUidIdxVal *)pVal)[0].version;
×
2403
  ret = tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &pVal, &nVal);
×
2404
  if (ret < 0) {
×
2405
    goto _err;
×
2406
  }
2407
  tDecoderInit(&dc, pVal, nVal);
×
2408
  ret = metaDecodeEntry(&dc, &stbEntry);
×
2409
  if (ret < 0) {
×
2410
    tDecoderClear(&dc);
×
2411
    goto _err;
×
2412
  }
2413

2414
  // Get target schema info
2415
  SSchemaWrapper *pTagSchema = &stbEntry.stbEntry.schemaTag;
×
2416
  if (pTagSchema->nCols == 1 && pTagSchema->pSchema[0].type == TSDB_DATA_TYPE_JSON) {
×
2417
    terrno = TSDB_CODE_VND_COL_ALREADY_EXISTS;
×
2418
    goto _err;
×
2419
  }
2420
  SSchema *pCol = NULL;
×
2421
  int32_t  iCol = 0;
×
2422
  for (;;) {
2423
    pCol = NULL;
×
2424
    if (iCol >= pTagSchema->nCols) break;
×
2425
    pCol = &pTagSchema->pSchema[iCol];
×
2426
    if (strcmp(pCol->name, pAlterTbReq->tagName) == 0) break;
×
2427
    iCol++;
×
2428
  }
2429

2430
  if (iCol == 0) {
×
2431
    terrno = TSDB_CODE_VND_COL_ALREADY_EXISTS;
×
2432
    goto _err;
×
2433
  }
2434
  if (pCol == NULL) {
×
2435
    terrno = TSDB_CODE_VND_COL_NOT_EXISTS;
×
2436
    goto _err;
×
2437
  }
2438

2439
  /*
2440
   * iterator all pTdDbc by uid and version
2441
   */
2442
  TBC *pCtbIdxc = NULL;
×
2443
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pCtbIdx, &pCtbIdxc, NULL));
×
2444
  int rc = tdbTbcMoveTo(pCtbIdxc, &(SCtbIdxKey){.suid = suid, .uid = INT64_MIN}, sizeof(SCtbIdxKey), &c);
×
2445
  if (rc < 0) {
×
2446
    tdbTbcClose(pCtbIdxc);
×
2447
    goto _err;
×
2448
  }
2449
  for (;;) {
×
2450
    void *pKey, *pVal;
2451
    int   nKey, nVal;
2452
    rc = tdbTbcNext(pCtbIdxc, &pKey, &nKey, &pVal, &nVal);
×
2453
    if (rc < 0) break;
×
2454
    if (((SCtbIdxKey *)pKey)->suid != uid) {
×
2455
      tdbFree(pKey);
×
2456
      tdbFree(pVal);
×
2457
      continue;
×
2458
    }
2459
    STagIdxKey *pTagIdxKey = NULL;
×
2460
    int32_t     nTagIdxKey;
2461

2462
    const void *pTagData = NULL;
×
2463
    int32_t     nTagData = 0;
×
2464

2465
    STagVal tagVal = {.cid = pCol->colId};
×
2466
    if (tTagGet((const STag *)pVal, &tagVal)) {
×
2467
      if (IS_VAR_DATA_TYPE(pCol->type)) {
×
2468
        pTagData = tagVal.pData;
×
2469
        nTagData = (int32_t)tagVal.nData;
×
2470
      } else {
2471
        pTagData = &(tagVal.i64);
×
2472
        nTagData = tDataTypes[pCol->type].bytes;
×
2473
      }
2474
    } else {
2475
      if (!IS_VAR_DATA_TYPE(pCol->type)) {
×
2476
        nTagData = tDataTypes[pCol->type].bytes;
×
2477
      }
2478
    }
2479
    if (metaCreateTagIdxKey(suid, pCol->colId, pTagData, nTagData, pCol->type, uid, &pTagIdxKey, &nTagIdxKey) < 0) {
×
2480
      tdbFree(pKey);
×
2481
      tdbFree(pVal);
×
2482
      metaDestroyTagIdxKey(pTagIdxKey);
×
2483
      tdbTbcClose(pCtbIdxc);
×
2484
      goto _err;
×
2485
    }
2486
    ret = tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn);
×
2487
    if (ret < 0) {
×
2488
      metaError("meta/table: failed to upsert tag idx:%s uid:%" PRId64, stbEntry.name, stbEntry.uid);
×
2489
    }
2490
    metaDestroyTagIdxKey(pTagIdxKey);
×
2491
    pTagIdxKey = NULL;
×
2492
  }
2493
  tdbTbcClose(pCtbIdxc);
×
2494
  return 0;
×
2495

2496
_err:
×
2497
  // tDecoderClear(&dc1);
2498
  // tDecoderClear(&dc2);
2499
  // if (ctbEntry.pBuf) taosMemoryFree(ctbEntry.pBuf);
2500
  // if (stbEntry.pBuf) tdbFree(stbEntry.pBuf);
2501
  // tdbTbcClose(pTbDbc);
2502
  // tdbTbcClose(pUidIdxc);
2503
  return TSDB_CODE_FAILED;
×
2504
}
2505

2506
typedef struct SMetaPair {
2507
  void *key;
2508
  int   nkey;
2509
} SMetaPair;
2510

2511
static int metaDropTagIndex(SMeta *pMeta, int64_t version, SVAlterTbReq *pAlterTbReq) {
×
2512
  SMetaEntry  stbEntry = {0};
×
2513
  void       *pVal = NULL;
×
2514
  int         nVal = 0;
×
2515
  int         ret;
2516
  int         c;
2517
  tb_uid_t    suid;
2518
  int64_t     oversion;
2519
  const void *pData = NULL;
×
2520
  int         nData = 0;
×
2521
  SDecoder    dc = {0};
×
2522

2523
  if (pAlterTbReq->tagName == NULL) {
×
2524
    return terrno = TSDB_CODE_INVALID_MSG;
×
2525
  }
2526

2527
  // search name index
2528
  ret = tdbTbGet(pMeta->pNameIdx, pAlterTbReq->tbName, strlen(pAlterTbReq->tbName) + 1, &pVal, &nVal);
×
2529
  if (ret < 0) {
×
2530
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
2531
  }
2532
  suid = *(tb_uid_t *)pVal;
×
2533
  tdbFree(pVal);
×
2534
  pVal = NULL;
×
2535

2536
  if (tdbTbGet(pMeta->pUidIdx, &suid, sizeof(tb_uid_t), &pVal, &nVal) == -1) {
×
2537
    ret = -1;
×
2538
    goto _err;
×
2539
  }
2540

2541
  STbDbKey tbDbKey = {0};
×
2542
  tbDbKey.uid = suid;
×
2543
  tbDbKey.version = ((SUidIdxVal *)pVal)[0].version;
×
2544
  ret = tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &pVal, &nVal);
×
2545
  if (ret < 0) {
×
2546
    goto _err;
×
2547
  }
2548

2549
  tDecoderInit(&dc, pVal, nVal);
×
2550
  ret = metaDecodeEntry(&dc, &stbEntry);
×
2551
  if (ret < 0) {
×
2552
    tDecoderClear(&dc);
×
2553
    goto _err;
×
2554
  }
2555

2556
  // Get targe schema info
2557
  SSchemaWrapper *pTagSchema = &stbEntry.stbEntry.schemaTag;
×
2558
  if (pTagSchema->nCols == 1 && pTagSchema->pSchema[0].type == TSDB_DATA_TYPE_JSON) {
×
2559
    terrno = TSDB_CODE_VND_COL_ALREADY_EXISTS;
×
2560
    goto _err;
×
2561
  }
2562
  SSchema *pCol = NULL;
×
2563
  int32_t  iCol = 0;
×
2564
  for (;;) {
2565
    pCol = NULL;
×
2566
    if (iCol >= pTagSchema->nCols) break;
×
2567
    pCol = &pTagSchema->pSchema[iCol];
×
2568
    if (strcmp(pCol->name, pAlterTbReq->tagName) == 0) break;
×
2569
    iCol++;
×
2570
  }
2571
  if (iCol == 0) {
×
2572
    // cannot drop 1th tag index
2573
    terrno = -1;
×
2574
    goto _err;
×
2575
  }
2576
  if (pCol == NULL) {
×
2577
    terrno = TSDB_CODE_VND_COL_NOT_EXISTS;
×
2578
    goto _err;
×
2579
  }
2580

2581
  if (IS_IDX_ON(pCol)) {
×
2582
    terrno = TSDB_CODE_VND_COL_ALREADY_EXISTS;
×
2583
    goto _err;
×
2584
  }
2585

2586
  SArray *tagIdxList = taosArrayInit(512, sizeof(SMetaPair));
×
2587
  if (tagIdxList == NULL) {
×
2588
    goto _err;
×
2589
  }
2590

2591
  TBC *pTagIdxc = NULL;
×
2592
  TAOS_CHECK_RETURN(tdbTbcOpen(pMeta->pTagIdx, &pTagIdxc, NULL));
×
2593
  int rc =
2594
      tdbTbcMoveTo(pTagIdxc, &(STagIdxKey){.suid = suid, .cid = INT32_MIN, .type = pCol->type}, sizeof(STagIdxKey), &c);
×
2595
  for (;;) {
×
2596
    void *pKey, *pVal;
2597
    int   nKey, nVal;
2598
    rc = tdbTbcNext(pTagIdxc, &pKey, &nKey, &pVal, &nVal);
×
2599
    STagIdxKey *pIdxKey = (STagIdxKey *)pKey;
×
2600
    if (pIdxKey->suid != suid || pIdxKey->cid != pCol->colId) {
×
2601
      tdbFree(pKey);
×
2602
      tdbFree(pVal);
×
2603
      continue;
×
2604
    }
2605

2606
    SMetaPair pair = {.key = pKey, nKey = nKey};
×
2607
    if (taosArrayPush(tagIdxList, &pair) == NULL) {
×
2608
      goto _err;
×
2609
    }
2610
  }
2611
  tdbTbcClose(pTagIdxc);
2612

2613
  metaWLock(pMeta);
2614
  for (int i = 0; i < taosArrayGetSize(tagIdxList); i++) {
2615
    SMetaPair *pair = taosArrayGet(tagIdxList, i);
2616
    ret = tdbTbDelete(pMeta->pTagIdx, pair->key, pair->nkey, pMeta->txn);
2617
    if (ret < 0) {
2618
      metaError("meta/table: failed to delete tag idx:%s uid:%" PRId64, stbEntry.name, stbEntry.uid);
2619
    }
2620
  }
2621
  metaULock(pMeta);
2622

2623
  taosArrayDestroy(tagIdxList);
2624

2625
  // set pCol->flags; INDEX_ON
2626
  return 0;
2627
_err:
×
2628
  return TSDB_CODE_FAILED;
×
2629
}
UNCOV
2630
int32_t metaUpdateTableColCompress(SMeta *pMeta, int64_t version, SVAlterTbReq *pReq) {
×
2631
  // impl later
UNCOV
2632
  SMetaEntry  tbEntry = {0};
×
UNCOV
2633
  void       *pVal = NULL;
×
UNCOV
2634
  int         nVal = 0;
×
2635
  int         ret;
2636
  int         c;
2637
  tb_uid_t    suid;
2638
  int64_t     oversion;
UNCOV
2639
  const void *pData = NULL;
×
UNCOV
2640
  int         nData = 0;
×
UNCOV
2641
  SDecoder    dc = {0};
×
UNCOV
2642
  ret = tdbTbGet(pMeta->pNameIdx, pReq->tbName, strlen(pReq->tbName) + 1, &pVal, &nVal);
×
UNCOV
2643
  if (ret < 0) {
×
2644
    return terrno = TSDB_CODE_TDB_TABLE_NOT_EXIST;
×
2645
  }
UNCOV
2646
  suid = *(tb_uid_t *)pVal;
×
UNCOV
2647
  tdbFree(pVal);
×
UNCOV
2648
  pVal = NULL;
×
2649

UNCOV
2650
  if (tdbTbGet(pMeta->pUidIdx, &suid, sizeof(tb_uid_t), &pVal, &nVal) == -1) {
×
2651
    terrno = TSDB_CODE_INVALID_MSG;
×
2652
    ret = -1;
×
2653
    goto _err;
×
2654
  }
2655

UNCOV
2656
  STbDbKey tbDbKey = {0};
×
UNCOV
2657
  tbDbKey.uid = suid;
×
UNCOV
2658
  tbDbKey.version = ((SUidIdxVal *)pVal)[0].version;
×
UNCOV
2659
  if (tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &pVal, &nVal) < 0) {
×
2660
    terrno = TSDB_CODE_INVALID_MSG;
×
2661
    tdbFree(pVal);
×
2662
    goto _err;
×
2663
  }
2664

UNCOV
2665
  tDecoderInit(&dc, pVal, nVal);
×
UNCOV
2666
  ret = metaDecodeEntry(&dc, &tbEntry);
×
UNCOV
2667
  if (ret < 0) {
×
2668
    terrno = TSDB_CODE_INVALID_MSG;
×
2669
    tdbFree(pVal);
×
2670
    tDecoderClear(&dc);
×
2671
    goto _err;
×
2672
  }
UNCOV
2673
  if (tbEntry.type != TSDB_NORMAL_TABLE && tbEntry.type != TSDB_SUPER_TABLE) {
×
2674
    terrno = TSDB_CODE_INVALID_MSG;
×
2675
    tdbFree(pVal);
×
2676
    tDecoderClear(&dc);
×
2677
    goto _err;
×
2678
  }
UNCOV
2679
  int8_t           updated = 0;
×
UNCOV
2680
  SColCmprWrapper *wp = &tbEntry.colCmpr;
×
UNCOV
2681
  for (int32_t i = 0; i < wp->nCols; i++) {
×
UNCOV
2682
    SColCmpr *p = &wp->pColCmpr[i];
×
UNCOV
2683
    if (p->id == pReq->colId) {
×
UNCOV
2684
      uint32_t dst = 0;
×
UNCOV
2685
      updated = tUpdateCompress(p->alg, pReq->compress, TSDB_COLVAL_COMPRESS_DISABLED, TSDB_COLVAL_LEVEL_DISABLED,
×
2686
                                TSDB_COLVAL_LEVEL_MEDIUM, &dst);
UNCOV
2687
      if (updated > 0) {
×
UNCOV
2688
        p->alg = dst;
×
2689
      }
2690
    }
2691
  }
UNCOV
2692
  if (updated == 0) {
×
2693
    tdbFree(pVal);
×
2694
    tDecoderClear(&dc);
×
2695
    terrno = TSDB_CODE_VND_COLUMN_COMPRESS_ALREADY_EXIST;
×
2696
    goto _err;
×
UNCOV
2697
  } else if (updated < 0) {
×
2698
    tdbFree(pVal);
×
2699
    tDecoderClear(&dc);
×
2700
    terrno = TSDB_CODE_TSC_COMPRESS_LEVEL_ERROR;
×
2701
    goto _err;
×
2702
  }
UNCOV
2703
  tbEntry.version = version;
×
2704

UNCOV
2705
  metaWLock(pMeta);
×
UNCOV
2706
  if (metaSaveToTbDb(pMeta, &tbEntry) < 0) {
×
2707
    metaError("meta/table: failed to save to tb db:%s uid:%" PRId64, tbEntry.name, tbEntry.uid);
×
2708
  }
2709

UNCOV
2710
  if (metaUpdateUidIdx(pMeta, &tbEntry) < 0) {
×
2711
    metaError("meta/table: failed to update uid idx:%s uid:%" PRId64, tbEntry.name, tbEntry.uid);
×
2712
  }
2713

UNCOV
2714
  if (metaUpdateChangeTime(pMeta, suid, pReq->ctimeMs) < 0) {
×
2715
    metaError("meta/table: failed to update change time:%s uid:%" PRId64, tbEntry.name, tbEntry.uid);
×
2716
  }
2717

UNCOV
2718
  metaULock(pMeta);
×
2719

UNCOV
2720
  tdbFree(pVal);
×
UNCOV
2721
  tDecoderClear(&dc);
×
2722

UNCOV
2723
  return 0;
×
2724
_err:
×
2725
  return TSDB_CODE_FAILED;
×
2726
}
2727

2728
int metaAlterTable(SMeta *pMeta, int64_t version, SVAlterTbReq *pReq, STableMetaRsp *pMetaRsp) {
903✔
2729
  pMeta->changed = true;
903✔
2730
  switch (pReq->action) {
903!
2731
    case TSDB_ALTER_TABLE_ADD_COLUMN:
230✔
2732
    case TSDB_ALTER_TABLE_ADD_COLUMN_WITH_COMPRESS_OPTION:
2733
    case TSDB_ALTER_TABLE_DROP_COLUMN:
2734
    case TSDB_ALTER_TABLE_UPDATE_COLUMN_BYTES:
2735
    case TSDB_ALTER_TABLE_UPDATE_COLUMN_NAME:
2736
      return metaAlterTableColumn(pMeta, version, pReq, pMetaRsp);
230✔
2737
    case TSDB_ALTER_TABLE_UPDATE_TAG_VAL:
591✔
2738
      return metaUpdateTableTagVal(pMeta, version, pReq);
591✔
2739
    case TSDB_ALTER_TABLE_UPDATE_OPTIONS:
82✔
2740
      return metaUpdateTableOptions(pMeta, version, pReq);
82✔
2741
    case TSDB_ALTER_TABLE_ADD_TAG_INDEX:
×
2742
      return metaAddTagIndex(pMeta, version, pReq);
×
2743
    case TSDB_ALTER_TABLE_DROP_TAG_INDEX:
×
2744
      return metaDropTagIndex(pMeta, version, pReq);
×
UNCOV
2745
    case TSDB_ALTER_TABLE_UPDATE_COLUMN_COMPRESS:
×
UNCOV
2746
      return metaUpdateTableColCompress(pMeta, version, pReq);
×
2747
    default:
×
2748
      return terrno = TSDB_CODE_VND_INVALID_TABLE_ACTION;
×
2749
      break;
2750
  }
2751
}
2752

2753
static int metaSaveToTbDb(SMeta *pMeta, const SMetaEntry *pME) {
44,847✔
2754
  STbDbKey tbDbKey;
2755
  void    *pKey = NULL;
44,847✔
2756
  void    *pVal = NULL;
44,847✔
2757
  int      kLen = 0;
44,847✔
2758
  int      vLen = 0;
44,847✔
2759
  SEncoder coder = {0};
44,847✔
2760

2761
  // set key and value
2762
  tbDbKey.version = pME->version;
44,847✔
2763
  tbDbKey.uid = pME->uid;
44,847✔
2764

2765
  metaDebug("vgId:%d, start to save table version:%" PRId64 " uid:%" PRId64, TD_VID(pMeta->pVnode), pME->version,
44,847✔
2766
            pME->uid);
2767

2768
  pKey = &tbDbKey;
44,853✔
2769
  kLen = sizeof(tbDbKey);
44,853✔
2770

2771
  int32_t ret = 0;
44,853✔
2772
  tEncodeSize(metaEncodeEntry, pME, vLen, ret);
44,853!
2773
  if (ret < 0) {
45,004!
2774
    goto _err;
×
2775
  }
2776

2777
  pVal = taosMemoryMalloc(vLen);
45,004✔
2778
  if (pVal == NULL) {
45,021!
2779
    terrno = TSDB_CODE_OUT_OF_MEMORY;
×
2780
    goto _err;
×
2781
  }
2782

2783
  tEncoderInit(&coder, pVal, vLen);
45,021✔
2784

2785
  if (metaEncodeEntry(&coder, pME) < 0) {
45,021!
2786
    goto _err;
×
2787
  }
2788

2789
  tEncoderClear(&coder);
45,041✔
2790

2791
  // write to table.db
2792
  if (tdbTbInsert(pMeta->pTbDb, pKey, kLen, pVal, vLen, pMeta->txn) < 0) {
45,052!
2793
    goto _err;
×
2794
  }
2795

2796
  taosMemoryFree(pVal);
45,046✔
2797
  return 0;
45,037✔
2798

2799
_err:
×
2800
  metaError("vgId:%d, failed to save table version:%" PRId64 "uid:%" PRId64 " %s", TD_VID(pMeta->pVnode), pME->version,
×
2801
            pME->uid, tstrerror(terrno));
2802

2803
  taosMemoryFree(pVal);
×
2804
  return TSDB_CODE_FAILED;
×
2805
}
2806

2807
static int metaUpdateUidIdx(SMeta *pMeta, const SMetaEntry *pME) {
45,029✔
2808
  // upsert cache
2809
  SMetaInfo info;
2810
  metaGetEntryInfo(pME, &info);
45,029✔
2811
  int32_t ret = metaCacheUpsert(pMeta, &info);
45,057✔
2812
  if (ret < 0) {
45,038!
2813
    metaError("vgId:%d, failed to upsert cache, uid: %" PRId64 " %s", TD_VID(pMeta->pVnode), pME->uid, tstrerror(ret));
×
2814
  }
2815

2816
  SUidIdxVal uidIdxVal = {.suid = info.suid, .version = info.version, .skmVer = info.skmVer};
45,038✔
2817

2818
  return tdbTbUpsert(pMeta->pUidIdx, &pME->uid, sizeof(tb_uid_t), &uidIdxVal, sizeof(uidIdxVal), pMeta->txn);
45,038✔
2819
}
2820

2821
static int metaUpdateSuidIdx(SMeta *pMeta, const SMetaEntry *pME) {
12,009✔
2822
  return tdbTbUpsert(pMeta->pSuidIdx, &pME->uid, sizeof(tb_uid_t), NULL, 0, pMeta->txn);
12,009✔
2823
}
2824

2825
static int metaUpdateNameIdx(SMeta *pMeta, const SMetaEntry *pME) {
42,828✔
2826
  return tdbTbUpsert(pMeta->pNameIdx, pME->name, strlen(pME->name) + 1, &pME->uid, sizeof(tb_uid_t), pMeta->txn);
42,828✔
2827
}
2828

2829
static void metaUpdateTtl(SMeta *pMeta, const SMetaEntry *pME) {
30,868✔
2830
  if (pME->type != TSDB_CHILD_TABLE && pME->type != TSDB_NORMAL_TABLE) return;
30,868!
2831

2832
  STtlUpdTtlCtx ctx = {.uid = pME->uid, .pTxn = pMeta->txn};
30,868✔
2833
  if (pME->type == TSDB_CHILD_TABLE) {
30,868✔
2834
    ctx.ttlDays = pME->ctbEntry.ttlDays;
28,443✔
2835
    ctx.changeTimeMs = pME->ctbEntry.btime;
28,443✔
2836
  } else {
2837
    ctx.ttlDays = pME->ntbEntry.ttlDays;
2,425✔
2838
    ctx.changeTimeMs = pME->ntbEntry.btime;
2,425✔
2839
  }
2840

2841
  int32_t ret = ttlMgrInsertTtl(pMeta->pTtlMgr, &ctx);
30,868✔
2842
  if (ret < 0) {
30,866!
2843
    metaError("vgId:%d, failed to insert ttl, uid: %" PRId64 " %s", TD_VID(pMeta->pVnode), pME->uid, tstrerror(ret));
×
2844
  }
2845

2846
  return;
30,865✔
2847
}
2848

2849
static int metaUpdateChangeTime(SMeta *pMeta, tb_uid_t uid, int64_t changeTimeMs) {
860✔
2850
  if (!tsTtlChangeOnWrite) return 0;
860✔
2851

2852
  if (changeTimeMs <= 0) {
1!
2853
    metaWarn("Skip to change ttl deletetion time on write, uid: %" PRId64, uid);
×
2854
    return TSDB_CODE_VERSION_NOT_COMPATIBLE;
×
2855
  }
2856

2857
  STtlUpdCtimeCtx ctx = {.uid = uid, .changeTimeMs = changeTimeMs, .pTxn = pMeta->txn};
1✔
2858

2859
  return ttlMgrUpdateChangeTime(pMeta->pTtlMgr, &ctx);
1✔
2860
}
2861

2862
int metaUpdateChangeTimeWithLock(SMeta *pMeta, tb_uid_t uid, int64_t changeTimeMs) {
1,066,054✔
2863
  if (!tsTtlChangeOnWrite) return 0;
1,066,054!
2864

2865
  metaWLock(pMeta);
×
2866
  int ret = metaUpdateChangeTime(pMeta, uid, changeTimeMs);
1✔
2867
  metaULock(pMeta);
1✔
2868
  return ret;
1✔
2869
}
2870

2871
static int metaUpdateCtbIdx(SMeta *pMeta, const SMetaEntry *pME) {
28,437✔
2872
  SCtbIdxKey ctbIdxKey = {.suid = pME->ctbEntry.suid, .uid = pME->uid};
28,437✔
2873

2874
  return tdbTbUpsert(pMeta->pCtbIdx, &ctbIdxKey, sizeof(ctbIdxKey), pME->ctbEntry.pTags,
56,871✔
2875
                     ((STag *)(pME->ctbEntry.pTags))->len, pMeta->txn);
28,437✔
2876
}
2877

2878
int metaCreateTagIdxKey(tb_uid_t suid, int32_t cid, const void *pTagData, int32_t nTagData, int8_t type, tb_uid_t uid,
57,369✔
2879
                        STagIdxKey **ppTagIdxKey, int32_t *nTagIdxKey) {
2880
  if (IS_VAR_DATA_TYPE(type)) {
57,369✔
2881
    *nTagIdxKey = sizeof(STagIdxKey) + nTagData + VARSTR_HEADER_SIZE + sizeof(tb_uid_t);
6,288✔
2882
  } else {
2883
    *nTagIdxKey = sizeof(STagIdxKey) + nTagData + sizeof(tb_uid_t);
51,081✔
2884
  }
2885

2886
  *ppTagIdxKey = (STagIdxKey *)taosMemoryMalloc(*nTagIdxKey);
57,369✔
2887
  if (*ppTagIdxKey == NULL) {
57,375✔
2888
    return terrno;
4✔
2889
  }
2890

2891
  (*ppTagIdxKey)->suid = suid;
57,371✔
2892
  (*ppTagIdxKey)->cid = cid;
57,371✔
2893
  (*ppTagIdxKey)->isNull = (pTagData == NULL) ? 1 : 0;
57,371✔
2894
  (*ppTagIdxKey)->type = type;
57,371✔
2895

2896
  // refactor
2897
  if (IS_VAR_DATA_TYPE(type)) {
57,371!
2898
    memcpy((*ppTagIdxKey)->data, (uint16_t *)&nTagData, VARSTR_HEADER_SIZE);
6,293✔
2899
    if (pTagData != NULL) memcpy((*ppTagIdxKey)->data + VARSTR_HEADER_SIZE, pTagData, nTagData);
6,293✔
2900
    *(tb_uid_t *)((*ppTagIdxKey)->data + VARSTR_HEADER_SIZE + nTagData) = uid;
6,293✔
2901
  } else {
2902
    if (pTagData != NULL) memcpy((*ppTagIdxKey)->data, pTagData, nTagData);
51,078✔
2903
    *(tb_uid_t *)((*ppTagIdxKey)->data + nTagData) = uid;
51,078✔
2904
  }
2905

2906
  return 0;
57,371✔
2907
}
2908

2909
static void metaDestroyTagIdxKey(STagIdxKey *pTagIdxKey) {
57,060✔
2910
  if (pTagIdxKey) taosMemoryFree(pTagIdxKey);
57,060!
2911
}
57,057✔
2912

2913
static int metaUpdateTagIdx(SMeta *pMeta, const SMetaEntry *pCtbEntry) {
29,023✔
2914
  void          *pData = NULL;
29,023✔
2915
  int            nData = 0;
29,023✔
2916
  STbDbKey       tbDbKey = {0};
29,023✔
2917
  SMetaEntry     stbEntry = {0};
29,023✔
2918
  STagIdxKey    *pTagIdxKey = NULL;
29,023✔
2919
  int32_t        nTagIdxKey;
2920
  const SSchema *pTagColumn;
2921
  const void    *pTagData = NULL;
29,023✔
2922
  int32_t        nTagData = 0;
29,023✔
2923
  SDecoder       dc = {0};
29,023✔
2924
  int32_t        ret = 0;
29,023✔
2925
  // get super table
2926
  if (tdbTbGet(pMeta->pUidIdx, &pCtbEntry->ctbEntry.suid, sizeof(tb_uid_t), &pData, &nData) != 0) {
29,023!
2927
    metaError("vgId:%d, failed to get stable suid for update. version:%" PRId64, TD_VID(pMeta->pVnode),
×
2928
              pCtbEntry->version);
2929
    ret = TSDB_CODE_TDB_INVALID_TABLE_ID;
×
2930
    goto end;
×
2931
  }
2932
  tbDbKey.uid = pCtbEntry->ctbEntry.suid;
29,017✔
2933
  tbDbKey.version = ((SUidIdxVal *)pData)[0].version;
29,017✔
2934
  ret = tdbTbGet(pMeta->pTbDb, &tbDbKey, sizeof(tbDbKey), &pData, &nData);
29,017✔
2935
  if (ret < 0) {
29,021!
2936
    metaError("vgId:%d, failed to get stable for update. version:%" PRId64, TD_VID(pMeta->pVnode), pCtbEntry->version);
×
2937
    goto end;
×
2938
  }
2939

2940
  tDecoderInit(&dc, pData, nData);
29,021✔
2941
  ret = metaDecodeEntry(&dc, &stbEntry);
29,021✔
2942
  if (ret < 0) {
29,006!
2943
    goto end;
×
2944
  }
2945

2946
  if (stbEntry.stbEntry.schemaTag.pSchema == NULL) {
29,006!
2947
    ret = TSDB_CODE_INVALID_PARA;
×
2948
    goto end;
×
2949
  }
2950

2951
  SSchemaWrapper *pTagSchema = &stbEntry.stbEntry.schemaTag;
29,006✔
2952
  if (pTagSchema->nCols == 1 && pTagSchema->pSchema[0].type == TSDB_DATA_TYPE_JSON) {
29,006✔
2953
    pTagColumn = &stbEntry.stbEntry.schemaTag.pSchema[0];
169✔
2954
    STagVal tagVal = {.cid = pTagColumn->colId};
169✔
2955

2956
    pTagData = pCtbEntry->ctbEntry.pTags;
169✔
2957
    nTagData = ((const STag *)pCtbEntry->ctbEntry.pTags)->len;
169✔
2958
    ret = metaSaveJsonVarToIdx(pMeta, pCtbEntry, pTagColumn);
169✔
2959
    goto end;
169✔
2960
  } else {
2961
    for (int i = 0; i < pTagSchema->nCols; i++) {
138,941✔
2962
      pTagData = NULL;
110,094✔
2963
      nTagData = 0;
110,094✔
2964
      pTagColumn = &pTagSchema->pSchema[i];
110,094✔
2965
      if (!IS_IDX_ON(pTagColumn)) continue;
110,094✔
2966

2967
      STagVal tagVal = {.cid = pTagColumn->colId};
28,817✔
2968
      if (tTagGet((const STag *)pCtbEntry->ctbEntry.pTags, &tagVal)) {
28,817✔
2969
        if (IS_VAR_DATA_TYPE(pTagColumn->type)) {
28,545!
2970
          pTagData = tagVal.pData;
2,181✔
2971
          nTagData = (int32_t)tagVal.nData;
2,181✔
2972
        } else {
2973
          pTagData = &(tagVal.i64);
26,364✔
2974
          nTagData = tDataTypes[pTagColumn->type].bytes;
26,364✔
2975
        }
2976
      } else {
2977
        if (!IS_VAR_DATA_TYPE(pTagColumn->type)) {
274!
2978
          nTagData = tDataTypes[pTagColumn->type].bytes;
181✔
2979
        }
2980
      }
2981
      if (metaCreateTagIdxKey(pCtbEntry->ctbEntry.suid, pTagColumn->colId, pTagData, nTagData, pTagColumn->type,
28,823!
2982
                              pCtbEntry->uid, &pTagIdxKey, &nTagIdxKey) < 0) {
28,819✔
2983
        ret = -1;
×
2984
        goto end;
×
2985
      }
2986
      if (tdbTbUpsert(pMeta->pTagIdx, pTagIdxKey, nTagIdxKey, NULL, 0, pMeta->txn) < 0) {
28,823!
2987
        metaError("vgId:%d, failed to update tag index. version:%" PRId64, TD_VID(pMeta->pVnode), pCtbEntry->version);
×
2988
      }
2989
      metaDestroyTagIdxKey(pTagIdxKey);
28,832✔
2990
      pTagIdxKey = NULL;
28,827✔
2991
    }
2992
  }
2993
end:
28,847✔
2994
  tDecoderClear(&dc);
29,016✔
2995
  tdbFree(pData);
29,024✔
2996
  return ret;
29,024✔
2997
}
2998

2999
static int metaSaveToSkmDb(SMeta *pMeta, const SMetaEntry *pME) {
15,197✔
3000
  SEncoder              coder = {0};
15,197✔
3001
  void                 *pVal = NULL;
15,197✔
3002
  int                   vLen = 0;
15,197✔
3003
  int                   rcode = 0;
15,197✔
3004
  SSkmDbKey             skmDbKey = {0};
15,197✔
3005
  const SSchemaWrapper *pSW;
3006

3007
  if (pME->type == TSDB_SUPER_TABLE) {
15,197✔
3008
    pSW = &pME->stbEntry.schemaRow;
12,626✔
3009
  } else if (pME->type == TSDB_NORMAL_TABLE) {
2,571!
3010
    pSW = &pME->ntbEntry.schemaRow;
2,598✔
3011
  } else {
3012
    metaError("meta/table: invalide table type: %" PRId8 " save skm db failed.", pME->type);
×
3013
    return TSDB_CODE_FAILED;
×
3014
  }
3015

3016
  skmDbKey.uid = pME->uid;
15,224✔
3017
  skmDbKey.sver = pSW->version;
15,224✔
3018

3019
  // if receive tmq meta message is: create stable1 then delete stable1 then create stable1 with multi vgroups
3020
  if (tdbTbGet(pMeta->pSkmDb, &skmDbKey, sizeof(skmDbKey), NULL, NULL) == 0) {
15,224✔
3021
    return rcode;
10✔
3022
  }
3023

3024
  // encode schema
3025
  int32_t ret = 0;
15,218✔
3026
  tEncodeSize(tEncodeSSchemaWrapper, pSW, vLen, ret);
30,436✔
3027
  if (ret < 0) return -1;
15,168!
3028
  pVal = taosMemoryMalloc(vLen);
15,168✔
3029
  if (pVal == NULL) {
15,192!
3030
    rcode = -1;
×
3031
    terrno = TSDB_CODE_OUT_OF_MEMORY;
×
3032
    goto _exit;
×
3033
  }
3034

3035
  tEncoderInit(&coder, pVal, vLen);
15,192✔
3036
  ret = tEncodeSSchemaWrapper(&coder, pSW);
15,193✔
3037
  if (ret < 0) {
15,193!
3038
    rcode = -1;
×
3039
    goto _exit;
×
3040
  }
3041

3042
  if (tdbTbInsert(pMeta->pSkmDb, &skmDbKey, sizeof(skmDbKey), pVal, vLen, pMeta->txn) < 0) {
15,193!
3043
    rcode = -1;
×
3044
    goto _exit;
×
3045
  }
3046

3047
  metaDebug("vgId:%d, set schema:(%" PRId64 ") sver:%d since %s", TD_VID(pMeta->pVnode), pME->uid, pSW->version,
15,207✔
3048
            tstrerror(terrno));
3049

3050
_exit:
10,257✔
3051
  taosMemoryFree(pVal);
15,209✔
3052
  tEncoderClear(&coder);
15,216✔
3053
  return rcode;
15,219✔
3054
}
3055

3056
int metaHandleEntry(SMeta *pMeta, const SMetaEntry *pME) {
42,830✔
3057
  int32_t code = 0;
42,830✔
3058
  int32_t line = 0;
42,830✔
3059
  metaWLock(pMeta);
42,830✔
3060

3061
  // save to table.db
3062
  code = metaSaveToTbDb(pMeta, pME);
42,852✔
3063
  VND_CHECK_CODE(code, line, _err);
42,846!
3064

3065
  // update uid.idx
3066
  code = metaUpdateUidIdx(pMeta, pME);
42,846✔
3067
  VND_CHECK_CODE(code, line, _err);
42,841!
3068

3069
  // update name.idx
3070
  code = metaUpdateNameIdx(pMeta, pME);
42,841✔
3071
  VND_CHECK_CODE(code, line, _err);
42,855!
3072

3073
  if (pME->type == TSDB_CHILD_TABLE) {
42,855✔
3074
    // update ctb.idx
3075
    code = metaUpdateCtbIdx(pMeta, pME);
28,437✔
3076
    VND_CHECK_CODE(code, line, _err);
28,433!
3077

3078
    // update tag.idx
3079
    code = metaUpdateTagIdx(pMeta, pME);
28,433✔
3080
    VND_CHECK_CODE(code, line, _err);
28,431!
3081
  } else {
3082
    // update schema.db
3083
    code = metaSaveToSkmDb(pMeta, pME);
14,418✔
3084
    VND_CHECK_CODE(code, line, _err);
14,420!
3085

3086
    if (pME->type == TSDB_SUPER_TABLE) {
14,420✔
3087
      code = metaUpdateSuidIdx(pMeta, pME);
12,014✔
3088
      VND_CHECK_CODE(code, line, _err);
12,009!
3089
    }
3090
  }
3091

3092
  code = metaUpdateBtimeIdx(pMeta, pME);
42,846✔
3093
  VND_CHECK_CODE(code, line, _err);
42,854!
3094

3095
  if (pME->type == TSDB_NORMAL_TABLE) {
42,854✔
3096
    code = metaUpdateNcolIdx(pMeta, pME);
2,411✔
3097
    VND_CHECK_CODE(code, line, _err);
2,411!
3098
  }
3099

3100
  if (pME->type != TSDB_SUPER_TABLE) {
42,854✔
3101
    metaUpdateTtl(pMeta, pME);
30,841✔
3102
  }
3103

3104
  if (pME->type == TSDB_SUPER_TABLE || pME->type == TSDB_NORMAL_TABLE) {
42,850✔
3105
  }
3106

3107
  metaULock(pMeta);
42,850✔
3108
  metaDebug("vgId:%d, handle meta entry, ver:%" PRId64 ", uid:%" PRId64 ", name:%s", TD_VID(pMeta->pVnode),
42,865✔
3109
            pME->version, pME->uid, pME->name);
3110
  return 0;
42,861✔
3111

3112
_err:
×
3113
  metaULock(pMeta);
×
3114
  metaError("vgId:%d, failed to handle meta entry since %s at line:%d, ver:%" PRId64 ", uid:%" PRId64 ", name:%s",
×
3115
            TD_VID(pMeta->pVnode), terrstr(), line, pME->version, pME->uid, pME->name);
3116
  return TSDB_CODE_FAILED;
×
3117
}
3118

3119
static void colCompressDebug(SHashObj *pColCmprObj) {
21,646✔
3120
  void *p = taosHashIterate(pColCmprObj, NULL);
21,646✔
3121
  while (p) {
218,449✔
3122
    uint32_t cmprAlg = *(uint32_t *)p;
196,807✔
3123
    col_id_t colId = *(col_id_t *)taosHashGetKey(p, NULL);
196,807✔
3124
    p = taosHashIterate(pColCmprObj, p);
196,805✔
3125

3126
    uint8_t l1, l2, lvl;
3127
    tcompressDebug(cmprAlg, &l1, &l2, &lvl);
196,827✔
3128

3129
    const char *l1str = columnEncodeStr(l1);
196,824✔
3130
    const char *l2str = columnCompressStr(l2);
196,820✔
3131
    const char *lvlstr = columnLevelStr(lvl);
196,791✔
3132
    metaDebug("colId: %d, encode:%s, compress:%s,level:%s", colId, l1str, l2str, lvlstr);
196,802✔
3133
  }
3134
  return;
21,642✔
3135
}
3136
int32_t metaGetColCmpr(SMeta *pMeta, tb_uid_t uid, SHashObj **ppColCmprObj) {
21,671✔
3137
  int rc = 0;
21,671✔
3138

3139
  SHashObj *pColCmprObj = taosHashInit(32, taosGetDefaultHashFunction(TSDB_DATA_TYPE_SMALLINT), false, HASH_NO_LOCK);
21,671✔
3140
  if (pColCmprObj == NULL) {
21,667!
3141
    pColCmprObj = NULL;
×
3142
    return TSDB_CODE_OUT_OF_MEMORY;
×
3143
  }
3144

3145
  void      *pData = NULL;
21,667✔
3146
  int        nData = 0;
21,667✔
3147
  SMetaEntry e = {0};
21,667✔
3148
  SDecoder   dc = {0};
21,667✔
3149

3150
  *ppColCmprObj = NULL;
21,667✔
3151

3152
  metaRLock(pMeta);
21,667✔
3153
  rc = tdbTbGet(pMeta->pUidIdx, &uid, sizeof(uid), &pData, &nData);
21,671✔
3154
  if (rc < 0) {
21,671✔
3155
    taosHashClear(pColCmprObj);
25✔
3156
    metaULock(pMeta);
25✔
3157
    return TSDB_CODE_FAILED;
25✔
3158
  }
3159
  int64_t version = ((SUidIdxVal *)pData)[0].version;
21,646✔
3160
  rc = tdbTbGet(pMeta->pTbDb, &(STbDbKey){.version = version, .uid = uid}, sizeof(STbDbKey), &pData, &nData);
21,646✔
3161
  if (rc < 0) {
21,646!
3162
    metaULock(pMeta);
×
3163
    taosHashClear(pColCmprObj);
×
3164
    metaError("failed to get table entry");
×
3165
    return rc;
×
3166
  }
3167

3168
  tDecoderInit(&dc, pData, nData);
21,646✔
3169
  rc = metaDecodeEntry(&dc, &e);
21,646✔
3170
  if (rc < 0) {
21,641!
3171
    tDecoderClear(&dc);
×
3172
    tdbFree(pData);
×
3173
    metaULock(pMeta);
×
3174
    taosHashClear(pColCmprObj);
×
3175
    return rc;
×
3176
  }
3177
  if (useCompress(e.type)) {
21,641!
3178
    SColCmprWrapper *p = &e.colCmpr;
21,645✔
3179
    for (int32_t i = 0; i < p->nCols; i++) {
218,458✔
3180
      SColCmpr *pCmpr = &p->pColCmpr[i];
196,813✔
3181
      rc = taosHashPut(pColCmprObj, &pCmpr->id, sizeof(pCmpr->id), &pCmpr->alg, sizeof(pCmpr->alg));
196,813✔
3182
      if (rc < 0) {
196,814✔
3183
        tDecoderClear(&dc);
1✔
3184
        tdbFree(pData);
×
3185
        metaULock(pMeta);
×
3186
        taosHashClear(pColCmprObj);
×
3187
        return rc;
×
3188
      }
3189
    }
3190
  } else {
3191
    tDecoderClear(&dc);
×
3192
    tdbFree(pData);
×
3193
    metaULock(pMeta);
×
3194
    taosHashClear(pColCmprObj);
×
3195
    return 0;
×
3196
  }
3197
  tDecoderClear(&dc);
21,645✔
3198
  tdbFree(pData);
21,646✔
3199
  metaULock(pMeta);
21,646✔
3200

3201
  *ppColCmprObj = pColCmprObj;
21,646✔
3202
  colCompressDebug(pColCmprObj);
21,646✔
3203

3204
  return 0;
21,643✔
3205
}
3206
// refactor later
3207
void *metaGetIdx(SMeta *pMeta) { return pMeta->pTagIdx; }
3,869✔
3208
void *metaGetIvtIdx(SMeta *pMeta) { return pMeta->pTagIvtIdx; }
3,870✔
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