source: azure_iot_hub/trunk/asp3_dcre/tecsgen/tecslib/plugin/SharedOpaqueRPCPlugin.rb@ 388

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

Azure IoT Hub Device C SDK を使ったサンプルの追加

  • Property svn:eol-style set to native
  • Property svn:mime-type set to text/x-ruby
File size: 13.1 KB
Line 
1# -*- coding: utf-8 -*-
2#
3# TECS Generator
4# Generator for TOPPERS Embedded Component System
5#
6# Copyright (C) 2008-2014 by TOPPERS Project
7#--
8# 上記著作権者
9は,以下の(1)~(4)の条件を満たす場合に限り,本ソフトウェ
10# ア(本ソフトウェアを改変したものを含む.以下同じ)を使用・複製・改
11# 変・再é…
12å¸ƒï¼ˆä»¥ä¸‹ï¼Œåˆ©ç”¨ã¨å‘¼ã¶ï¼‰ã™ã‚‹ã“とを無償で許諾する.
13# (1) 本ソフトウェアをソースコードの形で利用する場合には,上記の著作
14# 権表示,この利用条件および下記の無保証規定が,そのままの形でソー
15# スコード中に含まれていること.
16# (2) 本ソフトウェアを,ライブラリ形式など,他のソフトウェア開発に使
17# 用できる形で再é…
18å¸ƒã™ã‚‹å ´åˆã«ã¯ï¼Œå†é…
19å¸ƒã«ä¼´ã†ãƒ‰ã‚­ãƒ¥ãƒ¡ãƒ³ãƒˆï¼ˆåˆ©ç”¨
20# 者
21マニュアルなど)に,上記の著作権表示,この利用条件および下記
22# の無保証規定を掲載すること.
23# (3) 本ソフトウェアを,機器に組み込むなど,他のソフトウェア開発に使
24# 用できない形で再é…
25å¸ƒã™ã‚‹å ´åˆã«ã¯ï¼Œæ¬¡ã®ã„ずれかの条件を満たすこ
26# と.
27# (a) 再é…
28å¸ƒã«ä¼´ã†ãƒ‰ã‚­ãƒ¥ãƒ¡ãƒ³ãƒˆï¼ˆåˆ©ç”¨è€…
29マニュアルなど)に,上記の著
30# 作権表示,この利用条件および下記の無保証規定を掲載すること.
31# (b) 再é…
32å¸ƒã®å½¢æ…
33‹ã‚’,別に定める方法によって,TOPPERSプロジェクトに
34# 報告すること.
35# (4) 本ソフトウェアの利用により直接的または間接的に生じるいかなる損
36# 害からも,上記著作権者
37およびTOPPERSプロジェクトをå…
38è²¬ã™ã‚‹ã“と.
39# また,本ソフトウェアのユーザまたはエンドユーザからのいかなる理
40# 由に基づく請求からも,上記著作権者
41およびTOPPERSプロジェクトを
42# å…
43è²¬ã™ã‚‹ã“と.
44#
45# 本ソフトウェアは,無保証で提供されているものである.上記著作権者
46お
47# よびTOPPERSプロジェクトは,本ソフトウェアに関して,特定の使用目的
48# に対する適合性も含めて,いかなる保証も行わない.また,本ソフトウェ
49# アの利用により直接的または間接的に生じたいかなる損害に関しても,そ
50# の責任を負わない.
51#
52# $Id$
53#++
54
55require_tecsgen_lib "lib/GenOpaqueMarshaler.rb"
56require_tecsgen_lib "lib/GenParamCopy.rb"
57
58#= SharedOpaqueRPC プラグイン
59# SharedOpaqueRPC チャンネルを生成する
60# プラグイン引数は GenTransparentMarshaler 参ç…
61§
62
63# mikan through plugin: namespace が考æ…
64®ã•ã‚Œã¦ã„ない
65# これを利用する場合、以下のように toppers_jsp.cdl sChannel.cdl を指定する必
66要がある
67# tecsgen toppers_jsp.cdl sChannel.cdl your_description.cdl
68
69# 以下を仮定(制限事項
70)
71# 呼びå…
72ƒã€å‘¼ã³å…
73ˆã®ã‚¨ãƒ³ãƒ‡ã‚£ã‚¢ãƒ³ã€char, short, int_t, long_t, intptr_t のサイズが同じ
74# 有符号、無符号でサイズが同じ
75
76class SharedOpaqueRPCPlugin < ThroughPlugin
77
78 # チャンネルをå…
79±æœ‰ã™ã‚‹ãƒ—ラグインオブジェクトへのハッシュリスト
80 @@shared_channel_list = {} # { chan_name => [ Plugin_obj0, Plugin_Obj1, ... ] }
81
82 attr_reader :cell_name, :start_region, :end_region
83 include GenOpaqueMarshaler
84 include GenParamCopy
85
86 # SharedOpaqueRPCPlugin 専用のオプション
87 SharedOpaqueRPCPluginArgProc = RPCPluginArgProc.dup # 複製を作ってå…
88ƒã‚’変更しないようにする
89 SharedOpaqueRPCPluginArgProc[ "sharedChannelName" ] = Proc.new { |obj,rhs| obj.set_sharedChannelName rhs }
90
91 #=== RPCPlugin の initialize
92 # 説明は ThroughPlugin (plugin.rb) を参ç…
93§
94 def initialize( cell_name, plugin_arg, next_cell, next_cell_port_name, next_cell_port_subscript, signature, celltype, caller_cell )
95 super
96 initialize_opaque_marshaler
97 @entry_port_name = :"eClientEntry" # Marshaler の受け口名 (through セルのå…
98¥ã‚Šå£)
99
100 # オプション:GenOpaqueMarshaler 参ç…
101§
102 @plugin_arg_check_proc_tab = SharedOpaqueRPCPluginArgProc
103 @sharedChannelName = nil
104 parse_plugin_arg
105 check_opener_code
106 check_PPAllocator
107
108 @shared_channel_ct_name = :"tSharedOpaqueRPCPluginChannel_tTDR"
109 @shared_channel_server_ct_name = :"#{@shared_channel_ct_name}_Server"
110 @shared_channel_client_ct_name = :"#{@shared_channel_ct_name}_Client"
111 @shared_channel_ct_file_name = "#{$gen}/#{@shared_channel_ct_name}.cdl"
112 if @sharedChannelName == nil then
113 cdl_error( "'sharedChannelName' option: mandatory")
114 else
115 @shared_channel_cell = @sharedChannelName
116 end
117
118 if @@shared_channel_list[ @shared_channel_cell ] == nil then
119 @@shared_channel_list[ @shared_channel_cell ] = [ self ]
120 else
121 @@shared_channel_list[ @shared_channel_cell ] << self
122 end
123 @sub_channel_no = ( @@shared_channel_list[ @shared_channel_cell ].length ) -1
124
125 prev_start = @@shared_channel_list[ @shared_channel_cell ][0].start_region
126 if @start_region != prev_start then
127 # 初出と start リージョン不一致 (初出は、自分自身とチェックされる。無駄だが小さいので放置)
128 cdl_error( "SharedRPCPlugin: start region mismatch current: #{@region.get_name} previous: #{prev_start.get_name}")
129 end
130
131 prev_end = @@shared_channel_list[ @shared_channel_cell ][0].end_region
132 if @end_region != prev_end then
133 # 初出と end リージョン不一致 (初出は、自分自身とチェックされる。無駄だが小さいので放置)
134 cdl_error( "SharedRPCPlugin: end region mismatch current: #{@region.get_name} previous: #{prev_end.get_name}")
135 end
136
137 end
138
139 # def set_through_info( start_region, end_region, through_type )
140 # super
141 # end
142
143 #=== プラグイン引数 sharedChannelCell のチェック
144 def set_sharedChannelName( rhs )
145 @sharedChannelName = rhs
146 # path = [ "::", rhs ]
147 # obj = Namespace.find( path )
148 # if ! obj.instance_of?( Cell ) then
149 # cdl_error( "SharedOpaqueRPCPlugin: sharedChannelName '#{rhs}' not cell" )
150 # end
151 end
152
153 def gen_plugin_decl_code( file )
154
155 # このセルタイプ(同じシグニチャ)は既に生成されているか?
156 if @@generated_celltype[ @shared_channel_server_ct_name ] == nil then
157 @@generated_celltype[ @shared_channel_server_ct_name ] = [ self ]
158 else
159 @@generated_celltype[ @shared_channel_server_ct_name ] << self
160 end
161
162 gen_marshaler_celltype
163
164 # 同じ内
165容を二度書く可能性あり (AppFile は不可)
166
167 if @PPAllocatorSize then
168 alloc_call_port = " call sPPAllocator cPPAllocator;\n"
169 alloc_call_port_join = " cPPAllocator => composite.cPPAllocator;\n"
170 else
171 alloc_call_port = ""
172 alloc_call_port_join = ""
173 end
174
175 f = CFile.open( @shared_channel_ct_file_name, "w" )
176 # 同じ内
177容を二度書く可能性あり (AppFile は不可)
178
179 f.print <<EOT
180
181/* Shared Channel Celltype for Client */
182composite #{@shared_channel_client_ct_name} {
183 entry sTDR eTDR;
184 entry sSemaphore eSemaphore[];
185 call sChannel cClientChannel;
186
187 cell tTDR TDR {
188 cChannel => composite.cClientChannel;
189 };
190 cell tSemaphore Semaphore {
191 count = 1;
192 attribute = C_EXP("TA_NULL");
193 };
194 cell tRPCSharedChannelMan SharedChannelMan{
195 cSemaphore = Semaphore.eSemaphore;
196 cClientSideTDR = TDR.eTDR;
197 };
198 composite.eSemaphore => SharedChannelMan.eSemaphore;
199 composite.eTDR => TDR.eTDR;
200};
201
202/* Shared Channel Celltype for Server */
203[active]
204composite #{@shared_channel_server_ct_name} {
205 entry sTDR eTDR;
206 call sChannel cServerChannel;
207 call sUnmarshalerMain cUnmarshalAndCallFunction[];
208 call sServerChannelOpener cOpener;
209 attr {
210 PRI priority;
211 };
212
213 cell tTDR TDR {
214 cChannel => composite.cServerChannel;
215 };
216 cell tRPCSharedTaskMainWithOpener RPCSharedTaskMain {
217 cUnmarshalAndCallFunction => composite.cUnmarshalAndCallFunction;
218 cServerSideTDR = TDR.eTDR;
219 cOpener => composite.cOpener;
220 };
221 cell tTask Task {
222 cBody = RPCSharedTaskMain.eMain;
223 taskAttribute = C_EXP("TA_ACT");
224 stackSize = 4096;
225 priority = composite.priority;
226 };
227 composite.eTDR => TDR.eTDR;
228};
229
230EOT
231 f.close
232
233 end
234
235 #=== through cell コードを生成
236 #
237 #
238 def gen_through_cell_code( file )
239
240 gen_plugin_decl_code( file )
241
242 file.print <<EOT
243
244import( "#{@marshaler_celltype_file_name}" );
245import( "#{@shared_channel_ct_file_name}" );
246EOT
247
248# nest = @caller_cell.get_region.gen_region_str_pre file
249 nest = @start_region.gen_region_str_pre file
250 indent_str = " " * nest
251 nest_str = " " * nest
252 if @next_cell_port_subscript then
253 subscript = '[' + @next_cell_port_subscript.to_s + ']'
254 else
255 subscript = ""
256 end
257
258 # セルを探す
259 # path =["::",@next_cell.get_name]
260 # cell = Namespace.find( path )
261 cell = Namespace.find( @next_cell.get_namespace_path )
262
263 # å…
264±æœ‰ã•ã‚Œã‚‹é€šä¿¡ãƒãƒ£ãƒ³ãƒãƒ«ã®ç”Ÿæˆã®ãƒ—ロトタイプ宣言
265 file.print <<EOT
266#{indent_str}cell #{@shared_channel_client_ct_name} #{@shared_channel_cell};
267EOT
268
269 # マーシャラセルの生成(アロケータコードの生成から)
270 # アロケータの指定があるか?
271 if cell.get_allocator_list.length > 0 then
272
273 file.print "#{indent_str}[allocator("
274
275 delim = ""
276 cell.get_allocator_list.each do |type, eport, subsc, func, buf, alloc|
277
278 alloc_str = alloc.to_s
279 subst = @substituteAllocator[alloc_str.to_sym]
280
281 if subst then
282 alloc_str = subst[2]+"."+subst[3]
283 end
284
285 file.print delim
286 delim = ",\n#{indent_str} " # 最終行には出さない
287
288 if subsc then # é…
289åˆ—添数
290 subsc_str = '[#{subsc}]'
291 else
292 subsc_str = ""
293 end
294
295 eport = @entry_port_name #RPCの受け口名に変更
296 file.print "#{eport}#{subsc_str}.#{func}.#{buf} = #{alloc_str}"
297 end
298
299 file.puts ")]"
300 end
301
302 # マーシャラセル本体生成
303 file.print <<EOT
304/* OpaqueRPC Marshaler Cell */
305#{indent_str}cell #{@marshaler_celltype_name} #{@cell_name} {
306#{indent_str} cTDR = #{@shared_channel_cell}.eTDR;
307#{indent_str} cLockChannel = #{@shared_channel_cell}.eSemaphore[#{@sub_channel_no}];
308#{indent_str}};
309EOT
310 # @caller_cell.get_region.gen_region_str_post file
311 @start_region.gen_region_str_post file
312
313 # アンマーシャラセルの出力
314 # セル本体の生成
315 nest = @end_region.gen_region_str_pre file
316
317 file.print <<EOT
318/* Server Channel Cell prototype */
319#{indent_str}cell #{@shared_channel_server_ct_name} #{@sharedChannelName}_Server;
320
321EOT
322
323 # PPAllocator が必
324要か?
325 if @PPAllocatorSize then
326 if @sub_channel_no == 0 then
327 file.print <<EOT
328#{indent_str}cell tPPAllocator PPAllocator_#{@shared_channel_cell}{
329#{indent_str} heapSize = #{@PPAllocatorSize};
330#{indent_str}};
331EOT
332 end
333
334 ppallocator_join = "#{indent_str} cPPAllocator = PPAllocator_#{@shared_channel_cell}.ePPAllocator;\n"
335 else
336 ppallocator_join = ""
337 end
338
339 file.print <<EOT
340#{indent_str}cell #{@unmarshaler_celltype_name} #{@cell_name}_Server {
341#{indent_str} cTDR = #{@shared_channel_cell}_Server.eTDR;
342#{indent_str} cServerCall = #{@next_cell.get_namespace_path.get_path_str}.#{@next_cell_port_name}#{subscript};
343#{ppallocator_join}#{indent_str}};
344EOT
345 @end_region.gen_region_str_post file
346
347 end
348
349 #=== post コード(CDL) を生成
350 # プラグインの後のコードを生成
351 #file:: File:
352 def self.gen_post_code( file )
353
354 file.print "/* '#{self.name}' post code */\n"
355
356 @@shared_channel_list.each{ |chan_name,plugin_obj_array|
357 file.print "/* '#{chan_name}' shared channel */\n"
358 plugin_obj_array[0].gen_post_code( file, plugin_obj_array )
359 }
360
361 end
362
363 #=== post コード(CDL) を生成
364 # å…
365±æœ‰ãƒãƒ£ãƒ³ãƒãƒ«ã‚’生成する
366 # このメソッドは、チャンネルをå…
367±æœ‰ã™ã‚‹æœ€åˆã®ãƒ—ラグインオブジェクトのみ呼び出される
368 def gen_post_code( file, plugin_obj_array )
369
370 # å…
371±æœ‰ã•ã‚Œã¦ã„る通信チャンネルの生成
372 # 各プラグインインスタンスでは @shared_channel_ct_name として記憶している
373 # region = @caller_cell.get_region
374 nest = @start_region.gen_region_str_pre file
375 indent_str = " " * nest
376 file.print <<EOT
377#{indent_str}cell #{@shared_channel_client_ct_name} #{@sharedChannelName} {
378#{indent_str} cClientChannel = #{@clientChannelCell}.eC0;
379#{indent_str}};
380EOT
381 @start_region.gen_region_str_post file
382
383 nest = @end_region.gen_region_str_pre file
384 indent_str = " " * nest
385 file.print "#{indent_str}cell #{@shared_channel_server_ct_name} #{@sharedChannelName}_Server {\n"
386 file.print <<EOT
387#{indent_str} cServerChannel = #{@serverChannelCell}.eC1;
388#{indent_str} cOpener = #{@serverChannelCell}.eOpener;
389EOT
390 plugin_obj_array.each{ |po|
391 file.print <<EOT
392#{indent_str} cUnmarshalAndCallFunction[] = #{po.cell_name}_Server.eService;
393EOT
394 }
395 file.printf <<EOT
396#{indent_str} priority = #{@taskPriority};
397#{indent_str}};
398EOT
399 @end_region.gen_region_str_post file
400
401 end
402end
403
404
Note: See TracBrowser for help on using the repository browser.