mapinapatechdrv.c 21.9 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <stdio.h>
#include <stdarg.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <fcntl.h>
#include <time.h>
#include <errno.h>
#include <pthread.h>
#include <pcap.h>
#include <sys/mman.h>
#include <sys/shm.h>
#include <netinet/in.h>
#include "mapi.h"
#include "mapidrv.h"
#include "mapidlib.h"

#include "mapidevices.h"
#include "flist.h"
#include "debug.h"
#include "mapi_errors.h"

#ifdef PRECLASSIFICATION
#include "mapidflib.h"
#include "parseconf.h"
#include "printfstring.h"
#include "bpfcompiler.h"
#endif

#define bool_t int

/* The NTCommonInterface.h header provides the interface definitions
 *  * for the Napatech NTCI library */
#include <NTCommonInterface.h>

/* These headers are needed when capturing traffic */
#include <packetfeedstructure.h>
#include <packetdescriptor.h>
#include <NTCI_packetfeed.h>
#include <NTCI_errorcode.h>
#include <NTCI_capabilities.h>
#include <capabilitiesstructure.h>
#include <NTCI_packetclassification.h>
#include <packetclassificationstructure.h>
#include <extendeddescriptor05.h>

typedef struct napatech_instance {
  pthread_attr_t th_attr;
  pthread_t th_proc;
  handle_t napatechhandle;
  uint32_t packetfeedhandle;
  uint32_t channelsBitmask;
  FeedBufferInformationType1_t bufferInfo;
  int eventset;
  short skip;
  void *buf;
  int file;
  char *name;
  int id;
  mapi_offline_device_status_t *offline_status;
  mapid_hw_info_t hwinfo;
  mapidlib_instance_t mapidlib;
  u_int8_t *gpp_base;
} napatech_instance_t;

__attribute__ ((constructor)) void init ();
__attribute__ ((destructor))  void fini ();

static flist_t *devlist;

/* for mapidlib errorcode */
75
int
76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96
mapidrv_get_errno(int devid,int fd)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_get_errno"));

  napatech_instance_t *i=flist_get(devlist,devid);
  return mapid_get_errno(&i->mapidlib,fd);
}

#ifdef WITH_AUTHENTICATION
int mapidrv_authenticate(int devid, int fd, char *vo)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_authenticate"));
	napatech_instance_t *i = flist_get(devlist, devid);
	return mapid_authenticate(&i->mapidlib, fd, vo);
}
#endif

int
mapidrv_apply_function (int devid,int fd, int flags, char* function, mapiFunctArg *fargs)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_apply_function"));
97

98 99 100
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_apply_function; devid = %d; fd = %d; function = %s", devid, fd, function));

  napatech_instance_t *i=flist_get(devlist,devid);
101

102
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_apply_function; &i = %x", (int)i));
103

104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_apply_function; &i->mapidlib = %x", (int)(&i->mapidlib)));

  int _flags = flags;

  return mapid_apply_function(&i->mapidlib, fd, function, fargs, _flags);
}

int mapidrv_add_device(const char *devname, int file,int devid, global_function_list_t *gflist,void *olstatus)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_add_device"));

  napatech_instance_t *i=malloc(sizeof(napatech_instance_t));

  i->napatechhandle = NULL;
  i->packetfeedhandle = 0;

  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_add_device; devname: %s", devname));
  i->name=strdup(devname);
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_add_device; i->name: %s", i->name));
  i->id=devid;
  // i->dagfd=-1;
  i->file=file;
  // i->th_proc=0;
  i->hwinfo.offline=0;
  i->hwinfo.devfd=i->napatechhandle;
  i->hwinfo.gflist=gflist;
  i->hwinfo.pkt_drop=0;
  i->offline_status = olstatus;
  if(devid<0)
    i->hwinfo.offline = 1;
134

135 136 137 138 139 140 141 142 143 144 145 146 147 148
  DEBUG_CMD(Debug_Message("Added device %d: %s", devid, devname));

  flist_append(devlist,devid,i);
  mapid_init(&i->mapidlib);
  return 0;
}

