Hi,
Could you elaborate on what problem you are trying to solve?
I think I might have written this code, but it was over 20 years ago. I'll try
to refresh my memory to explain what is going on in this code.
Looking at the code:
587 ex_expr::exp_return_type errorCode = predPtr->getValue(atp0,workAtp);
588
589 Int32 dcErrFlag1 = dataConvErrorFlag;
590 Int32 dcErrFlag2 = 0;
591 if (errorCode == ex_expr::EXPR_OK &&
592 predPtr->getPredType() == MdamPred::MDAM_BETWEEN)
593 {
594 dataConvErrorFlag = 0;
595 errorCode = predPtr->getValue2(atp0,workAtp);
596 dcErrFlag2 = dataConvErrorFlag;
597 }
598
599 MdamPred::MdamPredType predType = MdamPred::MDAM_RETURN_FALSE;
600 // Next 2 used only for MDAM_BETWEEN.
601 MdamEnums::MdamInclusion startInclusion =
predPtr->getStartInclusion();
602 MdamEnums::MdamInclusion endInclusion = predPtr->getEndInclusion();
603 if (errorCode == ex_expr::EXPR_OK)
604 predType = predPtr->getTransformedPredType(dcErrFlag1, dcErrFlag2,
605 startInclusion,
endInclusion);
errorCode is set at line 587. It is checked at line 591; if everything is OK we
go ahead and process the second value if it is a BETWEEN. Then errCode is again
set at line 595.
At line 599, we are pessimistic; we set predType to FALSE. Then if there were
no errors at line 603, we then compute the predType at line 604.
If I remember correctly, the point is that when processing certain key
predicates (MDAM predicates are key predicates) we expect to get certain
errors. For example, if we have a SMALLINT column X, and we have a predicate X
> 100000, the compiler will down-cast the 100000 for the comparison. So when we
get here the predicate is transformed to X < CAST(100000 AS SMALLINT). This
CAST results in an error, because 100000 is greater than any possible SMALLINT
value. So in this case, we want the predicate to always evaluate as FALSE.
And that is precisely what this code does.
The handling of errorCode locally in this procedure is quite intentional.
If we change this code to instead pass the error up to the caller, we may get
compile time errors for a predicate that is perfectly OK.
Thanks,
Dave
-----Original Message-----
From: Zhu, Wen-Jun <[email protected]>
Sent: Tuesday, August 14, 2018 9:10 PM
To: [email protected]
Subject: problems in ExHbaseAccessTcb and MdamColumn
Hi,
in MdamColumn::buildDisjunct() at ../executor/ex_mdam.cpp:
587 ex_expr::exp_return_type errorCode =
predPtr->getValue(atp0,workAtp);
588
589 Int32 dcErrFlag1 = dataConvErrorFlag;
590 Int32 dcErrFlag2 = 0;
591 if (errorCode == ex_expr::EXPR_OK &&
592 predPtr->getPredType() == MdamPred::MDAM_BETWEEN)
593 {
594 dataConvErrorFlag = 0;
595 errorCode = predPtr->getValue2(atp0,workAtp);
596 dcErrFlag2 = dataConvErrorFlag;
597 }
when errorCode is not OK on line 587, it is not checked immediately and is then
reused.
So I suggest to change the interface of function MdamColumn::buildDisjunct(),
making the return value type from NABoolean to int, to distingush the normal
value and error code.
And in function keyMdamEx::buildNetwork(), which calls buildDisjunct(), the
current logic requires the returned value must be true, why?
If there is an error occurred, we can ignore that ex_assert() and just return
the errorCode, right?
Another problem, ExHbaseAccessTcb::initNextKeyRange() in
core/sql/executor/ExHbaseAccess.cpp:
2430 Lng32 ExHbaseAccessTcb::initNextKeyRange(sql_buffer_pool *pool,
2431 atp_struct * atp)
2432 {
2433 if (keyExeExpr())
2434 keyExeExpr()->initNextKeyRange(pool, atp);
2435 else
2436 return -1;
2437
2438 return 0;
2439 }
which does not check the returned value of initNextKeyRange(), so if there is
something wrong in it, but keyExeExpr() is fine, this function returns 0,
indicating success.
Regards,
Wenjun Zhu