source: asp_wo_cfg/trunk/kernel/alarm.c@ 72

Last change on this file since 72 was 49, checked in by ertl-hiro, 12 years ago

asp_wo_kernelをコミット。

  • Property svn:keywords set to Id
File size: 8.2 KB
Line 
1/*
2 * TOPPERS/ASP Kernel
3 * Toyohashi Open Platform for Embedded Real-Time Systems/
4 * Advanced Standard Profile Kernel
5 *
6 * Copyright (C) 2000-2003 by Embedded and Real-Time Systems Laboratory
7 * Toyohashi Univ. of Technology, JAPAN
8 * Copyright (C) 2005-2012 by Embedded and Real-Time Systems Laboratory
9 * Graduate School of Information Science, Nagoya Univ., JAPAN
10 *
11 * 上記著作権者は,以下の(1)〜(4)の条件を満たす場合に限り,本ソフトウェ
12 * ア(本ソフトウェアを改変したものを含む.以下同じ)を使用・複製・改
13 * 変・再配布(以下,利用と呼ぶ)することを無償で許諾する.
14 * (1) 本ソフトウェアをソースコードの形で利用する場合には,上記の著作
15 * 権表示,この利用条件および下記の無保証規定が,そのままの形でソー
16 * スコード中に含まれていること.
17 * (2) 本ソフトウェアを,ライブラリ形式など,他のソフトウェア開発に使
18 * 用できる形で再配布する場合には,再配布に伴うドキュメント(利用
19 * 者マニュアルなど)に,上記の著作権表示,この利用条件および下記
20 * の無保証規定を掲載すること.
21 * (3) 本ソフトウェアを,機器に組み込むなど,他のソフトウェア開発に使
22 * 用できない形で再配布する場合には,次のいずれかの条件を満たすこ
23 * と.
24 * (a) 再配布に伴うドキュメント(利用者マニュアルなど)に,上記の著
25 * 作権表示,この利用条件および下記の無保証規定を掲載すること.
26 * (b) 再配布の形態を,別に定める方法によって,TOPPERSプロジェクトに
27 * 報告すること.
28 * (4) 本ソフトウェアの利用により直接的または間接的に生じるいかなる損
29 * 害からも,上記著作権者およびTOPPERSプロジェクトを免責すること.
30 * また,本ソフトウェアのユーザまたはエンドユーザからのいかなる理
31 * 由に基づく請求からも,上記著作権者およびTOPPERSプロジェクトを
32 * 免責すること.
33 *
34 * 本ソフトウェアは,無保証で提供されているものである.上記著作権者お
35 * よびTOPPERSプロジェクトは,本ソフトウェアに関して,特定の使用目的
36 * に対する適合性も含めて,いかなる保証も行わない.また,本ソフトウェ
37 * アの利用により直接的または間接的に生じたいかなる損害に関しても,そ
38 * の責任を負わない.
39 *
40 * @(#) $Id: alarm.c 49 2012-09-06 04:41:53Z ertl-hiro $
41 */
42
43/*
44 * アラームハンドラ機能
45 */
46
47#include "kernel_impl.h"
48#include "check.h"
49#include "alarm.h"
50
51/*
52 * トレースログマクロのデフォルト定義
53 */
54#ifndef LOG_ALM_ENTER
55#define LOG_ALM_ENTER(p_almcb)
56#endif /* LOG_ALM_ENTER */
57
58#ifndef LOG_ALM_LEAVE
59#define LOG_ALM_LEAVE(p_almcb)
60#endif /* LOG_ALM_LEAVE */
61
62#ifndef LOG_CRE_ALM_ENTER
63#define LOG_CRE_ALM_ENTER(almid, pk_calm)
64#endif /* LOG_CRE_ALM_ENTER */
65
66#ifndef LOG_CRE_ALM_LEAVE
67#define LOG_CRE_ALM_LEAVE(ercd)
68#endif /* LOG_CRE_ALM_LEAVE */
69
70#ifndef LOG_STA_ALM_ENTER
71#define LOG_STA_ALM_ENTER(almid, almtim)
72#endif /* LOG_STA_ALM_ENTER */
73
74#ifndef LOG_STA_ALM_LEAVE
75#define LOG_STA_ALM_LEAVE(ercd)
76#endif /* LOG_STA_ALM_LEAVE */
77
78#ifndef LOG_ISTA_ALM_ENTER
79#define LOG_ISTA_ALM_ENTER(almid, almtim)
80#endif /* LOG_ISTA_ALM_ENTER */
81
82#ifndef LOG_ISTA_ALM_LEAVE
83#define LOG_ISTA_ALM_LEAVE(ercd)
84#endif /* LOG_ISTA_ALM_LEAVE */
85
86#ifndef LOG_STP_ALM_ENTER
87#define LOG_STP_ALM_ENTER(almid)
88#endif /* LOG_STP_ALM_ENTER */
89
90#ifndef LOG_STP_ALM_LEAVE
91#define LOG_STP_ALM_LEAVE(ercd)
92#endif /* LOG_STP_ALM_LEAVE */
93
94#ifndef LOG_ISTP_ALM_ENTER
95#define LOG_ISTP_ALM_ENTER(almid)
96#endif /* LOG_ISTP_ALM_ENTER */
97
98#ifndef LOG_ISTP_ALM_LEAVE
99#define LOG_ISTP_ALM_LEAVE(ercd)
100#endif /* LOG_ISTP_ALM_LEAVE */
101
102#ifndef LOG_REF_ALM_ENTER
103#define LOG_REF_ALM_ENTER(almid, pk_ralm)
104#endif /* LOG_REF_ALM_ENTER */
105
106#ifndef LOG_REF_ALM_LEAVE
107#define LOG_REF_ALM_LEAVE(ercd, pk_ralm)
108#endif /* LOG_REF_ALM_LEAVE */
109
110/*
111 * アラームハンドラの数
112 */
113#define tnum_alm ((uint_t)(tmax_almid - TMIN_ALMID + 1))
114
115/*
116 * アラームハンドラIDからアラームハンドラ管理ブロックを取り出すためのマクロ
117 */
118#define INDEX_ALM(almid) ((uint_t)((almid) - TMIN_ALMID))
119#define get_almcb(almid) (&(almcb_table[INDEX_ALM(almid)]))
120
121/*
122 * アラームハンドラ機能の初期化
123 */
124#ifdef TOPPERS_almini
125
126void
127initialize_alarm(void)
128{
129 uint_t i;
130 ALMCB *p_almcb;
131 ALMINIB *p_alminib;
132
133 for (i = 0; i < tnum_alm; i++) {
134 p_almcb = &(almcb_table[i]);
135 p_alminib = &(alminib_table[i]);
136 p_alminib->almatr = TA_NOEXS;
137 p_almcb->p_alminib = ((const ALMINIB *) p_alminib);
138 }
139}
140
141#endif /* TOPPERS_almini */
142
143/*
144 * アラームハンドラの生成
145 */
146#ifdef TOPPERS_cre_alm
147
148ER
149cre_alm(ID almid, const T_CALM *pk_calm)
150{
151 ALMCB *p_almcb;
152 ALMINIB *p_alminib;
153 ER ercd;
154
155 LOG_CRE_ALM_ENTER(almid, pk_calm);
156 CHECK_INIRTN();
157 CHECK_ALMID(almid);
158 CHECK_RSATR(pk_calm->almatr, TA_NULL);
159 CHECK_ALIGN_FUNC(pk_calm->almhdr);
160 CHECK_NONNULL_FUNC(pk_calm->almhdr);
161 p_almcb = get_almcb(almid);
162
163 if (p_almcb->p_alminib->almatr != TA_NOEXS) {
164 ercd = E_OBJ;
165 }
166 else {
167 p_alminib = (ALMINIB *)(p_almcb->p_alminib);
168 p_alminib->almatr = pk_calm->almatr;
169 p_alminib->exinf = pk_calm->exinf;
170 p_alminib->almhdr = pk_calm->almhdr;
171
172 p_almcb->almsta = false;
173 ercd = E_OK;
174 }
175
176 error_exit:
177 LOG_CRE_ALM_LEAVE(ercd);
178 return(ercd);
179}
180
181#endif /* TOPPERS_cre_alm */
182
183/*
184 * アラームハンドラの動作開始
185 */
186#ifdef TOPPERS_sta_alm
187
188ER
189sta_alm(ID almid, RELTIM almtim)
190{
191 ALMCB *p_almcb;
192 ER ercd;
193
194 LOG_STA_ALM_ENTER(almid, almtim);
195 CHECK_TSKCTX_UNL();
196 CHECK_ALMID(almid);
197 CHECK_PAR(almtim <= TMAX_RELTIM);
198 p_almcb = get_almcb(almid);
199 CHECK_NOEXS(p_almcb->p_alminib->almatr);
200
201 t_lock_cpu();
202 if (p_almcb->almsta) {
203 tmevtb_dequeue(&(p_almcb->tmevtb));
204 }
205 else {
206 p_almcb->almsta = true;
207 }
208 tmevtb_enqueue(&(p_almcb->tmevtb), almtim,
209 (CBACK) call_almhdr, (void *) p_almcb);
210 ercd = E_OK;
211 t_unlock_cpu();
212
213 error_exit:
214 LOG_STA_ALM_LEAVE(ercd);
215 return(ercd);
216}
217
218#endif /* TOPPERS_sta_alm */
219
220/*
221 * アラームハンドラの動作開始(非タスクコンテキスト用)
222 */
223#ifdef TOPPERS_ista_alm
224
225ER
226ista_alm(ID almid, RELTIM almtim)
227{
228 ALMCB *p_almcb;
229 ER ercd;
230
231 LOG_ISTA_ALM_ENTER(almid, almtim);
232 CHECK_INTCTX_UNL();
233 CHECK_ALMID(almid);
234 CHECK_PAR(almtim <= TMAX_RELTIM);
235 p_almcb = get_almcb(almid);
236 CHECK_NOEXS(p_almcb->p_alminib->almatr);
237
238 i_lock_cpu();
239 if (p_almcb->almsta) {
240 tmevtb_dequeue(&(p_almcb->tmevtb));
241 }
242 else {
243 p_almcb->almsta = true;
244 }
245 tmevtb_enqueue(&(p_almcb->tmevtb), almtim,
246 (CBACK) call_almhdr, (void *) p_almcb);
247 ercd = E_OK;
248 i_unlock_cpu();
249
250 error_exit:
251 LOG_ISTA_ALM_LEAVE(ercd);
252 return(ercd);
253}
254
255#endif /* TOPPERS_ista_alm */
256
257/*
258 * アラームハンドラの動作停止
259 */
260#ifdef TOPPERS_stp_alm
261
262ER
263stp_alm(ID almid)
264{
265 ALMCB *p_almcb;
266 ER ercd;
267
268 LOG_STP_ALM_ENTER(almid);
269 CHECK_TSKCTX_UNL();
270 CHECK_ALMID(almid);
271 p_almcb = get_almcb(almid);
272 CHECK_NOEXS(p_almcb->p_alminib->almatr);
273
274 t_lock_cpu();
275 if (p_almcb->almsta) {
276 p_almcb->almsta = false;
277 tmevtb_dequeue(&(p_almcb->tmevtb));
278 }
279 ercd = E_OK;
280 t_unlock_cpu();
281
282 error_exit:
283 LOG_STP_ALM_LEAVE(ercd);
284 return(ercd);
285}
286
287#endif /* TOPPERS_stp_alm */
288
289/*
290 * アラームハンドラの動作停止(非タスクコンテキスト用)
291 */
292#ifdef TOPPERS_istp_alm
293
294ER
295istp_alm(ID almid)
296{
297 ALMCB *p_almcb;
298 ER ercd;
299
300 LOG_ISTP_ALM_ENTER(almid);
301 CHECK_INTCTX_UNL();
302 CHECK_ALMID(almid);
303 p_almcb = get_almcb(almid);
304 CHECK_NOEXS(p_almcb->p_alminib->almatr);
305
306 i_lock_cpu();
307 if (p_almcb->almsta) {
308 p_almcb->almsta = false;
309 tmevtb_dequeue(&(p_almcb->tmevtb));
310 }
311 ercd = E_OK;
312 i_unlock_cpu();
313
314 error_exit:
315 LOG_ISTP_ALM_LEAVE(ercd);
316 return(ercd);
317}
318
319#endif /* TOPPERS_istp_alm */
320
321/*
322 * アラームハンドラの状態参照
323 */
324#ifdef TOPPERS_ref_alm
325
326ER
327ref_alm(ID almid, T_RALM *pk_ralm)
328{
329 ALMCB *p_almcb;
330 ER ercd;
331
332 LOG_REF_ALM_ENTER(almid, pk_ralm);
333 CHECK_TSKCTX_UNL();
334 CHECK_ALMID(almid);
335 p_almcb = get_almcb(almid);
336 CHECK_NOEXS(p_almcb->p_alminib->almatr);
337
338 t_lock_cpu();
339 if (p_almcb->almsta) {
340 pk_ralm->almstat = TALM_STA;
341 pk_ralm->lefttim = tmevt_lefttim(&(p_almcb->tmevtb));
342 }
343 else {
344 pk_ralm->almstat = TALM_STP;
345 }
346 ercd = E_OK;
347 t_unlock_cpu();
348
349 error_exit:
350 LOG_REF_ALM_LEAVE(ercd, pk_ralm);
351 return(ercd);
352}
353
354#endif /* TOPPERS_ref_alm */
355
356/*
357 * アラームハンドラ起動ルーチン
358 */
359#ifdef TOPPERS_almcal
360
361void
362call_almhdr(ALMCB *p_almcb)
363{
364 PRI saved_ipm;
365
366 /*
367 * アラームハンドラを停止状態にする.
368 */
369 p_almcb->almsta = false;
370
371 /*
372 * アラームハンドラを,CPUロック解除状態で呼び出す.
373 */
374 saved_ipm = i_get_ipm();
375 i_unlock_cpu();
376
377 LOG_ALM_ENTER(p_almcb);
378 (*((ALMHDR)(p_almcb->p_alminib->almhdr)))(p_almcb->p_alminib->exinf);
379 LOG_ALM_LEAVE(p_almcb);
380
381 if (!i_sense_lock()) {
382 i_lock_cpu();
383 }
384 i_set_ipm(saved_ipm);
385}
386
387#endif /* TOPPERS_almcal */
Note: See TracBrowser for help on using the repository browser.