source: rubycfg_ssp/trunk/kernel.trb@ 285

Last change on this file since 285 was 285, checked in by nmir-saito, 7 years ago

Tracのソース閲覧時に文字化けするためmimetypewo

  • Property svn:mime-type set to text/plain; charset=utf-8
File size: 11.8 KB
Line 
1# -*- coding: utf-8 -*-
2#
3# TOPPERS/SSP Kernel
4# Toyohashi Open Platform for Embedded Real-Time Systems/
5# Advanced Standard Profile Kernel
6#
7# Copyright (C) 2015 by FUJI SOFT INCORPORATED, JAPAN
8# Copyright (C) 2015,2016 by Embedded and Real-Time Systems Laboratory
9# Graduate School of Information Science, Nagoya Univ., JAPAN
10# Copyright (C) 2017 by Naoki Saito
11# Nagoya Municipal Industrial Research Institute, JAPAN
12#
13# 上記著作権者は,以下の(1)〜(4)の条件を満たす場合に限り,本ソフトウェ
14# ア(本ソフトウェアを改変したものを含む.以下同じ)を使用・複製・改
15# 変・再配布(以下,利用と呼ぶ)することを無償で許諾する.
16# (1) 本ソフトウェアをソースコードの形で利用する場合には,上記の著作
17# 権表示,この利用条件および下記の無保証規定が,そのままの形でソー
18# スコード中に含まれていること.
19# (2) 本ソフトウェアを,ライブラリ形式など,他のソフトウェア開発に使
20# 用できる形で再配布する場合には,再配布に伴うドキュメント(利用
21# 者マニュアルなど)に,上記の著作権表示,この利用条件および下記
22# の無保証規定を掲載すること.
23# (3) 本ソフトウェアを,機器に組み込むなど,他のソフトウェア開発に使
24# 用できない形で再配布する場合には,次のいずれかの条件を満たすこ
25# と.
26# (a) 再配布に伴うドキュメント(利用者マニュアルなど)に,上記の著
27# 作権表示,この利用条件および下記の無保証規定を掲載すること.
28# (b) 再配布の形態を,別に定める方法によって,TOPPERSプロジェクトに
29# 報告すること.
30# (4) 本ソフトウェアの利用により直接的または間接的に生じるいかなる損
31# 害からも,上記著作権者およびTOPPERSプロジェクトを免責すること.
32# また,本ソフトウェアのユーザまたはエンドユーザからのいかなる理
33# 由に基づく請求からも,上記著作権者およびTOPPERSプロジェクトを
34# 免責すること.
35#
36# 本ソフトウェアは,無保証で提供されているものである.上記著作権者お
37# よびTOPPERSプロジェクトは,本ソフトウェアに関して,特定の使用目的
38# に対する適合性も含めて,いかなる保証も行わない.また,本ソフトウェ
39# アの利用により直接的または間接的に生じたいかなる損害に関しても,そ
40# の責任を負わない.
41#
42# $Id: kernel.trb 670 2016-03-03 15:08:11Z ertl-hiro $
43#
44
45#
46# コンフィギュレータのパス2の生成スクリプト
47#
48
49#
50# タイムスタンプファイルの指定
51#
52$timeStampFileName = "kernel_cfg.timestamp"
53
54#
55# kernel_cfg.hの先頭部分の生成
56#
57$kernelCfgH = GenFile.new("kernel_cfg.h")
58$kernelCfgH.add(<<EOS)
59/* kernel_cfg.h */
60#ifndef TOPPERS_KERNEL_CFG_H
61#define TOPPERS_KERNEL_CFG_H
62EOS
63
64#
65# kernel_cfg.cの先頭部分の生成
66#
67$kernelCfgC = GenFile.new("kernel_cfg.c")
68$kernelCfgC.add(<<EOS)
69/* kernel_cfg.c */
70#include "kernel/kernel_int.h"
71#include "kernel_cfg.h"
72
73#ifndef TOPPERS_EMPTY_LABEL
74#define TOPPERS_EMPTY_LABEL(x,y) x y[0]
75#endif
76EOS
77
78#
79# インクルードディレクティブ(#include)
80#
81$kernelCfgC.comment_header("Include Directives")
82$includeFiles.each do |file|
83 $kernelCfgC.add("#include #{file}")
84end
85$kernelCfgC.add()
86
87#
88# スタック領域の確保関数
89#
90# スタック領域の定義分と,スタック領域のサイズ記述を配列で返す.
91#
92unless defined? AllocStack()
93 def AllocStack(stack, size)
94 # 大きい方に丸めたサイズで確保する
95 $kernelCfgC.add("static STK_T #{stack}[COUNT_STK_T(#{size})];")
96 return("ROUND_STK_T(#{size})")
97 end
98end
99
100#
101# カーネルオブジェクトに関する情報の生成(仮想クラス)
102#
103class KernelObject
104 def initialize(obj, object)
105 @obj = obj
106 @OBJ = obj.tr("a-z", "A-Z")
107 @object = object
108 @objid = (obj + "id").to_sym
109 @api = "CRE_#{@OBJ}".to_sym
110 end
111
112 # オブジェクトのID番号のマクロ定義生成
113 def generateIdMacro()
114 $cfgData[@api].sort.each do |key, params|
115 $kernelCfgH.add("#define #{params[@objid]}\t#{params[@objid].val}")
116 end
117 $kernelCfgH.add()
118 end
119
120 def generate()
121 # kernel_cfg.hの生成
122 $kernelCfgH.add("#define TNUM_#{@OBJ}ID\t#{$cfgData[@api].size}")
123
124 # オブジェクトのID番号のマクロ定義の生成
125 generateIdMacro()
126
127 # オブジェクトのID番号を保持する変数
128 if $USE_EXTERNAL_ID
129 $cfgData[@api].sort.each do |key, params|
130 $kernelCfgC.add("const ID #{params[@objid]}_id" \
131 " = #{params[@objid].val};")
132 end
133 $kernelCfgC.add()
134 end
135
136 # オブジェクトID番号の最大値
137 $kernelCfgC.add2("const ID _kernel_tmax_#{@obj}id" \
138 " = (TMIN_#{@OBJ}ID + TNUM_#{@OBJ}ID - 1);")
139
140 # データ構造の生成
141 if respond_to?(:generateData)
142 generateData()
143 end
144
145 if $cfgData[@api].size() > 0
146 # オブジェクト初期化関数の追加
147 $initializeFunctions.push("_kernel_initialize_#{@object}();")
148 end
149 end
150end
151
152#
153# 各機能モジュールのコンフィギュレーション
154#
155$initializeFunctions = []
156IncludeTrb("kernel/task.trb")
157IncludeTrb("extension/eventflag.trb")
158IncludeTrb("extension/dataqueue.trb")
159IncludeTrb("extension/cyclic.trb")
160IncludeTrb("extension/alarm.trb")
161IncludeTrb("kernel/interrupt.trb")
162IncludeTrb("kernel/exception.trb")
163
164#
165# 非タスクコンテキスト用のスタック領域
166#
167$kernelCfgC.comment_header("Stack Area for Non-task Context")
168
169# 非タスクコンテキスト用スタック領域のサイズ
170$istksz = 0
171
172# DEF_ICSのエントリが存在するか?
173if $cfgData[:DEF_ICS].size == 0
174 # ない場合,サイズは既定値(DEFAULT_ISTKSZ)を使う
175 $kernelCfgC.add2("#define TOPPERS_ISTKSZ DEFAULT_ISTKSZ")
176 $istksz = $DEFAULT_ISTKSZ
177else
178 # DEF_ICS のエントリがある場合
179
180 # 静的API「DEF_ICS」が複数ある(E_OBJ)
181 if $cfgData[:DEF_ICS].size > 1
182 error("E_OBJ: too many DEF_ICS")
183 end
184
185 params = $cfgData[:DEF_ICS][1]
186
187 # istksz に 0 を指定した場合(E_PAR)
188 if params[:istksz] == 0
189 error_wrong("E_PAR", params, :istksz, "size is 0")
190 # istk は常に NULL である (E_PAR)
191 elsif params[:istk] != "NULL"
192 error_wrong("E_PAR", params, :istk, "must be NULL")
193 end
194
195 $istksz = params[:istksz]
196 $kernelCfgC.add2("#define TOPPERS_ISTKSZ\t(#{$istksz})")
197end
198
199#
200# 共有スタック領域
201# SSPではすべての処理単位のスタックを共有するため,
202# ここでシステム全体のスタック領域を確保する.
203#
204
205#
206# 共有スタックのコンフィギュレーションに成功したかどうか
207# DEF_STK 処理中にエラーが発生した場合,この変数が false になる.
208#
209$defstk_success = true
210
211$kernelCfgC.comment_header("Stack Area for System")
212
213# 共有スタックのサイズ
214$stksz = 0
215
216stk_str = ""
217stksz_str = ""
218
219# DEF_STK のエントリが存在するか?
220if $cfgData[:DEF_STK].size == 0
221 # (1) DEF_STK のエントリがない場合
222 stk_str = "_kernel_stack"
223 stksz_str = AllocStack(stk_str, "TOPPERS_TSTKSZ+TOPPERS_ISTKSZ")
224
225 $stksz = $tstksz + $istksz
226else
227 # (2) DEF_STK のエントリがある場合
228
229 # 静的API「DEF_STK」が複数ある(E_OBJ)
230 if $cfgData[:DEF_STK].size > 1
231 $defstk_success = false
232 error("E_OBJ: too many DEF_STK")
233 end
234
235 params = $cfgData[:DEF_STK][1]
236
237 # DEF_STK の stksz で 0 を指定した場合(E_PAR)
238 if params[:stksz] == 0
239 $defstk_success = false
240 error_wrong("E_PAR", params, :stksz, "not allowed")
241 end
242
243 $stksz = params[:stksz]
244
245 if params[:stk] == "NULL"
246 # stk が NULL の場合,スタック領域を自動割付け
247 stk_str = "_kernel_stack"
248 stksz_str = AllocStack(stk_str, "#{$stksz}")
249 else
250 # stk が NULL 以外の場合(アプリ側でスタック領域を用意する場合)
251
252 # stksz がターゲット毎に定まるアライメントサイズの倍数にアライメントされていない場合(E_PAR)
253 if (defined? $CHECK_STKSZ_ALIGN) && (($stksz & ($CHECK_STKSZ_ALIGN - 1)) != 0)
254 $defstk_success = false
255 error_wrong("E_PAR", params, :stksz, "not aligned")
256 end
257
258 stk_str = params[:stk]
259 stksz_str = $stksz
260 end
261end
262
263#
264# 共有スタックのスタック領域
265#
266$kernelCfgC.add(<<EOS)
267#define TOPPERS_STK (#{stk_str})
268#define TOPPERS_STKSZ (#{stksz_str})
269
270const SIZE\t_kernel_stksz = TOPPERS_STKSZ;
271STK_T *const\t_kernel_stk = TOPPERS_STK;
272
273#ifdef TOPPERS_ISTKPT
274STK_T *const\t_kernel_istkpt = TOPPERS_ISTKPT(TOPPERS_STK, TOPPERS_STKSZ);
275#endif /* TOPPERS_ISTKPT */
276EOS
277
278#
279# 優先度割り当ておよびスタック設定に関する結果を標準出力へ表示
280# その際,スタックサイズの指定値が実際の割当てサイズより大きいかを確認する.
281#
282if $defepr_success && $defstk_success
283 result_str = <<EOS
284=====================================
285Stack size configuration result:
286\tEstimated task stack size = #{$tstksz}
287\tSpecified interrupt stack size = #{$istksz}(value=#{sprintf("%d", $istksz)})
288\tAllocated total stack size = #{$stksz}(value=#{sprintf("%d", $stksz)})
289EOS
290
291 print(result_str)
292 if $tstksz + $istksz > $stksz
293 print("\t!!!WARNING!!!: Estimated stack size is more than the allocated stack size.")
294 warning("Estimated stack size is more than the allocated stack size.")
295 end
296 print("=====================================\n")
297end
298
299#
300# タイムイベント管理
301#
302tnum_tmevt = $cfgData[:CRE_CYC].size + $cfgData[:CRE_ALM].size
303$kernelCfgC.comment_header("Time Event Management")
304$kernelCfgC.add(<<EOS)
305#define TNUM_TMEVT #{sprintf("%d", tnum_tmevt)}
306
307const uint_t _kernel_tnum_tmevt_queue = TNUM_TMEVT;
308
309QUEUE _kernel_tmevt_queue[TNUM_TMEVT+1];
310EVTTIM _kernel_tmevt_time[TNUM_TMEVT];
311CBACK _kernel_tmevt_callback[TNUM_TMEVT];
312uintptr_t _kernel_tmevt_arg[TNUM_TMEVT];
313EOS
314
315if tnum_tmevt > 0
316 # オブジェクト初期化関数の追加
317 $initializeFunctions.unshift("_kernel_initialize_time_event();")
318end
319
320#
321# 各モジュールの初期化関数
322#
323$kernelCfgC.comment_header("Module Initialization Function")
324$kernelCfgC.append(<<EOS)
325void
326_kernel_initialize_object(void)
327{
328EOS
329$initializeFunctions.each do |func|
330 $kernelCfgC.add("\t#{func}")
331end
332$kernelCfgC.add2("}")
333
334#
335# 初期化ルーチン機能
336#
337$kernelCfgC.comment_header("Initialization Routine")
338
339# エラーチェック
340$cfgData[:ATT_INI].each do |key, params|
341 # iniatrが無効の場合(E_RSATR)
342 #(TA_NULLでない場合)
343 if (params[:iniatr] != $TA_NULL)
344 error_illegal_sym("E_RSATR", params, :iniatr, :inirtn)
345 end
346end
347
348# 初期化ルーチンの実行関数の生成
349$kernelCfgC.append(<<EOS)
350void
351_kernel_call_inirtn(void)
352{
353EOS
354$cfgData[:ATT_INI].each do |key, params|
355 $kernelCfgC.add("\t((INIRTN)(#{params[:inirtn]}))" \
356 "((intptr_t)(#{params[:exinf]}));")
357end
358$kernelCfgC.add2("}")
359
360#
361# 終了処理ルーチン機能
362#
363$kernelCfgC.comment_header("Termination Routine")
364
365# エラーチェック
366$cfgData[:ATT_TER].each do |key, params|
367 # teratrが無効の場合(E_RSATR)
368 #(TA_NULLでない場合)
369 if (params[:teratr] != $TA_NULL)
370 error_illegal_sym("E_RSATR", params, :teratr, :terrtn)
371 end
372end
373
374# 終了処理ルーチンの実行関数の生成
375$kernelCfgC.append(<<EOS)
376void
377_kernel_call_terrtn(void)
378{
379EOS
380$cfgData[:ATT_TER].reverse_each do |key, params|
381 $kernelCfgC.add("\t((TERRTN)(#{params[:terrtn]}))" \
382 "((intptr_t)(#{params[:exinf]}));")
383end
384$kernelCfgC.add2("}")
385
386#
387# kernel_cfg.hの末尾部分の生成
388#
389$kernelCfgH.append(<<EOS)
390#endif /* TOPPERS_KERNEL_CFG_H */
391EOS
Note: See TracBrowser for help on using the repository browser.