행복한 하루

Raspberry Pi4를 이용한 멀티캐스트 송신 코드 및 테스트 (Multicast Sender) 본문

RaspberryPi

Raspberry Pi4를 이용한 멀티캐스트 송신 코드 및 테스트 (Multicast Sender)

변화의 물결 2022. 11. 22. 15:35

 

  

안녕하세요.

 

 IPTV나 네트워크 쪽으로 통신 프로그램할 경우가 아니면 주로 사용하는 방식은 아니지만 이번에 확인할 일이 있어서 찾아본 내용 공유드립니다. 송신부는 C 프로그램으로 테스트하였고, 다음 내용에 올릴 수신부는 Qt 소스 공개된 것이 있어서 PC에서 수정해서 테스트해보았습니다.


1. 멀티캐스트 간단한 개념

 - 컴퓨터 네트워크에서 멀티캐스트(multicast)란 한 번의 송신으로 메시지나 정보를 목표한 여러 컴퓨터에 동시에 전송하는 것을 말한다. 이때 망 접속 형태가 요구할 경우에 한해, 자동으로 라우터와 같은 다른 네트워크 요소들에 메시지의 복사본이 생성된다.

 

 멀티캐스트는 보통 IP 멀티캐스트 형태로 구현되는데, 이는 스트리밍을 위한 인터넷 프로토콜 응용 프로그램(Internet Protocol application) 및 인터넷 텔레비전에서 주로 사용된다. IP 멀티캐스트에서 멀티캐스트는 주로 IP 라우팅 단계에서 구현되며, 이때 라우터는 데이터그램을 멀티캐스트 대상 주소로 보내기 위한 최적의 전송 경로를 생성한다.

 

 - 다른 캐스팅과 비교해서 보면 개념적으로 조금 쉽게 알 수 있습니다. 이것보다 조금 더 상세한 내용은 한단 링크를 참조하시면 도움이 될 것입니다.

 

<WIKI-멀티캐스트 자료>

2. 라즈베리안 OS에서 멀티캐스팅 확인하는 방법

 - 라즈베리파이에 OS가 설치가 되어 있다면 기본적으로 Multicast가 설정되어 있지 않을까 합니다. 그렇지만 Multicast설정이 되어 있는지 확인합니다. 아래와 같이 명령어를 입력하면 MULTICAST라고 나타납니다. 

pi@raspberrypi:~ $ ifconfig

 pi@raspberrypi:~ $ ip  a

3. 멀티캐스트를 설정하는 방법

 - 만약 MULTICAST가 표시되지 않는다면 활성화시킵니다.

pi@raspberrypi:~ $ sudo ifconfig eth0 multicast

 - multicast 설정을 취소하려면 “-“를 추가해주면 됩니다.

pi@raspberrypi:~ $ sudo ifconfig eth0 -multicast

4. Sender 소스  작성

 - 우선 vim mCast.c로 해서 파일을 만듭니다.

 - 기본적으로 socket 통신과 유사한 형태를 가지므로 소켓과 ip주소를 위한 구조체를 선언합니다. 그리고 멀티캐스트를 위한 주소를 지정합니다.  그리고 멀티캐스트와 별도로 자신의 IP주소를 입력합니다.

#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>

int main (int argc, char* argv[])
{
    int sockfd, send_len;
    struct sockaddr_in multicast_addr;      
    struct in_addr     local_addr;
    char* pMsg;

    // Max Router Num
    char ttl=5;

    // multicast addr
    char *multicast_ip = "225.192.0.10";
    int   multicast_port  = 50000;

    // send device ip address [current computer]
    char *local_ip      = "192.168.0.133";

    // generatae socket
    sockfd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);

    if (sockfd < 0)
    {
        printf("Socket open error\n");
        return -1;
    }

    // setting multicast address
    multicast_addr.sin_family      = AF_INET;
    multicast_addr.sin_addr.s_addr = inet_addr(multicast_ip);
    multicast_addr.sin_port        = htons(multicast_port);

  

 - 저장된 메시지를 사용하지 않고 실행 시 입력한 문자열을 보내기 위해서 메모리 할당시켜 문자열을 저장합니다.

