* changed transport speed in session and slaves from float to double
authorHans Baier <hansfbaier@googlemail.com>
Fri, 9 Jan 2009 09:18:24 +0000 (09:18 +0000)
committerHans Baier <hansfbaier@googlemail.com>
Fri, 9 Jan 2009 09:18:24 +0000 (09:18 +0000)
* added some comments

git-svn-id: svn://localhost/ardour2/branches/3.0@4394 d708f5d6-7413-0410-9779-e7cbd77b26cf

12 files changed:
libs/ardour/ardour/diskstream.h
libs/ardour/ardour/session.h
libs/ardour/ardour/slave.h
libs/ardour/audio_diskstream.cc
libs/ardour/diskstream.cc
libs/ardour/jack_slave.cc
libs/ardour/midi_clock_slave.cc
libs/ardour/mtc_slave.cc
libs/ardour/session_process.cc
libs/ardour/session_transport.cc
libs/surfaces/control_protocol/basic_ui.cc
libs/surfaces/control_protocol/control_protocol/basic_ui.h

index 955f2ed8e7c6bad3dc72b9703c86cc6bcf13a69a..24655a1d416633e0ef72c368e7399b3b7f579053 100644 (file)
@@ -277,9 +277,13 @@ class Diskstream : public SessionObject
        nframes_t            wrap_buffer_size;
        nframes_t            speed_buffer_size;
 
-       uint64_t                  last_phase;
-       uint64_t                  phi;
-       uint64_t                  target_phi;
+       uint64_t             last_phase;
+       
+       /// diskstream speed in 40.24 fixed point math
+       uint64_t             phi;
+       
+       /// target diskstream speed in 40.24 fixed point math
+       uint64_t             target_phi;
        
        nframes_t            file_frame;                
        nframes_t            playback_sample;
index 81134d16fdfa209bf42c7c173bfa47e5aaf4957a..9d12aa79b83c0d4d015db396ea0205f329504110 100644 (file)
@@ -170,9 +170,9 @@ class Session : public PBD::StatefulDestructible
 
                Type           type;
            Action         action;
