gnash-commit
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Gnash-commit] gnash ChangeLog backend/sound_handler_gst.cpp b...


From: Tomas Groth
Subject: [Gnash-commit] gnash ChangeLog backend/sound_handler_gst.cpp b...
Date: Thu, 21 Jun 2007 09:02:06 +0000

CVSROOT:        /sources/gnash
Module name:    gnash
Changes by:     Tomas Groth <tgc>       07/06/21 09:02:06

Modified files:
        .              : ChangeLog 
        backend        : sound_handler_gst.cpp sound_handler_gst.h 
                         sound_handler_sdl.cpp sound_handler_sdl.h 

Log message:
                * backend/sound_handler_gst.{cpp,h}: Made it threadsafe, fixes 
                  bug #20186. Made the internal variables private.
                * backend/sound_handler_sdl.{cpp,h}: Made the internal
                  variables private.

CVSWeb URLs:
http://cvs.savannah.gnu.org/viewcvs/gnash/ChangeLog?cvsroot=gnash&r1=1.3592&r2=1.3593
http://cvs.savannah.gnu.org/viewcvs/gnash/backend/sound_handler_gst.cpp?cvsroot=gnash&r1=1.48&r2=1.49
http://cvs.savannah.gnu.org/viewcvs/gnash/backend/sound_handler_gst.h?cvsroot=gnash&r1=1.9&r2=1.10
http://cvs.savannah.gnu.org/viewcvs/gnash/backend/sound_handler_sdl.cpp?cvsroot=gnash&r1=1.69&r2=1.70
http://cvs.savannah.gnu.org/viewcvs/gnash/backend/sound_handler_sdl.h?cvsroot=gnash&r1=1.25&r2=1.26

Patches:
Index: ChangeLog
===================================================================
RCS file: /sources/gnash/gnash/ChangeLog,v
retrieving revision 1.3592
retrieving revision 1.3593
diff -u -b -r1.3592 -r1.3593
--- ChangeLog   21 Jun 2007 07:22:27 -0000      1.3592
+++ ChangeLog   21 Jun 2007 09:02:05 -0000      1.3593
@@ -1,3 +1,10 @@
+2007-06-21 Tomas Groth Christensen <address@hidden>
+
+       * backend/sound_handler_gst.{cpp,h}: Made it threadsafe, fixes 
+         bug #20186. Made the internal variables private.
+       * backend/sound_handler_sdl.{cpp,h}: Made the internal
+         variables private.
+
 2007-06-21 Zou Lunkai <address@hidden>
 
        * testsuite/actionscript.all/enumerate.as: more tests.

Index: backend/sound_handler_gst.cpp
===================================================================
RCS file: /sources/gnash/gnash/backend/sound_handler_gst.cpp,v
retrieving revision 1.48
retrieving revision 1.49
diff -u -b -r1.48 -r1.49
--- backend/sound_handler_gst.cpp       7 Jun 2007 12:10:21 -0000       1.48
+++ backend/sound_handler_gst.cpp       21 Jun 2007 09:02:05 -0000      1.49
@@ -20,7 +20,7 @@
 // Based on sound_handler_sdl.cpp by Thatcher Ulrich http://tulrich.com 2003
 // which has been donated to the Public Domain.
 
-/* $Id: sound_handler_gst.cpp,v 1.48 2007/06/07 12:10:21 tgc Exp $ */
+/* $Id: sound_handler_gst.cpp,v 1.49 2007/06/21 09:02:05 tgc Exp $ */
 
 #ifdef HAVE_CONFIG_H
 #include "config.h"
@@ -44,6 +44,8 @@
 
 #define BUFFER_SIZE 5000
 
+using namespace boost;
+
 GST_sound_handler::GST_sound_handler()
        : looping(false),
          muted(false)
