echarne@orion.cf.uci.edu (Eli B. Charne) (11/02/88)
I am writing a program, in which part of it does a fancy little display for the user. However, in order for the user to be able to see it, I need a delay. The Unix sleep command will only go in increments of one second. I was wondering if someone new of a nice little routine I could use, or has written one that will let me pause (in the Unix operating system) for a fraction of a second. If it could go to 100th of a second, that would be great! Thanks -Eli zecharne@uci.bitnet echarne@orion.cf.uci.edu
crossgl@ingr.UUCP (Gordon Cross) (11/02/88)
In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: > > The Unix sleep command will only go in increments of one second. I was > wondering if someone new of a nice little routine I could use, or has > written one that will let me pause (in the Unix operating system) for > a fraction of a second. If it could go to 100th of a second, that would > be great! You are not going to be able to do this without coding up some kind of "delay loop" yourself. Of course that solution is definitely NOT portable in any way since the loop would have to be fine tuned to your machines execution speed. Remember that in the UNIX kernal, scheduled wakeups occur at fixed one second intervals. Thus, unless you are using a non standard kernal, sleeps of only whole numbers of seconds are possible! Gordon Cross Intergraph Corp. Huntsville, AL
gckaplan@soup.ssl.berkeley.edu (George Kaplan) (11/04/88)
In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: > > The Unix sleep command will only go in increments of one second. I was > wondering if someone new of a nice little routine I could use, or has > written one that will let me pause (in the Unix operating system) for > a fraction of a second. If it could go to 100th of a second, that would > be great! On a Sun (and presumably under bsd 4.x as well) there's a usleep() function to sleep for a specified number of microseconds: void usleep(useconds) unsigned useconds; This actually pauses for _at least_ the specified number of useconds. The actual delay may be longer depending on other activity in the system. - George C. Kaplan gkaplan@sag4.ssl.berkeley.edu
henry@utzoo.uucp (Henry Spencer) (11/04/88)
In article <1145@orion.cf.uci.edu> echarne@orion.cf.uci.edu (Eli B. Charne) writes: >The Unix sleep command will only go in increments of one second. I was >wondering if someone new of a nice little routine I could use, or has >written one that will let me pause (in the Unix operating system) for >a fraction of a second. If it could go to 100th of a second, that would >be great! You are basically out of luck. There is no standard, portable way of doing this. Some Unix systems provide a primitive, sometimes named "nap", for doing it; some don't. Even those that do provide it tend to disagree on what units it works in. -- The Earth is our mother. | Henry Spencer at U of Toronto Zoology Our nine months are up. |uunet!attcan!utzoo!henry henry@zoo.toronto.edu
davidsen@steinmetz.ge.com (William E. Davidsen Jr) (11/04/88)
There is a system call "nap" in Xenix, which is in ms. My notes on V.4 indicate that it will be there as well. Probably in two years that feature will have propigated, but in the mean time you are out of luck as to a portable way to do it. Even if you have the feature it is granular to the nearest clock tick. -- bill davidsen (wedu@ge-crd.arpa) {uunet | philabs}!steinmetz!crdos1!davidsen "Stupidity, like virtue, is its own reward" -me
djones@megatest.UUCP (Dave Jones) (11/04/88)
From article <2804@ingr.UUCP>, by crossgl@ingr.UUCP (Gordon Cross): > In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: >> >> The Unix sleep command will only go in increments of one second. I was >> wondering if someone new of a nice little routine I could use, or has >> written one that will let me pause (in the Unix operating system) for >> a fraction of a second. If it could go to 100th of a second, that would >> be great! > > You are not going to be able to do this without coding up some kind of > "delay loop" yourself. Of course that solution is definitely NOT portable in > any way since the loop would have to be fine tuned to your machines execution > speed. Remember that in the UNIX kernal, scheduled wakeups occur at fixed > one second intervals. Thus, unless you are using a non standard kernal, sleeps > of only whole numbers of seconds are possible! > > > Gordon Cross > Intergraph Corp. Huntsville, AL Mr. Cross, perhaps it is time that *you* should wake up. You are dreaming up answers. :-) Pour yourself a cup of strong coffee, then try the following: #include <sys/time.h> delay(seconds, micro_seconds) long seconds; long micro_seconds; { struct timeval timev; timev.tv_sec = seconds; timev.tv_usec = micro_seconds; select(0,0,0,0, &timev); } Some unixes may name the include-file <time.h> and the structure "struct time_val", but it comes to the same thing. Read the man-pages on select(), setitimer(), and signal(). Also, please don't code tight spin-loops for delays or for polling. Particularly if you are on a time-shared system. Best regards, Dave J.
jas@ernie.Berkeley.EDU (Jim Shankland) (11/04/88)
In article <2804@ingr.UUCP> crossgl@ingr.UUCP (Gordon Cross) writes: >You are not going to be able to do [sub-second sleeps] without coding >up some kind of "delay loop" yourself.... >Remember that in the UNIX kernal, scheduled wakeups occur at fixed >one second intervals. Thus, unless you are using a non standard kernal, sleeps >of only whole numbers of seconds are possible! Never trust statements about the UNIX kernel from people who can't even spell the word. Kernel timeouts can occur at 1/HZ second intervals, where HZ is typically 60 or 100. The kernel CAN provide a system call to let processes set alarms at that granularity -- BSD and derivatives do (setitimer). SysV-flavored systems just don't bother. (Or is this fixed in SysVR3?) ----- Jim Shankland jas@ernie.berkeley.edu "The God I believe in isn't short of cash, MISTER!"
gpasq@picuxa.UUCP (Greg Pasquariello X1190) (11/04/88)
In article <2804@ingr.UUCP> crossgl@ingr.UUCP (Gordon Cross) writes: >In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: >> >> The Unix sleep command will only go in increments of one second. >> let me pause (in the Unix operating system) for a fraction of a second. > >You are not going to be able to do this without coding up some kind of >"delay loop" yourself. >Gordon Cross Although kludgy, you could do a read with timeout on some file descriptor as- sociated with a tty. See the man pages on read(1) and termio(7). ========================================================================== -- ========================================================================= "I crush your head!" Greg Pasquariello AT&T PMTC att!picuxa!gpasq Parsippany, NJ =========================================================================
gpasq@picuxa.UUCP (Greg Pasquariello X1190) (11/04/88)
In article <965@goofy.megatest.UUCP> djones@megatest.UUCP (Dave Jones) writes: >From article <2804@ingr.UUCP>, by crossgl@ingr.UUCP (Gordon Cross): >> >> You are not going to be able to do this without coding up some kind of >> "delay loop" yourself. > >Mr. Cross, perhaps it is time that *you* should wake up. >You are dreaming up answers. :-) Here the select() call is mentioned.... > > Dave J. Select is not available up to (at least) SVR3. It may be in R4, but I don't know for sure. -- ========================================================================= "I crush your head!" Greg Pasquariello AT&T PMTC att!picuxa!gpasq Parsippany, NJ =========================================================================
gee@dretor.dciem.dnd.ca (Tom Gee see wdf) (11/04/88)
>In <28247@utzoo.uucp> henry@utzoo.uucp (Henry Spencer) write: >>In <1145@orion.cf.uci.edu> echarne@orion.cf.uci.edu (Eli B. Charne) writes: >>The Unix sleep command will only go in increments of one second. I was >>wondering if someone new of a nice little routine I could use, or has >>written one that will let me pause (in the Unix operating system) for >>a fraction of a second. >You are basically out of luck. There is no standard, portable way of >doing this. Some Unix systems provide a primitive, sometimes named >"nap", for doing it; some don't. Even those that do provide it tend to >disagree on what units it works in. About two weeks ago, a version of nap() for System V.3 was posted to the net ( I think it was comp.sources.unix ). It is a device driver and interface written by zeff@b-tech. If anyone wants a copy, send me a message and I'll mail it to you. _________ "If you know what a bubble sort is, | Thomas Gee wipe it from your mind" | Aerospace Group -- Numerical Methods in C. | DCIEM | Department of National Defence {watmath,utzoo}!dciem!zorac!dretor!gee
colburn@src.honeywell.COM (Mark H. Colburn) (11/05/88)
In article <2804@ingr.UUCP> crossgl@ingr.UUCP (Gordon Cross) writes: >In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: #> The Unix sleep command will only go in increments of one second. I was #> wondering if someone new of a nice little routine I could use, or has #> written one that will let me pause (in the Unix operating system) for #> a fraction of a second. #> be great! #You are not going to be able to do this without coding up some kind of #"delay loop" yourself. Actually, under System V you can use the VMIN timer on the tty driver, which will give you granularity of about 1/10 of a second. As long as your are going to be doing terminal oriented work, this is fairly easy. This does not work on most BSD systems, although there you have higher granularity sleeps anyways...
guy@auspex.UUCP (Guy Harris) (11/05/88)
>Pour yourself a cup of strong coffee, then try the following:
And watch it fail to compile on many systems.
Unfortunately, neither "select" nor "setitimer" exist on all UNIX
systems. (They also tend not to exist on non-UNIX systems, which is why
this discussion is getting sent back to comp.unix.questions, where it
belongs.)
However, you can use "poll" instead of "select" on System V Release 3,
so at least there you can block for an amount of time < 1 second
(although there still isn't a way to get a signal delivered after an
interval of < 1 second in vanilla S5R3).
mkhaw@teknowledge-vaxc.ARPA (Mike Khaw) (11/05/88)
> On a Sun (and presumably under bsd 4.x as well) there's a usleep() > function to sleep for a specified number of microseconds: It's implemented using setitimer(2), so if you have the latter but not usleep(3), you should be able to invent your own. Mike Khaw -- internet: mkhaw@teknowledge.arpa uucp: {uunet|sun|ucbvax|decwrl|ames|hplabs}!mkhaw%teknowledge.arpa hardcopy: Teknowledge Inc, 1850 Embarcadero Rd, POB 10119, Palo Alto, CA 94303
billd@celerity.UUCP (Bill Davidson) (11/05/88)
In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: > > The Unix sleep command will only go in increments of one second. I was > wondering if someone new of a nice little routine I could use, or has > written one that will let me pause (in the Unix operating system) for > a fraction of a second. If it could go to 100th of a second, that would > be great! This is a function I wrote almost 2 years ago. (It comes back to haunt me now and then). It works on Celerity 1200, 1230, 1260D and the new FPS Model 500 and should be relatively portable to BSD systems. I was kind of new at using signals when I wrote it, so it could probably be improved a bit. I really don't want to spend any time thinking about it. This is, of course, not guaranteed to do anything useful. It's not even guaranteed to not trash your system (although I can't imagine how it could :-). Every architecture is going to generate timer interrupts at different intervals. Also, there's no guarantee that you'll get the right amount of time even given the correct intervals because in UNIX, you may be waiting to get swapped in. I should probably test it on our VAX but I'm too lazy. ------------------------------ cut here ---------------------------------- /******************************************************************************* * * FSLEEP.C - Fine sleep. This function allows you to sleep for * smaller intervals of time than 1 second. * * SYNOPISIS * void fsleep( secs, usecs ) * long secs, usecs; * * secs is the number of seconds. * usecs is the number of milleseconds. * * LIBRARY FUNCTIONS * setitimer(2) * signal(3C) * sigsetmask(2) * sigpause(2) * * The number of milliseconds is misleading. It is limited by the * resolution of the actual timers which is 10 milleseconds on an * Accel. * * Note that the manual page incorrectly identifies the timer * intervals as being setable to microseconds. It really meant * milleseconds (either that, or whoever set up setitimer on our * machine made a mistake). When I first tried it (naively * believing the manual) I used 500000 for usecs thinking it * would be half a second instead of 500 seconds which is what * it was. * *******************************************************************************/ #include <stdio.h> #include <time.h> #include <signal.h> #define valsec it_value.tv_sec #define valusec it_value.tv_usec #define intsec it_interval.tv_sec #define intusec it_interval.tv_usec static void fsleeptrap() { /* Zen function */ } void fsleep( secs, usecs ) unsigned long secs, usecs; { int omask, (*osig)(); struct itimerval tval[2]; osig = signal( SIGALRM, fsleeptrap ); /* set the trap */ if ( usecs >= 1000L ){ /* fix the interval */ secs += usecs / 1000L; usecs %= 1000L; } tval[1].intsec = tval[1].intusec = 0L; tval[1].valsec = secs; tval[1].valusec = usecs; omask = sigsetmask( ( 1 << (SIGALRM-1) ) ); setitimer( 0, &tval[1], &tval[0] ); sigpause( 0 ); /* wait for the timer */ signal( SIGALRM, osig ); /* reset the old trap */ setitimer( 0, &tval[0], &tval[1] ); sigsetmask( omask ); return; } ------------------------------ cut here -------------------------------- Ever notice how much more you enjoy sleeping as you get older? Bill Davidson .....!ucsd!celerity!billd
daveb@gonzo.UUCP (Dave Brower) (11/05/88)
In article <2804@ingr.UUCP> crossgl@ingr.UUCP (Gordon Cross) writes: >In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: >> >> The Unix sleep command will only go in increments of one second. I was >> wondering if someone new of a nice little routine I could use, or has >> written one that will let me pause (in the Unix operating system) for >> a fraction of a second. If it could go to 100th of a second, that would >> be great! > >You are not going to be able to do this without coding up some kind of >"delay loop" yourself... Unless you are: * on a BSD machine, with setitimer() * on most any machine with select(), where you can do a sub-second timeout value. * on a V.3 machine with poll(), which _i think_ has a sub-second timeout value. (I'm sure I'll be corrected if wrong :-) -dB
robert@pvab.UUCP (Robert Claeson) (11/06/88)
In article <12514@steinmetz.ge.com>, davidsen@steinmetz.ge.com (William E. Davidsen Jr) writes: > There is a system call "nap" in Xenix, which is in ms. My notes on V.4 > indicate that it will be there as well. In fact, the nap() system call is there in System V, Release 3.2.-- Robert Claeson, ERBE DATA AB, P.O. Box 77, S-175 22 Jarfalla, Sweden Tel: +46 758-202 50 Fax: +46 758-197 20 EUnet: rclaeson@erbe.se ARPAnet: rclaeson%erbe.se@uunet.uu.net
mikef@wyn386.UUCP (Mike Faber) (11/07/88)
If you wanted to be fancy (and don't need type ahead) you could flush the stdin buffer, set term.c_iflag(?) &= ~ICANON, and term.c_cc[VTIME] = (# of tenths you wanted tyo wait), and read from stdin (getchar()).. But only if you didn;t need the type ahead... IF all else fails, follow plumbers rule #1: If it dont fit, force it. If it cbreaks(), it didn't belong there in the first place... Or something like that... -- _ _ | My employer and sysop do not think, (/ (/ _ _ _ _ | so they cannot share my opinions. (/) /\_(/_(/_/|_)_/ \_/ | Joe C Programmer (mikef@wynalda.uucp) work (| (| | Michael Faber (sleepy@wybbs.uucp) play
billd@celerity.UUCP (Bill Davidson) (11/08/88)
Well, it seems that I have to flame myself: In article <191@celerity.UUCP> billd@celerity.UUCP (Bill Davidson) writes: >In article <1145@orion.cf.uci.edu>, echarne@orion.cf.uci.edu (Eli B. Charne) writes: >> ..... >> a fraction of a second. If it could go to 100th of a second, that would >> be great! > ..... >given the correct intervals because in UNIX, you may be waiting to get >swapped in. I should probably test it on our VAX but I'm too lazy. >* FSLEEP.C - Fine sleep. This function allows you to sleep for >* smaller intervals of time than 1 second. ..... >* Note that the manual page incorrectly identifies the timer >* intervals as being setable to microseconds. It really meant >* milleseconds (either that, or whoever set up setitimer on our >* machine made a mistake). When I first tried it (naively >* believing the manual) I used 500000 for usecs thinking it >* would be half a second instead of 500 seconds which is what >* it was. A kernel type engineer here informed me that this was fixed a LONG time ago and that it now works in microseconds on our machine. Of course, this means that my program is wrong as well. This is the part that needs to be changed: > if ( usecs >= 1000L ){ /* fix the interval */ > secs += usecs / 1000L; > usecs %= 1000L; > } All of the 1000L's should be changed to 1000000L's to reflect the microseconds. I should have assumed that other people's setitimer's worked correctly when I posted anyway. If anyone picked up my code, then they should make this change and it *should* work (but as I said before, I don't personally guarantee anything). I suppose this really belongs in comp.unix.questions but this is where the previous things were posted. There doesn't seem to be *any* portable way to write a delay function with delays < 1 second. On UNIX, ANY delay function is going to have an accuracy problem. Setitimer could have a smallest interval of 1/100 sec and there would probably be no functional difference. As long as I flaming myself, I'll also flame the guy who suggested spinning delay loops: ACK! GAG! BARF! :-( --Bill Davidson -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ....!{ucsd|sdcsvax}!celerity!billd
friedl@vsi.COM (Stephen J. Friedl) (11/08/88)
William E. Davidsen Jr. writes: > There is a system call "nap" in Xenix, which is in ms. My notes on V.4 > indicate that it will be there as well. Robert Claeson writes: > In fact, the nap() system call is there in System V, Release 3.2.-- Hmmm. Dollars to donuts that System V Release 3.2 provides nap() only on the 80286 and 80386 processors; I find it unlikely that 3B2 will have the Xenix migration code. In any case, none of the AT&T 3B2 C compilers currently shipping include nap() in the C libraries. Steve -- Steve Friedl V-Systems, Inc. +1 714 545 6442 3B2-kind-of-guy friedl@vsi.com {backbones}!vsi.com!friedl attmail!vsi!friedl ------------Nancy Reagan on the worm: "Just say OH NO!"------------
crossgl@ingr.UUCP (Gordon Cross) (11/09/88)
In article <26678@ucbvax.BERKELEY.EDU>, jas@ernie.Berkeley.EDU (Jim Shankland) writes: > > Never trust statements about the UNIX kernel from people who can't even > spell the word. Every so often this sort of thing pops up: people abusing other people about spelling errors. This often (once started) gets out of hand as everyone begins "flaming" other's spelling and/or punctuation errors swamping the net with meaningless dribble. So please if you wish to correct someone on a spelling error, how about e-mail... Now down to business... In a previous article I wrote the following in response to a question regarding how to sleep for a period of time less than one second in C: > > You are not going to be able to do this without coding up some kind of > "delay loop" yourself. Of course that solution is definitely NOT portable in > any way since the loop would have to be fine tuned to your machines execution > speed. Remember that in the UNIX kernel, scheduled wakeups occur at fixed > one second intervals. Thus, unless you are using a non standard kernel, > sleeps of only whole numbers of seconds are possible! I have of course been catching some heat (from the flames :-)) regarding this response. And I must say it is well deserved! In my attempt to keep the answer as short as possible, I oversimplified the problem. I also neglected to mention that I would not actually RECOMMEND a "delay loop" since other approaches (ie. NOT requiring sleeps of less than one second) are almost always available. Several responses to this question mentioned other methods whereby this could be accomplished. Each of these solutions rely on mechanisms (such as BSD's sockets) not available on all UNIX implementations. I was just attempting to come up with a method that would be workable (if you absolutly just HAD to have sub-second waits) on any implementation. Sorry about the confusion! Gordon Cross Intergraph Corp. Huntsville, AL