/* * WfaStaWaitStop(): This function sends the stop packet on behalf of the * station, the idea is to keep sending the Stop * till a stop is recd from the console,the functions * quits after stop threshold reaches. */ int WfaStaWaitStop(char psave,int sleep_period,int *state) { int myid=wmmps_info.ps_thread; PRINTF("\n Entering Sendwait"); wUSLEEP(sleep_period); if(!num_stops) { wfaSetDUTPwrMgmt(psave); wfaTGSetPrio(psSockfd, TG_WMM_AC_BE); } num_stops++; create_apts_msg(APTS_STOP, psTxMsg,wmmps_info.my_sta_id); wSENDTO(psSockfd, psTxMsg, msgsize, 0, (struct sockaddr *)&wmmps_info.psToAddr, sizeof(struct sockaddr)); mpx("STA msg",psTxMsg,64); wmm_thr[myid].stop_flag = 1; wPT_MUTEX_LOCK(&wmm_thr[myid].thr_stop_mutex); wPT_COND_SIGNAL(&wmm_thr[myid].thr_stop_cond); wPT_MUTEX_UNLOCK(&wmm_thr[myid].thr_stop_mutex); if(num_stops > MAX_STOPS) { DPRINT_ERR(WFA_ERR, "Too many stops sent\n"); gtgWmmPS = 0; if(psSockfd != -1) { wCLOSE(psSockfd); psSockfd = -1; } wSIGNAL(SIGALRM, SIG_IGN); } return 0; }
/* * wfaTGSendStart: instruct traffic generator to start sending based on a profile * input: cmd -- not used * response: inform controller for "running" * return: success or failed */ int wfaTGSendStart(int len, BYTE *parms, int *respLen, BYTE *respBuf) { int i=0, streamid=0; int numStreams = len/4; tgProfile_t *theProfile; tgStream_t *myStream = NULL; dutCmdResponse_t staSendResp; DPRINT_INFO(WFA_OUT, "Entering tgSendStart for %i streams ...\n", numStreams); for(i=0; i<numStreams; i++) { wMEMCPY(&streamid, parms+(4*i), 4); myStream = findStreamProfile(streamid); if(myStream == NULL) { staSendResp.status = STATUS_INVALID; wfaEncodeTLV(WFA_TRAFFIC_AGENT_SEND_RESP_TLV, 4, (BYTE *)&staSendResp, respBuf); *respLen = WFA_TLV_HDR_LEN + 4; return TRUE; } theProfile = &myStream->profile; if(theProfile == NULL) { staSendResp.status = STATUS_INVALID; wfaEncodeTLV(WFA_TRAFFIC_AGENT_SEND_RESP_TLV, 4, (BYTE *)&staSendResp, respBuf); *respLen = WFA_TLV_HDR_LEN + 4; return TRUE; } if(theProfile->direction != DIRECT_SEND) { staSendResp.status = STATUS_INVALID; wfaEncodeTLV(WFA_TRAFFIC_AGENT_SEND_RESP_TLV, 4, (BYTE *)&staSendResp, respBuf); *respLen = WFA_TLV_HDR_LEN + 4; return TRUE; } /* * need to reset the stats */ wMEMSET(&myStream->stats, 0, sizeof(tgStats_t)); // mark the stream active; myStream->state = WFA_STREAM_ACTIVE; switch(theProfile->profile) { case PROF_FILE_TX: case PROF_MCAST: case PROF_TRANSC: gtgTransac = streamid; gtgSend = streamid; case PROF_CALI_RTD: gtgCaliRTD = streamid; case PROF_IPTV: gtgSend = streamid; /* * singal the thread to Sending WMM traffic */ //if(usedThread < wmm_thr[usedThread].thr_flag = streamid; wPT_MUTEX_LOCK(&wmm_thr[usedThread].thr_flag_mutex); wPT_COND_SIGNAL(&wmm_thr[usedThread].thr_flag_cond); wPT_MUTEX_UNLOCK(&wmm_thr[usedThread].thr_flag_mutex); usedThread++; //wfaSetProcPriority(90); break; } } *respLen = 0; return TRUE; }
/* RecvStart: instruct traffic generator to start receiving * based on a profile * input: cmd -- not used * response: inform controller for "running" * return: success or failed */ int wfaTGRecvStart(int len, BYTE *parms, int *respLen, BYTE *respBuf) { int status = STATUS_COMPLETE, i; int numStreams = len/4; int streamid; tgProfile_t *theProfile; tgStream_t *myStream; DPRINT_INFO(WFA_OUT, "entering tgRecvStart\n"); /* * The function wfaSetProcPriority called here is to enhance the real-time * performance for packet receiving. It is only for tuning and optional * to implement */ //wfaSetProcPriority(60); for(i=0; i<numStreams; i++) { wMEMCPY(&streamid, parms+(4*i), 4); /* changed from 2 to 4, bug reported by n.ojanen */ myStream = findStreamProfile(streamid); if(myStream == NULL) { status = STATUS_INVALID; return status; } theProfile = &myStream->profile; if(theProfile == NULL) { status = STATUS_INVALID; return status; } /* calculate the frame interval which is used to derive its jitter */ if(theProfile->rate != 0 && theProfile->rate < 5000) myStream->fmInterval = 1000000/theProfile->rate; /* in ms */ else myStream->fmInterval = 0; if(theProfile->direction != DIRECT_RECV) { status = STATUS_INVALID; return status; } wMEMSET(&myStream->stats, 0, sizeof(tgStats_t)); // mark the stream active myStream->state = WFA_STREAM_ACTIVE; switch(theProfile->profile) { #ifdef WFA_WPA2_SINGLE_THREAD case PROF_MCAST: case PROF_FILE_TX: // case PROF_IPTV: btSockfd = wfaCreateUDPSock(theProfile->dipaddr, theProfile->dport); gtgRecv = streamid; if(btSockfd < 0) status = STATUS_ERROR; else { /* get current flags setting */ int ioflags = wFCNTL(btSockfd, F_GETFL, 0); /* set only BLOCKING flag to non-blocking */ wFCNTL(btSockfd, F_SETFL, ioflags | O_NONBLOCK); } break; #else case PROF_TRANSC: case PROF_CALI_RTD: /* Calibrate roundtrip delay */ gtgTransac = streamid; case PROF_MCAST: case PROF_FILE_TX: case PROF_IPTV: gtgRecv = streamid; wmm_thr[usedThread].thr_flag = streamid; wPT_MUTEX_LOCK(&wmm_thr[usedThread].thr_flag_mutex); wPT_COND_SIGNAL(&wmm_thr[usedThread].thr_flag_cond); wPT_MUTEX_UNLOCK(&wmm_thr[usedThread].thr_flag_mutex); printf("Recv Start in thread %i for streamid %i\n", usedThread, streamid); usedThread++; break; #endif case PROF_UAPSD: #ifdef WFA_WMM_PS_EXT status = STATUS_COMPLETE; psSockfd = wfaCreateUDPSock(theProfile->dipaddr, WFA_WMMPS_UDP_PORT); wmmps_info.sta_state = 0; wmmps_info.wait_state = WFA_WAIT_STAUT_00; wMEMSET(&wmmps_info.psToAddr, 0, sizeof(wmmps_info.psToAddr)); wmmps_info.psToAddr.sin_family = AF_INET; wmmps_info.psToAddr.sin_addr.s_addr = inet_addr(theProfile->sipaddr); wmmps_info.psToAddr.sin_port = htons(theProfile->sport); wmmps_info.reset = 0; wmm_thr[usedThread].thr_flag = streamid; wmmps_info.streamid = streamid; wPT_MUTEX_LOCK(&wmm_thr[usedThread].thr_flag_mutex); wPT_COND_SIGNAL(&wmm_thr[usedThread].thr_flag_cond); gtgWmmPS = streamid;; wPT_MUTEX_UNLOCK(&wmm_thr[usedThread].thr_flag_mutex); usedThread++; #endif /* WFA_WMM_PS_EXT */ break; } } /* encode a TLV for response for "complete/error ..." */ wfaEncodeTLV(WFA_TRAFFIC_AGENT_RECV_START_RESP_TLV, sizeof(int), (BYTE *)&status, respBuf); *respLen = WFA_TLV_HDR_LEN + sizeof(int); return TRUE; }