Mercurial > flash_v2
annotate packages/net/common/current/src/ipv6_routing_thread.c @ 1777:c16341b1bac6 default tip
* Added execute permissions to files missed in conversion from CVS
| author | alexs |
|---|---|
| date | Mon, 12 Oct 2009 02:26:09 +0100 |
| parents | fddabea2836c |
| children |
| rev | line source |
|---|---|
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
1 //========================================================================== |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
2 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
3 // ipv6_routing_thread.c |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
4 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
5 // IPv6 routing support |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
6 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
7 //========================================================================== |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
8 //####BSDCOPYRIGHTBEGIN#### |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
9 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
10 // ------------------------------------------- |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
11 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
12 // Portions of this software may have been derived from OpenBSD or other sources, |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
13 // and are covered by the appropriate copyright disclaimers included herein. |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
14 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
15 // ------------------------------------------- |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
16 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
17 //####BSDCOPYRIGHTEND#### |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
18 //========================================================================== |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
19 //#####DESCRIPTIONBEGIN#### |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
20 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
21 // Author(s): gthomas |
| 957 | 22 // Contributors: gthomas, lhamilton, andrew.lunn@ascom.ch |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
23 // Date: 2002-04-16 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
24 // Purpose: |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
25 // Description: |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
26 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
27 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
28 //####DESCRIPTIONEND#### |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
29 // |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
30 //========================================================================== |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
31 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
32 // IPv6 routing support |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
33 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
34 #include <pkgconf/net.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
35 #undef _KERNEL |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
36 #include <sys/param.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
37 #include <sys/types.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
38 #include <sys/ioctl.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
39 #include <sys/socket.h> |
| 1146 | 40 #include <sys/select.h> |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
41 #include <errno.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
42 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
43 #include <cyg/kernel/kapi.h> |
| 1146 | 44 #include <cyg/infra/diag.h> |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
45 #include <net/if.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
46 #include <ifaddrs.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
47 #include <net/if_var.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
48 #include <netinet/in.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
49 #include <netinet/ip6.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
50 #include <netinet/icmp6.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
51 #include <netdb.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
52 #include <netinet6/in6_var.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
53 #include <netinet6/nd6.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
54 |
| 300 | 55 #include <stdio.h> |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
56 #include <unistd.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
57 #include <stdlib.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
58 #include <string.h> |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
59 |
| 300 | 60 void _show_all_interfaces(void); |
| 61 | |
| 957 | 62 //#define DBG_PRINT 1 |
| 300 | 63 #define ALLROUTER "ff02::2" |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
64 |
| 300 | 65 #define STACK_SIZE CYGNUM_HAL_STACK_SIZE_TYPICAL+2048 |
| 66 #define _1_MILLION 1000000 | |
| 67 #define STATE_DELAY 0 | |
| 68 #define STATE_PROBE 1 | |
| 69 #define STATE_IDLE 2 | |
| 70 | |
| 71 #define MAX_RTR_SOLICITATIONS 3 | |
| 72 #define SEL_TIMEOUT_IDLE 145 | |
| 73 #define SECONDS_TILL_RS_SEND (12*60*60) | |
| 74 | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
75 static char rs_stack[STACK_SIZE]; |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
76 static cyg_thread rs_thread_data; |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
77 static cyg_handle_t rs_thread_handle; |
| 300 | 78 static int s; |
| 79 static int probe=0; | |
| 80 static int racount=0; | |
| 81 static int state; | |
| 82 static int badra; | |
| 83 static int cc = sizeof(struct icmp6_hdr); | |
| 84 static u_char outpack[sizeof(struct icmp6_hdr)]; | |
| 85 struct sockaddr_in6 to; | |
| 86 static struct timeval select_timeout; | |
| 87 static struct timeval last_ra_time; | |
| 88 static struct timeval idle_expire; | |
| 89 static struct icmp6stat *istat; | |
| 90 extern struct icmp6stat cyg_icmp6stat; | |
| 957 | 91 static struct sockaddr_in6 router; |
| 92 static int router_valid = 0; | |
| 93 | |
| 94 // Return the address of the last router to send us a router advertisement | |
| 95 // Copy the address into addr and return true. If we have not received an | |
| 96 // advertisement yet, return false | |
| 97 int cyg_net_get_ipv6_advrouter(struct sockaddr_in6 * addr) { | |
| 98 | |
| 99 if (addr) { | |
| 100 memcpy(addr,&router,sizeof(*addr)); | |
| 101 } | |
| 102 return router_valid; | |
| 103 } | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
104 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
105 static void |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
106 cyg_rs_exit(void) |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
107 { |
| 300 | 108 diag_printf("<%s>\n", __FUNCTION__); |
| 109 cyg_thread_exit(); | |
| 110 } | |
| 111 | |
| 112 static void | |
| 113 dprnt(const char *msg, ...) | |
| 114 { | |
| 115 #ifdef DBG_PRINT | |
| 116 va_list ap; | |
| 117 | |
| 118 va_start(ap, msg); | |
| 119 (void) vfprintf(stdout, msg, ap); | |
| 120 (void) fprintf(stdout, "\n"); | |
| 121 va_end(ap); | |
| 122 #endif | |
| 123 } | |
| 124 | |
| 125 #ifdef DBG_PRINT | |
| 126 void | |
| 127 sleep_msg(char *str, int total) | |
| 128 { | |
| 129 int hours, minutes; | |
| 130 | |
| 131 hours = total / 3600; | |
| 132 total -= hours * 3600; | |
| 133 minutes = total / 60; | |
| 134 total -= minutes * 60; | |
| 135 | |
| 136 if (hours > 0) | |
| 137 dprnt("%s: %d hr, %d min", str, hours, minutes); | |
| 138 else if (minutes > 0) | |
| 139 dprnt("%s: %d min, %d sec", str, minutes, total); | |
| 140 else | |
| 141 dprnt("%s: %d sec", str, total); | |
| 142 } | |
| 143 #endif | |
| 144 | |
| 145 void | |
| 146 get_realtime(struct timeval *now) | |
| 147 { | |
| 148 struct timespec tp; | |
| 149 clock_gettime(CLOCK_REALTIME, &tp); | |
| 150 now->tv_sec = tp.tv_sec; | |
| 151 now->tv_usec = 0; | |
| 152 } | |
| 153 | |
| 154 void | |
| 155 send_rs_packet(void) | |
| 156 { | |
| 157 probe++; | |
| 158 | |
| 159 dprnt("%s: probe=%d", __FUNCTION__, probe); | |
| 160 | |
| 161 if (sendto(s, outpack, cc, 0, (struct sockaddr *)&to, to.sin6_len) < 0) { | |
| 162 dprnt("%s: can't send RS: %s", __FUNCTION__, strerror(errno)); | |
| 163 } | |
| 164 } | |
| 165 | |
| 166 void | |
| 167 receive_ra_packet(void) | |
| 168 { | |
| 169 int len; | |
| 170 char msg[1024]; | |
| 957 | 171 struct nd_router_advert *advert; |
| 172 cyg_uint8 *opts; | |
| 173 int optlen; | |
| 174 int addrlen = sizeof(router); | |
| 175 char buf[64]; | |
| 300 | 176 |
| 177 dprnt("%s", __FUNCTION__); | |
| 178 | |
| 957 | 179 len = recvfrom(s, msg, sizeof(msg),0,(struct sockaddr *)&router,&addrlen); |
| 300 | 180 if (len < 0) { |
| 181 dprnt(" Can't read RA data: %s", strerror(errno)); | |
| 182 return; | |
| 183 } | |
| 957 | 184 router_valid = 1; |
| 185 | |
| 186 inet_ntop(AF_INET6,(void *)&router.sin6_addr,buf,64); | |
| 187 dprnt("Router Advertisement from %s",buf); | |
| 300 | 188 dprnt("packet data (buf len=%d) :", len); |
| 957 | 189 #ifdef DBG_PRINT |
| 300 | 190 diag_dump_buf(msg, len); |
| 957 | 191 #endif |
| 300 | 192 |
| 957 | 193 advert = (struct nd_router_advert *)msg; |
| 194 | |
| 195 dprnt("AdvCurHopLimit: %d", (int) advert->nd_ra_curhoplimit); | |
| 196 dprnt("AdvManagedFlag: %s", | |
| 197 (advert->nd_ra_flags_reserved & ND_RA_FLAG_MANAGED) ? "yes" : "no"); | |
| 198 dprnt("AdvOtherConfigFlag: %s", | |
| 199 (advert->nd_ra_flags_reserved & ND_RA_FLAG_OTHER) ? "yes":"no"); | |
| 200 dprnt("AdvHomeAgentFlag: %s", | |
| 201 (advert->nd_ra_flags_reserved & ND_RA_FLAG_HOME_AGENT) ? | |
| 202 "yes" : "no"); | |
| 203 dprnt("AdvReachableTime: %lu", | |
| 204 (unsigned long)ntohl(advert->nd_ra_reachable)); | |
| 205 dprnt("AdvRetransTimer: %lu", | |
| 206 (unsigned long)ntohl(advert->nd_ra_retransmit)); | |
| 207 | |
| 208 // Now process the optinal fields | |
| 209 len -= sizeof(*advert); | |
| 210 opts = (cyg_uint8 *)(msg + sizeof(struct nd_router_advert)); | |
| 211 | |
| 212 while (len > 0) { | |
| 213 optlen = (opts[1] << 3); | |
| 214 switch (*opts) { | |
| 215 case ND_OPT_MTU: { | |
| 216 struct nd_opt_mtu *mtu = (struct nd_opt_mtu *) opts; | |
| 217 | |
| 218 dprnt("AdvLinkMTU: %lu", | |
| 219 (unsigned long)ntohl(mtu->nd_opt_mtu_mtu)); | |
| 220 break; | |
| 221 } | |
| 222 case ND_OPT_PREFIX_INFORMATION: { | |
| 223 struct nd_opt_prefix_info *pinfo = (struct nd_opt_prefix_info *) opts; | |
| 224 | |
| 225 inet_ntop(AF_INET6,(void *)&pinfo->nd_opt_pi_prefix,buf,64); | |
| 226 dprnt("Prefix: %s/%d",buf,pinfo->nd_opt_pi_prefix_len); | |
| 227 break; | |
| 228 } | |
| 229 case ND_OPT_SOURCE_LINKADDR: { | |
| 230 char *cp = buf; | |
| 231 int i; | |
| 232 | |
| 233 for (i = 2 ; i < optlen ; i++) { | |
| 234 cp += diag_sprintf(cp,"%02x ", (unsigned int) opts[i]); | |
| 235 } | |
| 236 | |
| 237 dprnt("AdvSourceLinkAddress: %s",buf); | |
| 238 break; | |
| 239 } | |
| 240 case ND_OPT_ADVINTERVAL: | |
| 241 case ND_OPT_HOMEAGENT_INFO: | |
| 242 dprnt("Mobile IPv6 entension options (not decoded)"); | |
| 243 break; | |
| 244 default: | |
| 245 dprnt("Unknown option %d\n", (int)*opts); | |
| 246 break; | |
| 247 } | |
| 248 len -= optlen; | |
| 249 opts += optlen; | |
| 250 } | |
| 251 | |
| 300 | 252 racount++; |
| 253 get_realtime(&last_ra_time); | |
| 254 dprnt("racount=%d, timestamp=%d sec", | |
| 255 racount, last_ra_time.tv_sec); | |
| 256 | |
| 257 if (badra != istat->icp6s_badra) { | |
| 258 /* BAD RA received by ipv6 stack (nd6_ra_input). | |
| 259 Resend RS packet. */ | |
| 260 badra = istat->icp6s_badra; | |
| 261 dprnt("<Bad RA (Router Advertisement)>"); | |
| 262 return; | |
| 263 } | |
| 264 /* Check the ICMPv6 RA Code */ | |
| 265 if (msg[1] != 0) { | |
| 266 len = (int)msg[1]; | |
| 267 dprnt("<Bad ICMPv6 Code: %d>", len); | |
| 268 return; | |
| 269 } | |
| 270 | |
| 271 /* RA received, go idle for SECONDS_TILL_RS_SEND */ | |
| 272 idle_expire.tv_sec = last_ra_time.tv_sec + | |
| 273 SECONDS_TILL_RS_SEND; | |
| 274 probe = 0; | |
| 275 select_timeout.tv_sec = SEL_TIMEOUT_IDLE; | |
| 276 if (state != STATE_IDLE) | |
| 277 dprnt("Going IDLE, thread listening"); | |
| 278 state = STATE_IDLE; | |
| 279 } | |
| 280 | |
| 281 void | |
| 282 check_timer(void) | |
| 283 { | |
| 284 struct timeval now; | |
| 285 | |
| 286 if (state == STATE_DELAY) { | |
| 287 probe = 0; | |
| 288 select_timeout.tv_sec = RTR_SOLICITATION_INTERVAL; | |
| 289 state = STATE_PROBE; | |
| 290 send_rs_packet(); | |
| 291 } else if (state == STATE_PROBE) { | |
| 292 dprnt("%s: state: PROBE", __FUNCTION__); | |
| 293 if (probe < MAX_RTR_SOLICITATIONS) { | |
| 294 send_rs_packet(); | |
| 295 } else { | |
| 296 dprnt("Maximum %d rtr solicitations sent out", | |
| 297 MAX_RTR_SOLICITATIONS); | |
| 298 get_realtime(&now); | |
| 299 probe = 0; | |
| 300 idle_expire.tv_sec = now.tv_sec + | |
| 301 SECONDS_TILL_RS_SEND; | |
| 302 dprnt("Going IDLE"); | |
| 303 select_timeout.tv_sec = SEL_TIMEOUT_IDLE; | |
| 304 state = STATE_IDLE; | |
| 305 #ifdef DBG_PRINT | |
| 306 sleep_msg("Thread listening (state=IDLE)", | |
| 307 SECONDS_TILL_RS_SEND); | |
| 308 #endif | |
| 309 } | |
| 310 } else { | |
| 311 /* STATE_IDLE */ | |
| 312 get_realtime(&now); | |
| 313 if (now.tv_sec >= idle_expire.tv_sec) { | |
| 314 dprnt("<Leaving IDLE; Woke up to retry RS send>"); | |
| 315 select_timeout.tv_sec = 1; | |
| 316 state = STATE_DELAY; | |
| 317 } | |
| 318 #ifdef DBG_PRINT | |
| 319 else if ((idle_expire.tv_sec - now.tv_sec) < (5 * 60)) { | |
| 320 sleep_msg("Coming out of IDLE in", | |
| 321 idle_expire.tv_sec - now.tv_sec); | |
| 322 } | |
| 323 #endif | |
| 324 } | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
325 } |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
326 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
327 static void |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
328 cyg_rs(cyg_addrword_t param) |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
329 { |
| 300 | 330 struct addrinfo hints, *res; |
| 331 struct icmp6_hdr *icp; | |
| 332 struct icmp6_filter filt; | |
| 333 struct timeval loop_delay; | |
| 334 int err, status; | |
| 335 u_int hlim = 255; | |
| 336 fd_set fdset; | |
| 337 | |
| 957 | 338 #ifdef DBG_PRINT |
| 300 | 339 _show_all_interfaces(); |
| 957 | 340 #endif |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
341 |
| 300 | 342 memset(&hints, 0, sizeof(hints)); |
| 343 hints.ai_family = AF_INET6; | |
|
1007
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
344 hints.ai_flags = AI_NUMERICHOST; |
| 300 | 345 err = getaddrinfo(ALLROUTER, NULL, &hints, &res); |
| 346 if (err) { | |
| 347 dprnt("%s - failed to get ALL ROUTER: %s", | |
| 348 __FUNCTION__, gai_strerror(err)); | |
| 349 cyg_rs_exit(); | |
| 350 } | |
| 351 memcpy(&to, res->ai_addr, res->ai_addrlen); | |
| 352 *(u_int16_t *)&to.sin6_addr.s6_addr[2] = htons(1); | |
| 353 | |
| 354 if ((s = socket(AF_INET6, SOCK_RAW, IPPROTO_ICMPV6)) < 0) { | |
| 355 dprnt("%s - can't open socket: %s", | |
| 356 __FUNCTION__, strerror(errno)); | |
| 357 cyg_rs_exit(); | |
| 358 } | |
| 359 if (setsockopt(s, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, | |
| 360 &hlim, sizeof(hlim)) < 0) { | |
| 361 dprnt("%s - can't set IPV6 MULTICAST HOPS: %s", | |
| 362 __FUNCTION__, strerror(errno)); | |
| 363 cyg_rs_exit(); | |
| 364 } | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
365 |
| 300 | 366 /* Specify to accept only router advertisements on the socket */ |
| 367 ICMP6_FILTER_SETBLOCKALL(&filt); | |
| 368 ICMP6_FILTER_SETPASS(ND_ROUTER_ADVERT, &filt); | |
| 369 if (setsockopt(s, IPPROTO_ICMPV6, ICMP6_FILTER, | |
| 370 &filt, sizeof(filt)) < 0) { | |
| 371 dprnt("%s - can't set ICMP6 filter: %s", | |
| 372 __FUNCTION__, strerror(errno)); | |
| 373 cyg_rs_exit(); | |
| 374 } | |
| 375 | |
| 376 idle_expire.tv_usec = 0; | |
| 377 select_timeout.tv_usec = 0; | |
| 378 last_ra_time.tv_usec = 0; | |
| 957 | 379 last_ra_time.tv_sec = 2; |
| 300 | 380 select(0, 0, 0, 0, &last_ra_time); |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
381 |
| 300 | 382 racount = 0; |
| 383 istat = &(cyg_icmp6stat); | |
| 384 badra = istat->icp6s_badra; | |
| 385 | |
| 386 icp = (struct icmp6_hdr *)outpack; | |
| 387 icp->icmp6_type = ND_ROUTER_SOLICIT; | |
| 388 icp->icmp6_code = 0; | |
| 389 icp->icmp6_cksum = 0; | |
| 390 icp->icmp6_data32[0] = 0; /* RS reserved field */ | |
| 391 state = STATE_DELAY; | |
| 392 | |
| 393 while (true) { | |
| 394 FD_ZERO(&fdset); | |
| 395 FD_SET(s, &fdset); | |
| 396 | |
| 397 check_timer(); | |
| 398 | |
| 399 status = select(s + 1, &fdset, NULL, NULL, &select_timeout); | |
| 400 if (status < 0) { | |
| 401 dprnt("%s - select: %s", strerror(errno)); | |
| 402 continue; | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
403 } |
| 300 | 404 if (status == 1) |
| 405 receive_ra_packet(); | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
406 |
| 300 | 407 loop_delay.tv_sec = 2; |
| 408 loop_delay.tv_usec = 0; | |
| 409 select(0, 0, 0, 0, &loop_delay); | |
| 410 } | |
| 411 /* NOTREACHED */ | |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
412 } |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
413 |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
414 void |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
415 ipv6_start_routing_thread(void) |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
416 { |
|
1007
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
417 static int started = 0; |
|
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
418 |
|
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
419 started++; |
|
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
420 |
|
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
421 if (started == 1) { |
|
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
422 |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
423 cyg_thread_create( |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
424 CYGINT_NET_IPV6_ROUTING_THREAD_PRIORITY, // Priority |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
425 cyg_rs, // entry |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
426 0, // parameter |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
427 "IPv6 routing", // Name |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
428 &rs_stack[0], // Stack |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
429 STACK_SIZE, // Size |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
430 &rs_thread_handle, // Handle |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
431 &rs_thread_data // Thread data structure |
|
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
432 ); |
| 300 | 433 cyg_thread_resume(rs_thread_handle); // Start it |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
434 diag_printf("IPv6 routing thread started\n"); |
|
1007
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
435 } |
|
208
e0c0827131d1
Merge from eCos master repository on 2002-05-20-20:11:54-BST
jlarmour
parents:
diff
changeset
|
436 } |
| 300 | 437 |
|
1007
16d247bb9c70
* src/ifaddrs.c (getifaddrs): Fill in flags, netmask and broadcast
asl
parents:
957
diff
changeset
|
438 |
