示例#1
0
void Kernel::setArgument(unsigned int index, TypedValue value)
{
  assert(index < m_function->arg_size());

  const llvm::Value *argument = getArgument(index);

  // Deallocate existing argument
  if (m_values.count(argument))
  {
    delete[] m_values[argument].data;
  }

#if LLVM_VERSION >= 40
  if (getArgumentTypeName(index).str() == "sampler_t")
  {
    // Get an llvm::ConstantInt that represents the sampler value
    llvm::Type *i32 = llvm::Type::getInt32Ty(m_program->getLLVMContext());
    llvm::Constant *samplerValue = llvm::ConstantInt::get(i32, value.getSInt());

    // A sampler argument is a pointer to the llvm::ConstantInt value
    TypedValue sampler;
    sampler.size = sizeof(size_t);
    sampler.num = 1;
    sampler.data = new unsigned char[sizeof(size_t)];
    sampler.setPointer((size_t)samplerValue);

    m_values[argument] = sampler;
  }
  else
#endif
  {
    m_values[argument] = value.clone();
  }
}
bool InjectJoinFilters::findExactMinMaxValuesForAttributeHelper(
    const physical::PhysicalPtr &physical_plan,
    const expressions::AttributeReferencePtr &attribute,
    std::int64_t *min_cpp_value,
    std::int64_t *max_cpp_value) const {
  bool min_value_is_exact;
  bool max_value_is_exact;

  const TypedValue min_value =
      cost_model_->findMinValueStat(physical_plan, attribute, &min_value_is_exact);
  const TypedValue max_value =
      cost_model_->findMaxValueStat(physical_plan, attribute, &max_value_is_exact);
  if (min_value.isNull() || max_value.isNull() ||
      (!min_value_is_exact) || (!max_value_is_exact)) {
    return false;
  }

  switch (attribute->getValueType().getTypeID()) {
    case TypeID::kInt: {
      *min_cpp_value = min_value.getLiteral<int>();
      *max_cpp_value = max_value.getLiteral<int>();
      return true;
    }
    case TypeID::kLong: {
      *min_cpp_value = min_value.getLiteral<std::int64_t>();
      *max_cpp_value = max_value.getLiteral<std::int64_t>();
      return true;
    }
    default:
      return false;
  }
}
示例#3
0
bool WorkItem::printVariable(string name) const
{
  // Find variable
  const llvm::Value *value = getVariable(name);
  if (!value)
  {
    return false;
  }

  // Get variable value
  TypedValue result = getOperand(value);
  const llvm::Type *type = value->getType();

  if (value->getValueID() == llvm::Value::GlobalVariableVal ||
      ((const llvm::Instruction*)value)->getOpcode()
         == llvm::Instruction::Alloca)
  {
    // If value is alloca or global variable, look-up data at address
    size_t address = result.getPointer();
    Memory *memory = getMemory(value->getType()->getPointerAddressSpace());
    unsigned char *data = (unsigned char*)memory->getPointer(address);
    printTypedData(value->getType()->getPointerElementType(), data);
  }
  else
  {
    printTypedData(type, result.data);
  }

  return true;
}
  inline void iterateUnaryInl(AggregationStateSum *state, const TypedValue &value) const {
    DCHECK(value.isPlausibleInstanceOf(argument_type_.getSignature()));
    if (value.isNull()) return;

    SpinMutexLock lock(state->mutex_);
    state->sum_ = fast_operator_->applyToTypedValues(state->sum_, value);
    state->null_ = false;
  }
 /**
  * @brief Find the first code which is greater than the specified typed
  *        value, similar to std::upper_bound().
  * @warning value must not be NULL.
  *
  * @param value A typed value, which can be either the exact same Type as
  *        the values in this dictionary, or another Type which is comparable
  *        according to LessComparison.
  * @param value_type The Type that value belongs to.
  * @return The first code whose corresponding uncompressed value is greater
  *         than value. May return numberOfCodes() if every value in the
  *         dictionary is less than or equal to value.
  **/
 std::uint32_t getUpperBoundCodeForTypedValue(const TypedValue &value,
                                              const Type &value_type) const {
   DCHECK(!value.isNull());
   if (value_type.isSubsumedBy(type_)) {
     return getUpperBoundCodeForUntypedValue(value.getDataPtr());
   } else {
     return getUpperBoundCodeForDifferentTypedValue(value, value_type);
   }
 }
示例#6
0
文件: meta.cpp 项目: bacek/xscript
void
Meta::setMap(const std::string &name, const std::vector<StringUtils::NamedValue> &value) {
    TypedValue val = TypedValue::createMapValue();
    for (std::vector<StringUtils::NamedValue>::const_iterator it = value.begin();
         it != value.end();
         ++it) {
        val.add(it->first, TypedValue(it->second));
    }
    setTypedValue(name, val);
}
示例#7
0
文件: meta.cpp 项目: bacek/xscript
void
Meta::setArray(const std::string &name, const std::vector<std::string> &value) {
    TypedValue val = TypedValue::createArrayValue();
    for (std::vector<std::string>::const_iterator it = value.begin();
         it != value.end();
         ++it) {
        val.add(StringUtils::EMPTY_STRING, TypedValue(*it));
    }
    setTypedValue(name, val);
}
 /**
  * @brief Find the first code which is not less than the specified typed
  *        value, similar to std::lower_bound().
  * @warning value must not be NULL.
  *
  * @param value A typed value, which can be either the exact same Type as
  *        the values in this dictionary, or another Type which is comparable
  *        according to LessComparison.
  * @param value_type The Type that value belongs to.
  * @return The first code whose corresponding uncompressed value is not less
  *         than value. May return numberOfCodes() if every value in the
  *         dictionary is less than value.
  **/
 std::uint32_t getLowerBoundCodeForTypedValue(const TypedValue &value,
                                              const Type &value_type,
                                              const bool ignore_null_code = false) const {
   DCHECK(!value.isNull());
   if (value_type.isSubsumedBy(type_)) {
     return getLowerBoundCodeForUntypedValue(value.getDataPtr(), ignore_null_code);
   } else {
     return getLowerBoundCodeForDifferentTypedValue(value, value_type, ignore_null_code);
   }
 }
 /**
  * @brief Append a TypedValue to this NativeColumnVector.
  *
  * @param value A value to append to this NativeColumnVector.
  **/
 inline void appendTypedValue(const TypedValue &value) {
   DCHECK_LT(actual_length_, reserved_length_);
   DCHECK(value.isPlausibleInstanceOf(type_.getSignature()));
   if (null_bitmap_ && value.isNull()) {
     null_bitmap_->setBit(actual_length_, true);
   } else {
     DCHECK(!value.isNull());
     value.copyInto(static_cast<char*>(values_) + (actual_length_ * type_length_));
   }
   ++actual_length_;
 }
 /**
  * @brief Determine the range of codes that match a specified comparison with
  *        a specified typed value.
  *
  * @param comp The comparison to evaluate.
  * @param value A typed value, which can be either the exact same Type as
  *        the values in this dictionary, or another Type which is comparable
  *        according to LessComparison.
  * @param value_type The Type that value belongs to.
  * @return The limits of the range of codes which match the predicate
  *         "coded-value comp value". The range is [first, second) (i.e. it
  *         is inclusive of first but not second).
  **/
 std::pair<std::uint32_t, std::uint32_t> getLimitCodesForComparisonTyped(
     const ComparisonID comp,
     const TypedValue &value,
     const Type &value_type) const {
   if (value_type.isSubsumedBy(type_)) {
     return getLimitCodesForComparisonUntyped(comp,
                                              value.isNull() ? nullptr : value.getDataPtr());
   } else {
     return getLimitCodesForComparisonDifferentTyped(comp, value, value_type);
   }
 }