@@ -73,6 +75,8 @@
 // can be use for playing it.
 {
 
+       mutex::scoped_lock lock(_mutex);
+
        sound_data *sounddata = new sound_data;
        if (!sounddata) {
                gnash::log_error(_("Could not allocate memory for sound data"));
@@ -135,6 +139,7 @@
 // this gets called when a stream gets more data
 long   GST_sound_handler::fill_stream_data(void* data, int data_bytes, int 
/*sample_count*/, int handle_id)
 {
+       mutex::scoped_lock lock(_mutex);
        
        // @@ does a negative handle_id have any meaning ?
        //    should we change it to unsigned instead ?
@@ -146,15 +151,16 @@
                guint8* tmp_data = new guint8[data_bytes + 
sounddata->data_size];
                memcpy(tmp_data, sounddata->data, sounddata->data_size);
                memcpy(tmp_data + sounddata->data_size, data, data_bytes);
-               delete [] sounddata->data;
+               if (sounddata->data_size > 0) delete [] sounddata->data;
                sounddata->data = tmp_data;
                
                sounddata->data_size += data_bytes;
 
+               // If playback has already started, we also update the active 
sounds
                for (size_t i=0, e=sounddata->m_gst_elements.size(); i < e; 
++i) {
                        gst_elements* sound = sounddata->m_gst_elements[i];
                        sound->data_size = sounddata->data_size;
-                       sound->data = sounddata->data;
+                       sound->set_data(tmp_data);
                }
 
                return sounddata->data_size - data_bytes;
@@ -171,10 +177,13 @@
 }
 
 // The callback function which refills the buffer with data
-static void callback_handoff (GstElement * /*c*/, GstBuffer *buffer, GstPad* 
/*pad*/, gpointer user_data)
+void GST_sound_handler::callback_handoff (GstElement * /*c*/, GstBuffer 
*buffer, GstPad* /*pad*/, gpointer user_data)
 {
        gst_elements *gstelements = static_cast<gst_elements*>(user_data);
-       guint8* data_pos = gstelements->data+gstelements->position;
+
+       mutex::scoped_lock lock(gstelements->handler->_mutex);
+
+       guint8* data_pos = gstelements->get_data_ptr(gstelements->position);
 
        // First callback
        if (GST_BUFFER_SIZE(buffer) == 0) {
@@ -218,7 +227,7 @@
                } else {
                        // Copy what's left of the data, and then fill the rest 
with "new" data.
                        memcpy(GST_BUFFER_DATA(buffer), data_pos,  chunk_size);
-                       memcpy(GST_BUFFER_DATA(buffer) + chunk_size, 
gstelements->data, GST_BUFFER_SIZE(buffer)- chunk_size);
+                       memcpy(GST_BUFFER_DATA(buffer) + chunk_size, 
gstelements->get_data_ptr(0), GST_BUFFER_SIZE(buffer)- chunk_size);
                        gstelements->position = GST_BUFFER_SIZE(buffer) - 
chunk_size;
                        gstelements->loop_count--;
 
@@ -238,6 +247,7 @@
 void   GST_sound_handler::play_sound(int sound_handle, int loop_count, int 
/*offset*/, long start_position, const std::vector<sound_envelope>* 
/*envelopes*/)
 // Play the index'd sample.
 {
+       mutex::scoped_lock lock(_mutex);
 
        // Check if the sound exists, or if audio is muted
        if (sound_handle < 0 || (unsigned int) sound_handle >= 
m_sound_data.size() || muted)
@@ -269,9 +279,13 @@
                gnash::log_error (_("Could not allocate memory for 
gst_element"));
                return;
        }
+
+       // Set the handler
+       gst_element->handler = this;
+
        // Copy data-info to the "gst_elements"
        gst_element->data_size = sounddata->data_size;
-       gst_element->data = sounddata->data;
+       gst_element->set_data(sounddata->data);
        gst_element->position = start_position;
 
        // Set number of loop we should do. -1 is infinte loop, 0 plays it 
once, 1 twice etc.
@@ -440,6 +454,7 @@
 
 void   GST_sound_handler::stop_sound(int sound_handle)
 {
+       mutex::scoped_lock lock(_mutex);
        
        // Check if the sound exists.
        if (sound_handle < 0 || (unsigned int) sound_handle >= 
m_sound_data.size())
@@ -479,6 +494,7 @@
 void   GST_sound_handler::delete_sound(int sound_handle)
 // this gets called when it's done with a sample.
 {
+       mutex::scoped_lock lock(_mutex);
        
        if (sound_handle >= 0 && (unsigned int) sound_handle < 
m_sound_data.size())
        {
@@ -503,6 +519,8 @@
 //     where 0 is off and 100 is full volume. The default setting is 100.
 int    GST_sound_handler::get_volume(int sound_handle) {
 
+       mutex::scoped_lock lock(_mutex);
+
        // Check if the sound exists.
        if (sound_handle >= 0 && (unsigned int) sound_handle < 
m_sound_data.size())
        {
@@ -517,6 +535,8 @@
 //     100 is full volume and 0 is no volume. The default setting is 100.
 void   GST_sound_handler::set_volume(int sound_handle, int volume) {
 
+       mutex::scoped_lock lock(_mutex);
+
        // Check if the sound exists.
        if (sound_handle < 0 || (unsigned int) sound_handle >= 
m_sound_data.size())
        {
@@ -543,6 +563,8 @@
 
 void GST_sound_handler::get_info(int sound_handle, int* format, bool* stereo) {
 
+       mutex::scoped_lock lock(_mutex);
+
        // Check if the sound exists.
        if (sound_handle >= 0 && (unsigned int) sound_handle < 
m_sound_data.size())
        {
@@ -577,6 +599,16 @@
        gnash::log_unimpl(__PRETTY_FUNCTION__);
 }
 
+// Pointer handling and checking functions
+uint8_t* gst_elements::get_data_ptr(unsigned long int pos) {
+       assert(data_size > pos);
+       return data + pos;
+}
+
+void gst_elements::set_data(uint8_t* idata) {
+       data = idata;
+}
+
 gnash::sound_handler*  gnash::create_sound_handler_gst()
 // Factory.
 {

Index: backend/sound_handler_gst.h
===================================================================
RCS file: /sources/gnash/gnash/backend/sound_handler_gst.h,v
retrieving revision 1.9
retrieving revision 1.10
diff -u -b -r1.9 -r1.10
--- backend/sound_handler_gst.h 28 May 2007 15:40:57 -0000      1.9
+++ backend/sound_handler_gst.h 21 Jun 2007 09:02:06 -0000      1.10
@@ -23,9 +23,15 @@
 #include <vector>
 
 #include <gst/gst.h>
+#include <boost/thread/thread.hpp>
+#include <boost/bind.hpp>
+#include <boost/thread/mutex.hpp>
 
 #define BUFFER_SIZE 5000
 
+// forward declaration
+class GST_sound_handler;
+
 // Used to hold the gstreamer when doing on-demand-decoding
 class gst_elements
 {
@@ -49,9 +55,6 @@
        // position in the stream
        long position;
 
-       // The (un)compressed data
-       guint8* data;
-
        // data size
        long data_size;
 
@@ -60,6 +63,20 @@
        // signal id
        guint handoff_signal_id;
 
+       // The sound handler. Used to get access to the 
GST_sound_handler->_mutex
+       GST_sound_handler* handler;
+
+       /// Returns the data pointer in the undecoded datastream
+       /// for the given position. Boundaries are checked.
+       uint8_t* get_data_ptr(unsigned long int pos);
+
+       /// Set the undecoded data pointer
+       void set_data(uint8_t*);
+
+private:
+       // The (un)compressed data
+       guint8* data;
+
 };
 
 
@@ -97,7 +114,7 @@
 // Use gstreamer to handle sounds.
 class GST_sound_handler : public gnash::sound_handler
 {
-public:
+private:
        /// Vector containing all the sounds
        std::vector<sound_data*>        m_sound_data;
        
@@ -107,6 +124,14 @@
        /// Is the audio muted?
        bool muted;
 
+       /// Mutex for making sure threads doesn't mess things up
+       boost::mutex _mutex;
+
+public:
+
+       /// Gstreamer callback function
+       static void callback_handoff (GstElement * /*c*/, GstBuffer *buffer, 
GstPad* /*pad*/, gpointer user_data);
+
        GST_sound_handler();
        virtual ~GST_sound_handler();
 

Index: backend/sound_handler_sdl.cpp
===================================================================
RCS file: /sources/gnash/gnash/backend/sound_handler_sdl.cpp,v
retrieving revision 1.69
retrieving revision 1.70
diff -u -b -r1.69 -r1.70
--- backend/sound_handler_sdl.cpp       8 Jun 2007 11:38:17 -0000       1.69
+++ backend/sound_handler_sdl.cpp       21 Jun 2007 09:02:06 -0000      1.70
@@ -18,7 +18,7 @@
 // Based on sound_handler_sdl.cpp by Thatcher Ulrich http://tulrich.com 2003
 // which has been donated to the Public Domain.
 
-// $Id: sound_handler_sdl.cpp,v 1.69 2007/06/08 11:38:17 tgc Exp $
+// $Id: sound_handler_sdl.cpp,v 1.70 2007/06/21 09:02:06 tgc Exp $
 
 #ifdef HAVE_CONFIG_H
 #include "config.h"
@@ -33,8 +33,6 @@
 
 using namespace boost;
 
-static void sdl_audio_callback(void *udata, Uint8 *stream, int len); // SDL C 
audio handler
-
 SDL_sound_handler::SDL_sound_handler()
        : soundOpened(false),
                soundsPlaying(0),
@@ -44,7 +42,7 @@
        audioSpec.freq = 44100;
        audioSpec.format = AUDIO_S16SYS; // AUDIO_S8 AUDIO_U8;
        audioSpec.channels = 2;
-       audioSpec.callback = sdl_audio_callback;
+       audioSpec.callback = SDL_sound_handler::sdl_audio_callback;
        audioSpec.userdata = this;
        audioSpec.samples = 2048;               //512 - not enough for  
videostream
 }
@@ -650,36 +648,8 @@
 }
 
 
-/// Callback invoked by the SDL audio thread.
-//
-/// Refills the output stream/buffer with data.
-///
-/// We run trough all the attached auxiliary streamers fetching decoded
-/// audio blocks and mixing them into the given output stream.
-///
-/// <UnverifiedComment>
-///   If sound is compresssed (mp3) a mp3-frame is decoded into a buffer,
-///   and resampled if needed. When the buffer has been sampled, another
-///   frame is decoded until all frames has been decoded.
-///   If a sound is looping it will be decoded from the beginning again.
-/// </UnverifiedComment>
-///
-/// TODO: make a static method of the SDL_sound_handler class
-///
-/// @param udata
-///    User data pointer (SDL_sound_handler instance in our case).
-///    We'll lock the SDL_sound_handler::_mutex during operations.
-///
-/// @param stream
-///    The output stream/buffer to fill
-///
-/// @param buffer_length_in
-///    Length of the buffer.
-///    If zero or negative we log an error and return
-///    (negative is probably an SDL bug, zero dunno yet).
-///
-static void
-sdl_audio_callback (void *udata, Uint8 *stream, int buffer_length_in)
+// Callback invoked by the SDL audio thread.
+void SDL_sound_handler::sdl_audio_callback (void *udata, Uint8 *stream, int 
buffer_length_in)
 {
        if ( buffer_length_in < 0 )
        {

Index: backend/sound_handler_sdl.h
===================================================================
RCS file: /sources/gnash/gnash/backend/sound_handler_sdl.h,v
retrieving revision 1.25
retrieving revision 1.26
diff -u -b -r1.25 -r1.26
--- backend/sound_handler_sdl.h 28 May 2007 15:40:58 -0000      1.25
+++ backend/sound_handler_sdl.h 21 Jun 2007 09:02:06 -0000      1.26
@@ -14,7 +14,7 @@
 // along with this program; if not, write to the Free Software
 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 
-// $Id: sound_handler_sdl.h,v 1.25 2007/05/28 15:40:58 ann Exp $
+// $Id: sound_handler_sdl.h,v 1.26 2007/06/21 09:02:06 tgc Exp $
 
 #ifndef SOUND_HANDLER_SDL_H
 #define SOUND_HANDLER_SDL_H
@@ -145,7 +145,7 @@
 // Use SDL and ffmpeg/mad/nothing to handle sounds.
 class SDL_sound_handler : public gnash::sound_handler
 {
-public:
+private:
        /// NetStream audio callbacks
        hash_wrapper< void* /* owner */, aux_streamer_ptr /* callback */> 
m_aux_streamer;       //vv
 
@@ -167,6 +167,7 @@
        /// Mutex for making sure threads doesn't mess things up
        boost::mutex _mutex;
 
+public:
        SDL_sound_handler();
        virtual ~SDL_sound_handler();
 
@@ -212,6 +213,34 @@
 
        virtual void    attach_aux_streamer(aux_streamer_ptr ptr, void* owner); 
//vv
        virtual void    detach_aux_streamer(void* owner);       //vv
+
+       /// Callback invoked by the SDL audio thread.
+       //
+       /// Refills the output stream/buffer with data.
+       ///
+       /// We run trough all the attached auxiliary streamers fetching decoded
+       /// audio blocks and mixing them into the given output stream.
+       ///
+       /// If sound is compresssed (mp3) a mp3-frame is decoded into a buffer,
+       /// and resampled if needed. When the buffer has been sampled, another
+       /// frame is decoded until all frames has been decoded.
+       /// If a sound is looping it will be decoded from the beginning again.
+       ///
+       /// TODO: make a static method of the SDL_sound_handler class
+       ///
+       /// @param udata
+       ///     User data pointer (SDL_sound_handler instance in our case).
+       ///     We'll lock the SDL_sound_handler::_mutex during operations.
+       ///
+       /// @param stream
+       ///     The output stream/buffer to fill
+       ///
+       /// @param buffer_length_in
+       ///     Length of the buffer.
+       ///     If zero or negative we log an error and return
+       ///     (negative is probably an SDL bug, zero dunno yet).
+       ///
+       static void sdl_audio_callback (void *udata, Uint8 *stream, int 
buffer_length_in);
 };
 
 




reply via email to

[Prev in Thread] Current Thread [Next in Thread]