仮想RTSPカメラの作り方

2024年8月19日

/*
  dummy_cam_0.2.c
  
  ■環境設定を行います。
  sudo apt-get update
  sudo apt-get install libgstrtspserver-1.0-dev

  export PKG_CONFIG_PATH=/usr/lib/x86_64-linux-gnu/pkgconfig:$PKG_CONFIG_PATH

  "192.168.1.11.mp4"というmp4ファイルを用意しておいて下さい。

 
  ■プログラムをコンパイルして実行するには、以下のコマンドを使用します:
  gcc -o dummy_cam_0.2 dummy_cam_0.2.c `pkg-config --cflags --libs gstreamer-1.0 gstreamer-rtsp-server-1.0`

  ./dummy_cam_0.2 -r rtsp://127.0.0.1:8554/test -f 192.168.1.11.mp4

  ■また、ヘルプメッセージを表示するには、以下のコマンドを使用します:

  ./dummy_cam_0.2 -h

  ■稼動確認環境
   (車上) 192.168.101.30
   cam@cam-desktop:~/cpp/src$ ./dummy_cam_0.2
   cam@cam-desktop:~/cpp/src$ ./abc_vtp_0.1 -i 192.168.101.10 -p 38089 -r rtsp://127.0.0.1:8554/test

   (地上) 192.168.101.10
pt@pt-desktop:~/go/src$ more srt_rtsp_server_38089.sh 

#!/bin/bash
gst-launch-1.0 srtsrc uri=srt://:38089 keep-listening=true ! decodebin ! autovid
eosink

  
*/

#include <gst/gst.h>
#include <gst/rtsp-server/rtsp-server.h>
#include <stdio.h>
#include <string.h>

void print_usage(const char *prog_name) {
    g_print("Usage: %s -r [RTSP_URL] -f [MP4_FILE]\n", prog_name);
    g_print("Default RTSP_URL: rtsp://127.0.0.1:8554/test\n");
    g_print("Default MP4_FILE: 192.168.1.11.mp4\n");
    g_print("Example: %s -r rtsp://127.0.0.1:8554/test -f 192.168.1.11.mp4\n", prog_name);
}

int main(int argc, char *argv[]) {
    GMainLoop *loop;
    GstRTSPServer *server;
    GstRTSPMountPoints *mounts;
    GstRTSPMediaFactory *factory;
    const char *default_url = "rtsp://127.0.0.1:8554/test";
    const char *default_mp4 = "192.168.1.11.mp4";
    const char *rtsp_url = default_url;
    const char *mp4_file = default_mp4;
    char path[256] = "/test";
    char service[6] = "8554";  // ポート番号のデフォルト値

    for (int i = 1; i < argc; i++) {
        if (strcmp(argv[i], "-h") == 0) {
            print_usage(argv[0]);
            return 0;
        } else if (strcmp(argv[i], "-r") == 0 && i + 1 < argc) {
            rtsp_url = argv[++i];
            // RTSP URLのポート番号とパス部分を抽出
            const char *url_port = strchr(rtsp_url + strlen("rtsp://"), ':');
            if (url_port != NULL) {
                url_port++;
                const char *url_path = strchr(url_port, '/');
                if (url_path != NULL) {
                    strncpy(path, url_path, sizeof(path) - 1);
                    path[sizeof(path) - 1] = '\0';  // Null terminatorを追加

                    int port_length = url_path - url_port;
                    if (port_length < sizeof(service)) {
                        strncpy(service, url_port, port_length);
                        service[port_length] = '\0';  // Null terminatorを追加
                    }
                }
            }
        } else if (strcmp(argv[i], "-f") == 0 && i + 1 < argc) {
            mp4_file = argv[++i];
        }
    }

    gst_init(&argc, &argv);

    loop = g_main_loop_new(NULL, FALSE);

    server = gst_rtsp_server_new();
    gst_rtsp_server_set_service(server, service);

    mounts = gst_rtsp_server_get_mount_points(server);

    factory = gst_rtsp_media_factory_new();
    char launch_string[512];
    snprintf(launch_string, sizeof(launch_string),
             "( filesrc location=%s ! qtdemux name=d d.video_0 ! queue ! rtph264pay pt=96 name=pay0 )",
             mp4_file);
    gst_rtsp_media_factory_set_launch(factory, launch_string);

    // ループ設定を追加
    //g_object_set(factory, "loop", TRUE, NULL);

    gst_rtsp_mount_points_add_factory(mounts, path, factory);

    g_object_unref(mounts);

    gst_rtsp_server_attach(server, NULL);

    g_print("Stream ready at %s with file %s\n", rtsp_url, mp4_file);
    g_main_loop_run(loop);

    return 0;
}

2024年8月19日未分類

Posted by ebata