int wl_host_event(dhd_pub_t *dhd_pub, int *ifidx, void *pktdata, wl_event_msg_t *event, void **data_ptr) { /* check whether packet is a BRCM event pkt */ bcm_event_t *pvt_data = (bcm_event_t *)pktdata; char *event_data; uint32 type, status, reason, datalen; uint16 flags; int evlen; if (bcmp(BRCM_OUI, &pvt_data->bcm_hdr.oui[0], DOT11_OUI_LEN)) { DHD_ERROR(("%s: mismatched OUI, bailing\n", __FUNCTION__)); return (BCME_ERROR); } /* BRCM event pkt may be unaligned - use xxx_ua to load user_subtype. */ if (ntoh16_ua((void *)&pvt_data->bcm_hdr.usr_subtype) != BCMILCP_BCM_SUBTYPE_EVENT) { DHD_ERROR(("%s: mismatched subtype, bailing\n", __FUNCTION__)); return (BCME_ERROR); } *data_ptr = &pvt_data[1]; event_data = *data_ptr; /* memcpy since BRCM event pkt may be unaligned. */ memcpy(event, &pvt_data->event, sizeof(wl_event_msg_t)); type = ntoh32_ua((void *)&event->event_type); flags = ntoh16_ua((void *)&event->flags); status = ntoh32_ua((void *)&event->status); reason = ntoh32_ua((void *)&event->reason); datalen = ntoh32_ua((void *)&event->datalen); evlen = datalen + sizeof(bcm_event_t); switch (type) { case WLC_E_IF: { dhd_if_event_t *ifevent = (dhd_if_event_t *)event_data; if (ifevent->ifidx > 0 && ifevent->ifidx < DHD_MAX_IFS) { if (ifevent->action == WLC_E_IF_ADD) dhd_add_if(dhd_pub->info, ifevent->ifidx, NULL, event->ifname, event->addr.octet, ifevent->flags, ifevent->bssidx); else dhd_del_if(dhd_pub->info, ifevent->ifidx); } else { DHD_ERROR(("%s: Invalid ifidx %d for %s\n", __FUNCTION__, ifevent->ifidx, event->ifname)); } } /* send up the if event: btamp user needs it */ *ifidx = dhd_ifname2idx(dhd_pub->info, event->ifname); /* push up to external supp/auth */ dhd_event(dhd_pub->info, (char *)pvt_data, evlen, *ifidx); break; #ifdef WLMEDIA_HTSF case WLC_E_HTSFSYNC: htsf_update(dhd_pub->info, event_data); break; #endif /* WLMEDIA_HTSF */ case WLC_E_NDIS_LINK: { uint32 temp = hton32(WLC_E_LINK); memcpy((void *)(&pvt_data->event.event_type), &temp, sizeof(pvt_data->event.event_type)); } /* These are what external supplicant/authenticator wants */ /* fall through */ case WLC_E_LINK: case WLC_E_DEAUTH: case WLC_E_DEAUTH_IND: case WLC_E_DISASSOC: case WLC_E_DISASSOC_IND: DHD_EVENT(("%s: Link event %d, flags %x, status %x\n", __FUNCTION__, type, flags, status)); /* fall through */ default: *ifidx = dhd_ifname2idx(dhd_pub->info, event->ifname); /* push up to external supp/auth */ dhd_event(dhd_pub->info, (char *)pvt_data, evlen, *ifidx); DHD_TRACE(("%s: MAC event %d, flags %x, status %x\n", __FUNCTION__, type, flags, status)); /* put it back to WLC_E_NDIS_LINK */ if (type == WLC_E_NDIS_LINK) { uint32 temp; temp = ntoh32_ua((void *)&event->event_type); DHD_TRACE(("Converted to WLC_E_LINK type %d\n", temp)); temp = ntoh32(WLC_E_NDIS_LINK); memcpy((void *)(&pvt_data->event.event_type), &temp, sizeof(pvt_data->event.event_type)); } break; } #ifdef SHOW_EVENTS wl_show_host_event(event, (void *)event_data); #endif /* SHOW_EVENTS */ return (BCME_OK); }
int wl_host_event(struct dhd_info *dhd, int *ifidx, void *pktdata, wl_event_msg_t *event, void **data_ptr) { /* check whether packet is a BRCM event pkt */ bcm_event_t *pvt_data = (bcm_event_t *)pktdata; char *event_data; uint32 type, status; uint16 flags; int evlen; if (bcmp(BRCM_OUI, &pvt_data->bcm_hdr.oui[0], DOT11_OUI_LEN)) return (BCME_ERROR); /* BRCM event pkt may be unaligned - use xxx_ua to load user_subtype. */ if (ntoh16_ua((void *)&pvt_data->bcm_hdr.usr_subtype) != BCMILCP_BCM_SUBTYPE_EVENT) return (BCME_ERROR); *data_ptr = &pvt_data[1]; event_data = *data_ptr; /* memcpy since BRCM event pkt may be unaligned. */ memcpy(event, &pvt_data->event, sizeof(wl_event_msg_t)); type = ntoh32_ua((void *)&event->event_type); flags = ntoh16_ua((void *)&event->flags); status = ntoh32_ua((void *)&event->status); evlen = ntoh32_ua((void *)&event->datalen) + sizeof(bcm_event_t); switch (type) { case WLC_E_IF: { dhd_if_event_t *ifevent = (dhd_if_event_t *)event_data; if (ifevent->ifidx > 0 && ifevent->ifidx < DHD_MAX_IFS) { if (ifevent->action == WLC_E_IF_ADD) dhd_add_if(dhd, ifevent->ifidx, NULL, event->ifname, pvt_data->eth.ether_dhost, ifevent->flags, ifevent->bssidx); else dhd_del_if(dhd, ifevent->ifidx); } else { DHD_ERROR(("%s: Invalid ifidx %d for %s\n", __FUNCTION__, ifevent->ifidx, event->ifname)); } } /* send up the if event: btamp user needs it */ *ifidx = dhd_ifname2idx(dhd, event->ifname); /* push up to external supp/auth */ dhd_event(dhd, (char *)pvt_data, evlen, *ifidx); break; /* fall through */ /* These are what external supplicant/authenticator wants */ case WLC_E_LINK: case WLC_E_ASSOC_IND: case WLC_E_REASSOC_IND: case WLC_E_DISASSOC_IND: case WLC_E_MIC_ERROR: default: /* Fall through: this should get _everything_ */ *ifidx = dhd_ifname2idx(dhd, event->ifname); /* push up to external supp/auth */ dhd_event(dhd, (char *)pvt_data, evlen, *ifidx); DHD_TRACE(("%s: MAC event %d, flags %x, status %x\n", __FUNCTION__, type, flags, status)); /* put it back to WLC_E_NDIS_LINK */ if (type == WLC_E_NDIS_LINK) { uint32 temp; temp = ntoh32_ua((void *)&event->event_type); DHD_TRACE(("Converted to WLC_E_LINK type %d\n", temp)); temp = ntoh32(WLC_E_NDIS_LINK); memcpy((void *)(&pvt_data->event.event_type), &temp, sizeof(pvt_data->event.event_type)); } break; } #ifdef SHOW_EVENTS wl_show_host_event(event, event_data); #endif /* SHOW_EVENTS */ return (BCME_OK); }
int wl_host_event(struct dhd_info *dhd, int *ifidx, void *pktdata, wl_event_msg_t *event, void **data_ptr) { bcm_event_t *pvt_data = (bcm_event_t *)pktdata; char *event_data; uint32 type, status; uint16 flags; int evlen; if (bcmp(BRCM_OUI, &pvt_data->bcm_hdr.oui[0], DOT11_OUI_LEN)) return (BCME_ERROR); if (ntoh16_ua((void *)&pvt_data->bcm_hdr.usr_subtype) != BCMILCP_BCM_SUBTYPE_EVENT) return (BCME_ERROR); *data_ptr = &pvt_data[1]; event_data = *data_ptr; memcpy(event, &pvt_data->event, sizeof(wl_event_msg_t)); type = ntoh32_ua((void *)&event->event_type); flags = ntoh16_ua((void *)&event->flags); status = ntoh32_ua((void *)&event->status); evlen = ntoh32_ua((void *)&event->datalen) + sizeof(bcm_event_t); switch (type) { case WLC_E_IF: { dhd_if_event_t *ifevent = (dhd_if_event_t *)event_data; if (ifevent->ifidx > 0 && ifevent->ifidx < DHD_MAX_IFS) { if (ifevent->action == WLC_E_IF_ADD) dhd_add_if(dhd, ifevent->ifidx, NULL, event->ifname, pvt_data->eth.ether_dhost, ifevent->flags, ifevent->bssidx); else dhd_del_if(dhd, ifevent->ifidx); } else { DHD_ERROR(("%s: Invalid ifidx %d for %s\n", __FUNCTION__, ifevent->ifidx, event->ifname)); } } *ifidx = dhd_ifname2idx(dhd, event->ifname); dhd_event(dhd, (char *)pvt_data, evlen, *ifidx); break; case WLC_E_LINK: case WLC_E_ASSOC_IND: case WLC_E_REASSOC_IND: case WLC_E_DISASSOC_IND: case WLC_E_MIC_ERROR: default: *ifidx = dhd_ifname2idx(dhd, event->ifname); dhd_event(dhd, (char *)pvt_data, evlen, *ifidx); DHD_TRACE(("%s: MAC event %d, flags %x, status %x\n", __FUNCTION__, type, flags, status)); if (type == WLC_E_NDIS_LINK) { uint32 temp; temp = ntoh32_ua((void *)&event->event_type); DHD_TRACE(("Converted to WLC_E_LINK type %d\n", temp)); temp = ntoh32(WLC_E_NDIS_LINK); memcpy((void *)(&pvt_data->event.event_type), &temp, sizeof(pvt_data->event.event_type)); } break; } #ifdef SHOW_EVENTS wl_show_host_event(event, event_data); #endif return (BCME_OK); }