and adj = data.$lid:struct_name^"_"^name^"_adjustment"$ in
let offset = Int64.of_int offset
and adj = Int64.of_int adj in
- (* 'addr' is base of the virtual struct *)
- let addr = Int64.sub (Int64.add addr offset) adj in
+
+ (* 'addr' is base of the virtual struct, but when
+ * adding it to the map make sure we don't splat
+ * the real structure (can happen if offset=adj).
+ *)
let map =
- AddrMap.add addr ($str:dest_struct_name$, None) map in
+ if offset <> adj then (
+ let addr = Int64.sub (Int64.add addr offset) adj in
+ AddrMap.add addr ($str:dest_struct_name$, None) map
+ ) else map in
+
+ (* 'dest_addr' is the destination address of
+ * this pointer. It needs the usual list_head
+ * adjustment applied.
+ *)
let dest_addr = Int64.sub dest_addr adj in
let map =
$lid:dest_struct_name^"_follower"$
let offset = data.task_struct_run_list'next_offset
and adj = data.task_struct_run_list'next_adjustment in
let offset = Int64.of_int offset and adj = Int64.of_int adj in
- let addr = Int64.sub (Int64.add addr offset) adj in
- let map = AddrMap.add addr ("task_struct", None) map in
+ let map =
+ if offset <> adj
+ then
+ (let addr = Int64.sub (Int64.add addr offset) adj
+ in AddrMap.add addr ("task_struct", None) map)
+ else map in
let dest_addr = Int64.sub dest_addr adj in
let map = task_struct_follower kernel_version load map dest_addr
in map in
let offset = data.task_struct_tasks'next_offset
and adj = data.task_struct_tasks'next_adjustment in
let offset = Int64.of_int offset and adj = Int64.of_int adj in
- let addr = Int64.sub (Int64.add addr offset) adj in
- let map = AddrMap.add addr ("task_struct", None) map in
+ let map =
+ if offset <> adj
+ then
+ (let addr = Int64.sub (Int64.add addr offset) adj
+ in AddrMap.add addr ("task_struct", None) map)
+ else map in
let dest_addr = Int64.sub dest_addr adj in
let map = task_struct_follower kernel_version load map dest_addr
in map
let offset = data.net_device_dev_list'next_offset
and adj = data.net_device_dev_list'next_adjustment in
let offset = Int64.of_int offset and adj = Int64.of_int adj in
- let addr = Int64.sub (Int64.add addr offset) adj in
- let map = AddrMap.add addr ("net_device", None) map in
+ let map =
+ if offset <> adj
+ then
+ (let addr = Int64.sub (Int64.add addr offset) adj
+ in AddrMap.add addr ("net_device", None) map)
+ else map in
let dest_addr = Int64.sub dest_addr adj in
let map = net_device_follower kernel_version load map dest_addr
in map in
let offset = data.net_dev_base_head'next_offset
and adj = data.net_dev_base_head'next_adjustment in
let offset = Int64.of_int offset and adj = Int64.of_int adj in
- let addr = Int64.sub (Int64.add addr offset) adj in
- let map = AddrMap.add addr ("net_device", None) map in
+ let map =
+ if offset <> adj
+ then
+ (let addr = Int64.sub (Int64.add addr offset) adj
+ in AddrMap.add addr ("net_device", None) map)
+ else map in
let dest_addr = Int64.sub dest_addr adj in
let map = net_device_follower kernel_version load map dest_addr in map in
let dest_addr = data.net_dev_base_head'prev in
let offset = data.net_dev_base_head'prev_offset
and adj = data.net_dev_base_head'prev_adjustment in
let offset = Int64.of_int offset and adj = Int64.of_int adj in
- let addr = Int64.sub (Int64.add addr offset) adj in
- let map = AddrMap.add addr ("net_device", None) map in
+ let map =
+ if offset <> adj
+ then
+ (let addr = Int64.sub (Int64.add addr offset) adj
+ in AddrMap.add addr ("net_device", None) map)
+ else map in
let dest_addr = Int64.sub dest_addr adj in
let map = net_device_follower kernel_version load map dest_addr in map
in map)
let { ksyms = ksyms; have_ksyms = have_ksyms; utsname = utsname;
addrmap = addrmap } = kimage in
match have_ksyms, utsname with
- | true, Some { uts_kernel_release = kversion } ->
+ | true, Some { uts_kernel_release = kernel_version } ->
let kimage = ref kimage in
let load struct_name addr size =
if debug then
let bits = Virt_mem_mmap.get_bytes !kimage.mem addr size in
Bitstring.bitstring_of_string bits
in
- let init_task = Ksymmap.find "init_task" ksyms in
let addrmap =
- Kernel.task_struct_follower kversion load addrmap init_task in
- { !kimage with addrmap = addrmap }
+ try
+ let init_task = Ksymmap.find "init_task" ksyms in
+ Some (Kernel.task_struct_follower kernel_version
+ load addrmap init_task)
+ with
+ Not_found ->
+ eprintf (f_"%s: cannot find init_task symbol in kernel image.\n") !kimage.domname;
+ None in
+ (match addrmap with
+ | None -> !kimage
+ | Some addrmap ->
+ { !kimage with addrmap = addrmap; have_tasks = true }
+ )
| _, _ -> kimage
) in
let { ksyms = ksyms; have_ksyms = have_ksyms; utsname = utsname;
addrmap = addrmap } = kimage in
match have_ksyms, utsname with
- | true, Some { uts_kernel_release = kversion } ->
+ | true, Some { uts_kernel_release = kernel_version } ->
let kimage = ref kimage in
let load struct_name addr size =
if debug then
let addrmap =
try
let dev_base = Ksymmap.find "dev_base" ksyms in
- Kernel.net_device_follower kversion load addrmap dev_base
+ Some (Kernel.net_device_follower kernel_version
+ load addrmap dev_base)
with Not_found ->
try
let dev_base_head = Ksymmap.find "dev_base_head" ksyms in
with Not_found ->
try
let init_net = Ksymmap.find "init_net" ksyms in
- Kernel.net_follower kversion load addrmap init_net
+ Some (Kernel.net_follower kernel_version
+ load addrmap init_net)
with Not_found ->
eprintf (f_"%s: cannot find dev_base, dev_base_head or init_net symbols in kernel image.\n") !kimage.domname;
- addrmap in
- { !kimage with addrmap = addrmap }
+ None in
+ (match addrmap with
+ | None -> !kimage
+ | Some addrmap ->
+ { !kimage with addrmap = addrmap; have_net_devices = true }
+ )
| _, _ -> kimage
) in
virt_ps.cmo: ../lib/virt_mem_utils.cmo ../lib/virt_mem_types.cmi \
- ../lib/virt_mem_gettext.cmo ../lib/virt_mem.cmi
+ ../lib/virt_mem_gettext.cmo ../lib/virt_mem.cmi ../lib/kernel.cmi
virt_ps.cmx: ../lib/virt_mem_utils.cmx ../lib/virt_mem_types.cmx \
- ../lib/virt_mem_gettext.cmx ../lib/virt_mem.cmx
+ ../lib/virt_mem_gettext.cmx ../lib/virt_mem.cmx ../lib/kernel.cmx
open Virt_mem_utils
open Virt_mem_types
-(*
-open Kernel_task_struct
+open Kernel
-let run debug { domname = domname; mem = mem } { tasks = tasks } =
- let tasks = Option.get tasks in
+let run debug { addrmap = addrmap } =
+ (* Grab all the task_struct structures. *)
+ let tasks = AddrMap.fold (
+ fun _ v tasks ->
+ match v with
+ | _, Some (_, _, Task_struct task) -> task :: tasks
+ | _ -> tasks
+ ) addrmap [] in
(* Sort tasks by PID. *)
- let cmp { task_pid = p1 } { task_pid = p2 } = compare p1 p2 in
+ let cmp { task_struct_pid = p1 } { task_struct_pid = p2 } = compare p1 p2 in
let tasks = List.sort cmp tasks in
printf " PID STAT COMMAND\n";
List.iter (
- fun task ->
- printf "%5Ld %s\n" task.task_pid task.task_comm
+ fun { task_struct_pid = pid; task_struct_comm = comm } ->
+ let comm = truncate_c_string comm in
+ printf "%5Ld %s\n" pid comm
) tasks
-*)
-
-let run debug _ = ()
let summary = s_"list processes in virtual machine"
let description = s_"\