protected Socket socket;
...
void CreateMulticastSocket(string multicastIP, int port, bool exclusive)
{
sock = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
socket.Blocking = false;
socket.ExclusiveAddressUse = exclusive;
if (!exclusive) socket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, 1);
IPEndPoint endpoint = new IPEndPoint(IPAddress.Any, port);
socket.Bind(endpoint);
IPAddress ip = IPAddress.Parse(multicastIP);
socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, new MulticastOption(ip, IPAddress.Any));
}
2021년 4월 30일 금요일
C# 멀티캐스트 소켓 생성
2021년 4월 8일 목요일
C# 시리얼 통신 데이터 파싱
시리얼 통신 데이터는 TCP와 유사하게 전송되는 바이트 길이만큼 수신되지 않는다.
만약 송신자->수신자 에게 주기적으로 20 바이트를 전송한다고 했을때 수신측에서
시리얼 통신 데이터를 read 했을때 정확하게 20 바이트를 수신하지 않고 5+15 와 같이
잘려서 수신될 수 있다는 말이다.
연속해서 데이터를 수신할때는 더욱 다양한 상황이 발생할 수 있다.
20, 20 바이트를 연속해서 보냈을때 25+15로 받을 수도 있고 1+15+15+9 와 같이 받을 수도 있다.
이런 모든 경우의 수에 대해 올바르게 처리하려면 전송되는 데이터 단위가 고정길이(20 바이트)라고 가정했을때
수신 버퍼를 크게 할당한 다음 20 바이트씩 끊어서 처리해야 한다.
간단한 소스는 다음과 같다.
private SerialPort serial = new SerialPort();
private byte[] serialRecvBuffer = new byte[1024]; // 수신버퍼
private int serialRecvBufferIndex = 0; // 수신버퍼 인덱스 - 현재까지 수신한 데이터 길이와 같음
...
serial.DataReceived += Serial_DataReceived;
...
private void Serial_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
try
{
// 시리얼 데이터 수신
int size = serial.BytesToRead;
byte[] bytesRead = new byte[size];
int ret = serial.Read(bytesRead, 0, size);
// 수신버퍼에 복사
Buffer.BlockCopy(bytesRead, 0, serialRecvBuffer, serialRecvBufferIndex, size);
serialRecvBufferIndex += size;
while (serialRecvBufferIndex >= 20) // 수신버퍼 크기가 20보다 크거나 같으면 데이터 처리
{
ProcessSerialData(); // 데이터 처리
// 데이터 처리 후 뒤에 남은 데이터들 앞으로 복사
Buffer.BlockCopy(serialRecvBuffer, 20, serialRecvBuffer, 0, serialRecvBufferIndex - 20);
serialRecvBufferIndex -= 20;
}
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
serialRecvBufferIndex = 0;
}
}
피드 구독하기:
글 (Atom)