summaryrefslogtreecommitdiff
path: root/libstdc++-v3/python/libstdcxx/v6/printers.py
diff options
context:
space:
mode:
Diffstat (limited to 'libstdc++-v3/python/libstdcxx/v6/printers.py')
-rw-r--r--libstdc++-v3/python/libstdcxx/v6/printers.py111
1 files changed, 108 insertions, 3 deletions
diff --git a/libstdc++-v3/python/libstdcxx/v6/printers.py b/libstdc++-v3/python/libstdcxx/v6/printers.py
index f7a7f9961a7..0bd793c0897 100644
--- a/libstdc++-v3/python/libstdcxx/v6/printers.py
+++ b/libstdc++-v3/python/libstdcxx/v6/printers.py
@@ -218,7 +218,7 @@ class SmartPtrIterator(Iterator):
return ('get()', val)
class SharedPointerPrinter:
- "Print a shared_ptr or weak_ptr"
+ "Print a shared_ptr, weak_ptr, atomic<shared_ptr>, or atomic<weak_ptr>"
def __init__ (self, typename, val):
self.typename = strip_versioned_namespace(typename)
@@ -228,9 +228,21 @@ class SharedPointerPrinter:
def children (self):
return SmartPtrIterator(self.pointer)
+ # Return the _Sp_counted_base<>* that holds the refcounts.
+ def _get_refcounts (self):
+ if self.typename == 'std::atomic':
+ # A tagged pointer is stored as uintptr_t.
+ ptr_val = self.val['_M_refcount']['_M_val']['_M_i']
+ ptr_val = ptr_val - (ptr_val % 2) # clear lock bit
+ ptr_type = find_type(self.val['_M_refcount'].type, 'pointer')
+ return ptr_val.cast(ptr_type)
+ return self.val['_M_refcount']['_M_pi']
+
def to_string (self):
state = 'empty'
- refcounts = self.val['_M_refcount']['_M_pi']
+ refcounts = self._get_refcounts()
+ targ = self.val.type.template_argument(0)
+
if refcounts != 0:
usecount = refcounts['_M_use_count']
weakcount = refcounts['_M_weak_count']
@@ -238,7 +250,7 @@ class SharedPointerPrinter:
state = 'expired, weak count %d' % weakcount
else:
state = 'use count %d, weak count %d' % (usecount, weakcount - 1)
- return '%s<%s> (%s)' % (self.typename, str(self.val.type.template_argument(0)), state)
+ return '%s<%s> (%s)' % (self.typename, str(targ), state)
def _tuple_impl_get(val):
"Return the tuple element stored in a _Tuple_impl<N, T> base class."
@@ -1654,6 +1666,94 @@ class StdRegexStatePrinter:
s = "{}, {}={}".format(s, v, self.val['_M_' + v])
return "{%s}" % (s)
+class StdSpanPrinter:
+ "Print a std::span"
+
+ class iterator(Iterator):
+ def __init__(self, begin, size):
+ self.count = 0
+ self.begin = begin
+ self.size = size
+
+ def __iter__ (self):
+ return self
+
+ def __next__ (self):
+ if self.count == self.size:
+ raise StopIteration
+
+ count = self.count
+ self.count = self.count + 1
+ return '[%d]' % count, (self.begin + count).dereference()
+
+ def __init__(self, typename, val):
+ self.typename = typename
+ self.val = val
+ if val.type.template_argument(1) == gdb.parse_and_eval('static_cast<std::size_t>(-1)'):
+ self.size = val['_M_extent']['_M_extent_value']
+ else:
+ self.size = val.type.template_argument(1)
+
+ def to_string(self):
+ return '%s of length %d' % (self.typename, self.size)
+
+ def children(self):
+ return self.iterator(self.val['_M_ptr'], self.size)
+
+ def display_hint(self):
+ return 'array'
+
+class StdInitializerListPrinter:
+ "Print a std::initializer_list"
+
+ def __init__(self, typename, val):
+ self.typename = typename
+ self.val = val
+ self.size = val['_M_len']
+
+ def to_string(self):
+ return '%s of length %d' % (self.typename, self.size)
+
+ def children(self):
+ return StdSpanPrinter.iterator(self.val['_M_array'], self.size)
+
+ def display_hint(self):
+ return 'array'
+
+class StdAtomicPrinter:
+ "Print a std:atomic"
+
+ def __init__(self, typename, val):
+ self.typename = typename
+ self.val = val
+ self.shptr_printer = None
+ self.value_type = self.val.type.template_argument(0)
+ if self.value_type.tag is not None:
+ typ = strip_versioned_namespace(self.value_type.tag)
+ if typ.startswith('std::shared_ptr<') or typ.startswith('std::weak_ptr<'):
+ impl = val['_M_impl']
+ self.shptr_printer = SharedPointerPrinter(typename, impl)
+ self.children = self._shptr_children
+
+ def _shptr_children(self):
+ return SmartPtrIterator(self.shptr_printer.pointer)
+
+ def to_string(self):
+ if self.shptr_printer is not None:
+ return self.shptr_printer.to_string()
+
+ if self.value_type.code == gdb.TYPE_CODE_INT:
+ val = self.val['_M_i']
+ elif self.value_type.code == gdb.TYPE_CODE_FLT:
+ val = self.val['_M_fp']
+ elif self.value_type.code == gdb.TYPE_CODE_PTR:
+ val = self.val['_M_b']['_M_p']
+ elif self.value_type.code == gdb.TYPE_CODE_BOOL:
+ val = self.val['_M_base']['_M_i']
+ else:
+ val = self.val['_M_i']
+ return '%s<%s> = { %s }' % (self.typename, str(self.value_type), val)
+
# A "regular expression" printer which conforms to the
# "SubPrettyPrinter" protocol from gdb.printing.
class RxPrinter(object):
@@ -2119,6 +2219,10 @@ def build_libstdcxx_dictionary ():
libstdcxx_printer.add_version('std::tr1::', 'unordered_multiset',
Tr1UnorderedSetPrinter)
+ libstdcxx_printer.add_version('std::', 'initializer_list',
+ StdInitializerListPrinter)
+ libstdcxx_printer.add_version('std::', 'atomic', StdAtomicPrinter)
+
# std::regex components
libstdcxx_printer.add_version('std::__detail::', '_State',
StdRegexStatePrinter)
@@ -2170,6 +2274,7 @@ def build_libstdcxx_dictionary ():
libstdcxx_printer.add_version('std::', 'partial_ordering', StdCmpCatPrinter)
libstdcxx_printer.add_version('std::', 'weak_ordering', StdCmpCatPrinter)
libstdcxx_printer.add_version('std::', 'strong_ordering', StdCmpCatPrinter)
+ libstdcxx_printer.add_version('std::', 'span', StdSpanPrinter)
# Extensions.
libstdcxx_printer.add_version('__gnu_cxx::', 'slist', StdSlistPrinter)