Chrome's Native Client backend implementation

This commit is contained in:
Gabriel Jacobo 2014-06-06 15:45:59 -03:00
parent 04a0836b1a
commit 1e352d7929
37 changed files with 2265 additions and 10 deletions

60
README-nacl.txt Normal file
View File

@ -0,0 +1,60 @@
================================================================================
Simple DirectMedia Layer for Native Client
================================================================================
Requirements:
* Native Client SDK (https://developer.chrome.com/native-client),
(tested with Pepper version 33 or higher).
The SDL backend for Chrome's Native Client has been tested only with the PNaCl
toolchain, which generates binaries designed to run on ARM and x86_32/64
platforms. This does not mean it won't work with the other toolchains!
================================================================================
Building SDL for NaCl
================================================================================
Set up the right environment variables (see naclbuild.sh), then configure SDL with:
configure --host=pnacl --prefix some/install/destination
Then "make".
As an example of how to create a deployable app a Makefile project is provided
in test/nacl/Makefile, which includes some monkey patching of the common.mk file
provided by NaCl, without which linking properly to SDL won't work (the search
path can't be modified externally, so the linker won't find SDL's binaries unless
you dump them into the SDK path, which is inconvenient).
Also provided in test/nacl is the required support file, such as index.html,
manifest.json, etc.
================================================================================
Running tests
================================================================================
Due to the nature of NaCl programs, building and running SDL tests is not as
straightforward as one would hope. The script naclbuild.sh in build-scripts
automates the process and should serve as a guide for users of SDL trying to build
their own applications.
Basic usage:
./naclbuild.sh path/to/pepper/toolchain (i.e. ~/naclsdk/pepper_35)
This will build testgles2.c by default.
If you want to build a different test, for example testrendercopyex.c:
SOURCES=~/sdl/SDL/test/testrendercopyex.c ./naclbuild.sh ~/naclsdk/pepper_35
Once the build finishes, you have to serve the contents with a web server (the
script will give you instructions on how to do that with Python).
================================================================================
TODO - Known Issues
================================================================================
* Audio backend is not usable yet.
* Testing of all systems with a real application (something other than SDL's tests)

View File

@ -9,6 +9,7 @@ General:
* Added an event SDL_RENDER_DEVICE_RESET that is sent from the D3D renderers * Added an event SDL_RENDER_DEVICE_RESET that is sent from the D3D renderers
when the D3D device is lost, and from Android's event loop when the GLES when the D3D device is lost, and from Android's event loop when the GLES
context had to be re created. context had to be re created.
* Native Client backend
--------------------------------------------------------------------------- ---------------------------------------------------------------------------
2.0.3: 2.0.3:

View File

@ -359,6 +359,19 @@ case $basic_machine in
i*86 | x86_64) i*86 | x86_64)
basic_machine=$basic_machine-pc basic_machine=$basic_machine-pc
;; ;;
nacl64*)
basic_machine=x86_64-pc
os=-nacl
;;
nacl*)
basic_machine=i686-pc
os=-nacl
;;
pnacl*)
# le32-unknown-pnacl comes from http://www.chromium.org/nativeclient/pnacl/stability-of-the-pnacl-bitcode-abi
basic_machine=le32-unknown
os=-pnacl
;;
# Object if more than one company name word. # Object if more than one company name word.
*-*-*) *-*-*)
echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
@ -843,6 +856,10 @@ case $basic_machine in
basic_machine=le32-unknown basic_machine=le32-unknown
os=-nacl os=-nacl
;; ;;
pnacl)
basic_machine=le32-unknown
os=-pnacl
;;
ncr3000) ncr3000)
basic_machine=i486-ncr basic_machine=i486-ncr
os=-sysv4 os=-sysv4
@ -1384,6 +1401,12 @@ case $os in
;; ;;
esac esac
;; ;;
-nacl*)
os=-nacl
;;
-pnacl*)
os=-pnacl
;;
-nto-qnx*) -nto-qnx*)
;; ;;
-nto*) -nto*)
@ -1506,6 +1529,10 @@ case $os in
os=-dicos os=-dicos
;; ;;
-nacl*) -nacl*)
os=-nacl
;;
-pnacl*)
os=-pnacl
;; ;;
-none) -none)
;; ;;

105
build-scripts/naclbuild.sh Normal file
View File

@ -0,0 +1,105 @@
#!/bin/bash
if [ -z "$1" ] && [ -z "$NACL_SDK_ROOT" ]; then
echo "Usage: ./naclbuild ~/nacl/pepper_33"
echo "This will build SDL for Native Client, and testgles2.c as a demo"
echo "You can set env vars CC, AR, LD and RANLIB to override the default PNaCl toolchain used"
echo "You can set env var SOURCES to select a different source file than testgles2.c"
exit 1
fi
if [ -n "$1" ]; then
NACL_SDK_ROOT="$1"
fi
CC=""
if [ -n "$2" ]; then
CC="$2"
fi
echo "Using SDK at $NACL_SDK_ROOT"
export NACL_SDK_ROOT="$NACL_SDK_ROOT"
export CFLAGS="$CFLAGS -I$NACL_SDK_ROOT/include"
NCPUS="1"
case "$OSTYPE" in
darwin*)
NCPU=`sysctl -n hw.ncpu`
;;
linux*)
if [ -n `which nproc` ]; then
NCPUS=`nproc`
fi
;;
*);;
esac
CURDIR=`pwd -P`
SDLPATH="$( cd "$(dirname "$0")/.." ; pwd -P )"
BUILDPATH="$SDLPATH/build/nacl"
TESTBUILDPATH="$BUILDPATH/test"
SDL2_STATIC="$BUILDPATH/build/.libs/libSDL2.a"
mkdir -p $BUILDPATH
mkdir -p $TESTBUILDPATH
if [ -z "$CC" ]; then
export CC="$NACL_SDK_ROOT/toolchain/linux_pnacl/bin/pnacl-clang"
fi
if [ -z "$AR" ]; then
export AR="$NACL_SDK_ROOT/toolchain/linux_pnacl/bin/pnacl-ar"
fi
if [ -z "$LD" ]; then
export LD="$NACL_SDK_ROOT/toolchain/linux_pnacl/bin/pnacl-ar"
fi
if [ -z "$RANLIB" ]; then
export RANLIB="$NACL_SDK_ROOT/toolchain/linux_pnacl/bin/pnacl-ranlib"
fi
if [ -z "$SOURCES" ]; then
export SOURCES="$SDLPATH/test/testgles2.c"
fi
if [ ! -f "$CC" ]; then
echo "Could not find compiler at $CC"
exit 1
fi
cd $BUILDPATH
$SDLPATH/configure --host=pnacl --prefix $TESTBUILDPATH
make -j$NCPUS CFLAGS="$CFLAGS -I./include"
make install
if [ ! -f "$SDL2_STATIC" ]; then
echo "Build failed! $SDL2_STATIC"
exit 1
fi
echo "Building test"
cp -f $SDLPATH/test/nacl/* $TESTBUILDPATH
# Some tests need these resource files
cp -f $SDLPATH/test/*.bmp $TESTBUILDPATH
cp -f $SDLPATH/test/*.wav $TESTBUILDPATH
cp -f $SDL2_STATIC $TESTBUILDPATH
# Copy user sources
_SOURCES=($SOURCES)
for src in "${_SOURCES[@]}"
do
cp $src $TESTBUILDPATH
done
export SOURCES="$SOURCES"
cd $TESTBUILDPATH
make -j$NCPUS CONFIG="Release" CFLAGS="$CFLAGS -I$TESTBUILDPATH/include/SDL2 -I$SDLPATH/include"
make -j$NCPUS CONFIG="Debug" CFLAGS="$CFLAGS -I$TESTBUILDPATH/include/SDL2 -I$SDLPATH/include"
echo
echo "Run the test with: "
echo "cd $TESTBUILDPATH;python -m SimpleHTTPServer"
echo "Then visit http://localhost:8000 with Chrome"
cd $CURDIR

64
configure vendored
View File

@ -18984,6 +18984,55 @@ _ACEOF
fi fi
} }
CheckNativeClient()
{
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#if !defined(__native_client__)
#error "NO NACL"
#endif
int
main ()
{
;
return 0;
}
_ACEOF
if ac_fn_c_try_compile "$LINENO"; then :
$as_echo "#define SDL_VIDEO_DRIVER_NACL 1" >>confdefs.h
$as_echo "#define SDL_AUDIO_DRIVER_NACL 1" >>confdefs.h
$as_echo "#define HAVE_POW 1" >>confdefs.h
$as_echo "#define HAVE_OPENGLES2 1" >>confdefs.h
$as_echo "#define SDL_VIDEO_OPENGL_ES2 1" >>confdefs.h
$as_echo "#define SDL_VIDEO_RENDER_OGL_ES2 1" >>confdefs.h
SDL_LIBS="-lppapi_simple -lppapi_gles2 $SDL_LIBS"
SDLMAIN_SOURCES="$srcdir/src/main/nacl/*.c"
SOURCES="$SOURCES $srcdir/src/audio/nacl/*.c"
SUMMARY_audio="${SUMMARY_audio} nacl"
SOURCES="$SOURCES $srcdir/src/video/nacl/*.c"
SUMMARY_video="${SUMMARY_video} nacl opengles2"
fi
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
}
CheckX11() CheckX11()
{ {
@ -23156,6 +23205,21 @@ $as_echo "#define SDL_TIMER_UNIX 1" >>confdefs.h
EXTRA_LDFLAGS="$EXTRA_LDFLAGS -Wl,-framework,CoreAudio -Wl,-framework,AudioToolbox -Wl,-framework,AudioUnit" EXTRA_LDFLAGS="$EXTRA_LDFLAGS -Wl,-framework,CoreAudio -Wl,-framework,AudioToolbox -Wl,-framework,AudioUnit"
fi fi
;; ;;
*-nacl|*-pnacl)
ARCH=nacl
CheckNativeClient
CheckDummyAudio
CheckDummyVideo
CheckInputEvents
# Set up files for the timer library
if test x$enable_timers = xyes; then
$as_echo "#define SDL_TIMER_UNIX 1" >>confdefs.h
SOURCES="$SOURCES $srcdir/src/timer/unix/*.c"
have_timers=yes
fi
CheckPTHREAD
;;
*) *)
as_fn_error $? " as_fn_error $? "
*** Unsupported host: Please add to configure.in *** Unsupported host: Please add to configure.in

View File

@ -1317,6 +1317,32 @@ AC_HELP_STRING([--enable-mir-shared], [dynamically load Mir support [[default=ma
fi fi
} }
dnl Check for Native Client stuff
CheckNativeClient()
{
AC_TRY_COMPILE([
#if !defined(__native_client__)
#error "NO NACL"
#endif
],[
],[
AC_DEFINE(SDL_VIDEO_DRIVER_NACL)
AC_DEFINE(SDL_AUDIO_DRIVER_NACL)
AC_DEFINE(HAVE_POW, 1, [ ])
AC_DEFINE(HAVE_OPENGLES2, 1, [ ])
AC_DEFINE(SDL_VIDEO_OPENGL_ES2, 1, [ ])
AC_DEFINE(SDL_VIDEO_RENDER_OGL_ES2, 1, [ ])
SDL_LIBS="-lppapi_simple -lppapi_gles2 $SDL_LIBS"
SDLMAIN_SOURCES="$srcdir/src/main/nacl/*.c"
SOURCES="$SOURCES $srcdir/src/audio/nacl/*.c"
SUMMARY_audio="${SUMMARY_audio} nacl"
SOURCES="$SOURCES $srcdir/src/video/nacl/*.c"
SUMMARY_video="${SUMMARY_video} nacl opengles2"
])
}
dnl Find the X11 include and library directories dnl Find the X11 include and library directories
CheckX11() CheckX11()
@ -3119,6 +3145,20 @@ AC_HELP_STRING([--enable-render-d3d], [enable the Direct3D render driver [[defau
EXTRA_LDFLAGS="$EXTRA_LDFLAGS -Wl,-framework,CoreAudio -Wl,-framework,AudioToolbox -Wl,-framework,AudioUnit" EXTRA_LDFLAGS="$EXTRA_LDFLAGS -Wl,-framework,CoreAudio -Wl,-framework,AudioToolbox -Wl,-framework,AudioUnit"
fi fi
;; ;;
*-nacl|*-pnacl)
ARCH=nacl
CheckNativeClient
CheckDummyAudio
CheckDummyVideo
CheckInputEvents
# Set up files for the timer library
if test x$enable_timers = xyes; then
AC_DEFINE(SDL_TIMER_UNIX)
SOURCES="$SOURCES $srcdir/src/timer/unix/*.c"
have_timers=yes
fi
CheckPTHREAD
;;
*) *)
AC_MSG_ERROR([ AC_MSG_ERROR([
*** Unsupported host: Please add to configure.in *** Unsupported host: Please add to configure.in

View File

@ -51,7 +51,7 @@ assert can have unique static variables associated with it.
/* Don't include intrin.h here because it contains C++ code */ /* Don't include intrin.h here because it contains C++ code */
extern void __cdecl __debugbreak(void); extern void __cdecl __debugbreak(void);
#define SDL_TriggerBreakpoint() __debugbreak() #define SDL_TriggerBreakpoint() __debugbreak()
#elif (defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__))) #elif (!defined(__NACL__) && defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__)))
#define SDL_TriggerBreakpoint() __asm__ __volatile__ ( "int $3\n\t" ) #define SDL_TriggerBreakpoint() __asm__ __volatile__ ( "int $3\n\t" )
#elif defined(HAVE_SIGNAL_H) #elif defined(HAVE_SIGNAL_H)
#include <signal.h> #include <signal.h>