示例#11
0
 /**
  * @brief Overwrite the value at the specified position with the supplied
  *        TypedValue.
  * @warning You must call prepareForPositionalWrites() BEFORE calling this
  *          method.
  * @warning Do NOT use positional writes in combination with appends.
  * @warning It is intended that this and other positional write methods
  *          should be called exactly once for each position (if this is
  *          violated, NULLs may not be tracked properly).
  *
  * @param position The position of the value in this NativeColumnVector to
  *        overwrite.
  * @param value A TypedValue to write into this NativeColumnVector.
  **/
 inline void positionalWriteTypedValue(const std::size_t position,
                                       const TypedValue &value) {
   DCHECK_LT(position, actual_length_);
   DCHECK(value.isPlausibleInstanceOf(type_.getSignature()));
   if (null_bitmap_ && value.isNull()) {
     null_bitmap_->setBit(position, true);
   } else {
     DCHECK(!value.isNull());
     value.copyInto(static_cast<char*>(values_) + (position * type_length_));
   }
 }
 /**
  * @brief Get the compressed code that represents the specified typed value.
  * @note This uses a binary search to find the appropriate code. It runs in
  *       O(log(n)) time.
  *
  * @param value A typed value, which can be either the exact same Type as
  *        the values in this dictionary, or another Type which is comparable
  *        according to LessComparison.
  * @param value_type The Type that value belongs to.
  * @return The code for value in this dictionary, or the value of
  *         numberOfCodes() (the maximum code plus one) if value is not
  *         contained in this dictionary.
  **/
 std::uint32_t getCodeForTypedValue(const TypedValue &value,
                                    const Type &value_type) const {
   if (value.isNull()) {
     return getNullCode() == std::numeric_limits<std::uint32_t>::max() ? number_of_codes_including_null_
                                                                       : getNullCode();
   } else if (value_type.isSubsumedBy(type_)) {
     return getCodeForUntypedValue(value.getDataPtr());
   } else {
     return getCodeForDifferentTypedValue(value, value_type);
   }
 }
示例#13
0
void CharType::printValueToFile(const TypedValue &value,
                                FILE *file,
                                const int padding) const {
  DCHECK(!value.isNull());
  DCHECK_EQ(length_, static_cast<decltype(length_)>(static_cast<int>(length_)))
      << "Can not convert CHAR Type's maximum length " << length_
      << " to int for fprintf()";

  std::fprintf(file,
               "%*.*s",
               padding,
               static_cast<int>(length_),
               static_cast<const char*>(value.getOutOfLineData()));
}
示例#14
0
 /**
  * @brief Fill this entire ColumnVector with copies of value.
  *
  * @param value A value to fill this ColumnVector with.
  **/
 inline void fillWithValue(const TypedValue &value) {
   DCHECK(value.isPlausibleInstanceOf(type_.getSignature()));
   if (value.isNull()) {
     fillWithNulls();
   } else {
     if (null_bitmap_) {
       null_bitmap_->clear();
     }
     for (std::size_t pos = 0;
          pos < reserved_length_;
          ++pos) {
       value.copyInto(static_cast<char*>(values_) + (pos * type_length_));
     }
     actual_length_ = reserved_length_;
   }
 }
示例#15
0
 /**
  * @brief Calulate the partition id into which the attribute value
  *        should be inserted.
  *
  * @param value_of_attribute The attribute value for which the
  *                           partition id is to be determined.
  * @return The partition id of the partition for the attribute value.
  **/
 const partition_id getPartitionId(
     const TypedValue &value_of_attribute) const override {
   // TODO(gerald): Optimize for the case where the number of partitions is a
   // power of 2. We can just mask out the lower-order hash bits rather than
   // doing a division operation.
   return value_of_attribute.getHash() % num_partitions_;
 }
