diff --git a/dde_linux/src/drivers/usb/nic/nic.cc b/dde_linux/src/drivers/usb/nic/nic.cc index 58ad54b35e..0e2b1bb42e 100644 --- a/dde_linux/src/drivers/usb/nic/nic.cc +++ b/dde_linux/src/drivers/usb/nic/nic.cc @@ -16,6 +16,7 @@ #include #include #include +#include #include #include @@ -567,39 +568,6 @@ struct sk_buff *skb_dequeue(struct sk_buff_head *list) ** linux/inerrupt.h ** **********************/ -namespace Genode { - - /** - * Convert ASCII string to mac address - */ - template <> - inline size_t ascii_to(char const *s, Nic::Mac_address* mac, unsigned) - { - enum { - HEX = true, - }; - - if(strlen(s) < MAC_LEN) - throw -1; - - char mac_str[6]; - for (int i = 0; i < ETH_ALEN; i++) { - int hi = i * 3; - int lo = hi + 1; - - if (!is_digit(s[hi], HEX) || !is_digit(s[lo], HEX)) - throw -1; - - mac_str[i] = (digit(s[hi], HEX) << 4) | digit(s[lo], HEX); - } - - Genode::memcpy(mac->addr, mac_str, ETH_ALEN); - - return MAC_LEN; - } -} - - static void snprint_mac(char *buf, char *mac) { for (int i = 0; i < ETH_ALEN; i++) diff --git a/os/include/nic/xml_node.h b/os/include/nic/xml_node.h new file mode 100644 index 0000000000..af31503c1a --- /dev/null +++ b/os/include/nic/xml_node.h @@ -0,0 +1,56 @@ +/* + * \brief Xml-node routines used internally in NIC drivers + * \author Sebastian Sumpf + * \author Stefan Kalkowski + * \date 2012-10-22 + */ + +/* + * Copyright (C) 2012 Genode Labs GmbH + * + * This file is part of the Genode OS framework, which is distributed + * under the terms of the GNU General Public License version 2. + */ + +#ifndef _INCLUDE__NIC__XML_NODE_H_ +#define _INCLUDE__NIC__XML_NODE_H_ + +#include +#include + +namespace Genode { + + /** + * Convert ASCII string to mac address + */ + template <> + inline size_t ascii_to(char const *s, + Nic::Mac_address* mac, unsigned) + { + enum { + HEX = true, + MAC_CHAR_LEN = 17, /* 12 number and 6 colons */ + MAC_SIZE = 6, + }; + + if(strlen(s) < MAC_CHAR_LEN) + throw -1; + + char mac_str[6]; + for (int i = 0; i < MAC_SIZE; i++) { + int hi = i * 3; + int lo = hi + 1; + + if (!is_digit(s[hi], HEX) || !is_digit(s[lo], HEX)) + throw -1; + + mac_str[i] = (digit(s[hi], HEX) << 4) | digit(s[lo], HEX); + } + + Genode::memcpy(mac->addr, mac_str, MAC_SIZE); + + return MAC_CHAR_LEN; + } +} + +#endif /* _INCLUDE__NIC__XML_NODE_H_ */ diff --git a/os/src/server/nic_bridge/README b/os/src/server/nic_bridge/README new file mode 100644 index 0000000000..2f6e07279d --- /dev/null +++ b/os/src/server/nic_bridge/README @@ -0,0 +1,17 @@ +The nic_bridge provides multiple sessions of the 'Nic' service while +using a single 'Nic' session for forwarding requests. For proper working +it implements some kind of the 'proxy arp' protocol (rfc1027). That +means it allocates a MAC address for each client. Whenever a client +sends a packet it changes the sender MAC address to the one it hold +available for the client. Moreover, it monitors DHCP packets, and +tracks which IP address is used by which client. Whenever ARP packets +come from the outside it will answer them with the corresponding MAC +address. + +By adding the following attribute to the 'nic_bridge' config node: + +! + +one can define the first MAC address from which the nic_brigde +will allocate MACs for it's clients. Note: that the least relevant +byte will be ignored always starting from 0. \ No newline at end of file diff --git a/os/src/server/nic_bridge/mac.cc b/os/src/server/nic_bridge/mac.cc index 8d867136d6..f3fb111801 100644 --- a/os/src/server/nic_bridge/mac.cc +++ b/os/src/server/nic_bridge/mac.cc @@ -18,4 +18,4 @@ * it's likely, that we will have no clashes here. * (e.g. Linux uses 02:00... for its tap-devices.) */ -const Net::Ethernet_frame::Mac_address Net::Mac_allocator::_mac_addr_base(0x02); +Net::Ethernet_frame::Mac_address Net::Mac_allocator::mac_addr_base(0x02); diff --git a/os/src/server/nic_bridge/mac.h b/os/src/server/nic_bridge/mac.h index 27fbb48d00..283aa7a488 100644 --- a/os/src/server/nic_bridge/mac.h +++ b/os/src/server/nic_bridge/mac.h @@ -28,9 +28,6 @@ namespace Net { { private: - /* reference MAC address */ - static const Ethernet_frame::Mac_address _mac_addr_base; - /* limit available MAC addresses to one byte range */ enum { MSB_MAX = 0xFF }; @@ -47,6 +44,9 @@ namespace Net { class Alloc_failed : Genode::Exception {}; + /* reference MAC address */ + static Ethernet_frame::Mac_address mac_addr_base; + Mac_allocator() { Genode::memset(&_msbs, 0, sizeof(_msbs)); } @@ -61,7 +61,7 @@ namespace Net { for (int i=0; i < MSB_MAX; i++) { if (!_msbs[i].used) { _msbs[i].used = 1; - Ethernet_frame::Mac_address mac = _mac_addr_base; + Ethernet_frame::Mac_address mac = mac_addr_base; mac.addr[5] = i; return mac; } diff --git a/os/src/server/nic_bridge/main.cc b/os/src/server/nic_bridge/main.cc index 62ca97c42f..8e55218535 100644 --- a/os/src/server/nic_bridge/main.cc +++ b/os/src/server/nic_bridge/main.cc @@ -17,6 +17,8 @@ #include #include #include +#include +#include #include "packet_handler.h" #include "component.h" @@ -38,6 +40,14 @@ int main(int, char **) TX_BUF_SIZE = Nic::Session::TX_QUEUE_SIZE * PACKET_SIZE }; + /* read MAC address prefix from config file */ + try { + Nic::Mac_address mac; + Genode::config()->xml_node().attribute("mac").value(&mac); + Genode::memcpy(&Net::Mac_allocator::mac_addr_base, &mac, + sizeof(Net::Mac_allocator::mac_addr_base)); + } catch(...) {} + Root_capability nic_root_cap; try { static Nic::Connection nic(&tx_block_alloc, TX_BUF_SIZE, RX_BUF_SIZE);