2 * blktrace output analysis: generate a timeline & gather statistics
4 * Copyright (C) 2006 Alan D. Brunelle <Alan.Brunelle@hp.com>
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
26 struct rb_node rb_node;
34 struct rb_root root_pid, root_name;
36 struct p_info * __find_process_pid(__u32 pid)
39 struct rb_node *n = root_pid.rb_node;
42 this = rb_entry(n, struct pn_info, rb_node);
43 if (pid < this->u.pid)
45 else if (pid > this->u.pid)
54 struct p_info *__find_process_name(char *name)
58 struct rb_node *n = root_name.rb_node;
61 this = rb_entry(n, struct pn_info, rb_node);
62 cmp = strcmp(name, this->u.name);
74 struct p_info *find_process(__u32 pid, char *name)
78 if (pid != ((__u32)-1) && ((pip = __find_process_pid(pid)) != NULL))
82 return __find_process_name(name);
87 static void insert_pid(struct p_info *that)
90 struct rb_node *parent = NULL;
91 struct rb_node **p = &root_pid.rb_node;
95 this = rb_entry(parent, struct pn_info, rb_node);
97 if (that->pid < this->u.pid)
99 else if (that->pid > this->u.pid)
102 ASSERT(strcmp(that->name, this->pip->name) == 0);
103 return; // Already there
107 this = malloc(sizeof(struct pn_info));
108 this->u.pid = that->pid;
111 rb_link_node(&this->rb_node, parent, p);
112 rb_insert_color(&this->rb_node, &root_pid);
115 static void insert_name(struct p_info *that)
118 struct pn_info *this;
119 struct rb_node *parent = NULL;
120 struct rb_node **p = &root_name.rb_node;
124 this = rb_entry(parent, struct pn_info, rb_node);
125 cmp = strcmp(that->name, this->u.name);
132 return; // Already there...
135 this = malloc(sizeof(struct pn_info));
136 this->u.name = strdup(that->name);
139 rb_link_node(&this->rb_node, parent, p);
140 rb_insert_color(&this->rb_node, &root_name);
143 static void insert(struct p_info *pip)
149 void add_process(__u32 pid, char *name)
151 struct p_info *pip = find_process(pid, name);
154 size_t len = sizeof(struct p_info) + strlen(name) + 1;
156 pip = memset(malloc(len), 0, len);
158 init_region(&pip->regions);
159 pip->last_q = (__u64)-1;
160 strcpy(pip->name, name);
166 void pip_update_q(struct io *iop)
169 update_lq(&iop->pip->last_q, &iop->pip->avgs.q2q, iop->t.time);
170 update_qregion(&iop->pip->regions, iop->t.time);
174 void __foreach(struct rb_node *n, void (*f)(struct p_info *, void *), void *arg)
177 __foreach(n->rb_left, f, arg);
178 f(rb_entry(n, struct pn_info, rb_node)->pip, arg);
179 __foreach(n->rb_right, f, arg);
183 void pip_foreach_out(void (*f)(struct p_info *, void *), void *arg)
186 __foreach(root_name.rb_node, f, arg);
189 char *exe, *p, *next, *exes_save = strdup(exes);
192 while (exes_save != NULL) {
194 if ((next = strchr(exes_save, ',')) != NULL) {
201 pip = __find_process_name(exe);