ca74176a16f8014f7b3f4b4df2c749c2f7b9c95a
[ardour.git] / libs / ardour / audio_track.cc
1 /*
2     Copyright (C) 2002 Paul Davis 
3
4     This program is free software; you can redistribute it and/or modify
5     it under the terms of the GNU General Public License as published by
6     the Free Software Foundation; either version 2 of the License, or
7     (at your option) any later version.
8
9     This program is distributed in the hope that it will be useful,
10     but WITHOUT ANY WARRANTY; without even the implied warranty of
11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12     GNU General Public License for more details.
13
14     You should have received a copy of the GNU General Public License
15     along with this program; if not, write to the Free Software
16     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17
18 */
19
20 #include <sigc++/retype.h>
21 #include <sigc++/retype_return.h>
22 #include <sigc++/bind.h>
23
24 #include <pbd/error.h>
25 #include <pbd/enumwriter.h>
26
27 #include <ardour/audio_track.h>
28 #include <ardour/audio_diskstream.h>
29 #include <ardour/session.h>
30 #include <ardour/redirect.h>
31 #include <ardour/audioregion.h>
32 #include <ardour/audiosource.h>
33 #include <ardour/region_factory.h>
34 #include <ardour/route_group_specialized.h>
35 #include <ardour/insert.h>
36 #include <ardour/audioplaylist.h>
37 #include <ardour/playlist_factory.h>
38 #include <ardour/panner.h>
39 #include <ardour/utils.h>
40
41 #include "i18n.h"
42
43 using namespace std;
44 using namespace ARDOUR;
45 using namespace PBD;
46
47 AudioTrack::AudioTrack (Session& sess, string name, Route::Flag flag, TrackMode mode)
48         : Track (sess, name, flag, mode)
49 {
50         AudioDiskstream::Flag dflags = AudioDiskstream::Flag (0);
51
52         if (_flags & Hidden) {
53                 dflags = AudioDiskstream::Flag (dflags | AudioDiskstream::Hidden);
54         } else {
55                 dflags = AudioDiskstream::Flag (dflags | AudioDiskstream::Recordable);
56         }
57
58         if (mode == Destructive) {
59                 dflags = AudioDiskstream::Flag (dflags | AudioDiskstream::Destructive);
60         }
61
62         boost::shared_ptr<AudioDiskstream> ds (new AudioDiskstream (_session, name, dflags));
63         
64         _session.add_diskstream (ds);
65
66         set_diskstream (boost::dynamic_pointer_cast<AudioDiskstream> (ds), this);
67 }
68
69 AudioTrack::AudioTrack (Session& sess, const XMLNode& node)
70         : Track (sess, node)
71 {
72         _set_state (node, false);
73 }
74
75 AudioTrack::~AudioTrack ()
76 {
77 }
78
79 int
80 AudioTrack::set_mode (TrackMode m)
81 {
82         if (m != _mode) {
83
84                 if (_diskstream->set_destructive (m == Destructive)) {
85                         return -1;
86                 }
87
88                 _mode = m;
89                 
90                 TrackModeChanged (); /* EMIT SIGNAL */
91         }
92
93         return 0;
94 }
95
96 bool
97 AudioTrack::can_use_mode (TrackMode m, bool& bounce_required)
98 {
99         switch (m) {
100         case Normal:
101                 bounce_required = false;
102                 return true;
103                 
104         case Destructive:
105         default:
106                 return _diskstream->can_become_destructive (bounce_required);
107         }
108 }
109
110 int
111 AudioTrack::deprecated_use_diskstream_connections ()
112 {
113         boost::shared_ptr<AudioDiskstream> diskstream = audio_diskstream();
114
115         if (diskstream->deprecated_io_node == 0) {
116                 return 0;
117         }
118
119         const XMLProperty* prop;
120         XMLNode& node (*diskstream->deprecated_io_node);
121
122         /* don't do this more than once. */
123
124         diskstream->deprecated_io_node = 0;
125
126         set_input_minimum (-1);
127         set_input_maximum (-1);
128         set_output_minimum (-1);
129         set_output_maximum (-1);
130         
131         if ((prop = node.property ("gain")) != 0) {
132                 set_gain (atof (prop->value().c_str()), this);
133                 _gain = _desired_gain;
134         }
135
136         if ((prop = node.property ("input-connection")) != 0) {
137                 Connection* c = _session.connection_by_name (prop->value());
138                 
139                 if (c == 0) {
140                         error << string_compose(_("Unknown connection \"%1\" listed for input of %2"), prop->value(), _name) << endmsg;
141
142                         string replacement_connection;
143
144                         if (prop->value().find ('+') != string::npos) {
145                                 replacement_connection = _("in 1+2");
146                         } else {
147                                 replacement_connection = _("in 1");
148                         }
149                         
150                         if ((c = _session.connection_by_name (replacement_connection)) == 0) {
151                                 error << _("No input connections available as a replacement")
152                                 << endmsg;
153                                 return -1;
154                         } else {
155                                 info << string_compose (_("Connection %1 was not available - \"%2\" used instead"), prop->value(), replacement_connection)
156                                      << endmsg;
157                         }
158                 }
159
160                 use_input_connection (*c, this);
161
162         } else if ((prop = node.property ("inputs")) != 0) {
163                 if (set_inputs (prop->value())) {
164                         error << string_compose(_("improper input channel list in XML node (%1)"), prop->value()) << endmsg;
165                         return -1;
166                 }
167         }
168         
169         return 0;
170 }
171
172 int
173 AudioTrack::set_diskstream (boost::shared_ptr<AudioDiskstream> ds, void *src)
174 {
175         _diskstream = ds;
176         _diskstream->set_io (*this);
177         _diskstream->set_destructive (_mode == Destructive);
178
179         if (audio_diskstream()->deprecated_io_node) {
180
181                 if (!connecting_legal) {
182                         ConnectingLegal.connect (mem_fun (*this, &AudioTrack::deprecated_use_diskstream_connections));
183                 } else {
184                         deprecated_use_diskstream_connections ();
185                 }
186         }
187
188         _diskstream->set_record_enabled (false);
189         _diskstream->monitor_input (false);
190
191         ic_connection.disconnect();
192         ic_connection = input_changed.connect (mem_fun (*_diskstream, &Diskstream::handle_input_change));
193
194         DiskstreamChanged (); /* EMIT SIGNAL */
195
196         return 0;
197 }       
198
199 int 
200 AudioTrack::use_diskstream (string name)
201 {
202         boost::shared_ptr<AudioDiskstream> dstream;
203
204         if ((dstream = boost::dynamic_pointer_cast<AudioDiskstream>(_session.diskstream_by_name (name))) == 0) {
205                 error << string_compose(_("AudioTrack: audio diskstream \"%1\" not known by session"), name) << endmsg;
206                 return -1;
207         }
208         
209         return set_diskstream (dstream, this);
210 }
211
212 int 
213 AudioTrack::use_diskstream (const PBD::ID& id)
214 {
215         boost::shared_ptr<AudioDiskstream> dstream;
216
217         if ((dstream = boost::dynamic_pointer_cast<AudioDiskstream> (_session.diskstream_by_id (id))) == 0) {
218                 error << string_compose(_("AudioTrack: audio diskstream \"%1\" not known by session"), id) << endmsg;
219                 return -1;
220         }
221         
222         return set_diskstream (dstream, this);
223 }
224
225 boost::shared_ptr<AudioDiskstream>
226 AudioTrack::audio_diskstream() const
227 {
228         return boost::dynamic_pointer_cast<AudioDiskstream>(_diskstream);
229 }
230
231 int
232 AudioTrack::set_state (const XMLNode& node)
233 {
234         return _set_state (node, true);
235 }
236
237 int
238 AudioTrack::_set_state (const XMLNode& node, bool call_base)
239 {
240         const XMLProperty *prop;
241         XMLNodeConstIterator iter;
242
243         if (call_base) {
244                 if (Route::_set_state (node, call_base)) {
245                         return -1;
246                 }
247         }
248
249         if ((prop = node.property (X_("mode"))) != 0) {
250                 _mode = TrackMode (string_2_enum (prop->value(), _mode));
251         } else {
252                 _mode = Normal;
253         }
254
255         if ((prop = node.property ("diskstream-id")) == 0) {
256                 
257                 /* some old sessions use the diskstream name rather than the ID */
258
259                 if ((prop = node.property ("diskstream")) == 0) {
260                         fatal << _("programming error: AudioTrack given state without diskstream!") << endmsg;
261                         /*NOTREACHED*/
262                         return -1;
263                 }
264
265                 if (use_diskstream (prop->value())) {
266                         return -1;
267                 }
268
269         } else {
270                 
271                 PBD::ID id (prop->value());
272                 
273                 if (use_diskstream (id)) {
274                         return -1;
275                 }
276         }
277
278
279         XMLNodeList nlist;
280         XMLNodeConstIterator niter;
281         XMLNode *child;
282
283         nlist = node.children();
284         for (niter = nlist.begin(); niter != nlist.end(); ++niter){
285                 child = *niter;
286
287                 if (child->name() == X_("recenable")) {
288                         _rec_enable_control.set_state (*child);
289                         _session.add_controllable (&_rec_enable_control);
290                 }
291         }
292
293         pending_state = const_cast<XMLNode*> (&node);
294
295         _session.StateReady.connect (mem_fun (*this, &AudioTrack::set_state_part_two));
296
297         return 0;
298 }
299
300 XMLNode& 
301 AudioTrack::state(bool full_state)
302 {
303         XMLNode& root (Route::state(full_state));
304         XMLNode* freeze_node;
305         char buf[64];
306
307         if (_freeze_record.playlist) {
308                 XMLNode* inode;
309
310                 freeze_node = new XMLNode (X_("freeze-info"));
311                 freeze_node->add_property ("playlist", _freeze_record.playlist->name());
312                 freeze_node->add_property ("state", enum_2_string (_freeze_record.state));
313
314                 for (vector<FreezeRecordInsertInfo*>::iterator i = _freeze_record.insert_info.begin(); i != _freeze_record.insert_info.end(); ++i) {
315                         inode = new XMLNode (X_("insert"));
316                         (*i)->id.print (buf, sizeof (buf));
317                         inode->add_property (X_("id"), buf);
318                         inode->add_child_copy ((*i)->state);
319                 
320                         freeze_node->add_child_nocopy (*inode);
321                 }
322
323                 root.add_child_nocopy (*freeze_node);
324         }
325
326         /* Alignment: act as a proxy for the diskstream */
327         
328         XMLNode* align_node = new XMLNode (X_("alignment"));
329         AlignStyle as = _diskstream->alignment_style ();
330         align_node->add_property (X_("style"), enum_2_string (as));
331         root.add_child_nocopy (*align_node);
332
333         root.add_property (X_("mode"), enum_2_string (_mode));
334
335         /* we don't return diskstream state because we don't
336            own the diskstream exclusively. control of the diskstream
337            state is ceded to the Session, even if we create the
338            diskstream.
339         */
340
341         _diskstream->id().print (buf, sizeof (buf));
342         root.add_property ("diskstream-id", buf);
343
344         root.add_child_nocopy (_rec_enable_control.get_state());
345
346         return root;
347 }
348
349 void
350 AudioTrack::set_state_part_two ()
351 {
352         XMLNode* fnode;
353         XMLProperty* prop;
354         LocaleGuard lg (X_("POSIX"));
355
356         /* This is called after all session state has been restored but before
357            have been made ports and connections are established.
358         */
359
360         if (pending_state == 0) {
361                 return;
362         }
363
364         if ((fnode = find_named_node (*pending_state, X_("freeze-info"))) != 0) {
365
366                 
367                 _freeze_record.have_mementos = false;
368                 _freeze_record.state = Frozen;
369                 
370                 for (vector<FreezeRecordInsertInfo*>::iterator i = _freeze_record.insert_info.begin(); i != _freeze_record.insert_info.end(); ++i) {
371                         delete *i;
372                 }
373                 _freeze_record.insert_info.clear ();
374                 
375                 if ((prop = fnode->property (X_("playlist"))) != 0) {
376                         boost::shared_ptr<Playlist> pl = _session.playlist_by_name (prop->value());
377                         if (pl) {
378                                 _freeze_record.playlist = boost::dynamic_pointer_cast<AudioPlaylist> (pl);
379                         } else {
380                                 _freeze_record.playlist.reset ();
381                                 _freeze_record.state = NoFreeze;
382                         return;
383                         }
384                 }
385                 
386                 if ((prop = fnode->property (X_("state"))) != 0) {
387                         _freeze_record.state = FreezeState (string_2_enum (prop->value(), _freeze_record.state));
388                 }
389                 
390                 XMLNodeConstIterator citer;
391                 XMLNodeList clist = fnode->children();
392                 
393                 for (citer = clist.begin(); citer != clist.end(); ++citer) {
394                         if ((*citer)->name() != X_("insert")) {
395                                 continue;
396                         }
397                         
398                         if ((prop = (*citer)->property (X_("id"))) == 0) {
399                                 continue;
400                         }
401                         
402                         FreezeRecordInsertInfo* frii = new FreezeRecordInsertInfo (*((*citer)->children().front()),
403                                                                                    boost::shared_ptr<Insert>());
404                         frii->id = prop->value ();
405                         _freeze_record.insert_info.push_back (frii);
406                 }
407         }
408
409         /* Alignment: act as a proxy for the diskstream */
410
411         if ((fnode = find_named_node (*pending_state, X_("alignment"))) != 0) {
412
413                 if ((prop = fnode->property (X_("style"))) != 0) {
414
415                         /* fix for older sessions from before EnumWriter */
416
417                         string pstr;
418
419                         if (prop->value() == "capture") {
420                                 pstr = "CaptureTime";
421                         } else if (prop->value() == "existing") {
422                                 pstr = "ExistingMaterial";
423                         } else {
424                                 pstr = prop->value();
425                         }
426
427                         AlignStyle as = AlignStyle (string_2_enum (pstr, as));
428                         _diskstream->set_persistent_align_style (as);
429                 }
430         }
431         return;
432 }       
433
434 uint32_t
435 AudioTrack::n_process_buffers ()
436 {
437         return max ((uint32_t) _diskstream->n_channels(), redirect_max_outs);
438 }
439
440 void
441 AudioTrack::passthru_silence (nframes_t start_frame, nframes_t end_frame, nframes_t nframes, nframes_t offset, int declick, bool meter)
442 {
443         uint32_t nbufs = n_process_buffers ();
444         process_output_buffers (_session.get_silent_buffers (nbufs), nbufs, start_frame, end_frame, nframes, offset, true, declick, meter);
445 }
446
447 int 
448 AudioTrack::no_roll (nframes_t nframes, nframes_t start_frame, nframes_t end_frame, nframes_t offset, 
449                      bool session_state_changing, bool can_record, bool rec_monitors_input)
450 {
451         if (n_outputs() == 0) {
452                 return 0;
453         }
454
455         if (!_active) {
456                 silence (nframes, offset);
457                 return 0;
458         }
459
460         if (session_state_changing) {
461
462                 /* XXX is this safe to do against transport state changes? */
463
464                 passthru_silence (start_frame, end_frame, nframes, offset, 0, false);
465                 return 0;
466         }
467
468         audio_diskstream()->check_record_status (start_frame, nframes, can_record);
469
470         bool send_silence;
471         
472         if (_have_internal_generator) {
473                 /* since the instrument has no input streams,
474                    there is no reason to send any signal
475                    into the route.
476                 */
477                 send_silence = true;
478         } else {
479
480                 if (!Config->get_tape_machine_mode()) {
481                         /* 
482                            ADATs work in a strange way.. 
483                            they monitor input always when stopped.and auto-input is engaged. 
484                         */
485                         if ((Config->get_monitoring_model() == SoftwareMonitoring) && (Config->get_auto_input () || _diskstream->record_enabled())) {
486                                 send_silence = false;
487                         } else {
488                                 send_silence = true;
489                         }
490                 } else {
491                         /* 
492                            Other machines switch to input on stop if the track is record enabled,
493                            regardless of the auto input setting (auto input only changes the 
494                            monitoring state when the transport is rolling) 
495                         */
496                         if ((Config->get_monitoring_model() == SoftwareMonitoring) && _diskstream->record_enabled()) {
497                                 send_silence = false;
498                         } else {
499                                 send_silence = true;
500                         }
501                 }
502         }
503
504         apply_gain_automation = false;
505
506         if (send_silence) {
507                 
508                 /* if we're sending silence, but we want the meters to show levels for the signal,
509                    meter right here.
510                 */
511                 
512                 if (_have_internal_generator) {
513                         passthru_silence (start_frame, end_frame, nframes, offset, 0, true);
514                 } else {
515                         if (_meter_point == MeterInput) {
516                                 just_meter_input (start_frame, end_frame, nframes, offset);
517                         }
518                         passthru_silence (start_frame, end_frame, nframes, offset, 0, false);
519                 }
520
521         } else {
522         
523                 /* we're sending signal, but we may still want to meter the input. 
524                  */
525
526                 passthru (start_frame, end_frame, nframes, offset, 0, (_meter_point == MeterInput));
527         }
528
529         return 0;
530 }
531
532 int
533 AudioTrack::roll (nframes_t nframes, nframes_t start_frame, nframes_t end_frame, nframes_t offset, int declick,
534                   bool can_record, bool rec_monitors_input)
535 {
536         int dret;
537         Sample* b;
538         Sample* tmpb;
539         nframes_t transport_frame;
540         boost::shared_ptr<AudioDiskstream> diskstream = audio_diskstream();
541         
542         {
543                 Glib::RWLock::ReaderLock lm (redirect_lock, Glib::TRY_LOCK);
544                 if (lm.locked()) {
545                         // automation snapshot can also be called from the non-rt context
546                         // and it uses the redirect list, so we take the lock out here
547                         automation_snapshot (start_frame, false);
548                 }
549         }
550
551         
552         if (n_outputs() == 0 && _redirects.empty()) {
553                 return 0;
554         }
555
556         if (!_active) {
557                 silence (nframes, offset);
558                 return 0;
559         }
560
561         transport_frame = _session.transport_frame();
562
563         if ((nframes = check_initial_delay (nframes, offset, transport_frame)) == 0) {
564                 /* need to do this so that the diskstream sets its
565                    playback distance to zero, thus causing diskstream::commit
566                    to do nothing.
567                 */
568                 return diskstream->process (transport_frame, 0, 0, can_record, rec_monitors_input);
569         } 
570
571         _silent = false;
572         apply_gain_automation = false;
573
574         if ((dret = diskstream->process (transport_frame, nframes, offset, can_record, rec_monitors_input)) != 0) {
575                 
576                 silence (nframes, offset);
577
578                 return dret;
579         }
580
581         /* special condition applies */
582         
583         if (_meter_point == MeterInput) {
584                 just_meter_input (start_frame, end_frame, nframes, offset);
585         }
586
587         if (diskstream->record_enabled() && !can_record && !Config->get_auto_input()) {
588
589                 /* not actually recording, but we want to hear the input material anyway,
590                    at least potentially (depending on monitoring options)
591                  */
592
593                 passthru (start_frame, end_frame, nframes, offset, 0, true);
594
595         } else if ((b = diskstream->playback_buffer(0)) != 0) {
596
597                 /*
598                   XXX is it true that the earlier test on n_outputs()
599                   means that we can avoid checking it again here? i think
600                   so, because changing the i/o configuration of an IO
601                   requires holding the AudioEngine lock, which we hold
602                   while in the process() tree.
603                 */
604
605                 
606                 /* copy the diskstream data to all output buffers */
607                 
608                 vector<Sample*>& bufs = _session.get_passthru_buffers ();
609                 vector<Sample*>::size_type blimit = bufs.size();
610                 uint32_t limit = n_process_buffers ();
611                 
612                 uint32_t n;
613                 uint32_t i;
614
615                 if (limit > blimit) {
616
617                         /* example case: auditioner configured for stereo output,
618                            but loaded with an 8 channel file. there are only
619                            2 passthrough buffers, but n_process_buffers() will
620                            return 8.
621                            
622                            arbitrary decision: map all channels in the diskstream
623                            to the outputs available.
624                         */
625
626                         float scaling = limit/blimit;
627
628                         for (i = 0, n = 1; i < blimit; ++i, ++n) {
629
630                                 /* first time through just copy a channel into 
631                                    the output buffer.
632                                 */
633                                 
634                                 for (nframes_t xx = 0; xx < nframes; ++xx) {
635                                         bufs[i][xx] = b[xx] * scaling;
636                                 }
637
638                                 if (n < diskstream->n_channels()) {
639                                         tmpb = diskstream->playback_buffer(n);
640                                         if (tmpb!=0) {
641                                                 b = tmpb;
642                                         }
643                                 }
644                         }
645
646                         for (;i < limit; ++i, ++n) {
647                                 
648                                 /* for all remaining channels, sum with existing
649                                    data in the output buffers 
650                                 */
651                                 
652                                 _session.mix_buffers_with_gain (bufs[i%blimit], b, nframes, scaling);
653
654                                 if (n < diskstream->n_channels()) {
655                                         tmpb = diskstream->playback_buffer(n);
656                                         if (tmpb!=0) {
657                                                 b = tmpb;
658                                         }
659                                 }
660                                 
661                         }
662
663                 } else {
664                 
665                         for (i = 0, n = 1; i < limit; ++i, ++n) {
666                                 memcpy (bufs[i], b, sizeof (Sample) * nframes); 
667                                 if (n < diskstream->n_channels()) {
668                                         tmpb = diskstream->playback_buffer(n);
669                                         if (tmpb!=0) {
670                                                 b = tmpb;
671                                         }
672                                 }
673                         }
674                 }
675
676                 /* don't waste time with automation if we're recording or we've just stopped (yes it can happen) */
677
678                 if (!diskstream->record_enabled() && _session.transport_rolling()) {
679                         Glib::Mutex::Lock am (automation_lock, Glib::TRY_LOCK);
680                         
681                         if (am.locked() && gain_automation_playback()) {
682                                 apply_gain_automation = _gain_automation_curve.rt_safe_get_vector (start_frame, end_frame, _session.gain_automation_buffer(), nframes);
683                         }
684                 }
685
686                 process_output_buffers (bufs, blimit, start_frame, end_frame, nframes, offset, (!_session.get_record_enabled() || !Config->get_do_not_record_plugins()), declick, (_meter_point != MeterInput));
687                 
688         } else {
689                 /* problem with the diskstream; just be quiet for a bit */
690                 silence (nframes, offset);
691         }
692
693         return 0;
694 }
695
696 int
697 AudioTrack::silent_roll (nframes_t nframes, nframes_t start_frame, nframes_t end_frame, nframes_t offset, 
698                          bool can_record, bool rec_monitors_input)
699 {
700         if (n_outputs() == 0 && _redirects.empty()) {
701                 return 0;
702         }
703
704         if (!_active) {
705                 silence (nframes, offset);
706                 return 0;
707         }
708
709         _silent = true;
710         apply_gain_automation = false;
711
712         silence (nframes, offset);
713
714         return audio_diskstream()->process (_session.transport_frame() + offset, nframes, offset, can_record, rec_monitors_input);
715 }
716
717 int
718 AudioTrack::export_stuff (vector<Sample*>& buffers, uint32_t nbufs, nframes_t start, nframes_t nframes)
719 {
720         gain_t  gain_automation[nframes];
721         gain_t  gain_buffer[nframes];
722         float   mix_buffer[nframes];
723         RedirectList::iterator i;
724         bool post_fader_work = false;
725         gain_t this_gain = _gain;
726         vector<Sample*>::iterator bi;
727         Sample * b;
728         boost::shared_ptr<AudioDiskstream> diskstream = audio_diskstream();
729         
730         Glib::RWLock::ReaderLock rlock (redirect_lock);
731
732         boost::shared_ptr<AudioPlaylist> apl = boost::dynamic_pointer_cast<AudioPlaylist>(diskstream->playlist());
733         assert(apl);
734
735         if (apl->read (buffers[0], mix_buffer, gain_buffer, start, nframes) != nframes) {
736                 return -1;
737         }
738
739         uint32_t n=1;
740         bi = buffers.begin();
741         b = buffers[0];
742         ++bi;
743         for (; bi != buffers.end(); ++bi, ++n) {
744                 if (n < diskstream->n_channels()) {
745                         if (apl->read ((*bi), mix_buffer, gain_buffer, start, nframes, n) != nframes) {
746                                 return -1;
747                         }
748                         b = (*bi);
749                 }
750                 else {
751                         /* duplicate last across remaining buffers */
752                         memcpy ((*bi), b, sizeof (Sample) * nframes); 
753                 }
754         }
755
756
757         /* note: only run inserts during export. other layers in the machinery
758            will already have checked that there are no external port inserts.
759         */
760         
761         for (i = _redirects.begin(); i != _redirects.end(); ++i) {
762                 boost::shared_ptr<Insert> insert;
763                 
764                 if ((insert = boost::dynamic_pointer_cast<Insert>(*i)) != 0) {
765                         switch (insert->placement()) {
766                         case PreFader:
767                                 insert->run (buffers, nbufs, nframes, 0);
768                                 break;
769                         case PostFader:
770                                 post_fader_work = true;
771                                 break;
772                         }
773                 }
774         }
775         
776         if (_gain_automation_curve.automation_state() == Play) {
777                 
778                 _gain_automation_curve.get_vector (start, start + nframes, gain_automation, nframes);
779
780                 for (bi = buffers.begin(); bi != buffers.end(); ++bi) {
781                         Sample *b = *bi;
782                         for (nframes_t n = 0; n < nframes; ++n) {
783                                 b[n] *= gain_automation[n];
784                         }
785                 }
786
787         } else {
788
789                 for (bi = buffers.begin(); bi != buffers.end(); ++bi) {
790                         Sample *b = *bi;
791                         for (nframes_t n = 0; n < nframes; ++n) {
792                                 b[n] *= this_gain;
793                         }
794                 }
795         }
796
797         if (post_fader_work) {
798
799                 for (i = _redirects.begin(); i != _redirects.end(); ++i) {
800                         boost::shared_ptr<PluginInsert> insert;
801                         
802                         if ((insert = boost::dynamic_pointer_cast<PluginInsert>(*i)) != 0) {
803                                 switch ((*i)->placement()) {
804                                 case PreFader:
805                                         break;
806                                 case PostFader:
807                                         insert->run (buffers, nbufs, nframes, 0);
808                                         break;
809                                 }
810                         }
811                 }
812         } 
813
814         return 0;
815 }
816
817 boost::shared_ptr<Region>
818 AudioTrack::bounce (InterThreadInfo& itt)
819 {
820         vector<boost::shared_ptr<AudioSource> > srcs;
821         return _session.write_one_audio_track (*this, _session.current_start_frame(), _session.current_end_frame(), 
822                                                false, srcs, itt);
823 }
824
825
826 boost::shared_ptr<Region>
827 AudioTrack::bounce_range (nframes_t start, nframes_t end, InterThreadInfo& itt)
828 {
829         vector<boost::shared_ptr<AudioSource> > srcs;
830         return _session.write_one_audio_track (*this, start, end, false, srcs, itt);
831 }
832
833 void
834 AudioTrack::freeze (InterThreadInfo& itt)
835 {
836         vector<boost::shared_ptr<AudioSource> > srcs;
837         string new_playlist_name;
838         boost::shared_ptr<Playlist> new_playlist;
839         string dir;
840         string region_name;
841         boost::shared_ptr<AudioDiskstream> diskstream = audio_diskstream();
842         
843         if ((_freeze_record.playlist = boost::dynamic_pointer_cast<AudioPlaylist>(diskstream->playlist())) == 0) {
844                 return;
845         }
846
847         uint32_t n = 1;
848
849         while (n < (UINT_MAX-1)) {
850          
851                 string candidate;
852                 
853                 candidate = string_compose ("<F%2>%1", _freeze_record.playlist->name(), n);
854
855                 if (_session.playlist_by_name (candidate) == 0) {
856                         new_playlist_name = candidate;
857                         break;
858                 }
859
860                 ++n;
861
862         } 
863
864         if (n == (UINT_MAX-1)) {
865           error << string_compose (X_("There are too many frozen versions of playlist \"%1\""
866                             " to create another one"), _freeze_record.playlist->name())
867                << endmsg;
868                 return;
869         }
870
871         boost::shared_ptr<Region> res;
872
873         if ((res = _session.write_one_audio_track (*this, _session.current_start_frame(), _session.current_end_frame(), true, srcs, itt)) == 0) {
874                 return;
875         }
876
877         _freeze_record.insert_info.clear ();
878         _freeze_record.have_mementos = true;
879
880         {
881                 Glib::RWLock::ReaderLock lm (redirect_lock);
882                 
883                 for (RedirectList::iterator r = _redirects.begin(); r != _redirects.end(); ++r) {
884                         
885                         boost::shared_ptr<Insert> insert;
886
887                         if ((insert = boost::dynamic_pointer_cast<Insert>(*r)) != 0) {
888                                 
889                                 FreezeRecordInsertInfo* frii  = new FreezeRecordInsertInfo ((*r)->get_state(), insert);
890                                 
891                                 frii->id = insert->id();
892
893                                 _freeze_record.insert_info.push_back (frii);
894                                 
895                                 /* now deactivate the insert */
896                                 
897                                 insert->set_active (false, this);
898                         }
899                 }
900         }
901
902         _freeze_record.gain = _gain;
903         _freeze_record.gain_automation_state = _gain_automation_curve.automation_state();
904         _freeze_record.pan_automation_state = _panner->automation_state();
905
906         new_playlist = PlaylistFactory::create (_session, new_playlist_name, false);
907         region_name = new_playlist_name;
908
909         /* create a new region from all filesources, keep it private */
910
911         boost::shared_ptr<Region> region (RegionFactory::create (srcs, 0, srcs[0]->length(), 
912                                                                  region_name, 0, 
913                                                                  (AudioRegion::Flag) (AudioRegion::WholeFile|AudioRegion::DefaultFlags),
914                                                                  false));
915
916         new_playlist->set_orig_diskstream_id (diskstream->id());
917         new_playlist->add_region (region, _session.current_start_frame());
918         new_playlist->set_frozen (true);
919         region->set_locked (true);
920
921         diskstream->use_playlist (boost::dynamic_pointer_cast<AudioPlaylist>(new_playlist));
922         diskstream->set_record_enabled (false);
923
924         /* reset stuff that has already been accounted for in the freeze process */
925         
926         set_gain (1.0, this);
927         _gain_automation_curve.set_automation_state (Off);
928         _panner->set_automation_state (Off);
929
930         _freeze_record.state = Frozen;
931         FreezeChange(); /* EMIT SIGNAL */
932 }
933
934 void
935 AudioTrack::unfreeze ()
936 {
937         if (_freeze_record.playlist) {
938                 audio_diskstream()->use_playlist (_freeze_record.playlist);
939
940                 if (_freeze_record.have_mementos) {
941
942                         for (vector<FreezeRecordInsertInfo*>::iterator i = _freeze_record.insert_info.begin(); i != _freeze_record.insert_info.end(); ++i) {
943                                 (*i)->memento ();
944                         }
945
946                 } else {
947
948                         Glib::RWLock::ReaderLock lm (redirect_lock); // should this be a write lock? jlc
949                         for (RedirectList::iterator i = _redirects.begin(); i != _redirects.end(); ++i) {
950                                 for (vector<FreezeRecordInsertInfo*>::iterator ii = _freeze_record.insert_info.begin(); ii != _freeze_record.insert_info.end(); ++ii) {
951                                         if ((*ii)->id == (*i)->id()) {
952                                                 (*i)->set_state (((*ii)->state));
953                                                 break;
954                                         }
955                                 }
956                         }
957                 }
958                 
959                 _freeze_record.playlist.reset ();
960                 set_gain (_freeze_record.gain, this);
961                 _gain_automation_curve.set_automation_state (_freeze_record.gain_automation_state);
962                 _panner->set_automation_state (_freeze_record.pan_automation_state);
963         }
964
965         _freeze_record.state = UnFrozen;
966         FreezeChange (); /* EMIT SIGNAL */
967 }
968