2 Copyright (C) 2009-2016 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.
20 #include "ardour/analyser.h"
21 #include "ardour/audioengine.h"
22 #include "ardour/audiofilesource.h"
23 #include "ardour/audio_buffer.h"
24 #include "ardour/audioplaylist.h"
25 #include "ardour/audioregion.h"
26 #include "ardour/butler.h"
27 #include "ardour/debug.h"
28 #include "ardour/disk_writer.h"
29 #include "ardour/midi_playlist.h"
30 #include "ardour/midi_source.h"
31 #include "ardour/midi_track.h"
32 #include "ardour/port.h"
33 #include "ardour/region_factory.h"
34 #include "ardour/session.h"
35 #include "ardour/smf_source.h"
39 using namespace ARDOUR;
43 ARDOUR::samplecnt_t DiskWriter::_chunk_samples = DiskWriter::default_chunk_samples ();
44 PBD::Signal0<void> DiskWriter::Overrun;
46 DiskWriter::DiskWriter (Session& s, string const & str, DiskIOProcessor::Flag f)
47 : DiskIOProcessor (s, str, f)
50 , capture_start_sample (0)
51 , capture_captured (0)
52 , was_recording (false)
53 , first_recordable_sample (max_samplepos)
54 , last_recordable_sample (max_samplepos)
55 , last_possibly_recording (0)
56 , _alignment_style (ExistingMaterial)
57 , _num_captured_loops (0)
58 , _accumulated_capture_offset (0)
59 , _gui_feed_buffer(AudioEngine::instance()->raw_buffer_size (DataType::MIDI))
61 DiskIOProcessor::init ();
64 DiskWriter::~DiskWriter ()
66 DEBUG_TRACE (DEBUG::Destruction, string_compose ("DiskWriter %1 @ %2 deleted\n", _name, this));
68 boost::shared_ptr<ChannelList> c = channels.reader();
70 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
71 (*chan)->write_source.reset ();
76 DiskWriter::default_chunk_samples ()
82 DiskWriter::set_write_source_name (string const & str)
84 _write_source_name = str;
89 DiskWriter::check_record_status (samplepos_t transport_sample, double speed, bool can_record)
91 int possibly_recording;
94 const int transport_rolling = 0x4;
95 const int track_rec_enabled = 0x2;
96 const int global_rec_enabled = 0x1;
97 const int fully_rec_enabled = (transport_rolling|track_rec_enabled|global_rec_enabled);
99 /* merge together the 3 factors that affect record status, and compute what has changed. */
101 rolling = speed != 0.0f;
102 possibly_recording = (rolling << 2) | ((int)record_enabled() << 1) | (int)can_record;
103 change = possibly_recording ^ last_possibly_recording;
105 if (possibly_recording == last_possibly_recording) {
109 if (possibly_recording == fully_rec_enabled) {
111 if (last_possibly_recording == fully_rec_enabled) {
115 capture_start_sample = _session.transport_sample ();
116 first_recordable_sample = capture_start_sample;
118 if (_alignment_style == ExistingMaterial) {
119 first_recordable_sample += _capture_offset + _playback_offset;
122 last_recordable_sample = max_samplepos;
124 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1: @ %2 (STS: %3) CS:%4 FRS: %5 IL: %7, OL: %8 CO: %r9 PO: %10 WOL: %11 WIL: %12\n",
127 _session.transport_sample(),
128 capture_start_sample,
129 first_recordable_sample,
130 last_recordable_sample,
135 _session.worst_output_latency(),
136 _session.worst_input_latency()));
139 prepare_record_status (capture_start_sample);
143 if (last_possibly_recording == fully_rec_enabled) {
145 /* we were recording last time */
147 if (change & transport_rolling) {
149 /* transport-change (stopped rolling): last_recordable_sample was set in ::prepare_to_stop(). We
150 * had to set it there because we likely rolled past the stopping point to declick out,
151 * and then backed up.
157 last_recordable_sample = _session.transport_sample();
159 if (_alignment_style == ExistingMaterial) {
166 last_possibly_recording = possibly_recording;
170 DiskWriter::calculate_record_range (Evoral::OverlapType ot, samplepos_t transport_sample, samplecnt_t nframes, samplecnt_t & rec_nframes, samplecnt_t & rec_offset)
173 case Evoral::OverlapNone:
177 case Evoral::OverlapInternal:
178 /* ---------- recrange
181 rec_nframes = nframes;
185 case Evoral::OverlapStart:
186 /* |--------| recrange
189 rec_nframes = transport_sample + nframes - first_recordable_sample;
191 rec_offset = first_recordable_sample - transport_sample;
195 case Evoral::OverlapEnd:
196 /* |--------| recrange
197 * |-------- transrange
199 rec_nframes = last_recordable_sample - transport_sample;
203 case Evoral::OverlapExternal:
204 /* |--------| recrange
205 * -------------- transrange
207 rec_nframes = last_recordable_sample - first_recordable_sample;
208 rec_offset = first_recordable_sample - transport_sample;
212 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1 rec? %2 @ %3 (for %4) FRF %5 LRF %6 : rf %7 @ %8\n",
213 _name, enum_2_string (ot), transport_sample, nframes,
214 first_recordable_sample, last_recordable_sample, rec_nframes, rec_offset));
218 DiskWriter::engage_record_enable ()
220 g_atomic_int_set (&_record_enabled, 1);
224 DiskWriter::disengage_record_enable ()
226 g_atomic_int_set (&_record_enabled, 0);
230 DiskWriter::engage_record_safe ()
232 g_atomic_int_set (&_record_safe, 1);
236 DiskWriter::disengage_record_safe ()
238 g_atomic_int_set (&_record_safe, 0);
241 /** Get the start position (in session samples) of the nth capture in the current pass */
243 DiskWriter::get_capture_start_sample (uint32_t n) const
245 Glib::Threads::Mutex::Lock lm (capture_info_lock);
247 if (capture_info.size() > n) {
248 /* this is a completed capture */
249 return capture_info[n]->start;
251 /* this is the currently in-progress capture */
252 return capture_start_sample;
257 DiskWriter::get_captured_samples (uint32_t n) const
259 Glib::Threads::Mutex::Lock lm (capture_info_lock);
261 if (capture_info.size() > n) {
262 /* this is a completed capture */
263 return capture_info[n]->samples;
265 /* this is the currently in-progress capture */
266 return capture_captured;
271 DiskWriter::set_align_style (AlignStyle a, bool force)
273 if (record_enabled() && _session.actively_recording()) {
277 if ((a != _alignment_style) || force) {
278 _alignment_style = a;
279 AlignmentStyleChanged ();
284 DiskWriter::state (bool full)
286 XMLNode& node (DiskIOProcessor::state (full));
287 node.set_property (X_("type"), X_("diskwriter"));
288 node.set_property (X_("record-safe"), (_record_safe ? X_("yes" : "no")));
293 DiskWriter::set_state (const XMLNode& node, int version)
295 if (DiskIOProcessor::set_state (node, version)) {
299 if (!node.get_property (X_("record-safe"), _record_safe)) {
300 _record_safe = false;
303 reset_write_sources (false, true);
309 DiskWriter::non_realtime_locate (samplepos_t position)
311 if (_midi_write_source) {
312 _midi_write_source->set_timeline_position (position);
315 DiskIOProcessor::non_realtime_locate (position);
320 DiskWriter::prepare_record_status (samplepos_t capture_start_sample)
322 if (recordable() && destructive()) {
323 boost::shared_ptr<ChannelList> c = channels.reader ();
324 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
326 RingBufferNPT<CaptureTransition>::rw_vector transitions;
327 (*chan)->capture_transition_buf->get_write_vector (&transitions);
329 if (transitions.len[0] > 0) {
330 transitions.buf[0]->type = CaptureStart;
331 transitions.buf[0]->capture_val = capture_start_sample;
332 (*chan)->capture_transition_buf->increment_write_ptr(1);
335 fatal << X_("programming error: capture_transition_buf is full on rec start! inconceivable!")
343 /** Do some record stuff [not described in this comment!]
346 * - Setup playback_distance with the nframes, or nframes adjusted
347 * for current varispeed, if appropriate.
348 * - Setup current_playback_buffer in each ChannelInfo to point to data
349 * that someone can read playback_distance worth of data from.
352 DiskWriter::run (BufferSet& bufs, samplepos_t start_sample, samplepos_t end_sample,
353 double speed, pframes_t nframes, bool result_required)
355 if (!_active && !_pending_active) {
358 _active = _pending_active;
361 boost::shared_ptr<ChannelList> c = channels.reader();
362 ChannelList::iterator chan;
364 samplecnt_t rec_offset = 0;
365 samplecnt_t rec_nframes = 0;
366 bool nominally_recording;
368 bool re = record_enabled ();
369 bool can_record = _session.actively_recording ();
371 _need_butler = false;
374 if (speed != 0 && re) {
375 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1: run() start: %2 end: %3 NF: %4\n", _name, start_sample, end_sample, nframes));
379 check_record_status (start_sample, speed, can_record);
385 nominally_recording = (can_record && re);
387 // Safeguard against situations where process() goes haywire when autopunching
388 // and last_recordable_sample < first_recordable_sample
390 if (last_recordable_sample < first_recordable_sample) {
391 last_recordable_sample = max_samplepos;
394 const Location* const loop_loc = loop_location;
395 samplepos_t loop_start = 0;
396 samplepos_t loop_end = 0;
397 samplepos_t loop_length = 0;
400 get_location_times (loop_loc, &loop_start, &loop_end, &loop_length);
403 if (nominally_recording || (re && was_recording && _session.get_record_enabled() && (_session.config.get_punch_in() || _session.preroll_record_punch_enabled()))) {
405 Evoral::OverlapType ot = Evoral::coverage (first_recordable_sample, last_recordable_sample, start_sample, end_sample);
406 // XXX should this be transport_sample + nframes - 1 ? coverage() expects its parameter ranges to include their end points
407 // XXX also, first_recordable_sample & last_recordable_sample may both be == max_samplepos: coverage() will return OverlapNone in that case. Is thak OK?
408 calculate_record_range (ot, start_sample, nframes, rec_nframes, rec_offset);
410 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1: this time record %2 of %3 samples, offset %4\n", _name, rec_nframes, nframes, rec_offset));
412 if (rec_nframes && !was_recording) {
413 capture_captured = 0;
416 /* Loop recording, so pretend the capture started at the loop
417 start rgardless of what time it is now, so the source starts
418 at the loop start and can handle time wrapping around.
419 Otherwise, start the source right now as usual.
421 capture_captured = start_sample - loop_start;
422 capture_start_sample = loop_start;
425 if (_midi_write_source) {
426 _midi_write_source->mark_write_starting_now (capture_start_sample, capture_captured, loop_length);
429 g_atomic_int_set (const_cast<gint*> (&_samples_pending_write), 0);
430 g_atomic_int_set (const_cast<gint*> (&_num_captured_loops), 0);
432 was_recording = true;
436 /* For audio: not writing samples to the capture ringbuffer offsets
437 * the recording. For midi: we need to keep track of the record range
438 * and subtract the accumulated difference from the event time.
441 _accumulated_capture_offset += rec_offset;
443 _accumulated_capture_offset += nframes;
448 if (can_record && !_last_capture_sources.empty ()) {
449 _last_capture_sources.clear ();
456 const size_t n_buffers = bufs.count().n_audio();
458 for (chan = c->begin(), n = 0; chan != c->end(); ++chan, ++n) {
460 ChannelInfo* chaninfo (*chan);
461 AudioBuffer& buf (bufs.get_audio (n%n_buffers));
463 chaninfo->buf->get_write_vector (&chaninfo->rw_vector);
465 if (rec_nframes <= (samplecnt_t) chaninfo->rw_vector.len[0]) {
467 Sample *incoming = buf.data (rec_offset);
468 memcpy (chaninfo->rw_vector.buf[0], incoming, sizeof (Sample) * rec_nframes);
472 samplecnt_t total = chaninfo->rw_vector.len[0] + chaninfo->rw_vector.len[1];
474 if (rec_nframes > total) {
475 DEBUG_TRACE (DEBUG::Butler, string_compose ("%1 overrun in %2, rec_nframes = %3 total space = %4\n",
476 DEBUG_THREAD_SELF, name(), rec_nframes, total));
481 Sample *incoming = buf.data (rec_offset);
482 samplecnt_t first = chaninfo->rw_vector.len[0];
484 memcpy (chaninfo->rw_vector.buf[0], incoming, sizeof (Sample) * first);
485 memcpy (chaninfo->rw_vector.buf[1], incoming + first, sizeof (Sample) * (rec_nframes - first));
488 chaninfo->buf->increment_write_ptr (rec_nframes);
494 // Pump entire port buffer into the ring buffer (TODO: split cycles?)
495 MidiBuffer& buf = bufs.get_midi (0);
496 boost::shared_ptr<MidiTrack> mt = boost::dynamic_pointer_cast<MidiTrack>(_route);
497 MidiChannelFilter* filter = mt ? &mt->capture_filter() : 0;
499 for (MidiBuffer::iterator i = buf.begin(); i != buf.end(); ++i) {
500 Evoral::Event<MidiBuffer::TimeType> ev (*i, false);
501 if (ev.time() + rec_offset > rec_nframes) {
505 if (DEBUG_ENABLED(DEBUG::MidiIO)) {
506 const uint8_t* __data = ev.buffer();
508 DEBUG_STR_APPEND(a, string_compose ("mididiskstream %1 capture event @ %2 + %3 sz %4 ", this, ev.time(), start_sample, ev.size()));
509 for (size_t i=0; i < ev.size(); ++i) {
510 DEBUG_STR_APPEND(a,hex);
511 DEBUG_STR_APPEND(a,"0x");
512 DEBUG_STR_APPEND(a,(int)__data[i]);
513 DEBUG_STR_APPEND(a,' ');
515 DEBUG_STR_APPEND(a,'\n');
516 DEBUG_TRACE (DEBUG::MidiIO, DEBUG_STR(a).str());
519 /* Write events to the capture buffer in samples from session start,
520 but ignoring looping so event time progresses monotonically.
521 The source knows the loop length so it knows exactly where the
522 event occurs in the series of recorded loops and can implement
523 any desirable behaviour. We don't want to send event with
524 transport time here since that way the source can not
525 reconstruct their actual time; future clever MIDI looping should
526 probably be implemented in the source instead of here.
528 const samplecnt_t loop_offset = _num_captured_loops * loop_length;
529 const samplepos_t event_time = start_sample + loop_offset - _accumulated_capture_offset + ev.time();
530 if (event_time < 0 || event_time < first_recordable_sample) {
531 /* Event out of range, skip */
535 if (!filter || !filter->filter(ev.buffer(), ev.size())) {
536 _midi_buf->write (event_time, ev.event_type(), ev.size(), ev.buffer());
539 g_atomic_int_add (const_cast<gint*>(&_samples_pending_write), nframes);
541 if (buf.size() != 0) {
542 Glib::Threads::Mutex::Lock lm (_gui_feed_buffer_mutex, Glib::Threads::TRY_LOCK);
545 /* Copy this data into our GUI feed buffer and tell the GUI
546 that it can read it if it likes.
548 _gui_feed_buffer.clear ();
550 for (MidiBuffer::iterator i = buf.begin(); i != buf.end(); ++i) {
551 /* This may fail if buf is larger than _gui_feed_buffer, but it's not really
552 the end of the world if it does.
554 _gui_feed_buffer.push_back ((*i).time() + start_sample, (*i).size(), (*i).buffer());
558 DataRecorded (_midi_write_source); /* EMIT SIGNAL */
561 capture_captured += rec_nframes;
562 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("%1 now captured %2 (by %3)\n", name(), capture_captured, rec_nframes));
566 /* not recording this time, but perhaps we were before .. */
570 _accumulated_capture_offset = 0;
574 /* AUDIO BUTLER REQUIRED CODE */
576 if (_playlists[DataType::AUDIO] && !c->empty()) {
577 if (((samplecnt_t) c->front()->buf->read_space() >= _chunk_samples)) {
582 /* MIDI BUTLER REQUIRED CODE */
584 if (_playlists[DataType::MIDI] && (_midi_buf->read_space() < _midi_buf->bufsize() / 2)) {
588 // DEBUG_TRACE (DEBUG::Butler, string_compose ("%1 writer run, needs butler = %2\n", name(), _need_butler));
592 DiskWriter::finish_capture (boost::shared_ptr<ChannelList> c)
594 was_recording = false;
595 first_recordable_sample = max_samplepos;
596 last_recordable_sample = max_samplepos;
598 if (capture_captured == 0) {
602 if (recordable() && destructive()) {
603 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
605 RingBufferNPT<CaptureTransition>::rw_vector transvec;
606 (*chan)->capture_transition_buf->get_write_vector(&transvec);
608 if (transvec.len[0] > 0) {
609 transvec.buf[0]->type = CaptureEnd;
610 transvec.buf[0]->capture_val = capture_captured;
611 (*chan)->capture_transition_buf->increment_write_ptr(1);
615 fatal << string_compose (_("programmer error: %1"), X_("capture_transition_buf is full when stopping record! inconceivable!")) << endmsg;
621 CaptureInfo* ci = new CaptureInfo;
623 ci->start = capture_start_sample;
624 ci->samples = capture_captured;
626 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("Finish capture, add new CI, %1 + %2\n", ci->start, ci->samples));
628 /* XXX theoretical race condition here. Need atomic exchange ?
629 However, the circumstances when this is called right
630 now (either on record-disable or transport_stopped)
631 mean that no actual race exists. I think ...
632 We now have a capture_info_lock, but it is only to be used
633 to synchronize in the transport_stop and the capture info
634 accessors, so that invalidation will not occur (both non-realtime).
637 capture_info.push_back (ci);
638 capture_captured = 0;
640 /* now we've finished a capture, reset first_recordable_sample for next time */
641 first_recordable_sample = max_samplepos;
645 DiskWriter::set_record_enabled (bool yn)
647 if (!recordable() || !_session.record_enabling_legal() || record_safe ()) {
651 /* can't rec-enable in destructive mode if transport is before start */
653 if (destructive() && yn && _session.transport_sample() < _session.current_start_sample()) {
657 /* yes, i know that this not proof against race conditions, but its
658 good enough. i think.
661 if (record_enabled() != yn) {
663 engage_record_enable ();
665 disengage_record_enable ();
668 RecordEnableChanged (); /* EMIT SIGNAL */
673 DiskWriter::set_record_safe (bool yn)
675 if (!recordable() || !_session.record_enabling_legal() || channels.reader()->empty()) {
679 /* can't rec-safe in destructive mode if transport is before start ????
682 if (destructive() && yn && _session.transport_sample() < _session.current_start_sample()) {
686 /* yes, i know that this not proof against race conditions, but its
687 good enough. i think.
690 if (record_safe () != yn) {
692 engage_record_safe ();
694 disengage_record_safe ();
697 RecordSafeChanged (); /* EMIT SIGNAL */
702 DiskWriter::prep_record_enable ()
704 if (!recordable() || !_session.record_enabling_legal() || channels.reader()->empty() || record_safe ()) { // REQUIRES REVIEW "|| record_safe ()"
708 /* can't rec-enable in destructive mode if transport is before start */
710 if (destructive() && _session.transport_sample() < _session.current_start_sample()) {
714 boost::shared_ptr<ChannelList> c = channels.reader();
716 capturing_sources.clear ();
718 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
719 capturing_sources.push_back ((*chan)->write_source);
720 Source::Lock lock((*chan)->write_source->mutex());
721 (*chan)->write_source->mark_streaming_write_started (lock);
728 DiskWriter::prep_record_disable ()
730 capturing_sources.clear ();
735 DiskWriter::buffer_load () const
737 boost::shared_ptr<ChannelList> c = channels.reader();
743 return (float) ((double) c->front()->buf->write_space()/
744 (double) c->front()->buf->bufsize());
748 DiskWriter::set_note_mode (NoteMode m)
752 boost::shared_ptr<MidiPlaylist> mp = boost::dynamic_pointer_cast<MidiPlaylist> (_playlists[DataType::MIDI]);
755 mp->set_note_mode (m);
758 if (_midi_write_source && _midi_write_source->model())
759 _midi_write_source->model()->set_note_mode(m);
763 DiskWriter::seek (samplepos_t sample, bool complete_refill)
766 ChannelList::iterator chan;
767 boost::shared_ptr<ChannelList> c = channels.reader();
769 for (n = 0, chan = c->begin(); chan != c->end(); ++chan, ++n) {
770 (*chan)->buf->reset ();
774 g_atomic_int_set(&_samples_read_from_ringbuffer, 0);
775 g_atomic_int_set(&_samples_written_to_ringbuffer, 0);
777 /* can't rec-enable in destructive mode if transport is before start */
779 if (destructive() && record_enabled() && sample < _session.current_start_sample()) {
780 disengage_record_enable ();
783 playback_sample = sample;
789 DiskWriter::do_flush (RunContext ctxt, bool force_flush)
793 RingBufferNPT<Sample>::rw_vector vector;
794 RingBufferNPT<CaptureTransition>::rw_vector transvec;
802 boost::shared_ptr<ChannelList> c = channels.reader();
803 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
805 (*chan)->buf->get_read_vector (&vector);
807 total = vector.len[0] + vector.len[1];
809 if (total == 0 || (total < _chunk_samples && !force_flush && was_recording)) {
813 /* if there are 2+ chunks of disk i/o possible for
814 this track, let the caller know so that it can arrange
815 for us to be called again, ASAP.
817 if we are forcing a flush, then if there is* any* extra
818 work, let the caller know.
820 if we are no longer recording and there is any extra work,
821 let the caller know too.
824 if (total >= 2 * _chunk_samples || ((force_flush || !was_recording) && total > _chunk_samples)) {
828 to_write = min (_chunk_samples, (samplecnt_t) vector.len[0]);
830 // check the transition buffer when recording destructive
831 // important that we get this after the capture buf
834 (*chan)->capture_transition_buf->get_read_vector(&transvec);
835 size_t transcount = transvec.len[0] + transvec.len[1];
838 for (ti=0; ti < transcount; ++ti) {
839 CaptureTransition & captrans = (ti < transvec.len[0]) ? transvec.buf[0][ti] : transvec.buf[1][ti-transvec.len[0]];
841 if (captrans.type == CaptureStart) {
842 // by definition, the first data we got above represents the given capture pos
844 (*chan)->write_source->mark_capture_start (captrans.capture_val);
845 (*chan)->curr_capture_cnt = 0;
847 } else if (captrans.type == CaptureEnd) {
849 // capture end, the capture_val represents total samples in capture
851 if (captrans.capture_val <= (*chan)->curr_capture_cnt + to_write) {
853 // shorten to make the write a perfect fit
854 uint32_t nto_write = (captrans.capture_val - (*chan)->curr_capture_cnt);
856 if (nto_write < to_write) {
857 ret = 1; // should we?
859 to_write = nto_write;
861 (*chan)->write_source->mark_capture_end ();
863 // increment past this transition, but go no further
868 // actually ends just beyond this chunk, so force more work
876 (*chan)->capture_transition_buf->increment_read_ptr(ti);
880 if ((!(*chan)->write_source) || (*chan)->write_source->write (vector.buf[0], to_write) != to_write) {
881 error << string_compose(_("AudioDiskstream %1: cannot write to disk"), id()) << endmsg;
885 (*chan)->buf->increment_read_ptr (to_write);
886 (*chan)->curr_capture_cnt += to_write;
888 if ((to_write == vector.len[0]) && (total > to_write) && (to_write < _chunk_samples) && !destructive()) {
890 /* we wrote all of vector.len[0] but it wasn't an entire
891 disk_write_chunk_samples of data, so arrange for some part
892 of vector.len[1] to be flushed to disk as well.
895 to_write = min ((samplecnt_t)(_chunk_samples - to_write), (samplecnt_t) vector.len[1]);
897 DEBUG_TRACE (DEBUG::Butler, string_compose ("%1 additional write of %2\n", name(), to_write));
899 if ((*chan)->write_source->write (vector.buf[1], to_write) != to_write) {
900 error << string_compose(_("AudioDiskstream %1: cannot write to disk"), id()) << endmsg;
904 (*chan)->buf->increment_read_ptr (to_write);
905 (*chan)->curr_capture_cnt += to_write;
911 if (_midi_write_source) {
913 const samplecnt_t total = g_atomic_int_get(const_cast<gint*> (&_samples_pending_write));
916 _midi_buf->read_space() == 0 ||
917 (!force_flush && (total < _chunk_samples) && was_recording)) {
921 /* if there are 2+ chunks of disk i/o possible for
922 this track), let the caller know so that it can arrange
923 for us to be called again, ASAP.
925 if we are forcing a flush, then if there is* any* extra
926 work, let the caller know.
928 if we are no longer recording and there is any extra work,
929 let the caller know too.
932 if (total >= 2 * _chunk_samples || ((force_flush || !was_recording) && total > _chunk_samples)) {
937 /* push out everything we have, right now */
938 to_write = UINT32_MAX;
940 to_write = _chunk_samples;
943 if (record_enabled() && ((total > _chunk_samples) || force_flush)) {
944 Source::Lock lm(_midi_write_source->mutex());
945 if (_midi_write_source->midi_write (lm, *_midi_buf, get_capture_start_sample (0), to_write) != to_write) {
946 error << string_compose(_("MidiDiskstream %1: cannot write to disk"), id()) << endmsg;
949 g_atomic_int_add(const_cast<gint*> (&_samples_pending_write), -to_write);
959 DiskWriter::reset_write_sources (bool mark_write_complete, bool /*force*/)
961 ChannelList::iterator chan;
962 boost::shared_ptr<ChannelList> c = channels.reader();
965 if (!_session.writable() || !recordable()) {
969 capturing_sources.clear ();
971 for (chan = c->begin(), n = 0; chan != c->end(); ++chan, ++n) {
973 if (!destructive()) {
975 if ((*chan)->write_source) {
977 if (mark_write_complete) {
978 Source::Lock lock((*chan)->write_source->mutex());
979 (*chan)->write_source->mark_streaming_write_completed (lock);
980 (*chan)->write_source->done_with_peakfile_writes ();
983 if ((*chan)->write_source->removable()) {
984 (*chan)->write_source->mark_for_remove ();
985 (*chan)->write_source->drop_references ();
988 (*chan)->write_source.reset ();
991 use_new_write_source (DataType::AUDIO, n);
993 if (record_enabled()) {
994 capturing_sources.push_back ((*chan)->write_source);
999 if ((*chan)->write_source == 0) {
1000 use_new_write_source (DataType::AUDIO, n);
1005 if (_midi_write_source) {
1006 if (mark_write_complete) {
1007 Source::Lock lm(_midi_write_source->mutex());
1008 _midi_write_source->mark_streaming_write_completed (lm);
1012 if (_playlists[DataType::MIDI]) {
1013 use_new_write_source (DataType::MIDI);
1016 if (destructive() && !c->empty ()) {
1018 /* we now have all our write sources set up, so create the
1019 playlist's single region.
1022 if (_playlists[DataType::MIDI]->empty()) {
1023 setup_destructive_playlist ();
1029 DiskWriter::use_new_write_source (DataType dt, uint32_t n)
1031 if (dt == DataType::MIDI) {
1033 _accumulated_capture_offset = 0;
1034 _midi_write_source.reset();
1037 _midi_write_source = boost::dynamic_pointer_cast<SMFSource>(
1038 _session.create_midi_source_for_session (write_source_name ()));
1040 if (!_midi_write_source) {
1041 throw failed_constructor();
1045 catch (failed_constructor &err) {
1046 error << string_compose (_("%1:%2 new capture file not initialized correctly"), _name, n) << endmsg;
1047 _midi_write_source.reset();
1051 boost::shared_ptr<ChannelList> c = channels.reader();
1053 if (!recordable()) {
1057 if (n >= c->size()) {
1058 error << string_compose (_("AudioDiskstream: channel %1 out of range"), n) << endmsg;
1062 ChannelInfo* chan = (*c)[n];
1065 if ((chan->write_source = _session.create_audio_source_for_session (
1066 c->size(), write_source_name(), n, destructive())) == 0) {
1067 throw failed_constructor();
1071 catch (failed_constructor &err) {
1072 error << string_compose (_("%1:%2 new capture file not initialized correctly"), _name, n) << endmsg;
1073 chan->write_source.reset ();
1077 /* do not remove destructive files even if they are empty */
1079 chan->write_source->set_allow_remove_if_empty (!destructive());
1086 DiskWriter::transport_stopped_wallclock (struct tm& when, time_t twhen, bool abort_capture)
1088 bool more_work = true;
1090 samplecnt_t total_capture;
1091 SourceList audio_srcs;
1092 SourceList midi_srcs;
1093 ChannelList::iterator chan;
1094 vector<CaptureInfo*>::iterator ci;
1095 boost::shared_ptr<ChannelList> c = channels.reader();
1097 bool mark_write_completed = false;
1102 /* butler is already stopped, but there may be work to do
1103 to flush remaining data to disk.
1106 while (more_work && !err) {
1107 switch (do_flush (TransportContext, true)) {
1114 error << string_compose(_("AudioDiskstream \"%1\": cannot flush captured data to disk!"), _name) << endmsg;
1119 /* XXX is there anything we can do if err != 0 ? */
1120 Glib::Threads::Mutex::Lock lm (capture_info_lock);
1122 if (capture_info.empty()) {
1126 if (abort_capture) {
1128 if (destructive()) {
1132 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
1134 if ((*chan)->write_source) {
1136 (*chan)->write_source->mark_for_remove ();
1137 (*chan)->write_source->drop_references ();
1138 (*chan)->write_source.reset ();
1141 /* new source set up in "out" below */
1144 if (_midi_write_source) {
1145 _midi_write_source->mark_for_remove ();
1146 _midi_write_source->drop_references ();
1147 _midi_write_source.reset();
1153 for (total_capture = 0, ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1154 total_capture += (*ci)->samples;
1157 /* figure out the name for this take */
1159 for (n = 0, chan = c->begin(); chan != c->end(); ++chan, ++n) {
1161 boost::shared_ptr<AudioFileSource> as = (*chan)->write_source;
1164 audio_srcs.push_back (as);
1165 as->update_header (capture_info.front()->start, when, twhen);
1166 as->set_captured_for (_name.val());
1167 as->mark_immutable ();
1169 if (Config->get_auto_analyse_audio()) {
1170 Analyser::queue_source_for_analysis (as, true);
1173 DEBUG_TRACE (DEBUG::CaptureAlignment, string_compose ("newly captured source %1 length %2\n", as->path(), as->length (0)));
1176 if (_midi_write_source) {
1177 midi_srcs.push_back (_midi_write_source);
1184 if (_midi_write_source) {
1186 if (_midi_write_source->length (capture_info.front()->start) == 0) {
1187 /* No data was recorded, so this capture will
1188 effectively be aborted; do the same as we
1189 do for an explicit abort.
1191 if (_midi_write_source) {
1192 _midi_write_source->mark_for_remove ();
1193 _midi_write_source->drop_references ();
1194 _midi_write_source.reset();
1200 /* phew, we have data */
1202 Source::Lock source_lock(_midi_write_source->mutex());
1204 /* figure out the name for this take */
1206 midi_srcs.push_back (_midi_write_source);
1208 _midi_write_source->set_timeline_position (capture_info.front()->start);
1209 _midi_write_source->set_captured_for (_name);
1211 /* set length in beats to entire capture length */
1213 BeatsSamplesConverter converter (_session.tempo_map(), capture_info.front()->start);
1214 const Temporal::Beats total_capture_beats = converter.from (total_capture);
1215 _midi_write_source->set_length_beats (total_capture_beats);
1217 /* flush to disk: this step differs from the audio path,
1218 where all the data is already on disk.
1221 _midi_write_source->mark_midi_streaming_write_completed (source_lock, Evoral::Sequence<Temporal::Beats>::ResolveStuckNotes, total_capture_beats);
1224 _last_capture_sources.insert (_last_capture_sources.end(), audio_srcs.begin(), audio_srcs.end());
1225 _last_capture_sources.insert (_last_capture_sources.end(), midi_srcs.begin(), midi_srcs.end());
1229 _route->use_captured_sources (audio_srcs, capture_info);
1230 _route->use_captured_sources (midi_srcs, capture_info);
1233 mark_write_completed = true;
1236 reset_write_sources (mark_write_completed);
1240 for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1244 capture_info.clear ();
1245 capture_start_sample = 0;
1249 DiskWriter::transport_looped (samplepos_t transport_sample)
1251 if (was_recording) {
1252 // all we need to do is finish this capture, with modified capture length
1253 boost::shared_ptr<ChannelList> c = channels.reader();
1257 // the next region will start recording via the normal mechanism
1258 // we'll set the start position to the current transport pos
1259 // no latency adjustment or capture offset needs to be made, as that already happened the first time
1260 capture_start_sample = transport_sample;
1261 first_recordable_sample = transport_sample; // mild lie
1262 last_recordable_sample = max_samplepos;
1263 was_recording = true;
1265 if (recordable() && destructive()) {
1266 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
1268 RingBufferNPT<CaptureTransition>::rw_vector transvec;
1269 (*chan)->capture_transition_buf->get_write_vector(&transvec);
1271 if (transvec.len[0] > 0) {
1272 transvec.buf[0]->type = CaptureStart;
1273 transvec.buf[0]->capture_val = capture_start_sample;
1274 (*chan)->capture_transition_buf->increment_write_ptr(1);
1278 fatal << X_("programming error: capture_transition_buf is full on rec loop! inconceivable!")
1286 /* Here we only keep track of the number of captured loops so monotonic
1287 event times can be delivered to the write source in process(). Trying
1288 to be clever here is a world of trouble, it is better to simply record
1289 the input in a straightforward non-destructive way. In the future when
1290 we want to implement more clever MIDI looping modes it should be done in
1291 the Source and/or entirely after the capture is finished.
1293 if (was_recording) {
1294 g_atomic_int_add(const_cast<gint*> (&_num_captured_loops), 1);
1299 DiskWriter::setup_destructive_playlist ()
1302 boost::shared_ptr<ChannelList> c = channels.reader();
1304 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
1305 srcs.push_back ((*chan)->write_source);
1308 /* a single full-sized region */
1310 assert (!srcs.empty ());
1313 plist.add (Properties::name, _name.val());
1314 plist.add (Properties::start, 0);
1315 plist.add (Properties::length, max_samplepos - srcs.front()->natural_position());
1317 boost::shared_ptr<Region> region (RegionFactory::create (srcs, plist));
1318 _playlists[DataType::AUDIO]->add_region (region, srcs.front()->natural_position());
1320 /* apply region properties and update write sources */
1321 use_destructive_playlist();
1325 DiskWriter::use_destructive_playlist ()
1327 /* this is called from the XML-based constructor or ::set_destructive. when called,
1328 we already have a playlist and a region, but we need to
1329 set up our sources for write. we use the sources associated
1330 with the (presumed single, full-extent) region.
1333 boost::shared_ptr<Region> rp;
1335 const RegionList& rl (_playlists[DataType::AUDIO]->region_list_property().rlist());
1336 if (rl.size() > 0) {
1337 /* this can happen when dragging a region onto a tape track */
1338 assert((rl.size() == 1));
1344 reset_write_sources (false, true);
1348 boost::shared_ptr<AudioRegion> region = boost::dynamic_pointer_cast<AudioRegion> (rp);
1351 throw failed_constructor();
1354 /* be sure to stretch the region out to the maximum length (non-musical)*/
1356 region->set_length (max_samplepos - region->position(), 0);
1359 ChannelList::iterator chan;
1360 boost::shared_ptr<ChannelList> c = channels.reader();
1362 for (n = 0, chan = c->begin(); chan != c->end(); ++chan, ++n) {
1363 (*chan)->write_source = boost::dynamic_pointer_cast<AudioFileSource>(region->source (n));
1364 assert((*chan)->write_source);
1365 (*chan)->write_source->set_allow_remove_if_empty (false);
1367 /* this might be false if we switched modes, so force it */
1369 #ifdef XXX_OLD_DESTRUCTIVE_API_XXX
1370 (*chan)->write_source->set_destructive (true);
1372 // should be set when creating the source or loading the state
1373 assert ((*chan)->write_source->destructive());
1377 /* the source list will never be reset for a destructive track */
1381 DiskWriter::adjust_buffering ()
1383 boost::shared_ptr<ChannelList> c = channels.reader();
1385 for (ChannelList::iterator chan = c->begin(); chan != c->end(); ++chan) {
1386 (*chan)->resize (_session.butler()->audio_diskstream_capture_buffer_size());
1391 DiskWriter::realtime_handle_transport_stopped ()
1393 realtime_speed_change ();
1397 DiskWriter::set_name (string const & str)
1399 string my_name = X_("recorder:");
1402 if (_name != my_name) {
1403 SessionObject::set_name (my_name);
1410 DiskWriter::steal_write_source_name ()
1412 if (_playlists[DataType::MIDI]) {
1413 string our_old_name = _midi_write_source->name();
1415 /* this will bump the name of the current write source to the next one
1416 * (e.g. "MIDI 1-1" gets renamed to "MIDI 1-2"), thus leaving the
1417 * current write source name (e.g. "MIDI 1-1" available). See the
1418 * comments in Session::create_midi_source_by_stealing_name() about why
1423 string new_path = _session.new_midi_source_path (name());
1425 if (_midi_write_source->rename (new_path)) {
1432 return our_old_name;
1435 return std::string();
1439 DiskWriter::configure_io (ChanCount in, ChanCount out)
1441 if (!DiskIOProcessor::configure_io (in, out)) {
1445 reset_write_sources (false, true);