git-svn-id: http://subversion.jackaudio.org/jack/jack2/trunk/jackmp@4514 0c269be4-1314-0410-8aa9-9f06e86f4224tags/1.9.8
| @@ -57,7 +57,7 @@ int JackDummyDriver::Open(jack_nframes_t buffer_size, | |||||
| int buffer_size = lroundf((fWaitTime * fEngineControl->fSampleRate) / 1000000.0f); | int buffer_size = lroundf((fWaitTime * fEngineControl->fSampleRate) / 1000000.0f); | ||||
| if (buffer_size > BUFFER_SIZE_MAX) { | if (buffer_size > BUFFER_SIZE_MAX) { | ||||
| buffer_size = BUFFER_SIZE_MAX; | buffer_size = BUFFER_SIZE_MAX; | ||||
| jack_error("Buffer size set to %d ", BUFFER_SIZE_MAX); | |||||
| jack_error("Buffer size set to %d", BUFFER_SIZE_MAX); | |||||
| } | } | ||||
| SetBufferSize(buffer_size); | SetBufferSize(buffer_size); | ||||
| return 0; | return 0; | ||||
| @@ -156,8 +156,9 @@ extern "C" | |||||
| } | } | ||||
| } | } | ||||
| if (wait_time == 0) // Not set | |||||
| if (wait_time == 0) { // Not set | |||||
| wait_time = (unsigned long)((((float)period_size) / ((float)sample_rate)) * 1000000.0f); | wait_time = (unsigned long)((((float)period_size) / ((float)sample_rate)) * 1000000.0f); | ||||
| } | |||||
| Jack::JackDriverClientInterface* driver = new Jack::JackThreadedDriver(new Jack::JackDummyDriver("system", "dummy_pcm", engine, table, wait_time)); | Jack::JackDriverClientInterface* driver = new Jack::JackThreadedDriver(new Jack::JackDummyDriver("system", "dummy_pcm", engine, table, wait_time)); | ||||
| if (driver->Open(period_size, sample_rate, 1, 1, capture_ports, playback_ports, monitor, "dummy", "dummy", 0, 0) == 0) { | if (driver->Open(period_size, sample_rate, 1, 1, capture_ports, playback_ports, monitor, "dummy", "dummy", 0, 0) == 0) { | ||||
| @@ -194,7 +194,7 @@ struct JackNetExtMaster : public JackNetMasterInterface { | |||||
| } | } | ||||
| // Set a timeout on the multicast receive (the thread can now be cancelled) | // Set a timeout on the multicast receive (the thread can now be cancelled) | ||||
| if (fSocket.SetTimeOut(2000000) == SOCKET_ERROR) { | |||||
| if (fSocket.SetTimeOut(MANAGER_INIT_TIMEOUT) == SOCKET_ERROR) { | |||||
| fprintf(stderr, "Can't set timeout : %s\n", StrError(NET_ERROR_CODE)); | fprintf(stderr, "Can't set timeout : %s\n", StrError(NET_ERROR_CODE)); | ||||
| } | } | ||||
| @@ -630,7 +630,11 @@ struct JackNetExtSlave : public JackNetSlaveInterface, public JackRunnableInterf | |||||
| bool Init() | bool Init() | ||||
| { | { | ||||
| // Will do "something" on OSX only... | // Will do "something" on OSX only... | ||||
| fThread.SetParams(UInt64(float(fParams.fPeriodSize)/float(fParams.fSampleRate)*1000000), 100 * 1000, 500 * 1000); | |||||
| UInt64 period, constraint; | |||||
| period = constraint = float(fParams.fPeriodSize) / float(fParams.fSampleRate) * 1000000; | |||||
| UInt64 computation = JackTools::ComputationMicroSec(fParams.fPeriodSize); | |||||
| fThread.SetParams(period, computation, constraint); | |||||
| return (fThread.AcquireRealTime(80) == 0); // TODO: get a value from the server | return (fThread.AcquireRealTime(80) == 0); // TODO: get a value from the server | ||||
| } | } | ||||
| @@ -639,8 +643,9 @@ struct JackNetExtSlave : public JackNetSlaveInterface, public JackRunnableInterf | |||||
| try { | try { | ||||
| // Keep running even in case of error | // Keep running even in case of error | ||||
| while (fThread.GetStatus() == JackThread::kRunning) { | while (fThread.GetStatus() == JackThread::kRunning) { | ||||
| if (Process() == SOCKET_ERROR) | |||||
| if (Process() == SOCKET_ERROR) { | |||||
| return false; | return false; | ||||
| } | |||||
| } | } | ||||
| return false; | return false; | ||||
| } catch (JackNetException& e) { | } catch (JackNetException& e) { | ||||
| @@ -661,10 +666,9 @@ struct JackNetExtSlave : public JackNetSlaveInterface, public JackRunnableInterf | |||||
| int Read() | int Read() | ||||
| { | { | ||||
| // Don't return -1 in case of sync recv failure | |||||
| // we need the process to continue for network error detection | |||||
| //receive sync (launch the cycle) | |||||
| if (SyncRecv() == SOCKET_ERROR) { | if (SyncRecv() == SOCKET_ERROR) { | ||||
| return 0; | |||||
| return SOCKET_ERROR; | |||||
| } | } | ||||
| DecodeSyncPacket(); | DecodeSyncPacket(); | ||||
| @@ -684,8 +688,7 @@ struct JackNetExtSlave : public JackNetSlaveInterface, public JackRunnableInterf | |||||
| int Process() | int Process() | ||||
| { | { | ||||
| // Read data from the network | |||||
| // in case of fatal network error, stop the process | |||||
| // Read data from the network, throw JackNetException in case of network error... | |||||
| if (Read() == SOCKET_ERROR) { | if (Read() == SOCKET_ERROR) { | ||||
| return SOCKET_ERROR; | return SOCKET_ERROR; | ||||
| } | } | ||||
| @@ -701,8 +704,7 @@ struct JackNetExtSlave : public JackNetSlaveInterface, public JackRunnableInterf | |||||
| (void**)fMidiPlaybackBuffer, | (void**)fMidiPlaybackBuffer, | ||||
| fProcessArg); | fProcessArg); | ||||
| // Then write data to network | |||||
| // in case of failure, stop process | |||||
| // Then write data to network, throw JackNetException in case of network error... | |||||
| if (Write() == SOCKET_ERROR) { | if (Write() == SOCKET_ERROR) { | ||||
| return SOCKET_ERROR; | return SOCKET_ERROR; | ||||
| } | } | ||||
| @@ -801,8 +803,9 @@ struct JackNetAdapter : public JackAudioAdapterInterface { | |||||
| AdaptRingBufferSize(); | AdaptRingBufferSize(); | ||||
| jack_info("Ringbuffer automatic adaptative mode size = %d frames", fRingbufferCurSize); | jack_info("Ringbuffer automatic adaptative mode size = %d frames", fRingbufferCurSize); | ||||
| } else { | } else { | ||||
| if (fRingbufferCurSize > DEFAULT_RB_SIZE) | |||||
| if (fRingbufferCurSize > DEFAULT_RB_SIZE) { | |||||
| fRingbufferCurSize = DEFAULT_RB_SIZE; | fRingbufferCurSize = DEFAULT_RB_SIZE; | ||||
| } | |||||
| jack_info("Fixed ringbuffer size = %d frames", fRingbufferCurSize); | jack_info("Fixed ringbuffer size = %d frames", fRingbufferCurSize); | ||||
| } | } | ||||
| @@ -261,57 +261,56 @@ namespace Jack | |||||
| //audio | //audio | ||||
| port_flags = JackPortIsOutput | JackPortIsPhysical | JackPortIsTerminal; | port_flags = JackPortIsOutput | JackPortIsPhysical | JackPortIsTerminal; | ||||
| for (audio_port_index = 0; audio_port_index < fCaptureChannels; audio_port_index++) | |||||
| { | |||||
| for (audio_port_index = 0; audio_port_index < fCaptureChannels; audio_port_index++) { | |||||
| snprintf(alias, sizeof(alias) - 1, "%s:%s:out%d", fAliasName, fCaptureDriverName, audio_port_index + 1); | snprintf(alias, sizeof(alias) - 1, "%s:%s:out%d", fAliasName, fCaptureDriverName, audio_port_index + 1); | ||||
| snprintf(name, sizeof(name) - 1, "%s:capture_%d", fClientControl.fName, audio_port_index + 1); | snprintf(name, sizeof(name) - 1, "%s:capture_%d", fClientControl.fName, audio_port_index + 1); | ||||
| if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_AUDIO_TYPE, | if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_AUDIO_TYPE, | ||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) | |||||
| { | |||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) { | |||||
| jack_error("driver: cannot register port for %s", name); | jack_error("driver: cannot register port for %s", name); | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| //port latency | |||||
| port = fGraphManager->GetPort(port_index); | port = fGraphManager->GetPort(port_index); | ||||
| port->SetAlias(alias); | port->SetAlias(alias); | ||||
| //port latency | |||||
| range.min = range.max = fEngineControl->fBufferSize; | range.min = range.max = fEngineControl->fBufferSize; | ||||
| port->SetLatencyRange(JackCaptureLatency, &range); | port->SetLatencyRange(JackCaptureLatency, &range); | ||||
| fCapturePortList[audio_port_index] = port_index; | fCapturePortList[audio_port_index] = port_index; | ||||
| jack_log("JackNetDriver::AllocPorts() fCapturePortList[%d] audio_port_index = %ld fPortLatency = %ld", audio_port_index, port_index, port->GetLatency()); | jack_log("JackNetDriver::AllocPorts() fCapturePortList[%d] audio_port_index = %ld fPortLatency = %ld", audio_port_index, port_index, port->GetLatency()); | ||||
| } | } | ||||
| port_flags = JackPortIsInput | JackPortIsPhysical | JackPortIsTerminal; | port_flags = JackPortIsInput | JackPortIsPhysical | JackPortIsTerminal; | ||||
| for (audio_port_index = 0; audio_port_index < fPlaybackChannels; audio_port_index++) | |||||
| { | |||||
| for (audio_port_index = 0; audio_port_index < fPlaybackChannels; audio_port_index++) { | |||||
| snprintf(alias, sizeof(alias) - 1, "%s:%s:in%d", fAliasName, fPlaybackDriverName, audio_port_index + 1); | snprintf(alias, sizeof(alias) - 1, "%s:%s:in%d", fAliasName, fPlaybackDriverName, audio_port_index + 1); | ||||
| snprintf(name, sizeof(name) - 1, "%s:playback_%d",fClientControl.fName, audio_port_index + 1); | snprintf(name, sizeof(name) - 1, "%s:playback_%d",fClientControl.fName, audio_port_index + 1); | ||||
| if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_AUDIO_TYPE, | if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_AUDIO_TYPE, | ||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) | |||||
| { | |||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) { | |||||
| jack_error("driver: cannot register port for %s", name); | jack_error("driver: cannot register port for %s", name); | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| //port latency | |||||
| port = fGraphManager->GetPort(port_index); | port = fGraphManager->GetPort(port_index); | ||||
| port->SetAlias(alias); | port->SetAlias(alias); | ||||
| //port latency | |||||
| range.min = range.max = (fParams.fNetworkLatency * fEngineControl->fBufferSize + (fEngineControl->fSyncMode) ? 0 : fEngineControl->fBufferSize); | range.min = range.max = (fParams.fNetworkLatency * fEngineControl->fBufferSize + (fEngineControl->fSyncMode) ? 0 : fEngineControl->fBufferSize); | ||||
| port->SetLatencyRange(JackPlaybackLatency, &range); | port->SetLatencyRange(JackPlaybackLatency, &range); | ||||
| fPlaybackPortList[audio_port_index] = port_index; | fPlaybackPortList[audio_port_index] = port_index; | ||||
| jack_log("JackNetDriver::AllocPorts() fPlaybackPortList[%d] audio_port_index = %ld fPortLatency = %ld", audio_port_index, port_index, port->GetLatency()); | jack_log("JackNetDriver::AllocPorts() fPlaybackPortList[%d] audio_port_index = %ld fPortLatency = %ld", audio_port_index, port_index, port->GetLatency()); | ||||
| } | } | ||||
| //midi | //midi | ||||
| port_flags = JackPortIsOutput | JackPortIsPhysical | JackPortIsTerminal; | port_flags = JackPortIsOutput | JackPortIsPhysical | JackPortIsTerminal; | ||||
| for (midi_port_index = 0; midi_port_index < fParams.fSendMidiChannels; midi_port_index++) | |||||
| { | |||||
| for (midi_port_index = 0; midi_port_index < fParams.fSendMidiChannels; midi_port_index++) { | |||||
| snprintf(alias, sizeof(alias) - 1, "%s:%s:out%d", fAliasName, fCaptureDriverName, midi_port_index + 1); | snprintf(alias, sizeof(alias) - 1, "%s:%s:out%d", fAliasName, fCaptureDriverName, midi_port_index + 1); | ||||
| snprintf(name, sizeof (name) - 1, "%s:midi_capture_%d", fClientControl.fName, midi_port_index + 1); | snprintf(name, sizeof (name) - 1, "%s:midi_capture_%d", fClientControl.fName, midi_port_index + 1); | ||||
| if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_MIDI_TYPE, | if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_MIDI_TYPE, | ||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) | |||||
| { | |||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) { | |||||
| jack_error("driver: cannot register port for %s", name); | jack_error("driver: cannot register port for %s", name); | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| port = fGraphManager->GetPort(port_index); | |||||
| //port latency | //port latency | ||||
| port = fGraphManager->GetPort(port_index); | |||||
| range.min = range.max = fEngineControl->fBufferSize; | range.min = range.max = fEngineControl->fBufferSize; | ||||
| port->SetLatencyRange(JackCaptureLatency, &range); | port->SetLatencyRange(JackCaptureLatency, &range); | ||||
| fMidiCapturePortList[midi_port_index] = port_index; | fMidiCapturePortList[midi_port_index] = port_index; | ||||
| @@ -319,18 +318,17 @@ namespace Jack | |||||
| } | } | ||||
| port_flags = JackPortIsInput | JackPortIsPhysical | JackPortIsTerminal; | port_flags = JackPortIsInput | JackPortIsPhysical | JackPortIsTerminal; | ||||
| for (midi_port_index = 0; midi_port_index < fParams.fReturnMidiChannels; midi_port_index++) | |||||
| { | |||||
| for (midi_port_index = 0; midi_port_index < fParams.fReturnMidiChannels; midi_port_index++) { | |||||
| snprintf(alias, sizeof(alias) - 1, "%s:%s:in%d", fAliasName, fPlaybackDriverName, midi_port_index + 1); | snprintf(alias, sizeof(alias) - 1, "%s:%s:in%d", fAliasName, fPlaybackDriverName, midi_port_index + 1); | ||||
| snprintf(name, sizeof(name) - 1, "%s:midi_playback_%d", fClientControl.fName, midi_port_index + 1); | snprintf(name, sizeof(name) - 1, "%s:midi_playback_%d", fClientControl.fName, midi_port_index + 1); | ||||
| if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_MIDI_TYPE, | if (fEngine->PortRegister(fClientControl.fRefNum, name, JACK_DEFAULT_MIDI_TYPE, | ||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) | |||||
| { | |||||
| static_cast<JackPortFlags>(port_flags), fEngineControl->fBufferSize, &port_index) < 0) { | |||||
| jack_error("driver: cannot register port for %s", name); | jack_error("driver: cannot register port for %s", name); | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| port = fGraphManager->GetPort(port_index); | |||||
| //port latency | //port latency | ||||
| port = fGraphManager->GetPort(port_index); | |||||
| range.min = range.max = (fParams.fNetworkLatency * fEngineControl->fBufferSize + (fEngineControl->fSyncMode) ? 0 : fEngineControl->fBufferSize); | range.min = range.max = (fParams.fNetworkLatency * fEngineControl->fBufferSize + (fEngineControl->fSyncMode) ? 0 : fEngineControl->fBufferSize); | ||||
| port->SetLatencyRange(JackPlaybackLatency, &range); | port->SetLatencyRange(JackPlaybackLatency, &range); | ||||
| fMidiPlaybackPortList[midi_port_index] = port_index; | fMidiPlaybackPortList[midi_port_index] = port_index; | ||||
| @@ -480,8 +478,9 @@ namespace Jack | |||||
| fReturnTransportData.fNewState = ((fReturnTransportData.fState == JackTransportNetStarting) && | fReturnTransportData.fNewState = ((fReturnTransportData.fState == JackTransportNetStarting) && | ||||
| (fReturnTransportData.fState != fLastTransportState) && | (fReturnTransportData.fState != fLastTransportState) && | ||||
| (fReturnTransportData.fState != fSendTransportData.fState)); | (fReturnTransportData.fState != fSendTransportData.fState)); | ||||
| if (fReturnTransportData.fNewState) | |||||
| if (fReturnTransportData.fNewState) { | |||||
| jack_info("Sending '%s'.", GetTransportState(fReturnTransportData.fState)); | jack_info("Sending '%s'.", GetTransportState(fReturnTransportData.fState)); | ||||
| } | |||||
| fLastTransportState = fReturnTransportData.fState; | fLastTransportState = fReturnTransportData.fState; | ||||
| } | } | ||||
| @@ -74,7 +74,7 @@ namespace Jack | |||||
| JackNetDriver(const char* name, const char* alias, JackLockedEngine* engine, JackSynchro* table, | JackNetDriver(const char* name, const char* alias, JackLockedEngine* engine, JackSynchro* table, | ||||
| const char* ip, int port, int mtu, int midi_input_ports, int midi_output_ports, | const char* ip, int port, int mtu, int midi_input_ports, int midi_output_ports, | ||||
| char* net_name, uint transport_sync, int network_latency, int celt_encoding); | char* net_name, uint transport_sync, int network_latency, int celt_encoding); | ||||
| ~JackNetDriver(); | |||||
| virtual ~JackNetDriver(); | |||||
| int Open(jack_nframes_t frames_per_cycle, jack_nframes_t rate, bool capturing, bool playing, | int Open(jack_nframes_t frames_per_cycle, jack_nframes_t rate, bool capturing, bool playing, | ||||
| int inchannels, int outchannels, bool monitor, const char* capture_driver_name, | int inchannels, int outchannels, bool monitor, const char* capture_driver_name, | ||||
| @@ -318,6 +318,7 @@ namespace Jack | |||||
| case JackFloatEncoder: | case JackFloatEncoder: | ||||
| fNetAudioCaptureBuffer = new NetFloatAudioBuffer(&fParams, fParams.fSendAudioChannels, fTxData); | fNetAudioCaptureBuffer = new NetFloatAudioBuffer(&fParams, fParams.fSendAudioChannels, fTxData); | ||||
| //fNetAudioCaptureBuffer = new NetFloatAudioBuffer1(&fParams, fParams.fSendAudioChannels, fTxData); | |||||
| break; | break; | ||||
| case JackIntEncoder: | case JackIntEncoder: | ||||
| @@ -340,6 +341,7 @@ namespace Jack | |||||
| case JackFloatEncoder: | case JackFloatEncoder: | ||||
| fNetAudioPlaybackBuffer = new NetFloatAudioBuffer(&fParams, fParams.fReturnAudioChannels, fRxData); | fNetAudioPlaybackBuffer = new NetFloatAudioBuffer(&fParams, fParams.fReturnAudioChannels, fRxData); | ||||
| //fNetAudioPlaybackBuffer = new NetFloatAudioBuffer1(&fParams, fParams.fReturnAudioChannels, fRxData); | |||||
| break; | break; | ||||
| case JackIntEncoder: | case JackIntEncoder: | ||||
| @@ -476,7 +478,7 @@ namespace Jack | |||||
| bool JackNetMasterInterface::IsSynched() | bool JackNetMasterInterface::IsSynched() | ||||
| { | { | ||||
| return (fCycleOffset <= fMaxCycleOffset); | |||||
| return (fCurrentCycleOffset <= fMaxCycleOffset); | |||||
| } | } | ||||
| int JackNetMasterInterface::SyncSend() | int JackNetMasterInterface::SyncSend() | ||||
| @@ -520,7 +522,7 @@ namespace Jack | |||||
| return SOCKET_ERROR; | return SOCKET_ERROR; | ||||
| } | } | ||||
| fCycleOffset = fTxHeader.fCycle - rx_head->fCycle; | |||||
| fCurrentCycleOffset = fTxHeader.fCycle - rx_head->fCycle; | |||||
| */ | */ | ||||
| // receive sync (launch the cycle) | // receive sync (launch the cycle) | ||||
| @@ -533,7 +535,7 @@ namespace Jack | |||||
| } | } | ||||
| while ((strcmp(rx_head->fPacketType, "header") != 0) && (rx_head->fDataType != 's')); | while ((strcmp(rx_head->fPacketType, "header") != 0) && (rx_head->fDataType != 's')); | ||||
| fCycleOffset = fTxHeader.fCycle - rx_head->fCycle; | |||||
| fCurrentCycleOffset = fTxHeader.fCycle - rx_head->fCycle; | |||||
| /* | /* | ||||
| // Read active ports list | // Read active ports list | ||||
| @@ -542,8 +544,8 @@ namespace Jack | |||||
| } | } | ||||
| */ | */ | ||||
| if (fCycleOffset < fMaxCycleOffset) { | |||||
| jack_info("Synching with latency = %d", fCycleOffset); | |||||
| if (fCurrentCycleOffset < fMaxCycleOffset) { | |||||
| jack_info("Synching with latency = %d", fCurrentCycleOffset); | |||||
| return 0; | return 0; | ||||
| } else { | } else { | ||||
| rx_bytes = Recv(rx_head->fPacketSize, 0); | rx_bytes = Recv(rx_head->fPacketSize, 0); | ||||
| @@ -592,13 +594,13 @@ namespace Jack | |||||
| void JackNetMasterInterface::EncodeSyncPacket() | void JackNetMasterInterface::EncodeSyncPacket() | ||||
| { | { | ||||
| // This method contains every step of sync packet informations coding | // This method contains every step of sync packet informations coding | ||||
| // first of all, reset sync packet | |||||
| // first of all, clear sync packet | |||||
| memset(fTxData, 0, PACKET_AVAILABLE_SIZE(&fParams)); | memset(fTxData, 0, PACKET_AVAILABLE_SIZE(&fParams)); | ||||
| // then, first step : transport | // then, first step : transport | ||||
| if (fParams.fTransportSync) { | if (fParams.fTransportSync) { | ||||
| EncodeTransportData(); | EncodeTransportData(); | ||||
| TransportDataHToN(&fSendTransportData, &fSendTransportData); | |||||
| TransportDataHToN(&fSendTransportData, &fSendTransportData); | |||||
| // copy to TxBuffer | // copy to TxBuffer | ||||
| memcpy(fTxData, &fSendTransportData, sizeof(net_transport_data_t)); | memcpy(fTxData, &fSendTransportData, sizeof(net_transport_data_t)); | ||||
| } | } | ||||
| @@ -676,10 +678,10 @@ namespace Jack | |||||
| } | } | ||||
| // Separate the connection protocol into two separated step | // Separate the connection protocol into two separated step | ||||
| bool JackNetSlaveInterface::InitConnection(int time_out) | |||||
| bool JackNetSlaveInterface::InitConnection(int time_out_sec) | |||||
| { | { | ||||
| jack_log("JackNetSlaveInterface::InitConnection()"); | jack_log("JackNetSlaveInterface::InitConnection()"); | ||||
| uint try_count = (time_out > 0) ? ((1000000 * time_out) / SLAVE_INIT_TIMEOUT) : LONG_MAX; | |||||
| uint try_count = (time_out_sec > 0) ? ((1000000 * time_out_sec) / SLAVE_INIT_TIMEOUT) : LONG_MAX; | |||||
| // set the parameters to send | // set the parameters to send | ||||
| strcpy(fParams.fPacketType, "params"); | strcpy(fParams.fPacketType, "params"); | ||||
| @@ -800,7 +802,8 @@ namespace Jack | |||||
| bool JackNetSlaveInterface::SetParams() | bool JackNetSlaveInterface::SetParams() | ||||
| { | { | ||||
| jack_log("JackNetSlaveInterface::SetParams audio in = %d audio out = %d MIDI in = %d MIDI out = %d", | jack_log("JackNetSlaveInterface::SetParams audio in = %d audio out = %d MIDI in = %d MIDI out = %d", | ||||
| fParams.fSendAudioChannels, fParams.fReturnAudioChannels, fParams.fSendMidiChannels, fParams.fReturnMidiChannels); | |||||
| fParams.fSendAudioChannels, fParams.fReturnAudioChannels, | |||||
| fParams.fSendMidiChannels, fParams.fReturnMidiChannels); | |||||
| JackNetInterface::SetParams(); | JackNetInterface::SetParams(); | ||||
| @@ -823,6 +826,7 @@ namespace Jack | |||||
| case JackFloatEncoder: | case JackFloatEncoder: | ||||
| fNetAudioCaptureBuffer = new NetFloatAudioBuffer(&fParams, fParams.fSendAudioChannels, fRxData); | fNetAudioCaptureBuffer = new NetFloatAudioBuffer(&fParams, fParams.fSendAudioChannels, fRxData); | ||||
| //fNetAudioCaptureBuffer = new NetFloatAudioBuffer1(&fParams, fParams.fSendAudioChannels, fRxData); | |||||
| break; | break; | ||||
| case JackIntEncoder: | case JackIntEncoder: | ||||
| @@ -845,6 +849,7 @@ namespace Jack | |||||
| case JackFloatEncoder: | case JackFloatEncoder: | ||||
| fNetAudioPlaybackBuffer = new NetFloatAudioBuffer(&fParams, fParams.fReturnAudioChannels, fTxData); | fNetAudioPlaybackBuffer = new NetFloatAudioBuffer(&fParams, fParams.fReturnAudioChannels, fTxData); | ||||
| //fNetAudioPlaybackBuffer = new NetFloatAudioBuffer1(&fParams, fParams.fReturnAudioChannels, fTxData); | |||||
| break; | break; | ||||
| case JackIntEncoder: | case JackIntEncoder: | ||||
| @@ -1039,13 +1044,13 @@ namespace Jack | |||||
| void JackNetSlaveInterface::EncodeSyncPacket() | void JackNetSlaveInterface::EncodeSyncPacket() | ||||
| { | { | ||||
| // This method contains every step of sync packet informations coding | // This method contains every step of sync packet informations coding | ||||
| // first of all, reset sync packet | |||||
| // first of all, clear sync packet | |||||
| memset(fTxData, 0, PACKET_AVAILABLE_SIZE(&fParams)); | memset(fTxData, 0, PACKET_AVAILABLE_SIZE(&fParams)); | ||||
| // then first step : transport | // then first step : transport | ||||
| if (fParams.fTransportSync) { | if (fParams.fTransportSync) { | ||||
| EncodeTransportData(); | EncodeTransportData(); | ||||
| TransportDataHToN(&fReturnTransportData, &fReturnTransportData); | |||||
| TransportDataHToN(&fReturnTransportData, &fReturnTransportData); | |||||
| // copy to TxBuffer | // copy to TxBuffer | ||||
| memcpy(fTxData, &fReturnTransportData, sizeof(net_transport_data_t)); | memcpy(fTxData, &fReturnTransportData, sizeof(net_transport_data_t)); | ||||
| } | } | ||||
| @@ -1083,7 +1088,6 @@ namespace Jack | |||||
| if (fNetAudioPlaybackBuffer) { | if (fNetAudioPlaybackBuffer) { | ||||
| fNetAudioPlaybackBuffer->ActivePortsFromNetwork(fRxData, rx_head->fActivePorts); | fNetAudioPlaybackBuffer->ActivePortsFromNetwork(fRxData, rx_head->fActivePorts); | ||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| @@ -127,7 +127,8 @@ namespace Jack | |||||
| protected: | protected: | ||||
| bool fRunning; | bool fRunning; | ||||
| int fCycleOffset; | |||||
| int fCurrentCycleOffset; | |||||
| int fMaxCycleOffset; | int fMaxCycleOffset; | ||||
| int fLastfCycleOffset; | int fLastfCycleOffset; | ||||
| @@ -157,7 +158,7 @@ namespace Jack | |||||
| public: | public: | ||||
| JackNetMasterInterface() : JackNetInterface(), fRunning(false), fCycleOffset(0), fMaxCycleOffset(0), fLastfCycleOffset(0) | |||||
| JackNetMasterInterface() : JackNetInterface(), fRunning(false), fCurrentCycleOffset(0), fMaxCycleOffset(0), fLastfCycleOffset(0) | |||||
| {} | {} | ||||
| JackNetMasterInterface(session_params_t& params, JackNetSocket& socket, const char* multicast_ip) | JackNetMasterInterface(session_params_t& params, JackNetSocket& socket, const char* multicast_ip) | ||||
| : JackNetInterface(params, socket, multicast_ip) | : JackNetInterface(params, socket, multicast_ip) | ||||
| @@ -179,7 +180,7 @@ namespace Jack | |||||
| static uint fSlaveCounter; | static uint fSlaveCounter; | ||||
| bool Init(); | bool Init(); | ||||
| bool InitConnection(int time_out); | |||||
| bool InitConnection(int time_out_sec); | |||||
| bool InitRendering(); | bool InitRendering(); | ||||
| net_status_t SendAvailableToMaster(long count = LONG_MAX); // long here (and not int...) | net_status_t SendAvailableToMaster(long count = LONG_MAX); // long here (and not int...) | ||||
| @@ -58,7 +58,7 @@ class JackNetOneDriver : public JackAudioDriver | |||||
| int sample_rate, int period_size, int resample_factor, | int sample_rate, int period_size, int resample_factor, | ||||
| const char* net_name, uint transport_sync, int bitdepth, int use_autoconfig, | const char* net_name, uint transport_sync, int bitdepth, int use_autoconfig, | ||||
| int latency, int redundancy, int dont_htonl_floats, int always_deadline, int jitter_val); | int latency, int redundancy, int dont_htonl_floats, int always_deadline, int jitter_val); | ||||
| ~JackNetOneDriver(); | |||||
| virtual ~JackNetOneDriver(); | |||||
| int Open(jack_nframes_t frames_per_cycle, jack_nframes_t rate, bool capturing, bool playing, | int Open(jack_nframes_t frames_per_cycle, jack_nframes_t rate, bool capturing, bool playing, | ||||
| int inchannels, int outchannels, bool monitor, const char* capture_driver_name, | int inchannels, int outchannels, bool monitor, const char* capture_driver_name, | ||||
| @@ -101,8 +101,9 @@ namespace Jack | |||||
| fPortBuffer[port_index] = NULL; | fPortBuffer[port_index] = NULL; | ||||
| fNetBuffer = net_buffer; | fNetBuffer = net_buffer; | ||||
| fCycleSize = params->fMtu * (max(params->fSendMidiChannels, params->fReturnMidiChannels) * | |||||
| params->fPeriodSize * sizeof(sample_t) / (params->fMtu - sizeof(packet_header_t))); | |||||
| fCycleSize = params->fMtu | |||||
| * (max(params->fSendMidiChannels, params->fReturnMidiChannels) | |||||
| * params->fPeriodSize * sizeof(sample_t) / (params->fMtu - sizeof(packet_header_t))); | |||||
| } | } | ||||
| NetMidiBuffer::~NetMidiBuffer() | NetMidiBuffer::~NetMidiBuffer() | ||||
| @@ -137,10 +138,11 @@ namespace Jack | |||||
| { | { | ||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | for (int port_index = 0; port_index < fNPorts; port_index++) { | ||||
| for (uint event = 0; event < fPortBuffer[port_index]->event_count; event++) { | for (uint event = 0; event < fPortBuffer[port_index]->event_count; event++) { | ||||
| if (fPortBuffer[port_index]->IsValid()) | |||||
| if (fPortBuffer[port_index]->IsValid()) { | |||||
| jack_info("port %d : midi event %u/%u -> time : %u, size : %u", | jack_info("port %d : midi event %u/%u -> time : %u, size : %u", | ||||
| port_index + 1, event + 1, fPortBuffer[port_index]->event_count, | port_index + 1, event + 1, fPortBuffer[port_index]->event_count, | ||||
| fPortBuffer[port_index]->events[event].time, fPortBuffer[port_index]->events[event].size); | fPortBuffer[port_index]->events[event].time, fPortBuffer[port_index]->events[event].size); | ||||
| } | |||||
| } | } | ||||
| } | } | ||||
| } | } | ||||
| @@ -155,8 +157,9 @@ namespace Jack | |||||
| copy_size = sizeof(JackMidiBuffer) + fPortBuffer[port_index]->event_count * sizeof(JackMidiEvent); | copy_size = sizeof(JackMidiBuffer) + fPortBuffer[port_index]->event_count * sizeof(JackMidiEvent); | ||||
| memcpy(fBuffer + pos, fPortBuffer[port_index], copy_size); | memcpy(fBuffer + pos, fPortBuffer[port_index], copy_size); | ||||
| pos += copy_size; | pos += copy_size; | ||||
| memcpy(fBuffer + pos, fPortBuffer[port_index] + (fPortBuffer[port_index]->buffer_size - fPortBuffer[port_index]->write_pos), | |||||
| fPortBuffer[port_index]->write_pos); | |||||
| memcpy(fBuffer + pos, | |||||
| fPortBuffer[port_index] + (fPortBuffer[port_index]->buffer_size - fPortBuffer[port_index]->write_pos), | |||||
| fPortBuffer[port_index]->write_pos); | |||||
| pos += fPortBuffer[port_index]->write_pos; | pos += fPortBuffer[port_index]->write_pos; | ||||
| JackMidiBuffer* midi_buffer = reinterpret_cast<JackMidiBuffer*>(write_pos); | JackMidiBuffer* midi_buffer = reinterpret_cast<JackMidiBuffer*>(write_pos); | ||||
| @@ -168,7 +171,7 @@ namespace Jack | |||||
| void NetMidiBuffer::RenderToJackPorts() | void NetMidiBuffer::RenderToJackPorts() | ||||
| { | { | ||||
| int pos = 0; | int pos = 0; | ||||
| int copy_size; | |||||
| size_t copy_size; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | for (int port_index = 0; port_index < fNPorts; port_index++) { | ||||
| JackMidiBuffer* midi_buffer = reinterpret_cast<JackMidiBuffer*>(fBuffer + pos); | JackMidiBuffer* midi_buffer = reinterpret_cast<JackMidiBuffer*>(fBuffer + pos); | ||||
| @@ -177,7 +180,8 @@ namespace Jack | |||||
| memcpy(fPortBuffer[port_index], fBuffer + pos, copy_size); | memcpy(fPortBuffer[port_index], fBuffer + pos, copy_size); | ||||
| pos += copy_size; | pos += copy_size; | ||||
| memcpy(fPortBuffer[port_index] + (fPortBuffer[port_index]->buffer_size - fPortBuffer[port_index]->write_pos), | memcpy(fPortBuffer[port_index] + (fPortBuffer[port_index]->buffer_size - fPortBuffer[port_index]->write_pos), | ||||
| fBuffer + pos, fPortBuffer[port_index]->write_pos); | |||||
| fBuffer + pos, | |||||
| fPortBuffer[port_index]->write_pos); | |||||
| pos += fPortBuffer[port_index]->write_pos; | pos += fPortBuffer[port_index]->write_pos; | ||||
| } | } | ||||
| } | } | ||||
| @@ -197,59 +201,291 @@ namespace Jack | |||||
| // net audio buffer ********************************************************************************* | // net audio buffer ********************************************************************************* | ||||
| //network<->buffer | |||||
| void NetAudioBuffer::ActivePortsToNetwork(uint32_t& port_num) | |||||
| { | |||||
| // Init active port count | |||||
| port_num = 0; | |||||
| short* active_port_address = (short*)fNetBuffer; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| // Write the active port number | |||||
| if (fPortBuffer[port_index]) { | |||||
| *active_port_address = port_index; | |||||
| active_port_address++; | |||||
| port_num++; | |||||
| assert(port_num < 512); | |||||
| } | |||||
| } | |||||
| } | |||||
| void NetAudioBuffer::ActivePortsFromNetwork(uint32_t port_num) | |||||
| { | |||||
| short* active_port_address = (short*)fNetBuffer; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| fPortBuffer[port_index] = NULL; | |||||
| } | |||||
| for (uint port_index = 0; port_index < port_num; port_index++) { | |||||
| // Use -1 when port is actually connected on other side | |||||
| if (*active_port_address >= 0 && *active_port_address < fNPorts) { | |||||
| fPortBuffer[*active_port_address] = (sample_t*)-1; | |||||
| } else { | |||||
| jack_error("ActivePortsFromNetwork: incorrect port = %d", *active_port_address); | |||||
| } | |||||
| active_port_address++; | |||||
| } | |||||
| } | |||||
| // Float | |||||
| NetFloatAudioBuffer::NetFloatAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer) | NetFloatAudioBuffer::NetFloatAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer) | ||||
| : fPortBuffer(params, nports), fNetBuffer(net_buffer) | |||||
| {} | |||||
| : NetAudioBuffer(), fPortBuffer1(params, nports) | |||||
| { | |||||
| fNetBuffer = net_buffer; | |||||
| } | |||||
| NetFloatAudioBuffer::~NetFloatAudioBuffer() | NetFloatAudioBuffer::~NetFloatAudioBuffer() | ||||
| {} | {} | ||||
| size_t NetFloatAudioBuffer::GetCycleSize() | size_t NetFloatAudioBuffer::GetCycleSize() | ||||
| { | { | ||||
| return fPortBuffer.GetCycleSize(); | |||||
| return fPortBuffer1.GetCycleSize(); | |||||
| } | } | ||||
| void NetFloatAudioBuffer::SetBuffer(int index, sample_t* buffer) | void NetFloatAudioBuffer::SetBuffer(int index, sample_t* buffer) | ||||
| { | { | ||||
| fPortBuffer.SetBuffer(index, buffer); | |||||
| fPortBuffer1.SetBuffer(index, buffer); | |||||
| } | } | ||||
| sample_t* NetFloatAudioBuffer::GetBuffer(int index) | sample_t* NetFloatAudioBuffer::GetBuffer(int index) | ||||
| { | { | ||||
| return fPortBuffer.GetBuffer(index); | |||||
| return fPortBuffer1.GetBuffer(index); | |||||
| } | } | ||||
| void NetFloatAudioBuffer::RenderFromJackPorts() | void NetFloatAudioBuffer::RenderFromJackPorts() | ||||
| { | { | ||||
| fPortBuffer.RenderFromJackPorts(); | |||||
| fPortBuffer1.RenderFromJackPorts(); | |||||
| } | } | ||||
| void NetFloatAudioBuffer::RenderToJackPorts() | void NetFloatAudioBuffer::RenderToJackPorts() | ||||
| { | { | ||||
| fPortBuffer.RenderToJackPorts(); | |||||
| fPortBuffer1.RenderToJackPorts(); | |||||
| } | } | ||||
| //network<->buffer | //network<->buffer | ||||
| int NetFloatAudioBuffer::RenderFromNetwork(int cycle, int sub_cycle, size_t copy_size, uint32_t port_num) | int NetFloatAudioBuffer::RenderFromNetwork(int cycle, int sub_cycle, size_t copy_size, uint32_t port_num) | ||||
| { | { | ||||
| return fPortBuffer.RenderFromNetwork(fNetBuffer, cycle, sub_cycle, copy_size, port_num); | |||||
| return fPortBuffer1.RenderFromNetwork(fNetBuffer, cycle, sub_cycle, copy_size, port_num); | |||||
| } | } | ||||
| int NetFloatAudioBuffer::RenderToNetwork(int sub_cycle, uint32_t& port_num) | int NetFloatAudioBuffer::RenderToNetwork(int sub_cycle, uint32_t& port_num) | ||||
| { | { | ||||
| return fPortBuffer.RenderToNetwork(fNetBuffer, sub_cycle, port_num); | |||||
| return fPortBuffer1.RenderToNetwork(fNetBuffer, sub_cycle, port_num); | |||||
| } | } | ||||
| void NetFloatAudioBuffer::ActivePortsToNetwork(char* net_buffer, uint32_t& port_num) | void NetFloatAudioBuffer::ActivePortsToNetwork(char* net_buffer, uint32_t& port_num) | ||||
| { | { | ||||
| fPortBuffer.ActivePortsToNetwork(net_buffer, port_num); | |||||
| fPortBuffer1.ActivePortsToNetwork(net_buffer, port_num); | |||||
| } | } | ||||
| void NetFloatAudioBuffer::ActivePortsFromNetwork(char* net_buffer, uint32_t port_num) | void NetFloatAudioBuffer::ActivePortsFromNetwork(char* net_buffer, uint32_t port_num) | ||||
| { | { | ||||
| fPortBuffer.ActivePortsFromNetwork(net_buffer, port_num); | |||||
| fPortBuffer1.ActivePortsFromNetwork(net_buffer, port_num); | |||||
| } | } | ||||
| // New | |||||
| NetFloatAudioBuffer1::NetFloatAudioBuffer1(session_params_t* params, uint32_t nports, char* net_buffer) | |||||
| : NetAudioBuffer() | |||||
| { | |||||
| fNetBuffer = net_buffer; | |||||
| fNPorts = nports; | |||||
| fPeriodSize = params->fPeriodSize; | |||||
| fPacketSize = params->fMtu - sizeof(packet_header_t); | |||||
| if (params->fSendAudioChannels == 0 && params->fReturnAudioChannels == 0) { | |||||
| fSubPeriodSize = params->fPeriodSize; | |||||
| } else { | |||||
| jack_nframes_t period = (int) powf(2.f,(int)(log(float(fPacketSize) | |||||
| / (max(params->fReturnAudioChannels, params->fSendAudioChannels) | |||||
| * sizeof(sample_t))) / log(2.))); | |||||
| fSubPeriodSize = (period > fPeriodSize) ? fPeriodSize : period; | |||||
| } | |||||
| fSubPeriodBytesSize = fSubPeriodSize * sizeof(sample_t); | |||||
| fPortBuffer = new sample_t* [fNPorts]; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| fPortBuffer[port_index] = NULL; | |||||
| } | |||||
| fCycleDuration = float(fSubPeriodSize) / float(params->fSampleRate); | |||||
| fCycleSize = params->fMtu * (fPeriodSize / fSubPeriodSize); | |||||
| fLastSubCycle = -1; | |||||
| } | |||||
| NetFloatAudioBuffer1::~NetFloatAudioBuffer1() | |||||
| { | |||||
| delete [] fPortBuffer; | |||||
| } | |||||
| void NetFloatAudioBuffer1::SetBuffer(int index, sample_t* buffer) | |||||
| { | |||||
| //jack_info("NetFloatAudioBuffer1::SetBuffer %d %x", index, buffer); | |||||
| fPortBuffer[index] = buffer; | |||||
| } | |||||
| sample_t* NetFloatAudioBuffer1::GetBuffer(int index) | |||||
| { | |||||
| return fPortBuffer[index]; | |||||
| } | |||||
| // needed size in bytes for an entire cycle | |||||
| size_t NetFloatAudioBuffer1::GetCycleSize() | |||||
| { | |||||
| return fCycleSize; | |||||
| } | |||||
| // cycle duration in sec | |||||
| float NetFloatAudioBuffer1::GetCycleDuration() | |||||
| { | |||||
| return fCycleDuration; | |||||
| } | |||||
| int NetFloatAudioBuffer1::GetNumPackets() | |||||
| { | |||||
| // Count active ports | |||||
| int active_ports = 0; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| if (fPortBuffer[port_index]) active_ports++; | |||||
| } | |||||
| if (active_ports == 0) { | |||||
| fSubPeriodSize = fPeriodSize; | |||||
| } else { | |||||
| jack_nframes_t period = (int) powf(2.f, (int)(log(float(fPacketSize) / (active_ports * sizeof(sample_t))) / log(2.))); | |||||
| fSubPeriodSize = (period > fPeriodSize) ? fPeriodSize : period; | |||||
| } | |||||
| fSubPeriodBytesSize = fSubPeriodSize * sizeof(sample_t) + sizeof(uint32_t); // The port number in coded on 4 bytes | |||||
| /* | |||||
| jack_log("GetNumPackets packet = %d fPeriodSize = %d fSubPeriodSize = %d fSubPeriodBytesSize = %d", | |||||
| fPeriodSize / fSubPeriodSize, fPeriodSize, fSubPeriodSize, fSubPeriodBytesSize); | |||||
| */ | |||||
| return fPeriodSize / fSubPeriodSize; // At least one packet | |||||
| } | |||||
| //jack<->buffer | |||||
| int NetFloatAudioBuffer1::RenderFromNetwork(int cycle, int sub_cycle, size_t copy_size, uint32_t port_num) | |||||
| { | |||||
| int res = 0; | |||||
| // Cleanup all JACK ports at the beginning of the cycle | |||||
| if (sub_cycle == 0) { | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| if (fPortBuffer[port_index]) { | |||||
| memset(fPortBuffer[port_index], 0, fPeriodSize * sizeof(sample_t)); | |||||
| } | |||||
| } | |||||
| } | |||||
| if (port_num > 0) { | |||||
| /// Setup rendering parameters | |||||
| int sub_period_size, sub_period_bytes_size; | |||||
| if (port_num == 0) { | |||||
| sub_period_size = fPeriodSize; | |||||
| } else { | |||||
| jack_nframes_t period = (int) powf(2.f, (int)(log(float(fPacketSize) / (port_num * sizeof(sample_t))) / log(2.))); | |||||
| sub_period_size = (period > fPeriodSize) ? fPeriodSize : period; | |||||
| } | |||||
| sub_period_bytes_size = sub_period_size * sizeof(sample_t) + sizeof(uint32_t); // The port number in coded on 4 bytes | |||||
| for (uint32_t port_index = 0; port_index < port_num; port_index++) { | |||||
| // Only copy to active ports : read the active port number then audio data | |||||
| uint32_t* active_port_address = (uint32_t*)(fNetBuffer + port_index * sub_period_bytes_size); | |||||
| uint32_t active_port = (uint32_t)(*active_port_address); | |||||
| if (fPortBuffer[port_index]) { | |||||
| memcpy(fPortBuffer[active_port] + sub_cycle * sub_period_size, (char*)(active_port_address + 1), sub_period_bytes_size - sizeof(uint32_t)); | |||||
| } | |||||
| } | |||||
| if (sub_cycle != fLastSubCycle + 1) { | |||||
| jack_error("Packet(s) missing from... %d %d", fLastSubCycle, sub_cycle); | |||||
| res = NET_PACKET_ERROR; | |||||
| } | |||||
| fLastSubCycle = sub_cycle; | |||||
| } | |||||
| return res; | |||||
| } | |||||
| int NetFloatAudioBuffer1::RenderToNetwork(int sub_cycle, uint32_t& port_num) | |||||
| { | |||||
| // Init active port count | |||||
| port_num = 0; | |||||
| //jack_info("NetFloatAudioBuffer1::RenderToNetwork"); | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| // Only copy from active ports : write the active port number then audio data | |||||
| if (fPortBuffer[port_index]) { | |||||
| jack_info("NetFloatAudioBuffer1::RenderToNetwork %d", port_index); | |||||
| uint32_t* active_port_address = (uint32_t*)(fNetBuffer + port_num * fSubPeriodBytesSize); | |||||
| *active_port_address = port_index; | |||||
| memcpy((char*)(active_port_address + 1), fPortBuffer[port_index] + sub_cycle * fSubPeriodSize, fSubPeriodBytesSize - sizeof(uint32_t)); | |||||
| port_num++; | |||||
| } | |||||
| } | |||||
| return port_num * fSubPeriodBytesSize; | |||||
| } | |||||
| //network<->buffer | |||||
| /* | |||||
| void NetFloatAudioBuffer1::ActivePortsToNetwork(uint32_t& port_num) | |||||
| { | |||||
| // Init active port count | |||||
| port_num = 0; | |||||
| short* active_port_address = (short*)fNetBuffer; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| // Write the active port number | |||||
| if (fPortBuffer[port_index]) { | |||||
| *active_port_address = port_index; | |||||
| active_port_address++; | |||||
| port_num++; | |||||
| assert(port_num < 512); | |||||
| } | |||||
| } | |||||
| } | |||||
| void NetFloatAudioBuffer1::ActivePortsFromNetwork(uint32_t port_num) | |||||
| { | |||||
| short* active_port_address = (short*)fNetBuffer; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | |||||
| fPortBuffer[port_index] = NULL; | |||||
| } | |||||
| for (uint port_index = 0; port_index < port_num; port_index++) { | |||||
| // Use -1 when port is actually connected on other side | |||||
| if (*active_port_address >= 0 && *active_port_address < fNPorts) { | |||||
| fPortBuffer[*active_port_address] = (sample_t*)-1; | |||||
| } else { | |||||
| jack_error("ActivePortsFromNetwork: incorrect port = %d", *active_port_address); | |||||
| } | |||||
| active_port_address++; | |||||
| } | |||||
| } | |||||
| */ | |||||
| // Celt audio buffer ********************************************************************************* | // Celt audio buffer ********************************************************************************* | ||||
| @@ -259,10 +495,10 @@ namespace Jack | |||||
| #define KPS_DIV 8 | #define KPS_DIV 8 | ||||
| NetCeltAudioBuffer::NetCeltAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer, int kbps) | NetCeltAudioBuffer::NetCeltAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer, int kbps) | ||||
| : fNetBuffer(net_buffer) | |||||
| { | { | ||||
| int res1, res2; | int res1, res2; | ||||
| fNetBuffer = net_buffer; | |||||
| fNPorts = nports; | fNPorts = nports; | ||||
| fPeriodSize = params->fPeriodSize; | fPeriodSize = params->fPeriodSize; | ||||
| @@ -496,12 +732,12 @@ namespace Jack | |||||
| #endif | #endif | ||||
| NetIntAudioBuffer::NetIntAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer) | NetIntAudioBuffer::NetIntAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer) | ||||
| : fNetBuffer(net_buffer) | |||||
| { | { | ||||
| int res1, res2; | int res1, res2; | ||||
| fNPorts = nports; | fNPorts = nports; | ||||
| fPeriodSize = params->fPeriodSize; | fPeriodSize = params->fPeriodSize; | ||||
| fNetBuffer = net_buffer; | |||||
| fPortBuffer = new sample_t* [fNPorts]; | fPortBuffer = new sample_t* [fNPorts]; | ||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | for (int port_index = 0; port_index < fNPorts; port_index++) { | ||||
| @@ -638,63 +874,6 @@ namespace Jack | |||||
| } | } | ||||
| } | } | ||||
| // Buffered | |||||
| /* | |||||
| NetBufferedAudioBuffer::NetBufferedAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer) | |||||
| { | |||||
| fMaxCycle = 0; | |||||
| fNetBuffer = net_buffer; | |||||
| for (int i = 0; i < AUDIO_BUFFER_SIZE; i++) { | |||||
| fPortBuffer[i].Init(params, nports); | |||||
| } | |||||
| fJackPortBuffer = new sample_t* [nports]; | |||||
| for (uint32_t port_index = 0; port_index < nports; port_index++) | |||||
| fJackPortBuffer[port_index] = NULL; | |||||
| } | |||||
| NetBufferedAudioBuffer::~NetBufferedAudioBuffer() | |||||
| { | |||||
| delete [] fJackPortBuffer; | |||||
| } | |||||
| size_t NetBufferedAudioBuffer::GetCycleSize() | |||||
| { | |||||
| return fPortBuffer[0].GetCycleSize(); | |||||
| } | |||||
| void NetBufferedAudioBuffer::SetBuffer(int index, sample_t* buffer) | |||||
| { | |||||
| fJackPortBuffer[index] = buffer; | |||||
| } | |||||
| sample_t* NetBufferedAudioBuffer::GetBuffer(int index) | |||||
| { | |||||
| return fJackPortBuffer[index]; | |||||
| } | |||||
| void NetBufferedAudioBuffer::RenderFromJackPorts (int sub_cycle) | |||||
| { | |||||
| fPortBuffer[0].RenderFromJackPorts(fNetBuffer, sub_cycle); // Always use first buffer... | |||||
| } | |||||
| void NetBufferedAudioBuffer::RenderToJackPorts (int cycle, int sub_cycle) | |||||
| { | |||||
| if (cycle < fMaxCycle) { | |||||
| jack_info("Wrong order fCycle %d sub_cycle %d fMaxCycle %d", cycle, sub_cycle, fMaxCycle); | |||||
| } | |||||
| fPortBuffer[cycle % AUDIO_BUFFER_SIZE].RenderToJackPorts(fNetBuffer, sub_cycle); | |||||
| } | |||||
| void NetBufferedAudioBuffer::FinishRenderToJackPorts (int cycle) | |||||
| { | |||||
| fMaxCycle = std::max(fMaxCycle, cycle); | |||||
| fPortBuffer[(cycle + 1) % AUDIO_BUFFER_SIZE].Copy(fJackPortBuffer); // Copy internal buffer in JACK ports | |||||
| } | |||||
| */ | |||||
| // SessionParams ************************************************************************************ | // SessionParams ************************************************************************************ | ||||
| SERVER_EXPORT void SessionParamsHToN(session_params_t* src_params, session_params_t* dst_params) | SERVER_EXPORT void SessionParamsHToN(session_params_t* src_params, session_params_t* dst_params) | ||||
| @@ -273,6 +273,13 @@ namespace Jack | |||||
| class SERVER_EXPORT NetAudioBuffer | class SERVER_EXPORT NetAudioBuffer | ||||
| { | { | ||||
| protected: | |||||
| int fNPorts; | |||||
| int fLastSubCycle; | |||||
| char* fNetBuffer; | |||||
| sample_t** fPortBuffer; | |||||
| public: | public: | ||||
| NetAudioBuffer() | NetAudioBuffer() | ||||
| @@ -301,6 +308,11 @@ namespace Jack | |||||
| virtual void SetBuffer(int index, sample_t* buffer) = 0; | virtual void SetBuffer(int index, sample_t* buffer) = 0; | ||||
| virtual sample_t* GetBuffer(int index) = 0; | virtual sample_t* GetBuffer(int index) = 0; | ||||
| virtual void ActivePortsToNetwork(uint32_t& port_num); | |||||
| virtual void ActivePortsFromNetwork(uint32_t port_num); | |||||
| }; | }; | ||||
| /** | /** | ||||
| @@ -519,7 +531,7 @@ namespace Jack | |||||
| struct JackOptimizedPortList : JackPortList { | struct JackOptimizedPortList : JackPortList { | ||||
| // Consuming port list is transmitted in the Sync packed | // Consuming port list is transmitted in the Sync packed | ||||
| // "[---Header---|--active_port_num---audio data--|--active_port_num---audio data--]..." | |||||
| // "[---Header---|--active_port_num (uint32_t) ---audio data--|--active_port_num (uint32_t) ---audio data--]..." | |||||
| JackOptimizedPortList(session_params_t* params, uint32_t nports) | JackOptimizedPortList(session_params_t* params, uint32_t nports) | ||||
| :JackPortList(params, nports) | :JackPortList(params, nports) | ||||
| @@ -586,10 +598,10 @@ namespace Jack | |||||
| for (uint32_t port_index = 0; port_index < port_num; port_index++) { | for (uint32_t port_index = 0; port_index < port_num; port_index++) { | ||||
| // Only copy to active ports : read the active port number then audio data | // Only copy to active ports : read the active port number then audio data | ||||
| int* active_port_address = (int*)(net_buffer + port_index * sub_period_bytes_size); | |||||
| int active_port = (int)(*active_port_address); | |||||
| uint32_t* active_port_address = (uint32_t*)(net_buffer + port_index * sub_period_bytes_size); | |||||
| uint32_t active_port = (uint32_t)(*active_port_address); | |||||
| if (fPortBuffer[port_index]) { | if (fPortBuffer[port_index]) { | ||||
| memcpy(fPortBuffer[active_port] + sub_cycle * sub_period_size, (char*)(active_port_address + 1), sub_period_bytes_size - sizeof(int)); | |||||
| memcpy(fPortBuffer[active_port] + sub_cycle * sub_period_size, (char*)(active_port_address + 1), sub_period_bytes_size - sizeof(uint32_t)); | |||||
| } | } | ||||
| } | } | ||||
| @@ -612,7 +624,7 @@ namespace Jack | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) { | for (int port_index = 0; port_index < fNPorts; port_index++) { | ||||
| // Only copy from active ports : write the active port number then audio data | // Only copy from active ports : write the active port number then audio data | ||||
| if (fPortBuffer[port_index]) { | if (fPortBuffer[port_index]) { | ||||
| int* active_port_address = (int*)(net_buffer + port_num * fSubPeriodBytesSize); | |||||
| uint32_t* active_port_address = (uint32_t*)(net_buffer + port_num * fSubPeriodBytesSize); | |||||
| *active_port_address = port_index; | *active_port_address = port_index; | ||||
| memcpy((char*)(active_port_address + 1), fPortBuffer[port_index] + sub_cycle * fSubPeriodSize, fSubPeriodBytesSize - sizeof(uint32_t)); | memcpy((char*)(active_port_address + 1), fPortBuffer[port_index] + sub_cycle * fSubPeriodSize, fSubPeriodBytesSize - sizeof(uint32_t)); | ||||
| port_num++; | port_num++; | ||||
| @@ -667,16 +679,15 @@ namespace Jack | |||||
| private: | private: | ||||
| #ifdef OPTIMIZED_PROTOCOL | #ifdef OPTIMIZED_PROTOCOL | ||||
| JackOptimizedPortList fPortBuffer; | |||||
| JackOptimizedPortList fPortBuffer1; | |||||
| #else | #else | ||||
| JackPortList fPortBuffer; | |||||
| JackPortList fPortBuffer1; | |||||
| #endif | #endif | ||||
| char* fNetBuffer; | |||||
| public: | public: | ||||
| NetFloatAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer); | NetFloatAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer); | ||||
| ~NetFloatAudioBuffer(); | |||||
| virtual ~NetFloatAudioBuffer(); | |||||
| // needed size in bytes for an entire cycle | // needed size in bytes for an entire cycle | ||||
| size_t GetCycleSize(); | size_t GetCycleSize(); | ||||
| @@ -684,12 +695,12 @@ namespace Jack | |||||
| // cycle duration in sec | // cycle duration in sec | ||||
| float GetCycleDuration() | float GetCycleDuration() | ||||
| { | { | ||||
| return fPortBuffer.GetCycleDuration(); | |||||
| return fPortBuffer1.GetCycleDuration(); | |||||
| } | } | ||||
| int GetNumPackets() | int GetNumPackets() | ||||
| { | { | ||||
| return fPortBuffer.GetNumPackets(); | |||||
| return fPortBuffer1.GetNumPackets(); | |||||
| } | } | ||||
| //jack<->buffer | //jack<->buffer | ||||
| @@ -707,6 +718,59 @@ namespace Jack | |||||
| void ActivePortsToNetwork(char* net_buffer, uint32_t& port_num); | void ActivePortsToNetwork(char* net_buffer, uint32_t& port_num); | ||||
| }; | }; | ||||
| class SERVER_EXPORT NetFloatAudioBuffer1 : public NetAudioBuffer | |||||
| { | |||||
| private: | |||||
| jack_nframes_t fPeriodSize; | |||||
| jack_nframes_t fSubPeriodSize; | |||||
| size_t fSubPeriodBytesSize; | |||||
| //sample_t** fPortBuffer; | |||||
| int fPacketSize; | |||||
| //int fNPorts; | |||||
| size_t fCycleSize; // needed size in bytes for an entire cycle | |||||
| float fCycleDuration; // in sec | |||||
| //int fLastSubCycle; | |||||
| public: | |||||
| NetFloatAudioBuffer1(session_params_t* params, uint32_t nports, char* net_buffer); | |||||
| virtual ~NetFloatAudioBuffer1(); | |||||
| // needed size in bytes for an entire cycle | |||||
| size_t GetCycleSize(); | |||||
| // cycle duration in sec | |||||
| float GetCycleDuration(); | |||||
| int GetNumPackets(); | |||||
| void SetBuffer(int index, sample_t* buffer); | |||||
| sample_t* GetBuffer(int index); | |||||
| virtual void RenderFromJackPorts() | |||||
| {} | |||||
| virtual void RenderToJackPorts() | |||||
| { | |||||
| // reset for next cycle | |||||
| fLastSubCycle = -1; | |||||
| } | |||||
| //jack<->buffer | |||||
| int RenderFromNetwork(int cycle, int sub_cycle, size_t copy_size, uint32_t port_num); | |||||
| int RenderToNetwork(int sub_cycle, uint32_t& port_num); | |||||
| /* | |||||
| void ActivePortsToNetwork(uint32_t& port_num); | |||||
| void ActivePortsFromNetwork(uint32_t port_num); | |||||
| */ | |||||
| }; | |||||
| #if HAVE_CELT | #if HAVE_CELT | ||||
| #include <celt/celt.h> | #include <celt/celt.h> | ||||
| @@ -729,13 +793,9 @@ namespace Jack | |||||
| size_t fSubPeriodBytesSize; | size_t fSubPeriodBytesSize; | ||||
| size_t fLastSubPeriodBytesSize; | size_t fLastSubPeriodBytesSize; | ||||
| sample_t** fPortBuffer; | |||||
| char* fNetBuffer; | |||||
| //sample_t** fPortBuffer; | |||||
| unsigned char** fCompressedBuffer; | unsigned char** fCompressedBuffer; | ||||
| int fNPorts; | |||||
| int fLastSubCycle; | |||||
| void FreeCelt(); | void FreeCelt(); | ||||
| public: | public: | ||||
| @@ -772,21 +832,19 @@ namespace Jack | |||||
| jack_nframes_t fPeriodSize; | jack_nframes_t fPeriodSize; | ||||
| int fNumPackets; | int fNumPackets; | ||||
| float fCycleDuration; // in sec | float fCycleDuration; // in sec | ||||
| size_t fCycleSize; // needed size in bytes for an entire cycle | size_t fCycleSize; // needed size in bytes for an entire cycle | ||||
| size_t fSubPeriodSize; | size_t fSubPeriodSize; | ||||
| size_t fSubPeriodBytesSize; | size_t fSubPeriodBytesSize; | ||||
| size_t fLastSubPeriodSize; | size_t fLastSubPeriodSize; | ||||
| size_t fLastSubPeriodBytesSize; | size_t fLastSubPeriodBytesSize; | ||||
| sample_t** fPortBuffer; | |||||
| char* fNetBuffer; | |||||
| //sample_t** fPortBuffer; | |||||
| short** fIntBuffer; | short** fIntBuffer; | ||||
| int fNPorts; | |||||
| int fLastSubCycle; | |||||
| public: | public: | ||||
| NetIntAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer); | NetIntAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer); | ||||
| @@ -811,91 +869,6 @@ namespace Jack | |||||
| int RenderToNetwork(int sub_cycle, uint32_t& port_num); | int RenderToNetwork(int sub_cycle, uint32_t& port_num); | ||||
| }; | }; | ||||
| /* | |||||
| #define AUDIO_BUFFER_SIZE 8 | |||||
| struct JackPortListAllocate : public JackPortList { | |||||
| JackPortListAllocate() | |||||
| { | |||||
| fNPorts = 0; | |||||
| fPeriodSize = 0; | |||||
| fSubPeriodSize = 0; | |||||
| fSubPeriodBytesSize = 0; | |||||
| fPortBuffer = 0; | |||||
| } | |||||
| ~JackPortListAllocate() | |||||
| { | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) | |||||
| delete [] fPortBuffer[port_index]; | |||||
| delete [] fPortBuffer; | |||||
| } | |||||
| void Init(session_params_t* params, uint32_t nports) | |||||
| { | |||||
| fNPorts = nports; | |||||
| fPeriodSize = params->fPeriodSize; | |||||
| if (params->fSendAudioChannels == 0 && params->fReturnAudioChannels == 0) { | |||||
| fSubPeriodSize = params->fPeriodSize; | |||||
| } else { | |||||
| jack_nframes_t period = (int) powf(2.f, (int)(log(float((params->fMtu - sizeof(packet_header_t))) | |||||
| / (max(params->fReturnAudioChannels, params->fSendAudioChannels) * sizeof(sample_t))) / log(2.))); | |||||
| fSubPeriodSize = (period > params->fPeriodSize) ? params->fPeriodSize : period; | |||||
| } | |||||
| fSubPeriodBytesSize = fSubPeriodSize * sizeof(sample_t); | |||||
| fPortBuffer = new sample_t* [fNPorts]; | |||||
| for (int port_index = 0; port_index < fNPorts; port_index++) | |||||
| fPortBuffer[port_index] = new sample_t[fPeriodSize]; | |||||
| } | |||||
| }; | |||||
| class SERVER_EXPORT NetBufferedAudioBuffer : public NetAudioBuffer | |||||
| { | |||||
| private: | |||||
| char* fNetBuffer; | |||||
| JackPortListAllocate fPortBuffer[AUDIO_BUFFER_SIZE]; | |||||
| sample_t** fJackPortBuffer; | |||||
| int fMaxCycle; | |||||
| public: | |||||
| NetBufferedAudioBuffer(session_params_t* params, uint32_t nports, char* net_buffer); | |||||
| ~NetBufferedAudioBuffer(); | |||||
| // needed syze in bytes ofr an entire cycle | |||||
| size_t GetCycleSize(); | |||||
| // cycle duration in sec | |||||
| float GetCycleDuration() | |||||
| { | |||||
| return fPortBuffer[0].GetCycleDuration(); | |||||
| } | |||||
| //jack<->buffer | |||||
| void RenderFromJackPorts(int sub_cycle); | |||||
| void RenderToJackPorts(int cycle, int sub_cycle); | |||||
| //void FinishRenderToJackPorts(int cycle); | |||||
| //network<->buffer | |||||
| void RenderFromNetwork(int sub_cycle, size_t copy_size) | |||||
| { | |||||
| // TODO | |||||
| } | |||||
| int RenderToNetwork(int sub_cycle, size_t total_size) | |||||
| { | |||||
| // TODO | |||||
| return 0; | |||||
| } | |||||
| void SetBuffer(int index, sample_t* buffer); | |||||
| sample_t* GetBuffer(int index); | |||||
| }; | |||||
| */ | |||||
| //utility ************************************************************************************* | //utility ************************************************************************************* | ||||
| //socket API management | //socket API management | ||||
| @@ -35,6 +35,7 @@ JackPort::JackPort() | |||||
| bool JackPort::Allocate(int refnum, const char* port_name, const char* port_type, JackPortFlags flags) | bool JackPort::Allocate(int refnum, const char* port_name, const char* port_type, JackPortFlags flags) | ||||
| { | { | ||||
| jack_port_type_id_t id = GetPortTypeId(port_type); | jack_port_type_id_t id = GetPortTypeId(port_type); | ||||
| assert(id >= 0 && id <= PORT_TYPES_MAX); | |||||
| if (id == PORT_TYPES_MAX) | if (id == PORT_TYPES_MAX) | ||||
| return false; | return false; | ||||
| fTypeId = id; | fTypeId = id; | ||||
| @@ -21,6 +21,7 @@ | |||||
| #include "JackSystemDeps.h" | #include "JackSystemDeps.h" | ||||
| #include "JackThreadedDriver.h" | #include "JackThreadedDriver.h" | ||||
| #include "JackError.h" | #include "JackError.h" | ||||
| #include "JackTools.h" | |||||
| #include "JackGlobals.h" | #include "JackGlobals.h" | ||||
| #include "JackEngineControl.h" | #include "JackEngineControl.h" | ||||
| @@ -232,7 +233,7 @@ bool JackThreadedDriver::Init() | |||||
| jack_log("JackThreadedDriver::Init IsRealTime"); | jack_log("JackThreadedDriver::Init IsRealTime"); | ||||
| // Will do "something" on OSX only... | // Will do "something" on OSX only... | ||||
| GetEngineControl()->fPeriod = GetEngineControl()->fConstraint = GetEngineControl()->fPeriodUsecs * 1000; | GetEngineControl()->fPeriod = GetEngineControl()->fConstraint = GetEngineControl()->fPeriodUsecs * 1000; | ||||
| GetEngineControl()->fComputation = ComputationMicroSec(GetEngineControl()->fBufferSize) * 1000; | |||||
| GetEngineControl()->fComputation = JackTools::ComputationMicroSec(GetEngineControl()->fBufferSize) * 1000; | |||||
| fThread.SetParams(GetEngineControl()->fPeriod, GetEngineControl()->fComputation, GetEngineControl()->fConstraint); | fThread.SetParams(GetEngineControl()->fPeriod, GetEngineControl()->fComputation, GetEngineControl()->fConstraint); | ||||
| if (fThread.AcquireSelfRealTime(GetEngineControl()->fServerPriority) < 0) { | if (fThread.AcquireSelfRealTime(GetEngineControl()->fServerPriority) < 0) { | ||||
| jack_error("AcquireSelfRealTime error"); | jack_error("AcquireSelfRealTime error"); | ||||
| @@ -110,18 +110,6 @@ class SERVER_EXPORT JackThreadedDriver : public JackDriverClientInterface, publi | |||||
| virtual bool Execute(); | virtual bool Execute(); | ||||
| virtual bool Init(); | virtual bool Init(); | ||||
| // For OSX only | |||||
| int ComputationMicroSec(int buffer_size) | |||||
| { | |||||
| if (buffer_size < 128) { | |||||
| return 500; | |||||
| } else if (buffer_size < 256) { | |||||
| return 300; | |||||
| } else { | |||||
| return 100; | |||||
| } | |||||
| } | |||||
| }; | }; | ||||
| } // end of namespace | } // end of namespace | ||||
| @@ -68,8 +68,20 @@ namespace Jack | |||||
| static void CleanupFiles ( const char* server_name ); | static void CleanupFiles ( const char* server_name ); | ||||
| static int GetTmpdir(); | static int GetTmpdir(); | ||||
| static void RewriteName ( const char* name, char* new_name ); | static void RewriteName ( const char* name, char* new_name ); | ||||
| static void ThrowJackNetException(); | static void ThrowJackNetException(); | ||||
| // For OSX only | |||||
| static int ComputationMicroSec(int buffer_size) | |||||
| { | |||||
| if (buffer_size < 128) { | |||||
| return 500; | |||||
| } else if (buffer_size < 256) { | |||||
| return 300; | |||||
| } else { | |||||
| return 100; | |||||
| } | |||||
| } | |||||
| }; | }; | ||||
| /*! | /*! | ||||
| @@ -25,6 +25,7 @@ | |||||
| #include "JackEngineControl.h" | #include "JackEngineControl.h" | ||||
| #include "JackException.h" | #include "JackException.h" | ||||
| #include "JackError.h" | #include "JackError.h" | ||||
| #include "JackTools.h" | |||||
| namespace Jack | namespace Jack | ||||
| { | { | ||||
| @@ -47,7 +48,7 @@ bool JackWaitThreadedDriver::Execute() | |||||
| jack_log("JackWaitThreadedDriver::Init IsRealTime"); | jack_log("JackWaitThreadedDriver::Init IsRealTime"); | ||||
| // Will do "something" on OSX only... | // Will do "something" on OSX only... | ||||
| GetEngineControl()->fPeriod = GetEngineControl()->fConstraint = GetEngineControl()->fPeriodUsecs * 1000; | GetEngineControl()->fPeriod = GetEngineControl()->fConstraint = GetEngineControl()->fPeriodUsecs * 1000; | ||||
| GetEngineControl()->fComputation = ComputationMicroSec(GetEngineControl()->fBufferSize) * 1000; | |||||
| GetEngineControl()->fComputation = JackTools::ComputationMicroSec(GetEngineControl()->fBufferSize) * 1000; | |||||
| fThread.SetParams(GetEngineControl()->fPeriod, GetEngineControl()->fComputation, GetEngineControl()->fConstraint); | fThread.SetParams(GetEngineControl()->fPeriod, GetEngineControl()->fComputation, GetEngineControl()->fConstraint); | ||||
| if (fThread.AcquireSelfRealTime(GetEngineControl()->fServerPriority) < 0) { | if (fThread.AcquireSelfRealTime(GetEngineControl()->fServerPriority) < 0) { | ||||
| jack_error("AcquireSelfRealTime error"); | jack_error("AcquireSelfRealTime error"); | ||||
| @@ -155,7 +155,7 @@ int jack_net_slave_deactivate(jack_net_slave_t* net); | |||||
| typedef int (*JackNetSlaveBufferSizeCallback)(jack_nframes_t nframes, void *arg); | typedef int (*JackNetSlaveBufferSizeCallback)(jack_nframes_t nframes, void *arg); | ||||
| /** | /** | ||||
| * Prototype for SampleRate callback | |||||
| * Prototype for SampleRate callback. | |||||
| * @param nframes sample rate | * @param nframes sample rate | ||||
| * @param arg pointer to a client supplied structure supplied by jack_set_net_sample_rate_callback(). | * @param arg pointer to a client supplied structure supplied by jack_set_net_sample_rate_callback(). | ||||
| * | * | ||||
| @@ -184,7 +184,7 @@ int jack_set_net_slave_buffer_size_callback(jack_net_slave_t *net, JackNetSlaveB | |||||
| int jack_set_net_slave_sample_rate_callback(jack_net_slave_t *net, JackNetSlaveSampleRateCallback samplerate_callback, void *arg); | int jack_set_net_slave_sample_rate_callback(jack_net_slave_t *net, JackNetSlaveSampleRateCallback samplerate_callback, void *arg); | ||||
| /** | /** | ||||
| * Prototype for server Shutdown callback (if not set, the client will just restart, waiting for an available master again.) | |||||
| * Prototype for server Shutdown callback (if not set, the client will just restart, waiting for an available master again). | |||||
| * @param arg pointer to a client supplied structure supplied by jack_set_net_shutdown_callback(). | * @param arg pointer to a client supplied structure supplied by jack_set_net_shutdown_callback(). | ||||
| */ | */ | ||||
| typedef void (*JackNetSlaveShutdownCallback)(void* data); | typedef void (*JackNetSlaveShutdownCallback)(void* data); | ||||
| @@ -200,8 +200,8 @@ typedef void (*JackNetSlaveShutdownCallback)(void* data); | |||||
| int jack_set_net_slave_shutdown_callback(jack_net_slave_t *net, JackNetSlaveShutdownCallback shutdown_callback, void *arg); | int jack_set_net_slave_shutdown_callback(jack_net_slave_t *net, JackNetSlaveShutdownCallback shutdown_callback, void *arg); | ||||
| /** | /** | ||||
| * jack_net_master_t is an opaque type. You may only access it using the | |||||
| * API provided. | |||||
| * jack_net_master_t is an opaque type. | |||||
| * You may only access it using the API provided. | |||||
| */ | */ | ||||
| typedef struct _jack_net_master jack_net_master_t; | typedef struct _jack_net_master jack_net_master_t; | ||||
| @@ -217,7 +217,7 @@ typedef struct _jack_net_master jack_net_master_t; | |||||
| jack_net_master_t* jack_net_master_open(const char* ip, int port, const char* name, jack_master_t* request, jack_slave_t* result); | jack_net_master_t* jack_net_master_open(const char* ip, int port, const char* name, jack_master_t* request, jack_slave_t* result); | ||||
| /** | /** | ||||
| * Close the network connection with the master machine. | |||||
| * Close the network connection with the slave machine. | |||||
| * @param net the network connection to be closed | * @param net the network connection to be closed | ||||
| * | * | ||||
| * @return 0 on success, otherwise a non-zero error code | * @return 0 on success, otherwise a non-zero error code | ||||
| @@ -225,7 +225,7 @@ jack_net_master_t* jack_net_master_open(const char* ip, int port, const char* na | |||||
| int jack_net_master_close(jack_net_master_t* net); | int jack_net_master_close(jack_net_master_t* net); | ||||
| /** | /** | ||||
| * Receive sync and data from the network | |||||
| * Receive sync and data from the network. | |||||
| * @param net the network connection | * @param net the network connection | ||||
| * @param audio_input number of audio inputs | * @param audio_input number of audio inputs | ||||
| * @param audio_input_buffer an array of audio input buffers | * @param audio_input_buffer an array of audio input buffers | ||||
| @@ -55,7 +55,7 @@ main (int argc, char *argv[]) | |||||
| int option_index; | int option_index; | ||||
| extern int optind; | extern int optind; | ||||
| jack_port_t* port; | jack_port_t* port; | ||||
| struct option long_options[] = { | struct option long_options[] = { | ||||
| { "unalias", 0, 0, 'u' }, | { "unalias", 0, 0, 'u' }, | ||||
| { "help", 0, 0, 'h' }, | { "help", 0, 0, 'h' }, | ||||
| @@ -129,5 +129,5 @@ main (int argc, char *argv[]) | |||||
| jack_client_close (client); | jack_client_close (client); | ||||
| return ret; | return ret; | ||||
| } | } | ||||
| @@ -103,7 +103,7 @@ int main(int argc, char *argv[]) | |||||
| jack_on_shutdown(client, jack_shutdown, 0); | jack_on_shutdown(client, jack_shutdown, 0); | ||||
| if (just_print_bufsize) { | if (just_print_bufsize) { | ||||
| fprintf(stdout, "%d\n", jack_get_buffer_size( client ) ); | |||||
| fprintf(stdout, "%d %d\n", jack_get_buffer_size(client), jack_get_sample_rate(client)); | |||||
| rc=0; | rc=0; | ||||
| } | } | ||||
| else | else | ||||
| @@ -1,7 +1,7 @@ | |||||
| /* | /* | ||||
| Copyright (C) 2001 Paul Davis | Copyright (C) 2001 Paul Davis | ||||
| Copyright (C) 2003 Jack O'Quin | Copyright (C) 2003 Jack O'Quin | ||||
| This program is free software; you can redistribute it and/or modify | 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 | it under the terms of the GNU General Public License as published by | ||||
| the Free Software Foundation; either version 2 of the License, or | the Free Software Foundation; either version 2 of the License, or | ||||
| @@ -100,7 +100,7 @@ disk_thread (void *arg) | |||||
| info->status = EIO; /* write failed */ | info->status = EIO; /* write failed */ | ||||
| goto done; | goto done; | ||||
| } | } | ||||
| if (++total_captured >= info->duration) { | if (++total_captured >= info->duration) { | ||||
| printf ("disk thread finished\n"); | printf ("disk thread finished\n"); | ||||
| goto done; | goto done; | ||||
| @@ -116,7 +116,7 @@ disk_thread (void *arg) | |||||
| free (framebuf); | free (framebuf); | ||||
| return 0; | return 0; | ||||
| } | } | ||||
| static int | static int | ||||
| process (jack_nframes_t nframes, void *arg) | process (jack_nframes_t nframes, void *arg) | ||||
| { | { | ||||
| @@ -168,10 +168,10 @@ setup_disk_thread (jack_thread_info_t *info) | |||||
| { | { | ||||
| SF_INFO sf_info; | SF_INFO sf_info; | ||||
| int short_mask; | int short_mask; | ||||
| sf_info.samplerate = jack_get_sample_rate (info->client); | sf_info.samplerate = jack_get_sample_rate (info->client); | ||||
| sf_info.channels = info->channels; | sf_info.channels = info->channels; | ||||
| switch (info->bitdepth) { | switch (info->bitdepth) { | ||||
| case 8: short_mask = SF_FORMAT_PCM_U8; | case 8: short_mask = SF_FORMAT_PCM_U8; | ||||
| break; | break; | ||||
| @@ -183,7 +183,7 @@ setup_disk_thread (jack_thread_info_t *info) | |||||
| break; | break; | ||||
| default: short_mask = SF_FORMAT_PCM_16; | default: short_mask = SF_FORMAT_PCM_16; | ||||
| break; | break; | ||||
| } | |||||
| } | |||||
| sf_info.format = SF_FORMAT_WAV|short_mask; | sf_info.format = SF_FORMAT_WAV|short_mask; | ||||
| if ((info->sf = sf_open (info->path, SFM_WRITE, &sf_info)) == NULL) { | if ((info->sf = sf_open (info->path, SFM_WRITE, &sf_info)) == NULL) { | ||||
| @@ -253,7 +253,7 @@ setup_ports (int sources, char *source_names[], jack_thread_info_t *info) | |||||
| fprintf (stderr, "cannot connect input port %s to %s\n", jack_port_name (ports[i]), source_names[i]); | fprintf (stderr, "cannot connect input port %s to %s\n", jack_port_name (ports[i]), source_names[i]); | ||||
| jack_client_close (info->client); | jack_client_close (info->client); | ||||
| exit (1); | exit (1); | ||||
| } | |||||
| } | |||||
| } | } | ||||
| info->can_process = 1; /* process() can start, now */ | info->can_process = 1; /* process() can start, now */ | ||||
| @@ -315,7 +315,7 @@ main (int argc, char *argv[]) | |||||
| } | } | ||||
| if ((client = jack_client_open ("jackrec", JackNullOption, NULL)) == 0) { | if ((client = jack_client_open ("jackrec", JackNullOption, NULL)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| exit (1); | exit (1); | ||||
| } | } | ||||
| @@ -333,7 +333,7 @@ main (int argc, char *argv[]) | |||||
| } | } | ||||
| setup_ports (argc - optind, &argv[optind], &thread_info); | setup_ports (argc - optind, &argv[optind], &thread_info); | ||||
| /* install a signal handler to properly quits jack client */ | /* install a signal handler to properly quits jack client */ | ||||
| signal(SIGQUIT, signal_handler); | signal(SIGQUIT, signal_handler); | ||||
| signal(SIGTERM, signal_handler); | signal(SIGTERM, signal_handler); | ||||
| @@ -133,7 +133,7 @@ main (int argc, char *argv[]) | |||||
| /* try to become a client of the JACK server */ | /* try to become a client of the JACK server */ | ||||
| if ((client = jack_client_open (my_name, options, &status, server_name)) == 0) { | if ((client = jack_client_open (my_name, options, &status, server_name)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -2,7 +2,7 @@ | |||||
| * freewheel - start/stop JACK "freewheeling" mode | * freewheel - start/stop JACK "freewheeling" mode | ||||
| * | * | ||||
| * Copyright (C) 2003 Paul Davis. | * Copyright (C) 2003 Paul Davis. | ||||
| * | |||||
| * | |||||
| * This program is free software; you can redistribute it and/or modify | * 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 | * it under the terms of the GNU General Public License as published by | ||||
| * the Free Software Foundation; either version 2 of the License, or | * the Free Software Foundation; either version 2 of the License, or | ||||
| @@ -58,7 +58,7 @@ static void parse_arguments(int argc, char *argv[]) | |||||
| } | } | ||||
| } | } | ||||
| int | |||||
| int | |||||
| main (int argc, char *argv[]) | main (int argc, char *argv[]) | ||||
| { | { | ||||
| parse_arguments (argc, argv); | parse_arguments (argc, argv); | ||||
| @@ -36,7 +36,7 @@ unsigned long response_duration; | |||||
| unsigned long response_pos; | unsigned long response_pos; | ||||
| int grab_finished = 0; | int grab_finished = 0; | ||||
| jack_client_t *client; | jack_client_t *client; | ||||
| static void signal_handler(int sig) | static void signal_handler(int sig) | ||||
| { | { | ||||
| jack_client_close(client); | jack_client_close(client); | ||||
| @@ -60,7 +60,7 @@ process (jack_nframes_t nframes, void *arg) | |||||
| } | } | ||||
| if (response_pos >= response_duration) { | if (response_pos >= response_duration) { | ||||
| grab_finished = 1; | grab_finished = 1; | ||||
| } | |||||
| } | |||||
| for (i=0; i<nframes; i++) { | for (i=0; i<nframes; i++) { | ||||
| out[i] = 0.0f;; | out[i] = 0.0f;; | ||||
| } | } | ||||
| @@ -72,7 +72,7 @@ process (jack_nframes_t nframes, void *arg) | |||||
| impulse_sent = 1; | impulse_sent = 1; | ||||
| } | } | ||||
| return 0; | |||||
| return 0; | |||||
| } | } | ||||
| static void | static void | ||||
| @@ -132,7 +132,7 @@ main (int argc, char *argv[]) | |||||
| /* try to become a client of the JACK server */ | /* try to become a client of the JACK server */ | ||||
| if ((client = jack_client_open("impulse_grabber", JackNullOption, NULL)) == 0) { | if ((client = jack_client_open("impulse_grabber", JackNullOption, NULL)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -149,7 +149,7 @@ main (int argc, char *argv[]) | |||||
| jack_on_shutdown (client, jack_shutdown, 0); | jack_on_shutdown (client, jack_shutdown, 0); | ||||
| /* display the current sample rate. once the client is activated | |||||
| /* display the current sample rate. once the client is activated | |||||
| (see below), you should rely on your own sample rate | (see below), you should rely on your own sample rate | ||||
| callback (see above) for this value. | callback (see above) for this value. | ||||
| */ | */ | ||||
| @@ -187,7 +187,7 @@ main (int argc, char *argv[]) | |||||
| } | } | ||||
| free (ports); | free (ports); | ||||
| if ((ports = jack_get_ports (client, NULL, NULL, JackPortIsPhysical|JackPortIsInput)) == NULL) { | if ((ports = jack_get_ports (client, NULL, NULL, JackPortIsPhysical|JackPortIsInput)) == NULL) { | ||||
| fprintf(stderr, "Cannot find any physical playback ports"); | fprintf(stderr, "Cannot find any physical playback ports"); | ||||
| exit(1); | exit(1); | ||||
| @@ -198,7 +198,7 @@ main (int argc, char *argv[]) | |||||
| } | } | ||||
| free (ports); | free (ports); | ||||
| /* install a signal handler to properly quits jack client */ | /* install a signal handler to properly quits jack client */ | ||||
| signal(SIGQUIT, signal_handler); | signal(SIGQUIT, signal_handler); | ||||
| signal(SIGTERM, signal_handler); | signal(SIGTERM, signal_handler); | ||||
| @@ -85,9 +85,9 @@ main (int argc, char *argv[]) | |||||
| } else { | } else { | ||||
| fprintf (stdout, "%s unloaded.\n", client_name); | fprintf (stdout, "%s unloaded.\n", client_name); | ||||
| } | } | ||||
| jack_client_close(client); | jack_client_close(client); | ||||
| return 0; | return 0; | ||||
| } | } | ||||
| @@ -20,7 +20,7 @@ | |||||
| #include <unistd.h> | #include <unistd.h> | ||||
| #endif | #endif | ||||
| #include <string.h> | #include <string.h> | ||||
| #include <getopt.h> | |||||
| #include <getopt.h> | |||||
| #include <inttypes.h> | #include <inttypes.h> | ||||
| #include <jack/jack.h> | #include <jack/jack.h> | ||||
| @@ -246,3 +246,4 @@ error: | |||||
| jack_client_close (client); | jack_client_close (client); | ||||
| exit (0); | exit (0); | ||||
| } | } | ||||
| @@ -1,6 +1,6 @@ | |||||
| /* | /* | ||||
| Copyright (C) 2002 Anthony Van Groningen | Copyright (C) 2002 Anthony Van Groningen | ||||
| This program is free software; you can redistribute it and/or modify | 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 | it under the terms of the GNU General Public License as published by | ||||
| the Free Software Foundation; either version 2 of the License, or | the Free Software Foundation; either version 2 of the License, or | ||||
| @@ -69,18 +69,21 @@ usage () | |||||
| } | } | ||||
| static void | static void | ||||
| process_silence (jack_nframes_t nframes) | |||||
| process_silence (jack_nframes_t nframes) | |||||
| { | { | ||||
| sample_t *buffer = (sample_t *) jack_port_get_buffer (output_port, nframes); | sample_t *buffer = (sample_t *) jack_port_get_buffer (output_port, nframes); | ||||
| memset (buffer, 0, sizeof (jack_default_audio_sample_t) * nframes); | memset (buffer, 0, sizeof (jack_default_audio_sample_t) * nframes); | ||||
| } | } | ||||
| jack_nframes_t last_time; | |||||
| jack_time_t last_micro_time; | |||||
| static void | static void | ||||
| process_audio (jack_nframes_t nframes) | |||||
| process_audio (jack_nframes_t nframes) | |||||
| { | { | ||||
| sample_t *buffer = (sample_t *) jack_port_get_buffer (output_port, nframes); | sample_t *buffer = (sample_t *) jack_port_get_buffer (output_port, nframes); | ||||
| jack_nframes_t frames_left = nframes; | jack_nframes_t frames_left = nframes; | ||||
| while (wave_length - offset < frames_left) { | while (wave_length - offset < frames_left) { | ||||
| memcpy (buffer + (nframes - frames_left), wave + offset, sizeof (sample_t) * (wave_length - offset)); | memcpy (buffer + (nframes - frames_left), wave + offset, sizeof (sample_t) * (wave_length - offset)); | ||||
| frames_left -= wave_length - offset; | frames_left -= wave_length - offset; | ||||
| @@ -90,6 +93,13 @@ process_audio (jack_nframes_t nframes) | |||||
| memcpy (buffer + (nframes - frames_left), wave + offset, sizeof (sample_t) * frames_left); | memcpy (buffer + (nframes - frames_left), wave + offset, sizeof (sample_t) * frames_left); | ||||
| offset += frames_left; | offset += frames_left; | ||||
| } | } | ||||
| jack_nframes_t cur_time = jack_frame_time(client); | |||||
| jack_time_t cur_micro_time = jack_get_time(); | |||||
| printf("jack_frame_timed %lld micro %lld delta %d\n", cur_time, (cur_micro_time - last_micro_time), cur_time - last_time); | |||||
| last_time = cur_time; | |||||
| last_micro_time = cur_micro_time; | |||||
| } | } | ||||
| static int | static int | ||||
| @@ -141,7 +151,7 @@ main (int argc, char *argv[]) | |||||
| {"verbose", 0, 0, 'v'}, | {"verbose", 0, 0, 'v'}, | ||||
| {0, 0, 0, 0} | {0, 0, 0, 0} | ||||
| }; | }; | ||||
| while ((opt = getopt_long (argc, argv, options, long_options, &option_index)) != EOF) { | while ((opt = getopt_long (argc, argv, options, long_options, &option_index)) != EOF) { | ||||
| switch (opt) { | switch (opt) { | ||||
| case 'f': | case 'f': | ||||
| @@ -193,7 +203,7 @@ main (int argc, char *argv[]) | |||||
| transport_aware = 1; | transport_aware = 1; | ||||
| break; | break; | ||||
| default: | default: | ||||
| fprintf (stderr, "unknown option %c\n", opt); | |||||
| fprintf (stderr, "unknown option %c\n", opt); | |||||
| case 'h': | case 'h': | ||||
| usage (); | usage (); | ||||
| return -1; | return -1; | ||||
| @@ -211,7 +221,7 @@ main (int argc, char *argv[]) | |||||
| strcpy (client_name, "metro"); | strcpy (client_name, "metro"); | ||||
| } | } | ||||
| if ((client = jack_client_open (client_name, JackNoStartServer, &status)) == 0) { | if ((client = jack_client_open (client_name, JackNoStartServer, &status)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| jack_set_process_callback (client, process, 0); | jack_set_process_callback (client, process, 0); | ||||
| @@ -259,7 +269,7 @@ main (int argc, char *argv[]) | |||||
| fprintf (stderr, "cannot activate client\n"); | fprintf (stderr, "cannot activate client\n"); | ||||
| goto error; | goto error; | ||||
| } | } | ||||
| /* install a signal handler to properly quits jack client */ | /* install a signal handler to properly quits jack client */ | ||||
| #ifdef WIN32 | #ifdef WIN32 | ||||
| signal(SIGINT, signal_handler); | signal(SIGINT, signal_handler); | ||||
| @@ -280,9 +290,9 @@ main (int argc, char *argv[]) | |||||
| sleep(1); | sleep(1); | ||||
| #endif | #endif | ||||
| }; | }; | ||||
| jack_client_close(client); | jack_client_close(client); | ||||
| error: | error: | ||||
| free(amp); | free(amp); | ||||
| free(wave); | free(wave); | ||||
| @@ -1,6 +1,6 @@ | |||||
| /* | /* | ||||
| Copyright (C) 2004 Ian Esten | Copyright (C) 2004 Ian Esten | ||||
| This program is free software; you can redistribute it and/or modify | 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 | it under the terms of the GNU General Public License as published by | ||||
| the Free Software Foundation; either version 2 of the License, or | the Free Software Foundation; either version 2 of the License, or | ||||
| @@ -93,7 +93,7 @@ int main(int narg, char **args) | |||||
| } | } | ||||
| if((client = jack_client_open (args[1], JackNullOption, NULL)) == 0) | if((client = jack_client_open (args[1], JackNullOption, NULL)) == 0) | ||||
| { | { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| jack_set_process_callback (client, process, 0); | jack_set_process_callback (client, process, 0); | ||||
| @@ -117,7 +117,7 @@ int main(int narg, char **args) | |||||
| fprintf (stderr, "cannot activate client"); | fprintf (stderr, "cannot activate client"); | ||||
| return 1; | return 1; | ||||
| } | } | ||||
| /* install a signal handler to properly quits jack client */ | /* install a signal handler to properly quits jack client */ | ||||
| signal(SIGQUIT, signal_handler); | signal(SIGQUIT, signal_handler); | ||||
| signal(SIGTERM, signal_handler); | signal(SIGTERM, signal_handler); | ||||
| @@ -128,7 +128,7 @@ int main(int narg, char **args) | |||||
| while (1) { | while (1) { | ||||
| sleep(1); | sleep(1); | ||||
| }; | }; | ||||
| jack_client_close(client); | jack_client_close(client); | ||||
| exit (0); | exit (0); | ||||
| } | } | ||||
| @@ -1,6 +1,6 @@ | |||||
| /* | /* | ||||
| Copyright (C) 2004 Ian Esten | Copyright (C) 2004 Ian Esten | ||||
| This program is free software; you can redistribute it and/or modify | 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 | it under the terms of the GNU General Public License as published by | ||||
| the Free Software Foundation; either version 2 of the License, or | the Free Software Foundation; either version 2 of the License, or | ||||
| @@ -76,7 +76,7 @@ static int process(jack_nframes_t nframes, void *arg) | |||||
| if ((in_event.time == i) && (event_index < event_count)) | if ((in_event.time == i) && (event_index < event_count)) | ||||
| { | { | ||||
| if (((*(in_event.buffer) & 0xf0)) == 0x90) | if (((*(in_event.buffer) & 0xf0)) == 0x90) | ||||
| { | |||||
| { | |||||
| /* note on */ | /* note on */ | ||||
| note = *(in_event.buffer + 1); | note = *(in_event.buffer + 1); | ||||
| if (*(in_event.buffer + 2) == 0) { | if (*(in_event.buffer + 2) == 0) { | ||||
| @@ -99,7 +99,7 @@ static int process(jack_nframes_t nframes, void *arg) | |||||
| ramp = (ramp > 1.0) ? ramp - 2.0 : ramp; | ramp = (ramp > 1.0) ? ramp - 2.0 : ramp; | ||||
| out[i] = note_on*sin(2*M_PI*ramp); | out[i] = note_on*sin(2*M_PI*ramp); | ||||
| } | } | ||||
| return 0; | |||||
| return 0; | |||||
| } | } | ||||
| static int srate(jack_nframes_t nframes, void *arg) | static int srate(jack_nframes_t nframes, void *arg) | ||||
| @@ -118,10 +118,10 @@ int main(int narg, char **args) | |||||
| { | { | ||||
| if ((client = jack_client_open("midisine", JackNullOption, NULL)) == 0) | if ((client = jack_client_open("midisine", JackNullOption, NULL)) == 0) | ||||
| { | { | ||||
| fprintf(stderr, "jack server not running?\n"); | |||||
| fprintf(stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| calc_note_frqs(jack_get_sample_rate (client)); | calc_note_frqs(jack_get_sample_rate (client)); | ||||
| jack_set_process_callback (client, process, 0); | jack_set_process_callback (client, process, 0); | ||||
| @@ -138,7 +138,7 @@ int main(int narg, char **args) | |||||
| fprintf(stderr, "cannot activate client"); | fprintf(stderr, "cannot activate client"); | ||||
| return 1; | return 1; | ||||
| } | } | ||||
| /* install a signal handler to properly quits jack client */ | /* install a signal handler to properly quits jack client */ | ||||
| signal(SIGQUIT, signal_handler); | signal(SIGQUIT, signal_handler); | ||||
| signal(SIGTERM, signal_handler); | signal(SIGTERM, signal_handler); | ||||
| @@ -42,7 +42,7 @@ main (int argc, char *argv[]) | |||||
| } | } | ||||
| if ((client = jack_client_open ("input monitoring", JackNullOption, NULL)) == 0) { | if ((client = jack_client_open ("input monitoring", JackNullOption, NULL)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -108,7 +108,7 @@ main (int argc, char *argv[]) | |||||
| printf("Waiting for a slave...\n"); | printf("Waiting for a slave...\n"); | ||||
| if ((net = jack_net_master_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "net_master", &request, &result)) == 0) { | if ((net = jack_net_master_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "net_master", &request, &result)) == 0) { | ||||
| fprintf(stderr, "jack server not running?\n"); | |||||
| fprintf(stderr, "NetJack master can not be opened\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -120,13 +120,13 @@ main (int argc, char *argv[]) | |||||
| } | } | ||||
| } | } | ||||
| jack_slave_t request = { audio_input, audio_output, 0, 0, DEFAULT_MTU, -1, 2 }; | |||||
| jack_slave_t request = { audio_input, audio_output, 0, 0, DEFAULT_MTU, -1, JackFloatEncoder, 0, 2 }; | |||||
| jack_master_t result; | jack_master_t result; | ||||
| printf("Waiting for a master...\n"); | printf("Waiting for a master...\n"); | ||||
| if ((net = jack_net_slave_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "net_slave", &request, &result)) == 0) { | if ((net = jack_net_slave_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "net_slave", &request, &result)) == 0) { | ||||
| fprintf(stderr, "jack server not running?\n"); | |||||
| fprintf(stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -136,7 +136,7 @@ main (int argc, char *argv[]) | |||||
| jack_set_net_slave_shutdown_callback(net, net_shutdown, NULL); | jack_set_net_slave_shutdown_callback(net, net_shutdown, NULL); | ||||
| if (jack_net_slave_activate(net) != 0) { | if (jack_net_slave_activate(net) != 0) { | ||||
| fprintf(stderr, "Cannot sactivate client\n"); | |||||
| fprintf(stderr, "Cannot activate slave client\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -164,5 +164,5 @@ main (int argc, char *argv[]) | |||||
| // Wait for application end | // Wait for application end | ||||
| jack_net_slave_deactivate(net); | jack_net_slave_deactivate(net); | ||||
| jack_net_slave_close(net); | jack_net_slave_close(net); | ||||
| exit (0); | |||||
| exit(0); | |||||
| } | } | ||||
| @@ -34,7 +34,7 @@ showtime () | |||||
| transport_state = jack_transport_query (client, ¤t); | transport_state = jack_transport_query (client, ¤t); | ||||
| frame_time = jack_frame_time (client); | frame_time = jack_frame_time (client); | ||||
| printf ("frame = %u frame_time = %u usecs = %lld \t", current.frame, frame_time, current.usecs); | printf ("frame = %u frame_time = %u usecs = %lld \t", current.frame, frame_time, current.usecs); | ||||
| switch (transport_state) { | switch (transport_state) { | ||||
| @@ -81,7 +81,7 @@ main (int argc, char *argv[]) | |||||
| /* try to become a client of the JACK server */ | /* try to become a client of the JACK server */ | ||||
| if ((client = jack_client_open ("showtime", JackNullOption, NULL)) == 0) { | if ((client = jack_client_open ("showtime", JackNullOption, NULL)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| return 1; | return 1; | ||||
| } | } | ||||
| @@ -103,7 +103,7 @@ main (int argc, char *argv[]) | |||||
| fprintf (stderr, "cannot activate client"); | fprintf (stderr, "cannot activate client"); | ||||
| return 1; | return 1; | ||||
| } | } | ||||
| while (1) { | while (1) { | ||||
| usleep (20); | usleep (20); | ||||
| showtime (); | showtime (); | ||||
| @@ -54,7 +54,7 @@ main (int argc, char *argv[]) | |||||
| jack_client_t* client = NULL; | jack_client_t* client = NULL; | ||||
| /* try to become a client of the JACK server */ | /* try to become a client of the JACK server */ | ||||
| if ((client = jack_client_open ("zombie", JackNullOption, NULL)) == 0) { | if ((client = jack_client_open ("zombie", JackNullOption, NULL)) == 0) { | ||||
| fprintf (stderr, "jack server not running?\n"); | |||||
| fprintf (stderr, "JACK server not running?\n"); | |||||
| goto error; | goto error; | ||||
| } | } | ||||
| @@ -24,7 +24,7 @@ int buffer_size = 1024; | |||||
| int sample_rate = 22050; | int sample_rate = 22050; | ||||
| //int sample_rate = 32000; | //int sample_rate = 32000; | ||||
| jack_master_t request = { buffer_size, sample_rate, "master" }; | |||||
| jack_master_t request = { -1, -1, -1, -1, buffer_size, sample_rate, "master" }; | |||||
| jack_slave_t result; | jack_slave_t result; | ||||
| static void MixAudio(float** dst, float** src1, float** src2, int channels, int buffer_size) | static void MixAudio(float** dst, float** src1, float** src2, int channels, int buffer_size) | ||||
| @@ -38,33 +38,33 @@ static void MixAudio(float** dst, float** src1, float** src2, int channels, int | |||||
| static void MasterAudioCallback(int frames, float** inputs, float** outputs, void* arg) | static void MasterAudioCallback(int frames, float** inputs, float** outputs, void* arg) | ||||
| { | { | ||||
| int i; | |||||
| int i; | |||||
| // Copy from iPod input to network buffers | // Copy from iPod input to network buffers | ||||
| for (i = 0; i < result.audio_input; i++) { | for (i = 0; i < result.audio_input; i++) { | ||||
| memcpy(audio_input_buffer[i], inputs[i], buffer_size * sizeof(float)); | memcpy(audio_input_buffer[i], inputs[i], buffer_size * sizeof(float)); | ||||
| } | } | ||||
| /* | /* | ||||
| // Copy from network out buffers to network in buffers (audio thru) | // Copy from network out buffers to network in buffers (audio thru) | ||||
| for (i = 0; i < result.audio_input; i++) { | for (i = 0; i < result.audio_input; i++) { | ||||
| memcpy(audio_input_buffer[i], audio_output_buffer[i], buffer_size * sizeof(float)); | memcpy(audio_input_buffer[i], audio_output_buffer[i], buffer_size * sizeof(float)); | ||||
| } | } | ||||
| */ | */ | ||||
| // Mix iPod input and network in buffers to network out buffers | // Mix iPod input and network in buffers to network out buffers | ||||
| //MixAudio(audio_input_buffer, inputs, audio_output_buffer, result.audio_input, buffer_size); | //MixAudio(audio_input_buffer, inputs, audio_output_buffer, result.audio_input, buffer_size); | ||||
| // Send network buffers | // Send network buffers | ||||
| if (jack_net_master_send(net, result.audio_input, audio_input_buffer, 0, NULL) < 0) { | if (jack_net_master_send(net, result.audio_input, audio_input_buffer, 0, NULL) < 0) { | ||||
| printf("jack_net_master_send error..\n"); | printf("jack_net_master_send error..\n"); | ||||
| } | } | ||||
| // Recv network buffers | // Recv network buffers | ||||
| if (jack_net_master_recv(net, result.audio_output, audio_output_buffer, 0, NULL) < 0) { | if (jack_net_master_recv(net, result.audio_output, audio_output_buffer, 0, NULL) < 0) { | ||||
| printf("jack_net_master_recv error..\n"); | printf("jack_net_master_recv error..\n"); | ||||
| } | } | ||||
| // Copy from network buffers to iPod output | // Copy from network buffers to iPod output | ||||
| for (i = 0; i < result.audio_output; i++) { | for (i = 0; i < result.audio_output; i++) { | ||||
| memcpy(outputs[i], audio_output_buffer[i], buffer_size * sizeof(float)); | memcpy(outputs[i], audio_output_buffer[i], buffer_size * sizeof(float)); | ||||
| @@ -72,17 +72,17 @@ static void MasterAudioCallback(int frames, float** inputs, float** outputs, voi | |||||
| } | } | ||||
| int main(int argc, char *argv[]) { | int main(int argc, char *argv[]) { | ||||
| NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; | NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; | ||||
| int i; | int i; | ||||
| if ((net = jack_net_master_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "iPhone", &request, &result)) == 0) { | if ((net = jack_net_master_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "iPhone", &request, &result)) == 0) { | ||||
| printf("jack_net_master_open error..\n"); | printf("jack_net_master_open error..\n"); | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| TiPhoneCoreAudioRenderer audio_device(result.audio_input, result.audio_output); | TiPhoneCoreAudioRenderer audio_device(result.audio_input, result.audio_output); | ||||
| // Allocate buffers | // Allocate buffers | ||||
| if (result.audio_input > 0) { | if (result.audio_input > 0) { | ||||
| audio_input_buffer = (float**)calloc(result.audio_input, sizeof(float*)); | audio_input_buffer = (float**)calloc(result.audio_input, sizeof(float*)); | ||||
| @@ -90,66 +90,66 @@ int main(int argc, char *argv[]) { | |||||
| audio_input_buffer[i] = (float*)(calloc(buffer_size, sizeof(float))); | audio_input_buffer[i] = (float*)(calloc(buffer_size, sizeof(float))); | ||||
| } | } | ||||
| } | } | ||||
| if (result.audio_output > 0) { | if (result.audio_output > 0) { | ||||
| audio_output_buffer = (float**)calloc(result.audio_output, sizeof(float*)); | audio_output_buffer = (float**)calloc(result.audio_output, sizeof(float*)); | ||||
| for (i = 0; i < result.audio_output; i++) { | for (i = 0; i < result.audio_output; i++) { | ||||
| audio_output_buffer[i] = (float*)(calloc(buffer_size, sizeof(float))); | audio_output_buffer[i] = (float*)(calloc(buffer_size, sizeof(float))); | ||||
| } | } | ||||
| } | } | ||||
| if (audio_device.Open(buffer_size, sample_rate) < 0) { | if (audio_device.Open(buffer_size, sample_rate) < 0) { | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| audio_device.SetAudioCallback(MasterAudioCallback, NULL); | audio_device.SetAudioCallback(MasterAudioCallback, NULL); | ||||
| if (audio_device.Start() < 0) { | if (audio_device.Start() < 0) { | ||||
| return -1; | return -1; | ||||
| } | } | ||||
| /* | /* | ||||
| // Quite brutal way, the application actually does not start completely, the netjack audio processing loop is used instead... | // Quite brutal way, the application actually does not start completely, the netjack audio processing loop is used instead... | ||||
| // Run until interrupted | |||||
| // Run until interrupted | |||||
| int wait_usec = (unsigned long)((((float)buffer_size) / ((float)sample_rate)) * 1000000.0f); | int wait_usec = (unsigned long)((((float)buffer_size) / ((float)sample_rate)) * 1000000.0f); | ||||
| while (1) { | while (1) { | ||||
| // Copy input to output | // Copy input to output | ||||
| for (i = 0; i < result.audio_input; i++) { | for (i = 0; i < result.audio_input; i++) { | ||||
| memcpy(audio_output_buffer[i], audio_input_buffer[i], buffer_size * sizeof(float)); | memcpy(audio_output_buffer[i], audio_input_buffer[i], buffer_size * sizeof(float)); | ||||
| } | } | ||||
| if (jack_net_master_send(net, result.audio_output, audio_output_buffer, 0, NULL) < 0) { | if (jack_net_master_send(net, result.audio_output, audio_output_buffer, 0, NULL) < 0) { | ||||
| printf("jack_net_master_send error..\n"); | printf("jack_net_master_send error..\n"); | ||||
| } | } | ||||
| if (jack_net_master_recv(net, result.audio_input, audio_input_buffer, 0, NULL) < 0) { | if (jack_net_master_recv(net, result.audio_input, audio_input_buffer, 0, NULL) < 0) { | ||||
| printf("jack_net_master_recv error..\n"); | printf("jack_net_master_recv error..\n"); | ||||
| } | } | ||||
| usleep(wait_usec); | usleep(wait_usec); | ||||
| }; | }; | ||||
| */ | */ | ||||
| int retVal = UIApplicationMain(argc, argv, nil, nil); | int retVal = UIApplicationMain(argc, argv, nil, nil); | ||||
| audio_device.Stop(); | audio_device.Stop(); | ||||
| audio_device.Close(); | audio_device.Close(); | ||||
| // Wait for application end | // Wait for application end | ||||
| jack_net_master_close(net); | jack_net_master_close(net); | ||||
| for (i = 0; i < result.audio_input; i++) { | for (i = 0; i < result.audio_input; i++) { | ||||
| free(audio_input_buffer[i]); | free(audio_input_buffer[i]); | ||||
| } | } | ||||
| free(audio_input_buffer); | free(audio_input_buffer); | ||||
| for (i = 0; i < result.audio_output; i++) { | for (i = 0; i < result.audio_output; i++) { | ||||
| free(audio_output_buffer[i]); | free(audio_output_buffer[i]); | ||||
| } | } | ||||
| free(audio_output_buffer); | free(audio_output_buffer); | ||||
| [pool release]; | [pool release]; | ||||
| return retVal; | return retVal; | ||||
| } | } | ||||
| @@ -67,7 +67,7 @@ int main(int argc, char *argv[]) { | |||||
| //if ((net = jack_net_slave_open("169.254.112.119", DEFAULT_PORT, "iPhone", &request, &result)) == 0) { | //if ((net = jack_net_slave_open("169.254.112.119", DEFAULT_PORT, "iPhone", &request, &result)) == 0) { | ||||
| if ((net = jack_net_slave_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "iPod", &request, &result)) == 0) { | if ((net = jack_net_slave_open(DEFAULT_MULTICAST_IP, DEFAULT_PORT, "iPod", &request, &result)) == 0) { | ||||
| printf("jack_net_slave_open error..\n"); | |||||
| printf("jack_net_slave_open error...\n"); | |||||
| return -1; | return -1; | ||||
| } | } | ||||
| @@ -86,6 +86,7 @@ int main(int argc, char *argv[]) { | |||||
| jack_set_net_slave_shutdown_callback(net, net_shutdown, NULL); | jack_set_net_slave_shutdown_callback(net, net_shutdown, NULL); | ||||
| if (jack_net_slave_activate(net) != 0) { | if (jack_net_slave_activate(net) != 0) { | ||||
| printf("Cannot activate slave client\n"); | |||||
| return -1; | return -1; | ||||
| } | } | ||||