// sending message
    char *send_message ="Hello multicast";

    pMsg = malloc(sizeof(char) * 20);
    memcpy(pMsg, argv[1], strlen(argv[1]));

 

 

- setsockopt() 함수로 TTL(패킷을 얼마나 멀리 전달할지 결정하는 요소)을 설정합니다.

// set the maximum number of routers.
    if(setsockopt(sockfd, IPPROTO_IP, IP_MULTICAST_TTL,(void *)&ttl,sizeof(ttl))<0)
    {
        printf("Socket setsockopt error.[ttl]\n");

        close(sockfd);
        return -1;
    }

 

- 기존에 설정된 네트워크 설정을 무시하고 현재 프로그래머가 설정한 네트워크 인터페이스(IP_MULTICAT_IF)를 선택하게 설정합니다.

// set the Ip address to be transmitted(local ip)
    local_addr.s_addr = inet_addr(local_ip);   
    if(setsockopt(sockfd, IPPROTO_IP, IP_MULTICAST_IF,(char *)&local_addr, sizeof(local_addr))<0)
    {
        printf("Socket setsockopt error.[Interface]\n");

        close(sockfd);
        return -1;
    }

 

- 실행 시 같이 입력한 문자열의 길이를 계산한 후 멀티캐스트로 보냅니다. 그리고 사용한 리소스는 해제합니다.

 

    // send message
    send_len = sendto(sockfd, pMsg, strlen(pMsg), 0, (struct sockaddr*)&multicast_addr, sizeof(multicast_addr));

    //send_len = sendto(sockfd, send_message, strlen(send_message), 0, (struct sockaddr*)&multicast_addr, sizeof(multicast_addr));
    printf("send len : %d\n",send_len);
    if( send_len < 0 )
    {
        printf("Sending multicast message error");
    }
    else
        printf("Sending multicast message...Success\n");

    free(pMsg);
    close(sockfd);
    return 0;
}

5. 컴파일 방법

 - 이상 없이 컴파일이 실행되면 mcast 파일일 생성됩니다.

 pi@raspberrypi:~ $ gcc -o mcast mCast.c

6.  실행 및 결과 확인

 pi@raspberrypi:~ $ ./mcast FirstMessage

 - Wireshark로 전달되는 패킷을 확인해봅니다. 그러면 FirstMessage 문자열을 포함한 패킷을 확인할 수 있습니다.

  

다음에는 수신부를 확인해보겠습니다.

감사합니다.

  

 

<참고 사이트>

1. [Linux/C언어] 멀티캐스트 송신 코드 및 테스트 (Multicast Sender)

https://softtone-someday.tistory.com/16

2. Can't receive UDP Multicast packets

https://raspberrypi.stackexchange.com/questions/111201/cant-receive-udp-multicast-packets

https://ansan-survivor.tistory.com/1295

https://blockdmask.tistory.com/442

https://blockdmask.tistory.com/381

3. 멀티캐스트

https://ko.wikipedia.org/wiki/%EB%A9%80%ED%8B%B0%EC%BA%90%EC%8A%A4%ED%8A%B8

4. IP MultiCast 일반

https://www.joinc.co.kr/w/Site/Network_Programing/Documents/MultiCast

5. 멀티캐스트( Multicast )

https://m.blog.naver.com/PostView.naver?isHttpsRedirect=true&blogId=kirayamato4&logNo=220779462804

6. 멀티캐스트 프로그래밍

https://wiki.kldp.org/HOWTO/html/Multicast/Multicast-HOWTO-6.html

7. 와이어샤크(Wireshark) 사용법 #2 [인터페이스]

https://citizen.tistory.com/6

mCast.c
0.00MB

 

 

Comments