How to know if scheduler has started?

classic Classic list List threaded Threaded
3 messages Options
Reply | Threaded
Open this post in threaded view
|

How to know if scheduler has started?

Grant Edwards-6
This question has come up many times in the past 10-12 years, but I've
never seen a real answer:

How do you tell if the scheduler has been started?

Specifically, how do you know when it's safe to attempt to lock a mutex?

Several people have suggested this snippet:

 scheduler_running = cyg_thread_self() != cyg_thread_idle_thread();

That seems to work when called from cyg_user_start() and from normal
threads, but it doesn't work when called from initialization code in
a device driver.

So, I'll ask again:

how does one write code that knows to lock/unlock a mutex when called
from a normal user thread but not attempt the lock/unlock whcn called
from initialization code in cyg_user_start() or a device driver?

The function does not get called from ISR/DSR contexts: it is only
called during initialization (before the scheduler is started) and
from normal user threads.

OTOH, are you are allowed to lock/unlock mutexes from initialization
code?  Maybe I'm misremembering, but I thought that was forbidden?

--
Grant Edwards               grant.b.edwards        Yow! I was born in a
                                  at               Hostess Cupcake factory
                              gmail.com            before the sexual
                                                   revolution!


--
Before posting, please read the FAQ: http://ecos.sourceware.org/fom/ecos
and search the list archive: http://ecos.sourceware.org/ml/ecos-discuss

Reply | Threaded
Open this post in threaded view
|

Re: How to know if scheduler has started?

Nick Garnett-2


On 31/10/13 16:24, Grant Edwards wrote:

> This question has come up many times in the past 10-12 years, but I've
> never seen a real answer:
>
> How do you tell if the scheduler has been started?
>
> Specifically, how do you know when it's safe to attempt to lock a mutex?
>
> Several people have suggested this snippet:
>
>  scheduler_running = cyg_thread_self() != cyg_thread_idle_thread();
>
> That seems to work when called from cyg_user_start() and from normal
> threads, but it doesn't work when called from initialization code in
> a device driver.
>
> So, I'll ask again:
>
> how does one write code that knows to lock/unlock a mutex when called
> from a normal user thread but not attempt the lock/unlock whcn called
> from initialization code in cyg_user_start() or a device driver?
>
> The function does not get called from ISR/DSR contexts: it is only
> called during initialization (before the scheduler is started) and
> from normal user threads.
>
> OTOH, are you are allowed to lock/unlock mutexes from initialization
> code?  Maybe I'm misremembering, but I thought that was forbidden?
>

You are allowed to lock/unlock a mutex during initialization. That is
why the idle thread is set current throughout the init code, and why the
trick you mention above will work.

Obviously you need to avoid anything that might cause a thread to sleep,
and to leave any mutexes unlocked when you return.



--
Nick Garnett                                         Kernel Architect
eCosCentric Limited    http://www.eCosCentric.com    The eCos experts
Barnwell House, Barnwell Drive, Cambridge, UK.   Tel: +44 1223 245571
Registered in England and Wales:                      Reg No: 4422071

--
Before posting, please read the FAQ: http://ecos.sourceware.org/fom/ecos
and search the list archive: http://ecos.sourceware.org/ml/ecos-discuss

Reply | Threaded
Open this post in threaded view
|

Re: How to know if scheduler has started?

Grant Edwards-6
On 2013-11-01, Nick Garnett <[hidden email]> wrote:
>
>> OTOH, are you are allowed to lock/unlock mutexes from initialization
>> code?  Maybe I'm misremembering, but I thought that was forbidden?
>
> You are allowed to lock/unlock a mutex during initialization. That is
> why the idle thread is set current throughout the init code, and why the
> trick you mention above will work.

Except the trick I mentioned above does _not_ work when called from
device driver intialization code.  I haven't tracked down which of the
two calls fails in that case, but one of them causes a segfault when
called from driver init code (but works fine when called from
cyg_user_start()).

--
Grant


--
Before posting, please read the FAQ: http://ecos.sourceware.org/fom/ecos
and search the list archive: http://ecos.sourceware.org/ml/ecos-discuss