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.
34 #include <pbd/error.h>
35 #include <pbd/basename.h>
36 #include <pbd/lockmonitor.h>
37 #include <pbd/xml++.h>
39 #include <ardour/ardour.h>
40 #include <ardour/audioengine.h>
41 #include <ardour/diskstream.h>
42 #include <ardour/utils.h>
43 #include <ardour/configuration.h>
44 #include <ardour/filesource.h>
45 #include <ardour/send.h>
46 #include <ardour/audioplaylist.h>
47 #include <ardour/cycle_timer.h>
48 #include <ardour/audioregion.h>
54 using namespace ARDOUR;
56 jack_nframes_t DiskStream::disk_io_chunk_frames;
58 sigc::signal<void,DiskStream*> DiskStream::DiskStreamCreated;
59 sigc::signal<void,DiskStream*> DiskStream::CannotRecordNoInput;
60 sigc::signal<void,list<Source*>*> DiskStream::DeleteSources;
61 sigc::signal<void> DiskStream::DiskOverrun;
62 sigc::signal<void> DiskStream::DiskUnderrun;
64 DiskStream::DiskStream (Session &sess, const string &name, Flag flag)
68 /* prevent any write sources from being created */
75 DiskStreamCreated (this); /* EMIT SIGNAL */
78 DiskStream::DiskStream (Session& sess, const XMLNode& node)
85 if (set_state (node)) {
87 throw failed_constructor();
92 DiskStreamCreated (this); /* EMIT SIGNAL */
96 DiskStream::init_channel (ChannelInfo &chan)
98 chan.playback_wrap_buffer = 0;
99 chan.capture_wrap_buffer = 0;
100 chan.speed_buffer = 0;
101 chan.peak_power = 0.0f;
102 chan.fades_source = 0;
103 chan.write_source = 0;
105 chan.current_capture_buffer = 0;
106 chan.current_playback_buffer = 0;
108 chan.playback_buf = new RingBufferNPT<Sample> (_session.diskstream_buffer_size());
109 chan.capture_buf = new RingBufferNPT<Sample> (_session.diskstream_buffer_size());
111 /* touch the ringbuffer buffers, which will cause
112 them to be mapped into locked physical RAM if
113 we're running with mlockall(). this doesn't do
116 memset (chan.playback_buf->buffer(), 0, sizeof (Sample) * chan.playback_buf->bufsize());
117 memset (chan.capture_buf->buffer(), 0, sizeof (Sample) * chan.capture_buf->bufsize());
122 DiskStream::init (Flag f)
128 _alignment_style = ExistingMaterial;
129 _persistent_alignment_style = ExistingMaterial;
130 first_input_change = true;
132 i_am_the_modifier = 0;
133 atomic_set (&_record_enabled, 0);
134 was_recording = false;
135 capture_start_frame = 0;
136 capture_captured = 0;
137 _visible_speed = 1.0f;
138 _actual_speed = 1.0f;
139 _buffer_reallocation_required = false;
140 _seek_required = false;
141 first_recordable_frame = max_frames;
142 last_recordable_frame = max_frames;
147 adjust_capture_position = 0;
148 last_possibly_recording = 0;
150 wrap_buffer_size = 0;
151 speed_buffer_size = 0;
153 phi = (uint64_t) (0x1000000);
156 playback_distance = 0;
157 _read_data_count = 0;
158 _write_data_count = 0;
159 deprecated_io_node = 0;
161 /* there are no channels at this point, so these
162 two calls just get speed_buffer_size and wrap_buffer
163 size setup without duplicating their code.
166 set_block_size (_session.get_block_size());
167 allocate_temporary_buffers ();
169 pending_overwrite = false;
171 overwrite_queued = false;
172 input_change_pending = NoChange;
179 DiskStream::destroy_channel (ChannelInfo &chan)
181 if (chan.write_source) {
182 chan.write_source->release ();
183 chan.write_source = 0;
186 if (chan.speed_buffer) {
187 delete [] chan.speed_buffer;
190 if (chan.playback_wrap_buffer) {
191 delete [] chan.playback_wrap_buffer;
193 if (chan.capture_wrap_buffer) {
194 delete [] chan.capture_wrap_buffer;
197 delete chan.playback_buf;
198 delete chan.capture_buf;
200 chan.playback_buf = 0;
201 chan.capture_buf = 0;
204 DiskStream::~DiskStream ()
206 LockMonitor lm (state_lock, __LINE__, __FILE__);
212 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
213 destroy_channel((*chan));
220 DiskStream::handle_input_change (IOChange change, void *src)
222 LockMonitor lm (state_lock, __LINE__, __FILE__);
224 if (!(input_change_pending & change)) {
225 input_change_pending = IOChange (input_change_pending|change);
226 _session.request_input_change_handling ();
231 DiskStream::non_realtime_input_change ()
234 LockMonitor lm (state_lock, __LINE__, __FILE__);
236 if (input_change_pending == NoChange) {
240 if (input_change_pending & ConfigurationChanged) {
242 if (_io->n_inputs() > _n_channels) {
244 // we need to add new channel infos
246 int diff = _io->n_inputs() - channels.size();
248 for (int i = 0; i < diff; ++i) {
252 } else if (_io->n_inputs() < _n_channels) {
254 // we need to get rid of channels
256 int diff = channels.size() - _io->n_inputs();
258 for (int i = 0; i < diff; ++i) {
264 get_input_sources ();
265 set_capture_offset ();
267 if (first_input_change) {
268 set_align_style (_persistent_alignment_style);
269 first_input_change = false;
271 set_align_style_from_io ();
274 input_change_pending = NoChange;
277 /* reset capture files */
279 reset_write_sources (false);
281 /* now refill channel buffers */
283 if (speed() != 1.0f || speed() != -1.0f) {
284 seek ((jack_nframes_t) (_session.transport_frame() * (double) speed()));
287 seek (_session.transport_frame());
292 DiskStream::get_input_sources ()
294 uint32_t ni = _io->n_inputs();
296 for (uint32_t n = 0; n < ni; ++n) {
298 const char **connections = _io->input(n)->get_connections ();
299 ChannelInfo& chan = channels[n];
301 if (connections == 0 || connections[0] == 0) {
304 // _source->disable_metering ();
310 chan.source = _session.engine().get_port_by_name (connections[0]);
320 DiskStream::find_and_use_playlist (const string& name)
323 AudioPlaylist* playlist;
325 if ((pl = _session.get_playlist (name)) == 0) {
326 error << string_compose(_("DiskStream: Session doesn't know about a Playlist called \"%1\""), name) << endmsg;
330 if ((playlist = dynamic_cast<AudioPlaylist*> (pl)) == 0) {
331 error << string_compose(_("DiskStream: Playlist \"%1\" isn't an audio playlist"), name) << endmsg;
335 return use_playlist (playlist);
339 DiskStream::use_playlist (AudioPlaylist* playlist)
342 LockMonitor lm (state_lock, __LINE__, __FILE__);
344 if (playlist == _playlist) {
348 plstate_connection.disconnect();
349 plmod_connection.disconnect ();
350 plgone_connection.disconnect ();
356 _playlist = playlist;
359 if (!in_set_state && recordable()) {
360 reset_write_sources (false);
363 plstate_connection = _playlist->StateChanged.connect (mem_fun (*this, &DiskStream::playlist_changed));
364 plmod_connection = _playlist->Modified.connect (mem_fun (*this, &DiskStream::playlist_modified));
365 plgone_connection = _playlist->GoingAway.connect (mem_fun (*this, &DiskStream::playlist_deleted));
368 if (!overwrite_queued) {
369 _session.request_overwrite_buffer (this);
370 overwrite_queued = true;
373 PlaylistChanged (); /* EMIT SIGNAL */
374 _session.set_dirty ();
380 DiskStream::playlist_deleted (Playlist* pl)
382 /* this catches an ordering issue with session destruction. playlists
383 are destroyed before diskstreams. we have to invalidate any handles
384 we have to the playlist.
391 DiskStream::use_new_playlist ()
394 AudioPlaylist* playlist;
397 newname = Playlist::bump_name (_playlist->name(), _session);
399 newname = Playlist::bump_name (_name, _session);
402 if ((playlist = new AudioPlaylist (_session, newname, hidden())) != 0) {
403 playlist->set_orig_diskstream_id (id());
404 return use_playlist (playlist);
411 DiskStream::use_copy_playlist ()
413 if (_playlist == 0) {
414 error << string_compose(_("DiskStream %1: there is no existing playlist to make a copy of!"), _name) << endmsg;
419 AudioPlaylist* playlist;
421 newname = Playlist::bump_name (_playlist->name(), _session);
423 if ((playlist = new AudioPlaylist (*_playlist, newname)) != 0) {
424 playlist->set_orig_diskstream_id (id());
425 return use_playlist (playlist);
432 DiskStream::set_io (IO& io)
435 set_align_style_from_io ();
439 DiskStream::set_name (string str, void *src)
442 _playlist->set_name (str);
445 if (!in_set_state && recordable()) {
447 /* open new capture files so that they have the correct name */
449 reset_write_sources (false);
455 DiskStream::set_speed (double sp)
457 _session.request_diskstream_speed (*this, sp);
459 /* to force a rebuffering at the right place */
464 DiskStream::realtime_set_speed (double sp, bool global)
466 bool changed = false;
467 double new_speed = sp * _session.transport_speed();
469 if (_visible_speed != sp) {
474 if (new_speed != _actual_speed) {
476 jack_nframes_t required_wrap_size = (jack_nframes_t) floor (_session.get_block_size() *
477 fabs (new_speed)) + 1;
479 if (required_wrap_size > wrap_buffer_size) {
480 _buffer_reallocation_required = true;
483 _actual_speed = new_speed;
484 phi = (uint64_t) (0x1000000 * fabs(_actual_speed));
489 _seek_required = true;
491 speed_changed (); /* EMIT SIGNAL */
494 return _buffer_reallocation_required || _seek_required;
498 DiskStream::non_realtime_set_speed ()
500 if (_buffer_reallocation_required)
502 LockMonitor lm (state_lock, __LINE__, __FILE__);
503 allocate_temporary_buffers ();
505 _buffer_reallocation_required = false;
508 if (_seek_required) {
509 if (speed() != 1.0f || speed() != -1.0f) {
510 seek ((jack_nframes_t) (_session.transport_frame() * (double) speed()), true);
513 seek (_session.transport_frame(), true);
516 _seek_required = false;
521 DiskStream::prepare ()
524 playback_distance = 0;
528 DiskStream::check_record_status (jack_nframes_t transport_frame, jack_nframes_t nframes, bool can_record)
530 int possibly_recording;
533 const int transport_rolling = 0x4;
534 const int track_rec_enabled = 0x2;
535 const int global_rec_enabled = 0x1;
537 /* merge together the 3 factors that affect record status, and compute
541 rolling = _session.transport_speed() != 0.0f;
542 possibly_recording = (rolling << 2) | (record_enabled() << 1) | can_record;
543 change = possibly_recording ^ last_possibly_recording;
545 if (possibly_recording == last_possibly_recording) {
551 /* if per-track or global rec-enable turned on while the other was already on, we've started recording */
553 if ((change & track_rec_enabled) && record_enabled() && (!(change & global_rec_enabled) && can_record) ||
554 ((change & global_rec_enabled) && can_record && (!(change & track_rec_enabled) && record_enabled()))) {
556 /* starting to record: compute first+last frames */
558 first_recordable_frame = transport_frame + _capture_offset;
559 last_recordable_frame = max_frames;
560 capture_start_frame = transport_frame;
562 if (!(last_possibly_recording & transport_rolling) && (possibly_recording & transport_rolling)) {
564 /* was stopped, now rolling (and recording) */
566 if (_alignment_style == ExistingMaterial) {
567 first_recordable_frame += _session.worst_output_latency();
569 first_recordable_frame += _roll_delay;
574 /* was rolling, but record state changed */
576 if (_alignment_style == ExistingMaterial) {
579 if (!_session.get_punch_in()) {
581 /* manual punch in happens at the correct transport frame
582 because the user hit a button. but to get alignment correct
583 we have to back up the position of the new region to the
584 appropriate spot given the roll delay.
587 capture_start_frame -= _roll_delay;
589 /* XXX paul notes (august 2005): i don't know why
593 first_recordable_frame += _capture_offset;
597 /* autopunch toggles recording at the precise
598 transport frame, and then the DS waits
599 to start recording for a time that depends
600 on the output latency.
603 first_recordable_frame += _session.worst_output_latency();
608 if (_session.get_punch_in()) {
609 first_recordable_frame += _roll_delay;
611 capture_start_frame -= _roll_delay;
617 } else if (!record_enabled() || !can_record) {
621 last_recordable_frame = transport_frame + _capture_offset;
623 if (_alignment_style == ExistingMaterial) {
624 last_recordable_frame += _session.worst_output_latency();
626 last_recordable_frame += _roll_delay;
630 last_possibly_recording = possibly_recording;
634 DiskStream::process (jack_nframes_t transport_frame, jack_nframes_t nframes, jack_nframes_t offset, bool can_record, bool rec_monitors_input)
637 ChannelList::iterator c;
639 jack_nframes_t rec_offset = 0;
640 jack_nframes_t rec_nframes = 0;
641 bool nominally_recording;
642 bool re = record_enabled ();
643 bool collect_playback = false;
645 /* if we've already processed the frames corresponding to this call,
646 just return. this allows multiple routes that are taking input
647 from this diskstream to call our ::process() method, but have
648 this stuff only happen once. more commonly, it allows both
649 the AudioTrack that is using this DiskStream *and* the Session
650 to call process() without problems.
657 check_record_status (transport_frame, nframes, can_record);
659 nominally_recording = (can_record && re);
666 /* This lock is held until the end of DiskStream::commit, so these two functions
667 must always be called as a pair. The only exception is if this function
668 returns a non-zero value, in which case, ::commit should not be called.
671 if (pthread_mutex_trylock (state_lock.mutex())) {
675 adjust_capture_position = 0;
677 for (c = channels.begin(); c != channels.end(); ++c) {
678 (*c).current_capture_buffer = 0;
679 (*c).current_playback_buffer = 0;
682 if (nominally_recording || (_session.get_record_enabled() && _session.get_punch_in())) {
685 ot = coverage (first_recordable_frame, last_recordable_frame, transport_frame, transport_frame + nframes);
692 case OverlapInternal:
693 /* ---------- recrange
696 rec_nframes = nframes;
701 /* |--------| recrange
704 rec_nframes = transport_frame + nframes - first_recordable_frame;
706 rec_offset = first_recordable_frame - transport_frame;
711 /* |--------| recrange
714 rec_nframes = last_recordable_frame - transport_frame;
718 case OverlapExternal:
719 /* |--------| recrange
720 -------------- transrange
722 rec_nframes = last_recordable_frame - last_recordable_frame;
723 rec_offset = first_recordable_frame - transport_frame;
727 if (rec_nframes && !was_recording) {
728 capture_captured = 0;
729 was_recording = true;
734 if (can_record && !_last_capture_regions.empty()) {
735 _last_capture_regions.clear ();
738 if (nominally_recording || rec_nframes) {
740 for (n = 0, c = channels.begin(); c != channels.end(); ++c, ++n) {
742 ChannelInfo& chan (*c);
744 chan.capture_buf->get_write_vector (&chan.capture_vector);
746 if (rec_nframes <= chan.capture_vector.len[0]) {
748 chan.current_capture_buffer = chan.capture_vector.buf[0];
750 /* note: grab the entire port buffer, but only copy what we were supposed to for recording, and use
754 memcpy (chan.current_capture_buffer, _io->input(n)->get_buffer (rec_nframes) + offset + rec_offset, sizeof (Sample) * rec_nframes);
758 jack_nframes_t total = chan.capture_vector.len[0] + chan.capture_vector.len[1];
760 if (rec_nframes > total) {
765 Sample* buf = _io->input (n)->get_buffer (nframes) + offset;
766 jack_nframes_t first = chan.capture_vector.len[0];
768 memcpy (chan.capture_wrap_buffer, buf, sizeof (Sample) * first);
769 memcpy (chan.capture_vector.buf[0], buf, sizeof (Sample) * first);
770 memcpy (chan.capture_wrap_buffer+first, buf + first, sizeof (Sample) * (rec_nframes - first));
771 memcpy (chan.capture_vector.buf[1], buf + first, sizeof (Sample) * (rec_nframes - first));
773 chan.current_capture_buffer = chan.capture_wrap_buffer;
780 finish_capture (rec_monitors_input);
787 /* data will be written to disk */
789 if (rec_nframes == nframes && rec_offset == 0) {
791 for (c = channels.begin(); c != channels.end(); ++c) {
792 (*c).current_playback_buffer = (*c).current_capture_buffer;
795 playback_distance = nframes;
800 /* we can't use the capture buffer as the playback buffer, because
801 we recorded only a part of the current process' cycle data
805 collect_playback = true;
808 adjust_capture_position = rec_nframes;
810 } else if (nominally_recording) {
812 /* can't do actual capture yet - waiting for latency effects to finish before we start*/
814 for (c = channels.begin(); c != channels.end(); ++c) {
815 (*c).current_playback_buffer = (*c).current_capture_buffer;
818 playback_distance = nframes;
822 collect_playback = true;
825 if (collect_playback) {
827 /* we're doing playback */
829 jack_nframes_t necessary_samples;
831 /* no varispeed playback if we're recording, because the output .... TBD */
833 if (rec_nframes == 0 && _actual_speed != 1.0f) {
834 necessary_samples = (jack_nframes_t) floor ((nframes * fabs (_actual_speed))) + 1;
836 necessary_samples = nframes;
839 for (c = channels.begin(); c != channels.end(); ++c) {
840 (*c).playback_buf->get_read_vector (&(*c).playback_vector);
845 for (c = channels.begin(); c != channels.end(); ++c, ++n) {
847 ChannelInfo& chan (*c);
849 if (necessary_samples <= chan.playback_vector.len[0]) {
851 chan.current_playback_buffer = chan.playback_vector.buf[0];
854 jack_nframes_t total = chan.playback_vector.len[0] + chan.playback_vector.len[1];
856 if (necessary_samples > total) {
862 memcpy ((char *) chan.playback_wrap_buffer, chan.playback_vector.buf[0],
863 chan.playback_vector.len[0] * sizeof (Sample));
864 memcpy (chan.playback_wrap_buffer + chan.playback_vector.len[0], chan.playback_vector.buf[1],
865 (necessary_samples - chan.playback_vector.len[0]) * sizeof (Sample));
867 chan.current_playback_buffer = chan.playback_wrap_buffer;
872 if (rec_nframes == 0 && _actual_speed != 1.0f && _actual_speed != -1.0f) {
874 uint64_t phase = last_phase;
875 jack_nframes_t i = 0;
877 // Linearly interpolate into the alt buffer
878 // using 40.24 fixp maths (swh)
880 for (c = channels.begin(); c != channels.end(); ++c) {
883 ChannelInfo& chan (*c);
888 for (jack_nframes_t outsample = 0; outsample < nframes; ++outsample) {
890 fr = (phase & 0xFFFFFF) / 16777216.0f;
891 chan.speed_buffer[outsample] =
892 chan.current_playback_buffer[i] * (1.0f - fr) +
893 chan.current_playback_buffer[i+1] * fr;
897 chan.current_playback_buffer = chan.speed_buffer;
900 playback_distance = i + 1;
901 last_phase = (phase & 0xFFFFFF);
904 playback_distance = nframes;
916 /* we're exiting with failure, so ::commit will not
917 be called. unlock the state lock.
920 pthread_mutex_unlock (state_lock.mutex());
927 DiskStream::recover ()
929 pthread_mutex_unlock (state_lock.mutex());
934 DiskStream::commit (jack_nframes_t nframes)
936 bool need_butler = false;
938 if (_actual_speed < 0.0) {
939 playback_sample -= playback_distance;
941 playback_sample += playback_distance;
944 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
946 (*chan).playback_buf->increment_read_ptr (playback_distance);
948 if (adjust_capture_position) {
949 (*chan).capture_buf->increment_write_ptr (adjust_capture_position);
953 if (adjust_capture_position != 0) {
954 capture_captured += adjust_capture_position;
955 adjust_capture_position = 0;
959 need_butler = channels[0].playback_buf->write_space() >= channels[0].playback_buf->bufsize() / 2;
961 need_butler = channels[0].playback_buf->write_space() >= disk_io_chunk_frames
962 || channels[0].capture_buf->read_space() >= disk_io_chunk_frames;
965 pthread_mutex_unlock (state_lock.mutex());
973 DiskStream::set_pending_overwrite (bool yn)
975 /* called from audio thread, so we can use the read ptr and playback sample as we wish */
977 pending_overwrite = yn;
979 overwrite_frame = playback_sample;
980 overwrite_offset = channels.front().playback_buf->get_read_ptr();
984 DiskStream::overwrite_existing_buffers ()
986 Sample* mixdown_buffer;
989 bool reversed = (_visible_speed * _session.transport_speed()) < 0.0f;
991 overwrite_queued = false;
993 /* assume all are the same size */
994 jack_nframes_t size = channels[0].playback_buf->bufsize();
996 mixdown_buffer = new Sample[size];
997 gain_buffer = new float[size];
999 /* reduce size so that we can fill the buffer correctly. */
1003 jack_nframes_t start;
1005 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan, ++n) {
1007 start = overwrite_frame;
1008 jack_nframes_t cnt = size;
1010 /* to fill the buffer without resetting the playback sample, we need to
1011 do it one or two chunks (normally two).
1013 |----------------------------------------------------------------------|
1017 |<- second chunk->||<----------------- first chunk ------------------>|
1021 jack_nframes_t to_read = size - overwrite_offset;
1023 if (read ((*chan).playback_buf->buffer() + overwrite_offset, mixdown_buffer, gain_buffer,
1024 start, to_read, *chan, n, reversed)) {
1025 error << string_compose(_("DiskStream %1: when refilling, cannot read %2 from playlist at frame %3"),
1026 _id, size, playback_sample) << endmsg;
1030 if (cnt > to_read) {
1034 if (read ((*chan).playback_buf->buffer(), mixdown_buffer, gain_buffer,
1035 start, cnt, *chan, n, reversed)) {
1036 error << string_compose(_("DiskStream %1: when refilling, cannot read %2 from playlist at frame %3"),
1037 _id, size, playback_sample) << endmsg;
1046 pending_overwrite = false;
1047 delete [] gain_buffer;
1048 delete [] mixdown_buffer;
1053 DiskStream::seek (jack_nframes_t frame, bool complete_refill)
1055 LockMonitor lm (state_lock, __LINE__, __FILE__);
1058 ChannelList::iterator chan;
1060 for (n = 0, chan = channels.begin(); chan != channels.end(); ++chan, ++n) {
1061 (*chan).playback_buf->reset ();
1062 (*chan).capture_buf->reset ();
1065 playback_sample = frame;
1068 if (complete_refill) {
1069 while ((ret = do_refill (0, 0)) > 0);
1071 ret = do_refill (0, 0);
1078 DiskStream::can_internal_playback_seek (jack_nframes_t distance)
1080 ChannelList::iterator chan;
1082 for (chan = channels.begin(); chan != channels.end(); ++chan) {
1083 if ((*chan).playback_buf->read_space() < distance) {
1091 DiskStream::internal_playback_seek (jack_nframes_t distance)
1093 ChannelList::iterator chan;
1095 for (chan = channels.begin(); chan != channels.end(); ++chan) {
1096 (*chan).playback_buf->increment_read_ptr (distance);
1099 first_recordable_frame += distance;
1100 playback_sample += distance;
1106 DiskStream::read (Sample* buf, Sample* mixdown_buffer, float* gain_buffer, jack_nframes_t& start, jack_nframes_t cnt,
1108 ChannelInfo& channel_info, int channel, bool reversed)
1110 jack_nframes_t this_read = 0;
1111 bool reloop = false;
1112 jack_nframes_t loop_end = 0;
1113 jack_nframes_t loop_start = 0;
1114 jack_nframes_t loop_length = 0;
1115 jack_nframes_t offset = 0;
1119 /* Make the use of a Location atomic for this read operation.
1121 Note: Locations don't get deleted, so all we care about
1122 when I say "atomic" is that we are always pointing to
1123 the same one and using a start/length values obtained
1127 if ((loc = loop_location) != 0) {
1128 loop_start = loc->start();
1129 loop_end = loc->end();
1130 loop_length = loop_end - loop_start;
1133 /* if we are looping, ensure that the first frame we read is at the correct
1134 position within the loop.
1137 if (loc && start >= loop_end) {
1138 //cerr << "start adjusted from " << start;
1139 start = loop_start + ((start - loop_start) % loop_length);
1140 //cerr << "to " << start << endl;
1142 //cerr << "start is " << start << " loopstart: " << loop_start << " loopend: " << loop_end << endl;
1147 /* take any loop into account. we can't read past the end of the loop. */
1149 if (loc && (loop_end - start < cnt)) {
1150 this_read = loop_end - start;
1151 //cerr << "reloop true: thisread: " << this_read << " cnt: " << cnt << endl;
1158 if (this_read == 0) {
1162 this_read = min(cnt,this_read);
1164 if (_playlist->read (buf+offset, mixdown_buffer, gain_buffer, start, this_read, channel) != this_read) {
1165 error << string_compose(_("DiskStream %1: cannot read %2 from playlist at frame %3"), _id, this_read,
1170 _read_data_count = _playlist->read_data_count();
1174 /* don't adjust start, since caller has already done that
1177 swap_by_ptr (buf, buf + this_read - 1);
1181 /* if we read to the end of the loop, go back to the beginning */
1191 offset += this_read;
1198 DiskStream::do_refill (Sample* mixdown_buffer, float* gain_buffer)
1201 jack_nframes_t to_read;
1202 RingBufferNPT<Sample>::rw_vector vector;
1205 bool reversed = (_visible_speed * _session.transport_speed()) < 0.0f;
1206 jack_nframes_t total_space;
1207 jack_nframes_t zero_fill;
1209 ChannelList::iterator i;
1212 channels.front().playback_buf->get_write_vector (&vector);
1214 if ((total_space = vector.len[0] + vector.len[1]) == 0) {
1218 /* if there are 2+ chunks of disk i/o possible for
1219 this track, let the caller know so that it can arrange
1220 for us to be called again, ASAP.
1223 if (total_space >= (_slaved?3:2) * disk_io_chunk_frames) {
1227 /* if we're running close to normal speed and there isn't enough
1228 space to do disk_io_chunk_frames of I/O, then don't bother.
1230 at higher speeds, just do it because the sync between butler
1231 and audio thread may not be good enough.
1234 if ((total_space < disk_io_chunk_frames) && fabs (_actual_speed) < 2.0f) {
1238 /* when slaved, don't try to get too close to the read pointer. this
1239 leaves space for the buffer reversal to have something useful to
1243 if (_slaved && total_space < (channels.front().playback_buf->bufsize() / 2)) {
1247 total_space = min (disk_io_chunk_frames, total_space);
1251 if (file_frame == 0) {
1253 /* at start: nothing to do but fill with silence */
1255 for (chan_n = 0, i = channels.begin(); i != channels.end(); ++i, ++chan_n) {
1257 ChannelInfo& chan (*i);
1258 chan.playback_buf->get_write_vector (&vector);
1259 memset (vector.buf[0], 0, sizeof(Sample) * vector.len[0]);
1260 if (vector.len[1]) {
1261 memset (vector.buf[1], 0, sizeof(Sample) * vector.len[1]);
1263 chan.playback_buf->increment_write_ptr (vector.len[0] + vector.len[1]);
1268 if (file_frame < total_space) {
1270 /* too close to the start: read what we can,
1271 and then zero fill the rest
1274 zero_fill = total_space - file_frame;
1275 total_space = file_frame;
1280 /* move read position backwards because we are going
1281 to reverse the data.
1284 file_frame -= total_space;
1290 if (file_frame == max_frames) {
1292 /* at end: nothing to do but fill with silence */
1294 for (chan_n = 0, i = channels.begin(); i != channels.end(); ++i, ++chan_n) {
1296 ChannelInfo& chan (*i);
1297 chan.playback_buf->get_write_vector (&vector);
1298 memset (vector.buf[0], 0, sizeof(Sample) * vector.len[0]);
1299 if (vector.len[1]) {
1300 memset (vector.buf[1], 0, sizeof(Sample) * vector.len[1]);
1302 chan.playback_buf->increment_write_ptr (vector.len[0] + vector.len[1]);
1307 if (file_frame > max_frames - total_space) {
1309 /* to close to the end: read what we can, and zero fill the rest */
1311 zero_fill = total_space - (max_frames - file_frame);
1312 total_space = max_frames - file_frame;
1319 /* Please note: the code to allocate buffers isn't run
1320 during normal butler thread operation. Its there
1321 for other times when we need to call do_refill()
1322 from somewhere other than the butler thread.
1325 if (mixdown_buffer == 0) {
1326 mixdown_buffer = new Sample[disk_io_chunk_frames];
1327 free_mixdown = true;
1329 free_mixdown = false;
1332 if (gain_buffer == 0) {
1333 gain_buffer = new float[disk_io_chunk_frames];
1339 jack_nframes_t file_frame_tmp = 0;
1341 for (chan_n = 0, i = channels.begin(); i != channels.end(); ++i, ++chan_n) {
1343 ChannelInfo& chan (*i);
1346 jack_nframes_t len1, len2;
1348 chan.playback_buf->get_write_vector (&vector);
1351 file_frame_tmp = file_frame;
1354 buf1 = vector.buf[1];
1355 len1 = vector.len[1];
1356 buf2 = vector.buf[0];
1357 len2 = vector.len[0];
1359 buf1 = vector.buf[0];
1360 len1 = vector.len[0];
1361 buf2 = vector.buf[1];
1362 len2 = vector.len[1];
1366 to_read = min (ts, len1);
1367 to_read = min (to_read, disk_io_chunk_frames);
1371 if (read (buf1, mixdown_buffer, gain_buffer, file_frame_tmp, to_read, chan, chan_n, reversed)) {
1376 chan.playback_buf->increment_write_ptr (to_read);
1380 to_read = min (ts, len2);
1385 /* we read all of vector.len[0], but it wasn't an entire disk_io_chunk_frames of data,
1386 so read some or all of vector.len[1] as well.
1389 if (read (buf2, mixdown_buffer, gain_buffer, file_frame_tmp, to_read, chan, chan_n, reversed)) {
1394 chan.playback_buf->increment_write_ptr (to_read);
1403 file_frame = file_frame_tmp;
1407 delete [] mixdown_buffer;
1410 delete [] gain_buffer;
1417 DiskStream::do_flush (bool force_flush)
1421 RingBufferNPT<Sample>::rw_vector vector;
1422 jack_nframes_t total;
1424 /* important note: this function will write *AT MOST*
1425 disk_io_chunk_frames of data to disk. it will never
1426 write more than that. if its writes that much and there
1427 is more than that waiting to be written, it will return 1,
1428 otherwise 0 on success or -1 on failure.
1430 if there is less than disk_io_chunk_frames to be written,
1431 no data will be written at all unless `force_flush' is true.
1434 _write_data_count = 0;
1436 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
1438 (*chan).capture_buf->get_read_vector (&vector);
1440 total = vector.len[0] + vector.len[1];
1442 if (total == 0 || (total < disk_io_chunk_frames && !force_flush && was_recording)) {
1446 /* if there are 2+ chunks of disk i/o possible for
1447 this track, let the caller know so that it can arrange
1448 for us to be called again, ASAP.
1450 if we are forcing a flush, then if there is* any* extra
1451 work, let the caller know.
1453 if we are no longer recording and there is any extra work,
1454 let the caller know too.
1457 if (total >= 2 * disk_io_chunk_frames || ((force_flush || !was_recording) && total > disk_io_chunk_frames)) {
1461 to_write = min (disk_io_chunk_frames, (jack_nframes_t) vector.len[0]);
1463 if ((!(*chan).write_source) || (*chan).write_source->write (vector.buf[0], to_write) != to_write) {
1464 error << string_compose(_("DiskStream %1: cannot write to disk"), _id) << endmsg;
1468 (*chan).capture_buf->increment_read_ptr (to_write);
1470 if ((to_write == vector.len[0]) && (total > to_write) && (to_write < disk_io_chunk_frames)) {
1472 /* we wrote all of vector.len[0] but it wasn't an entire
1473 disk_io_chunk_frames of data, so arrange for some part
1474 of vector.len[1] to be flushed to disk as well.
1477 to_write = min ((jack_nframes_t)(disk_io_chunk_frames - to_write), (jack_nframes_t) vector.len[1]);
1479 if ((*chan).write_source->write (vector.buf[1], to_write) != to_write) {
1480 error << string_compose(_("DiskStream %1: cannot write to disk"), _id) << endmsg;
1484 _write_data_count += (*chan).write_source->write_data_count();
1486 (*chan).capture_buf->increment_read_ptr (to_write);
1495 DiskStream::playlist_changed (Change ignored)
1497 playlist_modified ();
1501 DiskStream::playlist_modified ()
1503 if (!i_am_the_modifier && !overwrite_queued) {
1504 _session.request_overwrite_buffer (this);
1505 overwrite_queued = true;
1510 DiskStream::transport_stopped (struct tm& when, time_t twhen, bool abort_capture)
1512 uint32_t buffer_position;
1513 bool more_work = true;
1515 AudioRegion* region = 0;
1516 jack_nframes_t total_capture;
1517 AudioRegion::SourceList srcs;
1518 AudioRegion::SourceList::iterator src;
1519 ChannelList::iterator chan;
1520 vector<CaptureInfo*>::iterator ci;
1522 list<Source*>* deletion_list;
1523 bool mark_write_completed = false;
1525 finish_capture (true);
1527 /* butler is already stopped, but there may be work to do
1528 to flush remaining data to disk.
1531 while (more_work && !err) {
1532 switch (do_flush (true)) {
1539 error << string_compose(_("DiskStream \"%1\": cannot flush captured data to disk!"), _name) << endmsg;
1544 /* XXX is there anything we can do if err != 0 ? */
1545 LockMonitor lm (capture_info_lock, __LINE__, __FILE__);
1547 if (capture_info.empty()) {
1551 if (abort_capture) {
1553 ChannelList::iterator chan;
1555 deletion_list = new list<Source*>;
1557 for ( chan = channels.begin(); chan != channels.end(); ++chan) {
1559 if ((*chan).write_source) {
1561 (*chan).write_source->mark_for_remove ();
1562 (*chan).write_source->release ();
1564 deletion_list->push_back ((*chan).write_source);
1566 (*chan).write_source = 0;
1569 /* new source set up in "out" below */
1572 if (!deletion_list->empty()) {
1573 DeleteSources (deletion_list);
1575 delete deletion_list;
1581 for (total_capture = 0, ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1582 total_capture += (*ci)->frames;
1585 /* figure out the name for this take */
1587 for (n = 0, chan = channels.begin(); chan != channels.end(); ++chan, ++n) {
1589 Source* s = (*chan).write_source;
1597 if ((fsrc = dynamic_cast<FileSource *>(s)) != 0) {
1598 fsrc->update_header (capture_info.front()->start, when, twhen);
1601 s->set_captured_for (_name);
1606 /* Register a new region with the Session that
1607 describes the entire source. Do this first
1608 so that any sub-regions will obviously be
1609 children of this one (later!)
1613 region = new AudioRegion (srcs, 0, total_capture,
1614 region_name_from_path (channels[0].write_source->name()),
1615 0, AudioRegion::Flag (AudioRegion::DefaultFlags|AudioRegion::Automatic|AudioRegion::WholeFile));
1617 region->special_set_position (capture_info.front()->start);
1620 catch (failed_constructor& err) {
1621 error << string_compose(_("%1: could not create region for complete audio file"), _name) << endmsg;
1625 _last_capture_regions.push_back (region);
1627 // cerr << _name << ": there are " << capture_info.size() << " capture_info records\n";
1629 _session.add_undo (_playlist->get_memento());
1630 _playlist->freeze ();
1632 for (buffer_position = 0, ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1635 _session.region_name (region_name, _name, false);
1637 // cerr << _name << ": based on ci of " << (*ci)->start << " for " << (*ci)->frames << " add a region\n";
1640 region = new AudioRegion (srcs, buffer_position, (*ci)->frames, region_name);
1643 catch (failed_constructor& err) {
1644 error << _("DiskStream: could not create region for captured audio!") << endmsg;
1645 continue; /* XXX is this OK? */
1648 _last_capture_regions.push_back (region);
1650 // cerr << "add new region, buffer position = " << buffer_position << " @ " << (*ci)->start << endl;
1652 i_am_the_modifier++;
1653 _playlist->add_region (*region, (*ci)->start);
1654 i_am_the_modifier--;
1656 buffer_position += (*ci)->frames;
1660 _session.add_redo_no_execute (_playlist->get_memento());
1662 mark_write_completed = true;
1664 reset_write_sources (mark_write_completed);
1667 for (ci = capture_info.begin(); ci != capture_info.end(); ++ci) {
1671 capture_info.clear ();
1672 capture_start_frame = 0;
1676 DiskStream::finish_capture (bool rec_monitors_input)
1678 was_recording = false;
1680 if (capture_captured == 0) {
1684 CaptureInfo* ci = new CaptureInfo;
1686 ci->start = capture_start_frame;
1687 ci->frames = capture_captured;
1689 /* XXX theoretical race condition here. Need atomic exchange ?
1690 However, the circumstances when this is called right
1691 now (either on record-disable or transport_stopped)
1692 mean that no actual race exists. I think ...
1693 We now have a capture_info_lock, but it is only to be used
1694 to synchronize in the transport_stop and the capture info
1695 accessors, so that invalidation will not occur (both non-realtime).
1698 // cerr << "Finish capture, add new CI, " << ci->start << '+' << ci->frames << endl;
1700 capture_info.push_back (ci);
1701 capture_captured = 0;
1705 DiskStream::set_record_enabled (bool yn, void* src)
1707 bool rolling = _session.transport_speed() != 0.0f;
1709 if (!recordable() || !_session.record_enabling_legal()) {
1713 /* if we're turning on rec-enable, there needs to be an
1717 if (yn && channels[0].source == 0) {
1719 /* pick up connections not initiated *from* the IO object
1720 we're associated with.
1723 get_input_sources ();
1725 if (channels[0].source == 0) {
1728 CannotRecordNoInput (this); /* emit signal */
1734 /* yes, i know that this not proof against race conditions, but its
1735 good enough. i think.
1738 if (record_enabled() != yn) {
1740 atomic_set (&_record_enabled, 1);
1741 capturing_sources.clear ();
1742 if (Config->get_use_hardware_monitoring()) {
1743 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
1744 if ((*chan).source) {
1745 (*chan).source->request_monitor_input (!(_session.get_auto_input() && rolling));
1747 capturing_sources.push_back ((*chan).write_source);
1750 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
1751 capturing_sources.push_back ((*chan).write_source);
1756 atomic_set (&_record_enabled, 0);
1757 if (Config->get_use_hardware_monitoring()) {
1758 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
1759 if ((*chan).source) {
1760 (*chan).source->request_monitor_input (false);
1764 capturing_sources.clear ();
1767 record_enable_changed (src); /* EMIT SIGNAL */
1772 DiskStream::get_state ()
1774 XMLNode* node = new XMLNode ("DiskStream");
1776 LocaleGuard lg (X_("POSIX"));
1778 snprintf (buf, sizeof(buf), "%zd", channels.size());
1779 node->add_property ("channels", buf);
1781 node->add_property ("playlist", _playlist->name());
1783 snprintf (buf, sizeof(buf), "%f", _visible_speed);
1784 node->add_property ("speed", buf);
1786 node->add_property("name", _name);
1787 snprintf (buf, sizeof(buf), "%" PRIu64, id());
1788 node->add_property("id", buf);
1790 if (!capturing_sources.empty() && _session.get_record_enabled()) {
1792 XMLNode* cs_child = new XMLNode (X_("CapturingSources"));
1793 XMLNode* cs_grandchild;
1795 for (vector<FileSource*>::iterator i = capturing_sources.begin(); i != capturing_sources.end(); ++i) {
1796 cs_grandchild = new XMLNode (X_("file"));
1797 cs_grandchild->add_property (X_("path"), (*i)->path());
1798 cs_child->add_child_nocopy (*cs_grandchild);
1801 /* store the location where capture will start */
1805 if (_session.get_punch_in() && ((pi = _session.locations()->auto_punch_location()) != 0)) {
1806 snprintf (buf, sizeof (buf), "%" PRIu32, pi->start());
1808 snprintf (buf, sizeof (buf), "%" PRIu32, _session.transport_frame());
1811 cs_child->add_property (X_("at"), buf);
1812 node->add_child_nocopy (*cs_child);
1816 node->add_child_copy (*_extra_xml);
1823 DiskStream::set_state (const XMLNode& node)
1825 const XMLProperty* prop;
1826 XMLNodeList nlist = node.children();
1827 XMLNodeIterator niter;
1828 uint32_t nchans = 1;
1829 XMLNode* capture_pending_node = 0;
1830 LocaleGuard lg (X_("POSIX"));
1832 in_set_state = true;
1834 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
1835 if ((*niter)->name() == IO::state_node_name) {
1836 deprecated_io_node = new XMLNode (**niter);
1839 if ((*niter)->name() == X_("CapturingSources")) {
1840 capture_pending_node = *niter;
1844 /* prevent write sources from being created */
1846 in_set_state = true;
1848 if ((prop = node.property ("name")) != 0) {
1849 _name = prop->value();
1852 if (deprecated_io_node) {
1853 if ((prop = deprecated_io_node->property ("id")) != 0) {
1854 sscanf (prop->value().c_str(), "%" PRIu64, &_id);
1857 if ((prop = node.property ("id")) != 0) {
1858 sscanf (prop->value().c_str(), "%" PRIu64, &_id);
1862 if ((prop = node.property ("channels")) != 0) {
1863 nchans = atoi (prop->value().c_str());
1866 // create necessary extra channels
1867 // we are always constructed with one
1868 // and we always need one
1870 if (nchans > _n_channels) {
1872 // we need to add new channel infos
1873 //LockMonitor lm (state_lock, __LINE__, __FILE__);
1875 int diff = nchans - channels.size();
1877 for (int i=0; i < diff; ++i) {
1881 } else if (nchans < _n_channels) {
1883 // we need to get rid of channels
1884 //LockMonitor lm (state_lock, __LINE__, __FILE__);
1886 int diff = channels.size() - nchans;
1888 for (int i = 0; i < diff; ++i) {
1893 if ((prop = node.property ("playlist")) == 0) {
1898 bool had_playlist = (_playlist != 0);
1900 if (find_and_use_playlist (prop->value())) {
1904 if (!had_playlist) {
1905 _playlist->set_orig_diskstream_id (_id);
1908 if (capture_pending_node) {
1909 use_pending_capture_data (*capture_pending_node);
1914 if ((prop = node.property ("speed")) != 0) {
1915 double sp = atof (prop->value().c_str());
1917 if (realtime_set_speed (sp, false)) {
1918 non_realtime_set_speed ();
1922 _n_channels = channels.size();
1924 in_set_state = false;
1926 /* now that we're all done with playlist+channel set up,
1927 go ahead and create write sources.
1931 capturing_sources.clear ();
1934 reset_write_sources (false);
1937 in_set_state = false;
1943 DiskStream::use_new_write_source (uint32_t n)
1945 if (!recordable()) {
1949 if (n >= channels.size()) {
1950 error << string_compose (_("DiskStream: channel %1 out of range"), n) << endmsg;
1954 ChannelInfo &chan = channels[n];
1956 if (chan.write_source) {
1958 if (FileSource::is_empty (chan.write_source->path())) {
1959 chan.write_source->mark_for_remove ();
1960 chan.write_source->release();
1961 delete chan.write_source;
1963 chan.write_source->release();
1964 chan.write_source = 0;
1969 if ((chan.write_source = _session.create_file_source (*this, n)) == 0) {
1970 throw failed_constructor();
1974 catch (failed_constructor &err) {
1975 error << string_compose (_("%1:%2 new capture file not initialized correctly"), _name, n) << endmsg;
1976 chan.write_source = 0;
1980 chan.write_source->use ();
1986 DiskStream::reset_write_sources (bool mark_write_complete)
1988 ChannelList::iterator chan;
1991 if (!recordable()) {
1995 capturing_sources.clear ();
1997 for (chan = channels.begin(), n = 0; chan != channels.end(); ++chan, ++n) {
1998 if (mark_write_complete) {
1999 (*chan).write_source->mark_streaming_write_completed ();
2001 use_new_write_source (n);
2002 if (record_enabled()) {
2003 capturing_sources.push_back ((*chan).write_source);
2009 DiskStream::set_block_size (jack_nframes_t nframes)
2011 if (_session.get_block_size() > speed_buffer_size) {
2012 speed_buffer_size = _session.get_block_size();
2014 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
2015 if ((*chan).speed_buffer) delete [] (*chan).speed_buffer;
2016 (*chan).speed_buffer = new Sample[speed_buffer_size];
2019 allocate_temporary_buffers ();
2023 DiskStream::allocate_temporary_buffers ()
2025 /* make sure the wrap buffer is at least large enough to deal
2026 with the speeds up to 1.2, to allow for micro-variation
2027 when slaving to MTC, SMPTE etc.
2030 double sp = max (fabsf (_actual_speed), 1.2f);
2031 jack_nframes_t required_wrap_size = (jack_nframes_t) floor (_session.get_block_size() * sp) + 1;
2033 if (required_wrap_size > wrap_buffer_size) {
2035 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
2036 if ((*chan).playback_wrap_buffer) delete [] (*chan).playback_wrap_buffer;
2037 (*chan).playback_wrap_buffer = new Sample[required_wrap_size];
2038 if ((*chan).capture_wrap_buffer) delete [] (*chan).capture_wrap_buffer;
2039 (*chan).capture_wrap_buffer = new Sample[required_wrap_size];
2042 wrap_buffer_size = required_wrap_size;
2047 DiskStream::monitor_input (bool yn)
2049 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
2051 if ((*chan).source) {
2052 (*chan).source->request_monitor_input (yn);
2058 DiskStream::set_capture_offset ()
2061 /* can't capture, so forget it */
2065 _capture_offset = _io->input_latency();
2069 DiskStream::set_persistent_align_style (AlignStyle a)
2071 _persistent_alignment_style = a;
2075 DiskStream::set_align_style_from_io ()
2077 bool have_physical = false;
2083 get_input_sources ();
2085 for (ChannelList::iterator chan = channels.begin(); chan != channels.end(); ++chan) {
2086 if ((*chan).source && (*chan).source->flags() & JackPortIsPhysical) {
2087 have_physical = true;
2092 if (have_physical) {
2093 set_align_style (ExistingMaterial);
2095 set_align_style (CaptureTime);
2100 DiskStream::set_align_style (AlignStyle a)
2102 if (record_enabled() && _session.actively_recording()) {
2107 if (a != _alignment_style) {
2108 _alignment_style = a;
2109 AlignmentStyleChanged ();
2114 DiskStream::add_channel ()
2116 /* XXX need to take lock??? */
2120 init_channel (chan);
2122 chan.speed_buffer = new Sample[speed_buffer_size];
2123 chan.playback_wrap_buffer = new Sample[wrap_buffer_size];
2124 chan.capture_wrap_buffer = new Sample[wrap_buffer_size];
2126 channels.push_back (chan);
2128 _n_channels = channels.size();
2134 DiskStream::remove_channel ()
2136 if (channels.size() > 1) {
2137 /* XXX need to take lock??? */
2138 ChannelInfo & chan = channels.back();
2139 destroy_channel (chan);
2140 channels.pop_back();
2142 _n_channels = channels.size();
2150 DiskStream::playback_buffer_load () const
2152 return (float) ((double) channels.front().playback_buf->read_space()/
2153 (double) channels.front().playback_buf->bufsize());
2157 DiskStream::capture_buffer_load () const
2159 return (float) ((double) channels.front().capture_buf->write_space()/
2160 (double) channels.front().capture_buf->bufsize());
2164 DiskStream::set_loop (Location *location)
2167 if (location->start() >= location->end()) {
2168 error << string_compose(_("Location \"%1\" not valid for track loop (start >= end)"), location->name()) << endl;
2173 loop_location = location;
2175 LoopSet (location); /* EMIT SIGNAL */
2180 DiskStream::get_capture_start_frame (uint32_t n)
2182 LockMonitor lm (capture_info_lock, __LINE__, __FILE__);
2184 if (capture_info.size() > n) {
2185 return capture_info[n]->start;
2188 return capture_start_frame;
2193 DiskStream::get_captured_frames (uint32_t n)
2195 LockMonitor lm (capture_info_lock, __LINE__, __FILE__);
2197 if (capture_info.size() > n) {
2198 return capture_info[n]->frames;
2201 return capture_captured;
2206 DiskStream::punch_in ()
2211 DiskStream::punch_out ()
2216 DiskStream::use_pending_capture_data (XMLNode& node)
2218 const XMLProperty* prop;
2219 XMLNodeList nlist = node.children();
2220 XMLNodeIterator niter;
2222 FileSource* first_fs = 0;
2223 AudioRegion::SourceList pending_sources;
2224 jack_nframes_t position;
2226 if ((prop = node.property (X_("at"))) == 0) {
2230 if (sscanf (prop->value().c_str(), "%" PRIu32, &position) != 1) {
2234 for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
2235 if ((*niter)->name() == X_("file")) {
2237 if ((prop = (*niter)->property (X_("path"))) == 0) {
2242 fs = new FileSource (prop->value(), _session.frame_rate(), true);
2245 catch (failed_constructor& err) {
2246 error << string_compose (_("%1: cannot restore pending capture source file %2"),
2247 _name, prop->value())
2252 pending_sources.push_back (fs);
2254 if (first_fs == 0) {
2258 fs->set_captured_for (_name);
2262 if (pending_sources.size() == 0) {
2263 /* nothing can be done */
2267 if (pending_sources.size() != _n_channels) {
2268 error << string_compose (_("%1: incorrect number of pending sources listed - ignoring them all"), _name)
2273 AudioRegion* region;
2276 region = new AudioRegion (pending_sources, 0, first_fs->length(),
2277 region_name_from_path (first_fs->name()),
2278 0, AudioRegion::Flag (AudioRegion::DefaultFlags|AudioRegion::Automatic|AudioRegion::WholeFile));
2280 region->special_set_position (0);
2283 catch (failed_constructor& err) {
2284 error << string_compose (_("%1: cannot create whole-file region from pending capture sources"),
2292 region = new AudioRegion (pending_sources, 0, first_fs->length(), region_name_from_path (first_fs->name()));
2295 catch (failed_constructor& err) {
2296 error << string_compose (_("%1: cannot create region from pending capture sources"),
2303 _playlist->add_region (*region, position);
2309 DiskStream::set_roll_delay (jack_nframes_t nframes)
2311 _roll_delay = nframes;