this is suitable for fedora 7 and yet to be tested
#include<linux/module.h>
#include<linux/netdevice.h>
#include<linux/kernel.h>
#include<linux/skbuff.h>
int mac_address[10]=0x0a0b0c010203;
struct net_device *my_dev;
#define SIM_DEVICE "sim"
static netdev_tx_t veth_xmit(struct sk_buff *skb, struct net_device *dev)
{
printk(KERN_INFO "I got a packet");
return NETDEV_TX_OK;
}
static int veth_open(struct net_device *dev)
{
memcpy(dev->dev_addr, "\0ABCD0", ETH_ALEN);
netif_start_queue(dev);
return 0;
}
int veth_close(struct net_device *dev)
{
printk("releasing mydev\n");
netif_stop_queue(dev);
return 0;
}
int veth_dev_init(struct net_device *dev)
{
printk("initialising\n");
return 0;
}
static struct net_device_ops veth_ops = {
.ndo_init = veth_dev_init,
.ndo_open = veth_open,
.ndo_stop = veth_close,
.ndo_start_xmit = veth_xmit,
};
int sim_dev_open(struct net_device *dev)
{
printk("opening dev\n");
netif_start_queue(dev);
return 0;
}
int sim_dev_stop(struct net_device *dev)
{
printk("stoping dev\n");
netif_stop_queue(dev);
return 0;
}
static netdev_tx_t sim_dev_tx(struct sk_buff *skb, struct net_device *dev)
{
struct net_device *priv_data== (struct net_device *) dev->priv;
priv_data->stats.tx_packets++;
return NETDEV_TX_OK;
}
static struct net_device_stats *sim_dev_stats(struct net_device *dev)
{
struct net_device *priv_data = (struct netdevice*) dev->priv;
return &priv_data->stats;
}
static void sim_init(struct net_device *dev)
{
dev->open=sim_dev_open;
dev->stop=sim_dev_stop;
dev->hard_start_xmit=sim_dev_tx;
dev->get_stats=sim_dev_stats;
dev->change_mtu=sim_dev_change_mtu;
}
static int sim_dev_change_mtu(struct net_device *dev, int new_mtu)
{
if(new_mtu<=1500)
dev->mtu=new_mtu;
}
static void NetDeviceCreate(unsinged char *name)
{
struct net_device *sim_dev=NULL;
sim_dev = alloc_netdev(sizeof(struct net_device), name, ether_setup);
if (sim_dev == NULL)
return -ENOMEM;
strcpy(sim_dev->name,name);
strcpy(sim_dev->dev_addr,mac_address);
sim_dev->init=sim_init;
mac_address[4]++;
}
static int veth_init()
{
NetDeviceCreate(SIM_DEVICE"0");
NetDeviceCreate(SIM_DEVICE"1");
NetDeviceCreate(SIM_DEVICE"2");
NetDeviceCreate(SIM_DEVICE"3");
NetDeviceCreate(SIM_DEVICE"4");
NetDeviceCreate(SIM_DEVICE"5");
NetDeviceCreate(SIM_DEVICE"6");
NetDeviceCreate(SIM_DEVICE"7");
int ret,i;
my_dev = alloc_netdev(sizeof(struct net_device), "my_dev", ether_setup);
if (my_dev == NULL)
return -ENOMEM;
register_netdev(my_dev);
return 0;
}
static void NetDeviceDelete()
{
struct net_device *dev;
dev = first_net_device(&init_net);
while (dev)
{
if(!strncmp(dev->name,SIM_DEVICE,strlen(SIM_DEVICE)))
{
unregister_netdev(my_dev);
free_netdev(my_dev);
}
dev = next_net_device(dev);
}
}
static void veth_exit()
{
NetDeviceDelete();
}
module_init(veth_init);
module_exit(veth_exit);
program following below steps:
---------------------------------------------------
module init - init will be called while loadin module
loading module will create 10 sim interface
in each create fucntions
- allocating net device structure by linux system call for each interface as ether_setup
- in allocated net device pointer
--> copying the interface mac address &
--> assign init function(inturn calls the call back functions for
== open - do net interface start queue for the allocated net device
== stop - do net interface stop queue for the allocated net device
== xmit - do extracting private date from the allocated net device and just increment tx_packets. and free skb
== get_stats - do "return the stats structre from the allocated net device"
== mtu - do "change the mtu field in the allcoated net device if its less than 1500"
- after assigned init(call back functions) do register with kernel stack
module exit - called to unload the module during rmmod
in this function
- Scan through the Interfaces available in the system and check
whether they are created by us
If so, deregister them from the system & clean the memory associated
with it
-- calls system call first net device to get the first interface
-- from the called system call we can get each net device structure
-- from this device strucutre take the name and compate its with sim without 1 to 10
-- if it matches call the delete function
== in the delete function use the system call get by name and get the strucutre
== if structure not null then unregister and free it
thats it of module init and module exit
reference:
1. experience
2. http://www.xml.com/ldd/chapter/book/ch14.html (short -> https://www.sics.se/~amir/files/download/device-driver/network.pdf)(one chapter from this book https://www.rose-hulman.edu/~yoder/Beagle/Linux%20Device%20Drivers%203rd.pdf)
3. http://stackoverflow.com/questions/14180717/passing-packets-from-ip-layer-to-device-driver
4. http://searchsrikanth.blogspot.in/2010/03/how-to-write-network-driver-in-linux.html
5. http://stackoverflow.com/questions/4494307/getting-list-of-network-devices-inside-the-linux-kernel
extra:
6. http://stackoverflow.com/questions/15190405/linux-kernel-getting-packets-from-a-netdevice
7.
8.
TCP/IP packet flow:
a. http://www.cubrid.org/blog/dev-platform/understanding-tcp-ip-network-stack/
(best)
kernel architecture course:
1.http://www.cs.columbia.edu/~nahum/w6998/lectures/
2. http://thomas.enix.org/pub/conf/rmll2010/kernel-architecture-for-drivers.pdf
#include<linux/module.h>
#include<linux/netdevice.h>
#include<linux/kernel.h>
#include<linux/skbuff.h>
int mac_address[10]=0x0a0b0c010203;
struct net_device *my_dev;
#define SIM_DEVICE "sim"
static netdev_tx_t veth_xmit(struct sk_buff *skb, struct net_device *dev)
{
printk(KERN_INFO "I got a packet");
return NETDEV_TX_OK;
}
static int veth_open(struct net_device *dev)
{
memcpy(dev->dev_addr, "\0ABCD0", ETH_ALEN);
netif_start_queue(dev);
return 0;
}
int veth_close(struct net_device *dev)
{
printk("releasing mydev\n");
netif_stop_queue(dev);
return 0;
}
int veth_dev_init(struct net_device *dev)
{
printk("initialising\n");
return 0;
}
static struct net_device_ops veth_ops = {
.ndo_init = veth_dev_init,
.ndo_open = veth_open,
.ndo_stop = veth_close,
.ndo_start_xmit = veth_xmit,
};
int sim_dev_open(struct net_device *dev)
{
printk("opening dev\n");
netif_start_queue(dev);
return 0;
}
int sim_dev_stop(struct net_device *dev)
{
printk("stoping dev\n");
netif_stop_queue(dev);
return 0;
}
static netdev_tx_t sim_dev_tx(struct sk_buff *skb, struct net_device *dev)
{
struct net_device *priv_data== (struct net_device *) dev->priv;
priv_data->stats.tx_packets++;
return NETDEV_TX_OK;
}
static struct net_device_stats *sim_dev_stats(struct net_device *dev)
{
struct net_device *priv_data = (struct netdevice*) dev->priv;
return &priv_data->stats;
}
static void sim_init(struct net_device *dev)
{
dev->open=sim_dev_open;
dev->stop=sim_dev_stop;
dev->hard_start_xmit=sim_dev_tx;
dev->get_stats=sim_dev_stats;
dev->change_mtu=sim_dev_change_mtu;
}
static int sim_dev_change_mtu(struct net_device *dev, int new_mtu)
{
if(new_mtu<=1500)
dev->mtu=new_mtu;
}
static void NetDeviceCreate(unsinged char *name)
{
struct net_device *sim_dev=NULL;
sim_dev = alloc_netdev(sizeof(struct net_device), name, ether_setup);
if (sim_dev == NULL)
return -ENOMEM;
strcpy(sim_dev->name,name);
strcpy(sim_dev->dev_addr,mac_address);
sim_dev->init=sim_init;
mac_address[4]++;
}
static int veth_init()
{
NetDeviceCreate(SIM_DEVICE"0");
NetDeviceCreate(SIM_DEVICE"1");
NetDeviceCreate(SIM_DEVICE"2");
NetDeviceCreate(SIM_DEVICE"3");
NetDeviceCreate(SIM_DEVICE"4");
NetDeviceCreate(SIM_DEVICE"5");
NetDeviceCreate(SIM_DEVICE"6");
NetDeviceCreate(SIM_DEVICE"7");
int ret,i;
my_dev = alloc_netdev(sizeof(struct net_device), "my_dev", ether_setup);
if (my_dev == NULL)
return -ENOMEM;
register_netdev(my_dev);
return 0;
}
static void NetDeviceDelete()
{
struct net_device *dev;
dev = first_net_device(&init_net);
while (dev)
{
if(!strncmp(dev->name,SIM_DEVICE,strlen(SIM_DEVICE)))
{
unregister_netdev(my_dev);
free_netdev(my_dev);
}
dev = next_net_device(dev);
}
}
static void veth_exit()
{
NetDeviceDelete();
}
module_init(veth_init);
module_exit(veth_exit);
program following below steps:
---------------------------------------------------
module init - init will be called while loadin module
loading module will create 10 sim interface
in each create fucntions
- allocating net device structure by linux system call for each interface as ether_setup
- in allocated net device pointer
--> copying the interface mac address &
--> assign init function(inturn calls the call back functions for
== open - do net interface start queue for the allocated net device
== stop - do net interface stop queue for the allocated net device
== xmit - do extracting private date from the allocated net device and just increment tx_packets. and free skb
== get_stats - do "return the stats structre from the allocated net device"
== mtu - do "change the mtu field in the allcoated net device if its less than 1500"
- after assigned init(call back functions) do register with kernel stack
module exit - called to unload the module during rmmod
in this function
- Scan through the Interfaces available in the system and check
whether they are created by us
If so, deregister them from the system & clean the memory associated
with it
-- calls system call first net device to get the first interface
-- from the called system call we can get each net device structure
-- from this device strucutre take the name and compate its with sim without 1 to 10
-- if it matches call the delete function
== in the delete function use the system call get by name and get the strucutre
== if structure not null then unregister and free it
thats it of module init and module exit
reference:
1. experience
2. http://www.xml.com/ldd/chapter/book/ch14.html (short -> https://www.sics.se/~amir/files/download/device-driver/network.pdf)(one chapter from this book https://www.rose-hulman.edu/~yoder/Beagle/Linux%20Device%20Drivers%203rd.pdf)
3. http://stackoverflow.com/questions/14180717/passing-packets-from-ip-layer-to-device-driver
4. http://searchsrikanth.blogspot.in/2010/03/how-to-write-network-driver-in-linux.html
5. http://stackoverflow.com/questions/4494307/getting-list-of-network-devices-inside-the-linux-kernel
extra:
6. http://stackoverflow.com/questions/15190405/linux-kernel-getting-packets-from-a-netdevice
7.
8.
TCP/IP packet flow:
a. http://www.cubrid.org/blog/dev-platform/understanding-tcp-ip-network-stack/
(best)
kernel architecture course:
1.http://www.cs.columbia.edu/~nahum/w6998/lectures/
2. http://thomas.enix.org/pub/conf/rmll2010/kernel-architecture-for-drivers.pdf