CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Page 1 of 3 123 LastLast
Results 1 to 15 of 33

Hybrid View

  1. #1
    Join Date
    Dec 2006
    Posts
    60

    while loop w/ sleep(1) doesnt work

    I am writing a software that periodically checks for CAN messages through calls to the driver libraries. And I must perform actions depending on the CAN messages I see.

    At first I used a system timer and function call in response to the windows message WM_TIMER.
    (i.e. SetTimer(1,10,NULL) and OnTimer() function where the processing of the messages occur.)

    But that solution has proven to be too slow, and I need a faster loop. So I though to use a while loop with a sleep of 1ms so as not to lock up the cpu. However, I've read that the sleep interval can only be as low as 15ms, and anything below that will sleep for 15ms.

    How can I create a faster loop without using all cpu resources?

  2. #2
    Join Date
    Nov 2003
    Posts
    1,902

    Re: while loop w/ sleep(1) doesnt work

    The best option would be to not poll at all, but instead be notified when an event occurs. If that isn't an option, then you have to poll.

    Do you really need to poll the driver more than once every 15ms? Why?

    What "driver libraries" are you referring to?

    gg

  3. #3
    Join Date
    Dec 2006
    Posts
    60

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by Codeplug View Post
    The best option would be to not poll at all, but instead be notified when an event occurs. If that isn't an option, then you have to poll.

    Do you really need to poll the driver more than once every 15ms? Why?

    What "driver libraries" are you referring to?

    gg
    I am using Kvaser and vectorCAN, which requires polling.

    And yes I do need a loop thats faster than 15ms. I am implementing a communication algorithm with handshaking. So i send a command, get its response, and send next command, get another response. All of this must occure sequentially. The response is much much faster than the polling on the PC side, so the PC side is my weakest link in the speed of this procedure. At the speed that I am polling and sending commands now, I am only using 4% of the CAN bus load, and I have plenty of space to put more messages on the bus. I just don't know how to speed it up on the PC side.

  4. #4
    VictorN's Avatar
    VictorN is offline Super Moderator Power Poster
    Join Date
    Jan 2003
    Location
    Hanover Germany
    Posts
    20,396

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by acerunner316 View Post
    ...
    How can I create a faster loop without using all cpu resources?
    I don't know what you mean by "without using all cpu resources", however, you could try Multimedia Timer
    Victor Nijegorodov

  5. #5
    Join Date
    Dec 2006
    Posts
    60

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by VictorN View Post
    I don't know what you mean by "without using all cpu resources", however, you could try Multimedia Timer
    what I mean is that I can't use ONLY a while loop without a pause inside of it. It is my understanding that that will comsume all cpu time.

  6. #6
    Join Date
    Nov 2003
    Posts
    1,902

    Re: while loop w/ sleep(1) doesnt work

    So I see the Kvaser products can be used with their CANlib SDK. Is that what you're using?

    Are their blocking API's you can use - instead of polling?

    gg

  7. #7
    Lindley is offline Elite Member Power Poster
    Join Date
    Oct 2007
    Location
    Seattle, WA
    Posts
    10,895

    Re: while loop w/ sleep(1) doesnt work

    The key to avoiding the "15ms" thing is to *not* make any call which would cause the OS to timeslice over to other running processes (or even check for them). In other words, you need a pause() function which remains strictly in user mode for the duration rather than entering kernel mode. Unfortunately, I'm not aware of a standard function which does this; the suggestion above to use blocking functions (possibly with timeouts if you need to detect failure) is probably the best.

    EDIT: A quick Google later, I found this:
    http://www.kvaser.com/index.htm

    Looks like canReadWait() is what you want.

  8. #8
    Join Date
    Dec 2006
    Posts
    60

    Re: while loop w/ sleep(1) doesnt work

    yes I am using the CANlib SDK. That is the only solution kvaser provides to communicate with their devices. I am not sure what you mean by "blocking API".

    In CANlib, the function to get a message is canRead.
    Code:
    canStatus canRead(
        int handle, long* id, 
        void* msg, unsigned int* dlc, 
        unsigned int* flag, DWORD* time);
    This is the function I want to call every 1ms, which retreives messages in the device's receive buffer.

  9. #9
    Join Date
    Nov 2003
    Posts
    1,902

    Re: while loop w/ sleep(1) doesnt work

    Looks like canReadWait() is the blocking version. This would be much better than polling.

    canReadSync() and canReadSyncSpecific() also look useful.

    gg

  10. #10
    Join Date
    Dec 2006
    Posts
    60

    Re: while loop w/ sleep(1) doesnt work

    i know about the canReadWait() function for kvaser. However, my app must also work with a few other CAN adapters that are user selectable. The APIs for these other devices do not have an equivalent function, so i have to write something in my app to do it.

    If by blocking function, you mean something like this:
    Code:
    void pauseforcount(int count)
    {
    int i=0;
    while (i<count)
     i++;
    }
    does the cpu freeze up during this loop?
    my sequence of cmd and response can take several minutes, and I don't want the CPU to hang on my app.

  11. #11
    Join Date
    Mar 2002
    Location
    St. Petersburg, Florida, USA
    Posts
    12,125

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by acerunner316 View Post
    i know about the canReadWait() function for kvaser. However, my app must also work with a few other CAN adapters that are user selectable. The APIs for these other devices do not have an equivalent function, so i have to write something in my app to do it.

    I have worked with a variety of CAN bus products over the past decade, and have never seen a commercial driver/library package that did NOT support notification. A few (typically raw, older ones) required an update in order for the adapter to generate a system interrupt..
    TheCPUWizard is a registered trademark, all rights reserved. (If this post was helpful, please RATE it!)
    2008, 2009,2010
    In theory, there is no difference between theory and practice; in practice there is.

    * Join the fight, refuse to respond to posts that contain code outside of [code] ... [/code] tags. See here for instructions
    * How NOT to post a question here
    * Of course you read this carefully before you posted
    * Need homework help? Read this first

  12. #12
    Join Date
    Dec 2006
    Posts
    60

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by TheCPUWizard View Post
    I have worked with a variety of CAN bus products over the past decade, and have never seen a commercial driver/library package that did NOT support notification. A few (typically raw, older ones) required an update in order for the adapter to generate a system interrupt..
    I am using Kvaser, VectorCAN, and PeakCAN. If you know of such a function in those libraries, please advise. Thanks!

  13. #13
    Join Date
    Mar 2002
    Location
    St. Petersburg, Florida, USA
    Posts
    12,125

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by acerunner316 View Post
    I am using Kvaser, VectorCAN, and PeakCAN. If you know of such a function in those libraries, please advise. Thanks!

    PeakCAN (which is ancient) does not. Typically this driver is best used on a thread wtih Huerestic delays.

    VectorCAN I cant find my documentation on, and most of the time I used it was with LabView (which has its own dedicated driver

    Kvaser we already determined does have it....

    Sounds like time for a decent class hierarchy and some background thread processing.
    TheCPUWizard is a registered trademark, all rights reserved. (If this post was helpful, please RATE it!)
    2008, 2009,2010
    In theory, there is no difference between theory and practice; in practice there is.

    * Join the fight, refuse to respond to posts that contain code outside of [code] ... [/code] tags. See here for instructions
    * How NOT to post a question here
    * Of course you read this carefully before you posted
    * Need homework help? Read this first

  14. #14
    Join Date
    Nov 2003
    Posts
    1,902

    Re: while loop w/ sleep(1) doesnt work

    >> If by blocking function...
    In this context, "blocking" means that the current thread is "blocked" or waiting efficiently within the OS. Meaning, the call does not return from the OS until some condition is met. For example, Sleep() is a blocking call which blocks for at least the amount of time given. If your code is spinning in a loop, that's called a "busy wait". This will count against you in the "&#37; CPU Usage" column of task manager.

    >> my sequence of cmd and response can take several minutes
    Then why not just poll once a second? I see no need for polling the data any faster. And if you are willing to call Sleep(), then just call canReadWait() with a 1 second timeout. Then if data is available it will return immediately. If not, the call will block for up to 1 second.

    Is this code multi-threaded? Or are you handling the UI and device interaction all within one thread?

    gg

  15. #15
    Join Date
    Dec 2006
    Posts
    60

    Re: while loop w/ sleep(1) doesnt work

    Quote Originally Posted by Codeplug View Post
    >> If by blocking function...
    In this context, "blocking" means that the current thread is "blocked" or waiting efficiently within the OS. Meaning, the call does not return from the OS until some condition is met. For example, Sleep() is a blocking call which blocks for at least the amount of time given. If your code is spinning in a loop, that's called a "busy wait". This will count against you in the "% CPU Usage" column of task manager.
    Thanks for providing the correct terminology. Yes, I want to avoid a busy wait at all costs.


    Quote Originally Posted by Codeplug View Post
    >> my sequence of cmd and response can take several minutes
    Then why not just poll once a second? I see no need for polling the data any faster. And if you are willing to call Sleep(), then just call canReadWait() with a 1 second timeout. Then if data is available it will return immediately. If not, the call will block for up to 1 second.
    what I mean is that there are so many cmd & response pairs of CAN messages that all of them in sequence can take several minutes. For example, I have 1000 cmds to send, each waiting for a response before sending the next command. Polling every 1 second will require at least 1000 seconds to complete the entire sequence of 1000 cmds. Polling every 1ms, however, dramatically reduces this time to 1 sec, which is what I'm trying to do.

    Quote Originally Posted by Codeplug View Post
    Is this code multi-threaded? Or are you handling the UI and device interaction all within one thread?

    gg
    it's single thread.

Page 1 of 3 123 LastLast

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured