~ubuntu-branches/ubuntu/precise/mysql-5.1/precise

« back to all changes in this revision

Viewing changes to storage/ndb/src/kernel/blocks/dbtux/DbtuxGen.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Norbert Tretkowski
  • Date: 2010-03-17 14:56:02 UTC
  • Revision ID: james.westby@ubuntu.com-20100317145602-x7e30l1b2sb5s6w6
Tags: upstream-5.1.45
ImportĀ upstreamĀ versionĀ 5.1.45

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* Copyright (C) 2003 MySQL AB
 
2
 
 
3
   This program is free software; you can redistribute it and/or modify
 
4
   it under the terms of the GNU General Public License as published by
 
5
   the Free Software Foundation; version 2 of the License.
 
6
 
 
7
   This program is distributed in the hope that it will be useful,
 
8
   but WITHOUT ANY WARRANTY; without even the implied warranty of
 
9
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
10
   GNU General Public License for more details.
 
11
 
 
12
   You should have received a copy of the GNU General Public License
 
13
   along with this program; if not, write to the Free Software
 
14
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA */
 
15
 
 
16
#define DBTUX_GEN_CPP
 
17
#include "Dbtux.hpp"
 
18
 
 
19
Dbtux::Dbtux(Block_context& ctx) :
 
20
  SimulatedBlock(DBTUX, ctx),
 
21
  c_tup(0),
 
22
  c_descPageList(RNIL),
 
23
#ifdef VM_TRACE
 
24
  debugFile(0),
 
25
  debugOut(*new NullOutputStream()),
 
26
  debugFlags(0),
 
27
#endif
 
28
  c_internalStartPhase(0),
 
29
  c_typeOfStart(NodeState::ST_ILLEGAL_TYPE),
 
30
  c_dataBuffer(0)
 
31
{
 
32
  BLOCK_CONSTRUCTOR(Dbtux);
 
33
  // verify size assumptions (also when release-compiled)
 
34
  ndbrequire(
 
35
      (sizeof(TreeEnt) & 0x3) == 0 &&
 
36
      (sizeof(TreeNode) & 0x3) == 0 &&
 
37
      (sizeof(DescHead) & 0x3) == 0 &&
 
38
      (sizeof(DescAttr) & 0x3) == 0
 
39
  );
 
40
  /*
 
41
   * DbtuxGen.cpp
 
42
   */
 
43
  addRecSignal(GSN_CONTINUEB, &Dbtux::execCONTINUEB);
 
44
  addRecSignal(GSN_STTOR, &Dbtux::execSTTOR);
 
45
  addRecSignal(GSN_READ_CONFIG_REQ, &Dbtux::execREAD_CONFIG_REQ, true);
 
46
  /*
 
47
   * DbtuxMeta.cpp
 
48
   */
 
49
  addRecSignal(GSN_TUXFRAGREQ, &Dbtux::execTUXFRAGREQ);
 
50
  addRecSignal(GSN_TUX_ADD_ATTRREQ, &Dbtux::execTUX_ADD_ATTRREQ);
 
51
  addRecSignal(GSN_ALTER_INDX_REQ, &Dbtux::execALTER_INDX_REQ);
 
52
  addRecSignal(GSN_DROP_TAB_REQ, &Dbtux::execDROP_TAB_REQ);
 
53
  /*
 
54
   * DbtuxMaint.cpp
 
55
   */
 
56
  addRecSignal(GSN_TUX_MAINT_REQ, &Dbtux::execTUX_MAINT_REQ);
 
57
  /*
 
58
   * DbtuxScan.cpp
 
59
   */
 
60
  addRecSignal(GSN_ACC_SCANREQ, &Dbtux::execACC_SCANREQ);
 
61
  addRecSignal(GSN_TUX_BOUND_INFO, &Dbtux::execTUX_BOUND_INFO);
 
62
  addRecSignal(GSN_NEXT_SCANREQ, &Dbtux::execNEXT_SCANREQ);
 
63
  addRecSignal(GSN_ACC_CHECK_SCAN, &Dbtux::execACC_CHECK_SCAN);
 
64
  addRecSignal(GSN_ACCKEYCONF, &Dbtux::execACCKEYCONF);
 
65
  addRecSignal(GSN_ACCKEYREF, &Dbtux::execACCKEYREF);
 
66
  addRecSignal(GSN_ACC_ABORTCONF, &Dbtux::execACC_ABORTCONF);
 
67
  /*
 
68
   * DbtuxStat.cpp
 
69
   */
 
70
  addRecSignal(GSN_READ_PSEUDO_REQ, &Dbtux::execREAD_PSEUDO_REQ);
 
71
  /*
 
72
   * DbtuxDebug.cpp
 
73
   */
 
74
  addRecSignal(GSN_DUMP_STATE_ORD, &Dbtux::execDUMP_STATE_ORD);
 
75
}
 
