1272343Sngie/* $NetBSD: t_getitimer.c,v 1.2 2012/03/22 18:20:46 christos Exp $ */ 2272343Sngie 3272343Sngie/*- 4272343Sngie * Copyright (c) 2011 The NetBSD Foundation, Inc. 5272343Sngie * All rights reserved. 6272343Sngie * 7272343Sngie * This code is derived from software contributed to The NetBSD Foundation 8272343Sngie * by Jukka Ruohonen. 9272343Sngie * 10272343Sngie * Redistribution and use in source and binary forms, with or without 11272343Sngie * modification, are permitted provided that the following conditions 12272343Sngie * are met: 13272343Sngie * 1. Redistributions of source code must retain the above copyright 14272343Sngie * notice, this list of conditions and the following disclaimer. 15272343Sngie * 2. Redistributions in binary form must reproduce the above copyright 16272343Sngie * notice, this list of conditions and the following disclaimer in the 17272343Sngie * documentation and/or other materials provided with the distribution. 18272343Sngie * 19272343Sngie * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20272343Sngie * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21272343Sngie * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22272343Sngie * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23272343Sngie * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24272343Sngie * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25272343Sngie * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26272343Sngie * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27272343Sngie * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28272343Sngie * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29272343Sngie * POSSIBILITY OF SUCH DAMAGE. 30272343Sngie */ 31272343Sngie#include <sys/cdefs.h> 32272343Sngie__RCSID("$NetBSD: t_getitimer.c,v 1.2 2012/03/22 18:20:46 christos Exp $"); 33272343Sngie 34272343Sngie#include <sys/time.h> 35272343Sngie 36272343Sngie#include <atf-c.h> 37272343Sngie#include <errno.h> 38272343Sngie#include <limits.h> 39272343Sngie#include <signal.h> 40272343Sngie#include <string.h> 41272343Sngie#include <unistd.h> 42272343Sngie 43272343Sngiestatic bool fail; 44272343Sngiestatic void sighandler(int); 45272343Sngie 46272343Sngiestatic void 47272343Sngiesighandler(int signo) 48272343Sngie{ 49272343Sngie 50272343Sngie if (signo == SIGALRM || signo == SIGVTALRM) 51272343Sngie fail = false; 52272343Sngie} 53272343Sngie 54272343SngieATF_TC(getitimer_empty); 55272343SngieATF_TC_HEAD(getitimer_empty, tc) 56272343Sngie{ 57272343Sngie atf_tc_set_md_var(tc, "descr", "getitimer(2) before setitimer(2)"); 58272343Sngie} 59272343Sngie 60272343SngieATF_TC_BODY(getitimer_empty, tc) 61272343Sngie{ 62272343Sngie struct itimerval it; 63272343Sngie 64272343Sngie /* 65272343Sngie * Verify that the passed structure remains 66272343Sngie * empty after calling getitimer(2) but before 67272343Sngie * actually arming the timer with setitimer(2). 68272343Sngie */ 69272343Sngie (void)memset(&it, 0, sizeof(struct itimerval)); 70272343Sngie 71272343Sngie ATF_REQUIRE(getitimer(ITIMER_REAL, &it) == 0); 72272343Sngie 73272343Sngie if (it.it_value.tv_sec != 0 || it.it_value.tv_usec != 0) 74272343Sngie goto fail; 75272343Sngie 76272343Sngie ATF_REQUIRE(getitimer(ITIMER_VIRTUAL, &it) == 0); 77272343Sngie 78272343Sngie if (it.it_value.tv_sec != 0 || it.it_value.tv_usec != 0) 79272343Sngie goto fail; 80272343Sngie 81272343Sngie ATF_REQUIRE(getitimer(ITIMER_PROF, &it) == 0); 82272343Sngie 83272343Sngie if (it.it_value.tv_sec != 0 || it.it_value.tv_usec != 0) 84272343Sngie goto fail; 85272343Sngie 86272343Sngie return; 87272343Sngie 88272343Sngiefail: 89272343Sngie atf_tc_fail("getitimer(2) modfied the timer before it was armed"); 90272343Sngie} 91272343Sngie 92272343SngieATF_TC(getitimer_err); 93272343SngieATF_TC_HEAD(getitimer_err, tc) 94272343Sngie{ 95272343Sngie atf_tc_set_md_var(tc, "descr", "Test errors from getitimer(2)"); 96272343Sngie} 97272343Sngie 98272343SngieATF_TC_BODY(getitimer_err, tc) 99272343Sngie{ 100272343Sngie struct itimerval it; 101272343Sngie 102272343Sngie errno = 0; 103272343Sngie ATF_REQUIRE_ERRNO(EINVAL, getitimer(-1, &it) == -1); 104272343Sngie 105272343Sngie errno = 0; 106272343Sngie ATF_REQUIRE_ERRNO(EINVAL, getitimer(INT_MAX, &it) == -1); 107272343Sngie 108272343Sngie errno = 0; 109272343Sngie ATF_REQUIRE_ERRNO(EFAULT, getitimer(ITIMER_REAL, (void *)-1) == -1); 110272343Sngie} 111272343Sngie 112272343SngieATF_TC(setitimer_basic); 113272343SngieATF_TC_HEAD(setitimer_basic, tc) 114272343Sngie{ 115272343Sngie atf_tc_set_md_var(tc, "descr", "A basic test of setitimer(2)"); 116272343Sngie} 117272343Sngie 118272343SngieATF_TC_BODY(setitimer_basic, tc) 119272343Sngie{ 120272343Sngie struct itimerval it; 121272343Sngie 122272343Sngie it.it_value.tv_sec = 0; 123272343Sngie it.it_value.tv_usec = 100; 124272343Sngie 125272343Sngie it.it_interval.tv_sec = 0; 126272343Sngie it.it_interval.tv_usec = 0; 127272343Sngie 128272343Sngie fail = true; 129272343Sngie 130272343Sngie ATF_REQUIRE(signal(SIGALRM, sighandler) != SIG_ERR); 131272343Sngie ATF_REQUIRE(setitimer(ITIMER_REAL, &it, NULL) == 0); 132272343Sngie 133272343Sngie /* 134272343Sngie * Although the interaction between 135272343Sngie * setitimer(2) and sleep(3) can be 136272343Sngie * unspecified, it is assumed that one 137272343Sngie * second suspension will be enough for 138272343Sngie * the timer to fire. 139272343Sngie */ 140272343Sngie (void)sleep(1); 141272343Sngie 142272343Sngie if (fail != false) 143272343Sngie atf_tc_fail("timer did not fire"); 144272343Sngie} 145272343Sngie 146272343SngieATF_TC(setitimer_err); 147272343SngieATF_TC_HEAD(setitimer_err, tc) 148272343Sngie{ 149272343Sngie atf_tc_set_md_var(tc, "descr", "Test errors from setitimer(2)" 150272343Sngie " (PR standards/44927)"); 151272343Sngie} 152272343Sngie 153272343SngieATF_TC_BODY(setitimer_err, tc) 154272343Sngie{ 155272343Sngie struct itimerval it, ot; 156272343Sngie 157272343Sngie errno = 0; 158272343Sngie ATF_REQUIRE_ERRNO(EINVAL, setitimer(-1, &it, &ot) == -1); 159272343Sngie 160272343Sngie errno = 0; 161272343Sngie ATF_REQUIRE_ERRNO(EINVAL, setitimer(INT_MAX, &it, &ot) == -1); 162272343Sngie 163272343Sngie errno = 0; 164272343Sngie ATF_REQUIRE_ERRNO(EFAULT, setitimer(ITIMER_REAL,(void*)-1, &ot) == -1); 165272343Sngie} 166272343Sngie 167272343SngieATF_TC(setitimer_old); 168272343SngieATF_TC_HEAD(setitimer_old, tc) 169272343Sngie{ 170272343Sngie atf_tc_set_md_var(tc, "descr", "Test old values from setitimer(2)"); 171272343Sngie} 172272343Sngie 173272343SngieATF_TC_BODY(setitimer_old, tc) 174272343Sngie{ 175272343Sngie struct itimerval it, ot; 176272343Sngie 177272343Sngie /* 178272343Sngie * Make two calls; the second one 179272343Sngie * should store the old values. 180272343Sngie */ 181272343Sngie it.it_value.tv_sec = 4; 182272343Sngie it.it_value.tv_usec = 3; 183272343Sngie 184272343Sngie it.it_interval.tv_sec = 0; 185272343Sngie it.it_interval.tv_usec = 0; 186272343Sngie 187272343Sngie ATF_REQUIRE(setitimer(ITIMER_REAL, &it, &ot) == 0); 188272343Sngie 189272343Sngie it.it_value.tv_sec = 2; 190272343Sngie it.it_value.tv_usec = 1; 191272343Sngie 192272343Sngie it.it_interval.tv_sec = 0; 193272343Sngie it.it_interval.tv_usec = 0; 194272343Sngie 195272343Sngie ATF_REQUIRE(setitimer(ITIMER_REAL, &it, &ot) == 0); 196272343Sngie 197276478Sngie#ifdef __FreeBSD__ 198276478Sngie if (ot.it_value.tv_sec == 4 && ot.it_value.tv_usec == 3) 199276478Sngie atf_tc_fail("setitimer(2) did not return remaining time"); 200276478Sngie#else 201272343Sngie if (ot.it_value.tv_sec != 4 || ot.it_value.tv_usec != 3) 202272343Sngie atf_tc_fail("setitimer(2) did not store old values"); 203276478Sngie#endif 204272343Sngie} 205272343Sngie 206272343SngieATF_TP_ADD_TCS(tp) 207272343Sngie{ 208272343Sngie 209272343Sngie ATF_TP_ADD_TC(tp, getitimer_empty); 210272343Sngie ATF_TP_ADD_TC(tp, getitimer_err); 211272343Sngie ATF_TP_ADD_TC(tp, setitimer_basic); 212272343Sngie ATF_TP_ADD_TC(tp, setitimer_err); 213272343Sngie ATF_TP_ADD_TC(tp, setitimer_old); 214272343Sngie 215272343Sngie return atf_no_error(); 216272343Sngie} 217