int mapidrv_delete_device(int devid)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_delete_device"));

  napatech_instance_t *i=flist_remove(devlist,devid);

  uint32_t result;
149

150 151 152 153 154 155
  if (i!=NULL) {
    int err=0;

    if (i->th_proc && pthread_equal(i->th_proc, pthread_self())==0) {
      DEBUG_CMD(Debug_Message("Calling thread != th_proc (%lu != %lu), cancelling", i->th_proc, pthread_self()));
      fflush(stdout);
156

157 158 159 160 161
      if ((err=pthread_cancel(i->th_proc))!=0) {
        if (!(i->hwinfo.offline==1 && err==ESRCH)) {
          DEBUG_CMD(Debug_Message("WARNING: Could not cancel thread for devid %d (%s)", devid, strerror(err)));
          fflush(stdout);
        }
162
      }
163 164 165
    }

    if(i->napatechhandle != NULL) {
's avatar
committed
166 167 168 169
      if((result = NTCI_StopPacketFeed(i->napatechhandle, i->packetfeedhandle)) != NTCI_ERRCODE_SUCCESS) {
        DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_delete_device; Failed to stop packet feed! (%i)\n", result));
      }

170
      if((result = NTCI_DestroyPacketFeed(i->napatechhandle, i->packetfeedhandle)) != NTCI_ERRCODE_SUCCESS) {
171 172 173 174 175 176 177 178 179 180 181 182 183
        DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_delete_device; Failed to destroy packet feed! (%i)\n", result));
      }
      NTCI_CloseCard(i->napatechhandle);
      DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_delete_device; Napatech device closed"));
    }

    mapid_destroy(&i->mapidlib);
    free(i->name);
    if(i->offline_status != NULL)
      *(i->offline_status) = DEVICE_DELETED;

    free(i);
  }
184

185 186 187
  return 0;
}

188
static unsigned
189 190 191 192 193 194 195 196 197 198
// process_pkts(void *buf,unsigned len, napatech_instance_t *i)
process_pkts(BufferInformationSectionType1_t* bufferInformation, napatech_instance_t *i)
{
  /* DEBUG_CMD(Debug_Message("napatechdrv: process_pkts"));
  DEBUG_CMD(Debug_Message("napatechdrv: process_pkts; packet count: %d", bufferInformation->numDescriptorsAvailable)); */

  mapid_pkthdr_t mhdr;

  uint32_t packet = 0;
  uint8_t *frame = NULL;
199

200
  PacketDescriptorType2_t *descriptor = (PacketDescriptorType2_t *)(((uint8_t*)(i->bufferInfo.bufferBaseAddress)) + bufferInformation->sectionOffset);
201

202 203 204 205 206 207
  // pNetFlow->flowStat.uiTotalDropped+=bufferInformation.numDroppedFrames;

  if(descriptor->ExtensionFormat == EXTENDED_DESCRIPTOR_05_TYPE) {
    for(packet=0; packet < bufferInformation->numDescriptorsAvailable; packet++) {
      i->hwinfo.pkts++;

208 209
      PacketExtDescriptorType05_t *pExtDescr = (PacketExtDescriptorType05_t*)(((uint8_t*)descriptor) + sizeof(PacketDescriptorType2_t));

's avatar
committed
210
      frame = ((uint8_t*)descriptor);
211

212
      mhdr.ts = ((4503599*(descriptor->Timestamp>>32))>>20)|(descriptor->Timestamp<<32) ;
213 214 215
      mhdr.ifindex = descriptor->Channel;
      mhdr.caplen = descriptor->StoredLength;
      mhdr.wlen = descriptor->WireLength;
216

217 218 219 220 221 222 223 224 225 226 227 228 229
			// Layer 2 type. (0:EtherII, 1:LLC, 2:SNAP, 3:Novell RAW)
			switch(pExtDescr->l2Type) {
				case 0:
					i->hwinfo.link_type = DLT_EN10MB;
					break;
				case 1:
				case 2:
				case 3:
				default:
					DEBUG_CMD(Debug_Message("WARNING: Unexpected Layer 2 type (%d) in Extended Packet Descriptor\n", pExtDescr->l2Type));
					break;
			}

230
      // ? TODO - modify third argument to pass test_packet_read
's avatar
committed
231
      mapid_process_pkt(&i->mapidlib, (unsigned char*)frame, frame + sizeof(PacketDescriptorType2_t) + (descriptor->ExtensionLength << 3), &mhdr);
232 233 234 235 236 237 238 239

      /* Avance to the next packet. */
      descriptor = (PacketDescriptorType2_t*)((uint8_t*)descriptor + descriptor->StoredLength);
    }
  } else {
    for(packet=0; packet < bufferInformation->numDescriptorsAvailable; packet++) {
      i->hwinfo.pkts++;

's avatar
committed
240
      frame = ((uint8_t*)descriptor);
241

242 243
      //Todo: temporary solution.
      mhdr.ts = ((4503599*(descriptor->Timestamp>>32))>>20)|(descriptor->Timestamp<<32) ;
244 245 246 247 248
      mhdr.ifindex = descriptor->Channel;
      mhdr.caplen = descriptor->StoredLength;
      mhdr.wlen = descriptor->WireLength;

      // ? TODO - modify third argument to pass test_packet_read
's avatar
committed
249
      mapid_process_pkt(&i->mapidlib, (unsigned char*)frame, frame + sizeof(PacketDescriptorType2_t), &mhdr);
250 251 252 253

      /* Avance to the next packet. */
      descriptor = (PacketDescriptorType2_t*)((uint8_t*)descriptor + descriptor->StoredLength);
    }
254 255
  }

256 257 258
  return 0;
}

