You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@trafodion.apache.org by db...@apache.org on 2017/10/03 15:19:55 UTC
[2/3] incubator-trafodion git commit: Merge branch 'master' into
MDAMCostingRewrite
Merge branch 'master' into MDAMCostingRewrite
Project: http://git-wip-us.apache.org/repos/asf/incubator-trafodion/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-trafodion/commit/200735a4
Tree: http://git-wip-us.apache.org/repos/asf/incubator-trafodion/tree/200735a4
Diff: http://git-wip-us.apache.org/repos/asf/incubator-trafodion/diff/200735a4
Branch: refs/heads/master
Commit: 200735a4442ed3402b8a43e2974b943449b7413d
Parents: fe2a6f6 e1ae98f
Author: DaveBirdsall <da...@esgyn.com>
Authored: Wed Sep 27 15:16:45 2017 -0700
Committer: GitHub <no...@github.com>
Committed: Wed Sep 27 15:16:45 2017 -0700
----------------------------------------------------------------------
core/conn/odb/Makefile | 7 +-
core/conn/odb/odb/odb.vcxproj | 342 +--
core/conn/odb/odb/odb.vcxproj.filters | 92 +-
core/conn/odb/src/JsonReader.c | 598 ++++
core/conn/odb/src/JsonReader.h | 301 ++
core/conn/odb/src/odb.c | 614 +++-
.../export/include/common/evl_sqlog_eventnum.h | 28 +-
core/sqf/monitor/linux/cluster.cxx | 1845 ++++++++++--
core/sqf/monitor/linux/cluster.h | 38 +-
core/sqf/monitor/linux/commaccept.cxx | 126 +-
core/sqf/monitor/linux/internal.h | 3 +
core/sqf/monitor/linux/msgdef.h | 2 +
core/sqf/monitor/linux/pnode.cxx | 20 +-
core/sqf/monitor/linux/pnode.h | 3 +
core/sqf/monitor/linux/redirector.cxx | 22 +-
core/sqf/monitor/linux/reqqueue.cxx | 16 +-
core/sqf/monitor/linux/reqtmleader.cxx | 19 +
core/sqf/monitor/linux/shell.cxx | 26 +-
core/sqf/monitor/linux/tmsync.cxx | 14 +-
core/sqf/monitor/linux/tmsync.h | 2 +-
core/sqf/monitor/linux/zclient.cxx | 8 +
core/sqf/sqenvcom.sh | 11 +-
core/sqf/src/seatrans/.gitignore | 1 +
core/sql/arkcmp/CmpCommon.cpp | 2 +-
core/sql/arkcmp/CmpStoredProc.h | 1 -
core/sql/arkcmp/ProcessEnv.cpp | 2 +-
core/sql/arkcmp/cmpargs.cpp | 2 +-
core/sql/arkcmp/vers_libarkcmp.cpp | 2 -
core/sql/bin/SqlciMain.cpp | 8 +-
core/sql/bin/arkcmp.cpp | 5 -
core/sql/bin/ex_esp_main.cpp | 4 -
core/sql/bin/ex_ssmp_main.cpp | 12 +-
core/sql/cli/Cli.cpp | 164 +-
core/sql/cli/Cli.h | 4 +-
core/sql/cli/CliDll.cpp | 36 -
core/sql/cli/CliExpExchange.cpp | 10 -
core/sql/cli/CliExtern.cpp | 86 -
core/sql/cli/CliImplLmExtFunc.cpp | 2 -
core/sql/cli/CliStubsStaticBuild.cpp | 23 -
core/sql/cli/Context.cpp | 32 +-
core/sql/cli/Context.h | 18 +-
core/sql/cli/Descriptor.h | 6 +-
core/sql/cli/ExSqlComp.cpp | 24 +-
core/sql/cli/Globals.cpp | 81 +-
core/sql/cli/Globals.h | 25 +-
core/sql/cli/Module.cpp | 1 -
core/sql/cli/NoWaitOp.h | 2 +-
core/sql/cli/QuasiFileManager.h | 2 +-
core/sql/cli/SQLCLIdev.h | 2 +-
core/sql/cli/Statement.cpp | 74 +-
core/sql/cli/Statement.h | 4 +-
core/sql/cli/VicKeyValuePair.h | 22 -
core/sql/cli/cli_stdh.h | 2 +-
core/sql/cli/globalsrlversion.cpp | 40 -
core/sql/cli/globalstubs.cpp | 37 -
core/sql/cli/privsrlversion.cpp | 41 -
core/sql/cli/rtdu.cpp | 37 -
core/sql/cli/rtdu.h | 24 -
core/sql/cli/rtdu2.cpp | 37 -
core/sql/cli/rtdu2.h | 28 -
core/sql/cli/sqlciSRLStubs.cpp | 32 -
core/sql/cli/sqlcli.h | 5 +-
core/sql/cli/test.cpp | 21 -
core/sql/comexe/ComKeyRange.cpp | 2 -
core/sql/comexe/ComPackDefs.h | 2 -
core/sql/comexe/ComTdb.cpp | 5 -
core/sql/comexe/ComTdb.h | 11 +-
core/sql/comexe/ComTdbCompoundStmt.cpp | 2 -
core/sql/comexe/ComTdbCompoundStmt.h | 4 -
core/sql/comexe/ComTdbControl.h | 2 -
core/sql/comexe/ComTdbExeUtil.cpp | 2 -
core/sql/comexe/ComTdbExplain.cpp | 2 -
core/sql/comexe/ComTdbHashGrby.h | 20 +-
core/sql/comexe/ComTdbHashj.cpp | 6 +-
core/sql/comexe/ComTdbHashj.h | 18 +-
core/sql/comexe/ComTdbMj.cpp | 4 +-
core/sql/comexe/ComTdbRoot.cpp | 4 +-
core/sql/comexe/ComTdbRoot.h | 8 +
core/sql/comexe/ComTdbSendBottom.cpp | 6 -
core/sql/comexe/ComTdbSendBottom.h | 2 -
core/sql/comexe/ComTdbSendTop.cpp | 6 -
core/sql/comexe/ComTdbSendTop.h | 2 +-
core/sql/comexe/ComTdbSequence.cpp | 4 -
core/sql/comexe/ComTdbSort.cpp | 9 +-
core/sql/comexe/ComTdbSort.h | 27 +-
core/sql/comexe/ComTdbSplitBottom.cpp | 4 -
core/sql/comexe/ComTdbSplitBottom.h | 2 -
core/sql/comexe/ComTdbSplitTop.cpp | 4 -
core/sql/comexe/ComTdbSplitTop.h | 4 -
core/sql/comexe/ComTdbStats.cpp | 10 +-
core/sql/comexe/ComTdbStats.h | 7 +-
core/sql/comexe/ComTdbTranspose.h | 2 -
core/sql/comexe/ComTdbTuple.cpp | 2 -
core/sql/comexe/ComTdbTuple.h | 4 -
core/sql/comexe/ComTdbUnPackRows.cpp | 4 -
core/sql/comexe/ComTdbUnPackRows.h | 2 -
core/sql/comexe/ComTdbUnion.cpp | 4 -
core/sql/comexe/ComTdbUnion.h | 4 -
core/sql/comexe/ExplainTuple.cpp | 6 +-
core/sql/comexe/FragmentDir.cpp | 2 +-
core/sql/comexe/LateBindInfo.cpp | 3 -
core/sql/comexe/PartInputDataDesc.cpp | 39 -
core/sql/common/BaseTypes.cpp | 6 +-
core/sql/common/BaseTypes.h | 9 +-
core/sql/common/CharType.cpp | 26 +-
core/sql/common/CmpCommon.h | 15 +-
core/sql/common/Collections.h | 8 +-
core/sql/common/ComAnsiNamePart.h | 4 -
core/sql/common/ComMvAttributeBitmap.cpp | 10 -
core/sql/common/ComMvAttributeBitmap.h | 2 -
core/sql/common/ComObjectName.h | 4 -
core/sql/common/ComRoutineActionNamePart.h | 6 -
core/sql/common/ComRtUtils.h | 2 -
core/sql/common/ComSmallDefs.cpp | 2 +-
core/sql/common/ComSmallDefs.h | 11 +-
core/sql/common/ComSpace.cpp | 15 +-
core/sql/common/ComSpace.h | 7 +-
core/sql/common/DateTimeType.cpp | 10 -
core/sql/common/DgBaseType.cpp | 2 +-
core/sql/common/ExprNode.cpp | 2 -
core/sql/common/Ipc.cpp | 42 +-
core/sql/common/Ipc.h | 6 -
core/sql/common/IpcGuardian.cpp | 1 -
core/sql/common/NAHeap.h | 6 +-
core/sql/common/NAMemory.cpp | 24 +-
core/sql/common/NAMemory.h | 15 +-
core/sql/common/NAString.cpp | 10 +-
core/sql/common/NAString2.cpp | 2 -
core/sql/common/NAType.cpp | 8 +-
core/sql/common/NumericType.cpp | 2 +-
core/sql/common/Platform.h | 6 -
core/sql/common/SqlExpDllDefines.h | 23 -
core/sql/common/SqlExportDllDefines.h | 20 -
core/sql/common/Timer.h | 2 -
core/sql/common/charinfo.cpp | 18 -
core/sql/common/charinfo.h | 2 -
core/sql/common/conversionSJIS.cpp | 2 -
core/sql/common/dfs2rec.h | 4 -
core/sql/common/nawstring.cpp | 6 -
core/sql/common/nchar_mp.h | 4 -
core/sql/common/purify.h | 36 -
core/sql/common/str.cpp | 10 +-
core/sql/common/wstr.cpp | 4 -
core/sql/eh/EHJmpBufStack.cpp | 2 +-
core/sql/executor/Allocator.h | 4 -
core/sql/executor/CliMsgObj.cpp | 2 -
core/sql/executor/ExAll.cpp | 1 -
core/sql/executor/ExComTdb.cpp | 8 +-
core/sql/executor/ExExeUtilGet.cpp | 3 -
core/sql/executor/ExExeUtilGetStats.cpp | 2 +-
core/sql/executor/ExExeUtilMisc.cpp | 1 -
core/sql/executor/ExHbaseAccess.h | 13 -
core/sql/executor/ExHdfsScan.h | 13 -
core/sql/executor/ExMeas.cpp | 22 -
core/sql/executor/ExMeas.h | 22 -
core/sql/executor/ExRsInfo.h | 16 +-
core/sql/executor/ExSequence.cpp | 70 +-
core/sql/executor/ExStats.cpp | 47 +-
core/sql/executor/ExStats.h | 4 +-
core/sql/executor/ExVPJoin.cpp | 2 -
core/sql/executor/ExVPJoin.h | 2 -
core/sql/executor/HdfsLogger.h | 2 -
core/sql/executor/MdamRefList.cpp | 4 -
core/sql/executor/MdamRefList.h | 4 -
core/sql/executor/MdamRefListEntry.h | 2 +-
core/sql/executor/cluster.cpp | 15 +-
core/sql/executor/cluster.h | 6 +-
core/sql/executor/dfs2fe.h | 3 +-
core/sql/executor/dmeasql.h | 22 -
core/sql/executor/ex_esp_frag_dir.cpp | 20 +-
core/sql/executor/ex_ex.cpp | 8 +-
core/sql/executor/ex_ex.h | 2 +-
core/sql/executor/ex_exe_stmt_globals.cpp | 9 +-
core/sql/executor/ex_exe_stmt_globals.h | 36 +-
core/sql/executor/ex_frag_rt.cpp | 113 +-
core/sql/executor/ex_frag_rt.h | 14 +-
core/sql/executor/ex_globals.cpp | 8 +-
core/sql/executor/ex_hash_grby.cpp | 29 +-
core/sql/executor/ex_hash_grby.h | 6 +-
core/sql/executor/ex_hashj.cpp | 4 +-
core/sql/executor/ex_mdam.cpp | 8 +-
core/sql/executor/ex_queue.cpp | 28 +-
core/sql/executor/ex_queue.h | 3 +-
core/sql/executor/ex_root.cpp | 51 +-
core/sql/executor/ex_send_bottom.cpp | 22 +-
core/sql/executor/ex_sort.cpp | 124 +-
core/sql/executor/ex_split_bottom.cpp | 14 +-
core/sql/executor/ex_split_top.cpp | 7 +-
core/sql/executor/ex_stdh.h | 2 +-
core/sql/executor/ex_tcb_private.cpp | 2 -
core/sql/executor/ex_timeout.cpp | 2 -
core/sql/executor/ex_timeout.h | 4 +-
core/sql/executor/ex_transaction.cpp | 15 +-
core/sql/executor/ex_transaction.h | 4 +-
core/sql/executor/ex_tuple.cpp | 6 -
core/sql/executor/ex_tuple.h | 10 +-
core/sql/executor/ex_tuple_flow.cpp | 22 +-
core/sql/executor/key_range.h | 4 +-
core/sql/executor/rcb.h | 20 -
core/sql/executor/stubs.cpp | 38 -
core/sql/executor/stubs2.cpp | 26 -
core/sql/executor/tempfile.cpp | 37 -
core/sql/executor/tempfile.h | 37 -
core/sql/executor/timeout_data.h | 6 +-
core/sql/exp/ExpAtp.h | 18 +-
core/sql/exp/ExpConvMxcs.cpp | 2 +-
core/sql/exp/ExpCriDesc.cpp | 2 +-
core/sql/exp/ExpCriDesc.h | 1 -
core/sql/exp/ExpDll.cpp | 3 -
core/sql/exp/ExpError.h | 1 -
core/sql/exp/ExpHbaseInterface.cpp | 6 +-
core/sql/exp/ExpLOB.h | 1 -
core/sql/exp/ExpLOBprocess.cpp | 8 +-
core/sql/exp/ExpPCode.cpp | 18 -
core/sql/exp/ExpPCodeInstruction.h | 1 -
core/sql/exp/ExpPCodeList.h | 1 -
core/sql/exp/ExpPCodeOptimizations.cpp | 2 -
core/sql/exp/ExpPCodeOptimizations.h | 2 +-
core/sql/exp/ExpSeqGen.h | 1 -
core/sql/exp/ExpSequenceFunction.cpp | 20 -
core/sql/exp/ExpSqlTupp.cpp | 2 -
core/sql/exp/ExpSqlTupp.h | 1 -
core/sql/exp/exp_aggregate.cpp | 4 -
core/sql/exp/exp_arith.cpp | 26 -
core/sql/exp/exp_bignum.cpp | 16 -
core/sql/exp/exp_clause.cpp | 36 -
core/sql/exp/exp_clause.h | 2 +-
core/sql/exp/exp_clause_derived.h | 1 -
core/sql/exp/exp_comp.cpp | 72 -
core/sql/exp/exp_conv.cpp | 144 +-
core/sql/exp/exp_datetime.cpp | 12 -
core/sql/exp/exp_expr.cpp | 6 -
core/sql/exp/exp_expr.h | 1 -
core/sql/exp/exp_fixup.cpp | 2 +-
core/sql/exp/exp_function.cpp | 29 +-
core/sql/exp/exp_like.cpp | 35 +-
core/sql/exp/exp_math_func.cpp | 11 -
core/sql/exp/exp_misc.cpp | 2 -
core/sql/exp/exp_space.cpp | 358 ---
core/sql/exp/exp_space.h | 22 -
core/sql/exp/exp_stdh.h | 3 +-
core/sql/exp/exp_tuple_desc.h | 1 -
core/sql/exp/srlversion.cpp | 41 -
core/sql/export/ComDiags.cpp | 5 -
core/sql/export/ComMemoryDiags.h | 6 -
core/sql/export/HeapLog.cpp | 5 -
core/sql/export/NABasicObject.cpp | 5 -
core/sql/export/NABasicObject.h | 29 -
core/sql/export/NAStringDef.cpp | 2 -
core/sql/export/NAStringDef.h | 2 -
core/sql/export/stubs.cpp | 53 -
core/sql/generator/GenExpGenerator.h | 2 +-
core/sql/generator/GenExplain.cpp | 56 +-
core/sql/generator/GenPreCode.cpp | 81 +-
core/sql/generator/GenProbeCache.cpp | 57 +-
core/sql/generator/GenRelEnforcer.cpp | 27 +-
core/sql/generator/GenRelGrby.cpp | 113 +-
core/sql/generator/GenRelJoin.cpp | 137 +-
core/sql/generator/GenRelMisc.cpp | 127 +-
core/sql/generator/GenRelPackedRows.cpp | 25 +-
core/sql/generator/GenRelSequence.cpp | 79 +-
core/sql/generator/Generator.cpp | 27 +-
core/sql/generator/Generator.h | 43 +-
core/sql/generator/vers_libgenerator.cpp | 2 -
core/sql/langman/LmAssert.cpp | 2 -
core/sql/langman/LmComQueue.cpp | 4 -
core/sql/langman/LmContManager.cpp | 4 -
core/sql/langman/LmDebug.cpp | 12 +-
core/sql/langman/LmJavaExceptionReporter.cpp | 6 -
core/sql/langman/LmJavaHooks.cpp | 2 -
core/sql/langman/LmLangManager.cpp | 2 -
core/sql/langman/LmResultSetJava.cpp | 2 -
core/sql/langman/LmUtility.cpp | 8 -
core/sql/langman/vers_libtdm_sqllangman.cpp | 2 -
core/sql/nskgmake/executor/Makefile | 4 -
core/sql/nskgmake/sqlcat/Makefile | 4 +-
core/sql/nskgmake/sqlci/Makefile | 3 +-
core/sql/nskgmake/sqlcilib/Makefile | 15 +-
core/sql/nskgmake/tdm_sqlcli/Makefile | 3 +-
core/sql/nskgmake/tdm_sqlshare/Makefile | 3 +-
core/sql/optimizer/Analyzer.cpp | 128 +-
core/sql/optimizer/Analyzer.h | 40 -
core/sql/optimizer/AppliedStatMan.cpp | 6 -
core/sql/optimizer/AppliedStatMan.h | 2 -
core/sql/optimizer/BindItemExpr.cpp | 8 +-
core/sql/optimizer/BindRI.cpp | 2 -
core/sql/optimizer/BindRelExpr.cpp | 24 -
core/sql/optimizer/BindWA.cpp | 8 -
core/sql/optimizer/ChangesTable.cpp | 16 +-
core/sql/optimizer/ChangesTable.h | 14 +-
core/sql/optimizer/ClusteredBitmap.cpp | 4 -
core/sql/optimizer/CmpProcess.cpp | 2 -
core/sql/optimizer/ColStatDesc.cpp | 60 +-
core/sql/optimizer/ColStatDesc.h | 2 -
core/sql/optimizer/ColumnDesc.cpp | 2 -
core/sql/optimizer/ColumnDesc.h | 2 -
core/sql/optimizer/ColumnNameMap.h | 2 -
core/sql/optimizer/ControlDB.cpp | 2 -
core/sql/optimizer/ControlDB.h | 4 -
core/sql/optimizer/Cost.cpp | 30 -
core/sql/optimizer/CostScalar.h | 27 +-
core/sql/optimizer/EncodedValue.cpp | 4 -
core/sql/optimizer/EstLogProp.cpp | 4 -
core/sql/optimizer/EstLogProp.h | 4 +-
core/sql/optimizer/GroupAttr.cpp | 14 +-
core/sql/optimizer/ImplRule.cpp | 74 +-
core/sql/optimizer/Inlining.cpp | 8 -
core/sql/optimizer/Inlining.h | 6 +-
core/sql/optimizer/ItemArith.h | 2 +-
core/sql/optimizer/ItemColRef.h | 14 +-
core/sql/optimizer/ItemConstr.h | 2 +-
core/sql/optimizer/ItemExpr.cpp | 26 +-
core/sql/optimizer/ItemExpr.h | 8 +-
core/sql/optimizer/ItmBitMuxFunction.cpp | 2 -
core/sql/optimizer/ItmBitMuxFunction.h | 2 -
core/sql/optimizer/ItmFlowControlFunction.cpp | 6 -
core/sql/optimizer/LargeScopeRules.cpp | 38 -
core/sql/optimizer/MVCandidates.cpp | 38 +-
core/sql/optimizer/MVCandidates.h | 2 -
core/sql/optimizer/MVInfo.cpp | 18 -
core/sql/optimizer/MjvBuilder.cpp | 6 -
core/sql/optimizer/MultiJoin.cpp | 18 +-
core/sql/optimizer/MultiJoin.h | 4 -
core/sql/optimizer/MvLog.cpp | 2 -
core/sql/optimizer/MvLog.h | 2 -
core/sql/optimizer/MvMultiTxnMavBuilder.cpp | 14 -
core/sql/optimizer/MvRefreshBuilder.cpp | 32 -
core/sql/optimizer/MvRefreshBuilder.h | 2 -
core/sql/optimizer/NAClusterInfo.cpp | 8 -
core/sql/optimizer/NAClusterInfo.h | 2 -
core/sql/optimizer/NAColumn.cpp | 8 -
core/sql/optimizer/NATable.cpp | 10 -
core/sql/optimizer/NATable.h | 6 -
core/sql/optimizer/NodeMap.cpp | 12 -
core/sql/optimizer/NormItemExpr.cpp | 2 +-
core/sql/optimizer/NormRelExpr.cpp | 3 -
core/sql/optimizer/ObjectNames.cpp | 4 -
core/sql/optimizer/OptRange.cpp | 30 +-
core/sql/optimizer/OptTrigger.cpp | 10 +-
core/sql/optimizer/OptTrigger.h | 8 +-
core/sql/optimizer/PackedColDesc.cpp | 2 -
core/sql/optimizer/PackedColDesc.h | 2 -
core/sql/optimizer/PartFunc.cpp | 38 -
core/sql/optimizer/PartFunc.h | 2 -
core/sql/optimizer/PartReq.cpp | 26 -
core/sql/optimizer/PartReq.h | 6 -
core/sql/optimizer/PhyProp.cpp | 9 +-
core/sql/optimizer/PhyProp.h | 8 +-
core/sql/optimizer/QRDescGenerator.cpp | 16 +-
core/sql/optimizer/QueryGraph.cpp | 2 -
core/sql/optimizer/QueryRewriteHandler.cpp | 18 +-
core/sql/optimizer/QueryRewriteHandler.h | 2 +-
core/sql/optimizer/Refresh.cpp | 2 -
core/sql/optimizer/RelEnforcer.h | 9 +-
core/sql/optimizer/RelExpr.cpp | 91 +-
core/sql/optimizer/RelExpr.h | 19 +-
core/sql/optimizer/RelGrby.h | 2 +-
core/sql/optimizer/RelJoin.h | 2 +-
core/sql/optimizer/RelProbeCache.h | 2 +-
core/sql/optimizer/RelSequence.h | 2 +-
core/sql/optimizer/Rule.cpp | 14 -
core/sql/optimizer/Rule.h | 8 -
core/sql/optimizer/ScanOptimizer.cpp | 68 +-
core/sql/optimizer/SearchKey.cpp | 12 +-
core/sql/optimizer/Stats.cpp | 92 +-
core/sql/optimizer/Stats.h | 4 -
core/sql/optimizer/SynthType.cpp | 28 +-
core/sql/optimizer/TableDesc.cpp | 8 +-
core/sql/optimizer/TableDesc.h | 4 -
core/sql/optimizer/TransRule.cpp | 4 +-
core/sql/optimizer/TransRule.h | 42 +-
core/sql/optimizer/TriggerDB.cpp | 16 -
core/sql/optimizer/Triggers.cpp | 18 -
core/sql/optimizer/Triggers.h | 15 +-
core/sql/optimizer/ValueDesc.cpp | 4 +-
core/sql/optimizer/costmethod.cpp | 58 +-
core/sql/optimizer/disjunct.h | 2 -
core/sql/optimizer/mdam.cpp | 28 +-
core/sql/optimizer/memo.cpp | 12 +-
core/sql/optimizer/opt.cpp | 16 -
core/sql/optimizer/tasks.cpp | 22 -
core/sql/optimizer/vers_liboptimizer.cpp | 2 -
core/sql/parser/BindStmtDDL.cpp | 4 -
.../ElemDDLCreateMVOneAttributeTableList.cpp | 2 -
.../ElemDDLCreateMVOneAttributeTableList.h | 2 -
core/sql/parser/ElemDDLLobAttrs.h | 2 -
core/sql/parser/ElemDDLLoggable.h | 1 -
core/sql/parser/ElemDDLNode.cpp | 2 +-
core/sql/parser/ElemDDLPartition.cpp | 2 +-
core/sql/parser/ElemDDLTableFeature.h | 1 -
core/sql/parser/HvRoles_templ.cpp | 2 +-
core/sql/parser/StmtDDLAlterMV.h | 4 -
core/sql/parser/StmtDDLCreate.cpp | 2 -
.../parser/StmtDDLCreateComponentPrivilege.h | 2 -
core/sql/parser/StmtDDLCreateMV.h | 8 -
core/sql/parser/StmtDDLCreateTrigger.h | 2 -
core/sql/parser/StmtDDLDrop.cpp | 2 -
core/sql/parser/StmtDDLDropComponentPrivilege.h | 2 -
core/sql/parser/StmtDDLDropMV.h | 2 -
.../sql/parser/StmtDDLGrantComponentPrivilege.h | 2 -
core/sql/parser/StmtDDLNode.cpp | 8 -
.../parser/StmtDDLRevokeComponentPrivilege.h | 2 -
core/sql/parser/sqlparser.y | 6 +-
core/sql/parser/vers_libparser.cpp | 2 -
core/sql/qms/QRDescriptorStubs.cpp | 2 -
core/sql/qms/QmpMain.cpp | 17 -
core/sql/qms/QmpPublish.cpp | 8 +-
core/sql/qms/QmsGroupLattice.cpp | 4 -
core/sql/qms/QmsInitializer.cpp | 10 -
core/sql/qms/QmsJoinGraph.cpp | 22 +-
core/sql/qms/QmsLatticeIndex.cpp | 14 -
core/sql/qms/QmsMVMemo.cpp | 10 -
core/sql/qms/QmsMain.cpp | 2 -
core/sql/qms/QmsQms.cpp | 14 -
core/sql/qms/QmsRequest.cpp | 22 +-
core/sql/qms/QmsRequest.h | 4 +-
core/sql/qms/QmsSelfJoinHandler.cpp | 6 -
core/sql/qms/QmsStubs.cpp | 2 -
core/sql/qmscommon/QRDescriptor.cpp | 118 +-
core/sql/qmscommon/QRDescriptor.h | 52 +-
core/sql/qmscommon/QRLogger.cpp | 8 +-
core/sql/qmscommon/QRLogger.h | 2 -
core/sql/qmscommon/QRQueries.cpp | 4 +-
core/sql/qmscommon/QRQueries.h | 2 -
core/sql/qmscommon/QRQueriesImpl.cpp | 16 +-
core/sql/qmscommon/QueryRewriteServer.cpp | 44 +-
core/sql/qmscommon/Range.cpp | 20 -
core/sql/qmscommon/XMLUtil.h | 14 +-
core/sql/qmscommon/vers_libqmscommon.cpp | 2 -
core/sql/refresh/RuAuditRefreshTaskExecutor.h | 2 -
core/sql/refresh/RuDeltaDef.cpp | 10 -
core/sql/refresh/RuDupElimGlobals.cpp | 4 -
core/sql/refresh/RuDupElimLogScanner.h | 2 -
core/sql/refresh/RuDupElimTaskExecutor.cpp | 10 -
core/sql/refresh/RuEmpCheckTaskExecutor.cpp | 8 -
core/sql/refresh/RuEmpCheckTaskExecutor.h | 2 -
core/sql/refresh/RuException.cpp | 8 -
core/sql/refresh/RuExecController.cpp | 8 -
core/sql/refresh/RuForceOptions.cpp | 2 -
core/sql/refresh/RuForceOptions.h | 4 -
core/sql/refresh/RuForceOptionsParser.cpp | 2 -
core/sql/refresh/RuForceOptionsParser.h | 2 -
core/sql/refresh/RuLockEquivSetTaskExecutor.h | 4 -
core/sql/refresh/RuLogCleanupTaskExecutor.cpp | 6 -
core/sql/refresh/RuLogCleanupTaskExecutor.h | 4 -
core/sql/refresh/RuMVEquivSetBuilder.cpp | 2 -
core/sql/refresh/RuMVEquivSetBuilder.h | 2 -
.../refresh/RuMultiTxnRefreshTaskExecutor.cpp | 14 -
core/sql/refresh/RuOptions.cpp | 6 -
core/sql/refresh/RuRcReleaseTaskExecutor.h | 2 -
core/sql/refresh/RuRefreshSQLComposer.cpp | 14 -
core/sql/refresh/RuRefreshTaskExecutor.cpp | 24 -
core/sql/refresh/RuSQLStatementContainer.cpp | 8 -
.../sql/refresh/RuSimpleRefreshTaskExecutor.cpp | 12 -
core/sql/refresh/RuTableSyncTaskExecutor.h | 2 -
core/sql/refresh/RuTask.cpp | 6 -
core/sql/refresh/RuTaskExecutor.cpp | 10 -
core/sql/refresh/RuTaskExecutor.h | 2 -
core/sql/refresh/RuTaskServerExecControler.cpp | 2 -
core/sql/refresh/RuTbl.cpp | 2 -
core/sql/refresh/RuTestTaskExecutor.cpp | 2 -
core/sql/refresh/RuTestTaskExecutor.h | 2 -
core/sql/refresh/RuUnAuditRefreshTaskExecutor.h | 2 -
core/sql/regress/executor/EXPECTED107 | 47 +
core/sql/regress/executor/EXPECTED131 | 4 +
core/sql/regress/executor/EXPECTED140 | 29 +-
core/sql/regress/executor/FILTER131 | 2 +
core/sql/regress/executor/FILTER140 | 2 +
core/sql/regress/executor/TEST107 | 6 +
core/sql/regress/hive/EXPECTED009 | 6 +-
core/sql/regress/hive/EXPECTED030 | 2636 ++++++++++++++++++
core/sql/regress/hive/FILTER009 | 1 +
core/sql/regress/seabase/EXPECTED010 | 532 ++--
core/sql/regress/seabase/EXPECTED011 | 14 +-
core/sql/regress/seabase/EXPECTED016 | 49 +-
core/sql/regress/tools/regress-filter-linux | 2 +
core/sql/runtimestats/CancelBroker.cpp | 14 +-
core/sql/runtimestats/RtsStubs.cpp | 2 -
core/sql/runtimestats/SqlStats.cpp | 122 +-
core/sql/runtimestats/SqlStats.h | 16 +-
core/sql/runtimestats/sscpipc.cpp | 67 +-
core/sql/runtimestats/ssmpipc.cpp | 166 +-
core/sql/smdio/vers_libsmdio.cpp | 2 -
core/sql/sort/DiskPool_base.h | 6 +-
core/sql/sort/DiskPool_sq.h | 4 +-
core/sql/sort/ScratchFileConnection.h | 2 -
core/sql/sort/SortAlgo.cpp | 2 +-
core/sql/sort/SortTopN.cpp | 6 +-
core/sql/sort/SortUtil.cpp | 23 +-
core/sql/sort/SortUtilCfg.cpp | 2 +-
core/sql/sort/SortUtilCfg.h | 6 +-
core/sql/sort/Statistics.cpp | 2 -
core/sql/sort/TourTree.cpp | 2 -
core/sql/sort/diskpool_sq.cpp | 2 +-
core/sql/sort/scratchfileconnection.cpp | 2 -
core/sql/sort/vers_libsort.cpp | 2 -
core/sql/sqlcat/ReadTableDef.cpp | 39 -
core/sql/sqlcat/ReadTableDef.h | 44 -
core/sql/sqlcat/enum.h | 20 -
core/sql/sqlcat/readRealArk.cpp | 34 -
core/sql/sqlcat/readRealArk.h | 23 -
core/sql/sqlci/CSInterface.h | 84 -
core/sql/sqlci/CharSetConstants.cpp | 47 -
core/sql/sqlci/CharSetConstants.h | 30 -
core/sql/sqlci/Define.cpp | 204 --
core/sql/sqlci/Define.h | 42 -
core/sql/sqlci/Formatter.cpp | 4 -
core/sql/sqlci/InputStmt.cpp | 42 +-
core/sql/sqlci/Log.cpp | 51 -
core/sql/sqlci/MsgCat.cpp | 76 -
core/sql/sqlci/MsgCat.h | 82 -
core/sql/sqlci/MxciEHCallBack.cpp | 53 -
core/sql/sqlci/MxciEHCallBack.h | 56 -
core/sql/sqlci/Obey.cpp | 14 -
core/sql/sqlci/Param.cpp | 8 -
core/sql/sqlci/Prepare.cpp | 11 -
core/sql/sqlci/RWInterface.cpp | 119 -
core/sql/sqlci/RWInterface.h | 155 -
core/sql/sqlci/ShellCmd.cpp | 2 +-
core/sql/sqlci/ShellCmd.h | 7 -
core/sql/sqlci/SqlCmd.cpp | 50 -
core/sql/sqlci/Sqlci.h | 3 -
core/sql/sqlci/SqlciCSCmd.cpp | 341 ---
core/sql/sqlci/SqlciCSCmd.h | 158 --
core/sql/sqlci/SqlciCSSimulator.cpp | 112 -
core/sql/sqlci/SqlciCmd.cpp | 102 +-
core/sql/sqlci/SqlciCmd.h | 45 +-
core/sql/sqlci/SqlciEnv.cpp | 80 -
core/sql/sqlci/SqlciEnv.h | 54 +-
core/sql/sqlci/SqlciError.cpp | 12 -
core/sql/sqlci/SqlciError.h | 4 -
core/sql/sqlci/SqlciHelp.cpp | 244 --
core/sql/sqlci/SqlciList_templ.h | 2 -
core/sql/sqlci/SqlciNode.cpp | 30 -
core/sql/sqlci/SqlciNode.h | 10 -
core/sql/sqlci/SqlciParser.cpp | 101 +-
core/sql/sqlci/SqlciRWCmd.cpp | 1172 --------
core/sql/sqlci/SqlciRWCmd.h | 299 --
core/sql/sqlci/SqlciRWSimulator.cpp | 375 ---
core/sql/sqlci/SqlciReset.cpp | 45 -
core/sql/sqlci/SqlciShow.cpp | 21 -
core/sql/sqlci/SqlciStats.h | 2 +-
core/sql/sqlci/SqlciStmts.cpp | 8 -
core/sql/sqlci/SqlciUsage.cpp | 889 ------
core/sql/sqlci/SqlciUtil.cpp | 59 -
core/sql/sqlci/SqlciUtil.h | 77 -
core/sql/sqlci/UtilInt.cpp | 86 -
core/sql/sqlci/UtilInt.h | 44 -
core/sql/sqlci/UtilMsg.cpp | 69 -
core/sql/sqlci/UtilMsg.h | 45 -
core/sql/sqlci/immudefs.cpp | 156 --
core/sql/sqlci/immudefs.h | 185 --
core/sql/sqlci/sqlci_lex.ll | 141 +-
core/sql/sqlci/sqlci_yacc.y | 422 +--
core/sql/sqlci/sqlclicmd.h | 4 -
core/sql/sqlci/sqlcmd.h | 24 -
core/sql/sqlcomp/CmpDescribe.cpp | 2 -
core/sql/sqlcomp/CmpMain.cpp | 36 +-
core/sql/sqlcomp/CmpMain.h | 6 +-
core/sql/sqlcomp/DefaultConstants.h | 30 +-
core/sql/sqlcomp/DefaultValidator.cpp | 4 -
core/sql/sqlcomp/DefaultValidator.h | 8 +
core/sql/sqlcomp/NADefaults.h | 4 -
core/sql/sqlcomp/NewDel.cpp | 2 -
core/sql/sqlcomp/QCache.cpp | 11 +-
core/sql/sqlcomp/nadefaults.cpp | 43 +-
core/sql/sqlcomp/parser.cpp | 4 +-
core/sql/sqlcomp/vers_libsqlcomp.cpp | 2 -
core/sql/sqlmsg/ComDiagsMsg.cpp | 2 +-
core/sql/sqlmsg/ErrorMessage.h | 1 -
core/sql/sqlmsg/GetErrorMessage.cpp | 6 +-
core/sql/sqlmsg/ParserMsg.cpp | 2 -
core/sql/sqlmxevents/logmxevent_sq.cpp | 7 -
core/sql/sqlshare/catapirequest.cpp | 1070 -------
core/sql/sqlshare/catapirequest.h | 594 ----
core/sql/udrserv/UdrAbortCallBack.cpp | 2 -
core/sql/udrserv/UdrDebug.cpp | 2 -
core/sql/udrserv/UdrFFDC.cpp | 2 -
core/sql/udrserv/UdrImplLmExtFunc.cpp | 2 -
core/sql/udrserv/UdrRSProcess.cpp | 8 -
core/sql/udrserv/UdrResultSet.cpp | 6 -
core/sql/udrserv/spinfo.cpp | 2 -
core/sql/udrserv/spinfoCallback.cpp | 6 -
core/sql/udrserv/udrglobals.cpp | 2 -
core/sql/udrserv/udrload.cpp | 2 -
core/sql/udrserv/udrserv.cpp | 10 -
core/sql/udrserv/udrunload.cpp | 4 -
core/sql/udrserv/udrutil.cpp | 2 -
core/sql/ustat/hs_cli.cpp | 22 -
core/sql/ustat/hs_cli.h | 2 -
core/sql/ustat/hs_globals.cpp | 56 +-
core/sql/ustat/hs_la.cpp | 11 +-
core/sql/ustat/hs_lex.ll | 4 +-
core/sql/ustat/hs_log.cpp | 4 +-
core/sql/ustat/hs_parser.cpp | 8 -
core/sql/ustat/hs_read.cpp | 24 +-
core/sql/ustat/hs_update.cpp | 6 +-
core/sql/ustat/hs_util.cpp | 12 -
core/sql/ustat/hs_util.h | 4 -
core/sql/ustat/vers_libustat.cpp | 2 -
win-odbc64/odbcclient/drvr35/drvrglobal.cpp | 109 +-
win-odbc64/odbcclient/drvr35/drvrglobal.h | 2 +
win-odbc64/odbcclient/drvr35/sqltocconv.cpp | 14 +-
603 files changed, 8212 insertions(+), 15349 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-trafodion/blob/200735a4/core/sql/optimizer/ScanOptimizer.cpp
----------------------------------------------------------------------
diff --cc core/sql/optimizer/ScanOptimizer.cpp
index 3ca3d6f,23caa79..2939c47
--- a/core/sql/optimizer/ScanOptimizer.cpp
+++ b/core/sql/optimizer/ScanOptimizer.cpp
@@@ -10118,1097 -9826,98 +10060,1094 @@@ const CostScalar & MDAMOptimalDisjunctP
const ValueIdSet & MDAMOptimalDisjunctPrefixWA::getOptKeyPreds() const
{ return optKeyPreds_; }
-// return true if has resuable shared basic cost for this mdam
-NABoolean
-FileScanOptimizer::getSharedCost(FileScanBasicCost * &fileScanBasicCostPtr /*out, never NULL*/
- ,NABoolean & hasLostBefore /*out*/
- ,SimpleCostVector * &disjunctsFRPtr /*out never NULL*/
- ,SimpleCostVector * &disjunctsLRPtr /*out never NULL*/
- ,CostScalar & numKBytes /*out*/
- ,MdamKey* & sharedMdamKeyPtr /*out*/
- ,NABoolean mdamTypeIsCommon /*in*/)
++
+// ZZZZZ New MDAM costing code goes here
+
+NewMDAMCostWA::NewMDAMCostWA
+(FileScanOptimizer & optimizer,
+ NABoolean mdamForced,
+ MdamKey *mdamKeyPtr,
+ const Cost *costBoundPtr,
+ const ValueIdSet & exePreds,
+ const CostScalar & singleSubsetSize) :
+ mdamWon_(FALSE)
+ ,noExePreds_(TRUE)
+ ,numKBytes_(0)
+ ,scmCost_(NULL)
+ ,mdamForced_(mdamForced)
+ ,mdamKeyPtr_(mdamKeyPtr)
+ ,costBoundPtr_(costBoundPtr)
+ ,optimizer_(optimizer)
+ ,singleSubsetSize_(singleSubsetSize)
+ ,isMultipleScanProbes_(optimizer.isMultipleProbes())
+ ,incomingScanProbes_(optimizer.getIncomingProbes())
+ ,disjunctMdamOK_(FALSE)
+
+ ,innerRowsUpperBound_( optimizer.getRawInnerHistograms().
+ getRowCount().getCeiling() )
+ ,innerBlocksUpperBound_(0) // initialized below
+ ,estimatedRowsPerBlock_( optimizer.getIndexDesc()->
+ getEstimatedRecordsPerBlock() )
+ ,disjunctIndex_(0)
+
+ ,exePreds_(exePreds) //optimizer.getRelExpr().getSelectionPred())
+ ,scanForcePtr_(optimizer.findScanForceWildCard())
+ ,outerHistograms_(optimizer.getContext().getInputLogProp()->getColStats())
{
+ // Compute inner blocks upper bound
+ computeBlocksUpperBound(innerBlocksUpperBound_ /* out*/
+ ,innerRowsUpperBound_ /* in */
+ ,estimatedRowsPerBlock_ /*in*/);
+}
- NABoolean sharedCostFound = FALSE;
- fileScanBasicCostPtr = shareBasicCost(sharedCostFound);
- if ( mdamTypeIsCommon )
+// This function computes whether MDAM wins over the cost bound
+// It sums up cost factors for all disjuncts, calculates the cost
+// and compares with the cost bound.
+void NewMDAMCostWA::compute()
+{
+ if (isMultipleScanProbes_)
{
- hasLostBefore = fileScanBasicCostPtr->hasMdamCommonLost();
- disjunctsFRPtr = &(fileScanBasicCostPtr->getFRBasicCostMdamCommon());
- disjunctsLRPtr = &(fileScanBasicCostPtr->getLRBasicCostMdamCommon());
- numKBytes = fileScanBasicCostPtr->getMdamCommonNumKBytes();
+ MDAM_DEBUG0(MTL2, "Mdam scan is multiple probes");
}
- else
+ else
{
- hasLostBefore = fileScanBasicCostPtr->hasMdamDisjunctsLost();
- disjunctsFRPtr = &(fileScanBasicCostPtr->getFRBasicCostMdamDisjuncts());
- disjunctsLRPtr = &(fileScanBasicCostPtr->getLRBasicCostMdamDisjuncts());
- numKBytes = fileScanBasicCostPtr->getMdamDisjunctsNumKBytes();
+ incomingScanProbes_ = 1; // TODO: why is this necessary?
+ MDAM_DEBUG0(MTL2, "Mdam scan is a single probe");
}
- sharedMdamKeyPtr = fileScanBasicCostPtr->getMdamKeyPtr(mdamTypeIsCommon);
- return ( sharedCostFound AND
- sharedMdamKeyPtr AND
- // disjunctsFRPtr->getCPUTime() > csZero AND
- // disjunctsLRPtr->getCPUTime() > csZero AND
- CURRSTMT_OPTDEFAULTS->reuseBasicCost() );
-}
+ // the next few variables are sums over the set of disjuncts; all of these
+ // are actually upper bounds
+ CostScalar sumMDAMFetchRows; // sum of rows fetched by MDAM key predicates
+ CostScalar sumMDAMProbeRows; // sum of rows returned on MDAM probes
+ CostScalar sumMDAMFetchSubsets; // sum of MDAM fetch subsets
+ CostScalar sumMDAMProbeSubsets; // sum of MDAM probe subsets
+ CostScalar totalSeqKBRead;
+ // -----------------------------------------------------------------------
+ // Loop through every disjunct and:
+ // 1 Find the optimal disjunct prefix for the disjunct
+ // 2 Compute the sum of the metrics of all disjuncts so far
+ // -----------------------------------------------------------------------
+ for (CollIndex disjunctIndex=0;
+ disjunctIndex < mdamKeyPtr_->getKeyDisjunctEntries();
+ disjunctIndex++)
+ {
+ // 1 find optimal prefix for disjunct
+ disjunctIndex_ = disjunctIndex;
+ computeDisjunct();
+ if(NOT disjunctMdamOK_)
+ {
+ mdamWon_ = FALSE;
+ MDAM_DEBUG0(MTL2, "Mdam scan lost because disjunctMdamOK_ is false");
+ return;
+ }
-Cost* FileScanOptimizer::newComputeCostForMultipleSubset
-( MdamKey* mdamKeyPtr,
- const Cost * costBoundPtr,
- NABoolean mdamForced,
- CostScalar & numKBytes,
- ValueIdSet exePreds,
- NABoolean checkExePreds,
- NABoolean mdamTypeIsCommon,
- MdamKey *&sharedMdamKeyPtr )
-{
- MDAM_DEBUG0(MTL2,"BEGIN MDAM Costing --------");
- MDAM_DEBUGX(MTL2, MdamTrace::printCostObject(this,
- costBoundPtr, "Cost Bound"));
- // MDAM only works for key sequenced files.
- DCMPASSERT(getIndexDesc()->getNAFileSet()->isKeySequenced());
- DCMPASSERT(getIndexDesc()->getIndexKey().entries() > 0);
+ // 2 Compute the sum of the costs of the disjuncts seen so far
- FileScanBasicCost *fileScanBasicCostPtr;
- SimpleCostVector *disjunctsFRPtr;
- SimpleCostVector *disjunctsLRPtr;
- NABoolean hasLostBefore = FALSE;
- NABoolean shareCost = getSharedCost(fileScanBasicCostPtr,
- hasLostBefore,
- disjunctsFRPtr,
- disjunctsLRPtr,
- numKBytes,
- sharedMdamKeyPtr,
- mdamTypeIsCommon);
+ // Add in counts from the disjunct just processed
+ sumMDAMFetchRows += disjunctOptMDAMFetchRows_;
+ sumMDAMProbeRows += disjunctOptMDAMProbeRows_;
+ sumMDAMFetchSubsets += disjunctOptMDAMFetchSubsets_;
+ sumMDAMProbeSubsets += disjunctOptMDAMProbeSubsets_;
+ } // for every disjunct
- SimpleCostVector & disjunctsFR = *disjunctsFRPtr;
- SimpleCostVector & disjunctsLR = *disjunctsLRPtr;
+ // Now compute the cost and see if MDAM wins or loses.
- if(shareCost){
- MDAM_DEBUG0(MTL2, "Use cached MDAM cost");
- if(hasLostBefore){
- MDAM_DEBUG0(MTL2, "MDAM Costing returning NULL cost");
- MDAM_DEBUG0(MTL2, "END MDAM Costing --------\n");
- return NULL;
- }
- else {
- Cost * costPtr = computeCostObject(disjunctsFR, disjunctsLR);
-// if ( costBoundPtr != NULL )
-// {
-// COMPARE_RESULT result =
-// costPtr->compareCosts(*costBoundPtr,
-// getContext().getReqdPhysicalProperty());
-// if ( result == MORE OR result == SAME )
-// {
-// delete costPtr;
-// MDAM_DEBUG0(MTL2, "MDAM Costing returning NULL cost");
-// MDAM_DEBUG0(MTL2, "END MDAM Costing --------\n");
-// return NULL;
-// }
+ // Note: The older version of this code computed this cost within
+ // the disjunct loop in hopes of taking an early out if the cost
+ // bound was exceeded. We don't do that here, because the I/O cost
+ // is not additive. Adding disjuncts can actually lower the I/O
+ // cost by increasing the amount of sequential I/O and lowering
+ // the amount of disk seeks.
+
+ // Worst case for sequential I/O is that we read all the blocks that a single
+ // subset scan would
+ CostScalar seqBlocksReadUpperBound =
+ (singleSubsetSize_/optimizer_.getIndexDesc()->getEstimatedRecordsPerBlock()).getCeiling();
+
+ if (optimizer_.getIndexDesc()->getPrimaryTableDesc()->getNATable()->isHbaseTable())
+ {
+ CostScalar totRowsProcessed = sumMDAMFetchRows + sumMDAMProbeRows;
+
+ CostScalar avgMDAMFetchSubsetSize = sumMDAMFetchRows / sumMDAMFetchSubsets;
+ CostScalar avgMDAMFetchBlocks =
+ (avgMDAMFetchSubsetSize/optimizer_.getIndexDesc()->getEstimatedRecordsPerBlock()).getCeiling();
+ CostScalar seqBlocksFetchUpperBound = avgMDAMFetchBlocks * sumMDAMFetchSubsets;
+ CostScalar seqBlocksProbeUpperBound = sumMDAMProbeSubsets;
+ CostScalar refinedSeqBlocksReadUpperBound = MINOF(seqBlocksReadUpperBound,
+ seqBlocksFetchUpperBound + seqBlocksProbeUpperBound);
+
+ CostScalar seeks = csZero;
+ if (refinedSeqBlocksReadUpperBound < seqBlocksReadUpperBound)
+ {
+ // Here we know that in the worst case, we won't touch all the blocks
+ // that a single subset scan will. Let's assume worst case placement
+ // of the blocks we do touch -- that is, spread them out as much
+ // as possible. The number of gaps is the number of seeks.
+ CostScalar maxNumberOfChunks = MINOF(refinedSeqBlocksReadUpperBound,
+ seqBlocksReadUpperBound - refinedSeqBlocksReadUpperBound);
+
+ // We don't count a seek for the first block. (Single subset scan
+ // costing doesn't count it either. So this makes it apples-to-apples.)
+ seeks = maxNumberOfChunks - csOne;
+ }
+
+ // Add into the seeks some overhead per subset. Not every subset will cause
+ // a seek, but there is some overhead per subset. (We subtract one, because
+ // simple scans don't charge for their one subset. That makes the comparison
+ // more applies-to-apples.)
+
+ CostScalar totalSubsets = sumMDAMProbeSubsets + sumMDAMFetchSubsets - csOne;
+ CostScalar MDAMSubsetAdjustmentFactor = ActiveSchemaDB()->getDefaults().getAsDouble(MDAM_SUBSET_FACTOR);
+ totalSubsets *= MDAMSubsetAdjustmentFactor;
+ seeks += totalSubsets;
+
+ CostScalar rowSize = optimizer_.getIndexDesc()->getRecordSizeInKb() * csOneKiloBytes;
+ CostScalar rowSizeFactor = optimizer_.scmRowSizeFactor(rowSize);
+ totRowsProcessed *= rowSizeFactor;
+
+ CostScalar randIORowSizeFactor =
+ optimizer_.scmRowSizeFactor(rowSize, ScanOptimizer::RAND_IO_ROWSIZE_FACTOR);
+ seeks *= randIORowSizeFactor;
+
+ CostScalar seqIORowSizeFactor =
+ optimizer_.scmRowSizeFactor(rowSize, ScanOptimizer::SEQ_IO_ROWSIZE_FACTOR);
+ refinedSeqBlocksReadUpperBound *= seqIORowSizeFactor;
+
+ CostScalar totalSeqKBRead = refinedSeqBlocksReadUpperBound *
+ optimizer_.getIndexDesc()->getBlockSizeInKb();
+
+ scmCost_ = optimizer_.scmComputeMDAMCostForHbase(totRowsProcessed, seeks,
+ totalSeqKBRead, incomingScanProbes_);
+ }
+ else // Not an HBase table
+ {
+ // None of the other storage engines we support currently have a direct access structure
+ // so MDAM doesn't make sense
+ disjunctMdamOK_ = FALSE;
+ mdamWon_ = FALSE;
+ MDAM_DEBUG0(MTL2, "Mdam scan lost because its not an HBase table");
+ return;
+ }
+
+ // scale up mdam cost by factor of NCM_MDAM_COST_ADJ_FACTOR --default is 1
+ CostScalar costAdj = (ActiveSchemaDB()->getDefaults()).getAsDouble(NCM_MDAM_COST_ADJ_FACTOR);
+ scmCost_->cpScmlr().scaleByValue(costAdj);
+
+ // If the cost exceeds the bound, MDAM loses
+
+ if (costBoundPtr_ != NULL &&
+ costBoundPtr_->scmCompareCosts(*scmCost_) == LESS)
+ {
+ mdamWon_ = FALSE;
+ MDAM_DEBUG0(MTL2, "Mdam scan lost due to higher cost determined by scmCompareCosts()");
+ return;
+ }
+
+ // update rows accessed
+ optimizer_.setEstRowsAccessed(sumMDAMFetchRows + sumMDAMProbeRows);
+ mdamWon_ = TRUE;
+ numKBytes_ = 0; // seqKBytesPerScan; // TODO: where does this come from?
+}
+
+// This function computes the cost factors of a MDAM disjunct
+// It computes the members below:
+// disjunctMdamOK_
+// disjunctOptMDAMFetchRows_
+// disjunctOptMDAMProbeRows_
+// disjunctOptMDAMFetchSubsets_
+// disjunctOptMDAMProbeSubsets_
+// noExePreds_
+// It also side effects member mdamKeyPtr_
+void NewMDAMCostWA::computeDisjunct()
+{
+ MDAM_DEBUG1(MTL2, "NewMDAMCostWA::computeDisjunct processing disjunct %d\n",disjunctIndex_);
+
+ // get the key preds for this disjunct:
+ NABoolean allKeyPredicates = FALSE;
+ ValueIdSet disjunctKeyPreds;
+ mdamKeyPtr_->getKeyPredicates(disjunctKeyPreds /*out*/,
+ &allKeyPredicates /*out*/,
+ disjunctIndex_ /*in*/);
+ if( NOT (allKeyPredicates) )
+ noExePreds_ = FALSE;
+
+
+ // return with a NULL cost if there are no key predicates
+ // "costBoundPtr_ == NULL" means "MDAM is forced"
+ if (disjunctKeyPreds.isEmpty() AND costBoundPtr_ != NULL)
+ {
+ MDAM_DEBUG0(MTL2, "NewMDAMCostWA::computeDisjunct(): disjunctKeyPreds is empty");
+ disjunctMdamOK_ = FALSE;
+ return; // full table scan, MDAM is worthless here
+ }
+
+ // Tabulate the key predicates using the key columns as the index
+ ColumnOrderList keyPredsByCol(optimizer_.getIndexDesc()->getIndexKey());
+ mdamKeyPtr_->getKeyPredicatesByColumn(keyPredsByCol,disjunctIndex_);
+
+ MDAM_DEBUG1(MTL2, "Disjunct: %d, keyPredsByCol:", disjunctIndex_);
+ MDAM_DEBUGX(MTL2, keyPredsByCol.print());
+ MDAM_DEBUG0(MTL2, "disjunctKeyPreds no recomputing");
+ MDAM_DEBUGX(MTL2, disjunctKeyPreds.display());
+
+ // compute the optimal prefix and the associated min cost
+ NewMDAMOptimalDisjunctPrefixWA prefixWA(optimizer_,
+ keyPredsByCol,
+ disjunctKeyPreds,
+ exePreds_,
+ outerHistograms_,
+ mdamKeyPtr_,
+ scanForcePtr_,
+ mdamForced_,
+ isMultipleScanProbes_,
+ incomingScanProbes_,
+ estimatedRowsPerBlock_,
+ innerRowsUpperBound_,
+ innerBlocksUpperBound_,
+ singleSubsetSize_,
+ disjunctIndex_);
+
+ prefixWA.compute(noExePreds_ /*out */);
+ CollIndex stopColumn = prefixWA.getStopColumn();
+ disjunctOptMDAMFetchRows_ = prefixWA.getOptMDAMFetchRows();
+ disjunctOptMDAMProbeRows_ = prefixWA.getOptMDAMProbeRows();
+ disjunctOptMDAMFetchSubsets_ = prefixWA.getOptMDAMFetchSubsets();
+ disjunctOptMDAMProbeSubsets_ = prefixWA.getOptMDAMProbeSubsets();
+
+ // Set the stop column for current disjunct:
+ mdamKeyPtr_->setStopColumn(disjunctIndex_, stopColumn);
+
+ NABoolean mdamMakeSense = TRUE;
+ if (NOT mdamForced_ AND stopColumn == 0) {
+ if (keyPredsByCol.getPredicateExpressionPtr(0) == NULL )
+ mdamMakeSense = FALSE;
+ else if (mdamKeyPtr_->getKeyDisjunctEntries() == 1)
+ {
+ // When there is a conflict in single subset, mdam should handle it
+ const ColumnOrderList::KeyColumn* currKeyColumn =
+ keyPredsByCol.getPredicateExpressionPtr(0);
+
+ NABoolean conflict =
+ ( (currKeyColumn->getType() == KeyColumns::KeyColumn:: CONFLICT)
+ OR
+ (currKeyColumn->getType() ==
+ KeyColumns::KeyColumn::CONFLICT_EQUALS)
+ OR
+ // added for patching (since it is a single disjunct now, but not a conflict)
+ // where a =10 or a=20 or a=30
+ (currKeyColumn->getType() ==
+ KeyColumns::KeyColumn::INLIST) );
+
+ if( NOT conflict )
+ {
+ // single subset should be chosen.
+ MDAM_DEBUG0(MTL2, "NewMDAMCostWA::computeDisjunct(): conflict predicate for single subset, force MDAM off");
+ mdamMakeSense = FALSE;
+ }
+ }
+ }
+
+ CollIndex noOfmissingKeyColumnsTot = 0;
+ CollIndex presentKeyColumnsTot = 0;
+
+
+ const IndexDesc *idesc = optimizer_.getFileScan().getIndexDesc();
+ const ColStatDescList& csdl = idesc->getPrimaryTableDesc()->getTableColStats();
+ Histograms hist(csdl);
+
+ Lng32 checkOption = (ActiveSchemaDB()->getDefaults()).getAsLong(MDAM_APPLY_RESTRICTION_CHECK);
+
+ if(CURRSTMT_OPTDEFAULTS->indexEliminationLevel() != OptDefaults::MINIMUM
+ && (!mdamForced_)
+ && (CmpCommon::getDefault(RANGESPEC_TRANSFORMATION) == DF_ON )
+ && checkOption >= 1
+ && (!checkMDAMadditionalRestriction(
+ keyPredsByCol,
+ optimizer_.computeLastKeyColumnOfDisjunct(keyPredsByCol),
+ hist,
+ (restrictCheckStrategy)checkOption,
+ noOfmissingKeyColumnsTot,
+ presentKeyColumnsTot))
+ )
+ {
+
+ MDAM_DEBUG0(MTL2, "NewMDAMCostWA::computeDisjunct(): MDAM additional restriction check failed");
+ mdamMakeSense = FALSE;
+ }
+ disjunctMdamOK_ = mdamMakeSense;
+}
+
+NABoolean NewMDAMCostWA::isMdamWon() const
+{
+ return mdamWon_;
+}
+
+NABoolean NewMDAMCostWA::hasNoExePreds() const
+{
+ return noExePreds_;
+}
+
+const CostScalar & NewMDAMCostWA::getNumKBytes() const
+{
+ return numKBytes_;
+}
+
+Cost * NewMDAMCostWA::getScmCost()
+{
+ return scmCost_;
+}
+
+
+// Implementation of NewMDAMOptimalDisjunctPrefixWA methods
+
+NewMDAMOptimalDisjunctPrefixWA::NewMDAMOptimalDisjunctPrefixWA
+(FileScanOptimizer & optimizer,
+ const ColumnOrderList & keyPredsByCol,
+ const ValueIdSet & disjunctKeyPreds,
+ const ValueIdSet & exePreds,
+ const Histograms & outerHistograms,
+ MdamKey *mdamKeyPtr,
+ const ScanForceWildCard *scanForcePtr,
+ NABoolean mdamForced,
+ NABoolean isMultipleProbes,
+ const CostScalar & incomingScanProbes,
+ const CostScalar & estimatedRecordsPerBlock,
+ const CostScalar & innerRowsUpperBound,
+ const CostScalar & innerBlocksUpperBound,
+ const CostScalar & singleSubsetSize,
+ CollIndex disjunctIndex)
+
+ :
+ optMDAMFetchRows_(0)
+ ,optMDAMFetchSubsets_(0)
+ ,optMDAMProbeRows_(0)
+ ,optMDAMProbeSubsets_(0)
+ ,optStopColumn_(0)
+ ,optimizer_(optimizer)
+ ,keyPredsByCol_(keyPredsByCol)
+ ,disjunctKeyPreds_(disjunctKeyPreds)
+ ,exePreds_(exePreds)
+ ,outerHistograms_(outerHistograms)
+ ,scanForcePtr_(scanForcePtr)
+ ,isMultipleProbes_(isMultipleProbes)
+ ,mdamForced_(mdamForced)
+ ,incomingScanProbes_(incomingScanProbes)
+ ,estimatedRecordsPerBlock_(estimatedRecordsPerBlock)
+ ,innerRowsUpperBound_(innerRowsUpperBound)
+ ,innerBlocksUpperBound_(innerBlocksUpperBound)
+ ,singleSubsetSize_(singleSubsetSize)
+ ,disjunctIndex_(disjunctIndex)
+ ,mdamKeyPtr_(mdamKeyPtr)
+ ,disjunctHistograms_( *(optimizer.getIndexDesc()), 0 )
+ ,optimalCost_(NULL)
+ ,crossProductApplied_(FALSE)
+ ,multiColUecInfoAvail_(disjunctHistograms_.isMultiColUecInfoAvail())
+ ,MCUECOfPriorPrefixFound_(FALSE)
+ ,MCUECOfPriorPrefix_(csZero)
+{}
+
+
+
+NewMDAMOptimalDisjunctPrefixWA::~NewMDAMOptimalDisjunctPrefixWA()
+{
+ if(optimalCost_)
+ delete optimalCost_;
+}
+
+
+// This function computes the optimal prefix of the disjunct
+
+// If we decide that the optimal prefix does not use all of the
+// key predicates, then the output parameter noExePreds will be
+// set to FALSE. Otherwise we leave it untouched.
+
+void NewMDAMOptimalDisjunctPrefixWA::compute(NABoolean & noExePreds /*out*/)
+{
+ // Cumulative probe counters (MDAM is a recursive algorithm; this
+ // represents the cost of recursion)
+
+ CostScalar cumulativeMDAMProbeRows;
+ CostScalar cumulativeMDAMProbeSubsets;
+
+ CostScalar previousColumnMDAMProbeRows(csOne);
+
+ const ValueIdList & keyColumns = optimizer_.getIndexDesc()->getIndexKey();
+ for (CollIndex i = 0; i < keyColumns.entries(); i++)
+ {
+ MDAM_DEBUG1(MTL2,"New Prefix compute, exploring column %d\n",i);
+
+ // Apply key predicates for that column to the histograms
+
+ // Because of a VEG predicate can contain more than one
+ // predicate encoded, add histograms incrementally so that
+ // the reduction of a VEG predicate for a later column
+ // than the current column position does not affect the
+ // distribution of the current column.
+ // Note that the append method receives a one-based column position,
+ // so add one to the prefix because the prefix is zero based.
+
+ disjunctHistograms_.appendHistogramForColumnPosition(i+1);
+ CostScalar ColumnUECBeforePreds = disjunctHistograms_.getColStatsForColumn(
+ optimizer_.getIndexDesc()->
+ getIndexKey()[i]).getTotalUec().getCeiling();
+ MDAM_DEBUG1(MTL2,"Column UEC from histograms before applying key predicates: %f",ColumnUECBeforePreds.value());
+
+ const ValueIdSet * predsPtr = keyPredsByCol_[i];
+ applyPredsToHistogram(predsPtr);
+ CostScalar columnUEC = disjunctHistograms_.getColStatsForColumn(
+ optimizer_.getIndexDesc()->
+ getIndexKey()[i]).getTotalUec().getCeiling();
+ MDAM_DEBUG1(MTL2,"Column UEC from histograms: %f",columnUEC.value());
+
+ // Determine if column is dense or sparse and set it accordingly
+
+ NABoolean isDense = isColumnDense(i);
+ if (isDense)
+ mdamKeyPtr_->setColumnToDense(i);
+ else
+ mdamKeyPtr_->setColumnToSparse(i);
+
+ // Analyze the key predicates
+
+ // We need to estimate how many
+ // MDAM intervals will result from them (as that determines
+ // subset counts), and also we need to know the estimated
+ // upper bound on the UEC of the key column. (Example: If we
+ // have a range predicate of the form A > ? AND A < ?, we
+ // estimate the selectivity as the square of the default
+ // selectivity for a ">" predicate. But when this is applied
+ // to histograms, it does not affect the histogram UEC
+ // estimate, only its cardinality estimate.)
+
+ CostScalar MDAMIntervalEstimate(csOne);
+ CostScalar MDAMUECEstimate(columnUEC);
+
+ if (predsPtr AND (NOT predsPtr->isEmpty()))
+ {
+ calculateMetricsFromKeyPreds(predsPtr, ColumnUECBeforePreds,
+ MDAMUECEstimate /*out*/, MDAMIntervalEstimate /*out*/);
+
+ MDAM_DEBUG1(MTL2,"Column UEC from predicates: %f",MDAMUECEstimate.value());
+ MDAM_DEBUG1(MTL2,"Interval estimate from predicates: %f",MDAMIntervalEstimate.value());
+ }
+
+ if (MDAMUECEstimate < columnUEC)
+ columnUEC = MDAMUECEstimate;
+
+ MDAM_DEBUG1(MTL2,"Minimal column UEC: %f",columnUEC.value());
+
+ // Calculate bound on column UEC from multicolumn histograms
+
+ // For example, it might be the case that there is a functional dependency
+ // within the set of key columns. If A, B, C, D has the same UEC as A, B, C,
+ // then we know that traversing to D results in at most one MDAM probe.
+ // So, we can use the ratio of the UEC of A, B, C, D divided by that of
+ // A, B, C as an upper bound on column UEC. Among others, this scenario
+ // happens when we have a "_SALT_" column or a "_DIVISION_n_" column.
+
+ if (multiColUecInfoAvail_)
+ {
+ // obtain the UEC of this prefix
+ CostScalar UECFromMCHistograms = csOne;
+ NABoolean UECFromMCFound = disjunctHistograms_.
+ estimateUecUsingMultiColUec(keyPredsByCol_, /*in*/
+ i, /*in*/
+ UECFromMCHistograms /*out*/);
+ if (UECFromMCFound)
+ {
+ MDAM_DEBUG2(MTL2, "Column UEC of prefix %d from MC histograms: %f:",
+ i, UECFromMCHistograms.value());
+
+ if (MCUECOfPriorPrefixFound_)
+ {
+ // we have UEC of this prefix and the prior prefix, so we can
+ // compute their ratio
+ CostScalar columnUECFromMCUECRatio = UECFromMCHistograms / MCUECOfPriorPrefix_;
+
+ MDAM_DEBUG1(MTL2, "Ratio of prefix UEC to prior prefix UEC: %f:",
+ columnUECFromMCUECRatio.value());
+
+ if (columnUECFromMCUECRatio < columnUEC)
+ columnUEC = columnUECFromMCUECRatio;
+
+ MDAM_DEBUG1(MTL2, "Minimal column UEC: %f", columnUEC.value());
+ }
+
+ MCUECOfPriorPrefix_ = UECFromMCHistograms; // save for next column
+ }
+
+ MCUECOfPriorPrefixFound_ = UECFromMCFound;
+ }
+
+ // Calculate the number of probe rows and probe subsets for that column
+
+ // Each probe subset returns at most one row; there will be exactly one
+ // probe subset that returns no row for each MDAM interval. Note that
+ // for dense columns, we don't do a scan for the probe; we just increment
+ // the last value we used, so MDAMProbeSubsets is zero in that case.
+
+ CostScalar MDAMProbeRows = previousColumnMDAMProbeRows * columnUEC;
+ CostScalar MDAMProbeSubsets =
+ isDense ? csZero : previousColumnMDAMProbeRows * (columnUEC + MDAMIntervalEstimate);
+
+ MDAM_DEBUG1(MTL2,"MDAM Probe Rows on this column: %f",MDAMProbeRows.value());
+ MDAM_DEBUG1(MTL2,"MDAM Probe Subsets on this column: %f",MDAMProbeSubsets.value());
+
+
+ // Calculate the number of fetch rows and fetch subsets for that column
+
+ CostScalar MDAMFetchRows = disjunctHistograms_.getColStatsForColumn(
+ optimizer_.getIndexDesc()->
+ getIndexKey()[i]).getRowcount().getCeiling();
+ CostScalar MDAMFetchSubsets = previousColumnMDAMProbeRows * MDAMIntervalEstimate;
+
+ MDAM_DEBUG1(MTL2,"MDAM Fetch Rows on this column: %f",MDAMFetchRows.value());
+ MDAM_DEBUG1(MTL2,"MDAM Fetch Subsets on this column: %f",MDAMFetchSubsets.value());
+
+ // Calculate cost assuming this column is the stop column
+
+ // A subset does not necessarily cause a disk seek. And disk seeks in
+ // general can't be predicted here as they are not additive (the block we
+ // need next might be the current block, or might be sequential after this
+ // one). So we don't try to estimate disk seeks here. Nor do we try to
+ // estimate sequential I/O here.
+
+ // However a subset does cause some positioning overhead in the Region
+ // Server apart from disk activity, as it involves traversal of index
+ // blocks (perhaps in memory). So, we include some cost in the
+ // totalSeeks param here.
+
+ CostScalar totalRowsProcessed = cumulativeMDAMProbeRows + MDAMFetchRows;
+
+ CostScalar totalSeeks = cumulativeMDAMProbeSubsets + MDAMFetchSubsets;
+ CostScalar MDAMSubsetAdjustmentFactor = ActiveSchemaDB()->getDefaults().getAsDouble(MDAM_SUBSET_FACTOR);
+ totalSeeks *= MDAMSubsetAdjustmentFactor;
+
+ CostScalar totalSeqKBRead = csZero; // not estimated here
+ Cost * currentCost = optimizer_.scmComputeMDAMCostForHbase(totalRowsProcessed, totalSeeks,
+ totalSeqKBRead, incomingScanProbes_);
+
+ // If the cost is a new minimum (or if this is the lead column), capture it
+
+ NABoolean forced = FALSE;
+ if (isMinimalCost(currentCost,i,forced /* out */))
+ //if ((optimalCost_ == NULL) OR (currentCost->compareCosts(*optimalCost_) == LESS))
+ {
+ // Capture new minimums
+ if (optimalCost_)
+ delete optimalCost_;
+
+ optMDAMFetchRows_ = MDAMFetchRows;
+ optMDAMFetchSubsets_ = MDAMFetchSubsets;
+ optMDAMProbeRows_ = cumulativeMDAMProbeRows;
+ optMDAMProbeSubsets_ = cumulativeMDAMProbeSubsets;
+
+ optimalCost_ = currentCost;
+ optStopColumn_ = i;
+
+ MDAM_DEBUG1(MTL2,"Column %d has optimal cost so far for this disjunct:",i);
+ MDAM_DEBUG1(MTL2," Optimal MDAM Probe Rows: %f",optMDAMProbeRows_.value());
+ MDAM_DEBUG1(MTL2," Optimal MDAM Probe Subsets: %f",optMDAMProbeSubsets_.value());
+ MDAM_DEBUG1(MTL2," Optimal MDAM Fetch Rows: %f",optMDAMFetchRows_.value());
+ MDAM_DEBUG1(MTL2," Optimal MDAM Fetch Subsets: %f",optMDAMFetchSubsets_.value());
+ MDAM_DEBUGX(MTL2,MdamTrace::printCostObject(&optimizer_,optimalCost_,"Optimal cost"));
+ }
+ else
+ {
+ MDAM_DEBUGX(MTL2,MdamTrace::printCostObject(&optimizer_,currentCost,"Not optimal cost"));
+ delete currentCost;
+
+ // if this is the last column and it is not optimal, indicate that there
+ // are some key predicates that must be generated as executor predicates
+ if (i == keyColumns.entries() - 1)
+ noExePreds = FALSE;
+ }
+
+ if (forced)
+ {
+ MDAM_DEBUG0(MTL2," (The choice above was forced.)");
+ }
+
+ // Update cumulative counters for the next column
+
+ cumulativeMDAMProbeRows += MDAMProbeRows;
+ cumulativeMDAMProbeSubsets += MDAMProbeSubsets;
+ previousColumnMDAMProbeRows = MDAMProbeRows;
+
+ MDAM_DEBUG1(MTL2,"Cumulative MDAM Probe Rows including this column: %f",cumulativeMDAMProbeRows.value());
+ MDAM_DEBUG1(MTL2,"Cumulative MDAM Probe Subsets including this column: %f\n",cumulativeMDAMProbeSubsets.value());
+ }
+}
+
+
+// This function applies predicates to the disjunctHistograms_
+// member. It has side effects on members
+// crossProductApplied_ and disjunctHistograms_
+void NewMDAMOptimalDisjunctPrefixWA::applyPredsToHistogram(const ValueIdSet * predsPtr)
+{
+ if ( predsPtr AND
+ (NOT predsPtr->isEmpty())
+ )
+ {
+ const SelectivityHint * selHint = optimizer_.getIndexDesc()->getPrimaryTableDesc()->getSelectivityHint();
+ const CardinalityHint * cardHint = optimizer_.getIndexDesc()->getPrimaryTableDesc()->getCardinalityHint();
+
+ MDAM_DEBUG0(MTL2, "Applying predicates to disjunct histograms");
+ MDAM_DEBUGX(MTL2, predsPtr->print());
+ if (NOT crossProductApplied_
+ AND
+ isMultipleProbes_)
+ {
+ MDAM_DEBUG0(MTL2, "Applying cross product");
+ // If this is multiple probes, we need to use joined histograms to
+ // estimate the cost factors (rows, uecs)
+ // Therefore, apply the cross product to the disjunctHistograms only once.
+ // Use the disjunctHistograms as normal after cross product is applied.
+ // ??? It seems that we need do the cross product even though there
+ // ??? is no pred on the current column. This is not being done?
+ crossProductApplied_ = TRUE;
+ disjunctHistograms_.
+ applyPredicatesWhenMultipleProbes(
+ *predsPtr
+ ,*(optimizer_.getContext().getInputLogProp())
+ ,optimizer_.getRelExpr().getGroupAttr()->
+ getCharacteristicInputs()
+ ,TRUE // doing MDAM!
+ ,selHint
+ ,cardHint
+ ,NULL
+ ,REL_SCAN);
+ }
+ else
+ disjunctHistograms_.applyPredicates(*predsPtr, (Scan &)optimizer_.getRelExpr(), selHint, cardHint, REL_SCAN);
+ }
+}
+
+// This function computes whether the column being scaned is dense or
+// sparse. Returns TRUE if dense, FALSE if sparse.
+NABoolean NewMDAMOptimalDisjunctPrefixWA::isColumnDense(CollIndex columnPosition)
+{
+ NABoolean rc = FALSE; // assume column is sparse
+ ScanForceWildCard::scanOptionEnum forceOption = ScanForceWildCard::UNDEFINED;
+
+ // Check if scan is being forced
+ // if so check if density is forced too
+ if (scanForcePtr_ && mdamForced_)
+ forceOption = scanForcePtr_->getEnumAlgorithmForColumn(columnPosition);
+
+ if (forceOption == ScanForceWildCard::COLUMN_DENSE)
+ {
+ rc = TRUE;
+ MDAM_DEBUG0(MTL2,"Column is dense (forced)");
+ }
+ else if (forceOption == ScanForceWildCard::COLUMN_SPARSE)
+ {
+ rc = FALSE;
+ MDAM_DEBUG0(MTL2,"Column is sparse (forced)");
+ }
+ else
+ {
+ // Sparse/dense was not forced, calculate it from histograms
+ // With single column histograms we can only do
+ // a good job estimating this for the first column
+ if (columnPosition == 0)
+ {
+ // why not use firstColHistogram ?
+ const ColStats & firstColumnColStats =
+ disjunctHistograms_.
+ getColStatsForColumn(optimizer_.getIndexDesc()->getIndexKey()[0]);
+ // may want to put the threshold in the defaults table:
+ const CostScalar DENSE_THRESHOLD = 0.90;
+ const CostScalar density =
+ (firstColumnColStats.getTotalUec().getCeiling()) /
+ ( firstColumnColStats.getMaxValue().getDblValue()
+ - firstColumnColStats.getMinValue().getDblValue()
+ + 1.0 );
+ if ( density > DENSE_THRESHOLD )
+ {
+ // It is dense!!!
+ rc = TRUE;
+ MDAM_DEBUG0(MTL2,"Column is dense (from histogram)");
+ }
+ else
+ {
+ // It is sparse!!!
+ rc = FALSE;
+ MDAM_DEBUG0(MTL2,"Column is sparse (from histogram)");
+ }
+ } // if columnPosition == 0
+ else
+ {
+ // columnPosition > 0, always sparse
+ rc = FALSE;
+ MDAM_DEBUG0(MTL2,"Column is sparse (non-leading column)");
+ }
+ } // dense/sparse not forced
+
+ return rc;
+}
+
+
+void NewMDAMOptimalDisjunctPrefixWA::calculateMetricsFromKeyPreds(const ValueIdSet * predsPtr,
+ const CostScalar & maxUEC, CostScalar & UECFromPreds, CostScalar & IntervalCountFromPreds)
+{
+ // If the key predicates for a column are all of the form
+ // column op constant (or column IS NULL), then the UEC of
+ // the result after applying key predicates can be read from
+ // the histogram. If even some of the key predicates are
+ // of this form, the UEC of the resulting histogram will
+ // still be a reasonable bound.
+
+ // But if there are key predicates, and none has a constant,
+ // then the row count of the histogram will be reduced but
+ // not the UEC. This is a problem for MDAM costing because
+ // we depend on the (true) UEC to determine the number of
+ // MDAM probes for the column.
+
+ // An example of this situation is a predicate X = ? on a
+ // column with UEC 1 million. We know that after X = ? is
+ // applied, the true UEC will be 1. However, the histogram
+ // will show reduced row counts but a UEC of 1,000,000.
+
+ // It's quite reasonable for the histogram code to behave
+ // this way, actually. Its foremost goal is to predict
+ // cardinalities. And scaling down the row count while
+ // retaining the 1 million UEC models the column after
+ // applying X = ? as a probability distribution.
+
+ // So, this method attempts to approximate the true UEC
+ // for such predicates by looking at the predicates
+ // themselves.
+
+ // For MDAM costing, we prefer to overestimate this UEC
+ // rather than underestimate (as MDAM performance degrades
+ // poorly when we underestimate). So, for example, when
+ // estimating an OR, we don't try to account for a possible
+ // non-empty intersection of values but instead just add
+ // the UECs. That is a reasonable upper bound without it
+ // being grossly overestimated.
+
+ // A fine point concerns the handling of range predicates.
+ // The default selectivity for A > ? is 1/3 (well, it's
+ // the value of CQD HIST_DEFAULT_SEL_FOR_PRED_RANGE).
+ // In a uniform distribution, this would translate into
+ // a UEC of 1/3 the original. For simplicity, this is the
+ // calculation we use. It's not quite right though. If we
+ // have a distribution that is skewed to the left or right
+ // (e.g. an exponential distribution), it would be more
+ // precise to find the point in the histogram where the
+ // *row count* to the right or left is 1/3 of the total,
+ // then compute the UEC of that subset of the histogram.
+ // We'll leave that complexity to a future improvement
+ // if and when it seems needed.
+
+ int lessCount = 0;
+ int greaterCount = 0;
+
+ ValueId vid = predsPtr->init();
+ predsPtr->next(vid); // expect it to return true, as caller insured predsPtr was not empty
+ calculateMetricsFromKeyPred(vid, maxUEC,
+ UECFromPreds /*out*/, IntervalCountFromPreds /*out*/,
+ lessCount /*in/out*/, greaterCount /*in/out*/);
+ predsPtr->advance(vid);
+
+ while (predsPtr->next(vid))
+ {
+ CostScalar UECFromPreds1;
+ CostScalar IntervalCountFromPreds1;
+ calculateMetricsFromKeyPred(vid, maxUEC,
+ UECFromPreds1 /*out*/, IntervalCountFromPreds1 /*out*/,
+ lessCount /*in/out*/, greaterCount /*in/out*/);
+ // this predicate is ANDed with the previous; so the
+ // UEC is at most the min of the two (but see below for
+ // special handling of the case A > ? AND A < ?)
+ UECFromPreds = MINOF(UECFromPreds,UECFromPreds1);
+ predsPtr->advance(vid);
+ }
+
+ if (UECFromPreds > maxUEC)
+ UECFromPreds = maxUEC;
+
+ // special handling if both A < ? and A > ? present
+ if ((lessCount > 0) && (greaterCount > 0))
+ {
+ CostScalar selectionFactor =
+ CostPrimitives::getBasicCostFactor(HIST_DEFAULT_SEL_FOR_PRED_RANGE);
+ CostScalar andedRange = maxUEC * selectionFactor * selectionFactor;
+ if (andedRange < UECFromPreds)
+ UECFromPreds = andedRange;
+ if (UECFromPreds < csOne)
+ UECFromPreds = csOne;
+ }
+
+}
+
+void NewMDAMOptimalDisjunctPrefixWA::calculateMetricsFromKeyPred(const ValueId & keyPred, const CostScalar & maxUEC,
+ CostScalar & UECFromPreds /*out*/, CostScalar & IntervalCountFromPreds /*out*/,
+ int & lessCount /*in/out*/, int & greaterCount /*in/out*/)
+{
+ // TODO: Add logic to make sure our key column is always on the left (otherwise our lessCount and greaterCount
+ // will be inaccurate)
+
+ ItemExpr * ie = keyPred.getItemExpr();
+ switch (ie->getOperatorType())
+ {
+ case ITM_LESS:
+ case ITM_LESS_EQ:
+ {
+ lessCount++;
+ UECFromPreds = maxUEC * CostPrimitives::getBasicCostFactor(HIST_DEFAULT_SEL_FOR_PRED_RANGE);
+ if (UECFromPreds < csOne)
+ UECFromPreds = csOne;
+ IntervalCountFromPreds = csOne;
+ break;
+ }
+ case ITM_GREATER:
+ case ITM_GREATER_EQ:
+ {
+ greaterCount++;
+ UECFromPreds = maxUEC * CostPrimitives::getBasicCostFactor(HIST_DEFAULT_SEL_FOR_PRED_RANGE);
+ if (UECFromPreds < csOne)
+ UECFromPreds = csOne;
+ IntervalCountFromPreds = csOne;
+ break;
+ }
+ case ITM_EQUAL:
+ case ITM_IS_NULL:
+ {
+ UECFromPreds = csOne;
+ IntervalCountFromPreds = csOne;
+ break;
+ }
+ case ITM_OR:
+ {
+ int localLessCount = 0;
+ int localGreaterCount = 0;
+ CostScalar UECFromPreds0;
+ CostScalar IntervalCountFromPreds0;
+ calculateMetricsFromKeyPred(ie->child(0),maxUEC,
+ UECFromPreds0,IntervalCountFromPreds0,
+ localLessCount,localGreaterCount);
+ CostScalar UECFromPreds1;
+ CostScalar IntervalCountFromPreds1;
+ calculateMetricsFromKeyPred(ie->child(1),maxUEC,
+ UECFromPreds1,IntervalCountFromPreds1,
+ localLessCount,localGreaterCount);
+ // we'll be pessimistic here and assume no overlap in the values satisfying each leg of the OR
+ UECFromPreds = UECFromPreds0 + UECFromPreds1;
+ IntervalCountFromPreds = IntervalCountFromPreds0 + IntervalCountFromPreds1;
+ break;
+ }
+ case ITM_AND:
+ {
+ CostScalar UECFromPreds0;
+ CostScalar IntervalCountFromPreds0;
+ calculateMetricsFromKeyPred(ie->child(0),maxUEC,
+ UECFromPreds0,IntervalCountFromPreds0,
+ lessCount,greaterCount);
+ CostScalar UECFromPreds1;
+ CostScalar IntervalCountFromPreds1;
+ calculateMetricsFromKeyPred(ie->child(1),maxUEC,
+ UECFromPreds1,IntervalCountFromPreds1,
+ lessCount,greaterCount);
+ // the most pessimistic assumption we can make is that the same set of rows that satisfies
+ // one leg of the AND is a subset of those that satisfy the other leg
+ UECFromPreds = MINOF(UECFromPreds0,UECFromPreds1);
+ IntervalCountFromPreds = MINOF(IntervalCountFromPreds0,IntervalCountFromPreds1);
+ break;
+ }
+ default:
+ {
+ UECFromPreds = csOne; // unexpected operator
+ IntervalCountFromPreds = csOne;
+ DCMPASSERT(ie->getOperatorType() != ITM_AND);
+ break;
+ }
+ }
+}
+
+
+// This function determines if the "currentCost" is a new minimum and returns TRUE if so,
+// FALSE otherwise. If the decision was forced, the "forced" parameter will be set to TRUE,
+// FALSE otherwise.
+
+NABoolean NewMDAMOptimalDisjunctPrefixWA::isMinimalCost(Cost * currentCost,
+ CollIndex columnPosition,
+ NABoolean & forced /* out */)
+{
+ NABoolean newMinimumFound = FALSE;
+ forced = FALSE; // assume not forced
+
+ if (scanForcePtr_ && mdamForced_)
+ {
+ if (columnPosition < scanForcePtr_->getNumMdamColumns())
+ {
+ // The user wants this column as part of the mdam key,
+ // so pretend that the cost is lower when the column is added
+ newMinimumFound = TRUE;
+ forced = TRUE;
+ }
+ else
+ {
+ if (scanForcePtr_->getMdamColumnsStatus()
+ == ScanForceWildCard::MDAM_COLUMNS_ALL)
+ {
+ // Unconditionally force all of the columns:
+ newMinimumFound = TRUE;
+ forced = TRUE;
+ }
+ else if (scanForcePtr_->getMdamColumnsStatus()
+ == ScanForceWildCard::MDAM_COLUMNS_NO_MORE)
+ {
+ // Unconditionally reject this and later columns:
+ newMinimumFound = FALSE;
+ forced = TRUE;
+ }
+ else
+ {
+ DCMPASSERT(scanForcePtr_->getMdamColumnsStatus()
+ == ScanForceWildCard::MDAM_COLUMNS_REST_BY_SYSTEM);
+ // leave forced as FALSE
+ }
+ }
+ } // if scanForcePtr_ && mdamForced_
+
+ if (NOT forced)
+ {
+ // Mdam has not been forced, or forced but with the choice
+ // of system decision for MDAM column. proceed with costing:
+
+ DCMPASSERT(currentCost != NULL);
+ newMinimumFound = (optimalCost_ == NULL) ? TRUE :
+ (currentCost->scmCompareCosts(*optimalCost_) == LESS);
+ }
+
+ return newMinimumFound;
+}
+
+const CostScalar & NewMDAMOptimalDisjunctPrefixWA::getOptMDAMProbeRows() const
+{
+ return optMDAMProbeRows_;
+}
+
+const CostScalar & NewMDAMOptimalDisjunctPrefixWA::getOptMDAMProbeSubsets() const
+{
+ return optMDAMProbeSubsets_;
+}
+
+const CostScalar & NewMDAMOptimalDisjunctPrefixWA::getOptMDAMFetchRows() const
+{
+ return optMDAMFetchRows_;
+}
+
+const CostScalar & NewMDAMOptimalDisjunctPrefixWA::getOptMDAMFetchSubsets() const
+{
+ return optMDAMFetchSubsets_;
+}
+
+CollIndex NewMDAMOptimalDisjunctPrefixWA::getStopColumn() const
+{
+ return optStopColumn_;
+}
+
+
+// ZZZZZ End of new MDAM costing code
+
+
- // LCOV_EXCL_START :cnu
+// return true if has resuable shared basic cost for this mdam
+NABoolean
+FileScanOptimizer::getSharedCost(FileScanBasicCost * &fileScanBasicCostPtr /*out, never NULL*/
+ ,NABoolean & hasLostBefore /*out*/
+ ,SimpleCostVector * &disjunctsFRPtr /*out never NULL*/
+ ,SimpleCostVector * &disjunctsLRPtr /*out never NULL*/
+ ,CostScalar & numKBytes /*out*/
+ ,MdamKey* & sharedMdamKeyPtr /*out*/
+ ,NABoolean mdamTypeIsCommon /*in*/)
+{
+
+ NABoolean sharedCostFound = FALSE;
+ fileScanBasicCostPtr = shareBasicCost(sharedCostFound);
+
+ if ( mdamTypeIsCommon )
+ {
+ hasLostBefore = fileScanBasicCostPtr->hasMdamCommonLost();
+ disjunctsFRPtr = &(fileScanBasicCostPtr->getFRBasicCostMdamCommon());
+ disjunctsLRPtr = &(fileScanBasicCostPtr->getLRBasicCostMdamCommon());
+ numKBytes = fileScanBasicCostPtr->getMdamCommonNumKBytes();
+ }
+ else
+ {
+ hasLostBefore = fileScanBasicCostPtr->hasMdamDisjunctsLost();
+ disjunctsFRPtr = &(fileScanBasicCostPtr->getFRBasicCostMdamDisjuncts());
+ disjunctsLRPtr = &(fileScanBasicCostPtr->getLRBasicCostMdamDisjuncts());
+ numKBytes = fileScanBasicCostPtr->getMdamDisjunctsNumKBytes();
+ }
+
+ sharedMdamKeyPtr = fileScanBasicCostPtr->getMdamKeyPtr(mdamTypeIsCommon);
+ return ( sharedCostFound AND
+ sharedMdamKeyPtr AND
+ // disjunctsFRPtr->getCPUTime() > csZero AND
+ // disjunctsLRPtr->getCPUTime() > csZero AND
+ CURRSTMT_OPTDEFAULTS->reuseBasicCost() );
+}
- // LCOV_EXCL_STOP
-
+
- // LCOV_EXCL_START :cnu
+
+Cost* FileScanOptimizer::newComputeCostForMultipleSubset
+( MdamKey* mdamKeyPtr,
+ const Cost * costBoundPtr,
+ NABoolean mdamForced,
+ CostScalar & numKBytes,
+ ValueIdSet exePreds,
+ NABoolean checkExePreds,
+ NABoolean mdamTypeIsCommon,
+ MdamKey *&sharedMdamKeyPtr )
+{
+ MDAM_DEBUG0(MTL2,"BEGIN MDAM Costing --------");
+ MDAM_DEBUGX(MTL2, MdamTrace::printCostObject(this,
+ costBoundPtr, "Cost Bound"));
+ // MDAM only works for key sequenced files.
+ DCMPASSERT(getIndexDesc()->getNAFileSet()->isKeySequenced());
+ DCMPASSERT(getIndexDesc()->getIndexKey().entries() > 0);
+
+ FileScanBasicCost *fileScanBasicCostPtr;
+ SimpleCostVector *disjunctsFRPtr;
+ SimpleCostVector *disjunctsLRPtr;
+ NABoolean hasLostBefore = FALSE;
+ NABoolean shareCost = getSharedCost(fileScanBasicCostPtr,
+ hasLostBefore,
+ disjunctsFRPtr,
+ disjunctsLRPtr,
+ numKBytes,
+ sharedMdamKeyPtr,
+ mdamTypeIsCommon);
+
+ SimpleCostVector & disjunctsFR = *disjunctsFRPtr;
+ SimpleCostVector & disjunctsLR = *disjunctsLRPtr;
+
+ if(shareCost){
+ MDAM_DEBUG0(MTL2, "Use cached MDAM cost");
+ if(hasLostBefore){
+ MDAM_DEBUG0(MTL2, "MDAM Costing returning NULL cost");
+ MDAM_DEBUG0(MTL2, "END MDAM Costing --------\n");
+ return NULL;
+ }
+ else {
+ Cost * costPtr = computeCostObject(disjunctsFR, disjunctsLR);
+// if ( costBoundPtr != NULL )
+// {
+// COMPARE_RESULT result =
+// costPtr->compareCosts(*costBoundPtr,
+// getContext().getReqdPhysicalProperty());
+// if ( result == MORE OR result == SAME )
+// {
+// delete costPtr;
+// MDAM_DEBUG0(MTL2, "MDAM Costing returning NULL cost");
+// MDAM_DEBUG0(MTL2, "END MDAM Costing --------\n");
+// return NULL;
+// }
// }
// use cached MDAM Cost
http://git-wip-us.apache.org/repos/asf/incubator-trafodion/blob/200735a4/core/sql/sqlcomp/DefaultConstants.h
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-trafodion/blob/200735a4/core/sql/sqlcomp/nadefaults.cpp
----------------------------------------------------------------------