static void* __timer_thread_start(void* arg) { PosixTimer* timer = reinterpret_cast<PosixTimer*>(arg); kernel_sigset_t sigset; sigaddset(sigset.get(), TIMER_SIGNAL); while (true) { // Wait for a signal... siginfo_t si; memset(&si, 0, sizeof(si)); int rc = __rt_sigtimedwait(sigset.get(), &si, NULL, sizeof(sigset)); if (rc == -1) { continue; } if (si.si_code == SI_TIMER) { // This signal was sent because a timer fired, so call the callback. timer->callback(timer->callback_argument); } else if (si.si_code == SI_TKILL) { // This signal was sent because someone wants us to exit. free(timer); return NULL; } } }
void ShellAndroid::run() { PosixTimer timer; double current_time = timer.get(); while (true) { struct android_poll_source *source; while (true) { int timeout = (settings_.animate && app_.window) ? 0 : -1; if (ALooper_pollAll(timeout, nullptr, nullptr, reinterpret_cast<void **>(&source)) < 0) break; if (source) source->process(&app_, source); } if (app_.destroyRequested) break; if (!app_.window) continue; acquire_back_buffer(); double t = timer.get(); add_game_time(static_cast<float>(t - current_time)); present_back_buffer(); current_time = t; } }
int UpdateBlobWindow(void* data) { if (data == 0) return 0; Rect rect = *((Rect*)data); SDL_mutexP(srvMutex); PosixTimer pt; bool fDone = false; while (!fDone) { try { newRange = srv->grabColorBin(7, rect); fYUVRangeChange = true; fDone = true; } catch (...) { // Are we out of time? if (pt.elapsed() > 5) { cerr << "Updating blob window timed out." << endl; fYUVRangeChange = false; fDone = true; } else { fYUVRangeChange = false; fDone = false; } } } SDL_mutexV(srvMutex); fUpdatingBlobWindow = false; return 0; }
int UpdateYUVRange(void* data) { if (data == 0) return 0; YUVRange yuv = *((YUVRange*)data); SDL_mutexP(srvMutex); PosixTimer pt; bool fDone = false; while (!fDone) { try { if (currentRange == yuv) { srv->setColorBin(5, currentRange); } else { srv->setColorBin(5, currentRange+yuv); undoList.push(currentRange); currentRange += yuv; } fYUVRangeChange = false; fDone = true; } catch (...) { // Are we out of time? if (pt.elapsed() > 5) { cerr << "Updating yuv range window timed out." << endl; fYUVRangeChange = true; fDone = true; } else { fYUVRangeChange = true; fDone = false; } } } SDL_mutexV(srvMutex); fUpdatingYUVRange = false; return 0; }
// A persistent read function. static ssize_t read_r(int fd, void *buf, size_t count, size_t ms) { double tMax = ms / 1000.0; // convert to seconds PosixTimer t; int r; unsigned int total = 0; while (total < count) { r = read(fd, ((unsigned char *)buf) + total, count - total); // did something seriously go wrong? if (r < 0 && errno != EINTR) { __dbg(string("PosixSerial: failed to read: ") + string(strerror(errno))); throw PosixSerial::ReadFailure(); } else if (r > 0) { // progress! total += r; t.start(); // restart the timer } // are we out of time? if (ms > 0 && t.elapsed() > tMax) { __dbg(string("PosixSerial: read timed out")); throw PosixSerial::ReadTimeout(); } } return total; }
// A persistent write function. static ssize_t write_r(int fd, const void *buf, size_t count, size_t ms) { double tMax = ms / 1000.0; // convert to seconds PosixTimer t; int r; unsigned int written = 0; while (written < count) { r = write(fd, ((const unsigned char *)buf) + written, count - written); // did something seriously go wrong? if (r < 0 && errno != EINTR) { __dbg(string("PosixSerial: failed to write: ") + string(strerror(errno))); throw PosixSerial::WriteFailure(); } else if (r > 0) { // progress! written += r; t.start(); // restart the timer } // are we out of time? if (ms > 0 && t.elapsed() > tMax) { __dbg(string("PosixSerial: write timed out")); throw PosixSerial::WriteTimeout(); } } return written; }
static void* __timer_thread_start(void* arg) { PosixTimer* timer = reinterpret_cast<PosixTimer*>(arg); sigset64_t sigset = {}; sigaddset64(&sigset, TIMER_SIGNAL); while (true) { // Wait for a signal... siginfo_t si = {}; if (__rt_sigtimedwait(&sigset, &si, nullptr, sizeof(sigset)) == -1) continue; if (si.si_code == SI_TIMER) { // This signal was sent because a timer fired, so call the callback. // All events to the callback will be ignored when the timer is deleted. if (atomic_load(&timer->deleted) == true) { continue; } timer->callback(timer->callback_argument); } else if (si.si_code == SI_TKILL) { // This signal was sent because someone wants us to exit. free(timer); return nullptr; } } }
int BlobFinder(void* data) { const unsigned int blobColor = SDL_MapRGB(screen->format, 255, 0, 255); const unsigned int blobBPP = screen->format->BitsPerPixel; const unsigned int blobWinW = 80; const unsigned int blobWinH = 64; list<Blob> blobs; while (!fQuitApplication) { // Get blobs. SDL_mutexP(srvMutex); PosixTimer pt; bool fDone = false; while (!fDone) { try { srv->getBlobs(5, blobs); fDone = true; } catch (...) { if (pt.elapsed() > 5) { cerr << "Blob finder timed out." << endl; fDone = true; blobs.clear(); } else { fDone = false; } } } SDL_mutexV(srvMutex); SDL_mutexP(blobImageMutex); if (blobImage == 0) { if ((blobImage = SDL_CreateRGBSurface(SDL_SWSURFACE,blobWinW,blobWinH,blobBPP,0,0,0,0)) < 0) { cerr << "Failed to create blob surface: " << SDL_GetError() << endl; } } if (blobImage != 0) { // Clear it. SDL_FillRect(blobImage, 0, 0); // Draw blobs. for (list<Blob>::iterator iter = blobs.begin(); iter != blobs.end(); ++iter) { SDL_Rect rect; rect.x = iter->getX1(); rect.y = blobWinH - iter->getY2() - 1; rect.w = abs(iter->getX2() - iter->getX1()); rect.h = abs(iter->getY2() - iter->getY1()); SDL_FillRect(blobImage, &rect, blobColor); } fUpdatedBlobs = true; } SDL_mutexV(blobImageMutex); usleep(10000); } return 0; }
void ShellXcb::loop_poll() { PosixTimer timer; double current_time = timer.get(); double profile_start_time = current_time; int profile_present_count = 0; while (true) { // handle pending events while (true) { xcb_generic_event_t *ev = xcb_poll_for_event(c_); if (!ev) break; handle_event(ev); free(ev); } if (quit_) break; acquire_back_buffer(); double t = timer.get(); add_game_time(static_cast<float>(t - current_time)); present_back_buffer(); current_time = t; profile_present_count++; if (current_time - profile_start_time >= 5.0) { const double fps = profile_present_count / (current_time - profile_start_time); std::stringstream ss; ss << profile_present_count << " presents in " << current_time - profile_start_time << " seconds " << "(FPS: " << fps << ")"; log(LOG_INFO, ss.str().c_str()); profile_start_time = current_time; profile_present_count = 0; } } }
Surveyor* CreateSurveyor(string devName, Surveyor::CameraResolution camRes, double timeout) { // Create the Surveyor object. Surveyor* ret = 0; PosixTimer pt; bool fDone = false; while (!fDone) { try { ret = new Surveyor(devName, camRes); ret->setColorBin(5, currentRange); fDone = true; } catch (...) { fDone = false; // Are we out of time? if (timeout > 0 && pt.elapsed() > timeout) { return 0; } } } return ret; }
int UpdateImage(void* data) { double timeout = data != 0 ? *((double*)data) : 5; Picture pic; SDL_mutexP(srvMutex); PosixTimer pt; bool fDone = false; while (!fDone) { try { pic = srv->takePicture(); fDone = true; } catch (...) { // Are we out of time? if (timeout > 0 && pt.elapsed() > timeout) { fDone = true; } else { fDone = false; } } } SDL_mutexV(srvMutex); if (pic) { SDL_mutexP(jpegImageMutex); if (jpegImage != 0) { SDL_FreeSurface(jpegImage); } if ((jpegImage = IMG_Load_RW(SDL_RWFromConstMem(pic.data(), pic.size()), 1)) == 0) { cerr << "Failed to load image: " << SDL_GetError() << endl; } else { fUpdatedImage = true; } SDL_mutexV(jpegImageMutex); } fUpdatingImage = false; return 0; }