box2f SphericalDeformation::deformedToLocalBounds(const vec3d &deformedCenter, double deformedRadius) const { vec3d p = deformedToLocal(deformedCenter); double r = deformedRadius; if (isInf(p.x) || isInf(p.y)) { return box2f(); } double k = (1.0 - r * r / (2.0 * R * R)) * vec3d(p.x, p.y, R).length(); double A = k * k - p.x * p.x; double B = k * k - p.y * p.y; double C = -2.0 * p.x * p.y; double D = -2.0 * R * R * p.x; double E = -2.0 * R * R * p.y; double F = R * R * (k * k - R * R); double a = C * C - 4.0 * A * B; double b = 2.0 * C * E - 4.0 * B * D; double c = E * E - 4.0 * B * F; double d = sqrt(b * b - 4.0 * a * c); double x1 = (- b - d) / (2.0 * a); double x2 = (- b + d) / (2.0 * a); b = 2.0 * C * D - 4.0 * A * E; c = D * D - 4.0 * A * F; d = sqrt(b * b - 4.0 * a * c); double y1 = (- b - d) / (2.0 * a); double y2 = (- b + d) / (2.0 * a); return box2f(vec2f(x1, y1), vec2f(x2, y2)); }
//----------------------------------------------------------------------------- double APowerPack::getBatteryLevel() const { if ( isInf(mBatteryCapacity) ) return 1.0; return mBatteryCapacity / mMaxBatteryCapacity; }
ArrayType::ArrayType(const NodePtr& node) { assert_true(node) << "Given node is null!"; // support expressions as input auto type = node.isa<GenericTypePtr>(); if (auto expr = node.isa<ExpressionPtr>()) type = expr->getType().isa<GenericTypePtr>(); // check given node type assert_true(isArrayType(type)) << "Given node " << *node << " is not a array type!"; // process node type if(isInf(type->getTypeParameter(1))) { // unknown sized array *this = ArrayType(type->getTypeParameter(0), ExpressionPtr()); } else if (auto num = type->getTypeParameter(1).isa<NumericTypePtr>()) { // variable or fixed sized array *this = ArrayType(type->getTypeParameter(0), num->getValue()); } else { // check validity auto size = type->getTypeParameter(1).isa<TypeVariablePtr>(); assert_true(size) << "Invalid size parameter: " << *size << " of kind: " << size->getNodeType(); // generic array type *this = ArrayType(type->getTypeParameter(0), size); } }
int DecimalUtil::quantum(Decimal64 x) { BSLS_ASSERT(!isInf(x)); BSLS_ASSERT(!isNan(x)); return decDoubleGetExponent(x.data()); }
int DecimalUtil::quantum(Decimal128 x) { BSLS_ASSERT(!isInf(x)); BSLS_ASSERT(!isNan(x)); return decQuadGetExponent(x.data()); }
bool broadCastLinkInfo(int messagetype, struct LINK link, struct NetworkTopoStruct* Topo) { char buf[MAXDATASIZE]; int length = 0; int i; length = 1+sizeof(struct LINK); buf[0] = (char)messagetype; memcpy(&buf[1],&link, sizeof(struct LINK)); buf[length] = '\0'; char broadresult[MAXDATASIZE]; char temp[MAXDATASIZE]; memset(broadresult,'\0',MAXDATASIZE); for(i=0;i<Topo->neighNum;i++) { if(isInf(Topo->Neighs[i].cost)) continue; // do not broadcast link info through links with infinite cost if(isNodeInLink(Topo->Neighs[i].addr,link)) continue; // do not broadcast link info to nodes the nodes in the link else{ if(udpTalkTo(Topo->Neighs[i].host,Topo->Neighs[i].udpport,buf,length) != 0) { perror("ERR broadCastLinkInfo: udp talking error."); exit(1); } else { sprintf(temp,"%d ", Topo->Neighs[i].addr); strcat(broadresult,temp); } } } if(strlen(broadresult)>0) printf("%d broadCastLinkInfo: %d <%d %d %.0f> through Neighs: %s\n",Topo->myaddr,messagetype,link.nodeAddr[0],link.nodeAddr[1],link.cost,broadresult); return 1; }
bool EXParser::evaluateFunction(std::string &_expression, const int index, EXFunctionSet::iterator fiter) { std::string paramExpression = isolateParenthesisExpression(_expression, index); size_t expressionLen = paramExpression.length(); if(expressionLen == 0){ mErrorStr = "function parameter error"; return false; } if(!priorityLoop(paramExpression)) return false; double value = fiter->second((double)atof(paramExpression.c_str())); if(isInf(value)){ mErrorStr = "infinity error"; return false; } if(isNan(value)){ mErrorStr = "not a number error"; return false; } steps.push_back(EXSolveStep(fiter->first+"("+paramExpression+") -> "+dblToStr(value), "")); _expression.replace(index-fiter->first.length(), fiter->first.length()+expressionLen+2, dblToStr(value)); return true; }
bool AbsScarRegionDetector::is_valid(float * val){ for(int i=0; i < this->dim; i++){ if(isNaN(val[i]) || isInf(val[i]) || isNegInf(val[i])) return false; } return true; }
bool runtime·isNaN(float64 f) { uint64 x; x = runtime·float64tobits(f); return ((uint32)(x>>52) & 0x7FF) == 0x7FF && !runtime·isInf(f, 0); }
double roundValue(double d) { double ad = fabs(d); if (ad == 0 || isNaN(d) || isInf(d)) { return d; } return copysign(floor(ad), d); }
int32_t toInt32(double d, bool &ok) { ok = true; if (isNaN(d) || isInf(d)) { ok = false; return 0; } return toInt32(d); }
double errcheck(double d, char* s) /* check result of library call */ { if(isNaN(d)) execerror(s, "argument out of domain"); if(isInf(d, 0)) execerror(s, "result out of range"); return d; }
int isNaN(double d) { FPdbleword a; a.x = d; if((a.hi & NANMASK) != NANEXP) return 0; return !isInf(d, 0); }
void addJointSoftLimits(const JointSoftLimitParams ¶ms, const DrakeRobotState &robot_state, const VectorXd &q_des, std::vector<SupportStateElement,Eigen::aligned_allocator<SupportStateElement>> &supports, std::vector<drake::lcmt_joint_pd_override> &joint_pd_override) { Matrix<bool, Dynamic, 1> has_joint_override = Matrix<bool, Dynamic, 1>::Zero(q_des.size()); for (std::vector<drake::lcmt_joint_pd_override>::iterator it = joint_pd_override.begin(); it != joint_pd_override.end(); ++it) { has_joint_override(it->position_ind - 1) = true; } for (int i=0; i < params.lb.size(); i++) { if (!has_joint_override(i) && params.enabled(i)) { int disable_body_1idx = params.disable_when_body_in_support(i); if (disable_body_1idx == 0 || !inSupport(supports, disable_body_1idx - 1)) { double w_lb = 0; double w_ub = 0; if (!isInf(params.lb(i))) { w_lb = logisticSigmoid(params.weight(i), params.k_logistic(i), params.lb(i), robot_state.q(i)); } if (!isInf(params.ub(i))) { w_ub = logisticSigmoid(params.weight(i), params.k_logistic(i), robot_state.q(i), params.ub(i)); } double weight = std::max(w_ub, w_lb); drake::lcmt_joint_pd_override override; override.position_ind = i + 1; override.qi_des = q_des(i);
uint16_t toUInt16(double dd) { double d = roundValue(dd); if (isNaN(d) || isInf(d)) { return 0; } double d16 = fmod(d, D16); if (d16 < 0) { d16 += D16; } return static_cast<uint16_t>(d16); }
uint32_t toUInt32(double dd) { double d = roundValue(dd); if (isNaN(d) || isInf(d)) { return 0; } double d32 = fmod(d, D32); if (d32 < 0) { d32 += D32; } return static_cast<uint32_t>(d32); }
int isNaN(double d) { union { double d; long x[2]; } a; a.d = d; if((a.x[1] & NANMASK) != NANEXP) return 0; return !isInf(d, 0); }
int32_t toInt32(double d) { if (isNaN(d) || isInf(d)) { return 0; } double d32 = fmod(roundValue(d), D32); if (d32 >= D32 / 2) { d32 -= D32; } else if (d32 < -D32 / 2) { d32 += D32; } return static_cast<int32_t>(d32); }
uint32_t JSValue::toUInt32SlowCase(double d, bool& ok) { ok = true; if (d >= 0.0 && d < D32) return static_cast<uint32_t>(d); if (isNaN(d) || isInf(d)) { ok = false; return 0; } double d32 = fmod(trunc(d), D32); if (d32 < 0) d32 += D32; return static_cast<uint32_t>(d32); }
bool ArrayType::isArrayType(const NodePtr& node) { auto type = node.isa<GenericTypePtr>(); if(!type) return false; // simple approach: use unification NodeManager& mgr = node.getNodeManager(); const ArrayExtension& ext = mgr.getLangExtension<ArrayExtension>(); // unify given type with template type auto ref = ext.getGenArray().as<GenericTypePtr>(); auto sub = types::match(mgr, type, ref); if(!sub) return false; // check instantiation const types::Substitution& map = *sub; auto size = map.applyTo(ref->getTypeParameter(1)); return size.isa<TypeVariablePtr>() || size.isa<NumericTypePtr>() || isInf(size); }
/* sqrtC returns the square root of its floating point argument. Newton's method. calls frexp */ double sqrtC(double arg) { double x, temp; int exp, i; if(arg <= 0) { if(arg < 0) return NaN(); return 0; } if(isInf(arg, 1)) return arg; x = frexp(arg, &exp); while(x < 0.5) { x *= 2; exp--; } /* * NOTE * this wont work on 1's comp */ if(exp & 1) { x *= 2; exp--; } temp = 0.5 * (1.0+x); while(exp > 60) { temp *= (1L<<30); exp -= 60; } while(exp < -60) { temp /= (1L<<30); exp += 60; } if(exp >= 0) temp *= 1L << (exp/2); else temp /= 1L << (-exp/2); for(i=0; i<=4; i++) temp = 0.5*(temp + arg/temp); return temp; }
int32_t JSValue::toInt32SlowCase(double d, bool& ok) { ok = true; if (d >= -D32 / 2 && d < D32 / 2) return static_cast<int32_t>(d); if (isNaN(d) || isInf(d)) { ok = false; return 0; } double d32 = fmod(trunc(d), D32); if (d32 >= D32 / 2) d32 -= D32; else if (d32 < -D32 / 2) d32 += D32; return static_cast<int32_t>(d32); }
void EXParser::evaluateFunction(std::string &_expression, const int index, EXFunctionSet::iterator fiter) { std::string paramExpression = isolateParenthesisExpression(_expression, index); size_t expressionLen = paramExpression.length(); if(expressionLen == 0){ throw EXError("function_parameter_error", ErrorIndex::FUNCTION_PARAMETER_ERROR); } priorityLoop(paramExpression); double value = fiter->second((double)atof(paramExpression.c_str())); if(isInf(value)){ throw EXError("infinity_error", ErrorIndex::INFINITY_ERROR); } if(isNan(value)){ throw EXError("not_a_number", ErrorIndex::NAN_ERROR); } steps.push_back(EXSolveStep(fiter->first+"("+paramExpression+") -> "+dblToStr(value), "")); _expression.replace(index-fiter->first.length(), fiter->first.length()+expressionLen+2, dblToStr(value)); }
STD1::uint32_t Document::writeNameMap( std::FILE* out ) { STD1::uint32_t offset( 0 ); if( !isInf() && !nameMap.empty() ) { offset = std::ftell( out ); ConstNameMapIter itr; for( itr = nameMap.begin(); itr != nameMap.end(); ++itr ) { STD1::uint16_t index( itr->first->index() ); if( std::fwrite( &index, sizeof( STD1::uint16_t ), 1, out ) != 1 ) throw FatalError( ERR_WRITE ); } for( itr = nameMap.begin(); itr != nameMap.end(); ++itr ) { STD1::uint16_t idx( itr->second.index() ); if( std::fwrite( &idx, sizeof( STD1::uint16_t ), 1, out ) != 1 ) throw FatalError( ERR_WRITE ); } } return offset; }
// Write the file void Document::write( std::FILE *out ) { hdr->write( out ); //write the header hdr->panelCount = static_cast< STD1::uint16_t>( resMap.size() ); hdr->panelOffset = writeResMap( out ); hdr->nameCount = !isInf() ? static_cast< STD1::uint16_t >( nameMap.size() ) : 0; hdr->nameOffset = writeNameMap( out ); eHdr->gNameOffset = gnames->write( out ); eHdr->gNameCount = gnames->size(); hdr->imageOffset = writeBitmaps( out ); hdr->tocCount = static_cast< STD1::uint16_t >( pages.size() ); hdr->tocOffset = writeTOCs( out ); hdr->tocOffsetOffset = writeTOCOffsets( out ); writeSynonyms( out ); hdr->indexOffset = writeIndex( out ); hdr->icmdOffset = writeICmd( out ); hdr->nlsOffset = nls->write( out ); hdr->nlsSize = nls->length(); eHdr->stringsOffset = strings->write( out ); eHdr->stringsSize = static_cast< STD1::uint16_t >( strings->length() ); eHdr->dbOffset = extfiles->write( out ); eHdr->dbCount = static_cast< STD1::uint16_t >( extfiles->size() ); eHdr->dbSize = extfiles->length(); eHdr->fontOffset = fonts->write( out ); eHdr->fontCount = static_cast< STD1::uint16_t >( fonts->size() ); eHdr->ctrlOffset = controls->write( out ); eHdr->ctrlSize = controls->length(); hdr->dictOffset = dict->write( out ); hdr->dictSize = dict->length(); hdr->dictCount = dict->size(); writeCells( out ); hdr->cellCount = static_cast< STD1::uint16_t >( cells.size() ); hdr->cellOffsetOffset = writeCellOffsets( out ); eHdr->childPagesOffset = writeChildWindows( out ); if( compiler.searchable() ) { hdr->searchOffset = dict->writeFTS( out, hdr->recSize ); hdr->searchSize = dict->ftsLength(); } hdr->extOffset = eHdr->write( out ); hdr->write( out ); //rewrite the header to update the offsets }
void EXParser::evaluateOperator(std::string & _expression, const int index, EXOperatorSet::iterator oiter) { if(oiter->first!='('){ std::string leftVal, rightVal, strVal; if((leftVal = getLeftOfOperator(_expression, index-1)).empty() || (rightVal = getRightOfOperator(_expression, index+1)).empty()){ throw EXError("operator_logic_error", ErrorIndex::OPERATOR_LOGIC_ERROR); } double value = oiter->second(strToDbl(leftVal.c_str()), strToDbl(rightVal.c_str())); if(isInf(value)){ throw EXError("infinity_error", ErrorIndex::INFINITY_ERROR); } if(isNan(value)){ throw EXError("not_a_number", ErrorIndex::NAN_ERROR); } _expression.replace(index-leftVal.length(), leftVal.length() + rightVal.length()+1, dblToStr(value)); } else{ evaluateParenthesis(_expression, index); } }
bool EXParser::evaluateOperator(std::string & _expression, const int index, EXOperatorSet::iterator oiter) { if(oiter->first!='('){ std::string leftVal, rightVal, strVal; if((leftVal = getLeftOfOperator(_expression, index-1)).empty() || (rightVal = getRightOfOperator(_expression, index+1)).empty()){ mErrorStr = "operator logic error"; return false; } double value = oiter->second(strToDbl(leftVal.c_str()), strToDbl(rightVal.c_str())); if(isInf(value)){ mErrorStr = "infinity error"; return false; } if(isNan(value)){ mErrorStr = "not a number"; return false; } _expression.replace(index-leftVal.length(), leftVal.length() + rightVal.length()+1, dblToStr(value)); } else{ evaluateParenthesis(_expression, index); } return true; }
static void xdtoa(Fmt *fmt, char *s2, double f) { char s1[NSIGNIF+10]; double g, h; int e, d, i, n; int c1, c2, c3, c4, ucase, sign, chr, prec; prec = FDEFLT; if(fmt->flags & FmtPrec) prec = fmt->prec; if(prec > FDIGIT) prec = FDIGIT; if(isNaN(f)) { strcpy(s2, "NaN"); return; } if(isInf(f, 1)) { strcpy(s2, "+Inf"); return; } if(isInf(f, -1)) { strcpy(s2, "-Inf"); return; } sign = 0; if(f < 0) { f = -f; sign++; } ucase = 0; chr = fmt->r; if(isupper(chr)) { ucase = 1; chr = tolower(chr); } e = 0; g = f; if(g != 0) { frexp(f, &e); e = e * .301029995664; if(e >= -150 && e <= +150) { d = 0; h = f; } else { d = e/2; h = f * pow10(-d); } g = h * pow10(d-e); while(g < 1) { e--; g = h * pow10(d-e); } while(g >= 10) { e++; g = h * pow10(d-e); } } /* * convert NSIGNIF digits and convert * back to get accuracy. */ for(i=0; i<NSIGNIF; i++) { d = g; s1[i] = d + '0'; g = (g - d) * 10; } s1[i] = 0; /* * try decimal rounding to eliminate 9s */ c2 = prec + 1; if(chr == 'f') c2 += e; if(c2 >= NSIGNIF-2) { strcpy(s2, s1); d = e; s1[NSIGNIF-2] = '0'; s1[NSIGNIF-1] = '0'; sprint(s1+NSIGNIF, "e%d", e-NSIGNIF+1); g = strtod(s1, nil); if(g == f) goto found; if(xadd(s1, NSIGNIF-3, 1)) { e++; sprint(s1+NSIGNIF, "e%d", e-NSIGNIF+1); } g = strtod(s1, nil); if(g == f) goto found; strcpy(s1, s2); e = d; } /* * convert back so s1 gets exact answer */ for(;;) { sprint(s1+NSIGNIF, "e%d", e-NSIGNIF+1); g = strtod(s1, nil); if(f > g) { if(xadd(s1, NSIGNIF-1, 1)) e--; continue; } if(f < g) { if(xsub(s1, NSIGNIF-1, 1)) e++; continue; } break; } found: /* * sign */ d = 0; i = 0; if(sign) s2[d++] = '-'; else if(fmt->flags & FmtSign) s2[d++] = '+'; else if(fmt->flags & FmtSpace) s2[d++] = ' '; /* * copy into final place * c1 digits of leading '0' * c2 digits from conversion * c3 digits of trailing '0' * c4 digits after '.' */ c1 = 0; c2 = prec + 1; c3 = 0; c4 = prec; switch(chr) { default: if(xadd(s1, c2, 5)) e++; break; case 'g': /* * decide on 'e' of 'f' style convers */ if(xadd(s1, c2, 5)) e++; if(e >= -5 && e <= prec) { c1 = -e - 1; c4 = prec - e; chr = 'h'; // flag for 'f' style } break; case 'f': if(xadd(s1, c2+e, 5)) e++; c1 = -e; if(c1 > prec) c1 = c2; c2 += e; break; } /* * clean up c1 c2 and c3 */ if(c1 < 0) c1 = 0; if(c2 < 0) c2 = 0; if(c2 > NSIGNIF) { c3 = c2-NSIGNIF; c2 = NSIGNIF; } /* * copy digits */ while(c1 > 0) { if(c1+c2+c3 == c4) s2[d++] = '.'; s2[d++] = '0'; c1--; } while(c2 > 0) { if(c2+c3 == c4) s2[d++] = '.'; s2[d++] = s1[i++]; c2--; } while(c3 > 0) { if(c3 == c4) s2[d++] = '.'; s2[d++] = '0'; c3--; } /* * strip trailing '0' on g conv */ if(fmt->flags & FmtSharp) { if(0 == c4) s2[d++] = '.'; } else if(chr == 'g' || chr == 'h') { for(n=d-1; n>=0; n--) if(s2[n] != '0') break; for(i=n; i>=0; i--) if(s2[i] == '.') { d = n; if(i != n) d++; break; } } if(chr == 'e' || chr == 'g') { if(ucase) s2[d++] = 'E'; else s2[d++] = 'e'; c1 = e; if(c1 < 0) { s2[d++] = '-'; c1 = -c1; } else s2[d++] = '+'; if(c1 >= 100) { s2[d++] = c1/100 + '0'; c1 = c1%100; } s2[d++] = c1/10 + '0'; s2[d++] = c1%10 + '0'; } s2[d] = 0; }
// // Do single unary node folding // TIntermTyped* TIntermConstantUnion::fold(TOperator op, const TType& returnType) { TConstUnion *unionArray = getUnionArrayPointer(); int objectSize = getType().getObjectSize(); // First, size the result, which is mostly the same as the argument's size, // but not always. TConstUnion* newConstArray; switch (op) { // TODO: functionality: constant folding: finish listing exceptions to size here case EOpDeterminant: case EOpAny: case EOpAll: case EOpLength: newConstArray = new TConstUnion[1]; break; case EOpEmitStreamVertex: case EOpEndStreamPrimitive: // These don't actually fold return 0; default: newConstArray = new TConstUnion[objectSize]; } // Process non-component-wise operations switch (op) { case EOpLength: case EOpNormalize: { double sum = 0; for (int i = 0; i < objectSize; i++) sum += double(unionArray[i].getDConst()) * unionArray[i].getDConst(); double length = sqrt(sum); if (op == EOpLength) newConstArray[0].setDConst(length); else { for (int i = 0; i < objectSize; i++) newConstArray[i].setDConst(unionArray[i].getDConst() / length); } break; } default: break; } for (int i = 0; i < objectSize; i++) { switch (op) { case EOpNegative: switch (getType().getBasicType()) { case EbtDouble: case EbtFloat: newConstArray[i].setDConst(-unionArray[i].getDConst()); break; case EbtInt: newConstArray[i].setIConst(-unionArray[i].getIConst()); break; case EbtUint: newConstArray[i].setUConst(static_cast<unsigned int>(-static_cast<int>(unionArray[i].getUConst()))); break; default: return 0; } break; case EOpLogicalNot: case EOpVectorLogicalNot: switch (getType().getBasicType()) { case EbtBool: newConstArray[i].setBConst(!unionArray[i].getBConst()); break; default: return 0; } break; case EOpBitwiseNot: newConstArray[i] = ~unionArray[i]; break; case EOpRadians: newConstArray[i].setDConst(unionArray[i].getDConst() * pi / 180.0); break; case EOpDegrees: newConstArray[i].setDConst(unionArray[i].getDConst() * 180.0 / pi); break; case EOpSin: newConstArray[i].setDConst(sin(unionArray[i].getDConst())); break; case EOpCos: newConstArray[i].setDConst(cos(unionArray[i].getDConst())); break; case EOpTan: newConstArray[i].setDConst(tan(unionArray[i].getDConst())); break; case EOpAsin: newConstArray[i].setDConst(asin(unionArray[i].getDConst())); break; case EOpAcos: newConstArray[i].setDConst(acos(unionArray[i].getDConst())); break; case EOpAtan: newConstArray[i].setDConst(atan(unionArray[i].getDConst())); break; case EOpLength: case EOpNormalize: // handled above as special case break; case EOpDPdx: case EOpDPdy: case EOpFwidth: // The derivatives are all mandated to create a constant 0. newConstArray[i].setDConst(0.0); break; case EOpExp: newConstArray[i].setDConst(exp(unionArray[i].getDConst())); break; case EOpLog: newConstArray[i].setDConst(log(unionArray[i].getDConst())); break; case EOpExp2: { const double inv_log2_e = 0.69314718055994530941723212145818; newConstArray[i].setDConst(exp(unionArray[i].getDConst() * inv_log2_e)); break; } case EOpLog2: { const double log2_e = 1.4426950408889634073599246810019; newConstArray[i].setDConst(log2_e * log(unionArray[i].getDConst())); break; } case EOpSqrt: newConstArray[i].setDConst(sqrt(unionArray[i].getDConst())); break; case EOpInverseSqrt: newConstArray[i].setDConst(1.0 / sqrt(unionArray[i].getDConst())); break; case EOpAbs: if (unionArray[i].getType() == EbtDouble) newConstArray[i].setDConst(fabs(unionArray[i].getDConst())); else if (unionArray[i].getType() == EbtInt) newConstArray[i].setIConst(abs(unionArray[i].getIConst())); else newConstArray[i] = unionArray[i]; break; case EOpSign: #define SIGN(X) (X == 0 ? 0 : (X < 0 ? -1 : 1)) if (unionArray[i].getType() == EbtDouble) newConstArray[i].setDConst(SIGN(unionArray[i].getDConst())); else newConstArray[i].setIConst(SIGN(unionArray[i].getIConst())); break; case EOpFloor: newConstArray[i].setDConst(floor(unionArray[i].getDConst())); break; case EOpTrunc: if (unionArray[i].getDConst() > 0) newConstArray[i].setDConst(floor(unionArray[i].getDConst())); else newConstArray[i].setDConst(ceil(unionArray[i].getDConst())); break; case EOpRound: newConstArray[i].setDConst(floor(0.5 + unionArray[i].getDConst())); break; case EOpRoundEven: { double flr = floor(unionArray[i].getDConst()); bool even = flr / 2.0 == floor(flr / 2.0); double rounded = even ? ceil(unionArray[i].getDConst() - 0.5) : floor(unionArray[i].getDConst() + 0.5); newConstArray[i].setDConst(rounded); break; } case EOpCeil: newConstArray[i].setDConst(ceil(unionArray[i].getDConst())); break; case EOpFract: { double x = unionArray[i].getDConst(); newConstArray[i].setDConst(x - floor(x)); break; } case EOpIsNan: { newConstArray[i].setBConst(isNan(unionArray[i].getDConst())); break; } case EOpIsInf: { newConstArray[i].setBConst(isInf(unionArray[i].getDConst())); break; } // TODO: Functionality: constant folding: the rest of the ops have to be fleshed out case EOpSinh: case EOpCosh: case EOpTanh: case EOpAsinh: case EOpAcosh: case EOpAtanh: case EOpFloatBitsToInt: case EOpFloatBitsToUint: case EOpIntBitsToFloat: case EOpUintBitsToFloat: case EOpPackSnorm2x16: case EOpUnpackSnorm2x16: case EOpPackUnorm2x16: case EOpUnpackUnorm2x16: case EOpPackHalf2x16: case EOpUnpackHalf2x16: case EOpDeterminant: case EOpMatrixInverse: case EOpTranspose: case EOpAny: case EOpAll: default: return 0; } } TIntermConstantUnion *newNode = new TIntermConstantUnion(newConstArray, returnType); newNode->getWritableType().getQualifier().storage = EvqConst; newNode->setLoc(getLoc()); return newNode; }
bool isFin(float f) { return !isInf(f) && !isNan(f); }