git-svn-id: http://subversion.jackaudio.org/jack/jack2/trunk/jackmp@2342 0c269be4-1314-0410-8aa9-9f06e86f4224tags/1.90
@@ -402,6 +402,15 @@ void JackSocketServerChannel::BuildPoolTable() | |||
} | |||
} | |||
bool JackSocketServerChannel::Init() | |||
{ | |||
sigset_t set; | |||
sigemptyset(&set); | |||
sigaddset(&set, SIGPIPE); | |||
pthread_sigmask(SIG_BLOCK, &set, 0); | |||
return true; | |||
} | |||
bool JackSocketServerChannel::Execute() | |||
{ | |||
// Global poll | |||
@@ -227,690 +227,3 @@ JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_control, "org.jackaudio.JackContro | |||
JACK_DBUS_IFACE_HANDLER(jack_control_run_method) | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
Copyright (C) 2007-2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
#include "controller_internal.h" | |||
#define controller_ptr ((struct jack_controller *)call->context) | |||
/* | |||
* Check if the supplied method name exists in org.jackaudio.JackControl, | |||
* if it does execute it and return true. Otherwise return false. | |||
*/ | |||
static | |||
bool | |||
jack_control_run_method( | |||
struct jack_dbus_method_call * call, | |||
const struct jack_dbus_interface_method_descriptor * methods) | |||
{ | |||
int ret; | |||
int type; | |||
message_arg_t arg; | |||
/* use empty reply if not overriden in the code that follows */ | |||
type = DBUS_TYPE_INVALID; | |||
if (strcmp (call->method_name, "Exit") == 0) | |||
{ | |||
g_exit_command = TRUE; | |||
} | |||
else if (strcmp (call->method_name, "IsStarted") == 0) | |||
{ | |||
type = DBUS_TYPE_BOOLEAN; | |||
arg.boolean = (dbus_bool_t) (controller_ptr->started ? TRUE : FALSE); | |||
} | |||
else if (strcmp (call->method_name, "StartServer") == 0) | |||
{ | |||
if (!jack_controller_start_server(controller_ptr, call)) | |||
{ | |||
jack_error ("Failed to start server"); | |||
} | |||
} | |||
else if (strcmp (call->method_name, "StopServer") == 0) | |||
{ | |||
if (!jack_controller_stop_server(controller_ptr, call)) | |||
{ | |||
jack_error ("Failed to stop server"); | |||
} | |||
} | |||
else if (strcmp (call->method_name, "GetLoad") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_DOUBLE; | |||
arg.doubl = jack_cpu_load(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "GetXruns") == 0) | |||
{ | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = controller_ptr->xruns; | |||
} | |||
else if (strcmp (call->method_name, "GetSampleRate") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = jack_get_sample_rate(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "GetLatency") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_DOUBLE; | |||
arg.doubl = ((float)jack_get_buffer_size(controller_ptr->client) / (float)jack_get_sample_rate(controller_ptr->client)) * 1000.0f; | |||
} | |||
else if (strcmp (call->method_name, "GetBufferSize") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = jack_get_buffer_size(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "SetBufferSize") == 0) | |||
{ | |||
dbus_uint32_t buffer_size; | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
if (!jack_dbus_get_method_args(call, DBUS_TYPE_UINT32, &buffer_size, DBUS_TYPE_INVALID)) | |||
{ | |||
/* jack_dbus_get_method_args() has set reply for us */ | |||
goto exit; | |||
} | |||
ret = jack_set_buffer_size(controller_ptr->client, buffer_size); | |||
if (ret != 0) | |||
{ | |||
jack_dbus_error( | |||
call, | |||
JACK_DBUS_ERROR_GENERIC, | |||
"jack_set_buffer_size(%u) failed with error %d", (unsigned int)buffer_size, ret); | |||
goto exit; | |||
} | |||
} | |||
else if (strcmp (call->method_name, "IsRealtime") == 0) | |||
{ | |||
type = DBUS_TYPE_BOOLEAN; | |||
arg.boolean = jack_is_realtime(controller_ptr->client) ? TRUE : FALSE; | |||
} | |||
else if (strcmp (call->method_name, "ResetXruns") == 0) | |||
{ | |||
controller_ptr->xruns = 0; | |||
} | |||
else | |||
{ | |||
return false; | |||
} | |||
jack_dbus_construct_method_return_single(call, type, arg); | |||
return true; | |||
not_started: | |||
jack_dbus_error (call, JACK_DBUS_ERROR_SERVER_NOT_RUNNING, | |||
"Can't execute method '%s' with stopped JACK server", call->method_name); | |||
exit: | |||
return true; | |||
} | |||
#undef controller_ptr | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(IsStarted) | |||
JACK_DBUS_METHOD_ARGUMENT("started", "b", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(StartServer) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(StopServer) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetLoad) | |||
JACK_DBUS_METHOD_ARGUMENT("load", "d", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetXruns) | |||
JACK_DBUS_METHOD_ARGUMENT("xruns_count", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetSampleRate) | |||
JACK_DBUS_METHOD_ARGUMENT("sample_rate", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetLatency) | |||
JACK_DBUS_METHOD_ARGUMENT("latency_ms", "d", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetBufferSize) | |||
JACK_DBUS_METHOD_ARGUMENT("buffer_size_frames", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(SetBufferSize) | |||
JACK_DBUS_METHOD_ARGUMENT("buffer_size_frames", "u", false) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(IsRealtime) | |||
JACK_DBUS_METHOD_ARGUMENT("realtime", "b", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(ResetXruns) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHOD_DESCRIBE(IsStarted, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(StartServer, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(StopServer, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetLoad, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetXruns, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetSampleRate, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetLatency, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetBufferSize, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(SetBufferSize, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(IsRealtime, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(ResetXruns, NULL) | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_control, "org.jackaudio.JackControl") | |||
JACK_DBUS_IFACE_HANDLER(jack_control_run_method) | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
Copyright (C) 2007-2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
#include "controller_internal.h" | |||
#define controller_ptr ((struct jack_controller *)call->context) | |||
/* | |||
* Check if the supplied method name exists in org.jackaudio.JackControl, | |||
* if it does execute it and return true. Otherwise return false. | |||
*/ | |||
static | |||
bool | |||
jack_control_run_method( | |||
struct jack_dbus_method_call * call, | |||
const struct jack_dbus_interface_method_descriptor * methods) | |||
{ | |||
int ret; | |||
int type; | |||
message_arg_t arg; | |||
/* use empty reply if not overriden in the code that follows */ | |||
type = DBUS_TYPE_INVALID; | |||
if (strcmp (call->method_name, "Exit") == 0) | |||
{ | |||
g_exit_command = TRUE; | |||
} | |||
else if (strcmp (call->method_name, "IsStarted") == 0) | |||
{ | |||
type = DBUS_TYPE_BOOLEAN; | |||
arg.boolean = (dbus_bool_t) (controller_ptr->started ? TRUE : FALSE); | |||
} | |||
else if (strcmp (call->method_name, "StartServer") == 0) | |||
{ | |||
if (!jack_controller_start_server(controller_ptr, call)) | |||
{ | |||
jack_error ("Failed to start server"); | |||
} | |||
} | |||
else if (strcmp (call->method_name, "StopServer") == 0) | |||
{ | |||
if (!jack_controller_stop_server(controller_ptr, call)) | |||
{ | |||
jack_error ("Failed to stop server"); | |||
} | |||
} | |||
else if (strcmp (call->method_name, "GetLoad") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_DOUBLE; | |||
arg.doubl = jack_cpu_load(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "GetXruns") == 0) | |||
{ | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = controller_ptr->xruns; | |||
} | |||
else if (strcmp (call->method_name, "GetSampleRate") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = jack_get_sample_rate(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "GetLatency") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_DOUBLE; | |||
arg.doubl = ((float)jack_get_buffer_size(controller_ptr->client) / (float)jack_get_sample_rate(controller_ptr->client)) * 1000.0f; | |||
} | |||
else if (strcmp (call->method_name, "GetBufferSize") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = jack_get_buffer_size(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "SetBufferSize") == 0) | |||
{ | |||
dbus_uint32_t buffer_size; | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
if (!jack_dbus_get_method_args(call, DBUS_TYPE_UINT32, &buffer_size, DBUS_TYPE_INVALID)) | |||
{ | |||
/* jack_dbus_get_method_args() has set reply for us */ | |||
goto exit; | |||
} | |||
ret = jack_set_buffer_size(controller_ptr->client, buffer_size); | |||
if (ret != 0) | |||
{ | |||
jack_dbus_error( | |||
call, | |||
JACK_DBUS_ERROR_GENERIC, | |||
"jack_set_buffer_size(%u) failed with error %d", (unsigned int)buffer_size, ret); | |||
goto exit; | |||
} | |||
} | |||
else if (strcmp (call->method_name, "IsRealtime") == 0) | |||
{ | |||
type = DBUS_TYPE_BOOLEAN; | |||
arg.boolean = jack_is_realtime(controller_ptr->client) ? TRUE : FALSE; | |||
} | |||
else if (strcmp (call->method_name, "ResetXruns") == 0) | |||
{ | |||
controller_ptr->xruns = 0; | |||
} | |||
else | |||
{ | |||
return false; | |||
} | |||
jack_dbus_construct_method_return_single(call, type, arg); | |||
return true; | |||
not_started: | |||
jack_dbus_error (call, JACK_DBUS_ERROR_SERVER_NOT_RUNNING, | |||
"Can't execute method '%s' with stopped JACK server", call->method_name); | |||
exit: | |||
return true; | |||
} | |||
#undef controller_ptr | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(IsStarted) | |||
JACK_DBUS_METHOD_ARGUMENT("started", "b", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(StartServer) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(StopServer) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetLoad) | |||
JACK_DBUS_METHOD_ARGUMENT("load", "d", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetXruns) | |||
JACK_DBUS_METHOD_ARGUMENT("xruns_count", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetSampleRate) | |||
JACK_DBUS_METHOD_ARGUMENT("sample_rate", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetLatency) | |||
JACK_DBUS_METHOD_ARGUMENT("latency_ms", "d", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetBufferSize) | |||
JACK_DBUS_METHOD_ARGUMENT("buffer_size_frames", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(SetBufferSize) | |||
JACK_DBUS_METHOD_ARGUMENT("buffer_size_frames", "u", false) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(IsRealtime) | |||
JACK_DBUS_METHOD_ARGUMENT("realtime", "b", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(ResetXruns) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHOD_DESCRIBE(IsStarted, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(StartServer, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(StopServer, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetLoad, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetXruns, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetSampleRate, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetLatency, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetBufferSize, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(SetBufferSize, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(IsRealtime, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(ResetXruns, NULL) | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_control, "org.jackaudio.JackControl") | |||
JACK_DBUS_IFACE_HANDLER(jack_control_run_method) | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
Copyright (C) 2007-2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
#include "controller_internal.h" | |||
#define controller_ptr ((struct jack_controller *)call->context) | |||
/* | |||
* Check if the supplied method name exists in org.jackaudio.JackControl, | |||
* if it does execute it and return true. Otherwise return false. | |||
*/ | |||
static | |||
bool | |||
jack_control_run_method( | |||
struct jack_dbus_method_call * call, | |||
const struct jack_dbus_interface_method_descriptor * methods) | |||
{ | |||
int ret; | |||
int type; | |||
message_arg_t arg; | |||
/* use empty reply if not overriden in the code that follows */ | |||
type = DBUS_TYPE_INVALID; | |||
if (strcmp (call->method_name, "Exit") == 0) | |||
{ | |||
g_exit_command = TRUE; | |||
} | |||
else if (strcmp (call->method_name, "IsStarted") == 0) | |||
{ | |||
type = DBUS_TYPE_BOOLEAN; | |||
arg.boolean = (dbus_bool_t) (controller_ptr->started ? TRUE : FALSE); | |||
} | |||
else if (strcmp (call->method_name, "StartServer") == 0) | |||
{ | |||
if (!jack_controller_start_server(controller_ptr, call)) | |||
{ | |||
jack_error ("Failed to start server"); | |||
} | |||
} | |||
else if (strcmp (call->method_name, "StopServer") == 0) | |||
{ | |||
if (!jack_controller_stop_server(controller_ptr, call)) | |||
{ | |||
jack_error ("Failed to stop server"); | |||
} | |||
} | |||
else if (strcmp (call->method_name, "GetLoad") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_DOUBLE; | |||
arg.doubl = jack_cpu_load(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "GetXruns") == 0) | |||
{ | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = controller_ptr->xruns; | |||
} | |||
else if (strcmp (call->method_name, "GetSampleRate") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = jack_get_sample_rate(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "GetLatency") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_DOUBLE; | |||
arg.doubl = ((float)jack_get_buffer_size(controller_ptr->client) / (float)jack_get_sample_rate(controller_ptr->client)) * 1000.0f; | |||
} | |||
else if (strcmp (call->method_name, "GetBufferSize") == 0) | |||
{ | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
type = DBUS_TYPE_UINT32; | |||
arg.uint32 = jack_get_buffer_size(controller_ptr->client); | |||
} | |||
else if (strcmp (call->method_name, "SetBufferSize") == 0) | |||
{ | |||
dbus_uint32_t buffer_size; | |||
if (!controller_ptr->started) | |||
{ | |||
goto not_started; | |||
} | |||
if (!jack_dbus_get_method_args(call, DBUS_TYPE_UINT32, &buffer_size, DBUS_TYPE_INVALID)) | |||
{ | |||
/* jack_dbus_get_method_args() has set reply for us */ | |||
goto exit; | |||
} | |||
ret = jack_set_buffer_size(controller_ptr->client, buffer_size); | |||
if (ret != 0) | |||
{ | |||
jack_dbus_error( | |||
call, | |||
JACK_DBUS_ERROR_GENERIC, | |||
"jack_set_buffer_size(%u) failed with error %d", (unsigned int)buffer_size, ret); | |||
goto exit; | |||
} | |||
} | |||
else if (strcmp (call->method_name, "IsRealtime") == 0) | |||
{ | |||
type = DBUS_TYPE_BOOLEAN; | |||
arg.boolean = jack_is_realtime(controller_ptr->client) ? TRUE : FALSE; | |||
} | |||
else if (strcmp (call->method_name, "ResetXruns") == 0) | |||
{ | |||
controller_ptr->xruns = 0; | |||
} | |||
else | |||
{ | |||
return false; | |||
} | |||
jack_dbus_construct_method_return_single(call, type, arg); | |||
return true; | |||
not_started: | |||
jack_dbus_error (call, JACK_DBUS_ERROR_SERVER_NOT_RUNNING, | |||
"Can't execute method '%s' with stopped JACK server", call->method_name); | |||
exit: | |||
return true; | |||
} | |||
#undef controller_ptr | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(IsStarted) | |||
JACK_DBUS_METHOD_ARGUMENT("started", "b", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(StartServer) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(StopServer) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetLoad) | |||
JACK_DBUS_METHOD_ARGUMENT("load", "d", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetXruns) | |||
JACK_DBUS_METHOD_ARGUMENT("xruns_count", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetSampleRate) | |||
JACK_DBUS_METHOD_ARGUMENT("sample_rate", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetLatency) | |||
JACK_DBUS_METHOD_ARGUMENT("latency_ms", "d", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(GetBufferSize) | |||
JACK_DBUS_METHOD_ARGUMENT("buffer_size_frames", "u", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(SetBufferSize) | |||
JACK_DBUS_METHOD_ARGUMENT("buffer_size_frames", "u", false) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(IsRealtime) | |||
JACK_DBUS_METHOD_ARGUMENT("realtime", "b", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(ResetXruns) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHOD_DESCRIBE(IsStarted, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(StartServer, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(StopServer, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetLoad, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetXruns, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetSampleRate, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetLatency, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(GetBufferSize, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(SetBufferSize, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(IsRealtime, NULL) | |||
JACK_DBUS_METHOD_DESCRIBE(ResetXruns, NULL) | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_control, "org.jackaudio.JackControl") | |||
JACK_DBUS_IFACE_HANDLER(jack_control_run_method) | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END |
@@ -150,459 +150,3 @@ jack_controller_introspect_init() | |||
*g_buffer_ptr = 0; | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007-2008 Nedko Arnaudov | |||
Copyright (C) 2007-2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
static char g_xml_data[102400]; | |||
static | |||
void | |||
jack_controller_dbus_introspect( | |||
struct jack_dbus_method_call * call) | |||
{ | |||
jack_dbus_construct_method_return_single( | |||
call, | |||
DBUS_TYPE_STRING, | |||
(message_arg_t)(const char *)g_xml_data); | |||
} | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(Introspect) | |||
JACK_DBUS_METHOD_ARGUMENT("xml_data", "s", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHOD_DESCRIBE(Introspect, jack_controller_dbus_introspect) | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_introspectable, "org.freedesktop.DBus.Introspectable") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
static char * g_buffer_ptr; | |||
static | |||
void | |||
write_line_format(const char * format, ...) | |||
{ | |||
va_list ap; | |||
va_start(ap, format); | |||
g_buffer_ptr += vsprintf(g_buffer_ptr, format, ap); | |||
va_end(ap); | |||
} | |||
static | |||
void | |||
write_line(const char * line) | |||
{ | |||
write_line_format("%s\n", line); | |||
} | |||
void jack_controller_introspect_init() __attribute__((constructor)); | |||
void | |||
jack_controller_introspect_init() | |||
{ | |||
struct jack_dbus_interface_descriptor ** interface_ptr_ptr; | |||
const struct jack_dbus_interface_method_descriptor * method_ptr; | |||
const struct jack_dbus_interface_method_argument_descriptor * method_argument_ptr; | |||
const struct jack_dbus_interface_signal_descriptor * signal_ptr; | |||
const struct jack_dbus_interface_signal_argument_descriptor * signal_argument_ptr; | |||
g_buffer_ptr = g_xml_data; | |||
write_line("<!DOCTYPE node PUBLIC \"-//freedesktop//DTD D-BUS Object Introspection 1.0//EN\""); | |||
write_line("\"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd\">"); | |||
write_line("<node name=\"" JACK_CONTROLLER_OBJECT_PATH "\">"); | |||
interface_ptr_ptr = g_jackcontroller_interfaces; | |||
while (*interface_ptr_ptr != NULL) | |||
{ | |||
write_line_format(" <interface name=\"%s\">\n", (*interface_ptr_ptr)->name); | |||
if ((*interface_ptr_ptr)->methods != NULL) | |||
{ | |||
method_ptr = (*interface_ptr_ptr)->methods; | |||
while (method_ptr->name != NULL) | |||
{ | |||
write_line_format(" <method name=\"%s\">\n", method_ptr->name); | |||
method_argument_ptr = method_ptr->arguments; | |||
while (method_argument_ptr->name != NULL) | |||
{ | |||
write_line_format( | |||
" <arg name=\"%s\" type=\"%s\" direction=\"%s\" />\n", | |||
method_argument_ptr->name, | |||
method_argument_ptr->type, | |||
method_argument_ptr->direction_out ? "out" : "in"); | |||
method_argument_ptr++; | |||
} | |||
write_line(" </method>"); | |||
method_ptr++; | |||
} | |||
} | |||
if ((*interface_ptr_ptr)->signals != NULL) | |||
{ | |||
signal_ptr = (*interface_ptr_ptr)->signals; | |||
while (signal_ptr->name != NULL) | |||
{ | |||
write_line_format(" <signal name=\"%s\">\n", signal_ptr->name); | |||
signal_argument_ptr = signal_ptr->arguments; | |||
while (signal_argument_ptr->name != NULL) | |||
{ | |||
write_line_format( | |||
" <arg name=\"%s\" type=\"%s\" />\n", | |||
signal_argument_ptr->name, | |||
signal_argument_ptr->type); | |||
signal_argument_ptr++; | |||
} | |||
write_line(" </signal>"); | |||
signal_ptr++; | |||
} | |||
} | |||
write_line(" </interface>"); | |||
interface_ptr_ptr++; | |||
} | |||
write_line("</node>"); | |||
*g_buffer_ptr = 0; | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007-2008 Nedko Arnaudov | |||
Copyright (C) 2007-2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
static char g_xml_data[102400]; | |||
static | |||
void | |||
jack_controller_dbus_introspect( | |||
struct jack_dbus_method_call * call) | |||
{ | |||
jack_dbus_construct_method_return_single( | |||
call, | |||
DBUS_TYPE_STRING, | |||
(message_arg_t)(const char *)g_xml_data); | |||
} | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(Introspect) | |||
JACK_DBUS_METHOD_ARGUMENT("xml_data", "s", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHOD_DESCRIBE(Introspect, jack_controller_dbus_introspect) | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_introspectable, "org.freedesktop.DBus.Introspectable") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
static char * g_buffer_ptr; | |||
static | |||
void | |||
write_line_format(const char * format, ...) | |||
{ | |||
va_list ap; | |||
va_start(ap, format); | |||
g_buffer_ptr += vsprintf(g_buffer_ptr, format, ap); | |||
va_end(ap); | |||
} | |||
static | |||
void | |||
write_line(const char * line) | |||
{ | |||
write_line_format("%s\n", line); | |||
} | |||
void jack_controller_introspect_init() __attribute__((constructor)); | |||
void | |||
jack_controller_introspect_init() | |||
{ | |||
struct jack_dbus_interface_descriptor ** interface_ptr_ptr; | |||
const struct jack_dbus_interface_method_descriptor * method_ptr; | |||
const struct jack_dbus_interface_method_argument_descriptor * method_argument_ptr; | |||
const struct jack_dbus_interface_signal_descriptor * signal_ptr; | |||
const struct jack_dbus_interface_signal_argument_descriptor * signal_argument_ptr; | |||
g_buffer_ptr = g_xml_data; | |||
write_line("<!DOCTYPE node PUBLIC \"-//freedesktop//DTD D-BUS Object Introspection 1.0//EN\""); | |||
write_line("\"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd\">"); | |||
write_line("<node name=\"" JACK_CONTROLLER_OBJECT_PATH "\">"); | |||
interface_ptr_ptr = g_jackcontroller_interfaces; | |||
while (*interface_ptr_ptr != NULL) | |||
{ | |||
write_line_format(" <interface name=\"%s\">\n", (*interface_ptr_ptr)->name); | |||
if ((*interface_ptr_ptr)->methods != NULL) | |||
{ | |||
method_ptr = (*interface_ptr_ptr)->methods; | |||
while (method_ptr->name != NULL) | |||
{ | |||
write_line_format(" <method name=\"%s\">\n", method_ptr->name); | |||
method_argument_ptr = method_ptr->arguments; | |||
while (method_argument_ptr->name != NULL) | |||
{ | |||
write_line_format( | |||
" <arg name=\"%s\" type=\"%s\" direction=\"%s\" />\n", | |||
method_argument_ptr->name, | |||
method_argument_ptr->type, | |||
method_argument_ptr->direction_out ? "out" : "in"); | |||
method_argument_ptr++; | |||
} | |||
write_line(" </method>"); | |||
method_ptr++; | |||
} | |||
} | |||
if ((*interface_ptr_ptr)->signals != NULL) | |||
{ | |||
signal_ptr = (*interface_ptr_ptr)->signals; | |||
while (signal_ptr->name != NULL) | |||
{ | |||
write_line_format(" <signal name=\"%s\">\n", signal_ptr->name); | |||
signal_argument_ptr = signal_ptr->arguments; | |||
while (signal_argument_ptr->name != NULL) | |||
{ | |||
write_line_format( | |||
" <arg name=\"%s\" type=\"%s\" />\n", | |||
signal_argument_ptr->name, | |||
signal_argument_ptr->type); | |||
signal_argument_ptr++; | |||
} | |||
write_line(" </signal>"); | |||
signal_ptr++; | |||
} | |||
} | |||
write_line(" </interface>"); | |||
interface_ptr_ptr++; | |||
} | |||
write_line("</node>"); | |||
*g_buffer_ptr = 0; | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007-2008 Nedko Arnaudov | |||
Copyright (C) 2007-2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
static char g_xml_data[102400]; | |||
static | |||
void | |||
jack_controller_dbus_introspect( | |||
struct jack_dbus_method_call * call) | |||
{ | |||
jack_dbus_construct_method_return_single( | |||
call, | |||
DBUS_TYPE_STRING, | |||
(message_arg_t)(const char *)g_xml_data); | |||
} | |||
JACK_DBUS_METHOD_ARGUMENTS_BEGIN(Introspect) | |||
JACK_DBUS_METHOD_ARGUMENT("xml_data", "s", true) | |||
JACK_DBUS_METHOD_ARGUMENTS_END | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHOD_DESCRIBE(Introspect, jack_controller_dbus_introspect) | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_introspectable, "org.freedesktop.DBus.Introspectable") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
static char * g_buffer_ptr; | |||
static | |||
void | |||
write_line_format(const char * format, ...) | |||
{ | |||
va_list ap; | |||
va_start(ap, format); | |||
g_buffer_ptr += vsprintf(g_buffer_ptr, format, ap); | |||
va_end(ap); | |||
} | |||
static | |||
void | |||
write_line(const char * line) | |||
{ | |||
write_line_format("%s\n", line); | |||
} | |||
void jack_controller_introspect_init() __attribute__((constructor)); | |||
void | |||
jack_controller_introspect_init() | |||
{ | |||
struct jack_dbus_interface_descriptor ** interface_ptr_ptr; | |||
const struct jack_dbus_interface_method_descriptor * method_ptr; | |||
const struct jack_dbus_interface_method_argument_descriptor * method_argument_ptr; | |||
const struct jack_dbus_interface_signal_descriptor * signal_ptr; | |||
const struct jack_dbus_interface_signal_argument_descriptor * signal_argument_ptr; | |||
g_buffer_ptr = g_xml_data; | |||
write_line("<!DOCTYPE node PUBLIC \"-//freedesktop//DTD D-BUS Object Introspection 1.0//EN\""); | |||
write_line("\"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd\">"); | |||
write_line("<node name=\"" JACK_CONTROLLER_OBJECT_PATH "\">"); | |||
interface_ptr_ptr = g_jackcontroller_interfaces; | |||
while (*interface_ptr_ptr != NULL) | |||
{ | |||
write_line_format(" <interface name=\"%s\">\n", (*interface_ptr_ptr)->name); | |||
if ((*interface_ptr_ptr)->methods != NULL) | |||
{ | |||
method_ptr = (*interface_ptr_ptr)->methods; | |||
while (method_ptr->name != NULL) | |||
{ | |||
write_line_format(" <method name=\"%s\">\n", method_ptr->name); | |||
method_argument_ptr = method_ptr->arguments; | |||
while (method_argument_ptr->name != NULL) | |||
{ | |||
write_line_format( | |||
" <arg name=\"%s\" type=\"%s\" direction=\"%s\" />\n", | |||
method_argument_ptr->name, | |||
method_argument_ptr->type, | |||
method_argument_ptr->direction_out ? "out" : "in"); | |||
method_argument_ptr++; | |||
} | |||
write_line(" </method>"); | |||
method_ptr++; | |||
} | |||
} | |||
if ((*interface_ptr_ptr)->signals != NULL) | |||
{ | |||
signal_ptr = (*interface_ptr_ptr)->signals; | |||
while (signal_ptr->name != NULL) | |||
{ | |||
write_line_format(" <signal name=\"%s\">\n", signal_ptr->name); | |||
signal_argument_ptr = signal_ptr->arguments; | |||
while (signal_argument_ptr->name != NULL) | |||
{ | |||
write_line_format( | |||
" <arg name=\"%s\" type=\"%s\" />\n", | |||
signal_argument_ptr->name, | |||
signal_argument_ptr->type); | |||
signal_argument_ptr++; | |||
} | |||
write_line(" </signal>"); | |||
signal_ptr++; | |||
} | |||
} | |||
write_line(" </interface>"); | |||
interface_ptr_ptr++; | |||
} | |||
write_line("</node>"); | |||
*g_buffer_ptr = 0; | |||
} |
@@ -32,105 +32,3 @@ JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_transport, "org.jackaudio.JackTransport") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2008 Nedko Arnaudov | |||
Copyright (C) 2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_transport, "org.jackaudio.JackTransport") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2008 Nedko Arnaudov | |||
Copyright (C) 2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_transport, "org.jackaudio.JackTransport") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2008 Nedko Arnaudov | |||
Copyright (C) 2008 Juuso Alasuutari | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <assert.h> | |||
#include <dbus/dbus.h> | |||
#include "jackdbus.h" | |||
JACK_DBUS_METHODS_BEGIN | |||
JACK_DBUS_METHODS_END | |||
JACK_DBUS_IFACE_BEGIN(g_jack_controller_iface_transport, "org.jackaudio.JackTransport") | |||
JACK_DBUS_IFACE_EXPOSE_METHODS | |||
JACK_DBUS_IFACE_END |
@@ -311,942 +311,3 @@ jack_controller_settings_save_driver_options( | |||
{ | |||
return jack_controller_settings_save_options(context, jackctl_driver_get_parameters(driver), dbus_call_context_ptr); | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <dbus/dbus.h> | |||
#include "controller_internal.h" | |||
void | |||
jack_controller_settings_set_bool_option( | |||
const char *value_str, | |||
int *value_ptr) | |||
{ | |||
if (strcmp(value_str, "true") == 0) | |||
{ | |||
*value_ptr = true; | |||
} | |||
else if (strcmp(value_str, "false") == 0) | |||
{ | |||
*value_ptr = false; | |||
} | |||
else | |||
{ | |||
jack_error("ignoring unknown bool value \"%s\"", value_str); | |||
} | |||
} | |||
void | |||
jack_controller_settings_set_sint_option( | |||
const char *value_str, | |||
int *value_ptr) | |||
{ | |||
*value_ptr = atoi(value_str); | |||
} | |||
void | |||
jack_controller_settings_set_uint_option( | |||
const char *value_str, | |||
unsigned int *value_ptr) | |||
{ | |||
*value_ptr = strtoul(value_str, NULL, 10); | |||
} | |||
void | |||
jack_controller_settings_set_char_option( | |||
const char *value_str, | |||
char *value_ptr) | |||
{ | |||
if (value_str[0] == 0 || value_str[1] != 0) | |||
{ | |||
jack_error("invalid char option value \"%s\"", value_str); | |||
return; | |||
} | |||
*value_ptr = *value_str; | |||
} | |||
void | |||
jack_controller_settings_set_string_option( | |||
const char *value_str, | |||
char *value_ptr, | |||
size_t max_size) | |||
{ | |||
size_t size; | |||
size = strlen(value_str); | |||
if (size >= max_size) | |||
{ | |||
jack_error("string option value \"%s\" is too long, max is %u chars (including terminating zero)", value_str, (unsigned int)max_size); | |||
return; | |||
} | |||
strcpy(value_ptr, value_str); | |||
} | |||
void | |||
jack_controller_settings_set_driver_option( | |||
jackctl_driver_t *driver, | |||
const char *option_name, | |||
const char *option_value) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
int value_int; | |||
unsigned int value_uint; | |||
union jackctl_parameter_value value; | |||
jack_info("setting driver option \"%s\" to value \"%s\"", option_name, option_value); | |||
parameter = jack_controller_find_parameter(jackctl_driver_get_parameters(driver), option_name); | |||
if (parameter == NULL) | |||
{ | |||
jack_error( | |||
"Unknown parameter \"%s\" of driver \"%s\"", | |||
option_name, | |||
jackctl_driver_get_name(driver)); | |||
return; | |||
} | |||
type = jackctl_parameter_get_type(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
jack_controller_settings_set_sint_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
case JackParamUInt: | |||
jack_controller_settings_set_uint_option(option_value, &value_uint); | |||
value.ui = value_uint; | |||
break; | |||
case JackParamChar: | |||
jack_controller_settings_set_char_option(option_value, &value.c); | |||
break; | |||
case JackParamString: | |||
jack_controller_settings_set_string_option(option_value, value.str, sizeof(value.str)); | |||
break; | |||
case JackParamBool: | |||
jack_controller_settings_set_bool_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
default: | |||
jack_error("Parameter \"%s\" of driver \"%s\" is of unknown type %d", | |||
jackctl_parameter_get_name(parameter), | |||
jackctl_driver_get_name(driver), | |||
type); | |||
} | |||
jackctl_parameter_set_value(parameter, &value); | |||
} | |||
void | |||
jack_controller_settings_set_engine_option( | |||
struct jack_controller *controller_ptr, | |||
const char *option_name, | |||
const char *option_value) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
int value_int; | |||
unsigned int value_uint; | |||
union jackctl_parameter_value value; | |||
jack_info("setting engine option \"%s\" to value \"%s\"", option_name, option_value); | |||
if (strcmp(option_name, "driver") == 0) | |||
{ | |||
if (!jack_controller_select_driver(controller_ptr, option_value)) | |||
{ | |||
jack_error("unknown driver '%s'", option_value); | |||
} | |||
return; | |||
} | |||
parameter = jack_controller_find_parameter(jackctl_server_get_parameters(controller_ptr->server), option_name); | |||
if (parameter == NULL) | |||
{ | |||
jack_error( | |||
"Unknown engine parameter \"%s\"", | |||
option_name); | |||
return; | |||
} | |||
type = jackctl_parameter_get_type(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
jack_controller_settings_set_sint_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
case JackParamUInt: | |||
jack_controller_settings_set_uint_option(option_value, &value_uint); | |||
value.ui = value_uint; | |||
break; | |||
case JackParamChar: | |||
jack_controller_settings_set_char_option(option_value, &value.c); | |||
break; | |||
case JackParamString: | |||
jack_controller_settings_set_string_option(option_value, value.str, sizeof(value.str)); | |||
break; | |||
case JackParamBool: | |||
jack_controller_settings_set_bool_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
default: | |||
jack_error("Engine parameter \"%s\" is of unknown type %d", | |||
jackctl_parameter_get_name(parameter), | |||
type); | |||
} | |||
jackctl_parameter_set_value(parameter, &value); | |||
} | |||
static | |||
bool | |||
jack_controller_settings_save_options( | |||
void *context, | |||
const JSList * parameters_list, | |||
void *dbus_call_context_ptr) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
union jackctl_parameter_value value; | |||
const char * name; | |||
char value_str[50]; | |||
while (parameters_list != NULL) | |||
{ | |||
parameter = (jackctl_parameter_t *)parameters_list->data; | |||
if (jackctl_parameter_is_set(parameter)) | |||
{ | |||
type = jackctl_parameter_get_type(parameter); | |||
value = jackctl_parameter_get_value(parameter); | |||
name = jackctl_parameter_get_name(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
sprintf(value_str, "%d", (int)value.i); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamUInt: | |||
sprintf(value_str, "%u", (unsigned int)value.ui); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamChar: | |||
sprintf(value_str, "%c", (char)value.c); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamString: | |||
if (!jack_controller_settings_write_option(context, name, value.str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamBool: | |||
if (!jack_controller_settings_write_option(context, name, value.b ? "true" : "false", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
default: | |||
jack_error("parameter of unknown type %d", type); | |||
} | |||
} | |||
parameters_list = jack_slist_next(parameters_list); | |||
} | |||
return true; | |||
} | |||
bool | |||
jack_controller_settings_save_engine_options( | |||
void *context, | |||
struct jack_controller *controller_ptr, | |||
void *dbus_call_context_ptr) | |||
{ | |||
if (controller_ptr->driver != NULL) | |||
{ | |||
if (!jack_controller_settings_write_option( | |||
context, | |||
"driver", | |||
jackctl_driver_get_name(controller_ptr->driver), | |||
dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
} | |||
return jack_controller_settings_save_options(context, jackctl_server_get_parameters(controller_ptr->server), dbus_call_context_ptr); | |||
} | |||
bool | |||
jack_controller_settings_save_driver_options( | |||
void *context, | |||
jackctl_driver_t *driver, | |||
void *dbus_call_context_ptr) | |||
{ | |||
return jack_controller_settings_save_options(context, jackctl_driver_get_parameters(driver), dbus_call_context_ptr); | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <dbus/dbus.h> | |||
#include "controller_internal.h" | |||
void | |||
jack_controller_settings_set_bool_option( | |||
const char *value_str, | |||
int *value_ptr) | |||
{ | |||
if (strcmp(value_str, "true") == 0) | |||
{ | |||
*value_ptr = true; | |||
} | |||
else if (strcmp(value_str, "false") == 0) | |||
{ | |||
*value_ptr = false; | |||
} | |||
else | |||
{ | |||
jack_error("ignoring unknown bool value \"%s\"", value_str); | |||
} | |||
} | |||
void | |||
jack_controller_settings_set_sint_option( | |||
const char *value_str, | |||
int *value_ptr) | |||
{ | |||
*value_ptr = atoi(value_str); | |||
} | |||
void | |||
jack_controller_settings_set_uint_option( | |||
const char *value_str, | |||
unsigned int *value_ptr) | |||
{ | |||
*value_ptr = strtoul(value_str, NULL, 10); | |||
} | |||
void | |||
jack_controller_settings_set_char_option( | |||
const char *value_str, | |||
char *value_ptr) | |||
{ | |||
if (value_str[0] == 0 || value_str[1] != 0) | |||
{ | |||
jack_error("invalid char option value \"%s\"", value_str); | |||
return; | |||
} | |||
*value_ptr = *value_str; | |||
} | |||
void | |||
jack_controller_settings_set_string_option( | |||
const char *value_str, | |||
char *value_ptr, | |||
size_t max_size) | |||
{ | |||
size_t size; | |||
size = strlen(value_str); | |||
if (size >= max_size) | |||
{ | |||
jack_error("string option value \"%s\" is too long, max is %u chars (including terminating zero)", value_str, (unsigned int)max_size); | |||
return; | |||
} | |||
strcpy(value_ptr, value_str); | |||
} | |||
void | |||
jack_controller_settings_set_driver_option( | |||
jackctl_driver_t *driver, | |||
const char *option_name, | |||
const char *option_value) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
int value_int; | |||
unsigned int value_uint; | |||
union jackctl_parameter_value value; | |||
jack_info("setting driver option \"%s\" to value \"%s\"", option_name, option_value); | |||
parameter = jack_controller_find_parameter(jackctl_driver_get_parameters(driver), option_name); | |||
if (parameter == NULL) | |||
{ | |||
jack_error( | |||
"Unknown parameter \"%s\" of driver \"%s\"", | |||
option_name, | |||
jackctl_driver_get_name(driver)); | |||
return; | |||
} | |||
type = jackctl_parameter_get_type(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
jack_controller_settings_set_sint_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
case JackParamUInt: | |||
jack_controller_settings_set_uint_option(option_value, &value_uint); | |||
value.ui = value_uint; | |||
break; | |||
case JackParamChar: | |||
jack_controller_settings_set_char_option(option_value, &value.c); | |||
break; | |||
case JackParamString: | |||
jack_controller_settings_set_string_option(option_value, value.str, sizeof(value.str)); | |||
break; | |||
case JackParamBool: | |||
jack_controller_settings_set_bool_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
default: | |||
jack_error("Parameter \"%s\" of driver \"%s\" is of unknown type %d", | |||
jackctl_parameter_get_name(parameter), | |||
jackctl_driver_get_name(driver), | |||
type); | |||
} | |||
jackctl_parameter_set_value(parameter, &value); | |||
} | |||
void | |||
jack_controller_settings_set_engine_option( | |||
struct jack_controller *controller_ptr, | |||
const char *option_name, | |||
const char *option_value) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
int value_int; | |||
unsigned int value_uint; | |||
union jackctl_parameter_value value; | |||
jack_info("setting engine option \"%s\" to value \"%s\"", option_name, option_value); | |||
if (strcmp(option_name, "driver") == 0) | |||
{ | |||
if (!jack_controller_select_driver(controller_ptr, option_value)) | |||
{ | |||
jack_error("unknown driver '%s'", option_value); | |||
} | |||
return; | |||
} | |||
parameter = jack_controller_find_parameter(jackctl_server_get_parameters(controller_ptr->server), option_name); | |||
if (parameter == NULL) | |||
{ | |||
jack_error( | |||
"Unknown engine parameter \"%s\"", | |||
option_name); | |||
return; | |||
} | |||
type = jackctl_parameter_get_type(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
jack_controller_settings_set_sint_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
case JackParamUInt: | |||
jack_controller_settings_set_uint_option(option_value, &value_uint); | |||
value.ui = value_uint; | |||
break; | |||
case JackParamChar: | |||
jack_controller_settings_set_char_option(option_value, &value.c); | |||
break; | |||
case JackParamString: | |||
jack_controller_settings_set_string_option(option_value, value.str, sizeof(value.str)); | |||
break; | |||
case JackParamBool: | |||
jack_controller_settings_set_bool_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
default: | |||
jack_error("Engine parameter \"%s\" is of unknown type %d", | |||
jackctl_parameter_get_name(parameter), | |||
type); | |||
} | |||
jackctl_parameter_set_value(parameter, &value); | |||
} | |||
static | |||
bool | |||
jack_controller_settings_save_options( | |||
void *context, | |||
const JSList * parameters_list, | |||
void *dbus_call_context_ptr) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
union jackctl_parameter_value value; | |||
const char * name; | |||
char value_str[50]; | |||
while (parameters_list != NULL) | |||
{ | |||
parameter = (jackctl_parameter_t *)parameters_list->data; | |||
if (jackctl_parameter_is_set(parameter)) | |||
{ | |||
type = jackctl_parameter_get_type(parameter); | |||
value = jackctl_parameter_get_value(parameter); | |||
name = jackctl_parameter_get_name(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
sprintf(value_str, "%d", (int)value.i); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamUInt: | |||
sprintf(value_str, "%u", (unsigned int)value.ui); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamChar: | |||
sprintf(value_str, "%c", (char)value.c); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamString: | |||
if (!jack_controller_settings_write_option(context, name, value.str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamBool: | |||
if (!jack_controller_settings_write_option(context, name, value.b ? "true" : "false", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
default: | |||
jack_error("parameter of unknown type %d", type); | |||
} | |||
} | |||
parameters_list = jack_slist_next(parameters_list); | |||
} | |||
return true; | |||
} | |||
bool | |||
jack_controller_settings_save_engine_options( | |||
void *context, | |||
struct jack_controller *controller_ptr, | |||
void *dbus_call_context_ptr) | |||
{ | |||
if (controller_ptr->driver != NULL) | |||
{ | |||
if (!jack_controller_settings_write_option( | |||
context, | |||
"driver", | |||
jackctl_driver_get_name(controller_ptr->driver), | |||
dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
} | |||
return jack_controller_settings_save_options(context, jackctl_server_get_parameters(controller_ptr->server), dbus_call_context_ptr); | |||
} | |||
bool | |||
jack_controller_settings_save_driver_options( | |||
void *context, | |||
jackctl_driver_t *driver, | |||
void *dbus_call_context_ptr) | |||
{ | |||
return jack_controller_settings_save_options(context, jackctl_driver_get_parameters(driver), dbus_call_context_ptr); | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <string.h> | |||
#include <stdio.h> | |||
#include <dbus/dbus.h> | |||
#include "controller_internal.h" | |||
void | |||
jack_controller_settings_set_bool_option( | |||
const char *value_str, | |||
int *value_ptr) | |||
{ | |||
if (strcmp(value_str, "true") == 0) | |||
{ | |||
*value_ptr = true; | |||
} | |||
else if (strcmp(value_str, "false") == 0) | |||
{ | |||
*value_ptr = false; | |||
} | |||
else | |||
{ | |||
jack_error("ignoring unknown bool value \"%s\"", value_str); | |||
} | |||
} | |||
void | |||
jack_controller_settings_set_sint_option( | |||
const char *value_str, | |||
int *value_ptr) | |||
{ | |||
*value_ptr = atoi(value_str); | |||
} | |||
void | |||
jack_controller_settings_set_uint_option( | |||
const char *value_str, | |||
unsigned int *value_ptr) | |||
{ | |||
*value_ptr = strtoul(value_str, NULL, 10); | |||
} | |||
void | |||
jack_controller_settings_set_char_option( | |||
const char *value_str, | |||
char *value_ptr) | |||
{ | |||
if (value_str[0] == 0 || value_str[1] != 0) | |||
{ | |||
jack_error("invalid char option value \"%s\"", value_str); | |||
return; | |||
} | |||
*value_ptr = *value_str; | |||
} | |||
void | |||
jack_controller_settings_set_string_option( | |||
const char *value_str, | |||
char *value_ptr, | |||
size_t max_size) | |||
{ | |||
size_t size; | |||
size = strlen(value_str); | |||
if (size >= max_size) | |||
{ | |||
jack_error("string option value \"%s\" is too long, max is %u chars (including terminating zero)", value_str, (unsigned int)max_size); | |||
return; | |||
} | |||
strcpy(value_ptr, value_str); | |||
} | |||
void | |||
jack_controller_settings_set_driver_option( | |||
jackctl_driver_t *driver, | |||
const char *option_name, | |||
const char *option_value) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
int value_int; | |||
unsigned int value_uint; | |||
union jackctl_parameter_value value; | |||
jack_info("setting driver option \"%s\" to value \"%s\"", option_name, option_value); | |||
parameter = jack_controller_find_parameter(jackctl_driver_get_parameters(driver), option_name); | |||
if (parameter == NULL) | |||
{ | |||
jack_error( | |||
"Unknown parameter \"%s\" of driver \"%s\"", | |||
option_name, | |||
jackctl_driver_get_name(driver)); | |||
return; | |||
} | |||
type = jackctl_parameter_get_type(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
jack_controller_settings_set_sint_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
case JackParamUInt: | |||
jack_controller_settings_set_uint_option(option_value, &value_uint); | |||
value.ui = value_uint; | |||
break; | |||
case JackParamChar: | |||
jack_controller_settings_set_char_option(option_value, &value.c); | |||
break; | |||
case JackParamString: | |||
jack_controller_settings_set_string_option(option_value, value.str, sizeof(value.str)); | |||
break; | |||
case JackParamBool: | |||
jack_controller_settings_set_bool_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
default: | |||
jack_error("Parameter \"%s\" of driver \"%s\" is of unknown type %d", | |||
jackctl_parameter_get_name(parameter), | |||
jackctl_driver_get_name(driver), | |||
type); | |||
} | |||
jackctl_parameter_set_value(parameter, &value); | |||
} | |||
void | |||
jack_controller_settings_set_engine_option( | |||
struct jack_controller *controller_ptr, | |||
const char *option_name, | |||
const char *option_value) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
int value_int; | |||
unsigned int value_uint; | |||
union jackctl_parameter_value value; | |||
jack_info("setting engine option \"%s\" to value \"%s\"", option_name, option_value); | |||
if (strcmp(option_name, "driver") == 0) | |||
{ | |||
if (!jack_controller_select_driver(controller_ptr, option_value)) | |||
{ | |||
jack_error("unknown driver '%s'", option_value); | |||
} | |||
return; | |||
} | |||
parameter = jack_controller_find_parameter(jackctl_server_get_parameters(controller_ptr->server), option_name); | |||
if (parameter == NULL) | |||
{ | |||
jack_error( | |||
"Unknown engine parameter \"%s\"", | |||
option_name); | |||
return; | |||
} | |||
type = jackctl_parameter_get_type(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
jack_controller_settings_set_sint_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
case JackParamUInt: | |||
jack_controller_settings_set_uint_option(option_value, &value_uint); | |||
value.ui = value_uint; | |||
break; | |||
case JackParamChar: | |||
jack_controller_settings_set_char_option(option_value, &value.c); | |||
break; | |||
case JackParamString: | |||
jack_controller_settings_set_string_option(option_value, value.str, sizeof(value.str)); | |||
break; | |||
case JackParamBool: | |||
jack_controller_settings_set_bool_option(option_value, &value_int); | |||
value.i = value_int; | |||
break; | |||
default: | |||
jack_error("Engine parameter \"%s\" is of unknown type %d", | |||
jackctl_parameter_get_name(parameter), | |||
type); | |||
} | |||
jackctl_parameter_set_value(parameter, &value); | |||
} | |||
static | |||
bool | |||
jack_controller_settings_save_options( | |||
void *context, | |||
const JSList * parameters_list, | |||
void *dbus_call_context_ptr) | |||
{ | |||
jackctl_parameter_t *parameter; | |||
jackctl_param_type_t type; | |||
union jackctl_parameter_value value; | |||
const char * name; | |||
char value_str[50]; | |||
while (parameters_list != NULL) | |||
{ | |||
parameter = (jackctl_parameter_t *)parameters_list->data; | |||
if (jackctl_parameter_is_set(parameter)) | |||
{ | |||
type = jackctl_parameter_get_type(parameter); | |||
value = jackctl_parameter_get_value(parameter); | |||
name = jackctl_parameter_get_name(parameter); | |||
switch (type) | |||
{ | |||
case JackParamInt: | |||
sprintf(value_str, "%d", (int)value.i); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamUInt: | |||
sprintf(value_str, "%u", (unsigned int)value.ui); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamChar: | |||
sprintf(value_str, "%c", (char)value.c); | |||
if (!jack_controller_settings_write_option(context, name, value_str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamString: | |||
if (!jack_controller_settings_write_option(context, name, value.str, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
case JackParamBool: | |||
if (!jack_controller_settings_write_option(context, name, value.b ? "true" : "false", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
break; | |||
default: | |||
jack_error("parameter of unknown type %d", type); | |||
} | |||
} | |||
parameters_list = jack_slist_next(parameters_list); | |||
} | |||
return true; | |||
} | |||
bool | |||
jack_controller_settings_save_engine_options( | |||
void *context, | |||
struct jack_controller *controller_ptr, | |||
void *dbus_call_context_ptr) | |||
{ | |||
if (controller_ptr->driver != NULL) | |||
{ | |||
if (!jack_controller_settings_write_option( | |||
context, | |||
"driver", | |||
jackctl_driver_get_name(controller_ptr->driver), | |||
dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
} | |||
return jack_controller_settings_save_options(context, jackctl_server_get_parameters(controller_ptr->server), dbus_call_context_ptr); | |||
} | |||
bool | |||
jack_controller_settings_save_driver_options( | |||
void *context, | |||
jackctl_driver_t *driver, | |||
void *dbus_call_context_ptr) | |||
{ | |||
return jack_controller_settings_save_options(context, jackctl_driver_get_parameters(driver), dbus_call_context_ptr); | |||
} |
@@ -315,954 +315,3 @@ exit_free_filename: | |||
exit: | |||
return; | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <sys/types.h> | |||
#include <sys/stat.h> | |||
#include <unistd.h> | |||
#include <fcntl.h> | |||
#include <errno.h> | |||
#include <string.h> | |||
#include <expat.h> | |||
#include <dbus/dbus.h> | |||
#include "controller_internal.h" | |||
#include "jackdbus.h" | |||
bool | |||
jack_controller_settings_init() | |||
{ | |||
return true; | |||
} | |||
void | |||
jack_controller_settings_uninit() | |||
{ | |||
} | |||
#define PARSE_CONTEXT_ROOT 0 | |||
#define PARSE_CONTEXT_JACK 1 | |||
#define PARSE_CONTEXT_ENGINE 1 | |||
#define PARSE_CONTEXT_DRIVERS 2 | |||
#define PARSE_CONTEXT_DRIVER 3 | |||
#define PARSE_CONTEXT_OPTION 4 | |||
#define MAX_STACK_DEPTH 10 | |||
struct parse_context | |||
{ | |||
struct jack_controller *controller_ptr; | |||
XML_Bool error; | |||
unsigned int element[MAX_STACK_DEPTH]; | |||
signed int depth; | |||
jackctl_driver_t *driver; | |||
char option[JACK_PARAM_STRING_MAX+1]; | |||
int option_used; | |||
char *name; | |||
}; | |||
#define context_ptr ((struct parse_context *)data) | |||
void | |||
jack_controller_settings_callback_chrdata(void *data, const XML_Char *s, int len) | |||
{ | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
if (context_ptr->element[context_ptr->depth] == PARSE_CONTEXT_OPTION) | |||
{ | |||
if (context_ptr->option_used + len >= JACK_PARAM_STRING_MAX) | |||
{ | |||
jack_error("xml parse max char data length reached"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
memcpy(context_ptr->option + context_ptr->option_used, s, len); | |||
context_ptr->option_used += len; | |||
} | |||
} | |||
void | |||
jack_controller_settings_callback_elstart(void *data, const char *el, const char **attr) | |||
{ | |||
jackctl_driver_t *driver; | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
if (context_ptr->depth + 1 >= MAX_STACK_DEPTH) | |||
{ | |||
jack_error("xml parse max stack depth reached"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
if (strcmp(el, "jack") == 0) | |||
{ | |||
//jack_info("<jack>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_JACK; | |||
return; | |||
} | |||
if (strcmp(el, "engine") == 0) | |||
{ | |||
//jack_info("<engine>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_ENGINE; | |||
return; | |||
} | |||
if (strcmp(el, "drivers") == 0) | |||
{ | |||
//jack_info("<drivers>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_DRIVERS; | |||
return; | |||
} | |||
if (strcmp(el, "driver") == 0) | |||
{ | |||
if ((attr[0] == NULL || attr[2] != NULL) || strcmp(attr[0], "name") != 0) | |||
{ | |||
jack_error("<driver> XML element must contain exactly one attribute, named \"name\""); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
//jack_info("<driver>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_DRIVER; | |||
driver = jack_controller_find_driver(context_ptr->controller_ptr->server, attr[1]); | |||
if (driver == NULL) | |||
{ | |||
jack_error("ignoring settings for unknown driver \"%s\"", attr[1]); | |||
} | |||
else | |||
{ | |||
jack_info("setting for driver \"%s\" found", attr[1]); | |||
} | |||
context_ptr->driver = driver; | |||
return; | |||
} | |||
if (strcmp(el, "option") == 0) | |||
{ | |||
//jack_info("<option>"); | |||
if ((attr[0] == NULL || attr[2] != NULL) || strcmp(attr[0], "name") != 0) | |||
{ | |||
jack_error("<option> XML element must contain exactly one attribute, named \"name\""); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
context_ptr->name = strdup(attr[1]); | |||
if (context_ptr->name == NULL) | |||
{ | |||
jack_error("strdup() failed"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_OPTION; | |||
context_ptr->option_used = 0; | |||
return; | |||
} | |||
jack_error("unknown element \"%s\"", el); | |||
context_ptr->error = XML_TRUE; | |||
} | |||
void | |||
jack_controller_settings_callback_elend(void *data, const char *el) | |||
{ | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
//jack_info("element end (depth = %d, element = %u)", context_ptr->depth, context_ptr->element[context_ptr->depth]); | |||
if (context_ptr->element[context_ptr->depth] == PARSE_CONTEXT_OPTION) | |||
{ | |||
context_ptr->option[context_ptr->option_used] = 0; | |||
if (context_ptr->depth == 2 && | |||
context_ptr->element[0] == PARSE_CONTEXT_JACK && | |||
context_ptr->element[1] == PARSE_CONTEXT_ENGINE) | |||
{ | |||
jack_controller_settings_set_engine_option(context_ptr->controller_ptr, context_ptr->name, context_ptr->option); | |||
} | |||
if (context_ptr->depth == 3 && | |||
context_ptr->element[0] == PARSE_CONTEXT_JACK && | |||
context_ptr->element[1] == PARSE_CONTEXT_DRIVERS && | |||
context_ptr->element[2] == PARSE_CONTEXT_DRIVER && | |||
context_ptr->driver != NULL) | |||
{ | |||
jack_controller_settings_set_driver_option(context_ptr->driver, context_ptr->name, context_ptr->option); | |||
} | |||
} | |||
context_ptr->depth--; | |||
if (context_ptr->name != NULL) | |||
{ | |||
free(context_ptr->name); | |||
context_ptr->name = NULL; | |||
} | |||
} | |||
#undef context_ptr | |||
void | |||
jack_controller_settings_load( | |||
struct jack_controller * controller_ptr) | |||
{ | |||
XML_Parser parser; | |||
int bytes_read; | |||
void *buffer; | |||
char *filename; | |||
size_t conf_len; | |||
struct stat st; | |||
int fd; | |||
enum XML_Status xmls; | |||
struct parse_context context; | |||
conf_len = strlen(JACKDBUS_CONF); | |||
filename = malloc(g_jackdbus_config_dir_len + conf_len + 1); | |||
if (filename == NULL) | |||
{ | |||
jack_error("Out of memory."); | |||
goto exit; | |||
} | |||
memcpy(filename, g_jackdbus_config_dir, g_jackdbus_config_dir_len); | |||
memcpy(filename + g_jackdbus_config_dir_len, JACKDBUS_CONF, conf_len); | |||
filename[g_jackdbus_config_dir_len + conf_len] = 0; | |||
jack_info("Loading settings from \"%s\" using %s ...", filename, XML_ExpatVersion()); | |||
if (stat(filename, &st) != 0) | |||
{ | |||
jack_error("failed to stat \"%s\", error is %d (%s)", filename, errno, strerror(errno)); | |||
} | |||
fd = open(filename, O_RDONLY); | |||
if (fd == -1) | |||
{ | |||
jack_error("open() failed to open conf filename."); | |||
goto exit_free_filename; | |||
} | |||
parser = XML_ParserCreate(NULL); | |||
if (parser == NULL) | |||
{ | |||
jack_error("XML_ParserCreate() failed to create parser object."); | |||
goto exit_close_file; | |||
} | |||
//jack_info("conf file size is %llu bytes", (unsigned long long)st.st_size); | |||
/* we are expecting that conf file has small enough size to fit in memory */ | |||
buffer = XML_GetBuffer(parser, st.st_size); | |||
if (buffer == NULL) | |||
{ | |||
jack_error("XML_GetBuffer() failed."); | |||
goto exit_free_parser; | |||
} | |||
bytes_read = read(fd, buffer, st.st_size); | |||
if (bytes_read != st.st_size) | |||
{ | |||
jack_error("read() returned unexpected result."); | |||
goto exit_free_parser; | |||
} | |||
context.controller_ptr = controller_ptr; | |||
context.error = XML_FALSE; | |||
context.depth = -1; | |||
context.name = NULL; | |||
XML_SetElementHandler(parser, jack_controller_settings_callback_elstart, jack_controller_settings_callback_elend); | |||
XML_SetCharacterDataHandler(parser, jack_controller_settings_callback_chrdata); | |||
XML_SetUserData(parser, &context); | |||
xmls = XML_ParseBuffer(parser, bytes_read, XML_TRUE); | |||
if (xmls == XML_STATUS_ERROR) | |||
{ | |||
jack_error("XML_ParseBuffer() failed."); | |||
goto exit_free_parser; | |||
} | |||
exit_free_parser: | |||
XML_ParserFree(parser); | |||
exit_close_file: | |||
close(fd); | |||
exit_free_filename: | |||
free(filename); | |||
exit: | |||
return; | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <sys/types.h> | |||
#include <sys/stat.h> | |||
#include <unistd.h> | |||
#include <fcntl.h> | |||
#include <errno.h> | |||
#include <string.h> | |||
#include <expat.h> | |||
#include <dbus/dbus.h> | |||
#include "controller_internal.h" | |||
#include "jackdbus.h" | |||
bool | |||
jack_controller_settings_init() | |||
{ | |||
return true; | |||
} | |||
void | |||
jack_controller_settings_uninit() | |||
{ | |||
} | |||
#define PARSE_CONTEXT_ROOT 0 | |||
#define PARSE_CONTEXT_JACK 1 | |||
#define PARSE_CONTEXT_ENGINE 1 | |||
#define PARSE_CONTEXT_DRIVERS 2 | |||
#define PARSE_CONTEXT_DRIVER 3 | |||
#define PARSE_CONTEXT_OPTION 4 | |||
#define MAX_STACK_DEPTH 10 | |||
struct parse_context | |||
{ | |||
struct jack_controller *controller_ptr; | |||
XML_Bool error; | |||
unsigned int element[MAX_STACK_DEPTH]; | |||
signed int depth; | |||
jackctl_driver_t *driver; | |||
char option[JACK_PARAM_STRING_MAX+1]; | |||
int option_used; | |||
char *name; | |||
}; | |||
#define context_ptr ((struct parse_context *)data) | |||
void | |||
jack_controller_settings_callback_chrdata(void *data, const XML_Char *s, int len) | |||
{ | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
if (context_ptr->element[context_ptr->depth] == PARSE_CONTEXT_OPTION) | |||
{ | |||
if (context_ptr->option_used + len >= JACK_PARAM_STRING_MAX) | |||
{ | |||
jack_error("xml parse max char data length reached"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
memcpy(context_ptr->option + context_ptr->option_used, s, len); | |||
context_ptr->option_used += len; | |||
} | |||
} | |||
void | |||
jack_controller_settings_callback_elstart(void *data, const char *el, const char **attr) | |||
{ | |||
jackctl_driver_t *driver; | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
if (context_ptr->depth + 1 >= MAX_STACK_DEPTH) | |||
{ | |||
jack_error("xml parse max stack depth reached"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
if (strcmp(el, "jack") == 0) | |||
{ | |||
//jack_info("<jack>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_JACK; | |||
return; | |||
} | |||
if (strcmp(el, "engine") == 0) | |||
{ | |||
//jack_info("<engine>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_ENGINE; | |||
return; | |||
} | |||
if (strcmp(el, "drivers") == 0) | |||
{ | |||
//jack_info("<drivers>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_DRIVERS; | |||
return; | |||
} | |||
if (strcmp(el, "driver") == 0) | |||
{ | |||
if ((attr[0] == NULL || attr[2] != NULL) || strcmp(attr[0], "name") != 0) | |||
{ | |||
jack_error("<driver> XML element must contain exactly one attribute, named \"name\""); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
//jack_info("<driver>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_DRIVER; | |||
driver = jack_controller_find_driver(context_ptr->controller_ptr->server, attr[1]); | |||
if (driver == NULL) | |||
{ | |||
jack_error("ignoring settings for unknown driver \"%s\"", attr[1]); | |||
} | |||
else | |||
{ | |||
jack_info("setting for driver \"%s\" found", attr[1]); | |||
} | |||
context_ptr->driver = driver; | |||
return; | |||
} | |||
if (strcmp(el, "option") == 0) | |||
{ | |||
//jack_info("<option>"); | |||
if ((attr[0] == NULL || attr[2] != NULL) || strcmp(attr[0], "name") != 0) | |||
{ | |||
jack_error("<option> XML element must contain exactly one attribute, named \"name\""); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
context_ptr->name = strdup(attr[1]); | |||
if (context_ptr->name == NULL) | |||
{ | |||
jack_error("strdup() failed"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_OPTION; | |||
context_ptr->option_used = 0; | |||
return; | |||
} | |||
jack_error("unknown element \"%s\"", el); | |||
context_ptr->error = XML_TRUE; | |||
} | |||
void | |||
jack_controller_settings_callback_elend(void *data, const char *el) | |||
{ | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
//jack_info("element end (depth = %d, element = %u)", context_ptr->depth, context_ptr->element[context_ptr->depth]); | |||
if (context_ptr->element[context_ptr->depth] == PARSE_CONTEXT_OPTION) | |||
{ | |||
context_ptr->option[context_ptr->option_used] = 0; | |||
if (context_ptr->depth == 2 && | |||
context_ptr->element[0] == PARSE_CONTEXT_JACK && | |||
context_ptr->element[1] == PARSE_CONTEXT_ENGINE) | |||
{ | |||
jack_controller_settings_set_engine_option(context_ptr->controller_ptr, context_ptr->name, context_ptr->option); | |||
} | |||
if (context_ptr->depth == 3 && | |||
context_ptr->element[0] == PARSE_CONTEXT_JACK && | |||
context_ptr->element[1] == PARSE_CONTEXT_DRIVERS && | |||
context_ptr->element[2] == PARSE_CONTEXT_DRIVER && | |||
context_ptr->driver != NULL) | |||
{ | |||
jack_controller_settings_set_driver_option(context_ptr->driver, context_ptr->name, context_ptr->option); | |||
} | |||
} | |||
context_ptr->depth--; | |||
if (context_ptr->name != NULL) | |||
{ | |||
free(context_ptr->name); | |||
context_ptr->name = NULL; | |||
} | |||
} | |||
#undef context_ptr | |||
void | |||
jack_controller_settings_load( | |||
struct jack_controller * controller_ptr) | |||
{ | |||
XML_Parser parser; | |||
int bytes_read; | |||
void *buffer; | |||
char *filename; | |||
size_t conf_len; | |||
struct stat st; | |||
int fd; | |||
enum XML_Status xmls; | |||
struct parse_context context; | |||
conf_len = strlen(JACKDBUS_CONF); | |||
filename = malloc(g_jackdbus_config_dir_len + conf_len + 1); | |||
if (filename == NULL) | |||
{ | |||
jack_error("Out of memory."); | |||
goto exit; | |||
} | |||
memcpy(filename, g_jackdbus_config_dir, g_jackdbus_config_dir_len); | |||
memcpy(filename + g_jackdbus_config_dir_len, JACKDBUS_CONF, conf_len); | |||
filename[g_jackdbus_config_dir_len + conf_len] = 0; | |||
jack_info("Loading settings from \"%s\" using %s ...", filename, XML_ExpatVersion()); | |||
if (stat(filename, &st) != 0) | |||
{ | |||
jack_error("failed to stat \"%s\", error is %d (%s)", filename, errno, strerror(errno)); | |||
} | |||
fd = open(filename, O_RDONLY); | |||
if (fd == -1) | |||
{ | |||
jack_error("open() failed to open conf filename."); | |||
goto exit_free_filename; | |||
} | |||
parser = XML_ParserCreate(NULL); | |||
if (parser == NULL) | |||
{ | |||
jack_error("XML_ParserCreate() failed to create parser object."); | |||
goto exit_close_file; | |||
} | |||
//jack_info("conf file size is %llu bytes", (unsigned long long)st.st_size); | |||
/* we are expecting that conf file has small enough size to fit in memory */ | |||
buffer = XML_GetBuffer(parser, st.st_size); | |||
if (buffer == NULL) | |||
{ | |||
jack_error("XML_GetBuffer() failed."); | |||
goto exit_free_parser; | |||
} | |||
bytes_read = read(fd, buffer, st.st_size); | |||
if (bytes_read != st.st_size) | |||
{ | |||
jack_error("read() returned unexpected result."); | |||
goto exit_free_parser; | |||
} | |||
context.controller_ptr = controller_ptr; | |||
context.error = XML_FALSE; | |||
context.depth = -1; | |||
context.name = NULL; | |||
XML_SetElementHandler(parser, jack_controller_settings_callback_elstart, jack_controller_settings_callback_elend); | |||
XML_SetCharacterDataHandler(parser, jack_controller_settings_callback_chrdata); | |||
XML_SetUserData(parser, &context); | |||
xmls = XML_ParseBuffer(parser, bytes_read, XML_TRUE); | |||
if (xmls == XML_STATUS_ERROR) | |||
{ | |||
jack_error("XML_ParseBuffer() failed."); | |||
goto exit_free_parser; | |||
} | |||
exit_free_parser: | |||
XML_ParserFree(parser); | |||
exit_close_file: | |||
close(fd); | |||
exit_free_filename: | |||
free(filename); | |||
exit: | |||
return; | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <sys/types.h> | |||
#include <sys/stat.h> | |||
#include <unistd.h> | |||
#include <fcntl.h> | |||
#include <errno.h> | |||
#include <string.h> | |||
#include <expat.h> | |||
#include <dbus/dbus.h> | |||
#include "controller_internal.h" | |||
#include "jackdbus.h" | |||
bool | |||
jack_controller_settings_init() | |||
{ | |||
return true; | |||
} | |||
void | |||
jack_controller_settings_uninit() | |||
{ | |||
} | |||
#define PARSE_CONTEXT_ROOT 0 | |||
#define PARSE_CONTEXT_JACK 1 | |||
#define PARSE_CONTEXT_ENGINE 1 | |||
#define PARSE_CONTEXT_DRIVERS 2 | |||
#define PARSE_CONTEXT_DRIVER 3 | |||
#define PARSE_CONTEXT_OPTION 4 | |||
#define MAX_STACK_DEPTH 10 | |||
struct parse_context | |||
{ | |||
struct jack_controller *controller_ptr; | |||
XML_Bool error; | |||
unsigned int element[MAX_STACK_DEPTH]; | |||
signed int depth; | |||
jackctl_driver_t *driver; | |||
char option[JACK_PARAM_STRING_MAX+1]; | |||
int option_used; | |||
char *name; | |||
}; | |||
#define context_ptr ((struct parse_context *)data) | |||
void | |||
jack_controller_settings_callback_chrdata(void *data, const XML_Char *s, int len) | |||
{ | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
if (context_ptr->element[context_ptr->depth] == PARSE_CONTEXT_OPTION) | |||
{ | |||
if (context_ptr->option_used + len >= JACK_PARAM_STRING_MAX) | |||
{ | |||
jack_error("xml parse max char data length reached"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
memcpy(context_ptr->option + context_ptr->option_used, s, len); | |||
context_ptr->option_used += len; | |||
} | |||
} | |||
void | |||
jack_controller_settings_callback_elstart(void *data, const char *el, const char **attr) | |||
{ | |||
jackctl_driver_t *driver; | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
if (context_ptr->depth + 1 >= MAX_STACK_DEPTH) | |||
{ | |||
jack_error("xml parse max stack depth reached"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
if (strcmp(el, "jack") == 0) | |||
{ | |||
//jack_info("<jack>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_JACK; | |||
return; | |||
} | |||
if (strcmp(el, "engine") == 0) | |||
{ | |||
//jack_info("<engine>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_ENGINE; | |||
return; | |||
} | |||
if (strcmp(el, "drivers") == 0) | |||
{ | |||
//jack_info("<drivers>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_DRIVERS; | |||
return; | |||
} | |||
if (strcmp(el, "driver") == 0) | |||
{ | |||
if ((attr[0] == NULL || attr[2] != NULL) || strcmp(attr[0], "name") != 0) | |||
{ | |||
jack_error("<driver> XML element must contain exactly one attribute, named \"name\""); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
//jack_info("<driver>"); | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_DRIVER; | |||
driver = jack_controller_find_driver(context_ptr->controller_ptr->server, attr[1]); | |||
if (driver == NULL) | |||
{ | |||
jack_error("ignoring settings for unknown driver \"%s\"", attr[1]); | |||
} | |||
else | |||
{ | |||
jack_info("setting for driver \"%s\" found", attr[1]); | |||
} | |||
context_ptr->driver = driver; | |||
return; | |||
} | |||
if (strcmp(el, "option") == 0) | |||
{ | |||
//jack_info("<option>"); | |||
if ((attr[0] == NULL || attr[2] != NULL) || strcmp(attr[0], "name") != 0) | |||
{ | |||
jack_error("<option> XML element must contain exactly one attribute, named \"name\""); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
context_ptr->name = strdup(attr[1]); | |||
if (context_ptr->name == NULL) | |||
{ | |||
jack_error("strdup() failed"); | |||
context_ptr->error = XML_TRUE; | |||
return; | |||
} | |||
context_ptr->element[++context_ptr->depth] = PARSE_CONTEXT_OPTION; | |||
context_ptr->option_used = 0; | |||
return; | |||
} | |||
jack_error("unknown element \"%s\"", el); | |||
context_ptr->error = XML_TRUE; | |||
} | |||
void | |||
jack_controller_settings_callback_elend(void *data, const char *el) | |||
{ | |||
if (context_ptr->error) | |||
{ | |||
return; | |||
} | |||
//jack_info("element end (depth = %d, element = %u)", context_ptr->depth, context_ptr->element[context_ptr->depth]); | |||
if (context_ptr->element[context_ptr->depth] == PARSE_CONTEXT_OPTION) | |||
{ | |||
context_ptr->option[context_ptr->option_used] = 0; | |||
if (context_ptr->depth == 2 && | |||
context_ptr->element[0] == PARSE_CONTEXT_JACK && | |||
context_ptr->element[1] == PARSE_CONTEXT_ENGINE) | |||
{ | |||
jack_controller_settings_set_engine_option(context_ptr->controller_ptr, context_ptr->name, context_ptr->option); | |||
} | |||
if (context_ptr->depth == 3 && | |||
context_ptr->element[0] == PARSE_CONTEXT_JACK && | |||
context_ptr->element[1] == PARSE_CONTEXT_DRIVERS && | |||
context_ptr->element[2] == PARSE_CONTEXT_DRIVER && | |||
context_ptr->driver != NULL) | |||
{ | |||
jack_controller_settings_set_driver_option(context_ptr->driver, context_ptr->name, context_ptr->option); | |||
} | |||
} | |||
context_ptr->depth--; | |||
if (context_ptr->name != NULL) | |||
{ | |||
free(context_ptr->name); | |||
context_ptr->name = NULL; | |||
} | |||
} | |||
#undef context_ptr | |||
void | |||
jack_controller_settings_load( | |||
struct jack_controller * controller_ptr) | |||
{ | |||
XML_Parser parser; | |||
int bytes_read; | |||
void *buffer; | |||
char *filename; | |||
size_t conf_len; | |||
struct stat st; | |||
int fd; | |||
enum XML_Status xmls; | |||
struct parse_context context; | |||
conf_len = strlen(JACKDBUS_CONF); | |||
filename = malloc(g_jackdbus_config_dir_len + conf_len + 1); | |||
if (filename == NULL) | |||
{ | |||
jack_error("Out of memory."); | |||
goto exit; | |||
} | |||
memcpy(filename, g_jackdbus_config_dir, g_jackdbus_config_dir_len); | |||
memcpy(filename + g_jackdbus_config_dir_len, JACKDBUS_CONF, conf_len); | |||
filename[g_jackdbus_config_dir_len + conf_len] = 0; | |||
jack_info("Loading settings from \"%s\" using %s ...", filename, XML_ExpatVersion()); | |||
if (stat(filename, &st) != 0) | |||
{ | |||
jack_error("failed to stat \"%s\", error is %d (%s)", filename, errno, strerror(errno)); | |||
} | |||
fd = open(filename, O_RDONLY); | |||
if (fd == -1) | |||
{ | |||
jack_error("open() failed to open conf filename."); | |||
goto exit_free_filename; | |||
} | |||
parser = XML_ParserCreate(NULL); | |||
if (parser == NULL) | |||
{ | |||
jack_error("XML_ParserCreate() failed to create parser object."); | |||
goto exit_close_file; | |||
} | |||
//jack_info("conf file size is %llu bytes", (unsigned long long)st.st_size); | |||
/* we are expecting that conf file has small enough size to fit in memory */ | |||
buffer = XML_GetBuffer(parser, st.st_size); | |||
if (buffer == NULL) | |||
{ | |||
jack_error("XML_GetBuffer() failed."); | |||
goto exit_free_parser; | |||
} | |||
bytes_read = read(fd, buffer, st.st_size); | |||
if (bytes_read != st.st_size) | |||
{ | |||
jack_error("read() returned unexpected result."); | |||
goto exit_free_parser; | |||
} | |||
context.controller_ptr = controller_ptr; | |||
context.error = XML_FALSE; | |||
context.depth = -1; | |||
context.name = NULL; | |||
XML_SetElementHandler(parser, jack_controller_settings_callback_elstart, jack_controller_settings_callback_elend); | |||
XML_SetCharacterDataHandler(parser, jack_controller_settings_callback_chrdata); | |||
XML_SetUserData(parser, &context); | |||
xmls = XML_ParseBuffer(parser, bytes_read, XML_TRUE); | |||
if (xmls == XML_STATUS_ERROR) | |||
{ | |||
jack_error("XML_ParseBuffer() failed."); | |||
goto exit_free_parser; | |||
} | |||
exit_free_parser: | |||
XML_ParserFree(parser); | |||
exit_close_file: | |||
close(fd); | |||
exit_free_filename: | |||
free(filename); | |||
exit: | |||
return; | |||
} |
@@ -268,813 +268,3 @@ jack_controller_settings_save_auto( | |||
{ | |||
jack_controller_settings_save(controller_ptr, NULL); | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <sys/types.h> | |||
#include <sys/stat.h> | |||
#include <unistd.h> | |||
#include <fcntl.h> | |||
#include <errno.h> | |||
#include <string.h> | |||
#include <dbus/dbus.h> | |||
#include <time.h> | |||
#include "controller_internal.h" | |||
#include "jackdbus.h" | |||
bool | |||
jack_controller_settings_write_string(int fd, const char * string, void *dbus_call_context_ptr) | |||
{ | |||
size_t len; | |||
len = strlen(string); | |||
if (write(fd, string, len) != len) | |||
{ | |||
jack_dbus_error(dbus_call_context_ptr, JACK_DBUS_ERROR_GENERIC, "write() failed to write config file."); | |||
return false; | |||
} | |||
return true; | |||
} | |||
struct save_context | |||
{ | |||
int fd; | |||
const char *indent; | |||
}; | |||
#define save_context_ptr ((struct save_context *)context) | |||
#define fd (save_context_ptr->fd) | |||
bool | |||
jack_controller_settings_write_option( | |||
void *context, | |||
const char *name, | |||
const char *content, | |||
void *dbus_call_context_ptr) | |||
{ | |||
if (!jack_controller_settings_write_string(fd, save_context_ptr->indent, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<option name=\"", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, name, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "\">", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, content, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "</option>\n", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
return true; | |||
} | |||
#undef fd | |||
bool | |||
jack_controller_settings_save( | |||
struct jack_controller * controller_ptr, | |||
void *dbus_call_context_ptr) | |||
{ | |||
char *filename; | |||
size_t conf_len; | |||
int fd; | |||
bool ret; | |||
time_t timestamp; | |||
char timestamp_str[26]; | |||
struct save_context context; | |||
const JSList * node_ptr; | |||
jackctl_driver_t *driver; | |||
time(×tamp); | |||
ctime_r(×tamp, timestamp_str); | |||
timestamp_str[24] = 0; | |||
ret = false; | |||
conf_len = strlen(JACKDBUS_CONF); | |||
filename = malloc(g_jackdbus_config_dir_len + conf_len + 1); | |||
if (filename == NULL) | |||
{ | |||
jack_error("Out of memory."); | |||
goto exit; | |||
} | |||
memcpy(filename, g_jackdbus_config_dir, g_jackdbus_config_dir_len); | |||
memcpy(filename + g_jackdbus_config_dir_len, JACKDBUS_CONF, conf_len); | |||
filename[g_jackdbus_config_dir_len + conf_len] = 0; | |||
jack_info("Saving settings to \"%s\" ...", filename); | |||
fd = open(filename, O_WRONLY | O_TRUNC | O_CREAT, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); | |||
if (fd == -1) | |||
{ | |||
jack_error("open() failed to open conf filename. error is %d (%s)", errno, strerror(errno)); | |||
goto exit_free_filename; | |||
} | |||
context.fd = fd; | |||
if (!jack_controller_settings_write_string(fd, "<?xml version=\"1.0\"?>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<!--\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, JACK_CONF_HEADER_TEXT, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "-->\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<!-- ", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, timestamp_str, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " -->\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<jack>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " <engine>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
context.indent = " "; | |||
if (!jack_controller_settings_save_engine_options(&context, controller_ptr, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </engine>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " <drivers>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
node_ptr = jackctl_server_get_drivers_list(controller_ptr->server); | |||
while (node_ptr != NULL) | |||
{ | |||
driver = (jackctl_driver_t *)node_ptr->data; | |||
if (!jack_controller_settings_write_string(fd, " <driver name=\"", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, jackctl_driver_get_name(driver), dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "\">\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
context.indent = " "; | |||
if (!jack_controller_settings_save_driver_options(&context, driver, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </driver>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
node_ptr = jack_slist_next(node_ptr); | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </drivers>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "</jack>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
ret = true; | |||
exit_close: | |||
close(fd); | |||
exit_free_filename: | |||
free(filename); | |||
exit: | |||
return ret; | |||
} | |||
void | |||
jack_controller_settings_save_auto( | |||
struct jack_controller * controller_ptr) | |||
{ | |||
jack_controller_settings_save(controller_ptr, NULL); | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <sys/types.h> | |||
#include <sys/stat.h> | |||
#include <unistd.h> | |||
#include <fcntl.h> | |||
#include <errno.h> | |||
#include <string.h> | |||
#include <dbus/dbus.h> | |||
#include <time.h> | |||
#include "controller_internal.h" | |||
#include "jackdbus.h" | |||
bool | |||
jack_controller_settings_write_string(int fd, const char * string, void *dbus_call_context_ptr) | |||
{ | |||
size_t len; | |||
len = strlen(string); | |||
if (write(fd, string, len) != len) | |||
{ | |||
jack_dbus_error(dbus_call_context_ptr, JACK_DBUS_ERROR_GENERIC, "write() failed to write config file."); | |||
return false; | |||
} | |||
return true; | |||
} | |||
struct save_context | |||
{ | |||
int fd; | |||
const char *indent; | |||
}; | |||
#define save_context_ptr ((struct save_context *)context) | |||
#define fd (save_context_ptr->fd) | |||
bool | |||
jack_controller_settings_write_option( | |||
void *context, | |||
const char *name, | |||
const char *content, | |||
void *dbus_call_context_ptr) | |||
{ | |||
if (!jack_controller_settings_write_string(fd, save_context_ptr->indent, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<option name=\"", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, name, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "\">", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, content, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "</option>\n", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
return true; | |||
} | |||
#undef fd | |||
bool | |||
jack_controller_settings_save( | |||
struct jack_controller * controller_ptr, | |||
void *dbus_call_context_ptr) | |||
{ | |||
char *filename; | |||
size_t conf_len; | |||
int fd; | |||
bool ret; | |||
time_t timestamp; | |||
char timestamp_str[26]; | |||
struct save_context context; | |||
const JSList * node_ptr; | |||
jackctl_driver_t *driver; | |||
time(×tamp); | |||
ctime_r(×tamp, timestamp_str); | |||
timestamp_str[24] = 0; | |||
ret = false; | |||
conf_len = strlen(JACKDBUS_CONF); | |||
filename = malloc(g_jackdbus_config_dir_len + conf_len + 1); | |||
if (filename == NULL) | |||
{ | |||
jack_error("Out of memory."); | |||
goto exit; | |||
} | |||
memcpy(filename, g_jackdbus_config_dir, g_jackdbus_config_dir_len); | |||
memcpy(filename + g_jackdbus_config_dir_len, JACKDBUS_CONF, conf_len); | |||
filename[g_jackdbus_config_dir_len + conf_len] = 0; | |||
jack_info("Saving settings to \"%s\" ...", filename); | |||
fd = open(filename, O_WRONLY | O_TRUNC | O_CREAT, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); | |||
if (fd == -1) | |||
{ | |||
jack_error("open() failed to open conf filename. error is %d (%s)", errno, strerror(errno)); | |||
goto exit_free_filename; | |||
} | |||
context.fd = fd; | |||
if (!jack_controller_settings_write_string(fd, "<?xml version=\"1.0\"?>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<!--\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, JACK_CONF_HEADER_TEXT, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "-->\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<!-- ", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, timestamp_str, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " -->\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<jack>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " <engine>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
context.indent = " "; | |||
if (!jack_controller_settings_save_engine_options(&context, controller_ptr, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </engine>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " <drivers>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
node_ptr = jackctl_server_get_drivers_list(controller_ptr->server); | |||
while (node_ptr != NULL) | |||
{ | |||
driver = (jackctl_driver_t *)node_ptr->data; | |||
if (!jack_controller_settings_write_string(fd, " <driver name=\"", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, jackctl_driver_get_name(driver), dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "\">\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
context.indent = " "; | |||
if (!jack_controller_settings_save_driver_options(&context, driver, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </driver>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
node_ptr = jack_slist_next(node_ptr); | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </drivers>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "</jack>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
ret = true; | |||
exit_close: | |||
close(fd); | |||
exit_free_filename: | |||
free(filename); | |||
exit: | |||
return ret; | |||
} | |||
void | |||
jack_controller_settings_save_auto( | |||
struct jack_controller * controller_ptr) | |||
{ | |||
jack_controller_settings_save(controller_ptr, NULL); | |||
} | |||
/* -*- Mode: C ; c-basic-offset: 4 -*- */ | |||
/* | |||
Copyright (C) 2007,2008 Nedko Arnaudov | |||
This program is free software; you can redistribute it and/or modify | |||
it under the terms of the GNU General Public License as published by | |||
the Free Software Foundation; either version 2 of the License. | |||
This program is distributed in the hope that it will be useful, | |||
but WITHOUT ANY WARRANTY; without even the implied warranty of | |||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |||
GNU General Public License for more details. | |||
You should have received a copy of the GNU General Public License | |||
along with this program; if not, write to the Free Software | |||
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | |||
*/ | |||
#include <stdbool.h> | |||
#include <stdint.h> | |||
#include <sys/types.h> | |||
#include <sys/stat.h> | |||
#include <unistd.h> | |||
#include <fcntl.h> | |||
#include <errno.h> | |||
#include <string.h> | |||
#include <dbus/dbus.h> | |||
#include <time.h> | |||
#include "controller_internal.h" | |||
#include "jackdbus.h" | |||
bool | |||
jack_controller_settings_write_string(int fd, const char * string, void *dbus_call_context_ptr) | |||
{ | |||
size_t len; | |||
len = strlen(string); | |||
if (write(fd, string, len) != len) | |||
{ | |||
jack_dbus_error(dbus_call_context_ptr, JACK_DBUS_ERROR_GENERIC, "write() failed to write config file."); | |||
return false; | |||
} | |||
return true; | |||
} | |||
struct save_context | |||
{ | |||
int fd; | |||
const char *indent; | |||
}; | |||
#define save_context_ptr ((struct save_context *)context) | |||
#define fd (save_context_ptr->fd) | |||
bool | |||
jack_controller_settings_write_option( | |||
void *context, | |||
const char *name, | |||
const char *content, | |||
void *dbus_call_context_ptr) | |||
{ | |||
if (!jack_controller_settings_write_string(fd, save_context_ptr->indent, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<option name=\"", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, name, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "\">", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, content, dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "</option>\n", dbus_call_context_ptr)) | |||
{ | |||
return false; | |||
} | |||
return true; | |||
} | |||
#undef fd | |||
bool | |||
jack_controller_settings_save( | |||
struct jack_controller * controller_ptr, | |||
void *dbus_call_context_ptr) | |||
{ | |||
char *filename; | |||
size_t conf_len; | |||
int fd; | |||
bool ret; | |||
time_t timestamp; | |||
char timestamp_str[26]; | |||
struct save_context context; | |||
const JSList * node_ptr; | |||
jackctl_driver_t *driver; | |||
time(×tamp); | |||
ctime_r(×tamp, timestamp_str); | |||
timestamp_str[24] = 0; | |||
ret = false; | |||
conf_len = strlen(JACKDBUS_CONF); | |||
filename = malloc(g_jackdbus_config_dir_len + conf_len + 1); | |||
if (filename == NULL) | |||
{ | |||
jack_error("Out of memory."); | |||
goto exit; | |||
} | |||
memcpy(filename, g_jackdbus_config_dir, g_jackdbus_config_dir_len); | |||
memcpy(filename + g_jackdbus_config_dir_len, JACKDBUS_CONF, conf_len); | |||
filename[g_jackdbus_config_dir_len + conf_len] = 0; | |||
jack_info("Saving settings to \"%s\" ...", filename); | |||
fd = open(filename, O_WRONLY | O_TRUNC | O_CREAT, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); | |||
if (fd == -1) | |||
{ | |||
jack_error("open() failed to open conf filename. error is %d (%s)", errno, strerror(errno)); | |||
goto exit_free_filename; | |||
} | |||
context.fd = fd; | |||
if (!jack_controller_settings_write_string(fd, "<?xml version=\"1.0\"?>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<!--\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, JACK_CONF_HEADER_TEXT, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "-->\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<!-- ", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, timestamp_str, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " -->\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "<jack>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " <engine>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
context.indent = " "; | |||
if (!jack_controller_settings_save_engine_options(&context, controller_ptr, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </engine>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " <drivers>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
node_ptr = jackctl_server_get_drivers_list(controller_ptr->server); | |||
while (node_ptr != NULL) | |||
{ | |||
driver = (jackctl_driver_t *)node_ptr->data; | |||
if (!jack_controller_settings_write_string(fd, " <driver name=\"", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, jackctl_driver_get_name(driver), dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "\">\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
context.indent = " "; | |||
if (!jack_controller_settings_save_driver_options(&context, driver, dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </driver>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
node_ptr = jack_slist_next(node_ptr); | |||
} | |||
if (!jack_controller_settings_write_string(fd, " </drivers>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
if (!jack_controller_settings_write_string(fd, "</jack>\n", dbus_call_context_ptr)) | |||
{ | |||
goto exit_close; | |||
} | |||
ret = true; | |||
exit_close: | |||
close(fd); | |||
exit_free_filename: | |||
free(filename); | |||
exit: | |||
return ret; | |||
} | |||
void | |||
jack_controller_settings_save_auto( | |||
struct jack_controller * controller_ptr) | |||
{ | |||
jack_controller_settings_save(controller_ptr, NULL); | |||
} |