Changeset 3a14f3b for lib/format_linux.c


Ignore:
Timestamp:
09/14/07 16:05:43 (14 years ago)
Author:
Scott Raynel <smr26@…>
Branches:
4.0.1-hotfixes, cachetimestamps, develop, dpdk-ndag, etsilive, getfragoff, help, libtrace4, master, ndag_format, pfring, rc-4.0.1, rc-4.0.2, rc-4.0.3, rc-4.0.4, ringdecrementfix, ringperformance, ringtimestampfixes
Children:
a81d2fc
Parents:
4c1302b
Message:

Allow libtrace applications to create filters based on pre-compiled BPF
bytecode as well as filterstrings. See trace_create_filter_from_bytecode()

File:
1 edited

Legend:

Unmodified
Added
Removed
  • lib/format_linux.c

    r394706e r3a14f3b  
    5151#include <errno.h>
    5252
     53#include <assert.h>
    5354
    5455struct libtrace_format_data_t {
     
    161162        }
    162163
    163         /* Push BPF filter into the kernel.
     164        /* Push BPF filter into the kernel. At this stage we can safely assume
     165         * that the filterstring has been compiled, or the filter was supplied
     166         * pre-compiled.
    164167         */
    165168        if (filter != NULL) {
     169                assert(filter->flag == 1);
    166170                if (setsockopt(FORMAT(libtrace->format_data)->fd,
    167171                                        SOL_SOCKET,
     
    234238        pcap_t *pcap;
    235239
    236         /* We've been passed a filter, which hasn't been compiled yet. We need
    237          * to figure out the linktype of the socket, compile the filter, check
    238          * to make sure it's sane, then save it for trace_start() to push down
    239          * into the kernel.
    240          */
    241         sock = socket(PF_INET, SOCK_STREAM, 0);
    242         memset(&ifr, 0, sizeof(struct ifreq));
    243         strncpy(ifr.ifr_name, libtrace->uridata, IF_NAMESIZE);
    244         if (ioctl(sock, SIOCGIFHWADDR, &ifr) != 0) {
    245                 perror("Can't get HWADDR for interface");
    246                 return -1;
    247         }
    248         close(socket);
    249 
    250         arphrd = ifr.ifr_hwaddr.sa_family;
    251         dlt = libtrace_to_pcap_dlt(arphrd_type_to_libtrace(arphrd));
    252 
     240        /* Take a copy of the filter object as it was passed in */
    253241        f = (libtrace_filter_t *) malloc(sizeof(libtrace_filter_t));
    254242        memcpy(f, filter, sizeof(libtrace_filter_t));
    255 
    256         pcap = pcap_open_dead(dlt, FORMAT(libtrace->format_data)->snaplen);
    257243       
    258         if (pcap_compile(pcap, &f->filter, f->filterstring, 0, 0) == -1) {
    259                 perror("PCAP failed to compile the filterstring");
    260                 return -1;
    261         }
    262 
    263         pcap_close(pcap);
    264 
     244        /* If we are passed a filter with "flag" set to zero, then we must
     245         * compile the filterstring before continuing. This involves
     246         * determining the linktype, passing the filterstring to libpcap to
     247         * compile, and saving the result for trace_start() to push into the
     248         * kernel.
     249         * If flag is set to one, then the filter was probably generated using
     250         * trace_create_filter_from_bytecode() and so we don't need to do
     251         * anything (we've just copied it above).
     252         */
     253        if (f->flag == 0) {
     254                sock = socket(PF_INET, SOCK_STREAM, 0);
     255                memset(&ifr, 0, sizeof(struct ifreq));
     256                strncpy(ifr.ifr_name, libtrace->uridata, IF_NAMESIZE);
     257                if (ioctl(sock, SIOCGIFHWADDR, &ifr) != 0) {
     258                        perror("Can't get HWADDR for interface");
     259                        return -1;
     260                }
     261                close(socket);
     262
     263                arphrd = ifr.ifr_hwaddr.sa_family;
     264                dlt = libtrace_to_pcap_dlt(arphrd_type_to_libtrace(arphrd));
     265
     266                pcap = pcap_open_dead(dlt,
     267                                FORMAT(libtrace->format_data)->snaplen);
     268
     269                if (pcap_compile(pcap, &f->filter, f->filterstring, 0, 0) == -1) {
     270                        perror("PCAP failed to compile the filterstring");
     271                        return -1;
     272                }
     273
     274                pcap_close(pcap);
     275               
     276                /* Set the "flag" to indicate that the filterstring has been
     277                 * compiled
     278                 */
     279                f->flag = 1;
     280        }
     281       
    265282        if (FORMAT(libtrace->format_data)->filter != NULL)
    266283                free(FORMAT(libtrace->format_data)->filter);
    267284       
    268285        FORMAT(libtrace->format_data)->filter = f;
     286       
    269287        return 0;
    270288#else
Note: See TracChangeset for help on using the changeset viewer.