]> rtime.felk.cvut.cz Git - l4.git/blob - l4/pkg/plr/server/src/fault_handlers/kiptime.cc
update
[l4.git] / l4 / pkg / plr / server / src / fault_handlers / kiptime.cc
1 /*
2  * kiptime.cc --
3  *
4  * (c) 2011-2013 Björn Döbel <doebel@os.inf.tu-dresden.de>,
5  *     economic rights: Technische Universität Dresden (Germany)
6  * This file is part of TUD:OS and distributed under the terms of the
7  * GNU General Public License 2.
8  * Please see the COPYING-GPL-2 file for details.
9  */
10
11 #include "../log"
12 #include "../app_loading"
13 #include "../configuration"
14 //#include "../emulation"
15
16 #include "observers.h"
17
18 #include <vector>
19 #include <stdlib.h>
20
21 namespace Romain {
22 class KipTimeObserver_priv : public KIPTimeObserver
23 {
24         private:
25                 std::vector<Breakpoint*> _breakpoints;
26
27                 void read_target_list(char *list)
28                 {
29                         char *end = list + strlen(list); // end of list
30                         char *c = list;                  // iterator
31
32                         while (c < end) {
33                                 char *c2 = c;
34
35                                 /* find next separator or end char */
36                                 while ((*c2 != ',') && (c2 < end)) ++c2;
37
38                                 *c2 = 0;
39
40                                 /* convert the address found */
41                                 errno = 0;
42                                 l4_addr_t a = strtol(c, NULL, 16); // XXX check return
43                                 if (errno) {
44                                         ERROR() << "Conversion error.";
45                                 } else {
46                                         _breakpoints.push_back(new Breakpoint(a));
47                                 }
48
49                                 c = c2+1;
50                         }
51                 }
52
53         DECLARE_OBSERVER("kip time");
54         KipTimeObserver_priv();
55 };
56 }
57
58 Romain::KIPTimeObserver* Romain::KIPTimeObserver::Create()
59 {
60         return new Romain::KipTimeObserver_priv();
61 }
62
63 Romain::KipTimeObserver_priv::KipTimeObserver_priv()
64 {
65         char *list = strdup(ConfigStringValue("kip-time:target", "none"));
66         if (list) {
67                 read_target_list(list);
68         }
69         free(list);
70 }
71
72
73 void Romain::KipTimeObserver_priv::status() const { }
74
75 /*****************************************************************
76  *                      Debugging stuff                          *
77  *****************************************************************/
78 void Romain::KipTimeObserver_priv::startup_notify(Romain::App_instance *inst,
79                                                   Romain::App_thread *,
80                                                   Romain::Thread_group *,
81                                                   Romain::App_model *am)
82 {
83         for (std::vector<Breakpoint*>::iterator i = _breakpoints.begin();
84                  i != _breakpoints.end(); ++i) {
85                 DEBUG() << std::hex << (*i)->address();
86                 (*i)->activate(inst, am);
87         }
88 }
89
90 Romain::Observer::ObserverReturnVal
91 Romain::KipTimeObserver_priv::notify(Romain::App_instance *i,
92                                      Romain::App_thread *t,
93                                      Romain::Thread_group *,
94                                      Romain::App_model *am)
95 {
96         if (!entry_reason_is_int3(t->vcpu(), i, am) &&
97                 !entry_reason_is_int1(t->vcpu()))
98                 return Romain::Observer::Ignored;
99
100         for (std::vector<Breakpoint*>::const_iterator it = _breakpoints.begin();
101                  it != _breakpoints.end(); ++it) {
102                 if ((*it)->was_hit(t)) {
103                         l4_cpu_time_t time = l4re_kip()->clock;
104
105                         t->vcpu()->r()->si = time & 0xFFFFFFFF;
106                         t->vcpu()->r()->di = (time >> 32) & 0xFFFFFFFF;
107                         t->vcpu()->r()->ip += 11;
108
109                         return Romain::Observer::Replicatable;
110                 }
111         }
112
113         return Romain::Observer::Ignored;
114 }