]> git.feebdaed.xyz Git - linuxyz.git/commitdiff
socket module for gpio irqsk
authorseantywork <seantywork@gmail.com>
Tue, 17 Jun 2025 12:16:32 +0000 (13:16 +0100)
committerseantywork <seantywork@gmail.com>
Tue, 17 Jun 2025 12:16:32 +0000 (13:16 +0100)
20 files changed:
deth/2504-01.xyz.md [deleted file]
deth/Makefile [deleted file]
deth/deth.c [deleted file]
deth/deth.h [deleted file]
deth/set.sh [deleted file]
deth/unset.sh [deleted file]
kdeth/2504-01.xyz.md [new file with mode: 0644]
kdeth/Makefile [new file with mode: 0644]
kdeth/deth.c [new file with mode: 0644]
kdeth/deth.h [new file with mode: 0644]
kdeth/set.sh [new file with mode: 0755]
kdeth/unset.sh [new file with mode: 0755]
kgpio-irqsock/2506-03.xyz.md [new file with mode: 0644]
kgpio-irqsock/2506-04.xyz.md [deleted file]
kgpio-irqsock/kgpio_irqsk.c
kgpio-irqsock/kgpio_irqsk.h
kxfrm/cbc/kxfrm.c
kxfrm/cbc/kxfrm.h
kxfrm/gcm/kxfrm.c
kxfrm/gcm/kxfrm.h

