2 Copyright (C) 2000-2003 Paul Davis
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.
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.
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.
18 $Id: diskstream.cc 567 2006-06-07 14:54:12Z trutkin $
34 #include <pbd/error.h>
35 #include <pbd/basename.h>
36 #include <glibmm/thread.h>
37 #include <pbd/xml++.h>
38 #include <pbd/memento_command.h>
40 #include <ardour/ardour.h>
41 #include <ardour/audioengine.h>
42 #include <ardour/midi_diskstream.h>
43 #include <ardour/utils.h>
44 #include <ardour/configuration.h>
45 #include <ardour/smf_source.h>
46 #include <ardour/destructive_filesource.h>
47 #include <ardour/send.h>
48 #include <ardour/midi_playlist.h>
49 #include <ardour/cycle_timer.h>
50 #include <ardour/midi_region.h>
51 #include <ardour/midi_port.h>
57 using namespace ARDOUR;
60 MidiDiskstream::MidiDiskstream (Session &sess, const string &name, Diskstream::Flag flag)
61 : Diskstream(sess, name, flag)
64 , _current_playback_buffer(0)
65 , _current_capture_buffer(0)
66 , _playback_wrap_buffer(0)
67 , _capture_wrap_buffer(0)
70 , _capture_transition_buf(0)
72 /* prevent any write sources from being created */
81 assert(!destructive());
82 DiskstreamCreated (this); /* EMIT SIGNAL */
85 MidiDiskstream::MidiDiskstream (Session& sess, const XMLNode& node)
86 : Diskstream(sess, node)
89 , _current_playback_buffer(0)
90 , _current_capture_buffer(0)
91 , _playback_wrap_buffer(0)
92 , _capture_wrap_buffer(0)
95 , _capture_transition_buf(0)
100 if (set_state (node)) {
101 in_set_state = false;
102 throw failed_constructor();
105 in_set_state = false;
108 use_destructive_playlist ();
111 DiskstreamCreated (this); /* EMIT SIGNAL */
115 MidiDiskstream::init (Diskstream::Flag f)
119 /* there are no channels at this point, so these
120 two calls just get speed_buffer_size and wrap_buffer
121 size setup without duplicating their code.
124 set_block_size (_session.get_block_size());
125 allocate_temporary_buffers ();
127 _playback_wrap_buffer = new RawMidi[wrap_buffer_size];
128 _capture_wrap_buffer = new RawMidi[wrap_buffer_size];
129 _playback_buf = new RingBufferNPT<RawMidi> (_session.diskstream_buffer_size());
130 _capture_buf = new RingBufferNPT<RawMidi> (_session.diskstream_buffer_size());
131 _capture_transition_buf = new RingBufferNPT<CaptureTransition> (128);
133 _n_channels = ChanCount(DataType::MIDI, 1);
135 assert(recordable());
138 MidiDiskstream::~MidiDiskstream ()
140 Glib::Mutex::Lock lm (state_lock);
144 MidiDiskstream::non_realtime_input_change ()
147 Glib::Mutex::Lock lm (state_lock);
149 if (input_change_pending == NoChange) {
153 if (input_change_pending & ConfigurationChanged) {
155 assert(_io->n_inputs() == _n_channels);
158 get_input_sources ();
159 set_capture_offset ();
161 if (first_input_change) {
162 set_align_style (_persistent_alignment_style);
163 first_input_change = false;
165 set_align_style_from_io ();
168 input_change_pending = NoChange;
171 /* reset capture files */
173 reset_write_sources (false);
175 /* now refill channel buffers */
177 if (speed() != 1.0f || speed() != -1.0f) {
178 seek ((jack_nframes_t) (_session.transport_frame() * (double) speed()));
181 seek (_session.transport_frame());
186 MidiDiskstream::get_input_sources ()
188 uint32_t ni = _io->n_inputs().get(DataType::MIDI);
194 // This is all we do for now at least
197 _source_port = _io->midi_input(0);
199 /* I don't get it....
200 const char **connections = _io->input(0)->get_connections ();
202 if (connections == 0 || connections[0] == 0) {
205 // _source_port->disable_metering ();
211 _source_port = dynamic_cast<MidiPort*>(
212 _session.engine().get_port_by_name (connections[0]) );
221 MidiDiskstream::find_and_use_playlist (const string& name)
224 MidiPlaylist* playlist;
226 if ((pl = _session.playlist_by_name (name)) == 0) {
227 playlist = new MidiPlaylist(_session, name);
231 if ((playlist = dynamic_cast<MidiPlaylist*> (pl)) == 0) {
232 error << string_compose(_("MidiDiskstream: Playlist \"%1\" isn't a midi playlist"), name) << endmsg;
236 return use_playlist (playlist);
240 MidiDiskstream::use_playlist (Playlist* playlist)
242 assert(dynamic_cast<MidiPlaylist*>(playlist));
244 return Diskstream::use_playlist(playlist);
248 MidiDiskstream::use_new_playlist ()
251 MidiPlaylist* playlist;
253 if (!in_set_state && destructive()) {
258 newname = Playlist::bump_name (_playlist->name(), _session);
260 newname = Playlist::bump_name (_name, _session);
263 if ((playlist = new MidiPlaylist (_session, newname, hidden())) != 0) {
264 playlist->set_orig_diskstream_id (id());
265 return use_playlist (playlist);
272 MidiDiskstream::use_copy_playlist ()
278 if (_playlist == 0) {
279 error << string_compose(_("MidiDiskstream %1: there is no existing playlist to make a copy of!"), _name) << endmsg;
284 MidiPlaylist* playlist;
286 newname = Playlist::bump_name (_playlist->name(), _session);
288 if ((playlist = new MidiPlaylist (*midi_playlist(), newname)) != 0) {
289 playlist->set_orig_diskstream_id (id());
290 return use_playlist (playlist);
296 /** Overloaded from parent to die horribly
299 MidiDiskstream::set_destructive (bool yn)
301 assert( ! destructive());
306 MidiDiskstream::check_record_status (jack_nframes_t transport_frame, jack_nframes_t nframes, bool can_record)
308 // FIXME: waaay too much code to duplicate (AudioDiskstream)
310 int possibly_recording;
313 const int transport_rolling = 0x4;
314 const int track_rec_enabled = 0x2;
315 const int global_rec_enabled = 0x1;
317 /* merge together the 3 factors that affect record status, and compute
321 rolling = _session.transport_speed() != 0.0f;
322 possibly_recording = (rolling << 2) | (record_enabled() << 1) | can_record;
323 change = possibly_recording ^ last_possibly_recording;
325 if (possibly_recording == last_possibly_recording) {
331 /* if per-track or global rec-enable turned on while the other was already on, we've started recording */
333 if ((change & track_rec_enabled) && record_enabled() && (!(change & global_rec_enabled) && can_record) ||
334 ((change & global_rec_enabled) && can_record && (!(change & track_rec_enabled) && record_enabled()))) {
336 /* starting to record: compute first+last frames */
338 first_recordable_frame = transport_frame + _capture_offset;
339 last_recordable_frame = max_frames;
340 capture_start_frame = transport_frame;
342 if (!(last_possibly_recording & transport_rolling) && (possibly_recording & transport_rolling)) {
344 /* was stopped, now rolling (and recording) */
346 if (_alignment_style == ExistingMaterial) {
347 first_recordable_frame += _session.worst_output_latency();
349 first_recordable_frame += _roll_delay;
354 /* was rolling, but record state changed */
356 if (_alignment_style == ExistingMaterial) {
359 if (!_session.get_punch_in()) {
361 /* manual punch in happens at the correct transport frame
362 because the user hit a button. but to get alignment correct
363 we have to back up the position of the new region to the
364 appropriate spot given the roll delay.
367 capture_start_frame -= _roll_delay;
369 /* XXX paul notes (august 2005): i don't know why
373 first_recordable_frame += _capture_offset;
377 /* autopunch toggles recording at the precise
378 transport frame, and then the DS waits
379 to start recording for a time that depends
380 on the output latency.
383 first_recordable_frame += _session.worst_output_latency();
388 if (_session.get_punch_in()) {
389 first_recordable_frame += _roll_delay;
391 capture_start_frame -= _roll_delay;
397 if (_flags & Recordable) {
398 RingBufferNPT<CaptureTransition>::rw_vector transvec;
399 _capture_transition_buf->get_write_vector(&transvec);
401 if (transvec.len[0] > 0) {
402 transvec.buf[0]->type = CaptureStart;
403 transvec.buf[0]->capture_val = capture_start_frame;
404 _capture_transition_buf->increment_write_ptr(1);
407 fatal << X_("programming error: capture_transition_buf is full on rec start! inconceivable!")
412 } else if (!record_enabled() || !can_record) {
416 last_recordable_frame = transport_frame + _capture_offset;
418 if (_alignment_style == ExistingMaterial) {
419 last_recordable_frame += _session.worst_output_latency();
421 last_recordable_frame += _roll_delay;
425 last_possibly_recording = possibly_recording;
429 MidiDiskstream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jack_nframes_t offset, bool can_record, bool rec_monitors_input)
431 // FIXME: waay too much code to duplicate (AudioDiskstream::process)
433 jack_nframes_t rec_offset = 0;
434 jack_nframes_t rec_nframes = 0;
435 bool nominally_recording;
436 bool re = record_enabled ();
437 bool collect_playback = false;
439 _current_capture_buffer = 0;
440 _current_playback_buffer = 0;
442 /* if we've already processed the frames corresponding to this call,
443 just return. this allows multiple routes that are taking input
444 from this diskstream to call our ::process() method, but have
445 this stuff only happen once. more commonly, it allows both
446 the AudioTrack that is using this AudioDiskstream *and* the Session
447 to call process() without problems.
454 check_record_status (transport_frame, nframes, can_record);
456 nominally_recording = (can_record && re);
463 /* This lock is held until the end of AudioDiskstream::commit, so these two functions
464 must always be called as a pair. The only exception is if this function
465 returns a non-zero value, in which case, ::commit should not be called.
468 // If we can't take the state lock return.
469 if (!state_lock.trylock()) {
473 adjust_capture_position = 0;
475 if (nominally_recording || (_session.get_record_enabled() && _session.get_punch_in())) {
478 ot = coverage (first_recordable_frame, last_recordable_frame, transport_frame, transport_frame + nframes);
485 case OverlapInternal:
486 /* ---------- recrange
489 rec_nframes = nframes;
494 /* |--------| recrange
497 rec_nframes = transport_frame + nframes - first_recordable_frame;
499 rec_offset = first_recordable_frame - transport_frame;
504 /* |--------| recrange
507 rec_nframes = last_recordable_frame - transport_frame;
511 case OverlapExternal:
512 /* |--------| recrange
513 -------------- transrange
515 rec_nframes = last_recordable_frame - last_recordable_frame;
516 rec_offset = first_recordable_frame - transport_frame;
520 if (rec_nframes && !was_recording) {
521 capture_captured = 0;
522 was_recording = true;
527 if (can_record && !_last_capture_regions.empty()) {
528 _last_capture_regions.clear ();
531 if (nominally_recording || rec_nframes) {
532 _capture_buf->get_write_vector (&_capture_vector);
534 if (rec_nframes <= _capture_vector.len[0]) {
536 _current_capture_buffer = _capture_vector.buf[0];
538 /* note: grab the entire port buffer, but only copy what we were supposed to for recording, and use
542 // FIXME: midi buffer size?
544 // FIXME: reading from a MIDI port is different, can't just memcpy
545 //memcpy (_current_capture_buffer, _io->input(0)->get_buffer (rec_nframes) + offset + rec_offset, sizeof (RawMidi) * rec_nframes);
546 assert(_source_port);
548 /*for (size_t i=0; i < _source_port->size(); ++i) {
549 cerr << "DISKSTREAM GOT EVENT(1) " << i << "!!\n";
552 if (_source_port->size() == 0)
553 cerr << "No events :/ (1)\n";
559 jack_nframes_t total = _capture_vector.len[0] + _capture_vector.len[1];
561 if (rec_nframes > total) {
562 cerr << "DiskOverrun\n";
563 //DiskOverrun (); // FIXME
568 //RawMidi* buf = _io->input (0)->get_buffer (nframes) + offset;
569 assert(_source_port);
572 for (size_t i=0; i < _source_port->size(); ++i) {
573 cerr << "DISKSTREAM GOT EVENT(2) " << i << "!!\n";
575 if (_source_port->size() == 0)
576 cerr << "No events :/ (2)\n";
579 RawMidi* buf = NULL; // FIXME FIXME FIXME (make it compile)
581 jack_nframes_t first = _capture_vector.len[0];
583 memcpy (_capture_wrap_buffer, buf, sizeof (RawMidi) * first);
584 memcpy (_capture_vector.buf[0], buf, sizeof (RawMidi) * first);
585 memcpy (_capture_wrap_buffer+first, buf + first, sizeof (RawMidi) * (rec_nframes - first));
586 memcpy (_capture_vector.buf[1], buf + first, sizeof (RawMidi) * (rec_nframes - first));
588 _current_capture_buffer = _capture_wrap_buffer;
593 finish_capture (rec_monitors_input);
600 // FIXME: filthy hack to fool the GUI into thinking we're doing something
602 // _write_source->ViewDataRangeReady (transport_frame, rec_nframes); /* EMIT SIGNAL */
604 /* data will be written to disk */
606 if (rec_nframes == nframes && rec_offset == 0) {
608 _current_playback_buffer = _current_capture_buffer;
609 playback_distance = nframes;
614 /* we can't use the capture buffer as the playback buffer, because
615 we recorded only a part of the current process' cycle data
619 collect_playback = true;
622 adjust_capture_position = rec_nframes;
624 } else if (nominally_recording) {
626 /* can't do actual capture yet - waiting for latency effects to finish before we start*/
628 _current_playback_buffer = _current_capture_buffer;
630 playback_distance = nframes;
634 collect_playback = true;
637 if (collect_playback) {
639 /* we're doing playback */
641 jack_nframes_t necessary_samples;
643 /* no varispeed playback if we're recording, because the output .... TBD */
645 if (rec_nframes == 0 && _actual_speed != 1.0f) {
646 necessary_samples = (jack_nframes_t) floor ((nframes * fabs (_actual_speed))) + 1;
648 necessary_samples = nframes;
651 _playback_buf->get_read_vector (&_playback_vector);
653 if (necessary_samples <= _playback_vector.len[0]) {
655 _current_playback_buffer = _playback_vector.buf[0];
658 jack_nframes_t total = _playback_vector.len[0] + _playback_vector.len[1];
660 if (necessary_samples > total) {
661 //cerr << "DiskUnderrun\n";
662 //DiskUnderrun (); // FIXME
667 memcpy (_playback_wrap_buffer, _playback_vector.buf[0],
668 _playback_vector.len[0] * sizeof (RawMidi));
669 memcpy (_playback_wrap_buffer + _playback_vector.len[0], _playback_vector.buf[1],
670 (necessary_samples - _playback_vector.len[0]) * sizeof (RawMidi));
672 _current_playback_buffer = _playback_wrap_buffer;
677 if (rec_nframes == 0 && _actual_speed != 1.0f && _actual_speed != -1.0f) {
679 uint64_t phase = last_phase;
680 jack_nframes_t i = 0;
682 // Linearly interpolate into the alt buffer
683 // using 40.24 fixp maths (swh)
685 for (c = channels.begin(); c != channels.end(); ++c) {
688 ChannelInfo& chan (*c);
693 for (jack_nframes_t outsample = 0; outsample < nframes; ++outsample) {
695 fr = (phase & 0xFFFFFF) / 16777216.0f;
696 chan.speed_buffer[outsample] =
697 chan._current_playback_buffer[i] * (1.0f - fr) +
698 chan._current_playback_buffer[i+1] * fr;
702 chan._current_playback_buffer = chan.speed_buffer;
705 playback_distance = i + 1;
706 last_phase = (phase & 0xFFFFFF);
709 playback_distance = nframes;
713 playback_distance = nframes;
724 /* we're exiting with failure, so ::commit will not
725 be called. unlock the state lock.
739 MidiDiskstream::commit (jack_nframes_t nframes)
741 bool need_butler = false;
743 if (_actual_speed < 0.0) {
744 playback_sample -= playback_distance;
746 playback_sample += playback_distance;
749 _playback_buf->increment_read_ptr (playback_distance);
751 if (adjust_capture_position) {
752 _capture_buf->increment_write_ptr (adjust_capture_position);
755 if (adjust_capture_position != 0) {
756 capture_captured += adjust_capture_position;
757 adjust_capture_position = 0;
761 need_butler = _playback_buf->write_space() >= _playback_buf->bufsize() / 2;
763 need_butler = _playback_buf->write_space() >= disk_io_chunk_frames
764 || _capture_buf->read_space() >= disk_io_chunk_frames;
775 MidiDiskstream::set_pending_overwrite (bool yn)
777 /* called from audio thread, so we can use the read ptr and playback sample as we wish */
779 pending_overwrite = yn;
781 overwrite_frame = playback_sample;
782 //overwrite_offset = channels.front().playback_buf->get_read_ptr();
786 MidiDiskstream::overwrite_existing_buffers ()
792 MidiDiskstream::seek (jack_nframes_t frame, bool complete_refill)
794 Glib::Mutex::Lock lm (state_lock);
799 MidiDiskstream::can_internal_playback_seek (jack_nframes_t distance)
805 MidiDiskstream::internal_playback_seek (jack_nframes_t distance)
811 MidiDiskstream::read (MidiBuffer& dst, jack_nframes_t& start, jack_nframes_t cnt, bool reversed)
817 MidiDiskstream::do_refill_with_alloc ()
823 MidiDiskstream::do_refill ()
825 // yeah, the data's ready. promise.
829 /** Flush pending data to disk.
831 * Important note: this function will write *AT MOST* disk_io_chunk_frames
832 * of data to disk. it will never write more than that. If it writes that
833 * much and there is more than that waiting to be written, it will return 1,
834 * otherwise 0 on success or -1 on failure.
836 * If there is less than disk_io_chunk_frames to be written, no data will be
837 * written at all unless @a force_flush is true.
840 MidiDiskstream::do_flush (Session::RunContext context, bool force_flush)
842 /* hey, so did you write that data? */
844 // oh yeah, you bet. wrote it good. honest.
850 MidiDiskstream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture)
852 uint32_t buffer_position;
853 bool more_work = true;
855 MidiRegion* region = 0;
856 jack_nframes_t total_capture;
857 MidiRegion::SourceList srcs;
858 MidiRegion::SourceList::iterator src;
859 vector<CaptureInfo*>::iterator ci;
860 bool mark_write_completed = false;
862 finish_capture (true);
864 /* butler is already stopped, but there may be work to do
865 to flush remaining data to disk.
868 while (more_work && !err) {
869 switch (do_flush (Session::TransportContext, true)) {
876 error << string_compose(_("MidiDiskstream \"%1\": cannot flush captured data to disk!"), _name) << endmsg;
881 /* XXX is there anything we can do if err != 0 ? */
882 Glib::Mutex::Lock lm (capture_info_lock);
884 if (capture_info.empty()) {
890 list<Source*>* deletion_list = new list<Source*>;
893 _write_source->mark_for_remove ();
894 _write_source->release ();
896 deletion_list->push_back (_write_source);
901 /* new source set up in "out" below */
903 if (!deletion_list->empty()) {
904 DeleteSources (deletion_list);
906 delete deletion_list;
911 assert(_write_source);
913 for (total_capture = 0, ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
914 total_capture += (*ci)->frames;
917 /* figure out the name for this take */
919 SMFSource* s = _write_source;
925 cerr << "MidiDiskstream: updating source after capture\n";
926 s->update_header (capture_info.front()->start, when, twhen);
928 s->set_captured_for (_name);
932 /* Register a new region with the Session that
933 describes the entire source. Do this first
934 so that any sub-regions will obviously be
935 children of this one (later!)
938 assert(_write_source);
939 region = new MidiRegion (srcs, _write_source->last_capture_start_frame(), total_capture,
940 region_name_from_path (_write_source->name()),
941 0, Region::Flag (Region::DefaultFlags|Region::Automatic|Region::WholeFile));
943 region->special_set_position (capture_info.front()->start);
947 catch (failed_constructor& err) {
948 error << string_compose(_("%1: could not create region for complete midi file"), _name) << endmsg;
952 _last_capture_regions.push_back (region);
954 // cerr << _name << ": there are " << capture_info.size() << " capture_info records\n";
956 XMLNode &before = _playlist->get_state();
957 _playlist->freeze ();
959 for (buffer_position = _write_source->last_capture_start_frame(), ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
962 _session.region_name (region_name, _write_source->name(), false);
964 // cerr << _name << ": based on ci of " << (*ci)->start << " for " << (*ci)->frames << " add a region\n";
967 region = new MidiRegion (srcs, buffer_position, (*ci)->frames, region_name);
970 catch (failed_constructor& err) {
971 error << _("MidiDiskstream: could not create region for captured audio!") << endmsg;
972 continue; /* XXX is this OK? */
975 _last_capture_regions.push_back (region);
977 // cerr << "add new region, buffer position = " << buffer_position << " @ " << (*ci)->start << endl;
980 _playlist->add_region (*region, (*ci)->start);
983 buffer_position += (*ci)->frames;
987 XMLNode &after = _playlist->get_state();
988 _session.add_command (new MementoCommand<Playlist>(*_playlist, before, after));
990 mark_write_completed = true;
992 reset_write_sources (mark_write_completed);
996 for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1000 capture_info.clear ();
1001 capture_start_frame = 0;
1005 MidiDiskstream::finish_capture (bool rec_monitors_input)
1007 was_recording = false;
1009 if (capture_captured == 0) {
1013 // Why must we destroy?
1014 assert(!destructive());
1016 CaptureInfo* ci = new CaptureInfo;
1018 ci->start = capture_start_frame;
1019 ci->frames = capture_captured;
1021 /* XXX theoretical race condition here. Need atomic exchange ?
1022 However, the circumstances when this is called right
1023 now (either on record-disable or transport_stopped)
1024 mean that no actual race exists. I think ...
1025 We now have a capture_info_lock, but it is only to be used
1026 to synchronize in the transport_stop and the capture info
1027 accessors, so that invalidation will not occur (both non-realtime).
1030 // cerr << "Finish capture, add new CI, " << ci->start << '+' << ci->frames << endl;
1032 capture_info.push_back (ci);
1033 capture_captured = 0;
1037 MidiDiskstream::set_record_enabled (bool yn)
1039 if (!recordable() || !_session.record_enabling_legal()) {
1043 assert(!destructive());
1045 if (yn && _source_port == 0) {
1047 /* pick up connections not initiated *from* the IO object
1048 we're associated with.
1051 get_input_sources ();
1054 /* yes, i know that this not proof against race conditions, but its
1055 good enough. i think.
1058 if (record_enabled() != yn) {
1060 engage_record_enable ();
1062 disengage_record_enable ();
1068 MidiDiskstream::engage_record_enable ()
1070 bool rolling = _session.transport_speed() != 0.0f;
1072 g_atomic_int_set (&_record_enabled, 1);
1074 if (Config->get_use_hardware_monitoring() && _source_port) {
1075 _source_port->request_monitor_input (!(_session.get_auto_input() && rolling));
1078 RecordEnableChanged (); /* EMIT SIGNAL */
1082 MidiDiskstream::disengage_record_enable ()
1084 g_atomic_int_set (&_record_enabled, 0);
1085 if (Config->get_use_hardware_monitoring()) {
1087 _source_port->request_monitor_input (false);
1091 RecordEnableChanged (); /* EMIT SIGNAL */
1095 MidiDiskstream::get_state ()
1097 XMLNode* node = new XMLNode ("MidiDiskstream");
1099 LocaleGuard lg (X_("POSIX"));
1101 snprintf (buf, sizeof(buf), "0x%x", _flags);
1102 node->add_property ("flags", buf);
1104 node->add_property ("playlist", _playlist->name());
1106 snprintf (buf, sizeof(buf), "%f", _visible_speed);
1107 node->add_property ("speed", buf);
1109 node->add_property("name", _name);
1111 node->add_property("id", buf);
1113 if (_write_source && _session.get_record_enabled()) {
1115 XMLNode* cs_child = new XMLNode (X_("CapturingSources"));
1116 XMLNode* cs_grandchild;
1118 cs_grandchild = new XMLNode (X_("file"));
1119 cs_grandchild->add_property (X_("path"), _write_source->path());
1120 cs_child->add_child_nocopy (*cs_grandchild);
1122 /* store the location where capture will start */
1126 if (_session.get_punch_in() && ((pi = _session.locations()->auto_punch_location()) != 0)) {
1127 snprintf (buf, sizeof (buf), "%" PRIu32, pi->start());
1129 snprintf (buf, sizeof (buf), "%" PRIu32, _session.transport_frame());
1132 cs_child->add_property (X_("at"), buf);
1133 node->add_child_nocopy (*cs_child);
1137 node->add_child_copy (*_extra_xml);
1144 MidiDiskstream::set_state (const XMLNode& node)
1146 const XMLProperty* prop;
1147 XMLNodeList nlist = node.children();
1148 XMLNodeIterator niter;
1149 uint32_t nchans = 1;
1150 XMLNode* capture_pending_node = 0;
1151 LocaleGuard lg (X_("POSIX"));
1153 in_set_state = true;
1155 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
1156 /*if ((*niter)->name() == IO::state_node_name) {
1157 deprecated_io_node = new XMLNode (**niter);
1159 assert ((*niter)->name() != IO::state_node_name);
1161 if ((*niter)->name() == X_("CapturingSources")) {
1162 capture_pending_node = *niter;
1166 /* prevent write sources from being created */
1168 in_set_state = true;
1170 if ((prop = node.property ("name")) != 0) {
1171 _name = prop->value();
1174 if ((prop = node.property ("id")) != 0) {
1175 _id = prop->value ();
1178 if ((prop = node.property ("flags")) != 0) {
1179 _flags = strtol (prop->value().c_str(), 0, 0);
1182 if ((prop = node.property ("channels")) != 0) {
1183 nchans = atoi (prop->value().c_str());
1186 if ((prop = node.property ("playlist")) == 0) {
1191 bool had_playlist = (_playlist != 0);
1193 if (find_and_use_playlist (prop->value())) {
1197 if (!had_playlist) {
1198 _playlist->set_orig_diskstream_id (_id);
1201 if (capture_pending_node) {
1202 use_pending_capture_data (*capture_pending_node);
1207 if ((prop = node.property ("speed")) != 0) {
1208 double sp = atof (prop->value().c_str());
1210 if (realtime_set_speed (sp, false)) {
1211 non_realtime_set_speed ();
1215 in_set_state = false;
1217 /* make sure this is clear before we do anything else */
1220 //_capturing_source = 0;
1222 /* write sources are handled when we handle the input set
1223 up of the IO that owns this DS (::non_realtime_input_change())
1226 in_set_state = false;
1232 MidiDiskstream::use_new_write_source (uint32_t n)
1234 if (!recordable()) {
1240 if (_write_source) {
1242 if (SMFSource::is_empty (_write_source->path())) {
1243 _write_source->mark_for_remove ();
1244 _write_source->release();
1245 delete _write_source;
1247 _write_source->release();
1253 _write_source = dynamic_cast<SMFSource*>(_session.create_midi_source_for_session (*this));
1254 if (!_write_source) {
1255 throw failed_constructor();
1259 catch (failed_constructor &err) {
1260 error << string_compose (_("%1:%2 new capture file not initialized correctly"), _name, n) << endmsg;
1265 _write_source->use ();
1266 _write_source->set_allow_remove_if_empty (true);
1272 MidiDiskstream::reset_write_sources (bool mark_write_complete, bool force)
1274 if (!recordable()) {
1278 if (_write_source && mark_write_complete) {
1279 _write_source->mark_streaming_write_completed ();
1281 use_new_write_source ();
1282 assert(_write_source);
1286 MidiDiskstream::rename_write_sources ()
1288 if (_write_source != 0) {
1289 _write_source->set_name (_name, destructive());
1290 /* XXX what to do if this fails ? */
1296 MidiDiskstream::set_block_size (jack_nframes_t nframes)
1301 MidiDiskstream::allocate_temporary_buffers ()
1306 MidiDiskstream::monitor_input (bool yn)
1309 _source_port->request_monitor_input (yn);
1311 cerr << "MidiDiskstream NO SOURCE PORT TO MONITOR\n";
1315 MidiDiskstream::set_align_style_from_io ()
1317 bool have_physical = false;
1323 get_input_sources ();
1325 if (_source_port && _source_port->flags() & JackPortIsPhysical) {
1326 have_physical = true;
1329 if (have_physical) {
1330 set_align_style (ExistingMaterial);
1332 set_align_style (CaptureTime);
1338 MidiDiskstream::playback_buffer_load () const
1340 return (float) ((double) _playback_buf->read_space()/
1341 (double) _playback_buf->bufsize());
1345 MidiDiskstream::capture_buffer_load () const
1347 return (float) ((double) _capture_buf->write_space()/
1348 (double) _capture_buf->bufsize());
1353 MidiDiskstream::use_pending_capture_data (XMLNode& node)