Please note: This project is no longer active. The website is kept online for historic purposes only.
If you´re looking for a Linux driver for your Atheros WLAN device, you should continue here .

Ticket #729: mattb-rate-procstats.diff

File mattb-rate-procstats.diff, 6.7 kB (added by matt@mattb.net.nz, 13 years ago)

Adds rate control statistics to /proc

  • ath_rate/onoe/onoe.c

    old new  
    429429} 
    430430EXPORT_SYMBOL(ath_rate_detach); 
    431431 
     432#ifdef CONFIG_SYSCTL 
     433void 
     434ath_rate_dynamic_proc_register(struct ieee80211vap *vap) 
     435{                
     436        /* Onoe rate module reports no statistics */ 
     437} 
     438EXPORT_SYMBOL(ath_rate_dynamic_proc_register); 
     439#endif /* CONFIG_SYSCTL */ 
     440 
    432441static int minrateinterval = 500;       /* 500ms */ 
    433442static int maxpercent = 100;            /* 100% */ 
    434443static int minpercent = 0;              /* 0% */ 
  • ath_rate/amrr/amrr.c

    old new  
    481481} 
    482482EXPORT_SYMBOL(ath_rate_detach); 
    483483 
     484#ifdef CONFIG_SYSCTL 
     485void 
     486ath_rate_dynamic_proc_register(struct ieee80211vap *vap) 
     487{                
     488        /* Amrr rate module reports no statistics */ 
     489} 
     490EXPORT_SYMBOL(ath_rate_dynamic_proc_register); 
     491#endif /* CONFIG_SYSCTL */ 
     492 
    484493static int minrateinterval = 500;       /* 500ms */ 
    485494static int maxint = 0x7fffffff;         /* 32-bit big */ 
    486495static int min_threshold = 1; 
  • ath_rate/sample/sample.c

    old new  
    5050#include <linux/random.h> 
    5151#include <linux/delay.h> 
    5252#include <linux/cache.h> 
    53 #include <linux/sysctl.h> 
    5453#include <linux/proc_fs.h> 
    5554#include <linux/if_arp.h> 
     55#include <linux/vmalloc.h> 
    5656 
    5757#include <asm/uaccess.h> 
    5858 
     
    936936} 
    937937EXPORT_SYMBOL(ath_rate_detach); 
    938938 
     939#ifdef CONFIG_SYSCTL 
     940static int 
     941proc_read_nodes(struct ieee80211vap *vap, const int size, char *buf, int space) 
     942{ 
     943        char *p = buf; 
     944        struct ieee80211_node *ni; 
     945        struct ath_node *an; 
     946        struct sample_node *sn; 
     947        struct ieee80211_node_table *nt =  
     948                (struct ieee80211_node_table *) &vap->iv_ic->ic_sta; 
     949        int x = 0; 
     950        int size_bin = 0; 
     951 
     952        TAILQ_FOREACH(ni, &nt->nt_node, ni_list) { 
     953                /* Assume each node needs 500 bytes */ 
     954                if (buf + space < p + 500) 
     955                        break; 
     956                an = ATH_NODE(ni); 
     957                sn = ATH_NODE_SAMPLE(an); 
     958                /* Skip ourself */ 
     959                if (memcmp(vap->iv_myaddr, ni->ni_macaddr,  
     960                                        IEEE80211_ADDR_LEN)==0) { 
     961                        continue; 
     962                } 
     963 
     964                size_bin = size_to_bin(size); 
     965                p += sprintf(p, "%s\n", ether_sprintf(ni->ni_macaddr)); 
     966                p += sprintf(p,  
     967                                "rate\ttt\tperfect\tfailed\tpkts\tavg_tries\tlast_tx\n"); 
     968                for (x = 0; x < sn->num_rates; x++) { 
     969                        int a = 1; 
     970                        int t = 1; 
     971 
     972                        p += sprintf(p, "%s",  
     973                                        (x == sn->current_rate[size_bin]) ? "*" : " "); 
     974 
     975                        p += sprintf(p, "%3d%s", 
     976                                        sn->rates[x].rate/2, 
     977                                        (sn->rates[x].rate & 0x1) != 0 ? ".5" : "  "); 
     978 
     979                        p += sprintf(p, "\t%4d\t%4d\t%2d\t%3d", 
     980                                        sn->stats[size_bin][x].average_tx_time, 
     981                                        sn->stats[size_bin][x].perfect_tx_time, 
     982                                        sn->stats[size_bin][x].successive_failures, 
     983                                        sn->stats[size_bin][x].total_packets); 
     984 
     985                        if (sn->stats[size_bin][x].total_packets) { 
     986                                a = sn->stats[size_bin][x].total_packets; 
     987                                t = sn->stats[size_bin][x].tries; 
     988                        } 
     989                        p += sprintf(p, "\t%d.%02d\t", t/a, (t*100/a) % 100); 
     990                        if (sn->stats[size_bin][x].last_tx) { 
     991                                unsigned d = jiffies -  
     992                                        sn->stats[size_bin][x].last_tx; 
     993                                p += sprintf(p, "%d.%02d", d / HZ, d % HZ); 
     994                        } else { 
     995                                p += sprintf(p, "-"); 
     996                        } 
     997                        p += sprintf(p, "\n"); 
     998                } 
     999                printk("\n"); 
     1000        } 
     1001 
     1002        return (p - buf); 
     1003} 
     1004 
     1005int 
     1006proc_ratesample_open(struct inode *inode, struct file *file) 
     1007{ 
     1008        struct proc_ieee80211_priv *pv = NULL; 
     1009        struct proc_dir_entry *dp = PDE(inode); 
     1010        struct ieee80211vap *vap = dp->data; 
     1011        int size = 0; 
     1012 
     1013        if (!(file->private_data = kmalloc(sizeof(struct proc_ieee80211_priv), 
     1014                                        GFP_KERNEL))) 
     1015                return -ENOMEM; 
     1016 
     1017        /* intially allocate both read and write buffers */ 
     1018        pv = (struct proc_ieee80211_priv *) file->private_data; 
     1019        memset(pv, 0, sizeof(struct proc_ieee80211_priv)); 
     1020        pv->rbuf = vmalloc(MAX_PROC_IEEE80211_SIZE); 
     1021        if (!pv->rbuf) { 
     1022                kfree(pv); 
     1023                return -ENOMEM; 
     1024        } 
     1025        pv->wbuf = vmalloc(MAX_PROC_IEEE80211_SIZE); 
     1026        if (!pv->wbuf) { 
     1027                vfree(pv->rbuf); 
     1028                kfree(pv); 
     1029                return -ENOMEM; 
     1030        } 
     1031        memset(pv->wbuf, 0, MAX_PROC_IEEE80211_SIZE); 
     1032        memset(pv->rbuf, 0, MAX_PROC_IEEE80211_SIZE); 
     1033        pv->max_wlen = MAX_PROC_IEEE80211_SIZE; 
     1034        pv->max_rlen = MAX_PROC_IEEE80211_SIZE; 
     1035 
     1036        /* Determine what size packets to get stats for based on proc filename */ 
     1037        size = (int)simple_strtol(dp->name + 10, NULL, 0); 
     1038 
     1039        /* now read the data into the buffer */ 
     1040        pv->rlen = proc_read_nodes(vap, size, pv->rbuf, MAX_PROC_IEEE80211_SIZE); 
     1041        return 0; 
     1042} 
     1043 
     1044static struct file_operations proc_ratesample_ops = { 
     1045        .read = NULL, 
     1046        .write = NULL, 
     1047        .open = proc_ratesample_open, 
     1048        .release = NULL, 
     1049}; 
     1050 
     1051void 
     1052ath_rate_dynamic_proc_register(struct ieee80211vap *vap) 
     1053{                
     1054        /* Create proc entries for the rate control algorithm */ 
     1055        ieee80211_proc_vcreate(vap, &proc_ratesample_ops, "ratestats_250"); 
     1056        ieee80211_proc_vcreate(vap, &proc_ratesample_ops, "ratestats_1600"); 
     1057        ieee80211_proc_vcreate(vap, &proc_ratesample_ops, "ratestats_3000");     
     1058} 
     1059EXPORT_SYMBOL(ath_rate_dynamic_proc_register); 
     1060#endif /* CONFIG_SYSCTL */ 
     1061 
    9391062MODULE_AUTHOR("John Bicket"); 
    9401063MODULE_DESCRIPTION("SampleRate bit-rate selection algorithm for Atheros devices"); 
    9411064#ifdef MODULE_VERSION 
  • ath_rate/sample/sample.h

    old new  
    4747        struct ath_ratectrl arc;        /* base state */ 
    4848        int ath_smoothing_rate;                 /* ewma percentage (out of 100) */ 
    4949        int ath_sample_rate;            /* send a different bit-rate 1/X packets */ 
    50  
    51 #ifdef CONFIG_SYSCTL 
    52         struct ctl_table_header *sysctl_header; 
    53         struct ctl_table *sysctls; 
    54 #endif 
    55  
    5650}; 
    5751#define ATH_SOFTC_SAMPLE(sc)    ((struct sample_softc *)sc->sc_rc) 
    5852 
  • ath/if_ath.c

    old new  
    10571057        vap->iv_comp_set = ath_comp_set; 
    10581058#endif 
    10591059 
     1060        /* Let rate control register proc entries for the vap */ 
     1061        ath_rate_dynamic_proc_register(vap); 
     1062 
    10601063        /* 
    10611064         * Change the interface type for monitor mode. 
    10621065         */ 
  • ath/if_athrate.h

    old new  
    8686struct ath_ratectrl *ath_rate_attach(struct ath_softc *); 
    8787void ath_rate_detach(struct ath_ratectrl *); 
    8888 
     89#ifdef CONFIG_SYSCTL 
     90/* 
     91 * Allow rate control module to register proc entries with a vap  
     92 * Deallocation of the entries will be dealt with when the vap is destroyed 
     93 */ 
     94void ath_rate_dynamic_proc_register(struct ieee80211vap *vap); 
     95#endif /* CONFIG_SYSCTL */ 
    8996 
    9097/* 
    9198 * State storage handling.