8ccdd9420e100169589f5f64b428e7cbef1ccb35
[ardour.git] / libs / ardour / midi_diskstream.cc
1 /*
2     Copyright (C) 2000-2003 Paul Davis
3
4     This program is free software; you can redistribute it and/or modify
5     it under the terms of the GNU General Public License as published by
6     the Free Software Foundation; either version 2 of the License, or
7     (at your option) any later version.
8
9     This program is distributed in the hope that it will be useful,
10     but WITHOUT ANY WARRANTY; without even the implied warranty of
11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12     GNU General Public License for more details.
13
14     You should have received a copy of the GNU General Public License
15     along with this program; if not, write to the Free Software
16     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17 */
18
19 #include <fstream>
20 #include <cstdio>
21 #include <unistd.h>
22 #include <cmath>
23 #include <cerrno>
24 #include <string>
25 #include <climits>
26 #include <fcntl.h>
27 #include <cstdlib>
28 #include <ctime>
29 #include <sys/stat.h>
30 #include <sys/mman.h>
31
32 #include "pbd/error.h"
33 #include "pbd/basename.h"
34 #include <glibmm/thread.h>
35 #include "pbd/xml++.h"
36 #include "pbd/memento_command.h"
37 #include "pbd/enumwriter.h"
38 #include "pbd/stateful_diff_command.h"
39 #include "pbd/stacktrace.h"
40
41 #include "ardour/ardour.h"
42 #include "ardour/audioengine.h"
43 #include "ardour/butler.h"
44 #include "ardour/configuration.h"
45 #include "ardour/cycle_timer.h"
46 #include "ardour/debug.h"
47 #include "ardour/io.h"
48 #include "ardour/midi_diskstream.h"
49 #include "ardour/midi_playlist.h"
50 #include "ardour/midi_port.h"
51 #include "ardour/midi_region.h"
52 #include "ardour/playlist_factory.h"
53 #include "ardour/region_factory.h"
54 #include "ardour/send.h"
55 #include "ardour/session.h"
56 #include "ardour/smf_source.h"
57 #include "ardour/utils.h"
58 #include "ardour/session_playlists.h"
59 #include "ardour/route.h"
60
61 #include "midi++/types.h"
62
63 #include "i18n.h"
64 #include <locale.h>
65
66 using namespace std;
67 using namespace ARDOUR;
68 using namespace PBD;
69
70 framecnt_t MidiDiskstream::midi_readahead = 4096;
71
72 MidiDiskstream::MidiDiskstream (Session &sess, const string &name, Diskstream::Flag flag)
73         : Diskstream(sess, name, flag)
74         , _playback_buf(0)
75         , _capture_buf(0)
76         , _source_port(0)
77         , _last_flush_frame(0)
78         , _note_mode(Sustained)
79         , _frames_written_to_ringbuffer(0)
80         , _frames_read_from_ringbuffer(0)
81 {
82         in_set_state = true;
83
84         init ();
85         use_new_playlist ();
86         use_new_write_source (0);
87
88         in_set_state = false;
89
90         assert(!destructive());
91 }
92
93 MidiDiskstream::MidiDiskstream (Session& sess, const XMLNode& node)
94         : Diskstream(sess, node)
95         , _playback_buf(0)
96         , _capture_buf(0)
97         , _source_port(0)
98         , _last_flush_frame(0)
99         , _note_mode(Sustained)
100         , _frames_written_to_ringbuffer(0)
101         , _frames_read_from_ringbuffer(0)
102 {
103         in_set_state = true;
104
105         init ();
106
107         if (set_state (node, Stateful::loading_state_version)) {
108                 in_set_state = false;
109                 throw failed_constructor();
110         }
111
112         use_new_write_source (0);
113
114         in_set_state = false;
115 }
116
117 void
118 MidiDiskstream::init ()
119 {
120         /* there are no channels at this point, so these
121            two calls just get speed_buffer_size and wrap_buffer
122            size setup without duplicating their code.
123         */
124
125         set_block_size (_session.get_block_size());
126         allocate_temporary_buffers ();
127
128         const size_t size = _session.butler()->midi_diskstream_buffer_size();
129         _playback_buf = new MidiRingBuffer<framepos_t>(size);
130         _capture_buf = new MidiRingBuffer<framepos_t>(size);
131
132         _n_channels = ChanCount(DataType::MIDI, 1);
133
134         assert(recordable());
135 }
136
137 MidiDiskstream::~MidiDiskstream ()
138 {
139         Glib::Mutex::Lock lm (state_lock);
140 }
141
142
143 void
144 MidiDiskstream::non_realtime_locate (framepos_t position)
145 {
146         if (_write_source) {
147                 _write_source->set_timeline_position (position);
148         }
149         cerr << name() << " Seeking to " << position << endl;
150         seek (position, false);
151 }
152
153
154 void
155 MidiDiskstream::non_realtime_input_change ()
156 {
157         {
158                 Glib::Mutex::Lock lm (state_lock);
159
160                 if (input_change_pending.type == IOChange::NoChange) {
161                         return;
162                 }
163
164                 if (input_change_pending.type & IOChange::ConfigurationChanged) {
165                         uint32_t ni = _io->n_ports().n_midi();
166
167                         if (ni != _n_channels.n_midi()) {
168                                 error << string_compose (_("%1: I/O configuration change %4 requested to use %2, but channel setup is %3"),
169                                                          name(),
170                                                          _io->n_ports(),
171                                                          _n_channels, input_change_pending.type)
172                                       << endmsg;
173                         }
174
175                         if (ni == 0) {
176                                 _source_port = 0;
177                         } else {
178                                 _source_port = _io->midi(0);
179                         }
180                 }
181
182                 if (input_change_pending.type & IOChange::ConnectionsChanged) {
183                         set_capture_offset ();
184                         set_align_style_from_io ();
185                 }
186
187                 input_change_pending.type = IOChange::NoChange;
188
189                 /* implicit unlock */
190         }
191
192         /* unlike with audio, there is never any need to reset write sources
193            based on input configuration changes because ... a MIDI track
194            has just 1 MIDI port as input, always.
195         */
196
197         /* now refill channel buffers */
198
199         if (speed() != 1.0f || speed() != -1.0f) {
200                 seek ((framepos_t) (_session.transport_frame() * (double) speed()));
201         }
202         else {
203                 seek (_session.transport_frame());
204         }
205
206         _last_flush_frame = _session.transport_frame();
207 }
208
209 int
210 MidiDiskstream::find_and_use_playlist (const string& name)
211 {
212         boost::shared_ptr<MidiPlaylist> playlist;
213
214         if ((playlist = boost::dynamic_pointer_cast<MidiPlaylist> (_session.playlists->by_name (name))) == 0) {
215                 playlist = boost::dynamic_pointer_cast<MidiPlaylist> (PlaylistFactory::create (DataType::MIDI, _session, name));
216         }
217
218         if (!playlist) {
219                 error << string_compose(_("MidiDiskstream: Playlist \"%1\" isn't an midi playlist"), name) << endmsg;
220                 return -1;
221         }
222
223         return use_playlist (playlist);
224 }
225
226 int
227 MidiDiskstream::use_playlist (boost::shared_ptr<Playlist> playlist)
228 {
229         assert(boost::dynamic_pointer_cast<MidiPlaylist>(playlist));
230
231         Diskstream::use_playlist(playlist);
232
233         return 0;
234 }
235
236 int
237 MidiDiskstream::use_new_playlist ()
238 {
239         string newname;
240         boost::shared_ptr<MidiPlaylist> playlist;
241
242         if (!in_set_state && destructive()) {
243                 return 0;
244         }
245
246         if (_playlist) {
247                 newname = Playlist::bump_name (_playlist->name(), _session);
248         } else {
249                 newname = Playlist::bump_name (_name, _session);
250         }
251
252         if ((playlist = boost::dynamic_pointer_cast<MidiPlaylist> (PlaylistFactory::create (
253                         DataType::MIDI, _session, newname, hidden()))) != 0) {
254
255                 playlist->set_orig_diskstream_id (id());
256                 return use_playlist (playlist);
257
258         } else {
259                 return -1;
260         }
261 }
262
263 int
264 MidiDiskstream::use_copy_playlist ()
265 {
266         assert(midi_playlist());
267
268         if (destructive()) {
269                 return 0;
270         }
271
272         if (_playlist == 0) {
273                 error << string_compose(_("MidiDiskstream %1: there is no existing playlist to make a copy of!"), _name) << endmsg;
274                 return -1;
275         }
276
277         string newname;
278         boost::shared_ptr<MidiPlaylist> playlist;
279
280         newname = Playlist::bump_name (_playlist->name(), _session);
281
282         if ((playlist  = boost::dynamic_pointer_cast<MidiPlaylist>(PlaylistFactory::create (midi_playlist(), newname))) != 0) {
283                 playlist->set_orig_diskstream_id (id());
284                 return use_playlist (playlist);
285         } else {
286                 return -1;
287         }
288 }
289
290 /** Overloaded from parent to die horribly
291  */
292 int
293 MidiDiskstream::set_destructive (bool yn)
294 {
295         assert( ! destructive());
296         assert( ! yn);
297         return -1;
298 }
299
300 void
301 MidiDiskstream::set_note_mode (NoteMode m)
302 {
303         _note_mode = m;
304         midi_playlist()->set_note_mode(m);
305         if (_write_source && _write_source->model())
306                 _write_source->model()->set_note_mode(m);
307 }
308
309 #if 0
310 static void
311 trace_midi (ostream& o, MIDI::byte *msg, size_t len)
312 {
313         using namespace MIDI;
314         eventType type;
315         const char trace_prefix = ':';
316
317         type = (eventType) (msg[0]&0xF0);
318
319         switch (type) {
320         case off:
321                 o << trace_prefix
322                    << "Channel "
323                    << (msg[0]&0xF)+1
324                    << " NoteOff NoteNum "
325                    << (int) msg[1]
326                    << " Vel "
327                    << (int) msg[2]
328                    << endl;
329                 break;
330
331         case on:
332                 o << trace_prefix
333                    << "Channel "
334                    << (msg[0]&0xF)+1
335                    << " NoteOn NoteNum "
336                    << (int) msg[1]
337                    << " Vel "
338                    << (int) msg[2]
339                    << endl;
340                 break;
341
342         case polypress:
343                 o << trace_prefix
344                    << "Channel "
345                    << (msg[0]&0xF)+1
346                    << " PolyPressure"
347                    << (int) msg[1]
348                    << endl;
349                 break;
350
351         case MIDI::controller:
352                 o << trace_prefix
353                    << "Channel "
354                    << (msg[0]&0xF)+1
355                    << " Controller "
356                    << (int) msg[1]
357                    << " Value "
358                    << (int) msg[2]
359                    << endl;
360                 break;
361
362         case program:
363                 o << trace_prefix
364                    << "Channel "
365                    << (msg[0]&0xF)+1
366                    <<  " Program Change ProgNum "
367                    << (int) msg[1]
368                    << endl;
369                 break;
370
371         case chanpress:
372                 o << trace_prefix
373                    << "Channel "
374                    << (msg[0]&0xF)+1
375                    << " Channel Pressure "
376                    << (int) msg[1]
377                    << endl;
378                 break;
379
380         case MIDI::pitchbend:
381                 o << trace_prefix
382                    << "Channel "
383                    << (msg[0]&0xF)+1
384                    << " Pitch Bend "
385                    << ((msg[2]<<7)|msg[1])
386                    << endl;
387                 break;
388
389         case MIDI::sysex:
390                 if (len == 1) {
391                         switch (msg[0]) {
392                         case 0xf8:
393                                 o << trace_prefix
394                                    << "Clock"
395                                    << endl;
396                                 break;
397                         case 0xfa:
398                                 o << trace_prefix
399                                    << "Start"
400                                    << endl;
401                                 break;
402                         case 0xfb:
403                                 o << trace_prefix
404                                    << "Continue"
405                                    << endl;
406                                 break;
407                         case 0xfc:
408                                 o << trace_prefix
409                                    << "Stop"
410                                    << endl;
411                                 break;
412                         case 0xfe:
413                                 o << trace_prefix
414                                    << "Active Sense"
415                                    << endl;
416                                 break;
417                         case 0xff:
418                                 o << trace_prefix
419                                    << "System Reset"
420                                    << endl;
421                                 break;
422                         default:
423                                 o << trace_prefix
424                                    << "System Exclusive (1 byte : " << hex << (int) *msg << dec << ')'
425                                    << endl;
426                                 break;
427                         }
428                 } else {
429                         o << trace_prefix
430                            << "System Exclusive (" << len << ") = [ " << hex;
431                         for (unsigned int i = 0; i < len; ++i) {
432                                 o << (int) msg[i] << ' ';
433                         }
434                         o << dec << ']' << endl;
435
436                 }
437                 break;
438
439         case MIDI::song:
440                 o << trace_prefix << "Song" << endl;
441                 break;
442
443         case MIDI::tune:
444                 o << trace_prefix << "Tune" << endl;
445                 break;
446
447         case MIDI::eox:
448                 o << trace_prefix << "End-of-System Exclusive" << endl;
449                 break;
450
451         case MIDI::timing:
452                 o << trace_prefix << "Timing" << endl;
453                 break;
454
455         case MIDI::start:
456                 o << trace_prefix << "Start" << endl;
457                 break;
458
459         case MIDI::stop:
460                 o << trace_prefix << "Stop" << endl;
461                 break;
462
463         case MIDI::contineu:
464                 o << trace_prefix << "Continue" << endl;
465                 break;
466
467         case active:
468                 o << trace_prefix << "Active Sense" << endl;
469                 break;
470
471         default:
472                 o << trace_prefix << "Unrecognized MIDI message" << endl;
473                 break;
474         }
475 }
476 #endif
477
478 int
479 MidiDiskstream::process (framepos_t transport_frame, pframes_t nframes, bool can_record, bool rec_monitors_input, bool& need_butler)
480 {
481         int       ret = -1;
482         framecnt_t rec_offset = 0;
483         framecnt_t rec_nframes = 0;
484         bool      nominally_recording;
485         bool      re = record_enabled ();
486
487         playback_distance = 0;
488
489         check_record_status (transport_frame, can_record);
490
491         nominally_recording = (can_record && re);
492
493         if (nframes == 0) {
494                 return 0;
495         }
496
497         if (_source_port == 0) {
498                 return 1;
499         }
500
501         Glib::Mutex::Lock sm (state_lock, Glib::TRY_LOCK);
502
503         if (!sm.locked()) {
504                 return 1;
505         }
506
507         adjust_capture_position = 0;
508
509         if (nominally_recording || (re && was_recording && _session.get_record_enabled() && _session.config.get_punch_in())) {
510                 OverlapType ot = coverage (first_recordable_frame, last_recordable_frame, transport_frame, transport_frame + nframes);
511
512                 calculate_record_range(ot, transport_frame, nframes, rec_nframes, rec_offset);
513
514                 if (rec_nframes && !was_recording) {
515                         _write_source->mark_write_starting_now ();
516                         capture_captured = 0;
517                         was_recording = true;
518                 }
519         }
520
521         if (can_record && !_last_capture_sources.empty()) {
522                 _last_capture_sources.clear ();
523         }
524
525         if (nominally_recording || rec_nframes) {
526
527                 // Pump entire port buffer into the ring buffer (FIXME: split cycles?)
528                 MidiBuffer& buf = _source_port->get_midi_buffer(nframes);
529                 for (MidiBuffer::iterator i = buf.begin(); i != buf.end(); ++i) {
530                         const Evoral::MIDIEvent<MidiBuffer::TimeType> ev(*i, false);
531                         assert(ev.buffer());
532 #ifndef NDEBUG
533                         if (DEBUG::MidiIO & PBD::debug_bits) {
534                                 const uint8_t* __data = ev.buffer();
535                                 DEBUG_STR_DECL(a);
536                                 DEBUG_STR_APPEND(a, string_compose ("mididiskstream %1 capture event @ %2 + %3 sz %4 ", this, ev.time(), transport_frame, ev.size()));
537                                 for (size_t i=0; i < ev.size(); ++i) {
538                                         DEBUG_STR_APPEND(a,hex);
539                                         DEBUG_STR_APPEND(a,"0x");
540                                         DEBUG_STR_APPEND(a,(int)__data[i]);
541                                         DEBUG_STR_APPEND(a,' ');
542                                 }
543                                 DEBUG_STR_APPEND(a,'\n');
544                                 DEBUG_TRACE (DEBUG::MidiIO, DEBUG_STR(a).str());
545                         }
546 #endif
547                         _capture_buf->write(ev.time() + transport_frame, ev.type(), ev.size(), ev.buffer());
548                 }
549
550                 if (buf.size() != 0) {
551                         /* XXX this needs fixing - realtime new() call for
552                            every time we get MIDI data in a process callback!
553                         */
554
555                         /* Make a copy of this data and emit it for the GUI to see */
556                         boost::shared_ptr<MidiBuffer> copy (new MidiBuffer (buf.capacity ()));
557                         for (MidiBuffer::iterator i = buf.begin(); i != buf.end(); ++i) {
558                                 copy->push_back ((*i).time() + transport_frame, (*i).size(), (*i).buffer());
559                         }
560
561                         DataRecorded (copy, _write_source); /* EMIT SIGNAL */
562                 }
563
564         } else {
565
566                 if (was_recording) {
567                         finish_capture (rec_monitors_input);
568                 }
569
570         }
571
572         if (rec_nframes) {
573
574                 /* data will be written to disk */
575
576                 if (rec_nframes == nframes && rec_offset == 0) {
577                         playback_distance = nframes;
578                 }
579
580                 adjust_capture_position = rec_nframes;
581
582         } else if (nominally_recording) {
583
584                 /* XXXX do this for MIDI !!!
585                    can't do actual capture yet - waiting for latency effects to finish before we start
586                    */
587
588                 playback_distance = nframes;
589
590         } else {
591
592                 /* XXX: should be doing varispeed stuff here, similar to the code in AudioDiskstream::process */
593
594                 playback_distance = nframes;
595
596         }
597
598         ret = 0;
599
600         if (commit (nframes)) {
601                 need_butler = true;
602         }
603
604         return ret;
605 }
606
607 bool
608 MidiDiskstream::commit (framecnt_t nframes)
609 {
610         bool need_butler = false;
611
612         if (_actual_speed < 0.0) {
613                 playback_sample -= playback_distance;
614         } else {
615                 playback_sample += playback_distance;
616         }
617
618         if (adjust_capture_position != 0) {
619                 capture_captured += adjust_capture_position;
620                 adjust_capture_position = 0;
621         }
622
623         uint32_t frames_read = g_atomic_int_get(&_frames_read_from_ringbuffer);
624         uint32_t frames_written = g_atomic_int_get(&_frames_written_to_ringbuffer);
625         if ((frames_written - frames_read) + nframes < midi_readahead) {
626                 need_butler = true;
627         }
628
629         /*cerr << "MDS written: " << frames_written << " - read: " << frames_read <<
630                 " = " << frames_written - frames_read
631                 << " + " << nframes << " < " << midi_readahead << " = " << need_butler << ")" << endl;*/
632
633         return need_butler;
634 }
635
636 void
637 MidiDiskstream::set_pending_overwrite (bool yn)
638 {
639         /* called from audio thread, so we can use the read ptr and playback sample as we wish */
640
641         _pending_overwrite = yn;
642         overwrite_frame = playback_sample;
643 }
644
645 int
646 MidiDiskstream::overwrite_existing_buffers ()
647 {
648         /* This is safe as long as the butler thread is suspended, which it should be */
649         _playback_buf->reset ();
650
651         g_atomic_int_set (&_frames_read_from_ringbuffer, 0);
652         g_atomic_int_set (&_frames_written_to_ringbuffer, 0);
653
654         read (overwrite_frame, disk_io_chunk_frames, false);
655         file_frame = overwrite_frame; // it was adjusted by ::read()
656         overwrite_queued = false;
657         _pending_overwrite = false;
658
659         return 0;
660 }
661
662 int
663 MidiDiskstream::seek (framepos_t frame, bool complete_refill)
664 {
665         Glib::Mutex::Lock lm (state_lock);
666         int ret = -1;
667
668         _playback_buf->reset();
669         _capture_buf->reset();
670         g_atomic_int_set(&_frames_read_from_ringbuffer, 0);
671         g_atomic_int_set(&_frames_written_to_ringbuffer, 0);
672
673         playback_sample = frame;
674         file_frame = frame;
675
676         if (complete_refill) {
677                 while ((ret = do_refill_with_alloc ()) > 0) ;
678         } else {
679                 ret = do_refill_with_alloc ();
680         }
681
682         return ret;
683 }
684
685 int
686 MidiDiskstream::can_internal_playback_seek (framecnt_t distance)
687 {
688         uint32_t frames_read    = g_atomic_int_get(&_frames_read_from_ringbuffer);
689         uint32_t frames_written = g_atomic_int_get(&_frames_written_to_ringbuffer);
690         return ((frames_written - frames_read) < distance);
691 }
692
693 int
694 MidiDiskstream::internal_playback_seek (framecnt_t distance)
695 {
696         first_recordable_frame += distance;
697         playback_sample += distance;
698
699         return 0;
700 }
701
702 /** @a start is set to the new frame position (TIME) read up to */
703 int
704 MidiDiskstream::read (framepos_t& start, framecnt_t dur, bool reversed)
705 {
706         framecnt_t this_read = 0;
707         bool reloop = false;
708         framepos_t loop_end = 0;
709         framepos_t loop_start = 0;
710         Location *loc = 0;
711
712         if (!reversed) {
713
714                 framecnt_t loop_length = 0;
715
716                 /* Make the use of a Location atomic for this read operation.
717
718                    Note: Locations don't get deleted, so all we care about
719                    when I say "atomic" is that we are always pointing to
720                    the same one and using a start/length values obtained
721                    just once.
722                 */
723
724                 if ((loc = loop_location) != 0) {
725                         loop_start = loc->start();
726                         loop_end = loc->end();
727                         loop_length = loop_end - loop_start;
728                 }
729
730                 /* if we are looping, ensure that the first frame we read is at the correct
731                    position within the loop.
732                 */
733
734                 if (loc && (start >= loop_end)) {
735                         //cerr << "start adjusted from " << start;
736                         start = loop_start + ((start - loop_start) % loop_length);
737                         //cerr << "to " << start << endl;
738                 }
739                 //cerr << "start is " << start << "  loopstart: " << loop_start << "  loopend: " << loop_end << endl;
740         }
741
742         while (dur) {
743
744                 /* take any loop into account. we can't read past the end of the loop. */
745
746                 if (loc && (loop_end - start < dur)) {
747                         this_read = loop_end - start;
748                         //cerr << "reloop true: thisread: " << this_read << "  dur: " << dur << endl;
749                         reloop = true;
750                 } else {
751                         reloop = false;
752                         this_read = dur;
753                 }
754
755                 if (this_read == 0) {
756                         break;
757                 }
758
759                 this_read = min(dur,this_read);
760
761                 if (midi_playlist()->read (*_playback_buf, start, this_read) != this_read) {
762                         error << string_compose(
763                                         _("MidiDiskstream %1: cannot read %2 from playlist at frame %3"),
764                                         _id, this_read, start) << endmsg;
765                         return -1;
766                 }
767
768                 g_atomic_int_add(&_frames_written_to_ringbuffer, this_read);
769
770                 _read_data_count = _playlist->read_data_count();
771
772                 if (reversed) {
773
774                         // Swap note ons with note offs here.  etc?
775                         // Fully reversing MIDI requires look-ahead (well, behind) to find previous
776                         // CC values etc.  hard.
777
778                 } else {
779
780                         /* if we read to the end of the loop, go back to the beginning */
781
782                         if (reloop) {
783                                 // Synthesize LoopEvent here, because the next events
784                                 // written will have non-monotonic timestamps.
785                                 _playback_buf->write(loop_end - 1, LoopEventType, sizeof (framepos_t), (uint8_t *) &loop_start);
786                                 start = loop_start;
787                         } else {
788                                 start += this_read;
789                         }
790                 }
791
792                 dur -= this_read;
793                 //offset += this_read;
794         }
795
796         return 0;
797 }
798
799 int
800 MidiDiskstream::do_refill_with_alloc ()
801 {
802         return do_refill();
803 }
804
805 int
806 MidiDiskstream::do_refill ()
807 {
808         int     ret         = 0;
809         size_t  write_space = _playback_buf->write_space();
810         bool    reversed    = (_visible_speed * _session.transport_speed()) < 0.0f;
811
812         if (write_space == 0) {
813                 return 0;
814         }
815
816         if (reversed) {
817                 return 0;
818         }
819
820         /* at end: nothing to do */
821         if (file_frame == max_framepos) {
822                 return 0;
823         }
824
825         // At this point we...
826         assert(_playback_buf->write_space() > 0); // ... have something to write to, and
827         assert(file_frame <= max_framepos); // ... something to write
828
829         // now calculate how much time is in the ringbuffer.
830         // and lets write as much as we need to get this to be midi_readahead;
831         uint32_t frames_read = g_atomic_int_get(&_frames_read_from_ringbuffer);
832         uint32_t frames_written = g_atomic_int_get(&_frames_written_to_ringbuffer);
833         if ((frames_written - frames_read) >= midi_readahead) {
834                 return 0;
835         }
836
837         framecnt_t to_read = midi_readahead - (frames_written - frames_read);
838
839         //cout << "MDS read for midi_readahead " << to_read << "  rb_contains: "
840         //      << frames_written - frames_read << endl;
841
842         to_read = (framecnt_t) min ((framecnt_t) to_read, (framecnt_t) (max_framepos - file_frame));
843
844         if (read (file_frame, to_read, reversed)) {
845                 ret = -1;
846         }
847
848         return ret;
849 }
850
851 /** Flush pending data to disk.
852  *
853  * Important note: this function will write *AT MOST* disk_io_chunk_frames
854  * of data to disk. it will never write more than that.  If it writes that
855  * much and there is more than that waiting to be written, it will return 1,
856  * otherwise 0 on success or -1 on failure.
857  *
858  * If there is less than disk_io_chunk_frames to be written, no data will be
859  * written at all unless @a force_flush is true.
860  */
861 int
862 MidiDiskstream::do_flush (RunContext /*context*/, bool force_flush)
863 {
864         uint32_t to_write;
865         int32_t ret = 0;
866         framecnt_t total;
867
868         cerr << name() << " flushing to disk, bufspace = " << _capture_buf->read_space() 
869              << " transport @ " << _session.transport_frame() << " last flush @ " << _last_flush_frame
870              << endl;
871         
872         _write_data_count = 0;
873
874         total = _session.transport_frame() - _last_flush_frame;
875
876         if (total == 0 || _capture_buf->read_space() == 0
877                         || (!force_flush && (total < disk_io_chunk_frames && was_recording))) {
878                 cerr << "\tFlush shortcut because total = " << total
879                      << " capture read space = " << _capture_buf->read_space()
880                      << " force flush = " << force_flush 
881                      << " was recording = " << was_recording
882                      << endl;
883                 goto out;
884         }
885
886         /* if there are 2+ chunks of disk i/o possible for
887            this track, let the caller know so that it can arrange
888            for us to be called again, ASAP.
889
890            if we are forcing a flush, then if there is* any* extra
891            work, let the caller know.
892
893            if we are no longer recording and there is any extra work,
894            let the caller know too.
895            */
896
897         if (total >= 2 * disk_io_chunk_frames || ((force_flush || !was_recording) && total > disk_io_chunk_frames)) {
898                 ret = 1;
899         }
900
901         to_write = disk_io_chunk_frames;
902
903         assert(!destructive());
904
905         if (record_enabled() &&
906             ((_session.transport_frame() - _last_flush_frame > disk_io_chunk_frames) ||
907              force_flush)) {
908                 if ((!_write_source) || _write_source->midi_write (*_capture_buf, get_capture_start_frame (0), to_write) != to_write) {
909                         error << string_compose(_("MidiDiskstream %1: cannot write to disk"), _id) << endmsg;
910                         return -1;
911                 } else {
912                         cerr << "didn't write, _write_source = " << _write_source << endl;
913                         _last_flush_frame = _session.transport_frame();
914                 }
915         } else {
916                 cerr << "\tdidn't write to disk because recenabled = " << record_enabled()
917                      << " last flush @ " << _last_flush_frame << " disk io " << disk_io_chunk_frames << " TF @ " << _session.transport_frame()
918                      << " force = " << force_flush << endl;
919         }
920
921 out:
922
923         if (ret == 0) {
924                 if (_last_flush_frame > _session.transport_frame() || _last_flush_frame < capture_start_frame) {
925                         _last_flush_frame = _session.transport_frame();
926                         cerr << name() << " set last flush frame to " << _last_flush_frame << endl;
927                 }
928         }
929
930         return ret;
931 }
932
933 void
934 MidiDiskstream::transport_stopped_wallclock (struct tm& /*when*/, time_t /*twhen*/, bool abort_capture)
935 {
936         bool more_work = true;
937         int err = 0;
938         boost::shared_ptr<MidiRegion> region;
939         MidiRegion::SourceList srcs;
940         MidiRegion::SourceList::iterator src;
941         vector<CaptureInfo*>::iterator ci;
942
943         finish_capture (true);
944
945         /* butler is already stopped, but there may be work to do
946            to flush remaining data to disk.
947            */
948
949         while (more_work && !err) {
950                 switch (do_flush (TransportContext, true)) {
951                 case 0:
952                         more_work = false;
953                         break;
954                 case 1:
955                         break;
956                 case -1:
957                         error << string_compose(_("MidiDiskstream \"%1\": cannot flush captured data to disk!"), _name) << endmsg;
958                         err++;
959                 }
960         }
961
962         /* XXX is there anything we can do if err != 0 ? */
963         Glib::Mutex::Lock lm (capture_info_lock);
964
965         if (capture_info.empty()) {
966                 return;
967         }
968
969         if (abort_capture) {
970
971                 if (_write_source) {
972                         _write_source->mark_for_remove ();
973                         _write_source->drop_references ();
974                         _write_source.reset();
975                 }
976
977                 /* new source set up in "out" below */
978
979         } else {
980
981                 assert(_write_source);
982
983                 framecnt_t total_capture = 0;
984                 for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
985                         total_capture += (*ci)->frames;
986                 }
987
988                 if (_write_source->length (capture_info.front()->start) != 0) {
989
990                         /* phew, we have data */
991
992                         /* figure out the name for this take */
993
994                         srcs.push_back (_write_source);
995
996                         _write_source->set_timeline_position (capture_info.front()->start);
997                         _write_source->set_captured_for (_name);
998
999                         /* flush to disk: this step differs from the audio path,
1000                            where all the data is already on disk.
1001                         */
1002
1003                         _write_source->mark_streaming_write_completed ();
1004
1005                         /* set length in beats to entire capture length */
1006
1007                         BeatsFramesConverter converter (_session.tempo_map(), capture_info.front()->start);
1008                         const double total_capture_beats = converter.from(total_capture);
1009                         _write_source->set_length_beats(total_capture_beats);
1010
1011                         /* we will want to be able to keep (over)writing the source
1012                            but we don't want it to be removable. this also differs
1013                            from the audio situation, where the source at this point
1014                            must be considered immutable. luckily, we can rely on
1015                            MidiSource::mark_streaming_write_completed() to have
1016                            already done the necessary work for that.
1017                         */
1018
1019                         string whole_file_region_name;
1020                         whole_file_region_name = region_name_from_path (_write_source->name(), true);
1021
1022                         /* Register a new region with the Session that
1023                            describes the entire source. Do this first
1024                            so that any sub-regions will obviously be
1025                            children of this one (later!)
1026                         */
1027
1028                         try {
1029                                 PropertyList plist;
1030
1031                                 plist.add (Properties::name, whole_file_region_name);
1032                                 plist.add (Properties::whole_file, true);
1033                                 plist.add (Properties::automatic, true);
1034                                 plist.add (Properties::start, 0);
1035                                 plist.add (Properties::length, total_capture);
1036                                 plist.add (Properties::layer, 0);
1037
1038                                 boost::shared_ptr<Region> rx (RegionFactory::create (srcs, plist));
1039
1040                                 region = boost::dynamic_pointer_cast<MidiRegion> (rx);
1041                                 region->special_set_position (capture_info.front()->start);
1042                         }
1043
1044
1045                         catch (failed_constructor& err) {
1046                                 error << string_compose(_("%1: could not create region for complete midi file"), _name) << endmsg;
1047                                 /* XXX what now? */
1048                         }
1049
1050                         _last_capture_sources.insert (_last_capture_sources.end(), srcs.begin(), srcs.end());
1051
1052                         _playlist->clear_changes ();
1053                         _playlist->freeze ();
1054
1055                         /* Session frame time of the initial capture in this pass, which is where the source starts */
1056                         framepos_t initial_capture = 0;
1057                         if (!capture_info.empty()) {
1058                                 initial_capture = capture_info.front()->start;
1059                         }
1060
1061                         for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1062
1063                                 string region_name;
1064
1065                                 RegionFactory::region_name (region_name, _write_source->name(), false);
1066
1067                                 // cerr << _name << ": based on ci of " << (*ci)->start << " for " << (*ci)->frames << " add a region\n";
1068
1069                                 try {
1070                                         PropertyList plist;
1071
1072                                         /* start of this region is the offset between the start of its capture and the start of the whole pass */
1073                                         plist.add (Properties::start, (*ci)->start - initial_capture);
1074                                         plist.add (Properties::length, (*ci)->frames);
1075                                         plist.add (Properties::length_beats, converter.from((*ci)->frames));
1076                                         plist.add (Properties::name, region_name);
1077
1078                                         boost::shared_ptr<Region> rx (RegionFactory::create (srcs, plist));
1079                                         region = boost::dynamic_pointer_cast<MidiRegion> (rx);
1080                                 }
1081
1082                                 catch (failed_constructor& err) {
1083                                         error << _("MidiDiskstream: could not create region for captured midi!") << endmsg;
1084                                         continue; /* XXX is this OK? */
1085                                 }
1086
1087                                 // cerr << "add new region, buffer position = " << buffer_position << " @ " << (*ci)->start << endl;
1088
1089                                 i_am_the_modifier++;
1090                                 _playlist->add_region (region, (*ci)->start);
1091                                 i_am_the_modifier--;
1092                         }
1093
1094                         _playlist->thaw ();
1095                         _session.add_command (new StatefulDiffCommand(_playlist));
1096
1097                 } else {
1098
1099                         /* No data was recorded, so this capture will
1100                            effectively be aborted; do the same as we
1101                            do for an explicit abort.
1102                         */
1103
1104                         if (_write_source) {
1105                                 _write_source->mark_for_remove ();
1106                                 _write_source->drop_references ();
1107                                 _write_source.reset();
1108                         }
1109                 }
1110
1111         }
1112
1113         use_new_write_source (0);
1114
1115         for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1116                 delete *ci;
1117         }
1118
1119         if (_playlist) {
1120                 midi_playlist()->clear_note_trackers ();
1121         }
1122
1123         capture_info.clear ();
1124         capture_start_frame = 0;
1125 }
1126
1127 void
1128 MidiDiskstream::transport_looped (framepos_t transport_frame)
1129 {
1130         if (was_recording) {
1131
1132                 // adjust the capture length knowing that the data will be recorded to disk
1133                 // only necessary after the first loop where we're recording
1134                 if (capture_info.size() == 0) {
1135                         capture_captured += _capture_offset;
1136
1137                         if (_alignment_style == ExistingMaterial) {
1138                                 capture_captured += _session.worst_output_latency();
1139                         } else {
1140                                 capture_captured += _roll_delay;
1141                         }
1142                 }
1143
1144                 finish_capture (true);
1145
1146                 // the next region will start recording via the normal mechanism
1147                 // we'll set the start position to the current transport pos
1148                 // no latency adjustment or capture offset needs to be made, as that already happened the first time
1149                 capture_start_frame = transport_frame;
1150                 first_recordable_frame = transport_frame; // mild lie
1151                 last_recordable_frame = max_framepos;
1152                 was_recording = true;
1153         }
1154 }
1155
1156 void
1157 MidiDiskstream::finish_capture (bool /*rec_monitors_input*/)
1158 {
1159         was_recording = false;
1160
1161         if (capture_captured == 0) {
1162                 return;
1163         }
1164
1165         // Why must we destroy?
1166         assert(!destructive());
1167
1168         CaptureInfo* ci = new CaptureInfo;
1169
1170         ci->start  = capture_start_frame;
1171         ci->frames = capture_captured;
1172
1173         /* XXX theoretical race condition here. Need atomic exchange ?
1174            However, the circumstances when this is called right
1175            now (either on record-disable or transport_stopped)
1176            mean that no actual race exists. I think ...
1177            We now have a capture_info_lock, but it is only to be used
1178            to synchronize in the transport_stop and the capture info
1179            accessors, so that invalidation will not occur (both non-realtime).
1180         */
1181
1182         // cerr << "Finish capture, add new CI, " << ci->start << '+' << ci->frames << endl;
1183
1184         capture_info.push_back (ci);
1185         capture_captured = 0;
1186 }
1187
1188 void
1189 MidiDiskstream::set_record_enabled (bool yn)
1190 {
1191         if (!recordable() || !_session.record_enabling_legal()) {
1192                 return;
1193         }
1194
1195         assert(!destructive());
1196
1197         /* yes, i know that this not proof against race conditions, but its
1198            good enough. i think.
1199         */
1200
1201         if (record_enabled() != yn) {
1202                 if (yn) {
1203                         engage_record_enable ();
1204                 } else {
1205                         disengage_record_enable ();
1206                 }
1207         }
1208 }
1209
1210 void
1211 MidiDiskstream::engage_record_enable ()
1212 {
1213         bool const rolling = _session.transport_speed() != 0.0f;
1214
1215         g_atomic_int_set (&_record_enabled, 1);
1216
1217         if (_source_port && Config->get_monitoring_model() == HardwareMonitoring) {
1218                 _source_port->request_monitor_input (!(_session.config.get_auto_input() && rolling));
1219         }
1220
1221         RecordEnableChanged (); /* EMIT SIGNAL */
1222 }
1223
1224 void
1225 MidiDiskstream::disengage_record_enable ()
1226 {
1227         g_atomic_int_set (&_record_enabled, 0);
1228         RecordEnableChanged (); /* EMIT SIGNAL */
1229 }
1230
1231 XMLNode&
1232 MidiDiskstream::get_state ()
1233 {
1234         XMLNode& node (Diskstream::get_state());
1235         char buf[64];
1236         LocaleGuard lg (X_("POSIX"));
1237
1238         node.add_property("channel-mode", enum_2_string(get_channel_mode()));
1239         snprintf (buf, sizeof(buf), "0x%x", get_channel_mask());
1240         node.add_property("channel-mask", buf);
1241
1242         if (_write_source && _session.get_record_enabled()) {
1243
1244                 XMLNode* cs_child = new XMLNode (X_("CapturingSources"));
1245                 XMLNode* cs_grandchild;
1246
1247                 cs_grandchild = new XMLNode (X_("file"));
1248                 cs_grandchild->add_property (X_("path"), _write_source->path());
1249                 cs_child->add_child_nocopy (*cs_grandchild);
1250
1251                 /* store the location where capture will start */
1252
1253                 Location* pi;
1254
1255                 if (_session.config.get_punch_in() && ((pi = _session.locations()->auto_punch_location()) != 0)) {
1256                         snprintf (buf, sizeof (buf), "%" PRId64, pi->start());
1257                 } else {
1258                         snprintf (buf, sizeof (buf), "%" PRId64, _session.transport_frame());
1259                 }
1260
1261                 cs_child->add_property (X_("at"), buf);
1262                 node.add_child_nocopy (*cs_child);
1263         }
1264
1265         return node;
1266 }
1267
1268 int
1269 MidiDiskstream::set_state (const XMLNode& node, int version)
1270 {
1271         const XMLProperty* prop;
1272         XMLNodeList nlist = node.children();
1273         XMLNodeIterator niter;
1274         XMLNode* capture_pending_node = 0;
1275         LocaleGuard lg (X_("POSIX"));
1276
1277         /* prevent write sources from being created */
1278
1279         in_set_state = true;
1280
1281         for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
1282                 assert ((*niter)->name() != IO::state_node_name);
1283
1284                 if ((*niter)->name() == X_("CapturingSources")) {
1285                         capture_pending_node = *niter;
1286                 }
1287         }
1288
1289         if (Diskstream::set_state (node, version)) {
1290                 return -1;
1291         }
1292
1293         ChannelMode channel_mode = AllChannels;
1294         if ((prop = node.property ("channel-mode")) != 0) {
1295                 channel_mode = ChannelMode (string_2_enum(prop->value(), channel_mode));
1296         }
1297
1298         unsigned int channel_mask = 0xFFFF;
1299         if ((prop = node.property ("channel-mask")) != 0) {
1300                 sscanf (prop->value().c_str(), "0x%x", &channel_mask);
1301                 if (channel_mask & (~0xFFFF)) {
1302                         warning << _("MidiDiskstream: XML property channel-mask out of range") << endmsg;
1303                 }
1304         }
1305
1306
1307         if (capture_pending_node) {
1308                 use_pending_capture_data (*capture_pending_node);
1309         }
1310
1311         set_channel_mode (channel_mode, channel_mask);
1312
1313         in_set_state = false;
1314
1315         return 0;
1316 }
1317
1318 int
1319 MidiDiskstream::use_new_write_source (uint32_t n)
1320 {
1321         if (!_session.writable() || !recordable()) {
1322                 return 1;
1323         }
1324
1325         assert(n == 0);
1326
1327         _write_source.reset();
1328
1329         try {
1330                 _write_source = boost::dynamic_pointer_cast<SMFSource>(
1331                         _session.create_midi_source_for_session (0, name ()));
1332
1333                 if (!_write_source) {
1334                         throw failed_constructor();
1335                 }
1336         }
1337
1338         catch (failed_constructor &err) {
1339                 error << string_compose (_("%1:%2 new capture file not initialized correctly"), _name, n) << endmsg;
1340                 _write_source.reset();
1341                 return -1;
1342         }
1343
1344         return 0;
1345 }
1346
1347 list<boost::shared_ptr<Source> >
1348 MidiDiskstream::steal_write_sources()
1349 {
1350         list<boost::shared_ptr<Source> > ret;
1351
1352         /* put some data on the disk, even if its just a header for an empty file */
1353         boost::dynamic_pointer_cast<SMFSource> (_write_source)->ensure_disk_file ();
1354
1355         /* never let it go away */
1356         _write_source->mark_nonremovable ();
1357
1358         ret.push_back (_write_source);
1359
1360         /* get a new one */
1361
1362         use_new_write_source (0);
1363
1364         return ret;
1365 }
1366
1367 void
1368 MidiDiskstream::reset_write_sources (bool mark_write_complete, bool /*force*/)
1369 {
1370         if (!_session.writable() || !recordable()) {
1371                 return;
1372         }
1373
1374         if (_write_source && mark_write_complete) {
1375                 _write_source->mark_streaming_write_completed ();
1376         }
1377         use_new_write_source (0);
1378 }
1379
1380 void
1381 MidiDiskstream::set_block_size (pframes_t /*nframes*/)
1382 {
1383 }
1384
1385 void
1386 MidiDiskstream::allocate_temporary_buffers ()
1387 {
1388 }
1389
1390 void
1391 MidiDiskstream::monitor_input (bool yn)
1392 {
1393         if (_source_port)
1394                 _source_port->ensure_monitor_input (yn);
1395 }
1396
1397 void
1398 MidiDiskstream::set_align_style_from_io ()
1399 {
1400         if (_alignment_choice != Automatic) {
1401                 return;
1402         }
1403
1404         /* XXX Not sure what, if anything we can do with MIDI
1405            as far as capture alignment etc.
1406         */
1407
1408         set_align_style (ExistingMaterial);
1409 }
1410
1411
1412 float
1413 MidiDiskstream::playback_buffer_load () const
1414 {
1415         return (float) ((double) _playback_buf->read_space()/
1416                         (double) _playback_buf->capacity());
1417 }
1418
1419 float
1420 MidiDiskstream::capture_buffer_load () const
1421 {
1422         return (float) ((double) _capture_buf->write_space()/
1423                         (double) _capture_buf->capacity());
1424 }
1425
1426 int
1427 MidiDiskstream::use_pending_capture_data (XMLNode& /*node*/)
1428 {
1429         return 0;
1430 }
1431
1432 /** Writes playback events in the given range to \a dst, translating time stamps
1433  * so that an event at \a start has time = 0
1434  */
1435 void
1436 MidiDiskstream::get_playback (MidiBuffer& dst, framepos_t start, framepos_t end)
1437 {
1438         dst.clear();
1439         assert(dst.size() == 0);
1440
1441         // Reverse.  ... We just don't do reverse, ok?  Back off.
1442         if (end <= start) {
1443                 return;
1444         }
1445
1446         // Translate stamps to be relative to start
1447
1448
1449 #ifndef NDEBUG
1450         DEBUG_TRACE (DEBUG::MidiDiskstreamIO, string_compose (
1451                              "%1 MDS pre-read read %4..%5 from %2 write to %3\n", _name,
1452                              _playback_buf->get_read_ptr(), _playback_buf->get_write_ptr(), start, end));
1453 //        cerr << "================\n";
1454 //        _playback_buf->dump (cerr);
1455 //        cerr << "----------------\n";
1456
1457         const size_t events_read = _playback_buf->read(dst, start, end);
1458         DEBUG_TRACE (DEBUG::MidiDiskstreamIO, string_compose (
1459                              "%1 MDS events read %2 range %3 .. %4 rspace %5 wspace %6 r@%7 w@%8\n",
1460                              _name, events_read, start, end,
1461                              _playback_buf->read_space(), _playback_buf->write_space(),
1462                          _playback_buf->get_read_ptr(), _playback_buf->get_write_ptr()));
1463 #else
1464         _playback_buf->read(dst, start, end);
1465 #endif
1466
1467         gint32 frames_read = end - start;
1468         g_atomic_int_add(&_frames_read_from_ringbuffer, frames_read);
1469 }
1470
1471 bool
1472 MidiDiskstream::set_name (string const & name)
1473 {
1474         Diskstream::set_name (name);
1475
1476         /* get a new write source so that its name reflects the new diskstream name */
1477         use_new_write_source (0);
1478
1479         return true;
1480 }
1481