*/
#include <stdlib.h>
-
#include <sys/time.h>
#include <unistd.h>
#include <alarm.h>
#include "cal_db_util.h"
#include "cal_db.h"
#include "cal_db_query.h"
+#include "cal_server_service.h"
+#include "cal_server_ondemand.h"
#include "cal_server_dbus.h"
+#include "cal_server_alarm.h"
+
+#define CAL_SERVER_ALARM_THREAD_NAME "cal_server_alarm"
-#define CAL_SEARCH_LOOP_MAX 4
+GThread *_cal_server_alarm_thread = NULL;
+GCond _cal_server_alarm_cond;
+GMutex _cal_server_alarm_mutex;
+static bool server_killed = false;
+static bool signal_called = false;
struct _alarm_data_s {
int event_id;
int system_type;
};
+struct alarm_ud {
+ GList *alarm_list;
+};
+
/* this api is necessary for repeat instance. */
-static int _cal_server_alarm_unset_alerted_alarmmgr_id(int alarm_id)
+static int cal_server_alarm_unset_alerted_alarmmgr_id(int alarm_id)
{
char query[CAL_DB_SQL_MAX_LEN] = {0};
int ret = 0;
int ret;
DBG("remove alarm id(%d)", alarm_id);
- _cal_server_alarm_unset_alerted_alarmmgr_id(alarm_id);
+ cal_server_alarm_unset_alerted_alarmmgr_id(alarm_id);
ret = alarmmgr_remove_alarm(alarm_id);
if (ret != ALARMMGR_RESULT_SUCCESS) {
/* LCOV_EXCL_START */
return (long long int)mktime(&st);
}
/*
- * to get aler time, time(NULL) is not accurate. 1 secs diff could be occured.
+ * time(NULL) is not appropriate as parameter.
+ * 1 seconds could be flowed before calling function.(1 sec time diff)
* so, searching DB is neccessary to find alert time.
*/
-int cal_server_alarm_get_alert_time(int alarm_id, time_t *tt_alert)
+static int cal_server_alarm_get_alert_time(int alarm_id, time_t *tt_alert)
{
int ret = 0;
RETV_IF(NULL == tt_alert, CALENDAR_ERROR_INVALID_PARAMETER);
return CALENDAR_ERROR_NONE;
}
-struct alarm_ud {
- GList *alarm_list;
-};
-
static bool __app_matched_cb(app_control_h app_control, const char *package, void *user_data)
{
CAL_FN_CALL();
}
}
-int cal_server_alarm_register_next_alarm(time_t utime)
+static void cal_server_alarm_register_next_alarm(time_t utime)
{
+ CAL_FN_CALL();
+
GList *l = NULL;
_cal_server_alarm_get_latest(utime, false, &l);
if (NULL == l)
- return CALENDAR_ERROR_NONE;
+ return;
l = g_list_sort(l, _cal_server_alarm_sort_cb);
g_list_foreach(l, (GFunc)_cal_server_alarm_print_cb, NULL);
_cal_server_alarm_register(l);
g_list_free_full(l, free);
- return CALENDAR_ERROR_NONE;
}
-void cal_server_alarm_alert(time_t tt_alert)
+static void cal_server_alarm_alert(time_t tt_alert)
{
GList *l = NULL;
_cal_server_alarm_get_latest(tt_alert, true, &l);
time_t tt_alert = 0;
cal_server_alarm_get_alert_time(alarm_id, &tt_alert);
cal_server_alarm_alert(tt_alert);
- _cal_server_alarm_unset_alerted_alarmmgr_id(alarm_id);
- cal_server_alarm_register_next_alarm(tt_alert);
+ cal_server_alarm_unset_alerted_alarmmgr_id(alarm_id);
+ signal_called = true;
+ cal_server_alarm_start();
return 0;
}
-static void _cal_server_alarm_timechange_cb(keynode_t *node, void *data)
+static void _timechanged_cb(keynode_t *node, void *data)
{
- time_t t = time(NULL);
- cal_server_alarm_alert(t);
- cal_server_alarm_register_next_alarm(t);
+ cal_server_alarm_alert(time(NULL));
+ signal_called = true;
+ cal_server_alarm_start();
}
-void _cal_server_alarm_set_timechange(void)
+static void _cal_server_alarm_set_timechange(void)
{
- vconf_notify_key_changed(VCONFKEY_SYSTEM_TIME_CHANGED,
- _cal_server_alarm_timechange_cb, NULL);
- vconf_notify_key_changed(VCONFKEY_TELEPHONY_NITZ_GMT,
- _cal_server_alarm_timechange_cb, NULL);
- vconf_notify_key_changed(VCONFKEY_TELEPHONY_NITZ_EVENT_GMT,
- _cal_server_alarm_timechange_cb, NULL);
- vconf_notify_key_changed(VCONFKEY_TELEPHONY_NITZ_ZONE,
- _cal_server_alarm_timechange_cb, NULL);
+ vconf_notify_key_changed(VCONFKEY_SYSTEM_TIME_CHANGED, _timechanged_cb, NULL);
+ vconf_notify_key_changed(VCONFKEY_TELEPHONY_NITZ_GMT, _timechanged_cb, NULL);
+ vconf_notify_key_changed(VCONFKEY_TELEPHONY_NITZ_ZONE, _timechanged_cb, NULL);
+ vconf_notify_key_changed(VCONFKEY_TELEPHONY_NITZ_EVENT_GMT, _timechanged_cb, NULL);
}
-void _cal_server_alarm_unset_timechange(void)
+static void _cal_server_alarm_unset_timechange(void)
{
- vconf_ignore_key_changed(VCONFKEY_SYSTEM_TIME_CHANGED,
- _cal_server_alarm_timechange_cb);
- vconf_ignore_key_changed(VCONFKEY_TELEPHONY_NITZ_GMT,
- _cal_server_alarm_timechange_cb);
- vconf_ignore_key_changed(VCONFKEY_TELEPHONY_NITZ_EVENT_GMT,
- _cal_server_alarm_timechange_cb);
- vconf_ignore_key_changed(VCONFKEY_TELEPHONY_NITZ_ZONE,
- _cal_server_alarm_timechange_cb);
+ vconf_ignore_key_changed(VCONFKEY_SYSTEM_TIME_CHANGED, _timechanged_cb);
+ vconf_ignore_key_changed(VCONFKEY_TELEPHONY_NITZ_GMT, _timechanged_cb);
+ vconf_ignore_key_changed(VCONFKEY_TELEPHONY_NITZ_ZONE, _timechanged_cb);
+ vconf_ignore_key_changed(VCONFKEY_TELEPHONY_NITZ_EVENT_GMT, _timechanged_cb);
}
static void _changed_cb(const char* view_uri, void* data)
{
- CAL_FN_CALL();
- cal_server_alarm_register_next_alarm(time(NULL));
+ DBG("Receive alarm change signal");
+ signal_called = true;
+ cal_server_alarm_start();
}
static int _cal_server_alarm_set_inotify(calendar_db_changed_cb callback)
cal_inotify_unsubscribe(CAL_NOTI_FILE_TODO, callback, NULL);
}
-int cal_server_alarm_init(void)
+static int cal_server_alarm_init(void)
{
- CAL_FN_CALL();
-
int ret = 0;
+
_cal_server_alarm_set_timechange();
_cal_server_alarm_set_inotify(_changed_cb);
/* LCOV_EXCL_STOP */
}
- cal_server_alarm_register_next_alarm(time(NULL));
return CALENDAR_ERROR_NONE;
}
-void cal_server_alarm_deinit(void)
+static gpointer _cal_server_alarm_main(gpointer user_data)
+{
+ int ret = 0;
+ bool is_initialized = false;
+
+ while (1) { /*
+ * While syncing with contacts,
+ * because calendar-service could be stopped by on-demand,
+ * holding on-demand is needed.
+ */
+ cal_server_ondemand_hold();
+
+ do {
+ if (false == is_initialized) {
+ ret = cal_server_alarm_init();
+ if (CALENDAR_ERROR_NONE != ret) {
+ /* LCOV_EXCL_START */
+ ERR("cal_server_alarm_init() Fail(%d)", ret);
+ break;
+ /* LCOV_EXCL_STOP */
+ }
+ DBG("init alarm");
+ is_initialized = true;
+ }
+ signal_called = false;
+
+ ret = cal_connect();
+ if (CALENDAR_ERROR_NONE != ret) {
+ /* LCOV_EXCL_START */
+ ERR("cal_connect() Fail(%d)", ret);
+ break;
+ /* LCOV_EXCL_STOP */
+ }
+
+ cal_server_alarm_register_next_alarm(time(NULL));
+
+ cal_disconnect();
+
+ /*
+ * to check whether _changed_cb is called while working.
+ */
+ if (true == signal_called) {
+ DBG("signal is true");
+ signal_called = false;
+ continue;
+ }
+ } while (0);
+
+ g_mutex_lock(&_cal_server_alarm_mutex);
+ DBG("wait");
+ cal_server_ondemand_release();
+ cal_server_ondemand_start();
+ g_cond_wait(&_cal_server_alarm_cond, &_cal_server_alarm_mutex);
+ g_mutex_unlock(&_cal_server_alarm_mutex);
+ if (server_killed)
+ break;
+ }
+ g_thread_exit(NULL);
+
+ return NULL;
+}
+
+void cal_server_alarm_start(void)
+{
+ CAL_FN_CALL();
+
+ if (server_killed)
+ return;
+
+ if (NULL == _cal_server_alarm_thread) {
+ g_mutex_init(&_cal_server_alarm_mutex);
+ g_cond_init(&_cal_server_alarm_cond);
+ _cal_server_alarm_thread = g_thread_new(CAL_SERVER_ALARM_THREAD_NAME,
+ _cal_server_alarm_main, NULL);
+ }
+ /* don't use mutex. */
+ g_cond_signal(&_cal_server_alarm_cond);
+}
+
+static void cal_server_alarm_deinit(void)
{
alarmmgr_fini();
_cal_server_alarm_unset_inotify(_changed_cb);
_cal_server_alarm_unset_timechange();
-
}
+void cal_server_alarm_end(void)
+{
+ server_killed = true;
+
+ cal_server_alarm_deinit();
+
+ /* don't use mutex. */
+ g_cond_signal(&_cal_server_alarm_cond);
+ g_thread_join(_cal_server_alarm_thread);
+ g_thread_unref(_cal_server_alarm_thread);
+}