Skip to content
Permalink
Browse files
Merge pull request #10338 from Pokechu22/natvis-improvements
Natvis improvements
  • Loading branch information
lioncash committed Jan 6, 2022
2 parents c16b8f4 + 8e2b069 commit 7bd14c5
Show file tree
Hide file tree
Showing 3 changed files with 68 additions and 34 deletions.
@@ -11,61 +11,64 @@
This is a re-implementation of the abstract bitfield class' algrothm (in BitField.h)
for Visual Studio to use for pretty-printing during debugging.
-->
<Type Name="BitField&lt;*,*,*&gt;">
<DisplayString Condition="$T2 == 1"><![CDATA[{(storage & (1 << $T1)) != 0}]]></DisplayString>
<DisplayString><![CDATA[{(storage >> $T1) & ((1 << $T2) - 1)}]]></DisplayString>
<Type Name="BitField&lt;*,*,*,*&gt;">
<DisplayString><![CDATA[{($T3)((storage >> $T1) & ((1 << $T2) - 1))}]]></DisplayString>
<Expand>
<Item Name="Offset">$T1</Item>
<Item Name="Size">$T2</Item>
</Expand>
</Type>


<!--Specialised versions for signed types-->
<Type Name="BitField&lt;*,*,__int64&gt;">
<!-- This is what I have do to get a sign extension in this crappy natvis "language"
Basically, we check the top bit, if it's one, we add the remaining
bits to the smallest (most negative) number. -->
<DisplayString Condition="(storage &amp; (1 &lt;&lt; ($T1 + $T2))) != 0">
<![CDATA[{(-1 * (1 << ($T2-1))) + ((storage >> $T1) & ((1 << ($T2-1)) - 1))}]]>
</DisplayString>
<DisplayString><![CDATA[{(storage >> $T1) & ((1 << ($T2-1)) - 1)}]]></DisplayString>
<!-- Similar re-implementation for BitFieldArray -->
<Type Name="BitFieldArray&lt;*,*,*,*,*&gt;">
<Expand>
<IndexListItems>
<Size>$T3</Size>
<ValueNode><![CDATA[($T4)((storage >> ($T1 + $T2*$i)) & ((1 << $T2) - 1))]]></ValueNode>
</IndexListItems>
<!-- Put these after the index list, so that the index list is the main thing in the unexpanded preview -->
<Item Name="Offset">$T1</Item>
<Item Name="Size">$T2</Item>
<Item Name="Count">$T3</Item>
</Expand>
</Type>

<!-- Oh, and I can't do a generic match for all signed types, so these are identical to the __int64 case above
Would be nice if std::numeric_limits<$T3>::is_signed or std::is_signed<$T3>::value worked -->
<Type Name="BitField&lt;*,*,__int32&gt;">
<DisplayString Condition="(storage &amp; (1 &lt;&lt; ($T1 + $T2))) != 0">
<![CDATA[{(-1 * (1 << ($T2-1))) + ((storage >> $T1) & ((1 << ($T2-1)) - 1))}]]>
</DisplayString>
<DisplayString><![CDATA[{(storage >> $T1) & ((1 << ($T2-1)) - 1)}]]></DisplayString>
<Expand>
<Item Name="Offset">$T1</Item>
<Item Name="Size">$T2</Item>
</Expand>
</Type>
<Type Name="BitField&lt;*,*,__int16&gt;">
<DisplayString Condition="(storage &amp; (1 &lt;&lt; ($T1 + $T2))) != 0">
<![CDATA[{(-1 * (1 << ($T2-1))) + ((storage >> $T1) & ((1 << ($T2-1)) - 1))}]]>
<!--Specialised versions for signed types-->
<Type Name="BitField&lt;*,*,signed char,*&gt;">
<!-- It seems like we can't use s8/s16/s32/s64, nor can we use std::int8_t or the like; we have to use these names -->
<AlternativeType Name="BitField&lt;*,*,short,*&gt;" />
<AlternativeType Name="BitField&lt;*,*,int,*&gt;" />
<AlternativeType Name="BitField&lt;*,*,long long,*&gt;" />

