f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna/* Licensed to the Apache Software Foundation (ASF) under one or more
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * contributor license agreements. See the NOTICE file distributed with
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * this work for additional information regarding copyright ownership.
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * The ASF licenses this file to You under the Apache License, Version 2.0
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * (the "License"); you may not use this file except in compliance with
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * the License. You may obtain a copy of the License at
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna *
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * http://www.apache.org/licenses/LICENSE-2.0
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna *
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * Unless required by applicable law or agreed to in writing, software
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * distributed under the License is distributed on an "AS IS" BASIS,
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * See the License for the specific language governing permissions and
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna * limitations under the License.
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna */
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
f020d1f91625f6de963b8c1ac44d8f31bb74b784pquerna/* #define APR_RING_DEBUG 1 */
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna#include "simple_types.h"
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna#include "simple_event.h"
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
6881fda812136efa364537ad49964b509a345bd2pquernastatic apr_status_t
6881fda812136efa364537ad49964b509a345bd2pquernasimple_timer_pool_cleanup(void *baton)
6881fda812136efa364537ad49964b509a345bd2pquerna{
6881fda812136efa364537ad49964b509a345bd2pquerna simple_timer_t *elem = (simple_timer_t *)baton;
6881fda812136efa364537ad49964b509a345bd2pquerna simple_core_t *sc = elem->sc;
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquerna apr_thread_mutex_lock(sc->mtx);
6881fda812136efa364537ad49964b509a345bd2pquerna APR_RING_REMOVE(elem, link);
6881fda812136efa364537ad49964b509a345bd2pquerna apr_thread_mutex_unlock(sc->mtx);
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquerna return APR_SUCCESS;
6881fda812136efa364537ad49964b509a345bd2pquerna}
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquernavoid
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquernasimple_register_timer(simple_core_t * sc,
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna simple_timer_cb cb,
6881fda812136efa364537ad49964b509a345bd2pquerna void *baton, apr_time_t relative_time,
6881fda812136efa364537ad49964b509a345bd2pquerna apr_pool_t *shutdown_pool)
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna{
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna simple_timer_t *elem = NULL;
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna simple_timer_t *ep = NULL;
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna int inserted = 0;
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna apr_time_t t = apr_time_now() + relative_time;
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna apr_thread_mutex_lock(sc->mtx);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_CHECK_CONSISTENCY(&sc->timer_ring, simple_timer_t, link);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
6881fda812136efa364537ad49964b509a345bd2pquerna elem = (simple_timer_t *) apr_pcalloc(shutdown_pool, sizeof(simple_timer_t));
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_ELEM_INIT(elem, link);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna elem->expires = t;
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna elem->cb = cb;
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna elem->baton = baton;
6881fda812136efa364537ad49964b509a345bd2pquerna elem->pool = shutdown_pool;
6881fda812136efa364537ad49964b509a345bd2pquerna elem->sc = sc;
6881fda812136efa364537ad49964b509a345bd2pquerna apr_pool_cleanup_register(elem->pool, elem, simple_timer_pool_cleanup, apr_pool_cleanup_null);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_CHECK_CONSISTENCY(&sc->timer_ring, simple_timer_t, link);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna /* pqXXXXXX: skiplist would be a nice optimization here. */
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna if (!APR_RING_EMPTY(&sc->timer_ring, simple_timer_t, link)) {
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna ep = APR_RING_FIRST(&sc->timer_ring);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna while (inserted == 0 &&
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna ep != APR_RING_SENTINEL(&sc->timer_ring, simple_timer_t, link))
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna {
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna if (ep->expires < elem->expires) {
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_CHECK_CONSISTENCY(&sc->timer_ring, simple_timer_t,
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna link);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_INSERT_BEFORE(ep, elem, link);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna inserted = 1;
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_CHECK_CONSISTENCY(&sc->timer_ring, simple_timer_t,
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna link);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna }
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna ep = APR_RING_NEXT(ep, link);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna }
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna }
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_CHECK_CONSISTENCY(&sc->timer_ring, simple_timer_t, link);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna if (!inserted) {
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_INSERT_TAIL(&sc->timer_ring, elem, simple_timer_t, link);
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna }
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna APR_RING_CHECK_CONSISTENCY(&sc->timer_ring, simple_timer_t, link);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna
52a5101047d0148d33df1f9f4f77b24bce7fdf70pquerna apr_thread_mutex_unlock(sc->mtx);
f997d134bcee6bfa4cd87b69acee96e80c5a358bpquerna}
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquernavoid
6881fda812136efa364537ad49964b509a345bd2pquernasimple_timer_run(simple_timer_t *ep)
6881fda812136efa364537ad49964b509a345bd2pquerna{
6881fda812136efa364537ad49964b509a345bd2pquerna apr_pool_cleanup_kill(ep->pool, ep, simple_timer_pool_cleanup);
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquerna ep->cb(ep->sc, ep->baton);
6881fda812136efa364537ad49964b509a345bd2pquerna}
6881fda812136efa364537ad49964b509a345bd2pquerna
6881fda812136efa364537ad49964b509a345bd2pquerna