From: Laurent Aimar Date: Sat, 23 Aug 2003 22:49:50 +0000 (+0000) Subject: * configure.ac : added --enable-goom and --with-goom-tree. Btw, I use a X-Git-Tag: 0.7.0~1061 X-Git-Url: https://git.sesse.net/?a=commitdiff_plain;h=1312bc9ee83bb3962380e172b87d8711ff164c73;p=vlc * configure.ac : added --enable-goom and --with-goom-tree. Btw, I use a special goom tree source as I was unable to use standard goom library. (I will provide it once mmx/ppc included) * modules/visualization/Modules.am: added goom * include/vlc_block.h src/misc/block.c: introduce a new data block api (not yet tested, ported from my local new input work). --- diff --git a/Makefile.am b/Makefile.am index d2608800b5..2fc6b8fba7 100644 --- a/Makefile.am +++ b/Makefile.am @@ -90,6 +90,7 @@ HEADERS_include = \ include/stream_output.h \ include/variables.h \ include/video_output.h \ + include/vlc_block.h \ include/vlc_common.h \ include/vlc_config.h \ include/vlc_cpu.h \ @@ -317,6 +318,7 @@ SOURCES_libvlc_common = \ src/stream_output/stream_output.c \ src/misc/charset.c \ src/misc/mtime.c \ + src/misc/block.c \ src/misc/modules.c \ src/misc/threads.c \ src/misc/cpu.c \ diff --git a/configure.ac b/configure.ac index 61870dc28f..05c12f38f4 100644 --- a/configure.ac +++ b/configure.ac @@ -1,5 +1,5 @@ dnl Autoconf settings for vlc -dnl $Id: configure.ac,v 1.66 2003/08/23 12:59:31 hartman Exp $ +dnl $Id: configure.ac,v 1.67 2003/08/23 22:49:50 fenrir Exp $ AC_INIT(vlc,0.6.3-cvs) @@ -2846,6 +2846,44 @@ then AX_ADD_PLUGINS([visual]) fi +dnl +dnl goom visualization plugin +dnl +AC_ARG_ENABLE(goom, +[ --enable-goom goom visualisation plugin (default disabled)]) +if test "${enable_goom}" = "yes" +then + AC_ARG_WITH(goom-tree, + [ --with-goom-tree=PATH goom tree for static linking (required)]) + + dnl + dnl test for --with-goom-tree + dnl + if test "${with_goom_tree}" != "no" -a -n "${with_goom_tree}";then + AC_MSG_CHECKING(for libgoom.a in ${with_goom_tree}) + real_goom_tree="`cd ${with_goom_tree} 2>/dev/null && pwd`" + if test -z "${real_goom_tree}"; then + dnl The given directory can't be found + AC_MSG_RESULT(no) + AC_MSG_ERROR([cannot cd to ${with_goom_tree}]) + fi + if test -f "${real_goom_tree}/libgoom.a"; then + AC_MSG_RESULT(${real_goom_tree}/libgoom.a) + AX_ADD_BUILTINS([goom]) + AX_ADD_LDFLAGS([goom],[-L${real_goom_tree} -lgoom]) + AX_ADD_CPPFLAGS([goom],[-I${real_goom_tree}]) + else + dnl The given libgoom wasn't built + AC_MSG_RESULT(no) + AC_MSG_ERROR([cannot find ${real_goom_tree}/libgoom.a, make sure you compiled goom in ${with_goom_tree}]) + fi + else + dnl The --with-goom-tree isn't specified wasn't built + AC_MSG_RESULT(no) + AC_MSG_ERROR([You have to specify a tree with --with-goom-tree]) + fi +fi + dnl dnl SLP access plugin dnl diff --git a/include/vlc_block.h b/include/vlc_block.h new file mode 100644 index 0000000000..ea3ccfadfe --- /dev/null +++ b/include/vlc_block.h @@ -0,0 +1,111 @@ +/***************************************************************************** + * block.h + ***************************************************************************** + * Copyright (C) 2003 VideoLAN + * $Id: vlc_block.h,v 1.1 2003/08/23 22:49:50 fenrir Exp $ + * + * Authors: Laurent Aimar + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. + *****************************************************************************/ + +#ifndef _BLOCK_H +#define _BLOCK_H 1 + + +/* + * block + */ +typedef struct block_sys_t block_sys_t; + +struct block_t +{ + block_t *p_next; + + vlc_bool_t b_frame_display; + vlc_bool_t b_frame_start; + mtime_t i_pts; + mtime_t i_dts; + + int i_buffer; + uint8_t *p_buffer; + + void (*pf_release) ( block_t * ); + + block_t *(*pf_modify) ( block_t *, vlc_bool_t ); + block_t *(*pf_duplicate) ( block_t * ); + block_t *(*pf_realloc) ( block_t *, int i_prebody, int i_body ); + + /* Following fields are private, user should never touch it */ + /* XXX never touch that OK !!! the first that access that will + * have cvs account removed ;) XXX */ + + /* It's an object that should be valid as long as the block_t is valid */ + /* It should become a true block manager to reduce malloc/free */ + vlc_object_t *p_manager; + + /* private member for block_New, .... manager */ + block_sys_t *p_sys; +}; + +struct block_fifo_t +{ + vlc_mutex_t lock; /* fifo data lock */ + vlc_cond_t wait; /* fifo data conditional variable */ + + int i_depth; + block_t *p_first; + block_t **pp_last; +}; + +/* + * block + */ +#define block_New( a, b ) __block_New( VLC_OBJECT(a), b ) +VLC_EXPORT( block_t *, __block_New, ( vlc_object_t *, int ) ); +static inline void block_Release( block_t *p_block ) +{ + p_block->pf_release( p_block ); +} +static inline block_t *block_Modify( block_t *p_block, vlc_bool_t b_willmodify ) +{ + return p_block->pf_modify( p_block, b_willmodify ); +} +static inline block_t *block_Duplicate( block_t *p_block ) +{ + return p_block->pf_duplicate( p_block ); +} +static inline block_t *block_Realloc( block_t *p_block, int i_pre, int i_body ) +{ + return p_block->pf_realloc( p_block, i_pre, i_body ); +} +VLC_EXPORT( void, block_ChainAppend, ( block_t **, block_t * ) ); +VLC_EXPORT( void, block_ChainRelease, ( block_t * ) ); +VLC_EXPORT( int, block_ChainExtract, ( block_t *, void *, int ) ); +VLC_EXPORT( block_t *, block_ChainGather, ( block_t * ) ); + +/* a bit special, only for new/other block manager */ +VLC_EXPORT( block_t *, block_NewEmpty, ( void ) ); + +#define block_FifoNew( a ) __block_FifoNew( VLC_OBJECT(a) ) +VLC_EXPORT( block_fifo_t *, __block_FifoNew, ( vlc_object_t * ) ); +VLC_EXPORT( void, block_FifoRelease, ( block_fifo_t * ) ); +VLC_EXPORT( void, block_FifoEmpty, ( block_fifo_t * ) ); +VLC_EXPORT( int, block_FifoPut, ( block_fifo_t *, block_t * ) ); +VLC_EXPORT( block_t *, block_FifoGet, ( block_fifo_t * ) ); +VLC_EXPORT( block_t *, block_FifoGetFrame, ( block_fifo_t * ) ); +VLC_EXPORT( block_t *, block_FifoShow, ( block_fifo_t * ) ); + +#endif diff --git a/include/vlc_common.h b/include/vlc_common.h index 7949e58887..8bfceced67 100644 --- a/include/vlc_common.h +++ b/include/vlc_common.h @@ -3,7 +3,7 @@ * Collection of useful common types and macros definitions ***************************************************************************** * Copyright (C) 1998, 1999, 2000 VideoLAN - * $Id: vlc_common.h,v 1.74 2003/08/17 23:02:51 fenrir Exp $ + * $Id: vlc_common.h,v 1.75 2003/08/23 22:49:50 fenrir Exp $ * * Authors: Samuel Hocevar * Vincent Seguin @@ -279,6 +279,10 @@ typedef struct bit_stream_t bit_stream_t; typedef struct network_socket_t network_socket_t; typedef struct iso639_lang_t iso639_lang_t; +/* block */ +typedef struct block_t block_t; +typedef struct block_fifo_t block_fifo_t; + /***************************************************************************** * Variable callbacks *****************************************************************************/ diff --git a/modules/visualization/Modules.am b/modules/visualization/Modules.am index e69de29bb2..f075156ec8 100644 --- a/modules/visualization/Modules.am +++ b/modules/visualization/Modules.am @@ -0,0 +1 @@ +SOURCES_goom = goom.c diff --git a/modules/visualization/goom.c b/modules/visualization/goom.c index 19a6bdfedc..bbfe582d2b 100644 --- a/modules/visualization/goom.c +++ b/modules/visualization/goom.c @@ -2,7 +2,7 @@ * goom.c: based on libgoom (see http://ios.free.fr/?page=projet&quoi=1) ***************************************************************************** * Copyright (C) 2003 VideoLAN - * $Id: goom.c,v 1.1 2003/08/23 17:23:45 fenrir Exp $ + * $Id: goom.c,v 1.2 2003/08/23 22:49:50 fenrir Exp $ * * Authors: Laurent Aimar * @@ -34,7 +34,7 @@ #include #include "aout_internal.h" -#include "goom/goom_core.h" +#include "goom_core.h" #define GOOM_WIDTH 160 #define GOOM_HEIGHT 120 diff --git a/src/misc/block.c b/src/misc/block.c new file mode 100644 index 0000000000..2e7db1dce3 --- /dev/null +++ b/src/misc/block.c @@ -0,0 +1,453 @@ +/***************************************************************************** + * block.c + ***************************************************************************** + * Copyright (C) 2003 VideoLAN + * $Id: block.c,v 1.1 2003/08/23 22:49:50 fenrir Exp $ + * + * Authors: Laurent Aimar + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA. + *****************************************************************************/ + +/***************************************************************************** + * Preamble + *****************************************************************************/ +#include +#include + +#include +#include "vlc_block.h" + +/* private */ +struct block_sys_t +{ + vlc_mutex_t lock; + + uint8_t *p_allocated_buffer; + int i_allocated_buffer; + + vlc_bool_t b_modify; /* has it be put in modify state */ + int i_duplicated; /* how many times it has been duplicated (only content) */ + +}; + +static void BlockRelease( block_t *p_block ) +{ + vlc_mutex_lock( &p_block->p_sys->lock ); + + p_block->p_sys->i_duplicated--; + if( p_block->p_sys->i_duplicated < 0 ) + { + vlc_mutex_unlock( &p_block->p_sys->lock ); + free( p_block->p_sys->p_allocated_buffer ); + free( p_block->p_sys ); + free( p_block ); + + return; + } + + vlc_mutex_unlock( &p_block->p_sys->lock ); + free( p_block ); +} + +static block_t *__BlockDupContent( block_t *p_block ) +{ + block_t *p_dup; + + p_dup = block_New( p_block->p_manager, p_block->i_buffer ); + memcpy( p_dup->p_buffer, p_block->p_buffer, p_block->i_buffer ); + p_dup->b_frame_display = p_block->b_frame_display; + p_dup->b_frame_start = p_block->b_frame_start; + p_dup->i_pts = p_block->i_pts; + p_dup->i_dts = p_block->i_dts; + + return p_dup; +} + +static block_t *BlockModify( block_t *p_block, vlc_bool_t b_will_modify ) +{ + block_t *p_mod = p_block; /* by default */ + + vlc_mutex_lock( &p_block->p_sys->lock ); + + if( p_block->p_sys->b_modify == b_will_modify ) + { + vlc_mutex_unlock( &p_block->p_sys->lock ); + return p_block; + } + + if( p_block->p_sys->i_duplicated == 0 ) + { + p_block->p_sys->b_modify = b_will_modify; + vlc_mutex_unlock( &p_block->p_sys->lock ); + return p_block; + } + + /* FIXME we could avoid that + * we just need to create a new p_sys with new mem FIXME */ + p_mod = __BlockDupContent( p_block ); + vlc_mutex_unlock( &p_block->p_sys->lock ); + + BlockRelease( p_block ); + + return p_mod; +} +static block_t *BlockDuplicate( block_t *p_block ) +{ + block_t *p_dup; + + vlc_mutex_lock( &p_block->p_sys->lock ); + if( !p_block->p_sys->b_modify ) + { + p_block->p_sys->i_duplicated++; + vlc_mutex_unlock( &p_block->p_sys->lock ); + p_dup = block_NewEmpty(); + memcpy( p_dup, p_block, sizeof( block_t ) ); + p_dup->p_next = NULL; + return p_dup; + } + p_dup = __BlockDupContent( p_block ); + vlc_mutex_unlock( &p_block->p_sys->lock ); + + return p_dup; +} + +static block_t *BlockRealloc( block_t *p_block, int i_prebody, int i_body ) +{ + + vlc_mutex_lock( &p_block->p_sys->lock ); + if( i_prebody < 0 || + ( p_block->p_buffer - i_prebody > p_block->p_sys->p_allocated_buffer ) ) + { + p_block->p_buffer -= i_prebody; + p_block->i_buffer += i_prebody; + i_prebody = 0; + } + if( i_body < 0 || + ( p_block->p_buffer + i_body < p_block->p_sys->p_allocated_buffer + p_block->p_sys->i_allocated_buffer ) ) + { + p_block->i_buffer = i_body; + i_body = 0; + } + vlc_mutex_unlock( &p_block->p_sys->lock ); + + if( i_prebody > 0 ) + { + block_t *p_rea = block_New( p_block->p_manager, i_prebody + i_body ); + + memcpy( &p_rea->p_buffer[i_prebody], p_block->p_buffer, p_block->i_buffer ); + + return p_rea; + } + + if( i_body > 0 ) + { + int i_start; + block_t *p_rea = BlockModify( p_block, VLC_TRUE ); + + i_start = p_rea->p_buffer - p_rea->p_sys->p_allocated_buffer; + + p_rea->p_sys->i_allocated_buffer += i_body - p_rea->i_buffer; + p_rea->p_sys->p_allocated_buffer = realloc( p_rea->p_sys->p_allocated_buffer, p_rea->p_sys->i_allocated_buffer ); + + p_rea->p_buffer = &p_rea->p_sys->p_allocated_buffer[i_start]; + p_rea->i_buffer = i_body; + + return p_rea; + } + + return p_block; +} +/***************************************************************************** + * Standard block management + * + *****************************************************************************/ +/* to be used by other block managment */ +block_t *block_NewEmpty( void ) +{ + block_t *p_block; + + p_block = malloc( sizeof( block_t ) ); + p_block->p_next = NULL; + p_block->b_frame_display= VLC_TRUE; + p_block->b_frame_start = VLC_FALSE; + p_block->i_pts = 0; + p_block->i_dts = 0; + + p_block->i_buffer = 0; + p_block->p_buffer = NULL; + + p_block->pf_release = NULL; + p_block->pf_duplicate = NULL; + p_block->pf_modify = NULL; + p_block->pf_realloc = NULL; + + p_block->p_sys = NULL; + return p_block; +} + +block_t *__block_New( vlc_object_t *p_obj, int i_size ) +{ + block_t *p_block; + block_sys_t *p_sys; + + + p_block = block_NewEmpty(); + + p_block->i_buffer = i_size; + if( i_size > 0 ) + { + p_block->p_buffer = malloc( i_size ); + } + + p_block->pf_release = BlockRelease; + p_block->pf_duplicate = BlockDuplicate; + p_block->pf_modify = BlockModify; + p_block->pf_realloc = BlockRealloc; + + /* that should be ok (no comunication between multiple p_vlc) */ + p_block->p_manager = p_obj->p_vlc; + + p_block->p_sys = p_sys = malloc( sizeof( block_sys_t ) ); + vlc_mutex_init( p_obj, &p_sys->lock ); + p_sys->p_allocated_buffer = p_block->p_buffer; + p_sys->i_allocated_buffer = p_block->i_buffer; + p_sys->i_duplicated = 0; + p_sys->b_modify = VLC_TRUE; + + return p_block; +} + +void block_ChainAppend( block_t **pp_list, block_t *p_block ) +{ + + if( *pp_list == NULL ) + { + *pp_list = p_block; + } + else + { + block_t *p = *pp_list; + + while( p->p_next ) + { + p = p->p_next; + } + p->p_next = p_block; + } +} + +void block_ChainRelease( block_t *p_block ) +{ + while( p_block ) + { + block_t *p_next; + p_next = p_block->p_next; + p_block->pf_release( p_block ); + p_block = p_next; + } +} + +int block_ChainExtract( block_t *p_list, void *p_data, int i_max ) +{ + block_t *b; + int i_total = 0; + uint8_t *p = p_data; + + for( b = p_list; b != NULL; b = b->p_next ) + { + int i_copy; + + i_copy = __MIN( i_max, b->i_buffer ); + if( i_copy > 0 ) + { + memcpy( p, b->p_buffer, i_copy ); + i_max -= i_copy; + i_total += i_copy; + p += i_copy; + + if( i_max == 0 ) + { + return i_total; + } + } + } + return i_total; +} + +block_t *block_ChainGather( block_t *p_list ) +{ + int i_total = 0; + block_t *b, *g; + + if( p_list->p_next == NULL ) + { + /* only one, so no need */ + return p_list; + } + + for( b = p_list; b != NULL; b = b->p_next ) + { + i_total += b->i_buffer; + } + + g = block_New( p_list->p_manager, i_total ); + block_ChainExtract( p_list, g->p_buffer, g->i_buffer ); + + g->b_frame_display = p_list->b_frame_display; + g->b_frame_start = p_list->b_frame_start; + g->i_pts = p_list->i_pts; + g->i_dts = p_list->i_dts; + + /* free p_list */ + block_ChainRelease( p_list ); + return g; +} + + +/***************************************************************************** + * block_fifo_t managment + *****************************************************************************/ +block_fifo_t * __block_FifoNew ( vlc_object_t *p_obj ) +{ + block_fifo_t *p_fifo; + + p_fifo = malloc( sizeof( vlc_object_t ) ); + vlc_mutex_init( p_obj, &p_fifo->lock ); + vlc_cond_init( p_obj, &p_fifo->wait ); + p_fifo->i_depth = 0; + p_fifo->p_first = NULL; + p_fifo->pp_last = &p_fifo->p_first; + + return p_fifo; +} + +void block_FifoRelease( block_fifo_t *p_fifo ) +{ + block_FifoEmpty( p_fifo ); + vlc_cond_destroy( &p_fifo->wait ); + vlc_mutex_destroy( &p_fifo->lock ); + free( p_fifo ); +} + +void block_FifoEmpty( block_fifo_t *p_fifo ) +{ + block_t *b; + + vlc_mutex_lock( &p_fifo->lock ); + for( b = p_fifo->p_first; b != NULL; ) + { + block_t *p_next; + + p_next = b->p_next; + block_Release( b ); + b = p_next; + } + + p_fifo->i_depth = 0; + p_fifo->p_first = NULL; + p_fifo->pp_last = &p_fifo->p_first; + vlc_mutex_unlock( &p_fifo->lock ); +} + +int block_FifoPut ( block_fifo_t *p_fifo, block_t *p_block ) +{ + int i_size = 0; + vlc_mutex_lock( &p_fifo->lock ); + + do + { + i_size += p_block->i_buffer; + + *p_fifo->pp_last = p_block; + p_fifo->pp_last = &p_block->p_next; + p_fifo->i_depth++; + + p_block = p_block->p_next; + + } while( p_block ); + + /* warm there is data in this fifo */ + vlc_cond_signal( &p_fifo->wait ); + vlc_mutex_unlock( &p_fifo->lock ); + + return i_size; +} + +block_t * block_FifoGet ( block_fifo_t *p_fifo ) +{ + block_t *b; + + vlc_mutex_lock( &p_fifo->lock ); + + if( p_fifo->p_first == NULL ) + { + vlc_cond_wait( &p_fifo->wait, &p_fifo->lock ); + } + + b = p_fifo->p_first; + + p_fifo->p_first = b->p_next; + p_fifo->i_depth--; + + if( p_fifo->p_first == NULL ) + { + p_fifo->pp_last = &p_fifo->p_first; + } + + vlc_mutex_unlock( &p_fifo->lock ); + + b->p_next = NULL; + return( b ); +} + +block_t * block_FifoShow ( block_fifo_t *p_fifo ) +{ + block_t *b; + + vlc_mutex_lock( &p_fifo->lock ); + + if( p_fifo->p_first == NULL ) + { + vlc_cond_wait( &p_fifo->wait, &p_fifo->lock ); + } + + b = p_fifo->p_first; + + vlc_mutex_unlock( &p_fifo->lock ); + + return( b ); + +} + +block_t * block_FifoGetFrame( block_fifo_t *p_fifo ) +{ + block_t *b = NULL; + + for( ;; ) + { + block_t *p_next; + block_ChainAppend( &b, block_FifoGet( p_fifo ) ); + p_next = block_FifoShow( p_fifo ); + if( p_next == NULL || p_next->b_frame_start ) + { + break; + } + } + + return b; +} + + diff --git a/src/misc/modules.c b/src/misc/modules.c index 82bbcefadf..f4e6f1c74a 100644 --- a/src/misc/modules.c +++ b/src/misc/modules.c @@ -2,7 +2,7 @@ * modules.c : Builtin and plugin modules management functions ***************************************************************************** * Copyright (C) 2001 VideoLAN - * $Id: modules.c,v 1.129 2003/08/23 14:14:01 hartman Exp $ + * $Id: modules.c,v 1.130 2003/08/23 22:49:50 fenrir Exp $ * * Authors: Samuel Hocevar * Ethan C. Baldridge @@ -93,6 +93,8 @@ #include "iso_lang.h" #include "charset.h" +#include "vlc_block.h" + #if defined( UNDER_CE ) # define MYCHAR wchar_t #else