示例#16
0
void FacetHelper::generateIDAndNameForMultiValued(const TypedValue & attributeValue ,
		std::vector< std::pair<unsigned , std::string> > & resultIdsAndNames){
	ASSERT(attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_INT ||
	        attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_LONG ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_FLOAT ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_DOUBLE ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_TEXT ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_TIME);
	std::vector<TypedValue> singleValues;
	attributeValue.breakMultiValueIntoSingleValueTypedValueObjects(&singleValues);
	for(std::vector<TypedValue>::iterator singleValue = singleValues.begin() ; singleValue != singleValues.end() ; ++singleValue){
		std::pair<unsigned, std::string>  idAndNamePair = generateIDAndName(*singleValue);
		if(std::find(resultIdsAndNames.begin() , resultIdsAndNames.end() , idAndNamePair) == resultIdsAndNames.end()){
			resultIdsAndNames.push_back(idAndNamePair);
		}
	}
}
示例#17
0
TypedValue CharType::coerceValue(const TypedValue &original_value,
                                 const Type &original_type) const {
  DCHECK(isCoercibleFrom(original_type))
      << "Can't coerce value of Type " << original_type.getName()
      << " to Type " << getName();

  if (original_value.isNull()) {
    return makeNullValue();
  }

  const void *original_data = original_value.getOutOfLineData();
  const std::size_t original_data_size = original_value.getDataSize();

  // VARCHAR always has a null-terminator. CHAR(X) has a null-terminator when
  // string's length is less than X.
  const bool null_terminated
      = (original_type.getTypeID() == kVarChar)
        || (original_data_size < original_type.maximumByteLength())
        || (std::memchr(original_data, '\0', original_data_size) != nullptr);

  if (original_data_size <= length_) {
    if (null_terminated || (original_data_size == length_)) {
      TypedValue value_copy(original_value);
      value_copy.markType(kChar);
      return value_copy;
    } else {
      // Need to make a new NULL-terminated copy of the string.
      char *null_terminated_str = static_cast<char*>(std::malloc(original_data_size + 1));
      std::memcpy(null_terminated_str, original_data, original_data_size);
      null_terminated_str[original_data_size] = '\0';
      return TypedValue::CreateWithOwnedData(kChar,
                                             null_terminated_str,
                                             original_data_size + 1);
    }
  } else {
    // Need to truncate.
    if (original_value.ownsOutOfLineData()) {
      char *truncated_str = static_cast<char*>(std::malloc(length_));
      std::memcpy(truncated_str, original_data, length_);
      return TypedValue::CreateWithOwnedData(kChar, truncated_str, length_);
    } else {
      // Original is a reference, so we will just make a shorter reference.
      return TypedValue(kChar, original_data, length_);
    }
  }
}
  TypedValue applyToTypedValue(const TypedValue &argument) const override {
    if (source_nullability && argument.isNull()) {
      return TypedValue(TargetType::kStaticTypeID);
    }

    return TypedValue(static_cast<typename TargetType::cpptype>(
        argument.getLiteral<typename SourceType::cpptype>()));
  }
示例#19
0
void FacetOperator::doProcessOneResult(const TypedValue & attributeValue, const unsigned facetFieldIndex){
	if(attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_INT ||
	        attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_LONG ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_FLOAT ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_DOUBLE ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_TEXT ||
			attributeValue.getType() == ATTRIBUTE_TYPE_MULTI_TIME){
		std::vector<std::pair<unsigned , std::string> > idsAndNames;
		this->facetHelpers.at(facetFieldIndex)->generateIDAndNameForMultiValued(attributeValue , idsAndNames);
		for(std::vector<std::pair<unsigned , std::string> >::iterator idAndName = idsAndNames.begin() ; idAndName != idsAndNames.end() ; ++idAndName){
			this->facetResults.at(facetFieldIndex).second->addResultToBucket(idAndName->first , idAndName->second , FacetAggregationTypeCount);
		}
	}else{ // single value
		std::pair<unsigned , std::string> idandName = this->facetHelpers.at(facetFieldIndex)->generateIDAndName(attributeValue);
		this->facetResults.at(facetFieldIndex).second->addResultToBucket(idandName.first , idandName.second , FacetAggregationTypeCount);
	}
}
示例#20
0
std::pair<unsigned , std::string> CategoricalFacetHelper::generateIDAndName(const TypedValue & attributeValue){
	std::string attributeValueLowerCase = attributeValue.toString();
	std::transform(attributeValueLowerCase.begin(), attributeValueLowerCase.end(), attributeValueLowerCase.begin(), ::tolower);

	if(categoryValueToBucketIdMap.find(attributeValueLowerCase) == categoryValueToBucketIdMap.end()){
		categoryValueToBucketIdMap[attributeValueLowerCase] = categoryValueToBucketIdMap.size();
	}
	return std::make_pair(categoryValueToBucketIdMap[attributeValueLowerCase] , attributeValueLowerCase);
}
示例#21
0
void IntType::printValueToFile(const TypedValue &value,
                               FILE *file,
                               const int padding) const {
  DCHECK(!value.isNull());

  std::fprintf(file,
               "%*d",
               static_cast<int>(padding),
               value.getLiteral<int>());
}
示例#22
0
void LongType::printValueToFile(const TypedValue &value,
                                FILE *file,
                                const int padding) const {
  DCHECK(!value.isNull());

  std::fprintf(file,
               "%*" PRId64,
               static_cast<int>(padding),
               value.getLiteral<std::int64_t>());
}
示例#23
0
bool install_catch_trace(_Unwind_Context* ctx, _Unwind_Exception* exn,
                         bool do_side_exit, TypedValue unwinder_tv) {
  auto const rip = (TCA)_Unwind_GetIP(ctx);
  auto catchTraceOpt = mcg->getCatchTrace(rip);
  FTRACE(1, "No catch trace entry for ip {}; bailing\n", rip);
  if (!catchTraceOpt) return false;

  auto catchTrace = *catchTraceOpt;
  if (!catchTrace) {
    // A few of our optimization passes must be aware of every path out of the
    // trace, so throwing through jitted code without a catch block is very
    // bad. This is indicated with a present but nullptr entry in the catch
    // trace map.
    const size_t kCallSize = 5;
    const uint8_t kCallOpcode = 0xe8;

    auto callAddr = rip - kCallSize;
    TCA helperAddr = nullptr;
    std::string helperName;
    if (*callAddr == kCallOpcode) {
      helperAddr = rip + *reinterpret_cast<int32_t*>(callAddr + 1);
    }

    always_assert_flog(false,
                       "Translated call to {} threw '{}' without "
                       "catch block, return address: {}\n",
                       getNativeFunctionName(helperAddr),
                       exceptionFromUnwindException(exn)->what(),
                       rip);
    return false;
  }

  FTRACE(1, "installing catch trace {} for call {} with tv {}, "
         "returning _URC_INSTALL_CONTEXT\n",
         catchTrace, rip, unwinder_tv.pretty());

  // In theory the unwind api will let us set registers in the frame
  // before executing our landing pad. In practice, trying to use
  // their recommended scratch registers results in a SEGV inside
  // _Unwind_SetGR, so we pass things to the handler using the
  // RDS. This also simplifies the handler code because it doesn't
  // have to worry about saving its arguments somewhere while
  // executing the exit trace.
  unwindRdsInfo->unwinderScratch = (int64_t)exn;
  unwindRdsInfo->doSideExit = do_side_exit;
  if (do_side_exit) {
    unwindRdsInfo->unwinderTv = unwinder_tv;
  }
  _Unwind_SetIP(ctx, (uint64_t)catchTrace);
  tl_regState = VMRegState::DIRTY;

  return true;
}
示例#24
0
/*
 * Example :
 * If we have two attributes : price,model (facet type : range, categorical)
 * and start,end and gap for price are 1,100 and 10. Then this function
 * produces an empty vector for model (because it's categorical) and a vector with the following
 * values for price:
 * -large_value, 1, 11, 21, 31, 41, ..., 91, 101
 */
