3 Copyright (C) 1999-2002 Paul Davis
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
30 #include <midi++/mmc.h>
31 #include <midi++/port.h>
32 #include <midi++/manager.h>
33 #include <pbd/error.h>
34 #include <glibmm/thread.h>
35 #include <pbd/pthread_utils.h>
37 #include <ardour/configuration.h>
38 #include <ardour/audioengine.h>
39 #include <ardour/session.h>
40 #include <ardour/audio_track.h>
41 #include <ardour/diskstream.h>
42 #include <ardour/slave.h>
43 #include <ardour/cycles.h>
44 #include <ardour/smpte.h>
49 using namespace ARDOUR;
50 //using namespace sigc;
53 MachineControl::CommandSignature MMC_CommandSignature;
54 MachineControl::ResponseSignature MMC_ResponseSignature;
56 MultiAllocSingleReleasePool Session::MIDIRequest::pool ("midi", sizeof (Session::MIDIRequest), 1024);
59 Session::use_config_midi_ports ()
63 if (default_mmc_port) {
64 set_mmc_port (default_mmc_port->name());
69 if (default_mtc_port) {
70 set_mtc_port (default_mtc_port->name());
75 if (default_midi_port) {
76 set_midi_port (default_midi_port->name());
85 /***********************************************************************
87 **********************************************************************/
90 Session::set_mmc_control (bool yn)
93 if (mmc_control == yn) {
101 ControlChanged (MMCControl); /* EMIT SIGNAL */
105 Session::set_midi_control (bool yn)
108 if (midi_control == yn) {
117 Glib::RWLock::ReaderLock guard (route_lock);
118 for (RouteList::iterator i = routes.begin(); i != routes.end(); ++i) {
119 (*i)->reset_midi_control (_midi_port, midi_control);
123 ControlChanged (MidiControl); /* EMIT SIGNAL */
127 Session::set_send_mtc (bool yn)
129 /* set the persistent option value regardless */
131 send_midi_timecode = yn;
134 /* only set the internal flag if we have
138 if (_mtc_port == 0 || send_mtc == yn) {
143 ControlChanged (SendMTC); /* EMIT SIGNAL */
147 Session::set_send_mmc (bool yn)
149 if (_mmc_port == 0) {
153 if (send_midi_machine_control == yn) {
157 /* only set the internal flag if we have
165 /* set the persistent option value regardless */
167 send_midi_machine_control = yn;
170 ControlChanged (SendMMC); /* EMIT SIGNAL */
174 Session::set_midi_feedback (bool yn)
179 Session::get_midi_feedback () const
185 Session::get_send_mtc () const
191 Session::get_send_mmc () const
197 Session::set_mtc_port (string port_tag)
201 if (port_tag.length() == 0) {
203 if (_slave && ((ms = dynamic_cast<MTC_Slave*> (_slave)) != 0)) {
204 error << _("Ardour is slaved to MTC - port cannot be reset") << endmsg;
208 if (_mtc_port == 0) {
218 if ((port = MIDI::Manager::instance()->port (port_tag)) == 0) {
219 error << string_compose (_("unknown port %1 requested for MTC"), port_tag) << endl;
225 if (_slave && ((ms = dynamic_cast<MTC_Slave*> (_slave)) != 0)) {
229 Config->set_mtc_port_name (port_tag);
232 MTC_PortChanged(); /* EMIT SIGNAL */
233 change_midi_ports ();
239 Session::set_mmc_port (string port_tag)
241 if (port_tag.length() == 0) {
242 if (_mmc_port == 0) {
251 if ((port = MIDI::Manager::instance()->port (port_tag)) == 0) {
261 mmc = new MIDI::MachineControl (*_mmc_port, 1.0,
262 MMC_CommandSignature,
263 MMC_ResponseSignature);
267 (mem_fun (*this, &Session::mmc_deferred_play));
268 mmc->DeferredPlay.connect
269 (mem_fun (*this, &Session::mmc_deferred_play));
271 (mem_fun (*this, &Session::mmc_stop));
272 mmc->FastForward.connect
273 (mem_fun (*this, &Session::mmc_fast_forward));
275 (mem_fun (*this, &Session::mmc_rewind));
277 (mem_fun (*this, &Session::mmc_pause));
278 mmc->RecordPause.connect
279 (mem_fun (*this, &Session::mmc_record_pause));
280 mmc->RecordStrobe.connect
281 (mem_fun (*this, &Session::mmc_record_strobe));
282 mmc->RecordExit.connect
283 (mem_fun (*this, &Session::mmc_record_exit));
285 (mem_fun (*this, &Session::mmc_locate));
287 (mem_fun (*this, &Session::mmc_step));
289 (mem_fun (*this, &Session::mmc_shuttle));
290 mmc->TrackRecordStatusChange.connect
291 (mem_fun (*this, &Session::mmc_record_enable));
293 /* also handle MIDI SPP because its so common */
295 _mmc_port->input()->start.connect (mem_fun (*this, &Session::spp_start));
296 _mmc_port->input()->contineu.connect (mem_fun (*this, &Session::spp_continue));
297 _mmc_port->input()->stop.connect (mem_fun (*this, &Session::spp_stop));
299 Config->set_mmc_port_name (port_tag);
302 MMC_PortChanged(); /* EMIT SIGNAL */
303 change_midi_ports ();
309 Session::set_midi_port (string port_tag)
311 if (port_tag.length() == 0) {
312 if (_midi_port == 0) {
321 if ((port = MIDI::Manager::instance()->port (port_tag)) == 0) {
327 /* XXX need something to forward this to control protocols ? or just
331 Config->set_midi_port_name (port_tag);
334 MIDI_PortChanged(); /* EMIT SIGNAL */
335 change_midi_ports ();
341 Session::set_trace_midi_input (bool yn, MIDI::Port* port)
343 MIDI::Parser* input_parser;
346 if ((input_parser = port->input()) != 0) {
347 input_parser->trace (yn, &cout, "input: ");
352 if ((input_parser = _mmc_port->input()) != 0) {
353 input_parser->trace (yn, &cout, "input: ");
357 if (_mtc_port && _mtc_port != _mmc_port) {
358 if ((input_parser = _mtc_port->input()) != 0) {
359 input_parser->trace (yn, &cout, "input: ");
363 if (_midi_port && _midi_port != _mmc_port && _midi_port != _mtc_port ) {
364 if ((input_parser = _midi_port->input()) != 0) {
365 input_parser->trace (yn, &cout, "input: ");
370 Config->set_trace_midi_input (yn);
374 Session::set_trace_midi_output (bool yn, MIDI::Port* port)
376 MIDI::Parser* output_parser;
379 if ((output_parser = port->output()) != 0) {
380 output_parser->trace (yn, &cout, "output: ");
384 if ((output_parser = _mmc_port->output()) != 0) {
385 output_parser->trace (yn, &cout, "output: ");
389 if (_mtc_port && _mtc_port != _mmc_port) {
390 if ((output_parser = _mtc_port->output()) != 0) {
391 output_parser->trace (yn, &cout, "output: ");
395 if (_midi_port && _midi_port != _mmc_port && _midi_port != _mtc_port ) {
396 if ((output_parser = _midi_port->output()) != 0) {
397 output_parser->trace (yn, &cout, "output: ");
403 Config->set_trace_midi_output (yn);
407 Session::get_trace_midi_input(MIDI::Port *port)
409 MIDI::Parser* input_parser;
411 if ((input_parser = port->input()) != 0) {
412 return input_parser->tracing();
417 if ((input_parser = _mmc_port->input()) != 0) {
418 return input_parser->tracing();
423 if ((input_parser = _mtc_port->input()) != 0) {
424 return input_parser->tracing();
429 if ((input_parser = _midi_port->input()) != 0) {
430 return input_parser->tracing();
439 Session::get_trace_midi_output(MIDI::Port *port)
441 MIDI::Parser* output_parser;
443 if ((output_parser = port->output()) != 0) {
444 return output_parser->tracing();
449 if ((output_parser = _mmc_port->output()) != 0) {
450 return output_parser->tracing();
455 if ((output_parser = _mtc_port->output()) != 0) {
456 return output_parser->tracing();
461 if ((output_parser = _midi_port->output()) != 0) {
462 return output_parser->tracing();
472 Session::setup_midi_control ()
474 outbound_mtc_smpte_frame = 0;
475 next_quarter_frame_to_send = 0;
477 /* setup the MMC buffer */
479 mmc_buffer[0] = 0xf0; // SysEx
480 mmc_buffer[1] = 0x7f; // Real Time SysEx ID for MMC
481 mmc_buffer[2] = 0x7f; // "broadcast" device ID
482 mmc_buffer[3] = 0x6; // MCC
484 /* Set up the qtr frame message */
495 if (_mmc_port != 0) {
497 send_mmc = send_midi_machine_control;
505 if (_mtc_port != 0) {
507 send_mtc = send_midi_timecode;
517 Session::midi_read (MIDI::Port* port)
521 /* reading from the MIDI port activates the Parser
522 that in turn generates signals that we care
523 about. the port is already set to NONBLOCK so that
524 can read freely here.
529 // cerr << "+++ READ ON " << port->name() << endl;
531 int nread = port->read (buf, sizeof (buf));
533 // cerr << "-- READ (" << nread << " ON " << port->name() << endl;
536 if ((size_t) nread < sizeof (buf)) {
541 } else if (nread == 0) {
543 } else if (errno == EAGAIN) {
546 fatal << string_compose(_("Error reading from MIDI port %1"), port->name()) << endmsg;
556 Session::spp_start (Parser& ignored)
558 if (mmc_control && (_slave_type != MTC)) {
559 request_transport_speed (1.0);
564 Session::spp_continue (Parser& ignored)
570 Session::spp_stop (Parser& ignored)
578 Session::mmc_deferred_play (MIDI::MachineControl &mmc)
580 if (mmc_control && (_slave_type != MTC)) {
581 request_transport_speed (1.0);
586 Session::mmc_record_pause (MIDI::MachineControl &mmc)
589 maybe_enable_record();
594 Session::mmc_record_strobe (MIDI::MachineControl &mmc)
599 /* record strobe does an implicit "Play" command */
601 if (_transport_speed != 1.0) {
603 /* start_transport() will move from Enabled->Recording, so we
604 don't need to do anything here except enable recording.
605 its not the same as maybe_enable_record() though, because
606 that *can* switch to Recording, which we do not want.
609 save_state ("", true);
610 g_atomic_int_set (&_record_status, Enabled);
611 RecordStateChanged (); /* EMIT SIGNAL */
613 request_transport_speed (1.0);
622 Session::mmc_record_exit (MIDI::MachineControl &mmc)
625 disable_record (false);
630 Session::mmc_stop (MIDI::MachineControl &mmc)
638 Session::mmc_pause (MIDI::MachineControl &mmc)
642 /* We support RECORD_PAUSE, so the spec says that
643 we must interpret PAUSE like RECORD_PAUSE if
647 if (actively_recording()) {
648 maybe_enable_record ();
655 static bool step_queued = false;
659 Session::mmc_step (MIDI::MachineControl &mmc, int steps)
666 struct timeval diff = { 0, 0 };
668 gettimeofday (&now, 0);
670 timersub (&now, &last_mmc_step, &diff);
672 gettimeofday (&now, 0);
673 timersub (&now, &last_mmc_step, &diff);
675 if (last_mmc_step.tv_sec != 0 && (diff.tv_usec + (diff.tv_sec * 1000000)) < _engine.usecs_per_cycle()) {
679 double diff_secs = diff.tv_sec + (diff.tv_usec / 1000000.0);
680 double cur_speed = (((steps * 0.5) * smpte_frames_per_second) / diff_secs) / smpte_frames_per_second;
682 if (_transport_speed == 0 || cur_speed * _transport_speed < 0) {
683 /* change direction */
684 step_speed = cur_speed;
686 step_speed = (0.6 * step_speed) + (0.4 * cur_speed);
692 cerr << "delta = " << diff_secs
693 << " ct = " << _transport_speed
694 << " steps = " << steps
695 << " new speed = " << cur_speed
696 << " speed = " << step_speed
700 request_transport_speed (step_speed);
704 midi_timeouts.push_back (mem_fun (*this, &Session::mmc_step_timeout));
710 Session::mmc_rewind (MIDI::MachineControl &mmc)
713 request_transport_speed(-8.0f);
718 Session::mmc_fast_forward (MIDI::MachineControl &mmc)
721 request_transport_speed(8.0f);
726 Session::mmc_locate (MIDI::MachineControl &mmc, const MIDI::byte* mmc_tc)
732 jack_nframes_t target_frame;
735 smpte.hours = mmc_tc[0] & 0xf;
736 smpte.minutes = mmc_tc[1];
737 smpte.seconds = mmc_tc[2];
738 smpte.frames = mmc_tc[3];
740 // Also takes smpte offset into account:
741 smpte_to_sample( smpte, target_frame, true /* use_offset */, false /* use_subframes */ );
743 if (target_frame > max_frames) {
744 target_frame = max_frames;
747 /* Some (all?) MTC/MMC devices do not send a full MTC frame
748 at the end of a locate, instead sending only an MMC
749 locate command. This causes the current position
750 of an MTC slave to become out of date. Catch this.
753 MTC_Slave* mtcs = dynamic_cast<MTC_Slave*> (_slave);
756 // cerr << "Locate *with* MTC slave\n";
757 mtcs->handle_locate (mmc_tc);
759 // cerr << "Locate without MTC slave\n";
760 request_locate (target_frame, false);
765 Session::mmc_shuttle (MIDI::MachineControl &mmc, float speed, bool forw)
767 cerr << "MMC shuttle, speed = " << speed << endl;
773 if (shuttle_speed_threshold >= 0 && speed > shuttle_speed_threshold) {
774 speed *= shuttle_speed_factor;
777 cerr << "requested MMC control speed = " << speed << endl;
780 request_transport_speed (speed);
782 request_transport_speed (-speed);
787 Session::mmc_record_enable (MIDI::MachineControl &mmc, size_t trk, bool enabled)
791 RouteList::iterator i;
792 Glib::RWLock::ReaderLock guard (route_lock);
794 for (i = routes.begin(); i != routes.end(); ++i) {
797 if ((at = dynamic_cast<AudioTrack*>(*i)) != 0) {
798 if (trk == at->remote_control_id()) {
799 at->set_record_enable (enabled, &mmc);
809 Session::change_midi_ports ()
812 MIDIRequest* request = new MIDIRequest;
814 request->type = MIDIRequest::PortChange;
815 midi_requests.write (&request, 1);
820 /** Send MTC Full Frame message (complete SMPTE time) for the start of this cycle.
821 * This resets the MTC code, the next quarter frame message that is sent will be
822 * the first one with the beginning of this cycle as the new start point.
824 * Audio thread only, realtime safe. MIDI::Manager::cycle_start must
825 * have been called with the appropriate nframes parameter this cycle.
828 Session::send_full_time_code(jack_nframes_t nframes)
830 /* This function could easily send at a given frame offset, but would
831 * that be useful? Does ardour do sub-block accurate locating? [DR] */
836 _send_smpte_update = false;
838 if (_mtc_port == 0 || !send_mtc) {
842 // Get smpte time for this transport frame
843 sample_to_smpte(_transport_frame, smpte, true /* use_offset */, false /* no subframes */);
845 transmitting_smpte_time = smpte;
846 outbound_mtc_smpte_frame = _transport_frame;
848 // I don't understand this bit yet.. [DR]
849 if (((mtc_smpte_bits >> 5) != MIDI::MTC_25_FPS) && (transmitting_smpte_time.frames % 2)) {
850 // start MTC quarter frame transmission on an even frame
851 SMPTE::increment( transmitting_smpte_time );
852 outbound_mtc_smpte_frame += (jack_nframes_t) _frames_per_smpte_frame;
855 // Compensate for audio latency
856 outbound_mtc_smpte_frame += _worst_output_latency;
858 next_quarter_frame_to_send = 0;
860 // Sync slave to the same SMPTE time as we are on
868 msg[5] = mtc_smpte_bits | smpte.hours;
869 msg[6] = smpte.minutes;
870 msg[7] = smpte.seconds;
871 msg[8] = smpte.frames;
873 cerr << "MTC: Sending full time code at " << outbound_mtc_smpte_frame << endl;
875 // Send message at offset 0, sent time is for the start of this cycle
876 if (!_mtc_port->midimsg (msg, sizeof (msg), 0)) {
877 error << _("Session: could not send full MIDI time code") << endmsg;
885 /** Sends MTC (quarter-frame) messages for this cycle.
886 * Must be called exactly once per cycle from the audio thread. Realtime safe.
887 * This function assumes the state of full SMPTE is sane, eg. the slave is
888 * expecting quarter frame messages and has the right frame of reference (any
889 * full MTC SMPTE time messages that needed to be sent should have been sent
890 * earlier already this cycle by send_full_time_code)
893 Session::send_midi_time_code_for_cycle(jack_nframes_t nframes)
895 assert (next_quarter_frame_to_send >= 0);
896 assert (next_quarter_frame_to_send <= 7);
898 if (next_quarter_frame_to_send < 0)
900 printf("Negative????\n");
903 if (_mtc_port == 0 || !send_mtc || transmitting_smpte_time.negative
904 /*|| (next_quarter_frame_to_send < 0)*/ ) {
905 printf("(MTC) Not sending MTC\n");
909 /* Duration of one quarter frame */
910 jack_nframes_t quarter_frame_duration = ((long) _frames_per_smpte_frame) >> 2;
912 //cerr << "(MTC) TR: " << _transport_frame << " - SF: " << outbound_mtc_smpte_frame
913 //<< " - NQ: " << next_quarter_frame_to_send << " - FD" << quarter_frame_duration << endl;
915 // FIXME: this should always be true
916 //assert((outbound_mtc_smpte_frame + (next_quarter_frame_to_send * quarter_frame_duration))
917 // > _transport_frame);
920 // Send quarter frames for this cycle
921 while (_transport_frame + nframes > (outbound_mtc_smpte_frame +
922 (next_quarter_frame_to_send * quarter_frame_duration))) {
924 //cerr << "(MTC) Next frame to send: " << next_quarter_frame_to_send << endl;
926 switch (next_quarter_frame_to_send) {
928 mtc_msg[1] = 0x00 | (transmitting_smpte_time.frames & 0xf);
931 mtc_msg[1] = 0x10 | ((transmitting_smpte_time.frames & 0xf0) >> 4);
934 mtc_msg[1] = 0x20 | (transmitting_smpte_time.seconds & 0xf);
937 mtc_msg[1] = 0x30 | ((transmitting_smpte_time.seconds & 0xf0) >> 4);
940 mtc_msg[1] = 0x40 | (transmitting_smpte_time.minutes & 0xf);
943 mtc_msg[1] = 0x50 | ((transmitting_smpte_time.minutes & 0xf0) >> 4);
946 mtc_msg[1] = 0x60 | ((mtc_smpte_bits|transmitting_smpte_time.hours) & 0xf);
949 mtc_msg[1] = 0x70 | (((mtc_smpte_bits|transmitting_smpte_time.hours) & 0xf0) >> 4);
953 const jack_nframes_t msg_time = (outbound_mtc_smpte_frame
954 + (quarter_frame_duration * next_quarter_frame_to_send));
956 // This message must fall within this block or something is broken
957 assert(msg_time >= _transport_frame);
958 assert(msg_time < _transport_frame + nframes);
960 jack_nframes_t out_stamp = msg_time - _transport_frame;
961 assert(out_stamp < nframes);
963 if (!_mtc_port->midimsg (mtc_msg, 2, out_stamp)) {
964 error << string_compose(_("Session: cannot send quarter-frame MTC message (%1)"), strerror (errno))
969 /*cerr << "(MTC) SMPTE: " << transmitting_smpte_time.hours
970 << ":" << transmitting_smpte_time.minutes
971 << ":" << transmitting_smpte_time.seconds
972 << ":" << transmitting_smpte_time.frames
973 << ", qfm = " << next_quarter_frame_to_send
974 << ", stamp = " << out_stamp
975 << ", delta = " << _transport_frame + out_stamp - last_time << endl;*/
977 // Increment quarter frame counter
978 next_quarter_frame_to_send++;
980 if (next_quarter_frame_to_send >= 8) {
981 // Wrap quarter frame counter
982 next_quarter_frame_to_send = 0;
983 // Increment smpte time twice
984 SMPTE::increment( transmitting_smpte_time );
985 SMPTE::increment( transmitting_smpte_time );
986 // Re-calculate timing of first quarter frame
987 //smpte_to_sample( transmitting_smpte_time, outbound_mtc_smpte_frame, true /* use_offset */, false );
988 outbound_mtc_smpte_frame += 8 * quarter_frame_duration;
989 // Compensate for audio latency
990 outbound_mtc_smpte_frame += _worst_output_latency;
997 /***********************************************************************
999 **********************************************************************/
1002 Session::send_mmc_in_another_thread (MIDI::MachineControl::Command cmd, jack_nframes_t target_frame)
1004 MIDIRequest* request;
1006 if (_mtc_port == 0 || !send_mmc) {
1010 request = new MIDIRequest;
1011 request->type = MIDIRequest::SendMMC;
1012 request->mmc_cmd = cmd;
1013 request->locate_frame = target_frame;
1015 midi_requests.write (&request, 1);
1016 poke_midi_thread ();
1020 Session::deliver_mmc (MIDI::MachineControl::Command cmd, jack_nframes_t where)
1023 using namespace MIDI;
1027 if (_mmc_port == 0 || !send_mmc) {
1031 mmc_buffer[nbytes++] = cmd;
1033 // cerr << "delivering MMC, cmd = " << hex << (int) cmd << dec << endl;
1036 case MachineControl::cmdLocate:
1037 smpte_time_subframes (where, smpte);
1039 mmc_buffer[nbytes++] = 0x6; // byte count
1040 mmc_buffer[nbytes++] = 0x1; // "TARGET" subcommand
1041 mmc_buffer[nbytes++] = smpte.hours;
1042 mmc_buffer[nbytes++] = smpte.minutes;
1043 mmc_buffer[nbytes++] = smpte.seconds;
1044 mmc_buffer[nbytes++] = smpte.frames;
1045 mmc_buffer[nbytes++] = smpte.subframes;
1048 case MachineControl::cmdStop:
1051 case MachineControl::cmdPlay:
1052 /* always convert Play into Deferred Play */
1053 mmc_buffer[4] = MachineControl::cmdDeferredPlay;
1056 case MachineControl::cmdDeferredPlay:
1059 case MachineControl::cmdRecordStrobe:
1062 case MachineControl::cmdRecordExit:
1065 case MachineControl::cmdRecordPause:
1074 mmc_buffer[nbytes++] = 0xf7; // terminate SysEx/MMC message
1076 Glib::Mutex::Lock lm (midi_lock);
1078 if (_mmc_port->write (mmc_buffer, nbytes) != nbytes) {
1079 error << string_compose(_("MMC: cannot send command %1%2%3"), &hex, cmd, &dec) << endmsg;
1083 cout << "MMC support broken." << endl;
1087 Session::mmc_step_timeout ()
1090 struct timeval diff;
1092 gettimeofday (&now, 0);
1094 timersub (&now, &last_mmc_step, &diff);
1095 diff_usecs = diff.tv_sec * 1000000 + diff.tv_usec;
1097 if (diff_usecs > 1000000.0 || fabs (_transport_speed) < 0.0000001) {
1098 /* too long or too slow, stop transport */
1099 request_transport_speed (0.0);
1100 step_queued = false;
1104 if (diff_usecs < 250000.0) {
1105 /* too short, just keep going */
1111 request_transport_speed (_transport_speed * 0.75);
1117 Session::send_midi_message (MIDI::Port * port, MIDI::eventType ev, MIDI::channel_t ch, MIDI::EventTwoBytes data)
1119 // in another thread, really
1121 MIDIRequest* request = new MIDIRequest;
1123 request->type = MIDIRequest::SendMessage;
1124 request->port = port;
1127 request->data = data;
1129 midi_requests.write (&request, 1);
1130 poke_midi_thread ();
1135 Session::deliver_midi (MIDI::Port * port, MIDI::byte* buf, int32_t bufsize)
1137 // in another thread, really
1139 MIDIRequest* request = new MIDIRequest;
1141 request->type = MIDIRequest::Deliver;
1142 request->port = port;
1144 request->size = bufsize;
1146 midi_requests.write (&request, 1);
1147 poke_midi_thread ();
1153 This is aaalll gone.
1157 Session::deliver_midi_message (MIDI::Port * port, MIDI::eventType ev, MIDI::channel_t ch, MIDI::EventTwoBytes data)
1159 if (port == 0 || ev == MIDI::none) {
1163 midi_msg[0] = (ev & 0xF0) | (ch & 0xF);
1164 midi_msg[1] = data.controller_number;
1165 midi_msg[2] = data.value;
1167 port->write (midi_msg, 3);
1171 Session::deliver_data (MIDI::Port * port, MIDI::byte* buf, int32_t size)
1174 port->write (buf, size);
1177 /* this is part of the semantics of the Deliver request */
1184 /*---------------------------------------------------------------------------
1186 ---------------------------------------------------------------------------*/
1190 Session::start_midi_thread ()
1192 if (pipe (midi_request_pipe)) {
1193 error << string_compose(_("Cannot create transport request signal pipe (%1)"), strerror (errno)) << endmsg;
1197 if (fcntl (midi_request_pipe[0], F_SETFL, O_NONBLOCK)) {
1198 error << string_compose(_("UI: cannot set O_NONBLOCK on " "signal read pipe (%1)"), strerror (errno)) << endmsg;
1202 if (fcntl (midi_request_pipe[1], F_SETFL, O_NONBLOCK)) {
1203 error << string_compose(_("UI: cannot set O_NONBLOCK on " "signal write pipe (%1)"), strerror (errno)) << endmsg;
1207 if (pthread_create_and_store ("transport", &midi_thread, 0, _midi_thread_work, this)) {
1208 error << _("Session: could not create transport thread") << endmsg;
1212 // pthread_detach (midi_thread);
1218 Session::terminate_midi_thread ()
1220 MIDIRequest* request = new MIDIRequest;
1223 request->type = MIDIRequest::Quit;
1225 midi_requests.write (&request, 1);
1226 poke_midi_thread ();
1228 pthread_join (midi_thread, &status);
1232 Session::poke_midi_thread ()
1236 if (write (midi_request_pipe[1], &c, 1) != 1) {
1237 error << string_compose(_("cannot send signal to midi thread! (%1)"), strerror (errno)) << endmsg;
1242 Session::_midi_thread_work (void* arg)
1244 pthread_setcancelstate (PTHREAD_CANCEL_ENABLE, 0);
1245 pthread_setcanceltype (PTHREAD_CANCEL_ASYNCHRONOUS, 0);
1247 ((Session *) arg)->midi_thread_work ();
1252 Session::midi_thread_work ()
1254 MIDIRequest* request;
1255 struct pollfd pfd[4];
1259 struct sched_param rtparam;
1262 vector<MIDI::Port*> ports;
1264 PBD::ThreadCreatedWithRequestSize (pthread_self(), X_("MIDI"), 2048);
1266 memset (&rtparam, 0, sizeof (rtparam));
1267 rtparam.sched_priority = 9; /* XXX should be relative to audio (JACK) thread */
1269 if ((x = pthread_setschedparam (pthread_self(), SCHED_FIFO, &rtparam)) != 0) {
1270 // do we care? not particularly.
1273 /* set up the port vector; 4 is the largest possible size for now */
1275 ports.push_back (0);
1276 ports.push_back (0);
1277 ports.push_back (0);
1278 ports.push_back (0);
1284 pfd[nfds].fd = midi_request_pipe[0];
1285 pfd[nfds].events = POLLIN|POLLHUP|POLLERR;
1288 /* if we are using MMC control, we obviously have to listen
1289 on the appropriate port.
1292 if (mmc_control && _mmc_port && _mmc_port->selectable() >= 0) {
1293 pfd[nfds].fd = _mmc_port->selectable();
1294 pfd[nfds].events = POLLIN|POLLHUP|POLLERR;
1295 ports[nfds] = _mmc_port;
1299 /* if MTC is being handled on a different port from MMC
1300 or we are not handling MMC at all, poll
1304 if (_mtc_port && (_mtc_port != _mmc_port || !mmc_control) && _mtc_port->selectable() >= 0) {
1305 pfd[nfds].fd = _mtc_port->selectable();
1306 pfd[nfds].events = POLLIN|POLLHUP|POLLERR;
1307 ports[nfds] = _mtc_port;
1311 if (_midi_port && (_midi_port != _mmc_port || !mmc_control) && (_midi_port != _mtc_port) && _midi_port->selectable() >= 0) {
1312 pfd[nfds].fd = _midi_port->selectable();
1313 pfd[nfds].events = POLLIN|POLLHUP|POLLERR;
1314 ports[nfds] = _midi_port;
1318 if (!midi_timeouts.empty()) {
1319 timeout = 100; /* 10msecs */
1321 timeout = -1; /* if there is no data, we don't care */
1325 // cerr << "MIDI poll on " << nfds << " for " << timeout << endl;
1326 if (poll (pfd, nfds, timeout) < 0) {
1327 if (errno == EINTR) {
1328 /* gdb at work, perhaps */
1332 error << string_compose(_("MIDI thread poll failed (%1)"), strerror (errno)) << endmsg;
1336 // cerr << "MIDI thread wakes at " << get_cycles () << endl;
1341 /* check the transport request pipe */
1343 if (pfd[0].revents & ~POLLIN) {
1344 error << _("Error on transport thread request pipe") << endmsg;
1348 if (pfd[0].revents & POLLIN) {
1352 // cerr << "MIDI request FIFO ready\n";
1355 /* empty the pipe of all current requests */
1358 size_t nread = read (midi_request_pipe[0], &foo, sizeof (foo));
1361 if ((size_t) nread < sizeof (foo)) {
1366 } else if (nread == 0) {
1368 } else if (errno == EAGAIN) {
1371 fatal << _("Error reading from transport request pipe") << endmsg;
1376 while (midi_requests.read (&request, 1) == 1) {
1378 switch (request->type) {
1380 case MIDIRequest::SendFullMTC:
1381 // cerr << "send full MTC\n";
1382 send_full_time_code ();
1383 // cerr << "... done\n";
1386 case MIDIRequest::SendMTC:
1387 // cerr << "send qtr MTC\n";
1388 send_midi_time_code ();
1389 // cerr << "... done\n";
1392 case MIDIRequest::SendMMC:
1393 // cerr << "send MMC\n";
1394 deliver_mmc (request->mmc_cmd, request->locate_frame);
1395 // cerr << "... done\n";
1398 case MIDIRequest::SendMessage:
1399 // cerr << "send Message\n";
1400 deliver_midi_message (request->port, request->ev, request->chan, request->data);
1401 // cerr << "... done\n";
1404 case MIDIRequest::Deliver:
1405 // cerr << "deliver\n";
1406 deliver_data (_midi_port, request->buf, request->size);
1407 // cerr << "... done\n";
1410 case MIDIRequest::PortChange:
1411 /* restart poll with new ports */
1412 // cerr << "rebind\n";
1416 case MIDIRequest::Quit:
1418 pthread_exit_pbd (0);
1436 /* now read the rest of the ports */
1438 for (int p = 1; p < nfds; ++p) {
1439 if ((pfd[p].revents & ~POLLIN)) {
1440 // error << string_compose(_("Transport: error polling MIDI port %1 (revents =%2%3%4"), p, &hex, pfd[p].revents, &dec) << endmsg;
1444 if (pfd[p].revents & POLLIN) {
1446 midi_read (ports[p]);
1450 /* timeout driven */
1452 if (fds_ready < 2 && timeout != -1) {
1454 for (MidiTimeoutList::iterator i = midi_timeouts.begin(); i != midi_timeouts.end(); ) {
1456 MidiTimeoutList::iterator tmp;
1461 midi_timeouts.erase (i);
1472 Session::get_mmc_control () const
1478 Session::get_midi_control () const
1480 return midi_control;