transactd 1.2.0 → 2.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/BUILD_UNIX-JA +46 -67
- data/BUILD_WIN-JA +106 -63
- data/CMakeLists.txt +40 -15
- data/README +219 -75
- data/README-JA +207 -76
- data/README_ORMSRCGEN +118 -0
- data/README_ORMSRCGEN-JA +115 -0
- data/bin/common/tdclc_32_2_0.dll +0 -0
- data/bin/common/tdclc_64_2_0.dll +0 -0
- data/build/common/check_for_link_iconv.cmake +18 -14
- data/build/common/create_symlink.cmake.in +25 -0
- data/build/common/get_boost_libs.cmake +23 -23
- data/build/common/options.cmake +0 -66
- data/build/common/smart_install.cmake +3 -3
- data/build/common/transactd.rc.in +15 -5
- data/build/common/transactd_cl_common.cmake +37 -18
- data/build/common/transactd_cl_output.cmake +55 -13
- data/build/common/transactd_common.cmake +108 -31
- data/build/swig/php/generate.cmake.in +15 -17
- data/build/swig/php/generate.cmd.in +15 -9
- data/build/swig/php/php.swg +124 -82
- data/build/swig/php/transactd.no_yield.php +4494 -0
- data/build/swig/php/transactd.no_yield.php.git.patch +685 -0
- data/build/swig/php/transactd.no_yield.php.patch +685 -0
- data/build/swig/php/transactd.yield.php +4461 -0
- data/build/swig/php/transactd.yield.php.git.patch +652 -0
- data/build/swig/php/transactd.yield.php.patch +652 -0
- data/build/swig/referencecounter.h +79 -0
- data/build/swig/ruby/ruby.swg +226 -76
- data/build/swig/ruby/threadBlockRegionWrapper.h +71 -0
- data/build/swig/ruby/without_gvl.swg +87 -0
- data/build/swig/tdcl.i +659 -170
- data/build/swig/validatablepointer.h +91 -0
- data/build/tdclc/CMakeLists.txt +49 -34
- data/build/tdclc/{tdclc_64.cbproj → tdclc.cbproj} +65 -20
- data/build/tdclc/tdclc.rc +0 -0
- data/build/tdclcpp/CMakeLists.txt +84 -20
- data/build/tdclcpp/tdclcpp.rc +0 -0
- data/build/tdclcpp/{tdclcpp_bcb_64.cbproj → tdclcpp_bc.cbproj} +168 -44
- data/build/tdclrb/CMakeLists.txt +84 -66
- data/build/tdclrb/bldgem/extconf.rb +28 -3
- data/build/tdclrb/gem/helper.rb +11 -1
- data/build/tdclrb/gem_output.cmake +20 -16
- data/index_ja.html +15 -0
- data/source/bzs/db/IBlobBuffer.h +15 -17
- data/source/bzs/db/blobBuffer.h +186 -140
- data/source/bzs/db/blobStructs.h +37 -37
- data/source/bzs/db/engine/mysql/IReadRecords.h +34 -34
- data/source/bzs/db/engine/mysql/bookmark.h +150 -147
- data/source/bzs/db/engine/mysql/database.cpp +1721 -1526
- data/source/bzs/db/engine/mysql/database.h +608 -370
- data/source/bzs/db/engine/mysql/dbManager.cpp +213 -201
- data/source/bzs/db/engine/mysql/dbManager.h +115 -104
- data/source/bzs/db/engine/mysql/errorMessage.cpp +49 -50
- data/source/bzs/db/engine/mysql/errorMessage.h +25 -26
- data/source/bzs/db/engine/mysql/fieldAccess.h +55 -61
- data/source/bzs/db/engine/mysql/mydebuglog.cpp +326 -292
- data/source/bzs/db/engine/mysql/mydebuglog.h +63 -55
- data/source/bzs/db/engine/mysql/mysqlInternal.h +182 -125
- data/source/bzs/db/engine/mysql/mysqlThd.cpp +121 -121
- data/source/bzs/db/engine/mysql/mysqlThd.h +20 -20
- data/source/bzs/db/engine/mysql/percentageKey.h +241 -228
- data/source/bzs/db/protocol/ICommandExecuter.h +18 -17
- data/source/bzs/db/protocol/hs/hsCommandExecuter.cpp +543 -514
- data/source/bzs/db/protocol/hs/hsCommandExecuter.h +155 -158
- data/source/bzs/db/protocol/tdap/btrDate.cpp +213 -180
- data/source/bzs/db/protocol/tdap/btrDate.h +39 -37
- data/source/bzs/db/protocol/tdap/client/activeTable.cpp +173 -0
- data/source/bzs/db/protocol/tdap/client/activeTable.h +165 -0
- data/source/bzs/db/protocol/tdap/client/activeTableImple.h +370 -0
- data/source/bzs/db/protocol/tdap/client/bulkInsert.h +13 -23
- data/source/bzs/db/protocol/tdap/client/client.cpp +81 -68
- data/source/bzs/db/protocol/tdap/client/client.h +361 -320
- data/source/bzs/db/protocol/tdap/client/connMgr.cpp +17 -22
- data/source/bzs/db/protocol/tdap/client/connMgr.h +17 -19
- data/source/bzs/db/protocol/tdap/client/connectionPool.cpp +243 -0
- data/source/bzs/db/protocol/tdap/client/connectionPool.h +109 -0
- data/source/bzs/db/protocol/tdap/client/database.cpp +327 -219
- data/source/bzs/db/protocol/tdap/client/database.h +141 -118
- data/source/bzs/db/protocol/tdap/client/databaseFactory.cpp +60 -62
- data/source/bzs/db/protocol/tdap/client/databaseManager.h +255 -0
- data/source/bzs/db/protocol/tdap/client/dbDef.cpp +315 -202
- data/source/bzs/db/protocol/tdap/client/dbDef.h +40 -32
- data/source/bzs/db/protocol/tdap/client/dllmain.cpp +390 -371
- data/source/bzs/db/protocol/tdap/client/errorMessage.cpp +148 -56
- data/source/bzs/db/protocol/tdap/client/errorMessage_ja.cpp +149 -57
- data/source/bzs/db/protocol/tdap/client/export.h +35 -0
- data/source/bzs/db/protocol/tdap/client/field.cpp +1985 -0
- data/source/bzs/db/protocol/tdap/client/field.h +393 -0
- data/source/bzs/db/protocol/tdap/client/fieldDDF.cpp +14 -14
- data/source/bzs/db/protocol/tdap/client/fieldDDF.h +11 -14
- data/source/bzs/db/protocol/tdap/client/fieldNameAlias.cpp +123 -0
- data/source/bzs/db/protocol/tdap/client/fieldNameAlias.h +58 -0
- data/source/bzs/db/protocol/tdap/client/fields.h +178 -0
- data/source/bzs/db/protocol/tdap/client/fileDDF.cpp +13 -16
- data/source/bzs/db/protocol/tdap/client/fileDDF.h +11 -17
- data/source/bzs/db/protocol/tdap/client/filter.h +423 -259
- data/source/bzs/db/protocol/tdap/client/groupComp.h +117 -0
- data/source/bzs/db/protocol/tdap/client/groupQuery.cpp +818 -0
- data/source/bzs/db/protocol/tdap/client/groupQuery.h +281 -0
- data/source/bzs/db/protocol/tdap/client/indexDDF.cpp +14 -17
- data/source/bzs/db/protocol/tdap/client/indexDDF.h +11 -14
- data/source/bzs/db/protocol/tdap/client/memRecord.cpp +231 -0
- data/source/bzs/db/protocol/tdap/client/memRecord.h +145 -0
- data/source/bzs/db/protocol/tdap/client/memRecordset.cpp +448 -0
- data/source/bzs/db/protocol/tdap/client/memRecordset.h +159 -0
- data/source/bzs/db/protocol/tdap/client/nsDatabase.cpp +300 -173
- data/source/bzs/db/protocol/tdap/client/nsDatabase.h +53 -36
- data/source/bzs/db/protocol/tdap/client/nsTable.cpp +171 -128
- data/source/bzs/db/protocol/tdap/client/nsTable.h +121 -87
- data/source/bzs/db/protocol/tdap/client/pooledDatabaseManager.h +173 -0
- data/source/bzs/db/protocol/tdap/client/recordset.cpp +209 -0
- data/source/bzs/db/protocol/tdap/client/recordset.h +86 -0
- data/source/bzs/db/protocol/tdap/client/recordsetImple.h +596 -0
- data/source/bzs/db/protocol/tdap/client/request.h +227 -170
- data/source/bzs/db/protocol/tdap/client/serializer.cpp +1288 -0
- data/source/bzs/db/protocol/tdap/client/serializer.h +295 -0
- data/source/bzs/db/protocol/tdap/client/sharedData.cpp +9 -12
- data/source/bzs/db/protocol/tdap/client/sharedData.h +18 -16
- data/source/bzs/db/protocol/tdap/client/sqlBuilder.cpp +494 -473
- data/source/bzs/db/protocol/tdap/client/sqlBuilder.h +51 -53
- data/source/bzs/db/protocol/tdap/client/stringConverter.h +214 -148
- data/source/bzs/db/protocol/tdap/client/table.cpp +929 -1665
- data/source/bzs/db/protocol/tdap/client/table.h +413 -87
- data/source/bzs/db/protocol/tdap/client/trdboostapi.h +642 -534
- data/source/bzs/db/protocol/tdap/client/trdboostapiInternal.h +25 -40
- data/source/bzs/db/protocol/tdap/client/trdclcppautolink.h +11 -15
- data/source/bzs/db/protocol/tdap/client/trdormapi.h +378 -437
- data/source/bzs/db/protocol/tdap/client/trnsctcl.def +1 -1
- data/source/bzs/db/protocol/tdap/fieldComp.h +127 -0
- data/source/bzs/db/protocol/tdap/myDateTime.cpp +352 -345
- data/source/bzs/db/protocol/tdap/mysql/characterset.cpp +75 -78
- data/source/bzs/db/protocol/tdap/mysql/characterset.h +18 -19
- data/source/bzs/db/protocol/tdap/mysql/databaseSchema.cpp +216 -199
- data/source/bzs/db/protocol/tdap/mysql/databaseSchema.h +23 -14
- data/source/bzs/db/protocol/tdap/mysql/debuglog.cpp +354 -314
- data/source/bzs/db/protocol/tdap/mysql/debuglog.h +57 -47
- data/source/bzs/db/protocol/tdap/mysql/recordsetReader.h +905 -739
- data/source/bzs/db/protocol/tdap/mysql/request.h +152 -159
- data/source/bzs/db/protocol/tdap/mysql/tdapCommandExecuter.cpp +1044 -879
- data/source/bzs/db/protocol/tdap/mysql/tdapCommandExecuter.h +87 -81
- data/source/bzs/db/protocol/tdap/tdapRequest.h +162 -130
- data/source/bzs/db/protocol/tdap/tdapSchema.cpp +368 -166
- data/source/bzs/db/protocol/tdap/tdapSchema.h +702 -566
- data/source/bzs/db/protocol/tdap/tdapcapi.h +387 -353
- data/source/bzs/db/transactd/appBuilderImple.h +21 -20
- data/source/bzs/db/transactd/appModule.cpp +350 -98
- data/source/bzs/db/transactd/appModule.h +31 -37
- data/source/bzs/db/transactd/connManager.cpp +138 -135
- data/source/bzs/db/transactd/connManager.h +28 -21
- data/source/bzs/db/transactd/connectionRecord.h +39 -39
- data/source/bzs/db/transactd/transactd.cpp +217 -203
- data/source/bzs/env/boost_bcb_link.h +131 -0
- data/source/bzs/env/compiler.h +136 -79
- data/source/bzs/env/crosscompile.cpp +57 -57
- data/source/bzs/env/crosscompile.h +130 -115
- data/source/bzs/env/fileopen.h +7 -8
- data/source/bzs/env/mbcswchrLinux.cpp +4 -9
- data/source/bzs/env/mbcswchrLinux.h +37 -34
- data/source/bzs/env/tcharMinGW.h +59 -0
- data/source/bzs/env/tstring.h +90 -95
- data/source/bzs/example/changeSchema.cpp +22 -23
- data/source/bzs/example/changeSchema_c.cpp +22 -24
- data/source/bzs/example/connection_pool_c.cpp +49 -104
- data/source/bzs/example/createDatabase.cpp +40 -47
- data/source/bzs/example/createDatabase_c.cpp +38 -43
- data/source/bzs/example/deleteRecords.cpp +10 -15
- data/source/bzs/example/deleteRecords_c.cpp +10 -14
- data/source/bzs/example/dropDatabase.cpp +3 -9
- data/source/bzs/example/dropDatabase_c.cpp +5 -6
- data/source/bzs/example/insertRecords.cpp +37 -29
- data/source/bzs/example/insertRecords_c.cpp +19 -25
- data/source/bzs/example/ormap_c.cpp +621 -0
- data/source/bzs/example/queryData.cpp +371 -0
- data/source/bzs/example/queryData.h +16 -0
- data/source/bzs/example/query_c.cpp +109 -0
- data/source/bzs/example/readRecords.cpp +27 -27
- data/source/bzs/example/readRecords_c.cpp +25 -23
- data/source/bzs/example/updateRecords.cpp +16 -21
- data/source/bzs/example/updateRecords_c.cpp +8 -12
- data/source/bzs/example/update_with_transaction.cpp +21 -24
- data/source/bzs/example/update_with_transaction_c.cpp +12 -15
- data/source/bzs/example/useORMRecord.cpp +177 -0
- data/source/bzs/netsvc/client/tcpClient.cpp +167 -156
- data/source/bzs/netsvc/client/tcpClient.h +541 -489
- data/source/bzs/netsvc/server/IAppModule.h +119 -32
- data/source/bzs/netsvc/server/iserver.h +21 -23
- data/source/bzs/netsvc/server/serverCpt.cpp +421 -391
- data/source/bzs/netsvc/server/serverCpt.h +41 -43
- data/source/bzs/netsvc/server/serverPipe.cpp +580 -565
- data/source/bzs/netsvc/server/serverPipe.h +44 -45
- data/source/bzs/netsvc/server/serverTpool.cpp +333 -303
- data/source/bzs/netsvc/server/serverTpool.h +38 -43
- data/source/bzs/rtl/benchmark.cpp +91 -31
- data/source/bzs/rtl/benchmark.h +76 -22
- data/source/bzs/rtl/datetime.cpp +231 -233
- data/source/bzs/rtl/datetime.h +16 -16
- data/source/bzs/rtl/debuglog.cpp +48 -51
- data/source/bzs/rtl/debuglog.h +55 -44
- data/source/bzs/rtl/exception.h +55 -48
- data/source/bzs/rtl/stl_uty.cpp +27 -28
- data/source/bzs/rtl/stl_uty.h +28 -29
- data/source/bzs/rtl/stringBuffers.cpp +8 -6
- data/source/bzs/rtl/stringBuffers.h +16 -9
- data/source/bzs/rtl/strtrim.cpp +90 -91
- data/source/bzs/rtl/strtrim.h +14 -16
- data/source/bzs/test/tdclatl/bench_query_atl.js +647 -0
- data/source/bzs/test/tdclatl/bench_tdclatl.js +303 -303
- data/source/bzs/test/tdclatl/test_query_atl.js +669 -0
- data/source/bzs/test/tdclphp/bench.php +357 -0
- data/source/bzs/test/tdclphp/transactd_Test.php +907 -303
- data/source/bzs/test/tdclphp/transactd_blob_Test.php +21 -49
- data/source/bzs/test/tdclphp/transactd_datetime_Test.php +41 -75
- data/source/bzs/test/tdclphp/transactd_kanjischema_Test.php +23 -37
- data/source/bzs/test/tdclphp/transactd_pool_Test.php +120 -0
- data/source/bzs/test/tdclrb/bench_tdclcpp.rb +4 -6
- data/source/bzs/test/tdclrb/prepare.rb +15 -12
- data/source/bzs/test/tdclrb/transactd_blob_spec.rb +29 -32
- data/source/bzs/test/tdclrb/transactd_datetime_spec.rb +0 -29
- data/source/bzs/test/tdclrb/transactd_kanjischema_spec.rb +18 -19
- data/source/bzs/test/tdclrb/transactd_pool_spec.rb +107 -0
- data/source/bzs/test/tdclrb/transactd_spec.rb +734 -142
- data/source/bzs/test/transactdBench/query_bench.cpp +156 -0
- data/source/bzs/test/transactdBench/scaling_bench.cpp +265 -0
- data/source/bzs/test/transactdBench/transactdBench.cpp +107 -83
- data/source/bzs/test/transactdBench/transactdBench2.cpp +122 -83
- data/source/bzs/test/transactdBench/workerBase.cpp +5 -0
- data/source/bzs/test/transactdBench/workerBase.h +88 -0
- data/source/bzs/test/transactdBench/workerMySQLImple.h +333 -0
- data/source/bzs/test/transactdBench/workerTransactdImple.h +201 -0
- data/source/bzs/test/trdclengn/test_blob.cpp +121 -73
- data/source/bzs/test/trdclengn/test_trdclengn.cpp +1244 -426
- data/source/global/ormsrcgen/confParam.h +80 -0
- data/source/global/ormsrcgen/fieldName.cpp +77 -0
- data/source/global/ormsrcgen/fieldName.h +43 -0
- data/source/global/ormsrcgen/main.cpp +196 -0
- data/source/global/ormsrcgen/srcgen.cpp +763 -0
- data/source/global/ormsrcgen/srcgen.h +72 -0
- data/source/global/ormsrcgen/template/fieldNameList_sample.txt +2 -0
- data/source/global/ormsrcgen/template/ormDataClass_template.cpp +48 -0
- data/source/global/ormsrcgen/template/ormDataClass_template.h +34 -0
- data/source/global/ormsrcgen/template/ormMapClass_template.cpp +51 -0
- data/source/global/ormsrcgen/template/ormMapClass_template.h +62 -0
- data/source/global/ormsrcgen/template/template.cnf +38 -0
- data/source/global/querystmts/querystmts.cpp +237 -0
- data/source/global/tdclatl/ConnectParams.cpp +77 -0
- data/source/global/tdclatl/ConnectParams.h +70 -0
- data/source/global/tdclatl/Database.cpp +132 -128
- data/source/global/tdclatl/Database.h +60 -49
- data/source/global/tdclatl/DbDef.cpp +68 -64
- data/source/global/tdclatl/DbDef.h +36 -36
- data/source/global/tdclatl/Field.cpp +12 -17
- data/source/global/tdclatl/Field.h +15 -12
- data/source/global/tdclatl/FieldDef.cpp +75 -36
- data/source/global/tdclatl/FieldDef.h +38 -19
- data/source/global/tdclatl/FieldDefs.cpp +74 -0
- data/source/global/tdclatl/FieldDefs.h +56 -0
- data/source/global/tdclatl/FieldNames.cpp +99 -0
- data/source/global/tdclatl/FieldNames.h +66 -0
- data/source/global/tdclatl/Flags.cpp +75 -37
- data/source/global/tdclatl/Flags.h +13 -12
- data/source/global/tdclatl/GroupQuery.cpp +119 -0
- data/source/global/tdclatl/GroupQuery.h +65 -0
- data/source/global/tdclatl/KeyDef.cpp +15 -14
- data/source/global/tdclatl/KeyDef.h +20 -17
- data/source/global/tdclatl/KeySegment.cpp +13 -12
- data/source/global/tdclatl/PooledDbManager.cpp +223 -0
- data/source/global/tdclatl/PooledDbManager.h +76 -0
- data/source/global/tdclatl/QueryBase.cpp +206 -127
- data/source/global/tdclatl/QueryBase.h +55 -59
- data/source/global/tdclatl/Record.cpp +214 -0
- data/source/global/tdclatl/Record.h +96 -0
- data/source/global/tdclatl/Recordset.cpp +278 -0
- data/source/global/tdclatl/Recordset.h +83 -0
- data/source/global/tdclatl/RecordsetQuery.cpp +118 -0
- data/source/global/tdclatl/RecordsetQuery.h +126 -0
- data/source/global/tdclatl/Table.cpp +57 -60
- data/source/global/tdclatl/Table.h +32 -29
- data/source/global/tdclatl/TableDef.cpp +63 -62
- data/source/global/tdclatl/TableDef.h +20 -22
- data/source/global/tdclatl/TdVersion.cpp +3 -3
- data/source/global/tdclatl/TdVersion.h +15 -11
- data/source/global/tdclatl/_IDatabaseEvents_CP.h +99 -92
- data/source/global/tdclatl/activeTable.cpp +355 -0
- data/source/global/tdclatl/activeTable.h +79 -0
- data/source/global/tdclatl/dllmain.cpp +4 -3
- data/source/global/tdclatl/dllmain.h +7 -6
- data/source/global/tdclatl/keySegment.h +22 -18
- data/source/global/tdclatl/resource.h +0 -0
- data/source/global/tdclatl/stdafx.h +6 -4
- data/source/global/tdclatl/targetver.h +0 -1
- data/source/global/tdclatl/tdclatl.cpp +10 -5
- data/source/global/tdclatl/tdclatl.idl +530 -14
- data/source/linux/charsetConvert.h +78 -79
- data/source/linux/linuxTypes.h +9 -12
- data/source/linux/tchar.h +168 -166
- data/transactd.gemspec +24 -16
- metadata +98 -12
- data/bin/common/tdclc_32_1_2.dll +0 -0
- data/bin/common/tdclc_64_1_2.dll +0 -0
- data/build/tdclc/tdclc_32.cbproj +0 -173
- data/build/tdclcpp/tdclcpp_bcb_32.cbproj +0 -232
- data/build/tdclrb/GEM_VERSION +0 -3
- data/source/bzs/db/protocol/tdap/client/filter.cpp +0 -43
- data/source/bzs/example/useORM.cpp +0 -585
|
@@ -1,35 +1,32 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
/* =================================================================
|
|
2
|
+
Copyright (C) 2012 2013 BizStation Corp All rights reserved.
|
|
3
3
|
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
4
|
+
This program is free software; you can redistribute it and/or
|
|
5
|
+
modify it under the terms of the GNU General Public License
|
|
6
|
+
as published by the Free Software Foundation; either version 2
|
|
7
|
+
of the License, or (at your option) any later version.
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
9
|
+
This program is distributed in the hope that it will be useful,
|
|
10
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
11
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
12
|
+
GNU General Public License for more details.
|
|
13
13
|
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
14
|
+
You should have received a copy of the GNU General Public License
|
|
15
|
+
along with this program; if not, write to the Free Software
|
|
16
|
+
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
|
17
|
+
02111-1307, USA.
|
|
18
|
+
================================================================= */
|
|
19
19
|
|
|
20
20
|
#include "database.h"
|
|
21
21
|
#include <boost/bind.hpp>
|
|
22
22
|
#include "IReadRecords.h"
|
|
23
23
|
#include "percentageKey.h"
|
|
24
|
-
|
|
25
24
|
#include "mydebuglog.h"
|
|
26
|
-
|
|
27
25
|
#include "mysqlThd.h"
|
|
28
26
|
#include "bookmark.h"
|
|
29
27
|
#include <bzs/rtl/stl_uty.h>
|
|
30
28
|
#include <boost/shared_array.hpp>
|
|
31
29
|
|
|
32
|
-
extern int g_useBtrvVariableTable;
|
|
33
30
|
namespace bzs
|
|
34
31
|
{
|
|
35
32
|
namespace db
|
|
@@ -41,1438 +38,1624 @@ namespace mysql
|
|
|
41
38
|
|
|
42
39
|
using namespace std;
|
|
43
40
|
|
|
41
|
+
#define KEYLEN_ALLCOPY 0
|
|
42
|
+
#define OPEN_TABLE_TIMEOUT_SEC 2
|
|
44
43
|
|
|
45
|
-
unsigned int hash(const char
|
|
44
|
+
unsigned int hash(const char* s, size_t len)
|
|
46
45
|
{
|
|
47
46
|
unsigned int h = 0;
|
|
48
|
-
for (size_t i=0;i < len; i++)
|
|
49
|
-
h = h * 137 + *(s+i);
|
|
50
|
-
|
|
47
|
+
for (size_t i = 0; i < len; i++)
|
|
48
|
+
h = h * 137 + *(s + i);
|
|
49
|
+
return h % 1987;
|
|
51
50
|
}
|
|
52
51
|
|
|
53
52
|
tableCacheCounter::tableCacheCounter()
|
|
54
53
|
{
|
|
55
|
-
|
|
56
54
|
}
|
|
57
55
|
|
|
58
|
-
int tableCacheCounter::getHash(const std::string& dbname,
|
|
56
|
+
int tableCacheCounter::getHash(const std::string& dbname,
|
|
57
|
+
const std::string& tbname)
|
|
59
58
|
{
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
59
|
+
char tmp[256];
|
|
60
|
+
sprintf_s(tmp, 256, "%s%s", dbname.c_str(), tbname.c_str());
|
|
61
|
+
return hash(tmp, strlen(tmp));
|
|
63
62
|
}
|
|
64
63
|
|
|
65
|
-
size_t tableCacheCounter::getCounterIndex(const std::string& dbname,
|
|
64
|
+
size_t tableCacheCounter::getCounterIndex(const std::string& dbname,
|
|
65
|
+
const std::string& tbname)
|
|
66
66
|
{
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
67
|
+
int h = getHash(dbname, tbname);
|
|
68
|
+
vector<int>::iterator pos = find(m_tables.begin(), m_tables.end(), h);
|
|
69
|
+
if (pos == m_tables.end())
|
|
70
|
+
{
|
|
71
|
+
m_tables.push_back(h);
|
|
72
|
+
m_counts.push_back(0);
|
|
73
|
+
return m_counts.size() - 1;
|
|
74
|
+
}
|
|
75
|
+
return pos - m_tables.begin();
|
|
76
76
|
}
|
|
77
77
|
|
|
78
|
-
void tableCacheCounter::addref(const std::string& dbname,
|
|
78
|
+
void tableCacheCounter::addref(const std::string& dbname,
|
|
79
|
+
const std::string& tbname)
|
|
79
80
|
{
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
81
|
+
|
|
82
|
+
boost::mutex::scoped_lock lck(m_mutex);
|
|
83
|
+
size_t pos = getCounterIndex(dbname, tbname);
|
|
84
|
+
++m_counts[pos];
|
|
84
85
|
}
|
|
85
86
|
|
|
86
|
-
int tableCacheCounter::count(const std::string& dbname,
|
|
87
|
+
int tableCacheCounter::count(const std::string& dbname,
|
|
88
|
+
const std::string& tbname)
|
|
87
89
|
{
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
90
|
+
boost::mutex::scoped_lock lck(m_mutex);
|
|
91
|
+
size_t pos = getCounterIndex(dbname, tbname);
|
|
92
|
+
return m_counts[pos];
|
|
91
93
|
}
|
|
92
94
|
|
|
93
|
-
void tableCacheCounter::release(const std::string& dbname,
|
|
95
|
+
void tableCacheCounter::release(const std::string& dbname,
|
|
96
|
+
const std::string& tbname)
|
|
94
97
|
{
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
+
boost::mutex::scoped_lock lck(m_mutex);
|
|
99
|
+
size_t pos = getCounterIndex(dbname, tbname);
|
|
100
|
+
--m_counts[pos];
|
|
98
101
|
}
|
|
99
102
|
|
|
100
|
-
#define KEYLEN_ALLCOPY 0
|
|
101
|
-
#define OPEN_TABLE_TIMEOUT_SEC 2
|
|
102
|
-
|
|
103
103
|
void lockTable(THD* thd, TABLE* tb)
|
|
104
104
|
{
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
MYSQL_LOCK *lockMrg=NULL;
|
|
105
|
+
bool append = (thd->lock != 0);
|
|
106
|
+
thd->in_lock_tables = 1;
|
|
108
107
|
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
108
|
+
MYSQL_LOCK* lock = mysql_lock_tables(thd, &tb, 1, 0);
|
|
109
|
+
if (!append)
|
|
110
|
+
thd->lock = lock;
|
|
111
|
+
else if (lock)
|
|
112
|
+
{
|
|
113
|
+
MYSQL_LOCK* lockMrg = mysql_lock_merge(thd->lock, lock);
|
|
114
|
+
if (lockMrg)
|
|
115
|
+
thd->lock = lockMrg;
|
|
116
|
+
}
|
|
117
|
+
thd->in_lock_tables = 0;
|
|
118
|
+
DEBUG_WRITELOG_SP1("LOCK TABLE table =%s\n", tb->s->table_name.str);
|
|
120
119
|
|
|
121
|
-
|
|
120
|
+
return;
|
|
122
121
|
}
|
|
123
122
|
|
|
124
|
-
/** The present lock type is returned.
|
|
123
|
+
/** The present lock type is returned.
|
|
125
124
|
* The true lock type of innodb is controlled by m_thd->lex->sql_command.
|
|
126
125
|
*/
|
|
127
126
|
thr_lock_type locktype(bool trn, enum_sql_command cmd)
|
|
128
127
|
{
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
return lock_type;
|
|
128
|
+
if (trn)
|
|
129
|
+
return TL_WRITE;
|
|
130
|
+
thr_lock_type lock_type = TL_READ;
|
|
131
|
+
switch (cmd)
|
|
132
|
+
{
|
|
133
|
+
case SQLCOM_INSERT:
|
|
134
|
+
case SQLCOM_DELETE:
|
|
135
|
+
case SQLCOM_UPDATE:
|
|
136
|
+
case SQLCOM_DROP_TABLE:
|
|
137
|
+
case SQLCOM_CREATE_TABLE:
|
|
138
|
+
case SQLCOM_CREATE_INDEX:
|
|
139
|
+
lock_type = TL_WRITE;
|
|
140
|
+
default:
|
|
141
|
+
break;
|
|
142
|
+
}
|
|
143
|
+
return lock_type;
|
|
146
144
|
}
|
|
147
145
|
|
|
148
146
|
bool unlockTables(bool releaseStatementLock, THD* thd, bool rollback)
|
|
149
147
|
{
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
148
|
+
if (thd->lock)
|
|
149
|
+
{
|
|
150
|
+
bool ret;
|
|
151
|
+
if (rollback)
|
|
152
|
+
ret = trans_rollback_stmt(thd);
|
|
153
|
+
else
|
|
154
|
+
ret = trans_commit_stmt(thd);
|
|
155
|
+
if (releaseStatementLock)
|
|
156
|
+
thd->mdl_context.release_statement_locks();
|
|
157
|
+
mysql_unlock_tables(thd, thd->lock);
|
|
158
|
+
thd->lock = 0;
|
|
159
|
+
return !ret;
|
|
160
|
+
}
|
|
161
|
+
return false;
|
|
165
162
|
}
|
|
166
163
|
|
|
167
164
|
#ifdef _MSC_VER
|
|
168
|
-
#pragma warning(disable:4355)
|
|
165
|
+
#pragma warning(disable : 4355)
|
|
169
166
|
#endif
|
|
170
167
|
|
|
171
|
-
|
|
172
|
-
bool g_safe_share_mode=false;
|
|
168
|
+
bool g_safe_share_mode = false;
|
|
173
169
|
tableCacheCounter database::tableRef;
|
|
174
170
|
|
|
175
171
|
database::database(const char* name, short cid)
|
|
176
|
-
|
|
177
|
-
|
|
172
|
+
: m_dbname(name), m_thd(createThdForThread()), m_cid(cid),
|
|
173
|
+
m_inTransaction(0), m_inSnapshot(0), m_trnType(0)
|
|
178
174
|
{
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
175
|
+
m_thd->security_ctx->skip_grants();
|
|
184
176
|
}
|
|
185
177
|
|
|
186
178
|
#ifdef _MSC_VER
|
|
187
|
-
#pragma warning(default:4355)
|
|
188
|
-
#endif
|
|
179
|
+
#pragma warning(default : 4355)
|
|
180
|
+
#endif
|
|
189
181
|
|
|
190
182
|
database::~database()
|
|
191
183
|
{
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
184
|
+
use();
|
|
185
|
+
unUseTables(false);
|
|
186
|
+
closeForReopen();
|
|
187
|
+
m_tables.clear(); // It clears ahead of the destructor of m_trn.
|
|
188
|
+
deleteThdForThread(m_thd);
|
|
197
189
|
}
|
|
198
190
|
|
|
199
191
|
void database::use() const
|
|
200
192
|
{
|
|
201
|
-
|
|
202
|
-
|
|
193
|
+
attachThd(m_thd);
|
|
194
|
+
m_thd->clear_error();
|
|
203
195
|
}
|
|
204
196
|
|
|
205
197
|
// locktable
|
|
206
198
|
table* database::useTable(int index, enum_sql_command cmd)
|
|
207
199
|
{
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
200
|
+
if (index >= (int)m_tables.size())
|
|
201
|
+
THROW_BZS_ERROR_WITH_CODEMSG(1, "Invalid table id.");
|
|
202
|
+
|
|
203
|
+
table* tb = m_tables[index].get();
|
|
204
|
+
if (tb == NULL)
|
|
205
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_FILE_NOT_OPENED,
|
|
206
|
+
"Invalid table id.");
|
|
207
|
+
|
|
208
|
+
if (tb->m_blobBuffer)
|
|
209
|
+
tb->m_blobBuffer->clear();
|
|
210
|
+
if (tb->islocked())
|
|
211
|
+
{
|
|
212
|
+
if (tb->m_table == NULL)
|
|
213
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_FILE_NOT_OPENED,
|
|
214
|
+
"Invalid table id.");
|
|
215
|
+
return tb;
|
|
216
|
+
}
|
|
217
|
+
if (g_safe_share_mode && tb->m_table == NULL)
|
|
218
|
+
reopen();
|
|
219
|
+
if (tb->m_table == NULL)
|
|
220
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_FILE_NOT_OPENED,
|
|
221
|
+
"Invalid table id.");
|
|
222
|
+
bool trn = ((m_inTransaction > 0) & (tb->mode() != TD_OPEN_READONLY));
|
|
223
|
+
tb->m_table->reginfo.lock_type = locktype(trn, cmd);
|
|
224
|
+
if ((tb->mode() == TD_OPEN_READONLY) &&
|
|
225
|
+
(tb->m_table->reginfo.lock_type == TL_WRITE))
|
|
226
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_ACCESS_DENIED, "Access denined.");
|
|
227
|
+
if (m_thd->lock == 0)
|
|
228
|
+
{
|
|
229
|
+
m_thd->lex->sql_command = cmd;
|
|
230
|
+
m_thd->tx_isolation = (enum_tx_isolation)m_thd->variables.tx_isolation;
|
|
231
|
+
cp_thd_set_read_only(m_thd);
|
|
232
|
+
}
|
|
233
|
+
lockTable(m_thd, tb->m_table);
|
|
234
|
+
|
|
235
|
+
if ((tb->m_table->reginfo.lock_type == TL_WRITE) &&
|
|
236
|
+
(m_thd->variables.sql_log_bin))
|
|
237
|
+
m_thd->set_current_stmt_binlog_format_row();
|
|
238
|
+
tb->setLocked(true);
|
|
239
|
+
if (g_safe_share_mode)
|
|
240
|
+
{
|
|
241
|
+
int ret = 0;
|
|
242
|
+
tb->m_keyconv.setKey(tb->m_table->key_info);
|
|
243
|
+
if (tb->keyNum() >= 0)
|
|
244
|
+
ret =
|
|
245
|
+
tb->m_table->file->ha_index_init(tb->keyNum(), 1 /* sorted */);
|
|
246
|
+
else if (tb->keyNum() == -2)
|
|
247
|
+
ret = tb->m_table->file->ha_rnd_init(false);
|
|
248
|
+
if (ret)
|
|
249
|
+
THROW_BZS_ERROR_WITH_CODEMSG(ERROR_INDEX_RND_INIT,
|
|
250
|
+
"UseTable index_init error.");
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
return tb;
|
|
253
254
|
}
|
|
254
255
|
|
|
255
256
|
void database::unUseTable(table* tb)
|
|
256
257
|
{
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
258
|
+
if (tb->islocked() && (m_inTransaction + m_inSnapshot == 0))
|
|
259
|
+
{ // Only this table is lock release.
|
|
260
|
+
bool needUnlock =
|
|
261
|
+
(locktype(false, m_thd->lex->sql_command) == TL_WRITE);
|
|
262
|
+
bool changed = tb->isChanged();
|
|
263
|
+
tb->resetTransctionInfo(m_thd);
|
|
264
|
+
bool rollback = (!changed && needUnlock);
|
|
265
|
+
if (unlockTables(needUnlock, m_thd, rollback))
|
|
266
|
+
{
|
|
267
|
+
DEBUG_WRITELOG_SP1("UNLOCK TABLE table =%s\n",
|
|
268
|
+
tb->m_table->s->table_name.str);
|
|
269
|
+
}
|
|
270
|
+
else
|
|
271
|
+
{
|
|
272
|
+
DEBUG_WRITELOG_SP1("UNLOCK TABLE ERROR table =%s\n",
|
|
273
|
+
tb->m_table->s->table_name.str);
|
|
274
|
+
if (m_thd->is_error())
|
|
275
|
+
{
|
|
276
|
+
|
|
277
|
+
if (ER_LOCK_WAIT_TIMEOUT == m_thd->cp_get_sql_error())
|
|
278
|
+
m_stat = STATUS_CANNOT_LOCK_TABLE;
|
|
279
|
+
else
|
|
280
|
+
m_stat = m_thd->cp_get_sql_error();
|
|
281
|
+
THROW_BZS_ERROR_WITH_CODEMSG(m_stat,
|
|
282
|
+
"Transaction commit error.");
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
if (g_safe_share_mode)
|
|
286
|
+
{
|
|
287
|
+
unUseTables(false);
|
|
288
|
+
closeForReopen();
|
|
289
|
+
}
|
|
290
|
+
}
|
|
286
291
|
}
|
|
287
292
|
|
|
288
293
|
void database::unUseTables(bool rollback)
|
|
289
294
|
{
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
295
|
+
// All the table lock release
|
|
296
|
+
bool needUnlock =
|
|
297
|
+
(locktype((m_inTransaction > 0), m_thd->lex->sql_command) == TL_WRITE);
|
|
298
|
+
m_inTransaction = 0;
|
|
299
|
+
m_inSnapshot = 0;
|
|
300
|
+
for (int i = 0; i < (int)m_tables.size(); i++)
|
|
301
|
+
{
|
|
302
|
+
if (m_tables[i])
|
|
303
|
+
m_tables[i]->resetTransctionInfo(m_thd);
|
|
304
|
+
}
|
|
305
|
+
if (unlockTables(needUnlock, m_thd, rollback))
|
|
306
|
+
{
|
|
307
|
+
DEBUG_WRITELOG("UNLOCK TABLES \n")
|
|
308
|
+
}
|
|
309
|
+
else
|
|
310
|
+
{
|
|
311
|
+
if (m_thd->is_error())
|
|
312
|
+
{
|
|
313
|
+
DEBUG_WRITELOG("UNLOCK TABLES ERROR \n");
|
|
314
|
+
if (ER_LOCK_WAIT_TIMEOUT == m_thd->cp_get_sql_error())
|
|
315
|
+
m_stat = STATUS_CANNOT_LOCK_TABLE;
|
|
316
|
+
else
|
|
317
|
+
m_stat = m_thd->cp_get_sql_error();
|
|
318
|
+
THROW_BZS_ERROR_WITH_CODEMSG(m_stat, "Transaction commit error.");
|
|
319
|
+
}
|
|
320
|
+
}
|
|
321
|
+
if (g_safe_share_mode)
|
|
322
|
+
closeForReopen();
|
|
318
323
|
}
|
|
319
324
|
|
|
320
325
|
bool database::beginTrn(short type)
|
|
321
326
|
{
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
327
|
+
++m_inTransaction;
|
|
328
|
+
if (m_inTransaction == 1)
|
|
329
|
+
{
|
|
330
|
+
m_trnType = type;
|
|
331
|
+
return true;
|
|
332
|
+
}
|
|
333
|
+
return false;
|
|
329
334
|
}
|
|
330
335
|
|
|
331
336
|
bool database::commitTrn()
|
|
332
337
|
{
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
338
|
+
if (m_inTransaction > 0)
|
|
339
|
+
{
|
|
340
|
+
--m_inTransaction;
|
|
341
|
+
if (m_inTransaction == 0)
|
|
342
|
+
unUseTables(false);
|
|
343
|
+
}
|
|
344
|
+
return (m_inTransaction == 0);
|
|
340
345
|
}
|
|
341
346
|
|
|
342
347
|
bool database::abortTrn()
|
|
343
348
|
{
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
349
|
+
if (m_inTransaction > 0)
|
|
350
|
+
{
|
|
351
|
+
--m_inTransaction;
|
|
352
|
+
if (m_inTransaction == 0)
|
|
353
|
+
unUseTables(true);
|
|
354
|
+
}
|
|
355
|
+
return (m_inTransaction == 0);
|
|
351
356
|
}
|
|
352
357
|
|
|
353
358
|
bool database::beginSnapshot()
|
|
354
359
|
{
|
|
355
|
-
|
|
356
|
-
|
|
360
|
+
++m_inSnapshot;
|
|
361
|
+
return (m_inSnapshot == 1);
|
|
357
362
|
}
|
|
358
363
|
|
|
359
364
|
bool database::endSnapshot()
|
|
360
365
|
{
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
366
|
+
if (m_inSnapshot > 0)
|
|
367
|
+
{
|
|
368
|
+
--m_inSnapshot;
|
|
369
|
+
if (m_inSnapshot == 0)
|
|
370
|
+
unUseTables(false);
|
|
371
|
+
}
|
|
372
|
+
return (m_inSnapshot == 0);
|
|
368
373
|
}
|
|
369
374
|
|
|
370
|
-
/** Metadata lock, a table name is case-sensitive
|
|
375
|
+
/** Metadata lock, a table name is case-sensitive
|
|
371
376
|
* However, in actual opening, it is not distinguished at Windows.
|
|
372
377
|
*/
|
|
373
|
-
TABLE* database::doOpenTable(const std::string& name, short mode,
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
378
|
+
TABLE* database::doOpenTable(const std::string& name, short mode,
|
|
379
|
+
const char* ownerName)
|
|
380
|
+
{
|
|
381
|
+
TABLE_LIST tables;
|
|
382
|
+
m_thd->variables.lock_wait_timeout = OPEN_TABLE_TIMEOUT_SEC;
|
|
383
|
+
enum_mdl_type type_arg =
|
|
384
|
+
(mode == TD_OPEN_EXCLUSIVE) ? MDL_EXCLUSIVE : MDL_SHARED_READ;
|
|
385
|
+
thr_lock_type locltype = (mode == TD_OPEN_EXCLUSIVE) ? TL_WRITE : TL_READ;
|
|
386
|
+
tables.init_one_table(m_dbname.c_str(), m_dbname.size(), name.c_str(),
|
|
387
|
+
name.size(), name.c_str(), locltype);
|
|
388
|
+
tables.mdl_request.set_type(type_arg);
|
|
389
|
+
|
|
390
|
+
Open_table_context ot_act(m_thd, MYSQL_OPEN_GET_NEW_TABLE);
|
|
391
|
+
m_thd->cp_set_overwrite_status(true);
|
|
392
|
+
if (cp_open_table(m_thd, &tables, &ot_act))
|
|
393
|
+
{
|
|
394
|
+
m_stat = STATUS_TABLE_NOTOPEN;
|
|
395
|
+
if (ER_LOCK_WAIT_TIMEOUT == m_thd->cp_get_sql_error())
|
|
396
|
+
m_stat = STATUS_CANNOT_LOCK_TABLE;
|
|
397
|
+
THROW_BZS_ERROR_WITH_CODEMSG(m_stat, name.c_str());
|
|
398
|
+
}
|
|
399
|
+
|
|
400
|
+
// Check owner name
|
|
401
|
+
if (ownerName && ownerName[0])
|
|
402
|
+
{
|
|
403
|
+
const char* p = tables.table->s->comment.str;
|
|
404
|
+
if ((p[0] == '%') && (p[1] == '@') && (p[2] == '%'))
|
|
405
|
+
{
|
|
406
|
+
int readNoNeed = p[3] - '0';
|
|
407
|
+
if ((mode == TD_OPEN_READONLY) && readNoNeed)
|
|
408
|
+
;
|
|
409
|
+
else if (strcmp(p + 4, ownerName))
|
|
410
|
+
{
|
|
411
|
+
m_stat = STATUS_INVALID_OWNERNAME;
|
|
412
|
+
return NULL;
|
|
413
|
+
}
|
|
414
|
+
}
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
tables.table->use_all_columns();
|
|
418
|
+
tables.table->open_by_handler = 1;
|
|
411
419
|
#if (defined(DEBUG) && defined(WIN32))
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
420
|
+
char buf[10];
|
|
421
|
+
sprintf(buf, "%d", tables.table->field[1]->key_length());
|
|
422
|
+
OutputDebugString(buf);
|
|
415
423
|
#endif
|
|
416
|
-
|
|
424
|
+
return tables.table;
|
|
417
425
|
}
|
|
418
426
|
|
|
419
|
-
table* database::openTable(const std::string& name, short mode,
|
|
427
|
+
table* database::openTable(const std::string& name, short mode,
|
|
428
|
+
const char* ownerName)
|
|
420
429
|
{
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
430
|
+
if (existsTable(name))
|
|
431
|
+
{
|
|
432
|
+
|
|
433
|
+
TABLE* t = doOpenTable(name, mode, ownerName);
|
|
434
|
+
if (t)
|
|
435
|
+
{
|
|
436
|
+
boost::shared_ptr<table> tb(
|
|
437
|
+
new table(t, *this, name, mode, (int)m_tables.size()));
|
|
438
|
+
m_tables.push_back(tb);
|
|
439
|
+
m_stat = STATUS_SUCCESS;
|
|
440
|
+
tableRef.addref(m_dbname, name); // addef first then table open.
|
|
441
|
+
return tb.get();
|
|
442
|
+
}
|
|
443
|
+
return NULL;
|
|
444
|
+
}
|
|
445
|
+
m_stat = STATUS_TABLE_NOTOPEN;
|
|
446
|
+
THROW_BZS_ERROR_WITH_CODEMSG(m_stat, name.c_str());
|
|
436
447
|
}
|
|
437
448
|
|
|
438
449
|
void database::closeTable(const std::string& name, bool drop)
|
|
439
450
|
{
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
451
|
+
for (int i = (int)m_tables.size() - 1; i >= 0; i--)
|
|
452
|
+
{
|
|
453
|
+
if (m_tables[i] && (m_tables[i]->m_name == name))
|
|
454
|
+
{
|
|
455
|
+
closeTable(m_tables[i].get());
|
|
456
|
+
return;
|
|
457
|
+
}
|
|
458
|
+
}
|
|
459
|
+
}
|
|
460
|
+
|
|
461
|
+
int tableUseCount(const std::vector<boost::shared_ptr<table> >& tables,
|
|
462
|
+
const char* name)
|
|
463
|
+
{
|
|
464
|
+
int ret = 0;
|
|
465
|
+
for (int i = (int)tables.size() - 1; i >= 0; i--)
|
|
466
|
+
{
|
|
467
|
+
if (tables[i] && (tables[i]->name() == name))
|
|
468
|
+
++ret;
|
|
469
|
+
}
|
|
470
|
+
return ret;
|
|
448
471
|
}
|
|
449
472
|
|
|
450
473
|
void database::closeTable(table* tb)
|
|
451
474
|
{
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
475
|
+
for (int i = (int)m_tables.size() - 1; i >= 0; i--)
|
|
476
|
+
{
|
|
477
|
+
if (m_tables[i] && (m_tables[i].get() == tb))
|
|
478
|
+
{
|
|
479
|
+
short mode = tb->m_mode;
|
|
480
|
+
TABLE* src = tb->m_table;
|
|
481
|
+
|
|
482
|
+
unUseTable(m_tables[i].get());
|
|
483
|
+
m_tables[i].reset();
|
|
484
|
+
if (mode == TD_OPEN_EXCLUSIVE)
|
|
485
|
+
{
|
|
486
|
+
if (tableUseCount(m_tables, src->s->table_name.str) == 1)
|
|
487
|
+
{
|
|
488
|
+
for (TABLE** tbl = &m_thd->open_tables; *tbl != 0;
|
|
489
|
+
*tbl = (*tbl)->next)
|
|
490
|
+
{
|
|
491
|
+
if (*tbl == src)
|
|
492
|
+
{
|
|
493
|
+
TABLE* tbptr = (*tbl);
|
|
494
|
+
MDL_ticket* tc = tbptr->mdl_ticket;
|
|
495
|
+
close_thread_table(m_thd, tbl);
|
|
496
|
+
m_thd->mdl_context
|
|
497
|
+
.set_explicit_duration_for_all_locks();
|
|
498
|
+
m_thd->mdl_context.release_all_locks_for_name(tc);
|
|
499
|
+
m_thd->mdl_context
|
|
500
|
+
.set_transaction_duration_for_all_locks();
|
|
501
|
+
}
|
|
502
|
+
break;
|
|
503
|
+
}
|
|
504
|
+
}
|
|
505
|
+
}
|
|
506
|
+
|
|
507
|
+
DEBUG_WRITELOG_SP1("CLOSE TABLE table id=%d \n", i);
|
|
508
|
+
}
|
|
509
|
+
}
|
|
460
510
|
}
|
|
461
511
|
|
|
462
512
|
void database::closeForReopen()
|
|
463
513
|
{
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
514
|
+
// A transaction is committed compulsorily.
|
|
515
|
+
|
|
516
|
+
for (size_t i = 0; i < m_tables.size(); i++)
|
|
517
|
+
{
|
|
518
|
+
if (m_tables[i] && (m_tables[i]->m_table != NULL))
|
|
519
|
+
m_tables[i]->resetInternalTable(NULL);
|
|
520
|
+
}
|
|
471
521
|
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
522
|
+
trans_commit_stmt(m_thd);
|
|
523
|
+
if (m_thd->mdl_context.has_locks())
|
|
524
|
+
close_thread_tables(m_thd);
|
|
525
|
+
m_thd->mdl_context.release_transactional_locks();
|
|
526
|
+
// It is certainly after close_thread_tables.
|
|
476
527
|
}
|
|
477
528
|
|
|
478
529
|
void database::reopen()
|
|
479
530
|
{
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
531
|
+
for (size_t i = 0; i < m_tables.size(); i++)
|
|
532
|
+
{
|
|
533
|
+
if (m_tables[i] && (m_tables[i]->m_table == NULL))
|
|
534
|
+
{
|
|
535
|
+
TABLE* table = doOpenTable(m_tables[i]->m_name.c_str(),
|
|
536
|
+
m_tables[i]->m_mode, NULL);
|
|
537
|
+
if (table)
|
|
538
|
+
m_tables[i]->resetInternalTable(table);
|
|
539
|
+
else
|
|
540
|
+
m_tables[i].reset();
|
|
541
|
+
}
|
|
542
|
+
}
|
|
491
543
|
}
|
|
492
544
|
|
|
493
545
|
bool database::existsTable(const std::string& name)
|
|
494
546
|
{
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
547
|
+
char tmp[FN_REFLEN + 1];
|
|
548
|
+
|
|
549
|
+
build_table_filename(tmp, sizeof(tmp) - 1, m_dbname.c_str(), name.c_str(),
|
|
550
|
+
reg_ext, 0);
|
|
551
|
+
MY_STAT st;
|
|
552
|
+
if (mysql_file_stat(0, tmp, &st, MYF(0)))
|
|
553
|
+
return true;
|
|
554
|
+
return false;
|
|
504
555
|
}
|
|
505
556
|
|
|
506
557
|
bool database::existsDatabase()
|
|
507
558
|
{
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
559
|
+
char tmp[FN_REFLEN + 1];
|
|
560
|
+
size_t len =
|
|
561
|
+
build_table_filename(tmp, sizeof(tmp) - 1, m_dbname.c_str(), "", "", 0);
|
|
562
|
+
tmp[len - 1] = 0x00;
|
|
511
563
|
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
564
|
+
MY_STAT stat;
|
|
565
|
+
if (mysql_file_stat(0, tmp, &stat, MYF(0)))
|
|
566
|
+
return true;
|
|
567
|
+
return false;
|
|
516
568
|
}
|
|
517
569
|
|
|
518
570
|
class autoincSetup
|
|
519
571
|
{
|
|
520
|
-
|
|
572
|
+
TABLE* m_table;
|
|
573
|
+
|
|
521
574
|
public:
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
m_table->next_number_field = 0;
|
|
529
|
-
}
|
|
575
|
+
autoincSetup(TABLE* table) : m_table(table)
|
|
576
|
+
{
|
|
577
|
+
m_table->next_number_field = m_table->found_next_number_field;
|
|
578
|
+
}
|
|
579
|
+
|
|
580
|
+
~autoincSetup() { m_table->next_number_field = 0; }
|
|
530
581
|
};
|
|
531
582
|
|
|
532
583
|
/** Number of NIS fields
|
|
533
584
|
*/
|
|
534
585
|
unsigned short nisFieldNum(TABLE* tb)
|
|
535
586
|
{
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
587
|
+
if (tb->s->null_fields)
|
|
588
|
+
{
|
|
589
|
+
int offset = 1;
|
|
590
|
+
|
|
591
|
+
for (int i = tb->s->fields - offset; i >= 0; --i)
|
|
592
|
+
if (isNisField(tb->s->field[i]->field_name) == false)
|
|
593
|
+
return (unsigned short)(tb->s->fields - i - offset);
|
|
594
|
+
return tb->s->fields;
|
|
595
|
+
}
|
|
596
|
+
|
|
597
|
+
return 0;
|
|
547
598
|
}
|
|
548
599
|
|
|
549
600
|
bool table::noKeybufResult = true;
|
|
550
601
|
|
|
551
|
-
table::table(TABLE* myTable, database& db, const std::string& name, short mode,
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
602
|
+
table::table(TABLE* myTable, database& db, const std::string& name, short mode,
|
|
603
|
+
int id)
|
|
604
|
+
: m_table(myTable), m_name(name), m_mode(mode), m_id(id), m_db(db),
|
|
605
|
+
m_keyNum(-1), m_keybuf(new unsigned char[MAX_KEYLEN]),
|
|
606
|
+
m_nonNccKeybuf(new unsigned char[MAX_KEYLEN]), m_nonNcc(false), m_stat(0),
|
|
607
|
+
m_validCursor(true), m_cursor(false), m_locked(false), m_changed(false),
|
|
608
|
+
m_nounlock(false), m_bulkInserting(false),
|
|
609
|
+
m_keyconv(m_table->key_info, m_table->s->keys), m_blobBuffer(NULL)
|
|
610
|
+
|
|
611
|
+
{
|
|
612
|
+
|
|
613
|
+
m_table->read_set = &m_table->s->all_set;
|
|
614
|
+
|
|
615
|
+
m_recordFormatType = RF_VALIABLE_LEN;
|
|
616
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
617
|
+
m_lastVarLenBytes = 0;
|
|
618
|
+
#endif
|
|
619
|
+
// Is the Nis field included or not?
|
|
620
|
+
m_nullFields = nisFieldNum(m_table);
|
|
621
|
+
|
|
622
|
+
if (m_table->s->varchar_fields + m_table->s->blob_fields == 0)
|
|
623
|
+
m_recordFormatType = RF_FIXED_LEN;
|
|
624
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
625
|
+
else if (m_table->s->varchar_fields == 1)
|
|
626
|
+
{
|
|
627
|
+
Field** fd = m_table->field + lastVarFiledNum();
|
|
628
|
+
if (isVarType((*fd)->type()) && ((*fd)->part_of_key.is_clear_all()) &&
|
|
629
|
+
((*fd)->key_start.is_clear_all()) &&
|
|
630
|
+
(((*fd)->charset()) == &my_charset_bin))
|
|
631
|
+
{
|
|
632
|
+
m_recordFormatType = RF_FIXED_PLUS_VALIABLE_LEN;
|
|
633
|
+
|
|
634
|
+
/* The number of bytes of the length area of the last VAR field */
|
|
635
|
+
m_lastVarLenBytes = lastVarFiled()->field_length < 256 ? 1 : 2;
|
|
636
|
+
}
|
|
637
|
+
}
|
|
638
|
+
#endif
|
|
639
|
+
if (m_nullFields)
|
|
640
|
+
m_recordFormatType |= RF_INCLUDE_NIS;
|
|
641
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
642
|
+
m_recordLenCl = (uint)(m_table->s->reclength - m_table->s->null_bytes -
|
|
643
|
+
m_nullFields - m_lastVarLenBytes);
|
|
644
|
+
#else
|
|
645
|
+
m_recordLenCl =
|
|
646
|
+
(uint)(m_table->s->reclength - m_table->s->null_bytes - m_nullFields);
|
|
647
|
+
#endif
|
|
648
|
+
// Chash null field
|
|
649
|
+
if (m_table->s->null_fields)
|
|
650
|
+
{
|
|
651
|
+
for (int i = 0; i < (int)m_table->s->fields; ++i)
|
|
652
|
+
{
|
|
653
|
+
Field* fd = m_table->field[i];
|
|
654
|
+
if (fd->null_bit && fd->part_of_key.is_clear_all())
|
|
655
|
+
m_nonKeySegNullFields.push_back(fd);
|
|
656
|
+
}
|
|
657
|
+
}
|
|
600
658
|
}
|
|
601
659
|
|
|
602
660
|
table::~table()
|
|
603
661
|
{
|
|
604
|
-
|
|
605
|
-
|
|
662
|
+
resetInternalTable(NULL);
|
|
663
|
+
database::tableRef.release(m_db.name(), m_name);
|
|
606
664
|
}
|
|
607
665
|
|
|
608
666
|
void table::resetTransctionInfo(THD* thd)
|
|
609
667
|
{
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
668
|
+
if (m_table)
|
|
669
|
+
{
|
|
670
|
+
if (m_changed)
|
|
671
|
+
query_cache_invalidate3(thd, m_table, 1);
|
|
672
|
+
m_changed = false;
|
|
673
|
+
m_table->next_number_field = 0;
|
|
674
|
+
m_table->file->next_insert_id = 0;
|
|
675
|
+
}
|
|
676
|
+
m_locked = false;
|
|
677
|
+
m_validCursor = false;
|
|
678
|
+
m_nounlock = false;
|
|
621
679
|
}
|
|
622
680
|
|
|
623
681
|
void table::resetInternalTable(TABLE* table)
|
|
624
682
|
{
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
683
|
+
if (table == NULL)
|
|
684
|
+
{
|
|
685
|
+
if (m_table)
|
|
686
|
+
m_table->file->ha_index_or_rnd_end();
|
|
687
|
+
m_table = NULL;
|
|
688
|
+
}
|
|
689
|
+
else
|
|
690
|
+
{
|
|
691
|
+
m_table = table;
|
|
692
|
+
m_table->read_set = &m_table->s->all_set;
|
|
693
|
+
m_locked = false;
|
|
694
|
+
m_changed = false;
|
|
695
|
+
m_validCursor = false;
|
|
696
|
+
m_nounlock = false;
|
|
697
|
+
}
|
|
640
698
|
}
|
|
641
699
|
|
|
642
700
|
bool table::setNonKey(bool scan)
|
|
643
701
|
{
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
702
|
+
if (m_keyNum != -2)
|
|
703
|
+
{
|
|
704
|
+
m_table->file->ha_index_or_rnd_end();
|
|
705
|
+
int ret = m_table->file->ha_rnd_init(scan);
|
|
706
|
+
if (ret)
|
|
707
|
+
THROW_BZS_ERROR_WITH_CODEMSG(ERROR_INDEX_RND_INIT,
|
|
708
|
+
"setNonKey rnd_init error.");
|
|
709
|
+
m_keyNum = -2;
|
|
710
|
+
}
|
|
711
|
+
return true;
|
|
651
712
|
}
|
|
652
713
|
|
|
653
714
|
bool table::setKeyNum(char num, bool sorted)
|
|
654
715
|
{
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
716
|
+
if ((m_keyNum != num) ||
|
|
717
|
+
((m_keyNum >= 0) && (m_table->file->inited == handler::NONE)))
|
|
718
|
+
{
|
|
719
|
+
m_table->file->ha_index_or_rnd_end();
|
|
720
|
+
|
|
721
|
+
if (keynumCheck(num))
|
|
722
|
+
{
|
|
723
|
+
m_keyNum = num;
|
|
724
|
+
m_table->file->ha_index_init(m_keyNum, sorted);
|
|
725
|
+
return true;
|
|
726
|
+
}
|
|
727
|
+
else
|
|
728
|
+
{
|
|
729
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
730
|
+
return false;
|
|
731
|
+
}
|
|
732
|
+
}
|
|
733
|
+
return true;
|
|
672
734
|
}
|
|
673
735
|
|
|
674
736
|
void table::fillNull(uchar* ptr, int size)
|
|
675
737
|
{
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
|
|
738
|
+
for (int i = 0; i < size; i++)
|
|
739
|
+
{
|
|
740
|
+
if (ptr[i] == 0)
|
|
741
|
+
{
|
|
742
|
+
memset(ptr + i, 0, size - i);
|
|
743
|
+
break;
|
|
744
|
+
}
|
|
745
|
+
}
|
|
684
746
|
}
|
|
685
747
|
|
|
686
748
|
void table::setKeyValues(const uchar* ptr, int size)
|
|
687
749
|
{
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
750
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
751
|
+
memcpy(&m_keybuf[0], ptr, std::min(MAX_KEYLEN, size));
|
|
752
|
+
int pos = 0;
|
|
753
|
+
for (int j = 0; j < (int)key.user_defined_key_parts; j++)
|
|
754
|
+
{
|
|
755
|
+
KEY_PART_INFO& seg = key.key_part[j];
|
|
756
|
+
if (seg.field->type() == MYSQL_TYPE_STRING)
|
|
757
|
+
fillNull(&m_keybuf[pos], seg.field->pack_length());
|
|
758
|
+
pos += seg.field->pack_length();
|
|
759
|
+
}
|
|
698
760
|
}
|
|
699
761
|
|
|
700
762
|
/**
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
*/
|
|
713
|
-
|
|
714
|
-
{
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
|
|
746
|
-
|
|
747
|
-
|
|
763
|
+
If null able field segment that need add null indicator byte befor segment.
|
|
764
|
+
Then key buffer length equal key length + null able segments.
|
|
765
|
+
|
|
766
|
+
The purpose of null key is non create index.
|
|
767
|
+
At read operation set not null(zero) to null indicator.
|
|
768
|
+
|
|
769
|
+
Size bytes of var and blob field is 2 byte fixed.
|
|
770
|
+
All most of key_part.length(segment lenght) is equal field.pack_length.
|
|
771
|
+
But blob and prefix index is not equal pack_length.
|
|
772
|
+
|
|
773
|
+
Client needs to make the right image except for null byte.
|
|
774
|
+
*/
|
|
775
|
+
short table::setKeyValuesPacked(const uchar* ptr, int size)
|
|
776
|
+
{
|
|
777
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
778
|
+
int to = 0;
|
|
779
|
+
const uchar* from = ptr;
|
|
780
|
+
int ret = -1;
|
|
781
|
+
for (int j = 0; j < (int)key.user_defined_key_parts; j++)
|
|
782
|
+
{
|
|
783
|
+
KEY_PART_INFO& seg = key.key_part[j];
|
|
784
|
+
if (seg.null_bit)
|
|
785
|
+
{
|
|
786
|
+
m_keybuf[to++] = 0x00;
|
|
787
|
+
seg.field->set_notnull();
|
|
788
|
+
}
|
|
789
|
+
if (seg.null_bit && isNisField(seg.field->field_name))
|
|
790
|
+
{
|
|
791
|
+
m_keybuf[to++] = 0x00;
|
|
792
|
+
seg.field->set_notnull();
|
|
793
|
+
}
|
|
794
|
+
else
|
|
795
|
+
{
|
|
796
|
+
unsigned short copylen = seg.length; // length = store_len - varlen
|
|
797
|
+
unsigned short copyspace = copylen;
|
|
798
|
+
if (seg.key_part_flag & HA_BLOB_PART ||
|
|
799
|
+
seg.key_part_flag & HA_VAR_LENGTH_PART)
|
|
800
|
+
{
|
|
801
|
+
copylen += 2; // varlen= allways 2byte
|
|
802
|
+
copyspace = copylen;
|
|
803
|
+
unsigned short len = *((unsigned short*)from) + 2;
|
|
804
|
+
copylen = std::min<unsigned short>(copylen, len);
|
|
805
|
+
if (copylen != copyspace)
|
|
806
|
+
memset(&m_keybuf[to], 0, copyspace);
|
|
807
|
+
}
|
|
808
|
+
|
|
809
|
+
if ((from + copylen) - ptr > size)
|
|
810
|
+
{
|
|
811
|
+
if (ret == -1)
|
|
812
|
+
ret = j;
|
|
813
|
+
// key data size is too short as whole key_parts length
|
|
814
|
+
memset(&m_keybuf[to], 0, copyspace);
|
|
815
|
+
}
|
|
816
|
+
else
|
|
817
|
+
{
|
|
818
|
+
memcpy(&m_keybuf[to], from, copylen);
|
|
819
|
+
from += copyspace;
|
|
820
|
+
}
|
|
821
|
+
to += copyspace;
|
|
822
|
+
|
|
823
|
+
if (to >= MAX_KEYLEN)
|
|
824
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_KEYBUFFERTOOSMALL, "");
|
|
825
|
+
}
|
|
826
|
+
}
|
|
827
|
+
return ret;
|
|
748
828
|
}
|
|
749
829
|
|
|
750
830
|
uint table::keyPackCopy(uchar* ptr)
|
|
751
831
|
{
|
|
752
|
-
|
|
753
|
-
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
|
|
757
|
-
|
|
758
|
-
|
|
759
|
-
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
770
|
-
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
775
|
-
|
|
776
|
-
|
|
777
|
-
|
|
778
|
-
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
832
|
+
// if nokey and getbookmark operation then keynum = -2
|
|
833
|
+
if (m_keyNum < 0)
|
|
834
|
+
return 0;
|
|
835
|
+
|
|
836
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
837
|
+
if ((key.flags & HA_NULL_PART_KEY) || (key.flags & HA_VAR_LENGTH_KEY))
|
|
838
|
+
{
|
|
839
|
+
int from = 0;
|
|
840
|
+
uchar* to = ptr;
|
|
841
|
+
for (int j = 0; j < (int)key.user_defined_key_parts; j++)
|
|
842
|
+
{
|
|
843
|
+
KEY_PART_INFO& seg = key.key_part[j];
|
|
844
|
+
if (seg.null_bit)
|
|
845
|
+
from++;
|
|
846
|
+
if (seg.null_bit && isNisField(seg.field->field_name))
|
|
847
|
+
from++;
|
|
848
|
+
else
|
|
849
|
+
{
|
|
850
|
+
int copylen = seg.length;
|
|
851
|
+
if (seg.key_part_flag & HA_BLOB_PART ||
|
|
852
|
+
seg.key_part_flag & HA_VAR_LENGTH_PART)
|
|
853
|
+
copylen += 2;
|
|
854
|
+
memcpy(to, &m_keybuf[from], copylen);
|
|
855
|
+
to += copylen;
|
|
856
|
+
from += copylen;
|
|
857
|
+
}
|
|
858
|
+
}
|
|
859
|
+
return (uint)(to - ptr);
|
|
860
|
+
}
|
|
861
|
+
memcpy(ptr, keybuf(), keylen());
|
|
862
|
+
return keylen();
|
|
863
|
+
}
|
|
864
|
+
|
|
865
|
+
void* table::record() const
|
|
866
|
+
{
|
|
867
|
+
Field* fd = m_table->field[0];
|
|
868
|
+
return fd->ptr;
|
|
869
|
+
}
|
|
870
|
+
|
|
871
|
+
/** if offset and lastVarLenBytes() is non zero that is
|
|
872
|
+
* m_recordFormatType=RF_FIXED_PLUS_VALIABLE_LEN.
|
|
793
873
|
* ptr is excluding null flag sgement.
|
|
794
874
|
*/
|
|
795
875
|
void table::setRecord(void* ptr, unsigned short size, int offset)
|
|
796
876
|
{
|
|
797
|
-
|
|
798
|
-
|
|
799
|
-
|
|
800
|
-
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
|
|
877
|
+
m_cursor = false;
|
|
878
|
+
Field* fd = m_table->field[0]; // remove null flag segment
|
|
879
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
880
|
+
if (offset + size <=
|
|
881
|
+
(unsigned short)m_table->s->reclength + lastVarLenBytes())
|
|
882
|
+
{
|
|
883
|
+
#else
|
|
884
|
+
if (offset + size <= (unsigned short)m_table->s->reclength)
|
|
885
|
+
{
|
|
886
|
+
|
|
887
|
+
#endif
|
|
888
|
+
|
|
889
|
+
if (size > 0)
|
|
890
|
+
memcpy(fd->ptr + offset, ptr, size);
|
|
891
|
+
}
|
|
892
|
+
else
|
|
893
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_INVALID_DATASIZE, "");
|
|
806
894
|
}
|
|
807
895
|
|
|
808
896
|
inline bool isNull(Field* fd)
|
|
809
897
|
{
|
|
810
|
-
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
898
|
+
if (isVarType(fd->type()))
|
|
899
|
+
{
|
|
900
|
+
int len = *((unsigned char*)fd->ptr);
|
|
901
|
+
if (fd->field_length > 255)
|
|
902
|
+
len = *((unsigned short*)fd->ptr);
|
|
903
|
+
|
|
904
|
+
return (len == 0);
|
|
905
|
+
}
|
|
906
|
+
else if (isBlobType(fd->type()))
|
|
907
|
+
return (0 == blob_len(fd));
|
|
908
|
+
else
|
|
909
|
+
{
|
|
910
|
+
unsigned int k = 0;
|
|
911
|
+
for (k = 0; k < fd->key_length(); k++)
|
|
912
|
+
if (fd->ptr[k])
|
|
913
|
+
break;
|
|
914
|
+
|
|
915
|
+
if (k == fd->key_length())
|
|
916
|
+
return true;
|
|
917
|
+
}
|
|
918
|
+
return false;
|
|
830
919
|
}
|
|
831
920
|
|
|
832
921
|
inline bool isNullNis(KEY& key, bool all)
|
|
833
922
|
{
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
|
|
844
|
-
|
|
845
|
-
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
|
|
923
|
+
for (int j = 1; j < (int)key.user_defined_key_parts; j++)
|
|
924
|
+
{
|
|
925
|
+
Field* fd = key.key_part[j].field;
|
|
926
|
+
if (key.key_part[j].null_bit)
|
|
927
|
+
{
|
|
928
|
+
bool v = isNull(fd);
|
|
929
|
+
v ? fd->set_null() : fd->set_notnull();
|
|
930
|
+
if (all && !v)
|
|
931
|
+
return false;
|
|
932
|
+
else if (!all && v)
|
|
933
|
+
return true;
|
|
934
|
+
}
|
|
935
|
+
}
|
|
936
|
+
if (all)
|
|
937
|
+
return true;
|
|
938
|
+
return false;
|
|
850
939
|
}
|
|
851
940
|
|
|
852
941
|
void table::setBlobFieldPointer(const bzs::db::blobHeader* hd)
|
|
853
942
|
{
|
|
854
|
-
|
|
855
|
-
|
|
943
|
+
|
|
944
|
+
if (hd)
|
|
856
945
|
{
|
|
857
946
|
assert(hd->curRow < hd->rows);
|
|
858
|
-
|
|
859
|
-
for (int i=0;i<hd->fieldCount;i++)
|
|
947
|
+
const blobField* f = hd->nextField;
|
|
948
|
+
for (int i = 0; i < hd->fieldCount; i++)
|
|
860
949
|
{
|
|
861
950
|
Field* fd = m_table->field[f->fieldNum];
|
|
862
951
|
int sizeByte = blob_var_bytes(fd);
|
|
863
952
|
memcpy(fd->ptr, &f->size, sizeByte);
|
|
864
953
|
const char* data = f->data();
|
|
865
|
-
memcpy(fd->ptr+sizeByte, &data, sizeof(char*));
|
|
954
|
+
memcpy(fd->ptr + sizeByte, &data, sizeof(char*));
|
|
866
955
|
f = f->next();
|
|
867
956
|
}
|
|
868
|
-
|
|
957
|
+
++hd->curRow;
|
|
869
958
|
hd->nextField = (blobField*)f;
|
|
870
959
|
}
|
|
871
|
-
|
|
872
960
|
}
|
|
873
961
|
|
|
874
962
|
/** A packed data set to the record buffer.
|
|
875
963
|
*/
|
|
876
|
-
void table::setRecordFromPacked(const uchar* packedPtr, uint size,
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
917
|
-
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
964
|
+
void table::setRecordFromPacked(const uchar* packedPtr, uint size,
|
|
965
|
+
const bzs::db::blobHeader* hd)
|
|
966
|
+
{
|
|
967
|
+
const uchar* p = packedPtr;
|
|
968
|
+
|
|
969
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
970
|
+
if (recordFormatType() & RF_FIXED_PLUS_VALIABLE_LEN)
|
|
971
|
+
{
|
|
972
|
+
int varlenbyte = lastVarLenBytes();
|
|
973
|
+
int varlenStartPos = lastVarFieldPos();
|
|
974
|
+
setRecord((void*)p, varlenStartPos);
|
|
975
|
+
int len = std::min((int)(size - varlenStartPos),
|
|
976
|
+
(int)recordLenCl() - varlenStartPos);
|
|
977
|
+
if (len > 0)
|
|
978
|
+
{
|
|
979
|
+
setRecord(&len, varlenbyte, varlenStartPos);
|
|
980
|
+
// if (len > 0)
|
|
981
|
+
setRecord((void*)(p + varlenStartPos), len,
|
|
982
|
+
varlenStartPos + varlenbyte);
|
|
983
|
+
}
|
|
984
|
+
else if (len == 0)
|
|
985
|
+
;
|
|
986
|
+
else
|
|
987
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_BUFFERTOOSMALL,
|
|
988
|
+
"setRecordFromPacked");
|
|
989
|
+
}
|
|
990
|
+
else if ((recordFormatType() & RF_VALIABLE_LEN) ||
|
|
991
|
+
(recordFormatType() & RF_INCLUDE_NIS))
|
|
992
|
+
{
|
|
993
|
+
#else
|
|
994
|
+
if ((recordFormatType() & RF_VALIABLE_LEN) ||
|
|
995
|
+
(recordFormatType() & RF_INCLUDE_NIS))
|
|
996
|
+
{
|
|
997
|
+
#endif
|
|
998
|
+
// It copies for every field.
|
|
999
|
+
for (uint i = 0; i < m_table->s->fields; i++)
|
|
1000
|
+
{
|
|
1001
|
+
Field* fd = m_table->field[i];
|
|
1002
|
+
if (isNisField(fd->field_name))
|
|
1003
|
+
fd->ptr[0] = 0x00; // The Nis field is not sent from a client.
|
|
1004
|
+
else
|
|
1005
|
+
{
|
|
1006
|
+
int len = fd->pack_length();
|
|
1007
|
+
if (isVarType(fd->type()))
|
|
1008
|
+
{
|
|
1009
|
+
len = var_total_len(p, var_bytes(fd));
|
|
1010
|
+
if (len > (int)fd->pack_length())
|
|
1011
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_BUFFERTOOSMALL,
|
|
1012
|
+
"setRecordFromPacked");
|
|
1013
|
+
}
|
|
1014
|
+
else if (size < (uint)len)
|
|
1015
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_BUFFERTOOSMALL,
|
|
1016
|
+
"setRecordFromPacked");
|
|
1017
|
+
memcpy(fd->ptr, p, len);
|
|
1018
|
+
p += len;
|
|
1019
|
+
size -= len;
|
|
1020
|
+
}
|
|
1021
|
+
}
|
|
1022
|
+
if (m_table->s->blob_fields)
|
|
1023
|
+
setBlobFieldPointer(hd);
|
|
1024
|
+
}
|
|
1025
|
+
else
|
|
1026
|
+
setRecord((void*)p, std::min(size, recordLenCl()));
|
|
1027
|
+
}
|
|
1028
|
+
|
|
1029
|
+
/** A record image is packed, and is copied to the specified buffer, and length
|
|
1030
|
+
*is returned.
|
|
1031
|
+
* -maxsize can be specified when recordFormatType() is RF_VALIABLE_LEN.
|
|
1032
|
+
* -Length is not inspected if maxsize is zero.
|
|
1033
|
+
* -When a buffer is too short, zero is returned to a result.
|
|
925
1034
|
*/
|
|
926
|
-
uint table::recordPackCopy(char* buf, uint maxsize)
|
|
927
|
-
{
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
|
|
937
|
-
|
|
938
|
-
|
|
939
|
-
|
|
940
|
-
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
1035
|
+
uint table::recordPackCopy(char* buf, uint maxsize)
|
|
1036
|
+
{
|
|
1037
|
+
char* p = buf;
|
|
1038
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
1039
|
+
if (recordFormatType() & RF_FIXED_PLUS_VALIABLE_LEN)
|
|
1040
|
+
{
|
|
1041
|
+
uint varLenBytes = lastVarLenBytes();
|
|
1042
|
+
uint varLenBytesPos = lastVarFieldPos();
|
|
1043
|
+
const uchar* data = (const uchar*)record();
|
|
1044
|
+
int len = recordLenCl();
|
|
1045
|
+
if (varLenBytes)
|
|
1046
|
+
{
|
|
1047
|
+
memcpy(p, data, varLenBytesPos);
|
|
1048
|
+
p += varLenBytesPos;
|
|
1049
|
+
data += varLenBytesPos;
|
|
1050
|
+
if (varLenBytes == 1)
|
|
1051
|
+
len = *data;
|
|
1052
|
+
else
|
|
1053
|
+
len = *((const unsigned short*)data);
|
|
1054
|
+
// In the variable length of tdap type, it returns except for
|
|
1055
|
+
// varsize.
|
|
1056
|
+
data += varLenBytes;
|
|
1057
|
+
}
|
|
1058
|
+
memcpy(p, data, len);
|
|
1059
|
+
p += len;
|
|
1060
|
+
}
|
|
1061
|
+
else if ((recordFormatType() & RF_VALIABLE_LEN) ||
|
|
1062
|
+
(recordFormatType() & RF_INCLUDE_NIS))
|
|
1063
|
+
{
|
|
1064
|
+
#else
|
|
1065
|
+
if ((recordFormatType() & RF_VALIABLE_LEN) ||
|
|
1066
|
+
(recordFormatType() & RF_INCLUDE_NIS))
|
|
1067
|
+
{
|
|
1068
|
+
#endif
|
|
1069
|
+
int blobs = 0;
|
|
1070
|
+
for (uint i = 0; i < m_table->s->fields; i++)
|
|
1071
|
+
{
|
|
1072
|
+
Field* fd = m_table->field[i];
|
|
1073
|
+
if (isNisField(fd->field_name))
|
|
1074
|
+
;
|
|
1075
|
+
// The Nis field is not sent to a client.
|
|
1076
|
+
else
|
|
1077
|
+
{
|
|
1078
|
+
uint len = fd->pack_length();
|
|
1079
|
+
if (isVarType(fd->type()))
|
|
1080
|
+
len = var_total_len(fd);
|
|
1081
|
+
if (maxsize && ((p - buf + len) > maxsize))
|
|
1082
|
+
return 0;
|
|
1083
|
+
memcpy(p, fd->ptr, len);
|
|
1084
|
+
p += len;
|
|
1085
|
+
if (isBlobType(fd->type()))
|
|
1086
|
+
{
|
|
1087
|
+
++blobs;
|
|
1088
|
+
addBlobBuffer(fd->field_index);
|
|
1089
|
+
}
|
|
1090
|
+
}
|
|
1091
|
+
}
|
|
1092
|
+
setBlobFieldCount(blobs);
|
|
1093
|
+
}
|
|
1094
|
+
else
|
|
1095
|
+
{
|
|
1096
|
+
const uchar* data = (const uchar*)record();
|
|
1097
|
+
int len = recordLenCl();
|
|
1098
|
+
memcpy(p, data, len);
|
|
1099
|
+
p += len;
|
|
1100
|
+
}
|
|
1101
|
+
return (uint)(p - buf);
|
|
978
1102
|
}
|
|
979
1103
|
|
|
980
|
-
|
|
1104
|
+
ushort table::fieldPackCopy(unsigned char* dest, short filedNum)
|
|
981
1105
|
{
|
|
982
|
-
|
|
983
|
-
|
|
1106
|
+
Field* fd = m_table->field[filedNum];
|
|
1107
|
+
uint len = fd->pack_length();
|
|
1108
|
+
if (isVarType(fd->type()))
|
|
1109
|
+
len = var_total_len(fd);
|
|
1110
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
1111
|
+
if (lastVarFiledNum() == filedNum)
|
|
1112
|
+
{
|
|
1113
|
+
len -= lastVarLenBytes();
|
|
1114
|
+
memcpy(dest, fd->ptr + lastVarLenBytes(), len);
|
|
1115
|
+
}
|
|
1116
|
+
else
|
|
1117
|
+
#endif
|
|
1118
|
+
memcpy(dest, fd->ptr, len);
|
|
1119
|
+
return (ushort)len;
|
|
1120
|
+
}
|
|
984
1121
|
|
|
1122
|
+
inline bool table::keynumCheck(char num)
|
|
1123
|
+
{
|
|
1124
|
+
return ((num >= 0) && (num < (short)m_table->s->keys));
|
|
985
1125
|
}
|
|
986
1126
|
|
|
987
1127
|
inline void table::unlockRow()
|
|
988
1128
|
{
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
1129
|
+
if (!m_nounlock && m_validCursor && m_db.inTransaction() &&
|
|
1130
|
+
(m_db.transactionType() == 0))
|
|
1131
|
+
{
|
|
1132
|
+
m_table->file->unlock_row();
|
|
1133
|
+
m_nounlock = false;
|
|
1134
|
+
}
|
|
995
1135
|
}
|
|
1136
|
+
|
|
996
1137
|
/* read by key
|
|
997
1138
|
* A key field value is set in advance
|
|
998
1139
|
*/
|
|
999
|
-
void
|
|
1000
|
-
{
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1140
|
+
void table::seekKey(enum ha_rkey_function find_flag, key_part_map keyMap)
|
|
1141
|
+
{
|
|
1142
|
+
m_nonNcc = false;
|
|
1143
|
+
if (keynumCheck(m_keyNum))
|
|
1144
|
+
{
|
|
1145
|
+
unlockRow();
|
|
1146
|
+
m_stat = m_table->file->ha_index_read_map(
|
|
1147
|
+
m_table->record[0], &m_keybuf[0], keyMap /* keymap() */, find_flag);
|
|
1148
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1149
|
+
if (m_stat == 0)
|
|
1150
|
+
{
|
|
1151
|
+
if (find_flag != HA_READ_KEY_EXACT)
|
|
1152
|
+
key_copy(&m_keybuf[0], m_table->record[0],
|
|
1153
|
+
&m_table->key_info[m_keyNum], KEYLEN_ALLCOPY);
|
|
1154
|
+
}
|
|
1155
|
+
}
|
|
1156
|
+
else
|
|
1157
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
1158
|
+
if ((m_stat == HA_ERR_KEY_NOT_FOUND) && (find_flag != HA_READ_KEY_EXACT))
|
|
1159
|
+
m_stat = HA_ERR_END_OF_FILE;
|
|
1016
1160
|
}
|
|
1017
1161
|
|
|
1018
1162
|
void table::moveKey(boost::function<int()> func)
|
|
1019
1163
|
{
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
|
|
1035
|
-
|
|
1036
|
-
|
|
1037
|
-
|
|
1038
|
-
|
|
1039
|
-
|
|
1040
|
-
|
|
1041
|
-
|
|
1042
|
-
|
|
1043
|
-
|
|
1044
|
-
|
|
1045
|
-
|
|
1046
|
-
|
|
1047
|
-
|
|
1048
|
-
|
|
1164
|
+
m_nonNcc = false;
|
|
1165
|
+
if (keynumCheck(m_keyNum))
|
|
1166
|
+
{
|
|
1167
|
+
unlockRow();
|
|
1168
|
+
|
|
1169
|
+
m_stat = func();
|
|
1170
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1171
|
+
if (m_stat == 0)
|
|
1172
|
+
key_copy(&m_keybuf[0], m_table->record[0],
|
|
1173
|
+
&m_table->key_info[m_keyNum], KEYLEN_ALLCOPY);
|
|
1174
|
+
}
|
|
1175
|
+
else
|
|
1176
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
1177
|
+
if (m_stat == HA_ERR_KEY_NOT_FOUND)
|
|
1178
|
+
m_stat = HA_ERR_END_OF_FILE;
|
|
1179
|
+
}
|
|
1180
|
+
|
|
1181
|
+
void table::getNextSame(key_part_map keyMap)
|
|
1182
|
+
{
|
|
1183
|
+
m_nonNcc = false;
|
|
1184
|
+
if (keynumCheck(m_keyNum))
|
|
1185
|
+
{
|
|
1186
|
+
if (m_validCursor && m_db.inTransaction() &&
|
|
1187
|
+
(m_db.transactionType() == 0))
|
|
1188
|
+
m_table->file->unlock_row();
|
|
1189
|
+
m_stat = m_table->file->ha_index_next_same(
|
|
1190
|
+
m_table->record[0], &m_keybuf[0], keyMap /* keymap() */);
|
|
1191
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1192
|
+
if (m_stat == 0)
|
|
1193
|
+
key_copy(&m_keybuf[0], m_table->record[0],
|
|
1194
|
+
&m_table->key_info[m_keyNum], KEYLEN_ALLCOPY);
|
|
1195
|
+
}
|
|
1196
|
+
else
|
|
1197
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
1049
1198
|
}
|
|
1050
1199
|
|
|
1051
1200
|
void table::getLast()
|
|
1052
1201
|
{
|
|
1053
|
-
|
|
1202
|
+
moveKey(boost::bind(&handler::ha_index_last, m_table->file,
|
|
1203
|
+
m_table->record[0]));
|
|
1054
1204
|
}
|
|
1055
1205
|
|
|
1056
1206
|
void table::getFirst()
|
|
1057
1207
|
{
|
|
1058
|
-
|
|
1059
|
-
|
|
1208
|
+
moveKey(boost::bind(&handler::ha_index_first, m_table->file,
|
|
1209
|
+
m_table->record[0]));
|
|
1210
|
+
|
|
1060
1211
|
#if (defined(DEBUG) && defined(WIN32))
|
|
1061
1212
|
|
|
1062
|
-
|
|
1063
|
-
|
|
1064
|
-
|
|
1065
|
-
|
|
1066
|
-
|
|
1067
|
-
|
|
1068
|
-
|
|
1069
|
-
|
|
1070
|
-
|
|
1071
|
-
|
|
1072
|
-
|
|
1073
|
-
|
|
1213
|
+
char buf[1024];
|
|
1214
|
+
sprintf(buf, "name=%s reclength=%d rec_buff_length=%d\r\n", m_name.c_str(),
|
|
1215
|
+
m_table->s->reclength, m_table->s->rec_buff_length);
|
|
1216
|
+
OutputDebugString(buf);
|
|
1217
|
+
for (uint i = 0; i < m_table->s->fields; i++)
|
|
1218
|
+
{
|
|
1219
|
+
Field* fd = m_table->s->field[i];
|
|
1220
|
+
|
|
1221
|
+
sprintf(buf, "\tpack_length=%d field_length=%d key_length=%d\r\n",
|
|
1222
|
+
fd->pack_length(), fd->field_length, fd->key_length());
|
|
1223
|
+
OutputDebugString(buf);
|
|
1224
|
+
}
|
|
1074
1225
|
#endif
|
|
1075
1226
|
}
|
|
1076
1227
|
|
|
1077
1228
|
void table::getNext()
|
|
1078
1229
|
{
|
|
1079
|
-
|
|
1080
|
-
|
|
1081
|
-
|
|
1082
|
-
|
|
1083
|
-
|
|
1084
|
-
|
|
1085
|
-
|
|
1086
|
-
|
|
1087
|
-
|
|
1088
|
-
|
|
1089
|
-
|
|
1090
|
-
|
|
1091
|
-
|
|
1230
|
+
if (!m_cursor)
|
|
1231
|
+
{
|
|
1232
|
+
m_stat = HA_ERR_NO_ACTIVE_RECORD;
|
|
1233
|
+
return;
|
|
1234
|
+
}
|
|
1235
|
+
if (m_nonNcc)
|
|
1236
|
+
{ // It moves to the position after updating.
|
|
1237
|
+
// Since it may be lost, ref is compared and the next is decided.
|
|
1238
|
+
movePos(position(true), m_keyNum, true);
|
|
1239
|
+
if (m_stat)
|
|
1240
|
+
return;
|
|
1241
|
+
}
|
|
1242
|
+
moveKey(boost::bind(&handler::ha_index_next, m_table->file,
|
|
1243
|
+
m_table->record[0]));
|
|
1092
1244
|
}
|
|
1093
1245
|
|
|
1094
1246
|
void table::getPrev()
|
|
1095
1247
|
{
|
|
1096
|
-
|
|
1097
|
-
|
|
1098
|
-
|
|
1099
|
-
|
|
1100
|
-
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1106
|
-
|
|
1248
|
+
if (!m_cursor)
|
|
1249
|
+
{
|
|
1250
|
+
m_stat = HA_ERR_NO_ACTIVE_RECORD;
|
|
1251
|
+
return;
|
|
1252
|
+
}
|
|
1253
|
+
if (m_nonNcc)
|
|
1254
|
+
{
|
|
1255
|
+
movePos(position(true), m_keyNum, true);
|
|
1256
|
+
if (m_stat)
|
|
1257
|
+
return;
|
|
1258
|
+
}
|
|
1259
|
+
moveKey(boost::bind(&handler::ha_index_prev, m_table->file,
|
|
1260
|
+
m_table->record[0]));
|
|
1107
1261
|
}
|
|
1108
1262
|
|
|
1109
1263
|
bool table::keyCheckForPercent()
|
|
1110
1264
|
{
|
|
1111
|
-
|
|
1112
|
-
|
|
1113
|
-
|
|
1114
|
-
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
1265
|
+
if (m_keyNum == -1)
|
|
1266
|
+
m_keyNum = m_table->s->primary_key;
|
|
1267
|
+
// The value of the beginning of a key
|
|
1268
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
1269
|
+
if (key.key_length > 128)
|
|
1270
|
+
return false;
|
|
1271
|
+
return true;
|
|
1118
1272
|
}
|
|
1119
1273
|
|
|
1120
1274
|
void table::preBuildPercent(uchar* first, uchar* last)
|
|
1121
1275
|
{
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1276
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
1277
|
+
getFirst();
|
|
1278
|
+
if (m_stat == 0)
|
|
1279
|
+
{
|
|
1280
|
+
key_copy(first, m_table->record[0], &key, KEYLEN_ALLCOPY);
|
|
1281
|
+
getLast();
|
|
1282
|
+
if (m_stat == 0)
|
|
1283
|
+
{
|
|
1284
|
+
key_copy(last, m_table->record[0], &key, KEYLEN_ALLCOPY);
|
|
1285
|
+
memset(m_keybuf.get(), 0, MAX_KEYLEN);
|
|
1286
|
+
}
|
|
1287
|
+
else
|
|
1288
|
+
THROW_BZS_ERROR_WITH_CODEMSG(m_stat, "connot seek last position.");
|
|
1289
|
+
}
|
|
1290
|
+
else
|
|
1291
|
+
THROW_BZS_ERROR_WITH_CODEMSG(m_stat, "connot seek first position.");
|
|
1136
1292
|
}
|
|
1137
1293
|
|
|
1138
1294
|
void table::getByPercentage(unsigned short per)
|
|
1139
1295
|
{
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
|
|
1177
|
-
|
|
1178
|
-
|
|
1179
|
-
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
|
|
1183
|
-
|
|
1184
|
-
|
|
1185
|
-
|
|
1186
|
-
|
|
1187
|
-
|
|
1188
|
-
|
|
1189
|
-
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1200
|
-
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1207
|
-
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
|
|
1212
|
-
|
|
1213
|
-
|
|
1214
|
-
|
|
1215
|
-
|
|
1216
|
-
|
|
1217
|
-
|
|
1218
|
-
|
|
1219
|
-
|
|
1220
|
-
|
|
1221
|
-
|
|
1222
|
-
|
|
1223
|
-
|
|
1224
|
-
|
|
1225
|
-
|
|
1226
|
-
|
|
1227
|
-
|
|
1228
|
-
|
|
1229
|
-
|
|
1230
|
-
|
|
1231
|
-
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1296
|
+
m_nonNcc = false;
|
|
1297
|
+
if (!keyCheckForPercent())
|
|
1298
|
+
{
|
|
1299
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
1300
|
+
return;
|
|
1301
|
+
}
|
|
1302
|
+
if (per > 9800)
|
|
1303
|
+
{
|
|
1304
|
+
getLast();
|
|
1305
|
+
return;
|
|
1306
|
+
}
|
|
1307
|
+
else if (per < 200)
|
|
1308
|
+
{
|
|
1309
|
+
getFirst();
|
|
1310
|
+
return;
|
|
1311
|
+
}
|
|
1312
|
+
|
|
1313
|
+
uchar keybufFirst[MAX_KEYLEN] = { 0x00 };
|
|
1314
|
+
uchar keybufLast[MAX_KEYLEN] = { 0x00 };
|
|
1315
|
+
preBuildPercent(keybufFirst, keybufLast);
|
|
1316
|
+
if (m_stat == 0)
|
|
1317
|
+
{
|
|
1318
|
+
// 5% of position is obtained.
|
|
1319
|
+
uchar* st = keybufFirst;
|
|
1320
|
+
uchar* en = keybufLast;
|
|
1321
|
+
uchar* cu = (uchar*)keybuf();
|
|
1322
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
1323
|
+
uint keylen = key.key_length + 10;
|
|
1324
|
+
boost::shared_array<uchar> stbuf(new uchar[keylen]);
|
|
1325
|
+
boost::shared_array<uchar> lsbuf(new uchar[keylen]);
|
|
1326
|
+
boost::shared_array<uchar> stbufResult(new uchar[keylen]);
|
|
1327
|
+
boost::shared_array<uchar> lsbufResult(new uchar[keylen]);
|
|
1328
|
+
percentageKey pk(key, st, en, cu);
|
|
1329
|
+
bool forwoard = true;
|
|
1330
|
+
int ov = 0;
|
|
1331
|
+
int sameCount = 0;
|
|
1332
|
+
while (1)
|
|
1333
|
+
{
|
|
1334
|
+
pk.reset(st, en, cu);
|
|
1335
|
+
int ret = pk.setKeyValueByPer(5000, forwoard);
|
|
1336
|
+
if (ret == KEY_ALL_SGMENTS_SAME)
|
|
1337
|
+
break; // THROW_BZS_ERROR_WITH_CODEMSG(1, "first and last record
|
|
1338
|
+
// are same key value.");
|
|
1339
|
+
else if (ret == KEY_NEED_SGMENT_COPY)
|
|
1340
|
+
pk.copyFirstDeferentSegment();
|
|
1341
|
+
int v = percentage(keybufFirst, keybufLast, cu) - 1000;
|
|
1342
|
+
(ov == v) ? ++sameCount : sameCount = 0;
|
|
1343
|
+
if (sameCount > 100)
|
|
1344
|
+
break;
|
|
1345
|
+
ov = v;
|
|
1346
|
+
if (v < -250)
|
|
1347
|
+
{
|
|
1348
|
+
memcpy(stbuf.get(), cu, keylen);
|
|
1349
|
+
st = stbuf.get();
|
|
1350
|
+
forwoard = true;
|
|
1351
|
+
}
|
|
1352
|
+
else if (v > 250)
|
|
1353
|
+
{
|
|
1354
|
+
memcpy(lsbuf.get(), cu, keylen);
|
|
1355
|
+
en = lsbuf.get();
|
|
1356
|
+
forwoard = false;
|
|
1357
|
+
}
|
|
1358
|
+
else
|
|
1359
|
+
break;
|
|
1360
|
+
}
|
|
1361
|
+
memcpy(stbufResult.get(), cu, keylen);
|
|
1362
|
+
if (per > 1000)
|
|
1363
|
+
{
|
|
1364
|
+
// 95% of position is obtained.
|
|
1365
|
+
forwoard = true;
|
|
1366
|
+
memcpy(cu, keybufLast, keylen);
|
|
1367
|
+
memcpy(lsbuf.get(), keybufLast, keylen);
|
|
1368
|
+
en = lsbuf.get();
|
|
1369
|
+
while (1)
|
|
1370
|
+
{
|
|
1371
|
+
pk.reset(st, en, cu);
|
|
1372
|
+
int ret = pk.setKeyValueByPer(5000, forwoard);
|
|
1373
|
+
if (ret == KEY_ALL_SGMENTS_SAME)
|
|
1374
|
+
break;
|
|
1375
|
+
/// THROW_BZS_ERROR_WITH_CODEMSG(1, "connot seek percant
|
|
1376
|
+
/// position.");
|
|
1377
|
+
else if (ret == KEY_NEED_SGMENT_COPY)
|
|
1378
|
+
pk.copyFirstDeferentSegment();
|
|
1379
|
+
int v = percentage(keybufFirst, keybufLast, cu) - 9000;
|
|
1380
|
+
(ov == v) ? ++sameCount : sameCount = 0;
|
|
1381
|
+
if (sameCount > 100)
|
|
1382
|
+
break;
|
|
1383
|
+
ov = v;
|
|
1384
|
+
if (v < -250)
|
|
1385
|
+
{
|
|
1386
|
+
memcpy(stbuf.get(), cu, keylen);
|
|
1387
|
+
st = stbuf.get();
|
|
1388
|
+
forwoard = true;
|
|
1389
|
+
}
|
|
1390
|
+
else if (v > 250)
|
|
1391
|
+
{
|
|
1392
|
+
memcpy(lsbuf.get(), cu, keylen);
|
|
1393
|
+
en = lsbuf.get();
|
|
1394
|
+
forwoard = false;
|
|
1395
|
+
}
|
|
1396
|
+
else
|
|
1397
|
+
break;
|
|
1398
|
+
}
|
|
1399
|
+
memcpy(lsbufResult.get(), cu, keylen);
|
|
1400
|
+
pk.reset(stbufResult.get(), lsbufResult.get(), cu);
|
|
1401
|
+
|
|
1402
|
+
pk.setKeyValueByPer(per, true);
|
|
1403
|
+
}
|
|
1404
|
+
seekKey(HA_READ_KEY_OR_NEXT, keymap());
|
|
1405
|
+
}
|
|
1243
1406
|
}
|
|
1244
1407
|
|
|
1245
1408
|
int table::percentage(uchar* first, uchar* last, uchar* cur)
|
|
1246
1409
|
{
|
|
1247
|
-
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
|
|
1269
|
-
|
|
1270
|
-
|
|
1271
|
-
|
|
1272
|
-
|
|
1410
|
+
initHandler();
|
|
1411
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
1412
|
+
// 1 cur to last
|
|
1413
|
+
key_range minkey;
|
|
1414
|
+
minkey.key = cur;
|
|
1415
|
+
minkey.length = key.key_length;
|
|
1416
|
+
minkey.keypart_map = keymap();
|
|
1417
|
+
minkey.flag = HA_READ_KEY_EXACT;
|
|
1418
|
+
key_range maxkey = minkey;
|
|
1419
|
+
maxkey.key = last;
|
|
1420
|
+
ha_rows rows1 = m_table->file->records_in_range(m_keyNum, &minkey, &maxkey);
|
|
1421
|
+
|
|
1422
|
+
// 2 first to last
|
|
1423
|
+
maxkey.key = first;
|
|
1424
|
+
ha_rows rows2 = m_table->file->records_in_range(m_keyNum, &maxkey, &minkey);
|
|
1425
|
+
|
|
1426
|
+
// 3 record count
|
|
1427
|
+
ha_rows total = recordCount(true);
|
|
1428
|
+
|
|
1429
|
+
// result
|
|
1430
|
+
int v1 = 10000 - (int)(rows1 * (double)10000 / total);
|
|
1431
|
+
|
|
1432
|
+
int v2 = (int)(rows2 * (double)10000 / total);
|
|
1433
|
+
if (abs(5000 - v1) > abs(5000 - v2))
|
|
1434
|
+
return v1;
|
|
1435
|
+
return v2;
|
|
1273
1436
|
}
|
|
1274
1437
|
|
|
1275
1438
|
void table::calcPercentage()
|
|
1276
|
-
{
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
|
|
1285
|
-
|
|
1286
|
-
|
|
1287
|
-
|
|
1288
|
-
|
|
1289
|
-
|
|
1290
|
-
|
|
1291
|
-
|
|
1292
|
-
|
|
1293
|
-
|
|
1294
|
-
|
|
1295
|
-
|
|
1296
|
-
|
|
1297
|
-
|
|
1439
|
+
{
|
|
1440
|
+
if (!keyCheckForPercent())
|
|
1441
|
+
{
|
|
1442
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
1443
|
+
return;
|
|
1444
|
+
}
|
|
1445
|
+
m_percentResult = 0;
|
|
1446
|
+
// The present key value is copied.
|
|
1447
|
+
uchar keybufCur[MAX_KEYLEN] = { 0x00 };
|
|
1448
|
+
key_copy(keybufCur, m_table->record[0], &m_table->key_info[m_keyNum],
|
|
1449
|
+
KEYLEN_ALLCOPY);
|
|
1450
|
+
|
|
1451
|
+
uchar keybufFirst[MAX_KEYLEN] = { 0x00 };
|
|
1452
|
+
uchar keybufLast[MAX_KEYLEN] = { 0x00 };
|
|
1453
|
+
preBuildPercent(keybufFirst, keybufLast);
|
|
1454
|
+
|
|
1455
|
+
if (m_stat == 0)
|
|
1456
|
+
{ // restore current
|
|
1457
|
+
setKeyValues(keybufCur, 128);
|
|
1458
|
+
seekKey(HA_READ_KEY_EXACT, keymap());
|
|
1459
|
+
if (m_stat == 0)
|
|
1460
|
+
m_percentResult = percentage(keybufFirst, keybufLast, keybufCur);
|
|
1461
|
+
}
|
|
1298
1462
|
}
|
|
1299
1463
|
|
|
1300
1464
|
void table::stepFirst()
|
|
1301
1465
|
{
|
|
1302
|
-
|
|
1303
|
-
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
|
|
1308
|
-
|
|
1309
|
-
|
|
1310
|
-
|
|
1311
|
-
|
|
1312
|
-
|
|
1313
|
-
|
|
1314
|
-
|
|
1315
|
-
|
|
1466
|
+
if (m_table->s->primary_key < m_table->s->keys)
|
|
1467
|
+
{
|
|
1468
|
+
setKeyNum(m_table->s->primary_key);
|
|
1469
|
+
getFirst();
|
|
1470
|
+
}
|
|
1471
|
+
else
|
|
1472
|
+
{
|
|
1473
|
+
if (setNonKey(true))
|
|
1474
|
+
{
|
|
1475
|
+
m_stat = m_table->file->ha_rnd_next(m_table->record[0]);
|
|
1476
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1477
|
+
}
|
|
1478
|
+
else
|
|
1479
|
+
m_stat = STATUS_INVALID_KEYNUM;
|
|
1480
|
+
}
|
|
1316
1481
|
}
|
|
1317
1482
|
|
|
1318
1483
|
void table::stepLast()
|
|
1319
1484
|
{
|
|
1320
|
-
|
|
1321
|
-
|
|
1322
|
-
|
|
1323
|
-
|
|
1324
|
-
|
|
1325
|
-
|
|
1485
|
+
if (m_table->s->primary_key < m_table->s->keys)
|
|
1486
|
+
{
|
|
1487
|
+
setKeyNum(m_table->s->primary_key);
|
|
1488
|
+
getLast();
|
|
1489
|
+
}
|
|
1490
|
+
else
|
|
1491
|
+
m_stat = STATUS_NOSUPPORT_OP;
|
|
1326
1492
|
}
|
|
1327
1493
|
|
|
1328
1494
|
void table::stepNext()
|
|
1329
1495
|
{
|
|
1330
|
-
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1338
|
-
|
|
1339
|
-
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
|
|
1343
|
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1496
|
+
m_nonNcc = false;
|
|
1497
|
+
if (m_table->s->primary_key < m_table->s->keys)
|
|
1498
|
+
{
|
|
1499
|
+
setKeyNum(m_table->s->primary_key);
|
|
1500
|
+
getNext();
|
|
1501
|
+
}
|
|
1502
|
+
else
|
|
1503
|
+
{
|
|
1504
|
+
if (m_keyNum != -2)
|
|
1505
|
+
{
|
|
1506
|
+
if (setNonKey(false))
|
|
1507
|
+
{
|
|
1508
|
+
m_stat = m_table->file->ha_rnd_pos(m_table->record[0],
|
|
1509
|
+
(uchar*)position(true));
|
|
1510
|
+
if (m_stat != 0)
|
|
1511
|
+
return;
|
|
1512
|
+
}
|
|
1513
|
+
}
|
|
1514
|
+
m_stat = m_table->file->ha_rnd_next(m_table->record[0]);
|
|
1515
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1516
|
+
}
|
|
1348
1517
|
}
|
|
1349
1518
|
|
|
1350
1519
|
void table::stepPrev()
|
|
1351
1520
|
{
|
|
1352
|
-
|
|
1353
|
-
|
|
1354
|
-
|
|
1355
|
-
|
|
1356
|
-
|
|
1357
|
-
|
|
1358
|
-
|
|
1359
|
-
|
|
1360
|
-
}
|
|
1361
|
-
|
|
1362
|
-
void table::readRecords(IReadRecordsHandler* hdr, bool includeCurrent, int type
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
|
|
1369
|
-
|
|
1370
|
-
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
|
|
1382
|
-
|
|
1383
|
-
|
|
1384
|
-
|
|
1385
|
-
|
|
1386
|
-
|
|
1387
|
-
|
|
1388
|
-
|
|
1389
|
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
|
|
1393
|
-
|
|
1394
|
-
|
|
1395
|
-
|
|
1396
|
-
|
|
1397
|
-
|
|
1398
|
-
|
|
1399
|
-
|
|
1400
|
-
|
|
1401
|
-
|
|
1402
|
-
|
|
1403
|
-
|
|
1404
|
-
|
|
1405
|
-
|
|
1406
|
-
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1410
|
-
|
|
1411
|
-
|
|
1412
|
-
|
|
1413
|
-
|
|
1414
|
-
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
|
|
1418
|
-
|
|
1419
|
-
|
|
1420
|
-
|
|
1421
|
-
|
|
1422
|
-
|
|
1423
|
-
|
|
1424
|
-
|
|
1425
|
-
|
|
1426
|
-
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
|
|
1521
|
+
m_nonNcc = false;
|
|
1522
|
+
if (m_table->s->primary_key < m_table->s->keys)
|
|
1523
|
+
{
|
|
1524
|
+
setKeyNum(m_table->s->primary_key);
|
|
1525
|
+
getPrev();
|
|
1526
|
+
}
|
|
1527
|
+
else
|
|
1528
|
+
m_stat = STATUS_NOSUPPORT_OP;
|
|
1529
|
+
}
|
|
1530
|
+
|
|
1531
|
+
void table::readRecords(IReadRecordsHandler* hdr, bool includeCurrent, int type,
|
|
1532
|
+
bool noBookmark)
|
|
1533
|
+
{
|
|
1534
|
+
|
|
1535
|
+
if ((m_table->file->inited == handler::NONE) || !m_cursor)
|
|
1536
|
+
{
|
|
1537
|
+
m_stat = STATUS_NO_CURRENT;
|
|
1538
|
+
return;
|
|
1539
|
+
}
|
|
1540
|
+
initHandler();
|
|
1541
|
+
m_nonNcc = false;
|
|
1542
|
+
int reject = (hdr->rejectCount() == 0) ? 4096 : hdr->rejectCount();
|
|
1543
|
+
if (reject == 0xFFFF)
|
|
1544
|
+
reject = -1;
|
|
1545
|
+
int rows = hdr->maxRows();
|
|
1546
|
+
|
|
1547
|
+
// dummy bookmark , use if bobbokmark=true
|
|
1548
|
+
unsigned int tmp = 0;
|
|
1549
|
+
const uchar* bm = (unsigned char*)&tmp;
|
|
1550
|
+
|
|
1551
|
+
// Is a current position read or not?
|
|
1552
|
+
bool read = !includeCurrent;
|
|
1553
|
+
bool unlock = (!m_db.inSnapshot() && !m_db.inTransaction()) ||
|
|
1554
|
+
(m_db.inTransaction() && (m_db.transactionType() == 0));
|
|
1555
|
+
bool forword =
|
|
1556
|
+
(type == READ_RECORD_GETNEXT) || (type == READ_RECORD_STEPNEXT);
|
|
1557
|
+
while ((reject != 0) && (rows != 0))
|
|
1558
|
+
{
|
|
1559
|
+
if (read)
|
|
1560
|
+
{
|
|
1561
|
+
|
|
1562
|
+
if (unlock && !m_nounlock && m_validCursor)
|
|
1563
|
+
{
|
|
1564
|
+
m_table->file->unlock_row();
|
|
1565
|
+
m_nounlock = false;
|
|
1566
|
+
}
|
|
1567
|
+
|
|
1568
|
+
if (type == READ_RECORD_GETNEXT)
|
|
1569
|
+
m_stat = m_table->file->ha_index_next(m_table->record[0]);
|
|
1570
|
+
else if (type == READ_RECORD_GETPREV)
|
|
1571
|
+
m_stat = m_table->file->ha_index_prev(m_table->record[0]);
|
|
1572
|
+
else if (type == READ_RECORD_STEPNEXT)
|
|
1573
|
+
m_stat = m_table->file->ha_rnd_next(m_table->record[0]);
|
|
1574
|
+
else if (type == READ_RECORD_STEPPREV)
|
|
1575
|
+
{
|
|
1576
|
+
m_stat = STATUS_NOSUPPORT_OP;
|
|
1577
|
+
return;
|
|
1578
|
+
}
|
|
1579
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1580
|
+
}
|
|
1581
|
+
else
|
|
1582
|
+
read = true;
|
|
1583
|
+
|
|
1584
|
+
if (m_stat)
|
|
1585
|
+
break;
|
|
1586
|
+
int ret = hdr->match(forword);
|
|
1587
|
+
if (ret == REC_MACTH)
|
|
1588
|
+
{
|
|
1589
|
+
|
|
1590
|
+
if (!noBookmark)
|
|
1591
|
+
bm = position();
|
|
1592
|
+
m_stat = hdr->write(bm, posPtrLen());
|
|
1593
|
+
if (m_stat)
|
|
1594
|
+
break;
|
|
1595
|
+
--rows;
|
|
1596
|
+
}
|
|
1597
|
+
else if (ret == REC_NOMACTH_NOMORE)
|
|
1598
|
+
{
|
|
1599
|
+
m_stat = STATUS_REACHED_FILTER_COND;
|
|
1600
|
+
return;
|
|
1601
|
+
}
|
|
1602
|
+
else
|
|
1603
|
+
--reject;
|
|
1604
|
+
}
|
|
1605
|
+
if (reject == 0)
|
|
1606
|
+
m_stat = STATUS_LIMMIT_OF_REJECT;
|
|
1607
|
+
}
|
|
1608
|
+
|
|
1609
|
+
/* seek to pos by ref
|
|
1431
1610
|
* need before set keybuf and keynum
|
|
1432
1611
|
*/
|
|
1433
|
-
//private
|
|
1434
|
-
void table::seekPos(const uchar* rawPos)
|
|
1435
|
-
{
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
|
|
1439
|
-
|
|
1440
|
-
|
|
1441
|
-
|
|
1442
|
-
|
|
1443
|
-
|
|
1444
|
-
|
|
1612
|
+
// private
|
|
1613
|
+
void table::seekPos(const uchar* rawPos)
|
|
1614
|
+
{
|
|
1615
|
+
seekKey(HA_READ_KEY_OR_NEXT, keymap());
|
|
1616
|
+
if (m_keyNum == (int)m_table->s->primary_key)
|
|
1617
|
+
return;
|
|
1618
|
+
int cmp;
|
|
1619
|
+
while ((m_stat == 0) &&
|
|
1620
|
+
((cmp = m_table->file->cmp_ref(position(true), rawPos)) != 0))
|
|
1621
|
+
{
|
|
1622
|
+
unlockRow();
|
|
1623
|
+
m_table->file->ha_index_next_same(m_table->record[0], &m_keybuf[0],
|
|
1624
|
+
keymap());
|
|
1625
|
+
}
|
|
1445
1626
|
}
|
|
1446
1627
|
|
|
1447
1628
|
void table::movePos(const uchar* pos, char keyNum, bool sureRawValue)
|
|
1448
1629
|
{
|
|
1449
|
-
|
|
1450
|
-
|
|
1451
|
-
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
|
|
1455
|
-
|
|
1456
|
-
|
|
1457
|
-
|
|
1458
|
-
|
|
1459
|
-
|
|
1460
|
-
|
|
1461
|
-
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
|
|
1466
|
-
|
|
1467
|
-
|
|
1468
|
-
|
|
1630
|
+
const uchar* rawPos = pos;
|
|
1631
|
+
if (!sureRawValue && (m_table->file->ref_length > REF_SIZE_MAX))
|
|
1632
|
+
rawPos = bms()->getRefByBm(*(unsigned int*)pos);
|
|
1633
|
+
|
|
1634
|
+
setNonKey();
|
|
1635
|
+
unlockRow();
|
|
1636
|
+
m_stat = m_table->file->ha_rnd_pos(m_table->record[0], (uchar*)rawPos);
|
|
1637
|
+
m_cursor = (m_stat == 0);
|
|
1638
|
+
if ((keyNum == -1) || (keyNum == -64) || (keyNum == -2))
|
|
1639
|
+
return;
|
|
1640
|
+
if (m_stat == 0)
|
|
1641
|
+
{
|
|
1642
|
+
if (m_keyNum != keyNum)
|
|
1643
|
+
{ // need key change
|
|
1644
|
+
key_copy(&m_keybuf[0], m_table->record[0],
|
|
1645
|
+
&m_table->key_info[keyNum], KEYLEN_ALLCOPY);
|
|
1646
|
+
// It seek(s) until ref becomes the same, since it is a duplication
|
|
1647
|
+
// key.
|
|
1648
|
+
setKeyNum(keyNum);
|
|
1649
|
+
seekPos(rawPos);
|
|
1650
|
+
}
|
|
1651
|
+
}
|
|
1469
1652
|
}
|
|
1470
1653
|
|
|
1471
|
-
bookmarks* table::bms()
|
|
1654
|
+
bookmarks* table::bms()
|
|
1472
1655
|
{
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
|
|
1656
|
+
if (m_bms == NULL)
|
|
1657
|
+
m_bms.reset(new bookmarks(m_table->file->ref_length));
|
|
1658
|
+
return m_bms.get();
|
|
1476
1659
|
}
|
|
1477
1660
|
|
|
1478
1661
|
/** get current record bookmark (position)
|
|
@@ -1480,123 +1663,121 @@ bookmarks* table::bms()
|
|
|
1480
1663
|
*/
|
|
1481
1664
|
const uchar* table::position(bool raw)
|
|
1482
1665
|
{
|
|
1483
|
-
|
|
1484
|
-
|
|
1485
|
-
|
|
1486
|
-
|
|
1666
|
+
m_table->file->position(m_table->record[0]);
|
|
1667
|
+
// handler is set uniqu number to ref.
|
|
1668
|
+
if (!raw && (m_table->file->ref_length > REF_SIZE_MAX))
|
|
1669
|
+
return bms()->getBookmarkPtr(m_table->file->ref);
|
|
1670
|
+
return m_table->file->ref;
|
|
1487
1671
|
}
|
|
1488
1672
|
|
|
1489
|
-
uint table::posPtrLen()const
|
|
1673
|
+
uint table::posPtrLen() const
|
|
1490
1674
|
{
|
|
1491
|
-
|
|
1675
|
+
return std::min(m_table->file->ref_length, (uint)REF_SIZE_MAX);
|
|
1492
1676
|
}
|
|
1493
1677
|
|
|
1494
1678
|
ha_rows table::recordCount(bool estimate)
|
|
1495
1679
|
{
|
|
1496
|
-
|
|
1497
|
-
|
|
1498
|
-
|
|
1499
|
-
|
|
1500
|
-
|
|
1501
|
-
|
|
1502
|
-
|
|
1503
|
-
|
|
1504
|
-
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
|
|
1517
|
-
|
|
1518
|
-
|
|
1519
|
-
|
|
1520
|
-
|
|
1521
|
-
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
}
|
|
1544
|
-
m_table->file->extra(HA_EXTRA_NO_KEYREAD);
|
|
1545
|
-
m_table->read_set = &m_table->s->all_set;
|
|
1546
|
-
m_table->write_set = &m_table->s->all_set;
|
|
1547
|
-
return n;
|
|
1680
|
+
if ((m_table->file->ha_table_flags() &
|
|
1681
|
+
(HA_HAS_RECORDS | HA_STATS_RECORDS_IS_EXACT)) != 0)
|
|
1682
|
+
return m_table->file->records();
|
|
1683
|
+
if (estimate)
|
|
1684
|
+
{ // Since the answer of innodb is random, 1 returns also 0.
|
|
1685
|
+
// Since it is important, in the case of 1
|
|
1686
|
+
// , whether there is nothing or it is scan and investigate.
|
|
1687
|
+
m_table->file->info(HA_STATUS_VARIABLE | HA_STATUS_NO_LOCK);
|
|
1688
|
+
ha_rows rows = m_table->file->records();
|
|
1689
|
+
if (rows > 1)
|
|
1690
|
+
return rows;
|
|
1691
|
+
}
|
|
1692
|
+
uint n = 0;
|
|
1693
|
+
fieldBitmap fb(m_table);
|
|
1694
|
+
char keynum = m_keyNum;
|
|
1695
|
+
int inited = m_table->file->inited;
|
|
1696
|
+
m_table->file->ha_index_or_rnd_end();
|
|
1697
|
+
fb.setKeyRead(true);
|
|
1698
|
+
if (setKeyNum((char)0, false /* sorted */))
|
|
1699
|
+
{
|
|
1700
|
+
initHandler();
|
|
1701
|
+
m_stat = m_table->file->ha_index_first(m_table->record[0]);
|
|
1702
|
+
while (m_stat == 0)
|
|
1703
|
+
{
|
|
1704
|
+
n++;
|
|
1705
|
+
m_stat = m_table->file->ha_index_next(m_table->record[0]);
|
|
1706
|
+
}
|
|
1707
|
+
fb.setKeyRead(false);
|
|
1708
|
+
|
|
1709
|
+
// restore index init
|
|
1710
|
+
if ((inited == (int)handler::INDEX) && (m_keyNum != keynum))
|
|
1711
|
+
setKeyNum(keynum);
|
|
1712
|
+
else if (inited == (int)handler::RND)
|
|
1713
|
+
setNonKey(true /* scan */);
|
|
1714
|
+
}
|
|
1715
|
+
else
|
|
1716
|
+
{
|
|
1717
|
+
setNonKey(true /* scan */);
|
|
1718
|
+
initHandler();
|
|
1719
|
+
m_stat = m_table->file->ha_rnd_next(m_table->record[0]);
|
|
1720
|
+
while (m_stat == 0)
|
|
1721
|
+
{
|
|
1722
|
+
++n;
|
|
1723
|
+
m_stat = m_table->file->ha_rnd_next(m_table->record[0]);
|
|
1724
|
+
}
|
|
1725
|
+
}
|
|
1726
|
+
return n;
|
|
1548
1727
|
}
|
|
1549
1728
|
|
|
1550
1729
|
void table::clearBuffer()
|
|
1551
1730
|
{
|
|
1552
|
-
|
|
1553
|
-
empty_record(m_table);
|
|
1731
|
+
empty_record(m_table);
|
|
1554
1732
|
}
|
|
1555
1733
|
|
|
1556
1734
|
bool table::isNisKey(char num) const
|
|
1557
1735
|
{
|
|
1558
|
-
|
|
1559
|
-
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
|
|
1566
|
-
|
|
1736
|
+
if ((num >= 0) && (num < (short)m_table->s->keys))
|
|
1737
|
+
{
|
|
1738
|
+
Field* fd = m_table->key_info[num].key_part[0].field;
|
|
1739
|
+
// Nis is only in a head segment.
|
|
1740
|
+
if (isNisField(fd->field_name))
|
|
1741
|
+
return true;
|
|
1742
|
+
else if ((fd->pack_length() == 1) && (fd->type() == MYSQL_TYPE_TINY) &&
|
|
1743
|
+
fd->null_bit)
|
|
1744
|
+
return true;
|
|
1745
|
+
}
|
|
1746
|
+
return false;
|
|
1567
1747
|
}
|
|
1568
1748
|
|
|
1569
1749
|
bool setNullIf(KEY& key)
|
|
1570
1750
|
{
|
|
1571
|
-
|
|
1572
|
-
|
|
1573
|
-
|
|
1574
|
-
|
|
1575
|
-
|
|
1576
|
-
|
|
1577
|
-
|
|
1578
|
-
|
|
1579
|
-
|
|
1580
|
-
|
|
1581
|
-
|
|
1582
|
-
|
|
1583
|
-
|
|
1584
|
-
|
|
1585
|
-
|
|
1586
|
-
|
|
1587
|
-
|
|
1588
|
-
|
|
1589
|
-
|
|
1590
|
-
|
|
1591
|
-
|
|
1592
|
-
|
|
1593
|
-
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1597
|
-
|
|
1598
|
-
|
|
1599
|
-
|
|
1751
|
+
bool nullkey = false;
|
|
1752
|
+
Field* fd = key.key_part[0].field; // Nis is only in a head segment.
|
|
1753
|
+
if (isNisField(fd->field_name))
|
|
1754
|
+
{
|
|
1755
|
+
if (isNullNis(key, fd->field_name[3] == 'a'))
|
|
1756
|
+
{
|
|
1757
|
+
fd->set_null();
|
|
1758
|
+
nullkey = true;
|
|
1759
|
+
}
|
|
1760
|
+
else
|
|
1761
|
+
fd->set_notnull();
|
|
1762
|
+
}
|
|
1763
|
+
else
|
|
1764
|
+
{
|
|
1765
|
+
for (int j = 0; j < (int)key.user_defined_key_parts; j++)
|
|
1766
|
+
{
|
|
1767
|
+
fd = key.key_part[j].field;
|
|
1768
|
+
if (key.key_part[j].null_bit && fd->ptr)
|
|
1769
|
+
{
|
|
1770
|
+
if (isNull(fd))
|
|
1771
|
+
{
|
|
1772
|
+
fd->set_null();
|
|
1773
|
+
nullkey = true;
|
|
1774
|
+
}
|
|
1775
|
+
else
|
|
1776
|
+
fd->set_notnull();
|
|
1777
|
+
}
|
|
1778
|
+
}
|
|
1779
|
+
}
|
|
1780
|
+
return nullkey;
|
|
1600
1781
|
}
|
|
1601
1782
|
|
|
1602
1783
|
/** Sets null value for all null able key fields
|
|
@@ -1604,355 +1785,369 @@ bool setNullIf(KEY& key)
|
|
|
1604
1785
|
*/
|
|
1605
1786
|
int table::setKeyNullFlags()
|
|
1606
1787
|
{
|
|
1607
|
-
|
|
1608
|
-
|
|
1609
|
-
|
|
1610
|
-
|
|
1611
|
-
|
|
1612
|
-
|
|
1613
|
-
|
|
1614
|
-
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1619
|
-
|
|
1620
|
-
|
|
1621
|
-
|
|
1788
|
+
int setCount = 0;
|
|
1789
|
+
if (m_table->s->null_fields)
|
|
1790
|
+
{
|
|
1791
|
+
for (int i = 0; i < (int)m_table->s->keys; i++)
|
|
1792
|
+
{
|
|
1793
|
+
KEY& key = m_table->key_info[i];
|
|
1794
|
+
if (key.flags & HA_NULL_PART_KEY)
|
|
1795
|
+
{
|
|
1796
|
+
bool nullKey = setNullIf(key);
|
|
1797
|
+
if (nullKey && (i == m_keyNum))
|
|
1798
|
+
++setCount;
|
|
1799
|
+
}
|
|
1800
|
+
}
|
|
1801
|
+
}
|
|
1802
|
+
return setCount;
|
|
1622
1803
|
}
|
|
1623
1804
|
|
|
1624
1805
|
/** Sets null value for all null able fields
|
|
1625
1806
|
*/
|
|
1626
1807
|
void table::setFiledNullFlags()
|
|
1627
1808
|
{
|
|
1628
|
-
|
|
1629
|
-
|
|
1630
|
-
|
|
1631
|
-
|
|
1632
|
-
|
|
1633
|
-
|
|
1634
|
-
|
|
1635
|
-
|
|
1636
|
-
|
|
1809
|
+
std::vector<Field*>::iterator it = m_nonKeySegNullFields.begin();
|
|
1810
|
+
while (it != m_nonKeySegNullFields.end())
|
|
1811
|
+
{
|
|
1812
|
+
if (isNull(*it))
|
|
1813
|
+
(*it)->set_null();
|
|
1814
|
+
else
|
|
1815
|
+
(*it)->set_notnull();
|
|
1816
|
+
++it;
|
|
1817
|
+
}
|
|
1637
1818
|
}
|
|
1638
1819
|
|
|
1639
1820
|
__int64 table::insert(bool ncc)
|
|
1640
1821
|
{
|
|
1641
|
-
|
|
1642
|
-
|
|
1643
|
-
|
|
1644
|
-
|
|
1645
|
-
|
|
1646
|
-
|
|
1647
|
-
|
|
1648
|
-
|
|
1649
|
-
|
|
1650
|
-
|
|
1651
|
-
|
|
1652
|
-
|
|
1653
|
-
|
|
1654
|
-
|
|
1655
|
-
|
|
1656
|
-
|
|
1657
|
-
|
|
1658
|
-
|
|
1659
|
-
|
|
1660
|
-
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
|
|
1664
|
-
|
|
1665
|
-
|
|
1666
|
-
|
|
1667
|
-
|
|
1668
|
-
|
|
1669
|
-
|
|
1670
|
-
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
|
|
1674
|
-
|
|
1675
|
-
|
|
1822
|
+
if ((m_mode == TD_OPEN_READONLY) || !cp_is_write_lock(m_table->file))
|
|
1823
|
+
{
|
|
1824
|
+
m_stat = STATUS_INVALID_LOCKTYPE;
|
|
1825
|
+
return 0;
|
|
1826
|
+
}
|
|
1827
|
+
__int64 autoincValue = 0;
|
|
1828
|
+
|
|
1829
|
+
{
|
|
1830
|
+
autoincSetup setup(m_table);
|
|
1831
|
+
if (!ncc)
|
|
1832
|
+
key_copy(&m_nonNccKeybuf[0], m_table->record[1],
|
|
1833
|
+
&m_table->key_info[m_keyNum], KEYLEN_ALLCOPY);
|
|
1834
|
+
setKeyNullFlags();
|
|
1835
|
+
setFiledNullFlags();
|
|
1836
|
+
|
|
1837
|
+
m_stat = m_table->file->ha_write_row(m_table->record[0]);
|
|
1838
|
+
autoincValue = m_table->file->insert_id_for_cur_row;
|
|
1839
|
+
|
|
1840
|
+
if (m_stat == 0 && m_table->file->insert_id_for_cur_row)
|
|
1841
|
+
{
|
|
1842
|
+
if (!m_bulkInserting)
|
|
1843
|
+
m_table->file->ha_release_auto_increment();
|
|
1844
|
+
}
|
|
1845
|
+
}
|
|
1846
|
+
|
|
1847
|
+
if (m_stat == 0)
|
|
1848
|
+
{
|
|
1849
|
+
if (!ncc) // innodb default is ncc=-1.
|
|
1850
|
+
m_nonNcc = true;
|
|
1851
|
+
else if (!m_bulkInserting)
|
|
1852
|
+
key_copy(&m_keybuf[0], m_table->record[0],
|
|
1853
|
+
&m_table->key_info[m_keyNum], KEYLEN_ALLCOPY);
|
|
1854
|
+
m_cursor = m_validCursor = m_nounlock = (m_stat == 0);
|
|
1855
|
+
|
|
1856
|
+
m_changed = true;
|
|
1857
|
+
}
|
|
1858
|
+
return autoincValue;
|
|
1676
1859
|
}
|
|
1677
1860
|
|
|
1678
1861
|
void table::beginUpdate(char keyNum)
|
|
1679
1862
|
{
|
|
1680
|
-
|
|
1681
|
-
|
|
1682
|
-
|
|
1683
|
-
|
|
1684
|
-
|
|
1685
|
-
|
|
1686
|
-
|
|
1687
|
-
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
|
-
|
|
1691
|
-
|
|
1863
|
+
m_stat = 0;
|
|
1864
|
+
m_table->file->try_semi_consistent_read(1);
|
|
1865
|
+
beginDel();
|
|
1866
|
+
if (m_stat == 0)
|
|
1867
|
+
{
|
|
1868
|
+
if (keyNum >= 0)
|
|
1869
|
+
{
|
|
1870
|
+
key_copy(&m_nonNccKeybuf[0], m_table->record[0],
|
|
1871
|
+
&m_table->key_info[keyNum], KEYLEN_ALLCOPY);
|
|
1872
|
+
setKeyNum(keyNum);
|
|
1873
|
+
}
|
|
1874
|
+
store_record(m_table, record[1]);
|
|
1875
|
+
}
|
|
1692
1876
|
}
|
|
1693
1877
|
|
|
1694
1878
|
void table::beginDel()
|
|
1695
1879
|
{
|
|
1696
|
-
|
|
1697
|
-
|
|
1698
|
-
|
|
1699
|
-
|
|
1700
|
-
|
|
1701
|
-
|
|
1702
|
-
|
|
1703
|
-
|
|
1704
|
-
|
|
1705
|
-
|
|
1706
|
-
|
|
1707
|
-
|
|
1708
|
-
|
|
1709
|
-
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
|
|
1721
|
-
|
|
1722
|
-
|
|
1723
|
-
|
|
1724
|
-
|
|
1725
|
-
|
|
1726
|
-
|
|
1727
|
-
|
|
1728
|
-
|
|
1729
|
-
|
|
1880
|
+
if ((m_mode == TD_OPEN_READONLY) || !cp_is_write_lock(m_table->file))
|
|
1881
|
+
{
|
|
1882
|
+
m_stat = STATUS_INVALID_LOCKTYPE;
|
|
1883
|
+
return;
|
|
1884
|
+
}
|
|
1885
|
+
if (m_cursor)
|
|
1886
|
+
{
|
|
1887
|
+
m_stat = 0;
|
|
1888
|
+
/* The current position is established in advance.
|
|
1889
|
+
If not in transaction then m_validCursor=false */
|
|
1890
|
+
if (m_validCursor == false)
|
|
1891
|
+
{
|
|
1892
|
+
store_record(m_table, record[1]);
|
|
1893
|
+
if (m_keyNum >= 0)
|
|
1894
|
+
{
|
|
1895
|
+
// seek until ref is same.
|
|
1896
|
+
uchar rawPos[128];
|
|
1897
|
+
memcpy(rawPos, position(true), m_table->file->ref_length);
|
|
1898
|
+
seekPos(rawPos);
|
|
1899
|
+
}
|
|
1900
|
+
else
|
|
1901
|
+
movePos(position(true), -1, true);
|
|
1902
|
+
|
|
1903
|
+
// Has blob fileds then ignore conflicts.
|
|
1904
|
+
if ((m_table->s->blob_fields == 0) &&
|
|
1905
|
+
cmp_record(m_table, record[1]))
|
|
1906
|
+
m_stat = STATUS_CHANGE_CONFLICT;
|
|
1907
|
+
|
|
1908
|
+
m_cursor = m_validCursor = (m_stat == 0);
|
|
1909
|
+
if (m_stat)
|
|
1910
|
+
return;
|
|
1911
|
+
}
|
|
1912
|
+
}
|
|
1913
|
+
else
|
|
1914
|
+
m_stat = STATUS_NO_CURRENT;
|
|
1730
1915
|
}
|
|
1731
1916
|
|
|
1732
1917
|
/** Update current record.
|
|
1733
|
-
* It is indispensable that there is a current record in advance
|
|
1734
|
-
* and beginUpdate() is called.
|
|
1918
|
+
* It is indispensable that there is a current record in advance
|
|
1919
|
+
* and beginUpdate() is called.
|
|
1735
1920
|
*/
|
|
1736
1921
|
void table::update(bool ncc)
|
|
1737
1922
|
{
|
|
1738
|
-
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
|
|
1742
|
-
|
|
1743
|
-
|
|
1744
|
-
|
|
1745
|
-
|
|
1746
|
-
|
|
1747
|
-
|
|
1748
|
-
|
|
1749
|
-
|
|
1750
|
-
|
|
1751
|
-
|
|
1752
|
-
|
|
1753
|
-
|
|
1754
|
-
|
|
1755
|
-
|
|
1756
|
-
|
|
1757
|
-
|
|
1758
|
-
|
|
1759
|
-
|
|
1760
|
-
|
|
1761
|
-
|
|
1762
|
-
|
|
1763
|
-
|
|
1764
|
-
|
|
1765
|
-
|
|
1766
|
-
|
|
1767
|
-
|
|
1768
|
-
|
|
1769
|
-
}
|
|
1770
|
-
|
|
1771
|
-
|
|
1772
|
-
|
|
1923
|
+
if (m_stat == 0)
|
|
1924
|
+
{
|
|
1925
|
+
|
|
1926
|
+
int nullFieldsOfCurrentKey = setKeyNullFlags();
|
|
1927
|
+
setFiledNullFlags();
|
|
1928
|
+
m_stat = m_table->file->ha_update_row(m_table->record[1],
|
|
1929
|
+
m_table->record[0]);
|
|
1930
|
+
if (m_stat == 0 || (m_stat == HA_ERR_RECORD_IS_THE_SAME))
|
|
1931
|
+
{
|
|
1932
|
+
m_stat = 0;
|
|
1933
|
+
m_nonNcc = false;
|
|
1934
|
+
if (!ncc) // innodb default is ncc=-1.
|
|
1935
|
+
{
|
|
1936
|
+
// Only when the present key value is changed
|
|
1937
|
+
if (m_keyNum >= 0)
|
|
1938
|
+
{
|
|
1939
|
+
const KEY& key = m_table->key_info[m_keyNum];
|
|
1940
|
+
key_copy(&m_keybuf[0], m_table->record[0], (KEY*)&key,
|
|
1941
|
+
KEYLEN_ALLCOPY);
|
|
1942
|
+
if (memcmp(&m_nonNccKeybuf[0], &m_keybuf[0],
|
|
1943
|
+
key.key_length))
|
|
1944
|
+
{
|
|
1945
|
+
// Since the NULL key was set, a current position is
|
|
1946
|
+
// lost.
|
|
1947
|
+
if (nullFieldsOfCurrentKey == 0)
|
|
1948
|
+
m_nonNcc = true;
|
|
1949
|
+
}
|
|
1950
|
+
}
|
|
1951
|
+
}
|
|
1952
|
+
m_cursor = m_validCursor = m_nounlock = (m_stat == 0);
|
|
1953
|
+
}
|
|
1954
|
+
}
|
|
1955
|
+
if (m_stat == 0)
|
|
1956
|
+
m_changed = true;
|
|
1957
|
+
m_table->file->try_semi_consistent_read(0);
|
|
1958
|
+
}
|
|
1959
|
+
|
|
1960
|
+
/** del current record.
|
|
1961
|
+
* It is indispensable that there is a current record in advance
|
|
1773
1962
|
* and beginDel() is called.
|
|
1774
|
-
*/
|
|
1963
|
+
*/
|
|
1775
1964
|
void table::del()
|
|
1776
1965
|
{
|
|
1777
|
-
|
|
1778
|
-
|
|
1779
|
-
|
|
1780
|
-
|
|
1966
|
+
if (m_stat == 0)
|
|
1967
|
+
m_stat = m_table->file->ha_delete_row(m_table->record[0]);
|
|
1968
|
+
if (m_stat == 0)
|
|
1969
|
+
m_changed = true;
|
|
1781
1970
|
}
|
|
1782
1971
|
|
|
1972
|
+
#ifdef USE_BTRV_VARIABLE_LEN
|
|
1973
|
+
|
|
1783
1974
|
/** The offset position of the last VAR field data
|
|
1784
1975
|
*/
|
|
1785
|
-
unsigned short table::lastVarFieldPos()const
|
|
1786
|
-
{
|
|
1787
|
-
|
|
1788
|
-
|
|
1789
|
-
|
|
1976
|
+
unsigned short table::lastVarFieldPos() const
|
|
1977
|
+
{
|
|
1978
|
+
if (m_table->s->varchar_fields &&
|
|
1979
|
+
(m_recordFormatType & RF_FIXED_PLUS_VALIABLE_LEN))
|
|
1980
|
+
return (unsigned short)(lastVarFiled()->ptr -
|
|
1981
|
+
m_table->s->field[0]->ptr);
|
|
1982
|
+
return 0;
|
|
1790
1983
|
}
|
|
1791
1984
|
|
|
1792
|
-
|
|
1985
|
+
#endif
|
|
1986
|
+
|
|
1987
|
+
/** The data length of the field
|
|
1793
1988
|
*/
|
|
1794
1989
|
unsigned short table::fieldDataLen(int fieldNum) const
|
|
1795
1990
|
{
|
|
1796
|
-
|
|
1797
|
-
|
|
1798
|
-
|
|
1799
|
-
|
|
1991
|
+
Field* fd = m_table->field[fieldNum];
|
|
1992
|
+
if (isVarType(fd->type()))
|
|
1993
|
+
return var_strlen(fd);
|
|
1994
|
+
return fd->pack_length();
|
|
1800
1995
|
}
|
|
1801
1996
|
|
|
1802
1997
|
const char* table::keyName(char keyNum)
|
|
1803
1998
|
{
|
|
1804
|
-
|
|
1805
|
-
|
|
1806
|
-
|
|
1807
|
-
|
|
1808
|
-
|
|
1809
|
-
|
|
1999
|
+
if ((keyNum >= 0) && (keyNum < (short)m_table->s->keys))
|
|
2000
|
+
{
|
|
2001
|
+
KEY& key = m_table->key_info[keyNum];
|
|
2002
|
+
return key.name;
|
|
2003
|
+
}
|
|
2004
|
+
return "";
|
|
1810
2005
|
}
|
|
1811
2006
|
|
|
1812
|
-
int table::keynumByName(const char* name)const
|
|
2007
|
+
int table::keynumByName(const char* name) const
|
|
1813
2008
|
{
|
|
1814
|
-
|
|
1815
|
-
|
|
1816
|
-
|
|
1817
|
-
|
|
1818
|
-
|
|
1819
|
-
|
|
1820
|
-
|
|
1821
|
-
|
|
2009
|
+
if (*name == 0x00)
|
|
2010
|
+
name = "PRIMARY";
|
|
2011
|
+
for (int i = 0; i < (int)m_table->s->keys; i++)
|
|
2012
|
+
{
|
|
2013
|
+
if (strcmp(m_table->key_info[i].name, name) == 0)
|
|
2014
|
+
return i;
|
|
2015
|
+
}
|
|
2016
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_INVALID_KEYNAME, name);
|
|
1822
2017
|
}
|
|
1823
2018
|
|
|
1824
2019
|
void table::startBulkInsert(ha_rows rows)
|
|
1825
2020
|
{
|
|
1826
|
-
|
|
1827
|
-
|
|
2021
|
+
m_table->file->ha_start_bulk_insert(rows);
|
|
2022
|
+
m_bulkInserting = true;
|
|
1828
2023
|
}
|
|
1829
2024
|
|
|
1830
2025
|
void table::endBulkInsert()
|
|
1831
2026
|
{
|
|
1832
|
-
|
|
1833
|
-
|
|
1834
|
-
|
|
1835
|
-
|
|
1836
|
-
|
|
1837
|
-
|
|
1838
|
-
|
|
2027
|
+
if (m_bulkInserting)
|
|
2028
|
+
{
|
|
2029
|
+
key_copy(&m_keybuf[0], m_table->record[0], &m_table->key_info[m_keyNum],
|
|
2030
|
+
KEYLEN_ALLCOPY);
|
|
2031
|
+
m_bulkInserting = false;
|
|
2032
|
+
m_table->file->ha_release_auto_increment();
|
|
2033
|
+
m_table->file->ha_end_bulk_insert();
|
|
2034
|
+
}
|
|
1839
2035
|
}
|
|
1840
2036
|
|
|
1841
|
-
const char* table::valStr(int filedNum, int
|
|
2037
|
+
const char* table::valStr(int filedNum, int& size)
|
|
1842
2038
|
{
|
|
1843
|
-
|
|
2039
|
+
assert((filedNum >= 0) && (filedNum < (int)m_table->s->fields));
|
|
1844
2040
|
|
|
1845
|
-
|
|
1846
|
-
|
|
1847
|
-
|
|
1848
|
-
|
|
1849
|
-
|
|
1850
|
-
|
|
1851
|
-
|
|
1852
|
-
|
|
1853
|
-
|
|
2041
|
+
Field* fd = m_table->field[filedNum];
|
|
2042
|
+
size = -1;
|
|
2043
|
+
if (fd->is_null())
|
|
2044
|
+
return "";
|
|
2045
|
+
else
|
|
2046
|
+
fd->val_str(&m_str, &m_str);
|
|
2047
|
+
size = m_str.length();
|
|
2048
|
+
return m_str.c_ptr();
|
|
1854
2049
|
}
|
|
1855
|
-
|
|
2050
|
+
|
|
1856
2051
|
uint table::makeBlobFieldList(int fieldNum)
|
|
1857
2052
|
{
|
|
1858
|
-
|
|
1859
|
-
|
|
1860
|
-
|
|
1861
|
-
|
|
1862
|
-
|
|
1863
|
-
|
|
1864
|
-
|
|
1865
|
-
|
|
1866
|
-
|
|
1867
|
-
|
|
1868
|
-
|
|
1869
|
-
|
|
1870
|
-
|
|
1871
|
-
|
|
1872
|
-
|
|
2053
|
+
m_blobBuffer->clear();
|
|
2054
|
+
int st = fieldNum == -1 ? 0 : fieldNum;
|
|
2055
|
+
int en = fieldNum == -1 ? m_table->s->fields : fieldNum + 1;
|
|
2056
|
+
uint count = 0;
|
|
2057
|
+
for (int i = st; i < en; i++)
|
|
2058
|
+
{
|
|
2059
|
+
Field* fd = m_table->field[fieldNum];
|
|
2060
|
+
if (isBlobType(fd->type()))
|
|
2061
|
+
{
|
|
2062
|
+
m_blobBuffer->addBlob(blob_len(fd), fd->field_index,
|
|
2063
|
+
fd->ptr + blob_var_bytes(fd));
|
|
2064
|
+
count++;
|
|
2065
|
+
}
|
|
2066
|
+
}
|
|
2067
|
+
m_blobBuffer->setFieldCount(count);
|
|
2068
|
+
return count;
|
|
1873
2069
|
}
|
|
1874
2070
|
|
|
1875
2071
|
#ifdef USE_HANDLERSOCKET
|
|
1876
|
-
|
|
2072
|
+
|
|
2073
|
+
int table::fieldIndexByName(const char* name) const
|
|
1877
2074
|
{
|
|
1878
|
-
|
|
1879
|
-
|
|
1880
|
-
|
|
1881
|
-
|
|
1882
|
-
|
|
1883
|
-
|
|
1884
|
-
|
|
1885
|
-
|
|
2075
|
+
int index = 0;
|
|
2076
|
+
for (Field** fd = m_table->field; *fd; ++fd)
|
|
2077
|
+
{
|
|
2078
|
+
if (strcmp(name, (*fd)->field_name) == 0)
|
|
2079
|
+
return index;
|
|
2080
|
+
++index;
|
|
2081
|
+
}
|
|
2082
|
+
THROW_BZS_ERROR_WITH_CODEMSG(STATUS_INVALID_FIELDNAME, name);
|
|
1886
2083
|
}
|
|
1887
2084
|
|
|
1888
2085
|
void table::setUseFieldList(const std::string& csv)
|
|
1889
2086
|
{
|
|
1890
|
-
|
|
1891
|
-
|
|
1892
|
-
|
|
1893
|
-
|
|
1894
|
-
|
|
2087
|
+
std::vector<std::string> values;
|
|
2088
|
+
split(values, csv, ",");
|
|
2089
|
+
for (int i = 0; i < values.size(); i++)
|
|
2090
|
+
addUseField(fieldIndexByName(values[i].c_str()));
|
|
1895
2091
|
}
|
|
1896
2092
|
|
|
1897
2093
|
inline void setSegmentValue(const KEY_PART_INFO& segment, const std::string& v)
|
|
1898
2094
|
{
|
|
1899
|
-
|
|
1900
|
-
|
|
1901
|
-
|
|
1902
|
-
|
|
1903
|
-
|
|
2095
|
+
segment.field->set_notnull();
|
|
2096
|
+
if (!((v.size() == 1) && (v[0] == 0x00)))
|
|
2097
|
+
segment.field->store(v.c_str(), (uint)v.size(), &my_charset_bin);
|
|
2098
|
+
else
|
|
2099
|
+
segment.field->set_null();
|
|
1904
2100
|
}
|
|
1905
2101
|
|
|
1906
|
-
void table::setKeyValues(const std::vector<std::string>& values, int keypart,
|
|
2102
|
+
void table::setKeyValues(const std::vector<std::string>& values, int keypart,
|
|
2103
|
+
const std::string* inValue)
|
|
1907
2104
|
{
|
|
1908
|
-
|
|
1909
|
-
|
|
1910
|
-
|
|
1911
|
-
|
|
1912
|
-
|
|
1913
|
-
|
|
1914
|
-
|
|
1915
|
-
|
|
2105
|
+
KEY& key = m_table->key_info[m_keyNum];
|
|
2106
|
+
for (int i = 0; i < (int)key.user_defined_key_parts; i++)
|
|
2107
|
+
if (i < (int)values.size())
|
|
2108
|
+
setSegmentValue(key.key_part[i], values[i]);
|
|
2109
|
+
if (keypart != -1)
|
|
2110
|
+
setSegmentValue(key.key_part[keypart], *inValue);
|
|
2111
|
+
key_copy(&m_keybuf[0], m_table->record[0], &key, KEYLEN_ALLCOPY);
|
|
1916
2112
|
}
|
|
1917
2113
|
|
|
1918
2114
|
void table::setValue(int index, const std::string& v, int type)
|
|
1919
2115
|
{
|
|
1920
|
-
|
|
1921
|
-
|
|
1922
|
-
|
|
1923
|
-
|
|
1924
|
-
|
|
1925
|
-
|
|
1926
|
-
|
|
1927
|
-
|
|
1928
|
-
|
|
1929
|
-
|
|
1930
|
-
|
|
1931
|
-
|
|
1932
|
-
|
|
1933
|
-
|
|
1934
|
-
|
|
2116
|
+
Field* field = *(m_table->field + index);
|
|
2117
|
+
if ((v.size() == 1) && (v[0] == 0x00))
|
|
2118
|
+
field->set_null();
|
|
2119
|
+
else
|
|
2120
|
+
field->set_notnull();
|
|
2121
|
+
if ((type == UPDATE_INC) || (type == UPDATE_DEC))
|
|
2122
|
+
{
|
|
2123
|
+
__int64 old = field->val_int();
|
|
2124
|
+
__int64 intv = _atoi64(v.c_str());
|
|
2125
|
+
if (type == UPDATE_INC)
|
|
2126
|
+
field->store(old + intv, false);
|
|
2127
|
+
else
|
|
2128
|
+
field->store(old - intv, false);
|
|
2129
|
+
}
|
|
2130
|
+
else
|
|
2131
|
+
field->store(v.c_str(), (uint)v.size(), &my_charset_bin);
|
|
1935
2132
|
}
|
|
1936
2133
|
|
|
1937
2134
|
void table::setUseValues(const std::vector<std::string>& values, int type)
|
|
1938
2135
|
{
|
|
1939
|
-
|
|
1940
|
-
|
|
1941
|
-
|
|
1942
|
-
|
|
1943
|
-
|
|
2136
|
+
for (int i = 0; i < (int)values.size(); i++)
|
|
2137
|
+
{
|
|
2138
|
+
if ((int)useFields().size() > i)
|
|
2139
|
+
setValue(m_useFields[i], values[i], type);
|
|
2140
|
+
}
|
|
1944
2141
|
}
|
|
1945
2142
|
|
|
1946
2143
|
void table::checkFiledIndex(int index)
|
|
1947
2144
|
{
|
|
1948
|
-
|
|
2145
|
+
assert(index >= 0);
|
|
1949
2146
|
}
|
|
1950
2147
|
|
|
1951
|
-
#endif //USE_HANDLERSOCKET
|
|
1952
|
-
|
|
1953
|
-
}//namespace mysql
|
|
1954
|
-
}//namespace engine
|
|
1955
|
-
}//namespace db
|
|
1956
|
-
}//namespace bzs
|
|
1957
|
-
|
|
2148
|
+
#endif // USE_HANDLERSOCKET
|
|
1958
2149
|
|
|
2150
|
+
} // namespace mysql
|
|
2151
|
+
} // namespace engine
|
|
2152
|
+
} // namespace db
|
|
2153
|
+
} // namespace bzs
|