Author: uweigand Date: Thu Apr 14 09:32:01 2016 New Revision: 266311 URL: http://llvm.org/viewvc/llvm-project?rev=266311&view=rev Log: Fix usage of APInt.getRawData for big-endian systems
The Scalar implementation and a few other places in LLDB directly access the internal implementation of APInt values using the getRawData method. Unfortunately, pretty much all of these places do not handle big-endian systems correctly. While on little-endian machines, the pointer returned by getRawData can simply be used as a pointer to the integer value in its natural format, no matter what size, this is not true on big-endian systems: getRawData actually points to an array of type uint64_t, with the first element of the array always containing the least-significant word of the integer. This means that if the bitsize of that integer is smaller than 64, we need to add an offset to the pointer returned by getRawData in order to access the value in its natural type, and if the bitsize is *larger* than 64, we actually have to swap the constituent words before we can access the value in its natural type. This patch fixes every incorrect use of getRawData in the code base. For the most part, this is done by simply removing uses of getRawData in the first place, and using other APInt member functions to operate on the integer data. This can be done in many member functions of Scalar itself, as well as in Symbol/Type.h and in IRInterpreter::Interpret. For the latter, I've had to add a Scalar::MakeUnsigned routine to parallel the existing Scalar::MakeSigned, e.g. in order to implement an unsigned divide. The Scalar::RawUInt, Scalar::RawULong, and Scalar::RawULongLong were already unused and can be simply removed. I've also removed the Scalar::GetRawBits64 function and its few users. The one remaining user of getRawData in Scalar.cpp is GetBytes. I've implemented all the cases described above to correctly implement access to the underlying integer data on big-endian systems. GetData now simply calls GetBytes instead of reimplementing its contents. Finally, two places in the clang interface code were also accessing APInt.getRawData in order to actually construct a byte representation of an integer. I've changed those to make use of a Scalar instead, to avoid having to re-implement the logic there. The patch also adds a couple of unit tests verifying correct operation of the GetBytes routine as well as the conversion routines. Those tests actually exposed more problems in the Scalar code: the SetValueFromData routine didn't work correctly for 128- and 256-bit data types, and the SChar routine should have an explicit "signed char" return type to work correctly on platforms where char defaults to unsigned. Differential Revision: http://reviews.llvm.org/D18981 Modified: lldb/trunk/include/lldb/Core/Scalar.h lldb/trunk/include/lldb/Symbol/Type.h lldb/trunk/source/Core/Scalar.cpp lldb/trunk/source/Expression/IRInterpreter.cpp lldb/trunk/source/Plugins/ExpressionParser/Clang/IRForTarget.cpp lldb/trunk/source/Symbol/ClangASTContext.cpp lldb/trunk/unittests/Core/ScalarTest.cpp Modified: lldb/trunk/include/lldb/Core/Scalar.h URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Core/Scalar.h?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/include/lldb/Core/Scalar.h (original) +++ lldb/trunk/include/lldb/Core/Scalar.h Thu Apr 14 09:32:01 2016 @@ -162,6 +162,9 @@ public: bool MakeSigned (); + bool + MakeUnsigned (); + static const char * GetValueTypeAsCString (Scalar::Type value_type); @@ -239,22 +242,10 @@ public: int SInt(int fail_value = 0) const; - // Return the raw unsigned integer without any casting or conversion - unsigned int - RawUInt () const; - - // Return the raw unsigned long without any casting or conversion - unsigned long - RawULong () const; - - // Return the raw unsigned long long without any casting or conversion - unsigned long long - RawULongLong () const; - unsigned char UChar(unsigned char fail_value = 0) const; - char + signed char SChar(char fail_value = 0) const; unsigned short @@ -299,9 +290,6 @@ public: long double LongDouble(long double fail_value = 0.0) const; - uint64_t - GetRawBits64 (uint64_t fail_value) const; - Error SetValueFromCString (const char *s, lldb::Encoding encoding, size_t byte_size); Modified: lldb/trunk/include/lldb/Symbol/Type.h URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/include/lldb/Symbol/Type.h?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/include/lldb/Symbol/Type.h (original) +++ lldb/trunk/include/lldb/Symbol/Type.h Thu Apr 14 09:32:01 2016 @@ -958,13 +958,13 @@ public: uint64_t GetValueAsUnsigned () const { - return *m_value.getRawData(); + return m_value.getZExtValue(); } int64_t GetValueAsSigned () const { - return (int64_t) *m_value.getRawData(); + return m_value.getSExtValue(); } protected: Modified: lldb/trunk/source/Core/Scalar.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Core/Scalar.cpp?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/source/Core/Scalar.cpp (original) +++ lldb/trunk/source/Core/Scalar.cpp Thu Apr 14 09:32:01 2016 @@ -16,6 +16,8 @@ #include <cstdio> // Other libraries and framework includes +#include "llvm/ADT/SmallString.h" + // Project includes #include "lldb/Interpreter/Args.h" #include "lldb/Core/Error.h" @@ -134,10 +136,10 @@ bool Scalar::GetData (DataExtractor &data, size_t limit_byte_size) const { size_t byte_size = GetByteSize(); - static float f_val; - static double d_val; if (byte_size > 0) { + const uint8_t *bytes = reinterpret_cast<const uint8_t *>(GetBytes()); + if (limit_byte_size < byte_size) { if (endian::InlHostByteOrder() == eByteOrderLittle) @@ -145,105 +147,19 @@ Scalar::GetData (DataExtractor &data, si // On little endian systems if we want fewer bytes from the // current type we just specify fewer bytes since the LSByte // is first... - switch(m_type) - { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - data.SetData((const uint8_t *)m_integer.getRawData(), limit_byte_size, endian::InlHostByteOrder()); - return true; - case e_float: - f_val = m_float.convertToFloat(); - data.SetData((uint8_t *)&f_val, limit_byte_size, endian::InlHostByteOrder()); - return true; - case e_double: - d_val = m_float.convertToDouble(); - data.SetData((uint8_t *)&d_val, limit_byte_size, endian::InlHostByteOrder()); - return true; - case e_long_double: - static llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - data.SetData((const uint8_t *)ldbl_val.getRawData(), limit_byte_size, endian::InlHostByteOrder()); - return true; - } + byte_size = limit_byte_size; } else if (endian::InlHostByteOrder() == eByteOrderBig) { // On big endian systems if we want fewer bytes from the // current type have to advance our initial byte pointer and // trim down the number of bytes since the MSByte is first - switch(m_type) - { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - data.SetData((const uint8_t *)m_integer.getRawData() + byte_size - limit_byte_size, limit_byte_size, endian::InlHostByteOrder()); - return true; - case e_float: - f_val = m_float.convertToFloat(); - data.SetData((uint8_t *)&f_val + byte_size - limit_byte_size, limit_byte_size, endian::InlHostByteOrder()); - return true; - case e_double: - d_val = m_float.convertToDouble(); - data.SetData((uint8_t *)&d_val + byte_size - limit_byte_size, limit_byte_size, endian::InlHostByteOrder()); - return true; - case e_long_double: - static llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - data.SetData((const uint8_t *)ldbl_val.getRawData() + byte_size - limit_byte_size, limit_byte_size, endian::InlHostByteOrder()); - return true; - } - } - } - else - { - // We want all of the data - switch(m_type) - { - case e_void: - break; - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - data.SetData((const uint8_t *)m_integer.getRawData(), byte_size, endian::InlHostByteOrder()); - return true; - case e_float: - f_val = m_float.convertToFloat(); - data.SetData((uint8_t *)&f_val, byte_size, endian::InlHostByteOrder()); - return true; - case e_double: - d_val = m_float.convertToDouble(); - data.SetData((uint8_t *)&d_val, byte_size, endian::InlHostByteOrder()); - return true; - case e_long_double: - static llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - data.SetData((const uint8_t *)ldbl_val.getRawData(), byte_size, endian::InlHostByteOrder()); - return true; + bytes += byte_size - limit_byte_size; + byte_size = limit_byte_size; } } + + data.SetData(bytes, byte_size, endian::InlHostByteOrder()); return true; } data.Clear(); @@ -253,8 +169,11 @@ Scalar::GetData (DataExtractor &data, si const void * Scalar::GetBytes() const { + const uint64_t *apint_words; + const uint8_t *bytes; static float_t flt_val; static double_t dbl_val; + static uint64_t swapped_words[4]; switch (m_type) { case e_void: @@ -265,11 +184,44 @@ Scalar::GetBytes() const case e_ulong: case e_slonglong: case e_ulonglong: + bytes = reinterpret_cast<const uint8_t *>(m_integer.getRawData()); + // getRawData always returns a pointer to an uint64_t. If we have a smaller type, + // we need to update the pointer on big-endian systems. + if (endian::InlHostByteOrder() == eByteOrderBig) + { + size_t byte_size = m_integer.getBitWidth() / 8; + if (byte_size < 8) + bytes += 8 - byte_size; + } + return bytes; case e_sint128: case e_uint128: + apint_words = m_integer.getRawData(); + // getRawData always returns a pointer to an array of two uint64_t values, + // where the least-significant word always comes first. On big-endian + // systems we need to swap the two words. + if (endian::InlHostByteOrder() == eByteOrderBig) + { + swapped_words[0] = apint_words[1]; + swapped_words[1] = apint_words[0]; + apint_words = swapped_words; + } + return reinterpret_cast<const void *>(apint_words); case e_sint256: case e_uint256: - return reinterpret_cast<const void *>(m_integer.getRawData()); + apint_words = m_integer.getRawData(); + // getRawData always returns a pointer to an array of four uint64_t values, + // where the least-significant word always comes first. On big-endian + // systems we need to swap the four words. + if (endian::InlHostByteOrder() == eByteOrderBig) + { + swapped_words[0] = apint_words[3]; + swapped_words[1] = apint_words[2]; + swapped_words[2] = apint_words[1]; + swapped_words[3] = apint_words[0]; + apint_words = swapped_words; + } + return reinterpret_cast<const void *>(apint_words); case e_float: flt_val = m_float.convertToFloat(); return reinterpret_cast<const void *>(&flt_val); @@ -278,7 +230,17 @@ Scalar::GetBytes() const return reinterpret_cast<const void *>(&dbl_val); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return reinterpret_cast<const void *>(ldbl_val.getRawData()); + apint_words = ldbl_val.getRawData(); + // getRawData always returns a pointer to an array of two uint64_t values, + // where the least-significant word always comes first. On big-endian + // systems we need to swap the two words. + if (endian::InlHostByteOrder() == eByteOrderBig) + { + swapped_words[0] = apint_words[1]; + swapped_words[1] = apint_words[0]; + apint_words = swapped_words; + } + return reinterpret_cast<const void *>(apint_words); } return nullptr; } @@ -338,7 +300,6 @@ Scalar::IsZero() const void Scalar::GetValue (Stream *s, bool show_type) const { - const uint64_t *src; if (show_type) s->Printf("(%s) ", GetTypeAsCString()); @@ -346,28 +307,26 @@ Scalar::GetValue (Stream *s, bool show_t { case e_void: break; - case e_sint: s->Printf("%i", *(const sint_t *) m_integer.getRawData()); break; - case e_uint: s->Printf("0x%8.8x", *(const uint_t *) m_integer.getRawData()); break; - case e_slong: s->Printf("%li", *(const slong_t *) m_integer.getRawData()); break; - case e_ulong: s->Printf("0x%8.8lx", *(const ulong_t *) m_integer.getRawData()); break; - case e_slonglong: s->Printf("%lli", *(const slonglong_t *) m_integer.getRawData()); break; - case e_ulonglong: s->Printf("0x%16.16llx", *(const ulonglong_t *) m_integer.getRawData()); break; + case e_sint: + case e_ulong: + case e_slonglong: case e_sint128: case e_sint256: s->Printf("%s",m_integer.toString(10,true).c_str()); break; + case e_uint: + case e_slong: + case e_ulonglong: case e_uint128: - src = m_integer.getRawData(); - s->Printf("0x%16.16llx%16.16llx", *(const ulonglong_t *)src, *(const ulonglong_t *)(src + 1)); - break; case e_uint256: s->Printf("%s",m_integer.toString(16,false).c_str()); break; - case e_float: s->Printf("%f", m_float.convertToFloat()); break; - case e_double: s->Printf("%g", m_float.convertToDouble()); break; + case e_float: + case e_double: case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - s->Printf("%Lg", *(const long_double_t *)ldbl_val.getRawData()); + llvm::SmallString<24> string; + m_float.toString(string); + s->Printf("%s", string.c_str()); break; } } @@ -535,39 +494,47 @@ Scalar::Promote(Scalar::Type type) case e_void: break; case e_sint: success = true; break; case e_uint: - m_integer = llvm::APInt(sizeof(uint_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(uint_t) * 8); success = true; break; case e_slong: - m_integer = llvm::APInt(sizeof(slong_t) * 8, *(const uint64_t *)m_integer.getRawData(), true); + m_integer = m_integer.sextOrTrunc(sizeof(slong_t) * 8); success = true; break; case e_ulong: - m_integer = llvm::APInt(sizeof(ulong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulong_t) * 8); success = true; break; case e_slonglong: - m_integer = llvm::APInt(sizeof(slonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), true); + m_integer = m_integer.sextOrTrunc(sizeof(slonglong_t) * 8); success = true; break; case e_ulonglong: - m_integer = llvm::APInt(sizeof(ulonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); success = true; break; case e_sint128: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); + success = true; + break; + case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -598,34 +565,42 @@ Scalar::Promote(Scalar::Type type) case e_sint: break; case e_uint: success = true; break; case e_slong: - m_integer = llvm::APInt(sizeof(slong_t) * 8, *(const uint64_t *)m_integer.getRawData(), true); + m_integer = m_integer.sextOrTrunc(sizeof(slong_t) * 8); success = true; break; case e_ulong: - m_integer = llvm::APInt(sizeof(ulong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulong_t) * 8); success = true; break; case e_slonglong: - m_integer = llvm::APInt(sizeof(slonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), true); + m_integer = m_integer.sextOrTrunc(sizeof(slonglong_t) * 8); success = true; break; case e_ulonglong: - m_integer = llvm::APInt(sizeof(ulonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); success = true; break; case e_sint128: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); + success = true; + break; + case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -657,29 +632,37 @@ Scalar::Promote(Scalar::Type type) case e_uint: break; case e_slong: success = true; break; case e_ulong: - m_integer = llvm::APInt(sizeof(ulong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulong_t) * 8); success = true; break; case e_slonglong: - m_integer = llvm::APInt(sizeof(slonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), true); + m_integer = m_integer.sextOrTrunc(sizeof(slonglong_t) * 8); success = true; break; case e_ulonglong: - m_integer = llvm::APInt(sizeof(ulonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); success = true; break; case e_sint128: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); + success = true; + break; + case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -712,24 +695,32 @@ Scalar::Promote(Scalar::Type type) case e_slong: break; case e_ulong: success = true; break; case e_slonglong: - m_integer = llvm::APInt(sizeof(slonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), true); + m_integer = m_integer.sextOrTrunc(sizeof(slonglong_t) * 8); success = true; break; case e_ulonglong: - m_integer = llvm::APInt(sizeof(ulonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); success = true; break; case e_sint128: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); + success = true; + break; + case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -763,19 +754,27 @@ Scalar::Promote(Scalar::Type type) case e_ulong: break; case e_slonglong: success = true; break; case e_ulonglong: - m_integer = llvm::APInt(sizeof(ulonglong_t) * 8, *(const uint64_t *)m_integer.getRawData(), false); + m_integer = m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8); success = true; break; case e_sint128: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); + success = true; + break; + case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -810,14 +809,22 @@ Scalar::Promote(Scalar::Type type) case e_slonglong: break; case e_ulonglong: success = true; break; case e_sint128: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT128); + success = true; + break; + case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -853,13 +860,17 @@ Scalar::Promote(Scalar::Type type) case e_ulonglong: break; case e_sint128: success = true; break; case e_uint128: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT128); success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -896,8 +907,12 @@ Scalar::Promote(Scalar::Type type) case e_sint128: break; case e_uint128: success = true; break; case e_sint256: + m_integer = m_integer.sextOrTrunc(BITWIDTH_INT256); + success = true; + break; + case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, ((const type256 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -935,7 +950,7 @@ Scalar::Promote(Scalar::Type type) case e_uint128: break; case e_sint256: success = true; break; case e_uint256: - m_integer = llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((const type128 *)m_integer.getRawData())); + m_integer = m_integer.zextOrTrunc(BITWIDTH_INT256); success = true; break; @@ -1369,9 +1384,35 @@ Scalar::MakeSigned () case e_slonglong: success = true; break; case e_ulonglong: m_type = e_slonglong; success = true; break; case e_sint128: success = true; break; - case e_uint128: m_type = e_sint; success = true; break; + case e_uint128: m_type = e_sint128; success = true; break; + case e_sint256: success = true; break; + case e_uint256: m_type = e_sint256; success = true; break; + case e_float: success = true; break; + case e_double: success = true; break; + case e_long_double: success = true; break; + } + + return success; +} + +bool +Scalar::MakeUnsigned () +{ + bool success = false; + + switch (m_type) + { + case e_void: break; + case e_sint: success = true; break; + case e_uint: m_type = e_uint; success = true; break; + case e_slong: success = true; break; + case e_ulong: m_type = e_ulong; success = true; break; + case e_slonglong: success = true; break; + case e_ulonglong: m_type = e_ulonglong; success = true; break; + case e_sint128: success = true; break; + case e_uint128: m_type = e_uint128; success = true; break; case e_sint256: success = true; break; - case e_uint256: m_type = e_sint; success = true; break; + case e_uint256: m_type = e_uint256; success = true; break; case e_float: success = true; break; case e_double: success = true; break; case e_long_double: success = true; break; @@ -1380,7 +1421,7 @@ Scalar::MakeSigned () return success; } -char +signed char Scalar::SChar(char fail_value) const { switch (m_type) @@ -1396,14 +1437,14 @@ Scalar::SChar(char fail_value) const case e_uint128: case e_sint256: case e_uint256: - return *(const schar_t *)(m_integer.sextOrTrunc(sizeof(schar_t) * 8)).getRawData(); + return (schar_t)(m_integer.sextOrTrunc(sizeof(schar_t) * 8)).getSExtValue(); case e_float: return (schar_t)m_float.convertToFloat(); case e_double: return (schar_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (schar_t)*ldbl_val.getRawData(); + return (schar_t)(ldbl_val.sextOrTrunc(sizeof(schar_t) * 8)).getSExtValue(); } return fail_value; } @@ -1424,14 +1465,14 @@ Scalar::UChar(unsigned char fail_value) case e_uint128: case e_sint256: case e_uint256: - return *(const uchar_t *)m_integer.getRawData(); + return (uchar_t)(m_integer.zextOrTrunc(sizeof(uchar_t) * 8)).getZExtValue(); case e_float: return (uchar_t)m_float.convertToFloat(); case e_double: return (uchar_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return (uchar_t)*ldbl_val.getRawData(); + return (uchar_t)(ldbl_val.zextOrTrunc(sizeof(uchar_t) * 8)).getZExtValue(); } return fail_value; } @@ -1452,14 +1493,14 @@ Scalar::SShort(short fail_value) const case e_uint128: case e_sint256: case e_uint256: - return *(const sshort_t *)(m_integer.sextOrTrunc(sizeof(sshort_t) * 8)).getRawData(); + return (sshort_t)(m_integer.sextOrTrunc(sizeof(sshort_t) * 8)).getSExtValue(); case e_float: return (sshort_t)m_float.convertToFloat(); case e_double: return (sshort_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const sshort_t *)ldbl_val.getRawData(); + return (sshort_t)(ldbl_val.sextOrTrunc(sizeof(sshort_t) * 8)).getSExtValue(); } return fail_value; } @@ -1480,14 +1521,14 @@ Scalar::UShort(unsigned short fail_value case e_uint128: case e_sint256: case e_uint256: - return *(const ushort_t *)m_integer.getRawData(); + return (ushort_t)(m_integer.zextOrTrunc(sizeof(ushort_t) * 8)).getZExtValue(); case e_float: return (ushort_t)m_float.convertToFloat(); case e_double: return (ushort_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const ushort_t *)ldbl_val.getRawData();; + return (ushort_t)(ldbl_val.zextOrTrunc(sizeof(ushort_t) * 8)).getZExtValue(); } return fail_value; } @@ -1508,14 +1549,14 @@ Scalar::SInt(int fail_value) const case e_uint128: case e_sint256: case e_uint256: - return *(const sint_t *)(m_integer.sextOrTrunc(sizeof(sint_t) * 8)).getRawData(); + return (sint_t)(m_integer.sextOrTrunc(sizeof(sint_t) * 8)).getSExtValue(); case e_float: return (sint_t)m_float.convertToFloat(); case e_double: return (sint_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const sint_t *)ldbl_val.getRawData(); + return (sint_t)(ldbl_val.sextOrTrunc(sizeof(sint_t) * 8)).getSExtValue(); } return fail_value; } @@ -1536,14 +1577,14 @@ Scalar::UInt(unsigned int fail_value) co case e_uint128: case e_sint256: case e_uint256: - return *(const uint_t *)m_integer.getRawData(); + return (uint_t)(m_integer.zextOrTrunc(sizeof(uint_t) * 8)).getZExtValue(); case e_float: return (uint_t)m_float.convertToFloat(); case e_double: return (uint_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const uint_t *)ldbl_val.getRawData(); + return (uint_t)(ldbl_val.zextOrTrunc(sizeof(uint_t) * 8)).getZExtValue(); } return fail_value; } @@ -1564,14 +1605,14 @@ Scalar::SLong(long fail_value) const case e_uint128: case e_sint256: case e_uint256: - return *(const slong_t *)(m_integer.sextOrTrunc(sizeof(slong_t) * 8)).getRawData(); + return (slong_t)(m_integer.sextOrTrunc(sizeof(slong_t) * 8)).getSExtValue(); case e_float: return (slong_t)m_float.convertToFloat(); case e_double: return (slong_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const slong_t *)ldbl_val.getRawData(); + return (slong_t)(ldbl_val.sextOrTrunc(sizeof(slong_t) * 8)).getSExtValue(); } return fail_value; } @@ -1592,44 +1633,14 @@ Scalar::ULong(unsigned long fail_value) case e_uint128: case e_sint256: case e_uint256: - return *(const ulong_t *)m_integer.getRawData(); + return (ulong_t)(m_integer.zextOrTrunc(sizeof(ulong_t) * 8)).getZExtValue(); case e_float: return (ulong_t)m_float.convertToFloat(); case e_double: return (ulong_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const ulong_t *)ldbl_val.getRawData(); - } - return fail_value; -} - -uint64_t -Scalar::GetRawBits64(uint64_t fail_value) const -{ - switch (m_type) - { - case e_void: - break; - - case e_sint: - case e_uint: - case e_slong: - case e_ulong: - case e_slonglong: - case e_ulonglong: - case e_sint128: - case e_uint128: - case e_sint256: - case e_uint256: - return *m_integer.getRawData(); - case e_float: - return (uint64_t)m_float.convertToFloat(); - case e_double: - return (uint64_t)m_float.convertToDouble(); - case e_long_double: - llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *ldbl_val.getRawData(); + return (ulong_t)(ldbl_val.zextOrTrunc(sizeof(ulong_t) * 8)).getZExtValue(); } return fail_value; } @@ -1650,14 +1661,14 @@ Scalar::SLongLong(long long fail_value) case e_uint128: case e_sint256: case e_uint256: - return *(const slonglong_t *)(m_integer.sextOrTrunc(sizeof(slonglong_t) * 8)).getRawData(); + return (slonglong_t)(m_integer.sextOrTrunc(sizeof(slonglong_t) * 8)).getSExtValue(); case e_float: return (slonglong_t)m_float.convertToFloat(); case e_double: return (slonglong_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const slonglong_t *)ldbl_val.getRawData(); + return (slonglong_t)(ldbl_val.sextOrTrunc(sizeof(slonglong_t) * 8)).getSExtValue(); } return fail_value; } @@ -1678,14 +1689,14 @@ Scalar::ULongLong(unsigned long long fai case e_uint128: case e_sint256: case e_uint256: - return *(const ulonglong_t *)m_integer.getRawData(); + return (ulonglong_t)(m_integer.zextOrTrunc(sizeof(ulonglong_t) * 8)).getZExtValue(); case e_float: return (ulonglong_t)m_float.convertToFloat(); case e_double: return (ulonglong_t)m_float.convertToDouble(); case e_long_double: llvm::APInt ldbl_val = m_float.bitcastToAPInt(); - return *(const ulonglong_t *)ldbl_val.getRawData(); + return (ulonglong_t)(ldbl_val.zextOrTrunc(sizeof(ulonglong_t) * 8)).getZExtValue(); } return fail_value; } @@ -1948,7 +1959,7 @@ Scalar::operator<<= (const Scalar& rhs) case e_uint128: case e_sint256: case e_uint256: - m_integer <<= *rhs.m_integer.getRawData(); + m_integer = m_integer << rhs.m_integer; break; } break; @@ -1996,7 +2007,8 @@ Scalar::ShiftRightLogical(const Scalar& case e_uint128: case e_sint256: case e_uint256: - m_integer = m_integer.lshr(*(const uint_t *) rhs.m_integer.getRawData()); break; + m_integer = m_integer.lshr(rhs.m_integer); + break; } break; } @@ -2043,7 +2055,7 @@ Scalar::operator>>= (const Scalar& rhs) case e_uint128: case e_sint256: case e_uint256: - m_integer = m_integer.ashr(*(const uint_t *)rhs.m_integer.getRawData()); + m_integer = m_integer.ashr(rhs.m_integer); break; } break; @@ -2258,18 +2270,24 @@ lldb_private::operator/ (const Scalar& l { case Scalar::e_void: break; case Scalar::e_sint: - case Scalar::e_uint: case Scalar::e_slong: - case Scalar::e_ulong: case Scalar::e_slonglong: - case Scalar::e_ulonglong: case Scalar::e_sint128: - case Scalar::e_uint128: case Scalar::e_sint256: + if (b->m_integer != 0) + { + result.m_integer = a->m_integer.sdiv(b->m_integer); + return result; + } + break; + case Scalar::e_uint: + case Scalar::e_ulong: + case Scalar::e_ulonglong: + case Scalar::e_uint128: case Scalar::e_uint256: if (b->m_integer != 0) { - result.m_integer = *a->m_integer.getRawData() / *b->m_integer.getRawData(); + result.m_integer = a->m_integer.udiv(b->m_integer); return result; } break; @@ -2405,18 +2423,23 @@ lldb_private::operator% (const Scalar& l default: break; case Scalar::e_void: break; case Scalar::e_sint: - case Scalar::e_uint: case Scalar::e_slong: - case Scalar::e_ulong: case Scalar::e_slonglong: - case Scalar::e_ulonglong: case Scalar::e_sint128: - case Scalar::e_uint128: case Scalar::e_sint256: + if (b->m_integer != 0) + { + result.m_integer = a->m_integer.srem(b->m_integer); + return result; + } + case Scalar::e_uint: + case Scalar::e_ulong: + case Scalar::e_ulonglong: + case Scalar::e_uint128: case Scalar::e_uint256: if (b->m_integer != 0) { - result.m_integer = *a->m_integer.getRawData() % *b->m_integer.getRawData(); + result.m_integer = a->m_integer.urem(b->m_integer); return result; } break; @@ -2477,27 +2500,6 @@ lldb_private::operator>> (const Scalar& return result; } -// Return the raw unsigned integer without any casting or conversion -unsigned int -Scalar::RawUInt () const -{ - return *(const uint_t *) m_integer.getRawData(); -} - -// Return the raw unsigned long without any casting or conversion -unsigned long -Scalar::RawULong () const -{ - return *(const ulong_t *) m_integer.getRawData(); -} - -// Return the raw unsigned long long without any casting or conversion -unsigned long long -Scalar::RawULongLong () const -{ - return *(const ulonglong_t *) m_integer.getRawData(); -} - Error Scalar::SetValueFromCString (const char *value_str, Encoding encoding, size_t byte_size) { @@ -2652,12 +2654,12 @@ Scalar::SetValueFromData (DataExtractor if (data.GetByteOrder() == eByteOrderBig) { int128.x[1] = (uint64_t)data.GetU64 (&offset); - int128.x[0] = (uint64_t)data.GetU64 (&offset + 1); + int128.x[0] = (uint64_t)data.GetU64 (&offset); } else { int128.x[0] = (uint64_t)data.GetU64 (&offset); - int128.x[1] = (uint64_t)data.GetU64 (&offset + 1); + int128.x[1] = (uint64_t)data.GetU64 (&offset); } operator=(llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, int128.x)); break; @@ -2665,16 +2667,16 @@ Scalar::SetValueFromData (DataExtractor if (data.GetByteOrder() == eByteOrderBig) { int256.x[3] = (uint64_t)data.GetU64 (&offset); - int256.x[2] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[1] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[0] = (uint64_t)data.GetU64 (&offset + 1); + int256.x[2] = (uint64_t)data.GetU64 (&offset); + int256.x[1] = (uint64_t)data.GetU64 (&offset); + int256.x[0] = (uint64_t)data.GetU64 (&offset); } else { int256.x[0] = (uint64_t)data.GetU64 (&offset); - int256.x[1] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[2] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[3] = (uint64_t)data.GetU64 (&offset + 1); + int256.x[1] = (uint64_t)data.GetU64 (&offset); + int256.x[2] = (uint64_t)data.GetU64 (&offset); + int256.x[3] = (uint64_t)data.GetU64 (&offset); } operator=(llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, int256.x)); break; @@ -2698,12 +2700,12 @@ Scalar::SetValueFromData (DataExtractor if (data.GetByteOrder() == eByteOrderBig) { int128.x[1] = (uint64_t)data.GetU64 (&offset); - int128.x[0] = (uint64_t)data.GetU64 (&offset + 1); + int128.x[0] = (uint64_t)data.GetU64 (&offset); } else { int128.x[0] = (uint64_t)data.GetU64 (&offset); - int128.x[1] = (uint64_t)data.GetU64 (&offset + 1); + int128.x[1] = (uint64_t)data.GetU64 (&offset); } operator=(llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, int128.x)); break; @@ -2711,16 +2713,16 @@ Scalar::SetValueFromData (DataExtractor if (data.GetByteOrder() == eByteOrderBig) { int256.x[3] = (uint64_t)data.GetU64 (&offset); - int256.x[2] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[1] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[0] = (uint64_t)data.GetU64 (&offset + 1); + int256.x[2] = (uint64_t)data.GetU64 (&offset); + int256.x[1] = (uint64_t)data.GetU64 (&offset); + int256.x[0] = (uint64_t)data.GetU64 (&offset); } else { int256.x[0] = (uint64_t)data.GetU64 (&offset); - int256.x[1] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[2] = (uint64_t)data.GetU64 (&offset + 1); - int256.x[3] = (uint64_t)data.GetU64 (&offset + 1); + int256.x[1] = (uint64_t)data.GetU64 (&offset); + int256.x[2] = (uint64_t)data.GetU64 (&offset); + int256.x[3] = (uint64_t)data.GetU64 (&offset); } operator=(llvm::APInt(BITWIDTH_INT256, NUM_OF_WORDS_INT256, int256.x)); break; @@ -2828,37 +2830,20 @@ Scalar::ExtractBitfield (uint32_t bit_si if (bit_size == 0) return true; - uint32_t msbit = bit_offset + bit_size - 1; - uint32_t lsbit = bit_offset; - uint64_t result; switch (m_type) { case Scalar::e_void: + case Scalar::e_float: + case Scalar::e_double: + case Scalar::e_long_double: break; - case e_float: - result = SignedBits ((uint64_t )m_float.convertToFloat(), msbit, lsbit); - m_float = llvm::APFloat((float_t)result); - return true; - case e_double: - result = SignedBits ((uint64_t )m_float.convertToDouble(), msbit, lsbit); - m_float = llvm::APFloat((double_t)result); - return true; - case e_long_double: - m_integer = m_float.bitcastToAPInt(); - result = SignedBits (*m_integer.getRawData(), msbit, lsbit); - if(m_ieee_quad) - m_float = llvm::APFloat(llvm::APFloat::IEEEquad, llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((type128 *)&result)->x)); - else - m_float = llvm::APFloat(llvm::APFloat::x87DoubleExtended, llvm::APInt(BITWIDTH_INT128, NUM_OF_WORDS_INT128, ((type128 *)&result)->x)); - return true; - case Scalar::e_sint: case Scalar::e_slong: case Scalar::e_slonglong: case Scalar::e_sint128: case Scalar::e_sint256: - m_integer = SignedBits (*m_integer.getRawData(), msbit, lsbit); + m_integer = m_integer.ashr(bit_offset).trunc(bit_size).sext(8 * GetByteSize()); return true; case Scalar::e_uint: @@ -2866,7 +2851,7 @@ Scalar::ExtractBitfield (uint32_t bit_si case Scalar::e_ulonglong: case Scalar::e_uint128: case Scalar::e_uint256: - m_integer = UnsignedBits (*m_integer.getRawData(), msbit, lsbit); + m_integer = m_integer.lshr(bit_offset).trunc(bit_size).zext(8 * GetByteSize()); return true; } return false; Modified: lldb/trunk/source/Expression/IRInterpreter.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Expression/IRInterpreter.cpp?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/source/Expression/IRInterpreter.cpp (original) +++ lldb/trunk/source/Expression/IRInterpreter.cpp Thu Apr 14 09:32:01 2016 @@ -231,7 +231,7 @@ public: lldb_private::Scalar cast_scalar; - if (!AssignToMatchType(cast_scalar, scalar.GetRawBits64(0), value->getType())) + if (!AssignToMatchType(cast_scalar, scalar.ULongLong(), value->getType())) return false; size_t value_byte_size = m_target_data.getTypeStoreSize(value->getType()); @@ -373,19 +373,18 @@ public: if (!ResolveConstantValue(resolved_value, constant)) return false; - lldb_private::StreamString buffer (lldb_private::Stream::eBinary, - m_execution_unit.GetAddressByteSize(), - m_execution_unit.GetByteOrder()); - size_t constant_size = m_target_data.getTypeStoreSize(constant->getType()); + lldb_private::DataBufferHeap buf(constant_size, 0); - const uint64_t *raw_data = resolved_value.getRawData(); + lldb_private::Error get_data_error; - buffer.PutRawBytes(raw_data, constant_size, lldb_private::endian::InlHostByteOrder()); + lldb_private::Scalar resolved_scalar(resolved_value.zextOrTrunc(llvm::NextPowerOf2(constant_size) * 8)); + if (!resolved_scalar.GetAsMemoryData(buf.GetBytes(), buf.GetByteSize(), m_byte_order, get_data_error)) + return false; lldb_private::Error write_error; - m_execution_unit.WriteMemory(process_address, (const uint8_t*)buffer.GetData(), constant_size, write_error); + m_execution_unit.WriteMemory(process_address, buf.GetBytes(), buf.GetByteSize(), write_error); return write_error.Success(); } @@ -819,7 +818,9 @@ IRInterpreter::Interpret (llvm::Module & result = L / R; break; case Instruction::UDiv: - result = L.GetRawBits64(0) / R.GetRawBits64(1); + L.MakeUnsigned(); + R.MakeUnsigned(); + result = L / R; break; case Instruction::SRem: L.MakeSigned(); @@ -827,7 +828,9 @@ IRInterpreter::Interpret (llvm::Module & result = L % R; break; case Instruction::URem: - result = L.GetRawBits64(0) % R.GetRawBits64(1); + L.MakeUnsigned(); + R.MakeUnsigned(); + result = L % R; break; case Instruction::Shl: result = L << R; @@ -1030,7 +1033,7 @@ IRInterpreter::Interpret (llvm::Module & return false; } - if (C.GetRawBits64(0)) + if (!C.IsZero()) frame.Jump(br_inst->getSuccessor(0)); else frame.Jump(br_inst->getSuccessor(1)); @@ -1181,16 +1184,24 @@ IRInterpreter::Interpret (llvm::Module & result = (L != R); break; case CmpInst::ICMP_UGT: - result = (L.GetRawBits64(0) > R.GetRawBits64(0)); + L.MakeUnsigned(); + R.MakeUnsigned(); + result = (L > R); break; case CmpInst::ICMP_UGE: - result = (L.GetRawBits64(0) >= R.GetRawBits64(0)); + L.MakeUnsigned(); + R.MakeUnsigned(); + result = (L >= R); break; case CmpInst::ICMP_ULT: - result = (L.GetRawBits64(0) < R.GetRawBits64(0)); + L.MakeUnsigned(); + R.MakeUnsigned(); + result = (L < R); break; case CmpInst::ICMP_ULE: - result = (L.GetRawBits64(0) <= R.GetRawBits64(0)); + L.MakeUnsigned(); + R.MakeUnsigned(); + result = (L <= R); break; case CmpInst::ICMP_SGT: L.MakeSigned(); Modified: lldb/trunk/source/Plugins/ExpressionParser/Clang/IRForTarget.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Plugins/ExpressionParser/Clang/IRForTarget.cpp?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/source/Plugins/ExpressionParser/Clang/IRForTarget.cpp (original) +++ lldb/trunk/source/Plugins/ExpressionParser/Clang/IRForTarget.cpp Thu Apr 14 09:32:01 2016 @@ -1105,7 +1105,13 @@ IRForTarget::MaterializeInitializer (uin if (ConstantInt *int_initializer = dyn_cast<ConstantInt>(initializer)) { - memcpy (data, int_initializer->getValue().getRawData(), m_target_data->getTypeStoreSize(initializer_type)); + size_t constant_size = m_target_data->getTypeStoreSize(initializer_type); + lldb_private::Scalar scalar = int_initializer->getValue().zextOrTrunc(llvm::NextPowerOf2(constant_size) * 8); + + lldb_private::Error get_data_error; + if (!scalar.GetAsMemoryData(data, constant_size, lldb_private::endian::InlHostByteOrder(), get_data_error)) + return false; + return true; } else if (ConstantDataArray *array_initializer = dyn_cast<ConstantDataArray>(initializer)) Modified: lldb/trunk/source/Symbol/ClangASTContext.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/source/Symbol/ClangASTContext.cpp?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/source/Symbol/ClangASTContext.cpp (original) +++ lldb/trunk/source/Symbol/ClangASTContext.cpp Thu Apr 14 09:32:01 2016 @@ -72,6 +72,7 @@ #include "lldb/Core/Module.h" #include "lldb/Core/PluginManager.h" #include "lldb/Core/RegularExpression.h" +#include "lldb/Core/Scalar.h" #include "lldb/Core/StreamFile.h" #include "lldb/Core/ThreadSafeDenseMap.h" #include "lldb/Core/UniqueCStringMap.h" @@ -8645,18 +8646,10 @@ ClangASTContext::ConvertStringToFloatVal const uint64_t byte_size = bit_size / 8; if (dst_size >= byte_size) { - if (bit_size == sizeof(float)*8) - { - float float32 = ap_float.convertToFloat(); - ::memcpy (dst, &float32, byte_size); + Scalar scalar = ap_float.bitcastToAPInt().zextOrTrunc(llvm::NextPowerOf2(byte_size) * 8); + lldb_private::Error get_data_error; + if (scalar.GetAsMemoryData(dst, byte_size, lldb_private::endian::InlHostByteOrder(), get_data_error)) return byte_size; - } - else if (bit_size >= 64) - { - llvm::APInt ap_int(ap_float.bitcastToAPInt()); - ::memcpy (dst, ap_int.getRawData(), byte_size); - return byte_size; - } } } } Modified: lldb/trunk/unittests/Core/ScalarTest.cpp URL: http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/Core/ScalarTest.cpp?rev=266311&r1=266310&r2=266311&view=diff ============================================================================== --- lldb/trunk/unittests/Core/ScalarTest.cpp (original) +++ lldb/trunk/unittests/Core/ScalarTest.cpp Thu Apr 14 09:32:01 2016 @@ -15,7 +15,10 @@ #include "gtest/gtest.h" +#include "lldb/Core/Error.h" #include "lldb/Core/Scalar.h" +#include "lldb/Core/DataExtractor.h" +#include "lldb/Host/Endian.h" using namespace lldb_private; @@ -30,3 +33,49 @@ TEST(ScalarTest, RightShiftOperator) ASSERT_EQ(a >> c, a_scalar >> c_scalar); ASSERT_EQ(b >> c, b_scalar >> c_scalar); } + +TEST(ScalarTest, GetBytes) +{ + int a = 0x01020304; + long long b = 0x0102030405060708LL; + float c = 1234567.89e42; + double d = 1234567.89e42; + char e[16] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16 }; + char f[32] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, + 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32 }; + Scalar a_scalar(a); + Scalar b_scalar(b); + Scalar c_scalar(c); + Scalar d_scalar(d); + Scalar e_scalar; + Scalar f_scalar; + DataExtractor e_data(e, sizeof(e), endian::InlHostByteOrder(), sizeof(void *)); + Error e_error = e_scalar.SetValueFromData(e_data, lldb::eEncodingUint, sizeof(e)); + DataExtractor f_data(f, sizeof(f), endian::InlHostByteOrder(), sizeof(void *)); + Error f_error = f_scalar.SetValueFromData(f_data, lldb::eEncodingUint, sizeof(f)); + ASSERT_EQ(0, memcmp(&a, a_scalar.GetBytes(), sizeof(a))); + ASSERT_EQ(0, memcmp(&b, b_scalar.GetBytes(), sizeof(b))); + ASSERT_EQ(0, memcmp(&c, c_scalar.GetBytes(), sizeof(c))); + ASSERT_EQ(0, memcmp(&d, d_scalar.GetBytes(), sizeof(d))); + ASSERT_EQ(0, e_error.Fail()); + ASSERT_EQ(0, memcmp(e, e_scalar.GetBytes(), sizeof(e))); + ASSERT_EQ(0, f_error.Fail()); + ASSERT_EQ(0, memcmp(f, f_scalar.GetBytes(), sizeof(f))); +} + +TEST(ScalarTest, CastOperations) +{ + long long a = 0xf1f2f3f4f5f6f7f8LL; + Scalar a_scalar(a); + ASSERT_EQ((signed char)a, a_scalar.SChar()); + ASSERT_EQ((unsigned char)a, a_scalar.UChar()); + ASSERT_EQ((signed short)a, a_scalar.SShort()); + ASSERT_EQ((unsigned short)a, a_scalar.UShort()); + ASSERT_EQ((signed int)a, a_scalar.SInt()); + ASSERT_EQ((unsigned int)a, a_scalar.UInt()); + ASSERT_EQ((signed long)a, a_scalar.SLong()); + ASSERT_EQ((unsigned long)a, a_scalar.ULong()); + ASSERT_EQ((signed long long)a, a_scalar.SLongLong()); + ASSERT_EQ((unsigned long long)a, a_scalar.ULongLong()); +} + _______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits