/* * Copyright (C) 2012 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ /* * Asynchronous interval timer. */ #include "IntervalTimer.h" #include <android-base/stringprintf.h> #include <base/logging.h> using android::base::StringPrintf; IntervalTimer::IntervalTimer() { mTimerId = 0; mCb = NULL; } bool IntervalTimer::set(int ms, TIMER_FUNC cb) { if (mTimerId == 0) { if (cb == NULL) return false; if (!create(cb)) return false; } if (cb != mCb) { kill(); if (!create(cb)) return false; } int stat = 0; struct itimerspec ts; ts.it_value.tv_sec = ms / 1000; ts.it_value.tv_nsec = (ms % 1000) * 1000000; ts.it_interval.tv_sec = 0; ts.it_interval.tv_nsec = 0; stat = timer_settime(mTimerId, 0, &ts, 0); if (stat == -1) LOG(ERROR) << StringPrintf("fail set timer"); return stat == 0; } IntervalTimer::~IntervalTimer() { kill(); } void IntervalTimer::kill() { if (mTimerId == 0) return; timer_delete(mTimerId); mTimerId = 0; mCb = NULL; } bool IntervalTimer::create(TIMER_FUNC cb) { struct sigevent se; int stat = 0; /* * Set the sigevent structure to cause the signal to be * delivered by creating a new thread. */ se.sigev_notify = SIGEV_THREAD; se.sigev_value.sival_ptr = &mTimerId; se.sigev_notify_function = cb; se.sigev_notify_attributes = NULL; mCb = cb; stat = timer_create(CLOCK_MONOTONIC, &se, &mTimerId); if (stat == -1) LOG(ERROR) << StringPrintf("fail create timer"); return stat == 0; }