diff --git a/Doxyfile b/Doxyfile
index fa05684..0866a53 100644
--- a/Doxyfile
+++ b/Doxyfile
@@ -1008,7 +1008,8 @@
 # Note that relative paths are relative to the directory from which doxygen is
 # run.
 
-EXCLUDE                =
+EXCLUDE                = src/tint/tint_gdb.py \
+                         src/tint/tint_lldb.py
 
 # The EXCLUDE_SYMLINKS tag can be used to select whether or not files or
 # directories that are symbolic links (a Unix file system feature) are excluded
diff --git a/src/tint/tint_gdb.py b/src/tint/tint_gdb.py
new file mode 100644
index 0000000..2dce446
--- /dev/null
+++ b/src/tint/tint_gdb.py
@@ -0,0 +1,249 @@
+# Copyright 2022 The Tint Authors.
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# Pretty printers for the Tint project.
+# Add a line to your ~/.gdbinit to source this file, e.g.:
+#
+# source /path/to/dawn/src/tint/tint_gdb.py
+
+import gdb
+import gdb.printing
+from itertools import chain
+
+# When debugging this module, set _DEBUGGING = True so that re-sourcing this file in gdb replaces
+# the existing printers.
+_DEBUGGING = True
+
+# Enable to display other data members along with child elements of compound data types (arrays, etc.).
+# This is useful in debuggers like VS Code that doesn't display the `to_string()` result in the watch window.
+# OTOH, it's less useful when using gdb/lldb's print command.
+_DISPLAY_MEMBERS_AS_CHILDREN = False
+
+
+# Tips for debugging using VS Code:
+# - Set a breakpoint where you can view the types you want to debug/write pretty printers for.
+# - Debug Console: source /path/to/dawn/src/tint/tint_gdb.py
+# - To execute Python code, in the Debug Console:
+#   -exec python foo = gdb.parse_and_eval('map.set_')
+#   -exec python v = (foo['slots_']['impl_']['slice']['data'] + 8).dereference()['value']
+#
+# - Useful docs:
+#   Python API: https://sourceware.org/gdb/onlinedocs/gdb/Python-API.html#Python-API
+#   Especially:
+#     Types: https://sourceware.org/gdb/onlinedocs/gdb/Types-In-Python.html#Types-In-Python
+#     Values: https://sourceware.org/gdb/onlinedocs/gdb/Values-From-Inferior.html#Values-From-Inferior
+
+
+pp_set = gdb.printing.RegexpCollectionPrettyPrinter("tint")
+
+
+class Printer(object):
+    '''Base class for Printers'''
+
+    def __init__(self, val):
+        self.val = val
+
+    def template_type(self, index):
+        '''Returns template type at index'''
+        return self.val.type.template_argument(index)
+
+
+class UtilsSlicePrinter(Printer):
+    '''Printer for tint::utils::Slice<T>'''
+
+    def __init__(self, val):
+        super(UtilsSlicePrinter, self).__init__(val)
+        self.len = self.val['len']
+        self.cap = self.val['cap']
+        self.data = self.val['data']
+        self.elem_type = self.data.type.target().unqualified()
+
+    def length(self):
+        return self.len
+
+    def value_at(self, index):
+        '''Returns array value at index'''
+        return (self.data + index).dereference().cast(self.elem_type)
+
+    def to_string(self):
+        return 'length={} capacity={}'.format(self.len, self.cap)
+
+    def members(self):
+        if _DISPLAY_MEMBERS_AS_CHILDREN:
+            return [
+                ('length', self.len),
+                ('capacity', self.cap),
+            ]
+        else:
+            return []
+
+    def children(self):
+        for m in self.members():
+            yield m
+        for i in range(self.len):
+            yield str(i), self.value_at(i)
+
+    def display_hint(self):
+        return 'array'
+
+
+pp_set.add_printer('UtilsSlicePrinter',
+                   '^tint::utils::Slice<.*>$', UtilsSlicePrinter)
+
+
+class UtilsVectorPrinter(Printer):
+    '''Printer for tint::utils::Vector<T, N>'''
+
+    def __init__(self, val):
+        super(UtilsVectorPrinter, self).__init__(val)
+        self.slice = self.val['impl_']['slice']
+        self.using_heap = self.slice['cap'] > self.template_type(1)
+
+    def slice_printer(self):
+        return UtilsSlicePrinter(self.slice)
+
+    def to_string(self):
+        return 'heap={} {}'.format(self.using_heap, self.slice)
+
+    def members(self):
+        if _DISPLAY_MEMBERS_AS_CHILDREN:
+            return [
+                ('heap', self.using_heap),
+            ]
+        else:
+            return []
+
+    def children(self):
+        return chain(self.members(), self.slice_printer().children())
+
+    def display_hint(self):
+        return 'array'
+
+
+pp_set.add_printer(
+    'UtilsVector', '^tint::utils::Vector<.*>$', UtilsVectorPrinter)
+
+
+class UtilsVectorRefPrinter(Printer):
+    '''Printer for tint::utils::VectorRef<T>'''
+
+    def __init__(self, val):
+        super(UtilsVectorRefPrinter, self).__init__(val)
+        self.slice = self.val['slice_']
+        self.can_move = self.val['can_move_']
+
+    def to_string(self):
+        return 'can_move={} {}'.format(self.can_move, self.slice)
+
+    def members(self):
+        if _DISPLAY_MEMBERS_AS_CHILDREN:
+            return [
+                ('can_move', self.can_move),
+            ]
+        else:
+            return []
+
+    def children(self):
+        return chain(self.members(), UtilsSlicePrinter(self.slice).children())
+
+    def display_hint(self):
+        return 'array'
+
+
+pp_set.add_printer(
+    'UtilsVector', '^tint::utils::VectorRef<.*>$', UtilsVectorRefPrinter)
+
+
+class UtilsHashsetPrinter(Printer):
+    '''Printer for Hashset<T, N, HASH, EQUAL>'''
+
+    def __init__(self, val):
+        super(UtilsHashsetPrinter, self).__init__(val)
+        self.slice = UtilsVectorPrinter(self.val['slots_']).slice_printer()
+        self.try_read_std_optional_func = self.try_read_std_optional
+
+    def to_string(self):
+        length = 0
+        for slot in range(0, self.slice.length()):
+            v = self.slice.value_at(slot)
+            if v['hash'] != 0:
+                length += 1
+        return 'length={}'.format(length)
+
+    def children(self):
+        for slot in range(0, self.slice.length()):
+            v = self.slice.value_at(slot)
+            if v['hash'] != 0:
+                value = v['value']
+
+                # value is a std::optional, let's try to extract its value for display
+                kvp = self.try_read_std_optional_func(slot, value)
+                if kvp is None:
+                    # If we failed, just output the slot and value as is, which will use
+                    # the default visualizer for each.
+                    kvp = slot, value
+
+                yield str(kvp[0]), kvp[1]
+
+    def display_hint(self):
+        return 'array'
+
+    def try_read_std_optional(self, slot, value):
+        try:
+            # libstdc++
+            v = value['_M_payload']['_M_payload']['_M_value']
+            return slot, v
+            # return str(kvp['key']), kvp['value']
+        except:
+            return None
+
+
+pp_set.add_printer(
+    'UtilsHashset', '^tint::utils::Hashset<.*>$', UtilsHashsetPrinter)
+
+
+class UtilsHashmapPrinter(Printer):
+    '''Printer for Hashmap<K, V, N, HASH, EQUAL>'''
+
+    def __init__(self, val):
+        super(UtilsHashmapPrinter, self).__init__(val)
+        self.hash_set = UtilsHashsetPrinter(self.val['set_'])
+        # Replace the lookup function so we can extract the key and value out of the std::optionals in the Hashset
+        self.hash_set.try_read_std_optional_func = self.try_read_std_optional
+
+    def to_string(self):
+        return self.hash_set.to_string()
+
+    def children(self):
+        return self.hash_set.children()
+
+    def display_hint(self):
+        return 'array'
+
+    def try_read_std_optional(self, slot, value):
+        try:
+            # libstdc++
+            kvp = value['_M_payload']['_M_payload']['_M_value']
+            return str(kvp['key']), kvp['value']
+        except:
+            pass
+        # Failed, fall back on hash_set
+        return self.hash_set.try_read_std_optional(slot, value)
+
+
+pp_set.add_printer(
+    'UtilsHashmap', '^tint::utils::Hashmap<.*>$', UtilsHashmapPrinter)
+
+
+gdb.printing.register_pretty_printer(gdb, pp_set, replace=_DEBUGGING)
diff --git a/src/tint/tint_lldb.py b/src/tint/tint_lldb.py
new file mode 100644
index 0000000..85a93ff
--- /dev/null
+++ b/src/tint/tint_lldb.py
@@ -0,0 +1,397 @@
+# Copyright 2022 The Tint Authors.
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+# Pretty printers for the Tint project.
+#
+# If using lldb from command line, add a line to your ~/.lldbinit to import the printers:
+#
+#    command script import /path/to/dawn/src/tint/tint_lldb.py
+#
+#
+# If using VS Code on MacOS with the Microsoft C/C++ extension, add the following to
+# your launch.json (make sure you specify an absolute path to tint_lldb.py):
+#
+#    "name": "Launch",
+#    "type": "cppdbg",
+#    "request": "launch",
+#    ...
+#    "setupCommands": [
+#        {
+#            "description": "Load tint pretty printers",
+#            "ignoreFailures": false,
+#            "text": "command script import /path/to/dawn/src/tint/tint_lldb.py,
+#        }
+#    ]
+#
+# If using VS Code with the CodeLLDB extension (https://github.com/vadimcn/vscode-lldb),
+# add the following to your launch.json:
+#
+#    "name": "Launch",
+#    "type": "lldb",
+#    "request": "launch",
+#    ...
+#    "initCommands": [
+#        "command script import /path/to/dawn/src/tint/tint_lldb.py"
+#    ]
+
+# Based on pretty printers for:
+# Rust: https://github.com/vadimcn/vscode-lldb/blob/master/formatters/rust.py
+# Dlang: https://github.com/Pure-D/dlang-debug/blob/master/lldb_dlang.py
+#
+#
+# Tips for debugging using VS Code:
+#
+# - Set a breakpoint where you can view the types you want to debug/write pretty printers for.
+# - Debug Console: -exec command script import /path/to/dawn/src/tint/tint_lldb.py
+# - You can re-run the above command to reload the printers after modifying the python script.
+
+# - Useful docs:
+#   Formattesr: https://lldb.llvm.org/use/variable.html
+#   Python API: https://lldb.llvm.org/python_api.html
+#   Especially:
+#     SBType: https://lldb.llvm.org/python_api/lldb.SBType.html
+#     SBValue: https://lldb.llvm.org/python_api/lldb.SBValue.html
+
+from __future__ import print_function, division
+import sys
+import logging
+import re
+import lldb
+import types
+
+if sys.version_info[0] == 2:
+    # python2-based LLDB accepts utf8-encoded ascii strings only.
+    def to_lldb_str(s): return s.encode(
+        'utf8', 'backslashreplace') if isinstance(s, unicode) else s
+    range = xrange
+else:
+    to_lldb_str = str
+
+string_encoding = "escape"  # remove | unicode | escape
+
+log = logging.getLogger(__name__)
+
+module = sys.modules[__name__]
+tint_category = None
+
+
+def __lldb_init_module(debugger, dict):
+    global tint_category
+
+    tint_category = debugger.CreateCategory('tint')
+    tint_category.SetEnabled(True)
+
+    attach_synthetic_to_type(
+        UtilsSlicePrinter, r'^tint::utils::Slice<.+>$', True)
+
+    attach_synthetic_to_type(
+        UtilsVectorPrinter, r'^tint::utils::Vector<.+>$', True)
+
+    attach_synthetic_to_type(
+        UtilsVectorRefPrinter, r'^tint::utils::VectorRef<.+>$', True)
+
+    attach_synthetic_to_type(
+        UtilsHashsetPrinter, r'^tint::utils::Hashset<.+>$', True)
+
+    attach_synthetic_to_type(
+        UtilsHashmapPrinter, r'^tint::utils::Hashmap<.+>$', True)
+
+
+def attach_synthetic_to_type(synth_class, type_name, is_regex=False):
+    global module, tint_category
+    synth = lldb.SBTypeSynthetic.CreateWithClassName(
+        __name__ + '.' + synth_class.__name__)
+    synth.SetOptions(lldb.eTypeOptionCascade)
+    ret = tint_category.AddTypeSynthetic(
+        lldb.SBTypeNameSpecifier(type_name, is_regex), synth)
+    log.debug('attaching synthetic %s to "%s", is_regex=%s -> %s',
+              synth_class.__name__, type_name, is_regex, ret)
+
+    def summary_fn(valobj, dict): return get_synth_summary(
+        synth_class, valobj, dict)
+    # LLDB accesses summary fn's by name, so we need to create a unique one.
+    summary_fn.__name__ = '_get_synth_summary_' + synth_class.__name__
+    setattr(module, summary_fn.__name__, summary_fn)
+    attach_summary_to_type(summary_fn, type_name, is_regex)
+
+
+def attach_summary_to_type(summary_fn, type_name, is_regex=False):
+    global module, tint_category
+    summary = lldb.SBTypeSummary.CreateWithFunctionName(
+        __name__ + '.' + summary_fn.__name__)
+    summary.SetOptions(lldb.eTypeOptionCascade)
+    ret = tint_category.AddTypeSummary(
+        lldb.SBTypeNameSpecifier(type_name, is_regex), summary)
+    log.debug('attaching summary %s to "%s", is_regex=%s -> %s',
+              summary_fn.__name__, type_name, is_regex, ret)
+
+
+def get_synth_summary(synth_class, valobj, dict):
+    ''''
+    get_summary' is annoyingly not a part of the standard LLDB synth provider API.
+    This trick allows us to share data extraction logic between synth providers and their sibling summary providers.
+    '''
+    synth = synth_class(valobj.GetNonSyntheticValue(), dict)
+    synth.update()
+    summary = synth.get_summary()
+    return to_lldb_str(summary)
+
+
+def member(valobj, *chain):
+    '''Performs chained GetChildMemberWithName lookups'''
+    for name in chain:
+        valobj = valobj.GetChildMemberWithName(name)
+    return valobj
+
+
+class Printer(object):
+    '''Base class for Printers'''
+
+    def __init__(self, valobj, dict={}):
+        self.valobj = valobj
+        self.initialize()
+
+    def initialize(self):
+        return None
+
+    def update(self):
+        return False
+
+    def num_children(self):
+        return 0
+
+    def has_children(self):
+        return False
+
+    def get_child_at_index(self, index):
+        return None
+
+    def get_child_index(self, name):
+        return None
+
+    def get_summary(self):
+        return None
+
+    def member(self, *chain):
+        '''Performs chained GetChildMemberWithName lookups'''
+        return member(self.valobj, *chain)
+
+    def template_params(self):
+        '''Returns list of template params values (as strings)'''
+        type_name = self.valobj.GetTypeName()
+        params = []
+        level = 0
+        start = 0
+        for i, c in enumerate(type_name):
+            if c == '<':
+                level += 1
+                if level == 1:
+                    start = i + 1
+            elif c == '>':
+                level -= 1
+                if level == 0:
+                    params.append(type_name[start:i].strip())
+            elif c == ',' and level == 1:
+                params.append(type_name[start:i].strip())
+                start = i + 1
+        return params
+
+    def template_param_at(self, index):
+        '''Returns template param value at index (as string)'''
+        return self.template_params()[index]
+
+
+class UtilsSlicePrinter(Printer):
+    '''Printer for tint::utils::Slice<T>'''
+
+    def initialize(self):
+        self.len = self.valobj.GetChildMemberWithName('len')
+        self.cap = self.valobj.GetChildMemberWithName('cap')
+        self.data = self.valobj.GetChildMemberWithName('data')
+        self.elem_type = self.data.GetType().GetPointeeType()
+        self.elem_size = self.elem_type.GetByteSize()
+
+    def get_summary(self):
+        return 'length={} capacity={}'.format(self.len.GetValueAsUnsigned(), self.cap.GetValueAsUnsigned())
+
+    def num_children(self):
+        # NOTE: VS Code on MacOS hangs if we try to expand something too large, so put an artificial limit
+        # until we can figure out how to know if this is a valid instance.
+        return min(self.len.GetValueAsUnsigned(), 256)
+
+    def has_children(self):
+        return True
+
+    def get_child_at_index(self, index):
+        try:
+            if not 0 <= index < self.num_children():
+                return None
+            # TODO: return self.value_at(index)
+            offset = index * self.elem_size
+            return self.data.CreateChildAtOffset('[%s]' % index, offset, self.elem_type)
+        except Exception as e:
+            log.error('%s', e)
+            raise
+
+    def value_at(self, index):
+        '''Returns array value at index'''
+        offset = index * self.elem_size
+        return self.data.CreateChildAtOffset('[%s]' % index, offset, self.elem_type)
+
+
+class UtilsVectorPrinter(Printer):
+    '''Printer for tint::utils::Vector<T, N>'''
+
+    def initialize(self):
+        self.slice = self.member('impl_', 'slice')
+        self.slice_printer = UtilsSlicePrinter(self.slice)
+        self.fixed_size = int(self.template_param_at(1))
+        self.cap = self.slice_printer.member('cap')
+
+    def get_summary(self):
+        using_heap = self.cap.GetValueAsUnsigned() > self.fixed_size
+        return 'heap={} {}'.format(using_heap, self.slice_printer.get_summary())
+
+    def num_children(self):
+        return self.slice_printer.num_children()
+
+    def has_children(self):
+        return self.slice_printer.has_children()
+
+    def get_child_at_index(self, index):
+        return self.slice_printer.get_child_at_index(index)
+
+    def make_slice_printer(self):
+        return UtilsSlicePrinter(self.slice)
+
+
+class UtilsVectorRefPrinter(Printer):
+    '''Printer for tint::utils::VectorRef<T>'''
+
+    def initialize(self):
+        self.slice = self.member('slice_')
+        self.slice_printer = UtilsSlicePrinter(self.slice)
+        self.can_move = self.member('can_move_')
+
+    def get_summary(self):
+        return 'can_move={} {}'.format(self.can_move.GetValue(), self.slice_printer.get_summary())
+
+    def num_children(self):
+        return self.slice_printer.num_children()
+
+    def has_children(self):
+        return self.slice_printer.has_children()
+
+    def get_child_at_index(self, index):
+        return self.slice_printer.get_child_at_index(index)
+
+
+class UtilsHashsetPrinter(Printer):
+    '''Printer for Hashset<T, N, HASH, EQUAL>'''
+
+    def initialize(self):
+        self.slice = UtilsVectorPrinter(
+            self.member('slots_')).make_slice_printer()
+
+        self.try_read_std_optional_func = self.try_read_std_optional
+
+    def update(self):
+        self.valid_slots = []
+        for slot in range(0, self.slice.num_children()):
+            v = self.slice.value_at(slot)
+            if member(v, 'hash').GetValueAsUnsigned() != 0:
+                self.valid_slots.append(slot)
+        return False
+
+    def get_summary(self):
+        return 'length={}'.format(self.num_children())
+
+    def num_children(self):
+        return len(self.valid_slots)
+
+    def has_children(self):
+        return True
+
+    def get_child_at_index(self, index):
+        slot = self.valid_slots[index]
+        v = self.slice.value_at(slot)
+        value = member(v, 'value')
+
+        # value is a std::optional, let's try to extract its value for display
+        kvp = self.try_read_std_optional_func(slot, value)
+        if kvp is None:
+            # If we failed, just output the slot and value as is, which will use
+            # the default printer for std::optional.
+            kvp = slot, value
+
+        return kvp[1].CreateChildAtOffset('[{}]'.format(kvp[0]), 0, kvp[1].GetType())
+
+    def try_read_std_optional(self, slot, value):
+        try:
+            # libc++
+            v = value.EvaluateExpression('__val_')
+            if v.name is not None:
+                return slot, v
+
+            # libstdc++
+            v = value.EvaluateExpression('_M_payload._M_payload._M_value')
+            if v.name is not None:
+                return slot, v
+            return None
+        except:
+            return None
+
+
+class UtilsHashmapPrinter(Printer):
+    '''Printer for Hashmap<K, V, N, HASH, EQUAL>'''
+
+    def initialize(self):
+        self.hash_set = UtilsHashsetPrinter(self.member('set_'))
+        # Replace the lookup function so we can extract the key and value out of the std::optionals in the Hashset
+        self.hash_set.try_read_std_optional_func = self.try_read_std_optional
+
+    def update(self):
+        self.hash_set.update()
+
+    def get_summary(self):
+        return self.hash_set.get_summary()
+
+    def num_children(self):
+        return self.hash_set.num_children()
+
+    def has_children(self):
+        return self.hash_set.has_children()
+
+    def get_child_at_index(self, index):
+        return self.hash_set.get_child_at_index(index)
+
+    def try_read_std_optional(self, slot, value):
+        try:
+            # libc++
+            val = value.EvaluateExpression('__val_')
+            k = val.EvaluateExpression('key')
+            v = val.EvaluateExpression('value')
+            if k.name is not None and v.name is not None:
+                return k.GetValue(), v
+
+            # libstdc++
+            val = value.EvaluateExpression('_M_payload._M_payload._M_value')
+            k = val.EvaluateExpression('key')
+            v = val.EvaluateExpression('value')
+            if k.name is not None and v.name is not None:
+                return k.GetValue(), v
+        except:
+            pass
+        # Failed, fall back on hash_set
+        return self.hash_set.try_read_std_optional(slot, value)
