new funtion to send CAPWAP packets

This commit is contained in:
7u83 2022-09-18 08:04:49 +02:00
parent b292b88d49
commit ae686f4634
6 changed files with 135 additions and 11 deletions

View File

@ -53,10 +53,10 @@ int conn_send_msg(struct cw_Conn * conn, uint8_t *rawmsg)
/* Zyxel doesn't count msg element length from
behind seqnum */
// Zyxel doesn't count msg element length from
// behind seqnum * /
// if (conn->capwap_mode == CW_MODE_ZYXEL){
/* // XXX val-=3; */
// * // XXX val-=3; * /
// }
@ -75,7 +75,7 @@ mtu = 9440;
int offset = cw_get_hdr_msg_offset(rawmsg);
return cw_send_msg(conn,rawmsg+offset);
/*
if (packetlen>mtu){
cw_set_hdr_flags(ptr,CAPWAP_FLAG_HDR_F,1);
cw_set_dword(ptr+4, conn->fragid<<16 | fragoffset<<3 );
@ -103,7 +103,7 @@ mtu = 9440;
if (conn->write(conn,ptr,mtu)<0)
return -1;
/* // XXX Fragmentation stuff.. */
/ * // XXX Fragmentation stuff.. * /
ptr +=mtu-hlen;
fragoffset+=(mtu-hlen)/8;
@ -122,6 +122,6 @@ mtu = 9440;
cw_dbg_pkt(DBG_PKT_OUT,conn,ptr,packetlen,(struct sockaddr*)&conn->addr);
return conn->write(conn,ptr,packetlen-0);
return conn->write(conn,ptr,packetlen-0); */
}

View File

@ -219,7 +219,7 @@ void cw_set_hdr_rid(uint8_t * th, int rid);
* @see #cw_is_request
*/
#define cw_is_response(msg_id) (!is_response(msg_id))
#define cw_is_response(msg_id) (!cw_is_resquest(msg_id))
uint8_t *cw_get_hdr_msg_elems_ptr(uint8_t * m);

View File

@ -136,7 +136,7 @@ int cw_set_hdr_rmac(uint8_t * th, bstr_t rmac)
hlen++;
}
cw_set_hdr_hlen(th, hlen);
return 1;
return rmac_len;
}

View File