259
static unsigned
260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282
process_pkts_offline(void *buf,unsigned len, napatech_instance_t *i)
{
  DEBUG_CMD(Debug_Message("napatechdrv: process_pkts_offline"));

  /* TODO */

  return 0;

}

static void
mapidrv_offline_proc_loop(void *arg)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_offline_proc_loop"));

  /* TODO */

}

static void
mapidrv_proc_loop (void *arg)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_proc_loop"));
283

284 285 286 287 288 289 290 291 292 293 294 295 296 297 298
  int devid = *(int *)arg;
  napatech_instance_t *i=flist_get(devlist,devid);
  int err;

  BufferRequestSampledType2_t request;
  // BufferInformationSectionType6_t bufferInformation;
  BufferInformationSectionType1_t bufferInformation;
  uint32_t result;

  request.common.waitTimeoutMS=GET_NEXT_BUFFER_INFINITE_WAIT;

  if ((err=pthread_setcanceltype(PTHREAD_CANCEL_ASYNCHRONOUS, NULL)) != 0) {
     DEBUG_CMD(Debug_Message("ERROR: pthread_setcanceltype failed (%s)",strerror(err)));
     return;
  }
299

300 301 302 303 304
  if ((err=pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL)) != 0) {
     DEBUG_CMD(Debug_Message("ERROR: pthread_setcancelstate (%s) failed", strerror(err)));
     return;
  }

305
  while (1) {
306

307 308
    // DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_proc_loop; i->napatechhandle: %d; i->packetfeedhandle: %d", i->napatechhandle, i->packetfeedhandle));

309 310 311 312 313 314
    result = NTCI_GetNextBuffer(i->napatechhandle,
                                i->packetfeedhandle,
                                STID_BUFFER_REQUEST_SAMPLED_TYPE2,
                                &request,
                                STID_BUFFER_INFORMATION_SECTION_TYPE1,
                                &bufferInformation);
315

316
    if(result == NTCI_ERRCODE_SUCCESS) {
317 318 319 320

      i->hwinfo.pkt_drop += bufferInformation.numDroppedFrames;

      if(bufferInformation.numDescriptorsAvailable > 0) process_pkts(&bufferInformation, i);
321 322 323 324

      NTCI_ReleaseBuffer(i->napatechhandle,
                         i->packetfeedhandle,
                         STID_BUFFER_INFORMATION_SECTION_TYPE1,
325
                         &bufferInformation);
326 327
    }
    else if(result != NTCI_STATUSCODE_NO_PACKETS_AVAILABLE) {
328 329 330 331
      DEBUG_CMD(Debug_Message("Failed to get buffers. Error code %d\n", result)); //stderr
      break;
    }

332 333
  }
}
334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390

