1 /* Inferior process information for the remote server for GDB.
2 Copyright (C) 2002, 2005, 2007 Free Software Foundation, Inc.
4 Contributed by MontaVista Software.
6 This file is part of GDB.
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA. */
29 struct inferior_list_entry entry
;
35 struct inferior_list all_threads
;
37 struct thread_info
*current_inferior
;
39 #define get_thread(inf) ((struct thread_info *)(inf))
42 add_inferior_to_list (struct inferior_list
*list
,
43 struct inferior_list_entry
*new_inferior
)
45 new_inferior
->next
= NULL
;
46 if (list
->tail
!= NULL
)
47 list
->tail
->next
= new_inferior
;
49 list
->head
= new_inferior
;
50 list
->tail
= new_inferior
;
54 for_each_inferior (struct inferior_list
*list
,
55 void (*action
) (struct inferior_list_entry
*))
57 struct inferior_list_entry
*cur
= list
->head
, *next
;
68 change_inferior_id (struct inferior_list
*list
,
71 if (list
->head
!= list
->tail
)
72 error ("tried to change thread ID after multiple threads are created");
74 list
->head
->id
= new_id
;
78 remove_inferior (struct inferior_list
*list
,
79 struct inferior_list_entry
*entry
)
81 struct inferior_list_entry
**cur
;
83 if (list
->head
== entry
)
85 list
->head
= entry
->next
;
86 if (list
->tail
== entry
)
87 list
->tail
= list
->head
;
92 while (*cur
&& (*cur
)->next
!= entry
)
98 (*cur
)->next
= entry
->next
;
100 if (list
->tail
== entry
)
105 add_thread (unsigned long thread_id
, void *target_data
, unsigned int gdb_id
)
107 struct thread_info
*new_thread
108 = (struct thread_info
*) malloc (sizeof (*new_thread
));
110 memset (new_thread
, 0, sizeof (*new_thread
));
112 new_thread
->entry
.id
= thread_id
;
114 add_inferior_to_list (&all_threads
, & new_thread
->entry
);
116 if (current_inferior
== NULL
)
117 current_inferior
= new_thread
;
119 new_thread
->target_data
= target_data
;
120 set_inferior_regcache_data (new_thread
, new_register_cache ());
121 new_thread
->gdb_id
= gdb_id
;
125 thread_id_to_gdb_id (unsigned long thread_id
)
127 struct inferior_list_entry
*inf
= all_threads
.head
;
131 struct thread_info
*thread
= get_thread (inf
);
132 if (inf
->id
== thread_id
)
133 return thread
->gdb_id
;
141 thread_to_gdb_id (struct thread_info
*thread
)
143 return thread
->gdb_id
;
147 gdb_id_to_thread (unsigned int gdb_id
)
149 struct inferior_list_entry
*inf
= all_threads
.head
;
153 struct thread_info
*thread
= get_thread (inf
);
154 if (thread
->gdb_id
== gdb_id
)
163 gdb_id_to_thread_id (unsigned int gdb_id
)
165 struct thread_info
*thread
= gdb_id_to_thread (gdb_id
);
167 return thread
? thread
->entry
.id
: 0;
171 free_one_thread (struct inferior_list_entry
*inf
)
173 struct thread_info
*thread
= get_thread (inf
);
174 free_register_cache (inferior_regcache_data (thread
));
179 remove_thread (struct thread_info
*thread
)
181 remove_inferior (&all_threads
, (struct inferior_list_entry
*) thread
);
182 free_one_thread (&thread
->entry
);
186 clear_inferiors (void)
188 for_each_inferior (&all_threads
, free_one_thread
);
190 all_threads
.head
= all_threads
.tail
= NULL
;
193 struct inferior_list_entry
*
194 find_inferior (struct inferior_list
*list
,
195 int (*func
) (struct inferior_list_entry
*, void *), void *arg
)
197 struct inferior_list_entry
*inf
= list
->head
;
201 if ((*func
) (inf
, arg
))
209 struct inferior_list_entry
*
210 find_inferior_id (struct inferior_list
*list
, unsigned long id
)
212 struct inferior_list_entry
*inf
= list
->head
;
225 inferior_target_data (struct thread_info
*inferior
)
227 return inferior
->target_data
;
231 set_inferior_target_data (struct thread_info
*inferior
, void *data
)
233 inferior
->target_data
= data
;
237 inferior_regcache_data (struct thread_info
*inferior
)
239 return inferior
->regcache_data
;
243 set_inferior_regcache_data (struct thread_info
*inferior
, void *data
)
245 inferior
->regcache_data
= data
;