Merge commit '6a3e7dfa87345244190403eaad71e760f11305ba' into kraken * commit '6a3e7dfa87345244190403eaad71e760f11305ba': Fix alarms with negative or very large wakup times.
This commit is contained in:
@@ -400,7 +400,7 @@ class AlarmManagerService extends IAlarmManager.Stub {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public long timeToNextAlarm() {
|
public long timeToNextAlarm() {
|
||||||
long nextAlarm = 0xfffffffffffffffl;
|
long nextAlarm = Long.MAX_VALUE;
|
||||||
synchronized (mLock) {
|
synchronized (mLock) {
|
||||||
for (int i=AlarmManager.RTC_WAKEUP;
|
for (int i=AlarmManager.RTC_WAKEUP;
|
||||||
i<=AlarmManager.ELAPSED_REALTIME; i++) {
|
i<=AlarmManager.ELAPSED_REALTIME; i++) {
|
||||||
@@ -420,7 +420,18 @@ class AlarmManagerService extends IAlarmManager.Stub {
|
|||||||
{
|
{
|
||||||
if (mDescriptor != -1)
|
if (mDescriptor != -1)
|
||||||
{
|
{
|
||||||
set(mDescriptor, alarm.type, (alarm.when * 1000 * 1000));
|
// The kernel never triggers alarms with negative wakeup times
|
||||||
|
// so we ensure they are positive.
|
||||||
|
long alarmSeconds, alarmNanoseconds;
|
||||||
|
if (alarm.when < 0) {
|
||||||
|
alarmSeconds = 0;
|
||||||
|
alarmNanoseconds = 0;
|
||||||
|
} else {
|
||||||
|
alarmSeconds = alarm.when / 1000;
|
||||||
|
alarmNanoseconds = (alarm.when % 1000) * 1000 * 1000;
|
||||||
|
}
|
||||||
|
|
||||||
|
set(mDescriptor, alarm.type, alarmSeconds, alarmNanoseconds);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -499,7 +510,7 @@ class AlarmManagerService extends IAlarmManager.Stub {
|
|||||||
|
|
||||||
private native int init();
|
private native int init();
|
||||||
private native void close(int fd);
|
private native void close(int fd);
|
||||||
private native void set(int fd, int type, long nanoseconds);
|
private native void set(int fd, int type, long seconds, long nanoseconds);
|
||||||
private native int waitForAlarm(int fd);
|
private native int waitForAlarm(int fd);
|
||||||
private native int setKernelTimezone(int fd, int minuteswest);
|
private native int setKernelTimezone(int fd, int minuteswest);
|
||||||
|
|
||||||
|
|||||||
@@ -38,10 +38,6 @@
|
|||||||
#include <linux/android_alarm.h>
|
#include <linux/android_alarm.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define ONE_NANOSECOND 1000000000LL
|
|
||||||
#define NANOSECONDS_TO_SECONDS(x) (x / ONE_NANOSECOND)
|
|
||||||
#define SECONDS_TO_NANOSECONDS(x) (x * ONE_NANOSECOND)
|
|
||||||
|
|
||||||
namespace android {
|
namespace android {
|
||||||
|
|
||||||
static jint android_server_AlarmManagerService_setKernelTimezone(JNIEnv* env, jobject obj, jint fd, jint minswest)
|
static jint android_server_AlarmManagerService_setKernelTimezone(JNIEnv* env, jobject obj, jint fd, jint minswest)
|
||||||
@@ -82,17 +78,17 @@ static void android_server_AlarmManagerService_close(JNIEnv* env, jobject obj, j
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
static void android_server_AlarmManagerService_set(JNIEnv* env, jobject obj, jint fd, jint type, jlong nanoseconds)
|
static void android_server_AlarmManagerService_set(JNIEnv* env, jobject obj, jint fd, jint type, jlong seconds, jlong nanoseconds)
|
||||||
{
|
{
|
||||||
#if HAVE_ANDROID_OS
|
#if HAVE_ANDROID_OS
|
||||||
struct timespec ts;
|
struct timespec ts;
|
||||||
ts.tv_sec = NANOSECONDS_TO_SECONDS(nanoseconds);
|
ts.tv_sec = seconds;
|
||||||
ts.tv_nsec = nanoseconds - SECONDS_TO_NANOSECONDS(ts.tv_sec);
|
ts.tv_nsec = nanoseconds;
|
||||||
|
|
||||||
int result = ioctl(fd, ANDROID_ALARM_SET(type), &ts);
|
int result = ioctl(fd, ANDROID_ALARM_SET(type), &ts);
|
||||||
if (result < 0)
|
if (result < 0)
|
||||||
{
|
{
|
||||||
LOGE("Unable to set alarm to %lld: %s\n", nanoseconds, strerror(errno));
|
LOGE("Unable to set alarm to %lld.%09lld: %s\n", seconds, nanoseconds, strerror(errno));
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@@ -121,7 +117,7 @@ static JNINativeMethod sMethods[] = {
|
|||||||
/* name, signature, funcPtr */
|
/* name, signature, funcPtr */
|
||||||
{"init", "()I", (void*)android_server_AlarmManagerService_init},
|
{"init", "()I", (void*)android_server_AlarmManagerService_init},
|
||||||
{"close", "(I)V", (void*)android_server_AlarmManagerService_close},
|
{"close", "(I)V", (void*)android_server_AlarmManagerService_close},
|
||||||
{"set", "(IIJ)V", (void*)android_server_AlarmManagerService_set},
|
{"set", "(IIJJ)V", (void*)android_server_AlarmManagerService_set},
|
||||||
{"waitForAlarm", "(I)I", (void*)android_server_AlarmManagerService_waitForAlarm},
|
{"waitForAlarm", "(I)I", (void*)android_server_AlarmManagerService_waitForAlarm},
|
||||||
{"setKernelTimezone", "(II)I", (void*)android_server_AlarmManagerService_setKernelTimezone},
|
{"setKernelTimezone", "(II)I", (void*)android_server_AlarmManagerService_setKernelTimezone},
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user