2 * GRUB -- GRand Unified Bootloader
3 * Copyright (C) 2010,2011,2012,2013 Free Software Foundation, Inc.
5 * GRUB is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * (at your option) any later version.
10 * GRUB is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with GRUB. If not, see <http://www.gnu.org/licenses/>.
20 #include <grub/net/netbuff.h>
21 #include <grub/time.h>
22 #include <grub/file.h>
23 #include <grub/i18n.h>
25 #include <grub/misc.h>
27 #include <grub/command.h>
29 #include <grub/net/ethernet.h>
30 #include <grub/net/arp.h>
31 #include <grub/net/ip.h>
32 #include <grub/loader.h>
33 #include <grub/bufio.h>
34 #include <grub/kernel.h>
36 GRUB_MOD_LICENSE ("GPLv3+");
38 char *grub_net_default_server
;
42 struct grub_net_route
*next
;
43 struct grub_net_route
**prev
;
44 grub_net_network_level_netaddress_t target
;
46 struct grub_net_network_level_protocol
*prot
;
50 struct grub_net_network_level_interface
*interface
;
51 grub_net_network_level_address_t gw
;
55 struct grub_net_route
*grub_net_routes
= NULL
;
56 struct grub_net_network_level_interface
*grub_net_network_level_interfaces
= NULL
;
57 struct grub_net_card
*grub_net_cards
= NULL
;
58 struct grub_net_network_level_protocol
*grub_net_network_level_protocols
= NULL
;
59 static struct grub_fs grub_net_fs
;
61 struct grub_net_link_layer_entry
{
63 grub_net_network_level_address_t nl_address
;
64 grub_net_link_level_address_t ll_address
;
67 #define LINK_LAYER_CACHE_SIZE 256
69 static struct grub_net_link_layer_entry
*
70 link_layer_find_entry (const grub_net_network_level_address_t
*proto
,
71 const struct grub_net_card
*card
)
74 if (!card
->link_layer_table
)
76 for (i
= 0; i
< LINK_LAYER_CACHE_SIZE
; i
++)
78 if (card
->link_layer_table
[i
].avail
== 1
79 && grub_net_addr_cmp (&card
->link_layer_table
[i
].nl_address
,
81 return &card
->link_layer_table
[i
];
87 grub_net_link_layer_add_address (struct grub_net_card
*card
,
88 const grub_net_network_level_address_t
*nl
,
89 const grub_net_link_level_address_t
*ll
,
92 struct grub_net_link_layer_entry
*entry
;
94 /* Check if the sender is in the cache table. */
95 entry
= link_layer_find_entry (nl
, card
);
96 /* Update sender hardware address. */
97 if (entry
&& override
)
98 grub_memcpy (&entry
->ll_address
, ll
, sizeof (entry
->ll_address
));
102 /* Add sender to cache table. */
103 if (card
->link_layer_table
== NULL
)
104 card
->link_layer_table
= grub_zalloc (LINK_LAYER_CACHE_SIZE
105 * sizeof (card
->link_layer_table
[0]));
106 entry
= &(card
->link_layer_table
[card
->new_ll_entry
]);
108 grub_memcpy (&entry
->ll_address
, ll
, sizeof (entry
->ll_address
));
109 grub_memcpy (&entry
->nl_address
, nl
, sizeof (entry
->nl_address
));
110 card
->new_ll_entry
++;
111 if (card
->new_ll_entry
== LINK_LAYER_CACHE_SIZE
)
112 card
->new_ll_entry
= 0;
116 grub_net_link_layer_resolve_check (struct grub_net_network_level_interface
*inf
,
117 const grub_net_network_level_address_t
*proto_addr
)
119 struct grub_net_link_layer_entry
*entry
;
121 if (proto_addr
->type
== GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
122 && proto_addr
->ipv4
== 0xffffffff)
124 entry
= link_layer_find_entry (proto_addr
, inf
->card
);
131 grub_net_link_layer_resolve (struct grub_net_network_level_interface
*inf
,
132 const grub_net_network_level_address_t
*proto_addr
,
133 grub_net_link_level_address_t
*hw_addr
)
135 struct grub_net_link_layer_entry
*entry
;
138 if ((proto_addr
->type
== GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
139 && proto_addr
->ipv4
== 0xffffffff)
140 || proto_addr
->type
== GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
141 || (proto_addr
->type
== GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
142 && proto_addr
->ipv6
[0] == grub_be_to_cpu64_compile_time (0xff02ULL
144 && proto_addr
->ipv6
[1] == (grub_be_to_cpu64_compile_time (1))))
146 hw_addr
->type
= GRUB_NET_LINK_LEVEL_PROTOCOL_ETHERNET
;
147 grub_memset (hw_addr
->mac
, -1, 6);
148 return GRUB_ERR_NONE
;
151 if (proto_addr
->type
== GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
152 && ((grub_be_to_cpu64 (proto_addr
->ipv6
[0]) >> 56) == 0xff))
154 hw_addr
->type
= GRUB_NET_LINK_LEVEL_PROTOCOL_ETHERNET
;
155 hw_addr
->mac
[0] = 0x33;
156 hw_addr
->mac
[1] = 0x33;
157 hw_addr
->mac
[2] = ((grub_be_to_cpu64 (proto_addr
->ipv6
[1]) >> 24) & 0xff);
158 hw_addr
->mac
[3] = ((grub_be_to_cpu64 (proto_addr
->ipv6
[1]) >> 16) & 0xff);
159 hw_addr
->mac
[4] = ((grub_be_to_cpu64 (proto_addr
->ipv6
[1]) >> 8) & 0xff);
160 hw_addr
->mac
[5] = ((grub_be_to_cpu64 (proto_addr
->ipv6
[1]) >> 0) & 0xff);
161 return GRUB_ERR_NONE
;
164 /* Check cache table. */
165 entry
= link_layer_find_entry (proto_addr
, inf
->card
);
168 *hw_addr
= entry
->ll_address
;
169 return GRUB_ERR_NONE
;
171 switch (proto_addr
->type
)
173 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
:
174 err
= grub_net_arp_send_request (inf
, proto_addr
);
176 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
:
177 err
= grub_net_icmp6_send_request (inf
, proto_addr
);
179 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
:
180 return grub_error (GRUB_ERR_BUG
, "shouldn't reach here");
182 return grub_error (GRUB_ERR_BUG
,
183 "unsupported address type %d", proto_addr
->type
);
187 entry
= link_layer_find_entry (proto_addr
, inf
->card
);
190 *hw_addr
= entry
->ll_address
;
191 return GRUB_ERR_NONE
;
193 return grub_error (GRUB_ERR_TIMEOUT
,
194 N_("timeout: could not resolve hardware address"));
198 grub_net_card_unregister (struct grub_net_card
*card
)
200 struct grub_net_network_level_interface
*inf
, *next
;
201 FOR_NET_NETWORK_LEVEL_INTERFACES_SAFE(inf
, next
)
202 if (inf
->card
== card
)
203 grub_net_network_level_interface_unregister (inf
);
206 if (card
->driver
->close
)
207 card
->driver
->close (card
);
210 grub_list_remove (GRUB_AS_LIST (card
));
213 static struct grub_net_slaac_mac_list
*
214 grub_net_ipv6_get_slaac (struct grub_net_card
*card
,
215 const grub_net_link_level_address_t
*hwaddr
)
217 struct grub_net_slaac_mac_list
*slaac
;
220 for (slaac
= card
->slaac_list
; slaac
; slaac
= slaac
->next
)
221 if (grub_net_hwaddr_cmp (&slaac
->address
, hwaddr
) == 0)
224 slaac
= grub_zalloc (sizeof (*slaac
));
228 slaac
->name
= grub_malloc (grub_strlen (card
->name
)
229 + GRUB_NET_MAX_STR_HWADDR_LEN
230 + sizeof (":slaac"));
231 ptr
= grub_stpcpy (slaac
->name
, card
->name
);
232 if (grub_net_hwaddr_cmp (&card
->default_address
, hwaddr
) != 0)
234 ptr
= grub_stpcpy (ptr
, ":");
235 grub_net_hwaddr_to_str (hwaddr
, ptr
);
236 ptr
+= grub_strlen (ptr
);
238 ptr
= grub_stpcpy (ptr
, ":slaac");
240 grub_memcpy (&slaac
->address
, hwaddr
, sizeof (slaac
->address
));
241 slaac
->next
= card
->slaac_list
;
242 card
->slaac_list
= slaac
;
247 grub_net_network_level_interface_register (struct grub_net_network_level_interface
*inter
);
249 static struct grub_net_network_level_interface
*
250 grub_net_add_addr_real (char *name
,
251 struct grub_net_card
*card
,
252 const grub_net_network_level_address_t
*addr
,
253 const grub_net_link_level_address_t
*hwaddress
,
254 grub_net_interface_flags_t flags
)
256 struct grub_net_network_level_interface
*inter
;
258 inter
= grub_zalloc (sizeof (*inter
));
263 grub_memcpy (&(inter
->address
), addr
, sizeof (inter
->address
));
264 grub_memcpy (&(inter
->hwaddress
), hwaddress
, sizeof (inter
->hwaddress
));
265 inter
->flags
= flags
;
267 inter
->dhcp_ack
= NULL
;
268 inter
->dhcp_acklen
= 0;
270 grub_net_network_level_interface_register (inter
);
275 struct grub_net_network_level_interface
*
276 grub_net_add_addr (const char *name
,
277 struct grub_net_card
*card
,
278 const grub_net_network_level_address_t
*addr
,
279 const grub_net_link_level_address_t
*hwaddress
,
280 grub_net_interface_flags_t flags
)
282 char *name_dup
= grub_strdup (name
);
283 struct grub_net_network_level_interface
*ret
;
287 ret
= grub_net_add_addr_real (name_dup
, card
, addr
, hwaddress
, flags
);
289 grub_free (name_dup
);
293 struct grub_net_network_level_interface
*
294 grub_net_ipv6_get_link_local (struct grub_net_card
*card
,
295 const grub_net_link_level_address_t
*hwaddr
)
297 struct grub_net_network_level_interface
*inf
;
300 grub_net_network_level_address_t addr
;
302 name
= grub_malloc (grub_strlen (card
->name
)
303 + GRUB_NET_MAX_STR_HWADDR_LEN
308 addr
.type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
;
309 addr
.ipv6
[0] = grub_cpu_to_be64_compile_time (0xfe80ULL
<< 48);
310 addr
.ipv6
[1] = grub_net_ipv6_get_id (hwaddr
);
312 FOR_NET_NETWORK_LEVEL_INTERFACES (inf
)
314 if (inf
->card
== card
315 && grub_net_hwaddr_cmp (&inf
->hwaddress
, hwaddr
) == 0
316 && grub_net_addr_cmp (&inf
->address
, &addr
) == 0)
320 ptr
= grub_stpcpy (name
, card
->name
);
321 if (grub_net_hwaddr_cmp (&card
->default_address
, hwaddr
) != 0)
323 ptr
= grub_stpcpy (ptr
, ":");
324 grub_net_hwaddr_to_str (hwaddr
, ptr
);
325 ptr
+= grub_strlen (ptr
);
327 ptr
= grub_stpcpy (ptr
, ":link");
328 return grub_net_add_addr_real (name
, card
, &addr
, hwaddr
, 0);
331 /* FIXME: allow to specify mac address. */
333 grub_cmd_ipv6_autoconf (struct grub_command
*cmd
__attribute__ ((unused
)),
334 int argc
, char **args
)
336 struct grub_net_card
*card
;
337 struct grub_net_network_level_interface
**ifaces
;
338 grub_size_t ncards
= 0;
342 struct grub_net_slaac_mac_list
**slaacs
;
346 if (argc
> 0 && grub_strcmp (card
->name
, args
[0]) != 0)
351 ifaces
= grub_zalloc (ncards
* sizeof (ifaces
[0]));
352 slaacs
= grub_zalloc (ncards
* sizeof (slaacs
[0]));
353 if (!ifaces
|| !slaacs
)
362 if (argc
> 0 && grub_strcmp (card
->name
, args
[0]) != 0)
364 ifaces
[j
] = grub_net_ipv6_get_link_local (card
, &card
->default_address
);
371 slaacs
[j
] = grub_net_ipv6_get_slaac (card
, &card
->default_address
);
381 for (interval
= 200; interval
< 10000; interval
*= 2)
384 for (j
= 0; j
< ncards
; j
++)
386 if (slaacs
[j
]->slaac_counter
)
388 err
= grub_net_icmp6_send_router_solicit (ifaces
[j
]);
395 grub_net_poll_cards (interval
, 0);
399 for (j
= 0; j
< ncards
; j
++)
401 if (slaacs
[j
]->slaac_counter
)
403 err
= grub_error (GRUB_ERR_FILE_NOT_FOUND
,
404 N_("couldn't autoconfigure %s"),
405 ifaces
[j
]->card
->name
);
414 grub_net_route_register (struct grub_net_route
*route
)
416 grub_list_push (GRUB_AS_LIST_P (&grub_net_routes
),
417 GRUB_AS_LIST (route
));
420 #define FOR_NET_ROUTES(var) for (var = grub_net_routes; var; var = var->next)
423 parse_ip (const char *val
, grub_uint32_t
*ip
, const char **rest
)
425 grub_uint32_t newip
= 0;
427 const char *ptr
= val
;
429 for (i
= 0; i
< 4; i
++)
432 t
= grub_strtoul (ptr
, (char **) &ptr
, 0);
435 grub_errno
= GRUB_ERR_NONE
;
438 if (*ptr
!= '.' && i
== 0)
447 if (i
!= 3 && *ptr
!= '.')
451 *ip
= grub_cpu_to_le32 (newip
);
458 parse_ip6 (const char *val
, grub_uint64_t
*ip
, const char **rest
)
460 grub_uint16_t newip
[8];
461 const char *ptr
= val
;
462 int word
, quaddot
= -1;
464 if (ptr
[0] == ':' && ptr
[1] != ':')
469 for (word
= 0; word
< 8; word
++)
479 t
= grub_strtoul (ptr
, (char **) &ptr
, 16);
482 grub_errno
= GRUB_ERR_NONE
;
487 newip
[word
] = grub_cpu_to_be16 (t
);
492 if (quaddot
== -1 && word
< 7)
496 grub_memmove (&newip
[quaddot
+ 7 - word
], &newip
[quaddot
],
497 (word
- quaddot
+ 1) * sizeof (newip
[0]));
498 grub_memset (&newip
[quaddot
], 0, (7 - word
) * sizeof (newip
[0]));
500 grub_memcpy (ip
, newip
, 16);
507 match_net (const grub_net_network_level_netaddress_t
*net
,
508 const grub_net_network_level_address_t
*addr
)
510 if (net
->type
!= addr
->type
)
514 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
:
516 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
:
518 grub_uint32_t mask
= (0xffffffffU
<< (32 - net
->ipv4
.masksize
));
519 if (net
->ipv4
.masksize
== 0)
521 return ((grub_be_to_cpu32 (net
->ipv4
.base
) & mask
)
522 == (grub_be_to_cpu32 (addr
->ipv4
) & mask
));
524 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
:
526 grub_uint64_t mask
[2];
527 if (net
->ipv6
.masksize
<= 64)
529 mask
[0] = 0xffffffffffffffffULL
<< (64 - net
->ipv6
.masksize
);
534 mask
[0] = 0xffffffffffffffffULL
;
535 mask
[1] = 0xffffffffffffffffULL
<< (128 - net
->ipv6
.masksize
);
537 return (((grub_be_to_cpu64 (net
->ipv6
.base
[0]) & mask
[0])
538 == (grub_be_to_cpu64 (addr
->ipv6
[0]) & mask
[0]))
539 && ((grub_be_to_cpu64 (net
->ipv6
.base
[1]) & mask
[1])
540 == (grub_be_to_cpu64 (addr
->ipv6
[1]) & mask
[1])));
547 grub_net_resolve_address (const char *name
,
548 grub_net_network_level_address_t
*addr
)
552 grub_size_t naddresses
;
553 struct grub_net_network_level_address
*addresses
= 0;
555 if (parse_ip (name
, &addr
->ipv4
, &rest
) && *rest
== 0)
557 addr
->type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
;
558 return GRUB_ERR_NONE
;
560 if (parse_ip6 (name
, addr
->ipv6
, &rest
) && *rest
== 0)
562 addr
->type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
;
563 return GRUB_ERR_NONE
;
565 err
= grub_net_dns_lookup (name
, 0, 0, &naddresses
, &addresses
, 1);
569 grub_error (GRUB_ERR_NET_BAD_ADDRESS
, N_("unresolvable address %s"),
571 /* FIXME: use other results as well. */
572 *addr
= addresses
[0];
573 grub_free (addresses
);
574 return GRUB_ERR_NONE
;
578 grub_net_resolve_net_address (const char *name
,
579 grub_net_network_level_netaddress_t
*addr
)
582 if (parse_ip (name
, &addr
->ipv4
.base
, &rest
))
584 addr
->type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
;
587 addr
->ipv4
.masksize
= grub_strtoul (rest
+ 1, (char **) &rest
, 0);
588 if (!grub_errno
&& *rest
== 0)
589 return GRUB_ERR_NONE
;
590 grub_errno
= GRUB_ERR_NONE
;
594 addr
->ipv4
.masksize
= 32;
595 return GRUB_ERR_NONE
;
598 if (parse_ip6 (name
, addr
->ipv6
.base
, &rest
))
600 addr
->type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
;
603 addr
->ipv6
.masksize
= grub_strtoul (rest
+ 1, (char **) &rest
, 0);
604 if (!grub_errno
&& *rest
== 0)
605 return GRUB_ERR_NONE
;
606 grub_errno
= GRUB_ERR_NONE
;
610 addr
->ipv6
.masksize
= 128;
611 return GRUB_ERR_NONE
;
614 return grub_error (GRUB_ERR_NET_BAD_ADDRESS
,
615 N_("unrecognised network address `%s'"),
620 route_cmp (const struct grub_net_route
*a
, const struct grub_net_route
*b
)
622 if (a
== NULL
&& b
== NULL
)
628 if (a
->target
.type
< b
->target
.type
)
630 if (a
->target
.type
> b
->target
.type
)
632 switch (a
->target
.type
)
634 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
:
636 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
:
637 if (a
->target
.ipv6
.masksize
> b
->target
.ipv6
.masksize
)
639 if (a
->target
.ipv6
.masksize
< b
->target
.ipv6
.masksize
)
642 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
:
643 if (a
->target
.ipv4
.masksize
> b
->target
.ipv4
.masksize
)
645 if (a
->target
.ipv4
.masksize
< b
->target
.ipv4
.masksize
)
653 grub_net_route_address (grub_net_network_level_address_t addr
,
654 grub_net_network_level_address_t
*gateway
,
655 struct grub_net_network_level_interface
**interf
)
657 struct grub_net_route
*route
;
658 unsigned int depth
= 0;
659 unsigned int routecnt
= 0;
660 struct grub_net_network_level_protocol
*prot
= NULL
;
661 grub_net_network_level_address_t curtarget
= addr
;
665 FOR_NET_ROUTES(route
)
668 for (depth
= 0; depth
< routecnt
+ 2 && depth
< GRUB_UINT_MAX
; depth
++)
670 struct grub_net_route
*bestroute
= NULL
;
671 FOR_NET_ROUTES(route
)
673 if (depth
&& prot
!= route
->prot
)
675 if (!match_net (&route
->target
, &curtarget
))
677 if (route_cmp (route
, bestroute
) > 0)
680 if (bestroute
== NULL
)
681 return grub_error (GRUB_ERR_NET_NO_ROUTE
,
682 N_("destination unreachable"));
684 if (!bestroute
->is_gateway
)
686 *interf
= bestroute
->interface
;
687 return GRUB_ERR_NONE
;
690 *gateway
= bestroute
->gw
;
691 curtarget
= bestroute
->gw
;
694 return grub_error (GRUB_ERR_NET_ROUTE_LOOP
,
695 /* TRANSLATORS: route loop is a condition when e.g.
696 to contact server A you need to go through B
697 and to contact B you need to go through A. */
698 N_("route loop detected"));
702 grub_cmd_deladdr (struct grub_command
*cmd
__attribute__ ((unused
)),
703 int argc
, char **args
)
705 struct grub_net_network_level_interface
*inter
;
708 return grub_error (GRUB_ERR_BAD_ARGUMENT
, N_("one argument expected"));
710 FOR_NET_NETWORK_LEVEL_INTERFACES (inter
)
711 if (grub_strcmp (inter
->name
, args
[0]) == 0)
714 return grub_error (GRUB_ERR_BAD_ARGUMENT
, N_("address not found"));
716 if (inter
->flags
& GRUB_NET_INTERFACE_PERMANENT
)
717 return grub_error (GRUB_ERR_IO
,
718 N_("you can't delete this address"));
720 grub_net_network_level_interface_unregister (inter
);
721 grub_free (inter
->name
);
724 return GRUB_ERR_NONE
;
728 grub_net_addr_to_str (const grub_net_network_level_address_t
*target
, char *buf
)
730 switch (target
->type
)
732 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
:
733 COMPILE_TIME_ASSERT (sizeof ("temporary") < GRUB_NET_MAX_STR_ADDR_LEN
);
734 grub_strcpy (buf
, "temporary");
736 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
:
739 grub_uint64_t n
= grub_be_to_cpu64 (target
->ipv6
[0]);
741 for (i
= 0; i
< 4; i
++)
743 grub_snprintf (ptr
, 6, "%" PRIxGRUB_UINT64_T
":",
744 (n
>> (48 - 16 * i
)) & 0xffff);
745 ptr
+= grub_strlen (ptr
);
747 n
= grub_be_to_cpu64 (target
->ipv6
[1]);
748 for (i
= 0; i
< 3; i
++)
750 grub_snprintf (ptr
, 6, "%" PRIxGRUB_UINT64_T
":",
751 (n
>> (48 - 16 * i
)) & 0xffff);
752 ptr
+= grub_strlen (ptr
);
754 grub_snprintf (ptr
, 5, "%" PRIxGRUB_UINT64_T
, n
& 0xffff);
757 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
:
759 grub_uint32_t n
= grub_be_to_cpu32 (target
->ipv4
);
760 grub_snprintf (buf
, GRUB_NET_MAX_STR_ADDR_LEN
, "%d.%d.%d.%d",
761 ((n
>> 24) & 0xff), ((n
>> 16) & 0xff),
762 ((n
>> 8) & 0xff), ((n
>> 0) & 0xff));
766 grub_snprintf (buf
, GRUB_NET_MAX_STR_ADDR_LEN
,
767 "Unknown address type %d", target
->type
);
772 grub_net_hwaddr_to_str (const grub_net_link_level_address_t
*addr
, char *str
)
777 case GRUB_NET_LINK_LEVEL_PROTOCOL_ETHERNET
:
781 for (ptr
= str
, i
= 0; i
< ARRAY_SIZE (addr
->mac
); i
++)
783 grub_snprintf (ptr
, GRUB_NET_MAX_STR_HWADDR_LEN
- (ptr
- str
),
784 "%02x:", addr
->mac
[i
] & 0xff);
785 ptr
+= (sizeof ("XX:") - 1);
790 grub_printf (_("Unsupported hw address type %d\n"), addr
->type
);
794 grub_net_hwaddr_cmp (const grub_net_link_level_address_t
*a
,
795 const grub_net_link_level_address_t
*b
)
797 if (a
->type
< b
->type
)
799 if (a
->type
> b
->type
)
803 case GRUB_NET_LINK_LEVEL_PROTOCOL_ETHERNET
:
804 return grub_memcmp (a
->mac
, b
->mac
, sizeof (a
->mac
));
806 grub_printf (_("Unsupported hw address type %d\n"), a
->type
);
811 grub_net_addr_cmp (const grub_net_network_level_address_t
*a
,
812 const grub_net_network_level_address_t
*b
)
814 if (a
->type
< b
->type
)
816 if (a
->type
> b
->type
)
820 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
:
821 return grub_memcmp (&a
->ipv4
, &b
->ipv4
, sizeof (a
->ipv4
));
822 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
:
823 return grub_memcmp (&a
->ipv6
, &b
->ipv6
, sizeof (a
->ipv6
));
824 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
:
827 grub_printf (_("Unsupported address type %d\n"), a
->type
);
831 /* FIXME: implement this. */
833 hwaddr_set_env (struct grub_env_var
*var
__attribute__ ((unused
)),
834 const char *val
__attribute__ ((unused
)))
839 /* FIXME: implement this. */
841 addr_set_env (struct grub_env_var
*var
__attribute__ ((unused
)),
842 const char *val
__attribute__ ((unused
)))
848 defserver_set_env (struct grub_env_var
*var
__attribute__ ((unused
)),
851 grub_free (grub_net_default_server
);
852 grub_net_default_server
= grub_strdup (val
);
853 return grub_strdup (val
);
857 defserver_get_env (struct grub_env_var
*var
__attribute__ ((unused
)),
858 const char *val
__attribute__ ((unused
)))
860 return grub_net_default_server
? : "";
864 defip_get_env (struct grub_env_var
*var
__attribute__ ((unused
)),
865 const char *val
__attribute__ ((unused
)))
867 const char *intf
= grub_env_get ("net_default_interface");
868 const char *ret
= NULL
;
871 char *buf
= grub_xasprintf ("net_%s_ip", intf
);
873 ret
= grub_env_get (buf
);
880 defip_set_env (struct grub_env_var
*var
__attribute__ ((unused
)),
883 const char *intf
= grub_env_get ("net_default_interface");
886 char *buf
= grub_xasprintf ("net_%s_ip", intf
);
888 grub_env_set (buf
, val
);
896 defmac_get_env (struct grub_env_var
*var
__attribute__ ((unused
)),
897 const char *val
__attribute__ ((unused
)))
899 const char *intf
= grub_env_get ("net_default_interface");
900 const char *ret
= NULL
;
903 char *buf
= grub_xasprintf ("net_%s_mac", intf
);
905 ret
= grub_env_get (buf
);
912 defmac_set_env (struct grub_env_var
*var
__attribute__ ((unused
)),
915 const char *intf
= grub_env_get ("net_default_interface");
918 char *buf
= grub_xasprintf ("net_%s_mac", intf
);
920 grub_env_set (buf
, val
);
928 grub_net_network_level_interface_register (struct grub_net_network_level_interface
*inter
)
931 char buf
[GRUB_NET_MAX_STR_HWADDR_LEN
];
934 grub_net_hwaddr_to_str (&inter
->hwaddress
, buf
);
935 name
= grub_xasprintf ("net_%s_mac", inter
->name
);
938 for (ptr
= name
; *ptr
; ptr
++)
941 grub_env_set (name
, buf
);
942 grub_register_variable_hook (name
, 0, hwaddr_set_env
);
943 grub_env_export (name
);
948 char buf
[GRUB_NET_MAX_STR_ADDR_LEN
];
951 grub_net_addr_to_str (&inter
->address
, buf
);
952 name
= grub_xasprintf ("net_%s_ip", inter
->name
);
955 for (ptr
= name
; *ptr
; ptr
++)
958 grub_env_set (name
, buf
);
959 grub_register_variable_hook (name
, 0, addr_set_env
);
960 grub_env_export (name
);
964 inter
->card
->num_ifaces
++;
965 inter
->prev
= &grub_net_network_level_interfaces
;
966 inter
->next
= grub_net_network_level_interfaces
;
968 inter
->next
->prev
= &inter
->next
;
969 grub_net_network_level_interfaces
= inter
;
974 grub_net_add_ipv4_local (struct grub_net_network_level_interface
*inter
,
977 grub_uint32_t ip_cpu
;
978 struct grub_net_route
*route
;
980 if (inter
->address
.type
!= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
)
983 ip_cpu
= grub_be_to_cpu32 (inter
->address
.ipv4
);
987 if (!(ip_cpu
& 0x80000000))
989 else if (!(ip_cpu
& 0x40000000))
991 else if (!(ip_cpu
& 0x20000000))
997 route
= grub_zalloc (sizeof (*route
));
1001 route
->name
= grub_xasprintf ("%s:local", inter
->name
);
1008 route
->target
.type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
;
1009 route
->target
.ipv4
.base
= grub_cpu_to_be32 (ip_cpu
& (0xffffffff << (32 - mask
)));
1010 route
->target
.ipv4
.masksize
= mask
;
1011 route
->is_gateway
= 0;
1012 route
->interface
= inter
;
1014 grub_net_route_register (route
);
1019 /* FIXME: support MAC specifying. */
1021 grub_cmd_addaddr (struct grub_command
*cmd
__attribute__ ((unused
)),
1022 int argc
, char **args
)
1024 struct grub_net_card
*card
;
1025 grub_net_network_level_address_t addr
;
1027 grub_net_interface_flags_t flags
= 0;
1028 struct grub_net_network_level_interface
*inf
;
1031 return grub_error (GRUB_ERR_BAD_ARGUMENT
, N_("three arguments expected"));
1033 FOR_NET_CARDS (card
)
1034 if (grub_strcmp (card
->name
, args
[1]) == 0)
1037 return grub_error (GRUB_ERR_BAD_ARGUMENT
, N_("card not found"));
1039 err
= grub_net_resolve_address (args
[2], &addr
);
1043 if (card
->flags
& GRUB_NET_CARD_NO_MANUAL_INTERFACES
)
1044 return grub_error (GRUB_ERR_IO
,
1045 "this card doesn't support address addition");
1047 if (card
->flags
& GRUB_NET_CARD_HWADDRESS_IMMUTABLE
)
1048 flags
|= GRUB_NET_INTERFACE_HWADDRESS_IMMUTABLE
;
1050 inf
= grub_net_add_addr (args
[0], card
, &addr
, &card
->default_address
,
1053 grub_net_add_ipv4_local (inf
, -1);
1059 grub_cmd_delroute (struct grub_command
*cmd
__attribute__ ((unused
)),
1060 int argc
, char **args
)
1062 struct grub_net_route
*route
;
1063 struct grub_net_route
**prev
;
1066 return grub_error (GRUB_ERR_BAD_ARGUMENT
, N_("one argument expected"));
1068 for (prev
= &grub_net_routes
, route
= *prev
; route
; prev
= &((*prev
)->next
),
1070 if (grub_strcmp (route
->name
, args
[0]) == 0)
1072 *prev
= route
->next
;
1073 grub_free (route
->name
);
1079 return GRUB_ERR_NONE
;
1083 grub_net_add_route (const char *name
,
1084 grub_net_network_level_netaddress_t target
,
1085 struct grub_net_network_level_interface
*inter
)
1087 struct grub_net_route
*route
;
1089 route
= grub_zalloc (sizeof (*route
));
1093 route
->name
= grub_strdup (name
);
1100 route
->target
= target
;
1101 route
->is_gateway
= 0;
1102 route
->interface
= inter
;
1104 grub_net_route_register (route
);
1106 return GRUB_ERR_NONE
;
1110 grub_net_add_route_gw (const char *name
,
1111 grub_net_network_level_netaddress_t target
,
1112 grub_net_network_level_address_t gw
)
1114 struct grub_net_route
*route
;
1116 route
= grub_zalloc (sizeof (*route
));
1120 route
->name
= grub_strdup (name
);
1127 route
->target
= target
;
1128 route
->is_gateway
= 1;
1131 grub_net_route_register (route
);
1133 return GRUB_ERR_NONE
;
1137 grub_cmd_addroute (struct grub_command
*cmd
__attribute__ ((unused
)),
1138 int argc
, char **args
)
1140 grub_net_network_level_netaddress_t target
;
1142 return grub_error (GRUB_ERR_BAD_ARGUMENT
,
1143 N_("three arguments expected"));
1145 grub_net_resolve_net_address (args
[1], &target
);
1147 if (grub_strcmp (args
[2], "gw") == 0 && argc
>= 4)
1150 grub_net_network_level_address_t gw
;
1152 err
= grub_net_resolve_address (args
[3], &gw
);
1155 return grub_net_add_route_gw (args
[0], target
, gw
);
1159 struct grub_net_network_level_interface
*inter
;
1161 FOR_NET_NETWORK_LEVEL_INTERFACES (inter
)
1162 if (grub_strcmp (inter
->name
, args
[2]) == 0)
1166 return grub_error (GRUB_ERR_BAD_ARGUMENT
,
1167 N_("unrecognised network interface `%s'"), args
[2]);
1168 return grub_net_add_route (args
[0], target
, inter
);
1173 print_net_address (const grub_net_network_level_netaddress_t
*target
)
1175 switch (target
->type
)
1177 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_DHCP_RECV
:
1178 /* TRANSLATORS: it refers to the network address. */
1179 grub_printf ("%s\n", _("temporary"));
1181 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV4
:
1183 grub_uint32_t n
= grub_be_to_cpu32 (target
->ipv4
.base
);
1184 grub_printf ("%d.%d.%d.%d/%d ", ((n
>> 24) & 0xff),
1188 target
->ipv4
.masksize
);
1191 case GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
:
1193 char buf
[GRUB_NET_MAX_STR_ADDR_LEN
];
1194 struct grub_net_network_level_address base
;
1195 base
.type
= GRUB_NET_NETWORK_LEVEL_PROTOCOL_IPV6
;
1196 grub_memcpy (&base
.ipv6
, &target
->ipv6
, 16);
1197 grub_net_addr_to_str (&base
, buf
);
1198 grub_printf ("%s/%d ", buf
, target
->ipv6
.masksize
);
1202 grub_printf (_("Unknown address type %d\n"), target
->type
);
1206 print_address (const grub_net_network_level_address_t
*target
)
1208 char buf
[GRUB_NET_MAX_STR_ADDR_LEN
];
1209 grub_net_addr_to_str (target
, buf
);
1214 grub_cmd_listroutes (struct grub_command
*cmd
__attribute__ ((unused
)),
1215 int argc
__attribute__ ((unused
)),
1216 char **args
__attribute__ ((unused
)))
1218 struct grub_net_route
*route
;
1219 FOR_NET_ROUTES(route
)
1221 grub_printf ("%s ", route
->name
);
1222 print_net_address (&route
->target
);
1223 if (route
->is_gateway
)
1225 grub_printf ("gw ");
1226 print_address (&route
->gw
);
1229 grub_printf ("%s", route
->interface
->name
);
1232 return GRUB_ERR_NONE
;
1236 grub_cmd_listcards (struct grub_command
*cmd
__attribute__ ((unused
)),
1237 int argc
__attribute__ ((unused
)),
1238 char **args
__attribute__ ((unused
)))
1240 struct grub_net_card
*card
;
1243 char buf
[GRUB_NET_MAX_STR_HWADDR_LEN
];
1244 grub_net_hwaddr_to_str (&card
->default_address
, buf
);
1245 grub_printf ("%s %s\n", card
->name
, buf
);
1247 return GRUB_ERR_NONE
;
1251 grub_cmd_listaddrs (struct grub_command
*cmd
__attribute__ ((unused
)),
1252 int argc
__attribute__ ((unused
)),
1253 char **args
__attribute__ ((unused
)))
1255 struct grub_net_network_level_interface
*inf
;
1256 FOR_NET_NETWORK_LEVEL_INTERFACES (inf
)
1258 char bufh
[GRUB_NET_MAX_STR_HWADDR_LEN
];
1259 char bufn
[GRUB_NET_MAX_STR_ADDR_LEN
];
1260 grub_net_hwaddr_to_str (&inf
->hwaddress
, bufh
);
1261 grub_net_addr_to_str (&inf
->address
, bufn
);
1262 grub_printf ("%s %s %s\n", inf
->name
, bufh
, bufn
);
1264 return GRUB_ERR_NONE
;
1267 grub_net_app_level_t grub_net_app_level_list
;
1268 struct grub_net_socket
*grub_net_sockets
;
1271 grub_net_open_real (const char *name
)
1273 grub_net_app_level_t proto
;
1274 const char *protname
, *server
;
1275 grub_size_t protnamelen
;
1278 if (grub_strncmp (name
, "pxe:", sizeof ("pxe:") - 1) == 0)
1281 protnamelen
= sizeof ("tftp") - 1;
1282 server
= name
+ sizeof ("pxe:") - 1;
1284 else if (grub_strcmp (name
, "pxe") == 0)
1287 protnamelen
= sizeof ("tftp") - 1;
1288 server
= grub_net_default_server
;
1293 comma
= grub_strchr (name
, ',');
1296 protnamelen
= comma
- name
;
1302 protnamelen
= grub_strlen (name
);
1303 server
= grub_net_default_server
;
1309 grub_error (GRUB_ERR_NET_BAD_ADDRESS
,
1310 N_("no server is specified"));
1314 for (try = 0; try < 2; try++)
1316 FOR_NET_APP_LEVEL (proto
)
1318 if (grub_memcmp (proto
->name
, protname
, protnamelen
) == 0
1319 && proto
->name
[protnamelen
] == 0)
1321 grub_net_t ret
= grub_zalloc (sizeof (*ret
));
1324 ret
->protocol
= proto
;
1327 ret
->server
= grub_strdup (server
);
1336 ret
->fs
= &grub_net_fs
;
1344 if (sizeof ("http") - 1 == protnamelen
1345 && grub_memcmp ("http", protname
, protnamelen
) == 0)
1347 grub_dl_load ("http");
1348 grub_errno
= GRUB_ERR_NONE
;
1351 if (sizeof ("tftp") - 1 == protnamelen
1352 && grub_memcmp ("tftp", protname
, protnamelen
) == 0)
1354 grub_dl_load ("tftp");
1355 grub_errno
= GRUB_ERR_NONE
;
1362 /* Restore original error. */
1363 grub_error (GRUB_ERR_UNKNOWN_DEVICE
, N_("disk `%s' not found"),
1370 grub_net_fs_dir (grub_device_t device
, const char *path
__attribute__ ((unused
)),
1371 grub_fs_dir_hook_t hook
__attribute__ ((unused
)),
1372 void *hook_data
__attribute__ ((unused
)))
1375 return grub_error (GRUB_ERR_BUG
, "invalid net device");
1376 return GRUB_ERR_NONE
;
1380 grub_net_fs_open (struct grub_file
*file_out
, const char *name
)
1383 struct grub_file
*file
, *bufio
;
1385 file
= grub_malloc (sizeof (*file
));
1389 grub_memcpy (file
, file_out
, sizeof (struct grub_file
));
1390 file
->device
->net
->packs
.first
= NULL
;
1391 file
->device
->net
->packs
.last
= NULL
;
1392 file
->device
->net
->name
= grub_strdup (name
);
1393 if (!file
->device
->net
->name
)
1396 err
= file
->device
->net
->protocol
->open (file
, name
);
1399 while (file
->device
->net
->packs
.first
)
1401 grub_netbuff_free (file
->device
->net
->packs
.first
->nb
);
1402 grub_net_remove_packet (file
->device
->net
->packs
.first
);
1404 grub_free (file
->device
->net
->name
);
1408 bufio
= grub_bufio_open (file
, 32768);
1411 while (file
->device
->net
->packs
.first
)
1413 grub_netbuff_free (file
->device
->net
->packs
.first
->nb
);
1414 grub_net_remove_packet (file
->device
->net
->packs
.first
);
1416 file
->device
->net
->protocol
->close (file
);
1417 grub_free (file
->device
->net
->name
);
1422 grub_memcpy (file_out
, bufio
, sizeof (struct grub_file
));
1424 return GRUB_ERR_NONE
;
1428 grub_net_fs_close (grub_file_t file
)
1430 while (file
->device
->net
->packs
.first
)
1432 grub_netbuff_free (file
->device
->net
->packs
.first
->nb
);
1433 grub_net_remove_packet (file
->device
->net
->packs
.first
);
1435 file
->device
->net
->protocol
->close (file
);
1436 grub_free (file
->device
->net
->name
);
1437 return GRUB_ERR_NONE
;
1441 receive_packets (struct grub_net_card
*card
, int *stop_condition
)
1444 if (card
->num_ifaces
== 0)
1448 grub_err_t err
= GRUB_ERR_NONE
;
1449 if (card
->driver
->open
)
1450 err
= card
->driver
->open (card
);
1453 grub_errno
= GRUB_ERR_NONE
;
1458 while (received
< 100)
1460 /* Maybe should be better have a fixed number of packets for each card
1461 and just mark them as used and not used. */
1462 struct grub_net_buff
*nb
;
1464 if (received
> 10 && stop_condition
&& *stop_condition
)
1467 nb
= card
->driver
->recv (card
);
1470 card
->last_poll
= grub_get_time_ms ();
1474 grub_net_recv_ethernet_packet (nb
, card
);
1477 grub_dprintf ("net", "error receiving: %d: %s\n", grub_errno
,
1479 grub_errno
= GRUB_ERR_NONE
;
1482 grub_print_error ();
1486 grub_env_write_readonly (struct grub_env_var
*var
__attribute__ ((unused
)),
1487 const char *val
__attribute__ ((unused
)))
1493 grub_env_set_net_property (const char *intername
, const char *suffix
,
1494 const char *value
, grub_size_t len
)
1496 char *varname
, *varvalue
;
1499 varname
= grub_xasprintf ("net_%s_%s", intername
, suffix
);
1502 for (ptr
= varname
; *ptr
; ptr
++)
1505 varvalue
= grub_malloc (len
+ 1);
1508 grub_free (varname
);
1512 grub_memcpy (varvalue
, value
, len
);
1514 grub_err_t ret
= grub_env_set (varname
, varvalue
);
1515 grub_register_variable_hook (varname
, 0, grub_env_write_readonly
);
1516 grub_env_export (varname
);
1517 grub_free (varname
);
1518 grub_free (varvalue
);
1524 grub_net_poll_cards (unsigned time
, int *stop_condition
)
1526 struct grub_net_card
*card
;
1527 grub_uint64_t start_time
;
1528 start_time
= grub_get_time_ms ();
1529 while ((grub_get_time_ms () - start_time
) < time
1530 && (!stop_condition
|| !*stop_condition
))
1531 FOR_NET_CARDS (card
)
1532 receive_packets (card
, stop_condition
);
1533 grub_net_tcp_retransmit ();
1537 grub_net_poll_cards_idle_real (void)
1539 struct grub_net_card
*card
;
1540 FOR_NET_CARDS (card
)
1542 grub_uint64_t ctime
= grub_get_time_ms ();
1544 if (ctime
< card
->last_poll
1545 || ctime
>= card
->last_poll
+ card
->idle_poll_delay_ms
)
1546 receive_packets (card
, 0);
1548 grub_net_tcp_retransmit ();
1551 /* Read from the packets list*/
1553 grub_net_fs_read_real (grub_file_t file
, char *buf
, grub_size_t len
)
1555 grub_net_t net
= file
->device
->net
;
1556 struct grub_net_buff
*nb
;
1558 grub_size_t amount
, total
= 0;
1561 while (try <= GRUB_NET_TRIES
)
1563 while (net
->packs
.first
)
1566 nb
= net
->packs
.first
->nb
;
1567 amount
= nb
->tail
- nb
->data
;
1572 file
->device
->net
->offset
+= amount
;
1573 if (grub_file_progress_hook
)
1574 grub_file_progress_hook (0, 0, amount
, file
);
1577 grub_memcpy (ptr
, nb
->data
, amount
);
1580 if (amount
== (grub_size_t
) (nb
->tail
- nb
->data
))
1582 grub_netbuff_free (nb
);
1583 grub_net_remove_packet (net
->packs
.first
);
1590 if (net
->protocol
->packets_pulled
)
1591 net
->protocol
->packets_pulled (file
);
1595 if (net
->protocol
->packets_pulled
)
1596 net
->protocol
->packets_pulled (file
);
1601 grub_net_poll_cards (GRUB_NET_INTERVAL
+
1602 (try * GRUB_NET_INTERVAL_ADDITION
), &net
->stall
);
1607 grub_error (GRUB_ERR_TIMEOUT
, N_("timeout reading `%s'"), net
->name
);
1612 have_ahead (struct grub_file
*file
)
1614 grub_net_t net
= file
->device
->net
;
1615 grub_off_t ret
= net
->offset
;
1616 struct grub_net_packet
*pack
;
1617 for (pack
= net
->packs
.first
; pack
; pack
= pack
->next
)
1618 ret
+= pack
->nb
->tail
- pack
->nb
->data
;
1623 grub_net_seek_real (struct grub_file
*file
, grub_off_t offset
)
1625 if (offset
== file
->device
->net
->offset
)
1626 return GRUB_ERR_NONE
;
1628 if (offset
> file
->device
->net
->offset
)
1630 if (!file
->device
->net
->protocol
->seek
|| have_ahead (file
) >= offset
)
1632 grub_net_fs_read_real (file
, NULL
,
1633 offset
- file
->device
->net
->offset
);
1636 return file
->device
->net
->protocol
->seek (file
, offset
);
1641 if (file
->device
->net
->protocol
->seek
)
1642 return file
->device
->net
->protocol
->seek (file
, offset
);
1643 while (file
->device
->net
->packs
.first
)
1645 grub_netbuff_free (file
->device
->net
->packs
.first
->nb
);
1646 grub_net_remove_packet (file
->device
->net
->packs
.first
);
1648 file
->device
->net
->protocol
->close (file
);
1650 file
->device
->net
->packs
.first
= NULL
;
1651 file
->device
->net
->packs
.last
= NULL
;
1652 file
->device
->net
->offset
= 0;
1653 file
->device
->net
->eof
= 0;
1654 err
= file
->device
->net
->protocol
->open (file
, file
->device
->net
->name
);
1657 grub_net_fs_read_real (file
, NULL
, offset
);
1663 grub_net_fs_read (grub_file_t file
, char *buf
, grub_size_t len
)
1665 if (file
->offset
!= file
->device
->net
->offset
)
1668 err
= grub_net_seek_real (file
, file
->offset
);
1672 return grub_net_fs_read_real (file
, buf
, len
);
1675 static struct grub_fs grub_net_fs
=
1678 .dir
= grub_net_fs_dir
,
1679 .open
= grub_net_fs_open
,
1680 .read
= grub_net_fs_read
,
1681 .close
= grub_net_fs_close
,
1688 grub_net_fini_hw (int noreturn
__attribute__ ((unused
)))
1690 struct grub_net_card
*card
;
1691 FOR_NET_CARDS (card
)
1694 if (card
->driver
->close
)
1695 card
->driver
->close (card
);
1698 return GRUB_ERR_NONE
;
1702 grub_net_restore_hw (void)
1704 return GRUB_ERR_NONE
;
1707 static struct grub_preboot
*fini_hnd
;
1709 static grub_command_t cmd_addaddr
, cmd_deladdr
, cmd_addroute
, cmd_delroute
;
1710 static grub_command_t cmd_lsroutes
, cmd_lscards
;
1711 static grub_command_t cmd_lsaddr
, cmd_slaac
;
1715 grub_register_variable_hook ("net_default_server", defserver_get_env
,
1717 grub_env_export ("net_default_server");
1718 grub_register_variable_hook ("pxe_default_server", defserver_get_env
,
1720 grub_env_export ("pxe_default_server");
1721 grub_register_variable_hook ("net_default_ip", defip_get_env
,
1723 grub_env_export ("net_default_ip");
1724 grub_register_variable_hook ("net_default_mac", defmac_get_env
,
1726 grub_env_export ("net_default_mac");
1728 cmd_addaddr
= grub_register_command ("net_add_addr", grub_cmd_addaddr
,
1729 /* TRANSLATORS: HWADDRESS stands for
1730 "hardware address". */
1731 N_("SHORTNAME CARD ADDRESS [HWADDRESS]"),
1732 N_("Add a network address."));
1733 cmd_slaac
= grub_register_command ("net_ipv6_autoconf",
1734 grub_cmd_ipv6_autoconf
,
1735 N_("[CARD [HWADDRESS]]"),
1736 N_("Perform an IPV6 autoconfiguration"));
1738 cmd_deladdr
= grub_register_command ("net_del_addr", grub_cmd_deladdr
,
1740 N_("Delete a network address."));
1741 cmd_addroute
= grub_register_command ("net_add_route", grub_cmd_addroute
,
1742 /* TRANSLATORS: "gw" is a keyword. */
1743 N_("SHORTNAME NET [INTERFACE| gw GATEWAY]"),
1744 N_("Add a network route."));
1745 cmd_delroute
= grub_register_command ("net_del_route", grub_cmd_delroute
,
1747 N_("Delete a network route."));
1748 cmd_lsroutes
= grub_register_command ("net_ls_routes", grub_cmd_listroutes
,
1749 "", N_("list network routes"));
1750 cmd_lscards
= grub_register_command ("net_ls_cards", grub_cmd_listcards
,
1751 "", N_("list network cards"));
1752 cmd_lsaddr
= grub_register_command ("net_ls_addr", grub_cmd_listaddrs
,
1753 "", N_("list network addresses"));
1757 grub_net_open
= grub_net_open_real
;
1758 fini_hnd
= grub_loader_register_preboot_hook (grub_net_fini_hw
,
1759 grub_net_restore_hw
,
1760 GRUB_LOADER_PREBOOT_HOOK_PRIO_DISK
);
1761 grub_net_poll_cards_idle
= grub_net_poll_cards_idle_real
;
1766 grub_register_variable_hook ("net_default_server", 0, 0);
1767 grub_register_variable_hook ("pxe_default_server", 0, 0);
1771 grub_unregister_command (cmd_addaddr
);
1772 grub_unregister_command (cmd_deladdr
);
1773 grub_unregister_command (cmd_addroute
);
1774 grub_unregister_command (cmd_delroute
);
1775 grub_unregister_command (cmd_lsroutes
);
1776 grub_unregister_command (cmd_lscards
);
1777 grub_unregister_command (cmd_lsaddr
);
1778 grub_unregister_command (cmd_slaac
);
1779 grub_fs_unregister (&grub_net_fs
);
1780 grub_net_open
= NULL
;
1781 grub_net_fini_hw (0);
1782 grub_loader_unregister_preboot_hook (fini_hnd
);
1783 grub_net_poll_cards_idle
= grub_net_poll_cards_idle_real
;