Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
M
MariaDB
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nexedi
MariaDB
Commits
b703c784
Commit
b703c784
authored
Jul 08, 2004
by
unknown
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
tux optim 12 - remove max prefix + related
parent
89647b1d
Changes
13
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
13 changed files
with
665 additions
and
373 deletions
+665
-373
ndb/include/kernel/ndb_limits.h
ndb/include/kernel/ndb_limits.h
+1
-1
ndb/src/kernel/blocks/dbtux/Dbtux.hpp
ndb/src/kernel/blocks/dbtux/Dbtux.hpp
+55
-23
ndb/src/kernel/blocks/dbtux/DbtuxCmp.cpp
ndb/src/kernel/blocks/dbtux/DbtuxCmp.cpp
+134
-72
ndb/src/kernel/blocks/dbtux/DbtuxDebug.cpp
ndb/src/kernel/blocks/dbtux/DbtuxDebug.cpp
+78
-17
ndb/src/kernel/blocks/dbtux/DbtuxGen.cpp
ndb/src/kernel/blocks/dbtux/DbtuxGen.cpp
+8
-0
ndb/src/kernel/blocks/dbtux/DbtuxMaint.cpp
ndb/src/kernel/blocks/dbtux/DbtuxMaint.cpp
+13
-9
ndb/src/kernel/blocks/dbtux/DbtuxNode.cpp
ndb/src/kernel/blocks/dbtux/DbtuxNode.cpp
+13
-22
ndb/src/kernel/blocks/dbtux/DbtuxScan.cpp
ndb/src/kernel/blocks/dbtux/DbtuxScan.cpp
+23
-122
ndb/src/kernel/blocks/dbtux/DbtuxSearch.cpp
ndb/src/kernel/blocks/dbtux/DbtuxSearch.cpp
+333
-0
ndb/src/kernel/blocks/dbtux/DbtuxTree.cpp
ndb/src/kernel/blocks/dbtux/DbtuxTree.cpp
+0
-106
ndb/src/kernel/blocks/dbtux/Makefile.am
ndb/src/kernel/blocks/dbtux/Makefile.am
+1
-0
ndb/src/kernel/blocks/dbtux/Times.txt
ndb/src/kernel/blocks/dbtux/Times.txt
+3
-0
ndb/test/ndbapi/testOIBasic.cpp
ndb/test/ndbapi/testOIBasic.cpp
+3
-1
No files found.
ndb/include/kernel/ndb_limits.h
View file @
b703c784
...
...
@@ -88,7 +88,7 @@
* Ordered index constants. Make configurable per index later.
*/
#define MAX_TTREE_NODE_SIZE 64 // total words in node
#define MAX_TTREE_PREF_SIZE 4 // words in min
/max prefix each
#define MAX_TTREE_PREF_SIZE 4 // words in min
prefix
#define MAX_TTREE_NODE_SLACK 3 // diff between max and min occupancy
/*
...
...
ndb/src/kernel/blocks/dbtux/Dbtux.hpp
View file @
b703c784
...
...
@@ -77,10 +77,14 @@
#define jam() jamLine(60000 + __LINE__)
#define jamEntry() jamEntryLine(60000 + __LINE__)
#endif
#ifdef DBTUX_
CMP
_CPP
#ifdef DBTUX_
SEARCH
_CPP
#define jam() jamLine(70000 + __LINE__)
#define jamEntry() jamEntryLine(70000 + __LINE__)
#endif
#ifdef DBTUX_CMP_CPP
#define jam() jamLine(80000 + __LINE__)
#define jamEntry() jamEntryLine(80000 + __LINE__)
#endif
#ifdef DBTUX_DEBUG_CPP
#define jam() jamLine(90000 + __LINE__)
#define jamEntry() jamEntryLine(90000 + __LINE__)
...
...
@@ -112,6 +116,7 @@ public:
static
const
unsigned
DescPageSize
=
256
;
private:
static
const
unsigned
MaxTreeNodeSize
=
MAX_TTREE_NODE_SIZE
;
static
const
unsigned
MaxPrefSize
=
MAX_TTREE_PREF_SIZE
;
static
const
unsigned
ScanBoundSegmentSize
=
7
;
static
const
unsigned
MaxAccLockOps
=
MAX_PARALLEL_OP_PER_SCAN
;
BLOCK_DEFINES
(
Dbtux
);
...
...
@@ -206,19 +211,19 @@ private:
unsigned
m_fragBit
:
1
;
// which duplicated table fragment
TreeEnt
();
// methods
bool
eq
(
const
TreeEnt
ent
)
const
;
int
cmp
(
const
TreeEnt
ent
)
const
;
};
static
const
unsigned
TreeEntSize
=
sizeof
(
TreeEnt
)
>>
2
;
static
const
TreeEnt
NullTreeEnt
;
/*
* Tree node has 1) fixed part 2) a
ctual table data for min and max
*
prefix
3) max and min entries 4) rest of entries 5) one extra entry
* Tree node has 1) fixed part 2) a
prefix of index key data for min
*
entry
3) max and min entries 4) rest of entries 5) one extra entry
* used as work space.
*
* struct TreeNode part 1, size 6 words
* min prefix part 2, size TreeHead::m_prefSize
* max prefix part 2, size TreeHead::m_prefSize
* max entry part 3
* min entry part 3
* rest of entries part 4
...
...
@@ -265,14 +270,14 @@ private:
friend
struct
TreeHead
;
struct
TreeHead
{
Uint8
m_nodeSize
;
// words in tree node
Uint8
m_prefSize
;
// words in min
/max prefix each
Uint8
m_prefSize
;
// words in min
prefix
Uint8
m_minOccup
;
// min entries in internal node
Uint8
m_maxOccup
;
// max entries in node
TupLoc
m_root
;
// root node
TreeHead
();
// methods
unsigned
getSize
(
AccSize
acc
)
const
;
Data
getPref
(
TreeNode
*
node
,
unsigned
i
)
const
;
Data
getPref
(
TreeNode
*
node
)
const
;
TreeEnt
*
getEntList
(
TreeNode
*
node
)
const
;
};
...
...
@@ -514,6 +519,8 @@ private:
NodeHandle
(
Frag
&
frag
);
NodeHandle
(
const
NodeHandle
&
node
);
NodeHandle
&
operator
=
(
const
NodeHandle
&
node
);
// check if unassigned
bool
isNull
();
// getters
TupLoc
getLink
(
unsigned
i
);
unsigned
getChilds
();
// cannot spell
...
...
@@ -528,7 +535,7 @@ private:
void
setBalance
(
int
b
);
void
setNodeScan
(
Uint32
scanPtrI
);
// access other parts of the node
Data
getPref
(
unsigned
i
);
Data
getPref
();
TreeEnt
getEnt
(
unsigned
pos
);
TreeEnt
getMinMax
(
unsigned
i
);
// for ndbrequire and ndbassert
...
...
@@ -618,7 +625,7 @@ private:
void
selectNode
(
Signal
*
signal
,
NodeHandle
&
node
,
TupLoc
loc
,
AccSize
acc
);
void
insertNode
(
Signal
*
signal
,
NodeHandle
&
node
,
AccSize
acc
);
void
deleteNode
(
Signal
*
signal
,
NodeHandle
&
node
);
void
setNodePref
(
Signal
*
signal
,
NodeHandle
&
node
,
unsigned
i
);
void
setNodePref
(
Signal
*
signal
,
NodeHandle
&
node
);
// node operations
void
nodePushUp
(
Signal
*
signal
,
NodeHandle
&
node
,
unsigned
pos
,
const
TreeEnt
&
ent
);
void
nodePopDown
(
Signal
*
signal
,
NodeHandle
&
node
,
unsigned
pos
,
TreeEnt
&
ent
);
...
...
@@ -633,7 +640,6 @@ private:
/*
* DbtuxTree.cpp
*/
void
treeSearch
(
Signal
*
signal
,
Frag
&
frag
,
TableData
searchKey
,
TreeEnt
searchEnt
,
TreePos
&
treePos
);
void
treeAdd
(
Signal
*
signal
,
Frag
&
frag
,
TreePos
treePos
,
TreeEnt
ent
);
void
treeRemove
(
Signal
*
signal
,
Frag
&
frag
,
TreePos
treePos
);
void
treeRotateSingle
(
Signal
*
signal
,
Frag
&
frag
,
NodeHandle
&
node
,
unsigned
i
);
...
...
@@ -657,12 +663,20 @@ private:
void
removeAccLockOp
(
ScanOp
&
scan
,
Uint32
accLockOp
);
void
releaseScanOp
(
ScanOpPtr
&
scanPtr
);
/*
* DbtuxSearch.cpp
*/
void
searchToAdd
(
Signal
*
signal
,
Frag
&
frag
,
TableData
searchKey
,
TreeEnt
searchEnt
,
TreePos
&
treePos
);
void
searchToRemove
(
Signal
*
signal
,
Frag
&
frag
,
TableData
searchKey
,
TreeEnt
searchEnt
,
TreePos
&
treePos
);
void
searchToScan
(
Signal
*
signal
,
Frag
&
frag
,
ConstData
boundInfo
,
unsigned
boundCount
,
TreePos
&
treePos
);
/*
* DbtuxCmp.cpp
*/
int
cmpSearchKey
(
const
Frag
&
frag
,
unsigned
&
start
,
TableData
data1
,
ConstData
data2
,
unsigned
maxlen2
=
MaxAttrDataSize
);
int
cmpSearchKey
(
const
Frag
&
frag
,
unsigned
&
start
,
TableData
data1
,
TableData
data2
);
int
cmpScanBound
(
const
Frag
&
frag
,
const
BoundPar
boundPar
);
int
cmpSearchKey
(
const
Frag
&
frag
,
unsigned
&
start
,
TableData
searchKey
,
ConstData
entryData
,
unsigned
maxlen
=
MaxAttrDataSize
);
int
cmpSearchKey
(
const
Frag
&
frag
,
unsigned
&
start
,
TableData
searchKey
,
TableData
entryKey
);
int
cmpScanBound
(
const
Frag
&
frag
,
unsigned
dir
,
ConstData
boundInfo
,
unsigned
boundCount
,
ConstData
entryData
,
unsigned
maxlen
=
MaxAttrDataSize
);
int
cmpScanBound
(
const
Frag
&
frag
,
unsigned
dir
,
ConstData
boundInfo
,
unsigned
boundCount
,
TableData
entryKey
);
/*
* DbtuxDebug.cpp
...
...
@@ -675,6 +689,7 @@ private:
TupLoc
m_parent
;
// expected parent address
int
m_depth
;
// returned depth
unsigned
m_occup
;
// returned occupancy
TreeEnt
m_minmax
[
2
];
// returned subtree min and max
bool
m_ok
;
// returned status
PrintPar
();
};
...
...
@@ -699,6 +714,8 @@ private:
DebugTree
=
4
,
// log and check tree after each op
DebugScan
=
8
// log scans
};
static
const
int
DataFillByte
=
0xa2
;
static
const
int
NodeFillByte
=
0xa4
;
#endif
// start up info
...
...
@@ -859,13 +876,18 @@ Dbtux::TreeEnt::TreeEnt() :
{
}
inline
bool
Dbtux
::
TreeEnt
::
eq
(
const
TreeEnt
ent
)
const
{
return
m_tupLoc
==
ent
.
m_tupLoc
&&
m_tupVersion
==
ent
.
m_tupVersion
&&
m_fragBit
==
ent
.
m_fragBit
;
}
inline
int
Dbtux
::
TreeEnt
::
cmp
(
const
TreeEnt
ent
)
const
{
if
(
m_fragBit
<
ent
.
m_fragBit
)
return
-
1
;
if
(
m_fragBit
>
ent
.
m_fragBit
)
return
+
1
;
if
(
m_tupLoc
.
m_pageId
<
ent
.
m_tupLoc
.
m_pageId
)
return
-
1
;
if
(
m_tupLoc
.
m_pageId
>
ent
.
m_tupLoc
.
m_pageId
)
...
...
@@ -878,6 +900,10 @@ Dbtux::TreeEnt::cmp(const TreeEnt ent) const
return
-
1
;
if
(
m_tupVersion
>
ent
.
m_tupVersion
)
return
+
1
;
if
(
m_fragBit
<
ent
.
m_fragBit
)
return
-
1
;
if
(
m_fragBit
>
ent
.
m_fragBit
)
return
+
1
;
return
0
;
}
...
...
@@ -920,7 +946,7 @@ Dbtux::TreeHead::getSize(AccSize acc) const
case
AccHead
:
return
NodeHeadSize
;
case
AccPref
:
return
NodeHeadSize
+
2
*
m_prefSize
+
2
*
TreeEntSize
;
return
NodeHeadSize
+
m_prefSize
+
2
*
TreeEntSize
;
case
AccFull
:
return
m_nodeSize
;
}
...
...
@@ -929,16 +955,16 @@ Dbtux::TreeHead::getSize(AccSize acc) const
}
inline
Dbtux
::
Data
Dbtux
::
TreeHead
::
getPref
(
TreeNode
*
node
,
unsigned
i
)
const
Dbtux
::
TreeHead
::
getPref
(
TreeNode
*
node
)
const
{
Uint32
*
ptr
=
(
Uint32
*
)
node
+
NodeHeadSize
+
i
*
m_prefSize
;
Uint32
*
ptr
=
(
Uint32
*
)
node
+
NodeHeadSize
;
return
ptr
;
}
inline
Dbtux
::
TreeEnt
*
Dbtux
::
TreeHead
::
getEntList
(
TreeNode
*
node
)
const
{
Uint32
*
ptr
=
(
Uint32
*
)
node
+
NodeHeadSize
+
2
*
m_prefSize
;
Uint32
*
ptr
=
(
Uint32
*
)
node
+
NodeHeadSize
+
m_prefSize
;
return
(
TreeEnt
*
)
ptr
;
}
...
...
@@ -1087,6 +1113,12 @@ Dbtux::NodeHandle::operator=(const NodeHandle& node)
return
*
this
;
}
inline
bool
Dbtux
::
NodeHandle
::
isNull
()
{
return
m_node
==
0
;
}
inline
Dbtux
::
TupLoc
Dbtux
::
NodeHandle
::
getLink
(
unsigned
i
)
{
...
...
@@ -1161,11 +1193,11 @@ Dbtux::NodeHandle::setNodeScan(Uint32 scanPtrI)
}
inline
Dbtux
::
Data
Dbtux
::
NodeHandle
::
getPref
(
unsigned
i
)
Dbtux
::
NodeHandle
::
getPref
()
{
TreeHead
&
tree
=
m_frag
.
m_tree
;
ndbrequire
(
m_acc
>=
AccPref
&&
i
<=
1
);
return
tree
.
getPref
(
m_node
,
i
);
ndbrequire
(
m_acc
>=
AccPref
);
return
tree
.
getPref
(
m_node
);
}
inline
Dbtux
::
TreeEnt
...
...
ndb/src/kernel/blocks/dbtux/DbtuxCmp.cpp
View file @
b703c784
This diff is collapsed.
Click to expand it.
ndb/src/kernel/blocks/dbtux/DbtuxDebug.cpp
View file @
b703c784
...
...
@@ -137,16 +137,17 @@ Dbtux::printNode(Signal* signal, Frag& frag, NdbOut& out, TupLoc loc, PrintPar&
par
.
m_ok
=
false
;
}
}
static
const
char
*
const
sep
=
" *** "
;
// check child-parent links
if
(
node
.
getLink
(
2
)
!=
par
.
m_parent
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"parent loc "
<<
hex
<<
node
.
getLink
(
2
);
out
<<
" should be "
<<
hex
<<
par
.
m_parent
<<
endl
;
}
if
(
node
.
getSide
()
!=
par
.
m_side
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"side "
<<
dec
<<
node
.
getSide
();
out
<<
" should be "
<<
dec
<<
par
.
m_side
<<
endl
;
}
...
...
@@ -154,26 +155,26 @@ Dbtux::printNode(Signal* signal, Frag& frag, NdbOut& out, TupLoc loc, PrintPar&
const
int
balance
=
-
cpar
[
0
].
m_depth
+
cpar
[
1
].
m_depth
;
if
(
node
.
getBalance
()
!=
balance
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"balance "
<<
node
.
getBalance
();
out
<<
" should be "
<<
balance
<<
endl
;
}
if
(
abs
(
node
.
getBalance
())
>
1
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"balance "
<<
node
.
getBalance
()
<<
" is invalid"
<<
endl
;
}
// check occupancy
if
(
node
.
getOccup
()
>
tree
.
m_maxOccup
)
{
if
(
node
.
getOccup
()
==
0
||
node
.
getOccup
()
>
tree
.
m_maxOccup
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"occupancy "
<<
node
.
getOccup
();
out
<<
" greater than max "
<<
tree
.
m_maxOccup
<<
endl
;
out
<<
"
zero or
greater than max "
<<
tree
.
m_maxOccup
<<
endl
;
}
// check for occupancy of interior node
if
(
node
.
getChilds
()
==
2
&&
node
.
getOccup
()
<
tree
.
m_minOccup
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"occupancy "
<<
node
.
getOccup
()
<<
" of interior node"
;
out
<<
" less than min "
<<
tree
.
m_minOccup
<<
endl
;
}
...
...
@@ -183,13 +184,74 @@ Dbtux::printNode(Signal* signal, Frag& frag, NdbOut& out, TupLoc loc, PrintPar&
node
.
getLink
(
1
-
i
)
==
NullTupLoc
&&
node
.
getOccup
()
+
cpar
[
i
].
m_occup
<=
tree
.
m_maxOccup
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
" *** "
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"missed merge with child "
<<
i
<<
endl
;
}
}
// check inline prefix
{
ConstData
data1
=
node
.
getPref
();
Uint32
data2
[
MaxPrefSize
];
memset
(
data2
,
DataFillByte
,
MaxPrefSize
<<
2
);
readKeyAttrs
(
frag
,
node
.
getMinMax
(
0
),
0
,
c_searchKey
);
copyAttrs
(
frag
,
c_searchKey
,
data2
,
tree
.
m_prefSize
);
for
(
unsigned
n
=
0
;
n
<
tree
.
m_prefSize
;
n
++
)
{
if
(
data1
[
n
]
!=
data2
[
n
])
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
sep
;
out
<<
"inline prefix mismatch word "
<<
n
;
out
<<
" value "
<<
hex
<<
data1
[
n
];
out
<<
" should be "
<<
hex
<<
data2
[
n
]
<<
endl
;
break
;
}
}
}
// check ordering within node
for
(
unsigned
j
=
1
;
j
<
node
.
getOccup
();
j
++
)
{
unsigned
start
=
0
;
const
TreeEnt
ent1
=
node
.
getEnt
(
j
-
1
);
const
TreeEnt
ent2
=
node
.
getEnt
(
j
);
if
(
j
==
1
)
{
readKeyAttrs
(
frag
,
ent1
,
start
,
c_searchKey
);
}
else
{
memcpy
(
c_searchKey
,
c_entryKey
,
frag
.
m_numAttrs
<<
2
);
}
readKeyAttrs
(
frag
,
ent2
,
start
,
c_entryKey
);
int
ret
=
cmpSearchKey
(
frag
,
start
,
c_searchKey
,
c_entryKey
);
if
(
ret
==
0
)
ret
=
ent1
.
cmp
(
ent2
);
if
(
ret
!=
-
1
)
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
sep
;
out
<<
" disorder within node at pos "
<<
j
<<
endl
;
}
}
// check ordering wrt subtrees
for
(
unsigned
i
=
0
;
i
<=
1
;
i
++
)
{
if
(
node
.
getLink
(
i
)
==
NullTupLoc
)
continue
;
const
TreeEnt
ent1
=
cpar
[
i
].
m_minmax
[
1
-
i
];
const
TreeEnt
ent2
=
node
.
getMinMax
(
i
);
unsigned
start
=
0
;
readKeyAttrs
(
frag
,
ent1
,
start
,
c_searchKey
);
readKeyAttrs
(
frag
,
ent2
,
start
,
c_entryKey
);
int
ret
=
cmpSearchKey
(
frag
,
start
,
c_searchKey
,
c_entryKey
);
if
(
ret
==
0
)
ret
=
ent1
.
cmp
(
ent2
);
if
(
ret
!=
(
i
==
0
?
-
1
:
+
1
))
{
par
.
m_ok
=
false
;
out
<<
par
.
m_path
<<
sep
;
out
<<
" disorder wrt subtree "
<<
i
<<
endl
;
}
}
// return values
par
.
m_depth
=
1
+
max
(
cpar
[
0
].
m_depth
,
cpar
[
1
].
m_depth
);
par
.
m_occup
=
node
.
getOccup
();
for
(
unsigned
i
=
0
;
i
<=
1
;
i
++
)
{
if
(
node
.
getLink
(
i
)
==
NullTupLoc
)
par
.
m_minmax
[
i
]
=
node
.
getMinMax
(
i
);
else
par
.
m_minmax
[
i
]
=
cpar
[
i
].
m_minmax
[
i
];
}
}
NdbOut
&
...
...
@@ -355,20 +417,19 @@ operator<<(NdbOut& out, const Dbtux::NodeHandle& node)
out
<<
" [acc "
<<
dec
<<
node
.
m_acc
<<
"]"
;
out
<<
" [node "
<<
*
node
.
m_node
<<
"]"
;
if
(
node
.
m_acc
>=
Dbtux
::
AccPref
)
{
for
(
unsigned
i
=
0
;
i
<=
1
;
i
++
)
{
out
<<
" [pref "
<<
dec
<<
i
;
const
Uint32
*
data
=
(
const
Uint32
*
)
node
.
m_node
+
Dbtux
::
NodeHeadSize
+
i
*
tree
.
m_prefSize
;
for
(
unsigned
j
=
0
;
j
<
node
.
m_frag
.
m_tree
.
m_prefSize
;
j
++
)
out
<<
" "
<<
hex
<<
data
[
j
];
out
<<
"]"
;
}
const
Uint32
*
data
;
out
<<
" [pref"
;
data
=
(
const
Uint32
*
)
node
.
m_node
+
Dbtux
::
NodeHeadSize
;
for
(
unsigned
j
=
0
;
j
<
tree
.
m_prefSize
;
j
++
)
out
<<
" "
<<
hex
<<
data
[
j
];
out
<<
"]"
;
out
<<
" [entList"
;
unsigned
numpos
=
node
.
m_node
->
m_occup
;
if
(
node
.
m_acc
<
Dbtux
::
AccFull
&&
numpos
>
2
)
{
numpos
=
2
;
out
<<
"("
<<
dec
<<
numpos
<<
")"
;
}
const
Uint32
*
data
=
(
const
Uint32
*
)
node
.
m_node
+
Dbtux
::
NodeHeadSize
+
2
*
tree
.
m_prefSize
;
data
=
(
const
Uint32
*
)
node
.
m_node
+
Dbtux
::
NodeHeadSize
+
tree
.
m_prefSize
;
const
Dbtux
::
TreeEnt
*
entList
=
(
const
Dbtux
::
TreeEnt
*
)
data
;
for
(
unsigned
pos
=
0
;
pos
<
numpos
;
pos
++
)
out
<<
" "
<<
entList
[
pos
];
...
...
ndb/src/kernel/blocks/dbtux/DbtuxGen.cpp
View file @
b703c784
...
...
@@ -26,7 +26,12 @@ Dbtux::Dbtux(const Configuration& conf) :
#ifdef VM_TRACE
debugFile
(
0
),
debugOut
(
*
new
NullOutputStream
()),
// until ndb_mgm supports dump
#ifdef DBTUX_DEBUG_TREE
debugFlags
(
DebugTree
),
#else
debugFlags
(
0
),
#endif
#endif
c_internalStartPhase
(
0
),
c_typeOfStart
(
NodeState
::
ST_ILLEGAL_TYPE
),
...
...
@@ -314,6 +319,9 @@ Dbtux::copyAttrs(const Frag& frag, TableData data1, Data data2, unsigned maxlen2
keyAttrs
+=
1
;
data1
+=
1
;
}
#ifdef VM_TRACE
memset
(
data2
,
DataFillByte
,
len2
<<
2
);
#endif
}
BLOCK_FUNCTIONS
(
Dbtux
);
ndb/src/kernel/blocks/dbtux/DbtuxMaint.cpp
View file @
b703c784
...
...
@@ -110,20 +110,19 @@ Dbtux::execTUX_MAINT_REQ(Signal* signal)
debugOut
<<
" entry="
<<
ent
;
debugOut
<<
endl
;
}
#endif
// find position in tree
TreePos
treePos
;
treeSearch
(
signal
,
frag
,
c_searchKey
,
ent
,
treePos
);
#ifdef VM_TRACE
if
(
debugFlags
&
DebugMaint
)
{
debugOut
<<
treePos
<<
endl
;
}
#endif
// do the operation
req
->
errorCode
=
0
;
TreePos
treePos
;
switch
(
opCode
)
{
case
TuxMaintReq
:
:
OpAdd
:
jam
();
searchToAdd
(
signal
,
frag
,
c_searchKey
,
ent
,
treePos
);
#ifdef VM_TRACE
if
(
debugFlags
&
DebugMaint
)
{
debugOut
<<
treePos
<<
endl
;
}
#endif
if
(
treePos
.
m_match
)
{
jam
();
// there is no "Building" state so this will have to do
...
...
@@ -152,6 +151,12 @@ Dbtux::execTUX_MAINT_REQ(Signal* signal)
break
;
case
TuxMaintReq
:
:
OpRemove
:
jam
();
searchToRemove
(
signal
,
frag
,
c_searchKey
,
ent
,
treePos
);
#ifdef VM_TRACE
if
(
debugFlags
&
DebugMaint
)
{
debugOut
<<
treePos
<<
endl
;
}
#endif
if
(
!
treePos
.
m_match
)
{
jam
();
// there is no "Building" state so this will have to do
...
...
@@ -167,7 +172,6 @@ Dbtux::execTUX_MAINT_REQ(Signal* signal)
ndbrequire
(
false
);
break
;
}
// commit and release nodes
#ifdef VM_TRACE
if
(
debugFlags
&
DebugTree
)
{
printTree
(
signal
,
frag
,
debugOut
);
...
...
ndb/src/kernel/blocks/dbtux/DbtuxNode.cpp
View file @
b703c784
...
...
@@ -85,10 +85,9 @@ Dbtux::insertNode(Signal* signal, NodeHandle& node, AccSize acc)
new
(
node
.
m_node
)
TreeNode
();
#ifdef VM_TRACE
TreeHead
&
tree
=
frag
.
m_tree
;
memset
(
node
.
getPref
(
0
),
0xa2
,
tree
.
m_prefSize
<<
2
);
memset
(
node
.
getPref
(
1
),
0xa2
,
tree
.
m_prefSize
<<
2
);
memset
(
node
.
getPref
(),
DataFillByte
,
tree
.
m_prefSize
<<
2
);
TreeEnt
*
entList
=
tree
.
getEntList
(
node
.
m_node
);
memset
(
entList
,
0xa4
,
(
tree
.
m_maxOccup
+
1
)
*
(
TreeEntSize
<<
2
));
memset
(
entList
,
NodeFillByte
,
(
tree
.
m_maxOccup
+
1
)
*
(
TreeEntSize
<<
2
));
#endif
}
...
...
@@ -116,12 +115,12 @@ Dbtux::deleteNode(Signal* signal, NodeHandle& node)
* attribute headers for now. XXX use null mask instead
*/
void
Dbtux
::
setNodePref
(
Signal
*
signal
,
NodeHandle
&
node
,
unsigned
i
)
Dbtux
::
setNodePref
(
Signal
*
signal
,
NodeHandle
&
node
)
{
const
Frag
&
frag
=
node
.
m_frag
;
const
TreeHead
&
tree
=
frag
.
m_tree
;
readKeyAttrs
(
frag
,
node
.
getMinMax
(
i
),
0
,
c_entryKey
);
copyAttrs
(
frag
,
c_entryKey
,
node
.
getPref
(
i
),
tree
.
m_prefSize
);
readKeyAttrs
(
frag
,
node
.
getMinMax
(
0
),
0
,
c_entryKey
);
copyAttrs
(
frag
,
c_entryKey
,
node
.
getPref
(),
tree
.
m_prefSize
);
}
// node operations
...
...
@@ -173,11 +172,9 @@ Dbtux::nodePushUp(Signal* signal, NodeHandle& node, unsigned pos, const TreeEnt&
tmpList
[
pos
]
=
ent
;
entList
[
0
]
=
entList
[
occup
+
1
];
node
.
setOccup
(
occup
+
1
);
// fix prefix
es
// fix prefix
if
(
occup
==
0
||
pos
==
0
)
setNodePref
(
signal
,
node
,
0
);
if
(
occup
==
0
||
pos
==
occup
)
setNodePref
(
signal
,
node
,
1
);
setNodePref
(
signal
,
node
);
}
/*
...
...
@@ -248,11 +245,9 @@ Dbtux::nodePopDown(Signal* signal, NodeHandle& node, unsigned pos, TreeEnt& ent)
}
entList
[
0
]
=
entList
[
occup
-
1
];
node
.
setOccup
(
occup
-
1
);
// fix prefix
es
// fix prefix
if
(
occup
!=
1
&&
pos
==
0
)
setNodePref
(
signal
,
node
,
0
);
if
(
occup
!=
1
&&
pos
==
occup
-
1
)
setNodePref
(
signal
,
node
,
1
);
setNodePref
(
signal
,
node
);
}
/*
...
...
@@ -325,11 +320,9 @@ Dbtux::nodePushDown(Signal* signal, NodeHandle& node, unsigned pos, TreeEnt& ent
tmpList
[
pos
]
=
ent
;
ent
=
oldMin
;
entList
[
0
]
=
entList
[
occup
];
// fix prefix
es
// fix prefix
if
(
true
)
setNodePref
(
signal
,
node
,
0
);
if
(
occup
==
1
||
pos
==
occup
-
1
)
setNodePref
(
signal
,
node
,
1
);
setNodePref
(
signal
,
node
);
}
/*
...
...
@@ -403,11 +396,9 @@ Dbtux::nodePopUp(Signal* signal, NodeHandle& node, unsigned pos, TreeEnt& ent)
}
tmpList
[
0
]
=
newMin
;
entList
[
0
]
=
entList
[
occup
];
// fix prefix
es
// fix prefix
if
(
true
)
setNodePref
(
signal
,
node
,
0
);
if
(
occup
==
1
||
pos
==
occup
-
1
)
setNodePref
(
signal
,
node
,
1
);
setNodePref
(
signal
,
node
);
}
/*
...
...
ndb/src/kernel/blocks/dbtux/DbtuxScan.cpp
View file @
b703c784
...
...
@@ -689,16 +689,9 @@ Dbtux::scanFirst(Signal* signal, ScanOpPtr scanPtr)
ScanOp
&
scan
=
*
scanPtr
.
p
;
Frag
&
frag
=
*
c_fragPool
.
getPtr
(
scan
.
m_fragPtrI
);
TreeHead
&
tree
=
frag
.
m_tree
;
if
(
tree
.
m_root
==
NullTupLoc
)
{
// tree may have become empty
jam
();
scan
.
m_state
=
ScanOp
::
Last
;
return
;
}
TreePos
pos
;
pos
.
m_loc
=
tree
.
m_root
;
NodeHandle
node
(
frag
);
// unpack lower bound
// set up index keys for this operation
setKeyAttrs
(
frag
);
// unpack lower bound into c_dataBuffer
const
ScanBound
&
bound
=
*
scan
.
m_bound
[
0
];
ScanBoundIterator
iter
;
bound
.
first
(
iter
);
...
...
@@ -707,103 +700,22 @@ Dbtux::scanFirst(Signal* signal, ScanOpPtr scanPtr)
c_dataBuffer
[
j
]
=
*
iter
.
data
;
bound
.
next
(
iter
);
}
// comparison parameters
BoundPar
boundPar
;
boundPar
.
m_data1
=
c_dataBuffer
;
boundPar
.
m_count1
=
scan
.
m_boundCnt
[
0
];
boundPar
.
m_dir
=
0
;
loop:
{
// search for scan start position
TreePos
treePos
;
searchToScan
(
signal
,
frag
,
c_dataBuffer
,
scan
.
m_boundCnt
[
0
],
treePos
);
if
(
treePos
.
m_loc
==
NullTupLoc
)
{
// empty tree
jam
();
selectNode
(
signal
,
node
,
pos
.
m_loc
,
AccPref
);
const
unsigned
occup
=
node
.
getOccup
();
ndbrequire
(
occup
!=
0
);
for
(
unsigned
i
=
0
;
i
<=
1
;
i
++
)
{
jam
();
// compare prefix
boundPar
.
m_data2
=
node
.
getPref
(
i
);
boundPar
.
m_len2
=
tree
.
m_prefSize
;
int
ret
=
cmpScanBound
(
frag
,
boundPar
);
if
(
ret
==
NdbSqlUtil
::
CmpUnknown
)
{
jam
();
// read full value
ReadPar
readPar
;
readPar
.
m_ent
=
node
.
getMinMax
(
i
);
readPar
.
m_first
=
0
;
readPar
.
m_count
=
frag
.
m_numAttrs
;
readPar
.
m_data
=
0
;
// leave in signal data
tupReadAttrs
(
signal
,
frag
,
readPar
);
// compare full value
boundPar
.
m_data2
=
readPar
.
m_data
;
boundPar
.
m_len2
=
ZNIL
;
// big
ret
=
cmpScanBound
(
frag
,
boundPar
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
}
if
(
i
==
0
&&
ret
<
0
)
{
jam
();
const
TupLoc
loc
=
node
.
getLink
(
i
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// continue to left subtree
pos
.
m_loc
=
loc
;
goto
loop
;
}
// start scanning this node
pos
.
m_pos
=
0
;
pos
.
m_match
=
false
;
pos
.
m_dir
=
3
;
scan
.
m_scanPos
=
pos
;
scan
.
m_state
=
ScanOp
::
Next
;
linkScan
(
node
,
scanPtr
);
return
;
}
if
(
i
==
1
&&
ret
>
0
)
{
jam
();
const
TupLoc
loc
=
node
.
getLink
(
i
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// continue to right subtree
pos
.
m_loc
=
loc
;
goto
loop
;
}
// start scanning upwards
pos
.
m_dir
=
1
;
scan
.
m_scanPos
=
pos
;
scan
.
m_state
=
ScanOp
::
Next
;
linkScan
(
node
,
scanPtr
);
return
;
}
}
// read rest of current node
accessNode
(
signal
,
node
,
AccFull
);
// look for first entry
ndbrequire
(
occup
>=
2
);
for
(
unsigned
j
=
1
;
j
<
occup
;
j
++
)
{
jam
();
ReadPar
readPar
;
readPar
.
m_ent
=
node
.
getEnt
(
j
);
readPar
.
m_first
=
0
;
readPar
.
m_count
=
frag
.
m_numAttrs
;
readPar
.
m_data
=
0
;
// leave in signal data
tupReadAttrs
(
signal
,
frag
,
readPar
);
// compare
boundPar
.
m_data2
=
readPar
.
m_data
;
boundPar
.
m_len2
=
ZNIL
;
// big
int
ret
=
cmpScanBound
(
frag
,
boundPar
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
if
(
ret
<
0
)
{
jam
();
// start scanning this node
pos
.
m_pos
=
j
;
pos
.
m_match
=
false
;
pos
.
m_dir
=
3
;
scan
.
m_scanPos
=
pos
;
scan
.
m_state
=
ScanOp
::
Next
;
linkScan
(
node
,
scanPtr
);
return
;
}
}
ndbrequire
(
false
);
scan
.
m_state
=
ScanOp
::
Last
;
return
;
}
// set position and state
scan
.
m_scanPos
=
treePos
;
scan
.
m_state
=
ScanOp
::
Next
;
// link the scan to node found
NodeHandle
node
(
frag
);
selectNode
(
signal
,
node
,
treePos
.
m_loc
,
AccFull
);
linkScan
(
node
,
scanPtr
);
}
/*
...
...
@@ -841,7 +753,9 @@ Dbtux::scanNext(Signal* signal, ScanOpPtr scanPtr)
scan
.
m_accLockOp
=
RNIL
;
scan
.
m_state
=
ScanOp
::
Current
;
}
// unpack upper bound
// set up index keys for this operation
setKeyAttrs
(
frag
);
// unpack upper bound into c_dataBuffer
const
ScanBound
&
bound
=
*
scan
.
m_bound
[
1
];
ScanBoundIterator
iter
;
bound
.
first
(
iter
);
...
...
@@ -850,11 +764,6 @@ Dbtux::scanNext(Signal* signal, ScanOpPtr scanPtr)
c_dataBuffer
[
j
]
=
*
iter
.
data
;
bound
.
next
(
iter
);
}
// comparison parameters
BoundPar
boundPar
;
boundPar
.
m_data1
=
c_dataBuffer
;
boundPar
.
m_count1
=
scan
.
m_boundCnt
[
1
];
boundPar
.
m_dir
=
1
;
// use copy of position
TreePos
pos
=
scan
.
m_scanPos
;
// get and remember original node
...
...
@@ -912,17 +821,9 @@ Dbtux::scanNext(Signal* signal, ScanOpPtr scanPtr)
jam
();
pos
.
m_ent
=
node
.
getEnt
(
pos
.
m_pos
);
pos
.
m_dir
=
3
;
// unchanged
// XXX implement prefix optimization
ReadPar
readPar
;
readPar
.
m_ent
=
pos
.
m_ent
;
readPar
.
m_first
=
0
;
readPar
.
m_count
=
frag
.
m_numAttrs
;
readPar
.
m_data
=
0
;
// leave in signal data
tupReadAttrs
(
signal
,
frag
,
readPar
);
// compare
boundPar
.
m_data2
=
readPar
.
m_data
;
boundPar
.
m_len2
=
ZNIL
;
// big
int
ret
=
cmpScanBound
(
frag
,
boundPar
);
// read and compare all attributes
readKeyAttrs
(
frag
,
pos
.
m_ent
,
0
,
c_entryKey
);
int
ret
=
cmpScanBound
(
frag
,
1
,
c_dataBuffer
,
scan
.
m_boundCnt
[
1
],
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
if
(
ret
<
0
)
{
jam
();
...
...
ndb/src/kernel/blocks/dbtux/DbtuxSearch.cpp
0 → 100644
View file @
b703c784
/* Copyright (C) 2003 MySQL AB
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
#define DBTUX_SEARCH_CPP
#include "Dbtux.hpp"
/*
* Search for entry to add.
*
* Similar to searchToRemove (see below).
*
* TODO optimize for initial equal attrs in node min/max
*/
void
Dbtux
::
searchToAdd
(
Signal
*
signal
,
Frag
&
frag
,
TableData
searchKey
,
TreeEnt
searchEnt
,
TreePos
&
treePos
)
{
const
TreeHead
&
tree
=
frag
.
m_tree
;
const
unsigned
numAttrs
=
frag
.
m_numAttrs
;
NodeHandle
currNode
(
frag
);
currNode
.
m_loc
=
tree
.
m_root
;
if
(
currNode
.
m_loc
==
NullTupLoc
)
{
// empty tree
jam
();
treePos
.
m_match
=
false
;
return
;
}
NodeHandle
glbNode
(
frag
);
// potential g.l.b of final node
/*
* In order to not (yet) change old behaviour, a position between
* 2 nodes returns the one at the bottom of the tree.
*/
NodeHandle
bottomNode
(
frag
);
while
(
true
)
{
jam
();
selectNode
(
signal
,
currNode
,
currNode
.
m_loc
,
AccPref
);
int
ret
;
// compare prefix
unsigned
start
=
0
;
ret
=
cmpSearchKey
(
frag
,
start
,
searchKey
,
currNode
.
getPref
(),
tree
.
m_prefSize
);
if
(
ret
==
NdbSqlUtil
::
CmpUnknown
)
{
jam
();
// read and compare remaining attributes
ndbrequire
(
start
<
numAttrs
);
readKeyAttrs
(
frag
,
currNode
.
getMinMax
(
0
),
start
,
c_entryKey
);
ret
=
cmpSearchKey
(
frag
,
start
,
searchKey
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
}
if
(
ret
==
0
)
{
jam
();
// keys are equal, compare entry values
ret
=
searchEnt
.
cmp
(
currNode
.
getMinMax
(
0
));
}
if
(
ret
<
0
)
{
jam
();
const
TupLoc
loc
=
currNode
.
getLink
(
0
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// continue to left subtree
currNode
.
m_loc
=
loc
;
continue
;
}
if
(
!
glbNode
.
isNull
())
{
jam
();
// move up to the g.l.b but remember the bottom node
bottomNode
=
currNode
;
currNode
=
glbNode
;
}
}
else
if
(
ret
>
0
)
{
jam
();
const
TupLoc
loc
=
currNode
.
getLink
(
1
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// save potential g.l.b
glbNode
=
currNode
;
// continue to right subtree
currNode
.
m_loc
=
loc
;
continue
;
}
}
else
{
jam
();
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
0
;
treePos
.
m_match
=
true
;
return
;
}
break
;
}
// access rest of current node
accessNode
(
signal
,
currNode
,
AccFull
);
for
(
unsigned
j
=
0
,
occup
=
currNode
.
getOccup
();
j
<
occup
;
j
++
)
{
jam
();
int
ret
;
// read and compare attributes
unsigned
start
=
0
;
readKeyAttrs
(
frag
,
currNode
.
getEnt
(
j
),
start
,
c_entryKey
);
ret
=
cmpSearchKey
(
frag
,
start
,
searchKey
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
if
(
ret
==
0
)
{
jam
();
// keys are equal, compare entry values
ret
=
searchEnt
.
cmp
(
currNode
.
getEnt
(
j
));
}
if
(
ret
<=
0
)
{
jam
();
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
j
;
treePos
.
m_match
=
(
ret
==
0
);
return
;
}
}
if
(
!
bottomNode
.
isNull
())
{
jam
();
// backwards compatible for now
treePos
.
m_loc
=
bottomNode
.
m_loc
;
treePos
.
m_pos
=
0
;
treePos
.
m_match
=
false
;
return
;
}
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
currNode
.
getOccup
();
treePos
.
m_match
=
false
;
}
/*
* Search for entry to remove.
*
* Compares search key to each node min. A move to right subtree can
* overshoot target node. The last such node is saved. The final node
* is a half-leaf or leaf. If search key is less than final node min
* then the saved node is the g.l.b of the final node and we move back
* to it.
*/
void
Dbtux
::
searchToRemove
(
Signal
*
signal
,
Frag
&
frag
,
TableData
searchKey
,
TreeEnt
searchEnt
,
TreePos
&
treePos
)
{
const
TreeHead
&
tree
=
frag
.
m_tree
;
const
unsigned
numAttrs
=
frag
.
m_numAttrs
;
NodeHandle
currNode
(
frag
);
currNode
.
m_loc
=
tree
.
m_root
;
if
(
currNode
.
m_loc
==
NullTupLoc
)
{
// empty tree
jam
();
treePos
.
m_match
=
false
;
return
;
}
NodeHandle
glbNode
(
frag
);
// potential g.l.b of final node
while
(
true
)
{
jam
();
selectNode
(
signal
,
currNode
,
currNode
.
m_loc
,
AccPref
);
int
ret
;
// compare prefix
unsigned
start
=
0
;
ret
=
cmpSearchKey
(
frag
,
start
,
searchKey
,
currNode
.
getPref
(),
tree
.
m_prefSize
);
if
(
ret
==
NdbSqlUtil
::
CmpUnknown
)
{
jam
();
// read and compare remaining attributes
ndbrequire
(
start
<
numAttrs
);
readKeyAttrs
(
frag
,
currNode
.
getMinMax
(
0
),
start
,
c_entryKey
);
ret
=
cmpSearchKey
(
frag
,
start
,
searchKey
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
}
if
(
ret
==
0
)
{
jam
();
// keys are equal, compare entry values
ret
=
searchEnt
.
cmp
(
currNode
.
getMinMax
(
0
));
}
if
(
ret
<
0
)
{
jam
();
const
TupLoc
loc
=
currNode
.
getLink
(
0
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// continue to left subtree
currNode
.
m_loc
=
loc
;
continue
;
}
if
(
!
glbNode
.
isNull
())
{
jam
();
// move up to the g.l.b
currNode
=
glbNode
;
}
}
else
if
(
ret
>
0
)
{
jam
();
const
TupLoc
loc
=
currNode
.
getLink
(
1
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// save potential g.l.b
glbNode
=
currNode
;
// continue to right subtree
currNode
.
m_loc
=
loc
;
continue
;
}
}
else
{
jam
();
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
0
;
treePos
.
m_match
=
true
;
return
;
}
break
;
}
// access rest of current node
accessNode
(
signal
,
currNode
,
AccFull
);
// pos 0 was handled above
for
(
unsigned
j
=
1
,
occup
=
currNode
.
getOccup
();
j
<
occup
;
j
++
)
{
jam
();
// compare only the entry
if
(
searchEnt
.
eq
(
currNode
.
getEnt
(
j
)))
{
jam
();
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
j
;
treePos
.
m_match
=
true
;
return
;
}
}
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
currNode
.
getOccup
();
treePos
.
m_match
=
false
;
}
/*
* Search for scan start position.
*
* Similar to searchToAdd.
*/
void
Dbtux
::
searchToScan
(
Signal
*
signal
,
Frag
&
frag
,
ConstData
boundInfo
,
unsigned
boundCount
,
TreePos
&
treePos
)
{
const
TreeHead
&
tree
=
frag
.
m_tree
;
NodeHandle
currNode
(
frag
);
currNode
.
m_loc
=
tree
.
m_root
;
if
(
currNode
.
m_loc
==
NullTupLoc
)
{
// empty tree
jam
();
treePos
.
m_match
=
false
;
return
;
}
NodeHandle
glbNode
(
frag
);
// potential g.l.b of final node
NodeHandle
bottomNode
(
frag
);
while
(
true
)
{
jam
();
selectNode
(
signal
,
currNode
,
currNode
.
m_loc
,
AccPref
);
int
ret
;
// compare prefix
ret
=
cmpScanBound
(
frag
,
0
,
boundInfo
,
boundCount
,
currNode
.
getPref
(),
tree
.
m_prefSize
);
if
(
ret
==
NdbSqlUtil
::
CmpUnknown
)
{
jam
();
// read and compare all attributes
readKeyAttrs
(
frag
,
currNode
.
getMinMax
(
0
),
0
,
c_entryKey
);
ret
=
cmpScanBound
(
frag
,
0
,
boundInfo
,
boundCount
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
}
if
(
ret
<
0
)
{
jam
();
const
TupLoc
loc
=
currNode
.
getLink
(
0
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// continue to left subtree
currNode
.
m_loc
=
loc
;
continue
;
}
if
(
!
glbNode
.
isNull
())
{
jam
();
// move up to the g.l.b but remember the bottom node
bottomNode
=
currNode
;
currNode
=
glbNode
;
}
else
{
// start scanning this node
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
0
;
treePos
.
m_match
=
false
;
treePos
.
m_dir
=
3
;
return
;
}
}
else
if
(
ret
>
0
)
{
jam
();
const
TupLoc
loc
=
currNode
.
getLink
(
1
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// save potential g.l.b
glbNode
=
currNode
;
// continue to right subtree
currNode
.
m_loc
=
loc
;
continue
;
}
}
else
{
ndbassert
(
false
);
}
break
;
}
// access rest of current node
accessNode
(
signal
,
currNode
,
AccFull
);
for
(
unsigned
j
=
0
,
occup
=
currNode
.
getOccup
();
j
<
occup
;
j
++
)
{
jam
();
int
ret
;
// read and compare attributes
readKeyAttrs
(
frag
,
currNode
.
getEnt
(
j
),
0
,
c_entryKey
);
ret
=
cmpScanBound
(
frag
,
0
,
boundInfo
,
boundCount
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
if
(
ret
<
0
)
{
// start scanning from current entry
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_pos
=
j
;
treePos
.
m_match
=
false
;
treePos
.
m_dir
=
3
;
return
;
}
}
if
(
!
bottomNode
.
isNull
())
{
jam
();
// start scanning the l.u.b
treePos
.
m_loc
=
bottomNode
.
m_loc
;
treePos
.
m_pos
=
0
;
treePos
.
m_match
=
false
;
treePos
.
m_dir
=
3
;
return
;
}
// start scanning upwards (pretend we came from right child)
treePos
.
m_loc
=
currNode
.
m_loc
;
treePos
.
m_dir
=
1
;
}
ndb/src/kernel/blocks/dbtux/DbtuxTree.cpp
View file @
b703c784
...
...
@@ -17,112 +17,6 @@
#define DBTUX_TREE_CPP
#include "Dbtux.hpp"
/*
* Search for entry.
*
* Search key is index attribute data and tree entry value. Start from
* root node and compare the key to min/max of each node. Use linear
* search on the final (bounding) node. Initial attributes which are
* same in min/max need not be checked.
*/
void
Dbtux
::
treeSearch
(
Signal
*
signal
,
Frag
&
frag
,
TableData
searchKey
,
TreeEnt
searchEnt
,
TreePos
&
treePos
)
{
const
TreeHead
&
tree
=
frag
.
m_tree
;
const
unsigned
numAttrs
=
frag
.
m_numAttrs
;
treePos
.
m_loc
=
tree
.
m_root
;
if
(
treePos
.
m_loc
==
NullTupLoc
)
{
// empty tree
jam
();
treePos
.
m_pos
=
0
;
treePos
.
m_match
=
false
;
return
;
}
NodeHandle
node
(
frag
);
loop:
{
jam
();
selectNode
(
signal
,
node
,
treePos
.
m_loc
,
AccPref
);
const
unsigned
occup
=
node
.
getOccup
();
ndbrequire
(
occup
!=
0
);
// number of equal initial attributes in bounding node
unsigned
start
=
ZNIL
;
for
(
unsigned
i
=
0
;
i
<=
1
;
i
++
)
{
jam
();
unsigned
start1
=
0
;
// compare prefix
int
ret
=
cmpSearchKey
(
frag
,
start1
,
searchKey
,
node
.
getPref
(
i
),
tree
.
m_prefSize
);
if
(
ret
==
NdbSqlUtil
::
CmpUnknown
)
{
jam
();
// read and compare remaining attributes
readKeyAttrs
(
frag
,
node
.
getMinMax
(
i
),
start1
,
c_entryKey
);
ret
=
cmpSearchKey
(
frag
,
start1
,
searchKey
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
}
if
(
start
>
start1
)
start
=
start1
;
if
(
ret
==
0
)
{
jam
();
// keys are equal, compare entry values
ret
=
searchEnt
.
cmp
(
node
.
getMinMax
(
i
));
}
if
(
i
==
0
?
(
ret
<
0
)
:
(
ret
>
0
))
{
jam
();
const
TupLoc
loc
=
node
.
getLink
(
i
);
if
(
loc
!=
NullTupLoc
)
{
jam
();
// continue to left/right subtree
treePos
.
m_loc
=
loc
;
goto
loop
;
}
// position is immediately before/after this node
treePos
.
m_pos
=
(
i
==
0
?
0
:
occup
);
treePos
.
m_match
=
false
;
return
;
}
if
(
ret
==
0
)
{
jam
();
// position is at first/last entry
treePos
.
m_pos
=
(
i
==
0
?
0
:
occup
-
1
);
treePos
.
m_match
=
true
;
return
;
}
}
// access rest of the bounding node
accessNode
(
signal
,
node
,
AccFull
);
// position is strictly within the node
ndbrequire
(
occup
>=
2
);
const
unsigned
numWithin
=
occup
-
2
;
for
(
unsigned
j
=
1
;
j
<=
numWithin
;
j
++
)
{
jam
();
int
ret
=
0
;
if
(
start
<
numAttrs
)
{
jam
();
// read and compare remaining attributes
unsigned
start1
=
start
;
readKeyAttrs
(
frag
,
node
.
getEnt
(
j
),
start1
,
c_entryKey
);
ret
=
cmpSearchKey
(
frag
,
start1
,
searchKey
,
c_entryKey
);
ndbrequire
(
ret
!=
NdbSqlUtil
::
CmpUnknown
);
}
if
(
ret
==
0
)
{
jam
();
// keys are equal, compare entry values
ret
=
searchEnt
.
cmp
(
node
.
getEnt
(
j
));
}
if
(
ret
<=
0
)
{
jam
();
// position is before or at this entry
treePos
.
m_pos
=
j
;
treePos
.
m_match
=
(
ret
==
0
);
return
;
}
}
// position is before last entry
treePos
.
m_pos
=
occup
-
1
;
treePos
.
m_match
=
false
;
return
;
}
}
/*
* Add entry.
*/
...
...
ndb/src/kernel/blocks/dbtux/Makefile.am
View file @
b703c784
...
...
@@ -7,6 +7,7 @@ libdbtux_a_SOURCES = \
DbtuxNode.cpp
\
DbtuxTree.cpp
\
DbtuxScan.cpp
\
DbtuxSearch.cpp
\
DbtuxCmp.cpp
\
DbtuxDebug.cpp
...
...
ndb/src/kernel/blocks/dbtux/Times.txt
View file @
b703c784
...
...
@@ -49,4 +49,7 @@ optim 10 mc02/a 44 ms 65 ms 46 pct
optim 11 mc02/a 43 ms 63 ms 46 pct
mc02/b 52 ms 86 ms 63 pct
optim 12 mc02/a 38 ms 55 ms 43 pct
mc02/b 47 ms 77 ms 63 pct
vim: set et:
ndb/test/ndbapi/testOIBasic.cpp
View file @
b703c784
...
...
@@ -2525,7 +2525,7 @@ tbusybuild(Par par)
for
(
unsigned
i
=
0
;
i
<
par
.
m_subloop
;
i
++
)
{
RUNSTEP
(
par
,
pkupdateindexbuild
,
MT
);
RUNSTEP
(
par
,
invalidateindex
,
MT
);
RUNSTEP
(
par
,
readverify
,
M
T
);
RUNSTEP
(
par
,
readverify
,
S
T
);
RUNSTEP
(
par
,
dropindex
,
ST
);
}
return
0
;
...
...
@@ -2564,9 +2564,11 @@ ttimemaint(Par par)
t1
.
off
(
par
.
m_totrows
);
RUNSTEP
(
par
,
createindex
,
ST
);
RUNSTEP
(
par
,
invalidateindex
,
MT
);
RUNSTEP
(
par
,
readverify
,
ST
);
t2
.
on
();
RUNSTEP
(
par
,
pkupdate
,
MT
);
t2
.
off
(
par
.
m_totrows
);
RUNSTEP
(
par
,
readverify
,
ST
);
RUNSTEP
(
par
,
dropindex
,
ST
);
}
LL1
(
"update - "
<<
t1
.
time
());
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment