diff --git a/RELEASE.md b/RELEASE.md index ba4da8e..a2b56fb 100644 --- a/RELEASE.md +++ b/RELEASE.md @@ -8,6 +8,7 @@ - http: add `/control` to provide simple JS interface to live edit camera settings - http: change `/option` to accept `device=`, `key=`, and `value=` - device: show stddev estimates to measure frame pacing +- webrtc: allow to specify `--webrtc-ice_servers=` on command line ## Variants diff --git a/cmd/camera-streamer/opts.c b/cmd/camera-streamer/opts.c index b43dd4a..b0c48c7 100644 --- a/cmd/camera-streamer/opts.c +++ b/cmd/camera-streamer/opts.c @@ -131,6 +131,8 @@ option_t all_options[] = { DEFINE_OPTION_DEFAULT(rtsp, port, uint, "8554", "Set the RTSP server port (default: 8854)."), + DEFINE_OPTION_PTR(webrtc, ice_servers, list, "Specify ICE servers: [(stun|turn|turns)(:|://)][username:password@]hostname[:port][?transport=udp|tcp|tls)]."), + DEFINE_OPTION_DEFAULT(log, debug, bool, "1", "Enable debug logging."), DEFINE_OPTION_DEFAULT(log, verbose, bool, "1", "Enable verbose logging."), DEFINE_OPTION_DEFAULT(log, stats, uint, "1", "Print statistics every duration."), diff --git a/output/webrtc/webrtc.cc b/output/webrtc/webrtc.cc index d40b505..4d53c5c 100644 --- a/output/webrtc/webrtc.cc +++ b/output/webrtc/webrtc.cc @@ -9,9 +9,12 @@ extern "C" { #include "util/opts/log.h" #include "util/opts/fourcc.h" #include "util/opts/control.h" +#include "util/opts/opts.h" #include "device/buffer.h" }; +#include "util/opts/helpers.hh" + #ifdef USE_LIBDATACHANNEL #include @@ -37,7 +40,7 @@ static std::mutex webrtc_clients_lock; static const auto webrtc_client_lock_timeout = 3 * 1000ms; static const auto webrtc_client_max_json_body = 10 * 1024; static const auto webrtc_client_video_payload_type = 102; // H264 -static const rtc::Configuration webrtc_configuration = { +static rtc::Configuration webrtc_configuration = { // .iceServers = { rtc::IceServer("stun:stun.l.google.com:19302") }, .disableAutoNegotiation = true }; @@ -390,6 +393,10 @@ extern "C" void http_webrtc_offer(http_worker_t *worker, FILE *stream) extern "C" int webrtc_server(webrtc_options_t *options) { + for (const auto &ice_server : str_split(options->ice_servers, OPTION_VALUE_LIST_SEP_CHAR)) { + webrtc_configuration.iceServers.push_back(rtc::IceServer(ice_server)); + } + buffer_lock_register_check_streaming(&video_lock, webrtc_h264_needs_buffer); buffer_lock_register_notify_buffer(&video_lock, webrtc_h264_capture); options->running = true; diff --git a/output/webrtc/webrtc.h b/output/webrtc/webrtc.h index cb5f3e8..8fcb729 100644 --- a/output/webrtc/webrtc.h +++ b/output/webrtc/webrtc.h @@ -2,11 +2,14 @@ #include +#define WEBRTC_OPTIONS_LENGTH 4096 + typedef struct http_worker_s http_worker_t; typedef struct webrtc_options_s { bool running; bool disabled; + char ice_servers[WEBRTC_OPTIONS_LENGTH]; } webrtc_options_t; // WebRTC diff --git a/util/opts/helpers.hh b/util/opts/helpers.hh new file mode 100644 index 0000000..006ea53 --- /dev/null +++ b/util/opts/helpers.hh @@ -0,0 +1,15 @@ +#pragma once + +#include +#include +#include + +inline std::vector str_split(const std::string& in, const char seperator) +{ + std::vector output; + std::istringstream stream(in); + for (std::string s; std::getline(stream, s, seperator); ) { + output.push_back(s); + } + return output; +} diff --git a/util/opts/opts.h b/util/opts/opts.h index f41ded6..81fa35e 100644 --- a/util/opts/opts.h +++ b/util/opts/opts.h @@ -26,6 +26,7 @@ typedef struct options_s { const char *description; } option_t; +#define OPTION_VALUE_LIST_SEP_CHAR ';' #define OPTION_VALUE_LIST_SEP ";" #define OPTION_FORMAT_uint "%u"