OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [ecos-2.0/] [packages/] [redboot/] [v2_0/] [src/] [net/] [ip.c] - Blame information for rev 1773

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1254 phoenix
//==========================================================================
2
//
3
//      net/ip.c
4
//
5
//      Stand-alone IP networking support for RedBoot
6
//
7
//==========================================================================
8
//####ECOSGPLCOPYRIGHTBEGIN####
9
// -------------------------------------------
10
// This file is part of eCos, the Embedded Configurable Operating System.
11
// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
12
// Copyright (C) 2002 Gary Thomas
13
//
14
// eCos is free software; you can redistribute it and/or modify it under
15
// the terms of the GNU General Public License as published by the Free
16
// Software Foundation; either version 2 or (at your option) any later version.
17
//
18
// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
19
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
20
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
21
// for more details.
22
//
23
// You should have received a copy of the GNU General Public License along
24
// with eCos; if not, write to the Free Software Foundation, Inc.,
25
// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
26
//
27
// As a special exception, if other files instantiate templates or use macros
28
// or inline functions from this file, or you compile this file and link it
29
// with other works to produce a work based on this file, this file does not
30
// by itself cause the resulting work to be covered by the GNU General Public
31
// License. However the source code for this file must still be made available
32
// in accordance with section (3) of the GNU General Public License.
33
//
34
// This exception does not invalidate any other reasons why a work based on
35
// this file might be covered by the GNU General Public License.
36
//
37
// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
38
// at http://sources.redhat.com/ecos/ecos-license/
39
// -------------------------------------------
40
//####ECOSGPLCOPYRIGHTEND####
41
//==========================================================================
42
//#####DESCRIPTIONBEGIN####
43
//
44
// Author(s):    gthomas
45
// Contributors: gthomas
46
// Date:         2000-07-14
47
// Purpose:      
48
// Description:  
49
//              
50
// This code is part of RedBoot (tm).
51
//
52
//####DESCRIPTIONEND####
53
//
54
//==========================================================================
55
 
56
#include <net/net.h>
57
 
58
#ifndef CYGDAT_REDBOOT_DEFAULT_IP_ADDR
59
# define CYGDAT_REDBOOT_DEFAULT_IP_ADDR 0, 0, 0, 0
60
#endif
61
#ifndef CYGDAT_REDBOOT_DEFAULT_IP_ADDR_MASK
62
# define CYGDAT_REDBOOT_DEFAULT_IP_ADDR_MASK 255, 255, 255, 0
63
#endif
64
#ifndef CYGDAT_REDBOOT_DEFAULT_GATEWAY_IP_ADDR
65
# define CYGDAT_REDBOOT_DEFAULT_GATEWAY_IP_ADDR 0, 0, 0, 0
66
#endif
67
 
68
ip_addr_t __local_ip_addr = { CYGDAT_REDBOOT_DEFAULT_IP_ADDR };
69
#ifdef CYGSEM_REDBOOT_NETWORKING_USE_GATEWAY
70
ip_addr_t __local_ip_mask = { CYGDAT_REDBOOT_DEFAULT_IP_ADDR_MASK };
71
ip_addr_t __local_ip_gate = { CYGDAT_REDBOOT_DEFAULT_GATEWAY_IP_ADDR };
72
#endif
73
 
74
static word ip_ident;
75
 
76
#ifdef CYGSEM_REDBOOT_NETWORKING_USE_GATEWAY
77
/*
78
 * See if an address is on the local network
79
 */
80
int
81
__ip_addr_local(ip_addr_t *addr)
82
{
83
  return !(
84
           ((__local_ip_addr[0] ^ (*addr)[0]) & __local_ip_mask[0]) |
85
           ((__local_ip_addr[1] ^ (*addr)[1]) & __local_ip_mask[1]) |
86
           ((__local_ip_addr[2] ^ (*addr)[2]) & __local_ip_mask[2]) |
87
           ((__local_ip_addr[3] ^ (*addr)[3]) & __local_ip_mask[3]));
88
}
89
#endif
90
 
91
/*
92
 * Match given IP address to our address.
93
 * Check for broadcast matches as well.
94
 */
95
static int
96
ip_addr_match(ip_addr_t addr)
97
{
98
    if (addr[0] == 255 && addr[1] == 255 && addr[2] == 255 && addr[3] == 255)
99
        return 1;
100
 
101
    if (!memcmp(addr, __local_ip_addr, sizeof(ip_addr_t)))
102
        return 1;
103
 
104
    /*
105
     * Consider it an address match if we haven't gotten our IP address yet.
106
     * Some DHCP servers will address IP packets to the assigned address
107
     * instead of a IP broadcast address.
108
     */
109
    if (__local_ip_addr[0] == 0 && __local_ip_addr[1] == 0 &&
110
        __local_ip_addr[2] == 0 && __local_ip_addr[3] == 0)
111
        return 1;
112
 
113
    return 0;
114
}
115
 
116
 
117
extern void __tcp_handler(pktbuf_t *, ip_route_t *);
118
 
119
/*
120
 * Handle IP packets coming from the polled ethernet interface.
121
 */
122
void
123
__ip_handler(pktbuf_t *pkt, enet_addr_t *src_enet_addr)
124
{
125
    ip_header_t *ip = pkt->ip_hdr;
126
    ip_route_t  r;
127
    int         hdr_bytes;
128
 
129
    /* first make sure its ours and has a good checksum. */
130
    if (!ip_addr_match(ip->destination) ||
131
        __sum((word *)ip, ip->hdr_len << 2, 0) != 0) {
132
        __pktbuf_free(pkt);
133
        return;
134
    }
135
 
136
    memcpy(r.ip_addr, ip->source, sizeof(ip_addr_t));
137
    memcpy(r.enet_addr, src_enet_addr, sizeof(enet_addr_t));
138
 
139
    hdr_bytes = ip->hdr_len << 2;
140
    pkt->pkt_bytes = ntohs(ip->length) - hdr_bytes;
141
 
142
    switch (ip->protocol) {
143
 
144
#if NET_SUPPORT_ICMP
145
      case IP_PROTO_ICMP:
146
        pkt->icmp_hdr = (icmp_header_t *)(((char *)ip) + hdr_bytes);
147
        __icmp_handler(pkt, &r);
148
        break;
149
#endif
150
 
151
#if NET_SUPPORT_TCP
152
      case IP_PROTO_TCP:
153
        pkt->tcp_hdr = (tcp_header_t *)(((char *)ip) + hdr_bytes);
154
        __tcp_handler(pkt, &r);
155
        break;
156
#endif
157
 
158
#if NET_SUPPORT_UDP
159
      case IP_PROTO_UDP:
160
        pkt->udp_hdr = (udp_header_t *)(((char *)ip) + hdr_bytes);
161
        __udp_handler(pkt, &r);
162
        break;
163
#endif
164
 
165
      default:
166
        __pktbuf_free(pkt);
167
        break;
168
    }
169
}
170
 
171
 
172
/*
173
 * Send an IP packet.
174
 *
175
 * The IP data field should contain pkt->pkt_bytes of data.
176
 * pkt->[udp|tcp|icmp]_hdr points to the IP data field. Any
177
 * IP options are assumed to be already in place in the IP
178
 * options field.
179
 */
180
int
181
__ip_send(pktbuf_t *pkt, int protocol, ip_route_t *dest)
182
{
183
    ip_header_t *ip = pkt->ip_hdr;
184
    int         hdr_bytes;
185
    unsigned short cksum;
186
 
187
    /*
188
     * Figure out header length. The use udp_hdr is
189
     * somewhat arbitrary, but works because it is
190
     * a union with other IP protocol headers.
191
     */
192
    hdr_bytes = (((char *)pkt->udp_hdr) - ((char *)ip));
193
 
194
    pkt->pkt_bytes += hdr_bytes;
195
 
196
    ip->version = 4;
197
    ip->hdr_len = hdr_bytes >> 2;
198
    ip->tos = 0;
199
    ip->length = htons(pkt->pkt_bytes);
200
    ip->ident = htons(ip_ident);
201
    ip_ident++;
202
    ip->fragment = 0;
203
    ip->ttl = 255;
204
    ip->ttl = 64;
205
    ip->protocol = protocol;
206
    ip->checksum = 0;
207
    memcpy(ip->source, __local_ip_addr, sizeof(ip_addr_t));
208
    memcpy(ip->destination, dest->ip_addr, sizeof(ip_addr_t));
209
    cksum = __sum((word *)ip, hdr_bytes, 0);
210
    ip->checksum = htons(cksum);
211
 
212
    __enet_send(pkt, &dest->enet_addr, ETH_TYPE_IP);
213
    return 0;
214
}
215
 
216
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.