JackMachClientChannel.cpp

00001 /*
00002 Copyright (C) 2004-2008 Grame  
00003 
00004 This program is free software; you can redistribute it and/or modify
00005   it under the terms of the GNU General Public License as published by
00006   the Free Software Foundation; either version 2 of the License, or
00007   (at your option) any later version.
00008 
00009   This program is distributed in the hope that it will be useful,
00010   but WITHOUT ANY WARRANTY; without even the implied warranty of
00011   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012   GNU General Public License for more details.
00013 
00014   You should have received a copy of the GNU General Public License
00015   along with this program; if not, write to the Free Software
00016   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
00017 
00018 */
00019 
00020 #include "JackMachClientChannel.h"
00021 #include "JackRPCEngine.h"
00022 #include "JackRPCClientServer.c"
00023 #include "JackError.h"
00024 #include "JackLibClient.h"
00025 #include "JackLibGlobals.h"
00026 #include "JackMachThread.h"
00027 #include "JackConstants.h"
00028 
00029 namespace Jack
00030 {
00031 
00032 JackMachClientChannel::JackMachClientChannel()
00033 {
00034     fThread = new JackMachThread(this);
00035 }
00036 
00037 JackMachClientChannel::~JackMachClientChannel()
00038 {
00039     delete fThread;
00040 }
00041 
00042 // Server <===> client
00043 
00044 int JackMachClientChannel::ServerCheck(const char* server_name)
00045 {
00046         JackLog("JackMachClientChannel::ServerCheck = %s\n", server_name);
00047         char jack_server_entry_name[512];
00048         snprintf(jack_server_entry_name, sizeof(jack_server_entry_name), "%s_%s", jack_server_entry, server_name);
00049         
00050     // Connect to server
00051     if (!fServerPort.ConnectPort(jack_server_entry_name)) {
00052         jack_error("Cannot connect to server Mach port");
00053         return -1;
00054     } else {
00055                 return 0;
00056         }
00057 }
00058 
00059 int JackMachClientChannel::Open(const char* server_name, const char* name, char* name_res, JackClient* client, jack_options_t options, jack_status_t* status)
00060 {
00061     JackLog("JackMachClientChannel::Open name = %s\n", name);
00062         char jack_server_entry_name[512];
00063         snprintf(jack_server_entry_name, sizeof(jack_server_entry_name), "%s_%s", jack_server_entry, server_name);
00064 
00065     // Connect to server
00066     if (!fServerPort.ConnectPort(jack_server_entry_name)) {
00067         jack_error("Cannot connect to server Mach port");
00068         return -1;
00069     }
00070         
00071         // Check name in server
00072         int result = 0;
00073         ClientCheck(name, name_res, JACK_PROTOCOL_VERSION, (int)options, (int*)status, &result);
00074     if (result < 0) {
00075                 int status1 = *status;
00076         if (status1 & JackVersionError)
00077                         jack_error("JACK protocol mismatch %d", JACK_PROTOCOL_VERSION);
00078         else
00079                         jack_error("Client name = %s conflits with another running client", name);
00080                 return -1;
00081     }
00082 
00083     // Prepare local port using client name
00084     char buf[JACK_CLIENT_NAME_SIZE];
00085     snprintf(buf, sizeof(buf) - 1, "%s:%s", jack_client_entry, name_res);
00086 
00087     if (!fClientPort.AllocatePort(buf, 16)) {
00088         jack_error("Cannot allocate client Mach port");
00089         return -1;
00090     }
00091 
00092     JackLibGlobals::fGlobals->fClientTable[fClientPort.GetPort()] = client;
00093     return 0;
00094 }
00095 
00096 void JackMachClientChannel::Close()
00097 {
00098     JackLog("JackMachClientChannel::Close\n");
00099     JackLibGlobals::fGlobals->fClientTable.erase(fClientPort.GetPort());
00100     fServerPort.DisconnectPort();
00101     fClientPort.DestroyPort();
00102 
00103     // TO CHECK
00104     kern_return_t res;
00105     if ((res = mach_port_destroy(mach_task_self(), fPrivatePort)) != KERN_SUCCESS) {
00106         jack_error("JackMachClientChannel::Close err = %s", mach_error_string(res));
00107     }
00108 }
00109 
00110 int JackMachClientChannel::Start()
00111 {
00112     JackLog("JackMachClientChannel::Start\n");
00113     if (fThread->Start() != 0) {
00114         jack_error("Cannot start Jack client listener");
00115         return -1;
00116     } else {
00117         return 0;
00118     }
00119 }
00120 
00121 void JackMachClientChannel::Stop()
00122 {
00123     JackLog("JackMachClientChannel::Stop\n");
00124     fThread->Kill();
00125 }
00126 
00127 void JackMachClientChannel::ClientCheck(const char* name, char* name_res, int protocol, int options, int* status, int* result)
00128 {
00129         kern_return_t res = rpc_jack_client_check(fServerPort.GetPort(), (char*)name, name_res, protocol, options, status, result);
00130     if (res != KERN_SUCCESS) {
00131         *result = -1;
00132         jack_error("JackMachClientChannel::ClientCheck err = %s", mach_error_string(res));
00133     }
00134 }
00135 
00136 void JackMachClientChannel::ClientOpen(const char* name, int* shared_engine, int* shared_client, int* shared_graph, int* result)
00137 {
00138     kern_return_t res = rpc_jack_client_open(fServerPort.GetPort(), (char*)name, &fPrivatePort, shared_engine, shared_client, shared_graph, result);
00139     if (res != KERN_SUCCESS) {
00140         *result = -1;
00141         jack_error("JackMachClientChannel::ClientOpen err = %s", mach_error_string(res));
00142     }
00143 }
00144 
00145 void JackMachClientChannel::ClientClose(int refnum, int* result)
00146 {
00147     kern_return_t res = rpc_jack_client_close(fPrivatePort, refnum, result);
00148     if (res != KERN_SUCCESS) {
00149         *result = -1;
00150         jack_error("JackMachClientChannel::ClientClose err = %s", mach_error_string(res));
00151     }
00152 }
00153 
00154 void JackMachClientChannel::ClientActivate(int refnum, int* result)
00155 {
00156     kern_return_t res = rpc_jack_client_activate(fPrivatePort, refnum, result);
00157     if (res != KERN_SUCCESS) {
00158         *result = -1;
00159         jack_error("JackMachClientChannel::ClientActivate err = %s", mach_error_string(res));
00160     }
00161 }
00162 
00163 void JackMachClientChannel::ClientDeactivate(int refnum, int* result)
00164 {
00165     kern_return_t res = rpc_jack_client_deactivate(fPrivatePort, refnum, result);
00166     if (res != KERN_SUCCESS) {
00167         *result = -1;
00168         jack_error("JackMachClientChannel::ClientDeactivate err = %s", mach_error_string(res));
00169     }
00170 }
00171 
00172 void JackMachClientChannel::PortRegister(int refnum, const char* name, const char* type, unsigned int flags, unsigned int buffer_size, unsigned int* port_index, int* result)
00173 {
00174         kern_return_t res = rpc_jack_port_register(fPrivatePort, refnum, (char*)name, (char*)type, flags, buffer_size, port_index, result);
00175     if (res != KERN_SUCCESS) {
00176         *result = -1;
00177         jack_error("JackMachClientChannel::PortRegister err = %s", mach_error_string(res));
00178     }
00179 }
00180 
00181 void JackMachClientChannel::PortUnRegister(int refnum, jack_port_id_t port_index, int* result)
00182 {
00183     kern_return_t res = rpc_jack_port_unregister(fPrivatePort, refnum, port_index, result);
00184     if (res != KERN_SUCCESS) {
00185         *result = -1;
00186         jack_error("JackMachClientChannel::PortUnRegister err = %s", mach_error_string(res));
00187     }
00188 }
00189 
00190 void JackMachClientChannel::PortConnect(int refnum, const char* src, const char* dst, int* result)
00191 {
00192     kern_return_t res = rpc_jack_port_connect_name(fPrivatePort, refnum, (char*)src, (char*)dst, result);
00193     if (res != KERN_SUCCESS) {
00194         jack_error("JackMachClientChannel::PortConnect err = %s", mach_error_string(res));
00195     }
00196 }
00197 
00198 void JackMachClientChannel::PortDisconnect(int refnum, const char* src, const char* dst, int* result)
00199 {
00200     kern_return_t res = rpc_jack_port_disconnect_name(fPrivatePort, refnum, (char*)src, (char*)dst, result);
00201     if (res != KERN_SUCCESS) {
00202         *result = -1;
00203         jack_error("JackMachClientChannel::PortDisconnect err = %s", mach_error_string(res));
00204     }
00205 }
00206 
00207 void JackMachClientChannel::PortConnect(int refnum, jack_port_id_t src, jack_port_id_t dst, int* result)
00208 {
00209     kern_return_t res = rpc_jack_port_connect(fPrivatePort, refnum, src, dst, result);
00210     if (res != KERN_SUCCESS) {
00211         *result = -1;
00212         jack_error("JackMachClientChannel::PortConnect err = %s", mach_error_string(res));
00213     }
00214 }
00215 
00216 void JackMachClientChannel::PortDisconnect(int refnum, jack_port_id_t src, jack_port_id_t dst, int* result)
00217 {
00218     kern_return_t res = rpc_jack_port_disconnect(fPrivatePort, refnum, src, dst, result);
00219     if (res != KERN_SUCCESS) {
00220         *result = -1;
00221         jack_error("JackMachClientChannel::PortDisconnect err = %s", mach_error_string(res));
00222     }
00223 }
00224 
00225 void JackMachClientChannel::SetBufferSize(jack_nframes_t buffer_size, int* result)
00226 {
00227     kern_return_t res = rpc_jack_set_buffer_size(fPrivatePort, buffer_size, result);
00228     if (res != KERN_SUCCESS) {
00229         *result = -1;
00230         jack_error("JackMachClientChannel::SetBufferSize err = %s", mach_error_string(res));
00231     }
00232 }
00233 
00234 void JackMachClientChannel::SetFreewheel(int onoff, int* result)
00235 {
00236     kern_return_t res = rpc_jack_set_freewheel(fPrivatePort, onoff, result);
00237     if (res != KERN_SUCCESS) {
00238         *result = -1;
00239         jack_error("JackMachClientChannel::SetFreewheel err = %s", mach_error_string(res));
00240     }
00241 }
00242 
00243 void JackMachClientChannel::ReleaseTimebase(int refnum, int* result)
00244 {
00245     kern_return_t res = rpc_jack_release_timebase(fPrivatePort, refnum, result);
00246     if (res != KERN_SUCCESS) {
00247         *result = -1;
00248         jack_error("JackMachClientChannel::ReleaseTimebase err = %s", mach_error_string(res));
00249     }
00250 }
00251 
00252 void JackMachClientChannel::SetTimebaseCallback(int refnum, int conditional, int* result)
00253 {
00254     kern_return_t res = rpc_jack_set_timebase_callback(fPrivatePort, refnum, conditional, result);
00255     if (res != KERN_SUCCESS) {
00256         *result = -1;
00257         jack_error("JackMachClientChannel::SetTimebaseCallback err = %s", mach_error_string(res));
00258     }
00259 }
00260 
00261 void JackMachClientChannel::GetInternalClientName(int refnum, int int_ref, char* name_res, int* result)
00262 {
00263     kern_return_t res = rpc_jack_get_internal_clientname(fPrivatePort, refnum, int_ref, name_res, result);
00264     if (res != KERN_SUCCESS) {
00265         *result = -1;
00266         jack_error("JackMachClientChannel::GetInternalClientName err = %s", mach_error_string(res));
00267     }
00268 }
00269 
00270 void JackMachClientChannel::InternalClientHandle(int refnum, const char* client_name, int* status, int* int_ref, int* result)
00271 {
00272     kern_return_t res = rpc_jack_internal_clienthandle(fPrivatePort, refnum, (char*)client_name, status, int_ref, result);
00273     if (res != KERN_SUCCESS) {
00274         *result = -1;
00275         jack_error("JackMachClientChannel::InternalClientHandle err = %s", mach_error_string(res));
00276     }
00277 }
00278 
00279 void JackMachClientChannel::InternalClientLoad(int refnum, const char* client_name, const char* so_name, const char* objet_data, int options, int* status, int* int_ref, int* result)
00280 {
00281     kern_return_t res = rpc_jack_internal_clientload(fPrivatePort, refnum, (char*)client_name, (char*)so_name, (char*)objet_data, options, status, int_ref, result);
00282     if (res != KERN_SUCCESS) {
00283         *result = -1;
00284         jack_error("JackMachClientChannel::InternalClientLoad err = %s", mach_error_string(res));
00285     }
00286 }
00287 
00288 void JackMachClientChannel::InternalClientUnload(int refnum, int int_ref, int* status, int* result)
00289 {
00290     kern_return_t res = rpc_jack_internal_clientunload(fPrivatePort, refnum, int_ref, status, result);
00291     if (res != KERN_SUCCESS) {
00292         *result = -1;
00293         jack_error("JackMachClientChannel::InternalClientUnload err = %s", mach_error_string(res));
00294     }
00295 }
00296 
00297 bool JackMachClientChannel::Execute()
00298 {
00299     kern_return_t res;
00300     if ((res = mach_msg_server(JackRPCClient_server, 1024, fClientPort.GetPort(), 0)) != KERN_SUCCESS) {
00301         jack_error("JackMachClientChannel::Execute err = %s", mach_error_string(res));
00302         //fClient->ShutDown();
00303         return false;
00304     } else {
00305         return true;
00306     }
00307 }
00308 
00309 } // end of namespace
00310 
00311 

Generated on Thu Feb 14 11:16:02 2008 for Jackdmp by  doxygen 1.5.1