yield_timeslice();
Frank Drebin

ok i got my server and client app working now but it seems they don't run parallel cause they both take up 100% cpu.
so i read in the docs that the awesome yield_timeslice(); functions gives other programs time to process or something like that (would be nice if someone could explain it to me)
i putted this function in my logic loop of both programs but it doesn't seem to change something.
so where to put this function and what does it do exactly?

Chris Katko

yield_tiemslice() gives up any extra cpu time to any other program that needs it. But if no other program does, it will still use 100% (*).

WIP 4.1.13 and later changed it though. (insert angry smiley)

Frank Drebin

k so this seems to me exactly what i need!
where to put it in my code (logic/non-logic-part) ?

ReyBrujo

Inside any of your cycles, either the main or the logic one.

Frank Drebin

i putted it after the logic_counter-- in my logic one.
no change.
don't want to use sleep instead of yield_timeslice() but if i put Sleep(1) here it works nearly perfectly.
btw: i use allegro 4.0.0

ReyBrujo

Those are two different things. A quick explanation first (I was told this at school 7 years ago, so I might be remembering this all wrong)...

The CPU works in quantums. A quantum is 1 second long (in fact, it is much, much smaller, say 5 microseconds, but 1 second will work for the example). The CPU gives one quantum to your program, then to another, then to another and continues until all have gotten a quantum.

Now, suppose your program needs to read from hd. It executes 0.5 seconds, and ask the hd to read something. Since hd accessing is much slower (suppose it needs 5 seconds), your program stops there. The other 9.5 seconds are lost because it is your quantum and your program is awaiting for the hd to answer. yield_timeslice will tell the CPU that the quantum is over, and so those 9.5 seconds will be given to another process. In fact is keeping the CPU busy.

Sleep, in the other hand, will stop the execution of your program for that amount of time. When the CPU gives you a quantum, you let the quantum pass, sleeping. Since nothing is being executed in the CPU, the load of the CPU lowers.

In other words, yield_timeslice will optimize your CPU usage. Sleep will give it more idling time.

Frank Drebin

alrighty that sounds nice to me but why doesn't it work for me?

ReyBrujo
/* sys_directx_yield_timeslice:
 *  Yields remaining timeslice portion to the system.
 */
static void sys_directx_yield_timeslice(void)
{
   Sleep(1);
}

Under Windows, it just calls Sleep... it should work...

Frank Drebin
Quote:

Under Windows, it just calls Sleep...

so it works just as fine as you explained on unix?

Quote:

it should work...

believe me yield_timesclice() has no effect but Sleep(1) does

Elias

As someone said, in the 4.0.x versions, yield_timeslice does Sleep(0) (which has no effect as far as this is concerned) and not Sleep(1), which only 4.1.14 does.

Cody Harris

I've found that rest(1) works well, because on unix, sleep(1) is actually one whole second.

ReyBrujo

Ah... that explains some... I took the code from 4.1.14. Microsoft said Sleep(0) is enough, but here we discovered that, under VB, you needed at least 5 to get it down. Explains why they are not similar.

(Edited: For unix systems, it uses select).

Cody Harris

Isn't select() for I/O Multiplexing?

(From Beej's Guide to Network Programming)

Frank Drebin

eeeh so in allegro 4.0.x yield_timslice() is the same as Sleep(0) and in later versions it is Sleep(1) so this is the thing for me to go?

ReyBrujo

Can be used too:

/* _unix_sysdrv_yield_timeslice:
 *  Yields remaining timeslice portion to the system
 */
void _unix_yield_timeslice(void)
{
  struct timeval timeout;
  timeout.tv_sec = 0;
  timeout.tv_usec = 1;
  select(0, NULL, NULL, NULL, &timeout);
}

Descriptor 0 is stdin. It waits for an input key for 1 millisecond.

Cody Harris

usec is microseconds, not miliseconds... It waits one microsecond for a key input.

There are 1,000 microseconds in a millisecond, and 1,000 milliseconds in a second. Thus, there are 1,000,000 microseconds in a second.

I would have never thought of doing it like that...

Frank Drebin

Frank Drebin said

Quote:

eeeh so in allegro 4.0.x yield_timslice() is the same as Sleep(0) and in later versions it is Sleep(1) so this is the thing for me to go?

just give me a yes if i am correct.

ReyBrujo

Yes.

orz

Generally, yield_timeslice() goes into your idle loop, if you have one. If you don't have an idle loop, instead sleep for 10 or 20 milliseconds after your rendering loop.

I (and lots of other people) have complained about yield_timeslice() not effecting the %cpu usage listed in the windows task manager. Perhaps the 4.1.14 change fixed that?

ReyBrujo

Under VB, in example, I need a Sleep of 5 at least to drop CPU usage. Neither 0 nor 1 works.

Chris Katko
Quote:

sleep(1) is actually one whole second.

Sleep is milliseconds. If it slept it seconds it wouldn't be very useful.

[edit] Added clicky, clarfication.

orz

Chris Katko: His statement was completely correct, though not entirely relevant. He was refering to the posix / iso / whatever standard function sleep() without the S capitalized, which takes an integer number of seconds to sleep for. Apparently some standards body thinks its useful.

Kitty Cat

If you want to reduce CPU usage, use rest(1) in your program. Under Windows and Linux, it'll do the same thing (give up the CPU for at least 1 millisecond). The function yield_timeslice has become a misnomer since it no longer does what its name implies, as well as changes the behavior of older programs. I don't think the fate of this function for 4.2 is, as of yet, known.

Frank Drebin

so Sleep(1) or rest(1) ? ? ?

ReyBrujo

As you wish. Check which works for you and use it.

orz

I believe that Sleep(1) is non-portable, so rest(1) would be the preferred method.

ReyBrujo

I think it is better if you work around the bug:

#if (ALLEGRO_SUB_VERSION < 1) && defined (ALLEGRO_WINDOWS)
    #define yield_timeslice() Sleep(1)
#endif

Kitty Cat

yield_timeslice should be calling Sleep(0), not Sleep(1). Either way though, calling rest(0) should have the same effect as the old, proper yield_timeslice, while rest(1) has the same effect as the current version.

Cody Harris

I've used rest(1) in my loops before, and i've had great sucess with it...

Frank Drebin

anyone knows a good tool to monitor cpu usage (of seperated threads) for win9x ?
would be nice so that i see if my program has lag cause of missing cpu performcane or cause of bad network code.
:-)
btw where are the smileys gone?

gnolam

For just total CPU usage you can use the system monitor.

As for the smileys, the King of the Potato People has taken them. You'll have to fly to him on a magic carpet and plead with him to get them back.

Thread #381961. Printed from Allegro.cc