jack2 codebase
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

966 lines
36KB

  1. /*
  2. Copyright (C) 2008-2011 Torben Horn
  3. This program is free software; you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation; either version 2 of the License, or
  6. (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program; if not, write to the Free Software
  13. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  14. */
  15. #ifdef WIN32
  16. #include <malloc.h>
  17. #endif
  18. #include "JackNetOneDriver.h"
  19. #include "JackEngineControl.h"
  20. #include "JackLockedEngine.h"
  21. #include "JackGraphManager.h"
  22. #include "JackWaitThreadedDriver.h"
  23. #include "JackTools.h"
  24. #include "driver_interface.h"
  25. #include "netjack.h"
  26. #include "netjack_packet.h"
  27. #if HAVE_SAMPLERATE
  28. #include <samplerate.h>
  29. #endif
  30. #if HAVE_CELT
  31. #include <celt/celt.h>
  32. #endif
  33. #define MIN(x,y) ((x)<(y) ? (x) : (y))
  34. using namespace std;
  35. namespace Jack
  36. {
  37. JackNetOneDriver::JackNetOneDriver(const char* name, const char* alias, JackLockedEngine* engine, JackSynchro* table,
  38. int port, int mtu, int capture_ports, int playback_ports, int midi_input_ports, int midi_output_ports,
  39. int sample_rate, int period_size, int resample_factor,
  40. const char* net_name, uint transport_sync, int bitdepth, int use_autoconfig,
  41. int latency, int redundancy, int dont_htonl_floats, int always_deadline, int jitter_val)
  42. : JackTimedDriver(name, alias, engine, table)
  43. {
  44. jack_log("JackNetOneDriver::JackNetOneDriver port %d", port);
  45. #ifdef WIN32
  46. WSADATA wsa;
  47. int rc = WSAStartup(MAKEWORD(2, 0), &wsa);
  48. #endif
  49. netjack_init(& (this->netj),
  50. NULL, // client
  51. name,
  52. capture_ports,
  53. playback_ports,
  54. midi_input_ports,
  55. midi_output_ports,
  56. sample_rate,
  57. period_size,
  58. port,
  59. transport_sync,
  60. resample_factor,
  61. 0,
  62. bitdepth,
  63. use_autoconfig,
  64. latency,
  65. redundancy,
  66. dont_htonl_floats,
  67. always_deadline,
  68. jitter_val);
  69. }
  70. JackNetOneDriver::~JackNetOneDriver()
  71. {
  72. // No destructor yet.
  73. }
  74. //open, close, attach and detach------------------------------------------------------
  75. int JackNetOneDriver::Close()
  76. {
  77. // Generic audio driver close
  78. int res = JackTimedDriver::Close();
  79. FreePorts();
  80. netjack_release(&netj);
  81. return res;
  82. }
  83. int JackNetOneDriver::Attach()
  84. {
  85. return 0;
  86. }
  87. int JackNetOneDriver::Detach()
  88. {
  89. return 0;
  90. }
  91. int JackNetOneDriver::AllocPorts()
  92. {
  93. jack_port_id_t port_index;
  94. char buf[64];
  95. unsigned int chn;
  96. //if (netj.handle_transport_sync)
  97. // jack_set_sync_callback(netj.client, (JackSyncCallback) net_driver_sync_cb, NULL);
  98. for (chn = 0; chn < netj.capture_channels_audio; chn++) {
  99. snprintf (buf, sizeof(buf) - 1, "system:capture_%u", chn + 1);
  100. if (fEngine->PortRegister(fClientControl.fRefNum, buf, JACK_DEFAULT_AUDIO_TYPE,
  101. CaptureDriverFlags, fEngineControl->fBufferSize, &port_index) < 0) {
  102. jack_error ( "driver: cannot register port for %s", buf );
  103. return -1;
  104. }
  105. //port = fGraphManager->GetPort ( port_index );
  106. netj.capture_ports = jack_slist_append (netj.capture_ports, (void *)(intptr_t)port_index);
  107. if (netj.bitdepth == CELT_MODE) {
  108. #if HAVE_CELT
  109. #if HAVE_CELT_API_0_11
  110. celt_int32 lookahead;
  111. CELTMode *celt_mode = celt_mode_create( netj.sample_rate, netj.period_size, NULL );
  112. netj.capture_srcs = jack_slist_append(netj.capture_srcs, celt_decoder_create_custom( celt_mode, 1, NULL ) );
  113. #elif HAVE_CELT_API_0_7 || HAVE_CELT_API_0_8
  114. celt_int32 lookahead;
  115. CELTMode *celt_mode = celt_mode_create( netj.sample_rate, netj.period_size, NULL );
  116. netj.capture_srcs = jack_slist_append(netj.capture_srcs, celt_decoder_create( celt_mode, 1, NULL ) );
  117. #else
  118. celt_int32_t lookahead;
  119. CELTMode *celt_mode = celt_mode_create( netj.sample_rate, 1, netj.period_size, NULL );
  120. netj.capture_srcs = jack_slist_append(netj.capture_srcs, celt_decoder_create( celt_mode ) );
  121. #endif
  122. celt_mode_info( celt_mode, CELT_GET_LOOKAHEAD, &lookahead );
  123. netj.codec_latency = 2 * lookahead;
  124. #endif
  125. } else {
  126. #if HAVE_SAMPLERATE
  127. netj.capture_srcs = jack_slist_append(netj.capture_srcs, (void *)src_new(SRC_LINEAR, 1, NULL));
  128. #endif
  129. }
  130. }
  131. for (chn = netj.capture_channels_audio; chn < netj.capture_channels; chn++) {
  132. snprintf (buf, sizeof(buf) - 1, "system:capture_%u", chn + 1);
  133. if (fEngine->PortRegister(fClientControl.fRefNum, buf, JACK_DEFAULT_MIDI_TYPE,
  134. CaptureDriverFlags, fEngineControl->fBufferSize, &port_index) < 0) {
  135. jack_error ( "driver: cannot register port for %s", buf );
  136. return -1;
  137. }
  138. //port = fGraphManager->GetPort ( port_index );
  139. netj.capture_ports =
  140. jack_slist_append (netj.capture_ports, (void *)(intptr_t)port_index);
  141. }
  142. for (chn = 0; chn < netj.playback_channels_audio; chn++) {
  143. snprintf (buf, sizeof(buf) - 1, "system:playback_%u", chn + 1);
  144. if (fEngine->PortRegister(fClientControl.fRefNum, buf, JACK_DEFAULT_AUDIO_TYPE,
  145. PlaybackDriverFlags, fEngineControl->fBufferSize, &port_index) < 0) {
  146. jack_error ( "driver: cannot register port for %s", buf );
  147. return -1;
  148. }
  149. //port = fGraphManager->GetPort ( port_index );
  150. netj.playback_ports = jack_slist_append (netj.playback_ports, (void *)(intptr_t)port_index);
  151. if( netj.bitdepth == CELT_MODE ) {
  152. #if HAVE_CELT
  153. #if HAVE_CELT_API_0_11
  154. CELTMode *celt_mode = celt_mode_create( netj.sample_rate, netj.period_size, NULL );
  155. netj.playback_srcs = jack_slist_append(netj.playback_srcs, celt_encoder_create_custom( celt_mode, 1, NULL ) );
  156. #elif HAVE_CELT_API_0_7 || HAVE_CELT_API_0_8
  157. CELTMode *celt_mode = celt_mode_create( netj.sample_rate, netj.period_size, NULL );
  158. netj.playback_srcs = jack_slist_append(netj.playback_srcs, celt_encoder_create( celt_mode, 1, NULL ) );
  159. #else
  160. CELTMode *celt_mode = celt_mode_create( netj.sample_rate, 1, netj.period_size, NULL );
  161. netj.playback_srcs = jack_slist_append(netj.playback_srcs, celt_encoder_create( celt_mode ) );
  162. #endif
  163. #endif
  164. } else {
  165. #if HAVE_SAMPLERATE
  166. netj.playback_srcs = jack_slist_append(netj.playback_srcs, (void *)src_new(SRC_LINEAR, 1, NULL));
  167. #endif
  168. }
  169. }
  170. for (chn = netj.playback_channels_audio; chn < netj.playback_channels; chn++) {
  171. snprintf (buf, sizeof(buf) - 1, "system:playback_%u", chn + 1);
  172. if (fEngine->PortRegister(fClientControl.fRefNum, buf, JACK_DEFAULT_MIDI_TYPE,
  173. PlaybackDriverFlags, fEngineControl->fBufferSize, &port_index) < 0) {
  174. jack_error ( "driver: cannot register port for %s", buf );
  175. return -1;
  176. }
  177. //port = fGraphManager->GetPort ( port_index );
  178. netj.playback_ports =
  179. jack_slist_append (netj.playback_ports, (void *)(intptr_t)port_index);
  180. }
  181. return 0;
  182. }
  183. //init and restart--------------------------------------------------------------------
  184. bool JackNetOneDriver::Initialize()
  185. {
  186. jack_log ( "JackNetOneDriver::Init()" );
  187. FreePorts();
  188. netjack_release( &netj );
  189. //display some additional infos
  190. jack_info ( "NetOne driver started" );
  191. if( netjack_startup( &netj ) ) {
  192. return false;
  193. }
  194. //register jack ports
  195. if ( AllocPorts() != 0 ) {
  196. jack_error ( "Can't allocate ports." );
  197. return false;
  198. }
  199. //monitor
  200. //driver parametering
  201. JackTimedDriver::SetBufferSize ( netj.period_size );
  202. JackTimedDriver::SetSampleRate ( netj.sample_rate );
  203. JackDriver::NotifyBufferSize ( netj.period_size );
  204. JackDriver::NotifySampleRate ( netj.sample_rate );
  205. //transport engine parametering
  206. fEngineControl->fTransport.SetNetworkSync ( true );
  207. return true;
  208. }
  209. //jack ports and buffers--------------------------------------------------------------
  210. //driver processes--------------------------------------------------------------------
  211. int JackNetOneDriver::Process()
  212. {
  213. return (fEngineControl->fSyncMode) ? ProcessSync() : ProcessAsync();
  214. }
  215. int JackNetOneDriver::Read()
  216. {
  217. int delay;
  218. delay = netjack_wait( &netj );
  219. if( delay ) {
  220. NotifyXRun(fBeginDateUst, (float) delay);
  221. jack_error( "netxruns... duration: %dms", delay / 1000 );
  222. }
  223. if( (netj.num_lost_packets * netj.period_size / netj.sample_rate) > 2 )
  224. JackTools::ThrowJackNetException();
  225. //netjack_read( &netj, netj.period_size );
  226. JackDriver::CycleTakeBeginTime();
  227. jack_position_t local_trans_pos;
  228. jack_transport_state_t local_trans_state;
  229. unsigned int *packet_buf, *packet_bufX;
  230. if( ! netj.packet_data_valid ) {
  231. jack_log( "data not valid" );
  232. render_payload_to_jack_ports (netj.bitdepth, NULL, netj.net_period_down, netj.capture_ports, netj.capture_srcs, netj.period_size, netj.dont_htonl_floats );
  233. return 0;
  234. }
  235. packet_buf = netj.rx_buf;
  236. jacknet_packet_header *pkthdr = (jacknet_packet_header *)packet_buf;
  237. packet_bufX = packet_buf + sizeof(jacknet_packet_header) / sizeof(jack_default_audio_sample_t);
  238. netj.reply_port = pkthdr->reply_port;
  239. netj.latency = pkthdr->latency;
  240. // Special handling for latency=0
  241. if( netj.latency == 0 )
  242. netj.resync_threshold = 0;
  243. else
  244. netj.resync_threshold = MIN( 15, pkthdr->latency - 1 );
  245. // check whether, we should handle the transport sync stuff, or leave trnasports untouched.
  246. if (netj.handle_transport_sync) {
  247. #if 1
  248. unsigned int compensated_tranport_pos = (pkthdr->transport_frame + (pkthdr->latency * netj.period_size) + netj.codec_latency);
  249. // read local transport info....
  250. //local_trans_state = jack_transport_query(netj.client, &local_trans_pos);
  251. local_trans_state = fEngineControl->fTransport.Query ( &local_trans_pos );
  252. // Now check if we have to start or stop local transport to sync to remote...
  253. switch (pkthdr->transport_state) {
  254. case JackTransportStarting:
  255. // the master transport is starting... so we set our reply to the sync_callback;
  256. if (local_trans_state == JackTransportStopped) {
  257. fEngineControl->fTransport.SetCommand ( TransportCommandStart );
  258. //jack_transport_start(netj.client);
  259. //last_transport_state = JackTransportStopped;
  260. netj.sync_state = 0;
  261. jack_info("locally stopped... starting...");
  262. }
  263. if (local_trans_pos.frame != compensated_tranport_pos) {
  264. jack_position_t new_pos = local_trans_pos;
  265. new_pos.frame = compensated_tranport_pos + 2 * netj.period_size;
  266. new_pos.valid = (jack_position_bits_t) 0;
  267. fEngineControl->fTransport.RequestNewPos ( &new_pos );
  268. //jack_transport_locate(netj.client, compensated_tranport_pos);
  269. //last_transport_state = JackTransportRolling;
  270. netj.sync_state = 0;
  271. jack_info("starting locate to %d", compensated_tranport_pos );
  272. }
  273. break;
  274. case JackTransportStopped:
  275. netj.sync_state = 1;
  276. if (local_trans_pos.frame != (pkthdr->transport_frame)) {
  277. jack_position_t new_pos = local_trans_pos;
  278. new_pos.frame = pkthdr->transport_frame;
  279. new_pos.valid = (jack_position_bits_t)0;
  280. fEngineControl->fTransport.RequestNewPos ( &new_pos );
  281. //jack_transport_locate(netj.client, (pkthdr->transport_frame));
  282. jack_info("transport is stopped locate to %d", pkthdr->transport_frame);
  283. }
  284. if (local_trans_state != JackTransportStopped)
  285. //jack_transport_stop(netj.client);
  286. fEngineControl->fTransport.SetCommand ( TransportCommandStop );
  287. break;
  288. case JackTransportRolling:
  289. netj.sync_state = 1;
  290. // if(local_trans_pos.frame != (pkthdr->transport_frame + (pkthdr->latency) * netj.period_size)) {
  291. // jack_transport_locate(netj.client, (pkthdr->transport_frame + (pkthdr->latency + 2) * netj.period_size));
  292. // jack_info("running locate to %d", pkthdr->transport_frame + (pkthdr->latency)*netj.period_size);
  293. // }
  294. if (local_trans_state != JackTransportRolling)
  295. fEngineControl->fTransport.SetState ( JackTransportRolling );
  296. break;
  297. case JackTransportLooping:
  298. break;
  299. }
  300. #endif
  301. }
  302. render_payload_to_jack_ports (netj.bitdepth, packet_bufX, netj.net_period_down, netj.capture_ports, netj.capture_srcs, netj.period_size, netj.dont_htonl_floats );
  303. packet_cache_release_packet(netj.packcache, netj.expected_framecnt );
  304. return 0;
  305. }
  306. int JackNetOneDriver::Write()
  307. {
  308. int syncstate = netj.sync_state | ((fEngineControl->fTransport.GetState() == JackTransportNetStarting) ? 1 : 0 );
  309. uint32_t *packet_buf, *packet_bufX;
  310. int packet_size = get_sample_size(netj.bitdepth) * netj.playback_channels * netj.net_period_up + sizeof(jacknet_packet_header);
  311. jacknet_packet_header *pkthdr;
  312. packet_buf = (uint32_t *) alloca(packet_size);
  313. pkthdr = (jacknet_packet_header *)packet_buf;
  314. if( netj.running_free ) {
  315. return 0;
  316. }
  317. // offset packet_bufX by the packetheader.
  318. packet_bufX = packet_buf + sizeof(jacknet_packet_header) / sizeof(jack_default_audio_sample_t);
  319. pkthdr->sync_state = syncstate;;
  320. pkthdr->latency = netj.time_to_deadline;
  321. //printf( "time to deadline = %d goodness=%d\n", (int)netj.time_to_deadline, netj.deadline_goodness );
  322. pkthdr->framecnt = netj.expected_framecnt;
  323. render_jack_ports_to_payload(netj.bitdepth, netj.playback_ports, netj.playback_srcs, netj.period_size, packet_bufX, netj.net_period_up, netj.dont_htonl_floats );
  324. packet_header_hton(pkthdr);
  325. if (netj.srcaddress_valid) {
  326. unsigned int r;
  327. static const int flag = 0;
  328. if (netj.reply_port)
  329. netj.syncsource_address.sin_port = htons(netj.reply_port);
  330. for( r = 0; r < netj.redundancy; r++ )
  331. netjack_sendto(netj.sockfd, (char *)packet_buf, packet_size,
  332. flag, (struct sockaddr*) & (netj.syncsource_address), sizeof(struct sockaddr_in), netj.mtu);
  333. }
  334. return 0;
  335. }
  336. void
  337. JackNetOneDriver::FreePorts ()
  338. {
  339. JSList *node = netj.capture_ports;
  340. while( node != NULL ) {
  341. JSList *this_node = node;
  342. jack_port_id_t port_index = (jack_port_id_t)(intptr_t) node->data;
  343. node = jack_slist_remove_link( node, this_node );
  344. jack_slist_free_1( this_node );
  345. fEngine->PortUnRegister(fClientControl.fRefNum, port_index);
  346. }
  347. netj.capture_ports = NULL;
  348. node = netj.playback_ports;
  349. while( node != NULL ) {
  350. JSList *this_node = node;
  351. jack_port_id_t port_index = (jack_port_id_t)(intptr_t) node->data;
  352. node = jack_slist_remove_link( node, this_node );
  353. jack_slist_free_1( this_node );
  354. fEngine->PortUnRegister(fClientControl.fRefNum, port_index);
  355. }
  356. netj.playback_ports = NULL;
  357. if( netj.bitdepth == CELT_MODE ) {
  358. #if HAVE_CELT
  359. node = netj.playback_srcs;
  360. while( node != NULL ) {
  361. JSList *this_node = node;
  362. CELTEncoder *enc = (CELTEncoder *) node->data;
  363. node = jack_slist_remove_link( node, this_node );
  364. jack_slist_free_1( this_node );
  365. celt_encoder_destroy( enc );
  366. }
  367. netj.playback_srcs = NULL;
  368. node = netj.capture_srcs;
  369. while( node != NULL ) {
  370. JSList *this_node = node;
  371. CELTDecoder *dec = (CELTDecoder *) node->data;
  372. node = jack_slist_remove_link( node, this_node );
  373. jack_slist_free_1( this_node );
  374. celt_decoder_destroy( dec );
  375. }
  376. netj.capture_srcs = NULL;
  377. #endif
  378. } else {
  379. #if HAVE_SAMPLERATE
  380. node = netj.playback_srcs;
  381. while( node != NULL ) {
  382. JSList *this_node = node;
  383. SRC_STATE *state = (SRC_STATE *) node->data;
  384. node = jack_slist_remove_link( node, this_node );
  385. jack_slist_free_1( this_node );
  386. src_delete( state );
  387. }
  388. netj.playback_srcs = NULL;
  389. node = netj.capture_srcs;
  390. while( node != NULL ) {
  391. JSList *this_node = node;
  392. SRC_STATE *state = (SRC_STATE *) node->data;
  393. node = jack_slist_remove_link( node, this_node );
  394. jack_slist_free_1( this_node );
  395. src_delete( state );
  396. }
  397. netj.capture_srcs = NULL;
  398. #endif
  399. }
  400. }
  401. //Render functions--------------------------------------------------------------------
  402. // render functions for float
  403. void
  404. JackNetOneDriver::render_payload_to_jack_ports_float ( void *packet_payload, jack_nframes_t net_period_down, JSList *capture_ports, JSList *capture_srcs, jack_nframes_t nframes, int dont_htonl_floats)
  405. {
  406. uint32_t chn = 0;
  407. JSList *node = capture_ports;
  408. #if HAVE_SAMPLERATE
  409. JSList *src_node = capture_srcs;
  410. #endif
  411. uint32_t *packet_bufX = (uint32_t *)packet_payload;
  412. if( !packet_payload )
  413. return;
  414. while (node != NULL) {
  415. unsigned int i;
  416. int_float_t val;
  417. #if HAVE_SAMPLERATE
  418. SRC_DATA src;
  419. #endif
  420. jack_port_id_t port_index = (jack_port_id_t)(intptr_t) node->data;
  421. JackPort *port = fGraphManager->GetPort( port_index );
  422. jack_default_audio_sample_t* buf =
  423. (jack_default_audio_sample_t*)fGraphManager->GetBuffer(port_index, fEngineControl->fBufferSize);
  424. const char *porttype = port->GetType();
  425. if (strncmp (porttype, JACK_DEFAULT_AUDIO_TYPE, jack_port_type_size()) == 0) {
  426. #if HAVE_SAMPLERATE
  427. // audio port, resample if necessary
  428. if (net_period_down != nframes) {
  429. SRC_STATE *src_state = (SRC_STATE *)src_node->data;
  430. for (i = 0; i < net_period_down; i++) {
  431. packet_bufX[i] = ntohl (packet_bufX[i]);
  432. }
  433. src.data_in = (float *) packet_bufX;
  434. src.input_frames = net_period_down;
  435. src.data_out = buf;
  436. src.output_frames = nframes;
  437. src.src_ratio = (float) nframes / (float) net_period_down;
  438. src.end_of_input = 0;
  439. src_set_ratio (src_state, src.src_ratio);
  440. src_process (src_state, &src);
  441. src_node = jack_slist_next (src_node);
  442. } else
  443. #endif
  444. {
  445. if( dont_htonl_floats ) {
  446. memcpy( buf, packet_bufX, net_period_down * sizeof(jack_default_audio_sample_t));
  447. } else {
  448. for (i = 0; i < net_period_down; i++) {
  449. val.i = packet_bufX[i];
  450. val.i = ntohl (val.i);
  451. buf[i] = val.f;
  452. }
  453. }
  454. }
  455. } else if (strncmp (porttype, JACK_DEFAULT_MIDI_TYPE, jack_port_type_size()) == 0) {
  456. // midi port, decode midi events
  457. // convert the data buffer to a standard format (uint32_t based)
  458. unsigned int buffer_size_uint32 = net_period_down;
  459. uint32_t * buffer_uint32 = (uint32_t*)packet_bufX;
  460. decode_midi_buffer (buffer_uint32, buffer_size_uint32, buf);
  461. }
  462. packet_bufX = (packet_bufX + net_period_down);
  463. node = jack_slist_next (node);
  464. chn++;
  465. }
  466. }
  467. void
  468. JackNetOneDriver::render_jack_ports_to_payload_float (JSList *playback_ports, JSList *playback_srcs, jack_nframes_t nframes, void *packet_payload, jack_nframes_t net_period_up, int dont_htonl_floats )
  469. {
  470. uint32_t chn = 0;
  471. JSList *node = playback_ports;
  472. #if HAVE_SAMPLERATE
  473. JSList *src_node = playback_srcs;
  474. #endif
  475. uint32_t *packet_bufX = (uint32_t *) packet_payload;
  476. while (node != NULL) {
  477. #if HAVE_SAMPLERATE
  478. SRC_DATA src;
  479. #endif
  480. unsigned int i;
  481. int_float_t val;
  482. jack_port_id_t port_index = (jack_port_id_t)(intptr_t) node->data;
  483. JackPort *port = fGraphManager->GetPort( port_index );
  484. jack_default_audio_sample_t* buf =
  485. (jack_default_audio_sample_t*)fGraphManager->GetBuffer(port_index, fEngineControl->fBufferSize);
  486. const char *porttype = port->GetType();
  487. if (strncmp (porttype, JACK_DEFAULT_AUDIO_TYPE, jack_port_type_size()) == 0) {
  488. // audio port, resample if necessary
  489. #if HAVE_SAMPLERATE
  490. if (net_period_up != nframes) {
  491. SRC_STATE *src_state = (SRC_STATE *) src_node->data;
  492. src.data_in = buf;
  493. src.input_frames = nframes;
  494. src.data_out = (float *) packet_bufX;
  495. src.output_frames = net_period_up;
  496. src.src_ratio = (float) net_period_up / (float) nframes;
  497. src.end_of_input = 0;
  498. src_set_ratio (src_state, src.src_ratio);
  499. src_process (src_state, &src);
  500. for (i = 0; i < net_period_up; i++) {
  501. packet_bufX[i] = htonl (packet_bufX[i]);
  502. }
  503. src_node = jack_slist_next (src_node);
  504. } else
  505. #endif
  506. {
  507. if( dont_htonl_floats ) {
  508. memcpy( packet_bufX, buf, net_period_up * sizeof(jack_default_audio_sample_t) );
  509. } else {
  510. for (i = 0; i < net_period_up; i++) {
  511. val.f = buf[i];
  512. val.i = htonl (val.i);
  513. packet_bufX[i] = val.i;
  514. }
  515. }
  516. }
  517. } else if (strncmp(porttype, JACK_DEFAULT_MIDI_TYPE, jack_port_type_size()) == 0) {
  518. // encode midi events from port to packet
  519. // convert the data buffer to a standard format (uint32_t based)
  520. unsigned int buffer_size_uint32 = net_period_up;
  521. uint32_t * buffer_uint32 = (uint32_t*) packet_bufX;
  522. encode_midi_buffer (buffer_uint32, buffer_size_uint32, buf);
  523. }
  524. packet_bufX = (packet_bufX + net_period_up);
  525. node = jack_slist_next (node);
  526. chn++;
  527. }
  528. }
  529. #if HAVE_CELT
  530. // render functions for celt.
  531. void
  532. JackNetOneDriver::render_payload_to_jack_ports_celt (void *packet_payload, jack_nframes_t net_period_down, JSList *capture_ports, JSList *capture_srcs, jack_nframes_t nframes)
  533. {
  534. uint32_t chn = 0;
  535. JSList *node = capture_ports;
  536. JSList *src_node = capture_srcs;
  537. unsigned char *packet_bufX = (unsigned char *)packet_payload;
  538. while (node != NULL) {
  539. jack_port_id_t port_index = (jack_port_id_t) (intptr_t)node->data;
  540. JackPort *port = fGraphManager->GetPort( port_index );
  541. jack_default_audio_sample_t* buf =
  542. (jack_default_audio_sample_t*)fGraphManager->GetBuffer(port_index, fEngineControl->fBufferSize);
  543. const char *portname = port->GetType();
  544. if (strncmp(portname, JACK_DEFAULT_AUDIO_TYPE, jack_port_type_size()) == 0) {
  545. // audio port, decode celt data.
  546. CELTDecoder *decoder = (CELTDecoder *)src_node->data;
  547. #if HAVE_CELT_API_0_8 || HAVE_CELT_API_0_11
  548. if( !packet_payload )
  549. celt_decode_float( decoder, NULL, net_period_down, buf, nframes );
  550. else
  551. celt_decode_float( decoder, packet_bufX, net_period_down, buf, nframes );
  552. #else
  553. if( !packet_payload )
  554. celt_decode_float( decoder, NULL, net_period_down, buf );
  555. else
  556. celt_decode_float( decoder, packet_bufX, net_period_down, buf );
  557. #endif
  558. src_node = jack_slist_next (src_node);
  559. } else if (strncmp(portname, JACK_DEFAULT_MIDI_TYPE, jack_port_type_size()) == 0) {
  560. // midi port, decode midi events
  561. // convert the data buffer to a standard format (uint32_t based)
  562. unsigned int buffer_size_uint32 = net_period_down / 2;
  563. uint32_t * buffer_uint32 = (uint32_t*) packet_bufX;
  564. if( packet_payload )
  565. decode_midi_buffer (buffer_uint32, buffer_size_uint32, buf);
  566. }
  567. packet_bufX = (packet_bufX + net_period_down);
  568. node = jack_slist_next (node);
  569. chn++;
  570. }
  571. }
  572. void
  573. JackNetOneDriver::render_jack_ports_to_payload_celt (JSList *playback_ports, JSList *playback_srcs, jack_nframes_t nframes, void *packet_payload, jack_nframes_t net_period_up)
  574. {
  575. uint32_t chn = 0;
  576. JSList *node = playback_ports;
  577. JSList *src_node = playback_srcs;
  578. unsigned char *packet_bufX = (unsigned char *)packet_payload;
  579. while (node != NULL) {
  580. jack_port_id_t port_index = (jack_port_id_t) (intptr_t) node->data;
  581. JackPort *port = fGraphManager->GetPort( port_index );
  582. jack_default_audio_sample_t* buf =
  583. (jack_default_audio_sample_t*)fGraphManager->GetBuffer(port_index, fEngineControl->fBufferSize);
  584. const char *portname = port->GetType();
  585. if (strncmp (portname, JACK_DEFAULT_AUDIO_TYPE, jack_port_type_size()) == 0) {
  586. // audio port, encode celt data.
  587. int encoded_bytes;
  588. jack_default_audio_sample_t *floatbuf = (jack_default_audio_sample_t *)alloca (sizeof(jack_default_audio_sample_t) * nframes );
  589. memcpy( floatbuf, buf, nframes * sizeof(jack_default_audio_sample_t) );
  590. CELTEncoder *encoder = (CELTEncoder *)src_node->data;
  591. #if HAVE_CELT_API_0_8 || HAVE_CELT_API_0_11
  592. encoded_bytes = celt_encode_float( encoder, floatbuf, nframes, packet_bufX, net_period_up );
  593. #else
  594. encoded_bytes = celt_encode_float( encoder, floatbuf, NULL, packet_bufX, net_period_up );
  595. #endif
  596. if( encoded_bytes != (int)net_period_up )
  597. jack_error( "something in celt changed. netjack needs to be changed to handle this." );
  598. src_node = jack_slist_next( src_node );
  599. } else if (strncmp(portname, JACK_DEFAULT_MIDI_TYPE, jack_port_type_size()) == 0) {
  600. // encode midi events from port to packet
  601. // convert the data buffer to a standard format (uint32_t based)
  602. unsigned int buffer_size_uint32 = net_period_up / 2;
  603. uint32_t * buffer_uint32 = (uint32_t*) packet_bufX;
  604. encode_midi_buffer (buffer_uint32, buffer_size_uint32, buf);
  605. }
  606. packet_bufX = (packet_bufX + net_period_up);
  607. node = jack_slist_next (node);
  608. chn++;
  609. }
  610. }
  611. #endif
  612. /* Wrapper functions with bitdepth argument... */
  613. void
  614. JackNetOneDriver::render_payload_to_jack_ports (int bitdepth, void *packet_payload, jack_nframes_t net_period_down, JSList *capture_ports, JSList *capture_srcs, jack_nframes_t nframes, int dont_htonl_floats)
  615. {
  616. #if HAVE_CELT
  617. if (bitdepth == CELT_MODE)
  618. render_payload_to_jack_ports_celt (packet_payload, net_period_down, capture_ports, capture_srcs, nframes);
  619. else
  620. #endif
  621. render_payload_to_jack_ports_float (packet_payload, net_period_down, capture_ports, capture_srcs, nframes, dont_htonl_floats);
  622. }
  623. void
  624. JackNetOneDriver::render_jack_ports_to_payload (int bitdepth, JSList *playback_ports, JSList *playback_srcs, jack_nframes_t nframes, void *packet_payload, jack_nframes_t net_period_up, int dont_htonl_floats)
  625. {
  626. #if HAVE_CELT
  627. if (bitdepth == CELT_MODE)
  628. render_jack_ports_to_payload_celt (playback_ports, playback_srcs, nframes, packet_payload, net_period_up);
  629. else
  630. #endif
  631. render_jack_ports_to_payload_float (playback_ports, playback_srcs, nframes, packet_payload, net_period_up, dont_htonl_floats);
  632. }
  633. //driver loader-----------------------------------------------------------------------
  634. #ifdef __cplusplus
  635. extern "C"
  636. {
  637. #endif
  638. SERVER_EXPORT jack_driver_desc_t* driver_get_descriptor ()
  639. {
  640. jack_driver_desc_t * desc;
  641. jack_driver_desc_filler_t filler;
  642. jack_driver_param_value_t value;
  643. desc = jack_driver_descriptor_construct("netone", JackDriverMaster, "netjack one slave backend component", &filler);
  644. value.ui = 2U;
  645. jack_driver_descriptor_add_parameter(desc, &filler, "audio-ins", 'i', JackDriverParamUInt, &value, NULL, "Number of capture channels (defaults to 2)", NULL);
  646. jack_driver_descriptor_add_parameter(desc, &filler, "audio-outs", 'o', JackDriverParamUInt, &value, NULL, "Number of playback channels (defaults to 2)", NULL);
  647. value.ui = 1U;
  648. jack_driver_descriptor_add_parameter(desc, &filler, "midi-ins", 'I', JackDriverParamUInt, &value, NULL, "Number of midi capture channels (defaults to 1)", NULL);
  649. jack_driver_descriptor_add_parameter(desc, &filler, "midi-outs", 'O', JackDriverParamUInt, &value, NULL, "Number of midi playback channels (defaults to 1)", NULL);
  650. value.ui = 48000U;
  651. jack_driver_descriptor_add_parameter(desc, &filler, "rate", 'r', JackDriverParamUInt, &value, NULL, "Sample rate", NULL);
  652. value.ui = 1024U;
  653. jack_driver_descriptor_add_parameter(desc, &filler, "period", 'p', JackDriverParamUInt, &value, NULL, "Frames per period", NULL);
  654. value.ui = 5U;
  655. jack_driver_descriptor_add_parameter(desc, &filler, "num-periods", 'n', JackDriverParamUInt, &value, NULL, "Network latency setting in no. of periods", NULL);
  656. value.ui = 3000U;
  657. jack_driver_descriptor_add_parameter(desc, &filler, "listen-port", 'l', JackDriverParamUInt, &value, NULL, "The socket port we are listening on for sync packets", NULL);
  658. value.ui = 1U;
  659. jack_driver_descriptor_add_parameter(desc, &filler, "factor", 'f', JackDriverParamUInt, &value, NULL, "Factor for sample rate reduction", NULL);
  660. value.ui = 0U;
  661. jack_driver_descriptor_add_parameter(desc, &filler, "upstream-factor", 'u', JackDriverParamUInt, &value, NULL, "Factor for sample rate reduction on the upstream", NULL);
  662. #if HAVE_CELT
  663. value.ui = 0U;
  664. jack_driver_descriptor_add_parameter(desc, &filler, "celt", 'c', JackDriverParamUInt, &value, NULL, "Set CELT encoding and number of kbits per channel", NULL);
  665. #endif
  666. value.ui = 0U;
  667. jack_driver_descriptor_add_parameter(desc, &filler, "bit-depth", 'b', JackDriverParamUInt, &value, NULL, "Sample bit-depth (0 for float, 8 for 8bit and 16 for 16bit)", NULL);
  668. value.i = true;
  669. jack_driver_descriptor_add_parameter(desc, &filler, "transport-sync", 't', JackDriverParamBool, &value, NULL, "Whether to slave the transport to the master transport", NULL);
  670. value.ui = true;
  671. jack_driver_descriptor_add_parameter(desc, &filler, "autoconf", 'a', JackDriverParamBool, &value, NULL, "Whether to use Autoconfig, or just start", NULL);
  672. value.ui = 1U;
  673. jack_driver_descriptor_add_parameter(desc, &filler, "redundancy", 'R', JackDriverParamUInt, &value, NULL, "Send packets N times", NULL);
  674. value.ui = false;
  675. jack_driver_descriptor_add_parameter(desc, &filler, "native-endian", 'e', JackDriverParamBool, &value, NULL, "Dont convert samples to network byte order", NULL);
  676. value.i = 0;
  677. jack_driver_descriptor_add_parameter(desc, &filler, "jitterval", 'J', JackDriverParamInt, &value, NULL, "Attempted jitterbuffer microseconds on master", NULL);
  678. value.i = false;
  679. jack_driver_descriptor_add_parameter(desc, &filler, "always-deadline", 'D', JackDriverParamBool, &value, NULL, "Always use deadline", NULL);
  680. return desc;
  681. }
  682. SERVER_EXPORT Jack::JackDriverClientInterface* driver_initialize ( Jack::JackLockedEngine* engine, Jack::JackSynchro* table, const JSList* params )
  683. {
  684. jack_nframes_t sample_rate = 48000;
  685. jack_nframes_t resample_factor = 1;
  686. jack_nframes_t period_size = 1024;
  687. unsigned int capture_ports = 2;
  688. unsigned int playback_ports = 2;
  689. unsigned int capture_ports_midi = 1;
  690. unsigned int playback_ports_midi = 1;
  691. unsigned int listen_port = 3000;
  692. unsigned int bitdepth = 0;
  693. unsigned int handle_transport_sync = 1;
  694. unsigned int use_autoconfig = 1;
  695. unsigned int latency = 5;
  696. unsigned int redundancy = 1;
  697. unsigned int mtu = 1400;
  698. #if HAVE_SAMPLERATE
  699. unsigned int resample_factor_up = 1;
  700. #endif
  701. int dont_htonl_floats = 0;
  702. int always_deadline = 0;
  703. int jitter_val = 0;
  704. const JSList * node;
  705. const jack_driver_param_t * param;
  706. for ( node = params; node; node = jack_slist_next ( node ) ) {
  707. param = ( const jack_driver_param_t* ) node->data;
  708. switch ( param->character ) {
  709. case 'i':
  710. capture_ports = param->value.ui;
  711. break;
  712. case 'o':
  713. playback_ports = param->value.ui;
  714. break;
  715. case 'I':
  716. capture_ports_midi = param->value.ui;
  717. break;
  718. case 'O':
  719. playback_ports_midi = param->value.ui;
  720. break;
  721. case 'r':
  722. sample_rate = param->value.ui;
  723. break;
  724. case 'p':
  725. period_size = param->value.ui;
  726. break;
  727. case 'l':
  728. listen_port = param->value.ui;
  729. break;
  730. case 'f':
  731. #if HAVE_SAMPLERATE
  732. resample_factor = param->value.ui;
  733. #else
  734. jack_error( "not built with libsamplerate support" );
  735. return NULL;
  736. #endif
  737. break;
  738. case 'u':
  739. #if HAVE_SAMPLERATE
  740. resample_factor_up = param->value.ui;
  741. #else
  742. jack_error( "not built with libsamplerate support" );
  743. return NULL;
  744. #endif
  745. break;
  746. case 'b':
  747. bitdepth = param->value.ui;
  748. break;
  749. case 'c':
  750. #if HAVE_CELT
  751. bitdepth = CELT_MODE;
  752. resample_factor = param->value.ui;
  753. #else
  754. jack_error( "not built with celt support" );
  755. return NULL;
  756. #endif
  757. break;
  758. case 't':
  759. handle_transport_sync = param->value.ui;
  760. break;
  761. case 'a':
  762. use_autoconfig = param->value.ui;
  763. break;
  764. case 'n':
  765. latency = param->value.ui;
  766. break;
  767. case 'R':
  768. redundancy = param->value.ui;
  769. break;
  770. case 'H':
  771. dont_htonl_floats = param->value.ui;
  772. break;
  773. case 'J':
  774. jitter_val = param->value.i;
  775. break;
  776. case 'D':
  777. always_deadline = param->value.ui;
  778. break;
  779. }
  780. }
  781. try {
  782. Jack::JackDriverClientInterface* driver = new Jack::JackWaitThreadedDriver (
  783. new Jack::JackNetOneDriver ( "system", "net_pcm", engine, table, listen_port, mtu,
  784. capture_ports_midi, playback_ports_midi, capture_ports, playback_ports,
  785. sample_rate, period_size, resample_factor,
  786. "net_pcm", handle_transport_sync, bitdepth, use_autoconfig, latency, redundancy,
  787. dont_htonl_floats, always_deadline, jitter_val ) );
  788. if ( driver->Open ( period_size, sample_rate, 1, 1, capture_ports, playback_ports,
  789. 0, "from_master_", "to_master_", 0, 0 ) == 0 ) {
  790. return driver;
  791. } else {
  792. delete driver;
  793. return NULL;
  794. }
  795. } catch ( ... ) {
  796. return NULL;
  797. }
  798. }
  799. #ifdef __cplusplus
  800. }
  801. #endif
  802. }