int
mapidrv_read_results (int devid,int fd, int fid, mapid_result_t** result)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_read_results"));

  napatech_instance_t *i=flist_get(devlist,devid);
  return mapid_read_results(&i->mapidlib,fd,fid,result);
}

mapid_funct_info_t* mapidrv_get_flow_functions(int devid,int fd)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_get_flow_functions"));

  napatech_instance_t *i=flist_get(devlist,devid);
  return mapid_get_flow_functions(&i->mapidlib,fd);
}

int mapidrv_get_flow_info(int devid,int fd,mapi_flow_info_t *info) {
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_get_flow_info"));

  napatech_instance_t *i=flist_get(devlist,devid);
  return mapid_get_flow_info(&i->mapidlib,fd,info);
}

int
mapidrv_create_offline_flow (int devid, int format,int fd,char **devtype)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_create_offline_flow"));

  napatech_instance_t *i=flist_get(devlist,devid);

  /* TODO */

  return 0;
}

int
mapidrv_create_flow (int devid, int fd, char **devtype)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_create_flow"));

  napatech_instance_t *i;

  uint32_t result=0;
  uint32_t feedPriorities[] = { 1 };
  FeedConfigSampledType2_t feedConfig;
  // BufferInformationSectionType6_t bufferInformation;
  // FeedBufferInformationType1_t bufferInfo;
  // BufferRequestSampledType2_t request;
  CardHardwareCapabilitiesType1_t cardCapabilities;
  uint32_t channelsBitmask=0;
  CardHardwareVersionCapabilitiesType3_t data3;

  if(devid < 0)
    {
      napatech_instance_t *inst=flist_get(devlist,devid);
391

392 393
      *devtype=MAPI_DEVICE_NAPATECH;
      inst->hwinfo.offline=1;
394

395
      inst->hwinfo.cap_length=1500;
396
			inst->hwinfo.link_type=DLT_EN10MB;
397 398 399
      inst->hwinfo.devtype=MAPI_DEVICE_NAPATECH;
      inst->hwinfo.devid=inst->id;
      inst->hwinfo.pkts=0;
400

401 402 403 404 405 406 407 408
      DEBUG_CMD(Debug_Message("Reading from trace file: %s", inst->name));

      return mapid_add_flow(&inst->mapidlib,fd,&inst->hwinfo,NULL);
    }

  i=flist_get(devlist,devid);

  i->hwinfo.offline=0;
409

410
  *devtype=MAPI_DEVICE_NAPATECH;
411

