카테고리 없음
sdbus 예제
2025. 12. 26. 14:27반응형
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <systemd/sd-bus.h>
#include <signal.h>
static sd_bus *bus = NULL;
static sd_bus_slot *slot = NULL;
static int running = 1;
// Add 메서드 핸들러
static int method_add(sd_bus_message *m, void *userdata, sd_bus_error *ret_error) {
int a, b, result;
int r;
// 입력 파라미터 읽기
r = sd_bus_message_read(m, "ii", &a, &b);
if (r < 0) {
fprintf(stderr, "Failed to parse parameters: %s\n", strerror(-r));
return r;
}
result = a + b;
printf("Add called: %d + %d = %d\n", a, b, result);
// 결과 반환
return sd_bus_reply_method_return(m, "i", result);
}
// Sub 메서드 핸들러
static int method_sub(sd_bus_message *m, void *userdata, sd_bus_error *ret_error) {
int a, b, result;
int r;
// 입력 파라미터 읽기
r = sd_bus_message_read(m, "ii", &a, &b);
if (r < 0) {
fprintf(stderr, "Failed to parse parameters: %s\n", strerror(-r));
return r;
}
result = a - b;
printf("Sub called: %d - %d = %d\n", a, b, result);
// 결과 반환
return sd_bus_reply_method_return(m, "i", result);
}
// VTable 정의 (인터페이스 메서드 매핑)
static const sd_bus_vtable calculator_vtable[] = {
SD_BUS_VTABLE_START(0),
SD_BUS_METHOD("Add", "ii", "i", method_add, SD_BUS_VTABLE_UNPRIVILEGED),
SD_BUS_METHOD("Sub", "ii", "i", method_sub, SD_BUS_VTABLE_UNPRIVILEGED),
SD_BUS_VTABLE_END
};
// SIGINT 핸들러
static void signal_handler(int sig) {
printf("\nReceived signal %d, shutting down...\n", sig);
running = 0;
}
int main(int argc, char *argv[]) {
int r;
// SIGINT 핸들러 설정
signal(SIGINT, signal_handler);
signal(SIGTERM, signal_handler);
// 세션 버스에 연결
r = sd_bus_open_user(&bus);
if (r < 0) {
fprintf(stderr, "Failed to connect to session bus: %s\n", strerror(-r));
goto finish;
}
printf("Connected to D-Bus\n");
// 객체에 인터페이스 추가
r = sd_bus_add_object_vtable(bus,
&slot,
"/org/example/Calculator", // 객체 경로
"org.example.Calculator", // 인터페이스 이름
calculator_vtable,
NULL);
if (r < 0) {
fprintf(stderr, "Failed to issue method call: %s\n", strerror(-r));
goto finish;
}
printf("Object registered at /org/example/Calculator\n");
// 버스 이름 요청
r = sd_bus_request_name(bus, "org.example.Calculator", 0);
if (r < 0) {
fprintf(stderr, "Failed to acquire service name: %s\n", strerror(-r));
goto finish;
}
printf("Service name acquired: org.example.Calculator\n");
printf("Calculator server started. Press Ctrl+C to exit.\n");
// 메인 루프
while (running) {
// 이벤트 처리 (타임아웃: 1초)
r = sd_bus_process(bus, NULL);
if (r < 0) {
fprintf(stderr, "Failed to process bus: %s\n", strerror(-r));
goto finish;
}
if (r > 0) {
// 메시지를 처리했으면 계속
continue;
}
// 다음 이벤트 대기
r = sd_bus_wait(bus, 1000000); // 1초 타임아웃
if (r < 0) {
fprintf(stderr, "Failed to wait on bus: %s\n", strerror(-r));
goto finish;
}
}
printf("Shutting down...\n");
finish:
// 슬롯 해제 (vtable 연결 해제)
if (slot) {
sd_bus_slot_unref(slot);
printf("Object unregistered\n");
}
// 버스 연결 해제
if (bus) {
sd_bus_unref(bus);
printf("Disconnected from D-Bus\n");
}
printf("Server stopped.\n");
return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS;
}반응형