76
 
 
77
Dbtux::~Dbtux()
 
78
{
 
79
}
 
80
 
 
81
void
 
82
Dbtux::execCONTINUEB(Signal* signal)
 
83
{
 
84
  jamEntry();
 
85
  const Uint32* data = signal->getDataPtr();
 
86
  switch (data[0]) {
 
87
  case TuxContinueB::DropIndex: // currently unused
 
88
    {
 
89
      IndexPtr indexPtr;
 
90
      c_indexPool.getPtr(indexPtr, data[1]);
 
91
      dropIndex(signal, indexPtr, data[2], data[3]);
 
92
    }
 
93
    break;
 
94
  default:
 
95
    ndbrequire(false);
 
96
    break;
 
97
  }
 
98
}
 
99
 
 
100
/*
 
101
 * STTOR is sent to one block at a time.  In NDBCNTR it triggers
 
102
 * NDB_STTOR to the "old" blocks.  STTOR carries start phase (SP) and
 
103
 * NDB_STTOR carries internal start phase (ISP).
 
104
 *
 
105
 *      SP      ISP     activities
 
106
 *      1       none
 
107
 *      2       1       
 
108
 *      3       2       recover metadata, activate indexes
 
109
 *      4       3       recover data
 
110
 *      5       4-6     
 
111
 *      6       skip    
 
112
 *      7       skip    
 
113
 *      8       7       build non-logged indexes on SR
 
114
 *
 
115
 * DBTUX catches type of start (IS, SR, NR, INR) at SP 3 and updates
 
116
 * internal start phase at SP 7.  These are used to prevent index
 
117
 * maintenance operations caused by redo log at SR.
 
118
 */
 
119
void
 
120
Dbtux::execSTTOR(Signal* signal)
 
121
{
 
122
  jamEntry();
 
123
  Uint32 startPhase = signal->theData[1];
 
124
  switch (startPhase) {
 
125
  case 1:
 
126
    jam();
 
127
    CLEAR_ERROR_INSERT_VALUE;
 
128
    c_tup = (Dbtup*)globalData.getBlock(DBTUP);
 
129
    ndbrequire(c_tup != 0);
 
130
    break;
 
131
  case 3:
 
132
    jam();
 
133
    c_typeOfStart = signal->theData[7];
 
134
    break;
 
135
  case 7:
 
136
    c_internalStartPhase = 6;
 
137
  default:
 
138
    jam();
 
139
    break;
 
140
  }
 
141
  signal->theData[0] = 0;       // garbage
 
142
  signal->theData[1] = 0;       // garbage
 
143
  signal->theData[2] = 0;       // garbage
 
144
  signal->theData[3] = 1;
 
145
  signal->theData[4] = 3;       // for c_typeOfStart
 
146
  signal->theData[5] = 7;       // for c_internalStartPhase
 
147
  signal->theData[6] = 255;
 
148
  sendSignal(NDBCNTR_REF, GSN_STTORRY, signal, 7, JBB);
 
149
}
 
150
 
 
151
void
 
152
Dbtux::execREAD_CONFIG_REQ(Signal* signal)
 
153
{
 
154
  jamEntry();
 
155
 
 
156
  const ReadConfigReq * req = (ReadConfigReq*)signal->getDataPtr();
 
157
  Uint32 ref = req->senderRef;
 
158
  Uint32 senderData = req->senderData;
 
159
  ndbrequire(req->noOfParameters == 0);
 
160
 
 
161
  Uint32 nIndex;
 
162
  Uint32 nFragment;
 
163
  Uint32 nAttribute;
 
164
  Uint32 nScanOp; 
 
165
  Uint32 nScanBatch;
 
166
 
 
167
  const ndb_mgm_configuration_iterator * p = 
 
168
    m_ctx.m_config.getOwnConfigIterator();
 
169
  ndbrequire(p != 0);
 
170
 
 
171
  ndbrequire(!ndb_mgm_get_int_parameter(p, CFG_TUX_INDEX, &nIndex));
 
172
  ndbrequire(!ndb_mgm_get_int_parameter(p, CFG_TUX_FRAGMENT, &nFragment));
 
173
  ndbrequire(!ndb_mgm_get_int_parameter(p, CFG_TUX_ATTRIBUTE, &nAttribute));
 
174
  ndbrequire(!ndb_mgm_get_int_parameter(p, CFG_TUX_SCAN_OP, &nScanOp));
 
175
  ndbrequire(!ndb_mgm_get_int_parameter(p, CFG_DB_BATCH_SIZE, &nScanBatch));
 
176
 
 
177
  const Uint32 nDescPage = (nIndex * DescHeadSize + nAttribute * DescAttrSize + DescPageSize - 1) / DescPageSize;
 
178
  const Uint32 nScanBoundWords = nScanOp * ScanBoundSegmentSize * 4;
 
179
  const Uint32 nScanLock = nScanOp * nScanBatch;
 
180
  
 
181
  c_indexPool.setSize(nIndex);
 
182
  c_fragPool.setSize(nFragment);
 
183
  c_descPagePool.setSize(nDescPage);
 
184
  c_fragOpPool.setSize(MaxIndexFragments);
 
185
  c_scanOpPool.setSize(nScanOp);
 
186
  c_scanBoundPool.setSize(nScanBoundWords);
 
187
  c_scanLockPool.setSize(nScanLock);
 
188
  /*
 
189
   * Index id is physical array index.  We seize and initialize all
 
190
   * index records now.
 
191
   */
 
192
  IndexPtr indexPtr;
 
193
  while (1) {
 
194
    jam();
 
195
    refresh_watch_dog();
 
196
    c_indexPool.seize(indexPtr);
 
197
    if (indexPtr.i == RNIL) {
 
198
      jam();
 
199
      break;
 
200
    }
 
201
    new (indexPtr.p) Index();
 
202
  }
 
203
  // allocate buffers
 
204
  c_keyAttrs = (Uint32*)allocRecord("c_keyAttrs", sizeof(Uint32), MaxIndexAttributes);
 
205
  c_sqlCmp = (NdbSqlUtil::Cmp**)allocRecord("c_sqlCmp", sizeof(NdbSqlUtil::Cmp*), MaxIndexAttributes);
 
206
  c_searchKey = (Uint32*)allocRecord("c_searchKey", sizeof(Uint32), MaxAttrDataSize);
 
207
  c_entryKey = (Uint32*)allocRecord("c_entryKey", sizeof(Uint32), MaxAttrDataSize);
 
208
  c_dataBuffer = (Uint32*)allocRecord("c_dataBuffer", sizeof(Uint64), (MaxAttrDataSize + 1) >> 1);
 
209
  // ack
 
210
  ReadConfigConf * conf = (ReadConfigConf*)signal->getDataPtrSend();
 
211
  conf->senderRef = reference();
 
212
  conf->senderData = senderData;
 
213
  sendSignal(ref, GSN_READ_CONFIG_CONF, signal, 
 
214
             ReadConfigConf::SignalLength, JBB);
 
215
}
 
216
 
 
217
// utils
 
218
 
 
219
void
 
220
Dbtux::setKeyAttrs(const Frag& frag)
 
221
{
 
222
  Data keyAttrs = c_keyAttrs; // global
 
223
  NdbSqlUtil::Cmp** sqlCmp = c_sqlCmp; // global
 
224
  const unsigned numAttrs = frag.m_numAttrs;
 
225
  const DescEnt& descEnt = getDescEnt(frag.m_descPage, frag.m_descOff);
 
226
  for (unsigned i = 0; i < numAttrs; i++) {
 
227
    jam();
 
228
    const DescAttr& descAttr = descEnt.m_descAttr[i];
 
229
    Uint32 size = AttributeDescriptor::getSizeInWords(descAttr.m_attrDesc);
 
230
    // set attr id and fixed size
 
231
    ah(keyAttrs) = AttributeHeader(descAttr.m_primaryAttrId, size);
 
232
    keyAttrs += 1;
 
233
    // set comparison method pointer
 
234
    const NdbSqlUtil::Type& sqlType = NdbSqlUtil::getTypeBinary(descAttr.m_typeId);
 
235
    ndbrequire(sqlType.m_cmp != 0);
 
236
    *(sqlCmp++) = sqlType.m_cmp;
 
237
  }
 
238
}
 
239
 
 
240
void
 
