#include <mdb/mdb_modapi.h>
#include <mdb/mdb_ks.h>
#include <mdb/mdb_ctf.h>
#include <smbsrv/hash_table.h>
struct hw_info {
HT_HANDLE hw_handle;
HT_TABLE_ENTRY hw_tblent;
HT_ITEM hw_item;
int hw_idx;
};
int
smb_ht_walk_init(mdb_walk_state_t *wsp)
{
struct hw_info *hw;
uintptr_t addr = wsp->walk_addr;
HT_HANDLE *ht;
if (addr == 0) {
mdb_printf("require address of an HT_HANDLE\n");
return (WALK_ERR);
}
wsp->walk_data = hw = mdb_zalloc(sizeof (*hw), UM_GC|UM_SLEEP);
ht = &hw->hw_handle;
if (mdb_vread(ht, sizeof (*ht), wsp->walk_addr) == -1) {
mdb_warn("failed to read %s at %#lx",
"HT_HANDLE", wsp->walk_addr);
return (WALK_ERR);
}
hw->hw_idx = -1;
wsp->walk_addr = 0;
wsp->walk_data = hw;
return (WALK_NEXT);
}
int
smb_ht_walk_step(mdb_walk_state_t *wsp)
{
struct hw_info *hw = wsp->walk_data;
HT_TABLE_ENTRY *he = &hw->hw_tblent;
HT_ITEM *hi = &hw->hw_item;
uintptr_t he_addr;
int rv;
while (wsp->walk_addr == 0) {
if (++hw->hw_idx >= hw->hw_handle.ht_table_size)
return (WALK_DONE);
he_addr = (uintptr_t)hw->hw_handle.ht_table +
(hw->hw_idx * sizeof (HT_TABLE_ENTRY));
if (mdb_vread(he, sizeof (*he), he_addr) == -1) {
mdb_warn("failed to read %s at %p",
"HT_TABLE_ENTRY", wsp->walk_addr);
return (WALK_ERR);
}
wsp->walk_addr = (uintptr_t)he->he_head;
}
if (mdb_vread(hi, sizeof (*hi), wsp->walk_addr) == -1) {
mdb_warn("failed to read %s at %p",
"HT_ITEM", wsp->walk_addr);
return (WALK_ERR);
}
rv = wsp->walk_callback(wsp->walk_addr, hi,
wsp->walk_cbdata);
wsp->walk_addr = (uintptr_t)hi->hi_next;
return (rv);
}