@ -679,7 +679,7 @@ void cw_dbg_dot11_elems(const uint8_t *src,int len)
uint8_t id,l;
int p;
char str[1024];
for(p=0; p<len; p+=l+2){
if (len-p<3){
cw_dbg(DBG_X,"Error in dot11 element");
@ -707,7 +707,9 @@ void cw_dbg_dot11_frame(uint8_t * frame,int len)
cw_dbg_dot11_elems(frame+28,len-28);
break;
case DOT11_ASSOC_RESP:
cw_dbg_dot11_elems((frame),len-6);
cw_dbg_dot11_elems((frame+DOT11_BODY_POS+DOT11_ASSOC_RESP_BODY_LEN),
len-DOT11_BODY_POS-DOT11_ASSOC_RESP_BODY_LEN);
break;
}

View File

@ -271,12 +271,15 @@ extern struct cw_StrListElem dot11_names[];
#define dot11_get_seq(frame) dot11_get_word((frame)+22)
#define dot11_get_body(frame) ((frame)+24)
#define DOT11_BODY_POS 24
#define dot11_set_duration(frame,d) dot11_set_word(frame+2,d)
#define dot11_set_seq(frame,s) dot11_set_word((frame)+22,s)
#define DOT11_ASSOC_RESP_BODY_LEN 6
#define dot11_assoc_req_get_cap(frame) \
dot11_get_word((frame)+24)
#define dot11_assoc_req_get_listen_interval(frame) \

View File

@ -90,10 +90,129 @@ int conn_send_data_msg(struct cw_Conn * conn, uint8_t *rawmsg,int len)
return 0;
}
#define MAX_MTU 9500
/**
* Initialize a capwap header
*
* @param buf Buffer to be initialized
* @param wbid Wireless Binding ID
* @param rid Radio ID
* @param rmac Radio MAC, NULL if not present
* @param wd Wireless Data, NULL if not present
*
* @return Length of the header that was initialized
*/
int
cw_init_capwap_packet( uint8_t * buf, int wbid ,int rid, bstr_t rmac, bstr_t wd)
{
int len,hlen;
/* header len */
len = 8;
/* zero the first 8 bytes */
cw_set_dword(buf + 0, 0);
cw_set_dword(buf + 4, 0);
/* capwap version/unencrypted */
#if CAPWAP_VERSION != 0
cw_set_hdr_preamble(buf, CAPWAP_VERSION << 4 | 0);
#endif
/* set wbid and rid */
cw_set_hdr_wbid(buf, wbid);
cw_set_hdr_rid(buf, rid);
/* add rmac if present */
if (rmac != NULL){
int rmac_len = bstr_len(rmac);
memcpy(cw_get_hdr_rmac(buf), rmac, rmac_len + 1);
cw_set_hdr_flags(buf, CAPWAP_FLAG_HDR_M, 1);
len+=rmac_len+1;
}
/* Add wireless data if present */
if (wd!=NULL){
int wd_len = bstr_len(wd);
memcpy(buf+len, wd, wd_len + 1);
cw_set_hdr_flags(buf, CAPWAP_FLAG_HDR_M, 1);
len+=wd_len;
}
hlen = len / 4;
if (len % 4 != 0) {
hlen++;
}
cw_set_hdr_hlen(buf, hlen);
return hlen*4;
}
int cw_send_capwap_packet(struct cw_Conn * conn, uint8_t * buf, int hlen, uint8_t * data, int len)
{
int fragoffset,mtu;
/* get mtu and align it to 8 */
mtu = conn->mtu;
mtu &= ~3;
fragoffset = 0;
while (len + hlen > mtu){
memcpy(buf+hlen,data+(fragoffset*8),mtu-hlen);
len -= (mtu - hlen);
cw_set_hdr_flags(buf,CAPWAP_FLAG_HDR_F,1);
cw_set_dword(buf+4, conn->fragid<<16 | fragoffset<<3 );
cw_dbg_pkt(DBG_PKT_OUT,conn,buf,mtu,(struct sockaddr*)&conn->addr);
if (conn->write(conn,buf,mtu)<0)
return -1;
fragoffset+=(mtu-hlen)/8;
cw_set_hdr_flags(buf,CAPWAP_FLAG_HDR_M,0);
cw_set_hdr_flags(buf,CAPWAP_FLAG_HDR_W,0);
hlen = 8;
cw_set_hdr_hlen(buf,hlen/4);
}
if (fragoffset)
cw_set_hdr_flags(buf,CAPWAP_FLAG_HDR_F | CAPWAP_FLAG_HDR_L,1);
else
cw_set_hdr_flags(buf,CAPWAP_FLAG_HDR_F,0);
memcpy(buf+hlen,data+(fragoffset*8),mtu-hlen);
cw_set_dword(buf+4, conn->fragid<<16 | fragoffset<<3 );
cw_dbg_pkt(DBG_PKT_OUT,conn,buf,len+hlen,(struct sockaddr*)&conn->addr);
return conn->write(conn,buf,len + hlen);
}
int
cw_send_msg( struct cw_Conn * conn, uint8_t *msg)
{
uint8_t buf[MAX_MTU];
int hlen,msglen;
hlen = cw_init_capwap_packet(buf,1,0,NULL,NULL);
msglen = cw_get_msg_elems_len(msg) + 8;
return cw_send_capwap_packet(conn,buf,hlen,msg,msglen);
}
int
cw_send_msg_old( struct cw_Conn * conn, uint8_t *msg)
{
uint8_t buf[MAX_MTU];
int fragoffset,hlen,mtu;