diff --git a/src/gausskernel/storage/mot/core/src/storage/table.cpp b/src/gausskernel/storage/mot/core/src/storage/table.cpp index 35be7565a..f84d0a5dc 100644 --- a/src/gausskernel/storage/mot/core/src/storage/table.cpp +++ b/src/gausskernel/storage/mot/core/src/storage/table.cpp @@ -451,18 +451,18 @@ RC Table::InsertRow(Row* row, TxnManager* txn) uint64_t surrogateprimaryKey = 0; MOT::Index* ix = GetPrimaryIndex(); uint32_t numIndexes = GetNumIndexes(); + MOT::Key* cleanupKeys[numIndexes] = {nullptr}; // add row // set primary key row->SetRowId(txn->GetSurrogateKey()); - mot_vector cleanupKeys; key = txn->GetTxnKey(ix); if (key == nullptr) { MOT_REPORT_ERROR(MOT_ERROR_OOM, "Insert Row", "Failed to create primary key"); return RC_MEMORY_ALLOCATION_ERROR; } - cleanupKeys.push_back(key); + cleanupKeys[0] = key; if (ix->IsFakePrimary()) { surrogateprimaryKey = htobe64(row->GetRowId()); row->SetSurrogateKey(surrogateprimaryKey); @@ -480,16 +480,19 @@ RC Table::InsertRow(Row* row, TxnManager* txn) if (key == nullptr) { MOT_REPORT_ERROR( MOT_ERROR_OOM, "Insert Row", "Failed to create key for secondary index %s", ix->GetName().c_str()); - std::for_each(cleanupKeys.begin(), cleanupKeys.end(), [](Key*& key) { MOTCurrTxn->DestroyTxnKey(key); }); + for (uint16_t j = 0; j < numIndexes; j++) { + if (cleanupKeys[j] != nullptr) { + MOTCurrTxn->DestroyTxnKey(cleanupKeys[j]); + } + } MOTCurrTxn->Rollback(); return RC_MEMORY_ALLOCATION_ERROR; } - cleanupKeys.push_back(key); + cleanupKeys[i] = key; ix->BuildKey(this, row, key); txn->GetNextInsertItem()->SetItem(row, ix, key); } - cleanupKeys.clear(); // subsequent call to insert row takes care of key cleanup return txn->InsertRow(row); } @@ -979,19 +982,23 @@ RC Table::CreateIndexFromMeta( if (addToTable) { // In transactional recovery we set index as committed only during commit. ix->SetIsCommited(true); + WrLock(); if (primary) { if (UpdatePrimaryIndex(ix, nullptr, tid) != true) { + Unlock(); MOT_REPORT_ERROR(MOT_ERROR_INTERNAL, "Create Index from meta-data", "Failed to add primary index"); delete ix; return RC_ERROR; } } else { if (AddSecondaryIndex(ix->GetName(), (Index*)ix, nullptr, tid) != true) { + Unlock(); MOT_REPORT_ERROR(MOT_ERROR_INTERNAL, "Create Index from meta-data", "Failed to add secondary index"); delete ix; return RC_ERROR; } } + Unlock(); } if (outIndex != nullptr) { diff --git a/src/gausskernel/storage/mot/core/src/system/recovery/recovery_ops.cpp b/src/gausskernel/storage/mot/core/src/system/recovery/recovery_ops.cpp index 36a3d1f19..cef4f2382 100644 --- a/src/gausskernel/storage/mot/core/src/system/recovery/recovery_ops.cpp +++ b/src/gausskernel/storage/mot/core/src/system/recovery/recovery_ops.cpp @@ -490,8 +490,7 @@ void RecoveryManager::InsertRow(uint64_t tableId, uint64_t exId, char* keyData, Key* key = nullptr; MOT::Index* ix = nullptr; - - mot_vector cleanupKeys; + MOT::Key* cleanupKeys[table->GetNumIndexes()] = {nullptr}; ix = table->GetPrimaryIndex(); key = MOTCurrTxn->GetTxnKey(ix); if (key == nullptr) { @@ -500,7 +499,7 @@ void RecoveryManager::InsertRow(uint64_t tableId, uint64_t exId, char* keyData, MOT_REPORT_ERROR(MOT_ERROR_OOM, "Recover Insert Row", "Failed to create primary key"); return; } - cleanupKeys.push_back(key); + cleanupKeys[0] = key; if (ix->IsFakePrimary()) { row->SetSurrogateKey(*(uint64_t*)keyData); sState.UpdateMaxKey(rowId); @@ -516,15 +515,18 @@ void RecoveryManager::InsertRow(uint64_t tableId, uint64_t exId, char* keyData, "Recover Insert Row", "Failed to create key for secondary index %s", ix->GetName().c_str()); - std::for_each(cleanupKeys.begin(), cleanupKeys.end(), [](Key*& key) { MOTCurrTxn->DestroyTxnKey(key); }); + for (uint16_t j = 0; j < table->GetNumIndexes(); j++) { + if (cleanupKeys[j] != nullptr) { + MOTCurrTxn->DestroyTxnKey(cleanupKeys[j]); + } + } MOTCurrTxn->Rollback(); return; } - cleanupKeys.push_back(key); + cleanupKeys[i] = key; ix->BuildKey(table, row, key); MOTCurrTxn->GetNextInsertItem()->SetItem(row, ix, key); } - cleanupKeys.clear(); // subsequent call to insert row takes care of key cleanup status = MOTCurrTxn->InsertRow(row); if (insertLocked == true) { @@ -786,7 +788,9 @@ void RecoveryManager::DropIndex(char* data, RC& status) if (index == nullptr) { res = RC_INDEX_NOT_FOUND; } else { + table->WrLock(); res = MOTCurrTxn->DropIndex(index); + table->Unlock(); } if (res != RC_OK) { MOT_REPORT_ERROR(MOT_ERROR_INTERNAL, diff --git a/src/gausskernel/storage/mot/core/src/system/transaction/txn.cpp b/src/gausskernel/storage/mot/core/src/system/transaction/txn.cpp index 4bef0df1e..64fe08692 100644 --- a/src/gausskernel/storage/mot/core/src/system/transaction/txn.cpp +++ b/src/gausskernel/storage/mot/core/src/system/transaction/txn.cpp @@ -1136,11 +1136,23 @@ RC TxnManager::DropTable(Table* table) if (ddl_access->GetDDLAccessType() == DDL_ACCESS_CREATE_TABLE) { // this table was created in this transaction, can delete it from the ddl_access m_txnDdlAccess->EraseByOid(table->GetTableExId()); + // check for create and drop index ddls + for (uint16_t i = 0; i < table->GetNumIndexes(); i++) { + m_txnDdlAccess->EraseByOid(table->GetIndex(i)->GetExtId()); + } + // erase drop fake primary index if exists + TxnDDLAccess::DDLAccess* iddl = m_txnDdlAccess->GetByOid(table->GetTableExId() + 1); + if (iddl != nullptr) { + MOT::Index* ix = (MOT::Index*)iddl->GetEntry(); + GcManager::ClearIndexElements(ix->GetIndexId()); + table->DeletePrimaryIndex(ix); + } table->DropImpl(); RemoveTableFromStat(table); delete table; } else if (ddl_access->GetDDLAccessType() == DDL_ACCESS_TRUNCATE_TABLE) { Index** indexes = (Index**)ddl_access->GetEntry(); + table->WrLock(); for (int i = 0; i < table->GetNumIndexes(); i++) { Index* newIndex = table->m_indexes[i]; Index* oldIndex = indexes[i]; @@ -1153,6 +1165,7 @@ RC TxnManager::DropTable(Table* table) // assumption is the we deleted all rows delete newIndex; } + table->Unlock(); delete[] indexes; m_txnDdlAccess->EraseByOid(table->GetTableExId()); m_txnDdlAccess->Add(new_ddl_access); diff --git a/src/gausskernel/storage/mot/fdw_adapter/src/mot_internal.cpp b/src/gausskernel/storage/mot/fdw_adapter/src/mot_internal.cpp index f1dd1f1ea..6bd0c8438 100644 --- a/src/gausskernel/storage/mot/fdw_adapter/src/mot_internal.cpp +++ b/src/gausskernel/storage/mot/fdw_adapter/src/mot_internal.cpp @@ -1925,10 +1925,15 @@ MOT::RC MOTAdaptor::DropIndex(DropForeignStmt* stmt, ::TransactionId tid) stmt->indexoid, stmt->reloid); res = MOT::RC_INDEX_NOT_FOUND; + } else if (index->IsPrimaryKey()) { + elog(LOG, "Drop primary index is not supported, failed to drop index: %s", stmt->name); } else { - uint64_t table_relid = index->GetTable()->GetTableExId(); + MOT::Table* table = index->GetTable(); + uint64_t table_relid = table->GetTableExId(); JitExec::PurgeJitSourceCache(table_relid); + table->WrLock(); res = txn->DropIndex(index); + table->Unlock(); } } while (0);