source: azure_iot_hub_riscv/trunk/asp_baseplatform/kernel/dataqueue.c@ 453

Last change on this file since 453 was 453, checked in by coas-nagasima, 4 years ago

ファイルを追加

  • Property svn:eol-style set to native
  • Property svn:mime-type set to text/x-csrc;charset=UTF-8
File size: 19.5 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-2017 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$
41 */
42
43/*
44 * データキュー機能
45 */
46
47#include "kernel_impl.h"
48#include "check.h"
49#include "task.h"
50#include "wait.h"
51#include "dataqueue.h"
52
53/*
54 * トレースログマクロのデフォルト定義
55 */
56#ifndef LOG_ACRE_DTQ_ENTER
57#define LOG_ACRE_DTQ_ENTER(pk_cdtq)
58#endif /* LOG_ACRE_DTQ_ENTER */
59
60#ifndef LOG_ACRE_DTQ_LEAVE
61#define LOG_ACRE_DTQ_LEAVE(ercd)
62#endif /* LOG_ACRE_DTQ_LEAVE */
63
64#ifndef LOG_DEL_DTQ_ENTER
65#define LOG_DEL_DTQ_ENTER(dtqid)
66#endif /* LOG_DEL_DTQ_ENTER */
67
68#ifndef LOG_DEL_DTQ_LEAVE
69#define LOG_DEL_DTQ_LEAVE(ercd)
70#endif /* LOG_DEL_DTQ_LEAVE */
71
72#ifndef LOG_SND_DTQ_ENTER
73#define LOG_SND_DTQ_ENTER(dtqid, data)
74#endif /* LOG_SND_DTQ_ENTER */
75
76#ifndef LOG_SND_DTQ_LEAVE
77#define LOG_SND_DTQ_LEAVE(ercd)
78#endif /* LOG_SND_DTQ_LEAVE */
79
80#ifndef LOG_PSND_DTQ_ENTER
81#define LOG_PSND_DTQ_ENTER(dtqid, data)
82#endif /* LOG_PSND_DTQ_ENTER */
83
84#ifndef LOG_PSND_DTQ_LEAVE
85#define LOG_PSND_DTQ_LEAVE(ercd)
86#endif /* LOG_PSND_DTQ_LEAVE */
87
88#ifndef LOG_IPSND_DTQ_ENTER
89#define LOG_IPSND_DTQ_ENTER(dtqid, data)
90#endif /* LOG_IPSND_DTQ_ENTER */
91
92#ifndef LOG_IPSND_DTQ_LEAVE
93#define LOG_IPSND_DTQ_LEAVE(ercd)
94#endif /* LOG_IPSND_DTQ_LEAVE */
95
96#ifndef LOG_TSND_DTQ_ENTER
97#define LOG_TSND_DTQ_ENTER(dtqid, data, tmout)
98#endif /* LOG_TSND_DTQ_ENTER */
99
100#ifndef LOG_TSND_DTQ_LEAVE
101#define LOG_TSND_DTQ_LEAVE(ercd)
102#endif /* LOG_TSND_DTQ_LEAVE */
103
104#ifndef LOG_FSND_DTQ_ENTER
105#define LOG_FSND_DTQ_ENTER(dtqid, data)
106#endif /* LOG_FSND_DTQ_ENTER */
107
108#ifndef LOG_FSND_DTQ_LEAVE
109#define LOG_FSND_DTQ_LEAVE(ercd)
110#endif /* LOG_FSND_DTQ_LEAVE */
111
112#ifndef LOG_IFSND_DTQ_ENTER
113#define LOG_IFSND_DTQ_ENTER(dtqid, data)
114#endif /* LOG_IFSND_DTQ_ENTER */
115
116#ifndef LOG_IFSND_DTQ_LEAVE
117#define LOG_IFSND_DTQ_LEAVE(ercd)
118#endif /* LOG_IFSND_DTQ_LEAVE */
119
120#ifndef LOG_RCV_DTQ_ENTER
121#define LOG_RCV_DTQ_ENTER(dtqid, p_data)
122#endif /* LOG_RCV_DTQ_ENTER */
123
124#ifndef LOG_RCV_DTQ_LEAVE
125#define LOG_RCV_DTQ_LEAVE(ercd, data)
126#endif /* LOG_RCV_DTQ_LEAVE */
127
128#ifndef LOG_PRCV_DTQ_ENTER
129#define LOG_PRCV_DTQ_ENTER(dtqid, p_data)
130#endif /* LOG_PRCV_DTQ_ENTER */
131
132#ifndef LOG_PRCV_DTQ_LEAVE
133#define LOG_PRCV_DTQ_LEAVE(ercd, data)
134#endif /* LOG_PRCV_DTQ_LEAVE */
135
136#ifndef LOG_TRCV_DTQ_ENTER
137#define LOG_TRCV_DTQ_ENTER(dtqid, p_data, tmout)
138#endif /* LOG_TRCV_DTQ_ENTER */
139
140#ifndef LOG_TRCV_DTQ_LEAVE
141#define LOG_TRCV_DTQ_LEAVE(ercd, data)
142#endif /* LOG_TRCV_DTQ_LEAVE */
143
144#ifndef LOG_INI_DTQ_ENTER
145#define LOG_INI_DTQ_ENTER(dtqid)
146#endif /* LOG_INI_DTQ_ENTER */
147
148#ifndef LOG_INI_DTQ_LEAVE
149#define LOG_INI_DTQ_LEAVE(ercd)
150#endif /* LOG_INI_DTQ_LEAVE */
151
152#ifndef LOG_REF_DTQ_ENTER
153#define LOG_REF_DTQ_ENTER(dtqid, pk_rdtq)
154#endif /* LOG_REF_DTQ_ENTER */
155
156#ifndef LOG_REF_DTQ_LEAVE
157#define LOG_REF_DTQ_LEAVE(ercd, pk_rdtq)
158#endif /* LOG_REF_DTQ_LEAVE */
159
160/*
161 * データキューの数
162 */
163#define tnum_dtq ((uint_t)(tmax_dtqid - TMIN_DTQID + 1))
164#define tnum_sdtq ((uint_t)(tmax_sdtqid - TMIN_DTQID + 1))
165
166/*
167 * データキューIDからデータキュー管理ブロックを取り出すためのマクロ
168 */
169#define INDEX_DTQ(dtqid) ((uint_t)((dtqid) - TMIN_DTQID))
170#define get_dtqcb(dtqid) (&(dtqcb_table[INDEX_DTQ(dtqid)]))
171
172#ifdef TOPPERS_dtqini
173
174/*
175 * 使用していないデータキュー管理ブロックのリスト
176 */
177QUEUE free_dtqcb;
178
179/*
180 * データキュー機能の初期化
181 */
182void
183initialize_dataqueue(void)
184{
185 uint_t i, j;
186 DTQCB *p_dtqcb;
187 DTQINIB *p_dtqinib;
188
189 for (i = 0; i < tnum_sdtq; i++) {
190 p_dtqcb = &(dtqcb_table[i]);
191 queue_initialize(&(p_dtqcb->swait_queue));
192 p_dtqcb->p_dtqinib = &(dtqinib_table[i]);
193 queue_initialize(&(p_dtqcb->rwait_queue));
194 p_dtqcb->count = 0U;
195 p_dtqcb->head = 0U;
196 p_dtqcb->tail = 0U;
197 }
198 queue_initialize(&free_dtqcb);
199 for (j = 0; i < tnum_dtq; i++, j++) {
200 p_dtqcb = &(dtqcb_table[i]);
201 p_dtqinib = &(adtqinib_table[j]);
202 p_dtqinib->dtqatr = TA_NOEXS;
203 p_dtqcb->p_dtqinib = ((const DTQINIB *) p_dtqinib);
204 queue_insert_prev(&free_dtqcb, &(p_dtqcb->swait_queue));
205 }
206}
207
208#endif /* TOPPERS_dtqini */
209
210/*
211 * データキュー管理領域へのデータの格納
212 */
213#ifdef TOPPERS_dtqenq
214
215void
216enqueue_data(DTQCB *p_dtqcb, intptr_t data)
217{
218 (p_dtqcb->p_dtqinib->p_dtqmb + p_dtqcb->tail)->data = data;
219 p_dtqcb->count++;
220 p_dtqcb->tail++;
221 if (p_dtqcb->tail >= p_dtqcb->p_dtqinib->dtqcnt) {
222 p_dtqcb->tail = 0U;
223 }
224}
225
226#endif /* TOPPERS_dtqenq */
227
228/*
229 * データキュー管理領域へのデータの強制格納
230 */
231#ifdef TOPPERS_dtqfenq
232
233void
234force_enqueue_data(DTQCB *p_dtqcb, intptr_t data)
235{
236 (p_dtqcb->p_dtqinib->p_dtqmb + p_dtqcb->tail)->data = data;
237 p_dtqcb->tail++;
238 if (p_dtqcb->tail >= p_dtqcb->p_dtqinib->dtqcnt) {
239 p_dtqcb->tail = 0U;
240 }
241 if (p_dtqcb->count < p_dtqcb->p_dtqinib->dtqcnt) {
242 p_dtqcb->count++;
243 }
244 else {
245 p_dtqcb->head = p_dtqcb->tail;
246 }
247}
248
249#endif /* TOPPERS_dtqfenq */
250
251/*
252 * データキュー管理領域からのデータの取出し
253 */
254#ifdef TOPPERS_dtqdeq
255
256void
257dequeue_data(DTQCB *p_dtqcb, intptr_t *p_data)
258{
259 *p_data = (p_dtqcb->p_dtqinib->p_dtqmb + p_dtqcb->head)->data;
260 p_dtqcb->count--;
261 p_dtqcb->head++;
262 if (p_dtqcb->head >= p_dtqcb->p_dtqinib->dtqcnt) {
263 p_dtqcb->head = 0U;
264 }
265}
266
267#endif /* TOPPERS_dtqdeq */
268
269/*
270 * データキューへのデータ送信
271 */
272#ifdef TOPPERS_dtqsnd
273
274bool_t
275send_data(DTQCB *p_dtqcb, intptr_t data, bool_t *p_dspreq)
276{
277 TCB *p_tcb;
278
279 if (!queue_empty(&(p_dtqcb->rwait_queue))) {
280 p_tcb = (TCB *) queue_delete_next(&(p_dtqcb->rwait_queue));
281 ((WINFO_DTQ *)(p_tcb->p_winfo))->data = data;
282 *p_dspreq = wait_complete(p_tcb);
283 return(true);
284 }
285 else if (p_dtqcb->count < p_dtqcb->p_dtqinib->dtqcnt) {
286 enqueue_data(p_dtqcb, data);
287 *p_dspreq = false;
288 return(true);
289 }
290 else {
291 return(false);
292 }
293}
294
295#endif /* TOPPERS_dtqsnd */
296
297/*
298 * データキューへのデータ強制送信
299 */
300#ifdef TOPPERS_dtqfsnd
301
302bool_t
303force_send_data(DTQCB *p_dtqcb, intptr_t data)
304{
305 TCB *p_tcb;
306
307 if (!queue_empty(&(p_dtqcb->rwait_queue))) {
308 p_tcb = (TCB *) queue_delete_next(&(p_dtqcb->rwait_queue));
309 ((WINFO_DTQ *)(p_tcb->p_winfo))->data = data;
310 return(wait_complete(p_tcb));
311 }
312 else {
313 force_enqueue_data(p_dtqcb, data);
314 return(false);
315 }
316}
317
318#endif /* TOPPERS_dtqfsnd */
319
320/*
321 * データキューからのデータ受信
322 */
323#ifdef TOPPERS_dtqrcv
324
325bool_t
326receive_data(DTQCB *p_dtqcb, intptr_t *p_data, bool_t *p_dspreq)
327{
328 TCB *p_tcb;
329 intptr_t data;
330
331 if (p_dtqcb->count > 0U) {
332 dequeue_data(p_dtqcb, p_data);
333 if (!queue_empty(&(p_dtqcb->swait_queue))) {
334 p_tcb = (TCB *) queue_delete_next(&(p_dtqcb->swait_queue));
335 data = ((WINFO_DTQ *)(p_tcb->p_winfo))->data;
336 enqueue_data(p_dtqcb, data);
337 *p_dspreq = wait_complete(p_tcb);
338 }
339 else {
340 *p_dspreq = false;
341 }
342 return(true);
343 }
344 else if (!queue_empty(&(p_dtqcb->swait_queue))) {
345 p_tcb = (TCB *) queue_delete_next(&(p_dtqcb->swait_queue));
346 *p_data = ((WINFO_DTQ *)(p_tcb->p_winfo))->data;
347 *p_dspreq = wait_complete(p_tcb);
348 return(true);
349 }
350 else {
351 return(false);
352 }
353}
354
355#endif /* TOPPERS_dtqrcv */
356
357/*
358 * データキューの生成
359 */
360#ifdef TOPPERS_acre_dtq
361
362ER_UINT
363acre_dtq(const T_CDTQ *pk_cdtq)
364{
365 DTQCB *p_dtqcb;
366 DTQINIB *p_dtqinib;
367 ATR dtqatr;
368 DTQMB *p_dtqmb;
369 ER ercd;
370
371 LOG_ACRE_DTQ_ENTER(pk_cdtq);
372 CHECK_TSKCTX_UNL();
373 CHECK_RSATR(pk_cdtq->dtqatr, TA_TPRI);
374 if (pk_cdtq->dtqmb != NULL) {
375 CHECK_ALIGN_MB(pk_cdtq->dtqmb);
376 }
377 dtqatr = pk_cdtq->dtqatr;
378 p_dtqmb = pk_cdtq->dtqmb;
379
380 t_lock_cpu();
381 if (tnum_dtq == 0 || queue_empty(&free_dtqcb)) {
382 ercd = E_NOID;
383 }
384 else {
385 if (pk_cdtq->dtqcnt != 0 && p_dtqmb == NULL) {
386 p_dtqmb = kernel_malloc(sizeof(DTQMB) * pk_cdtq->dtqcnt);
387 dtqatr |= TA_MBALLOC;
388 }
389 if (pk_cdtq->dtqcnt != 0 && p_dtqmb == NULL) {
390 ercd = E_NOMEM;
391 }
392 else {
393 p_dtqcb = ((DTQCB *) queue_delete_next(&free_dtqcb));
394 p_dtqinib = (DTQINIB *)(p_dtqcb->p_dtqinib);
395 p_dtqinib->dtqatr = dtqatr;
396 p_dtqinib->dtqcnt = pk_cdtq->dtqcnt;
397 p_dtqinib->p_dtqmb = p_dtqmb;
398
399 queue_initialize(&(p_dtqcb->swait_queue));
400 queue_initialize(&(p_dtqcb->rwait_queue));
401 p_dtqcb->count = 0U;
402 p_dtqcb->head = 0U;
403 p_dtqcb->tail = 0U;
404 ercd = DTQID(p_dtqcb);
405 }
406 }
407 t_unlock_cpu();
408
409 error_exit:
410 LOG_ACRE_DTQ_LEAVE(ercd);
411 return(ercd);
412}
413
414#endif /* TOPPERS_acre_dtq */
415
416/*
417 * データキューの削除
418 */
419#ifdef TOPPERS_del_dtq
420
421ER
422del_dtq(ID dtqid)
423{
424 DTQCB *p_dtqcb;
425 DTQINIB *p_dtqinib;
426 bool_t dspreq;
427 ER ercd;
428
429 LOG_DEL_DTQ_ENTER(dtqid);
430 CHECK_TSKCTX_UNL();
431 CHECK_DTQID(dtqid);
432 p_dtqcb = get_dtqcb(dtqid);
433
434 t_lock_cpu();
435 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
436 ercd = E_NOEXS;
437 }
438 else if (DTQID(p_dtqcb) > tmax_sdtqid) {
439 dspreq = init_wait_queue(&(p_dtqcb->swait_queue));
440 if (init_wait_queue(&(p_dtqcb->rwait_queue))) {
441 dspreq = true;
442 }
443 p_dtqinib = (DTQINIB *)(p_dtqcb->p_dtqinib);
444 if ((p_dtqinib->dtqatr & TA_MBALLOC) != 0U) {
445 kernel_free(p_dtqinib->p_dtqmb);
446 }
447 p_dtqinib->dtqatr = TA_NOEXS;
448 queue_insert_prev(&free_dtqcb, &(p_dtqcb->swait_queue));
449 if (dspreq) {
450 dispatch();
451 }
452 ercd = E_OK;
453 }
454 else {
455 ercd = E_OBJ;
456 }
457 t_unlock_cpu();
458
459 error_exit:
460 LOG_DEL_DTQ_LEAVE(ercd);
461 return(ercd);
462}
463
464#endif /* TOPPERS_del_dtq */
465
466/*
467 * データキューへの送信
468 */
469#ifdef TOPPERS_snd_dtq
470
471ER
472snd_dtq(ID dtqid, intptr_t data)
473{
474 DTQCB *p_dtqcb;
475 WINFO_DTQ winfo_dtq;
476 bool_t dspreq;
477 ER ercd;
478
479 LOG_SND_DTQ_ENTER(dtqid, data);
480 CHECK_DISPATCH();
481 CHECK_DTQID(dtqid);
482 p_dtqcb = get_dtqcb(dtqid);
483
484 t_lock_cpu();
485 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
486 ercd = E_NOEXS;
487 }
488 else if (send_data(p_dtqcb, data, &dspreq)) {
489 if (dspreq) {
490 dispatch();
491 }
492 ercd = E_OK;
493 }
494 else {
495 winfo_dtq.data = data;
496 p_runtsk->tstat = (TS_WAITING | TS_WAIT_SDTQ);
497 wobj_make_wait((WOBJCB *) p_dtqcb, (WINFO_WOBJ *) &winfo_dtq);
498 dispatch();
499 ercd = winfo_dtq.winfo.wercd;
500 }
501 t_unlock_cpu();
502
503 error_exit:
504 LOG_SND_DTQ_LEAVE(ercd);
505 return(ercd);
506}
507
508#endif /* TOPPERS_snd_dtq */
509
510/*
511 * データキューへの送信(ポーリング)
512 */
513#ifdef TOPPERS_psnd_dtq
514
515ER
516psnd_dtq(ID dtqid, intptr_t data)
517{
518 DTQCB *p_dtqcb;
519 bool_t dspreq;
520 ER ercd;
521
522 LOG_PSND_DTQ_ENTER(dtqid, data);
523 CHECK_TSKCTX_UNL();
524 CHECK_DTQID(dtqid);
525 p_dtqcb = get_dtqcb(dtqid);
526
527 t_lock_cpu();
528 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
529 ercd = E_NOEXS;
530 }
531 else if (send_data(p_dtqcb, data, &dspreq)) {
532 if (dspreq) {
533 dispatch();
534 }
535 ercd = E_OK;
536 }
537 else {
538 ercd = E_TMOUT;
539 }
540 t_unlock_cpu();
541
542 error_exit:
543 LOG_PSND_DTQ_LEAVE(ercd);
544 return(ercd);
545}
546
547#endif /* TOPPERS_psnd_dtq */
548
549/*
550 * データキューへの送信(ポーリング,非タスクコンテキスト用)
551 */
552#ifdef TOPPERS_ipsnd_dtq
553
554ER
555ipsnd_dtq(ID dtqid, intptr_t data)
556{
557 DTQCB *p_dtqcb;
558 bool_t dspreq;
559 ER ercd;
560
561 LOG_IPSND_DTQ_ENTER(dtqid, data);
562 CHECK_INTCTX_UNL();
563 CHECK_DTQID(dtqid);
564 p_dtqcb = get_dtqcb(dtqid);
565
566 i_lock_cpu();
567 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
568 ercd = E_NOEXS;
569 }
570 else if (send_data(p_dtqcb, data, &dspreq)) {
571 if (dspreq) {
572 reqflg = true;
573 }
574 ercd = E_OK;
575 }
576 else {
577 ercd = E_TMOUT;
578 }
579 i_unlock_cpu();
580
581 error_exit:
582 LOG_IPSND_DTQ_LEAVE(ercd);
583 return(ercd);
584}
585
586#endif /* TOPPERS_ipsnd_dtq */
587
588/*
589 * データキューへの送信(タイムアウトあり)
590 */
591#ifdef TOPPERS_tsnd_dtq
592
593ER
594tsnd_dtq(ID dtqid, intptr_t data, TMO tmout)
595{
596 DTQCB *p_dtqcb;
597 WINFO_DTQ winfo_dtq;
598 TMEVTB tmevtb;
599 bool_t dspreq;
600 ER ercd;
601
602 LOG_TSND_DTQ_ENTER(dtqid, data, tmout);
603 CHECK_DISPATCH();
604 CHECK_DTQID(dtqid);
605 CHECK_TMOUT(tmout);
606 p_dtqcb = get_dtqcb(dtqid);
607
608 t_lock_cpu();
609 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
610 ercd = E_NOEXS;
611 }
612 else if (send_data(p_dtqcb, data, &dspreq)) {
613 if (dspreq) {
614 dispatch();
615 }
616 ercd = E_OK;
617 }
618 else if (tmout == TMO_POL) {
619 ercd = E_TMOUT;
620 }
621 else {
622 winfo_dtq.data = data;
623 p_runtsk->tstat = (TS_WAITING | TS_WAIT_SDTQ);
624 wobj_make_wait_tmout((WOBJCB *) p_dtqcb, (WINFO_WOBJ *) &winfo_dtq,
625 &tmevtb, tmout);
626 dispatch();
627 ercd = winfo_dtq.winfo.wercd;
628 }
629 t_unlock_cpu();
630
631 error_exit:
632 LOG_TSND_DTQ_LEAVE(ercd);
633 return(ercd);
634}
635
636#endif /* TOPPERS_tsnd_dtq */
637
638/*
639 * データキューへの強制送信
640 */
641#ifdef TOPPERS_fsnd_dtq
642
643ER
644fsnd_dtq(ID dtqid, intptr_t data)
645{
646 DTQCB *p_dtqcb;
647 ER ercd;
648
649 LOG_FSND_DTQ_ENTER(dtqid, data);
650 CHECK_TSKCTX_UNL();
651 CHECK_DTQID(dtqid);
652 p_dtqcb = get_dtqcb(dtqid);
653
654 t_lock_cpu();
655 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
656 ercd = E_NOEXS;
657 }
658 else if (!(p_dtqcb->p_dtqinib->dtqcnt > 0U)) {
659 ercd = E_ILUSE;
660 }
661 else {
662 if (force_send_data(p_dtqcb, data)) {
663 dispatch();
664 }
665 ercd = E_OK;
666 }
667 t_unlock_cpu();
668
669 error_exit:
670 LOG_FSND_DTQ_LEAVE(ercd);
671 return(ercd);
672}
673
674#endif /* TOPPERS_fsnd_dtq */
675
676/*
677 * データキューへの強制送信(非タスクコンテキスト用)
678 */
679#ifdef TOPPERS_ifsnd_dtq
680
681ER
682ifsnd_dtq(ID dtqid, intptr_t data)
683{
684 DTQCB *p_dtqcb;
685 ER ercd;
686
687 LOG_IFSND_DTQ_ENTER(dtqid, data);
688 CHECK_INTCTX_UNL();
689 CHECK_DTQID(dtqid);
690 p_dtqcb = get_dtqcb(dtqid);
691
692 i_lock_cpu();
693 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
694 ercd = E_NOEXS;
695 }
696 else if (!(p_dtqcb->p_dtqinib->dtqcnt > 0U)) {
697 ercd = E_ILUSE;
698 }
699 else {
700 if (force_send_data(p_dtqcb, data)) {
701 reqflg = true;
702 }
703 ercd = E_OK;
704 }
705 i_unlock_cpu();
706
707 error_exit:
708 LOG_IFSND_DTQ_LEAVE(ercd);
709 return(ercd);
710}
711
712#endif /* TOPPERS_ifsnd_dtq */
713
714/*
715 * データキューからの受信
716 */
717#ifdef TOPPERS_rcv_dtq
718
719ER
720rcv_dtq(ID dtqid, intptr_t *p_data)
721{
722 DTQCB *p_dtqcb;
723 WINFO_DTQ winfo_dtq;
724 bool_t dspreq;
725 ER ercd;
726
727 LOG_RCV_DTQ_ENTER(dtqid, p_data);
728 CHECK_DISPATCH();
729 CHECK_DTQID(dtqid);
730 p_dtqcb = get_dtqcb(dtqid);
731
732 t_lock_cpu();
733 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
734 ercd = E_NOEXS;
735 }
736 else if (receive_data(p_dtqcb, p_data, &dspreq)) {
737 if (dspreq) {
738 dispatch();
739 }
740 ercd = E_OK;
741 }
742 else {
743 p_runtsk->tstat = (TS_WAITING | TS_WAIT_RDTQ);
744 make_wait(&(winfo_dtq.winfo));
745 queue_insert_prev(&(p_dtqcb->rwait_queue), &(p_runtsk->task_queue));
746 winfo_dtq.p_dtqcb = p_dtqcb;
747 LOG_TSKSTAT(p_runtsk);
748 dispatch();
749 ercd = winfo_dtq.winfo.wercd;
750 if (ercd == E_OK) {
751 *p_data = winfo_dtq.data;
752 }
753 }
754 t_unlock_cpu();
755
756 error_exit:
757 LOG_RCV_DTQ_LEAVE(ercd, *p_data);
758 return(ercd);
759}
760
761#endif /* TOPPERS_rcv_dtq */
762
763/*
764 * データキューからの受信(ポーリング)
765 */
766#ifdef TOPPERS_prcv_dtq
767
768ER
769prcv_dtq(ID dtqid, intptr_t *p_data)
770{
771 DTQCB *p_dtqcb;
772 bool_t dspreq;
773 ER ercd;
774
775 LOG_PRCV_DTQ_ENTER(dtqid, p_data);
776 CHECK_TSKCTX_UNL();
777 CHECK_DTQID(dtqid);
778 p_dtqcb = get_dtqcb(dtqid);
779
780 t_lock_cpu();
781 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
782 ercd = E_NOEXS;
783 }
784 else if (receive_data(p_dtqcb, p_data, &dspreq)) {
785 if (dspreq) {
786 dispatch();
787 }
788 ercd = E_OK;
789 }
790 else {
791 ercd = E_TMOUT;
792 }
793 t_unlock_cpu();
794
795 error_exit:
796 LOG_PRCV_DTQ_LEAVE(ercd, *p_data);
797 return(ercd);
798}
799
800#endif /* TOPPERS_prcv_dtq */
801
802/*
803 * データキューからの受信(タイムアウトあり)
804 */
805#ifdef TOPPERS_trcv_dtq
806
807ER
808trcv_dtq(ID dtqid, intptr_t *p_data, TMO tmout)
809{
810 DTQCB *p_dtqcb;
811 WINFO_DTQ winfo_dtq;
812 TMEVTB tmevtb;
813 bool_t dspreq;
814 ER ercd;
815
816 LOG_TRCV_DTQ_ENTER(dtqid, p_data, tmout);
817 CHECK_DISPATCH();
818 CHECK_DTQID(dtqid);
819 CHECK_TMOUT(tmout);
820 p_dtqcb = get_dtqcb(dtqid);
821
822 t_lock_cpu();
823 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
824 ercd = E_NOEXS;
825 }
826 else if (receive_data(p_dtqcb, p_data, &dspreq)) {
827 if (dspreq) {
828 dispatch();
829 }
830 ercd = E_OK;
831 }
832 else if (tmout == TMO_POL) {
833 ercd = E_TMOUT;
834 }
835 else {
836 p_runtsk->tstat = (TS_WAITING | TS_WAIT_RDTQ);
837 make_wait_tmout(&(winfo_dtq.winfo), &tmevtb, tmout);
838 queue_insert_prev(&(p_dtqcb->rwait_queue), &(p_runtsk->task_queue));
839 winfo_dtq.p_dtqcb = p_dtqcb;
840 LOG_TSKSTAT(p_runtsk);
841 dispatch();
842 ercd = winfo_dtq.winfo.wercd;
843 if (ercd == E_OK) {
844 *p_data = winfo_dtq.data;
845 }
846 }
847 t_unlock_cpu();
848
849 error_exit:
850 LOG_TRCV_DTQ_LEAVE(ercd, *p_data);
851 return(ercd);
852}
853
854#endif /* TOPPERS_trcv_dtq */
855
856/*
857 * データキューの再初期化
858 */
859#ifdef TOPPERS_ini_dtq
860
861ER
862ini_dtq(ID dtqid)
863{
864 DTQCB *p_dtqcb;
865 bool_t dspreq;
866 ER ercd;
867
868 LOG_INI_DTQ_ENTER(dtqid);
869 CHECK_TSKCTX_UNL();
870 CHECK_DTQID(dtqid);
871 p_dtqcb = get_dtqcb(dtqid);
872
873 t_lock_cpu();
874 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
875 ercd = E_NOEXS;
876 }
877 else {
878 dspreq = init_wait_queue(&(p_dtqcb->swait_queue));
879 if (init_wait_queue(&(p_dtqcb->rwait_queue))) {
880 dspreq = true;
881 }
882 p_dtqcb->count = 0U;
883 p_dtqcb->head = 0U;
884 p_dtqcb->tail = 0U;
885 if (dspreq) {
886 dispatch();
887 }
888 ercd = E_OK;
889 }
890 t_unlock_cpu();
891
892 error_exit:
893 LOG_INI_DTQ_LEAVE(ercd);
894 return(ercd);
895}
896
897#endif /* TOPPERS_ini_dtq */
898
899/*
900 * データキューの状態参照
901 */
902#ifdef TOPPERS_ref_dtq
903
904ER
905ref_dtq(ID dtqid, T_RDTQ *pk_rdtq)
906{
907 DTQCB *p_dtqcb;
908 ER ercd;
909
910 LOG_REF_DTQ_ENTER(dtqid, pk_rdtq);
911 CHECK_TSKCTX_UNL();
912 CHECK_DTQID(dtqid);
913 p_dtqcb = get_dtqcb(dtqid);
914
915 t_lock_cpu();
916 if (p_dtqcb->p_dtqinib->dtqatr == TA_NOEXS) {
917 ercd = E_NOEXS;
918 }
919 else {
920 pk_rdtq->stskid = wait_tskid(&(p_dtqcb->swait_queue));
921 pk_rdtq->rtskid = wait_tskid(&(p_dtqcb->rwait_queue));
922 pk_rdtq->sdtqcnt = p_dtqcb->count;
923 ercd = E_OK;
924 }
925 t_unlock_cpu();
926
927 error_exit:
928 LOG_REF_DTQ_LEAVE(ercd, pk_rdtq);
929 return(ercd);
930}
931
932#endif /* TOPPERS_ref_dtq */
Note: See TracBrowser for help on using the repository browser.