Hint added.
[AROS.git] / workbench / c / TaskList.c
blob5f71ad4ee7f70c458f0bffabc3f0dabea14053d3
1 /*
2 Copyright © 1995-2016, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc:
6 Lang: english
7 */
9 /******************************************************************************
12 NAME
14 TaskList
16 SYNOPSIS
18 (N/A)
20 LOCATION
24 FUNCTION
26 Prints a list of all tasks.
28 INPUTS
30 RESULT
32 NOTES
34 EXAMPLE
36 BUGS
38 SEE ALSO
40 INTERNALS
42 HISTORY
44 ******************************************************************************/
46 int __nocommandline;
48 #include <exec/memory.h>
49 #include <exec/tasks.h>
50 #include <exec/execbase.h>
51 #include <proto/exec.h>
52 #include <proto/timer.h>
53 #include <aros/debug.h>
54 #include <devices/timer.h>
55 #include <dos/dosextens.h>
56 #include <proto/dos.h>
57 #include <proto/task.h>
59 #include <resources/task.h>
61 const TEXT version[] = "$VER: TaskList 42.1 (5.4.2016)\n";
63 APTR TaskResBase = NULL;
64 ULONG eclock;
66 struct task
68 CONST_STRPTR name;
69 APTR address;
70 WORD type;
71 WORD state;
72 IPTR stacksize;
73 IPTR stackused;
74 WORD pri;
75 struct timeval cputime;
78 static int addtask(struct Task *task, struct task **t, STRPTR *e)
80 STRPTR s1,s2;
81 struct TagItem QueryTaskTags[] =
83 {TaskTag_CPUTime , (IPTR)&(*t)->cputime },
84 {TAG_DONE , 0 }
87 QueryTaskTagList(task, QueryTaskTags);
89 (*t)->address = task;
90 (*t)->type = task->tc_Node.ln_Type;
91 (*t)->pri = (WORD)task->tc_Node.ln_Pri;
92 (*t)->state = task->tc_State;
93 (*t)->stacksize = (STRPTR)task->tc_SPUpper - (STRPTR)task->tc_SPLower;
94 #if AROS_STACK_GROWS_DOWNWARDS
95 (*t)->stackused = (STRPTR)task->tc_SPUpper - SP_OFFSET - (STRPTR)task->tc_SPReg;
96 #else
97 (*t)->stackused = (STRPTR)task->tc_SPReg - SP_OFFSET - (STRPTR)task->tc_SPLower;
98 #endif
99 if (task->tc_State == TS_RUN)
101 /* The tc_SPReg for the actual process is invalid
102 if it had no context switch yet */
103 (*t)->stackused = 0;
105 s1 = task->tc_Node.ln_Name;
106 if (task->tc_Node.ln_Type == NT_PROCESS && ((struct Process *)task)->pr_CLI)
108 /* TODO: Use cli_CommandName field for the name */
109 (*t)->type = -1;
111 if (s1 != NULL)
113 s2 = s1;
115 while (*s2++)
118 while (s2 > s1)
120 if (*e<=(STRPTR)*t)
121 return 0;
122 *--(*e)=*--s2;
125 if ((STRPTR)(*t + 1) > *e)
126 return 0;
128 (*t)->name = *e;
129 ++*t;
131 return 1;
134 static int fillbuffer(struct task **buffer, IPTR size)
136 STRPTR end = (STRPTR)*buffer + size;
137 struct Task *task;
139 #if !defined(__AROS__)
140 Disable();
142 if (!addtask(FindTask(NULL), buffer, &end))
144 Enable();
145 return 0;
147 for (task = (struct Task *)SysBase->TaskReady.lh_Head;
148 task->tc_Node.ln_Succ != NULL;
149 task = (struct Task *)task->tc_Node.ln_Succ)
151 if (!addtask(task, buffer, &end))
153 Enable();
154 return 0;
157 for (task = (struct Task *)SysBase->TaskWait.lh_Head;
158 task->tc_Node.ln_Succ != NULL;
159 task = (struct Task *)task->tc_Node.ln_Succ)
161 if (!addtask(task, buffer, &end))
163 Enable();
164 return 0;
167 Enable();
168 #else
169 struct TaskList *taskList;
171 taskList = LockTaskList(0);
172 while ((task = NextTaskEntry(taskList, 0)) != NULL)
174 if (!addtask(task, buffer, &end))
176 break;
179 UnLockTaskList(0);
180 #endif
182 return 1;
185 int main(void)
187 IPTR size;
188 struct task *buffer,*tasks,*tasks2;
190 TaskResBase = OpenResource("task.resource");
191 if (!TaskResBase) {
192 PutStr("Can't open task.resource\n");
193 return RETURN_FAIL;
196 for(size = 2048; ; size += 2048)
198 buffer = AllocVec(size, MEMF_ANY);
199 if (buffer == NULL)
201 PutStr("Not enough memory for task buffer\n");
202 return RETURN_FAIL;
204 tasks = buffer;
205 if (fillbuffer(&tasks, size))
207 PutStr("Address\t\tType\tPri\tState\tCPU Time\tStack\tUsed\tName\n");
208 for (tasks2 = buffer; tasks2 < tasks; tasks2++)
210 ULONG time;
212 time = tasks2->cputime.tv_secs;
213 Printf("0x%08.ix\t%s\t%ld\t%s\t%02ld:%02ld:%02ld\t%id\t%id\t%s\n",
214 tasks2->address,
215 (tasks2->type == NT_TASK) ? "task" :
216 (tasks2->type == NT_PROCESS) ? "process" : "CLI",
217 (ULONG)tasks2->pri,
218 (tasks2->state == TS_RUN) ? "running" :
219 (tasks2->state == TS_READY) ? "ready" : "waiting",
220 time % 60, (time / 60) % 60, (time / 60 / 60) % 60,
221 tasks2->stacksize, tasks2->stackused,
222 (tasks2->name != NULL) ? tasks2->name : (CONST_STRPTR)"(null)");
225 FreeVec(buffer);
226 return RETURN_OK;
228 FreeVec(buffer);
230 return RETURN_OK;