* @brief The event thread's logic. * When this method exits, the thread shuts down. * * This thread is very simple at its core, it calls "ReceiveMessages()" * in a loop forever. * * The complexity comes in from throttling this thread correctly. * If the client is actively sending messages to/from Soar we don't * what this thread to slow it down by polling for messages. * Also when the clien
| 59 | * (empirical tests on my laptop show 0%). |
| 60 | *************************************************************/ |
| 61 | void EventThread::Run() |
| 62 | { |
| 63 | // When we last received a message (if its recent we barely sleep so we're maximally responsive) |
| 64 | clock_t last = 0 ; |
| 65 | |
| 66 | // How long to wait before sleeping (currently 1 sec) |
| 67 | clock_t delay = CLOCKS_PER_SEC ; |
| 68 | /* |
| 69 | #ifdef _DEBUG |
| 70 | sml::PrintDebugFormat("Starting EventThread\n") ; |
| 71 | int64_t counter = 0 ; |
| 72 | #endif |
| 73 | */ |
| 74 | while (!m_QuitNow && !m_pConnection->IsClosed()) |
| 75 | { |
| 76 | // Our purpose is to check for incoming messages when the |
| 77 | // client itself is sleeping for some reason. It makes |
| 78 | // the client logic simpler. |
| 79 | bool receivedMessage = m_pConnection->ReceiveMessages(true) ; |
| 80 | |
| 81 | if (receivedMessage) |
| 82 | { |
| 83 | // Record the time of the last incoming message |
| 84 | last = clock() ; |
| 85 | } |
| 86 | |
| 87 | /* |
| 88 | #ifdef _DEBUG |
| 89 | counter++ ; |
| 90 | if (counter % 1000 == 0) |
| 91 | sml::PrintDebugFormat("EventThread alive\n") ; |
| 92 | #endif |
| 93 | */ |
| 94 | clock_t current = clock() ; |
| 95 | |
| 96 | // If it's been a while since the last incoming message |
| 97 | // then start sleeping a reasonable amount. |
| 98 | // Sleep(0) just allows other threads to run before we continue |
| 99 | // to execute. |
| 100 | if (current - last > delay) |
| 101 | { |
| 102 | sml::Sleep(0, 5) ; |
| 103 | } |
| 104 | else |
| 105 | // Changed this to always use sleep 5 now. |
| 106 | // Calling sleep(0) here as we used to can cause a single threaded app |
| 107 | // to take over the CPU, slowing down the entire system. Doesn't happen |
| 108 | // on a hyper threaded CPU, but on a normal CPU it's a significant problem. |
| 109 | // The trade-off is that the response to events may not be quite as fast. |
| 110 | { |
| 111 | sml::Sleep(0, 5) ; |
| 112 | } |
| 113 | } |
| 114 | |
| 115 | /* |
| 116 | #ifdef _DEBUG |
| 117 | sml::PrintDebugFormat("EventThread terminated\n") ; |
| 118 | #endif |
no test coverage detected