drivers: eth_smsc91x: Implement promiscuous mode
Add the RCR_PRMS field to toggle the promiscuous mode in the Ethernet controller. Register a set_config function that can make use of the field when CONFIG_NET_PROMISCUOUS_MODE is enabled. Signed-off-by: Ambroise Vincent <ambroise.vincent@arm.com>
This commit is contained in:
parent
4f88b831e7
commit
b6af1ac66e
2 changed files with 46 additions and 3 deletions
|
@ -678,7 +678,12 @@ static enum ethernet_hw_caps eth_smsc_get_caps(const struct device *dev)
|
|||
{
|
||||
ARG_UNUSED(dev);
|
||||
|
||||
return ETHERNET_LINK_10BASE_T | ETHERNET_LINK_100BASE_T;
|
||||
return (ETHERNET_LINK_10BASE_T
|
||||
| ETHERNET_LINK_100BASE_T
|
||||
#if defined(CONFIG_NET_PROMISCUOUS_MODE)
|
||||
| ETHERNET_PROMISC_MODE
|
||||
#endif
|
||||
);
|
||||
}
|
||||
|
||||
static int eth_tx(const struct device *dev, struct net_pkt *pkt)
|
||||
|
@ -696,6 +701,42 @@ static int eth_tx(const struct device *dev, struct net_pkt *pkt)
|
|||
return smsc_send_pkt(sc, tx_buffer, len);
|
||||
}
|
||||
|
||||
static int eth_smsc_set_config(const struct device *dev,
|
||||
enum ethernet_config_type type,
|
||||
const struct ethernet_config *config)
|
||||
{
|
||||
struct eth_context *data = dev->data;
|
||||
struct smsc_data *sc = &data->sc;
|
||||
uint8_t reg_val;
|
||||
int ret = 0;
|
||||
|
||||
(void) reg_val;
|
||||
|
||||
switch (type) {
|
||||
#if defined(CONFIG_NET_PROMISCUOUS_MODE)
|
||||
case ETHERNET_CONFIG_TYPE_PROMISC_MODE:
|
||||
SMSC_LOCK(sc);
|
||||
smsc_select_bank(sc, 0);
|
||||
reg_val = smsc_read_1(sc, RCR);
|
||||
if (config->promisc_mode && !(reg_val & RCR_PRMS)) {
|
||||
smsc_write_1(sc, RCR, reg_val | RCR_PRMS);
|
||||
} else if (!config->promisc_mode && (reg_val & RCR_PRMS)) {
|
||||
smsc_write_1(sc, RCR, reg_val & ~RCR_PRMS);
|
||||
} else {
|
||||
ret = -EALREADY;
|
||||
}
|
||||
SMSC_UNLOCK(sc);
|
||||
break;
|
||||
#endif
|
||||
|
||||
default:
|
||||
ret = -ENOTSUP;
|
||||
break;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void eth_initialize(struct net_if *iface)
|
||||
{
|
||||
const struct device *dev = net_if_get_device(iface);
|
||||
|
@ -727,6 +768,7 @@ static void eth_initialize(struct net_if *iface)
|
|||
static const struct ethernet_api api_funcs = {
|
||||
.iface_api.init = eth_initialize,
|
||||
.get_capabilities = eth_smsc_get_caps,
|
||||
.set_config = eth_smsc_set_config,
|
||||
.send = eth_tx,
|
||||
};
|
||||
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
|
||||
/* Bank 0, Offset 0x4: Receive Control Register */
|
||||
#define RCR 0x4
|
||||
#define RCR_PRMS 0x0002 /* Promiscuous mode */
|
||||
#define RCR_RXEN 0x0100 /* Enable/disable receiver */
|
||||
#define RCR_STRIP_CRC 0x0200 /* Strip CRC from RX packets */
|
||||
#define RCR_SOFT_RST 0x8000 /* Software reset */
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue