timer.c revision 1.4
1/* $OpenBSD: timer.c,v 1.4 2011/01/26 17:07:59 reyk Exp $ */ 2 3/* 4 * Copyright (c) 2010 Reyk Floeter <reyk@vantronix.net> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18 19#include <sys/param.h> 20#include <sys/queue.h> 21#include <sys/socket.h> 22#include <sys/uio.h> 23 24#include <stdio.h> 25#include <stdlib.h> 26#include <unistd.h> 27#include <string.h> 28#include <errno.h> 29#include <fcntl.h> 30#include <ctype.h> 31#include <event.h> 32 33#include "iked.h" 34 35struct timer_cbarg { 36 int tmr_active; 37 struct event tmr_ev; 38 struct iked *tmr_env; 39 struct timeval tmr_first; 40 struct timeval tmr_last; 41 struct timeval tmr_tv; 42 int (*tmr_initcb)(struct iked *, struct iked_policy *); 43} timer_initiator; 44 45void timer_initiator_cb(int, short, void *); 46 47#define IKED_TIMER_INITIATOR_INITIAL 2 48#define IKED_TIMER_INITIATOR_INTERVAL 60 49 50void 51timer_register_initiator(struct iked *env, 52 int (*cb)(struct iked *, struct iked_policy *)) 53{ 54 struct timer_cbarg *tmr; 55 56 timer_unregister_initiator(env); 57 58 if (env->sc_passive) 59 return; 60 61 tmr = &timer_initiator; 62 gettimeofday(&tmr->tmr_first, NULL); 63 gettimeofday(&tmr->tmr_last, NULL); 64 65 tmr->tmr_env = env; 66 tmr->tmr_initcb = cb; 67 tmr->tmr_active = 1; 68 evtimer_set(&tmr->tmr_ev, timer_initiator_cb, tmr); 69 70 tmr->tmr_tv.tv_sec = IKED_TIMER_INITIATOR_INITIAL; 71 tmr->tmr_tv.tv_usec = 0; 72 evtimer_add(&tmr->tmr_ev, &tmr->tmr_tv); 73} 74 75void 76timer_unregister_initiator(struct iked *env) 77{ 78 struct timer_cbarg *tmr; 79 80 tmr = &timer_initiator; 81 if (!tmr->tmr_active) 82 return; 83 84 event_del(&tmr->tmr_ev); 85 bzero(tmr, sizeof(*tmr)); 86} 87 88void 89timer_initiator_cb(int fd, short event, void *arg) 90{ 91 struct timer_cbarg *tmr = arg; 92 struct iked *env = tmr->tmr_env; 93 struct iked_policy *pol; 94 95 gettimeofday(&tmr->tmr_last, NULL); 96 97 TAILQ_FOREACH(pol, &env->sc_policies, pol_entry) { 98 if ((pol->pol_flags & IKED_POLICY_ACTIVE) == 0) 99 continue; 100 if (sa_peer_lookup(pol, &pol->pol_peer.addr) != NULL) { 101 log_debug("%s: \"%s\" is already active", 102 __func__, pol->pol_name); 103 continue; 104 } 105 106 log_debug("%s: initiating \"%s\"", __func__, pol->pol_name); 107 108 if (tmr->tmr_initcb != NULL) { 109 /* Ignore error but what should we do on failure? */ 110 (void)tmr->tmr_initcb(env, pol); 111 } 112 } 113 114 tmr->tmr_tv.tv_sec = IKED_TIMER_INITIATOR_INTERVAL; 115 tmr->tmr_tv.tv_usec = 0; 116 evtimer_add(&tmr->tmr_ev, &tmr->tmr_tv); 117} 118