source: azure_iot_hub/trunk/ntshell/echonet/echonet.c@ 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:keywords set to Id
  • Property svn:mime-type set to text/x-csrc
File size: 23.0 KB
RevLine 
[388]1/*
2 * TOPPERS ECHONET Lite Communication Middleware
3 *
4 * Copyright (C) 2014 Cores Co., Ltd. Japan
5 *
6 * 上記著作権者
7は,以下の(1)~(4)の条件を満たす場合に限り,本ソフトウェ
8 * ア(本ソフトウェアを改変したものを含む.以下同じ)を使用・複製・改
9 * 変・再é…
10å¸ƒï¼ˆä»¥ä¸‹ï¼Œåˆ©ç”¨ã¨å‘¼ã¶ï¼‰ã™ã‚‹ã“とを無償で許諾する.
11 * (1) 本ソフトウェアをソースコードの形で利用する場合には,上記の著作
12 * 権表示,この利用条件および下記の無保証規定が,そのままの形でソー
13 * スコード中に含まれていること.
14 * (2) 本ソフトウェアを,ライブラリ形式など,他のソフトウェア開発に使
15 * 用できる形で再é…
16å¸ƒã™ã‚‹å ´åˆã«ã¯ï¼Œå†é…
17å¸ƒã«ä¼´ã†ãƒ‰ã‚­ãƒ¥ãƒ¡ãƒ³ãƒˆï¼ˆåˆ©ç”¨
18 * 者
19マニュアルなど)に,上記の著作権表示,この利用条件および下記
20 * の無保証規定を掲載すること.
21 * (3) 本ソフトウェアを,機器に組み込むなど,他のソフトウェア開発に使
22 * 用できない形で再é…
23å¸ƒã™ã‚‹å ´åˆã«ã¯ï¼Œæ¬¡ã®ã„ずれかの条件を満たすこ
24 * と.
25 * (a) 再é…
26å¸ƒã«ä¼´ã†ãƒ‰ã‚­ãƒ¥ãƒ¡ãƒ³ãƒˆï¼ˆåˆ©ç”¨è€…
27マニュアルなど)に,上記の著
28 * 作権表示,この利用条件および下記の無保証規定を掲載すること.
29 * (b) 再é…
30å¸ƒã®å½¢æ…
31‹ã‚’,別に定める方法によって,TOPPERSプロジェクトに
32 * 報告すること.
33 * (4) 本ソフトウェアの利用により直接的または間接的に生じるいかなる損
34 * 害からも,上記著作権者
35およびTOPPERSプロジェクトをå…
36è²¬ã™ã‚‹ã“と.
37 * また,本ソフトウェアのユーザまたはエンドユーザからのいかなる理
38 * 由に基づく請求からも,上記著作権者
39およびTOPPERSプロジェクトを
40 * å…
41è²¬ã™ã‚‹ã“と.
42 *
43 * 本ソフトウェアは,無保証で提供されているものである.上記著作権者
44お
45 * よびTOPPERSプロジェクトは,本ソフトウェアに関して,特定の使用目的
46 * に対する適合性も含めて,いかなる保証も行わない.また,本ソフトウェ
47 * アの利用により直接的または間接的に生じたいかなる損害に関しても,そ
48 * の責任を負わない.
49 *
50 * @(#) $Id: echonet.c 388 2019-05-22 11:25:18Z coas-nagasima $
51 */
52
53#include <kernel.h>
54#include <stdio.h>
55#include <string.h>
56#include <t_stdlib.h>
57
58#include "echonet.h"
59#include "echonet_fbs.h"
60#include "echonet_task.h"
61#include "echonet_dbg.h"
62#include "echonet_agent.h"
63
64/*
65 * ECHONET Liteサービス処理開始
66 */
67ER ecn_sta_svc()
68{
69 return act_tsk(ecn_udp_taskid);
70}
71
72/*
73 * インスタンスリスト通知の送信
74 */
75ER ecn_ntf_inl()
76{
77 return _ecn_tsk_ntf_inl();
78}
79
80/*
81 * ECHONETオブジェクト参ç…
82§
83 * 引数
84 * ID fa_eobjid ECHONETオブジェクトID
85 * T_REOBJ *fp_eobj ECHONETオブジェクトの設定内
86容コピーå…
87ˆ
88 *
89 * eobjidで指定したECHONETオブジェクトの設定内
90容を参ç…
91§ã™ã‚‹ã€‚
92 * 参ç…
93§ã—た設定内
94容はpk_eobjに指定したメモリに返される。
95 */
96ER ecn_ref_eobj(ID fa_eobjid, T_REOBJ *fp_eobj)
97{
98 const EOBJINIB *p_obj;
99
100 if (!fp_eobj)
101 return E_PAR; /* パラメータエラー */
102
103 if ((fa_eobjid <= 0) || (fa_eobjid > tmax_eobjid))
104 return E_OBJ; /* オブジェクト未登録 */
105
106 p_obj = &eobjinib_table[fa_eobjid - 1];
107
108 *fp_eobj = *p_obj;
109
110 return E_OK;
111}
112
113/*
114 * ECHONETプロパティ参ç…
115§
116 * 引数
117 * ID fa_eobjid ECHONETオブジェクトID
118 * uint8_t fa_epc プロパティコード
119 * T_RPRP *fp_eprp ECHONETオブジェクトのプロパティ設定内
120容コピーå…
121ˆ
122 *
123 * eobjidで指定したECHONETオブジェクトの、epcで指定したプロパティの設定内
124容を参ç…
125§ã™ã‚‹ã€‚
126 * 参ç…
127§ã—た設定内
128容はpk_eprpに指定したメモリに返される。
129 */
130ER ecn_ref_eprp(ID fa_eobjid, uint8_t fa_epc, T_RPRP *fp_eprp)
131{
132 const EOBJINIB *p_obj;
133 const EPRPINIB *p;
134 uint_t i;
135
136 if (!fp_eprp)
137 return E_PAR; /* パラメータエラー */
138
139 if ((fa_eobjid <= 0) || (fa_eobjid > tmax_eobjid))
140 return E_OBJ; /* オブジェクト未登録 */
141
142 p_obj = &eobjinib_table[fa_eobjid - 1];
143
144 /* eojの持つプロパティ初期化定義é…
145åˆ—から検索 */
146 p = p_obj->eprp;
147 for (i = 0; i < p_obj->eprpcnt; i++, p++) {
148 if (p->eprpcd != fa_epc)
149 continue;
150 *fp_eprp = *p;
151 return E_OK;
152 }
153
154 return E_PAR; /* パラメータエラー */
155}
156
157/*
158 * プロパティ値書き込み要求(応答不要)電文作成
159 * 引数
160 * T_EDATA **ppk_esv 取得した電文の格納å…
161ˆ
162 * ID fa_deoj 宛å…
163ˆã®ECHONETオブジェクトID
164 * uint8_t fa_epc プロパティコード
165 * uint8_t fa_pdc プロパティ値データサイズ
166 * const void *p_edt プロパティ値データ
167 *
168 * プロパティ値書き込み要求(応答不要)電文を作成する。
169 * 電文はdeojで指定したECHONETオブジェクトを宛å…
170ˆã¨ã—、
171 * 電文の初めのプロパティ値として、epcとpdc、p_edtで指定された
172 * プロパティコード、データサイズ、データを電文に設定する。
173 * 作成した電文のå…
174ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ã¯ãƒã‚¤ãƒ³ã‚¿çµŒç”±ã§è¿”される。
175 */
176ER ecn_esv_seti(T_EDATA **ppk_esv, ID fa_deoj, uint8_t fa_epc, uint8_t fa_pdc,
177 const void *p_edt)
178{
179 return _ecn_tsk_mk_esv((ECN_FBS_ID *)ppk_esv, (ID)1, fa_deoj, fa_epc, fa_pdc, p_edt, ESV_SET_I);
180}
181
182/*
183 * プロパティ値書き込み要求(応答要)電文作成
184 * 引数
185 * T_EDATA **ppk_esv 取得した電文の格納å…
186ˆ
187 * ID fa_deoj 宛å…
188ˆã®ECHONETオブジェクトID
189 * uint8_t fa_epc プロパティコード
190 * uint8_t fa_pdc プロパティ値データサイズ
191 * const void *p_edt プロパティ値データ
192 *
193 * プロパティ値書き込み要求(応答要)電文を作成する。
194 * 電文はdeojで指定したECHONETオブジェクトを宛å…
195ˆã¨ã—、
196 * 電文の初めのプロパティ値として、epcとpdc、p_edtで指定された
197 * プロパティコード、データサイズ、データを電文に設定する。
198 * 作成した電文のå…
199ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ã¯ãƒã‚¤ãƒ³ã‚¿çµŒç”±ã§è¿”される。
200 */
201ER ecn_esv_setc(T_EDATA **ppk_esv, ID fa_deoj, uint8_t fa_epc, uint8_t fa_pdc,
202 const void *p_edt)
203{
204 return _ecn_tsk_mk_esv((ECN_FBS_ID *)ppk_esv, (ID)1, fa_deoj, fa_epc, fa_pdc, p_edt, ESV_SET_C);
205}
206
207/*
208 * プロパティ値読み出し要求電文作成
209 * 引数
210 * T_EDATA **ppk_esv 取得した電文の格納å…
211ˆ
212 * ID fa_deoj 宛å…
213ˆã®ECHONETオブジェクトID
214 * uint8_t fa_epc プロパティコード
215 *
216 * プロパティ値読み出し要求電文を作成する。
217 * 電文はdeojで指定したECHONETオブジェクトを宛å…
218ˆã¨ã—、
219 * 電文の初めのプロパティ値として、epcで指定された
220 * プロパティコードを電文に設定する。
221 * 作成した電文のå…
222ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ã¯ãƒã‚¤ãƒ³ã‚¿çµŒç”±ã§è¿”される。
223 */
224ER ecn_esv_get(T_EDATA **ppk_esv, ID fa_deoj, uint8_t fa_epc)
225{
226 return _ecn_tsk_mk_esv((ECN_FBS_ID *)ppk_esv, (ID)1, fa_deoj, fa_epc, 0, NULL, ESV_GET);
227}
228
229/*
230 * プロパティ値通知要求電文作成
231 * 引数
232 * T_EDATA **ppk_esv 取得した電文の格納å…
233ˆ
234 * ID fa_deoj 宛å…
235ˆã®ECHONETオブジェクトID
236 * uint8_t fa_epc プロパティコード
237 *
238 * プロパティ値通知要求電文を作成する。
239 * 電文はdeojで指定したECHONETオブジェクトを宛å…
240ˆã¨ã—、
241 * 電文の初めのプロパティ値として、epcで指定された
242 * プロパティコードを電文に設定する。
243 * 作成した電文のå…
244ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ã¯ãƒã‚¤ãƒ³ã‚¿çµŒç”±ã§è¿”される。
245 */
246ER ecn_esv_inf_req(T_EDATA **ppk_esv, ID fa_deoj, uint8_t fa_epc)
247{
248 return _ecn_tsk_mk_esv((ECN_FBS_ID *)ppk_esv, (ID)1, fa_deoj, fa_epc, 0, NULL, ESV_INF_REQ);
249}
250
251/*
252 * プロパティ値書き込み・読み出し要求電文作成
253 * 引数
254 * T_EDATA **ppk_esv 取得した電文の格納å…
255ˆ
256 * ID fa_deoj 宛å…
257ˆã®ECHONETオブジェクトID
258 * uint8_t fa_epc プロパティコード
259 * uint8_t fa_pdc プロパティ値データサイズ
260 * const void *p_edt プロパティ値データ
261 *
262 * プロパティ値書き込み・読み出し要求電文を作成する。
263 * 電文はdeojで指定したECHONETオブジェクトを宛å…
264ˆã¨ã—、
265 * 電文の初めのプロパティ値として、epcとpdc、p_edtで指定された
266 * プロパティコード、データサイズ、データを電文に設定する。
267 * 作成した電文のå…
268ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ã¯ãƒã‚¤ãƒ³ã‚¿çµŒç”±ã§è¿”される。
269 */
270ER ecn_esv_set_get(T_EDATA **ppk_esv, ID fa_deoj, uint8_t fa_epc, uint8_t fa_pdc,
271 const void *p_edt)
272{
273 return _ecn_tsk_mk_esv((ECN_FBS_ID *)ppk_esv, (ID)1, fa_deoj, fa_epc, fa_pdc, p_edt, ESV_SET_GET);
274}
275
276/*
277 * プロパティ値書き込み・読み出し要求電文作成:折り返し指定
278 * プロパティ値書き込み・読み出し要求電文作成中の、書き込みプロパティé…
279åˆ—を終えて
280 * 読み出しプロパティé…
281åˆ—に移る時に用いる。
282 */
283ER ecn_trn_set_get(T_EDATA *ppk_esv, int *p_trn_pos)
284{
285 ER a_ret;
286
287 if (!ppk_esv)
288 return E_PAR;
289 if (!p_trn_pos)
290 return E_PAR;
291
292 /* プロパティ読み込み件数書き込み時のヘッド情
293報を記録 */
294 *p_trn_pos = _ecn_fbs_get_datalen(*(ECN_FBS_ID *)&ppk_esv);
295
296 /* 応答電文用メモリにデータ追加・この時点での応答電文中プロパティ件数を記録 */
297 a_ret = _ecn_fbs_add_data_ex(*(ECN_FBS_ID *)&ppk_esv, &ppk_esv->hdr.edata.opc, 1);
298 if (a_ret) {
299 ECN_DBG_PUT_2("ecn_trn_set_get(): _ecn_fbs_add_data_ex() result = %d:%s", a_ret, itron_strerror(a_ret));
300 return a_ret;
301 }
302
303 /* 応答電文中プロパティ件数を 0 に戻す(今後、終了指定するまでは読み出しプロパティ件数になる) */
304 ppk_esv->hdr.edata.opc = 0;
305
306 return E_OK;
307}
308
309/*
310 * プロパティ値書き込み・読み出し要求電文作成:終了指定
311 * プロパティ値書き込み・読み出し要求電文作成中の、読み出しプロパティé…
312åˆ—を終える時に用いる。
313 */
314ER ecn_end_set_get(T_EDATA *ppk_esv, int fa_trn_pos)
315{
316 ER a_ret;
317 int a_wr_opc;
318 uint8_t a_rd_opc;
319
320 if (!ppk_esv)
321 return E_PAR;
322
323 /* この時点での応答電文中プロパティ件数(読み出しプロパティ件数)を保持 */
324 a_rd_opc = ppk_esv->hdr.edata.opc;
325
326 /* 応答電文中プロパティ件数(書き込みプロパティ件数)を保存位置から読み取り */
327 a_wr_opc = _ecn_fbs_peek(*(ECN_FBS_ID *)&ppk_esv, fa_trn_pos);
328 if (a_wr_opc < 0) {
329 ECN_DBG_PUT_2("ecn_end_set_get(): _ecn_fbs_peek() result = %d:%s", a_wr_opc, itron_strerror(a_wr_opc));
330 return a_wr_opc;
331 }
332
333 /* 応答電文中プロパティ件数(書き込みプロパティ件数)を復å…
334ƒ */
335 ppk_esv->hdr.edata.opc = (uint8_t)a_wr_opc;
336
337 /* 応答電文中プロパティ件数(読み出しプロパティ件数)を保存位置に書き込み */
338 a_ret = _ecn_fbs_poke(*(ECN_FBS_ID *)&ppk_esv, fa_trn_pos, a_rd_opc);
339 if (a_ret) {
340 ECN_DBG_PUT_2("ecn_end_set_get(): _ecn_fbs_poke() result = %d:%s", a_ret, itron_strerror(a_ret));
341 return a_ret;
342 }
343
344 return E_OK;
345}
346
347/*
348 * プロパティ値通知(応答要)電文作成
349 * 引数
350 * T_EDATA **ppk_esv 取得した電文の格納å…
351ˆ
352 * ID fa_deoj 宛å…
353ˆã®ECHONETオブジェクトID
354 * ID fa_seoj 送信å…
355ƒã®ECHONETオブジェクトID
356 * uint8_t fa_sepc 送信å…
357ƒã®ãƒ—ロパティコード
358 */
359ER ecn_esv_infc(T_EDATA **ppk_esv, ID fa_deoj, ID fa_seoj, uint8_t fa_sepc)
360{
361 return _ecn_tsk_mk_esv((ECN_FBS_ID *)ppk_esv, fa_seoj, fa_deoj, fa_sepc, 0, NULL, ESV_INFC);
362}
363
364/*
365 * 要求電文へのプロパティ指定追加 (プロパティデータが付随しない場合に用いる)
366 */
367ER ecn_add_epc(T_EDATA *pk_esv, uint8_t epc)
368{
369 return ecn_add_edt(pk_esv, epc, 0, 0);
370}
371
372/*
373 * 要求電文へのプロパティデータ追加 (プロパティおよび付随データを追加する)
374 */
375ER ecn_add_edt(T_EDATA *pk_esv, uint8_t fa_epc, uint8_t fa_pdc, const void *p_edt)
376{
377 ECN_FBS_ID a_fbs_id;
378 ER a_ret;
379 T_ECN_PRP a_ecn_prp;
380
381 if (!pk_esv)
382 return E_PAR; /* 取得したFBS_IDの格納å…
383ˆãŒNULL */
384 if (ECHONET_MEMPOOL_BLOCK_SIZE <= fa_pdc)
385 return E_PAR; /* プロパティ値サイズが大きすぎる */
386 if (!p_edt && 0 < fa_pdc)
387 return E_PAR; /* プロパティ値サイズが1以上なのにデータポインタがNULL */
388
389 a_fbs_id.ptr = (T_ECN_FST_BLK *)pk_esv;
390 if (((T_EDATA *)a_fbs_id.ptr)->hdr.edata.opc == 0xFF)
391 return E_PAR; /* プロパティが多すぎる */
392
393 /* 要求電文用メモリにデータ追加 */
394 memset(&a_ecn_prp, 0, sizeof(a_ecn_prp));
395 a_ecn_prp.epc = fa_epc;
396 a_ecn_prp.pdc = fa_pdc;
397 a_ret = _ecn_fbs_add_data_ex(a_fbs_id, &a_ecn_prp, sizeof(a_ecn_prp));
398 if (a_ret) {
399 ECN_DBG_PUT_4("ecn_add_edt(): _ecn_fbs_add_data_ex(*, ecn_prp{epc:0x%02X}, %u) result = %d:%s",
400 a_ecn_prp.epc, sizeof(a_ecn_prp),
401 a_ret, itron_strerror(a_ret));
402 goto lb_except;
403 }
404 if (0 < fa_pdc) {
405 /* 付随データ追加 */
406 a_ret = _ecn_fbs_add_data_ex(a_fbs_id, p_edt, fa_pdc);
407 if (a_ret) {
408 ECN_DBG_PUT_4("ecn_add_edt(): _ecn_fbs_add_data_ex(*, ecn_prp{epc:0x%02X} edt, %u) result = %d:%s",
409 a_ecn_prp.epc, fa_pdc,
410 a_ret, itron_strerror(a_ret));
411 goto lb_except;
412 }
413 }
414 /* プロパティ数インクリメント */
415 ((T_EDATA *)a_fbs_id.ptr)->hdr.edata.opc++;
416
417lb_except:
418 return a_ret;
419}
420
421/*
422 * 要求電文の送信
423 * esvで指定された要求電文を送信する。
424 * 電文に指定された宛å…
425ˆã‹ã‚‰IPアドレスを特定し、UDPパケットとして送信する。
426 */
427ER ecn_snd_esv(T_EDATA *pk_esv)
428{
429 ECN_FBS_ID a_rsp_fbs;
430 a_rsp_fbs.ptr = (T_ECN_FST_BLK *)pk_esv;
431 return _ecn_tsk_snd_dtq(a_rsp_fbs, true);
432}
433
434/*
435 * 応答電文の受信永遠待
436ち
437 * 応答電文を受信するのを待
438つ。
439 * 受信した応答電文はppk_esvで指定したポインターにå…
440ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ãŒè¿”される。
441 * 要求電文の宛å…
442ˆã®ECHONETオブジェクトがネットワークに存在しない場合、
443 * 応答電文は返送されないので、永遠に待
444つことになるのでタイムアウト付きの
445 * ecn_trcv_esvを使用することを推奨する。
446 */
447ER ecn_rcv_esv(T_EDATA **ppk_esv)
448{
449 return ecn_trcv_esv(ppk_esv, TMO_FEVR);
450}
451
452/*
453 * 応答電文の受信待
454ちタイムアウトあり
455 * 応答電文を受信するのを待
456つ。
457 * 受信した応答電文はppk_esvで指定したポインターにå…
458ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ãŒè¿”される。
459 * tmoで指定されたタイムアウト時間が経過しても応答電文を受信しない場合、
460 * 待
461ちが解除され、戻り値がE_TMOで返される。
462 * tmoにTMO_FEVRを指定するとecn_rcv_esvと同じ振る舞いをする。
463 * tmoに0を指定するとecn_prcv_esvと同じ振る舞いをする。
464 */
465ER ecn_trcv_esv(T_EDATA **ppk_esv, int fa_tmout)
466{
467 T_MSG *p_msg = 0;
468 ER a_ret;
469
470 if (!ppk_esv)
471 return E_PAR;
472
473 a_ret = trcv_dtq(ecn_api_dataqueueid, (intptr_t *)&p_msg, fa_tmout);
474 if (a_ret != E_OK) {
475 *ppk_esv = NULL;
476 return a_ret;
477 }
478
479 *ppk_esv = (T_EDATA *)p_msg;
480 return (((T_ECN_FST_BLK *)p_msg)->hdr.type == ECN_MSG_ECHONET) ? E_OK : E_BRK;
481}
482
483/*
484 * 応答電文の受信ポーリング
485 * 応答電文を受信するのを待
486つ。
487 * 受信した応答電文はppk_esvで指定したポインターにå…
488ˆé ­ã‚¢ãƒ‰ãƒ¬ã‚¹ãŒè¿”される。
489 * 応答電文の受信の有無にかかわらず、待
490たずに関数を抜ける。
491 */
492ER ecn_prcv_esv(T_EDATA **ppk_esv)
493{
494 return ecn_trcv_esv(ppk_esv, TMO_POL);
495}
496
497/*
498 * 応答電文の破棄
499 */
500ER ecn_rel_esv(T_EDATA *pk_esv)
501{
502 ECN_FBS_ID a_fbs;
503 ER a_ret;
504
505 a_fbs.ptr = (T_ECN_FST_BLK *)pk_esv;
506 a_ret = _ecn_fbs_del(a_fbs);
507 return a_ret;
508}
509
510/*
511 * 応答電文の送信å…
512ƒãƒŽãƒ¼ãƒ‰ã‚’取得する
513 */
514ID ecn_get_enod(T_EDATA *pk_esv)
515{
516 const EOBJCB *p_snod;
517 const EOBJINIB *p_sobj = NULL;
518
519 p_snod = _ecn_eno_fnd(((T_ECN_FST_BLK *)pk_esv)->hdr.sender.id);
520 if (p_snod != NULL) {
521 p_sobj = p_snod->profile;
522 }
523
524 if (p_sobj == NULL)
525 return EOBJ_NULL;
526#ifdef ECHONET_CONTROLLER_EXTENTION
527 if (p_sobj->eprpcnt == 0)
528 return ecn_agent_get_eobj(p_sobj);
529#endif
530 return 1 + (((intptr_t)p_sobj - (intptr_t)eobjinib_table) / sizeof(EOBJINIB));
531}
532
533/*
534 * 応答電文の送信å…
535ƒæ©Ÿå™¨ã‚ªãƒ–ジェクトを取得する
536 */
537ID ecn_get_eobj(T_EDATA *pk_esv)
538{
539 const EOBJCB *p_snod;
540 const EOBJINIB *p_sobj = NULL;
541 T_ECN_EDT_HDR *p_esv;
542
543 p_esv = &pk_esv->hdr;
544 p_snod = _ecn_eno_fnd(((T_ECN_FST_BLK *)pk_esv)->hdr.sender.id);
545 if (p_snod != NULL) {
546 /* ノードプロファイルの場合 */
547 if ((p_esv->edata.seoj.eojx1 == EOJ_X1_PROFILE)
548 && (p_esv->edata.seoj.eojx2 == EOJ_X2_NODE_PROFILE)) {
549 p_sobj = p_snod->profile;
550 }
551 /* 機器オブジェクトの場合 */
552 else {
553 p_sobj = _ecn_eoj_fnd(p_snod, &p_esv->edata.seoj);
554 }
555 }
556
557 if (p_sobj == NULL)
558 return EOBJ_NULL;
559#ifdef ECHONET_CONTROLLER_EXTENTION
560 if (p_sobj->eprpcnt == 0)
561 return ecn_agent_get_eobj(p_sobj);
562#endif
563 return 1 + (((intptr_t)p_sobj - (intptr_t)eobjinib_table) / sizeof(EOBJINIB));
564}
565
566/*
567 * 応答電文解析イテレーター初期化
568 */
569ER ecn_itr_ini(T_ENUM_EPC *pk_itr, T_EDATA *pk_esv)
570{
571 if (!pk_itr)
572 return E_PAR;
573 if (!pk_esv)
574 return E_PAR;
575
576 memset(pk_itr, 0, sizeof(*pk_itr));
577 pk_itr->pk_esv = pk_esv;
578 pk_itr->count = pk_esv->hdr.edata.opc;
579 /* 今のブロックでのプロパティ総数 */
580 pk_itr->got_ct = 0; /* 今のブロックで、読み取った数 */
581 pk_itr->next_blk_ct = 0; /* 後続ブロック数 */
582 pk_itr->is_eof = 0; /* 終端に達した時、非0 */
583 pk_itr->cur = offsetof(T_ECN_EDT_HDR, ecn_prp);
584
585 switch (pk_esv->hdr.edata.esv) {
586 case ESV_SET_GET: /* 0x6E プロパティ値書き込み・読み出し要求 */
587 case ESV_SET_GET_RES: /* 0x7E プロパティ値書き込み・読み出し応答 */
588 case ESV_SET_GET_SNA: /* 0x5E プロパティ値書き込み・読み出し不可応答 */
589 pk_itr->next_blk_ct ++;
590 default:
591 break;
592 }
593
594 return E_OK;
595}
596
597/*
598 * 応答電文解析イテレーターインクリメント
599 */
600ER ecn_itr_nxt(T_ENUM_EPC *pk_itr, uint8_t *p_epc, uint8_t *p_pdc, void *p_edt)
601{
602 ECN_FBS_ID a_fbs_id;
603 int a_rd_bak;
604 ER a_ret;
605 ECN_FBS_SSIZE_T a_rd_len;
606 T_ECN_PRP a_ecn_prp;
607
608 if (!pk_itr)
609 return E_PAR;
610 if (!p_epc)
611 return E_PAR;
612 if (!p_pdc)
613 return E_PAR;
614 if (!pk_itr->pk_esv)
615 return E_PAR;
616
617 if (pk_itr->is_eof)
618 return E_BOVR; /* データ終了 */
619 if (pk_itr->count <= pk_itr->got_ct && pk_itr->next_blk_ct < 1) {
620 pk_itr->is_eof = 1; /* 終端に達した時、非0 */
621 return E_BOVR; /* データ終了 */
622 }
623
624 a_fbs_id.ptr = (T_ECN_FST_BLK *)pk_itr->pk_esv;
625
626 /* å…
627ƒã®ã‚«ãƒ¼ã‚½ãƒ«ä½ç½®ã‚’保存し、イテレータのカーソル位置にする */
628 a_rd_bak = a_fbs_id.ptr->hdr.rd;
629 a_fbs_id.ptr->hdr.rd = pk_itr->cur;
630
631#ifdef ECN_ENA_ITR_NXT_CARP
632 ECN_CAP_PUT("ecn_itr_nxt() rd.cur=b%dp%d", pk_itr->cur.blk, pk_itr->cur.pos ECN_CAP_PUT(;
633#endif
634 if (pk_itr->count <= pk_itr->got_ct && 0 < pk_itr->next_blk_ct) {
635 /* 次ブロックに移動 */
636 pk_itr->next_blk_ct --;
637 pk_itr->count = 0; /* 今のブロックでのプロパティ総数 */
638 pk_itr->got_ct = 0; /* 今のブロックで、読み取った数 */
639
640 /* 次ブロックのプロパティ数を読み取る */
641 a_rd_len = 0;
642 a_ret = _ecn_fbs_get_data(a_fbs_id, &a_ecn_prp.pdc, 1, &a_rd_len);
643 if (a_ret != E_OK)
644 goto lb_except;
645 if (0 < a_rd_len) {
646 pk_itr->count = a_ecn_prp.pdc; /* 今のブロックでのプロパティ総数 */
647 }
648 a_ret = E_BOVR; /* データ終了 */
649 goto lb_finally;
650 }
651
652 /* プロパティコードとデータサイズを読み取る */
653 memset(&a_ecn_prp, 0, sizeof(a_ecn_prp));
654 a_rd_len = 0;
655 a_ret = _ecn_fbs_get_data(a_fbs_id, &a_ecn_prp, sizeof(a_ecn_prp), &a_rd_len);
656 if (a_ret != E_OK)
657 goto lb_except;
658 if (a_rd_len < sizeof(a_ecn_prp)) {
659 ECN_DBG_PUT_1("ecn_itr_nxt() ecn_prp read fault. rd.cur=%d", pk_itr->cur);
660 pk_itr->is_eof = 1; /* 終端に達した時、非0 */
661 a_ret = E_BOVR; /* データ終了 */
662 goto lb_finally;
663 }
664 *p_epc = a_ecn_prp.epc;
665 *p_pdc = a_ecn_prp.pdc;
666
667 if (0 < a_ecn_prp.pdc) {
668 if (p_edt == NULL) {
669 a_ret = _ecn_fbs_seek_rpos(a_fbs_id, a_ecn_prp.pdc);
670 if (a_ret != E_OK)
671 goto lb_except;
672 }
673 else {
674 /* 付随データを読み取る */
675 a_rd_len = 0;
676 a_ret = _ecn_fbs_get_data(a_fbs_id, p_edt, a_ecn_prp.pdc, &a_rd_len);
677 if (a_ret != E_OK)
678 goto lb_except;
679 if (a_rd_len < (ECN_FBS_SSIZE_T)a_ecn_prp.pdc) {
680 ECN_DBG_PUT_3("ecn_itr_nxt() edt read fault. rd.cur=%d,epc=0x%02X,pdc=%u",
681 pk_itr->cur, a_ecn_prp.epc , a_ecn_prp.pdc);
682 pk_itr->is_eof = 1; /* 終端に達した時、非0 */
683 a_ret = E_BOVR; /* データ終了 */
684 goto lb_finally;
685 }
686 }
687 }
688 pk_itr->got_ct++;
689
690#ifdef ECN_ENA_ITR_NXT_CARP
691 ECN_CAP_PUT("ecn_itr_nxt() read: ct=%d/%d", pk_itr->got_ct, pk_itr->count ECN_CAP_PUT(;
692#endif
693
694lb_finally:
695 /* イテレータのカーソル位置を更新 */
696 pk_itr->cur = a_fbs_id.ptr->hdr.rd;
697
698lb_except:
699 /* å…
700ƒã®ã‚«ãƒ¼ã‚½ãƒ«ä½ç½®ã«æˆ»ã™ */
701 a_fbs_id.ptr->hdr.rd = a_rd_bak;
702 return a_ret;
703}
704
705/*
706 * 応答電文待
707ちの割り込み送信
708 */
709ER ecn_brk_wai(const void *p_dat, int fa_datsz)
710{
711 ER a_ret;
712 ECN_FBS_ID a_fbs_id = { 0 }; /* 要求電文用メモリ */
713
714 /* 応答電文待
715ちの割り込み電文作成 */
716 a_ret = _ecn_mk_brk_wai(&a_fbs_id, p_dat, fa_datsz);
717 if (a_ret)
718 return a_ret;
719
720 /* 割り込み送信 */
721 a_ret = _ecn_tsk_snd_dtq(a_fbs_id, true);
722 if (a_ret) {
723 ECN_DBG_PUT_2("_ecn_tsk_snd_dtq() result = %d:%s", a_ret, itron_strerror(a_ret));
724 goto lb_except;
725 }
726
727 /* 正常終了 */
728 return a_ret;
729
730lb_except:
731 /* データ作成失敗したら領域解放 */
732 if (a_fbs_id.ptr)
733 _ecn_fbs_del(a_fbs_id);
734
735 return a_ret;
736}
737
738/*
739 * 割り込みデータの取得
740 */
741ER ecn_get_brk_dat(T_EDATA *pk_esv, void *p_buf, int fa_bufsz, int *p_datsz)
742{
743 ECN_FBS_ID a_fbs;
744 ER a_ret;
745 ECN_FBS_SSIZE_T a_len;
746
747 if (p_datsz)
748 *p_datsz = 0;
749 if (!pk_esv)
750 return E_PAR;
751
752 a_fbs.ptr = (T_ECN_FST_BLK *)pk_esv;
753 if (a_fbs.ptr->hdr.type != ECN_MSG_USER_BREAK) {
754 ECN_DBG_PUT_1("ecn_get_brk_dat: fbs-type:%d != ECN_MSG_USER_BREAK",
755 a_fbs.ptr->hdr.type);
756 return E_PAR;
757 }
758
759 /* 読み取り位置をå…
760ˆé ­ã«æˆ»ã™ */
761 a_ret = _ecn_fbs_set_rpos(a_fbs, 0);
762 if (a_ret) {
763 ECN_DBG_PUT_2("_ecn_fbs_set_rpos(*, 0) result = %d:%s",
764 a_ret, itron_strerror(a_ret));
765 return a_ret;
766 }
767
768 /* 付随データを読み込む */
769 if (p_buf && 0 < fa_bufsz) {
770 a_len = 0;
771 a_ret = _ecn_fbs_get_data(a_fbs, p_buf, fa_bufsz, &a_len);
772 if (a_ret || !a_len) {
773 ECN_DBG_PUT_2("_ecn_fbs_get_data(*, p_buf, fa_bufsz) result = %d:%s",
774 a_ret, itron_strerror(a_ret));
775 return E_PAR;
776 }
777 *p_datsz = a_len;
778 }
779
780 return E_OK;
781}
782
783#ifndef ECN_USER_DATA_PROP_SET
784/*
785 * データ設定関数
786 */
787int ecn_data_prop_set(const EPRPINIB *item, const void *src, int size, bool_t *anno)
788{
789 if (size > item->eprpsz)
790 size = item->eprpsz;
791
792 if (*anno)
793 *anno = memcmp((uint8_t *)item->exinf, src, size) != 0;
794
795 memcpy((uint8_t *)item->exinf, src, size);
796
797 return size;
798}
799#endif
800
801#ifndef ECN_USER_DATA_PROP_GET
802/*
803 * データ取得関数
804 */
805int ecn_data_prop_get(const EPRPINIB *item, void *dst, int size)
806{
807 if (size > item->eprpsz)
808 size = item->eprpsz;
809
810 memcpy(dst, (uint8_t *)item->exinf, size);
811
812 return size;
813}
814#endif
Note: See TracBrowser for help on using the repository browser.