241
Dbtux::readKeyAttrs(const Frag& frag, TreeEnt ent, unsigned start, Data keyData)
 
242
{
 
243
  ConstData keyAttrs = c_keyAttrs; // global
 
244
  const Uint32 tableFragPtrI = frag.m_tupTableFragPtrI;
 
245
  const TupLoc tupLoc = ent.m_tupLoc;
 
246
  const Uint32 tupVersion = ent.m_tupVersion;
 
247
  ndbrequire(start < frag.m_numAttrs);
 
248
  const Uint32 numAttrs = frag.m_numAttrs - start;
 
249
  // skip to start position in keyAttrs only
 
250
  keyAttrs += start;
 
251
  int ret = c_tup->tuxReadAttrs(tableFragPtrI, tupLoc.getPageId(), tupLoc.getPageOffset(), tupVersion, keyAttrs, numAttrs, keyData);
 
252
  jamEntry();
 
253
  // TODO handle error
 
254
  ndbrequire(ret > 0);
 
255
#ifdef VM_TRACE
 
256
  if (debugFlags & (DebugMaint | DebugScan)) {
 
257
    debugOut << "readKeyAttrs:" << endl;
 
258
    ConstData data = keyData;
 
259
    Uint32 totalSize = 0;
 
260
    for (Uint32 i = start; i < frag.m_numAttrs; i++) {
 
261
      Uint32 attrId = ah(data).getAttributeId();
 
262
      Uint32 dataSize = ah(data).getDataSize();
 
263
      debugOut << i << " attrId=" << attrId << " size=" << dataSize;
 
264
      data += 1;
 
265
      for (Uint32 j = 0; j < dataSize; j++) {
 
266
        debugOut << " " << hex << data[0];
 
267
        data += 1;
 
268
      }
 
269
      debugOut << endl;
 
270
      totalSize += 1 + dataSize;
 
271
    }
 
272
    ndbassert((int)totalSize == ret);
 
273
  }
 
274
#endif
 
275
}
 
276
 
 
277
void
 
278
Dbtux::readTablePk(const Frag& frag, TreeEnt ent, Data pkData, unsigned& pkSize)
 
279
{
 
280
  const Uint32 tableFragPtrI = frag.m_tupTableFragPtrI;
 
281
  const TupLoc tupLoc = ent.m_tupLoc;
 
282
  int ret = c_tup->tuxReadPk(tableFragPtrI, tupLoc.getPageId(), tupLoc.getPageOffset(), pkData, true);
 
283
  jamEntry();
 
284
  // TODO handle error
 
285
  ndbrequire(ret > 0);
 
286
  pkSize = ret;
 
287
}
 
288
 
 
289
/*
 
290
 * Copy attribute data with headers.  Input is all index key data.
 
291
 * Copies whatever fits.
 
292
 */
 
293
void
 
294
Dbtux::copyAttrs(const Frag& frag, ConstData data1, Data data2, unsigned maxlen2)
 
295
{
 
296
  unsigned n = frag.m_numAttrs;
 
297
  unsigned len2 = maxlen2;
 
298
  while (n != 0) {
 
299
    jam();
 
300
    const unsigned dataSize = ah(data1).getDataSize();
 
301
    // copy header
 
302
    if (len2 == 0)
 
303
      return;
 
304
    data2[0] = data1[0];
 
305
    data1 += 1;
 
306
    data2 += 1;
 
307
    len2 -= 1;
 
308
    // copy data
 
309
    for (unsigned i = 0; i < dataSize; i++) {
 
310
      if (len2 == 0)
 
311
        return;
 
312
      data2[i] = data1[i];
 
313
      len2 -= 1;
 
314
    }
 
315
    data1 += dataSize;
 
316
    data2 += dataSize;
 
317
    n -= 1;
 
318
  }
 
319
#ifdef VM_TRACE
 
320
  memset(data2, DataFillByte, len2 << 2);
 
321
#endif
 
322
}
 
323
 
 
324
void
 
325
Dbtux::unpackBound(const ScanBound& bound, Data dest)
 
326
{
 
327
  ScanBoundIterator iter;
 
328
  bound.first(iter);
 
329
  const unsigned n = bound.getSize();
 
330
  unsigned j;
 
331
  for (j = 0; j < n; j++) {
 
332
    dest[j] = *iter.data;
 
333
    bound.next(iter);
 
334
  }
 
335
}
 
336
 
 
337
BLOCK_FUNCTIONS(Dbtux)