LLDB mainline
RegisterValue.cpp
Go to the documentation of this file.
1//===-- RegisterValue.cpp -------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
10
12#include "lldb/Utility/Scalar.h"
13#include "lldb/Utility/Status.h"
14#include "lldb/Utility/Stream.h"
16#include "lldb/lldb-defines.h"
18
19#include "llvm/ADT/ArrayRef.h"
20#include "llvm/ADT/StringRef.h"
21
22#include <cstdint>
23#include <string>
24#include <tuple>
25#include <vector>
26
27#include <cassert>
28#include <cinttypes>
29#include <cstdio>
30
31using namespace lldb;
32using namespace lldb_private;
33
35 return data.SetData(GetBytes(), GetByteSize(), GetByteOrder()) > 0;
36}
37
38uint32_t RegisterValue::GetAsMemoryData(const RegisterInfo &reg_info, void *dst,
39 uint32_t dst_len,
40 lldb::ByteOrder dst_byte_order,
41 Status &error) const {
42 // ReadRegister should have already been called on this object prior to
43 // calling this.
44 if (GetType() == eTypeInvalid) {
45 // No value has been read into this object...
47 "invalid register value type for register {0}", reg_info.name);
48 return 0;
49 }
50
51 const uint32_t src_len = reg_info.byte_size;
52
53 // Extract the register data into a data extractor
54 DataExtractor reg_data;
55 if (!GetData(reg_data)) {
56 error = Status::FromErrorString("invalid register value to copy into");
57 return 0;
58 }
59
60 // Prepare a memory buffer that contains some or all of the register value
61 const uint32_t bytes_copied =
62 reg_data.CopyByteOrderedData(0, // src offset
63 src_len, // src length
64 dst, // dst buffer
65 dst_len, // dst length
66 dst_byte_order); // dst byte order
67 if (bytes_copied == 0)
69 "failed to copy data for register write of %s", reg_info.name);
70
71 return bytes_copied;
72}
73
75 const void *src, uint32_t src_len,
76 lldb::ByteOrder src_byte_order,
77 Status &error) {
78 // Moving from addr into a register
79 //
80 // Case 1: src_len == dst_len
81 //
82 // |AABBCCDD| Address contents
83 // |AABBCCDD| Register contents
84 //
85 // Case 2: src_len > dst_len
86 //
87 // Status! (The register should always be big enough to hold the data)
88 //
89 // Case 3: src_len < dst_len
90 //
91 // |AABB| Address contents
92 // |AABB0000| Register contents [on little-endian hardware]
93 // |0000AABB| Register contents [on big-endian hardware]
94 const uint32_t dst_len = reg_info.byte_size;
95
96 if (src_len > dst_len) {
98 "%u bytes is too big to store in register %s (%u bytes)", src_len,
99 reg_info.name, dst_len);
100 return 0;
101 }
102
103 // Use a data extractor to correctly copy and pad the bytes read into the
104 // register value
105 DataExtractor src_data(src, src_len, src_byte_order, 4);
106
107 error = SetValueFromData(reg_info, src_data, 0, true);
108 if (error.Fail())
109 return 0;
110
111 // If SetValueFromData succeeded, we must have copied all of src_len
112 return src_len;
113}
114
116 switch (m_type) {
117 case eTypeInvalid:
118 break;
119 case eTypeBytes: {
120 DataExtractor data(buffer.bytes.data(), buffer.bytes.size(),
121 buffer.byte_order, 1);
122 if (scalar.SetValueFromData(data, lldb::eEncodingUint, buffer.bytes.size())
123 .Success())
124 return true;
125 } break;
126 case eTypeUInt8:
127 case eTypeUInt16:
128 case eTypeUInt32:
129 case eTypeUInt64:
130 case eTypeUIntN:
131 case eTypeFloat:
132 case eTypeDouble:
133 case eTypeLongDouble:
134 scalar = m_scalar;
135 return true;
136 }
137 return false;
138}
139
141
143 // To change the type, we simply copy the data in again, using the new format
144 RegisterValue copy;
145 DataExtractor copy_data;
146 if (copy.CopyValue(*this) && copy.GetData(copy_data)) {
147 Status error = SetValueFromData(reg_info, copy_data, 0, true);
148 assert(error.Success() && "Expected SetValueFromData to succeed.");
150 }
151
152 return m_type;
153}
154
156 DataExtractor &src,
157 lldb::offset_t src_offset,
158 bool partial_data_ok) {
160
161 if (src.GetByteSize() == 0) {
162 error = Status::FromErrorString("empty data.");
163 return error;
164 }
165
166 if (reg_info.byte_size == 0) {
167 error = Status::FromErrorString("invalid register info.");
168 return error;
169 }
170
171 uint32_t src_len = src.GetByteSize() - src_offset;
172
173 if (!partial_data_ok && (src_len < reg_info.byte_size)) {
174 error = Status::FromErrorString("not enough data.");
175 return error;
176 }
177
178 // Cap the data length if there is more than enough bytes for this register
179 // value
180 if (src_len > reg_info.byte_size)
181 src_len = reg_info.byte_size;
182
184 switch (reg_info.encoding) {
185 case eEncodingInvalid:
186 break;
187 case eEncodingUint:
188 case eEncodingSint:
189 if (reg_info.byte_size == 1)
190 SetUInt8(src.GetMaxU32(&src_offset, src_len));
191 else if (reg_info.byte_size <= 2)
192 SetUInt16(src.GetMaxU32(&src_offset, src_len));
193 else if (reg_info.byte_size <= 4)
194 SetUInt32(src.GetMaxU32(&src_offset, src_len));
195 else if (reg_info.byte_size <= 8)
196 SetUInt64(src.GetMaxU64(&src_offset, src_len));
197 else {
198 std::vector<uint8_t> native_endian_src(src_len, 0);
199 src.ExtractBytes(src_offset, src_len,
200 llvm::sys::IsLittleEndianHost ? eByteOrderLittle
202 native_endian_src.data());
203 llvm::APInt uint = llvm::APInt::getZero(src_len * 8);
204 llvm::LoadIntFromMemory(uint, native_endian_src.data(), src_len);
205 SetUIntN(uint);
206 }
207 break;
208 case eEncodingIEEE754:
209 if (reg_info.byte_size == sizeof(float))
210 SetFloat(src.GetFloat(&src_offset));
211 else if (reg_info.byte_size == sizeof(double))
212 SetDouble(src.GetDouble(&src_offset));
213 else if (reg_info.byte_size == sizeof(long double))
214 SetLongDouble(src.GetLongDouble(&src_offset));
215 break;
216 case eEncodingVector: {
218 assert(reg_info.byte_size <= kMaxRegisterByteSize);
219 buffer.bytes.resize(reg_info.byte_size);
220 buffer.byte_order = src.GetByteOrder();
221 if (src.CopyByteOrderedData(
222 src_offset, // offset within "src" to start extracting data
223 src_len, // src length
224 buffer.bytes.data(), // dst buffer
225 buffer.bytes.size(), // dst length
226 buffer.byte_order) == 0) // dst byte order
227 {
229 "failed to copy data for register write of %s", reg_info.name);
230 return error;
231 }
232 }
233 }
234
235 if (m_type == eTypeInvalid)
237 "invalid register value type for register %s", reg_info.name);
238 return error;
239}
240
241// Helper function for RegisterValue::SetValueFromString()
242static bool ParseVectorEncoding(const RegisterInfo *reg_info,
243 llvm::StringRef vector_str,
244 const uint32_t byte_size,
245 RegisterValue *reg_value) {
246 // Example: vector_str = "{0x2c 0x4b 0x2a 0x3e 0xd0 0x4f 0x2a 0x3e 0xac 0x4a
247 // 0x2a 0x3e 0x84 0x4f 0x2a 0x3e}".
248 vector_str = vector_str.trim();
249 vector_str.consume_front("{");
250 vector_str.consume_back("}");
251 vector_str = vector_str.trim();
252
253 char Sep = ' ';
254
255 // The first split should give us:
256 // ('0x2c', '0x4b 0x2a 0x3e 0xd0 0x4f 0x2a 0x3e 0xac 0x4a 0x2a 0x3e 0x84 0x4f
257 // 0x2a 0x3e').
258 llvm::StringRef car;
259 llvm::StringRef cdr = vector_str;
260 std::tie(car, cdr) = vector_str.split(Sep);
261 std::vector<uint8_t> bytes;
262 unsigned byte = 0;
263
264 // Using radix auto-sensing by passing 0 as the radix. Keep on processing the
265 // vector elements as long as the parsing succeeds and the vector size is <
266 // byte_size.
267 while (!car.getAsInteger(0, byte) && bytes.size() < byte_size) {
268 bytes.push_back(byte);
269 std::tie(car, cdr) = cdr.split(Sep);
270 }
271
272 // Check for vector of exact byte_size elements.
273 if (bytes.size() != byte_size)
274 return false;
275
276 reg_value->SetBytes(&(bytes.front()), byte_size, eByteOrderLittle);
277 return true;
278}
279
280static bool UInt64ValueIsValidForByteSize(uint64_t uval64,
281 size_t total_byte_size) {
282 if (total_byte_size > 8)
283 return false;
284
285 if (total_byte_size == 8)
286 return true;
287
288 const uint64_t max =
289 (static_cast<uint64_t>(1) << static_cast<uint64_t>(total_byte_size * 8)) -
290 1;
291 return uval64 <= max;
292}
293
294static bool SInt64ValueIsValidForByteSize(int64_t sval64,
295 size_t total_byte_size) {
296 if (total_byte_size > 8)
297 return false;
298
299 if (total_byte_size == 8)
300 return true;
301
302 const int64_t max = (static_cast<int64_t>(1)
303 << static_cast<uint64_t>(total_byte_size * 8 - 1)) -
304 1;
305 const int64_t min = ~(max);
306 return min <= sval64 && sval64 <= max;
307}
308
310 llvm::StringRef value_str) {
312 if (reg_info == nullptr) {
313 error = Status::FromErrorString("Invalid register info argument.");
314 return error;
315 }
316
318 if (value_str.empty()) {
319 error = Status::FromErrorString("Invalid c-string value string.");
320 return error;
321 }
322 const uint32_t byte_size = reg_info->byte_size;
323
324 uint64_t uval64;
325 int64_t ival64;
326 float flt_val;
327 double dbl_val;
328 long double ldbl_val;
329 switch (reg_info->encoding) {
330 case eEncodingInvalid:
331 error = Status::FromErrorString("Invalid encoding.");
332 break;
333
334 case eEncodingUint:
335 if (byte_size > sizeof(uint64_t)) {
337 "unsupported unsigned integer byte size: %u", byte_size);
338 break;
339 }
340 if (value_str.getAsInteger(0, uval64)) {
342 "'{0}' is not a valid unsigned integer string value", value_str);
343 break;
344 }
345
346 if (!UInt64ValueIsValidForByteSize(uval64, byte_size)) {
348 "value 0x%" PRIx64
349 " is too large to fit in a %u byte unsigned integer value",
350 uval64, byte_size);
351 break;
352 }
353
354 if (!SetUInt(uval64, reg_info->byte_size)) {
356 "unsupported unsigned integer byte size: %u", byte_size);
357 break;
358 }
359 break;
360
361 case eEncodingSint:
362 if (byte_size > sizeof(long long)) {
364 "unsupported signed integer byte size: %u", byte_size);
365 break;
366 }
367
368 if (value_str.getAsInteger(0, ival64)) {
370 "'{0}' is not a valid signed integer string value", value_str);
371 break;
372 }
373
374 if (!SInt64ValueIsValidForByteSize(ival64, byte_size)) {
376 "value 0x%" PRIx64
377 " is too large to fit in a %u byte signed integer value",
378 ival64, byte_size);
379 break;
380 }
381
382 if (!SetUInt(ival64, reg_info->byte_size)) {
384 "unsupported signed integer byte size: %u", byte_size);
385 break;
386 }
387 break;
388
389 case eEncodingIEEE754: {
390 std::string value_string = std::string(value_str);
391 if (byte_size == sizeof(float)) {
392 if (::sscanf(value_string.c_str(), "%f", &flt_val) != 1) {
394 "'%s' is not a valid float string value", value_string.c_str());
395 break;
396 }
397 m_scalar = flt_val;
399 } else if (byte_size == sizeof(double)) {
400 if (::sscanf(value_string.c_str(), "%lf", &dbl_val) != 1) {
402 "'%s' is not a valid float string value", value_string.c_str());
403 break;
404 }
405 m_scalar = dbl_val;
407 } else if (byte_size == sizeof(long double)) {
408 if (::sscanf(value_string.c_str(), "%Lf", &ldbl_val) != 1) {
410 "'%s' is not a valid float string value", value_string.c_str());
411 break;
412 }
413 m_scalar = ldbl_val;
415 } else {
417 "unsupported float byte size: %u", byte_size);
418 return error;
419 }
420 break;
421 }
422 case eEncodingVector:
423 if (!ParseVectorEncoding(reg_info, value_str, byte_size, this))
424 error =
425 Status::FromErrorString("unrecognized vector encoding string value.");
426 break;
427 }
428
429 return error;
430}
431
432bool RegisterValue::SignExtend(uint32_t sign_bitpos) {
433 switch (m_type) {
434 case eTypeInvalid:
435 break;
436
437 case eTypeUInt8:
438 case eTypeUInt16:
439 case eTypeUInt32:
440 case eTypeUInt64:
441 case eTypeUIntN:
442 return m_scalar.SignExtend(sign_bitpos);
443 case eTypeFloat:
444 case eTypeDouble:
445 case eTypeLongDouble:
446 case eTypeBytes:
447 break;
448 }
449 return false;
450}
451
453 if (this == &rhs)
454 return rhs.m_type != eTypeInvalid;
455
456 m_type = rhs.m_type;
457 switch (m_type) {
458 case eTypeInvalid:
459 return false;
460 case eTypeUInt8:
461 case eTypeUInt16:
462 case eTypeUInt32:
463 case eTypeUInt64:
464 case eTypeUIntN:
465 case eTypeFloat:
466 case eTypeDouble:
467 case eTypeLongDouble:
468 m_scalar = rhs.m_scalar;
469 break;
470 case eTypeBytes:
471 buffer.bytes = rhs.buffer.bytes;
472 buffer.byte_order = rhs.buffer.byte_order;
473 break;
474 }
475 return true;
476}
477
478uint16_t RegisterValue::GetAsUInt16(uint16_t fail_value,
479 bool *success_ptr) const {
480 if (success_ptr)
481 *success_ptr = true;
482
483 switch (m_type) {
484 default:
485 break;
486 case eTypeUInt8:
487 case eTypeUInt16:
488 return m_scalar.UShort(fail_value);
489 case eTypeBytes: {
490 switch (buffer.bytes.size()) {
491 default:
492 break;
493 case 1:
494 case 2:
495 return *reinterpret_cast<const uint16_t *>(buffer.bytes.data());
496 }
497 } break;
498 }
499 if (success_ptr)
500 *success_ptr = false;
501 return fail_value;
502}
503
504uint32_t RegisterValue::GetAsUInt32(uint32_t fail_value,
505 bool *success_ptr) const {
506 if (success_ptr)
507 *success_ptr = true;
508 switch (m_type) {
509 default:
510 break;
511 case eTypeUInt8:
512 case eTypeUInt16:
513 case eTypeUInt32:
514 case eTypeFloat:
515 case eTypeDouble:
516 case eTypeLongDouble:
517 return m_scalar.UInt(fail_value);
518 case eTypeBytes: {
519 switch (buffer.bytes.size()) {
520 default:
521 break;
522 case 1:
523 case 2:
524 case 4:
525 return *reinterpret_cast<const uint32_t *>(buffer.bytes.data());
526 }
527 } break;
528 }
529 if (success_ptr)
530 *success_ptr = false;
531 return fail_value;
532}
533
534uint64_t RegisterValue::GetAsUInt64(uint64_t fail_value,
535 bool *success_ptr) const {
536 if (success_ptr)
537 *success_ptr = true;
538 switch (m_type) {
539 default:
540 break;
541 case eTypeUInt8:
542 case eTypeUInt16:
543 case eTypeUInt32:
544 case eTypeUInt64:
545 case eTypeFloat:
546 case eTypeDouble:
547 case eTypeLongDouble:
548 return m_scalar.ULongLong(fail_value);
549 case eTypeBytes: {
550 switch (buffer.bytes.size()) {
551 default:
552 break;
553 case 1:
554 return *(const uint8_t *)buffer.bytes.data();
555 case 2:
556 return *reinterpret_cast<const uint16_t *>(buffer.bytes.data());
557 case 4:
558 return *reinterpret_cast<const uint32_t *>(buffer.bytes.data());
559 case 8:
560 return *reinterpret_cast<const uint64_t *>(buffer.bytes.data());
561 }
562 } break;
563 }
564 if (success_ptr)
565 *success_ptr = false;
566 return fail_value;
567}
568
569llvm::APInt RegisterValue::GetAsUInt128(const llvm::APInt &fail_value,
570 bool *success_ptr) const {
571 if (success_ptr)
572 *success_ptr = true;
573 switch (m_type) {
574 default:
575 break;
576 case eTypeUInt8:
577 case eTypeUInt16:
578 case eTypeUInt32:
579 case eTypeUInt64:
580 case eTypeUIntN:
581 case eTypeFloat:
582 case eTypeDouble:
583 case eTypeLongDouble:
584 return m_scalar.UInt128(fail_value);
585 case eTypeBytes: {
586 switch (buffer.bytes.size()) {
587 default:
588 break;
589 case 1:
590 case 2:
591 case 4:
592 case 8:
593 case 16:
594 return llvm::APInt(
596 llvm::ArrayRef(
597 (reinterpret_cast<const type128 *>(buffer.bytes.data()))->x,
599 }
600 } break;
601 }
602 if (success_ptr)
603 *success_ptr = false;
604 return fail_value;
605}
606
607float RegisterValue::GetAsFloat(float fail_value, bool *success_ptr) const {
608 if (success_ptr)
609 *success_ptr = true;
610 switch (m_type) {
611 default:
612 break;
613 case eTypeUInt32:
614 case eTypeUInt64:
615 case eTypeUIntN:
616 case eTypeFloat:
617 case eTypeDouble:
618 case eTypeLongDouble:
619 return m_scalar.Float(fail_value);
620 }
621 if (success_ptr)
622 *success_ptr = false;
623 return fail_value;
624}
625
626double RegisterValue::GetAsDouble(double fail_value, bool *success_ptr) const {
627 if (success_ptr)
628 *success_ptr = true;
629 switch (m_type) {
630 default:
631 break;
632
633 case eTypeUInt32:
634 case eTypeUInt64:
635 case eTypeUIntN:
636 case eTypeFloat:
637 case eTypeDouble:
638 case eTypeLongDouble:
639 return m_scalar.Double(fail_value);
640 }
641 if (success_ptr)
642 *success_ptr = false;
643 return fail_value;
644}
645
646long double RegisterValue::GetAsLongDouble(long double fail_value,
647 bool *success_ptr) const {
648 if (success_ptr)
649 *success_ptr = true;
650 switch (m_type) {
651 default:
652 break;
653
654 case eTypeUInt32:
655 case eTypeUInt64:
656 case eTypeUIntN:
657 case eTypeFloat:
658 case eTypeDouble:
659 case eTypeLongDouble:
660 return m_scalar.LongDouble();
661 }
662 if (success_ptr)
663 *success_ptr = false;
664 return fail_value;
665}
666
667const void *RegisterValue::GetBytes() const {
668 switch (m_type) {
669 case eTypeInvalid:
670 break;
671 case eTypeUInt8:
672 case eTypeUInt16:
673 case eTypeUInt32:
674 case eTypeUInt64:
675 case eTypeUIntN:
676 case eTypeFloat:
677 case eTypeDouble:
678 case eTypeLongDouble:
679 m_scalar.GetBytes(buffer.bytes);
680 return buffer.bytes.data();
681 case eTypeBytes:
682 return buffer.bytes.data();
683 }
684 return nullptr;
685}
686
688 switch (m_type) {
689 case eTypeInvalid:
690 break;
691 case eTypeUInt8:
692 return 1;
693 case eTypeUInt16:
694 return 2;
695 case eTypeUInt32:
696 case eTypeUInt64:
697 case eTypeUIntN:
698 case eTypeFloat:
699 case eTypeDouble:
700 case eTypeLongDouble:
701 return m_scalar.GetByteSize();
702 case eTypeBytes:
703 return buffer.bytes.size();
704 }
705 return 0;
706}
707
708bool RegisterValue::SetUInt(uint64_t uint, uint32_t byte_size) {
709 if (byte_size == 0) {
710 SetUInt64(uint);
711 } else if (byte_size == 1) {
712 SetUInt8(uint);
713 } else if (byte_size <= 2) {
714 SetUInt16(uint);
715 } else if (byte_size <= 4) {
716 SetUInt32(uint);
717 } else if (byte_size <= 8) {
718 SetUInt64(uint);
719 } else if (byte_size <= 16) {
720 SetUIntN(llvm::APInt(128, uint));
721 } else
722 return false;
723 return true;
724}
725
726void RegisterValue::SetBytes(const void *bytes, size_t length,
727 lldb::ByteOrder byte_order) {
728 if (bytes && length > 0) {
730 buffer.bytes.resize(length);
731 memcpy(buffer.bytes.data(), bytes, length);
732 buffer.byte_order = byte_order;
733 } else {
735 buffer.bytes.resize(0);
736 }
737}
738
740 if (m_type == rhs.m_type) {
741 switch (m_type) {
742 case eTypeInvalid:
743 return true;
744 case eTypeUInt8:
745 case eTypeUInt16:
746 case eTypeUInt32:
747 case eTypeUInt64:
748 case eTypeUIntN:
749 case eTypeFloat:
750 case eTypeDouble:
751 case eTypeLongDouble:
752 return m_scalar == rhs.m_scalar;
753 case eTypeBytes:
754 return buffer.bytes == rhs.buffer.bytes;
755 }
756 }
757 return false;
758}
759
761 return !(*this == rhs);
762}
763
765 switch (m_type) {
766 case eTypeInvalid:
767 break;
768
769 case eTypeUInt8:
770 case eTypeUInt16:
771 case eTypeUInt32:
772 case eTypeUInt64:
773 case eTypeUIntN:
774 if (bit < (GetByteSize() * 8)) {
775 return m_scalar.ClearBit(bit);
776 }
777 break;
778
779 case eTypeFloat:
780 case eTypeDouble:
781 case eTypeLongDouble:
782 break;
783
784 case eTypeBytes:
785 if (buffer.byte_order == eByteOrderBig ||
786 buffer.byte_order == eByteOrderLittle) {
787 uint32_t byte_idx;
788 if (buffer.byte_order == eByteOrderBig)
789 byte_idx = buffer.bytes.size() - (bit / 8) - 1;
790 else
791 byte_idx = bit / 8;
792
793 const uint32_t byte_bit = bit % 8;
794 if (byte_idx < buffer.bytes.size()) {
795 buffer.bytes[byte_idx] &= ~(1u << byte_bit);
796 return true;
797 }
798 }
799 break;
800 }
801 return false;
802}
803
805 switch (m_type) {
806 case eTypeInvalid:
807 break;
808
809 case eTypeUInt8:
810 case eTypeUInt16:
811 case eTypeUInt32:
812 case eTypeUInt64:
813 case eTypeUIntN:
814 if (bit < (GetByteSize() * 8)) {
815 return m_scalar.SetBit(bit);
816 }
817 break;
818
819 case eTypeFloat:
820 case eTypeDouble:
821 case eTypeLongDouble:
822 break;
823
824 case eTypeBytes:
825 if (buffer.byte_order == eByteOrderBig ||
826 buffer.byte_order == eByteOrderLittle) {
827 uint32_t byte_idx;
828 if (buffer.byte_order == eByteOrderBig)
829 byte_idx = buffer.bytes.size() - (bit / 8) - 1;
830 else
831 byte_idx = bit / 8;
832
833 const uint32_t byte_bit = bit % 8;
834 if (byte_idx < buffer.bytes.size()) {
835 buffer.bytes[byte_idx] |= (1u << byte_bit);
836 return true;
837 }
838 }
839 break;
840 }
841 return false;
842}
static llvm::raw_ostream & error(Stream &strm)
static bool ParseVectorEncoding(const RegisterInfo *reg_info, llvm::StringRef vector_str, const uint32_t byte_size, RegisterValue *reg_value)
static bool UInt64ValueIsValidForByteSize(uint64_t uval64, size_t total_byte_size)
static bool SInt64ValueIsValidForByteSize(int64_t sval64, size_t total_byte_size)
#define NUM_OF_WORDS_INT128
Definition Scalar.h:27
#define BITWIDTH_INT128
Definition Scalar.h:28
An data extractor class.
float GetFloat(lldb::offset_t *offset_ptr) const
Extract a float from *offset_ptr.
long double GetLongDouble(lldb::offset_t *offset_ptr) const
uint32_t GetMaxU32(lldb::offset_t *offset_ptr, size_t byte_size) const
Extract an integer of size byte_size from *offset_ptr.
uint64_t GetByteSize() const
Get the number of bytes contained in this object.
lldb::offset_t SetData(const void *bytes, lldb::offset_t length, lldb::ByteOrder byte_order)
Set data with a buffer that is caller owned.
uint64_t GetMaxU64(lldb::offset_t *offset_ptr, size_t byte_size) const
Extract an unsigned integer of size byte_size from *offset_ptr.
lldb::ByteOrder GetByteOrder() const
Get the current byte order value.
lldb::offset_t CopyByteOrderedData(lldb::offset_t src_offset, lldb::offset_t src_len, void *dst, lldb::offset_t dst_len, lldb::ByteOrder dst_byte_order) const
Copy dst_len bytes from *offset_ptr and ensure the copied data is treated as a value that can be swap...
double GetDouble(lldb::offset_t *offset_ptr) const
size_t ExtractBytes(lldb::offset_t offset, lldb::offset_t length, lldb::ByteOrder dst_byte_order, void *dst) const
Extract an arbitrary number of bytes in the specified byte order.
bool operator==(const RegisterValue &rhs) const
RegisterValue::Type m_type
uint16_t GetAsUInt16(uint16_t fail_value=UINT16_MAX, bool *success_ptr=nullptr) const
bool SignExtend(uint32_t sign_bitpos)
uint32_t SetFromMemoryData(const RegisterInfo &reg_info, const void *src, uint32_t src_len, lldb::ByteOrder src_byte_order, Status &error)
long double GetAsLongDouble(long double fail_value=0.0, bool *success_ptr=nullptr) const
bool GetData(DataExtractor &data) const
void SetUInt64(uint64_t uint, Type t=eTypeUInt64)
void SetUInt16(uint16_t uint)
double GetAsDouble(double fail_value=0.0, bool *success_ptr=nullptr) const
void SetUIntN(llvm::APInt uint)
bool SetUInt(uint64_t uint, uint32_t byte_size)
Status SetValueFromString(const RegisterInfo *reg_info, llvm::StringRef value_str)
uint32_t GetAsMemoryData(const RegisterInfo &reg_info, void *dst, uint32_t dst_len, lldb::ByteOrder dst_byte_order, Status &error) const
uint64_t GetAsUInt64(uint64_t fail_value=UINT64_MAX, bool *success_ptr=nullptr) const
float GetAsFloat(float fail_value=0.0f, bool *success_ptr=nullptr) const
void SetUInt8(uint8_t uint)
llvm::APInt GetAsUInt128(const llvm::APInt &fail_value, bool *success_ptr=nullptr) const
struct lldb_private::RegisterValue::RegisterValueBuffer buffer
void SetBytes(const void *bytes, size_t length, lldb::ByteOrder byte_order)
bool GetScalarValue(Scalar &scalar) const
const void * GetBytes() const
RegisterValue::Type GetType() const
void SetLongDouble(long double f)
bool operator!=(const RegisterValue &rhs) const
Status SetValueFromData(const RegisterInfo &reg_info, DataExtractor &data, lldb::offset_t offset, bool partial_data_ok)
void SetType(RegisterValue::Type type)
uint32_t GetAsUInt32(uint32_t fail_value=UINT32_MAX, bool *success_ptr=nullptr) const
bool CopyValue(const RegisterValue &rhs)
void SetUInt32(uint32_t uint, Type t=eTypeUInt32)
lldb::ByteOrder GetByteOrder() const
@ eTypeFloat
< This value is used when the (integer) register is larger than 64-bits.
Status SetValueFromData(const DataExtractor &data, lldb::Encoding encoding, size_t byte_size)
Definition Scalar.cpp:718
An error handling class.
Definition Status.h:118
static Status FromErrorStringWithFormat(const char *format,...) __attribute__((format(printf
Definition Status.cpp:106
static Status FromErrorString(const char *str)
Definition Status.h:141
static Status static Status FromErrorStringWithFormatv(const char *format, Args &&...args)
Definition Status.h:151
bool Success() const
Test for success condition.
Definition Status.cpp:304
#define UNUSED_IF_ASSERT_DISABLED(x)
A class that represents a running process on the host machine.
static uint32_t bit(const uint32_t val, const uint32_t msbit)
Definition ARMUtils.h:270
uint64_t offset_t
Definition lldb-types.h:85
@ eEncodingIEEE754
float
@ eEncodingVector
vector registers
@ eEncodingUint
unsigned integer
@ eEncodingSint
signed integer
ByteOrder
Byte ordering definitions.
Every register is described in detail including its name, alternate name (optional),...
lldb::Encoding encoding
Encoding of the register bits.
uint32_t byte_size
Size in bytes of the register.
const char * name
Name of this register, can't be NULL.