mirror of
https://github.com/morgan9e/UxPlay
synced 2026-04-14 00:04:13 +09:00
add ability to use a configuration file uxplayrc
This commit is contained in:
91
uxplay.cpp
91
uxplay.cpp
@@ -28,6 +28,9 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
#include <fstream>
|
||||
#include <sstream>
|
||||
#include <iterator>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#ifdef _WIN32 /*modifications for Windows compilation */
|
||||
#include <glib.h>
|
||||
@@ -39,6 +42,8 @@
|
||||
#include <sys/utsname.h>
|
||||
#include <sys/socket.h>
|
||||
#include <ifaddrs.h>
|
||||
#include <sys/types.h>
|
||||
#include <pwd.h>
|
||||
# ifdef __linux__
|
||||
# include <netpacket/packet.h>
|
||||
# else
|
||||
@@ -269,6 +274,37 @@ static int parse_hw_addr (std::string str, std::vector<char> &hw_addr) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static std::string find_uxplay_config_file() {
|
||||
std::string no_config_file = "";
|
||||
const char *homedir = NULL;
|
||||
const char *uxplayrc = NULL;
|
||||
std::string config0, config1, config2;
|
||||
struct stat sb;
|
||||
uxplayrc = getenv("UXPLAYRC"); /* first look for $UXPLAYRC */
|
||||
if (uxplayrc) {
|
||||
config0 = uxplayrc;
|
||||
if (stat(config0.c_str(), &sb) == 0) return config0;
|
||||
}
|
||||
homedir = getenv("XDG_CONFIG_HOMEDIR");
|
||||
if (homedir == NULL) {
|
||||
homedir = getenv("HOME");
|
||||
}
|
||||
#ifndef _WIN32
|
||||
if (homedir == NULL){
|
||||
homedir = getpwuid(getuid())->pw_dir;
|
||||
}
|
||||
#endif
|
||||
if (homedir) {
|
||||
config1 = homedir;
|
||||
config1.append("/.uxplayrc");
|
||||
if (stat(config1.c_str(), &sb) == 0) return config1; /* look for ~/.uxplayrc */
|
||||
config2 = homedir;
|
||||
config2.append("/.config/uxplayrc"); /* look for ~/.config/uxplayrc */
|
||||
if (stat(config2.c_str(), &sb) == 0) return config2;
|
||||
}
|
||||
return no_config_file;
|
||||
}
|
||||
|
||||
static std::string find_mac () {
|
||||
/* finds the MAC address of a network interface *
|
||||
* in a Windows, Linux, *BSD or macOS system. */
|
||||
@@ -363,13 +399,16 @@ static std::string random_mac () {
|
||||
|
||||
static void print_info (char *name) {
|
||||
printf("UxPlay %s: An open-source AirPlay mirroring server based on RPiPlay\n", VERSION);
|
||||
printf("=========== Website: https://github.com/FDH2/UxPlay =============\n");
|
||||
printf("Usage: %s [-n name] [-s wxh] [-p [n]]\n", name);
|
||||
printf("Options:\n");
|
||||
printf("-n name Specify the network name of the AirPlay server\n");
|
||||
printf("-nh Do not add \"@hostname\" at the end of the AirPlay server name\n");
|
||||
printf("-vsync [x]Mirror mode: sync audio to video (default: stream w/o sync)\n");
|
||||
printf(" x is optional audio delay in millisecs, can be neg., decimal\n");
|
||||
printf("-vsync no Switch off vsync audio/(server)video timestamp synchronization \n");
|
||||
printf("-async [x]Audio-Only mode: sync audio to client video (default: no sync)\n");
|
||||
printf("-async no Switch off async audio/(client)video timestamp synchronization\n");
|
||||
printf("-s wxh[@r]Set display resolution [refresh_rate] default 1920x1080[@60]\n");
|
||||
printf("-o Set display \"overscanned\" mode on (not usually needed)\n");
|
||||
printf("-fs Full-screen (only works with X11, Wayland and VAAPI)\n");
|
||||
@@ -566,6 +605,11 @@ static void parse_arguments (int argc, char *argv[]) {
|
||||
} else if (arg == "-async") {
|
||||
audio_sync = true;
|
||||
if (i < argc - 1) {
|
||||
if (strlen(argv[i+1]) == 2 && strncmp(argv[i+1], "no", 2) == 0) {
|
||||
audio_sync = false;
|
||||
i++;
|
||||
continue;
|
||||
}
|
||||
char *end;
|
||||
int n = (int) (strtof(argv[i + 1], &end) * 1000);
|
||||
if (*end == '\0') {
|
||||
@@ -581,6 +625,11 @@ static void parse_arguments (int argc, char *argv[]) {
|
||||
} else if (arg == "-vsync") {
|
||||
video_sync = true;
|
||||
if (i < argc - 1) {
|
||||
if (strlen(argv[i+1]) == 2 && strncmp(argv[i+1], "no", 2) == 0) {
|
||||
video_sync = false;
|
||||
i++;
|
||||
continue;
|
||||
}
|
||||
char *end;
|
||||
int n = (int) (strtof(argv[i + 1], &end) * 1000);
|
||||
if (*end == '\0') {
|
||||
@@ -1252,9 +1301,47 @@ static void stop_raop_server () {
|
||||
return;
|
||||
}
|
||||
|
||||
static void read_config_file(const char * filename, const char * uxplay_name) {
|
||||
std::string config_file = filename;
|
||||
std::string option_char = "-";
|
||||
std::vector<std::string> options;
|
||||
options.push_back(uxplay_name);
|
||||
std::ifstream file(config_file);
|
||||
if (file.is_open()) {
|
||||
fprintf(stdout,"UxPlay: reading configuration from %s\n", config_file.c_str());
|
||||
std::string line;
|
||||
while (std::getline(file, line)) {
|
||||
if (line[0] == '#') continue;
|
||||
std::stringstream ss(line);
|
||||
std::istream_iterator<std::string> begin(ss);
|
||||
std::istream_iterator<std::string> end;
|
||||
std::vector<std::string> tokens(begin,end);
|
||||
if (tokens.size() > 0) {
|
||||
options.push_back(option_char + tokens[0]);
|
||||
for (int i = 1; i < tokens.size(); i++) {
|
||||
options.push_back(tokens[i].c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
file.close();
|
||||
} else {
|
||||
fprintf(stderr,"UxPlay: failed to open configuration file at %s\n", config_file.c_str());
|
||||
}
|
||||
if (options.size() > 1) {
|
||||
int argc = options.size();
|
||||
char **argv = (char **) malloc(sizeof(char*) * argc);
|
||||
for (int i = 0; i < argc; i++) {
|
||||
argv[i] = (char *) options[i].c_str();
|
||||
}
|
||||
parse_arguments (argc, argv);
|
||||
free (argv);
|
||||
}
|
||||
}
|
||||
|
||||
int main (int argc, char *argv[]) {
|
||||
std::vector<char> server_hw_addr;
|
||||
std::string mac_address;
|
||||
std::string config_file = "";
|
||||
|
||||
#ifdef SUPPRESS_AVAHI_COMPAT_WARNING
|
||||
// suppress avahi_compat nag message. avahi emits a "nag" warning (once)
|
||||
@@ -1263,6 +1350,10 @@ int main (int argc, char *argv[]) {
|
||||
if (!getenv("AVAHI_COMPAT_NOWARN")) putenv(avahi_compat_nowarn);
|
||||
#endif
|
||||
|
||||
config_file = find_uxplay_config_file();
|
||||
if (config_file.length()) {
|
||||
read_config_file(config_file.c_str(), argv[0]);
|
||||
}
|
||||
parse_arguments (argc, argv);
|
||||
|
||||
#ifdef _WIN32 /* use utf-8 terminal output; don't buffer stdout in WIN32 when debug_log = false */
|
||||
|
||||
Reference in New Issue
Block a user