本文整理汇总了C++中ExpGenerator类的典型用法代码示例。如果您正苦于以下问题:C++ ExpGenerator类的具体用法?C++ ExpGenerator怎么用?C++ ExpGenerator使用的例子?那么, 这里精选的类代码示例或许可以为您提供帮助。
在下文中一共展示了ExpGenerator类的12个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。
示例1: nowarn
short BiArithCount::codeGen(Generator * generator)
{
Attributes ** attr;
ExpGenerator * eg = generator->getExpGenerator();
if (eg->genItemExpr(this, &attr, (1+getArity()), -1) == 1)
return 0;
// if temp space is needed for this operation, set it.
if (attr[0]->isComplexType())
{
eg->addTempsLength(((ComplexType *)attr[0])->setTempSpaceInfo(getOperatorType(),
#pragma nowarn(1506) // warning elimination
eg->getTempsLength()));
#pragma warn(1506) // warning elimination
}
ex_arith_count_clause * arith_clause =
new(generator->getSpace())
ex_arith_count_clause(getOperatorType(),
attr,
generator->getSpace());
generator->getExpGenerator()->linkClause(this, arith_clause);
return 0;
}
示例2: new
short UnArith::codeGen(Generator * generator)
{
Attributes ** attr;
ExpGenerator * eg = generator->getExpGenerator();
if (eg->genItemExpr(this, &attr, (1+getArity()), -1) == 1)
return 0;
ex_arith_clause * arith_clause =
new(generator->getSpace())
ex_arith_clause(getOperatorType(), attr, generator->getSpace(),
0, FALSE);
generator->getExpGenerator()->linkClause(this, arith_clause);
return 0;
}
示例3: child
// ItmBlockFunction::codeGen
//
// The Block function executes the code represented by both its children and
// then returns the result of the right child (child(1)).
//
short ItmBlockFunction::codeGen(Generator * generator) {
// Get local handles...
//
Attributes **attr;
Space* space = generator->getSpace();
CollHeap *heap = generator->wHeap();
ExpGenerator *exp = generator->getExpGenerator();
// If this Block has already been codeGenned, then bug out...
// Otherwise, allocate space for the result if necessary and set
// attr[0] to point to the result attribute data. Also, mark this
// node as codeGenned.
//
if (exp->genItemExpr(this, &attr, 2, 0) == 1)
return 0;
// CodeGen the left child.
//
child(0)->codeGen(generator);
// CodeGen the right child.
//
child(1)->codeGen(generator);
// The result of the Block is the result of the right child. Set
// the src attribute for the convert (added below) to be the right child
// The dst attribute has already been set in genItemExpr().
//
attr[1] = generator->getMapInfo
(child(1)->castToItemExpr()->getValueId())->getAttr();
// Allocate a convert clause to move the result from child(1) to the
// result of this node. This move is necessary so that future
// side-effects of the result of child(1) -- if it is a local variable,
// for instance -- will not change the result of the Block.
//
ex_conv_clause * convClause =
new(generator->getSpace()) ex_conv_clause
(getOperatorType(), attr, space);
generator->getExpGenerator()->linkClause(this, convClause);
return 0;
}
示例4: generatePivLayout
void PartitioningFunction::generatePivLayout(
Generator *generator,
Lng32 &partitionInputDataLength,
Lng32 atp,
Lng32 atpIndex,
Attributes ***pivAttrs)
{
// assign offsets to the PIVs in a standard way
ExpGenerator *expGen = generator->getExpGenerator();
expGen->processValIdList(
getPartitionInputValuesLayout(),
ExpTupleDesc::SQLARK_EXPLODED_FORMAT,
(ULng32 &) partitionInputDataLength,
atp,
atpIndex,
NULL,
ExpTupleDesc::SHORT_FORMAT,
0,
pivAttrs);
}
示例5: codegen_and_set_attributes
short BiLogic::codeGen(Generator * generator)
{
Attributes ** attr;
if (generator->getExpGenerator()->genItemExpr(this, &attr, (1+getArity()), 0) == 1)
return 0;
Space * space = generator->getSpace();
ExpGenerator * expGen = generator->getExpGenerator();
// Normally, if code for a value id has been generated, and if
// that value id is seen again, then code is not generated. The
// location where the result is available is returned instead.
// The case of a logical operator is different. Code is generated
// again if a value id from the left child is also present in
// the right child. This is done
// because at expression evaluation time, some of the expressions
// may be skipped due to short circuit evaluation.
//
// Allocate a new map table before generating code for each child.
// This map table contains all the temporary results produced by
// the child.
// Remove this map table after generating code for each child.
generator->appendAtEnd();
expGen->incrementLevel();
codegen_and_set_attributes(generator, attr, 2);
// generator->getExpGenerator()->setClauseLinked(FALSE);
// child(0)->codeGen(generator);
// attr[1] = generator->getAttr(child(0));
// generator->getExpGenerator()->setClauseLinked(FALSE);
/* generate boolean short circuit code */
Attributes ** branch_attr = new(generator->wHeap()) Attributes * [2];
branch_attr[0] = attr[0]->newCopy(generator->wHeap());
branch_attr[0]->copyLocationAttrs(attr[0]);
branch_attr[1] = attr[1]->newCopy(generator->wHeap());
branch_attr[1]->copyLocationAttrs(attr[1]);
branch_attr[0]->resetShowplan();
ex_branch_clause * branch_clause
= new(space) ex_branch_clause(getOperatorType(), branch_attr, space);
generator->getExpGenerator()->linkClause(0, branch_clause);
generator->removeLast();
expGen->decrementLevel();
generator->appendAtEnd();
expGen->incrementLevel();
ValueIdSet markedEntries;
// This ia a MapTable entry related fix for RangeSpec transformation.
if( child(1)->getOperatorType() == ITM_RANGE_SPEC_FUNC )
markGeneratedEntries(generator, child(1)->child(1), markedEntries);
else
markGeneratedEntries(generator, child(1), markedEntries);
// if( child(1)->getOperatorType() == ITM_RANGE_SPEC_FUNC )
// child(1)->child(1)->codeGen(generator);
// else
child(1)->codeGen(generator);
ItemExpr *rightMost;
if( child(1)->getOperatorType() == ITM_RANGE_SPEC_FUNC )
rightMost = child(1)->child(1)->castToItemExpr();
else
rightMost = child(1)->castToItemExpr();
while (rightMost->getOperatorType() == ITM_ITEM_LIST)
rightMost = rightMost->child(1)->castToItemExpr();
attr[2] = generator->
getMapInfo(rightMost->getValueId())->getAttr();
ex_bool_clause * bool_clause =
new(space) ex_bool_clause(getOperatorType(), attr, space);
generator->getExpGenerator()->linkClause(this, bool_clause);
branch_clause->set_branch_clause((ex_clause *)bool_clause);
generator->removeLast();
expGen->decrementLevel();
if( child(1)->getOperatorType() == ITM_RANGE_SPEC_FUNC )
unGenerate(generator, child(1)->child(1));
else
unGenerate(generator, child(1));
generateMarkedEntries(generator, markedEntries);
return 0;
}
示例6: generateSPIOExpr
/////////////////////////////////////////////////////////////////////
//
// Contents:
//
// RelStoredProc::codeGen()
//
//////////////////////////////////////////////////////////////////////
short generateSPIOExpr(RelInternalSP * sp,
Generator * generator,
ExSPInputOutput * &inputExpr,
ExSPInputOutput * &outputExpr)
{
ExpGenerator * expGen = generator->getExpGenerator();
Space * genSpace = generator->getSpace();
// Generate input(extract) expr
FragmentDir * compFragDir = generator->getFragmentDir();
// create the fragment (independent code space) for this expression
CollIndex myFragmentId = compFragDir->pushFragment(FragmentDir::MASTER);
Space * space = generator->getSpace();
// Start generation by creating the ExSPInputOutput class.
//It will be initialized later.
ExSPInputOutput * lInputExpr = new(space) ExSPInputOutput();
ULng32 recordLen;
ExpTupleDesc * tupleDesc = NULL;
if (expGen->processValIdList(sp->procTypes(),
ExpTupleDesc::SQLARK_EXPLODED_FORMAT,
recordLen,
0, 1,
&tupleDesc,
ExpTupleDesc::LONG_FORMAT) == -1)
return -1;
ConvInstruction * cia =
(ConvInstruction *)space->allocateMemory(sp->procTypes().entries() *
sizeof(ConvInstruction));
ULng32 totalLen = space->getAllocatedSpaceSize();
lInputExpr->initialize(tupleDesc, totalLen, cia);
ExSPInputOutputPtr(lInputExpr).pack(space);
// the generated expr is generated in chunks internally by
// the space class. Make it contiguous by allocating and
// moving it to a contiguous area.
char * expr = new(generator->wHeap()) char[totalLen];
space->makeContiguous((char *)expr, totalLen);
inputExpr =
(ExSPInputOutput *)(genSpace->allocateAndCopyToAlignedSpace((char *)expr, totalLen, 0));
compFragDir->removeFragment();
// Delete expr
NADELETEBASIC(expr, generator->wHeap());
expr = NULL;
// Now generate the move to output row expr
myFragmentId = compFragDir->pushFragment(FragmentDir::MASTER);
space = generator->getSpace();
ExSPInputOutput * lOutputExpr = new(space) ExSPInputOutput();
if (expGen->processValIdList(sp->getTableDesc()->getColumnList(),
ExpTupleDesc::SQLARK_EXPLODED_FORMAT,
recordLen,
0, 1,
&tupleDesc,
ExpTupleDesc::LONG_FORMAT) == -1)
return -1;
cia =
(ConvInstruction *)space->allocateMemory(sp->getTableDesc()->getColumnList().entries() *
sizeof(ConvInstruction));
for (short i = 0; i < (short) tupleDesc->numAttrs(); i++)
{
ex_conv_clause tempClause;
cia[i] = tempClause.findInstruction(REC_BYTE_V_ASCII,
-1, // no op
tupleDesc->getAttr(i)->getDatatype(),
tupleDesc->getAttr(i)->getLength(),
0);
}
totalLen = space->getAllocatedSpaceSize();
lOutputExpr->initialize(tupleDesc, totalLen, cia);
ExSPInputOutputPtr(lOutputExpr).pack(space);
expr = new(generator->wHeap()) char[totalLen];
space->makeContiguous((char *)expr, totalLen);
outputExpr =
//.........这里部分代码省略.........
示例7: new
short RelInternalSP::codeGen(Generator * generator)
{
Space * space = generator->getSpace();
ExpGenerator * exp_gen = generator->getExpGenerator();
MapTable * last_map_table = generator->getLastMapTable();
ex_expr * input_expr = NULL;
ex_expr * output_expr = NULL;
////////////////////////////////////////////////////////////////////////////
//
// Returned atp layout:
//
// |--------------------------------|
// | input data | stored proc row |
// | ( I tupps ) | ( 1 tupp ) |
// |--------------------------------|
// <-- returned row to parent ---->
//
// input data: the atp input to this node by its parent.
// stored proc row: tupp where the row read from SP is moved.
//
////////////////////////////////////////////////////////////////////////////
ex_cri_desc * given_desc
= generator->getCriDesc(Generator::DOWN);
ex_cri_desc * returned_desc
= new(space) ex_cri_desc(given_desc->noTuples() + 1, space);
// cri descriptor for work atp has 3 entries:
// -- the first two entries for consts and temps.
// -- Entry 3(index #2) is where the input and output rows will be created.
ex_cri_desc * work_cri_desc = new(space) ex_cri_desc(3, space);
const Int32 work_atp = 1;
const Int32 work_atp_index = 2;
ExpTupleDesc * input_tuple_desc = NULL;
ExpTupleDesc * output_tuple_desc = NULL;
// Generate expression to create the input row that will be
// given to the stored proc.
// The input value is in sp->getProcAllParams()
// and has to be converted to sp->procType().
// Generate Cast node to convert procParam to ProcType.
// If procType is a varchar, explode it. This is done
// so that values could be extracted correctly.
ValueIdList procVIDList;
for (CollIndex i = 0; i < procTypes().entries(); i++)
{
Cast * cn;
if ((procTypes())[i].getType().getVarLenHdrSize() > 0)
{
// 5/9/98: add support for VARNCHAR
const CharType& char_type =
(CharType&)((procTypes())[i].getType());
// Explode varchars by moving them to a fixed field
// whose length is equal to the max length of varchar.
cn = new(generator->wHeap())
Cast ((getProcAllParamsVids())[i].getItemExpr(),
(new(generator->wHeap())
SQLChar(generator->wHeap(),
CharLenInfo(char_type.getStrCharLimit(), char_type.getDataStorageSize()),
char_type.supportsSQLnull(),
FALSE, FALSE, FALSE,
char_type.getCharSet(),
char_type.getCollation(),
char_type.getCoercibility()
/*
(procTypes())[i].getType().getNominalSize(),
(procTypes())[i].getType().supportsSQLnull()
*/
)
)
);
// Move the exploded field to a varchar field since
// procType is varchar.
// Can optimize by adding an option to convert node to
// blankpad. TBD.
//
cn = new(generator->wHeap())
Cast(cn, &((procTypes())[i].getType()));
}
else
cn = new(generator->wHeap()) Cast((getProcAllParamsVids())[i].getItemExpr(),
&((procTypes())[i].getType()));
cn->bindNode(generator->getBindWA());
procVIDList.insert(cn->getValueId());
}
ULng32 inputRowlen_ = 0;
exp_gen->generateContiguousMoveExpr(procVIDList, -1, /*add conv nodes*/
work_atp, work_atp_index,
ExpTupleDesc::SQLARK_EXPLODED_FORMAT,
inputRowlen_,
//.........这里部分代码省略.........
示例8: buildEncodeTree
ItemExpr * buildEncodeTree(desc_struct * column,
desc_struct * key,
NAString * dataBuffer, //IN:contains original value
Generator * generator,
ComDiagsArea * diagsArea)
{
ExpGenerator * expGen = generator->getExpGenerator();
// values are encoded by evaluating the expression:
// encode (cast (<dataBuffer> as <datatype>))
// where <dataBuffer> points to the string representation of the
// data value to be encoded, and <datatype> contains the
// PIC repsentation of the columns's datatype.
// create the CAST part of the expression using the parser.
// if this is a nullable column and the key value passed in
// is a NULL value, then treat it as a special case. A NULL value
// is passed in as an unquoted string of characters NULL in the
// dataBuffer. This case has to be treated different since the
// parser doesn't recognize the syntax "CAST (NULL as <datatype>)".
NAString ns;
ItemExpr * itemExpr;
NABoolean nullValue = FALSE;
NABoolean caseinsensitiveEncode = FALSE;
if (column->body.columns_desc.caseinsensitive)
caseinsensitiveEncode = TRUE;
if (column->body.columns_desc.null_flag &&
dataBuffer->length() >= 4 &&
str_cmp(*dataBuffer, "NULL", 4) == 0)
{
nullValue = TRUE;
ns = "CAST ( @A1 AS ";
ns += column->body.columns_desc.pictureText;
ns += ");";
// create a NULL constant
ConstValue * nullConst = new(expGen->wHeap()) ConstValue();
nullConst->synthTypeAndValueId();
itemExpr = expGen->createExprTree(ns,
CharInfo::UTF8,
ns.length(),
1, nullConst);
}
else
{
ns = "CAST ( ";
ns += *dataBuffer;
ns += " AS ";
ns += column->body.columns_desc.pictureText;
ns += ");";
itemExpr = expGen->createExprTree(ns,
CharInfo::UTF8,
ns.length());
}
CMPASSERT(itemExpr != NULL);
ItemExpr *boundItemExpr =
itemExpr->bindNode(generator->getBindWA());
if (boundItemExpr == NULL)
return NULL;
// make sure that the source and target values have compatible type.
// Do this only if source is not a null value.
NAString srcval;
srcval = "";
srcval += *dataBuffer;
srcval += ";";
ItemExpr * srcNode = expGen->createExprTree(srcval, CharInfo::UTF8, srcval.length());
CMPASSERT(srcNode != NULL);
srcNode->synthTypeAndValueId();
if ((NOT nullValue) &&
(NOT srcNode->getValueId().getType().isCompatible(itemExpr->getValueId().getType())))
{
if (diagsArea)
{
emitDyadicTypeSQLnameMsg(-4039,
itemExpr->getValueId().getType(),
srcNode->getValueId().getType(),
column->body.columns_desc.colname,
NULL,
diagsArea);
}
return NULL;
}
if (column->body.columns_desc.null_flag)
((NAType *)&(itemExpr->getValueId().getType()))->setNullable(TRUE);
else
((NAType *)&(itemExpr->getValueId().getType()))->setNullable(FALSE);
// Explode varchars by moving them to a fixed field
// whose length is equal to the max length of varchar.
////collation??
//.........这里部分代码省略.........
示例9: child
short
PhysUnPackRows::codeGen(Generator *generator)
{
// Get handles on expression generator, map table, and heap allocator
//
ExpGenerator *expGen = generator->getExpGenerator();
Space *space = generator->getSpace();
// Allocate a new map table for this operation
//
MapTable *localMapTable = generator->appendAtEnd();
// Generate the child and capture the task definition block and a description
// of the reply composite row layout and the explain information.
//
child(0)->codeGen(generator);
ComTdb *childTdb = (ComTdb*)(generator->getGenObj());
ex_cri_desc *childCriDesc = generator->getCriDesc(Generator::UP);
ExplainTuple *childExplainTuple = generator->getExplainTuple();
// Make all of my child's outputs map to ATP 1. Since they are
// not needed above, they will not be in the work ATP (0).
// (Later, they will be removed from the map table)
//
localMapTable->setAllAtp(1);
// Generate the given and returned composite row descriptors.
// unPackRows adds a tupp (for the generated outputs) to the
// row given by the parent. The workAtp will have the 2 more
// tupps (1 for the generated outputs and another for the
// indexValue) than the given.
//
ex_cri_desc *givenCriDesc = generator->getCriDesc(Generator::DOWN);
ex_cri_desc *returnedCriDesc =
#pragma nowarn(1506) // warning elimination
new(space) ex_cri_desc(givenCriDesc->noTuples() + 1, space);
#pragma warn(1506) // warning elimination
ex_cri_desc *workCriDesc =
#pragma nowarn(1506) // warning elimination
new(space) ex_cri_desc(givenCriDesc->noTuples() + 2, space);
#pragma warn(1506) // warning elimination
// unPackCols is the next to the last Tp in Atp 0, the work ATP.
// and the last Tp in the returned ATP.
//
const Int32 unPackColsAtpIndex = workCriDesc->noTuples() - 2;
const Int32 unPackColsAtp = 0;
// The length of the new tuple which will contain the columns
// generated by unPackRows
//
ULng32 unPackColsTupleLen;
// The Tuple Desc describing the tuple containing the new unPacked columns
// It is generated when the expression is generated.
//
ExpTupleDesc *unPackColsTupleDesc = 0;
// indexValue is the last Tp in Atp 0, the work ATP.
//
const Int32 indexValueAtpIndex = workCriDesc->noTuples() - 1;
const Int32 indexValueAtp = 0;
// The length of the work tuple which will contain the value
// of the index. This should always be sizeof(int).
//
ULng32 indexValueTupleLen = 0;
// The Tuple Desc describing the tuple containing the new unPacked columns
// It is generated when the expression is generated.
//
ExpTupleDesc *indexValueTupleDesc = 0;
ValueIdList indexValueList;
if (indexValue() != NULL_VALUE_ID)
{
indexValueList.insert(indexValue());
expGen->processValIdList(indexValueList,
ExpTupleDesc::SQLARK_EXPLODED_FORMAT,
indexValueTupleLen,
indexValueAtp,
indexValueAtpIndex,
&indexValueTupleDesc,
ExpTupleDesc::SHORT_FORMAT);
GenAssert(indexValueTupleLen == sizeof(Int32),
"UnPackRows::codeGen: Internal Error");
}
// If a packingFactor exists, generate a move expression for this.
// It is assumed that the packingFactor expression evaluates to a
// 4 byte integer.
//.........这里部分代码省略.........
示例10: child
short
PhysSequence::codeGen(Generator *generator)
{
// Get a local handle on some of the generator objects.
//
CollHeap *wHeap = generator->wHeap();
Space *space = generator->getSpace();
ExpGenerator *expGen = generator->getExpGenerator();
MapTable *mapTable = generator->getMapTable();
// Allocate a new map table for this node. This must be done
// before generating the code for my child so that this local
// map table will be sandwiched between the map tables already
// generated and the map tables generated by my offspring.
//
// Only the items available as output from this node will
// be put in the local map table. Before exiting this function, all of
// my offsprings map tables will be removed. Thus, none of the outputs
// from nodes below this node will be visible to nodes above it except
// those placed in the local map table and those that already exist in
// my ancestors map tables. This is the standard mechanism used in the
// generator for managing the access to item expressions.
//
MapTable *localMapTable = generator->appendAtEnd();
// Since this operation doesn't modify the row on the way down the tree,
// go ahead and generate the child subtree. Capture the given composite row
// descriptor and the child's returned TDB and composite row descriptor.
//
ex_cri_desc * givenCriDesc = generator->getCriDesc(Generator::DOWN);
child(0)->codeGen(generator);
ComTdb *childTdb = (ComTdb*)generator->getGenObj();
ex_cri_desc * childCriDesc = generator->getCriDesc(Generator::UP);
ExplainTuple *childExplainTuple = generator->getExplainTuple();
// Make all of my child's outputs map to ATP 1. The child row is only
// accessed in the project expression and it will be the second ATP
// (ATP 1) passed to this expression.
//
localMapTable->setAllAtp(1);
// My returned composite row has an additional tupp.
//
Int32 numberTuples = givenCriDesc->noTuples() + 1;
ex_cri_desc * returnCriDesc
#pragma nowarn(1506) // warning elimination
= new (space) ex_cri_desc(numberTuples, space);
#pragma warn(1506) // warning elimination
// For now, the history buffer row looks just the return row. Later,
// it may be useful to add an additional tupp for sequence function
// itermediates that are not needed above this node -- thus, this
// ATP is kept separate from the returned ATP.
//
const Int32 historyAtp = 0;
const Int32 historyAtpIndex = numberTuples-1;
#pragma nowarn(1506) // warning elimination
ex_cri_desc *historyCriDesc = new (space) ex_cri_desc(numberTuples, space);
#pragma warn(1506) // warning elimination
ExpTupleDesc *historyDesc = 0;
//seperate the read and retur expressions
seperateReadAndReturnItems(wHeap);
// The history buffer consists of items projected directly from the
// child, the root sequence functions, the value arguments of the
// offset functions, and running sequence functions. These elements must
// be materialized in the history buffer in order to be able to compute
// the outputs of this node -- the items projected directly from the child
// (projectValues) and the root sequence functions (sequenceFunctions).
//
// Compute the set of sequence function items that must be materialized
// int the history buffer. -- sequenceItems
//
// Compute the set of items in the history buffer: the union of the
// projected values and the value arguments. -- historyIds
//
// Compute the set of items in the history buffer that are computed:
// the difference between all the elements in the history buffer
// and the projected items. -- computedHistoryIds
//
// KB---will need to return atp with 3 tups only 0,1 and 2
// 2 -->values from history buffer after ther are moved to it
addCheckPartitionChangeExpr(generator, TRUE);
ValueIdSet historyIds;
historyIds += movePartIdsExpr();
historyIds += sequencedColumns();
ValueIdSet outputFromChild = child(0)->getGroupAttr()->getCharacteristicOutputs();
getHistoryAttributes(readSeqFunctions(),outputFromChild, historyIds, TRUE, wHeap);
// Add in the top level sequence functions.
historyIds += readSeqFunctions();
//.........这里部分代码省略.........
示例11: codeGen
// ItmDoWhileFunction::codeGen
//
// The DoWhile function executes the code represented by child(0) until
// the condition represented by child(1) becomes false. The result of
// the DoWhile is the final value of child(0).
//
// The looping is accomplished by inserting a NOOP/BRANCH pair. The NOOP
// is inserted before generating the code for either child and serves as a
// branch target. The BRANCH is inserted after generating the code for
// both children and is targeted at the NOOP clause based on the result of
// child(1). Between the NOOP and the BRANCH the body of the loop (child(0))
// and the termination condition (child(1)) are repeatedly evaluated. After
// the branch the final result of the loop body is assigned as the result
// of the DoWhile.
//
short ItmDoWhileFunction::codeGen(Generator * generator) {
// Get local handles...
//
Attributes **attr;
Space* space = generator->getSpace();
CollHeap *wHeap = generator->wHeap();
ExpGenerator *exp = generator->getExpGenerator();
// If this DoWhile has already been codeGenned, then bug out...
// Otherwise, allocate space for the result if necessary and set
// attr[0] to point to the result attribute data. Also, mark this
// node as codeGenned.
//
if (exp->genItemExpr(this, &attr, 2, 0) == 1)
return 0;
// Insert the NOOP clause to use as the branch target for the
// start of the loop body.
//
ex_clause * branchTarget = new(space) ex_noop_clause();
exp->linkClause(this, branchTarget);
// CodeGen the body of the loop.
//
child(0)->codeGen(generator);
// The result of the DoWhile is the result of the body of the loop. Set
// the src attribute for the convert (added below) to be the body of
// the while loop. The dst attribute has already been set in genItemExpr().
//
attr[1] = generator->getMapInfo
(child(0)->castToItemExpr()->getValueId())->getAttr();
// CodeGen the loop termination condition.
//
child(1)->codeGen(generator);
// Construct a BRANCH clause to loop back and repeat the expression
// and condition if the condition evaluates to TRUE.
//
Attributes ** branchAttrs = new(wHeap) Attributes*[2];
Attributes *boolAttr = generator->getMapInfo
(child(1)->castToItemExpr()->getValueId())->getAttr();
branchAttrs[0] = boolAttr->newCopy(wHeap);
branchAttrs[1] = boolAttr->newCopy(wHeap);
// branchAttrs[0]->copyLocationAttrs(boolAttr);
// branchAttrs[1]->copyLocationAttrs(boolAttr);
branchAttrs[0]->resetShowplan();
ex_branch_clause * branchClause
= new(space) ex_branch_clause(ITM_OR, branchAttrs, space);
branchClause->set_branch_clause(branchTarget);
// Insert the branch clause into the expression.
//
exp->linkClause(this, branchClause);
// Allocate a convert clause to move the result from child(0) to the
// result of this node. This move is necessary so that future
// side-effects of the result of child(0) -- if it is a local variable,
// for instance -- will not change the result of the DoWhile.
//
ex_conv_clause * convClause =
new(generator->getSpace()) ex_conv_clause
(getOperatorType(), attr, space);
exp->linkClause(this, convClause);
return 0;
}
示例12: child
short
PhysSample::codeGen(Generator *generator)
{
// Get a local handle on some of the generator objects.
//
CollHeap *wHeap = generator->wHeap();
Space *space = generator->getSpace();
MapTable *mapTable = generator->getMapTable();
ExpGenerator *expGen = generator->getExpGenerator();
// Allocate a new map table for this node. This must be done
// before generating the code for my child so that this local
// map table will be sandwiched between the map tables already
// generated and the map tables generated by my offspring.
//
// Only the items available as output from this node will
// be put in the local map table. Before exiting this function, all of
// my offsprings map tables will be removed. Thus, none of the outputs
// from nodes below this node will be visible to nodes above it except
// those placed in the local map table and those that already exist in
// my ancestors map tables. This is the standard mechanism used in the
// generator for managing the access to item expressions.
//
MapTable *localMapTable = generator->appendAtEnd();
// Since this operation doesn't modify the row on the way down the tree,
// go ahead and generate the child subtree. Capture the given composite row
// descriptor and the child's returned TDB and composite row descriptor.
//
ex_cri_desc * givenCriDesc = generator->getCriDesc(Generator::DOWN);
child(0)->codeGen(generator);
ComTdb *childTdb = (ComTdb*)generator->getGenObj();
ex_cri_desc * childCriDesc = generator->getCriDesc(Generator::UP);
ExplainTuple *childExplainTuple = generator->getExplainTuple();
// Geneate the sampling expression.
//
ex_expr *balExpr = NULL;
Int32 returnFactorOffset = 0;
ValueId val;
val = balanceExpr().init();
if(balanceExpr().next(val))
expGen->generateSamplingExpr(val, &balExpr, returnFactorOffset);
// Alias the sampleColumns() so that they reference the underlying
// expressions directly. This is done to avoid having to generate and
// execute a project expression that simply moves the columns from
// one tupp to another to reflect the application of the sampledCol
// function.
//
// ValueId valId;
// for(valId = sampledColumns().init();
// sampledColumns().next(valId);
// sampledColumns().advance(valId))
// {
// MapInfo *mapInfoChild = localMapTable->getMapInfoAsIs
// (valId.getItemExpr()->child(0)->castToItemExpr()->getValueId());
// GenAssert(mapInfoChild, "Sample::codeGen -- no child map info.");
// Attributes *attr = mapInfoChild->getAttr();
// MapInfo *mapInfo = localMapTable->addMapInfoToThis(valId, attr);
// mapInfo->codeGenerated();
// }
// check if any of the columns inthe sampled columns are lob columns. If so, return an error.
ValueId valId;
for(valId = sampledColumns().init();
sampledColumns().next(valId);
sampledColumns().advance(valId))
{
const NAType &colType = valId.getType();
if ((colType.getFSDatatype() == REC_BLOB) ||
(colType.getFSDatatype() == REC_CLOB))
{
*CmpCommon::diags() << DgSqlCode(-4322);
GenExit();
}
}
// Now, remove all attributes from the map table except the
// the stuff in the local map table -- the result of this node.
//
// localMapTable->removeAll();
// Generate the expression to evaluate predicate on the sampled row.
//
ex_expr *postPred = 0;
if (!selectionPred().isEmpty()) {
ItemExpr * newPredTree
= selectionPred().rebuildExprTree(ITM_AND,TRUE,TRUE);
expGen->generateExpr(newPredTree->getValueId(), ex_expr::exp_SCAN_PRED,
&postPred);
}
// Construct the Sample TDB.
//
ComTdbSample *sampleTdb
= new(space) ComTdbSample(NULL,
balExpr,
returnFactorOffset,
postPred,
childTdb,
//.........这里部分代码省略.........