412 413 414 415 416 417 418 419
  //Open device if it is not already open
  if (i->napatechhandle == NULL)
    {

  /* Open the correct card. */
  DEBUG_CMD(Debug_Message("mapinapatechdrv: mapidrv_create_flow; Trying to open NTCI based adapter #%d\n", i->name[strlen(i->name) - 1] - '0'));
  if(strstr(i->name, "xyxs") != NULL) {
    /* X card series. */
420
    DEBUG_CMD(Debug_Message("mapinapatechdrv: mapidrv_create_flow; Opening X card series."));
421 422
    i->napatechhandle = NTCI_OpenCard(NTCI_CARD_TYPE_ANY, i->name[strlen(i->name) - 1] - '0');
  } else if(strstr(i->name, "ntx") != NULL) {
423
    DEBUG_CMD(Debug_Message("mapinapatechdrv: mapidrv_create_flow; Opening ntxc card series."));
424 425 426 427
    i->napatechhandle = NTCI_OpenCard(NTCI_ANY_NAPATECH_CARD_TYPE, i->name[strlen(i->name) - 1] - '0');
  }
  if(i->napatechhandle==NULL) {
    DEBUG_CMD(Debug_Message("mapinapatechdrv: mapidrv_create_flow; Failed to open adapter.\n"));
428 429
    return NTCI_ERRCODE_NO_DEVICE_OPEN; // TODO
  }
430 431 432

  i->hwinfo.devfd = (int)i->napatechhandle;

433 434
  i->hwinfo.cap_length=0;
  /* TODO cap_length from hw */
435 436 437 438
  if (i->hwinfo.cap_length==0) {
    DEBUG_CMD(Debug_Message("WARNING: Could not get info hardware-info, using default = 1500"));
    i->hwinfo.cap_length=1500;
  }
439
  i->hwinfo.link_type=DLT_EN10MB; // TODO
440

441

442 443 444
  DEBUG_CMD(Debug_Message("mapinapatechdrv: mapidrv_create_flow; NTCI_CardIdentification() = %d", NTCI_CardIdentification(i->napatechhandle)));


445
  if((result = NTCI_GetCapabilities(i->napatechhandle,
446 447 448 449 450 451 452
                                    CAPID_HARDWARE,
                                    NOT_SUB_CAPABILITIES,
                                    STID_CARD_HARDWARE_CAPABILITIES_TYPE1,
                                    &cardCapabilities)) != NTCI_ERRCODE_SUCCESS) {

    DEBUG_CMD(Debug_Message(stderr, "Error finding adapter capabilities: %i\n", result));
  }
453

454
  channelsBitmask = cardCapabilities.totalChannelsBitmask;
455

's avatar
committed
456
  if (NTCI_CardIdentification(i->napatechhandle)==NT_CARD_TYPE) {
457

458 459 460 461 462 463 464 465 466 467 468
  /* Check if we need to use NTPL to set up feeds. */
  if((result = NTCI_GetCapabilities(i->napatechhandle,
                                    CAPID_VERSION,
                                    NOT_SUB_CAPABILITIES,
                                    STID_CARD_HARDWARE_VERSION_CAPABILITIES_TYPE3,
                                    &data3)) != NTCI_ERRCODE_SUCCESS) {
    DEBUG_CMD(Debug_Message(stderr, "Error finding HW capabilities: %i\n", result));
  }

  switch (data3.AdapterCard.dwInfoType) {
  case 1:
's avatar
committed
469 470 471 472 473 474 475
    if((uint16_t)((data3.AdapterCard.u.InfoType1.qwFpgaId>>8)&0xFF) == 32) {
      if(system("grep \"disableMultiFeed\" /opt/napatech/config/default.cfg > /dev/null") == 0) {
        if(system("grep \"#disableMultiFeed\" /opt/napatech/config/default.cfg > /dev/null") != 0) {
          if(system("grep disableMultiFeed /opt/napatech/config/default.cfg | grep 0 > /dev/null") == 0) {
            channelsBitmask = 0;
          }
        } else {
476 477 478 479 480 481 482 483
          channelsBitmask = 0;
        }
      } else {
        channelsBitmask = 0;
      }
    }
    break;
  case 2:
's avatar
committed
484 485 486 487 488 489 490
    if((uint16_t)((data3.AdapterCard.u.InfoType2.qwFpgaId>>8)&0xFF) == 32) {
      if(system("grep \"disableMultiFeed\" /opt/napatech/config/default.cfg > /dev/null") == 0) {
        if(system("grep \"#disableMultiFeed\" /opt/napatech/config/default.cfg > /dev/null") != 0) {
          if(system("grep disableMultiFeed /opt/napatech/config/default.cfg | grep 0 > /dev/null") == 0) {
            channelsBitmask = 0;
          }
        } else {
491 492 493 494 495
          channelsBitmask = 0;
        }
      } else {
        channelsBitmask = 0;
      }
496
    }
497 498 499 500 501 502
    break;
  default:
    // DEBUG_MSG(Debug_Message("Unsupported FPGA!")); // ?
    return;
  }

's avatar
committed
503 504
  } /* if (NTCI_CardIdentification(i->napatechhandle)==NT_CARD_TYPE) */

505 506 507 508 509 510 511
  i->hwinfo.devtype=MAPI_DEVICE_NAPATECH;
  i->hwinfo.devid=i->id;
  i->hwinfo.pkts=0;


  /* Set up the packet feed engine for a single feed.
   *
512 513 514 515
   * The feedPriorities array is used to assign the
   * priorities of different feeds when creating multiple
   * simultaneous feeds; in this example it is redundant
   * as only one entry is required */
516 517 518 519 520 521 522 523 524

  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_create_flow; NTCI_SetupPacketFeedEngine(%d, %d, %d)", i->napatechhandle, 1, feedPriorities[0]));

  if((result = NTCI_SetupPacketFeedEngine(i->napatechhandle, 1, feedPriorities)) != NTCI_ERRCODE_SUCCESS) {
    DEBUG_CMD(Debug_Message("Failed to initialise packet feed engine (%i)\n", result)); //stderr
    NTCI_CloseCard(i->napatechhandle);
    return -1;
  }

525

526 527 528 529 530
  /* Create the packet feed.
   *
   * First, initialise the feedConfig structure */
  /* provide packets in sections */
  feedConfig.bufferType = BUFFER_SECTION;
531

532
  /* hardware native timestamps */
533
  feedConfig.timestampType = TIMESTAMP_PCAP_NANOTIME;
534

535
  /* do not deliver corrupted packets */
536
  //feedConfig.dropErroredPacketsFlag = 1;
537

538 539
  /* slicing is disabled */
  feedConfig.sliceLength = 0;
540

541 542 543
  /* large samples are used: these better handle network
   * traffic fluctuations */
  feedConfig.bufferBehaviour = SMALL_REGULAR_SAMPLES;
544

545
  /* Create the packet feed.
546 547 548
   *
   * PACKET_FEED_SOURCE_SAMPLED is used to specify real time
   * sampling of network traffic. */
549 550 551 552 553 554 555 556 557 558
  if((result = NTCI_CreatePacketFeed(i->napatechhandle,
                                     0,
                                     channelsBitmask,
                                     PACKET_FEED_SOURCE_SAMPLED,
                                     PACKET_FEED_DESTINATION_EXTERNAL,
                                     STID_FEED_CONFIG_SAMPLED_TYPE2,
                                     &feedConfig,
                                     &i->packetfeedhandle)) != NTCI_ERRCODE_SUCCESS) {
    DEBUG_CMD(Debug_Message("Failed to create a packet feed (%i)\n", result)); //stderr
    NTCI_CloseCard(i->napatechhandle);
559
    return -1;
560 561
  }

's avatar
committed
562 563 564 565 566
  if(channelsBitmask == 0) {
    PassFilter_t command;
    command.WriteHW = TRUE;
    sprintf(command.achFilterString, "Capture[Priority=0;Feed=0]=ALL");
	/* TODO - preclasification ^^^ */
567

's avatar
committed
568 569 570 571 572 573 574
    if((result = NTCI_PacketClassification(i->napatechhandle,
                                           STID_PASS_FILTER,
                                           &command)) != NTCI_ERRCODE_SUCCESS) {
      FilterError_t error;
      result = NTCI_PacketClassification(i->napatechhandle,
                                         STID_GET_FILTER_ERROR,
                                         &error);
575

's avatar
committed
576 577 578 579 580 581 582 583
      DEBUG_CMD(Debug_Message("%s\n",error.achFilterError1)); // stderr
      DEBUG_CMD(Debug_Message("%s\n",error.achFilterError2)); // stderr
      DEBUG_CMD(Debug_Message("%s\n",error.achFilterError3)); // stderr
      NTCI_CloseCard(i->napatechhandle);
      return -1;
    }
  }

584
  // i->packetfeedhandle = packetFeedHandle;
585

's avatar
committed
586 587 588 589
  if((result = NTCI_StartPacketFeed(i->napatechhandle, i->packetfeedhandle)) != NTCI_ERRCODE_SUCCESS) {
    DEBUG_CMD(Debug_Message("Error while starting packet feed (%i)\n", result)); // stderr
    NTCI_CloseCard(i->napatechhandle);
    return -1;
590
  }
's avatar
committed
591

592 593
  /* find the location of the feed buffer where new
   * data will be stored */
594
  if((result = NTCI_GetPacketFeedBuffers(i->napatechhandle,
595 596 597 598 599 600 601
                                         i->packetfeedhandle,
                                         STID_FEED_BUFFER_INFORMATION_TYPE1,
                                         &i->bufferInfo)) != NTCI_ERRCODE_SUCCESS) {
    DEBUG_CMD(Debug_Message("Unable to retrieve the location of the feed buffer.\n")); // stderr
    NTCI_CloseCard(i->napatechhandle);
    return -1;
  }
's avatar
committed
602

603 604 605 606 607 608 609

      //Start processing thread
      if (pthread_attr_init (&i->th_attr) != 0)
        {
          DEBUG_CMD(Debug_Message("ERROR: pthread_attr_init failed"));
          return DAGDRV_PTHR_ERR; // TODO
        }
610

611 612 613 614
      if (pthread_create(&i->th_proc, &i->th_attr, (void *) mapidrv_proc_loop, (void *) &(i->id)) != 0)
        {
          DEBUG_CMD(Debug_Message("ERROR: pthread_create failed"));
          return DAGDRV_PTHR_ERR; // TODO
's avatar
committed
615
        }
616
     }
