int static do_save(mbag_t itemstore, struct conn *conn, struct cw_action_in *a, uint8_t * data, int len, struct sockaddr *from) { if (a->itemtype == MBAG_BYTE) { mbag_set_byte(itemstore, a->item_id, *data); return 1; } if (a->itemtype == MBAG_WORD) { mbag_set_word(itemstore, a->item_id, cw_get_word(data)); return 1; } if (a->itemtype == MBAG_DWORD) { mbag_set_dword(itemstore, a->item_id, cw_get_dword(data)); return 1; } if (a->itemtype == MBAG_STR) { mbag_set_strn(itemstore, a->item_id, (char *) data, len); return 1; } if (a->itemtype == MBAG_BSTR) { mbag_set_bstrn(itemstore, a->item_id, data, len); return 1; } if (a->itemtype == MBAG_BSTR16) { mbag_set_bstr16n(itemstore, a->item_id, data, len); return 1; } /* if (a->itemtype == MBAG_DATA) { mbag_set_data(itemstore, a->item_id, data, len); return 1; } */ if (a->itemtype == MBAG_VENDORSTR) { mbag_set_bstrv(itemstore, a->item_id, cw_get_dword(data), data + 4, len - 4); return 1; } cw_log(LOG_ERR, "Can't handle item type %d in definition for incomming msg %d (%s) - %d, cw_in_generic.", a->itemtype, a->msg_id, cw_strmsg(a->msg_id), a->elem_id); return 0; }
int cw_in_cisco_image_identifier(struct conn *conn,struct cw_action_in * a,uint8_t *data,int len,struct sockaddr *from) { if (len<a->min_len) { cw_dbg(DBG_ELEM_ERR,"Message element too short, %d < %d", len,a->min_len); return 0; } uint32_t vendor_id = cw_get_dword(data); int dstart; switch (vendor_id) { case CW_VENDOR_ID_ZYXEL: case CW_VENDOR_ID_CISCO: case CW_VENDOR_ID_FSF: case 0: dstart=4; len-=4; break; default: vendor_id=CW_VENDOR_ID_CISCO; dstart=0; } // mbag_set(conn->remote,a->item_id,a->itemtype,data+dstart,len); mbag_set_bstrv(conn->incomming,a->item_id,vendor_id,data+dstart,len); return 1; }
static int detect(struct conn *conn, const uint8_t * rawmsg, int rawlen, int elems_len, struct sockaddr *from, int mode) { int offset = cw_get_hdr_msg_offset(rawmsg); const uint8_t *msg_ptr = rawmsg + offset; const uint8_t *elems_ptr = cw_get_msg_elems_ptr(msg_ptr); const uint8_t *elem; /* To detect a Fortinet AP we look for any vendor * specific payload Fortinet identifier */ cw_foreach_elem(elem, elems_ptr, elems_len) { int id = cw_get_elem_id(elem); if (id == CW_ELEM_VENDOR_SPECIFIC_PAYLOAD) { uint32_t vendor_id = cw_get_dword(cw_get_elem_data(elem)); if (vendor_id == CW_VENDOR_ID_FORTINET) { // conn->actions = &actions; if (mode == MOD_MODE_CAPWAP) { cw_dbg(DBG_MOD, "Fortinet capwap detected: yes"); } else { cw_dbg(DBG_MOD, "Fortinet bindings detected: yes"); } return 1; } } }
int cw_cisco_get_wlan_(mbag_t wlan, uint8_t *data, int len) { mbag_set_word(wlan,"enc_capab", cw_get_word(data+1)); int wlan_id=cw_get_word(data+3); mbag_set_word(wlan,"wlan_id",wlan_id); mbag_set_dword(wlan,"enc_policy",cw_get_dword(data+5)); mbag_set_bstr16n(wlan,"key",data+9,32); mbag_set_byte(wlan,"key_index",cw_get_byte(data+41)); mbag_set_byte(wlan,"key_shared",cw_get_byte(data+42)); mbag_set_byte(wlan,"wpa_len",cw_get_byte(data+43)); mbag_set_bstr16n(wlan,"wpa_data",data+44,32); mbag_set_byte(wlan,"rsn_len",cw_get_byte(data+76)); mbag_set_bstr16n(wlan,"rsn_data",data+77,64); mbag_set_bstr16n(wlan,"reserved",data+141,49); mbag_set_byte(wlan,"wme_len",cw_get_byte(data+190)); mbag_set_bstr16n(wlan,"wme_data",data+191,32); mbag_set_byte(wlan,"dot11e_len",cw_get_byte(data+223)); mbag_set_bstr16n(wlan,"dot11e_data",data+224,32); mbag_set_byte(wlan,"qos",cw_get_byte(data+256)); // mbag_set_byte(wlan,"ssid_broadcast",cw_get_byte(data+257)); mbag_set_byte(wlan,"ssid_broadcast",cw_get_byte(data+435)); mbag_set_byte(wlan,"aironet_ie",cw_get_byte(data+436)); mbag_set_bstr16n(wlan,"reserved2",data+258,40); mbag_set_byte(wlan,"dtim_period",cw_get_byte(data+554)); mbag_set_bstr16n(wlan,"wlan_name",data+558,32); mbag_set_byte(wlan,"allow_aaa_override",cw_get_byte(data+591)); mbag_set_byte(wlan,"max_clients",cw_get_byte(data+593)); mbag_set_bstr16n(wlan,"ssid",data+622,len-622); return 0; }
/** * Parse a WTP Board Data messag element and put results to itemstore. */ int cw_in_wtp_board_data(struct conn *conn, struct cw_action_in *a, uint8_t * data, int len, struct sockaddr *from) { if (len < 4) { cw_dbg(DBG_ELEM_ERR, "Discarding WTP_BOARD_DATA msgelem, wrong size, type=%d, len=%d", a->elem_id, len); return 0; } mbag_t itemstore = conn->incomming; mbag_set_dword(itemstore, CW_ITEM_WTP_BOARD_VENDOR, cw_get_dword(data)); readsubelems_wtp_board_data(itemstore, data + 4, len - 4); return 1; }
static int cw_read_wtp_descriptor_versions(mbag_t mbag, uint8_t * data, int len, int silent) { int i = 0; while (i<len) { if (i + 8 > len) { if (!silent) cw_dbg(DBG_ELEM_ERR, "WTP descriptor subelement to long, length=%d>%d", i + 8, len); return 0; } uint32_t vendor_id = cw_get_dword(data + i); uint32_t val = cw_get_dword(data + i + 4); int subtype = (val >> 16) & 0xffff; int sublen = val & 0xffff; i += 8; if (sublen + i > len) { if (!silent) cw_dbg(DBG_ELEM_ERR, "WTP Descriptor sub-element too long, length = %d", sublen); return 0; } if (!silent) { char *dmp; char *dmpmem = NULL; if (cw_dbg_is_level(DBG_SUBELEM_DMP)) { dmpmem = cw_dbg_mkdmp(data + i, sublen); dmp = dmpmem; } else dmp = ""; cw_dbg(DBG_SUBELEM, "WTP Descriptor subtype=%d,len=%d%s", subtype, sublen, dmp); if (dmpmem) free(dmpmem); } switch (subtype) { case CW_SUBELEM_WTP_HARDWARE_VERSION: /* mbag_set_dword(mbag, CW_ITEM_WTP_HARDWARE_VENDOR, vendor_id); mbag_set_bstrn(mbag, CW_ITEM_WTP_HARDWARE_VERSION, data + i, sublen); */ mbag_set_vendorstr(mbag, CW_ITEM_WTP_HARDWARE_VERSION, vendor_id, data + i, sublen); break; case CW_SUBELEM_WTP_SOFTWARE_VERSION: mbag_set_vendorstr(mbag, CW_ITEM_WTP_SOFTWARE_VERSION, vendor_id, data + i, sublen); /* mbag_set_dword(mbag, CW_ITEM_WTP_SOFTWARE_VENDOR, vendor_id); mbag_set_bstrn(mbag, CW_ITEM_WTP_SOFTWARE_VERSION, data + i, sublen); */ break; case CW_SUBELEM_WTP_BOOTLOADER_VERSION: mbag_set_vendorstr(mbag, CW_ITEM_WTP_BOOTLOADER_VERSION, vendor_id, data + i, sublen); /* mbag_set_dword(mbag, CW_ITEM_WTP_BOOTLOADER_VENDOR, vendor_id); mbag_set_bstrn(mbag, CW_ITEM_WTP_BOOTLOADER_VERSION, data + i, sublen); */ break; default: if (!silent) cw_dbg(DBG_ELEM_ERR, "Unknown WTP descriptor subelement, type = %d", subtype); break; } i += sublen; } //while (i < len); return 1; }
int cw_read_descriptor_subelems(mavl_t cfg, const char * parent_key, uint8_t * data, int len, struct cw_DescriptorSubelemDef *elems) { uint32_t vendor_id; int sublen,subtype; int errors = 0; int success = 0; int sub = 0; while (sub < len) { int i; if (len - sub < 8) { return 0; } vendor_id = cw_get_dword(data + sub); sublen = cw_get_word(data + sub + 6); subtype = cw_get_word(data + sub + 4); /* search sub-element */ for (i = 0; elems[i].maxlen; i++) { if (elems[i].type == subtype /* && elems[i].vendor_id==vendor_id*/) break; } if (!elems[i].maxlen) { cw_dbg_version_subelem(DBG_ELEM_ERR, "Can't handle sub-elem, vendor or type unknown", subtype, vendor_id, data+sub+8, sublen); errors++; } else { int l = sublen; char dbgstr[1048]; char key[1024]; if (elems[i].maxlen < sublen) { cw_dbg(DBG_ELEM_ERR, "SubType %d Too long (truncating), len = %d,max. len=%d", subtype, sublen, elems[i].maxlen); l = elems[i].maxlen; } /* vendor */ sprintf(key,"%s/%s/%s",parent_key,elems[i].key,CW_SKEY_VENDOR); cw_ktv_add(cfg,key,CW_TYPE_DWORD,NULL,data + sub,4); /* version */ sprintf(key,"%s/%s/%s",parent_key,elems[i].key,CW_SKEY_VERSION); cw_ktv_add(cfg,key,CW_TYPE_BSTR16,NULL,data+sub+8,l); sprintf(dbgstr, "%s", key); cw_dbg_version_subelem(DBG_SUBELEM, dbgstr, subtype, vendor_id, data+sub+8,l); success++; } if (sub + sublen > len) return -1; sub += sublen + 8; } return success; }
int static do_save(mbag_t itemstore, struct conn *conn, struct cw_action_in *a, uint8_t * data, int len, struct sockaddr *from) { const cw_itemdef_t * idef = cw_itemdef_get(conn->actions->items,a->item_id,CW_ITEM_NONE); if (!idef) { cw_log(LOG_ERR,"No itemdef found for %s",a->item_id); return 0; } if (idef->type == MBAG_BYTE) { mbag_set_byte(itemstore, a->item_id, *data); return 1; } if (idef->type == MBAG_WORD) { mbag_set_word(itemstore, a->item_id, cw_get_word(data)); return 1; } if (idef->type == MBAG_DWORD) { mbag_set_dword(itemstore, a->item_id, cw_get_dword(data)); return 1; } if (idef->type == MBAG_STR) { mbag_set_strn(itemstore, a->item_id, (char *) data, len); return 1; } if (idef->type == MBAG_BSTR) { mbag_set_bstrn(itemstore, a->item_id, data, len); return 1; } if (idef->type == MBAG_BSTR16) { mbag_set_bstr16n(itemstore, a->item_id, data, len); return 1; } /* if (idef->type == MBAG_DATA) { mbag_set_data(itemstore, a->item_id, data, len); return 1; } */ if (idef->type == MBAG_VENDORSTR) { mbag_set_bstrv(itemstore, a->item_id, cw_get_dword(data), data + 4, len - 4); return 1; } // printf("Idef: %s\n",idef->type->name); cw_log(LOG_ERR, "Can't handle item type %d in definition for incomming msg %d (%s) - %d, cw_in_generic.", idef->type, a->msg_id, cw_strmsg(a->msg_id), a->elem_id); return 0; }
static struct cw_KTV *get(struct cw_KTV * data, const uint8_t * src, int len) { data->type = &cw_type_dword; data->val.dword = cw_get_dword(src); return data; }