-           nframes_t action_frame;
-           nframes_t target_frame;
-           float          speed;
+           nframes_t      action_frame;
+           nframes_t      target_frame;
+           double         speed;
 
            union {
                        void*                ptr;
@@ -187,7 +187,7 @@ class Session : public PBD::StatefulDestructible
            list<AudioRange>     audio_range;
            list<MusicRange>     music_range;
 
-           Event(Type t, Action a, nframes_t when, nframes_t where, float spd, bool yn = false)
+           Event(Type t, Action a, nframes_t when, nframes_t where, double spd, bool yn = false)
                    : type (t),
                      action (a),
                      action_frame (when),
@@ -388,9 +388,9 @@ class Session : public PBD::StatefulDestructible
        void set_session_end (nframes_t end) { end_location->set_start(end); _end_location_is_free = false; }
        void use_rf_shuttle_speed ();
        void allow_auto_play (bool yn);
-       void request_transport_speed (float speed);
+       void request_transport_speed (double speed);
        void request_overwrite_buffer (Diskstream*);
-       void request_diskstream_speed (Diskstream&, float speed);
+       void request_diskstream_speed (Diskstream&, double speed);
        void request_input_change_handling ();
 
        bool locate_pending() const { return static_cast<bool>(post_transport_work&PostTransportLocate); }
@@ -572,7 +572,7 @@ class Session : public PBD::StatefulDestructible
        void        request_slave_source (SlaveSource);
        bool        synced_to_jack() const { return Config->get_slave_source() == JACK; }
 
-       float       transport_speed() const { return _transport_speed; }
+       double      transport_speed() const { return _transport_speed; }
        bool        transport_stopped() const { return _transport_speed == 0.0f; }
        bool        transport_rolling() const { return _transport_speed != 0.0f; }
 
@@ -1023,8 +1023,8 @@ class Session : public PBD::StatefulDestructible
        Location*                start_location;
        Slave*                  _slave;
        bool                    _silent;
-       volatile float          _transport_speed;
-       float                   _last_transport_speed;
+       volatile double         _transport_speed;
+       double                  _last_transport_speed;
        bool                     auto_play_legal;
        nframes_t               _last_slave_transport_frame;
        nframes_t                maximum_output_latency;
@@ -1419,8 +1419,8 @@ class Session : public PBD::StatefulDestructible
        void locate (nframes_t, bool with_roll, bool with_flush, bool with_loop=false);
        void start_locate (nframes_t, bool with_roll, bool with_flush, bool with_loop=false);
        void force_locate (nframes_t frame, bool with_roll = false);
-       void set_diskstream_speed (Diskstream*, float speed);
-       void set_transport_speed (float speed, bool abort = false);
+       void set_diskstream_speed (Diskstream*, double speed);
+       void set_transport_speed (double speed, bool abort = false);
        void stop_transport (bool abort = false);
        void start_transport ();
        void realtime_stop (bool abort);
index 07d7a4cf6af261acfe43a83be27141cdf562a133..1f2610e0281f5eb4befa04133150e38d0064d0ab 100644 (file)
@@ -105,7 +105,7 @@ class Slave {
         * @param position - The transport position requested
         * @return - The return value is currently ignored (see Session::follow_slave)
         */
-       virtual bool speed_and_position (float& speed, nframes_t& position) = 0;
+       virtual bool speed_and_position (double& speed, nframes_t& position) = 0;
        
        /**
         * reports to ARDOUR whether the Slave is currently synced to its external 
@@ -174,7 +174,7 @@ class MTC_Slave : public Slave, public sigc::trackable {
        ~MTC_Slave ();
 
        void rebind (MIDI::Port&);
-       bool speed_and_position (float&, nframes_t&);
+       bool speed_and_position (double&, nframes_t&);
 
        bool locked() const;
        bool ok() const;
@@ -194,12 +194,12 @@ class MTC_Slave : public Slave, public sigc::trackable {
        nframes_t   last_inbound_frame;      /* when we got it; audio clocked */
        MIDI::byte  last_mtc_fps_byte;
 
-       float       mtc_speed;
+       double      mtc_speed;
        nframes_t   first_mtc_frame;
        nframes_t   first_mtc_time;
 
        static const int32_t accumulator_size = 128;
-       float   accumulator[accumulator_size];
+       double   accumulator[accumulator_size];
        int32_t accumulator_index;
        bool    have_first_accumulated_speed;
 
@@ -216,7 +216,7 @@ class MIDIClock_Slave : public Slave, public sigc::trackable {
        ~MIDIClock_Slave ();
 
        void rebind (MIDI::Port&);
-       bool speed_and_position (float&, nframes_t&);
+       bool speed_and_position (double&, nframes_t&);
 
        bool locked() const;
        bool ok() const;
@@ -289,7 +289,7 @@ class ADAT_Slave : public Slave
        ADAT_Slave () {}
        ~ADAT_Slave () {}
 
-       bool speed_and_position (float& speed, nframes_t& pos) {
+       bool speed_and_position (double& speed, nframes_t& pos) {
                speed = 0;
                pos = 0;
                return false;
@@ -307,7 +307,7 @@ class JACK_Slave : public Slave
        JACK_Slave (jack_client_t*);
        ~JACK_Slave ();
 
-       bool speed_and_position (float& speed, nframes_t& pos);
+       bool speed_and_position (double& speed, nframes_t& pos);
 
        bool starting() const { return _starting; }
        bool locked() const;
@@ -319,7 +319,7 @@ class JACK_Slave : public Slave
 
   private:
        jack_client_t* jack;
-       float speed;
+       double speed;
        bool _starting;
 };
 
index 8ba1825759de5ba8f59cf83427625e2843655e20..dbd16e920b20cd03b07e67f96813b884469cad77 100644 (file)
@@ -785,8 +785,17 @@ AudioDiskstream::process (nframes_t transport_frame, nframes_t nframes, nframes_
                        nframes_t i = 0;
 
                        // Linearly interpolate into the alt buffer
-                       // using 40.24 fixp maths (swh)
-
+                       // using 40.24 fixp maths
+                       //
+                       // Fixedpoint is just an integer with an implied scaling factor. 
+                       // In 40.24 the scaling factor is 2^24 = 16777216,  
+                       // so a value of 10*2^24 (in integer space) is equivalent to 10.0. 
+                       //
+                       // The advantage is that addition and modulus [like x = (x + y) % 2^40]  
+                       // has no rounding errors and no drift, and just requires a single integer add.
+                       // (swh)
+
+                       // phi = fixed point speed
                        if (phi != target_phi) {
                                phi_delta = ((int64_t)(target_phi - phi)) / nframes;
                        } else {
@@ -795,7 +804,7 @@ AudioDiskstream::process (nframes_t transport_frame, nframes_t nframes, nframes_
 
                        for (chan = c->begin(); chan != c->end(); ++chan) {
 
-                               float fr;
+                               Sample fractional_part;
                                ChannelInfo* chaninfo (*chan);
 
                                i = 0;
@@ -803,10 +812,10 @@ AudioDiskstream::process (nframes_t transport_frame, nframes_t nframes, nframes_
 
                                for (nframes_t outsample = 0; outsample < nframes; ++outsample) {
                                        i = phase >> 24;
-                                       fr = (phase & 0xFFFFFF) / 16777216.0f;
+                                       fractional_part = (phase & 0xFFFFFF) / 16777216.0f;
                                        chaninfo->speed_buffer[outsample] = 
-                                               chaninfo->current_playback_buffer[i] * (1.0f - fr) +
-                                               chaninfo->current_playback_buffer[i+1] * fr;
+                                               chaninfo->current_playback_buffer[i] * (1.0f - fractional_part) +
+                                               chaninfo->current_playback_buffer[i+1] * fractional_part;
                                        phase += phi + phi_delta;
                                }
                                
index 334e4336af821478b0ed76f31e97e0348513ee97..afd5d214708ba6b145f4053ac6a339a73c16f002 100644 (file)
@@ -109,6 +109,7 @@ Diskstream::init (Flag f)
        wrap_buffer_size = 0;
        speed_buffer_size = 0;
        last_phase = 0;
+       // speed = 1 in 40.24 fixed point math
        phi = (uint64_t) (0x1000000);
        target_phi = phi;
        file_frame = 0;
index 40729d33704056600ccde5f3ca0c8c20329538f4..b7160489ff40d93570a8ae96c3a90483ffe9bba6 100644 (file)
@@ -34,7 +34,7 @@ using namespace sigc;
 JACK_Slave::JACK_Slave (jack_client_t* j)
        : jack (j)
 {
-       float x;
+       double x;
        nframes_t p;
        /* call this to initialize things */
        speed_and_position (x, p);
@@ -63,7 +63,7 @@ JACK_Slave::ok() const
 }
 
 bool 
-JACK_Slave::speed_and_position (float& sp, nframes_t& position) 
+JACK_Slave::speed_and_position (double& sp, nframes_t& position) 
 {
        jack_position_t pos;
        jack_transport_state_t state;
index ec5dc3e5c9f91f88d0881ca15c53eb4d3b6e2d57..f1ec1ad924416f4afd09113a0c4a6e0e61d4282a 100644 (file)
@@ -133,8 +133,8 @@ MIDIClock_Slave::update_midi_clock (Parser& parser, nframes_t timestamp)
 
                // calculate loop error
                // we use session.transport_frame() instead of t1 here
-               // because t1 is used to calculate the transport speed, and since this
-               // is float, the loop will compensate for accumulating rounding errors
+               // because t1 is used to calculate the transport speed,
+               // so the loop will compensate for accumulating rounding errors
                e = (double(last_position) - double(session.transport_frame())) 
                    / double(session.frame_rate());
                
@@ -242,7 +242,7 @@ MIDIClock_Slave::stop_if_no_more_clock_events(nframes_t& pos, nframes_t now)
 }
 
 bool
-MIDIClock_Slave::speed_and_position (float& speed, nframes_t& pos)
+MIDIClock_Slave::speed_and_position (double& speed, nframes_t& pos)
 {
        if (!_started || _starting) {
                speed = 0.0;
@@ -257,15 +257,14 @@ MIDIClock_Slave::speed_and_position (float& speed, nframes_t& pos)
        }
 
        // calculate speed
-       double speed_double = ((t1 - t0) * session.frame_rate()) / one_ppqn_in_frames;
-       speed = float(speed_double);
+       speed = ((t1 - t0) * session.frame_rate()) / one_ppqn_in_frames;
        
        // calculate position
        if (engine_now > last_timestamp) {
                // we are in between MIDI clock messages
                // so we interpolate position according to speed
                nframes_t elapsed = engine_now - last_timestamp;
-               pos = nframes_t (last_position + double(elapsed) * speed_double);
+               pos = nframes_t (last_position + double(elapsed) * speed);
        } else {
                // A new MIDI clock message has arrived this cycle
                pos = last_position;
index 1a8cd589da22f075f3c84bdeee592c2fec3d9c17..e45e76025112e4987fb005db1ea752fe397d873d 100644 (file)
@@ -257,13 +257,13 @@ MTC_Slave::ok() const
 }
 
 bool 
-MTC_Slave::speed_and_position (float& speed, nframes_t& pos)
+MTC_Slave::speed_and_position (double& speed, nframes_t& pos)
 {
        nframes_t now = session.engine().frame_time();
        SafeTime last;
        nframes_t frame_rate;
        nframes_t elapsed;
-       float speed_now;
+       double speed_now;
 
        read_current (&last);
 
@@ -287,7 +287,7 @@ MTC_Slave::speed_and_position (float& speed, nframes_t& pos)
 
        frame_rate = session.frame_rate();
 
-       speed_now = (float) ((last.position - first_mtc_frame) / (double) (now - first_mtc_time));
+       speed_now = (double) ((last.position - first_mtc_frame) / (double) (now - first_mtc_time));
 
        accumulator[accumulator_index++] = speed_now;
 
@@ -297,7 +297,7 @@ MTC_Slave::speed_and_position (float& speed, nframes_t& pos)
        }
 
        if (have_first_accumulated_speed) {
-               float total = 0;
+               double total = 0;
 
                for (int32_t i = 0; i < accumulator_size; ++i) {
                        total += accumulator[i];
index 08f614db0795b105c86af21ce21945c934e69a5a..6247a4d654dd89e10877e972fd07e30065dec28e 100644 (file)
@@ -465,7 +465,7 @@ Session::transport_locked () const
 bool
 Session::follow_slave (nframes_t nframes, nframes_t offset)
 {
-       float slave_speed;
+       double slave_speed;
        nframes_t slave_transport_frame;
        nframes_t this_delta;
        int dir;
index 9163dfd5ea6f54eb2977410425a15ececcb218a8..0649d16848a2a8e9f0d992fe388c0aba93cef8d2 100644 (file)
@@ -74,14 +74,14 @@ Session::request_slave_source (SlaveSource src)
 }
 
 void
-Session::request_transport_speed (float speed)
+Session::request_transport_speed (double speed)
 {
        Event* ev = new Event (Event::SetTransportSpeed, Event::Add, Event::Immediate, 0, speed);
        queue_event (ev);
 }
 
 void
-Session::request_diskstream_speed (Diskstream& ds, float speed)
+Session::request_diskstream_speed (Diskstream& ds, double speed)
 {
        Event* ev = new Event (Event::SetDiskstreamSpeed, Event::Add, Event::Immediate, 0, speed);
        ev->set_ptr (&ds);
@@ -628,7 +628,7 @@ Session::start_locate (nframes_t target_frame, bool with_roll, bool with_flush,
 {
        if (synced_to_jack()) {
 
-               float sp;
+               double sp;
                nframes_t pos;
 
                _slave->speed_and_position (sp, pos);
@@ -799,16 +799,16 @@ Session::locate (nframes_t target_frame, bool with_roll, bool with_flush, bool w
  * @param abort
  */
 void
-Session::set_transport_speed (float speed, bool abort)
+Session::set_transport_speed (double speed, bool abort)
 {
        if (_transport_speed == speed) {
                return;
        }
 
        if (speed > 0) {
-               speed = min (8.0f, speed);
+               speed = min (8.0, speed);
        } else if (speed < 0) {
-               speed = max (-8.0f, speed);
+               speed = max (-8.0, speed);
        }
 
        if (transport_rolling() && speed == 0.0) {
@@ -875,11 +875,11 @@ Session::set_transport_speed (float speed, bool abort)
                        return;
                }
 
-               if (speed > 0.0f && _transport_frame == current_end_frame()) {
+               if (speed > 0.0 && _transport_frame == current_end_frame()) {
                        return;
                }
 
-               if (speed < 0.0f && _transport_frame == 0) {
+               if (speed < 0.0 && _transport_frame == 0) {
                        return;
                }
 
@@ -889,7 +889,7 @@ Session::set_transport_speed (float speed, bool abort)
                   before the last stop, then we have to do extra work.
                */
 
-               if ((_transport_speed && speed * _transport_speed < 0.0f) || (_last_transport_speed * speed < 0.0f) || (_last_transport_speed == 0.0f && speed < 0.0f)) {
+               if ((_transport_speed && speed * _transport_speed < 0.0) || (_last_transport_speed * speed < 0.0) || (_last_transport_speed == 0.0f && speed < 0.0f)) {
                        post_transport_work = PostTransportWork (post_transport_work | PostTransportReverse);
                        last_stop_frame = _transport_frame;
                }
@@ -1144,7 +1144,7 @@ Session::reverse_diskstream_buffers ()
 }
 
 void
-Session::set_diskstream_speed (Diskstream* stream, float speed)
+Session::set_diskstream_speed (Diskstream* stream, double speed)
 {
        if (stream->realtime_set_speed (speed, false)) {
                post_transport_work = PostTransportWork (post_transport_work | PostTransportSpeed);
index b88e002374f4bf2b19ca04b838d75795838e2daf..a0eeda5a96b2bc7fb82d92a5bfa8046b16644d6b 100644 (file)
@@ -184,12 +184,12 @@ BasicUI::next_marker ()
 }
 
 void
-BasicUI::set_transport_speed (float speed)
+BasicUI::set_transport_speed (double speed)
 {
        session->request_transport_speed (speed);
 }
 
-float
+double
 BasicUI::get_transport_speed ()
 {
        return session->transport_speed ();
index c8b5a2a0b65102f26872e6674df59c74c6bf6fae..279d1c6394077c02430df8bd10d0e7c8d94340d8 100644 (file)
@@ -50,8 +50,8 @@ class BasicUI {
        void ffwd ();
        void transport_stop ();
        void transport_play (bool jump_back = true);
-       void set_transport_speed (float speed);
-       float get_transport_speed ();
+       void set_transport_speed (double speed);
+       double get_transport_speed ();
 
        jack_nframes_t transport_frame ();
        void locate (jack_nframes_t frame, bool play = false);