617

618 619 620 621 622 623 624 625 626 627 628 629 630 631 632 633 634 635 636 637 638 639 640 641 642 643 644 645
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_create_flow_; i->napatechhandle: %d; i->packetfeedhandle: %d", i->napatechhandle, i->packetfeedhandle));

  return   mapid_add_flow(&i->mapidlib,fd,&i->hwinfo,NULL);
}

int
mapidrv_connect (int devid,int fd)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_connect"));

  int ret;
  napatech_instance_t *i=flist_get(devlist,devid);
  if(i == NULL)
  	return -1;

  ret=mapid_connect(&i->mapidlib,fd);

  if(i->hwinfo.offline==4) {
    if (pthread_attr_init (&i->th_attr) != 0)
      {
		DEBUG_CMD(Debug_Message("ERROR: pthread_attr_init failed"));
		return NICDRV_PTHR_ERR;
      }
    if (pthread_create
		(&i->th_proc, &i->th_attr, (void *) mapidrv_offline_proc_loop, (void *) &(i->id)) != 0)
      {
		DEBUG_CMD(Debug_Message("ERROR: pthread_create failed"));
		return NICDRV_PTHR_ERR;
646
      }
647 648 649 650
  }
  return ret;
}

651
int
652 653 654 655 656
mapidrv_start_offline_device( int devid)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_start_offline_device"));

  napatech_instance_t *i = flist_get(devlist,devid);