View File

@ -208,6 +208,7 @@
#undef SDL_AUDIO_DRIVER_DSOUND #undef SDL_AUDIO_DRIVER_DSOUND
#undef SDL_AUDIO_DRIVER_ESD #undef SDL_AUDIO_DRIVER_ESD
#undef SDL_AUDIO_DRIVER_ESD_DYNAMIC #undef SDL_AUDIO_DRIVER_ESD_DYNAMIC
#undef SDL_AUDIO_DRIVER_NACL
#undef SDL_AUDIO_DRIVER_NAS #undef SDL_AUDIO_DRIVER_NAS
#undef SDL_AUDIO_DRIVER_NAS_DYNAMIC #undef SDL_AUDIO_DRIVER_NAS_DYNAMIC
#undef SDL_AUDIO_DRIVER_SNDIO #undef SDL_AUDIO_DRIVER_SNDIO
@ -297,6 +298,7 @@
#undef SDL_VIDEO_DRIVER_X11_CONST_PARAM_XDATA32 #undef SDL_VIDEO_DRIVER_X11_CONST_PARAM_XDATA32
#undef SDL_VIDEO_DRIVER_X11_CONST_PARAM_XEXTADDDISPLAY #undef SDL_VIDEO_DRIVER_X11_CONST_PARAM_XEXTADDDISPLAY
#undef SDL_VIDEO_DRIVER_X11_HAS_XKBKEYCODETOKEYSYM #undef SDL_VIDEO_DRIVER_X11_HAS_XKBKEYCODETOKEYSYM
#undef SDL_VIDEO_DRIVER_NACL
#undef SDL_VIDEO_RENDER_D3D #undef SDL_VIDEO_RENDER_D3D
#undef SDL_VIDEO_RENDER_D3D11 #undef SDL_VIDEO_RENDER_D3D11

View File

@ -67,6 +67,15 @@
*/ */
#define SDL_MAIN_NEEDED #define SDL_MAIN_NEEDED
#elif defined(__NACL__)
/* On NACL we use ppapi_simple to set up the application helper code,
then wait for the first PSE_INSTANCE_DIDCHANGEVIEW event before
starting the user main function.
All user code is run in a separate thread by ppapi_simple, thus
allowing for blocking io to take place via nacl_io
*/
#define SDL_MAIN_NEEDED
#endif #endif
#endif /* SDL_MAIN_HANDLED */ #endif /* SDL_MAIN_HANDLED */

View File

@ -56,7 +56,7 @@
#undef __IRIX__ #undef __IRIX__
#define __IRIX__ 1 #define __IRIX__ 1
#endif #endif
#if defined(linux) || defined(__linux) || defined(__linux__) #if (defined(linux) || defined(__linux) || defined(__linux__))
#undef __LINUX__ #undef __LINUX__
#define __LINUX__ 1 #define __LINUX__ 1
#endif #endif
@ -142,6 +142,23 @@
#define __PSP__ 1 #define __PSP__ 1
#endif #endif
/* The NACL compiler defines __native_client__ and __pnacl__
* Ref: http://www.chromium.org/nativeclient/pnacl/stability-of-the-pnacl-bitcode-abi
*/
#if defined(__native_client__)
#undef __LINUX__
#undef __NACL__
#define __NACL__ 1
#endif
#if defined(__pnacl__)
#undef __LINUX__
#undef __PNACL__
#define __PNACL__ 1
/* PNACL with newlib supports static linking only */
#define __SDL_NOGETPROCADDR__
#endif
#include "begin_code.h" #include "begin_code.h"
/* Set up for C function definitions, even when using C++ */ /* Set up for C function definitions, even when using C++ */
#ifdef __cplusplus #ifdef __cplusplus

View File

@ -220,6 +220,16 @@ extern DECLSPEC size_t SDLCALL SDL_WriteLE64(SDL_RWops * dst, Uint64 value);
extern DECLSPEC size_t SDLCALL SDL_WriteBE64(SDL_RWops * dst, Uint64 value); extern DECLSPEC size_t SDLCALL SDL_WriteBE64(SDL_RWops * dst, Uint64 value);
/* @} *//* Write endian functions */ /* @} *//* Write endian functions */
/**
* \name Mount/umount functions
*
* Required for RWOps on Native Client
*/
/* @{ */
extern DECLSPEC int SDLCALL SDL_RWMount(const char* source, const char* target,
const char* filesystemtype,
unsigned long mountflags, const void *data);
extern DECLSPEC int SDLCALL SDL_RWUmount(const char *target);
/* Ends C function definitions when using C++ */ /* Ends C function definitions when using C++ */
#ifdef __cplusplus #ifdef __cplusplus

View File

@ -413,6 +413,9 @@ SDL_LogOutput(void *userdata, int category, SDL_LogPriority priority,
#endif #endif
#if HAVE_STDIO_H #if HAVE_STDIO_H
fprintf(stderr, "%s: %s\n", SDL_priority_prefixes[priority], message); fprintf(stderr, "%s: %s\n", SDL_priority_prefixes[priority], message);
#if __NACL__
fflush(stderr);
#endif
#endif #endif
} }

View File

