2015/01/11 - [IT / Development/WIZnet] - W5500-EVB를 이용한 Chat Client 구현해 보자 - 1

2015/01/12 - [IT / Development/WIZnet] - W5500-EVB를 이용한 Chat Client 구현해 보자 - 2

2015/01/26 - [IT / Development/WIZnet] - W5500-EVB를 이용한 Chat Client 구현해 보자 - 3

2015/01/26 - [IT / Development/WIZnet] - W5500-EVB를 이용한 Chat Client 구현해 보자 - 4

2015/03/19 - [IT / Development/WIZnet] - W5500-EVB를 이용한 Chat Client 구현해 보자 - 5


지난번에는 1차로 Chat Client를 구현해 보았다. 이번에는 지난번에 이어 조금 업그레이드 해보았다.

  1. “Socket Status Register”의 상태에 따라 해당 동작 진행
  2. Serial로 입력 받은 값을 버퍼에 저장을 하다가, CR과 LF 값을 입력 받으면 저장된 버퍼의 값을 TCP로 전송

위의 2가지를 업그레이드 했다.


첫번째 수정,

main 함수의 while문에서 “Socket Status Register”의 상태를 계속 확인을 하고, 그 상태에 따라 동작하게 된다.

SOCK_CLOSED 상태일때, 소켓을 생성함.

SOCK_INIT 상태일때, 서버에 접속 시도함.

SOCK_ESTABLISHED 상태일때, 데이터를 주고 받음.

while(1) {
		switch(getSn_SR(sn)) {
			case SOCK_CLOSED:
		        /* Socket Closed State */
				//Socket Creation
				if(socket(sn, Sn_MR_TCP, port, 0x00)==sn){
					printf("%d:Socket Opened\r\n",sn);
				}
				else{
					printf("%d:Socket Error\r\n",sn);
					while(1);
				}
		        break;

		    case SOCK_INIT:
		        /* TCP Socket Creatation */
		    	printf("%d:Connecting, ip[%d.%d.%d.%d] port [%d]\r\n", sn, ip[0], ip[1], ip[2], ip[3], port);
		    	//Connent TCP Server
		    	if(connect(sn,ip,port)==SOCK_OK);
		    	else {
		    		printf("%d:Connect Error\r\n",sn);
		    		while(1);
		    	}
		        break;
		    case SOCK_LISTEN:
		        /* TCP Server Mode */

		        break;
		    case SOCK_ESTABLISHED:
		        /* TCP ESTABLISHED */
		    	//Connect Interrupt Check
		    	if(getSn_IR(sn) & Sn_IR_CON) {
		    		printf("%d:Connected\r\n",sn);
		    		setSn_IR(sn,Sn_IR_CON);
		    	    Board_LED_Set(0, false);
		    	    Board_LED_Set(1, true);
		    	}
		    	//Receive Data Check
		    	if((size = getSn_RX_RSR(sn)) > 0) {
		    		if(size > DATA_BUF_SIZE) size = DATA_BUF_SIZE;
		    	    recv(sn,gDATABUF,size);
		    	    EtherToSerial(gDATABUF, size);
		    	}
		    	SerialToEther(sn);
		        break;

		    case SOCK_CLOSE_WAIT:
		        /* Disconnect request */

		        break;
		}
    }


두번째 수정,

기존에는 수신된 Serial 데이터를 1바이트씩 TCP로 전송을 했지만, 수정된 코드에서는 수신된 Serial 데이터를 버퍼에 계속 쌓으면서 CR과 LF 값이 입력되면 TCP로 지금까지 수신한 Serial 데이터를 전송하도록 수정했고, UART를 인터럽트 처리했다.

아래 코드는 UART 인터럽트를 Enable 시켜주는 부분으로 main 문에 추가해주었다.

// Enable UART interrupt Chip_UART_IntEnable(LPC_USART, (UART_IER_RBRINT | UART_IER_RLSINT)); // Start UART interrupt NVIC_EnableIRQ(UART0_IRQn);

아래코드는 UART 인터럽트가 발생되면, UART로 입력된 데이터를 sr_rx_data 버퍼에 계속 쌓아 나가다가  CR과 LF 값이 입력되면 TCP로 지금까지 수신한 Serial 데이터를 전송하도록 한는 부분이다.

// Serial => Ethernet
int SerialToEther(uint8_t sn)
{
	if(sr_rx_data[sr_rx_size-2]==CR && sr_rx_data[sr_rx_size-1]==LF){
			send(sn, sr_rx_data, sr_rx_size);
			sr_rx_size = 0;
		}
	/*if((Chip_UART_ReadLineStatus(LPC_USART) & UART_LSR_RDR) == 1){
		sr_rx_data[sr_rx_size]=Chip_UART_ReadByte(LPC_USART);
		sr_rx_size++;
		// Serial CR LF Check
		if(sr_rx_data[sr_rx_size-2]==CR && sr_rx_data[sr_rx_size-1]==LF){
			send(sn, sr_rx_data, sr_rx_size);
			sr_rx_size = 0;
		}
	    //Chip_UART_SendBlocking(LPC_USART, &sr_rx_data, 1);
	}*/
	return 0 ;
}
//UART interrupt function
void UART_IRQHandler(void)
{
	sr_rx_data[sr_rx_size]=Chip_UART_ReadByte(LPC_USART);
	sr_rx_size++;
}


보완점

  1. uart 수신단 보완
  2. TCP Disconnect 처리
  3. 예외 처리 및 에러 처리


+ Recent posts