use GET_THIS_TASK internally throughout exec - since it will result in faster/smaller...
[AROS.git] / rom / exec / findtask.c
blob5956f60540a281ac771de5969de91e662f54b7c9
1 /*
2 Copyright © 1995-2015, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc: Search a task by name.
6 Lang: english
7 */
8 #include <exec/execbase.h>
9 #include <aros/libcall.h>
10 #include <proto/exec.h>
12 #include "exec_intern.h"
14 /*****************************************************************************
16 NAME */
18 AROS_LH1(struct Task *, FindTask,
20 /* SYNOPSIS */
21 AROS_LHA(CONST_STRPTR, name, A1),
23 /* LOCATION */
24 struct ExecBase *, SysBase, 49, Exec)
26 /* FUNCTION
27 Find a task with a given name or get the address of the current task.
28 Finding the address of the current task is a very quick function
29 call, but finding a special task is a very CPU intensive instruction.
30 Note that generally a task may already be gone when this function
31 returns.
33 INPUTS
34 name - Pointer to name or NULL for current task.
36 RESULT
37 Address of task structure found.
39 NOTES
41 EXAMPLE
43 BUGS
45 SEE ALSO
47 INTERNALS
49 ******************************************************************************/
51 AROS_LIBFUNC_INIT
53 #if defined(__AROSEXEC_SMP__)
54 spinlock_t *listLock;
55 #endif
56 struct Task *ret;
58 /* Quick return for a quick argument */
59 if (name == NULL)
60 return GET_THIS_TASK;
62 /* Always protect task lists */
63 #if defined(__AROSEXEC_SMP__)
64 listLock = EXEC_SPINLOCK_LOCK(&PrivExecBase(SysBase)->TaskRunningSpinLock, SPINLOCK_MODE_READ);
65 Forbid();
66 /* Then into the waiting list. */
67 ret = (struct Task *)FindName(&PrivExecBase(SysBase)->TaskRunning, name);
68 if (ret == NULL)
70 EXEC_SPINLOCK_UNLOCK(listLock);
71 Permit();
72 listLock = EXEC_SPINLOCK_LOCK(&PrivExecBase(SysBase)->TaskReadySpinLock, SPINLOCK_MODE_READ);
73 Forbid();
74 #else
75 Disable();
76 #endif
78 /* First look into the ready list. */
79 ret = (struct Task *)FindName(&SysBase->TaskReady, name);
80 if (ret == NULL)
82 #if defined(__AROSEXEC_SMP__)
83 EXEC_SPINLOCK_UNLOCK(listLock);
84 Permit();
85 listLock = EXEC_SPINLOCK_LOCK(&PrivExecBase(SysBase)->TaskWaitSpinLock, SPINLOCK_MODE_READ);
86 Forbid();
87 #endif
88 /* Then into the waiting list. */
89 ret = (struct Task *)FindName(&SysBase->TaskWait, name);
90 if (ret == NULL)
93 Finally test the running task(s). Note that generally
94 you know the name of your own task - so it is close
95 to nonsense to look for it this way.
97 char *s1;
98 const char *s2 = name;
100 #if defined(__AROSEXEC_SMP__)
101 EXEC_SPINLOCK_UNLOCK(listLock);
102 Permit();
103 listLock = EXEC_SPINLOCK_LOCK(&PrivExecBase(SysBase)->TaskRunningSpinLock, SPINLOCK_MODE_READ);
104 Forbid();
105 ForeachNode(&PrivExecBase(SysBase)->TaskRunning, ret)
107 s1 = ret->tc_Node.ln_Name;
108 #else
109 s1 = GET_THIS_TASK->tc_Node.ln_Name;
110 #endif
111 /* Check as long as the names are identical. */
112 while (*s1++ == *s2)
113 /* Terminator found? */
114 if (!*s2++)
116 /* Got it. */
117 #if defined(__AROSEXEC_SMP__)
118 #else
119 ret = GET_THIS_TASK;
120 #endif
121 break;
123 #if defined(__AROSEXEC_SMP__)
125 #endif
129 #if defined(__AROSEXEC_SMP__)
131 EXEC_SPINLOCK_UNLOCK(listLock);
132 Permit();
133 #else
134 Enable();
135 #endif
137 /* Return whatever was found. */
138 return ret;
140 AROS_LIBFUNC_EXIT
141 } /* FindTask */