3 #include "jdb_module.h"
8 class Jdb_kobject_handler;
10 class Jdb_kobject : public Jdb_module
16 Jdb_kobject_handler *_first;
17 Jdb_kobject_handler **_tail;
22 class Jdb_kobject_handler
24 friend class Jdb_kobject;
27 Jdb_kobject_handler(char const *type) : kobj_type(type) {}
28 char const *kobj_type;
29 virtual bool show_kobject(Kobject_common *o, int level) = 0;
30 virtual int show_kobject_short(char *, int, Kobject_common *) { return 0; }
31 virtual Kobject_common *follow_link(Kobject_common *o) { return o; }
32 virtual ~Jdb_kobject_handler() {}
33 virtual bool invoke(Kobject_common *o, Syscall_frame *f, Utcb *utcb);
34 virtual bool handle_key(Kobject_common *, int /*keycode*/) { return false; }
35 virtual Kobject *parent(Kobject_common *) { return 0; }
36 virtual char const *kobject_type() const { return kobj_type; }
48 Jdb_kobject_handler *_next;
51 class Jdb_kobject_extension : public Kobject_dbg::Dbg_extension
54 virtual ~Jdb_kobject_extension() {}
55 virtual char const *type() const = 0;
58 class Jdb_kobject_list : public Jdb_list
61 typedef bool Filter_func(Kobject_common const *);
70 Mode(char const *name, Filter_func *filter)
71 : name(name), filter(filter)
73 // make sure that non-filtered mode is first in the list so that we
74 // get this one displayed initially
75 if (!filter || !first)
88 void *get_head() const
89 { return Kobject::from_dbg(Kobject_dbg::_jdb_head.get_unused()); }
92 Mode const *_current_mode;
97 //--------------------------------------------------------------------------
105 #include "entry_frame.h"
107 #include "jdb_core.h"
108 #include "jdb_module.h"
109 #include "jdb_screen.h"
110 #include "kernel_console.h"
112 #include "keycodes.h"
113 #include "ram_quota.h"
114 #include "simpleio.h"
116 #include "static_init.h"
118 Jdb_kobject_list::Mode *Jdb_kobject_list::Mode::first;
120 class Jdb_kobject_id_hdl : public Jdb_kobject_handler
123 Jdb_kobject_id_hdl() : Jdb_kobject_handler(0) {}
124 virtual bool show_kobject(Kobject_common *, int) { return false; }
125 virtual ~Jdb_kobject_id_hdl() {}
130 Jdb_kobject_id_hdl::invoke(Kobject_common *o, Syscall_frame *f, Utcb *utcb)
132 if ( utcb->values[0] != Op_global_id
133 && utcb->values[0] != Op_kobj_to_id)
136 if (utcb->values[0] == Op_global_id)
137 utcb->values[0] = o->dbg_info()->dbg_id();
139 utcb->values[0] = Kobject_dbg::pointer_to_id((void *)utcb->values[1]);
140 f->tag(Kobject_iface::commit_result(0, 1));
147 Jdb_kobject_list::get_first()
149 Kobject *f = static_cast<Kobject*>(get_head());
150 while (f && _filter && !_filter(f))
151 f = Kobject::from_dbg(f->dbg_info()->_next);
157 Jdb_kobject_list::Jdb_kobject_list(Filter_func *filt)
158 : Jdb_list(), _current_mode(0), _filter(filt)
159 { set_start(get_first()); }
162 Jdb_kobject_list::Jdb_kobject_list()
163 : Jdb_list(), _current_mode(Mode::first), _filter(0)
166 _filter = _current_mode->filter;
168 set_start(get_first());
173 Jdb_kobject_list::show_item(char *buffer, int max, void *item) const
175 return Jdb_kobject::obj_description(buffer, max, false, static_cast<Kobject*>(item));
180 Jdb_kobject_list::enter_item(void *item) const
182 Kobject *o = static_cast<Kobject*>(item);
183 return Jdb_kobject::module()->handle_obj(o, 1);
188 Jdb_kobject_list::follow_link(void *item)
190 Kobject *o = static_cast<Kobject*>(item);
191 Jdb_kobject_handler *h = Jdb_kobject::module()->find_handler(o);
193 return h->follow_link(o);
200 Jdb_kobject_list::handle_key(void *item, int keycode)
202 Kobject *o = static_cast<Kobject*>(item);
203 Jdb_kobject_handler *h = Jdb_kobject::module()->first_global_handler();
204 bool handled = false;
207 handled |= h->handle_key(o, keycode);
208 h = h->next_global();
211 h = Jdb_kobject::module()->find_handler(o);
213 handled |= h->handle_key(o, keycode);
218 PRIVATE inline NOEXPORT
220 Jdb_kobject_list::next(Kobject *o)
227 o = Kobject::from_dbg(o->dbg_info()->_next);
229 while (o && _filter && !_filter(o));
233 PRIVATE inline NOEXPORT
235 Jdb_kobject_list::prev(Kobject *o)
242 o = Kobject::from_dbg(o->dbg_info()->_pref);
244 while (o && _filter && !_filter(o));
250 Jdb_kobject_list::seek(int cnt, void **item)
252 Kobject *c = static_cast<Kobject*>(*item);
256 for (i = 0; i < cnt; ++i)
258 Kobject *n = next(c);
266 for (i = 0; i < -cnt; ++i)
268 Kobject *n = prev(c);
288 Jdb_kobject_list::show_head() const
296 Jdb_kobject_list::get_mode_str() const
300 return _current_mode->name;
307 Jdb_kobject_list::next_mode()
312 _current_mode = _current_mode->next;
314 _current_mode = Mode::first;
316 _filter = _current_mode->filter;
319 /* When the mode changes the current object may get invisible,
320 * get a new visible one */
323 Jdb_kobject_list::get_valid(void *o)
328 if (_filter && _filter(static_cast<Kobject*>(o)))
335 Jdb_kobject_handler::invoke(Kobject_common *, Syscall_frame *, Utcb *)
339 Jdb_kobject_handler *
340 Jdb_kobject_handler::next_global()
342 Jdb_kobject_handler *h = this->_next;
352 void *Jdb_kobject::kobjp;
355 Jdb_kobject::Jdb_kobject()
356 : Jdb_module("INFO"),
365 Jdb_kobject::register_handler(Jdb_kobject_handler *h)
373 Jdb_kobject_handler *
374 Jdb_kobject::first_global_handler() const
376 if (!_first || !_first->kobj_type)
378 return _first->next_global();
382 Jdb_kobject_handler *
383 Jdb_kobject::find_handler(Kobject_common *o)
385 Jdb_kobject_handler *h = _first;
388 if (o->kobj_type() == h->kobj_type)
397 Jdb_kobject::handle_obj(Kobject *o, int lvl)
399 Jdb_kobject_handler *h = find_handler(o);
401 return h->show_kobject(o, lvl);
408 Jdb_kobject::kobject_type(Kobject_common *o)
410 Jdb_kobject_handler *h = module()->find_handler(o);
412 return h->kobject_type();
413 return o->kobj_type();
419 Jdb_kobject::obj_description(char *buffer, int max, bool dense, Kobject_common *o)
421 int pos = snprintf(buffer, max,
422 dense ? "%lx %lx [%-*s]" : "%8lx %08lx [%-*s]",
423 o->dbg_info()->dbg_id(), (Mword)o, 7, kobject_type(o));
425 Jdb_kobject_handler *h = Jdb_kobject::module()->first_global_handler();
428 pos += h->show_kobject_short(buffer + pos, max-pos, o);
429 h = h->next_global();
432 Jdb_kobject_handler *oh = Jdb_kobject::module()->find_handler(o);
434 pos += oh->show_kobject_short(buffer + pos, max-pos, o);
441 Jdb_kobject::print_kobj(Kobject *o)
443 printf("%p [type=%s]", o, o->kobj_type());
447 Jdb_module::Action_code
448 Jdb_kobject::action(int cmd, void *&, char const *&, int &)
453 Kobject *k = Kobject::pointer_to_obj(kobjp);
455 printf("Not a kobj.\n");
458 if (!handle_obj(k, 0))
459 printf("Kobj w/o handler: ");
467 Jdb_kobject_list list;
474 Jdb_module::Cmd const *
475 Jdb_kobject::cmds() const
479 { 0, "K", "kobj", "%p", "K<kobj_ptr>\tshow information for kernel object",
481 { 1, "Q", "listkobj", "", "Q\tshow information for kernel objects", 0 },
488 Jdb_kobject::num_cmds() const
491 STATIC_INITIALIZE_P(Jdb_kobject, JDB_MODULE_INIT_PRIO);
495 Jdb_kobject::fmt_handler(char /*fmt*/, int *size, char const *cmd_str, void *arg)
503 *size = sizeof(void*);
505 while((c = Jdb_core::cmd_getchar(cmd_str)) != ' ' && c!=KEY_RETURN)
510 if(c==KEY_BACKSPACE && pos>0)
516 if (pos < (int)sizeof(buffer) - 1)
524 void **a = (void**)arg;
532 char const *num = buffer;
533 if (buffer[0] == 'P')
536 n = strtoul(num, 0, 16);
540 if (buffer[0] != 'P')
541 ko = Kobject::id_to_obj(n);
543 ko = Kobject::pointer_to_obj((void*)n);
556 Jdb_core::add_fmt_handler('q', fmt_handler);
558 // static Jdb_handler enter(at_jdb_enter);
560 static Jdb_kobject_id_hdl id_hdl;
561 module()->register_handler(&id_hdl);
566 Jdb_kobject::module()
568 static Jdb_kobject jdb_kobj_module;
569 return &jdb_kobj_module;
572 // Be robust if this object is invalid
575 Jdb_kobject::print_uid(Kobject_common *o, int task_format = 0)
579 printf("%*.s", task_format, "---");
583 if (Kobject_dbg::is_kobj(o))
585 printf("%*.lx", task_format, o->dbg_info()->dbg_id());
589 printf("\033[31;1m%*s%p\033[m", task_format, "???", o);
595 sys_invoke_debug(Kobject_iface *o, Syscall_frame *f)
599 f->tag(Kobject_iface::commit_result(-L4_err::EInval));
603 Utcb *utcb = current_thread()->utcb().access();
604 //printf("sys_invoke_debug: [%p] -> %p\n", o, f);
605 Jdb_kobject_handler *h = Jdb_kobject::module()->find_handler(o);
606 if (h && h->invoke(o, f, utcb))
609 h = Jdb_kobject::module()->first_global_handler();
612 if (h->invoke(o, f, utcb))
614 h = h->next_global();
617 f->tag(Kobject_iface::commit_result(-L4_err::ENosys));
621 template< typename T >
624 Jdb_kobject_extension::find_extension(Kobject_common const *o)
626 Kobject_dbg::Dbg_extension *ex = o->dbg_info()->_jdb_data;
629 Jdb_kobject_extension *je = static_cast<Jdb_kobject_extension*>(ex);
630 if (je->type() == T::static_type)
631 return static_cast<T*>(je);
639 static Jdb_kobject_list::Mode INIT_PRIORITY(JDB_MODULE_INIT_PRIO) all("[ALL]", 0);