void RangeFacetHelper::generateListOfIdsAndNames(std::vector<std::pair<unsigned, std::string> > * idsAndNames){

	if(generateListOfIdsAndNamesFlag == true || idsAndNames == NULL){
		ASSERT(false);
		return;
	}
	TypedValue lowerBoundToAdd = start;
    std::vector<TypedValue> lowerBounds;
	// Example : start : 1, gap : 10 , end : 100
	// first -large_value is added as the first category
	// then 1, 11, 21, ...and 91 are added in the loop.
	// and 101 is added after loop.
	lowerBounds.push_back(lowerBoundToAdd.minimumValue()); // to collect data smaller than start
	while (lowerBoundToAdd < end) {
		lowerBounds.push_back(lowerBoundToAdd); // data of normal categories
		lowerBoundToAdd = lowerBoundToAdd + gap;
	}
	lowerBounds.push_back(end); // to collect data greater than end
	// now set the number of buckets
	numberOfBuckets = lowerBounds.size();
	// now fill the output
	for(int lowerBoundsIndex = 0; lowerBoundsIndex < lowerBounds.size() ; lowerBoundsIndex++){
		string bucketName = lowerBounds.at(lowerBoundsIndex).toString();
		/*
		 * If the type of this facet attribute is time, we should translate the number of
		 * seconds from Jan 1st 1970 (aka "epoch") to a human readable representation of time.
		 * For example, if this value is 1381271294, the name of this bucket is 10/8/2013 3:28:14.
		 */
		if(attributeType == ATTRIBUTE_TYPE_TIME){
			long timeValue = lowerBounds.at(lowerBoundsIndex).getTimeTypedValue();
			bucketName = DateAndTimeHandler::convertSecondsFromEpochToDateTimeString(&timeValue);
		}
		idsAndNames->push_back(std::make_pair(lowerBoundsIndex , bucketName));
	}
	// And set the flag to make sure this function is called only once.
	generateListOfIdsAndNamesFlag = false;

}
示例#25
0
/*
 * This function finds the interval in which attributeValue is placed. ID and name will be returned. since all the names are returned once
 * in generateListOfIdsAndNames, all names are returned as "" to save copying string values.
 */