diff --git a/deth/2504-01.xyz.md b/deth/2504-01.xyz.md
deleted file mode 100644 (file)
index 046a203..0000000
+++ /dev/null
@@ -1,221 +0,0 @@
-# 01
-
-```shell
-
--------------------------
-|                       |
-|                       |
-|    host network       |
-|         veth01        |
-|           |           |
-|           |           |
-------------|-------------
-            |
-            |
-------------|---------------
-|           |             |
-|           |             |
-|          veth02         |  
-|    namespaced network   |
-|                         |
-|                         |
----------------------------
-
-
-```
-
-# 02
-
-
-```shell
-
-[Apr 6 05:18] entered xmit
-[  +0.000010] entered hw tx
-[  +0.000003] kxfrm: ipproto ESP
-[  +0.000002] kxfrm: spi: 01000000
-[  +0.000005] kxfrm: got xfrm state
-[  +0.000001] kxfrm: totlen: 154: esplen: 96: payloadlen: 80
-[  +0.000004] esp: spi: 01000000
-[  +0.000003] esp: seq: 00000010
-[  +0.000002] aalgname: hmac(sha256)
-[  +0.000003] aalg key start: AABBCCDD
-[  +0.000003] ealgname: cbc(aes)
-[  +0.000002] ealg key start: AABBCCDD
-[  +0.000002] kxfrm: got nonce
-[  +0.000002] kxfrm: nonce: A6A34725
-[  +0.000035] hmac: 582E5B00
-[  +0.000002] calc hmac: 582E5B00
-[  +0.000003] kxfrm: hmac verification success
-[  +0.000010] kxfrm: decrypt success
-[  +0.000002] decap ip src: 0aa84201
-[  +0.000002] decap ip dst: 0aa84202
-[  +0.000002] decap ip data len: 66
-[  +0.000002] decap pad exists: 
-[  +0.000001] ==========PAD START==========
-[  +0.000002] 1
-[  +0.000002] 2
-[  +0.000002] 3
-[  +0.000001] 4
-[  +0.000002] 5
-[  +0.000002] 6
-[  +0.000001] 7
-[  +0.000002] 8
-[  +0.000001] 9
-[  +0.000002] 10
-[  +0.000002] 11
-[  +0.000001] 12
-[  +0.000002] ==========PAD END==========
-[  +0.000002] total padlen: 12
-[  +0.000002] next header: 4
-[  +0.000002] decap ip padded data len: 80
-[  +0.000001] dec ip proto tcp: dst port: 09999
-[  +0.000003] 9999: data: \x01\x01\x08
-              \x9a\x8c?t\x0e\x05/\xc2helloxfrm!!!!
-              \x01\x02\x03\x04\x05\x06\x07\x08
-              
-
-
-              \x04
-[  +0.000002] kxfrm: reencrpyted
-[  +0.000002] kxfrm: reencrypted result match
-[  +0.000007] kxfrm: hmac recalculated
-[  +0.000002] kxfrm: copied generated values
-[  +0.000001] kxfrm: old ipcsum: EDA0
-[  +0.000002] kxfrm: new ipcsum: EDA0
-[  +0.000002] kxfrm: success
-
-```
-
-# 03
-
-
-```shell
-
-# the moment you insert the kernel module
-# using `insmod deth.ko`
-
-# this function will initiate
-# two ethernet interfaces
-# and invokes...
-deth_init_module
-  |
-  |         # ...this function
-  |         # which sets up
-  |         # data structures and
-  |         # operations for each interface
-  |         # and registers..
-  --------> deth_setup
-              |
-              |  #... this function
-              |  # which sets MAC address and
-              |  # enable NAPI for RX
-              --------> deth_open
-              |
-              |  #... and this function
-              |  # which is used
-              |  # to send packet to the other end
-              --------> deth_xmit
-                 # ... and few others
-
-
-```
-
-# 04
-
-
-```
-
----------------------------
-|                         |
-|                         |
-|    host network         |
-|         deth1           |
-|    (192.168.10.1/24)    |
-|           |             |
-|           |             |
-------------|--------------
-            |
-            |
-------------|--------------
-|           |             |
-|           |             |
-|     (192.168.10.2/24)   |
-|          deth2          |  
-|    vnet network         |
-|                         |
-|                         |
----------------------------
-
-
-
-
-```
-
-# 05
-
-
-```shell
-
-# the moment you connect (or send)
-# from your client on host to the server 
-# on the vnet namespace,
-# this function triggers...
-deth_xmit
- |
- |  # ...this function
- |  # which prints eth src,dst
- |  # checks protocol,
- |  # prints ip src, dst
- |  # get the device pointer of the other end
- |  # and invokes...
- ---------> deth_hw_tx
-             |
-             | # ... this function 
-             | # to get the tx slot of sender interface
-             ----> deth_tx_cons_buffer
-             | # ... this function
-             | # to set the rx slot of receiver interface
-             ----> deth_rx_prod_buffer
-             | # ... this function
-             | # to trigger the receiver interface
-             | # to start napi polling (receiving)
-             ----> deth_interrupt(deth_napi_interrupt)
-
-# and here, this is what happens
-# when deth_napi_interrupt is triggered
-# this function, if real network interface card was used,
-# will be triggerd as actual hardware irq is fired
-# after registering using request_irq function.
-# however, since there is no real nic involved in this scenario
-# this function is manually triggered by calling deth_interrupt 
-# within hw_tx
-# this function invokes...
-deth_napi_interrupt
- |
- | # ...this function if statusword is RX_INTR
- ----> napi_schedule
-
-# and here, this is what happens
-# when napi_schedule is triggered
-# this function start...
-napi_schedule
- |
- | # ...this function
- | # which is registered using netif_napi_add_weight
- | # within deth_setup
- | # this is the receiving logic 
- | # this invokes....
- ----> deth_poll
-        |
-        | # ... this function
-        | # which gets the packet set within hw_tx
-        ----> deth_rx_cons_buf
-        |
-        | # ... and this function
-        | # which frees up the space for another
-        | # transmission by the sending side
-        ----> deth_tx_release_buffer
-
-
-
-```
\ No newline at end of file
diff --git a/deth/Makefile b/deth/Makefile
deleted file mode 100644 (file)
index dcc11b3..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-obj-m += deth.o
-
-all:
-       make -C /lib/modules/`uname -r`/build M=`pwd` modules
-
-clean:
-       make -C /lib/modules/`uname -r`/build M=`pwd` clean
\ No newline at end of file
diff --git a/deth/deth.c b/deth/deth.c
deleted file mode 100644 (file)
index 0087775..0000000
+++ /dev/null
@@ -1,540 +0,0 @@
-
-#include "deth.h"
-
-
-
-struct net_device *deth_devs[DRV_COUNT];
-struct deth_priv *deth_privs[DRV_COUNT];
-int setup_ptr= 0;
-
-
-int lockup = 0;
-int timeout = DETH_TIMEOUT;
-int pool_size = 8;
-
-
-void (*deth_interrupt)(int, void *, struct pt_regs *);
-
-
-void deth_setup_pool(struct net_device *dev){
-
-       struct deth_priv *priv = netdev_priv(dev);
-       int i;
-       struct deth_packet *pkt;
-
-       priv->ppool = NULL;
-       for (i = 0; i < pool_size; i++) {
-               pkt = kmalloc (sizeof (struct deth_packet), GFP_KERNEL);
-               if (pkt == NULL) {
-                       printk (KERN_INFO "out of memory allocating packet pool\n");
-                       return;
-               }
-               pkt->dev = dev;
-               pkt->next = priv->ppool;
-               priv->ppool = pkt;
-       }
-
-
-}
-
-
-void deth_teardown_pool(struct net_device *dev){
-
-       struct deth_priv *priv = netdev_priv(dev);
-       struct deth_packet *pkt;
-
-       while ((pkt = priv->ppool)) {
-               priv->ppool = pkt->next;
-               kfree (pkt);
-       }
-}    
-
-
-struct deth_packet *deth_tx_cons_buffer(struct net_device *dev){
-
-       struct deth_priv *priv = netdev_priv(dev);
-       unsigned long flags;
-       struct deth_packet *pkt;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       pkt = priv->ppool;
-       if(!pkt) {
-        printk (KERN_INFO "out of pool\n");
-               return pkt;
-       }
-       priv->ppool = pkt->next;
-       if (priv->ppool == NULL) {
-               printk (KERN_INFO "pool empty\n");
-               netif_stop_queue(dev);
-       }
-       spin_unlock_irqrestore(&priv->lock, flags);
-       return pkt;
-
-
-}
-
-void deth_tx_release_buffer(struct deth_packet *pkt){
-
-       unsigned long flags;
-       struct deth_priv *priv = netdev_priv(pkt->dev);
-
-       spin_lock_irqsave(&priv->lock, flags);
-       pkt->next = priv->ppool;
-       priv->ppool = pkt;
-       spin_unlock_irqrestore(&priv->lock, flags);
-       if (netif_queue_stopped(pkt->dev) && pkt->next == NULL){
-
-        netif_wake_queue(pkt->dev);
-    }
-
-
-}
-
-void deth_rx_prod_buf(struct net_device *dev, struct deth_packet *pkt){
-
-       unsigned long flags;
-       struct deth_priv *priv = netdev_priv(dev);
-
-       spin_lock_irqsave(&priv->lock, flags);
-       pkt->next = priv->rx_queue;  
-       priv->rx_queue = pkt;
-       spin_unlock_irqrestore(&priv->lock, flags);
-
-
-}
-
-
-
-struct deth_packet *deth_rx_cons_buf(struct net_device *dev){
-
-       struct deth_priv *priv = netdev_priv(dev);
-       struct deth_packet *pkt;
-       unsigned long flags;
-
-       spin_lock_irqsave(&priv->lock, flags);
-       pkt = priv->rx_queue;
-       if (pkt != NULL){
-        priv->rx_queue = pkt->next;
-    }
-       spin_unlock_irqrestore(&priv->lock, flags);
-       return pkt;
-
-}
-
-void deth_rx_ints(struct net_device *dev, int enable){
-
-       struct deth_priv *priv = netdev_priv(dev);
-       priv->rx_int_enabled = enable;
-}
-
-
-
-
-void deth_napi_interrupt(int irq, void *dev_id, struct pt_regs *regs){
-
-    printk(KERN_INFO "napi interrupt\n");
-
-       int statusword;
-       struct deth_priv *priv;
-
-
-       struct net_device *dev = (struct net_device *)dev_id;
-
-       if (!dev){
-        printk(KERN_INFO "invalid dev\n");
-               return;
-    }
-
-       priv = netdev_priv(dev);
-       spin_lock(&priv->lock);
-
-
-       statusword = priv->status;
-       priv->status = 0;
-       if (statusword & DETH_RX_INTR) {
-        printk(KERN_INFO "napi receive\n");
-               napi_schedule(&priv->napi);
-       }
-       if (statusword & DETH_TX_INTR) {
-        printk(KERN_INFO "napi transmit\n");
-               priv->stats.tx_packets++;
-               priv->stats.tx_bytes += priv->tx_packetlen;
-               if(priv->skb) {
-                       dev_kfree_skb(priv->skb);
-                       priv->skb = 0;
-               }
-       }
-
-    printk(KERN_INFO "napi interrupt end\n");
-
-       spin_unlock(&priv->lock);
-       return;
-}
-
-
-int deth_poll(struct napi_struct *napi, int budget){
-
-
-       int npackets = 0;
-       struct sk_buff *skb;
-       struct deth_priv *priv = container_of(napi, struct deth_priv, napi);
-       struct net_device *dev = priv->dev;
-       struct deth_packet *pkt;
-
-    printk(KERN_INFO "polling\n");
-
-       while (npackets < budget && priv->rx_queue) {
-               pkt = deth_rx_cons_buf(dev);
-               skb = dev_alloc_skb(NET_IP_ALIGN + pkt->datalen);
-               if (! skb) {
-                       if (printk_ratelimit()){
-                printk(KERN_INFO "deth: packet dropped\n");
-            }
-                       priv->stats.rx_dropped++;
-                       npackets++;
-                       deth_tx_release_buffer(pkt);
-                       continue;
-               }
-               skb_reserve(skb, NET_IP_ALIGN);  
-               memcpy(skb_put(skb, pkt->datalen), pkt->data, pkt->datalen);
-               skb->dev = dev;
-               skb->protocol = eth_type_trans(skb, dev);
-               skb->ip_summed = CHECKSUM_UNNECESSARY;
-               netif_receive_skb(skb);
-
-               npackets++;
-               priv->stats.rx_packets++;
-               priv->stats.rx_bytes += pkt->datalen;
-               deth_tx_release_buffer(pkt);
-       }
-
-    printk(KERN_INFO "polling done\n");
-
-       if (npackets < budget) {
-        printk(KERN_INFO "npackets smaller than budget\n");
-               unsigned long flags;
-               spin_lock_irqsave(&priv->lock, flags);
-               if (napi_complete_done(napi, npackets)){
-                       printk(KERN_INFO "napi complete\n");
-            //deth_rx_ints(dev, 1);
-        }
-               spin_unlock_irqrestore(&priv->lock, flags);
-       }
-
-    printk(KERN_INFO "polling end\n");
-
-       return npackets;
-
-}
-
-
-
-netdev_tx_t deth_xmit(struct sk_buff *skb, struct net_device *dev){
-
-    printk("entered xmit\n");
-
-       int len;
-       char *data, shortpkt[ETH_ZLEN];
-       struct deth_priv *priv = netdev_priv(dev);
-
-       data = skb->data;
-       len = skb->len;
-       if (len < ETH_ZLEN) {
-               memset(shortpkt, 0, ETH_ZLEN);
-               memcpy(shortpkt, skb->data, skb->len);
-               len = ETH_ZLEN;
-               data = shortpkt;
-       }
-       netif_trans_update(dev);
-
-       priv->skb = skb;
-
-       deth_hw_tx(data, len, dev);
-
-    printk("exiting xmit\n");
-
-       return 0;
-
-
-}
-
-
-void deth_hw_tx(char *buf, int len, struct net_device *dev){
-
-
-    printk(KERN_INFO "entered hw tx\n");
-
-       struct ethhdr *eh;
-       struct iphdr *ih;
-       struct udphdr *uh;
-       struct tcphdr *th;
-
-       struct net_device *dest;
-       struct deth_priv *priv;
-       u16 sport;
-       u16 dport;
-       struct deth_packet *tx_buffer;
-
-       if (len < sizeof(struct ethhdr) + sizeof(struct iphdr)) {
-               printk("deth: packet too short (%i octets)\n",
-                               len);
-               return;
-       }
-
-
-       eh = (struct ethhdr*)buf;
-
-       ih = (struct iphdr*)(buf + sizeof(struct ethhdr));
-
-
-       printk("eth src: %02X:%02X:%02X:%02X:%02X:%02X\n", 
-               eh->h_source[0],  
-               eh->h_source[1],  
-               eh->h_source[2],  
-               eh->h_source[3],  
-               eh->h_source[4],  
-               eh->h_source[5]);
-       printk("eth dst: %02X:%02X:%02X:%02X:%02X:%02X\n", 
-               eh->h_dest[0], 
-               eh->h_dest[1], 
-               eh->h_dest[2], 
-               eh->h_dest[3], 
-               eh->h_dest[4], 
-               eh->h_dest[5]);
-
-
-       if(ih->protocol == IPPROTO_UDP){
-
-               uh = (struct udphdr*)(buf + sizeof(struct ethhdr) + sizeof(struct iphdr));
-
-               sport = ntohs(uh->source);
-               dport = ntohs(uh->dest);
-
-       } else if (ih->protocol == IPPROTO_TCP){
-
-               th = (struct tcphdr*)(buf + sizeof(struct ethhdr) + sizeof(struct iphdr));
-
-               sport = ntohs(th->source);
-               dport = ntohs(th->dest);
-
-       }
-
-       printk("src: %08x:%05i\n",
-               ntohl(ih->daddr), sport);
-
-       printk("dst: %08x:%05i\n",
-               ntohl(ih->daddr), dport);
-
-       dest = deth_devs[dev == deth_devs[0] ? 1 : 0];
-       priv = netdev_priv(dest);
-
-       tx_buffer = deth_tx_cons_buffer(dev);
-
-       if(!tx_buffer) {
-               printk(KERN_INFO "out of tx buffer, len is %i\n",len);
-               return;
-       }
-
-       tx_buffer->datalen = len;
-       memcpy(tx_buffer->data, buf, len);
-       deth_rx_prod_buf(dest, tx_buffer);
-       if (priv->rx_int_enabled) {
-
-               priv->status |= DETH_RX_INTR;
-               deth_interrupt(0, dest, NULL);
-       }
-
-       priv = netdev_priv(dev);
-       priv->tx_packetlen = len;
-       priv->tx_packetdata = buf;
-       priv->status |= DETH_TX_INTR;
-       if (lockup && ((priv->stats.tx_packets + 1) % lockup) == 0) {
-
-               netif_stop_queue(dev);
-               printk(KERN_INFO "simulate lockup at %ld, txp %ld\n", jiffies, (unsigned long) priv->stats.tx_packets);
-
-       } else{
-
-        deth_interrupt(0, dev, NULL);
-    }
-
-
-}
-
-
-
-
-int deth_open(struct net_device *dev){
-
-       if (dev == deth_devs[1]){
-
-        memcpy((void*)dev->dev_addr, "DETH01", ETH_ALEN);
-
-
-    } else {
-
-               memcpy((void*)dev->dev_addr, "DETH00", ETH_ALEN);
-       }
-
-       struct deth_priv *priv = netdev_priv(dev);
-       napi_enable(&priv->napi);
-
-       netif_start_queue(dev);
-
-    printk(KERN_INFO "started deth\n");
-
-       return 0;
-}
-
-int deth_stop(struct net_device *dev){
-
-       netif_stop_queue(dev);
-
-       struct deth_priv *priv = netdev_priv(dev);
-       napi_disable(&priv->napi);
-
-       return 0;
-
-    printk(KERN_INFO "stopped deth\n");
-}
-
-
-
-
-#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
-
-void deth_tx_timeout(struct net_device *dev)
-
-#else 
-
-void deth_tx_timeout(struct net_device *dev, unsigned int txqueue)
-
-#endif 
-
-{
-       struct deth_priv *priv = netdev_priv(dev);
-    struct netdev_queue *txq = netdev_get_tx_queue(dev, 0);
-
-       printk(KERN_INFO "transmit timeout at %ld, latency %ld\n", jiffies,
-                       jiffies - txq->trans_start);
-
-       priv->status |= DETH_TX_INTR;
-       deth_interrupt(0, dev, NULL);
-       priv->stats.tx_errors++;
-
-       spin_lock(&priv->lock);
-       deth_teardown_pool(dev);
-       deth_setup_pool(dev);
-       spin_unlock(&priv->lock);
-
-       netif_wake_queue(dev);
-       return;
-}
-
-
-
-const struct net_device_ops deth_netdev_ops = {
-       .ndo_open            = deth_open,
-       .ndo_stop            = deth_stop,
-       .ndo_start_xmit      = deth_xmit,
-       .ndo_tx_timeout      = deth_tx_timeout,
-};
-
-
-
-
-void deth_setup(struct net_device *dev){
-
-       ether_setup(dev); 
-       dev->watchdog_timeo = timeout;
-       dev->netdev_ops = &deth_netdev_ops;
-       dev->features        |= NETIF_F_HW_CSUM;
-
-       deth_privs[setup_ptr] = netdev_priv(dev);
-
-       memset(deth_privs[setup_ptr], 0, sizeof(struct deth_priv));
-
-#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
-       netif_napi_add(dev, &(deth_privs[setup_ptr])->napi, deth_poll,2);
-#else 
-       netif_napi_add_weight(dev, &(deth_privs[setup_ptr])->napi, deth_poll,2);
-#endif
-
-       spin_lock_init(&(deth_privs[setup_ptr])->lock);
-       deth_privs[setup_ptr]->dev = dev;
-
-       deth_rx_ints(dev, 1);   
-       deth_setup_pool(dev);
-
-       setup_ptr += 1;
-
-       printk(KERN_INFO "deth: setup success: %d\n", setup_ptr);
-}
-
-
-static int __init deth_init_module(void){
-
-       int err;
-
-       deth_interrupt = deth_napi_interrupt;
-
-       deth_devs[0] = alloc_netdev(sizeof(struct deth_priv), "deth%d", NET_NAME_UNKNOWN, deth_setup);
-       if (!deth_devs[0]){
-        return -ENOMEM;
-    }
-
-       deth_devs[1] = alloc_netdev(sizeof(struct deth_priv), "deth%d", NET_NAME_UNKNOWN, deth_setup);
-
-       if (!deth_devs[1]){
-        return -ENOMEM;
-    }
-
-       err = register_netdevice(deth_devs[0]);
-       if (err < 0) {
-        goto err1;
-    }
-
-    err = register_netdevice(deth_devs[1]);
-
-    if(err < 0) {
-
-        goto err2;
-    }
-
-
-       return 0;
-
-err1:
-
-       free_netdev(deth_devs[0]);
-       return err;
-
-err2:
-       free_netdev(deth_devs[0]);
-    free_netdev(deth_devs[1]);
-       return err; 
-
-}
-
-
-
-static void __exit deth_cleanup_module(void)
-{
-       int i;
-
-       for (i = 0; i < DRV_COUNT; i++) {
-               if (deth_devs[i]) {
-                       unregister_netdev(deth_devs[i]);
-                       deth_teardown_pool(deth_devs[i]);
-                       free_netdev(deth_devs[i]);
-               }
-       }
-       return;
-}
-
-
-
-
-module_init(deth_init_module);
-module_exit(deth_cleanup_module);
-MODULE_LICENSE("GPL");
\ No newline at end of file
diff --git a/deth/deth.h b/deth/deth.h
deleted file mode 100644 (file)
index efbf30d..0000000
+++ /dev/null
@@ -1,133 +0,0 @@
-#ifndef _DETH_X_H_ 
-#define _DETH_X_H_ 
-
-
-
-#include <linux/module.h>
-#include <linux/init.h>
-#include <linux/moduleparam.h>
-
-#include <linux/sched.h>
-#include <linux/kernel.h>
-#include <linux/slab.h> 
-#include <linux/errno.h>  
-#include <linux/types.h>  
-#include <linux/interrupt.h> 
-
-#include <linux/netdevice.h>  
-#include <linux/etherdevice.h> 
-  
-#include <linux/skbuff.h>
-#include <linux/version.h> 
-
-#include <linux/in6.h>
-#include <asm/checksum.h>
-
-#include <linux/in.h>
-#include <linux/ip.h>          
-#include <linux/tcp.h>       
-#include <linux/udp.h>
-
-
-#define DRV_NAME       "deth"
-#define DRV_COUNT   2
-
-
-#define DETH_RX_INTR 0x0001
-#define DETH_TX_INTR 0x0002
-
-
-#define DETH_TIMEOUT 5   
-
-
-
-struct deth_packet {
-       struct deth_packet *next;
-       struct net_device *dev;
-       int     datalen;
-       u8 data[ETH_DATA_LEN];
-};
-
-struct deth_priv {
-    struct net_device_stats stats;
-    int status;
-    struct deth_packet *ppool;
-    struct deth_packet *rx_queue; 
-    int rx_int_enabled;
-    int tx_packetlen;
-    u8 *tx_packetdata;
-    struct sk_buff *skb;
-    spinlock_t lock;
-       struct net_device *dev;
-       struct napi_struct napi;
-};
-
-
-extern struct net_device *deth_devs[DRV_COUNT];
-extern struct deth_priv *deth_privs[DRV_COUNT];
-extern int setup_ptr;
-
-extern const struct net_device_ops deth_netdev_ops;
-
-extern const struct header_ops deth_header_ops;
-
-extern int lockup;
-
-extern int timeout;
-
-extern int pool_size;
-
-extern void (*deth_interrupt)(int, void *, struct pt_regs *);
-
-
-
-void deth_setup_pool(struct net_device *dev);
-
-void deth_teardown_pool(struct net_device *dev);
-
-struct deth_packet *deth_tx_cons_buffer(struct net_device *dev);
-
-void deth_tx_release_buffer(struct deth_packet *pkt);
-
-void deth_rx_prod_buf(struct net_device *dev, struct deth_packet *pkt);
-
-struct deth_packet *deth_rx_cons_buf(struct net_device *dev);
-
-
-
-void deth_rx_ints(struct net_device *dev, int enable);
-
-void deth_napi_interrupt(int irq, void *dev_id, struct pt_regs *regs);
-
-int deth_poll(struct napi_struct *napi, int budget);
-
-
-
-netdev_tx_t deth_xmit(struct sk_buff *skb, struct net_device *dev);
-
-void deth_hw_tx(char *buf, int len, struct net_device *dev);
-
-
-int deth_open(struct net_device *dev);
-
-int deth_stop(struct net_device *dev);
-
-
-
-
-#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
-
-void deth_tx_timeout(struct net_device *dev);
-
-#else 
-
-void deth_tx_timeout(struct net_device *dev, unsigned int txqueue);
-
-#endif 
-
-
-/* module entry */
-
-void deth_setup(struct net_device *dev);
-
-#endif
\ No newline at end of file
diff --git a/deth/set.sh b/deth/set.sh
deleted file mode 100755 (executable)
index 6a66006..0000000
+++ /dev/null
@@ -1,14 +0,0 @@
-#!/bin/bash
-
-sudo ip netns add vnet
-
-sudo ip link set deth1 netns vnet 
-
-sudo ip addr add 192.168.10.1/24 dev deth0
-
-sudo ip link set dev deth0 up
-
-sudo ip netns exec vnet ip addr add 192.168.10.2/24 dev deth1
-
-sudo ip netns exec vnet ip link set dev deth1 up
-
diff --git a/deth/unset.sh b/deth/unset.sh
deleted file mode 100755 (executable)
index c25383e..0000000
+++ /dev/null
@@ -1,16 +0,0 @@
-#!/bin/bash
-
-
-sudo ip link set dev deth0 down
-
-sudo ip netns exec vnet ip link set dev deth1 down
-
-sudo ip addr del 192.168.10.1/24 dev deth0
-
-sudo ip netns exec vnet ip addr del 192.168.10.2/24 dev deth1
-
-sudo ip netns del vnet
-
-
-
-
diff --git a/kdeth/2504-01.xyz.md b/kdeth/2504-01.xyz.md
new file mode 100644 (file)
index 0000000..046a203
--- /dev/null
@@ -0,0 +1,221 @@
+# 01
+
+```shell
+
+-------------------------
+|                       |
+|                       |
+|    host network       |
+|         veth01        |
+|           |           |
+|           |           |
+------------|-------------
+            |
+            |
+------------|---------------
+|           |             |
+|           |             |
+|          veth02         |  
+|    namespaced network   |
+|                         |
+|                         |
+---------------------------
+
+
+```
+
+# 02
+
+
+```shell
+
+[Apr 6 05:18] entered xmit
+[  +0.000010] entered hw tx
+[  +0.000003] kxfrm: ipproto ESP
+[  +0.000002] kxfrm: spi: 01000000
+[  +0.000005] kxfrm: got xfrm state
+[  +0.000001] kxfrm: totlen: 154: esplen: 96: payloadlen: 80
+[  +0.000004] esp: spi: 01000000
+[  +0.000003] esp: seq: 00000010
+[  +0.000002] aalgname: hmac(sha256)
+[  +0.000003] aalg key start: AABBCCDD
+[  +0.000003] ealgname: cbc(aes)
+[  +0.000002] ealg key start: AABBCCDD
+[  +0.000002] kxfrm: got nonce
+[  +0.000002] kxfrm: nonce: A6A34725
+[  +0.000035] hmac: 582E5B00
+[  +0.000002] calc hmac: 582E5B00
+[  +0.000003] kxfrm: hmac verification success
+[  +0.000010] kxfrm: decrypt success
+[  +0.000002] decap ip src: 0aa84201
+[  +0.000002] decap ip dst: 0aa84202
+[  +0.000002] decap ip data len: 66
+[  +0.000002] decap pad exists: 
+[  +0.000001] ==========PAD START==========
+[  +0.000002] 1
+[  +0.000002] 2
+[  +0.000002] 3
+[  +0.000001] 4
+[  +0.000002] 5
+[  +0.000002] 6
+[  +0.000001] 7
+[  +0.000002] 8
+[  +0.000001] 9
+[  +0.000002] 10
+[  +0.000002] 11
+[  +0.000001] 12
+[  +0.000002] ==========PAD END==========
+[  +0.000002] total padlen: 12
+[  +0.000002] next header: 4
+[  +0.000002] decap ip padded data len: 80
+[  +0.000001] dec ip proto tcp: dst port: 09999
+[  +0.000003] 9999: data: \x01\x01\x08
+              \x9a\x8c?t\x0e\x05/\xc2helloxfrm!!!!
+              \x01\x02\x03\x04\x05\x06\x07\x08
+              
+
+
+              \x04
+[  +0.000002] kxfrm: reencrpyted
+[  +0.000002] kxfrm: reencrypted result match
+[  +0.000007] kxfrm: hmac recalculated
+[  +0.000002] kxfrm: copied generated values
+[  +0.000001] kxfrm: old ipcsum: EDA0
+[  +0.000002] kxfrm: new ipcsum: EDA0
+[  +0.000002] kxfrm: success
+
+```
+
+# 03
+
+
+```shell
+
+# the moment you insert the kernel module
+# using `insmod deth.ko`
+
+# this function will initiate
+# two ethernet interfaces
+# and invokes...
+deth_init_module
+  |
+  |         # ...this function
+  |         # which sets up
+  |         # data structures and
+  |         # operations for each interface
+  |         # and registers..
+  --------> deth_setup
+              |
+              |  #... this function
+              |  # which sets MAC address and
+              |  # enable NAPI for RX
+              --------> deth_open
+              |
+              |  #... and this function
+              |  # which is used
+              |  # to send packet to the other end
+              --------> deth_xmit
+                 # ... and few others
+
+
+```
+
+# 04
+
+
+```
+
+---------------------------
+|                         |
+|                         |
+|    host network         |
+|         deth1           |
+|    (192.168.10.1/24)    |
+|           |             |
+|           |             |
+------------|--------------
+            |
+            |
+------------|--------------
+|           |             |
+|           |             |
+|     (192.168.10.2/24)   |
+|          deth2          |  
+|    vnet network         |
+|                         |
+|                         |
+---------------------------
+
+
+
+
+```
+
+# 05
+
+
+```shell
+
+# the moment you connect (or send)
+# from your client on host to the server 
+# on the vnet namespace,
+# this function triggers...
+deth_xmit
+ |
+ |  # ...this function
+ |  # which prints eth src,dst
+ |  # checks protocol,
+ |  # prints ip src, dst
+ |  # get the device pointer of the other end
+ |  # and invokes...
+ ---------> deth_hw_tx
+             |
+             | # ... this function 
+             | # to get the tx slot of sender interface
+             ----> deth_tx_cons_buffer
+             | # ... this function
+             | # to set the rx slot of receiver interface
+             ----> deth_rx_prod_buffer
+             | # ... this function
+             | # to trigger the receiver interface
+             | # to start napi polling (receiving)
+             ----> deth_interrupt(deth_napi_interrupt)
+
+# and here, this is what happens
+# when deth_napi_interrupt is triggered
+# this function, if real network interface card was used,
+# will be triggerd as actual hardware irq is fired
+# after registering using request_irq function.
+# however, since there is no real nic involved in this scenario
+# this function is manually triggered by calling deth_interrupt 
+# within hw_tx
+# this function invokes...
+deth_napi_interrupt
+ |
+ | # ...this function if statusword is RX_INTR
+ ----> napi_schedule
+
+# and here, this is what happens
+# when napi_schedule is triggered
+# this function start...
+napi_schedule
+ |
+ | # ...this function
+ | # which is registered using netif_napi_add_weight
+ | # within deth_setup
+ | # this is the receiving logic 
+ | # this invokes....
+ ----> deth_poll
+        |
+        | # ... this function
+        | # which gets the packet set within hw_tx
+        ----> deth_rx_cons_buf
+        |
+        | # ... and this function
+        | # which frees up the space for another
+        | # transmission by the sending side
+        ----> deth_tx_release_buffer
+
+
+
+```
\ No newline at end of file
diff --git a/kdeth/Makefile b/kdeth/Makefile
new file mode 100644 (file)
index 0000000..dcc11b3
--- /dev/null
@@ -0,0 +1,7 @@
+obj-m += deth.o
+
+all:
+       make -C /lib/modules/`uname -r`/build M=`pwd` modules
+
+clean:
+       make -C /lib/modules/`uname -r`/build M=`pwd` clean
\ No newline at end of file
diff --git a/kdeth/deth.c b/kdeth/deth.c
new file mode 100644 (file)
index 0000000..16ccb4d
--- /dev/null
@@ -0,0 +1,540 @@
+
+#include "deth.h"
+
+
+
+struct net_device *deth_devs[DRV_COUNT];
+struct deth_priv *deth_privs[DRV_COUNT];
+int setup_ptr= 0;
+
+
+int lockup = 0;
+int timeout = DETH_TIMEOUT;
+int pool_size = 8;
+
+
+void (*deth_interrupt)(int, void *, struct pt_regs *);
+
+
+void deth_setup_pool(struct net_device *dev){
+
+       struct deth_priv *priv = netdev_priv(dev);
+       int i;
+       struct deth_packet *pkt;
+
+       priv->ppool = NULL;
+       for (i = 0; i < pool_size; i++) {
+               pkt = kmalloc (sizeof (struct deth_packet), GFP_KERNEL);
+               if (pkt == NULL) {
+                       printk (KERN_INFO "out of memory allocating packet pool\n");
+                       return;
+               }
+               pkt->dev = dev;
+               pkt->next = priv->ppool;
+               priv->ppool = pkt;
+       }
+
+
+}
+
+
+void deth_teardown_pool(struct net_device *dev){
+
+       struct deth_priv *priv = netdev_priv(dev);
+       struct deth_packet *pkt;
+
+       while ((pkt = priv->ppool)) {
+               priv->ppool = pkt->next;
+               kfree (pkt);
+       }
+}    
+
+
+struct deth_packet *deth_tx_reserve_buffer(struct net_device *dev){
+
+       struct deth_priv *priv = netdev_priv(dev);
+       unsigned long flags;
+       struct deth_packet *pkt;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       pkt = priv->ppool;
+       if(!pkt) {
+        printk (KERN_INFO "out of pool\n");
+               return pkt;
+       }
+       priv->ppool = pkt->next;
+       if (priv->ppool == NULL) {
+               printk (KERN_INFO "pool empty\n");
+               netif_stop_queue(dev);
+       }
+       spin_unlock_irqrestore(&priv->lock, flags);
+       return pkt;
+
+
+}
+
+void deth_tx_release_buffer(struct deth_packet *pkt){
+
+       unsigned long flags;
+       struct deth_priv *priv = netdev_priv(pkt->dev);
+
+       spin_lock_irqsave(&priv->lock, flags);
+       pkt->next = priv->ppool;
+       priv->ppool = pkt;
+       spin_unlock_irqrestore(&priv->lock, flags);
+       if (netif_queue_stopped(pkt->dev) && pkt->next == NULL){
+
+        netif_wake_queue(pkt->dev);
+    }
+
+
+}
+
+void deth_rx_prod_buf(struct net_device *dev, struct deth_packet *pkt){
+
+       unsigned long flags;
+       struct deth_priv *priv = netdev_priv(dev);
+
+       spin_lock_irqsave(&priv->lock, flags);
+       pkt->next = priv->rx_queue;  
+       priv->rx_queue = pkt;
+       spin_unlock_irqrestore(&priv->lock, flags);
+
+
+}
+
+
+
+struct deth_packet *deth_rx_cons_buf(struct net_device *dev){
+
+       struct deth_priv *priv = netdev_priv(dev);
+       struct deth_packet *pkt;
+       unsigned long flags;
+
+       spin_lock_irqsave(&priv->lock, flags);
+       pkt = priv->rx_queue;
+       if (pkt != NULL){
+        priv->rx_queue = pkt->next;
+    }
+       spin_unlock_irqrestore(&priv->lock, flags);
+       return pkt;
+
+}
+
+void deth_rx_ints(struct net_device *dev, int enable){
+
+       struct deth_priv *priv = netdev_priv(dev);
+       priv->rx_int_enabled = enable;
+}
+
+
+
+
+void deth_napi_interrupt(int irq, void *dev_id, struct pt_regs *regs){
+
+    printk(KERN_INFO "napi interrupt\n");
+
+       int statusword;
+       struct deth_priv *priv;
+
+
+       struct net_device *dev = (struct net_device *)dev_id;
+
+       if (!dev){
+        printk(KERN_INFO "invalid dev\n");
+               return;
+    }
+
+       priv = netdev_priv(dev);
+       spin_lock(&priv->lock);
+
+
+       statusword = priv->status;
+       priv->status = 0;
+       if (statusword & DETH_RX_INTR) {
+        printk(KERN_INFO "napi receive\n");
+               napi_schedule(&priv->napi);
+       }
+       if (statusword & DETH_TX_INTR) {
+        printk(KERN_INFO "napi transmit\n");
+               priv->stats.tx_packets++;
+               priv->stats.tx_bytes += priv->tx_packetlen;
+               if(priv->skb) {
+                       dev_kfree_skb(priv->skb);
+                       priv->skb = 0;
+               }
+       }
+
+    printk(KERN_INFO "napi interrupt end\n");
+
+       spin_unlock(&priv->lock);
+       return;
+}
+
+
+int deth_poll(struct napi_struct *napi, int budget){
+
+
+       int npackets = 0;
+       struct sk_buff *skb;
+       struct deth_priv *priv = container_of(napi, struct deth_priv, napi);
+       struct net_device *dev = priv->dev;
+       struct deth_packet *pkt;
+
+    printk(KERN_INFO "polling\n");
+
+       while (npackets < budget && priv->rx_queue) {
+               pkt = deth_rx_cons_buf(dev);
+               skb = dev_alloc_skb(NET_IP_ALIGN + pkt->datalen);
+               if (! skb) {
+                       if (printk_ratelimit()){
+                printk(KERN_INFO "deth: packet dropped\n");
+            }
+                       priv->stats.rx_dropped++;
+                       npackets++;
+                       deth_tx_release_buffer(pkt);
+                       continue;
+               }
+               skb_reserve(skb, NET_IP_ALIGN);  
+               memcpy(skb_put(skb, pkt->datalen), pkt->data, pkt->datalen);
+               skb->dev = dev;
+               skb->protocol = eth_type_trans(skb, dev);
+               skb->ip_summed = CHECKSUM_UNNECESSARY;
+               netif_receive_skb(skb);
+
+               npackets++;
+               priv->stats.rx_packets++;
+               priv->stats.rx_bytes += pkt->datalen;
+               deth_tx_release_buffer(pkt);
+       }
+
+    printk(KERN_INFO "polling done\n");
+
+       if (npackets < budget) {
+        printk(KERN_INFO "npackets smaller than budget\n");
+               unsigned long flags;
+               spin_lock_irqsave(&priv->lock, flags);
+               if (napi_complete_done(napi, npackets)){
+                       printk(KERN_INFO "napi complete\n");
+            //deth_rx_ints(dev, 1);
+        }
+               spin_unlock_irqrestore(&priv->lock, flags);
+       }
+
+    printk(KERN_INFO "polling end\n");
+
+       return npackets;
+
+}
+
+
+
+netdev_tx_t deth_xmit(struct sk_buff *skb, struct net_device *dev){
+
+    printk("entered xmit\n");
+
+       int len;
+       char *data, shortpkt[ETH_ZLEN];
+       struct deth_priv *priv = netdev_priv(dev);
+
+       data = skb->data;
+       len = skb->len;
+       if (len < ETH_ZLEN) {
+               memset(shortpkt, 0, ETH_ZLEN);
+               memcpy(shortpkt, skb->data, skb->len);
+               len = ETH_ZLEN;
+               data = shortpkt;
+       }
+       netif_trans_update(dev);
+
+       priv->skb = skb;
+
+       deth_hw_tx(data, len, dev);
+
+    printk("exiting xmit\n");
+
+       return 0;
+
+
+}
+
+
+void deth_hw_tx(char *buf, int len, struct net_device *dev){
+
+
+    printk(KERN_INFO "entered hw tx\n");
+
+       struct ethhdr *eh;
+       struct iphdr *ih;
+       struct udphdr *uh;
+       struct tcphdr *th;
+
+       struct net_device *dest;
+       struct deth_priv *priv;
+       u16 sport;
+       u16 dport;
+       struct deth_packet *tx_buffer;
+
+       if (len < sizeof(struct ethhdr) + sizeof(struct iphdr)) {
+               printk("deth: packet too short (%i octets)\n",
+                               len);
+               return;
+       }
+
+
+       eh = (struct ethhdr*)buf;
+
+       ih = (struct iphdr*)(buf + sizeof(struct ethhdr));
+
+
+       printk("eth src: %02X:%02X:%02X:%02X:%02X:%02X\n", 
+               eh->h_source[0],  
+               eh->h_source[1],  
+               eh->h_source[2],  
+               eh->h_source[3],  
+               eh->h_source[4],  
+               eh->h_source[5]);
+       printk("eth dst: %02X:%02X:%02X:%02X:%02X:%02X\n", 
+               eh->h_dest[0], 
+               eh->h_dest[1], 
+               eh->h_dest[2], 
+               eh->h_dest[3], 
+               eh->h_dest[4], 
+               eh->h_dest[5]);
+
+
+       if(ih->protocol == IPPROTO_UDP){
+
+               uh = (struct udphdr*)(buf + sizeof(struct ethhdr) + sizeof(struct iphdr));
+
+               sport = ntohs(uh->source);
+               dport = ntohs(uh->dest);
+
+       } else if (ih->protocol == IPPROTO_TCP){
+
+               th = (struct tcphdr*)(buf + sizeof(struct ethhdr) + sizeof(struct iphdr));
+
+               sport = ntohs(th->source);
+               dport = ntohs(th->dest);
+
+       }
+
+       printk("src: %08x:%05i\n",
+               ntohl(ih->daddr), sport);
+
+       printk("dst: %08x:%05i\n",
+               ntohl(ih->daddr), dport);
+
+       dest = deth_devs[dev == deth_devs[0] ? 1 : 0];
+       priv = netdev_priv(dest);
+
+       tx_buffer = deth_tx_reserve_buffer(dev);
+
+       if(!tx_buffer) {
+               printk(KERN_INFO "out of tx buffer, len is %i\n",len);
+               return;
+       }
+
+       tx_buffer->datalen = len;
+       memcpy(tx_buffer->data, buf, len);
+       deth_rx_prod_buf(dest, tx_buffer);
+       if (priv->rx_int_enabled) {
+
+               priv->status |= DETH_RX_INTR;
+               deth_interrupt(0, dest, NULL);
+       }
+
+       priv = netdev_priv(dev);
+       priv->tx_packetlen = len;
+       priv->tx_packetdata = buf;
+       priv->status |= DETH_TX_INTR;
+       if (lockup && ((priv->stats.tx_packets + 1) % lockup) == 0) {
+
+               netif_stop_queue(dev);
+               printk(KERN_INFO "simulate lockup at %ld, txp %ld\n", jiffies, (unsigned long) priv->stats.tx_packets);
+
+       } else{
+
+        deth_interrupt(0, dev, NULL);
+    }
+
+
+}
+
+
+
+
+int deth_open(struct net_device *dev){
+
+       if (dev == deth_devs[1]){
+
+        memcpy((void*)dev->dev_addr, "DETH01", ETH_ALEN);
+
+
+    } else {
+
+               memcpy((void*)dev->dev_addr, "DETH00", ETH_ALEN);
+       }
+
+       struct deth_priv *priv = netdev_priv(dev);
+       napi_enable(&priv->napi);
+
+       netif_start_queue(dev);
+
+    printk(KERN_INFO "started deth\n");
+
+       return 0;
+}
+
+int deth_stop(struct net_device *dev){
+
+       netif_stop_queue(dev);
+
+       struct deth_priv *priv = netdev_priv(dev);
+       napi_disable(&priv->napi);
+
+       return 0;
+
+    printk(KERN_INFO "stopped deth\n");
+}
+
+
+
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
+
+void deth_tx_timeout(struct net_device *dev)
+
+#else 
+
+void deth_tx_timeout(struct net_device *dev, unsigned int txqueue)
+
+#endif 
+
+{
+       struct deth_priv *priv = netdev_priv(dev);
+    struct netdev_queue *txq = netdev_get_tx_queue(dev, 0);
+
+       printk(KERN_INFO "transmit timeout at %ld, latency %ld\n", jiffies,
+                       jiffies - txq->trans_start);
+
+       priv->status |= DETH_TX_INTR;
+       deth_interrupt(0, dev, NULL);
+       priv->stats.tx_errors++;
+
+       spin_lock(&priv->lock);
+       deth_teardown_pool(dev);
+       deth_setup_pool(dev);
+       spin_unlock(&priv->lock);
+
+       netif_wake_queue(dev);
+       return;
+}
+
+
+
+const struct net_device_ops deth_netdev_ops = {
+       .ndo_open            = deth_open,
+       .ndo_stop            = deth_stop,
+       .ndo_start_xmit      = deth_xmit,
+       .ndo_tx_timeout      = deth_tx_timeout,
+};
+
+
+
+
+void deth_setup(struct net_device *dev){
+
+       ether_setup(dev); 
+       dev->watchdog_timeo = timeout;
+       dev->netdev_ops = &deth_netdev_ops;
+       dev->features        |= NETIF_F_HW_CSUM;
+
+       deth_privs[setup_ptr] = netdev_priv(dev);
+
+       memset(deth_privs[setup_ptr], 0, sizeof(struct deth_priv));
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
+       netif_napi_add(dev, &(deth_privs[setup_ptr])->napi, deth_poll,2);
+#else 
+       netif_napi_add_weight(dev, &(deth_privs[setup_ptr])->napi, deth_poll,2);
+#endif
+
+       spin_lock_init(&(deth_privs[setup_ptr])->lock);
+       deth_privs[setup_ptr]->dev = dev;
+
+       deth_rx_ints(dev, 1);   
+       deth_setup_pool(dev);
+
+       setup_ptr += 1;
+
+       printk(KERN_INFO "deth: setup success: %d\n", setup_ptr);
+}
+
+
+static int __init deth_init_module(void){
+
+       int err;
+
+       deth_interrupt = deth_napi_interrupt;
+
+       deth_devs[0] = alloc_netdev(sizeof(struct deth_priv), "deth%d", NET_NAME_UNKNOWN, deth_setup);
+       if (!deth_devs[0]){
+        return -ENOMEM;
+    }
+
+       deth_devs[1] = alloc_netdev(sizeof(struct deth_priv), "deth%d", NET_NAME_UNKNOWN, deth_setup);
+
+       if (!deth_devs[1]){
+        return -ENOMEM;
+    }
+
+       err = register_netdevice(deth_devs[0]);
+       if (err < 0) {
+        goto err1;
+    }
+
+    err = register_netdevice(deth_devs[1]);
+
+    if(err < 0) {
+
+        goto err2;
+    }
+
+
+       return 0;
+
+err1:
+
+       free_netdev(deth_devs[0]);
+       return err;
+
+err2:
+       free_netdev(deth_devs[0]);
+    free_netdev(deth_devs[1]);
+       return err; 
+
+}
+
+
+
+static void __exit deth_cleanup_module(void)
+{
+       int i;
+
+       for (i = 0; i < DRV_COUNT; i++) {
+               if (deth_devs[i]) {
+                       unregister_netdev(deth_devs[i]);
+                       deth_teardown_pool(deth_devs[i]);
+                       free_netdev(deth_devs[i]);
+               }
+       }
+       return;
+}
+
+
+
+
+module_init(deth_init_module);
+module_exit(deth_cleanup_module);
+MODULE_LICENSE("GPL");
\ No newline at end of file
diff --git a/kdeth/deth.h b/kdeth/deth.h
new file mode 100644 (file)
index 0000000..2ecc06e
--- /dev/null
@@ -0,0 +1,133 @@
+#ifndef _DETH_X_H_ 
+#define _DETH_X_H_ 
+
+
+
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/moduleparam.h>
+
+#include <linux/sched.h>
+#include <linux/kernel.h>
+#include <linux/slab.h> 
+#include <linux/errno.h>  
+#include <linux/types.h>  
+#include <linux/interrupt.h> 
+
+#include <linux/netdevice.h>  
+#include <linux/etherdevice.h> 
+  
+#include <linux/skbuff.h>
+#include <linux/version.h> 
+
+#include <linux/in6.h>
+#include <asm/checksum.h>
+
+#include <linux/in.h>
+#include <linux/ip.h>          
+#include <linux/tcp.h>       
+#include <linux/udp.h>
+
+
+#define DRV_NAME       "deth"
+#define DRV_COUNT   2
+
+
+#define DETH_RX_INTR 0x0001
+#define DETH_TX_INTR 0x0002
+
+
+#define DETH_TIMEOUT 5   
+
+
+
+struct deth_packet {
+       struct deth_packet *next;
+       struct net_device *dev;
+       int     datalen;
+       u8 data[ETH_DATA_LEN];
+};
+
+struct deth_priv {
+    struct net_device_stats stats;
+    int status;
+    struct deth_packet *ppool;
+    struct deth_packet *rx_queue; 
+    int rx_int_enabled;
+    int tx_packetlen;
+    u8 *tx_packetdata;
+    struct sk_buff *skb;
+    spinlock_t lock;
+       struct net_device *dev;
+       struct napi_struct napi;
+};
+
+
+extern struct net_device *deth_devs[DRV_COUNT];
+extern struct deth_priv *deth_privs[DRV_COUNT];
+extern int setup_ptr;
+
+extern const struct net_device_ops deth_netdev_ops;
+
+extern const struct header_ops deth_header_ops;
+
+extern int lockup;
+
+extern int timeout;
+
+extern int pool_size;
+
+extern void (*deth_interrupt)(int, void *, struct pt_regs *);
+
+
+
+void deth_setup_pool(struct net_device *dev);
+
+void deth_teardown_pool(struct net_device *dev);
+
+struct deth_packet *deth_tx_reserve_buffer(struct net_device *dev);
+
+void deth_tx_release_buffer(struct deth_packet *pkt);
+
+void deth_rx_prod_buf(struct net_device *dev, struct deth_packet *pkt);
+
+struct deth_packet *deth_rx_cons_buf(struct net_device *dev);
+
+
+
+void deth_rx_ints(struct net_device *dev, int enable);
+
+void deth_napi_interrupt(int irq, void *dev_id, struct pt_regs *regs);
+
+int deth_poll(struct napi_struct *napi, int budget);
+
+
+
+netdev_tx_t deth_xmit(struct sk_buff *skb, struct net_device *dev);
+
+void deth_hw_tx(char *buf, int len, struct net_device *dev);
+
+
+int deth_open(struct net_device *dev);
+
+int deth_stop(struct net_device *dev);
+
+
+
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
+
+void deth_tx_timeout(struct net_device *dev);
+
+#else 
+
+void deth_tx_timeout(struct net_device *dev, unsigned int txqueue);
+
+#endif 
+
+
+/* module entry */
+
+void deth_setup(struct net_device *dev);
+
+#endif
\ No newline at end of file
diff --git a/kdeth/set.sh b/kdeth/set.sh
new file mode 100755 (executable)
index 0000000..6a66006
--- /dev/null
@@ -0,0 +1,14 @@
+#!/bin/bash
+
+sudo ip netns add vnet
+
+sudo ip link set deth1 netns vnet 
+
+sudo ip addr add 192.168.10.1/24 dev deth0
+
+sudo ip link set dev deth0 up
+
+sudo ip netns exec vnet ip addr add 192.168.10.2/24 dev deth1
+
+sudo ip netns exec vnet ip link set dev deth1 up
+
diff --git a/kdeth/unset.sh b/kdeth/unset.sh
new file mode 100755 (executable)
index 0000000..c25383e
--- /dev/null
@@ -0,0 +1,16 @@
+#!/bin/bash
+
+
+sudo ip link set dev deth0 down
+
+sudo ip netns exec vnet ip link set dev deth1 down
+
+sudo ip addr del 192.168.10.1/24 dev deth0
+
+sudo ip netns exec vnet ip addr del 192.168.10.2/24 dev deth1
+
+sudo ip netns del vnet
+
+
+
+
diff --git a/kgpio-irqsock/2506-03.xyz.md b/kgpio-irqsock/2506-03.xyz.md
new file mode 100644 (file)
index 0000000..5fb112c
--- /dev/null
@@ -0,0 +1,107 @@
+#
+
+```shell
+seantywork@raspberrypi2:~/hack/linux/linuxyz/kgpio-irqsock $ cat ins.conf 
+#CTLOUT=GPIO17
+#DATAOUT=GPIO23
+CTLIN=GPIO24
+DATAIN=GPIO27
+CTLOUT=0
+DATAOUT=0
+```
+
+#
+
+```shell
+seantywork@raspberrypi2:~/hack/linux/linuxyz/kgpio-irqsock $ sudo ./ins.sh 
+CTL OUT: 0 = 0
+DATA OUT: 0 = 0
+CTL IN : GPIO24 = 536
+DATA IN : GPIO27 = 539
+```
+
+```shell
+[Jun17 10:53] gpio irqsk: gpio_ctl_i to IRQ 55
+[  +0.000012] gpio irqsk: gpio_data_i to IRQ 54
+[  +0.000002] gpio irqsk: module is initialized into the kernel
+[  +0.000002] gpio irqsk: ctl_o: 0 ctl_i: 536
+[  +0.000002] gpio irqsk: data_o: 0 data_i: 539
+[  +1.788774] hwmon hwmon1: Undervoltage detected!
+[  +4.032053] hwmon hwmon1: Voltage normalised
+[ +22.627644] value: c906ea54...b98f7b6f
+[  +1.268015] value: c906ea54...b98f7b6f
+[  +1.267979] value: c906ea54...b98f7b6f
+[  +1.267823] value: c906ea54...b98f7b6f
+[  +1.268179] value: c906ea54...b98f7b6f
+[  +1.267929] value: c906ea54...b98f7b6f
+[  +1.267974] value: c906ea54...b98f7b6f
+[  +1.268064] value: c906ea54...b98f7b6f
+[  +1.268899] value: c906ea54...b98f7b6f
+[  +1.267049] value: c906ea54...b98f7b6f
+
+```
+
+
+#
+
+```shell
+seantywork@raspberrypi:~/hack/linux/linuxyz/kgpio-irqsock $ cat ins.conf 
+CTLOUT=GPIO24
+DATAOUT=GPIO27
+CTLIN=0
+DATAIN=0
+#CTLIN=GPIO17
+#DATAIN=GPIO23
+```
+
+#
+```shell
+
+seantywork@raspberrypi:~/hack/linux/linuxyz/kgpio-irqsock $ sudo ./ins.sh 
+CTL OUT: GPIO24 = 536
+DATA OUT: GPIO27 = 539
+CTL IN : 0 = 0
+DATA IN : 0 = 0
+
+```
+
+```shell
+[Jun17 10:53] gpio irqsk: module is initialized into the kernel
+[  +0.000015] gpio irqsk: ctl_o: 536 ctl_i: 0
+[  +0.000005] gpio irqsk: data_o: 539 data_i: 0
+[  +0.000004] gpio irqsk: test mode
+[  +0.000020] value: c906ea54...b98f7b6f
+[  +0.000038] waitqueue handler: job_handler
+[  +0.000004] waitqueue handler waiting...
+[  +0.104805] sending ctl start preamble
+[  +1.172572] waitqueue handler: job_handler
+[  +0.000013] waitqueue handler waiting...
+[  +0.107381] sending ctl start preamble
+[  +1.160622] waitqueue handler: job_handler
+[  +0.000013] waitqueue handler waiting...
+[  +0.107374] sending ctl start preamble
+[  +1.160590] waitqueue handler: job_handler
+[  +0.000012] waitqueue handler waiting...
+[  +0.107411] sending ctl start preamble
+[  +1.160399] waitqueue handler: job_handler
+[  +0.000012] waitqueue handler waiting...
+[  +0.107614] sending ctl start preamble
+[  +1.160547] waitqueue handler: job_handler
+[  +0.000013] waitqueue handler waiting...
+[  +0.107441] sending ctl start preamble
+[  +1.160471] waitqueue handler: job_handler
+[  +0.000012] waitqueue handler waiting...
+[  +0.107531] sending ctl start preamble
+[  +1.160428] waitqueue handler: job_handler
+[  +0.000011] waitqueue handler waiting...
+[  +0.107573] sending ctl start preamble
+[  +1.160478] waitqueue handler: job_handler
+[  +0.000013] waitqueue handler waiting...
+[  +0.107522] sending ctl start preamble
+[  +1.161356] waitqueue handler: job_handler
+[  +0.000011] waitqueue handler waiting...
+[  +0.106649] sending ctl start preamble
+[  +1.160377] job done
+
+```
+
diff --git a/kgpio-irqsock/2506-04.xyz.md b/kgpio-irqsock/2506-04.xyz.md
deleted file mode 100644 (file)
index 4287ca8..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#
\ No newline at end of file
index 4dccab77013291b768967baa1d1a8970048d9a90..9a96d1e00b69e0182402ce335b95d6e2737ea0e3 100644 (file)
@@ -1,6 +1,17 @@
 #include "kgpio_irqsk.h"
 
 
+struct net_device *geth_devs;
+struct geth_priv *geth_privs;
+
+
+int lockup = 0;
+int timeout = GETH_TIMEOUT;
+int pool_size = 8;
+
+
+void (*geth_interrupt)(int, void *, struct pt_regs *);
+
 int gpio_ctl_o;
 int gpio_ctl_i;
 int gpio_data_o;
@@ -24,11 +35,310 @@ u8 o_value[MAX_PKTLEN] = {0};
 u8 i_value[MAX_PKTLEN] = {0};
 
 
+
+
+
+void geth_napi_interrupt(int irq, void *dev_id, struct pt_regs *regs){
+
+    printk(KERN_INFO "napi interrupt\n");
+
+       struct geth_priv *priv;
+
+
+       struct net_device *dev = (struct net_device *)dev_id;
+
+       if (!dev){
+        printk(KERN_INFO "invalid dev\n");
+               return;
+    }
+
+       priv = netdev_priv(dev);
+       spin_lock(&priv->lock);
+
+       printk(KERN_INFO "napi receive\n");
+       napi_schedule(&priv->napi);
+
+    printk(KERN_INFO "napi interrupt end\n");
+
+       spin_unlock(&priv->lock);
+       return;
+}
+
+
+int geth_poll(struct napi_struct *napi, int budget){
+
+
+       int npackets = 0;
+       struct sk_buff *skb;
+       struct geth_priv *priv = container_of(napi, struct geth_priv, napi);
+       struct net_device *dev = priv->dev;
+       struct geth_packet *pkt;
+
+    printk(KERN_INFO "polling\n");
+
+       while (npackets < budget) {
+
+               // copy value to pkt
+               // pkt = 
+               skb = dev_alloc_skb(NET_IP_ALIGN + pkt->datalen);
+               if (! skb) {
+                       if (printk_ratelimit()){
+                printk(KERN_INFO "geth: packet dropped\n");
+            }
+                       priv->stats.rx_dropped++;
+                       npackets++;
+                       continue;
+               }
+               skb_reserve(skb, NET_IP_ALIGN);  
+               memcpy(skb_put(skb, pkt->datalen), pkt->data, pkt->datalen);
+               skb->dev = dev;
+               skb->protocol = eth_type_trans(skb, dev);
+               skb->ip_summed = CHECKSUM_UNNECESSARY;
+               netif_receive_skb(skb);
+
+               npackets++;
+               priv->stats.rx_packets++;
+               priv->stats.rx_bytes += pkt->datalen;
+       }
+
+    printk(KERN_INFO "polling done\n");
+
+       if (npackets < budget) {
+        printk(KERN_INFO "npackets smaller than budget\n");
+               unsigned long flags;
+               spin_lock_irqsave(&priv->lock, flags);
+               if (napi_complete_done(napi, npackets)){
+                       printk(KERN_INFO "napi complete\n");
+        }
+               spin_unlock_irqrestore(&priv->lock, flags);
+       }
+
+    printk(KERN_INFO "polling end\n");
+
+       return npackets;
+
+}
+
+
+
+netdev_tx_t geth_xmit(struct sk_buff *skb, struct net_device *dev){
+
+    printk("entered xmit\n");
+
+       int len;
+       char *data, shortpkt[ETH_ZLEN];
+       struct geth_priv *priv = netdev_priv(dev);
+
+       data = skb->data;
+       len = skb->len;
+       if (len < ETH_ZLEN) {
+               memset(shortpkt, 0, ETH_ZLEN);
+               memcpy(shortpkt, skb->data, skb->len);
+               len = ETH_ZLEN;
+               data = shortpkt;
+       }
+       netif_trans_update(dev);
+
+       priv->skb = skb;
+
+       geth_hw_tx(data, len, dev);
+
+    printk("exiting xmit\n");
+
+       return 0;
+
+
+}
+
+
+void geth_hw_tx(char *buf, int len, struct net_device *dev){
+
+
+    printk(KERN_INFO "entered hw tx\n");
+
+       struct ethhdr *eh;
+       struct iphdr *ih;
+       struct udphdr *uh;
+       struct tcphdr *th;
+
+       struct geth_priv *priv;
+       u16 sport;
+       u16 dport;
+
+
+       if (len < sizeof(struct ethhdr) + sizeof(struct iphdr)) {
+               printk("geth: packet too short (%i octets)\n",
+                               len);
+               return;
+       }
+
+
+       eh = (struct ethhdr*)buf;
+
+       ih = (struct iphdr*)(buf + sizeof(struct ethhdr));
+
+
+       printk("eth src: %02X:%02X:%02X:%02X:%02X:%02X\n", 
+               eh->h_source[0],  
+               eh->h_source[1],  
+               eh->h_source[2],  
+               eh->h_source[3],  
+               eh->h_source[4],  
+               eh->h_source[5]);
+       printk("eth dst: %02X:%02X:%02X:%02X:%02X:%02X\n", 
+               eh->h_dest[0], 
+               eh->h_dest[1], 
+               eh->h_dest[2], 
+               eh->h_dest[3], 
+               eh->h_dest[4], 
+               eh->h_dest[5]);
+
+
+       if(ih->protocol == IPPROTO_UDP){
+
+               uh = (struct udphdr*)(buf + sizeof(struct ethhdr) + sizeof(struct iphdr));
+
+               sport = ntohs(uh->source);
+               dport = ntohs(uh->dest);
+
+       } else if (ih->protocol == IPPROTO_TCP){
+
+               th = (struct tcphdr*)(buf + sizeof(struct ethhdr) + sizeof(struct iphdr));
+
+               sport = ntohs(th->source);
+               dport = ntohs(th->dest);
+
+       }
+
+       printk("src: %08x:%05i\n",
+               ntohl(ih->daddr), sport);
+
+       printk("dst: %08x:%05i\n",
+               ntohl(ih->daddr), dport);
+
+
+       
+       // gpio tx
+
+       priv = netdev_priv(dev);
+
+       priv->stats.tx_packets++;
+       priv->stats.tx_bytes += len;
+       if(priv->skb) {
+               dev_kfree_skb(priv->skb);
+               priv->skb = 0;
+       }
+       if (lockup && ((priv->stats.tx_packets + 1) % lockup) == 0) {
+
+               netif_stop_queue(dev);
+               printk(KERN_INFO "simulate lockup at %ld, txp %ld\n", jiffies, (unsigned long) priv->stats.tx_packets);
+
+       } 
+
+}
+
+
+
+
+int geth_open(struct net_device *dev){
+
+       memcpy((void*)dev->dev_addr, "GETH01", ETH_ALEN);
+
+       struct geth_priv *priv = netdev_priv(dev);
+       napi_enable(&priv->napi);
+
+       netif_start_queue(dev);
+
+    printk(KERN_INFO "started geth\n");
+
+       return 0;
+}
+
+int geth_stop(struct net_device *dev){
+
+       netif_stop_queue(dev);
+
+       struct geth_priv *priv = netdev_priv(dev);
+       napi_disable(&priv->napi);
+
+       return 0;
+
+    printk(KERN_INFO "stopped geth\n");
+}
+
+
+
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
+
+void geth_tx_timeout(struct net_device *dev)
+
+#else 
+
+void geth_tx_timeout(struct net_device *dev, unsigned int txqueue)
+
+#endif 
+
+{
+       struct geth_priv *priv = netdev_priv(dev);
+    struct netdev_queue *txq = netdev_get_tx_queue(dev, 0);
+
+       printk(KERN_INFO "transmit timeout at %ld, latency %ld\n", jiffies,
+                       jiffies - txq->trans_start);
+
+       geth_interrupt(0, dev, NULL);
+       priv->stats.tx_errors++;
+
+       spin_lock(&priv->lock);
+       spin_unlock(&priv->lock);
+
+       netif_wake_queue(dev);
+       return;
+}
+
+
+
+const struct net_device_ops geth_netdev_ops = {
+       .ndo_open            = geth_open,
+       .ndo_stop            = geth_stop,
+       .ndo_start_xmit      = geth_xmit,
+       .ndo_tx_timeout      = geth_tx_timeout,
+};
+
+
+
+
+void geth_setup(struct net_device *dev){
+
+       ether_setup(dev); 
+       dev->watchdog_timeo = timeout;
+       dev->netdev_ops = &geth_netdev_ops;
+       dev->features        |= NETIF_F_HW_CSUM;
+
+       geth_privs = netdev_priv(dev);
+
+       memset(geth_privs, 0, sizeof(struct geth_priv));
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
+       netif_napi_add(dev, &geth_privs->napi, geth_poll,2);
+#else 
+       netif_napi_add_weight(dev, &geth_privs->napi, geth_poll,2);
+#endif
+
+       spin_lock_init(&geth_privs->lock);
+       geth_privs->dev = dev;
+
+       printk(KERN_INFO "geth: setup success\n");
+}
+
+
+
+
 void gpio_ctl_on(void){
 
        gpio_set_value(gpio_ctl_o, IRQF_TRIGGER_RISING);
 
-       udelay(64);
+       udelay(SYNC_UDELAY);
 
        gpio_set_value(gpio_ctl_o, IRQF_TRIGGER_NONE);
 }
