source: EcnlProtoTool/trunk/asp3_dcre/tinet/netdev/if_mbed/if_mbed.c@ 331

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

prototoolに関連するプロジェクトをnewlibからmuslを使うよう変更・更新
ntshellをnewlibの下位の実装から、muslのsyscallの実装に変更・更新
以下のOSSをアップデート
・mruby-1.3.0
・musl-1.1.18
・onigmo-6.1.3
・tcc-0.9.27
以下のOSSを追加
・openssl-1.1.0e
・curl-7.57.0
・zlib-1.2.11
以下のmrbgemsを追加
・iij/mruby-digest
・iij/mruby-env
・iij/mruby-errno
・iij/mruby-iijson
・iij/mruby-ipaddr
・iij/mruby-mock
・iij/mruby-require
・iij/mruby-tls-openssl

  • Property svn:eol-style set to native
  • Property svn:mime-type set to text/x-csrc;charset=UTF-8
File size: 12.6 KB
Line 
1/*
2 * TINET (TCP/IP Protocol Stack)
3 *
4 * Copyright (C) 2001-2009 by Dep. of Computer Science and Engineering
5 * Tomakomai National College of Technology, JAPAN
6 * Copyright (C) 2014 Cores Co., Ltd. Japan
7 *
8 * 上記著作権者は,以下の(1)~(4)の条件を満たす場合に限り,本ソフトウェ
9 * ア(本ソフトウェアを改変したものを含む.以下同じ)を使用・複製・改
10 * 変・再配布(以下,利用と呼ぶ)することを無償で許諾する.
11 * (1) 本ソフトウェアをソースコードの形で利用する場合には,上記の著作
12 * 権表示,この利用条件および下記の無保証規定が,そのままの形でソー
13 * スコード中に含まれていること.
14 * (2) 本ソフトウェアを,ライブラリ形式など,他のソフトウェア開発に使
15 * 用できる形で再配布する場合には,再配布に伴うドキュメント(利用
16 * 者マニュアルなど)に,上記の著作権表示,この利用条件および下記
17 * の無保証規定を掲載すること.
18 * (3) 本ソフトウェアを,機器に組み込むなど,他のソフトウェア開発に使
19 * 用できない形で再配布する場合には,次のいずれかの条件を満たすこ
20 * と.
21 * (a) 再配布に伴うドキュメント(利用者マニュアルなど)に,上記の著
22 * 作権表示,この利用条件および下記の無保証規定を掲載すること.
23 * (b) 再配布の形態を,別に定める方法によって,TOPPERSプロジェクトに
24 * 報告すること.
25 * (4) 本ソフトウェアの利用により直接的または間接的に生じるいかなる損
26 * 害からも,上記著作権者およびTOPPERSプロジェクトを免責すること.
27 * また,本ソフトウェアのユーザまたはエンドユーザからのいかなる理
28 * 由に基づく請求からも,上記著作権者およびTOPPERSプロジェクトを
29 * 免責すること.
30 *
31 * 本ソフトウェアは,無保証で提供されているものである.上記著作権者お
32 * よびTOPPERSプロジェクトは,本ソフトウェアに関して,特定の使用目的
33 * に対する適合性も含めて,いかなる保証も行わない.また,本ソフトウェ
34 * アの利用により直接的または間接的に生じたいかなる損害に関しても,そ
35 * の責任を負わない.
36 *
37 * @(#) $Id$
38 */
39
40/*
41 * Copyright (c) 1995, David Greenman
42 * All rights reserved.
43 *
44 * Redistribution and use in source and binary forms, with or without
45 * modification, are permitted provided that the following conditions
46 * are met:
47 * 1. Redistributions of source code must retain the above copyright
48 * notice unmodified, this list of conditions, and the following
49 * disclaimer.
50 * 2. Redistributions in binary form must reproduce the above copyright
51 * notice, this list of conditions and the following disclaimer in the
52 * documentation and/or other materials provided with the distribution.
53 *
54 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
55 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
56 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
57 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
58 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
59 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
60 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
61 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
62 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
63 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
64 * SUCH DAMAGE.
65 *
66 * $FreeBSD: src/sys/i386/isa/if_mbed.c,v 1.148.2.4 1999/09/25 13:08:18 nyan Exp $
67 */
68
69#define CAST(type, val) ((type)(val))
70
71#include <kernel.h>
72#include <sil.h>
73#include <t_syslog.h>
74#include "kernel_cfg.h"
75#include "kernel/kernel_impl.h"
76
77#include <tinet_defs.h>
78#include <tinet_config.h>
79
80#include <net/if.h>
81#include <net/ethernet.h>
82#include <net/if_arp.h>
83#include <net/net.h>
84#include <net/net_timer.h>
85#include <net/net_count.h>
86#include <net/net_buf.h>
87#include <net/ethernet.h>
88
89#include "mbed_interface.h"
90#include "ethernet_api.h"
91#include "ethernetext_api.h"
92#include <string.h>
93#include "if_mbed.h"
94#include "iodefine.h"
95
96#ifdef _MSC_VER
97#include <stdlib.h>
98#endif
99
100extern uint8_t mac_addr[ETHER_ADDR_LEN];
101
102/*
103 * ネットワークインタフェースに依存するソフトウェア情報
104 */
105
106typedef struct t_mbed_softc {
107 bool_t link_pre;
108 bool_t link_now;
109 bool_t over_flow;
110} T_MBED_SOFTC;
111
112/*
113 * ネットワークインタフェースのソフトウェア情報
114 */
115
116/* ネットワークインタフェースに依存するソフトウェア情報 */
117
118static T_MBED_SOFTC mbed_softc;
119
120/* ネットワークインタフェースに依存しないソフトウェア情報 */
121
122T_IF_SOFTC if_softc = {
123 {0,}, /* ネットワークインタフェースのアドレス */
124 0, /* 送信タイムアウト */
125 &mbed_softc, /* ディバイス依存のソフトウェア情報 */
126 SEM_IF_MBED_SBUF_READY, /* 送信セマフォ */
127 SEM_IF_MBED_RBUF_READY, /* 受信セマフォ */
128
129#ifdef SUPPORT_INET6
130
131 IF_MADDR_INIT, /* マルチキャストアドレスリスト */
132
133#endif /* of #ifdef SUPPORT_INET6 */
134};
135
136/*
137 * 局所変数
138 */
139
140static void if_mbed_stop(T_MBED_SOFTC *sc);
141static void if_mbed_init_sub(T_IF_SOFTC *ic);
142
143#ifdef SUPPORT_INET6
144
145static uint32_t ds_crc(uint8_t *addr);
146static void ds_getmcaf(T_IF_SOFTC *ic, uint32_t *mcaf);
147
148/*
149 * ds_crc -- イーサネットアドレスの CRC を計算する。
150 */
151
152#define POLYNOMIAL 0x04c11db6
153
154static uint32_t
155ds_crc(uint8_t *addr)
156{
157 uint32_t crc = ULONG_C(0xffffffff);
158 int_t carry, len, bit;
159 uint8_t byte;
160
161 for (len = ETHER_ADDR_LEN; len-- > 0; ) {
162 byte = *addr++;
163 for (bit = 8; bit-- > 0; ) {
164 carry = ((crc & ULONG_C(0x80000000)) ? 1 : 0) ^ (byte & UINT_C(0x01));
165 crc <<= 1;
166 byte >>= 1;
167 if (carry)
168 crc = (crc ^ POLYNOMIAL) | carry;
169 }
170 }
171 return crc;
172}
173
174#undef POLYNOMIAL
175
176/*
177 * ds_getmcaf -- マルチキャストアドレスのリストからマルチキャストアドレス
178 * フィルタを計算する。
179 */
180
181static void
182ds_getmcaf(T_IF_SOFTC *ic, uint32_t *mcaf)
183{
184 uint32_t count, index;
185 uint8_t *af = (uint8_t*)mcaf;
186
187 mcaf[0] = mcaf[1] = 0;
188
189 for (count = MAX_IF_MADDR_CNT; count-- > 0; ) {
190 index = ds_crc(ic->maddrs[count].lladdr) >> 26;
191 af[index >> 3] |= 1 << (index & 7);
192 }
193}
194
195/*
196 * mbed_setrcr -- 受信構成レジスタ (RCR) を設定する。
197 */
198
199static void
200if_mbed_setrcr(T_IF_SOFTC *ic)
201{
202 T_MBED_SOFTC *sc = ic->sc;
203}
204
205/*
206 * mbed_addmulti -- マルチキャストアドレスを追加する。
207 */
208
209ER
210if_mbed_addmulti(T_IF_SOFTC *ic)
211{
212 if_mbed_setrcr(ic);
213 return E_OK;
214}
215
216#endif /* of #ifdef SUPPORT_INET6 */
217
218/*
219 * mbed_stop -- ネットワークインタフェースを停止する。
220 *
221 * 注意: NIC 割り込み禁止状態で呼び出すこと。
222 */
223
224static void
225if_mbed_stop(T_MBED_SOFTC *sc)
226{
227 ethernetext_start_stop(0);
228}
229
230static void rza1_recv_callback(void)
231{
232 sig_sem(if_softc.semid_rxb_ready);
233}
234
235#define EDMAC_EESIPR_INI_TRANS (0xF4380000)
236#define EDMAC_EESIPR_INI_RECV (0x0205001F) /* 0x02000000 : Detect reception suspended */
237 /* 0x00040000 : Detect frame reception */
238 /* 0x00010000 : Receive FIFO overflow */
239 /* 0x00000010 : Residual bit frame reception */
240 /* 0x00000008 : Long frame reception */
241 /* 0x00000004 : Short frame reception */
242 /* 0x00000002 : PHY-LSI reception error */
243 /* 0x00000001 : Receive frame CRC error */
244#define EDMAC_EESIPR_INI_EtherC (0x00400000) /* 0x00400000 : E-MAC status register */
245
246static void
247if_mbed_init_sub(T_IF_SOFTC *ic)
248{
249 ethernet_cfg_t ethcfg;
250
251 /* Initialize the hardware */
252 ethcfg.int_priority = 6;
253 ethcfg.recv_cb = &rza1_recv_callback;
254 ethcfg.ether_mac = (char *)ic->ifaddr.lladdr;
255 ethernetext_init(&ethcfg);
256}
257
258/*
259 * mbed_reset -- ネットワークインタフェースをリセットする。
260 */
261
262void
263if_mbed_reset(T_IF_SOFTC *ic)
264{
265 ethernetext_start_stop(0);
266
267 NET_COUNT_ETHER_NIC(net_count_ether_nic[NC_ETHER_NIC_RESETS], 1);
268 if_mbed_stop(ic->sc);
269 if_mbed_init_sub(ic);
270
271 ethernetext_start_stop(1);
272}
273
274/*
275 * get_mbed_softc -- ネットワークインタフェースのソフトウェア情報を返す。
276 */
277
278T_IF_SOFTC *
279if_mbed_get_softc(void)
280{
281 return &if_softc;
282}
283
284/*
285 * mbed_watchdog -- ネットワークインタフェースのワッチドッグタイムアウト
286 */
287
288void
289if_mbed_watchdog(T_IF_SOFTC *ic)
290{
291 if_mbed_reset(ic);
292}
293
294/*
295 * mbed_probe -- ネットワークインタフェースの検出
296 */
297
298void
299if_mbed_probe(T_IF_SOFTC *ic)
300{
301#if (MBED_MAC_ADDRESS_SUM != MBED_MAC_ADDR_INTERFACE)
302 netif->hwaddr[0] = MBED_MAC_ADDR_0;
303 netif->hwaddr[1] = MBED_MAC_ADDR_1;
304 netif->hwaddr[2] = MBED_MAC_ADDR_2;
305 netif->hwaddr[3] = MBED_MAC_ADDR_3;
306 netif->hwaddr[4] = MBED_MAC_ADDR_4;
307 netif->hwaddr[5] = MBED_MAC_ADDR_5;
308#else
309 mbed_mac_address((char *)ic->ifaddr.lladdr);
310#endif
311}
312
313/*
314 * mbed_init -- ネットワークインタフェースの初期化
315 */
316
317void
318if_mbed_init(T_IF_SOFTC *ic)
319{
320 T_MBED_SOFTC *sc = ic->sc;
321
322 /* mbed_init 本体を呼び出す。*/
323 if_mbed_init_sub(ic);
324
325 act_tsk(IF_MBED_PHY_TASK);
326
327 ethernet_set_link(-1, 0);
328
329 ETHER.EESIPR0 |= EDMAC_EESIPR_INI_TRANS;
330}
331
332void if_mbed_phy_task(intptr_t arg)
333{
334 T_IFNET *ether = ether_get_ifnet();
335 int32_t connect_sts = 0; /* 0: disconnect, 1:connect */
336 int32_t link_sts;
337 int32_t link_mode_new = NEGO_FAIL;
338 int32_t link_mode_old = NEGO_FAIL;
339
340 while (1) {
341 link_sts = ethernet_link();
342 if (link_sts == 1) {
343 link_mode_new = ethernetext_chk_link_mode();
344 if (link_mode_new != link_mode_old) {
345 if (connect_sts == 1) {
346 ether_set_link_down(ether);
347 }
348 if (link_mode_new != NEGO_FAIL) {
349 ethernetext_set_link_mode(link_mode_new);
350 ETHER.EESIPR0 |= EDMAC_EESIPR_INI_TRANS;
351 ether_set_link_up(ether);
352 connect_sts = 1;
353 }
354 }
355 }
356 else {
357 if (connect_sts != 0) {
358 ether_set_link_down(ether);
359 link_mode_new = NEGO_FAIL;
360 connect_sts = 0;
361 }
362 }
363 link_mode_old = link_mode_new;
364 dly_tsk(PHY_TASK_WAIT);
365 }
366}
367
368/*
369 * mbed_read -- フレームの読み込み
370 */
371
372T_NET_BUF *
373if_mbed_read(T_IF_SOFTC *ic)
374{
375 T_MBED_SOFTC *sc = ic->sc;
376 T_NET_BUF *input = NULL;
377 uint_t align;
378 int len;
379 uint8_t *dst;
380 ER error;
381
382 len = ethernet_receive();
383 if (len <= 0)
384 return NULL;
385
386 align = ((((len - sizeof(T_IF_HDR)) + 3) >> 2) << 2) + sizeof(T_IF_HDR);
387 if ((error = tget_net_buf(&input, align, TMO_IF_MBED_GET_NET_BUF)) == E_OK && input != NULL) {
388 dst = input->buf + IF_ETHER_NIC_HDR_ALIGN;
389 input->len = ethernet_read((char *)dst, len);
390 }
391 else {
392 NET_COUNT_ETHER_NIC(net_count_ether_nic[NC_ETHER_NIC_IN_ERR_PACKETS], 1);
393 NET_COUNT_ETHER_NIC(net_count_ether_nic[NC_ETHER_NIC_NO_BUFS], 1);
394 }
395
396 sig_sem(ic->semid_rxb_ready);
397
398 return input;
399}
400
401/*
402 * mbed_start -- 送信フレームをバッファリングする。
403 */
404
405void
406if_mbed_start(T_IF_SOFTC *ic, T_NET_BUF *output)
407{
408 T_MBED_SOFTC *sc = ic->sc;
409 int32_t len, res, pos;
410
411 for (res = output->len, pos = 0; res > 0; res -= len, pos += len) {
412 len = ethernet_write((char *)output->buf + IF_ETHER_NIC_HDR_ALIGN + pos, res);
413 if (len == 0) {
414 syslog(LOG_WARNING, "ethernet_write => 0");
415 break;
416 }
417 }
418
419 if (ethernet_send() == 0) {
420 syslog(LOG_WARNING, "ethernet_send => 0");
421 }
422}
423
424/*
425 * MBED Ethernet Controler 送受信割り込みハンドラ
426 */
427
428void
429if_mbed_eth_handler(void)
430{
431 uint32_t stat_edmac;
432 uint32_t stat_etherc;
433
434 /* Clear the interrupt request flag */
435 stat_edmac = (ETHER.EESR0 & ETHER.EESIPR0); /* Targets are restricted to allowed interrupts */
436 ETHER.EESR0 = stat_edmac;
437 /* Reception-related */
438 if (stat_edmac & EDMAC_EESIPR_INI_RECV) {
439 isig_sem(if_softc.semid_rxb_ready);
440 }
441 if (stat_edmac & EDMAC_EESIPR_INI_TRANS) {
442 isig_sem(if_softc.semid_txb_ready);
443 }
444 /* E-MAC-related */
445 if (stat_edmac & EDMAC_EESIPR_INI_EtherC) {
446 /* Clear the interrupt request flag */
447 stat_etherc = (ETHER.ECSR0 & ETHER.ECSIPR0); /* Targets are restricted to allowed interrupts */
448 ETHER.ECSR0 = stat_etherc;
449 }
450}
Note: See TracBrowser for help on using the repository browser.