]> git.kernelconcepts.de Git - karo-tx-redboot.git/blob - packages/devs/watchdog/synth/v2_0/src/synth_watchdog.cxx
Initial revision
[karo-tx-redboot.git] / packages / devs / watchdog / synth / v2_0 / src / synth_watchdog.cxx
1 //==========================================================================
2 //
3 //      synth_watchdog.cxx
4 //
5 //      Watchdog driver for the synthetic target
6 //
7 //==========================================================================
8 //####ECOSGPLCOPYRIGHTBEGIN####
9 // -------------------------------------------
10 // This file is part of eCos, the Embedded Configurable Operating System.
11 // Copyright (C) 2002 Bart Veer
12 //
13 // eCos is free software; you can redistribute it and/or modify it under
14 // the terms of the GNU General Public License as published by the Free
15 // Software Foundation; either version 2 or (at your option) any later version.
16 //
17 // eCos is distributed in the hope that it will be useful, but WITHOUT ANY
18 // WARRANTY; without even the implied warranty of MERCHANTABILITY or
19 // FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
20 // for more details.
21 //
22 // You should have received a copy of the GNU General Public License along
23 // with eCos; if not, write to the Free Software Foundation, Inc.,
24 // 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
25 //
26 // As a special exception, if other files instantiate templates or use macros
27 // or inline functions from this file, or you compile this file and link it
28 // with other works to produce a work based on this file, this file does not
29 // by itself cause the resulting work to be covered by the GNU General Public
30 // License. However the source code for this file must still be made available
31 // in accordance with section (3) of the GNU General Public License.
32 //
33 // This exception does not invalidate any other reasons why a work based on
34 // this file might be covered by the GNU General Public License.
35 //
36 // Alternative licenses for eCos may be arranged by contacting the
37 // copyright holder(s).
38 // -------------------------------------------
39 //####ECOSGPLCOPYRIGHTEND####
40 //==========================================================================
41 //#####DESCRIPTIONBEGIN####
42 //
43 // Author(s):    bartv
44 // Contributors: bartv
45 // Date:         2002-09-04
46 //
47 //####DESCRIPTIONEND####
48 //==========================================================================
49
50 #include <pkgconf/system.h>
51 #include <pkgconf/devs_watchdog_synth.h>
52
53 #ifdef CYGIMP_WATCHDOG_HARDWARE
54
55 #include <cyg/hal/hal_arch.h>
56 #include <cyg/infra/cyg_type.h>
57 #include <cyg/infra/cyg_ass.h>
58 #include <cyg/infra/diag.h>
59 #include <cyg/hal/hal_io.h>
60
61 // FIXME: right now the generic watchdog header depends on the
62 // kernel. That should be fixed in the watchdog code, but will
63 // affect some device drivers as well
64 #include <pkgconf/kernel.h>
65 #include <cyg/io/watchdog.hxx>
66
67 // Protocol between host and target
68 #define SYNTH_WATCHDOG_START    0x01
69 #define SYNTH_WATCHDOG_RESET    0x02
70
71 // The synthetic target's watchdog implementation involves interaction
72 // with a watchdog.tcl script running in the I/O auxiliary. The device
73 // must be instantiated during system initialization, preferably via
74 // a prioritized C++ static constructor. The generic watchdog package
75 // does have a static object, but it is not prioritized. If
76 // CYGSEM_HAL_STOP_CONSTRUCTORS_ON_FLAG is enabled then that object's
77 // constructor would get called too late.
78 //
79 // Instead a private class is defined here, and once instance is created.
80 // That instance gets referenced by the Cyg_Watchdog members, so
81 // selective linking does not get in the way. Instantiation happens inside
82 // the constructor, and the main Cyg_Watchdog::start() and reset() functions
83 // involve passing a message to the host-side.
84 //
85 // There is an open issue re. resolution. Usually the hardware imposes
86 // limits on what resolutions are valid, in fact there may be only one.
87 // With the synthetic target it would be possible to configure the
88 // desired resolution either on the target-side using a CDL option, or
89 // on the host-side using the target definition file. The resolution
90 // would have to be fairly coarse, probably at least 0.1 seconds,
91 // to allow for communication overheads. It is not clear whether
92 // target-side or host-side configuration is more appropriate, so for
93 // now a fixed resolution of one second is used.
94
95 class _Synth_Watchdog {
96   public:
97     _Synth_Watchdog();
98     ~_Synth_Watchdog() { }
99
100     cyg_uint64  resolution;
101 };
102
103 // A static instance of the _Synth_Watchdog class, whose constructor will
104 // be called at the right time to instantiate host-side support.
105 static _Synth_Watchdog _synth_watchdog_object CYGBLD_ATTRIB_INIT_PRI(CYG_INIT_DRIVERS);
106
107 // Id for communicating with the watchdog instance in the auxiliary
108 static int aux_id   = -1;
109
110 _Synth_Watchdog::_Synth_Watchdog()
111 {
112     // SIGPWR is disabled by default. It has to be reenabled.
113     struct cyg_hal_sys_sigset_t blocked;
114     CYG_HAL_SYS_SIGEMPTYSET(&blocked);
115     CYG_HAL_SYS_SIGADDSET(&blocked, CYG_HAL_SYS_SIGPWR);
116     cyg_hal_sys_sigprocmask(CYG_HAL_SYS_SIG_UNBLOCK, &blocked, (cyg_hal_sys_sigset_t*) 0);
117     
118     resolution = 1000000000LL;
119     if (synth_auxiliary_running) {
120         aux_id  = synth_auxiliary_instantiate("devs/watchdog/synth",
121                                               SYNTH_MAKESTRING(CYGPKG_DEVS_WATCHDOG_SYNTH),
122                                               "watchdog",
123                                               (const char*) 0,
124                                               (const char*) 0);
125     }
126 }
127
128 // Hardware initialization. This has already happened in the
129 // _Synth_Watchdog constructor, all that is needed here is to
130 // propagate the resolution.
131 void
132 Cyg_Watchdog::init_hw(void)
133 {
134     resolution  = _synth_watchdog_object.resolution;
135 }
136
137 void
138 Cyg_Watchdog::start(void)
139 {
140     if (synth_auxiliary_running && (-1 != aux_id)) {
141         synth_auxiliary_xchgmsg(aux_id, SYNTH_WATCHDOG_START, 0, 0,
142                                (const unsigned char*)0, 0,
143                                (int *) 0,
144                                (unsigned char*) 0, (int*) 0, 0);
145     }
146 }
147
148 void
149 Cyg_Watchdog::reset()
150 {
151     if (synth_auxiliary_running && (-1 != aux_id)) {
152         synth_auxiliary_xchgmsg(aux_id, SYNTH_WATCHDOG_RESET, 0, 0,
153                                (const unsigned char*)0, 0,
154                                (int *) 0,
155                                (unsigned char*) 0, (int*) 0, 0);
156     }
157 }
158
159 #endif // CYGIMP_WATCHDOG_HARDWARE