bool Ndbinfo::Row::check_buffer_space(AttributeHeader& ah) const { const Uint32 needed = ah.getHeaderSize() + ah.getDataSize(); const Uint32 avail = (Uint32)(end - curr); if(needed > avail) { ndbout_c("Warning, too small row buffer for attribute: %d, " "needed: %d, avail: %d", ah.getAttributeId(), needed, avail); assert(false); return false; // Not enough room in row buffer } return true; }
void NdbIndexStat::stat_verify() { Uint32 idir; for (idir = 0; idir <= 1; idir++) { Uint32 i; const Area& a = m_area[idir]; assert(a.m_offset == idir * m_areasize); assert(a.m_data == &m_cache[a.m_offset]); Uint32 pointerwords = PointerSize * a.m_entries; Uint32 entrywords = 0; for (i = 0; i < a.m_entries; i++) { const Pointer& p = a.get_pointer(i); const Entry& e = a.get_entry(i); assert(a.get_pos(e) == p.m_pos); entrywords += EntrySize + e.m_keylen; } assert(a.m_free <= m_areasize); assert(pointerwords + a.m_free + entrywords == m_areasize); Uint32 off = pointerwords + a.m_free; for (i = 0; i < a.m_entries; i++) { assert(off < m_areasize); const Entry& e = *(const Entry*)&a.m_data[off]; off += EntrySize + e.m_keylen; } assert(off == m_areasize); for (i = 0; i < a.m_entries; i++) { const Entry& e = a.get_entry(i); const Uint32* entrykey = (const Uint32*)&e + EntrySize; Uint32 n = 0; while (n + 2 <= e.m_keylen) { Uint32 t = entrykey[n++]; assert(t == 2 * idir || t == 2 * idir + 1 || t == 4); AttributeHeader ah = *(const AttributeHeader*)&entrykey[n++]; n += ah.getDataSize(); } assert(n == e.m_keylen); } for (i = 0; i + 1 < a.m_entries; i++) { const Entry& e1 = a.get_entry(i); const Entry& e2 = a.get_entry(i + 1); const Uint32* entrykey1 = (const Uint32*)&e1 + EntrySize; const Uint32* entrykey2 = (const Uint32*)&e2 + EntrySize; int ret = stat_cmpkey(a, entrykey1, e1.m_keylen, entrykey2, e2.m_keylen); assert(ret == -1); } } }
void Trix::executeInsertTransaction(Signal* signal, SubscriptionRecPtr subRecPtr, SegmentedSectionPtr headerPtr, SegmentedSectionPtr dataPtr) { jam(); SubscriptionRecord* subRec = subRecPtr.p; UtilExecuteReq * utilExecuteReq = (UtilExecuteReq *)signal->getDataPtrSend(); Uint32* headerBuffer = signal->theData + 25; Uint32* dataBuffer = headerBuffer + headerPtr.sz; utilExecuteReq->senderRef = reference(); utilExecuteReq->senderData = subRecPtr.i; utilExecuteReq->prepareId = subRec->prepareId; #if 0 printf("Header size %u\n", headerPtr.sz); for(int i = 0; i < headerPtr.sz; i++) printf("H'%.8x ", headerBuffer[i]); printf("\n"); printf("Data size %u\n", dataPtr.sz); for(int i = 0; i < dataPtr.sz; i++) printf("H'%.8x ", dataBuffer[i]); printf("\n"); #endif // Save scan result in linear buffers copy(headerBuffer, headerPtr); copy(dataBuffer, dataPtr); // Calculate packed key size Uint32 noOfKeyData = 0; for(Uint32 i = 0; i < headerPtr.sz; i++) { AttributeHeader* keyAttrHead = (AttributeHeader *) headerBuffer + i; // Filter out NULL attributes if (keyAttrHead->isNULL()) return; if (i < subRec->noOfIndexColumns) // Renumber index attributes in consequtive order keyAttrHead->setAttributeId(i); else // Calculate total size of PK attribute noOfKeyData += keyAttrHead->getDataSize(); } // Increase expected CONF count subRec->expectedConf++; // Pack key attributes AttributeHeader::init(headerBuffer + subRec->noOfIndexColumns, subRec->noOfIndexColumns, noOfKeyData << 2); struct LinearSectionPtr sectionsPtr[UtilExecuteReq::NoOfSections]; sectionsPtr[UtilExecuteReq::HEADER_SECTION].p = headerBuffer; sectionsPtr[UtilExecuteReq::HEADER_SECTION].sz = subRec->noOfIndexColumns + 1; sectionsPtr[UtilExecuteReq::DATA_SECTION].p = dataBuffer; sectionsPtr[UtilExecuteReq::DATA_SECTION].sz = dataPtr.sz; sendSignal(DBUTIL_REF, GSN_UTIL_EXECUTE_REQ, signal, UtilExecuteReq::SignalLength, JBB, sectionsPtr, UtilExecuteReq::NoOfSections); }