<!-- This is what I have do to get a sign extension in this crappy natvis "language"
Basically, we check the top bit, if it's one, we add the remaining
bits to the smallest (most negative) number. -->
<DisplayString Condition="(storage &amp; (1 &lt;&lt; ($T1 + $T2 - 1))) != 0">
<![CDATA[{($T3)((-1 * (1 << ($T2-1))) + ((storage >> $T1) & ((1 << ($T2-1)) - 1)))}]]>
</DisplayString>
<DisplayString><![CDATA[{(storage >> $T1) & ((1 << ($T2-1)) - 1)}]]></DisplayString>
<DisplayString><![CDATA[{($T3)((storage >> $T1) & ((1 << ($T2-1)) - 1))}]]></DisplayString>
<Expand>
<Item Name="Offset">$T1</Item>
<Item Name="Size">$T2</Item>
</Expand>
</Type>
<Type Name="BitField&lt;*,*,__int8&gt;">
<DisplayString Condition="(storage &amp; (1 &lt;&lt; ($T1 + $T2))) != 0">
<![CDATA[{(-1 * (1 << ($T2-1))) + ((storage >> $T1) & ((1 << ($T2-1)) - 1))}]]>
</DisplayString>
<DisplayString><![CDATA[{(storage >> $T1) & ((1 << ($T2-1)) - 1)}]]></DisplayString>

<Type Name="BitFieldArray&lt;*,*,*,signed char,*&gt;">
<AlternativeType Name="BitFieldArray&lt;*,*,*,short,*&gt;" />
<AlternativeType Name="BitFieldArray&lt;*,*,*,int,*&gt;" />
<AlternativeType Name="BitFieldArray&lt;*,*,*,long,*&gt;" />

<Expand>
<IndexListItems>
<Size>$T3</Size>
<ValueNode Condition="(storage &amp; (1 &lt;&lt; ($T1 + $T2 * $i + $T2 - 1))) != 0">
<![CDATA[($T4)((-1 * (1 << ($T2-1))) + ((storage >> ($T1 + $T2*$i)) & ((1 << ($T2-1)) - 1)))]]>
</ValueNode>
<ValueNode><![CDATA[($T4)((storage >> ($T1 + $T2*$i)) & ((1 << ($T2-1)) - 1))]]></ValueNode>
</IndexListItems>
<Item Name="Offset">$T1</Item>
<Item Name="Size">$T2</Item>
<Item Name="Count">$T3</Item>
</Expand>
</Type>
</AutoVisualizer>
@@ -0,0 +1,30 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
Copyright 2022 Dolphin Emulator Project
SPDX-License-Identifier: GPL-2.0-or-later
-->

<AutoVisualizer xmlns="http://schemas.microsoft.com/vstudio/debugger/natvis/2010">
<Type Name="Common::EnumMap&lt;*,*,*&gt;">
<Expand>
<!-- The following would work, except ValueNode for IndexListItems doesn't support the Name attribute.
It's only allowed for LinkedListItems and TreeItems, for some reason. So we get to reimplement it with CustomListItems. -->
<!--
<IndexListItems>
<Size>$T2 + 1</Size>
<ValueNode Name="[{($T3)$i}]">m_array[$i]</ValueNode>
</IndexListItems>
-->
<CustomListItems MaxItemsPerView="5000">
<Variable Name="i" InitialValue="0" />
<!-- Size is incremented by 1 since the template argument is the last member (inclusive), but we want the count (exclusive) -->
<Size>$T2 + 1</Size>
<Loop>
<Break Condition="i > $T2" />
<Item Name="[{($T3)i}]">m_array[i]</Item>
<Exec>i++</Exec>
</Loop>
</CustomListItems>
</Expand>
</Type>
</AutoVisualizer>
@@ -1236,5 +1236,6 @@
</ItemGroup>
<ItemGroup>
<Natvis Include="Common\BitField.natvis" />
<Natvis Include="Common\EnumMap.natvis" />
</ItemGroup>
</Project>

0 comments on commit 7bd14c5

Please sign in to comment.