Thread overview | |||||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
January 27, 2007 Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Hi, i just started to learn D (have been using c++ or java up to now) and am wondering how to implement some kind of timer, a thread that calls a delegate every n seconds. This was my first idea (without flags for stopping the timer etc): class Timer: Thread { int run() { while(true) { this.wait(1000); // wait one second writefln("one second passed"); } return 0; } } But writefln never gets executed, because this.wait is used to wait for other threads than the current one. Is there any other way to get let Thread sleep for some seconds (I know that there is a Sleep function for Win32, but a platform independend way would be very great). regards Dennis |
January 29, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Dennis Kempin | Dennis Kempin Wrote: > Hi, > > i just started to learn D (have been using c++ or java up to now) and am > wondering how to implement some kind of timer, a thread that calls a > delegate every n seconds. > This was my first idea (without flags for stopping the timer etc): > > class Timer: Thread > { > int run() > { > while(true) > { > this.wait(1000); // wait one second > writefln("one second passed"); > } > return 0; > } > } > > But writefln never gets executed, because this.wait is used to wait for other threads than the current one. Is there any other way to get let Thread sleep for some seconds (I know that there is a Sleep function for Win32, but a platform independend way would be very great). > > regards > Dennis You could insert a block of asm code. Look here http://www.digitalmars.com/d/iasm.html for valid opcodes. Here http://www.acm.uiuc.edu/sigmil/talks/shellcode/sleep.asm is an approach. This method is platform independant but not architecture independant, anyway, most computers processors are x86. Good luck. |
January 29, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Heinz | Heinz wrote:
> You could insert a block of asm code. Look here http://www.digitalmars.com/d/iasm.html for valid opcodes. Here http://www.acm.uiuc.edu/sigmil/talks/shellcode/sleep.asm is an approach.
>
> This method is platform independant but not architecture independant, anyway, most computers processors are x86.
>
> Good luck.
Hi Heinz,
thanks for your reply. I tried the following solution:
int timerFunction()
{
while(true)
{
writefln("a");
asm
{
xor EAX,EAX;
mov EBX,0x77e61bea;
mov AX,1000;
push EAX;
call EBX;
}
}
return 0;
}
but the result is a crash without any error message or warning. As the
comment of the asm code says "windows shellcode" i think it simply uses the
windows internel Sleep method. Still no way to make the thread go sleep in
linux.
Maybe I just should use linux/windows c API methods and insert a platform
fork. I will report here if i got a working solution.. Maybe I am not the
only one who needs timing.
regards
Dennis
|
January 29, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Heinz | okay here we go, i have a simple conditional compilation added to use windows Sleep or linux usleep function. Maybe someone has use for this simple class. You can decide if the timed event shall be called once or forever until the process/thread is terminated. I have not tested this in windows but it "should" work ;) regards Dennis import std.thread; version(Windows) { extern (C) { void Sleep(int); } } version(linux) { extern (C) { void usleep(int); } } class Timer: Thread { private void delegate() action; private int waitTime; private bit autoRestart; this(int waitTime, void delegate() action, bit autoRestart=false) { this.action = action; this.waitTime = waitTime; this.autoRestart = autoRestart; } protected this(int waitTime, bit autoRestart=false) { this.waitTime = waitTime; this.autoRestart = autoRestart; } override int run() { sleep(waitTime); execute(); while(autoRestart) { sleep(waitTime); execute(); } return 0; } void execute() { action(); } private void sleep(int time) { version(Windows) { Sleep(time); } version(linux) { usleep(time*1000); } } } |
January 29, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Dennis Kempin | Dennis Kempin wrote:
> Hi,
>
> i just started to learn D (have been using c++ or java up to now) and am
> wondering how to implement some kind of timer, a thread that calls a
> delegate every n seconds.
> This was my first idea (without flags for stopping the timer etc):
>
> class Timer: Thread
> {
> int run()
> {
> while(true)
> {
> this.wait(1000); // wait one second
> writefln("one second passed");
> }
> return 0;
> }
> }
>
> But writefln never gets executed, because this.wait is used to wait for
> other threads than the current one. Is there any other way to get let
> Thread sleep for some seconds (I know that there is a Sleep function for
> Win32, but a platform independend way would be very great).
>
> regards
> Dennis
I'd try something with Thread.yield and a time check.
Example (insert your favorite time API)
class Timer : Thread
{
run()
{
auto next = CurrentTime()+inc;
while(running)
{
auto now = CurrentTime();
if(now > next)
{
dg();
next += inc;
}
else
this.yield();
}
}
}
|
January 29, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Dennis Kempin | Dennis Kempin wrote:
> ...
> Maybe I just should use linux/windows c API methods and insert a platform
> fork. I will report here if i got a working solution.. Maybe I am not the
> only one who needs timing.
No, I suspect you're probably not the only one. Seems like most Thread apis I've seen have had some sort of Sleep() method. Not sure why Phobos' doesn't. Hopefully Tango will have a sleep().
--bb
|
January 30, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to BCS | On Mon, 29 Jan 2007 10:55:37 -0800, BCS <BCS@pathlink.com> wrote: >Dennis Kempin wrote: >> Hi, >> >> i just started to learn D (have been using c++ or java up to now) and am >> wondering how to implement some kind of timer, a thread that calls a >> delegate every n seconds. >> This was my first idea (without flags for stopping the timer etc): >> >> class Timer: Thread >> { >> int run() >> { >> while(true) >> { >> this.wait(1000); // wait one second >> writefln("one second passed"); >> } >> return 0; >> } >> } >> >> But writefln never gets executed, because this.wait is used to wait for other threads than the current one. Is there any other way to get let Thread sleep for some seconds (I know that there is a Sleep function for Win32, but a platform independend way would be very great). >> >> regards >> Dennis > >I'd try something with Thread.yield and a time check. > >Example (insert your favorite time API) > >class Timer : Thread >{ > run() > { > auto next = CurrentTime()+inc; > while(running) > { > auto now = CurrentTime(); > if(now > next) > { > dg(); > next += inc; > } > else > this.yield(); > } > } >} Be careful about Thread.yield under Windows. It calls Sleep(0) that won't yield to a thread of a lower priority. In case of the proposed timer this is not a problem except it will use 100% of CPU and won't let any lower priority thread run but if you use something like a spin lock waiting for a lower priority thread to release it, the lock will never be released. You could use Sleep(1) or SwitchToThread() on single processor systems. And you should use 'rep nop' for hyperthreaded CPUs. A platform independent way to put a thread to sleep using Phobos: import std.c.time; sleep(1);// secs msleep(1000); millisecs http://www.digitalmars.com/d/archives/digitalmars/D/29144.html |
January 30, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Bill Baxter | Bill Baxter wrote: > Dennis Kempin wrote: > > ... >> Maybe I just should use linux/windows c API methods and insert a platform >> fork. I will report here if i got a working solution.. Maybe I am not the >> only one who needs timing. > > No, I suspect you're probably not the only one. Seems like most Thread apis I've seen have had some sort of Sleep() method. Not sure why Phobos' doesn't. > Hopefully Tango will have a sleep(). It does. > > --bb |
January 30, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to Max Samukha | Max Samukha wrote: > On Mon, 29 Jan 2007 10:55:37 -0800, BCS <BCS@pathlink.com> wrote: > > >>Dennis Kempin wrote: >> >>>Hi, >>> >>>i just started to learn D (have been using c++ or java up to now) and am >>>wondering how to implement some kind of timer, a thread that calls a >>>delegate every n seconds. >>>This was my first idea (without flags for stopping the timer etc): >>> >>>class Timer: Thread >>>{ >>> int run() >>> { >>> while(true) >>> { >>> this.wait(1000); // wait one second >>> writefln("one second passed"); >>> } >>> return 0; >>> } >>>} >>> >>>But writefln never gets executed, because this.wait is used to wait for >>>other threads than the current one. Is there any other way to get let >>>Thread sleep for some seconds (I know that there is a Sleep function for >>>Win32, but a platform independend way would be very great). >>> >>>regards >>>Dennis >> >>I'd try something with Thread.yield and a time check. >> >>Example (insert your favorite time API) >> >>class Timer : Thread >>{ >> run() >> { >> auto next = CurrentTime()+inc; >> while(running) >> { >> auto now = CurrentTime(); >> if(now > next) >> { >> dg(); >> next += inc; >> } >> else >> this.yield(); >> } >> } >>} > > > Be careful about Thread.yield under Windows. It calls Sleep(0) that > won't yield to a thread of a lower priority. In case of the proposed > timer this is not a problem except it will use 100% of CPU and won't > let any lower priority thread run but if you use something like a spin > lock waiting for a lower priority thread to release it, the lock will > never be released. Ouch, I hadn't head of that. > You could use Sleep(1) or SwitchToThread() on > single processor systems. And you should use 'rep nop' for > hyperthreaded CPUs. > > A platform independent way to put a thread to sleep using Phobos: > import std.c.time; > > sleep(1);// secs > msleep(1000); millisecs > http://www.digitalmars.com/d/archives/digitalmars/D/29144.html > > However that gives the problem of not accounting for the run time of the threads "action". Not alwyas a problem, but... What is thread suposed to do to "kill time"? e.i. let other things run with out using up much CPU but keep poling the thread. while(NothingToDo()) thisThread.MarkTime(); |
January 30, 2007 Re: Implementing a timer using threads | ||||
---|---|---|---|---|
| ||||
Posted in reply to BCS | BCS wrote:
> Max Samukha wrote:
>> A platform independent way to put a thread to sleep using Phobos:
>> import std.c.time;
>>
>> sleep(1);// secs
>> msleep(1000); millisecs
>> http://www.digitalmars.com/d/archives/digitalmars/D/29144.html
>>
>>
>
> However that gives the problem of not accounting for the run time of the threads "action". Not alwyas a problem, but...
>
> What is thread suposed to do to "kill time"? e.i. let other things run with out using up much CPU but keep poling the thread.
>
> while(NothingToDo())
> thisThread.MarkTime();
Couldn't you just do something like:
-----
time_t nextEvent = currentTime() + interval;
time_t now;
while (true) {
while ((now = currentTime()) < nextEvent)
sleep(nextEvent - now); // or msleep, if you prefer
nextEvent += interval;
action();
}
-----
(where time_t is some type suitable for measuring time)
That should sleep until it's time, right?
|
Copyright © 1999-2021 by the D Language Foundation