@@ -37,7 +347,7 @@ void gpio_data_on(void){
 
        gpio_set_value(gpio_data_o, IRQF_TRIGGER_RISING);
 
-       udelay(64);
+       udelay(SYNC_UDELAY);
 
        gpio_set_value(gpio_data_o, IRQF_TRIGGER_NONE);
 
@@ -109,17 +419,20 @@ irqreturn_t gpio_data_irq_handler(int irq, void *dev_id) {
                if(data_bits_count == 0){
                        return IRQ_HANDLED;
                } else {
-                       // skb
-                       printk("value: %02x%02x%02x%02x...%02x%02x%02x%02x\n", 
-                               i_value[0],
-                               i_value[1],
-                               i_value[2],
-                               i_value[3],
-                               i_value[MAX_PKTLEN-4],
-                               i_value[MAX_PKTLEN-3],
-                               i_value[MAX_PKTLEN-2],
-                               i_value[MAX_PKTLEN-1]
-                       );
+                       if(gpio_ctl_i != 0 && gpio_ctl_o != 0){
+                               // geth interrupt
+                       }else {
+                               printk("value: %02x%02x%02x%02x...%02x%02x%02x%02x\n", 
+                                       i_value[0],
+                                       i_value[1],
+                                       i_value[2],
+                                       i_value[3],
+                                       i_value[MAX_PKTLEN-4],
+                                       i_value[MAX_PKTLEN-3],
+                                       i_value[MAX_PKTLEN-2],
+                                       i_value[MAX_PKTLEN-1]
+                               );
+                       }
                        data_bits_count = 0;
                        return IRQ_HANDLED;
                }
@@ -179,6 +492,8 @@ static void job_handler(struct work_struct* work){
 
 static int __init ksock_gpio_init(void) {
 
+       int err;
+
        if(gpio_ctl_o == 0 && gpio_ctl_i == 0){
 
                printk("gpio irqsk: at least one ctl should be set\n");
@@ -339,6 +654,38 @@ static int __init ksock_gpio_init(void) {
                printk(KERN_INFO "job done\n");
 
        }
+       if(gpio_ctl_o != 0 && gpio_ctl_i != 0){
+
+               printk("gpio irqsk: prod mode\n");
+
+               geth_interrupt = geth_napi_interrupt;
+
+               geth_devs = alloc_netdev(sizeof(struct geth_priv), "geth%d", NET_NAME_UNKNOWN, geth_setup);
+               if (!geth_devs){
+                       printk("gpio irqsk: can't alloc netdev\n");
+                       gpio_free(gpio_ctl_o);
+                       gpio_free(gpio_data_o);
+                       gpio_free(gpio_ctl_i);
+                       gpio_free(gpio_data_i);
+                       free_irq(gpio_ctl_i_irq, NULL);
+                       free_irq(gpio_data_i_irq, NULL);
+                       return -ENOMEM;
+               }
+
+               err = register_netdevice(geth_devs);
+               if (err < 0) {
+                       printk("gpio irqsk: can't register netdev\n");
+                       gpio_free(gpio_ctl_o);
+                       gpio_free(gpio_data_o);
+                       gpio_free(gpio_ctl_i);
+                       gpio_free(gpio_data_i);
+                       free_irq(gpio_ctl_i_irq, NULL);
+                       free_irq(gpio_data_i_irq, NULL);
+                       free_netdev(geth_devs);
+                       return -1;
+               }
+
+       }
 
 
        return 0;
@@ -347,6 +694,9 @@ static int __init ksock_gpio_init(void) {
 
 static void __exit ksock_gpio_exit(void) {
 
+       unregister_netdev(geth_devs);
+       free_netdev(geth_devs);
+
        if(gpio_ctl_o != 0){
 
                gpio_free(gpio_ctl_o);
index eebdbc588a5153092ea65bf18abbdae220eee39f..5ced54a30e4c72012ec45b73235ab75e3a1264b5 100644 (file)
@@ -20,6 +20,7 @@
 #include <linux/udp.h>
 #include <linux/string.h>
 #include <linux/version.h> 
+#include <linux/skbuff.h>
 
 #include <linux/in6.h>
 #include <linux/sched.h>
 #include <asm/atomic.h>
 #include <asm/checksum.h>
 
+#define DRV_NAME       "geth"
+
+#define GETH_TIMEOUT 5
 
 #define CHECK_BIT(var,pos) ((var) & (1<<(pos)))
 
 #define MAX_PKTLEN 1500
 
+#define SYNC_UDELAY 64
+
+
+
+struct geth_packet {
+       struct geth_packet *next;
+       struct net_device *dev;
+       int     datalen;
+       u8 data[ETH_DATA_LEN];
+};
+
+struct geth_priv {
+    struct net_device_stats stats;
+    int status;
+    struct geth_packet *ppool;
+    struct geth_packet *rx_queue; 
+    int rx_int_enabled;
+    int tx_packetlen;
+    u8 *tx_packetdata;
+    struct sk_buff *skb;
+    spinlock_t lock;
+       struct net_device *dev;
+       struct napi_struct napi;
+};
+
+
+extern struct net_device *geth_devs;
+extern struct geth_priv *geth_privs;
+
+
+extern const struct net_device_ops geth_netdev_ops;
+
+extern const struct header_ops geth_header_ops;
+
+extern int lockup;
+
+extern int timeout;
+
+extern int pool_size;
+
+extern void (*geth_interrupt)(int, void *, struct pt_regs *);
+
+
 
 extern int gpio_ctl_o;
 extern int gpio_ctl_i;
@@ -54,6 +101,42 @@ extern u8 o_value[MAX_PKTLEN];
 extern u8 i_value[MAX_PKTLEN];
 
 
+
+
+
+void geth_napi_interrupt(int irq, void *dev_id, struct pt_regs *regs);
+
+int geth_poll(struct napi_struct *napi, int budget);
+
+
+netdev_tx_t geth_xmit(struct sk_buff *skb, struct net_device *dev);
+
+void geth_hw_tx(char *buf, int len, struct net_device *dev);
+
+
+int geth_open(struct net_device *dev);
+
+int geth_stop(struct net_device *dev);
+
+
+
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
+
+void geth_tx_timeout(struct net_device *dev);
+
+#else 
+
+void geth_tx_timeout(struct net_device *dev, unsigned int txqueue);
+
+#endif 
+
+
+/* module entry */
+
+void geth_setup(struct net_device *dev);
+
+
 void gpio_ctl_on(void);
 
 void gpio_data_on(void);
index 4f60d2574662940ef920533f5408a8193ce9a9d6..b3563534b297ddf630882cd885f134a881e275cc 100644 (file)
@@ -139,7 +139,7 @@ void kxfrm_teardown_pool(struct net_device *dev){
 }    
 
 
-struct kxfrm_packet *kxfrm_tx_cons_buffer(struct net_device *dev){
+struct kxfrm_packet *kxfrm_tx_reserve_buffer(struct net_device *dev){
 
        struct kxfrm_priv *priv = netdev_priv(dev);
        unsigned long flags;
@@ -794,7 +794,7 @@ esp_end:
 
        priv = netdev_priv(dest);
 
-       tx_buffer = kxfrm_tx_cons_buffer(dev);
+       tx_buffer = kxfrm_tx_reserve_buffer(dev);
 
        if(!tx_buffer) {
                printk(KERN_INFO "out of tx buffer, len is %i\n",len);
index a5ea9e3f4ad555b48f30fa06e121d86a0bb5b5db..5f227b217dbd99df8c557b92aaa30ec481268918 100644 (file)
@@ -94,7 +94,7 @@ void kxfrm_setup_pool(struct net_device *dev);
 
 void kxfrm_teardown_pool(struct net_device *dev);
 
-struct kxfrm_packet *kxfrm_tx_cons_buffer(struct net_device *dev);
+struct kxfrm_packet *kxfrm_tx_reserve_buffer(struct net_device *dev);
 
 void kxfrm_tx_release_buffer(struct kxfrm_packet *pkt);
 
index b12a7731459f923eb91bdb59a2e51e42b4faec42..6f0ed039aaabfe5a4cb76080e9d7c6dd1a720646 100644 (file)
@@ -51,7 +51,7 @@ void kxfrm_teardown_pool(struct net_device *dev){
 }    
 
 
-struct kxfrm_packet *kxfrm_tx_cons_buffer(struct net_device *dev){
+struct kxfrm_packet *kxfrm_tx_reserve_buffer(struct net_device *dev){
 
        struct kxfrm_priv *priv = netdev_priv(dev);
        unsigned long flags;
@@ -703,7 +703,7 @@ esp_end:
 
        priv = netdev_priv(dest);
 
-       tx_buffer = kxfrm_tx_cons_buffer(dev);
+       tx_buffer = kxfrm_tx_reserve_buffer(dev);
 
        if(!tx_buffer) {
                printk(KERN_INFO "out of tx buffer, len is %i\n",len);
index e25cab7c46cd769ee80ffbde033d596ecaf712d2..916fe02e9bcea2abf4cbc61927ffc0c505b20565 100644 (file)
@@ -94,7 +94,7 @@ void kxfrm_setup_pool(struct net_device *dev);
 
 void kxfrm_teardown_pool(struct net_device *dev);
 
-struct kxfrm_packet *kxfrm_tx_cons_buffer(struct net_device *dev);
+struct kxfrm_packet *kxfrm_tx_reserve_buffer(struct net_device *dev);
 
 void kxfrm_tx_release_buffer(struct kxfrm_packet *pkt);