The debugger provides parameterized aliases and debugger variables of arbitrary types. Clever use of these can do almost any list traversal.
For example, here is how to navigate an array:
alias elt(e_) "{ p e_ }"
alias pa0(a) "{ set $a = &a[0]; set $i = 0; elt($a[$i]); set $i = $i+1 }"
alias pan "{ elt($a[$i]); set $i = $i+1 }"
pa0
pan
pan
pan
%idb a.out
...
(idb) alias elt(e_) "{ p e_ }"
(idb) alias a0(a) "{ set $a = &a[0]; set $i = 0; elt($a[$i]); set $i = $i+1 }"
(idb) alias pan "{ elt($a[$i]); set $i = $i+1 }"
...
(idb) pa0(a)
struct S {
next = 0x140000178;
}
(idb) pan
struct S {
next = 0x140000180;
}
(idb)
struct S {
next = 0x140000188;
}
(idb)
struct S {
next = 0x140000190;
}