X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;f=libs%2Fardour%2Fardour%2Fsession.h;h=dac08af29bc7e8272368063a9c299c7c7952d53c;hb=3e6ce20fd71022dad54508b652e851148ae4a4c4;hp=66ab5ce0824d07b1d5f90859b7c52d5f8b003ad2;hpb=24ec0b974d84df061cbbe645668dc62fa7120678;p=ardour.git diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h index 66ab5ce082..dac08af29b 100644 --- a/libs/ardour/ardour/session.h +++ b/libs/ardour/ardour/session.h @@ -20,7 +20,9 @@ #ifndef __ardour_session_h__ #define __ardour_session_h__ +#ifdef WAF_BUILD #include "libardour-config.h" +#endif #include #include @@ -42,6 +44,7 @@ #include "pbd/error.h" #include "pbd/event_loop.h" +#include "pbd/file_archive.h" #include "pbd/rcu.h" #include "pbd/reallocpool.h" #include "pbd/statefuldestructible.h" @@ -80,6 +83,8 @@ class XMLNode; struct _AEffect; typedef struct _AEffect AEffect; +class PTFFormat; + namespace MIDI { class Port; class MachineControl; @@ -113,7 +118,6 @@ class BufferSet; class Bundle; class Butler; class Click; -class ControllableDescriptor; class CoreSelection; class ExportHandler; class ExportStatus; @@ -140,17 +144,19 @@ class Region; class Return; class Route; class RouteGroup; +class RTTaskList; class SMFSource; class Send; class SceneChanger; class SessionDirectory; class SessionMetadata; class SessionPlaylists; -class Slave; class Source; class Speakers; class TempoMap; +class TransportMaster; class Track; +class UI_TransportMaster; class VCAManager; class WindowsVSTPlugin; @@ -170,17 +176,9 @@ private: /** Ardour Session */ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::ScopedConnectionList, public SessionEventManager { - private: - enum SubState { - PendingDeclickIn = 0x1, ///< pending de-click fade-in for start - PendingDeclickOut = 0x2, ///< pending de-click fade-out for stop - StopPendingCapture = 0x4, - PendingLoopDeclickIn = 0x8, ///< pending de-click fade-in at the start of a loop - PendingLoopDeclickOut = 0x10, ///< pending de-click fade-out at the end of a loop - PendingLocate = 0x20, - }; +private: - public: +public: enum RecordState { Disabled = 0, Enabled = 1, @@ -215,16 +213,21 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop bool path_is_within_session (const std::string&); bool writable() const { return _writable; } - void set_dirty (); - void set_clean (); - bool dirty() const { return _state_of_the_state & Dirty; } - void set_deletion_in_progress (); - void clear_deletion_in_progress (); - bool reconnection_in_progress() const { return _reconnecting_routes_in_progress; } - bool deletion_in_progress() const { return _state_of_the_state & Deletion; } - bool routes_deletion_in_progress() const { return _route_deletion_in_progress; } - bool peaks_cleanup_in_progres() const { return _state_of_the_state & PeakCleanup; } - bool loading () const { return _state_of_the_state & Loading; } + void set_clean (); // == Clean and emit DirtyChanged IFF session was Dirty + void set_dirty (); // |= Dirty and emit DirtyChanged (unless already dirty or Loading, Deletion) + void unset_dirty (bool emit_dirty_changed = false); // &= ~Dirty + void set_deletion_in_progress (); // |= Deletion + void clear_deletion_in_progress (); // &= ~Deletion + + bool reconnection_in_progress () const { return _reconnecting_routes_in_progress; } + bool routes_deletion_in_progress () const { return _route_deletion_in_progress; } + bool dirty () const { return _state_of_the_state & Dirty; } + bool deletion_in_progress () const { return _state_of_the_state & Deletion; } + bool peaks_cleanup_in_progres () const { return _state_of_the_state & PeakCleanup; } + bool loading () const { return _state_of_the_state & Loading; } + bool cannot_save () const { return _state_of_the_state & CannotSave; } + bool in_cleanup () const { return _state_of_the_state & InCleanup; } + bool inital_connect_or_deletion_in_progress () { return _state_of_the_state & (InitialConnecting | Deletion); } PBD::Signal0 DirtyChanged; @@ -287,6 +290,10 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop return routes.reader (); } + boost::shared_ptr rt_tasklist () { return _rt_tasklist; } + + RouteList get_routelist (bool mixer_order = false, PresentationInfo::Flag fl = PresentationInfo::MixerRoutes) const; + CoreSelection& selection () { return *_selection; } /* because the set of Stripables consists of objects managed @@ -296,12 +303,14 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop * with get_routes() */ - void get_stripables (StripableList&) const; + void get_stripables (StripableList&, PresentationInfo::Flag fl = PresentationInfo::MixerStripables) const; StripableList get_stripables () const; boost::shared_ptr get_tracks() const; boost::shared_ptr get_routes_with_internal_returns() const; boost::shared_ptr get_routes_with_regions_at (samplepos_t const) const; + boost::shared_ptr get_nth_audio_track (int nth) const; + uint32_t nstripables (bool with_monitor = false) const; uint32_t nroutes() const { return routes.reader()->size(); } uint32_t ntracks () const; @@ -359,10 +368,6 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop PBD::Signal0 IOConnectionsComplete; - /* Timecode status signals */ - PBD::Signal1 MTCSyncStateChanged; - PBD::Signal1 LTCSyncStateChanged; - /* Record status signals */ PBD::Signal0 RecordStateChanged; /* signals changes in recording state (i.e. are we recording) */ @@ -416,8 +421,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void request_roll_at_and_return (samplepos_t start, samplepos_t return_to); void request_bounded_roll (samplepos_t start, samplepos_t end); - void request_stop (bool abort = false, bool clear_state = false); - void request_locate (samplepos_t sample, bool with_roll = false); + void request_stop (bool abort = false, bool clear_state = false, TransportRequestSource origin = TRS_UI); + void request_locate (samplepos_t sample, bool with_roll = false, TransportRequestSource origin = TRS_UI); void request_play_loop (bool yn, bool leave_rolling = false); bool get_play_loop () const { return play_loop; } @@ -427,15 +432,14 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void goto_start (bool and_roll = false); void use_rf_shuttle_speed (); void allow_auto_play (bool yn); - void request_transport_speed (double speed, bool as_default = true); - void request_transport_speed_nonzero (double, bool as_default = true); + void request_transport_speed (double speed, bool as_default = true, TransportRequestSource origin = TRS_UI); + void request_transport_speed_nonzero (double, bool as_default = true, TransportRequestSource origin = TRS_UI); void request_overwrite_buffer (boost::shared_ptr); void adjust_playback_buffering(); void adjust_capture_buffering(); bool global_locate_pending() const { return _global_locate_pending; } bool locate_pending() const { return static_cast(post_transport_work()&PostTransportLocate); } - bool declick_out_pending() const { return static_cast(transport_sub_state&(PendingDeclickOut)); } bool transport_locked () const; int wipe (); @@ -469,16 +473,13 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void set_auto_punch_location (Location *); void set_auto_loop_location (Location *); void set_session_extents (samplepos_t start, samplepos_t end); - bool end_is_free () const { return _session_range_end_is_free; } - void set_end_is_free (bool); - int location_name(std::string& result, std::string base = std::string("")); - - pframes_t get_block_size () const { return current_block_size; } - samplecnt_t worst_output_latency () const { return _worst_output_latency; } - samplecnt_t worst_input_latency () const { return _worst_input_latency; } - samplecnt_t worst_track_latency () const { return _worst_track_latency; } - samplecnt_t worst_track_out_latency () const { return _worst_track_out_latency; } - samplecnt_t worst_playback_latency () const { return std::max (_worst_output_latency, _worst_track_latency); } + bool session_range_is_free () const { return _session_range_is_free; } + void set_session_range_is_free (bool); + + pframes_t get_block_size () const { return current_block_size; } + samplecnt_t worst_output_latency () const { return _worst_output_latency; } + samplecnt_t worst_input_latency () const { return _worst_input_latency; } + samplecnt_t worst_route_latency () const { return _worst_route_latency; } samplecnt_t worst_latency_preroll () const; struct SaveAs { @@ -510,6 +511,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop }; int save_as (SaveAs&); + /** save session * @param snapshot_name name of the session (use an empty string for the current name) * @param pending save a 'recovery', not full state (default: false) @@ -517,7 +519,12 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop * @param template_only save a session template (default: false) * @return zero on success */ - int save_state (std::string snapshot_name, bool pending = false, bool switch_to_snapshot = false, bool template_only = false); + int save_state (std::string snapshot_name, + bool pending = false, + bool switch_to_snapshot = false, + bool template_only = false, + bool for_archive = false, + bool only_used_assets = false); enum ArchiveEncode { NO_ENCODE, @@ -525,7 +532,11 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop FLAC_24BIT }; - int archive_session (const std::string&, const std::string&, ArchiveEncode compress_audio = FLAC_16BIT, bool only_used_sources = false, Progress* p = 0); + int archive_session (const std::string&, const std::string&, + ArchiveEncode compress_audio = FLAC_16BIT, + PBD::FileArchive::CompressionLevel compression_level = PBD::FileArchive::CompressGood, + bool only_used_sources = false, + Progress* p = 0); int restore_state (std::string snapshot_name); int save_template (const std::string& template_name, const std::string& description = "", bool replace_existing = false); @@ -560,10 +571,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop std::vector possible_states() const; static std::vector possible_states (std::string path); - XMLNode& get_state(); - int set_state(const XMLNode& node, int version); // not idempotent - XMLNode& get_template(); - bool export_track_state (boost::shared_ptr rl, const std::string& path); + bool export_track_state (boost::shared_ptr rl, const std::string& path); /// The instant xml file is written to the session directory void add_instant_xml (XMLNode&, bool write_to_config = true); @@ -580,8 +588,6 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop PeakCleanup = 0x40 }; - StateOfTheState state_of_the_state() const { return _state_of_the_state; } - class StateProtector { public: StateProtector (Session* s) : _session (s) { @@ -685,6 +691,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop samplepos_t requested_return_sample() const { return _requested_return_sample; } void set_requested_return_sample(samplepos_t return_to); + bool compute_audible_delta (samplepos_t& pos_and_delta) const; samplecnt_t remaining_latency_preroll () const { return _remaining_latency_preroll; } enum PullupFormat { @@ -717,11 +724,15 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop static PBD::Signal1 StartTimeChanged; static PBD::Signal1 EndTimeChanged; - void request_sync_source (Slave*); - bool synced_to_engine() const { return _slave && config.get_external_sync() && Config->get_sync_source() == Engine; } - bool synced_to_mtc () const { return config.get_external_sync() && Config->get_sync_source() == MTC && g_atomic_int_get (const_cast(&_mtc_active)); } - bool synced_to_ltc () const { return config.get_external_sync() && Config->get_sync_source() == LTC && g_atomic_int_get (const_cast(&_ltc_active)); } + void request_sync_source (boost::shared_ptr); + bool synced_to_engine() const; + double engine_speed() const { return _engine_speed; } + double actual_speed() const { + if (_transport_speed > 0) return _engine_speed; + if (_transport_speed < 0) return - _engine_speed; + return 0; + } double transport_speed() const { return _count_in_samples > 0 ? 0. : _transport_speed; } bool transport_stopped() const { return _transport_speed == 0.0; } bool transport_rolling() const { return _transport_speed != 0.0 && _count_in_samples == 0 && _remaining_latency_preroll == 0; } @@ -730,6 +741,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop TempoMap& tempo_map() { return *_tempo_map; } const TempoMap& tempo_map() const { return *_tempo_map; } + void maybe_update_tempo_from_midiclock_tempo (float bpm); unsigned int get_xrun_count () const {return _xrun_count; } void reset_xrun_count () {_xrun_count = 0; } @@ -845,6 +857,9 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop bool solo_isolated() const { return _solo_isolated_cnt > 0; } void cancel_all_solo (); + bool solo_selection_active(); + void solo_selection( StripableList&, bool ); + static const SessionEvent::RTeventCallback rt_cleanup; void clear_all_solo_state (boost::shared_ptr); @@ -861,15 +876,14 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop PBD::Signal0 MuteChanged; PBD::Signal0 IsolatedChanged; PBD::Signal0 MonitorChanged; + PBD::Signal0 MonitorBusAddedOrRemoved; PBD::Signal0 session_routes_reconnected; /* monitor/master out */ int add_master_bus (ChanCount const&); - void add_monitor_section (); void reset_monitor_section (); - void remove_monitor_section (); bool monitor_active() const { return (_monitor_out && _monitor_out->monitor_control () && _monitor_out->monitor_control ()->monitor_active()); } boost::shared_ptr monitor_out() const { return _monitor_out; } @@ -1013,13 +1027,9 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop /* preroll */ samplecnt_t preroll_samples (samplepos_t) const; - void request_preroll_record_punch (samplepos_t start, samplecnt_t preroll); void request_preroll_record_trim (samplepos_t start, samplecnt_t preroll); void request_count_in_record (); - samplepos_t preroll_record_punch_pos () const { return _preroll_record_punch_pos; } - bool preroll_record_punch_enabled () const { return _preroll_record_punch_pos >= 0; } - samplecnt_t preroll_record_trim_len () const { return _preroll_record_trim_len; } /* temporary hacks to allow selection to be pushed from GUI into backend. @@ -1067,10 +1077,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop boost::shared_ptr controllable_by_id (const PBD::ID&); boost::shared_ptr automation_control_by_id (const PBD::ID&); - boost::shared_ptr controllable_by_descriptor (const ARDOUR::ControllableDescriptor&); void add_controllable (boost::shared_ptr); - void remove_controllable (PBD::Controllable*); boost::shared_ptr solo_cut_control() const; @@ -1098,26 +1106,17 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop PostTransportRoll = 0x8, PostTransportAbort = 0x10, PostTransportOverWrite = 0x20, - PostTransportSpeed = 0x40, + /* PostTransportSpeed = 0x40, */ PostTransportAudition = 0x80, PostTransportReverse = 0x100, - PostTransportInputChange = 0x200, - PostTransportCurveRealloc = 0x400, + /* PostTransportInputChange = 0x200, */ + /*PostTransportCurveRealloc = 0x400, */ PostTransportClearSubstate = 0x800, PostTransportAdjustPlaybackBuffering = 0x1000, PostTransportAdjustCaptureBuffering = 0x2000 }; - enum SlaveState { - Stopped, - Waiting, - Running - }; - - SlaveState slave_state() const { return _slave_state; } - Slave* slave() const { return _slave; } - - boost::shared_ptr playlists; + boost::shared_ptr playlists () const { return _playlists; } void send_mmc_locate (samplepos_t); void queue_full_time_code () { _send_timecode_update = true; } @@ -1183,22 +1182,16 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop /* synchronous MIDI ports used for synchronization */ boost::shared_ptr midi_clock_output_port () const; - boost::shared_ptr midi_clock_input_port () const; boost::shared_ptr mtc_output_port () const; - boost::shared_ptr mtc_input_port () const; - boost::shared_ptr ltc_input_port() const; boost::shared_ptr ltc_output_port() const; - boost::shared_ptr ltc_input_io() { return _ltc_input; } boost::shared_ptr ltc_output_io() { return _ltc_output; } MIDI::MachineControl& mmc() { return *_mmc; } void reconnect_midi_scene_ports (bool); - void reconnect_mtc_ports (); void reconnect_mmc_ports (bool); - void reconnect_ltc_input (); void reconnect_ltc_output (); VCAManager& vca_manager() { return *_vca_manager; } @@ -1206,8 +1199,15 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void auto_connect_thread_wakeup (); + double compute_speed_from_master (pframes_t nframes); + bool transport_master_is_external() const; + bool transport_master_no_external_or_using_engine() const; + boost::shared_ptr transport_master() const; + + void import_pt (PTFFormat& ptf, ImportStatus& status); + bool import_sndfile_as_region (std::string path, SrcQuality quality, samplepos_t& pos, SourceList& sources, ImportStatus& status); - protected: +protected: friend class AudioEngine; void set_block_size (pframes_t nframes); void set_sample_rate (samplecnt_t nframes); @@ -1215,12 +1215,10 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void reconnect_existing_routes (bool withLock, bool reconnect_master = true, bool reconnect_inputs = true, bool reconnect_outputs = true); #endif - protected: friend class Route; - void schedule_curve_reallocation (); void update_latency_compensation (bool force = false); - private: +private: int create (const std::string& mix_template, BusProfile*); void destroy (); @@ -1228,6 +1226,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop static void init_name_id_counter (guint n); static unsigned int name_id_counter (); + boost::shared_ptr _playlists; + /* stuff used in process() should be close together to maximise cache hits */ @@ -1240,7 +1240,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop process_function_type last_process_function; bool _bounce_processing_active; bool waiting_for_sync_offset; - samplecnt_t _base_sample_rate; // sample-rate of the session at creation time, "native" SR + samplecnt_t _base_sample_rate; // sample-rate of the session at creation time, "native" SR samplecnt_t _nominal_sample_rate; // overridden by audioengine setting samplecnt_t _current_sample_rate; // this includes video pullup offset int transport_sub_state; @@ -1248,28 +1248,25 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop samplepos_t _transport_sample; gint _seek_counter; Location* _session_range_location; ///< session range, or 0 if there is nothing in the session yet - bool _session_range_end_is_free; - Slave* _slave; + bool _session_range_is_free; bool _silent; samplecnt_t _remaining_latency_preroll; - // varispeed playback - double _transport_speed; + // varispeed playback -- TODO: move out of session to backend. + double _engine_speed; + double _transport_speed; // only: -1, 0, +1 double _default_transport_speed; double _last_transport_speed; double _signalled_varispeed; double _target_transport_speed; - CubicInterpolation interpolation; bool auto_play_legal; - samplepos_t _last_slave_transport_sample; - samplecnt_t maximum_output_latency; - samplepos_t _requested_return_sample; + samplepos_t _requested_return_sample; pframes_t current_block_size; - samplecnt_t _worst_output_latency; - samplecnt_t _worst_input_latency; - samplecnt_t _worst_track_latency; - samplecnt_t _worst_track_out_latency; + samplecnt_t _worst_output_latency; + samplecnt_t _worst_input_latency; + samplecnt_t _worst_route_latency; + uint32_t _send_latency_changes; bool _have_captured; bool _non_soloed_outs_muted; bool _listening; @@ -1282,22 +1279,19 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop std::string _missing_file_replacement; - void mtc_status_changed (bool); - PBD::ScopedConnection mtc_status_connection; - void ltc_status_changed (bool); - PBD::ScopedConnection ltc_status_connection; + void add_monitor_section (); + void remove_monitor_section (); void initialize_latencies (); + void update_latency (bool playback); + bool update_route_latency (bool reverse, bool apply_to_delayline); + void set_worst_io_latencies (); - void set_worst_playback_latency (); - void set_worst_capture_latency (); - void set_worst_io_latencies_x (IOChange, void *) { - set_worst_io_latencies (); - } - void post_capture_latency (); - void post_playback_latency (); + void set_worst_output_latency (); + void set_worst_input_latency (); - void update_latency_compensation_proxy (void* ignored); + void send_latency_compensation_change (); + void set_worst_io_latencies_x (IOChange, void *); void ensure_buffers (ChanCount howmany = ChanCount::ZERO); @@ -1314,28 +1308,21 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop static const samplecnt_t bounce_chunk_size; - /* slave tracking */ + /* Transport master DLL */ - static const int delta_accumulator_size = 25; - int delta_accumulator_cnt; - int32_t delta_accumulator[delta_accumulator_size]; - int32_t average_slave_delta; - int average_dir; - bool have_first_delta_accumulator; + enum TransportMasterState { + Stopped, /* no incoming or invalid signal/data for master to run with */ + Waiting, /* waiting to get full lock on incoming signal/data */ + Running /* lock achieved, master is generating meaningful speed & position */ + }; - SlaveState _slave_state; - gint _mtc_active; - gint _ltc_active; - samplepos_t slave_wait_end; + TransportMasterState transport_master_tracking_state; + samplepos_t master_wait_end; + void track_transport_master (float slave_speed, samplepos_t slave_transport_sample); + bool follow_transport_master (pframes_t nframes); + void sync_source_changed (SyncSource, samplepos_t pos, pframes_t cycle_nframes); void reset_slave_state (); - bool follow_slave (pframes_t); - void calculate_moving_average_of_slave_delta (int dir, samplecnt_t this_delta); - void track_slave_state (float slave_speed, samplepos_t slave_transport_sample, samplecnt_t this_delta); - - void switch_to_sync_source (SyncSource); /* !RT context */ - void drop_sync_source (); /* !RT context */ - void use_sync_source (Slave*); /* RT context */ bool post_export_sync; samplepos_t post_export_position; @@ -1365,31 +1352,9 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop -1 if there is a pending declick fade-out, 0 if there is no pending declick. */ - int get_transport_declick_required () { - if (transport_sub_state & PendingDeclickIn) { - transport_sub_state &= ~PendingDeclickIn; - return 1; - } else if (transport_sub_state & PendingDeclickOut) { - /* XXX: not entirely sure why we don't clear this */ - return -1; - } else if (transport_sub_state & PendingLoopDeclickOut) { - /* Return the declick out first ... */ - transport_sub_state &= ~PendingLoopDeclickOut; - return -1; - } else if (transport_sub_state & PendingLoopDeclickIn) { - /* ... then the declick in on the next call */ - transport_sub_state &= ~PendingLoopDeclickIn; - return 1; - } else { - return 0; - } - } - bool maybe_stop (samplepos_t limit); bool maybe_sync_start (pframes_t &); - void check_declick_out (); - std::string _path; std::string _name; bool _is_new; @@ -1400,7 +1365,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop pframes_t _pframes_since_last_mtc; bool play_loop; bool loop_changing; - samplepos_t last_loopend; + samplepos_t last_loopend; boost::scoped_ptr _session_dir; @@ -1420,6 +1385,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop gint _suspend_save; /* atomic */ volatile bool _save_queued; Glib::Threads::Mutex save_state_lock; + Glib::Threads::Mutex save_source_lock; Glib::Threads::Mutex peak_cleanup_lock; int load_options (const XMLNode&); @@ -1431,9 +1397,6 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop samplepos_t _last_roll_or_reversal_location; samplepos_t _last_record_location; - bool pending_locate_roll; - samplepos_t pending_locate_sample; - bool pending_locate_flush; bool pending_abort; bool pending_auto_loop; @@ -1456,9 +1419,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop static const PostTransportWork ProcessCannotProceedMask = PostTransportWork ( - PostTransportInputChange| PostTransportReverse| - PostTransportCurveRealloc| PostTransportAudition| PostTransportStop| PostTransportClearSubstate); @@ -1471,12 +1432,6 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void schedule_playback_buffering_adjustment (); void schedule_capture_buffering_adjustment (); - uint32_t cumulative_rf_motion; - uint32_t rf_scale; - - void set_rf_speed (float speed); - void reset_rf_scale (samplecnt_t samples_moved); - Locations* _locations; void location_added (Location*); void location_removed (Location*); @@ -1583,6 +1538,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop ChanCount output_offset; }; + Glib::Threads::Mutex _update_latency_lock; + typedef std::queue AutoConnectQueue; Glib::Threads::Mutex _auto_connect_queue_lock; AutoConnectQueue _auto_connect_queue; @@ -1661,13 +1618,13 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop double ltc_speed; int32_t ltc_enc_byte; - samplepos_t ltc_enc_pos; + samplepos_t ltc_enc_pos; double ltc_enc_cnt; - samplepos_t ltc_enc_off; + samplepos_t ltc_enc_off; bool restarting; - samplepos_t ltc_prev_cycle; + samplepos_t ltc_prev_cycle; - samplepos_t ltc_timecode_offset; + samplepos_t ltc_timecode_offset; bool ltc_timecode_negative_offset; LatencyRange ltc_out_latency; @@ -1694,6 +1651,9 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop int start_midi_thread (); + bool should_ignore_transport_request (TransportRequestSource, TransportRequestType) const; + bool declick_in_progress () const; + void set_play_loop (bool yn, double speed); void unset_play_loop (); void overwrite_some_buffers (Track *); @@ -1793,15 +1753,27 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop mutable Glib::Threads::Mutex source_lock; - public: +public: + + /* Emited when a new source is added to the session */ + PBD::Signal1< void, boost::shared_ptr > SourceAdded; + PBD::Signal1< void, boost::shared_ptr > SourceRemoved; + typedef std::map > SourceMap; - private: + void foreach_source (boost::function )> f) { + Glib::Threads::Mutex::Lock ls (source_lock); + for (SourceMap::iterator i = sources.begin(); i != sources.end(); ++i) { + f ( (*i).second ); + } + } + + bool playlist_is_active( boost::shared_ptr); + +private: void reset_write_sources (bool mark_write_complete, bool force = false); SourceMap sources; - - private: int load_sources (const XMLNode& node); XMLNode& get_sources_as_xml (); @@ -1903,43 +1875,47 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void process_rtop (SessionEvent*); - void update_latency (bool playback); - enum snapshot_t { NormalSave, SnapshotKeep, SwitchToSnapshot }; - XMLNode& state(bool, snapshot_t snapshot_type = NormalSave); + XMLNode& state (bool save_template, + snapshot_t snapshot_type = NormalSave, + bool only_used_assets = false); + + XMLNode& get_state (); + int set_state (const XMLNode& node, int version); // not idempotent + XMLNode& get_template (); /* click track */ - typedef std::list Clicks; - Clicks clicks; - bool _clicking; - bool _click_rec_only; - boost::shared_ptr _click_io; - boost::shared_ptr _click_gain; - Sample* click_data; - Sample* click_emphasis_data; - samplecnt_t click_length; - samplecnt_t click_emphasis_length; - mutable Glib::Threads::RWLock click_lock; + typedef std::list Clicks; + Clicks clicks; + bool _clicking; + bool _click_rec_only; + boost::shared_ptr _click_io; + boost::shared_ptr _click_gain; + Sample* click_data; + Sample* click_emphasis_data; + samplecnt_t click_length; + samplecnt_t click_emphasis_length; + mutable Glib::Threads::RWLock click_lock; static const Sample default_click[]; static const samplecnt_t default_click_length; static const Sample default_click_emphasis[]; static const samplecnt_t default_click_emphasis_length; - Click *get_click(); + Click* get_click(); samplepos_t _clicks_cleared; - void setup_click_sounds (int which); - void setup_click_sounds (Sample**, Sample const *, samplecnt_t*, samplecnt_t, std::string const &); - void clear_clicks (); - void click (samplepos_t start, samplecnt_t nframes); - void run_click (samplepos_t start, samplecnt_t nframes); - void add_click (samplepos_t pos, bool emphasis); samplecnt_t _count_in_samples; + void setup_click_sounds (int which); + void setup_click_sounds (Sample**, Sample const *, samplecnt_t*, samplecnt_t, std::string const &); + void clear_clicks (); + void click (samplepos_t start, samplecnt_t nframes); + void run_click (samplepos_t start, samplecnt_t nframes); + void add_click (samplepos_t pos, bool emphasis); /* range playback */ @@ -1954,10 +1930,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop Evoral::Range _range_selection; Evoral::Range _object_selection; - void unset_preroll_record_punch (); void unset_preroll_record_trim (); - samplepos_t _preroll_record_punch_pos; samplecnt_t _preroll_record_trim_len; bool _count_in_once; @@ -2069,9 +2043,10 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop MidiClockTicker* midi_clock; - boost::shared_ptr _ltc_input; boost::shared_ptr _ltc_output; + boost::shared_ptr _rt_tasklist; + /* Scene Changing */ SceneChanger* _scene_changer; @@ -2101,6 +2076,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop void rewire_midi_selection_ports (); boost::weak_ptr current_midi_target; + StripableList _soloSelection; //the items that are soloe'd during a solo-selection operation; need to unsolo after the roll + CoreSelection* _selection; bool _global_locate_pending;