657

658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673 674
  /* TODO */

  return 0;
}


int
mapidrv_close_flow (int devid,int fd)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_close_flow"));

  napatech_instance_t *i=flist_get(devlist,devid);
  int rc = mapid_close_flow(&i->mapidlib,fd);

  return rc;
}

675
int
676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 718 719 720 721
mapidrv_load_library(MAPI_UNUSED int devid,char* lib)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_load_library"));

  return mapid_load_library(lib);
}

__attribute__ ((constructor))
     void init ()
{
  DEBUG_CMD(Debug_Message("napatechdrv: init"));

  devlist=malloc(sizeof(flist_t));
  flist_init(devlist);
  printf ("DAG driver loaded [%s:%d]\n",__FILE__,__LINE__);
}

__attribute__ ((destructor))
     void fini ()
{
  DEBUG_CMD(Debug_Message("napatechdrv: fini"));

  free(devlist);
  printf ("NAPATECH driver unloaded [%s:%d]\n",__FILE__,__LINE__);
}

int
mapidrv_stats (int devid, char **devtype, struct mapi_stat *stats)
{
  DEBUG_CMD(Debug_Message("napatechdrv: mapidrv_stats"));

  napatech_instance_t *i=flist_get(devlist,devid);

  *devtype=MAPI_DEVICE_NAPATECH;

  if (i!=NULL)
  {
	stats->ps_recv=i->hwinfo.pkts + i->hwinfo.pkt_drop;
	stats->ps_drop=i->hwinfo.pkt_drop;
	stats->ps_ifdrop=0;
	return 0;
  }

  return MAPI_STATS_ERROR;
}

722
/* vim: set shiftwidth=2 tabstop=2 smarttab expandtab : */