source: rtems/cpukit/posix/src/timersettime.c @ 2903090

4.115
Last change on this file since 2903090 was 2903090, checked in by Sebastian Huber <sebastian.huber@…>, on 04/15/15 at 09:26:46

score: Add header to _Watchdog_Remove()

Add watchdog header parameter to _Watchdog_Remove() to be in line with
the other operations. Add _Watchdog_Remove_ticks() and
_Watchdog_Remove_seconds() for convenience.

Update #2307.

  • Property mode set to 100644
File size: 3.9 KB
Line 
1/**
2 * @file
3 *
4 * @brief Function Arms or Disarms the Timer Identified by timerid
5 * @ingroup POSIXAPI
6 */
7
8/*
9 *  14.2.4 Per-Process Timers, P1003.1b-1993, p. 267
10 *
11 *  COPYRIGHT (c) 1989-2008.
12 *  On-Line Applications Research Corporation (OAR).
13 *
14 *  The license and distribution terms for this file may be
15 *  found in the file LICENSE in this distribution or at
16 *  http://www.rtems.org/license/LICENSE.
17 */
18
19#if HAVE_CONFIG_H
20#include "config.h"
21#endif
22
23#include <time.h>
24#include <errno.h>
25
26#include <rtems/posix/time.h>
27#include <rtems/posix/ptimer.h>
28#include <rtems/posix/timerimpl.h>
29#include <rtems/score/todimpl.h>
30#include <rtems/score/watchdogimpl.h>
31#include <rtems/seterr.h>
32
33int timer_settime(
34  timer_t                  timerid,
35  int                      flags,
36  const struct itimerspec *__restrict value,
37  struct itimerspec       *__restrict ovalue
38)
39{
40  POSIX_Timer_Control *ptimer;
41  Objects_Locations    location;
42  bool                 activated;
43  uint32_t             initial_period;
44  struct itimerspec    normalize;
45
46  if ( !value )
47    rtems_set_errno_and_return_minus_one( EINVAL );
48
49  /*
50   * First, it verifies if the structure "value" is correct   
51   * if the number of nanoseconds is not correct return EINVAL
52   */
53  if ( !_Timespec_Is_valid( &(value->it_value) ) ) {
54    rtems_set_errno_and_return_minus_one( EINVAL );
55  }
56  if ( !_Timespec_Is_valid( &(value->it_interval) ) ) {
57    rtems_set_errno_and_return_minus_one( EINVAL );
58  }
59
60  if ( flags != TIMER_ABSTIME && flags != POSIX_TIMER_RELATIVE ) {
61    rtems_set_errno_and_return_minus_one( EINVAL );
62  }
63
64  normalize = *value;
65
66  /* Convert absolute to relative time */
67  if (flags == TIMER_ABSTIME) {
68    struct timespec now;
69    _TOD_Get( &now );
70    /* Check for seconds in the past */
71    if ( _Timespec_Greater_than( &now, &normalize.it_value ) )
72      rtems_set_errno_and_return_minus_one( EINVAL );
73    _Timespec_Subtract( &now, &normalize.it_value, &normalize.it_value );
74  }
75
76  /* If the function reaches this point, then it will be necessary to do
77   * something with the structure of times of the timer: to stop, start
78   * or start it again
79   */
80
81  ptimer = _POSIX_Timer_Get( timerid, &location );
82  switch ( location ) {
83
84    case OBJECTS_LOCAL:
85      /* First, it verifies if the timer must be stopped */
86      if ( normalize.it_value.tv_sec == 0 && normalize.it_value.tv_nsec == 0 ) {
87         /* Stop the timer */
88         _Watchdog_Remove_ticks( &ptimer->Timer );
89         /* The old data of the timer are returned */
90         if ( ovalue )
91           *ovalue = ptimer->timer_data;
92         /* The new data are set */
93         ptimer->timer_data = normalize;
94         /* Indicates that the timer is created and stopped */
95         ptimer->state = POSIX_TIMER_STATE_CREATE_STOP;
96         /* Returns with success */
97        _Objects_Put( &ptimer->Object );
98        return 0;
99       }
100
101       /* Convert from seconds and nanoseconds to ticks */
102       ptimer->ticks  = _Timespec_To_ticks( &value->it_interval );
103       initial_period = _Timespec_To_ticks( &normalize.it_value );
104
105
106       activated = _POSIX_Timer_Insert_helper(
107         &ptimer->Timer,
108         initial_period,
109         ptimer->Object.id,
110         _POSIX_Timer_TSR,
111         ptimer
112       );
113       if ( !activated ) {
114         _Objects_Put( &ptimer->Object );
115         return 0;
116       }
117
118       /*
119        * The timer has been started and is running.  So we return the
120        * old ones in "ovalue"
121        */
122       if ( ovalue )
123         *ovalue = ptimer->timer_data;
124       ptimer->timer_data = normalize;
125
126       /* Indicate that the time is running */
127       ptimer->state = POSIX_TIMER_STATE_CREATE_RUN;
128       _TOD_Get( &ptimer->time );
129      _Objects_Put( &ptimer->Object );
130       return 0;
131
132#if defined(RTEMS_MULTIPROCESSING)
133    case OBJECTS_REMOTE:
134#endif
135    case OBJECTS_ERROR:
136      break;
137  }
138
139  rtems_set_errno_and_return_minus_one( EINVAL );
140}
Note: See TracBrowser for help on using the repository browser.