std::pair<unsigned , std::string> RangeFacetHelper::generateIDAndName(const TypedValue & attributeValue){
	if(attributeValue >= end){
		return std::make_pair(numberOfBuckets-1 , "");
	}
	unsigned bucketId = attributeValue.findIndexOfContainingInterval(start, end, gap);
    if(bucketId == -1){ // Something has gone wrong and Score class has been unable to calculate the index.
    	ASSERT(false);
        return std::make_pair(0 , "");;
    }
    if(bucketId >= numberOfBuckets){
    	bucketId =  numberOfBuckets - 1;
    }
    return std::make_pair(bucketId , "");
}
示例#26
0
文件: meta.cpp 项目: bacek/xscript
static void
processNewMetaNode(const std::string &name, const TypedValue &value,
        XmlNodeHelper &result, xmlNodePtr &last_node) {
    XmlTypedVisitor visitor;
    value.visit(&visitor);
    XmlNodeHelper res = visitor.result();
    xmlNewProp(res.get(), (const xmlChar*)"name", (const xmlChar*)name.c_str());
    if (result.get()) {
        last_node = xmlAddNextSibling(last_node, res.release());
    }
    else {
        result = res;
        last_node = result.get();
    }
}
示例#27
0
文件: stack.cpp 项目: bacek/xscript
static TypedValue
luaReadTableInternal(lua_State *lua, int index) {
    lua_pushnil(lua);
    TypedValue value = TypedValue::createArrayValue();
    bool is_map  = false;
    bool is_first  = true;
    while (lua_next(lua, index)) {
        if (is_first) {
            is_first = false;
            is_map = !lua_isnumber(lua, -2);
            if (is_map) {
                value = TypedValue::createMapValue();
            }
        }
        std::string key;
        if (is_map) {
            key.assign(lua_tostring(lua, -2));
        }
        switch (lua_type(lua, -1)) {
            case LUA_TNIL:
                value.add(key, TypedValue());
                break;
            case LUA_TBOOLEAN:
                value.add(key, TypedValue(0 != lua_toboolean(lua, -1)));
                break;
            case LUA_TNUMBER: {
                double d = lua_tonumber(lua, -1);
                isLongInteger(d) ? value.add(key, TypedValue((boost::int64_t)d)) :
                    value.add(key, TypedValue(d));
                break;
            }
            case LUA_TSTRING:
                value.add(key, TypedValue(std::string(lua_tostring(lua, -1))));
                break;
            case LUA_TTABLE:
                value.add(key, luaReadTableInternal(lua, lua_gettop(lua)));
                break;
            default:
                throw BadType("nil, bool, number, string or table", -1);
        }
        lua_pop(lua, 1);
    }
    return value;
}
示例#28
0
文件: args.cpp 项目: bacek/xscript
void
ArgList::addAs(const std::string &type, const TypedValue &value) {
    if (!type.empty()) {
        addAs(type, value.asString());
    }
    else if (value.nil()) {
        add(StringUtils::EMPTY_STRING);
    }
    else if (value.type() == TypedValue::TYPE_STRING) {
        add(value.asString());
    }
    else {
        addAs(value.stringType(), value.asString());
    }
}
示例#29
0
bool install_catch_trace(_Unwind_Context* ctx, _Unwind_Exception* exn,
                         bool do_side_exit, TypedValue unwinder_tv) {
  auto const rip = (TCA)_Unwind_GetIP(ctx);
  auto catchTrace = lookup_catch_trace(rip, exn);
  if (!catchTrace) {
    FTRACE(1, "No catch trace entry for ip {}; bailing\n", rip);
    return false;
  }

  FTRACE(1, "installing catch trace {} for call {} with tv {}, "
         "returning _URC_INSTALL_CONTEXT\n",
         catchTrace, rip, unwinder_tv.pretty());

  // If the catch trace isn't going to finish by calling _Unwind_Resume, we
  // consume the exception here. Otherwise, we leave a pointer to it in RDS so
  // endCatchHelper can pass it to _Unwind_Resume when it's done.
  if (do_side_exit) {
    unwindRdsInfo->exn = nullptr;
#ifndef _MSC_VER
    __cxxabiv1::__cxa_begin_catch(exn);
    __cxxabiv1::__cxa_end_catch();
#endif
  } else {
    unwindRdsInfo->exn = exn;
  }

  // In theory the unwind api will let us set registers in the frame before
  // executing our landing pad. In practice, trying to use their recommended
  // scratch registers results in a SEGV inside _Unwind_SetGR, so we pass
  // things to the handler using the RDS. This also simplifies the handler code
  // because it doesn't have to worry about saving its arguments somewhere
  // while executing the exit trace.
  unwindRdsInfo->doSideExit = do_side_exit;
  if (do_side_exit) unwindRdsInfo->unwinderTv = unwinder_tv;
  _Unwind_SetIP(ctx, (uint64_t)catchTrace);
  tl_regState = VMRegState::DIRTY;

  return true;
}
示例#30
0
TypedValue LongType::coerceValue(const TypedValue &original_value,
                                 const Type &original_type) const {
  DCHECK(isCoercibleFrom(original_type))
      << "Can't coerce value of Type " << original_type.getName()
      << " to Type " << getName();

  if (original_value.isNull()) {
    return makeNullValue();
  }

  switch (original_type.getTypeID()) {
    case kInt:
      return TypedValue(static_cast<std::int64_t>(original_value.getLiteral<int>()));
    case kLong:
      return original_value;
    case kFloat:
      return TypedValue(static_cast<std::int64_t>(original_value.getLiteral<float>()));
    case kDouble:
      return TypedValue(static_cast<std::int64_t>(original_value.getLiteral<double>()));
    default:
      LOG(FATAL) << "Attempted to coerce Type " << original_type.getName()
                 << " (not recognized as a numeric Type) to " << getName();
  }
}