source: rubycfg_asp/trunk/asp_dcre/tinet/net/net_buf.c@ 313

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

ソースを追加

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
  • Property svn:mime-type set to text/x-csrc
File size: 13.3 KB
Line 
1/*
2 * TINET (TCP/IP Protocol Stack)
3 *
4 * Copyright (C) 2001-2017 by Dep. of Computer Science and Engineering
5 * Tomakomai National College of Technology, JAPAN
6 *
7 * 上記著作権者
8は,以下の (1)~(4) の条件か,Free Software Foundation
9 * によってå…
10¬è¡¨ã•ã‚Œã¦ã„ã‚‹ GNU General Public License の Version 2 に記
11 * 述されている条件を満たす場合に限り,本ソフトウェア(本ソフトウェア
12 * を改変したものを含む.以下同じ)を使用・複製・改変・再é…
13å¸ƒï¼ˆä»¥ä¸‹ï¼Œ
14 * 利用と呼ぶ)することを無償で許諾する.
15 * (1) 本ソフトウェアをソースコードの形で利用する場合には,上記の著作
16 * 権表示,この利用条件および下記の無保証規定が,そのままの形でソー
17 * スコード中に含まれていること.
18 * (2) 本ソフトウェアを,ライブラリ形式など,他のソフトウェア開発に使
19 * 用できる形で再é…
20å¸ƒã™ã‚‹å ´åˆã«ã¯ï¼Œå†é…
21å¸ƒã«ä¼´ã†ãƒ‰ã‚­ãƒ¥ãƒ¡ãƒ³ãƒˆï¼ˆåˆ©ç”¨
22 * 者
23マニュアルなど)に,上記の著作権表示,この利用条件および下記
24 * の無保証規定を掲載すること.
25 * (3) 本ソフトウェアを,機器に組み込むなど,他のソフトウェア開発に使
26 * 用できない形で再é…
27å¸ƒã™ã‚‹å ´åˆã«ã¯ï¼Œæ¬¡ã®æ¡ä»¶ã‚’満たすこと.
28 * (a) 再é…
29å¸ƒã«ä¼´ã†ãƒ‰ã‚­ãƒ¥ãƒ¡ãƒ³ãƒˆï¼ˆåˆ©ç”¨è€…
30マニュアルなど)に,上記の著
31 * 作権表示,この利用条件および下記の無保証規定を掲載すること.
32 * (4) 本ソフトウェアの利用により直接的または間接的に生じるいかなる損
33 * 害からも,上記著作権者
34およびTOPPERSプロジェクトをå…
35è²¬ã™ã‚‹ã“と.
36 *
37 * 本ソフトウェアは,無保証で提供されているものである.上記著作権者
38お
39 * よびTOPPERSプロジェクトは,本ソフトウェアに関して,その適用可能性も
40 * 含めて,いかなる保証も行わない.また,本ソフトウェアの利用により直
41 * 接的または間接的に生じたいかなる損害に関しても,その責任を負わない.
42 *
43 * @(#) $Id: net_buf.c 313 2017-07-23 04:50:32Z coas-nagasima $
44 */
45
46#ifdef TARGET_KERNEL_ASP
47
48#include <kernel.h>
49#include <sil.h>
50#include <t_syslog.h>
51#include "kernel_cfg.h"
52
53#endif /* of #ifdef TARGET_KERNEL_ASP */
54
55#ifdef TARGET_KERNEL_JSP
56
57#include <s_services.h>
58#include <t_services.h>
59#include "kernel_id.h"
60
61#endif /* of #ifdef TARGET_KERNEL_JSP */
62
63#include <tinet_defs.h>
64#include <tinet_config.h>
65
66#include <net/if.h>
67#include <net/if_loop.h>
68#include <net/if_ppp.h>
69#include <net/ethernet.h>
70#include <net/net.h>
71#include <net/net_endian.h>
72#include <net/net_buf.h>
73#include <net/net_count.h>
74
75#include <netinet/in.h>
76#include <netinet/in_var.h>
77#include <netinet/ip.h>
78#include <netinet/ip_var.h>
79#include <netinet/tcp.h>
80#include <netinet/tcp_var.h>
81
82/*
83 * 関数
84 */
85
86extern const char *itron_strerror (ER ercd);
87
88/*
89 * 変数
90 */
91
92static T_NET_BUF_ENTRY net_buf_table[] = {
93
94#if defined(NUM_MPF_NET_BUF6_65536) && NUM_MPF_NET_BUF6_65536 > 0
95 {
96 MPF_NET_BUF6_65536,
97 IF_IP6_HDR_SIZE + 65536,
98
99#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
100
101 NUM_MPF_NET_BUF6_65536,
102
103#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
104
105 },
106#endif /* of #if defined(NUM_MPF_NET_BUF6_65536) && NUM_MPF_NET_BUF6_65536 > 0 */
107
108#if defined(NUM_MPF_NET_BUF6_REASSM) && NUM_MPF_NET_BUF6_REASSM > 0
109
110 {
111 MPF_NET_BUF_REASSM,
112 IP6_CFG_FRAG_REASSM_SIZE,
113
114#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
115
116 NUM_MPF_NET_BUF6_REASSM,
117
118#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
119
120 },
121
122#else /* of #if defined(NUM_MPF_NET_BUF6_REASSM) && NUM_MPF_NET_BUF6_REASSM > 0 */
123
124#if defined(NUM_MPF_NET_BUF4_REASSM) && NUM_MPF_NET_BUF4_REASSM > 0
125
126 {
127 MPF_NET_BUF_REASSM,
128 IP4_CFG_FRAG_REASSM_SIZE,
129
130#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
131
132 NUM_MPF_NET_BUF4_REASSM,
133
134#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
135
136 },
137
138#endif /* of #if defined(NUM_MPF_NET_BUF4_REASSM) && NUM_MPF_NET_BUF4_REASSM > 0 */
139
140#endif /* of #if defined(NUM_MPF_NET_BUF6_REASSM) && NUM_MPF_NET_BUF6_REASSM > 0 */
141
142#if defined(NUM_MPF_NET_BUF_IF_PDU) && NUM_MPF_NET_BUF_IF_PDU > 0
143 {
144 MPF_NET_BUF_IF_PDU,
145 IF_PDU_SIZE,
146
147#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
148
149 NUM_MPF_NET_BUF_IF_PDU,
150
151#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
152
153 },
154#endif /* of #if defined(NUM_MPF_NET_BUF_IF_PDU) && NUM_MPF_NET_BUF_IF_PDU > 0 */
155
156#if defined(NUM_MPF_NET_BUF_IPV6_MMTU) && NUM_MPF_NET_BUF_IPV6_MMTU > 0
157 {
158 MPF_NET_BUF_IPV6_MMTU,
159 IF_HDR_SIZE + IPV6_MMTU,
160
161#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
162
163 NUM_MPF_NET_BUF_IPV6_MMTU,
164
165#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
166
167 },
168#endif /* of #if defined(NUM_MPF_NET_BUF_IPV6_MMTU) && NUM_MPF_NET_BUF_IPV6_MMTU > 0 */
169
170#if defined(NUM_MPF_NET_BUF_1024) && NUM_MPF_NET_BUF_1024 > 0
171 {
172 MPF_NET_BUF_1024,
173 UINT_C(1024),
174
175#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
176
177 NUM_MPF_NET_BUF_1024,
178
179#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
180
181 },
182#endif /* of #if defined(NUM_MPF_NET_BUF_1024) && NUM_MPF_NET_BUF_1024 > 0 */
183
184#if defined(NUM_MPF_NET_BUF_IP_MSS) && NUM_MPF_NET_BUF_IP_MSS > 0
185 {
186 MPF_NET_BUF_IP_MSS,
187 IF_HDR_SIZE + IP4_MSS,
188
189#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
190
191 NUM_MPF_NET_BUF_IP_MSS,
192
193#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
194
195 },
196#endif /* of #if defined(NUM_MPF_NET_BUF_IP_MSS) && NUM_MPF_NET_BUF_IP_MSS > 0 */
197
198#if defined(NUM_MPF_NET_BUF_512) && NUM_MPF_NET_BUF_512 > 0
199 {
200 MPF_NET_BUF_512,
201 UINT_C(512),
202
203#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
204
205 NUM_MPF_NET_BUF_512,
206
207#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
208
209 },
210#endif /* of #if defined(NUM_MPF_NET_BUF_512) && NUM_MPF_NET_BUF_512 > 0 */
211
212#if defined(NUM_MPF_NET_BUF_256) && NUM_MPF_NET_BUF_256 > 0
213 {
214 MPF_NET_BUF_256,
215 UINT_C(256),
216
217#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
218
219 NUM_MPF_NET_BUF_256,
220
221#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
222
223 },
224#endif /* of #if defined(NUM_MPF_NET_BUF_256) && NUM_MPF_NET_BUF_256 > 0 */
225
226#if defined(NUM_MPF_NET_BUF_128) && NUM_MPF_NET_BUF_128 > 0
227 {
228 MPF_NET_BUF_128,
229 UINT_C(128),
230
231#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
232
233 NUM_MPF_NET_BUF_128,
234
235#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
236
237 },
238#endif /* of #if defined(NUM_MPF_NET_BUF_128) && NUM_MPF_NET_BUF_128 > 0 */
239
240#if defined(_IP4_CFG)
241
242#if defined(NUM_MPF_NET_BUF_64) && NUM_MPF_NET_BUF_64 > 0
243 {
244 MPF_NET_BUF_64,
245 UINT_C(64),
246
247#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
248
249 NUM_MPF_NET_BUF_64,
250
251#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
252
253 },
254#endif /* of #if defined(NUM_MPF_NET_BUF_64) && NUM_MPF_NET_BUF_64 > 0 */
255
256#endif /* of #if defined(_IP4_CFG) */
257
258#if defined(NUM_MPF_NET_BUF_CSEG) && NUM_MPF_NET_BUF_CSEG > 0
259 {
260 MPF_NET_BUF_CSEG,
261 IF_HDR_SIZE + IP_HDR_SIZE + TCP_HDR_SIZE,
262
263#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
264
265 NUM_MPF_NET_BUF_CSEG,
266
267#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
268
269 },
270#endif /* of #if defined(NUM_MPF_NET_BUF_CSEG) && NUM_MPF_NET_BUF_CSEG > 0 */
271
272 };
273
274#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
275
276/*
277 * nbuf_get_tbl -- ネットワークバッファ管理表を獲得する。
278 *
279 * 注意: ネットワーク統計情
280報の計測用
281 */
282
283const T_NET_BUF_ENTRY *
284nbuf_get_tbl (void)
285{
286 return net_buf_table;
287 }
288
289/*
290 * nbuf_get_tbl_size -- ネットワークバッファ管理エントリ数を獲得する。
291 *
292 * 注意: ネットワーク統計情
293報の計測用
294 */
295
296uint_t
297nbuf_get_tbl_size (void)
298{
299 return sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY);
300 }
301
302#endif /* of #if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF */
303
304/*
305 * tget_net_buf_up -- 大きなサイズの方向に探索して、ネットワークバッファを獲得する。
306 */
307
308static ER
309tget_net_buf_up (T_NET_BUF **buf, uint_t minlen, uint_t maxlen, TMO tmout)
310{
311 int_t ix, req_ix;
312 ER error = E_OK;
313
314 /* 最適なサイズの固定長メモリプールを探す。*/
315 ix = sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY);
316 while (ix -- > 0 && minlen > net_buf_table[ix].size)
317 ;
318 req_ix = ix;
319
320 NET_COUNT_NET_BUF(net_buf_table[req_ix].requests, 1);
321
322 while (1) {
323 if ((error = tget_mpf((ID)net_buf_table[ix].index, (void*)buf, ix == 0 ? tmout : TMO_POL)) == E_OK) {
324 (*buf)->idix = (uint8_t)ix;
325 (*buf)->len = (uint16_t)minlen;
326 (*buf)->flags = 0;
327
328#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
329 NET_COUNT_NET_BUF(net_buf_table[ix].allocs, 1);
330 net_buf_table[ix].busies ++;
331#endif
332 return error;
333 }
334 else if (ix == 0 || net_buf_table[ix].size > maxlen)
335 break;
336 ix --;
337 }
338
339 syslog(LOG_WARNING, "[BUF] busy, up index:%d,%d[%4d], len:%4d.",
340 (uint16_t)req_ix, ix, net_buf_table[req_ix].size, minlen);
341 *buf = NULL;
342 NET_COUNT_NET_BUF(net_buf_table[req_ix].errors, 1);
343 return error;
344 }
345
346/*
347 * tget_net_buf_down -- 小さなサイズの方向に探索して、ネットワークバッファを獲得する。
348 */
349
350static ER
351tget_net_buf_down (T_NET_BUF **buf, uint_t minlen, uint_t maxlen, TMO tmout)
352{
353 int_t ix, req_ix;
354 ER error = E_OK;
355
356 /* 最適なサイズの固定長メモリプールを探す。*/
357 ix = sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY);
358 while (ix -- > 0 && maxlen > net_buf_table[ix].size)
359 ;
360 req_ix = ix;
361
362 NET_COUNT_NET_BUF(net_buf_table[req_ix].requests, 1);
363
364 while (1) {
365 if ((error = tget_mpf((ID)net_buf_table[ix].index, (void*)buf,
366 ix == sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY) - 1 ? tmout : TMO_POL)) == E_OK) {
367 (*buf)->idix = (uint8_t)ix;
368 (*buf)->len = net_buf_table[ix].size;
369 (*buf)->flags = 0;
370
371#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
372 NET_COUNT_NET_BUF(net_buf_table[ix].allocs, 1);
373 net_buf_table[ix].busies ++;
374#endif
375 return error;
376 }
377 ix ++;
378 if (ix == sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY) || net_buf_table[ix].size < minlen)
379 break;
380 }
381
382 syslog(LOG_WARNING, "[BUF] busy, down index:%d,%d[%4d], len:%4d.",
383 (uint16_t)req_ix, ix, net_buf_table[req_ix].size, minlen);
384 *buf = NULL;
385 NET_COUNT_NET_BUF(net_buf_table[req_ix].errors, 1);
386 return error;
387 }
388
389/*
390 * tget_net_buf_ex -- ネットワークバッファを獲得する(拡張機能)。
391 */
392
393ER
394tget_net_buf_ex (T_NET_BUF **buf, uint_t minlen, uint_t maxlen, ATR nbatr, TMO tmout)
395{
396 /* 最小サイズが最大サイズを超
397えていたらエラー */
398 if ((nbatr & NBA_SEARCH_DESCENT) != 0 && minlen > maxlen) {
399 syslog(LOG_WARNING, "[NET BUF] E_PAR, minlen=%4d > maxlen=%4d.", minlen, maxlen);
400 return E_PAR;
401 }
402
403 /* 割当て可能な最大のサイズを超
404えていたらエラー */
405 if (minlen > net_buf_table[0].size || maxlen > net_buf_table[0].size) {
406 syslog(LOG_WARNING, "[NET BUF] E_PAR, minlen=%4d or maxlen=%4d > %4d",
407 minlen, maxlen, net_buf_table[0].size);
408 return E_PAR;
409 }
410
411#if defined(SUPPORT_TCP) && defined(TCP_CFG_SWBUF_CSAVE)
412
413 /* TCP で予約したネットワークバッファを取り出す。*/
414 if ((nbatr & NBA_RESERVE_TCP) != 0) {
415 if ((*buf = TCP_PULL_RES_NBUF(nbatr)) != NULL) {
416 return E_OK;
417 }
418 }
419
420#endif /* of #if defined(SUPPORT_TCP) && defined(TCP_CFG_SWBUF_CSAVE) */
421
422 if ((nbatr & NBA_SEARCH_DESCENT) != 0)
423 return tget_net_buf_down(buf, minlen, maxlen, tmout);
424 else if ((nbatr & NBA_SEARCH_ASCENT) != 0)
425 return tget_net_buf_up(buf, minlen, (uint_t)net_buf_table[0].size, tmout);
426 else {
427 syslog(LOG_WARNING, "[NET BUF] E_PAR, nbatr=%08x.", nbatr);
428 return E_PAR;
429 }
430 }
431
432/*
433 * tget_net_buf -- ネットワークバッファを獲得する(互換)。
434 */
435
436ER
437tget_net_buf (T_NET_BUF **buf, uint_t len, TMO tmout)
438{
439 return tget_net_buf_ex(buf, len, (uint_t)net_buf_table[0].size, NBA_SEARCH_ASCENT, tmout);
440 }
441
442/*
443 * rel_net_buf -- ネットワークバッファを返却する。
444 */
445
446ER
447rel_net_buf (T_NET_BUF *buf)
448{
449 ER error = E_OK;
450
451 /* ネットワークバッファの ID の正当性を検証する。*/
452 if ((int_t)buf->idix >= (int_t)(sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY))) {
453 syslog(LOG_WARNING, "[NET BUF] E_ID, ID=%d.", buf->idix);
454 error = E_ID;
455 }
456 else {
457
458#if defined(SUPPORT_TCP) && defined(TCP_CFG_SWBUF_CSAVE)
459
460 /* TCP で、ネットワークバッファを予約する。*/
461 if (TCP_PUSH_RES_NBUF(buf) == NULL)
462 return E_OK;
463
464#endif /* of #if defined(SUPPORT_TCP) && defined(TCP_CFG_SWBUF_CSAVE) */
465
466 /* 固定メモリプールに返す。*/
467
468#if NET_COUNT_ENABLE & PROTO_FLG_NET_BUF
469 net_buf_table[buf->idix].busies --;
470#endif
471 if ((error = rel_mpf((ID)net_buf_table[buf->idix].index, buf)) != E_OK) {
472 syslog(LOG_WARNING, "[NET BUF] %s, ID=%d.", itron_strerror(error), buf->idix);
473 }
474 }
475 return error;
476 }
477
478/*
479 * rus_net_buf -- ネットワークバッファを再利用する。
480 */
481
482ER
483rus_net_buf (T_NET_BUF *buf)
484{
485 ER error = E_OK;
486
487 if (buf->idix >= sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY)) {
488 syslog(LOG_WARNING, "[NET BUF] E_ID, ID=%d.", buf->idix);
489 error = E_ID;
490 }
491 else {
492 buf->len = net_buf_table[buf->idix].size;
493 buf->flags = 0;
494 error = E_OK;
495 }
496 return error;
497 }
498
499/*
500 * net_buf_siz -- ネットワークバッファのサイズを返す。
501 */
502
503ER_UINT
504net_buf_siz (T_NET_BUF *buf)
505{
506 if (buf->idix >= sizeof(net_buf_table) / sizeof(T_NET_BUF_ENTRY)) {
507 syslog(LOG_WARNING, "[BUF SIZ] E_ID, ID=%d.", buf->idix);
508 return E_ID;
509 }
510 else
511 return (ER_UINT)net_buf_table[buf->idix].size;
512 }
513
514/*
515 * net_buf_max_siz -- ネットワークバッファの最大サイズを返す。
516 */
517
518uint_t
519net_buf_max_siz (void)
520{
521 return (uint_t)net_buf_table[0].size;
522 }
Note: See TracBrowser for help on using the repository browser.