Remove threading dependencies with --disable-multithread
Avoid a pthreads dependency via pthread_once() when compiled with --disable-multithread. In addition, this synchronization is disabled for Win32 as well, even though we can be sure that the required primatives exist, so that the requirements on the application when built with --disable-multithread are consistent across platforms. Users using libvpx built with --disable-multithread in a multithreaded context should provide their own synchronization. Updated the documentation to vpx_codec_enc_init_ver() and vpx_codec_dec_init_ver() to note this requirement. Moved the RTCD initialization call to match this description, as previously it didn't happen until the first frame. Change-Id: Id576f6bce2758362188278d3085051c218a56d4a
This commit is contained in:
@@ -211,6 +211,8 @@ common_top() {
|
|||||||
$(process_forward_decls)
|
$(process_forward_decls)
|
||||||
|
|
||||||
$(declare_function_pointers c $ALL_ARCHS)
|
$(declare_function_pointers c $ALL_ARCHS)
|
||||||
|
|
||||||
|
void ${symbol:-rtcd}(void);
|
||||||
EOF
|
EOF
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -231,11 +233,10 @@ x86() {
|
|||||||
|
|
||||||
cat <<EOF
|
cat <<EOF
|
||||||
$(common_top)
|
$(common_top)
|
||||||
void ${symbol:-rtcd}(void);
|
|
||||||
|
|
||||||
#ifdef RTCD_C
|
#ifdef RTCD_C
|
||||||
#include "vpx_ports/x86.h"
|
#include "vpx_ports/x86.h"
|
||||||
void ${symbol:-rtcd}(void)
|
static void setup_rtcd_internal(void)
|
||||||
{
|
{
|
||||||
int flags = x86_simd_caps();
|
int flags = x86_simd_caps();
|
||||||
|
|
||||||
@@ -261,11 +262,9 @@ arm() {
|
|||||||
$(common_top)
|
$(common_top)
|
||||||
#include "vpx_config.h"
|
#include "vpx_config.h"
|
||||||
|
|
||||||
void ${symbol:-rtcd}(void);
|
|
||||||
|
|
||||||
#ifdef RTCD_C
|
#ifdef RTCD_C
|
||||||
#include "vpx_ports/arm.h"
|
#include "vpx_ports/arm.h"
|
||||||
void ${symbol:-rtcd}(void)
|
static void setup_rtcd_internal(void)
|
||||||
{
|
{
|
||||||
int flags = arm_cpu_caps();
|
int flags = arm_cpu_caps();
|
||||||
|
|
||||||
@@ -285,10 +284,8 @@ unoptimized() {
|
|||||||
$(common_top)
|
$(common_top)
|
||||||
#include "vpx_config.h"
|
#include "vpx_config.h"
|
||||||
|
|
||||||
void ${symbol:-rtcd}(void);
|
|
||||||
|
|
||||||
#ifdef RTCD_C
|
#ifdef RTCD_C
|
||||||
void ${symbol:-rtcd}(void)
|
static void setup_rtcd_internal(void)
|
||||||
{
|
{
|
||||||
$(set_function_pointers c)
|
$(set_function_pointers c)
|
||||||
}
|
}
|
||||||
|
@@ -83,57 +83,6 @@ static int get_cpu_count()
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
#if HAVE_PTHREAD_H
|
|
||||||
#include <pthread.h>
|
|
||||||
static void once(void (*func)(void))
|
|
||||||
{
|
|
||||||
static pthread_once_t lock = PTHREAD_ONCE_INIT;
|
|
||||||
pthread_once(&lock, func);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
#elif defined(_WIN32)
|
|
||||||
static void once(void (*func)(void))
|
|
||||||
{
|
|
||||||
/* Using a static initializer here rather than InitializeCriticalSection()
|
|
||||||
* since there's no race-free context in which to execute it. Protecting
|
|
||||||
* it with an atomic op like InterlockedCompareExchangePointer introduces
|
|
||||||
* an x86 dependency, and InitOnceExecuteOnce requires Vista.
|
|
||||||
*/
|
|
||||||
static CRITICAL_SECTION lock = {(void *)-1, -1, 0, 0, 0, 0};
|
|
||||||
static int done;
|
|
||||||
|
|
||||||
EnterCriticalSection(&lock);
|
|
||||||
|
|
||||||
if (!done)
|
|
||||||
{
|
|
||||||
func();
|
|
||||||
done = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
LeaveCriticalSection(&lock);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
#else
|
|
||||||
/* No-op version that performs no synchronization. vpx_rtcd() is idempotent,
|
|
||||||
* so as long as your platform provides atomic loads/stores of pointers
|
|
||||||
* no synchronization is strictly necessary.
|
|
||||||
*/
|
|
||||||
|
|
||||||
static void once(void (*func)(void))
|
|
||||||
{
|
|
||||||
static int done;
|
|
||||||
|
|
||||||
if(!done)
|
|
||||||
{
|
|
||||||
func();
|
|
||||||
done = 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
void vp8_machine_specific_config(VP8_COMMON *ctx)
|
void vp8_machine_specific_config(VP8_COMMON *ctx)
|
||||||
{
|
{
|
||||||
#if CONFIG_MULTITHREAD
|
#if CONFIG_MULTITHREAD
|
||||||
@@ -145,6 +94,4 @@ void vp8_machine_specific_config(VP8_COMMON *ctx)
|
|||||||
#elif ARCH_X86 || ARCH_X86_64
|
#elif ARCH_X86 || ARCH_X86_64
|
||||||
ctx->cpu_caps = x86_simd_caps();
|
ctx->cpu_caps = x86_simd_caps();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
once(vpx_rtcd);
|
|
||||||
}
|
}
|
||||||
|
@@ -10,3 +10,60 @@
|
|||||||
#include "vpx_config.h"
|
#include "vpx_config.h"
|
||||||
#define RTCD_C
|
#define RTCD_C
|
||||||
#include "vpx_rtcd.h"
|
#include "vpx_rtcd.h"
|
||||||
|
|
||||||
|
#if CONFIG_MULTITHREAD && HAVE_PTHREAD_H
|
||||||
|
#include <pthread.h>
|
||||||
|
static void once(void (*func)(void))
|
||||||
|
{
|
||||||
|
static pthread_once_t lock = PTHREAD_ONCE_INIT;
|
||||||
|
pthread_once(&lock, func);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#elif CONFIG_MULTITHREAD && defined(_WIN32)
|
||||||
|
#include <windows.h>
|
||||||
|
static void once(void (*func)(void))
|
||||||
|
{
|
||||||
|
/* Using a static initializer here rather than InitializeCriticalSection()
|
||||||
|
* since there's no race-free context in which to execute it. Protecting
|
||||||
|
* it with an atomic op like InterlockedCompareExchangePointer introduces
|
||||||
|
* an x86 dependency, and InitOnceExecuteOnce requires Vista.
|
||||||
|
*/
|
||||||
|
static CRITICAL_SECTION lock = {(void *)-1, -1, 0, 0, 0, 0};
|
||||||
|
static int done;
|
||||||
|
|
||||||
|
EnterCriticalSection(&lock);
|
||||||
|
|
||||||
|
if (!done)
|
||||||
|
{
|
||||||
|
func();
|
||||||
|
done = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
LeaveCriticalSection(&lock);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#else
|
||||||
|
/* No-op version that performs no synchronization. vpx_rtcd() is idempotent,
|
||||||
|
* so as long as your platform provides atomic loads/stores of pointers
|
||||||
|
* no synchronization is strictly necessary.
|
||||||
|
*/
|
||||||
|
|
||||||
|
static void once(void (*func)(void))
|
||||||
|
{
|
||||||
|
static int done;
|
||||||
|
|
||||||
|
if(!done)
|
||||||
|
{
|
||||||
|
func();
|
||||||
|
done = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
void vpx_rtcd()
|
||||||
|
{
|
||||||
|
once(setup_rtcd_internal);
|
||||||
|
}
|
||||||
|
@@ -9,6 +9,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include "vpx_rtcd.h"
|
||||||
#include "vpx/vpx_codec.h"
|
#include "vpx/vpx_codec.h"
|
||||||
#include "vpx/internal/vpx_codec_internal.h"
|
#include "vpx/internal/vpx_codec_internal.h"
|
||||||
#include "vpx_version.h"
|
#include "vpx_version.h"
|
||||||
@@ -568,6 +569,8 @@ static vpx_codec_err_t vp8e_init(vpx_codec_ctx_t *ctx,
|
|||||||
|
|
||||||
struct VP8_COMP *optr;
|
struct VP8_COMP *optr;
|
||||||
|
|
||||||
|
vpx_rtcd();
|
||||||
|
|
||||||
if (!ctx->priv)
|
if (!ctx->priv)
|
||||||
{
|
{
|
||||||
priv = calloc(1, sizeof(struct vpx_codec_alg_priv));
|
priv = calloc(1, sizeof(struct vpx_codec_alg_priv));
|
||||||
|
@@ -11,6 +11,7 @@
|
|||||||
|
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
#include "vpx_rtcd.h"
|
||||||
#include "vpx/vpx_decoder.h"
|
#include "vpx/vpx_decoder.h"
|
||||||
#include "vpx/vp8dx.h"
|
#include "vpx/vp8dx.h"
|
||||||
#include "vpx/internal/vpx_codec_internal.h"
|
#include "vpx/internal/vpx_codec_internal.h"
|
||||||
@@ -187,6 +188,8 @@ static vpx_codec_err_t vp8_init(vpx_codec_ctx_t *ctx,
|
|||||||
vpx_codec_err_t res = VPX_CODEC_OK;
|
vpx_codec_err_t res = VPX_CODEC_OK;
|
||||||
(void) data;
|
(void) data;
|
||||||
|
|
||||||
|
vpx_rtcd();
|
||||||
|
|
||||||
/* This function only allocates space for the vpx_codec_alg_priv_t
|
/* This function only allocates space for the vpx_codec_alg_priv_t
|
||||||
* structure. More memory may be required at the time the stream
|
* structure. More memory may be required at the time the stream
|
||||||
* information becomes known.
|
* information becomes known.
|
||||||
|
@@ -113,6 +113,10 @@ extern "C" {
|
|||||||
* function directly, to ensure that the ABI version number parameter
|
* function directly, to ensure that the ABI version number parameter
|
||||||
* is properly initialized.
|
* is properly initialized.
|
||||||
*
|
*
|
||||||
|
* If the library was configured with --disable-multithread, this call
|
||||||
|
* is not thread safe and should be guarded with a lock if being used
|
||||||
|
* in a multithreaded context.
|
||||||
|
*
|
||||||
* In XMA mode (activated by setting VPX_CODEC_USE_XMA in the flags
|
* In XMA mode (activated by setting VPX_CODEC_USE_XMA in the flags
|
||||||
* parameter), the storage pointed to by the cfg parameter must be
|
* parameter), the storage pointed to by the cfg parameter must be
|
||||||
* kept readable and stable until all memory maps have been set.
|
* kept readable and stable until all memory maps have been set.
|
||||||
|
@@ -655,6 +655,10 @@ extern "C" {
|
|||||||
* function directly, to ensure that the ABI version number parameter
|
* function directly, to ensure that the ABI version number parameter
|
||||||
* is properly initialized.
|
* is properly initialized.
|
||||||
*
|
*
|
||||||
|
* If the library was configured with --disable-multithread, this call
|
||||||
|
* is not thread safe and should be guarded with a lock if being used
|
||||||
|
* in a multithreaded context.
|
||||||
|
*
|
||||||
* In XMA mode (activated by setting VPX_CODEC_USE_XMA in the flags
|
* In XMA mode (activated by setting VPX_CODEC_USE_XMA in the flags
|
||||||
* parameter), the storage pointed to by the cfg parameter must be
|
* parameter), the storage pointed to by the cfg parameter must be
|
||||||
* kept readable and stable until all memory maps have been set.
|
* kept readable and stable until all memory maps have been set.
|
||||||
|
Reference in New Issue
Block a user