@ -51,6 +51,9 @@ extern AudioBootStrap QSAAUDIO_bootstrap;
extern AudioBootStrap SUNAUDIO_bootstrap; extern AudioBootStrap SUNAUDIO_bootstrap;
extern AudioBootStrap ARTS_bootstrap; extern AudioBootStrap ARTS_bootstrap;
extern AudioBootStrap ESD_bootstrap; extern AudioBootStrap ESD_bootstrap;
#if SDL_AUDIO_DRIVER_NACL
extern AudioBootStrap NACLAUD_bootstrap;
#endif
extern AudioBootStrap NAS_bootstrap; extern AudioBootStrap NAS_bootstrap;
extern AudioBootStrap XAUDIO2_bootstrap; extern AudioBootStrap XAUDIO2_bootstrap;
extern AudioBootStrap DSOUND_bootstrap; extern AudioBootStrap DSOUND_bootstrap;
@ -69,6 +72,7 @@ extern AudioBootStrap ANDROIDAUD_bootstrap;
extern AudioBootStrap PSPAUD_bootstrap; extern AudioBootStrap PSPAUD_bootstrap;
extern AudioBootStrap SNDIO_bootstrap; extern AudioBootStrap SNDIO_bootstrap;
/* Available audio drivers */ /* Available audio drivers */
static const AudioBootStrap *const bootstrap[] = { static const AudioBootStrap *const bootstrap[] = {
#if SDL_AUDIO_DRIVER_PULSEAUDIO #if SDL_AUDIO_DRIVER_PULSEAUDIO
@ -98,6 +102,9 @@ static const AudioBootStrap *const bootstrap[] = {
#if SDL_AUDIO_DRIVER_ESD #if SDL_AUDIO_DRIVER_ESD
&ESD_bootstrap, &ESD_bootstrap,
#endif #endif
#if SDL_AUDIO_DRIVER_NACL
&NACLAUD_bootstrap,
#endif
#if SDL_AUDIO_DRIVER_NAS #if SDL_AUDIO_DRIVER_NAS
&NAS_bootstrap, &NAS_bootstrap,
#endif #endif

View File

@ -0,0 +1,135 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#include "SDL_naclaudio.h"
#include "SDL_audio.h"
#include "SDL_mutex.h"
#include "../SDL_audiomem.h"
#include "../SDL_audio_c.h"
#include "../SDL_audiodev_c.h"
#include "ppapi/c/pp_errors.h"
#include "ppapi/c/pp_instance.h"
#include "ppapi_simple/ps.h"
#include "ppapi_simple/ps_interface.h"
#include "ppapi_simple/ps_event.h"
/* The tag name used by NACL audio */
#define NACLAUD_DRIVER_NAME "nacl"
#define SAMPLE_FRAME_COUNT 4096
/* Audio driver functions */
static int NACLAUD_OpenDevice(_THIS, const char *devname, int iscapture);
static void NACLAUD_CloseDevice(_THIS);
static void nacl_audio_callback(void* samples, uint32_t buffer_size, PP_TimeDelta latency, void* data);
/* FIXME: Make use of latency if needed */
static void nacl_audio_callback(void* samples, uint32_t buffer_size, PP_TimeDelta latency, void* data) {
SDL_AudioDevice* _this = (SDL_AudioDevice*) data;
SDL_LockMutex(private->mutex);
/*if (private->opened) {*/
SDL_memset(samples, _this->spec.silence, buffer_size);
SDL_LockMutex(_this->mixer_lock);
(*_this->spec.callback)(_this->spec.userdata, (Uint8*)samples, buffer_size);
SDL_UnlockMutex(_this->mixer_lock);
/*} else {
SDL_memset(samples, 0, buffer_size);
}*/
SDL_UnlockMutex(private->mutex);
return;
}
static void NACLAUD_CloseDevice(SDL_AudioDevice *device) {
const PPB_Core *core = PSInterfaceCore();
const PPB_Audio *ppb_audio = PSInterfaceAudio();
SDL_PrivateAudioData *hidden = (SDL_PrivateAudioData *) device->hidden;
ppb_audio->StopPlayback(hidden->audio);
SDL_DestroyMutex(hidden->mutex);
core->ReleaseResource(hidden->audio);
}
static int
NACLAUD_OpenDevice(_THIS, const char *devname, int iscapture) {
PP_Instance instance = PSGetInstanceId();
const PPB_Audio *ppb_audio = PSInterfaceAudio();
const PPB_AudioConfig *ppb_audiocfg = PSInterfaceAudioConfig();
private = (SDL_PrivateAudioData *) SDL_calloc(1, (sizeof *private));
if (private == NULL) {
SDL_OutOfMemory();
return 0;
}
private->mutex = SDL_CreateMutex();
_this->spec.freq = 44100;
_this->spec.format = AUDIO_S16LSB;
_this->spec.channels = 2;
_this->spec.samples = ppb_audiocfg->RecommendSampleFrameCount(
instance,
PP_AUDIOSAMPLERATE_44100,
SAMPLE_FRAME_COUNT);
private->audio = ppb_audio->Create(
instance,
ppb_audiocfg->CreateStereo16Bit(instance, PP_AUDIOSAMPLERATE_44100, _this->spec.samples),
nacl_audio_callback,
_this);
/* Start audio playback while we are still on the main thread. */
ppb_audio->StartPlayback(private->audio);
return 1;
}
static int
NACLAUD_Init(SDL_AudioDriverImpl * impl)
{
if (PSGetInstanceId() == 0) {
return 0;
}
/* Set the function pointers */
impl->OpenDevice = NACLAUD_OpenDevice;
impl->CloseDevice = NACLAUD_CloseDevice;
impl->HasCaptureSupport = 0;
impl->OnlyHasDefaultOutputDevice = 1;
impl->OnlyHasDefaultInputDevice = 1;
impl->ProvidesOwnCallbackThread = 1;
/*
* impl->WaitDevice = NACLAUD_WaitDevice;
* impl->GetDeviceBuf = NACLAUD_GetDeviceBuf;
* impl->PlayDevice = NACLAUD_PlayDevice;
* impl->Deinitialize = NACLAUD_Deinitialize;
*/
return 1;
}
AudioBootStrap NACLAUD_bootstrap = {
NACLAUD_DRIVER_NAME, "SDL NaCl Audio Driver",
NACLAUD_Init, 0
};

View File

@ -0,0 +1,41 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#ifndef _SDL_naclaudio_h
#define _SDL_naclaudio_h
#include "SDL_audio.h"
#include "../SDL_sysaudio.h"
#include "SDL_mutex.h"
#include "ppapi/c/ppb_audio.h"
#define _THIS SDL_AudioDevice *_this
#define private _this->hidden
typedef struct SDL_PrivateAudioData {
SDL_mutex* mutex;
PP_Resource audio;
} SDL_PrivateAudioData;
#endif /* _SDL_naclaudio_h */

View File

@ -43,7 +43,7 @@
#include "TargetConditionals.h" #include "TargetConditionals.h"
#endif #endif
#if TARGET_OS_IPHONE /* probably not useful on iOS. */ #if TARGET_OS_IPHONE || __native_client__ /* probably not useful on iOS or NACL. */
#define SDL_DYNAMIC_API 0 #define SDL_DYNAMIC_API 0
#elif SDL_BUILDING_WINRT /* probaly not useful on WinRT, given current .dll loading restrictions */ #elif SDL_BUILDING_WINRT /* probaly not useful on WinRT, given current .dll loading restrictions */
#define SDL_DYNAMIC_API 0 #define SDL_DYNAMIC_API 0

View File

@ -43,6 +43,10 @@
#include "SDL_system.h" #include "SDL_system.h"
#endif #endif
#if __NACL__
#include "nacl_io/nacl_io.h"
#endif
#ifdef __WIN32__ #ifdef __WIN32__
/* Functions to read/write Win32 API file pointers */ /* Functions to read/write Win32 API file pointers */
@ -762,4 +766,28 @@ SDL_WriteBE64(SDL_RWops * dst, Uint64 value)
return SDL_RWwrite(dst, &swapped, sizeof (swapped), 1); return SDL_RWwrite(dst, &swapped, sizeof (swapped), 1);
} }
/* SDL_RWops on NACL are implemented using nacl_io, and require mount points
* to be established before actual file operations are performed
*
* Ref: https://developers.google.com/native-client/dev/devguide/coding/nacl_io?hl=es
*/
int
SDL_RWMount(const char* source, const char* target, const char* filesystemtype,
unsigned long mountflags, const void *data) {
#if __NACL__
return mount(source, target, filesystemtype, mountflags, data);
#endif /* __NACL__ */
return SDL_SetError ("Mount not supported on this platform");
}
int
SDL_RWUmount(const char *target) {
#if __NACL__
return umount(target);
#endif /* __NACL__ */
return SDL_SetError ("Umount not supported on this platform");
}
/* vi: set ts=4 sw=4 expandtab: */ /* vi: set ts=4 sw=4 expandtab: */

View File

@ -0,0 +1,77 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#if SDL_VIDEO_DRIVER_NACL
/* Include the SDL main definition header */
#include "SDL_main.h"
#include "ppapi_simple/ps_main.h"
#include "ppapi_simple/ps_event.h"
#include "ppapi_simple/ps_interface.h"
extern void NACL_SetScreenResolution(int width, int height, Uint32 format);
int
nacl_main(int argc, char *argv[])
{
int status;
PSEvent* ps_event;
PP_Resource event;
struct PP_Rect rect;
int ready = 0;
const PPB_View *ppb_view = PSInterfaceView();
/* This is started in a worker thread by ppapi_simple! */
/* Wait for the first PSE_INSTANCE_DIDCHANGEVIEW event before starting the app */
PSEventSetFilter(PSE_INSTANCE_DIDCHANGEVIEW);
while (!ready) {
/* Process all waiting events without blocking */
while (!ready && (ps_event = PSEventWaitAcquire()) != NULL) {
event = ps_event->as_resource;
switch(ps_event->type) {
/* From DidChangeView, contains a view resource */
case PSE_INSTANCE_DIDCHANGEVIEW:
ppb_view->GetRect(event, &rect);
NACL_SetScreenResolution(rect.size.width, rect.size.height, 0);
ready = 1;
break;
default:
break;
}
PSEventRelease(ps_event);
}
}
/* Everything is ready, start the user main function */
SDL_SetMainReady();
status = SDL_main(argc, argv);
return 0;
}
/* ppapi_simple will start nacl_main in a worker thread */
PPAPI_SIMPLE_REGISTER_MAIN(nacl_main);
#endif /* SDL_VIDEO_DRIVER_NACL */

View File

@ -68,4 +68,4 @@ SDL_PROC(void, glFramebufferTexture2D, (GLenum, GLenum, GLenum, GLuint, GLint))
SDL_PROC(GLenum, glCheckFramebufferStatus, (GLenum)) SDL_PROC(GLenum, glCheckFramebufferStatus, (GLenum))
SDL_PROC(void, glDeleteFramebuffers, (GLsizei, const GLuint *)) SDL_PROC(void, glDeleteFramebuffers, (GLsizei, const GLuint *))
SDL_PROC(GLint, glGetAttribLocation, (GLuint, const GLchar *)) SDL_PROC(GLint, glGetAttribLocation, (GLuint, const GLchar *))
SDL_PROC(void, glGetProgramInfoLog, (GLuint, GLsizei, GLsizei*, GLchar*))

View File

@ -141,12 +141,15 @@ SDL_SYS_SetupThread(const char *name)
#endif #endif
} }
/* NativeClient does not yet support signals.*/
#ifndef __NACL__
/* Mask asynchronous signals for this thread */ /* Mask asynchronous signals for this thread */
sigemptyset(&mask); sigemptyset(&mask);
for (i = 0; sig_list[i]; ++i) { for (i = 0; sig_list[i]; ++i) {
sigaddset(&mask, sig_list[i]); sigaddset(&mask, sig_list[i]);
} }
pthread_sigmask(SIG_BLOCK, &mask, 0); pthread_sigmask(SIG_BLOCK, &mask, 0);
#endif
#ifdef PTHREAD_CANCEL_ASYNCHRONOUS #ifdef PTHREAD_CANCEL_ASYNCHRONOUS
/* Allow ourselves to be asynchronously cancelled */ /* Allow ourselves to be asynchronously cancelled */
@ -166,7 +169,10 @@ SDL_ThreadID(void)
int int
SDL_SYS_SetThreadPriority(SDL_ThreadPriority priority) SDL_SYS_SetThreadPriority(SDL_ThreadPriority priority)
{ {
#ifdef __LINUX__ #if __NACL__
/* FIXME: Setting thread priority does not seem to be supported in NACL */
return 0;
#elif __LINUX__
int value; int value;
if (priority == SDL_THREAD_PRIORITY_LOW) { if (priority == SDL_THREAD_PRIORITY_LOW) {

View File

@ -381,6 +381,9 @@ extern VideoBootStrap DUMMY_bootstrap;
#if SDL_VIDEO_DRIVER_WAYLAND #if SDL_VIDEO_DRIVER_WAYLAND
extern VideoBootStrap Wayland_bootstrap; extern VideoBootStrap Wayland_bootstrap;
#endif #endif
#if SDL_VIDEO_DRIVER_NACL
extern VideoBootStrap NACL_bootstrap;
#endif
extern SDL_VideoDevice *SDL_GetVideoDevice(void); extern SDL_VideoDevice *SDL_GetVideoDevice(void);
extern int SDL_AddBasicVideoDisplay(const SDL_DisplayMode * desktop_mode); extern int SDL_AddBasicVideoDisplay(const SDL_DisplayMode * desktop_mode);

View File

@ -92,6 +92,9 @@ static VideoBootStrap *bootstrap[] = {
#if SDL_VIDEO_DRIVER_WAYLAND #if SDL_VIDEO_DRIVER_WAYLAND
&Wayland_bootstrap, &Wayland_bootstrap,
#endif #endif
#if SDL_VIDEO_DRIVER_NACL
&NACL_bootstrap,
#endif
#if SDL_VIDEO_DRIVER_DUMMY #if SDL_VIDEO_DRIVER_DUMMY
&DUMMY_bootstrap, &DUMMY_bootstrap,
#endif #endif
@ -253,7 +256,7 @@ SDL_CreateWindowTexture(_THIS, SDL_Window * window, Uint32 * format, void ** pix
} }
} }
} }
if (!renderer) { if (!renderer) {
for (i = 0; i < SDL_GetNumRenderDrivers(); ++i) { for (i = 0; i < SDL_GetNumRenderDrivers(); ++i) {
SDL_GetRenderDriverInfo(i, &info); SDL_GetRenderDriverInfo(i, &info);
@ -1239,7 +1242,7 @@ SDL_CreateWindow(const char *title, int x, int y, int w, int h, Uint32 flags)
} }
/* Some platforms have OpenGL enabled by default */ /* Some platforms have OpenGL enabled by default */
#if (SDL_VIDEO_OPENGL && __MACOSX__) || __IPHONEOS__ || __ANDROID__ #if (SDL_VIDEO_OPENGL && __MACOSX__) || __IPHONEOS__ || __ANDROID__ || __NACL__
flags |= SDL_WINDOW_OPENGL; flags |= SDL_WINDOW_OPENGL;
#endif #endif
if (flags & SDL_WINDOW_OPENGL) { if (flags & SDL_WINDOW_OPENGL) {

View File

@ -0,0 +1,432 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#include "SDL.h"
#include "../../events/SDL_sysevents.h"
#include "../../events/SDL_events_c.h"
#include "SDL_naclevents_c.h"
#include "SDL_naclvideo.h"
#include "ppapi_simple/ps_event.h"
/* Ref: https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent */
static SDL_Scancode NACL_Keycodes[] = {
SDL_SCANCODE_UNKNOWN, /* 0 */
SDL_SCANCODE_UNKNOWN, /* 1 */
SDL_SCANCODE_UNKNOWN, /* 2 */
SDL_SCANCODE_CANCEL, /* DOM_VK_CANCEL 3 */
SDL_SCANCODE_UNKNOWN, /* 4 */
SDL_SCANCODE_UNKNOWN, /* 5 */
SDL_SCANCODE_HELP, /* DOM_VK_HELP 6 */
SDL_SCANCODE_UNKNOWN, /* 7 */
SDL_SCANCODE_BACKSPACE, /* DOM_VK_BACK_SPACE 8 */
SDL_SCANCODE_TAB, /* DOM_VK_TAB 9 */
SDL_SCANCODE_UNKNOWN, /* 10 */
SDL_SCANCODE_UNKNOWN, /* 11 */
SDL_SCANCODE_CLEAR, /* DOM_VK_CLEAR 12 */
SDL_SCANCODE_RETURN, /* DOM_VK_RETURN 13 */
SDL_SCANCODE_RETURN, /* DOM_VK_ENTER 14 */
SDL_SCANCODE_UNKNOWN, /* 15 */
SDL_SCANCODE_LSHIFT, /* DOM_VK_SHIFT 16 */
SDL_SCANCODE_LCTRL, /* DOM_VK_CONTROL 17 */
SDL_SCANCODE_LALT, /* DOM_VK_ALT 18 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_PAUSE 19 */
SDL_SCANCODE_CAPSLOCK, /* DOM_VK_CAPS_LOCK 20 */
SDL_SCANCODE_LANG1, /* DOM_VK_KANA DOM_VK_HANGUL 21 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_EISU 22 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_JUNJA 23 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_FINAL 24 */
SDL_SCANCODE_LANG2, /* DOM_VK_HANJA DOM_VK_KANJI 25 */
SDL_SCANCODE_UNKNOWN, /* 26 */
SDL_SCANCODE_ESCAPE, /* DOM_VK_ESCAPE 27 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_CONVERT 28 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_NONCONVERT 29 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_ACCEPT 30 */
SDL_SCANCODE_MODE, /* DOM_VK_MODECHANGE 31 */
SDL_SCANCODE_SPACE, /* DOM_VK_SPACE 32 */
SDL_SCANCODE_PAGEUP, /* DOM_VK_PAGE_UP 33 */
SDL_SCANCODE_PAGEDOWN, /* DOM_VK_PAGE_DOWN 34 */
SDL_SCANCODE_END, /* DOM_VK_END 35 */
SDL_SCANCODE_HOME, /* DOM_VK_HOME 36 */
SDL_SCANCODE_LEFT, /* DOM_VK_LEFT 37 */
SDL_SCANCODE_UP, /* DOM_VK_UP 38 */
SDL_SCANCODE_RIGHT, /* DOM_VK_RIGHT 39 */
SDL_SCANCODE_DOWN, /* DOM_VK_DOWN 40 */
SDL_SCANCODE_SELECT, /* DOM_VK_SELECT 41 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_PRINT 42 */
SDL_SCANCODE_EXECUTE, /* DOM_VK_EXECUTE 43 */
SDL_SCANCODE_PRINTSCREEN, /* DOM_VK_PRINTSCREEN 44 */
SDL_SCANCODE_INSERT, /* DOM_VK_INSERT 45 */
SDL_SCANCODE_DELETE, /* DOM_VK_DELETE 46 */
SDL_SCANCODE_UNKNOWN, /* 47 */
SDL_SCANCODE_0, /* DOM_VK_0 48 */
SDL_SCANCODE_1, /* DOM_VK_1 49 */
SDL_SCANCODE_2, /* DOM_VK_2 50 */
SDL_SCANCODE_3, /* DOM_VK_3 51 */
SDL_SCANCODE_4, /* DOM_VK_4 52 */
SDL_SCANCODE_5, /* DOM_VK_5 53 */
SDL_SCANCODE_6, /* DOM_VK_6 54 */
SDL_SCANCODE_7, /* DOM_VK_7 55 */
SDL_SCANCODE_8, /* DOM_VK_8 56 */
SDL_SCANCODE_9, /* DOM_VK_9 57 */
SDL_SCANCODE_KP_COLON, /* DOM_VK_COLON 58 */
SDL_SCANCODE_SEMICOLON, /* DOM_VK_SEMICOLON 59 */
SDL_SCANCODE_KP_LESS, /* DOM_VK_LESS_THAN 60 */
SDL_SCANCODE_EQUALS, /* DOM_VK_EQUALS 61 */
SDL_SCANCODE_KP_GREATER, /* DOM_VK_GREATER_THAN 62 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_QUESTION_MARK 63 */
SDL_SCANCODE_KP_AT, /* DOM_VK_AT 64 */
SDL_SCANCODE_A, /* DOM_VK_A 65 */
SDL_SCANCODE_B, /* DOM_VK_B 66 */
SDL_SCANCODE_C, /* DOM_VK_C 67 */
SDL_SCANCODE_D, /* DOM_VK_D 68 */
SDL_SCANCODE_E, /* DOM_VK_E 69 */
SDL_SCANCODE_F, /* DOM_VK_F 70 */
SDL_SCANCODE_G, /* DOM_VK_G 71 */
SDL_SCANCODE_H, /* DOM_VK_H 72 */
SDL_SCANCODE_I, /* DOM_VK_I 73 */
SDL_SCANCODE_J, /* DOM_VK_J 74 */
SDL_SCANCODE_K, /* DOM_VK_K 75 */
SDL_SCANCODE_L, /* DOM_VK_L 76 */
SDL_SCANCODE_M, /* DOM_VK_M 77 */
SDL_SCANCODE_N, /* DOM_VK_N 78 */
SDL_SCANCODE_O, /* DOM_VK_O 79 */
SDL_SCANCODE_P, /* DOM_VK_P 80 */
SDL_SCANCODE_Q, /* DOM_VK_Q 81 */
SDL_SCANCODE_R, /* DOM_VK_R 82 */
SDL_SCANCODE_S, /* DOM_VK_S 83 */
SDL_SCANCODE_T, /* DOM_VK_T 84 */
SDL_SCANCODE_U, /* DOM_VK_U 85 */
SDL_SCANCODE_V, /* DOM_VK_V 86 */
SDL_SCANCODE_W, /* DOM_VK_W 87 */
SDL_SCANCODE_X, /* DOM_VK_X 88 */
SDL_SCANCODE_Y, /* DOM_VK_Y 89 */
SDL_SCANCODE_Z, /* DOM_VK_Z 90 */
SDL_SCANCODE_LGUI, /* DOM_VK_WIN 91 */
SDL_SCANCODE_UNKNOWN, /* 92 */
SDL_SCANCODE_APPLICATION, /* DOM_VK_CONTEXT_MENU 93 */
SDL_SCANCODE_UNKNOWN, /* 94 */
SDL_SCANCODE_SLEEP, /* DOM_VK_SLEEP 95 */
SDL_SCANCODE_KP_0, /* DOM_VK_NUMPAD0 96 */
SDL_SCANCODE_KP_1, /* DOM_VK_NUMPAD1 97 */
SDL_SCANCODE_KP_2, /* DOM_VK_NUMPAD2 98 */
SDL_SCANCODE_KP_3, /* DOM_VK_NUMPAD3 99 */
SDL_SCANCODE_KP_4, /* DOM_VK_NUMPAD4 100 */
SDL_SCANCODE_KP_5, /* DOM_VK_NUMPAD5 101 */
SDL_SCANCODE_KP_6, /* DOM_VK_NUMPAD6 102 */
SDL_SCANCODE_KP_7, /* DOM_VK_NUMPAD7 103 */
SDL_SCANCODE_KP_8, /* DOM_VK_NUMPAD8 104 */
SDL_SCANCODE_KP_9, /* DOM_VK_NUMPAD9 105 */
SDL_SCANCODE_KP_MULTIPLY, /* DOM_VK_MULTIPLY 106 */
SDL_SCANCODE_KP_PLUS, /* DOM_VK_ADD 107 */
SDL_SCANCODE_KP_COMMA, /* DOM_VK_SEPARATOR 108 */
SDL_SCANCODE_KP_MINUS, /* DOM_VK_SUBTRACT 109 */
SDL_SCANCODE_KP_PERIOD, /* DOM_VK_DECIMAL 110 */
SDL_SCANCODE_KP_DIVIDE, /* DOM_VK_DIVIDE 111 */
SDL_SCANCODE_F1, /* DOM_VK_F1 112 */
SDL_SCANCODE_F2, /* DOM_VK_F2 113 */
SDL_SCANCODE_F3, /* DOM_VK_F3 114 */
SDL_SCANCODE_F4, /* DOM_VK_F4 115 */
SDL_SCANCODE_F5, /* DOM_VK_F5 116 */
SDL_SCANCODE_F6, /* DOM_VK_F6 117 */
SDL_SCANCODE_F7, /* DOM_VK_F7 118 */
SDL_SCANCODE_F8, /* DOM_VK_F8 119 */
SDL_SCANCODE_F9, /* DOM_VK_F9 120 */
SDL_SCANCODE_F10, /* DOM_VK_F10 121 */
SDL_SCANCODE_F11, /* DOM_VK_F11 122 */
SDL_SCANCODE_F12, /* DOM_VK_F12 123 */
SDL_SCANCODE_F13, /* DOM_VK_F13 124 */
SDL_SCANCODE_F14, /* DOM_VK_F14 125 */
SDL_SCANCODE_F15, /* DOM_VK_F15 126 */
SDL_SCANCODE_F16, /* DOM_VK_F16 127 */
SDL_SCANCODE_F17, /* DOM_VK_F17 128 */
SDL_SCANCODE_F18, /* DOM_VK_F18 129 */
SDL_SCANCODE_F19, /* DOM_VK_F19 130 */
SDL_SCANCODE_F20, /* DOM_VK_F20 131 */
SDL_SCANCODE_F21, /* DOM_VK_F21 132 */
SDL_SCANCODE_F22, /* DOM_VK_F22 133 */
SDL_SCANCODE_F23, /* DOM_VK_F23 134 */
SDL_SCANCODE_F24, /* DOM_VK_F24 135 */
SDL_SCANCODE_UNKNOWN, /* 136 */
SDL_SCANCODE_UNKNOWN, /* 137 */
SDL_SCANCODE_UNKNOWN, /* 138 */
SDL_SCANCODE_UNKNOWN, /* 139 */
SDL_SCANCODE_UNKNOWN, /* 140 */
SDL_SCANCODE_UNKNOWN, /* 141 */
SDL_SCANCODE_UNKNOWN, /* 142 */
SDL_SCANCODE_UNKNOWN, /* 143 */
SDL_SCANCODE_NUMLOCKCLEAR, /* DOM_VK_NUM_LOCK 144 */
SDL_SCANCODE_SCROLLLOCK, /* DOM_VK_SCROLL_LOCK 145 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_FJ_JISHO 146 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_FJ_MASSHOU 147 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_FJ_TOUROKU 148 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_FJ_LOYA 149 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_FJ_ROYA 150 */
SDL_SCANCODE_UNKNOWN, /* 151 */
SDL_SCANCODE_UNKNOWN, /* 152 */
SDL_SCANCODE_UNKNOWN, /* 153 */
SDL_SCANCODE_UNKNOWN, /* 154 */
SDL_SCANCODE_UNKNOWN, /* 155 */
SDL_SCANCODE_UNKNOWN, /* 156 */
SDL_SCANCODE_UNKNOWN, /* 157 */
SDL_SCANCODE_UNKNOWN, /* 158 */
SDL_SCANCODE_UNKNOWN, /* 159 */
SDL_SCANCODE_GRAVE, /* DOM_VK_CIRCUMFLEX 160 */
SDL_SCANCODE_KP_EXCLAM, /* DOM_VK_EXCLAMATION 161 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_DOUBLE_QUOTE 162 */
SDL_SCANCODE_KP_HASH, /* DOM_VK_HASH 163 */
SDL_SCANCODE_CURRENCYUNIT, /* DOM_VK_DOLLAR 164 */
SDL_SCANCODE_KP_PERCENT, /* DOM_VK_PERCENT 165 */
SDL_SCANCODE_KP_AMPERSAND, /* DOM_VK_AMPERSAND 166 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_UNDERSCORE 167 */
SDL_SCANCODE_KP_LEFTPAREN, /* DOM_VK_OPEN_PAREN 168 */
SDL_SCANCODE_KP_RIGHTPAREN, /* DOM_VK_CLOSE_PAREN 169 */
SDL_SCANCODE_KP_MULTIPLY, /* DOM_VK_ASTERISK 170 */
SDL_SCANCODE_KP_PLUS, /* DOM_VK_PLUS 171 */
SDL_SCANCODE_KP_PLUS, /* DOM_VK_PIPE 172 */
SDL_SCANCODE_MINUS, /* DOM_VK_HYPHEN_MINUS 173 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_OPEN_CURLY_BRACKET 174 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_CLOSE_CURLY_BRACKET 175 */
SDL_SCANCODE_NONUSBACKSLASH, /* DOM_VK_TILDE 176 */
SDL_SCANCODE_UNKNOWN, /* 177 */
SDL_SCANCODE_UNKNOWN, /* 178 */
SDL_SCANCODE_UNKNOWN, /* 179 */
SDL_SCANCODE_UNKNOWN, /* 180 */
SDL_SCANCODE_MUTE, /* DOM_VK_VOLUME_MUTE 181 */
SDL_SCANCODE_VOLUMEDOWN, /* DOM_VK_VOLUME_DOWN 182 */
SDL_SCANCODE_VOLUMEUP, /* DOM_VK_VOLUME_UP 183 */
SDL_SCANCODE_UNKNOWN, /* 184 */
SDL_SCANCODE_UNKNOWN, /* 185 */
SDL_SCANCODE_UNKNOWN, /* 186 */
SDL_SCANCODE_UNKNOWN, /* 187 */
SDL_SCANCODE_COMMA, /* DOM_VK_COMMA 188 */
SDL_SCANCODE_UNKNOWN, /* 189 */
SDL_SCANCODE_PERIOD, /* DOM_VK_PERIOD 190 */
SDL_SCANCODE_SLASH, /* DOM_VK_SLASH 191 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_BACK_QUOTE 192 */
SDL_SCANCODE_UNKNOWN, /* 193 */
SDL_SCANCODE_UNKNOWN, /* 194 */
SDL_SCANCODE_UNKNOWN, /* 195 */
SDL_SCANCODE_UNKNOWN, /* 196 */
SDL_SCANCODE_UNKNOWN, /* 197 */
SDL_SCANCODE_UNKNOWN, /* 198 */
SDL_SCANCODE_UNKNOWN, /* 199 */
SDL_SCANCODE_UNKNOWN, /* 200 */
SDL_SCANCODE_UNKNOWN, /* 201 */
SDL_SCANCODE_UNKNOWN, /* 202 */
SDL_SCANCODE_UNKNOWN, /* 203 */
SDL_SCANCODE_UNKNOWN, /* 204 */
SDL_SCANCODE_UNKNOWN, /* 205 */
SDL_SCANCODE_UNKNOWN, /* 206 */
SDL_SCANCODE_UNKNOWN, /* 207 */
SDL_SCANCODE_UNKNOWN, /* 208 */
SDL_SCANCODE_UNKNOWN, /* 209 */
SDL_SCANCODE_UNKNOWN, /* 210 */
SDL_SCANCODE_UNKNOWN, /* 211 */
SDL_SCANCODE_UNKNOWN, /* 212 */
SDL_SCANCODE_UNKNOWN, /* 213 */
SDL_SCANCODE_UNKNOWN, /* 214 */
SDL_SCANCODE_UNKNOWN, /* 215 */
SDL_SCANCODE_UNKNOWN, /* 216 */
SDL_SCANCODE_UNKNOWN, /* 217 */
SDL_SCANCODE_UNKNOWN, /* 218 */
SDL_SCANCODE_LEFTBRACKET, /* DOM_VK_OPEN_BRACKET 219 */
SDL_SCANCODE_BACKSLASH, /* DOM_VK_BACK_SLASH 220 */
SDL_SCANCODE_RIGHTBRACKET, /* DOM_VK_CLOSE_BRACKET 221 */
SDL_SCANCODE_APOSTROPHE, /* DOM_VK_QUOTE 222 */
SDL_SCANCODE_UNKNOWN, /* 223 */
SDL_SCANCODE_RGUI, /* DOM_VK_META 224 */
SDL_SCANCODE_RALT, /* DOM_VK_ALTGR 225 */
SDL_SCANCODE_UNKNOWN, /* 226 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_ICO_HELP 227 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_ICO_00 228 */
SDL_SCANCODE_UNKNOWN, /* 229 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_ICO_CLEAR 230 */
SDL_SCANCODE_UNKNOWN, /* 231 */
SDL_SCANCODE_UNKNOWN, /* 232 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_RESET 233 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_JUMP 234 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_PA1 235 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_PA2 236 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_PA3 237 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_WSCTRL 238 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_CUSEL 239 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_ATTN 240 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_FINISH 241 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_COPY 242 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_AUTO 243 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_ENLW 244 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_BACKTAB 245 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_ATTN 246 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_CRSEL 247 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_EXSEL 248 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_EREOF 249 */
SDL_SCANCODE_AUDIOPLAY, /* DOM_VK_PLAY 250 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_ZOOM 251 */
SDL_SCANCODE_UNKNOWN, /* 252 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_PA1 253 */
SDL_SCANCODE_UNKNOWN, /* DOM_VK_WIN_OEM_CLEAR 254 */
SDL_SCANCODE_UNKNOWN, /* 255 */
};
static Uint8 SDL_NACL_translate_mouse_button(int32_t button) {
switch (button) {
case PP_INPUTEVENT_MOUSEBUTTON_LEFT:
return SDL_BUTTON_LEFT;
case PP_INPUTEVENT_MOUSEBUTTON_MIDDLE:
return SDL_BUTTON_MIDDLE;
case PP_INPUTEVENT_MOUSEBUTTON_RIGHT:
return SDL_BUTTON_RIGHT;
case PP_INPUTEVENT_MOUSEBUTTON_NONE:
default:
return 0;
}
}
static SDL_Scancode
SDL_NACL_translate_keycode(int keycode)
{
SDL_Scancode scancode = SDL_SCANCODE_UNKNOWN;
if (keycode < SDL_arraysize(NACL_Keycodes)) {
scancode = NACL_Keycodes[keycode];
}
if (scancode == SDL_SCANCODE_UNKNOWN) {
SDL_Log("The key you just pressed is not recognized by SDL. To help get this fixed, please report this to the SDL mailing list <sdl@libsdl.org> EVDEV KeyCode %d \n", keycode);
}
return scancode;
}
void NACL_PumpEvents(_THIS) {
PSEvent* ps_event;
PP_Resource event;
PP_InputEvent_Type type;
PP_InputEvent_Modifier modifiers;
struct PP_Rect rect;
struct PP_FloatPoint fp;
struct PP_Point location;
struct PP_Var var;
const char *str;
char text[64];
Uint32 str_len;
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
SDL_Mouse *mouse = SDL_GetMouse();
if (driverdata->window) {
while ((ps_event = PSEventTryAcquire()) != NULL) {
event = ps_event->as_resource;
switch(ps_event->type) {
/* From DidChangeView, contains a view resource */
case PSE_INSTANCE_DIDCHANGEVIEW:
driverdata->ppb_view->GetRect(event, &rect);
NACL_SetScreenResolution(rect.size.width, rect.size.height, SDL_PIXELFORMAT_UNKNOWN);
// FIXME: Rebuild context? See life.c UpdateContext
break;
/* From HandleInputEvent, contains an input resource. */
case PSE_INSTANCE_HANDLEINPUT:
type = driverdata->ppb_input_event->GetType(event);
modifiers = driverdata->ppb_input_event->GetModifiers(event);
switch(type) {
case PP_INPUTEVENT_TYPE_MOUSEDOWN:
SDL_SendMouseButton(mouse->focus, mouse->mouseID, SDL_PRESSED, SDL_NACL_translate_mouse_button(driverdata->ppb_mouse_input_event->GetButton(event)));
break;
case PP_INPUTEVENT_TYPE_MOUSEUP:
SDL_SendMouseButton(mouse->focus, mouse->mouseID, SDL_RELEASED, SDL_NACL_translate_mouse_button(driverdata->ppb_mouse_input_event->GetButton(event)));
break;
case PP_INPUTEVENT_TYPE_WHEEL:
/* FIXME: GetTicks provides high resolution scroll events */
fp = driverdata->ppb_wheel_input_event->GetDelta(event);
SDL_SendMouseWheel(mouse->focus, mouse->mouseID, (int) fp.x, (int) fp.y);
break;
case PP_INPUTEVENT_TYPE_MOUSEENTER:
case PP_INPUTEVENT_TYPE_MOUSELEAVE:
/* FIXME: Mouse Focus */
break;
case PP_INPUTEVENT_TYPE_MOUSEMOVE:
location = driverdata->ppb_mouse_input_event->GetPosition(event);
SDL_SendMouseMotion(mouse->focus, mouse->mouseID, SDL_FALSE, location.x, location.y);
break;
case PP_INPUTEVENT_TYPE_TOUCHSTART:
case PP_INPUTEVENT_TYPE_TOUCHMOVE:
case PP_INPUTEVENT_TYPE_TOUCHEND:
case PP_INPUTEVENT_TYPE_TOUCHCANCEL:
/* FIXME: Touch events */
break;
case PP_INPUTEVENT_TYPE_KEYDOWN:
SDL_SendKeyboardKey(SDL_PRESSED, SDL_NACL_translate_keycode(driverdata->ppb_keyboard_input_event->GetKeyCode(event)));
break;
case PP_INPUTEVENT_TYPE_KEYUP:
SDL_SendKeyboardKey(SDL_RELEASED, SDL_NACL_translate_keycode(driverdata->ppb_keyboard_input_event->GetKeyCode(event)));
break;
case PP_INPUTEVENT_TYPE_CHAR:
var = driverdata->ppb_keyboard_input_event->GetCharacterText(event);
str = driverdata->ppb_var->VarToUtf8(var, &str_len);
/* str is not null terminated! */
if ( str_len >= SDL_arraysize(text) ) {
str_len = SDL_arraysize(text) - 1;
}
SDL_strlcpy(text, str, str_len );
text[str_len] = '\0';
SDL_SendKeyboardText(text);
/* FIXME: Do we have to handle ref counting? driverdata->ppb_var->Release(var);*/
break;
default:
break;
}
break;
/* From HandleMessage, contains a PP_Var. */
case PSE_INSTANCE_HANDLEMESSAGE:
break;
/* From DidChangeFocus, contains a PP_Bool with the current focus state. */
case PSE_INSTANCE_DIDCHANGEFOCUS:
break;
/* When the 3D context is lost, no resource. */
case PSE_GRAPHICS3D_GRAPHICS3DCONTEXTLOST:
break;
/* When the mouse lock is lost. */
case PSE_MOUSELOCK_MOUSELOCKLOST:
break;
default:
break;
}
PSEventRelease(ps_event);
}
}
}

View File

@ -0,0 +1,30 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#ifndef _SDL_naclevents_c_h
#define _SDL_naclevents_c_h
#include "SDL_naclvideo.h"
extern void NACL_PumpEvents(_THIS);
#endif /* _SDL_naclevents_c_h */

View File

@ -0,0 +1,24 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#if SDL_VIDEO_DRIVER_NACL
#endif /* SDL_VIDEO_DRIVER_NACL */

View File

@ -0,0 +1,171 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#if SDL_VIDEO_DRIVER_NACL
/* NaCl SDL video GLES 2 driver implementation */
#include "SDL_video.h"
#include "SDL_naclvideo.h"
#if SDL_LOADSO_DLOPEN
#include "dlfcn.h"
#endif
#include "ppapi/gles2/gl2ext_ppapi.h"
#include "ppapi_simple/ps.h"
/* GL functions */
int
NACL_GLES_LoadLibrary(_THIS, const char *path)
{
/* FIXME: Support dynamic linking when PNACL supports it */
return glInitializePPAPI(PSGetInterface) == 0;
}
void *
NACL_GLES_GetProcAddress(_THIS, const char *proc)
{
#if SDL_LOADSO_DLOPEN
return dlsym( 0 /* RTLD_DEFAULT */, proc);
#else
return NULL;
#endif
}
void
NACL_GLES_UnloadLibrary(_THIS)
{
/* FIXME: Support dynamic linking when PNACL supports it */
glTerminatePPAPI();
}
int
NACL_GLES_MakeCurrent(_THIS, SDL_Window * window, SDL_GLContext sdl_context)
{
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
/* FIXME: Check threading issues...otherwise use a hardcoded _this->context across all threads */
driverdata->ppb_instance->BindGraphics(driverdata->instance, (PP_Resource) sdl_context);
glSetCurrentContextPPAPI((PP_Resource) sdl_context);
return 0;
}
SDL_GLContext
NACL_GLES_CreateContext(_THIS, SDL_Window * window)
{
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
PP_Resource context, share_context = 0;
/* 64 seems nice. */
Sint32 attribs[64];
int i = 0;
if (_this->gl_config.share_with_current_context) {
share_context = (PP_Resource) SDL_GL_GetCurrentContext();
}
/* FIXME: Some ATTRIBS from PP_Graphics3DAttrib are not set here */
attribs[i++] = PP_GRAPHICS3DATTRIB_WIDTH;
attribs[i++] = window->w;
attribs[i++] = PP_GRAPHICS3DATTRIB_HEIGHT;
attribs[i++] = window->h;
attribs[i++] = PP_GRAPHICS3DATTRIB_RED_SIZE;
attribs[i++] = _this->gl_config.red_size;
attribs[i++] = PP_GRAPHICS3DATTRIB_GREEN_SIZE;
attribs[i++] = _this->gl_config.green_size;
attribs[i++] = PP_GRAPHICS3DATTRIB_BLUE_SIZE;
attribs[i++] = _this->gl_config.blue_size;
if (_this->gl_config.alpha_size) {
attribs[i++] = PP_GRAPHICS3DATTRIB_ALPHA_SIZE;
attribs[i++] = _this->gl_config.alpha_size;
}
/*if (_this->gl_config.buffer_size) {
attribs[i++] = EGL_BUFFER_SIZE;
attribs[i++] = _this->gl_config.buffer_size;
}*/
attribs[i++] = PP_GRAPHICS3DATTRIB_DEPTH_SIZE;
attribs[i++] = _this->gl_config.depth_size;
if (_this->gl_config.stencil_size) {
attribs[i++] = PP_GRAPHICS3DATTRIB_STENCIL_SIZE;
attribs[i++] = _this->gl_config.stencil_size;
}
if (_this->gl_config.multisamplebuffers) {
attribs[i++] = PP_GRAPHICS3DATTRIB_SAMPLE_BUFFERS;
attribs[i++] = _this->gl_config.multisamplebuffers;
}
if (_this->gl_config.multisamplesamples) {
attribs[i++] = PP_GRAPHICS3DATTRIB_SAMPLES;
attribs[i++] = _this->gl_config.multisamplesamples;
}
attribs[i++] = PP_GRAPHICS3DATTRIB_NONE;
context = driverdata->ppb_graphics->Create(driverdata->instance, share_context, attribs);
if (context) {
/* We need to make the context current, otherwise nothing works */
SDL_GL_MakeCurrent(window, (SDL_GLContext) context);
}
return (SDL_GLContext) context;
}
int
NACL_GLES_SetSwapInterval(_THIS, int interval)
{
/* STUB */
return 0;
}
int
NACL_GLES_GetSwapInterval(_THIS)
{
/* STUB */
return 0;
}
void
NACL_GLES_SwapWindow(_THIS, SDL_Window * window)
{
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
struct PP_CompletionCallback callback = { NULL, 0, PP_COMPLETIONCALLBACK_FLAG_NONE };
driverdata->ppb_graphics->SwapBuffers((PP_Resource) SDL_GL_GetCurrentContext(), callback );
}
void
NACL_GLES_DeleteContext(_THIS, SDL_GLContext context)
{
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
driverdata->ppb_core->ReleaseResource((PP_Resource) context);
}
#endif /* SDL_VIDEO_DRIVER_NACL */
/* vi: set ts=4 sw=4 expandtab: */

View File

@ -0,0 +1,38 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#ifndef _SDL_naclgl_h
#define _SDL_naclgl_h
extern int NACL_GLES_LoadLibrary(_THIS, const char *path);
extern void *NACL_GLES_GetProcAddress(_THIS, const char *proc);
extern void NACL_GLES_UnloadLibrary(_THIS);
extern SDL_GLContext NACL_GLES_CreateContext(_THIS, SDL_Window * window);
extern int NACL_GLES_MakeCurrent(_THIS, SDL_Window * window, SDL_GLContext context);
extern int NACL_GLES_SetSwapInterval(_THIS, int interval);
extern int NACL_GLES_GetSwapInterval(_THIS);
extern void NACL_GLES_SwapWindow(_THIS, SDL_Window * window);
extern void NACL_GLES_DeleteContext(_THIS, SDL_GLContext context);
#endif /* _SDL_naclgl_h */
/* vi: set ts=4 sw=4 expandtab: */

View File

@ -0,0 +1,183 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#if SDL_VIDEO_DRIVER_NACL
#include "ppapi/c/pp_errors.h"
#include "ppapi/c/pp_instance.h"
#include "ppapi_simple/ps.h"
#include "ppapi_simple/ps_interface.h"
#include "ppapi_simple/ps_event.h"
#include "nacl_io/nacl_io.h"
#include "SDL_naclvideo.h"
#include "SDL_naclwindow.h"
#include "SDL_naclevents_c.h"
#include "SDL_naclopengles.h"
#include "SDL_video.h"
#include "../SDL_sysvideo.h"
#include "../../events/SDL_events_c.h"
#define NACLVID_DRIVER_NAME "nacl"
/* Static init required because NACL_SetScreenResolution
* may appear even before SDL starts and we want to remember
* the window width and height
*/
static SDL_VideoData nacl = {0};
void
NACL_SetScreenResolution(int width, int height, Uint32 format)
{
PP_Resource context;
nacl.w = width;
nacl.h = height;
nacl.format = format;
if (nacl.window) {
nacl.window->w = width;
nacl.window->h = height;
SDL_SendWindowEvent(nacl.window, SDL_WINDOWEVENT_RESIZED, width, height);
}
/* FIXME: Check threading issues...otherwise use a hardcoded _this->context across all threads */
context = (PP_Resource) SDL_GL_GetCurrentContext();
if (context) {
PSInterfaceGraphics3D()->ResizeBuffers(context, width, height);
}
}
/* Initialization/Query functions */
static int NACL_VideoInit(_THIS);
static void NACL_VideoQuit(_THIS);
static int NACL_Available(void) {
return PSGetInstanceId() != 0;
}
static void NACL_DeleteDevice(SDL_VideoDevice *device) {
SDL_VideoData *driverdata = (SDL_VideoData*) device->driverdata;
driverdata->ppb_core->ReleaseResource((PP_Resource) driverdata->ppb_message_loop);
SDL_free(device->driverdata);
SDL_free(device);
}
static int
NACL_SetDisplayMode(_THIS, SDL_VideoDisplay * display, SDL_DisplayMode * mode)
{
return 0;
}
static SDL_VideoDevice *NACL_CreateDevice(int devindex) {
SDL_VideoDevice *device;
/* Initialize all variables that we clean on shutdown */
device = (SDL_VideoDevice *) SDL_calloc(1, sizeof(SDL_VideoDevice));
if (!device) {
SDL_OutOfMemory();
return NULL;
}
device->driverdata = &nacl;
/* Set the function pointers */
device->VideoInit = NACL_VideoInit;
device->VideoQuit = NACL_VideoQuit;
device->PumpEvents = NACL_PumpEvents;
device->CreateWindow = NACL_CreateWindow;
device->SetWindowTitle = NACL_SetWindowTitle;
device->DestroyWindow = NACL_DestroyWindow;
device->SetDisplayMode = NACL_SetDisplayMode;
device->free = NACL_DeleteDevice;
/* GL pointers */
device->GL_LoadLibrary = NACL_GLES_LoadLibrary;
device->GL_GetProcAddress = NACL_GLES_GetProcAddress;
device->GL_UnloadLibrary = NACL_GLES_UnloadLibrary;
device->GL_CreateContext = NACL_GLES_CreateContext;
device->GL_MakeCurrent = NACL_GLES_MakeCurrent;
device->GL_SetSwapInterval = NACL_GLES_SetSwapInterval;
device->GL_GetSwapInterval = NACL_GLES_GetSwapInterval;
device->GL_SwapWindow = NACL_GLES_SwapWindow;
device->GL_DeleteContext = NACL_GLES_DeleteContext;
return device;
}
VideoBootStrap NACL_bootstrap = {
NACLVID_DRIVER_NAME, "SDL Native Client Video Driver",
NACL_Available, NACL_CreateDevice
};
int NACL_VideoInit(_THIS) {
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
SDL_DisplayMode mode;
mode.format = driverdata->format;
mode.w = driverdata->w;
mode.h = driverdata->h;
mode.refresh_rate = 0;
mode.driverdata = NULL;
if (SDL_AddBasicVideoDisplay(&mode) < 0) {
return -1;
}
SDL_zero(mode);
SDL_AddDisplayMode(&_this->displays[0], &mode);
PSInterfaceInit();
driverdata->instance = PSGetInstanceId();
driverdata->ppb_graphics = PSInterfaceGraphics3D();
driverdata->ppb_message_loop = PSInterfaceMessageLoop();
driverdata->ppb_core = PSInterfaceCore();
driverdata->ppb_fullscreen = PSInterfaceFullscreen();
driverdata->ppb_instance = PSInterfaceInstance();
driverdata->ppb_image_data = PSInterfaceImageData();
driverdata->ppb_view = PSInterfaceView();
driverdata->ppb_var = PSInterfaceVar();
driverdata->ppb_input_event = (PPB_InputEvent*) PSGetInterface(PPB_INPUT_EVENT_INTERFACE);
driverdata->ppb_keyboard_input_event = (PPB_KeyboardInputEvent*) PSGetInterface(PPB_KEYBOARD_INPUT_EVENT_INTERFACE);
driverdata->ppb_mouse_input_event = (PPB_MouseInputEvent*) PSGetInterface(PPB_MOUSE_INPUT_EVENT_INTERFACE);
driverdata->ppb_wheel_input_event = (PPB_WheelInputEvent*) PSGetInterface(PPB_WHEEL_INPUT_EVENT_INTERFACE);
driverdata->ppb_touch_input_event = (PPB_TouchInputEvent*) PSGetInterface(PPB_TOUCH_INPUT_EVENT_INTERFACE);
driverdata->message_loop = driverdata->ppb_message_loop->Create(driverdata->instance);
PSEventSetFilter(PSE_ALL);
/* We're done! */
return 0;
}
void NACL_VideoQuit(_THIS) {
}
#endif /* SDL_VIDEO_DRIVER_NACL */
/* vi: set ts=4 sw=4 expandtab: */

View File

@ -0,0 +1,67 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#ifndef _SDL_naclvideo_h
#define _SDL_naclvideo_h
#include "../SDL_sysvideo.h"
#include "ppapi_simple/ps_interface.h"
#include "ppapi/c/pp_input_event.h"
/* Hidden "this" pointer for the video functions */
#define _THIS SDL_VideoDevice *_this
/* Private display data */
typedef struct SDL_VideoData {
Uint32 format;
int w, h;
SDL_Window *window;
const PPB_Graphics3D *ppb_graphics;
const PPB_MessageLoop *ppb_message_loop;
const PPB_Core *ppb_core;
const PPB_Fullscreen *ppb_fullscreen;
const PPB_Instance *ppb_instance;
const PPB_ImageData *ppb_image_data;
const PPB_View *ppb_view;
const PPB_Var *ppb_var;
const PPB_InputEvent *ppb_input_event;
const PPB_KeyboardInputEvent *ppb_keyboard_input_event;
const PPB_MouseInputEvent *ppb_mouse_input_event;
const PPB_WheelInputEvent *ppb_wheel_input_event;
const PPB_TouchInputEvent *ppb_touch_input_event;
PP_Resource message_loop;
PP_Instance instance;
/* FIXME: Check threading issues...otherwise use a hardcoded _this->context across all threads */
/* PP_Resource context; */
} SDL_VideoData;
extern void NACL_SetScreenResolution(int width, int height, Uint32 format);
#endif /* _SDL_naclvideo_h */

View File

@ -0,0 +1,74 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#if SDL_VIDEO_DRIVER_NACL
#include "../SDL_sysvideo.h"
#include "SDL_naclvideo.h"
#include "SDL_naclwindow.h"
int
NACL_CreateWindow(_THIS, SDL_Window * window)
{
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
if (driverdata->window) {
SDL_SetError("NaCl only supports one window");
return -1;
}
driverdata->window = window;
/* Adjust the window data to match the screen */
window->x = 0;
window->y = 0;
window->w = driverdata->w;
window->h = driverdata->h;
window->flags &= ~SDL_WINDOW_RESIZABLE; /* window is NEVER resizeable */
window->flags |= SDL_WINDOW_FULLSCREEN; /* window is always fullscreen */
window->flags &= ~SDL_WINDOW_HIDDEN;
window->flags |= SDL_WINDOW_SHOWN; /* only one window on NaCl */
window->flags |= SDL_WINDOW_INPUT_FOCUS; /* always has input focus */
window->flags |= SDL_WINDOW_OPENGL;
return 0;
}
void
NACL_SetWindowTitle(_THIS, SDL_Window * window)
{
/* TODO */
}
void
NACL_DestroyWindow(_THIS, SDL_Window * window)
{
SDL_VideoData *driverdata = (SDL_VideoData *) _this->driverdata;
if (window == driverdata->window) {
driverdata->window = NULL;
}
}
#endif /* SDL_VIDEO_DRIVER_NACL */
/* vi: set ts=4 sw=4 expandtab: */

View File

@ -0,0 +1,32 @@
/*
Simple DirectMedia Layer
Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
This software is provided 'as-is', without any express or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
1. The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
2. Altered source versions must be plainly marked as such, and must not be
misrepresented as being the original software.
3. This notice may not be removed or altered from any source distribution.
*/
#include "../../SDL_internal.h"
#ifndef _SDL_naclwindow_h
#define _SDL_naclwindow_h
extern int NACL_CreateWindow(_THIS, SDL_Window * window);
extern void NACL_SetWindowTitle(_THIS, SDL_Window * window);
extern void NACL_DestroyWindow(_THIS, SDL_Window * window);
#endif /* _SDL_naclwindow_h */
/* vi: set ts=4 sw=4 expandtab: */

40
test/nacl/background.js Normal file
View File

@ -0,0 +1,40 @@
// Copyright (c) 2013 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
function makeURL(toolchain, config) {
return 'index.html?tc=' + toolchain + '&config=' + config;
}
function createWindow(url) {
console.log('loading ' + url);
chrome.app.window.create(url, {
width: 1024,
height: 800,
frame: 'none'
});
}
function onLaunched(launchData) {
// Send and XHR to get the URL to load from a configuration file.
// Normally you won't need to do this; just call:
//
// chrome.app.window.create('<your url>', {...});
//
// In the SDK we want to be able to load different URLs (for different
// toolchain/config combinations) from the commandline, so we to read
// this information from the file "run_package_config".
var xhr = new XMLHttpRequest();
xhr.open('GET', 'run_package_config', true);
xhr.onload = function() {
var toolchain_config = this.responseText.split(' ');
createWindow(makeURL.apply(null, toolchain_config));
};
xhr.onerror = function() {
// Can't find the config file, just load the default.
createWindow('index.html');
};
xhr.send();
}
chrome.app.runtime.onLaunched.addListener(onLaunched);

469
test/nacl/common.js Normal file
View File

@ -0,0 +1,469 @@
// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// Set to true when the Document is loaded IFF "test=true" is in the query
// string.
var isTest = false;
// Set to true when loading a "Release" NaCl module, false when loading a
// "Debug" NaCl module.
var isRelease = true;
// Javascript module pattern:
// see http://en.wikipedia.org/wiki/Unobtrusive_JavaScript#Namespaces
// In essence, we define an anonymous function which is immediately called and
// returns a new object. The new object contains only the exported definitions;
// all other definitions in the anonymous function are inaccessible to external
// code.
var common = (function() {
function isHostToolchain(tool) {
return tool == 'win' || tool == 'linux' || tool == 'mac';
}
/**
* Return the mime type for NaCl plugin.
*
* @param {string} tool The name of the toolchain, e.g. "glibc", "newlib" etc.
* @return {string} The mime-type for the kind of NaCl plugin matching
* the given toolchain.
*/
function mimeTypeForTool(tool) {
// For NaCl modules use application/x-nacl.
var mimetype = 'application/x-nacl';
if (isHostToolchain(tool)) {
// For non-NaCl PPAPI plugins use the x-ppapi-debug/release
// mime type.
if (isRelease)
mimetype = 'application/x-ppapi-release';
else
mimetype = 'application/x-ppapi-debug';
} else if (tool == 'pnacl' && isRelease) {
mimetype = 'application/x-pnacl';
}
return mimetype;
}
/**
* Check if the browser supports NaCl plugins.
*
* @param {string} tool The name of the toolchain, e.g. "glibc", "newlib" etc.
* @return {bool} True if the browser supports the type of NaCl plugin
* produced by the given toolchain.
*/
function browserSupportsNaCl(tool) {
// Assume host toolchains always work with the given browser.
// The below mime-type checking might not work with
// --register-pepper-plugins.
if (isHostToolchain(tool)) {
return true;
}
var mimetype = mimeTypeForTool(tool);
return navigator.mimeTypes[mimetype] !== undefined;
}
/**
* Inject a script into the DOM, and call a callback when it is loaded.
*
* @param {string} url The url of the script to load.
* @param {Function} onload The callback to call when the script is loaded.
* @param {Function} onerror The callback to call if the script fails to load.
*/
function injectScript(url, onload, onerror) {
var scriptEl = document.createElement('script');
scriptEl.type = 'text/javascript';
scriptEl.src = url;
scriptEl.onload = onload;
if (onerror) {
scriptEl.addEventListener('error', onerror, false);
}
document.head.appendChild(scriptEl);
}
/**
* Run all tests for this example.
*
* @param {Object} moduleEl The module DOM element.
*/
function runTests(moduleEl) {
console.log('runTests()');
common.tester = new Tester();
// All NaCl SDK examples are OK if the example exits cleanly; (i.e. the
// NaCl module returns 0 or calls exit(0)).
//
// Without this exception, the browser_tester thinks that the module
// has crashed.
common.tester.exitCleanlyIsOK();
common.tester.addAsyncTest('loaded', function(test) {
test.pass();
});
if (typeof window.addTests !== 'undefined') {
window.addTests();
}
common.tester.waitFor(moduleEl);
common.tester.run();
}
/**
* Create the Native Client <embed> element as a child of the DOM element
* named "listener".
*
* @param {string} name The name of the example.
* @param {string} tool The name of the toolchain, e.g. "glibc", "newlib" etc.
* @param {string} path Directory name where .nmf file can be found.
* @param {number} width The width to create the plugin.
* @param {number} height The height to create the plugin.
* @param {Object} attrs Dictionary of attributes to set on the module.
*/
function createNaClModule(name, tool, path, width, height, attrs) {
var moduleEl = document.createElement('embed');
moduleEl.setAttribute('name', 'nacl_module');
moduleEl.setAttribute('id', 'nacl_module');
moduleEl.setAttribute('width', width);
moduleEl.setAttribute('height', height);
moduleEl.setAttribute('path', path);
moduleEl.setAttribute('src', path + '/' + name + '.nmf');
// Add any optional arguments
if (attrs) {
for (var key in attrs) {
moduleEl.setAttribute(key, attrs[key]);
}
}
var mimetype = mimeTypeForTool(tool);
moduleEl.setAttribute('type', mimetype);
// The <EMBED> element is wrapped inside a <DIV>, which has both a 'load'
// and a 'message' event listener attached. This wrapping method is used
// instead of attaching the event listeners directly to the <EMBED> element
// to ensure that the listeners are active before the NaCl module 'load'
// event fires.
var listenerDiv = document.getElementById('listener');
listenerDiv.appendChild(moduleEl);
// Host plugins don't send a moduleDidLoad message. We'll fake it here.
var isHost = isHostToolchain(tool);
if (isHost) {
window.setTimeout(function() {
moduleEl.readyState = 1;
moduleEl.dispatchEvent(new CustomEvent('loadstart'));
moduleEl.readyState = 4;
moduleEl.dispatchEvent(new CustomEvent('load'));
moduleEl.dispatchEvent(new CustomEvent('loadend'));
}, 100); // 100 ms
}
// This is code that is only used to test the SDK.
if (isTest) {
var loadNaClTest = function() {
injectScript('nacltest.js', function() {
runTests(moduleEl);
});
};
// Try to load test.js for the example. Whether or not it exists, load
// nacltest.js.
injectScript('test.js', loadNaClTest, loadNaClTest);
}
}
/**
* Add the default "load" and "message" event listeners to the element with
* id "listener".
*
* The "load" event is sent when the module is successfully loaded. The
* "message" event is sent when the naclModule posts a message using
* PPB_Messaging.PostMessage() (in C) or pp::Instance().PostMessage() (in
* C++).
*/
function attachDefaultListeners() {
var listenerDiv = document.getElementById('listener');
listenerDiv.addEventListener('load', moduleDidLoad, true);
listenerDiv.addEventListener('message', handleMessage, true);
listenerDiv.addEventListener('error', handleError, true);
listenerDiv.addEventListener('crash', handleCrash, true);
if (typeof window.attachListeners !== 'undefined') {
window.attachListeners();
}
}
/**
* Called when the NaCl module fails to load.
*
* This event listener is registered in createNaClModule above.
*/
function handleError(event) {
// We can't use common.naclModule yet because the module has not been
// loaded.
var moduleEl = document.getElementById('nacl_module');
updateStatus('ERROR [' + moduleEl.lastError + ']');
}
/**
* Called when the Browser can not communicate with the Module
*
* This event listener is registered in attachDefaultListeners above.
*/
function handleCrash(event) {
if (common.naclModule.exitStatus == -1) {
updateStatus('CRASHED');
} else {
updateStatus('EXITED [' + common.naclModule.exitStatus + ']');
}
if (typeof window.handleCrash !== 'undefined') {
window.handleCrash(common.naclModule.lastError);
}
}
/**
* Called when the NaCl module is loaded.
*
* This event listener is registered in attachDefaultListeners above.
*/
function moduleDidLoad() {
common.naclModule = document.getElementById('nacl_module');
updateStatus('RUNNING');
if (typeof window.moduleDidLoad !== 'undefined') {
window.moduleDidLoad();
}
}
/**
* Hide the NaCl module's embed element.
*
* We don't want to hide by default; if we do, it is harder to determine that
* a plugin failed to load. Instead, call this function inside the example's
* "moduleDidLoad" function.
*
*/
function hideModule() {
// Setting common.naclModule.style.display = "None" doesn't work; the
// module will no longer be able to receive postMessages.
common.naclModule.style.height = '0';
}
/**
* Remove the NaCl module from the page.
*/
function removeModule() {
common.naclModule.parentNode.removeChild(common.naclModule);
common.naclModule = null;
}
/**
* Return true when |s| starts with the string |prefix|.
*
* @param {string} s The string to search.
* @param {string} prefix The prefix to search for in |s|.
*/
function startsWith(s, prefix) {
// indexOf would search the entire string, lastIndexOf(p, 0) only checks at
// the first index. See: http://stackoverflow.com/a/4579228
return s.lastIndexOf(prefix, 0) === 0;
}
/** Maximum length of logMessageArray. */
var kMaxLogMessageLength = 20;
/** An array of messages to display in the element with id "log". */
var logMessageArray = [];
/**
* Add a message to an element with id "log".
*
* This function is used by the default "log:" message handler.
*
* @param {string} message The message to log.
*/
function logMessage(message) {
logMessageArray.push(message);
if (logMessageArray.length > kMaxLogMessageLength)
logMessageArray.shift();
document.getElementById('log').textContent = logMessageArray.join('\n');
console.log(message);
}
/**
*/
var defaultMessageTypes = {
'alert': alert,
'log': logMessage
};
/**
* Called when the NaCl module sends a message to JavaScript (via
* PPB_Messaging.PostMessage())
*
* This event listener is registered in createNaClModule above.
*
* @param {Event} message_event A message event. message_event.data contains
* the data sent from the NaCl module.
*/
function handleMessage(message_event) {
if (typeof message_event.data === 'string') {
for (var type in defaultMessageTypes) {
if (defaultMessageTypes.hasOwnProperty(type)) {
if (startsWith(message_event.data, type + ':')) {
func = defaultMessageTypes[type];
func(message_event.data.slice(type.length + 1));
return;
}
}
}
}
if (typeof window.handleMessage !== 'undefined') {
window.handleMessage(message_event);
return;
}
logMessage('Unhandled message: ' + message_event.data);
}
/**
* Called when the DOM content has loaded; i.e. the page's document is fully
* parsed. At this point, we can safely query any elements in the document via
* document.querySelector, document.getElementById, etc.
*
* @param {string} name The name of the example.
* @param {string} tool The name of the toolchain, e.g. "glibc", "newlib" etc.
* @param {string} path Directory name where .nmf file can be found.
* @param {number} width The width to create the plugin.
* @param {number} height The height to create the plugin.
* @param {Object} attrs Optional dictionary of additional attributes.
*/
function domContentLoaded(name, tool, path, width, height, attrs) {
// If the page loads before the Native Client module loads, then set the
// status message indicating that the module is still loading. Otherwise,
// do not change the status message.
updateStatus('Page loaded.');
if (!browserSupportsNaCl(tool)) {
updateStatus(
'Browser does not support NaCl (' + tool + '), or NaCl is disabled');
} else if (common.naclModule == null) {
updateStatus('Creating embed: ' + tool);
// We use a non-zero sized embed to give Chrome space to place the bad
// plug-in graphic, if there is a problem.
width = typeof width !== 'undefined' ? width : 200;
height = typeof height !== 'undefined' ? height : 200;
attachDefaultListeners();
createNaClModule(name, tool, path, width, height, attrs);
} else {
// It's possible that the Native Client module onload event fired
// before the page's onload event. In this case, the status message
// will reflect 'SUCCESS', but won't be displayed. This call will
// display the current message.
updateStatus('Waiting.');
}
}
/** Saved text to display in the element with id 'statusField'. */
var statusText = 'NO-STATUSES';
/**
* Set the global status message. If the element with id 'statusField'
* exists, then set its HTML to the status message as well.
*
* @param {string} opt_message The message to set. If null or undefined, then
* set element 'statusField' to the message from the last call to
* updateStatus.
*/
function updateStatus(opt_message) {
if (opt_message) {
statusText = opt_message;
}
var statusField = document.getElementById('statusField');
if (statusField) {
statusField.innerHTML = statusText;
}
}
// The symbols to export.
return {
/** A reference to the NaCl module, once it is loaded. */
naclModule: null,
attachDefaultListeners: attachDefaultListeners,
domContentLoaded: domContentLoaded,
createNaClModule: createNaClModule,
hideModule: hideModule,
removeModule: removeModule,
logMessage: logMessage,
updateStatus: updateStatus
};
}());
// Listen for the DOM content to be loaded. This event is fired when parsing of
// the page's document has finished.
document.addEventListener('DOMContentLoaded', function() {
var body = document.body;
// The data-* attributes on the body can be referenced via body.dataset.
if (body.dataset) {
var loadFunction;
if (!body.dataset.customLoad) {
loadFunction = common.domContentLoaded;
} else if (typeof window.domContentLoaded !== 'undefined') {
loadFunction = window.domContentLoaded;
}
// From https://developer.mozilla.org/en-US/docs/DOM/window.location
var searchVars = {};
if (window.location.search.length > 1) {
var pairs = window.location.search.substr(1).split('&');
for (var key_ix = 0; key_ix < pairs.length; key_ix++) {
var keyValue = pairs[key_ix].split('=');
searchVars[unescape(keyValue[0])] =
keyValue.length > 1 ? unescape(keyValue[1]) : '';
}
}
if (loadFunction) {
var toolchains = body.dataset.tools.split(' ');
var configs = body.dataset.configs.split(' ');
var attrs = {};
if (body.dataset.attrs) {
var attr_list = body.dataset.attrs.split(' ');
for (var key in attr_list) {
var attr = attr_list[key].split('=');
var key = attr[0];
var value = attr[1];
attrs[key] = value;
}
}
var tc = toolchains.indexOf(searchVars.tc) !== -1 ?
searchVars.tc : toolchains[0];
// If the config value is included in the search vars, use that.
// Otherwise default to Release if it is valid, or the first value if
// Release is not valid.
if (configs.indexOf(searchVars.config) !== -1)
var config = searchVars.config;
else if (configs.indexOf('Release') !== -1)
var config = 'Release';
else
var config = configs[0];
var pathFormat = body.dataset.path;
var path = pathFormat.replace('{tc}', tc).replace('{config}', config);
isTest = searchVars.test === 'true';
isRelease = path.toLowerCase().indexOf('release') != -1;
loadFunction(body.dataset.name, tc, path, body.dataset.width,
body.dataset.height, attrs);
}
}
});

21
test/nacl/index.html Normal file
View File

@ -0,0 +1,21 @@
<!DOCTYPE html>
<html>
<!--
Copyright (c) 2012 The Chromium Authors. All rights reserved.
Use of this source code is governed by a BSD-style license that can be
found in the LICENSE file.
-->
<head>
<meta http-equiv="Pragma" content="no-cache">
<meta http-equiv="Expires" content="-1">
<title>SDL NACL Test</title>
<script type="text/javascript" src="common.js"></script>
</head>
<body data-width="640" data-height="640" data-name="sdl_app" data-tools="pnacl" data-configs="Debug Release" data-path="{tc}/{config}">
<h1>SDL NACL Test</h1>
<h2>Status: <code id="statusField">NO-STATUS</code></h2>
<!-- The NaCl plugin will be embedded inside the element with id "listener".
See common.js.-->
<div id="listener"></div>
</body>
</html>

22
test/nacl/manifest.json Normal file
View File

@ -0,0 +1,22 @@
{
"name": "SDL testgles2",
"version": "33.0.1750.117",
"minimum_chrome_version": "33.0.1750.117",
"manifest_version": 2,
"description": "testgles2",
"offline_enabled": true,
"icons": {
"128": "icon128.png"
},
"app": {
"background": {
"scripts": ["background.js"]
}
},
"key": "MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCMN716Qyu0l2EHNFqIJVqVysFcTR6urqhaGGqW4UK7slBaURz9+Sb1b4Ot5P1uQNE5c+CTU5Vu61wpqmSqMMxqHLWdPPMh8uRlyctsb2cxWwG6XoGSvpX29NsQVUFXd4v2tkJm3G9t+V0X8TYskrvWQmnyOW8OEIDvrBhUEfFxWQIDAQAB",
"oauth2": {
"client_id": "903965034255.apps.googleusercontent.com",
"scopes": ["https://www.googleapis.com/auth/drive"]
},
"permissions": []
}

View File

@ -16,7 +16,7 @@
#include "SDL_test_common.h" #include "SDL_test_common.h"
#if defined(__IPHONEOS__) || defined(__ANDROID__) #if defined(__IPHONEOS__) || defined(__ANDROID__) || defined(__NACL__)
#define HAVE_OPENGLES2 #define HAVE_OPENGLES2
#endif #endif
@ -195,6 +195,8 @@ process_shader(GLuint *shader, const char * source, GLint shader_type)
{ {
GLint status = GL_FALSE; GLint status = GL_FALSE;
const char *shaders[1] = { NULL }; const char *shaders[1] = { NULL };
char buffer[1024];
GLsizei length;
/* Create shader and load into GL. */ /* Create shader and load into GL. */
*shader = GL_CHECK(ctx.glCreateShader(shader_type)); *shader = GL_CHECK(ctx.glCreateShader(shader_type));
@ -212,7 +214,9 @@ process_shader(GLuint *shader, const char * source, GLint shader_type)
/* Dump debug info (source and log) if compilation failed. */ /* Dump debug info (source and log) if compilation failed. */
if(status != GL_TRUE) { if(status != GL_TRUE) {
SDL_Log("Shader compilation failed"); ctx.glGetProgramInfoLog(*shader, sizeof(buffer), &length, &buffer[0]);
buffer[length] = '\0';
SDL_Log("Shader compilation failed: %s", buffer);fflush(stderr);
quit(-1); quit(-1);
} }
} }
@ -675,7 +679,7 @@ main(int argc, char *argv[])
SDL_Log("%2.2f frames per second\n", SDL_Log("%2.2f frames per second\n",
((double) frames * 1000) / (now - then)); ((double) frames * 1000) / (now - then));
} }
#if !defined(__ANDROID__) #if !defined(__ANDROID__) && !defined(__NACL__)
quit(0); quit(0);
#endif #endif
return 0; return 0;

View File

@ -161,6 +161,16 @@ main(int argc, char *argv[])
quit(2); quit(2);
} }
#if __NACL__
SDL_RWUmount("/");
SDL_RWMount(
"", /* source */
"/", /* target */
"httpfs", /* filesystemtype */
0, /* mountflags */
""); /* data specific to the html5fs type */
#endif
drawstates = SDL_stack_alloc(DrawState, state->num_windows); drawstates = SDL_stack_alloc(DrawState, state->num_windows);
for (i = 0; i < state->num_windows; ++i) { for (i = 0; i < state->num_windows; ++i) {
DrawState *drawstate = &drawstates[i]; DrawState *drawstate = &drawstates[i];