Linux/Kernel(커널)
[Kernel] Netlink 메시지 수신하기
i5
2024. 8. 9. 01:38
반응형
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <pthread.h>
#include <errno.h>
#include <sys/socket.h>
#include <linux/netlink.h>
#include <linux/genetlink.h>
#define NETLINK_GENERIC 16
#define MAX_PAYLOAD 1024 // 최대 페이로드 크기
static int running = 1;
void *event_listener(void *arg) {
int sock_fd;
struct sockaddr_nl src_addr, dest_addr;
struct nlmsghdr *nlh = NULL;
struct iovec iov;
struct msghdr msg;
// 소켓 생성
sock_fd = socket(PF_NETLINK, SOCK_RAW, NETLINK_GENERIC);
if (sock_fd < 0) {
perror("소켓 생성 실패");
pthread_exit(NULL);
}
// 주소 설정
memset(&src_addr, 0, sizeof(src_addr));
src_addr.nl_family = AF_NETLINK;
src_addr.nl_pid = getpid(); // 사용자 프로세스 ID
src_addr.nl_groups = 0; // 멀티캐스트 그룹
// 바인드
if (bind(sock_fd, (struct sockaddr*)&src_addr, sizeof(src_addr)) < 0) {
perror("바인드 실패");
close(sock_fd);
pthread_exit(NULL);
}
// 메시지 수신 대기
nlh = (struct nlmsghdr *)malloc(NLMSG_SPACE(MAX_PAYLOAD));
memset(&dest_addr, 0, sizeof(dest_addr));
memset(nlh, 0, NLMSG_SPACE(MAX_PAYLOAD));
nlh->nlmsg_len = NLMSG_SPACE(MAX_PAYLOAD);
nlh->nlmsg_pid = getpid();
nlh->nlmsg_flags = 0;
iov.iov_base = (void *)nlh;
iov.iov_len = NLMSG_SPACE(MAX_PAYLOAD);
msg.msg_name = (void *)&dest_addr;
msg.msg_namelen = sizeof(dest_addr);
msg.msg_iov = &iov;
msg.msg_iovlen = 1;
printf("MPTCP 이벤트 수신 시작\n");
while (running) {
ssize_t len = recvmsg(sock_fd, &msg, 0);
if (len < 0) {
perror("메시지 수신 실패");
continue;
}
printf("수신된 메시지: %s\n", (char *)NLMSG_DATA(nlh));
}
// 자원 해제
close(sock_fd);
free(nlh);
printf("MPTCP 이벤트 수신 중지\n");
pthread_exit(NULL);
}
int main() {
pthread_t listener_thread;
// 스레드 생성
if (pthread_create(&listener_thread, NULL, event_listener, NULL) != 0) {
perror("스레드 생성 실패");
return EXIT_FAILURE;
}
// 종료 대기
printf("종료하려면 Enter 키를 누르세요...\n");
getchar();
// 종료 플래그 설정 및 스레드 종료 대기
running = 0;
pthread_join(listener_thread, NULL);
return EXIT_SUCCESS;
}
반응형