⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 prism2.c

📁 linux下从网卡远程启动
💻 C
📖 第 1 页 / 共 3 页
字号:
  /* Get RX FID */    rxfid = hfa384x_getreg(hw, HFA384x_RXFID);  /* Get the descriptor (including headers) */  result = hfa384x_copy_from_bap(hw, rxfid, 0, &rxdesc, sizeof(rxdesc));  if ( result ) {    return 0; /* fail */  }  /* Byte order convert once up front. */  rxdesc.status = hfa384x2host_16(rxdesc.status);  rxdesc.time = hfa384x2host_32(rxdesc.time);  rxdesc.data_len = hfa384x2host_16(rxdesc.data_len);  /* Fill in nic->packetlen */  nic->packetlen = rxdesc.data_len;  if ( nic->packetlen > 0 ) {    /* Fill in nic->packet */    /*     * NOTE: Packets as received have an 8-byte header (LLC+SNAP(?)) terminating with the packet type.     * Etherboot expects a 14-byte header terminating with the packet type (it ignores the rest of the     * header), so we use a quick hack to achieve this.     */    result = hfa384x_copy_from_bap(hw, rxfid, HFA384x_RX_DATA_OFF,				   nic->packet + ETH_HLEN - sizeof(wlan_80211hdr_t), nic->packetlen);    if ( result ) {      return 0; /* fail */    }  }  return 1; /* Packet successfully received */}/**************************************************************************TRANSMIT - Transmit a frame***************************************************************************/static void prism2_transmit(			    struct nic *nic,			    const char *d,			/* Destination */			    unsigned int t,			/* Type */			    unsigned int s,			/* size */			    const char *p)			/* Packet */{  hfa384x_t *hw = &hw_global;  hfa384x_tx_frame_t txdesc;  wlan_80211hdr_t p80211hdr = { wlan_llc_snap, {{0,0,0},0} };  UINT16 fid;  UINT16 status;  int result;  // Request FID allocation  result = hfa384x_docmd_wait(hw, HFA384x_CMD_CMDCODE_SET(HFA384x_CMDCODE_ALLOC), HFA384x_DRVR_TXBUF_MAX, 0, 0);  if (result != 0) {    printf("hfa384x: Tx FID allocate command failed: Aborting transmit..\n");    return;  }  if ( !hfa384x_wait_for_event(hw, HFA384x_EVSTAT_ALLOC, HFA384x_EVACK_INFO, 10, 50, "Tx FID to be allocated\n" ) ) return;  fid = hfa384x_getreg(hw, HFA384x_ALLOCFID);  /* Build Tx frame structure */  memset(&txdesc, 0, sizeof(txdesc));  txdesc.tx_control = host2hfa384x_16( HFA384x_TX_MACPORT_SET(0) | HFA384x_TX_STRUCTYPE_SET(1) | 				       HFA384x_TX_TXEX_SET(1) | HFA384x_TX_TXOK_SET(1) );  txdesc.frame_control =  host2ieee16( WLAN_SET_FC_FTYPE(WLAN_FTYPE_DATA) |				       WLAN_SET_FC_FSTYPE(WLAN_FSTYPE_DATAONLY) |				       WLAN_SET_FC_TODS(1) );  memcpy(txdesc.address1, hw->bssid, WLAN_ADDR_LEN);  memcpy(txdesc.address2, nic->node_addr, WLAN_ADDR_LEN);  memcpy(txdesc.address3, d, WLAN_ADDR_LEN);  txdesc.data_len = host2hfa384x_16( sizeof(txdesc) + sizeof(p80211hdr) + s );  /* Set up SNAP header */  /* Let OUI default to RFC1042 (0x000000) */  p80211hdr.snap.type = htons(t);    /* Copy txdesc, p80211hdr and payload parts to FID */  result = hfa384x_copy_to_bap(hw, fid, 0, &txdesc, sizeof(txdesc));  if ( result ) return; /* fail */  result = hfa384x_copy_to_bap( hw, fid, sizeof(txdesc), &p80211hdr, sizeof(p80211hdr) );  if ( result ) return; /* fail */  result = hfa384x_copy_to_bap( hw, fid, sizeof(txdesc) + sizeof(p80211hdr), (UINT8*)p, s );  if ( result ) return; /* fail */  /* Issue Tx command */  result = hfa384x_docmd_wait(hw, HFA384x_CMD_CMDCODE_SET(HFA384x_CMDCODE_TX), fid, 0, 0);  if ( result != 0 ) {    printf("hfa384x: Transmit failed with result %#hx.\n", result);    return;  }    /* Wait for transmit completion (or exception) */  result = hfa384x_wait_for_event(hw, HFA384x_EVSTAT_TXEXC | HFA384x_EVSTAT_TX, HFA384x_EVACK_INFO,				  200, 500, "Tx to complete\n" );  if ( !result ) return; /* timeout failure */  if ( HFA384x_EVSTAT_ISTXEXC(result) ) {    fid = hfa384x_getreg(hw, HFA384x_TXCOMPLFID);    printf ( "Tx exception occurred with fid %#hx\n", fid );    result = hfa384x_copy_from_bap(hw, fid, 0, &status, sizeof(status));    if ( result ) return; /* fail */    printf("hfa384x: Tx error occurred (status %#hx):\n", status);    if ( HFA384x_TXSTATUS_ISACKERR(status) ) { printf(" ...acknowledgement error\n"); }    if ( HFA384x_TXSTATUS_ISFORMERR(status) ) { printf(" ...format error\n"); }    if ( HFA384x_TXSTATUS_ISDISCON(status) ) { printf(" ...disconnected error\n"); }    if ( HFA384x_TXSTATUS_ISAGEDERR(status) ) { printf(" ...AGED error\n"); }    if ( HFA384x_TXSTATUS_ISRETRYERR(status) ) { printf(" ...retry error\n"); }    return; /* fail */  }}/**************************************************************************DISABLE - Turn off ethernet interface***************************************************************************/static void prism2_disable(struct dev *dev __unused){  /* put the card in its initial state */}/**************************************************************************PROBE - Look for an adapter, this routine's visible to the outsideYou should omit the last argument struct pci_device * for a non-PCI NIC***************************************************************************/#if (WLAN_HOSTIF == WLAN_PLX)static int prism2_plx_probe(struct dev *dev, struct pci_device *p)#elif (WLAN_HOSTIF == WLAN_PCI)static int prism2_pci_probe(struct dev *dev, struct pci_device *p)#endif{  struct nic *nic = (struct nic *)dev;  hfa384x_t *hw = &hw_global;  int result;  UINT16 tmp16 = 0;  UINT16 infofid;  hfa384x_InfFrame_t inf;  char ssid[HFA384x_RID_CNFDESIREDSSID_LEN];  int info_count = 0;  /* Find and intialise PLX Prism2 card */#if (WLAN_HOSTIF == WLAN_PLX)  if ( ! prism2_find_plx ( hw, p ) ) return 0;#elif (WLAN_HOSTIF == WLAN_PCI)  if ( ! prism2_find_pci ( hw, p ) ) return 0;#endif  /* Initialize card */  result = hfa384x_docmd_wait(hw, HFA384x_CMDCODE_INIT, 0,0,0); /* Send initialize command */  if ( result ) printf ( "Initialize command returned %#hx\n", result );  hfa384x_setreg(hw, 0, HFA384x_INTEN); /* Disable interrupts */  hfa384x_setreg(hw, 0xffff, HFA384x_EVACK); /* Acknowledge any spurious events */  /* Retrieve MAC address (and fill out nic->node_addr) */  hfa384x_drvr_getconfig ( hw, HFA384x_RID_CNFOWNMACADDR, nic->node_addr, HFA384x_RID_CNFOWNMACADDR_LEN );  printf ( "MAC address %!\n", nic->node_addr );  /* Prepare card for autojoin */  /* This procedure is reverse-engineered from a register-level trace of the Linux driver's join process */  tmp16 = WLAN_DATA_MAXLEN; /* Set maximum data length */  result = hfa384x_drvr_setconfig16(hw, HFA384x_RID_CNFMAXDATALEN, &tmp16);  if ( result ) printf ( "Set Max Data Length command returned %#hx\n", result );  tmp16 = 0x000f; /* Set transmit rate(?) */  result = hfa384x_drvr_setconfig16(hw, HFA384x_RID_TXRATECNTL, &tmp16);  if ( result ) printf ( "Set Transmit Rate command returned %#hx\n", result );  tmp16 = HFA384x_CNFAUTHENTICATION_OPENSYSTEM; /* Set authentication type to OpenSystem */  result = hfa384x_drvr_setconfig16(hw, HFA384x_RID_CNFAUTHENTICATION, &tmp16);  if ( result ) printf ( "Set Authentication Type command returned %#hx\n", result );  /* Set SSID */  memset(ssid, 0, HFA384x_RID_CNFDESIREDSSID_LEN);  for ( tmp16=0; tmp16<sizeof(hardcoded_ssid); tmp16++ ) { ssid[2+tmp16] = hardcoded_ssid[tmp16]; }  ssid[0] = sizeof(hardcoded_ssid) - 1; /* Ignore terminating zero */  result = hfa384x_drvr_setconfig(hw, HFA384x_RID_CNFDESIREDSSID, ssid, HFA384x_RID_CNFDESIREDSSID_LEN); /* Set the SSID */  if ( result ) printf ( "Set SSID command returned %#hx\n", result );  tmp16 = 1; /* Set port type to ESS port */  result = hfa384x_drvr_setconfig16(hw, HFA384x_RID_CNFPORTTYPE, &tmp16);  if ( result ) printf ( "Set port type command returned %#hx\n", result );  /* Enable card */  result = hfa384x_docmd_wait(hw, HFA384x_CMD_CMDCODE_SET(HFA384x_CMDCODE_ENABLE) | HFA384x_CMD_MACPORT_SET(0), 0,0,0);  if ( result ) printf ( "Enable command returned %#hx\n", result );  do {    /* Increment info_count, abort if too many attempts.     * See comment next to definition of MAX_JOIN_INFO_COUNT for explanation.     */    info_count++;    if ( info_count > MAX_JOIN_INFO_COUNT ) {      printf ( "Too many failed attempts - aborting\n" );      return 0;    }    /* Wait for info frame to indicate link status */    if ( sizeof(hardcoded_ssid) == 1 ) {      /* Empty SSID => join to any SSID */      printf ( "Attempting to autojoin to any available access point (attempt %d)...", info_count );    } else {      printf ( "Attempting to autojoin to SSID %s (attempt %d)...", &ssid[2], info_count );    }        if ( !hfa384x_wait_for_event(hw, HFA384x_EVSTAT_INFO, 0, 1000, 2000, "Info event" ) ) return 0;    printf("done\n");    infofid = hfa384x_getreg(hw, HFA384x_INFOFID);    /* Retrieve the length */    result = hfa384x_copy_from_bap( hw, infofid, 0, &inf.framelen, sizeof(UINT16));    if ( result ) return 0; /* fail */    inf.framelen = hfa384x2host_16(inf.framelen);    /* Retrieve the rest */    result = hfa384x_copy_from_bap( hw, infofid, sizeof(UINT16),				    &(inf.infotype), inf.framelen * sizeof(UINT16));    if ( result ) return 0; /* fail */    if ( inf.infotype != HFA384x_IT_LINKSTATUS ) {      /* Not a Link Status info frame: die */      printf ( "Unexpected info frame type %#hx (not LinkStatus type)\n", inf.infotype );      return 0;    }    inf.info.linkstatus.linkstatus = hfa384x2host_16(inf.info.linkstatus.linkstatus);    if ( inf.info.linkstatus.linkstatus != HFA384x_LINK_CONNECTED ) {      /* Link not connected - retry */      printf ( "Link not connected (status %#hx)\n", inf.info.linkstatus.linkstatus );    }  } while ( inf.info.linkstatus.linkstatus != HFA384x_LINK_CONNECTED );      /* Retrieve BSSID and print Connected message */  result = hfa384x_drvr_getconfig(hw, HFA384x_RID_CURRENTBSSID, hw->bssid, WLAN_BSSID_LEN);  printf ( "Link connected (BSSID %! - MAC address %!)\n", hw->bssid, nic->node_addr );    /* point to NIC specific routines */  dev->disable  = prism2_disable;   nic->poll     = prism2_poll;  nic->transmit = prism2_transmit;  return 1;}#if (WLAN_HOSTIF == WLAN_PLX)/* * Find PLX card.  Prints out information strings from PCMCIA CIS as visual * confirmation of presence of card. * * Arguments: *	hw		device structure to be filled in *      p               PCI device structure * * Returns: *      1               Success */static int prism2_find_plx ( hfa384x_t *hw, struct pci_device *p ){  int found = 0;  uint32_t plx_lcr  = 0; /* PLX9052 Local Configuration Register Base (I/O) */  uint32_t attr_mem = 0; /* Prism2 Attribute Memory Base */  uint32_t iobase   = 0; /* Prism2 I/O Base */  unsigned char *cis_tpl  = NULL;  unsigned char *cis_string;    /* Obtain all memory and IO base addresses */  pcibios_read_config_dword( p->bus, p->devfn, PLX_LOCAL_CONFIG_REGISTER_BASE, &plx_lcr);  plx_lcr &= PCI_BASE_ADDRESS_IO_MASK;  pcibios_read_config_dword( p->bus, p->devfn, PRISM2_PLX_ATTR_MEM_BASE, &attr_mem);  pcibios_read_config_dword( p->bus, p->devfn, PRISM2_PLX_IO_BASE, &iobase);  iobase &= PCI_BASE_ADDRESS_IO_MASK;  /* Fill out hw structure */  hw->membase = attr_mem;  hw->iobase = iobase;  printf ( "PLX9052 has local config registers at %#hx\n", plx_lcr );  printf ( "Prism2 has attribute memory at %#x and I/O base at %#hx\n", attr_mem, iobase );  /* Search for CIS strings */  printf ( "Searching for PCMCIA card...\n" );  cis_tpl = bus_to_virt(attr_mem);  while ( *cis_tpl != CISTPL_END ) {    if ( *cis_tpl == CISTPL_VERS_1 ) {      /* CISTPL_VERS_1 contains some nice text strings */      printf ( "...found " );      found = 1;      cis_string = cis_tpl + CISTPL_VERS_1_STR_OFF;      while ( ! ( ( *cis_string == 0 ) && ( *(cis_string+CIS_STEP) == 0 ) ) ) {	printf ( "%c", *cis_string == 0 ? ' ' : *cis_string );	cis_string += CIS_STEP;      }      printf ( "\n" );    }    /* printf ( "CIS tuple type %#hhx, length %#hhx\n", *cis_tpl, *(cis_tpl+CISTPL_LEN_OFF) ); */    cis_tpl += CISTPL_HEADER_LEN + CIS_STEP * ( *(cis_tpl+CISTPL_LEN_OFF) );  }  if ( found == 0 ) {    printf ( "...nothing found\n" );  }  ((unsigned char *)bus_to_virt(attr_mem))[COR_OFFSET] = COR_VALUE; /* Write COR to enable PC card */  return found;}#endif /* WLAN_PLX */#if (WLAN_HOSTIF == WLAN_PCI)/* * Find PCI card. * * Arguments: *	hw		device structure to be filled in *      p               PCI device structure * * Returns: *      1               Success */static int prism2_find_pci ( hfa384x_t *hw, struct pci_device *p ){  uint32_t membase = 0; /* Prism2.5 Memory Base */  pcibios_read_config_dword( p->bus, p->devfn, PRISM2_PCI_MEM_BASE, &membase);  membase &= PCI_BASE_ADDRESS_MEM_MASK;  hw->membase = membase;  printf ( "Prism2.5 has registers at %#x\n", membase );  return 1;}#endif /* WLAN_PCI */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -