diff options
author | binji <binji@chromium.org> | 2015-02-23 17:01:05 -0800 |
---|---|---|
committer | Commit bot <commit-bot@chromium.org> | 2015-02-24 01:01:54 +0000 |
commit | cd3968da9da9621a56afaf185ebc416a5955cb09 (patch) | |
tree | 9a3a484432cbfe94238b0e88b676692b0259a88e /native_client_sdk | |
parent | 062b5642c4199a8ddc882c8ae06a794d211c0bf9 (diff) | |
download | chromium_src-cd3968da9da9621a56afaf185ebc416a5955cb09.zip chromium_src-cd3968da9da9621a56afaf185ebc416a5955cb09.tar.gz chromium_src-cd3968da9da9621a56afaf185ebc416a5955cb09.tar.bz2 |
[NaCl SDK] Switch ppapi_simple to C library
Actually, this creates two libraries:
ppapi_simple
ppapi_simple_cpp
The second must be used if you want to use ppapi_cpp. If you use the C
interfaces exclusively, you can use ppapi_simple instead.
BUG=
Review URL: https://codereview.chromium.org/914983003
Cr-Commit-Position: refs/heads/master@{#317704}
Diffstat (limited to 'native_client_sdk')
34 files changed, 1093 insertions, 1044 deletions
diff --git a/native_client_sdk/src/build_tools/sdk_files.list b/native_client_sdk/src/build_tools/sdk_files.list index 161ac2b..20e78a9 100644 --- a/native_client_sdk/src/build_tools/sdk_files.list +++ b/native_client_sdk/src/build_tools/sdk_files.list @@ -95,26 +95,28 @@ include/sdk_util/* [win]include/win/* include/win/poll.h include/win/sys/poll.h -[linux]lib/${PLATFORM}_host/Debug/libgmock.a -[linux]lib/${PLATFORM}_host/Debug/libgtest.a +[linux,mac]lib/${PLATFORM}_host/Debug/libgmock.a +[linux,mac]lib/${PLATFORM}_host/Debug/libgtest.a [linux]lib/${PLATFORM}_host/Debug/libjsoncpp.a -[linux]lib/${PLATFORM}_host/Debug/libnacl_io.a +[linux,mac]lib/${PLATFORM}_host/Debug/libnacl_io.a [linux,mac]lib/${PLATFORM}_host/Debug/libppapi.a -[linux]lib/${PLATFORM}_host/Debug/libppapi_cpp.a -[linux]lib/${PLATFORM}_host/Debug/libppapi_cpp_private.a -[linux]lib/${PLATFORM}_host/Debug/libppapi_gles2.a -[linux]lib/${PLATFORM}_host/Debug/libppapi_simple.a -[linux]lib/${PLATFORM}_host/Debug/libsdk_util.a -[linux]lib/${PLATFORM}_host/Release/libgmock.a -[linux]lib/${PLATFORM}_host/Release/libgtest.a +[linux,mac]lib/${PLATFORM}_host/Debug/libppapi_cpp.a +[linux,mac]lib/${PLATFORM}_host/Debug/libppapi_cpp_private.a +[linux,mac]lib/${PLATFORM}_host/Debug/libppapi_gles2.a +[linux,mac]lib/${PLATFORM}_host/Debug/libppapi_simple.a +[linux,mac]lib/${PLATFORM}_host/Debug/libppapi_simple_cpp.a +[linux,mac]lib/${PLATFORM}_host/Debug/libsdk_util.a +[linux,mac]lib/${PLATFORM}_host/Release/libgmock.a +[linux,mac]lib/${PLATFORM}_host/Release/libgtest.a [linux]lib/${PLATFORM}_host/Release/libjsoncpp.a -[linux]lib/${PLATFORM}_host/Release/libnacl_io.a +[linux,mac]lib/${PLATFORM}_host/Release/libnacl_io.a [linux,mac]lib/${PLATFORM}_host/Release/libppapi.a -[linux]lib/${PLATFORM}_host/Release/libppapi_cpp.a -[linux]lib/${PLATFORM}_host/Release/libppapi_cpp_private.a -[linux]lib/${PLATFORM}_host/Release/libppapi_gles2.a -[linux]lib/${PLATFORM}_host/Release/libppapi_simple.a -[linux]lib/${PLATFORM}_host/Release/libsdk_util.a +[linux,mac]lib/${PLATFORM}_host/Release/libppapi_cpp.a +[linux,mac]lib/${PLATFORM}_host/Release/libppapi_cpp_private.a +[linux,mac]lib/${PLATFORM}_host/Release/libppapi_gles2.a +[linux,mac]lib/${PLATFORM}_host/Release/libppapi_simple.a +[linux,mac]lib/${PLATFORM}_host/Release/libppapi_simple_cpp.a +[linux,mac]lib/${PLATFORM}_host/Release/libsdk_util.a [win]lib/${PLATFORM}_x86_32_host/Debug/gmock.lib [win]lib/${PLATFORM}_x86_32_host/Debug/gtest.lib [win]lib/${PLATFORM}_x86_32_host/Debug/jsoncpp.lib @@ -140,6 +142,7 @@ lib/clang-newlib_arm/Debug/libppapi_cpp.a lib/clang-newlib_arm/Debug/libppapi_cpp_private.a lib/clang-newlib_arm/Debug/libppapi_gles2.a lib/clang-newlib_arm/Debug/libppapi_simple.a +lib/clang-newlib_arm/Debug/libppapi_simple_cpp.a lib/clang-newlib_arm/Debug/libsdk_util.a lib/clang-newlib_arm/Release/libgmock.a lib/clang-newlib_arm/Release/libgtest.a @@ -148,6 +151,7 @@ lib/clang-newlib_arm/Release/libppapi_cpp.a lib/clang-newlib_arm/Release/libppapi_cpp_private.a lib/clang-newlib_arm/Release/libppapi_gles2.a lib/clang-newlib_arm/Release/libppapi_simple.a +lib/clang-newlib_arm/Release/libppapi_simple_cpp.a lib/clang-newlib_arm/Release/libsdk_util.a lib/clang-newlib_x86_32/Debug/libgmock.a lib/clang-newlib_x86_32/Debug/libgtest.a @@ -156,6 +160,7 @@ lib/clang-newlib_x86_32/Debug/libppapi_cpp.a lib/clang-newlib_x86_32/Debug/libppapi_cpp_private.a lib/clang-newlib_x86_32/Debug/libppapi_gles2.a lib/clang-newlib_x86_32/Debug/libppapi_simple.a +lib/clang-newlib_x86_32/Debug/libppapi_simple_cpp.a lib/clang-newlib_x86_32/Debug/libsdk_util.a lib/clang-newlib_x86_32/Release/libgmock.a lib/clang-newlib_x86_32/Release/libgtest.a @@ -164,6 +169,7 @@ lib/clang-newlib_x86_32/Release/libppapi_cpp.a lib/clang-newlib_x86_32/Release/libppapi_cpp_private.a lib/clang-newlib_x86_32/Release/libppapi_gles2.a lib/clang-newlib_x86_32/Release/libppapi_simple.a +lib/clang-newlib_x86_32/Release/libppapi_simple_cpp.a lib/clang-newlib_x86_32/Release/libsdk_util.a lib/clang-newlib_x86_64/Debug/libgmock.a lib/clang-newlib_x86_64/Debug/libgtest.a @@ -172,6 +178,7 @@ lib/clang-newlib_x86_64/Debug/libppapi_cpp.a lib/clang-newlib_x86_64/Debug/libppapi_cpp_private.a lib/clang-newlib_x86_64/Debug/libppapi_gles2.a lib/clang-newlib_x86_64/Debug/libppapi_simple.a +lib/clang-newlib_x86_64/Debug/libppapi_simple_cpp.a lib/clang-newlib_x86_64/Debug/libsdk_util.a lib/clang-newlib_x86_64/Release/libgmock.a lib/clang-newlib_x86_64/Release/libgtest.a @@ -180,6 +187,7 @@ lib/clang-newlib_x86_64/Release/libppapi_cpp.a lib/clang-newlib_x86_64/Release/libppapi_cpp_private.a lib/clang-newlib_x86_64/Release/libppapi_gles2.a lib/clang-newlib_x86_64/Release/libppapi_simple.a +lib/clang-newlib_x86_64/Release/libppapi_simple_cpp.a lib/clang-newlib_x86_64/Release/libsdk_util.a lib/glibc_x86_32/Debug/libgmock.a lib/glibc_x86_32/Debug/libgmock.so @@ -197,6 +205,8 @@ lib/glibc_x86_32/Debug/libppapi_gles2.a lib/glibc_x86_32/Debug/libppapi_gles2.so lib/glibc_x86_32/Debug/libppapi_simple.a lib/glibc_x86_32/Debug/libppapi_simple.so +lib/glibc_x86_32/Debug/libppapi_simple_cpp.a +lib/glibc_x86_32/Debug/libppapi_simple_cpp.so lib/glibc_x86_32/Debug/libsdk_util.a lib/glibc_x86_32/Debug/libsdk_util.so lib/glibc_x86_32/Release/libgmock.a @@ -215,6 +225,8 @@ lib/glibc_x86_32/Release/libppapi_gles2.a lib/glibc_x86_32/Release/libppapi_gles2.so lib/glibc_x86_32/Release/libppapi_simple.a lib/glibc_x86_32/Release/libppapi_simple.so +lib/glibc_x86_32/Release/libppapi_simple_cpp.a +lib/glibc_x86_32/Release/libppapi_simple_cpp.so lib/glibc_x86_32/Release/libsdk_util.a lib/glibc_x86_32/Release/libsdk_util.so lib/glibc_x86_64/Debug/libgmock.a @@ -233,6 +245,8 @@ lib/glibc_x86_64/Debug/libppapi_gles2.a lib/glibc_x86_64/Debug/libppapi_gles2.so lib/glibc_x86_64/Debug/libppapi_simple.a lib/glibc_x86_64/Debug/libppapi_simple.so +lib/glibc_x86_64/Debug/libppapi_simple_cpp.a +lib/glibc_x86_64/Debug/libppapi_simple_cpp.so lib/glibc_x86_64/Debug/libsdk_util.a lib/glibc_x86_64/Debug/libsdk_util.so lib/glibc_x86_64/Release/libgmock.a @@ -251,24 +265,10 @@ lib/glibc_x86_64/Release/libppapi_gles2.a lib/glibc_x86_64/Release/libppapi_gles2.so lib/glibc_x86_64/Release/libppapi_simple.a lib/glibc_x86_64/Release/libppapi_simple.so +lib/glibc_x86_64/Release/libppapi_simple_cpp.a +lib/glibc_x86_64/Release/libppapi_simple_cpp.so lib/glibc_x86_64/Release/libsdk_util.a lib/glibc_x86_64/Release/libsdk_util.so -[mac]lib/mac_host/Debug/libgmock.a -[mac]lib/mac_host/Debug/libgtest.a -[mac]lib/mac_host/Debug/libnacl_io.a -[mac]lib/mac_host/Debug/libppapi_cpp.a -[mac]lib/mac_host/Debug/libppapi_cpp_private.a -[mac]lib/mac_host/Debug/libppapi_gles2.a -[mac]lib/mac_host/Debug/libppapi_simple.a -[mac]lib/mac_host/Debug/libsdk_util.a -[mac]lib/mac_host/Release/libgmock.a -[mac]lib/mac_host/Release/libgtest.a -[mac]lib/mac_host/Release/libnacl_io.a -[mac]lib/mac_host/Release/libppapi_cpp.a -[mac]lib/mac_host/Release/libppapi_cpp_private.a -[mac]lib/mac_host/Release/libppapi_gles2.a -[mac]lib/mac_host/Release/libppapi_simple.a -[mac]lib/mac_host/Release/libsdk_util.a lib/newlib_arm/Debug/liberror_handling.a lib/newlib_arm/Debug/libgmock.a lib/newlib_arm/Debug/libgtest.a @@ -278,6 +278,7 @@ lib/newlib_arm/Debug/libppapi_cpp.a lib/newlib_arm/Debug/libppapi_cpp_private.a lib/newlib_arm/Debug/libppapi_gles2.a lib/newlib_arm/Debug/libppapi_simple.a +lib/newlib_arm/Debug/libppapi_simple_cpp.a lib/newlib_arm/Debug/libsdk_util.a lib/newlib_arm/Release/liberror_handling.a lib/newlib_arm/Release/libgmock.a @@ -288,6 +289,7 @@ lib/newlib_arm/Release/libppapi_cpp.a lib/newlib_arm/Release/libppapi_cpp_private.a lib/newlib_arm/Release/libppapi_gles2.a lib/newlib_arm/Release/libppapi_simple.a +lib/newlib_arm/Release/libppapi_simple_cpp.a lib/newlib_arm/Release/libsdk_util.a lib/newlib_x86_32/Debug/liberror_handling.a lib/newlib_x86_32/Debug/libgmock.a @@ -298,6 +300,7 @@ lib/newlib_x86_32/Debug/libppapi_cpp.a lib/newlib_x86_32/Debug/libppapi_cpp_private.a lib/newlib_x86_32/Debug/libppapi_gles2.a lib/newlib_x86_32/Debug/libppapi_simple.a +lib/newlib_x86_32/Debug/libppapi_simple_cpp.a lib/newlib_x86_32/Debug/libsdk_util.a lib/newlib_x86_32/Release/liberror_handling.a lib/newlib_x86_32/Release/libgmock.a @@ -308,6 +311,7 @@ lib/newlib_x86_32/Release/libppapi_cpp.a lib/newlib_x86_32/Release/libppapi_cpp_private.a lib/newlib_x86_32/Release/libppapi_gles2.a lib/newlib_x86_32/Release/libppapi_simple.a +lib/newlib_x86_32/Release/libppapi_simple_cpp.a lib/newlib_x86_32/Release/libsdk_util.a lib/newlib_x86_64/Debug/liberror_handling.a lib/newlib_x86_64/Debug/libgmock.a @@ -318,6 +322,7 @@ lib/newlib_x86_64/Debug/libppapi_cpp.a lib/newlib_x86_64/Debug/libppapi_cpp_private.a lib/newlib_x86_64/Debug/libppapi_gles2.a lib/newlib_x86_64/Debug/libppapi_simple.a +lib/newlib_x86_64/Debug/libppapi_simple_cpp.a lib/newlib_x86_64/Debug/libsdk_util.a lib/newlib_x86_64/Release/liberror_handling.a lib/newlib_x86_64/Release/libgmock.a @@ -328,6 +333,7 @@ lib/newlib_x86_64/Release/libppapi_cpp.a lib/newlib_x86_64/Release/libppapi_cpp_private.a lib/newlib_x86_64/Release/libppapi_gles2.a lib/newlib_x86_64/Release/libppapi_simple.a +lib/newlib_x86_64/Release/libppapi_simple_cpp.a lib/newlib_x86_64/Release/libsdk_util.a lib/pnacl/Debug/libgmock.a lib/pnacl/Debug/libgtest.a @@ -337,6 +343,7 @@ lib/pnacl/Debug/libppapi_cpp.a lib/pnacl/Debug/libppapi_cpp_private.a lib/pnacl/Debug/libppapi_gles2.a lib/pnacl/Debug/libppapi_simple.a +lib/pnacl/Debug/libppapi_simple_cpp.a lib/pnacl/Debug/libsdk_util.a lib/pnacl/Release/libgmock.a lib/pnacl/Release/libgtest.a @@ -346,6 +353,7 @@ lib/pnacl/Release/libppapi_cpp.a lib/pnacl/Release/libppapi_cpp_private.a lib/pnacl/Release/libppapi_gles2.a lib/pnacl/Release/libppapi_simple.a +lib/pnacl/Release/libppapi_simple_cpp.a lib/pnacl/Release/libsdk_util.a LICENSE NOTICE @@ -365,6 +373,7 @@ src/ppapi_cpp/* src/ppapi_cpp_private/* src/ppapi_gles2/* src/ppapi_simple/* +src/ppapi_simple_cpp/* [win]src/pthread/* [win]src/pthread/README src/sdk_util/* diff --git a/native_client_sdk/src/build_tools/test_projects.py b/native_client_sdk/src/build_tools/test_projects.py index 206bef0..f89eefe 100755 --- a/native_client_sdk/src/build_tools/test_projects.py +++ b/native_client_sdk/src/build_tools/test_projects.py @@ -336,8 +336,7 @@ def main(args): parser.add_argument('-b', '--build', help='Build each project before testing.', action='store_true') parser.add_argument('--retry-times', - help='Number of types to retry on failure (Default: %default)', - type=int, default=1) + help='Number of types to retry on failure', type=int, default=1) parser.add_argument('projects', nargs='*') options = parser.parse_args(args) diff --git a/native_client_sdk/src/examples/benchmarks/example.dsc b/native_client_sdk/src/examples/benchmarks/example.dsc index 3fc8d50..f2c3af6 100644 --- a/native_client_sdk/src/examples/benchmarks/example.dsc +++ b/native_client_sdk/src/examples/benchmarks/example.dsc @@ -24,8 +24,8 @@ 'thread_pool.h', 'thread_pool.cc' ], - 'DEPS': ['ppapi_simple', 'nacl_io'], - 'LIBS': ['ppapi_simple', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] + 'DEPS': [], + 'LIBS': ['sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/demo/earth/example.dsc b/native_client_sdk/src/examples/demo/earth/example.dsc index 4d4829c..79bde6f 100644 --- a/native_client_sdk/src/examples/demo/earth/example.dsc +++ b/native_client_sdk/src/examples/demo/earth/example.dsc @@ -7,7 +7,7 @@ 'SOURCES' : [ 'earth.cc' ], - 'LIBS': ['ppapi_simple', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] + 'LIBS': ['ppapi_simple_cpp', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/demo/earth_simd/example.dsc b/native_client_sdk/src/examples/demo/earth_simd/example.dsc index b6ab87a..b5744ea 100644 --- a/native_client_sdk/src/examples/demo/earth_simd/example.dsc +++ b/native_client_sdk/src/examples/demo/earth_simd/example.dsc @@ -7,7 +7,7 @@ 'SOURCES' : [ 'earth.cc' ], - 'LIBS': ['ppapi_simple', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] + 'LIBS': ['ppapi_simple_cpp', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/demo/flock/example.dsc b/native_client_sdk/src/examples/demo/flock/example.dsc index e32cb06..23d7625 100644 --- a/native_client_sdk/src/examples/demo/flock/example.dsc +++ b/native_client_sdk/src/examples/demo/flock/example.dsc @@ -13,7 +13,7 @@ 'vector2.h' ], 'DEPS': ['ppapi_simple', 'nacl_io'], - 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi_cpp', 'ppapi', 'pthread'] + 'LIBS': ['ppapi_simple_cpp', 'nacl_io', 'ppapi_cpp', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/demo/life/example.dsc b/native_client_sdk/src/examples/demo/life/example.dsc index aedef27..383ab59 100644 --- a/native_client_sdk/src/examples/demo/life/example.dsc +++ b/native_client_sdk/src/examples/demo/life/example.dsc @@ -8,7 +8,7 @@ 'life.c', ], 'DEPS': ['ppapi_simple', 'nacl_io'], - 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi_cpp', 'ppapi', 'pthread'] + 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi', 'pthread'] } ], 'DEST': 'examples/demo', diff --git a/native_client_sdk/src/examples/demo/life_simd/example.dsc b/native_client_sdk/src/examples/demo/life_simd/example.dsc index 2768624..38def72 100644 --- a/native_client_sdk/src/examples/demo/life_simd/example.dsc +++ b/native_client_sdk/src/examples/demo/life_simd/example.dsc @@ -8,7 +8,7 @@ 'life.cc', ], 'DEPS': ['ppapi_simple', 'nacl_io'], - 'LIBS': ['ppapi_simple', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] + 'LIBS': ['ppapi_simple_cpp', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/demo/life_simd/life.cc b/native_client_sdk/src/examples/demo/life_simd/life.cc index e784b99..b99f2bc 100644 --- a/native_client_sdk/src/examples/demo/life_simd/life.cc +++ b/native_client_sdk/src/examples/demo/life_simd/life.cc @@ -14,6 +14,7 @@ #include <ppapi/c/ppb_input_event.h> #include <ppapi/cpp/fullscreen.h> #include <ppapi/cpp/input_event.h> +#include <ppapi/cpp/instance_handle.h> #include <ppapi/cpp/var.h> #include <ppapi/cpp/var_array.h> #include <ppapi/cpp/var_array_buffer.h> @@ -274,7 +275,7 @@ void Life::HandleEvent(PSEvent* ps_event) { } case PP_INPUTEVENT_TYPE_KEYDOWN: { - pp::Fullscreen fullscreen(PSInstance::GetInstance()); + pp::Fullscreen fullscreen((pp::InstanceHandle(PSGetInstanceId()))); bool isFullscreen = fullscreen.IsFullscreen(); fullscreen.SetFullscreen(!isFullscreen); break; diff --git a/native_client_sdk/src/examples/demo/pi_generator/example.dsc b/native_client_sdk/src/examples/demo/pi_generator/example.dsc index a1cef4c..79bf8bd 100644 --- a/native_client_sdk/src/examples/demo/pi_generator/example.dsc +++ b/native_client_sdk/src/examples/demo/pi_generator/example.dsc @@ -5,8 +5,8 @@ 'NAME' : 'pi_generator', 'TYPE' : 'main', 'SOURCES' : ['pi_generator.cc'], - 'DEPS': ['ppapi_simple', 'nacl_io', 'ppapi_cpp'], - 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi_cpp', 'ppapi', 'pthread'] + 'DEPS': ['ppapi_simple', 'nacl_io'], + 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/demo/voronoi/example.dsc b/native_client_sdk/src/examples/demo/voronoi/example.dsc index 1d766d6..64aa998 100644 --- a/native_client_sdk/src/examples/demo/voronoi/example.dsc +++ b/native_client_sdk/src/examples/demo/voronoi/example.dsc @@ -8,7 +8,7 @@ 'voronoi.cc' ], - 'LIBS': ['ppapi_simple', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] + 'LIBS': ['ppapi_simple_cpp', 'nacl_io', 'sdk_util', 'ppapi_cpp', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/examples/tutorial/testing/example.dsc b/native_client_sdk/src/examples/tutorial/testing/example.dsc index 8a1f551..d210f60 100644 --- a/native_client_sdk/src/examples/tutorial/testing/example.dsc +++ b/native_client_sdk/src/examples/tutorial/testing/example.dsc @@ -6,7 +6,7 @@ 'NAME' : 'testing', 'TYPE' : 'main', 'SOURCES' : ['testing.cc'], - 'LIBS' : ['ppapi_simple', 'ppapi', 'gtest', 'nacl_io', 'ppapi_cpp', 'pthread'], + 'LIBS' : ['ppapi_simple_cpp', 'ppapi_cpp', 'ppapi', 'gtest', 'nacl_io', 'pthread'], 'CXXFLAGS': ['-Wno-sign-compare'] } ], diff --git a/native_client_sdk/src/examples/tutorial/using_ppapi_simple/example.dsc b/native_client_sdk/src/examples/tutorial/using_ppapi_simple/example.dsc index 856ae50..ee462d2 100644 --- a/native_client_sdk/src/examples/tutorial/using_ppapi_simple/example.dsc +++ b/native_client_sdk/src/examples/tutorial/using_ppapi_simple/example.dsc @@ -6,8 +6,8 @@ 'NAME' : 'using_ppapi_simple', 'TYPE' : 'main', 'SOURCES' : ['hello_world.c'], - 'DEPS': ['ppapi_simple', 'nacl_io', 'ppapi_cpp'], - 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi_cpp', 'ppapi', 'pthread'] + 'DEPS': ['ppapi_simple', 'nacl_io'], + 'LIBS': ['ppapi_simple', 'nacl_io', 'ppapi', 'pthread'] } ], 'DATA': [ diff --git a/native_client_sdk/src/libraries/ppapi_simple/library.dsc b/native_client_sdk/src/libraries/ppapi_simple/library.dsc index ada1bce..bf4880b 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/library.dsc +++ b/native_client_sdk/src/libraries/ppapi_simple/library.dsc @@ -5,14 +5,15 @@ 'NAME' : 'ppapi_simple', 'TYPE' : 'lib', 'SOURCES' : [ - "ps.cc", - "ps_context_2d.cc", - "ps_event.cc", - "ps_instance.cc", - "ps_interface.cc", - "ps_main.cc", + "ps.c", + "ps_context_2d.c", + "ps_event.c", + "ps_instance.c", + "ps_interface.c", + "ps_main.c", + "ps_entrypoints_c.c" ], - } + }, ], 'HEADERS': [ { diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps.c b/native_client_sdk/src/libraries/ppapi_simple/ps.c new file mode 100644 index 0000000..6af5b08 --- /dev/null +++ b/native_client_sdk/src/libraries/ppapi_simple/ps.c @@ -0,0 +1,20 @@ +/* Copyright 2015 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. */ + +#include "ppapi_simple/ps.h" + +#include "ppapi/c/pp_instance.h" +#include "ppapi/c/ppb.h" + +/* Defined in ps_instance.c */ +extern PP_Instance g_ps_instance; +extern PPB_GetInterface g_ps_get_interface; + +PP_Instance PSGetInstanceId(void) { + return g_ps_instance; +} + +const void* PSGetInterface(const char *name) { + return g_ps_get_interface(name); +} diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps.cc b/native_client_sdk/src/libraries/ppapi_simple/ps.cc deleted file mode 100644 index 2ba183e..0000000 --- a/native_client_sdk/src/libraries/ppapi_simple/ps.cc +++ /dev/null @@ -1,55 +0,0 @@ -// 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. - -#include "ppapi/c/pp_instance.h" -#include "ppapi/c/pp_module.h" - -#include "ppapi/cpp/instance.h" -#include "ppapi/cpp/module.h" - -#include "ppapi_simple/ps.h" - -static pp::Instance* s_Instance = NULL; - -PP_Instance PSGetInstanceId(void) { - if (s_Instance == NULL) - return 0; - return s_Instance->pp_instance(); -} - -const void* PSGetInterface(const char *name) { - pp::Module* module = pp::Module::Get(); - if (module == NULL) - return NULL; - return module->GetBrowserInterface(name); -} - - -// The Module class. The browser calls the CreateInstance() method to create -// an instance of your NaCl module on the web page. The browser creates a new -// instance for each <embed> tag with type="application/x-nacl". -class PSModule : public pp::Module { - public: - PSModule() : pp::Module() {} - virtual ~PSModule() {} - - virtual pp::Instance* CreateInstance(PP_Instance instance) { - s_Instance = static_cast<pp::Instance*>(PSUserCreateInstance(instance)); - return s_Instance; - } -}; - -namespace pp { - -// Factory function called by the browser when the module is first loaded. -// The browser keeps a singleton of this module. It calls the -// CreateInstance() method on the object you return to make instances. There -// is one instance per <embed> tag on the page. This is the main binding -// point for your NaCl module with the browser. -Module* CreateModule() { - return new PSModule(); -} - -} // namespace pp - diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps.h b/native_client_sdk/src/libraries/ppapi_simple/ps.h index 1e345af..54a7d86 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps.h +++ b/native_client_sdk/src/libraries/ppapi_simple/ps.h @@ -1,4 +1,4 @@ -/* Copyright (c) 2012 The Chromium Authors. All rights reserved. +/* Copyright 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. */ @@ -53,18 +53,6 @@ PP_Instance PSGetInstanceId(void); */ const void* PSGetInterface(const char *name); -/** - * PSUserCreateInstance - * - * Prototype for the user provided function which creates and configures - * the instance object. This function is defined by one of the macros below, - * or by the equivalent macro in one of the other headers. For 'C' - * development, one of the basic instances which support C callback are used. - * For C++, this function should instantiate the user defined instance. See - * the two macros below. - */ -extern void* PSUserCreateInstance(PP_Instance inst); - EXTERN_C_END #endif /* PPAPI_SIMPLE_PS_H_ */ diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_context_2d.cc b/native_client_sdk/src/libraries/ppapi_simple/ps_context_2d.c index d422cf7..5760f02 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_context_2d.cc +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_context_2d.c @@ -1,6 +1,6 @@ -// Copyright 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. +/* Copyright 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. */ #include <stdlib.h> #include <string.h> @@ -13,7 +13,6 @@ #include "ppapi/c/ppb_image_data.h" #include "ppapi/c/ppb_instance.h" #include "ppapi/c/ppb_view.h" -#include "ppapi/cpp/image_data.h" #include "ppapi_simple/ps.h" #include "ppapi_simple/ps_context_2d.h" @@ -22,7 +21,7 @@ #include "ppapi_simple/ps_interface.h" PSContext2D_t* PSContext2DAllocate(PP_ImageDataFormat format) { - PSContext2D_t* ctx = (PSContext2D_t*) malloc(sizeof(PSContext2D_t)); + PSContext2D_t* ctx = (PSContext2D_t*)malloc(sizeof(PSContext2D_t)); memset(ctx, 0, sizeof(PSContext2D_t)); ctx->format = format; @@ -48,7 +47,7 @@ PP_ImageDataFormat PSContext2DGetNativeImageDataFormat() { // Update the 2D context if the message is appropriate, returning non-zero // if the event was consumed. int PSContext2DHandleEvent(PSContext2D_t* ctx, PSEvent* event) { - switch(event->type) { + switch (event->type) { case PSE_INSTANCE_DIDCHANGEVIEW: { struct PP_Rect rect; @@ -59,15 +58,13 @@ int PSContext2DHandleEvent(PSContext2D_t* ctx, PSEvent* event) { ctx->height = rect.size.height; // Create an opaque graphic context of the specified size. - ctx->graphic_2d = - PSInterfaceGraphics2D()->Create(PSGetInstanceId(), &rect.size, - PP_TRUE); + ctx->graphic_2d = PSInterfaceGraphics2D()->Create(PSGetInstanceId(), + &rect.size, PP_TRUE); // Bind the context to so that draws will be visible. if (ctx->graphic_2d) { - ctx->bound = - PSInterfaceInstance()->BindGraphics(PSGetInstanceId(), - ctx->graphic_2d); + ctx->bound = PSInterfaceInstance()->BindGraphics(PSGetInstanceId(), + ctx->graphic_2d); } // Typically this resource would not be allocated yet, but just in case @@ -79,35 +76,36 @@ int PSContext2DHandleEvent(PSContext2D_t* ctx, PSEvent* event) { return 1; } - default: break; + default: + break; } return 0; } - // Allocates (if needed) a new image context which will be swapped in when // drawing is complete. PSContextGetBuffer and PSContext2DSwapBuffer // implemented the suggested image/graphic_2d use specified in the // ppb_graphics_2d header. int PSContext2DGetBuffer(PSContext2D_t* ctx) { - if (!ctx->bound) return 0; + if (!ctx->bound) + return 0; // Check if we are already holding an image - if (ctx->image) return 1; + if (ctx->image) + return 1; - PP_Size size; + struct PP_Size size; size.width = ctx->width; size.height = ctx->height; // Allocate a new image resource with the specified size and format, but // do not ZERO out the buffer first since we will fill it. - PP_Resource image = - PSInterfaceImageData()->Create(PSGetInstanceId(), ctx->format, &size, - PP_FALSE); + PP_Resource image = PSInterfaceImageData()->Create( + PSGetInstanceId(), ctx->format, &size, PP_FALSE); if (0 == image) { - PSInstance::GetInstance()->Error("Unable to create 2D image.\n"); + PSInstanceError("Unable to create 2D image.\n"); return 0; } @@ -116,7 +114,7 @@ int PSContext2DGetBuffer(PSContext2D_t* ctx) { PSInterfaceImageData()->Describe(image, &desc); ctx->image = image; - ctx->data = static_cast<uint32_t*>(PSInterfaceImageData()->Map(image)); + ctx->data = (uint32_t*)(PSInterfaceImageData()->Map(image)); ctx->stride = desc.stride; return 1; } @@ -135,4 +133,3 @@ int PSContext2DSwapBuffer(PSContext2D_t* ctx) { } return 0; } - diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_entrypoints_c.c b/native_client_sdk/src/libraries/ppapi_simple/ps_entrypoints_c.c new file mode 100644 index 0000000..8eb4cbb --- /dev/null +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_entrypoints_c.c @@ -0,0 +1,32 @@ +/* Copyright 2015 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. */ + +#include <ppapi/c/pp_errors.h> +#include <ppapi/c/pp_module.h> +#include <ppapi/c/ppb.h> + +#include "ppapi_simple/ps_interface.h" + +/* Defined in ps_instance.c. */ +const void* PSGetInterfaceImplementation(const char*); + +extern PPB_GetInterface g_ps_get_interface; + +/* This is defined to allow an executable to force inclusion of this object + * file. Otherwise PPP_* functions won't be linked in (because they are not + * needed until -lppapi on the link-line, which is usually last. */ +FORCE_LINK_THIS(ps_entry) + +int32_t PPP_InitializeModule(PP_Module module, PPB_GetInterface get_interface) { + g_ps_get_interface = get_interface; + PSInterfaceInit(); + return PP_OK; +} + +const void* PPP_GetInterface(const char* interface_name) { + return PSGetInterfaceImplementation(interface_name); +} + +void PPP_ShutdownModule(void) { +} diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_event.c b/native_client_sdk/src/libraries/ppapi_simple/ps_event.c new file mode 100644 index 0000000..9d51994 --- /dev/null +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_event.c @@ -0,0 +1,271 @@ +// Copyright 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. + +#include "ppapi_simple/ps_event.h" + +#include <assert.h> +#include <pthread.h> +#include <stdlib.h> +#include <string.h> + +#include "ppapi_simple/ps_instance.h" +#include "ppapi_simple/ps_interface.h" + +#define NO_BLOCK 0 +#define BLOCK 1 + +struct PSMessageHandlerInfo { + char* message_name; + PSMessageHandler_t func; + void* user_data; + struct PSMessageHandlerInfo* prev; + struct PSMessageHandlerInfo* next; +}; + +static uint32_t s_events_enabled = PSE_NONE; +static struct PSEvent* s_event_head; +static struct PSEvent* s_event_tail; +static pthread_mutex_t s_lock = PTHREAD_MUTEX_INITIALIZER; +static pthread_cond_t s_cond = PTHREAD_COND_INITIALIZER; +static struct PSMessageHandlerInfo* s_handler_head; +static struct PSMessageHandlerInfo* s_handler_tail; + +static struct PSMessageHandlerInfo* FindMessageHandler( + const char* message_name) { + struct PSMessageHandlerInfo* info = s_handler_head; + while (info) { + if (strcmp(info->message_name, message_name) == 0) { + return info; + } + + info = info->next; + } + + return NULL; +} + +static void EnqueueEvent(struct PSEvent* event) { + pthread_mutex_lock(&s_lock); + + if (!s_event_tail) { + s_event_head = s_event_tail = event; + event->next = NULL; + } else { + s_event_tail->next = event; + s_event_tail = event; + } + + pthread_cond_signal(&s_cond); + pthread_mutex_unlock(&s_lock); +} + +static struct PSEvent* DequeueEvent(int block) { + pthread_mutex_lock(&s_lock); + + if (block) { + while (s_event_head == NULL) { + pthread_cond_wait(&s_cond, &s_lock); + } + } + + if (s_event_head == NULL) { + pthread_mutex_unlock(&s_lock); + return NULL; + } + + struct PSEvent* item = s_event_head; + + if (s_event_head == s_event_tail) { + s_event_head = s_event_tail = NULL; + } else { + s_event_head = s_event_head->next; + } + + pthread_mutex_unlock(&s_lock); + + return item; +} + +struct PSEvent* PSEventTryAcquire() { + struct PSEvent* event; + while (1) { + event = DequeueEvent(NO_BLOCK); + if (NULL == event) + break; + if (s_events_enabled & event->type) + break; + /* Release filtered events & continue to acquire. */ + PSEventRelease(event); + } + return event; +} + +struct PSEvent* PSEventWaitAcquire() { + struct PSEvent* event; + while (1) { + event = DequeueEvent(BLOCK); + if (s_events_enabled & event->type) + break; + /* Release filtered events & continue to acquire. */ + PSEventRelease(event); + } + return event; +} + +void PSEventRelease(struct PSEvent* event) { + if (event) { + switch (event->type) { + case PSE_INSTANCE_HANDLEMESSAGE: + PSInterfaceVar()->Release(event->as_var); + break; + case PSE_INSTANCE_HANDLEINPUT: + case PSE_INSTANCE_DIDCHANGEVIEW: + if (event->as_resource) { + PSInterfaceCore()->ReleaseResource(event->as_resource); + } + break; + default: + break; + } + free(event); + } +} + +void PSEventSetFilter(PSEventTypeMask filter) { + s_events_enabled = filter; + if (filter == 0) { + static int s_warn_once = 1; + if (s_warn_once) { + PSInstanceWarn( + "PSInstance::SetEnabledEvents(mask) where mask == 0 will block\n"); + PSInstanceWarn( + "all events. This can come from PSEventSetFilter(PSE_NONE);\n"); + s_warn_once = 0; + } + } +} + +void PSEventPost(PSEventType type) { + assert(PSE_GRAPHICS3D_GRAPHICS3DCONTEXTLOST == type || + PSE_MOUSELOCK_MOUSELOCKLOST == type); + + struct PSEvent* event = malloc(sizeof(struct PSEvent)); + memset(event, 0, sizeof(*event)); + event->type = type; + EnqueueEvent(event); +} + +void PSEventPostBool(PSEventType type, PP_Bool bool_value) { + assert(PSE_INSTANCE_DIDCHANGEFOCUS == type); + + struct PSEvent* event = malloc(sizeof(struct PSEvent)); + memset(event, 0, sizeof(*event)); + event->type = type; + event->as_bool = bool_value; + EnqueueEvent(event); +} + +void PSEventPostVar(PSEventType type, struct PP_Var var) { + assert(PSE_INSTANCE_HANDLEMESSAGE == type); + + /* If the message is a dictionary then see if it matches one of the specific + * handlers, then call that handler rather than queuing an event. */ + if (var.type == PP_VARTYPE_DICTIONARY) { + struct PP_Var keys_var = PSInterfaceVarDictionary()->GetKeys(var); + if (PSInterfaceVarArray()->GetLength(keys_var) == 1) { + struct PP_Var key_var = PSInterfaceVarArray()->Get(keys_var, 0); + uint32_t key_len; + const char* key_str = PSInterfaceVar()->VarToUtf8(key_var, &key_len); + char* key_cstr = alloca(key_len + 1); + memcpy(key_cstr, key_str, key_len); + key_cstr[key_len] = 0; + PSInstanceTrace("calling handler for: %s\n", key_cstr); + + struct PSMessageHandlerInfo* handler_info = FindMessageHandler(key_cstr); + if (handler_info) { + struct PP_Var value_var = PSInterfaceVarDictionary()->Get(var, key_var); + handler_info->func(key_var, value_var, handler_info->user_data); + PSInterfaceVar()->Release(value_var); + PSInterfaceVar()->Release(key_var); + PSInterfaceVar()->Release(keys_var); + return; + } + + PSInterfaceVar()->Release(key_var); + } + + PSInterfaceVar()->Release(keys_var); + } + + PSInterfaceVar()->AddRef(var); + struct PSEvent *env = malloc(sizeof(struct PSEvent)); + memset(env, 0, sizeof(*env)); + env->type = type; + env->as_var = var; + EnqueueEvent(env); +} + +void PSEventPostResource(PSEventType type, PP_Resource resource) { + assert(PSE_INSTANCE_HANDLEINPUT == type || + PSE_INSTANCE_DIDCHANGEVIEW == type); + + if (resource) { + PSInterfaceCore()->AddRefResource(resource); + } + struct PSEvent* event = malloc(sizeof(struct PSEvent)); + memset(event, 0, sizeof(*event)); + event->type = type; + event->as_resource = resource; + EnqueueEvent(event); +} + +void PSEventRegisterMessageHandler(const char* message_name, + PSMessageHandler_t func, + void* user_data) { + PSInstanceTrace("registering msg handler: %s\n", message_name); + struct PSMessageHandlerInfo* handler = FindMessageHandler(message_name); + + if (func == NULL) { + /* Unregister handler, if it exists */ + if (handler) { + if (handler->prev) { + handler->prev->next = handler->next; + } else { + s_handler_head = handler->next; + } + + if (handler->next) { + handler->next->prev = handler->prev; + } else { + s_handler_tail = handler->prev; + } + + free(handler->message_name); + free(handler); + } + return; + } + + if (handler) { + /* Already registered, change its function */ + handler->func = func; + handler->user_data = user_data; + } else { + /* Not registered, append a new handler info */ + struct PSMessageHandlerInfo* handler_info = + malloc(sizeof(struct PSMessageHandlerInfo)); + handler_info->message_name = strdup(message_name); + handler_info->func = func; + handler_info->user_data = user_data; + handler_info->next = NULL; + handler_info->prev = s_handler_tail; + + if (s_handler_tail) { + s_handler_tail->next = handler_info; + s_handler_tail = handler_info; + } else { + s_handler_head = s_handler_tail = handler_info; + } + } +} diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_event.cc b/native_client_sdk/src/libraries/ppapi_simple/ps_event.cc deleted file mode 100644 index daecb40..0000000 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_event.cc +++ /dev/null @@ -1,44 +0,0 @@ -// 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. - -#include "ppapi/c/pp_instance.h" -#include "ppapi/c/pp_module.h" - -#include "ppapi_simple/ps_event.h" -#include "ppapi_simple/ps_instance.h" -#include "ppapi_simple/ps_main.h" - - -void PSEventPost(PSEventType type) { - PSInstance::GetInstance()->PostEvent(type); -} - -void PSEventPostBool(PSEventType type, PP_Bool state) { - PSInstance::GetInstance()->PostEvent(type, state); -} - -void PSEventPostVar(PSEventType type, struct PP_Var var) { - PSInstance::GetInstance()->PostEvent(type, var); -} - -void PSEventPostResource(PSEventType type, PP_Resource resource) { - PSInstance::GetInstance()->PostEvent(type, resource); -} - -PSEvent* PSEventTryAcquire() { - return PSInstance::GetInstance()->TryAcquireEvent(); -} - -PSEvent* PSEventWaitAcquire() { - return PSInstance::GetInstance()->WaitAcquireEvent(); -} - -void PSEventRelease(PSEvent* event) { - PSInstance::GetInstance()->ReleaseEvent(event); -} - -void PSEventSetFilter(PSEventTypeMask filter) { - PSInstance::GetInstance()->SetEnabledEvents(filter); -} - diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_event.h b/native_client_sdk/src/libraries/ppapi_simple/ps_event.h index 731f053..7c2f0d4d 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_event.h +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_event.h @@ -1,4 +1,4 @@ -/* Copyright (c) 2013 The Chromium Authors. All rights reserved. +/* Copyright 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. */ @@ -61,15 +61,21 @@ typedef enum { typedef uint32_t PSEventTypeMask; // Generic Event -typedef struct { +typedef struct PSEvent { PSEventType type; union { PP_Bool as_bool; PP_Resource as_resource; struct PP_Var as_var; }; + + /* Internal */ + struct PSEvent* next; } PSEvent; +typedef void (*PSMessageHandler_t)(struct PP_Var key, + struct PP_Var value, + void* user_data); /** * Function for queuing, acquiring, and releasing events. @@ -88,6 +94,32 @@ void PSEventPostBool(PSEventType type, PP_Bool state); void PSEventPostVar(PSEventType type, struct PP_Var var); void PSEventPostResource(PSEventType type, PP_Resource resource); + +/* Register a message handler for messages that arrive from JavaScript with a + * give names. + * Messages are of the form: { message_name : <value> }. + * + * PSInstance will then not generate events but instead cause the handler to be + * called upon message arrival. If handler is NULL then the current handler + * will be removed. Example usage: + * + * JavaScript: + * nacl_module.postMessage({'foo': 123}); + * + * C: + * void MyMessageHandler(struct PP_Var key, + * struct PP_Var value, + * void* user_data) { + * assert(key.type == PP_VARTYPE_STRING); + * assert(value.type == PP_VARTYPE_INT32)); + * assert(value.value.as_int == 123); + * } + * ... + * PSInstanceRegisterMessageHandler("foo", &MyMessageHandler, NULL); */ +void PSEventRegisterMessageHandler(const char* message_name, + PSMessageHandler_t handler, + void* user_data); + EXTERN_C_END #endif /* PPAPI_SIMPLE_PS_EVENT_H_ */ diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_instance.c b/native_client_sdk/src/libraries/ppapi_simple/ps_instance.c new file mode 100644 index 0000000..bc81c27 --- /dev/null +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_instance.c @@ -0,0 +1,492 @@ +/* Copyright 2015 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. */ + +#include "ppapi_simple/ps_instance.h" + +#include <alloca.h> +#include <assert.h> +#include <ctype.h> +#include <errno.h> +#include <fcntl.h> +#include <pthread.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/ioctl.h> +#include <unistd.h> + +#include <ppapi/c/pp_errors.h> +#include <ppapi/c/pp_instance.h> +#include <ppapi/c/pp_module.h> +#include <ppapi/c/pp_rect.h> +#include <ppapi/c/pp_size.h> +#include <ppapi/c/ppb.h> +#include <ppapi/c/ppp.h> +#include <ppapi/c/ppp_graphics_3d.h> +#include <ppapi/c/ppp_input_event.h> +#include <ppapi/c/ppp_instance.h> +#include <ppapi/c/ppp_messaging.h> +#include <ppapi/c/ppp_mouse_lock.h> + +#include "nacl_io/ioctl.h" +#include "nacl_io/nacl_io.h" +#include "nacl_io/log.h" +#include "ppapi_simple/ps_interface.h" +#include "ppapi_simple/ps_main.h" + +struct StartInfo { + uint32_t argc_; + char** argv_; +}; + +PP_Instance g_ps_instance; +PPB_GetInterface g_ps_get_interface; +PSMainFunc_t g_ps_main_cb; + +static enum PSVerbosity s_verbosity; + +/* TTY handling */ +static int s_tty_fd; +static const char* s_tty_prefix; + +/* Condition variable and lock used to wait for exit confirmation from + * JavaScript. */ +static pthread_cond_t s_exit_cond; +static pthread_mutex_t s_exit_lock; + +/* A message to Post to JavaScript instead of exiting, or NULL if exit() should + * be called instead. */ +static char* s_exit_message; + +static int ProcessProperties(void); +ssize_t TtyOutputHandler(const char* buf, size_t count, void* user_data); +static void MessageHandlerExit(struct PP_Var key, + struct PP_Var value, + void* user_data); +static void MessageHandlerInput(struct PP_Var key, + struct PP_Var value, + void* user_data); +static void MessageHandlerResize(struct PP_Var key, + struct PP_Var value, + void* user_data); +static void HandleResize(int width, int height); +static void* MainThread(void* info); +static void ExitHandshake(int status, void* user_data); + +static void PostMessageString(const char* message) { + struct PP_Var message_var = + PSInterfaceVar()->VarFromUtf8(message, strlen(message)); + PSInterfaceMessaging()->PostMessage(g_ps_instance, message_var); + PSInterfaceVar()->Release(message_var); +} + +static PP_Bool Instance_DidCreate(PP_Instance instance, + uint32_t argc, + const char* argn[], + const char* argv[]) { + g_ps_instance = instance; + g_ps_main_cb = PSUserMainGet(); + s_verbosity = PSV_LOG; + PSInterfaceInputEvent()->RequestInputEvents( + g_ps_instance, PP_INPUTEVENT_CLASS_MOUSE | PP_INPUTEVENT_CLASS_KEYBOARD | + PP_INPUTEVENT_CLASS_WHEEL | PP_INPUTEVENT_CLASS_TOUCH); + + uint32_t i; + struct StartInfo* si = malloc(sizeof(struct StartInfo)); + + si->argc_ = 0; + si->argv_ = calloc(argc + 1, sizeof(char*)); + si->argv_[0] = NULL; + + /* Process embed attributes into the environment. + * Convert the attribute names to uppercase as environment variables are case + * sensitive but are almost universally uppercase in practice. */ + for (i = 0; i < argc; i++) { + char* key = strdup(argn[i]); + char* c = key; + while (*c) { + *c = toupper((int)*c); + ++c; + } + setenv(key, argv[i], 1); + free(key); + } + + /* Set a default value for SRC. */ + setenv("SRC", "NMF?", 0); + /* Use the src tag name if ARG0 is not explicitly specified. */ + setenv("ARG0", getenv("SRC"), 0); + + /* Walk ARG0..ARGn populating argv until an argument is missing. */ + for (;;) { + char arg_name[32]; + snprintf(arg_name, 32, "ARG%d", si->argc_); + const char* next_arg = getenv(arg_name); + if (NULL == next_arg) + break; + + si->argv_[si->argc_++] = strdup(next_arg); + } + + int props_processed = ProcessProperties(); + + /* Log arg values only once ProcessProperties has been called so that the + * PS_VERBOSITY attribute will be in effect. */ + for (i = 0; i < argc; i++) { + if (argv[i]) { + PSInstanceTrace("attribs[%d] '%s=%s'\n", i, argn[i], argv[i]); + } else { + PSInstanceTrace("attribs[%d] '%s'\n", i, argn[i]); + } + } + + for (i = 0; i < si->argc_; i++) { + PSInstanceTrace("argv[%d] '%s'\n", i, si->argv_[i]); + } + + if (!props_processed) { + PSInstanceWarn("Skipping create thread.\n"); + return PP_FALSE; + } + + pthread_t main_thread; + int ret = pthread_create(&main_thread, NULL, MainThread, si); + PSInstanceTrace("Created thread: %d.\n", ret); + return ret == 0 ? PP_TRUE : PP_FALSE; +} + +int ProcessProperties(void) { + /* Reset verbosity if passed in */ + const char* verbosity = getenv("PS_VERBOSITY"); + if (verbosity) + PSInstanceSetVerbosity(atoi(verbosity)); + + /* Enable NaCl IO to map STDIN, STDOUT, and STDERR */ + nacl_io_init_ppapi(PSGetInstanceId(), PSGetInterface); + + s_tty_prefix = getenv("PS_TTY_PREFIX"); + if (s_tty_prefix) { + s_tty_fd = open("/dev/tty", O_WRONLY); + if (s_tty_fd >= 0) { + PSEventRegisterMessageHandler(s_tty_prefix, MessageHandlerInput, NULL); + const char* tty_resize = getenv("PS_TTY_RESIZE"); + if (tty_resize) + PSEventRegisterMessageHandler(tty_resize, MessageHandlerResize, NULL); + + char* tty_rows = getenv("PS_TTY_ROWS"); + char* tty_cols = getenv("PS_TTY_COLS"); + if (tty_rows && tty_cols) { + char* end = tty_rows; + int rows = strtol(tty_rows, &end, 10); + if (*end != '\0' || rows < 0) { + PSInstanceError("Invalid value for PS_TTY_ROWS: %s\n", tty_rows); + } else { + end = tty_cols; + int cols = strtol(tty_cols, &end, 10); + if (*end != '\0' || cols < 0) + PSInstanceError("Invalid value for PS_TTY_COLS: %s\n", tty_cols); + else + HandleResize(cols, rows); + } + } else if (tty_rows || tty_cols) { + PSInstanceError("PS_TTY_ROWS and PS_TTY_COLS must be set together\n"); + } + + struct tioc_nacl_output handler; + handler.handler = TtyOutputHandler; + handler.user_data = NULL; + ioctl(s_tty_fd, TIOCNACLOUTPUT, &handler); + } else { + PSInstanceError("Failed to open /dev/tty.\n"); + } + } + + /* Set default values */ + setenv("PS_STDIN", "/dev/stdin", 0); + setenv("PS_STDOUT", "/dev/stdout", 0); + setenv("PS_STDERR", "/dev/console3", 0); + + int fd0 = open(getenv("PS_STDIN"), O_RDONLY); + dup2(fd0, 0); + + int fd1 = open(getenv("PS_STDOUT"), O_WRONLY); + dup2(fd1, 1); + + int fd2 = open(getenv("PS_STDERR"), O_WRONLY); + dup2(fd2, 2); + + PSEventRegisterMessageHandler("jspipe1", MessageHandlerInput, NULL); + PSEventRegisterMessageHandler("jspipe2", MessageHandlerInput, NULL); + PSEventRegisterMessageHandler("jspipe3", MessageHandlerInput, NULL); + + s_exit_message = getenv("PS_EXIT_MESSAGE"); + + /* If PS_EXIT_MESSAGE is set in the environment then we perform a handshake + * with JavaScript when program exits. */ + if (s_exit_message != NULL) + nacl_io_set_exit_callback(ExitHandshake, NULL); + + /* Set line buffering on stdout and stderr */ +#if !defined(WIN32) + setvbuf(stderr, NULL, _IOLBF, 0); + setvbuf(stdout, NULL, _IOLBF, 0); +#endif + return 1; +} + +ssize_t TtyOutputHandler(const char* data, size_t count, void* user_data) { + /* We prepend the s_tty_prefix to the data in buf, then package it up and + * post it as a message to javascript. */ + size_t tty_prefix_len = strlen(s_tty_prefix); + char* message = alloca(tty_prefix_len + count + 1); + memcpy(message, s_tty_prefix, tty_prefix_len); + memcpy(message + tty_prefix_len, data, count); + message[tty_prefix_len + count] = 0; + PostMessageString(message); + return count; +} + +void MessageHandlerExit(struct PP_Var key, + struct PP_Var value, + void* user_data) { + pthread_mutex_lock(&s_exit_lock); + pthread_cond_signal(&s_exit_cond); + pthread_mutex_unlock(&s_exit_lock); +} + +void MessageHandlerInput(struct PP_Var key, + struct PP_Var value, + void* user_data) { + uint32_t key_len; + const char* key_str = PSInterfaceVar()->VarToUtf8(key, &key_len); + + const char* filename = NULL; + if (strncmp(key_str, s_tty_prefix, key_len) == 0) { + filename = "/dev/tty"; + } else if (strncmp(key_str, "jspipe1", key_len) == 0) { + filename = "/dev/jspipe1"; + } else if (strncmp(key_str, "jspipe2", key_len) == 0) { + filename = "/dev/jspipe2"; + } else if (strncmp(key_str, "jspipe3", key_len) == 0) { + filename = "/dev/jspipe3"; + } else { + PSInstanceError("unexpected input key: %s", key_str); + return; + } + + int fd = open(filename, O_RDONLY); + if (fd < 0) { + PSInstanceError("error opening file: %s (%s)", filename, strerror(errno)); + return; + } + + int ret = ioctl(fd, NACL_IOC_HANDLEMESSAGE, &value); + if (ret != 0) { + PSInstanceError("ioctl on %s failed: %d.\n", filename, ret); + close(fd); + return; + } + + close(fd); +} + +void MessageHandlerResize(struct PP_Var key, + struct PP_Var value, + void* user_data) { + assert(value.type == PP_VARTYPE_ARRAY); + assert(PSInterfaceVarArray()->GetLength(value) == 2); + + struct PP_Var width_var = PSInterfaceVarArray()->Get(value, 0); + struct PP_Var height_var = PSInterfaceVarArray()->Get(value, 1); + + assert(width_var.type == PP_VARTYPE_INT32); + assert(height_var.type == PP_VARTYPE_INT32); + + int width = width_var.value.as_int; + int height = height_var.value.as_int; + + HandleResize(width, height); +} + +void HandleResize(int width, int height) { + struct winsize size; + memset(&size, 0, sizeof(size)); + size.ws_col = width; + size.ws_row = height; + ioctl(s_tty_fd, TIOCSWINSZ, &size); +} + +void* MainThread(void* info) { + int ret; + uint32_t i; + PSInstanceTrace("Running MainThread.\n"); + struct StartInfo* si = (struct StartInfo*)info; + + PP_Resource message_loop = PSInterfaceMessageLoop()->Create(g_ps_instance); + if (PSInterfaceMessageLoop()->AttachToCurrentThread(message_loop) != PP_OK) { + PSInstanceError("Unable to attach message loop to thread.\n"); + return NULL; + } + + if (!g_ps_main_cb) { + PSInstanceError("No main defined.\n"); + return 0; + } + + PSInstanceTrace("Starting MAIN.\n"); + ret = g_ps_main_cb(si->argc_, si->argv_); + PSInstanceLog("Main thread returned with %d.\n", ret); + + /* Clean up StartInfo. */ + for (i = 0; i < si->argc_; i++) { + free(si->argv_[i]); + } + free(si->argv_); + free(si); + + /* Exit the entire process once the 'main' thread returns. The error code + * will be available to javascript via the exitcode parameter of the crash + * event. */ +#ifdef __native_client__ + exit(ret); +#else + ExitHandshake(ret, NULL); +#endif + return NULL; +} + +void ExitHandshake(int status, void* user_data) { + if (s_exit_message == NULL) + return; + + PSEventRegisterMessageHandler(s_exit_message, MessageHandlerExit, NULL); + + /* exit message + ':' + num + \0 */ + size_t message_len = strlen(s_exit_message) + 1 + 11 + 1; + char* message = alloca(message_len); + snprintf(message, message_len, "%s:%d", s_exit_message, status); + + pthread_mutex_lock(&s_exit_lock); + PostMessageString(message); + pthread_cond_wait(&s_exit_cond, &s_exit_lock); + pthread_mutex_unlock(&s_exit_lock); +} + +static void Instance_DidDestroy(PP_Instance instance) { +} + +static void Instance_DidChangeView(PP_Instance instance, PP_Resource view) { + struct PP_Rect rect; + if (PSInterfaceView()->GetRect(view, &rect)) { + PSInstanceLog("Got View change: %d,%d\n", rect.size.width, + rect.size.height); + PSEventPostResource(PSE_INSTANCE_DIDCHANGEVIEW, view); + } +} + +static void Instance_DidChangeFocus(PP_Instance instance, PP_Bool has_focus) { + PSInstanceLog("Got Focus change: %s\n", has_focus ? "FOCUS ON" : "FOCUS OFF"); + PSEventPostBool(PSE_INSTANCE_DIDCHANGEFOCUS, has_focus ? PP_TRUE : PP_FALSE); +} + +static PP_Bool Instance_HandleDocumentLoad(PP_Instance instance, + PP_Resource url_loader) { + return PP_FALSE; +} + +static void Messaging_HandleMessage(PP_Instance instance, + struct PP_Var message) { + PSInstanceTrace("Got Message\n"); + PSEventPostVar(PSE_INSTANCE_HANDLEMESSAGE, message); +} + +static PP_Bool InputEvent_HandleInputEvent(PP_Instance instance, + PP_Resource input_event) { + PSEventPostResource(PSE_INSTANCE_HANDLEINPUT, input_event); + return PP_TRUE; +} + +static void MouseLock_MouseLockLost(PP_Instance instance) { + PSInstanceLog("MouseLockLost\n"); + PSEventPost(PSE_MOUSELOCK_MOUSELOCKLOST); +} + +static void Graphics3D_Graphics3DContextLost(PP_Instance instance) { + PSInstanceLog("Graphics3DContextLost\n"); + PSEventPost(PSE_GRAPHICS3D_GRAPHICS3DCONTEXTLOST); +} + +void PSInstanceSetVerbosity(enum PSVerbosity verbosity) { + s_verbosity = verbosity; +} + +static void VALog(enum PSVerbosity verbosity, const char* fmt, va_list args) { + if (verbosity <= s_verbosity) { + fprintf(stderr, "ps: "); + vfprintf(stderr, fmt, args); + } +} + +void PSInstanceTrace(const char* fmt, ...) { + va_list ap; + va_start(ap, fmt); + VALog(PSV_TRACE, fmt, ap); + va_end(ap); +} + +void PSInstanceLog(const char* fmt, ...) { + va_list ap; + va_start(ap, fmt); + VALog(PSV_LOG, fmt, ap); + va_end(ap); +} + +void PSInstanceWarn(const char* fmt, ...) { + va_list ap; + va_start(ap, fmt); + VALog(PSV_WARN, fmt, ap); + va_end(ap); +} + +void PSInstanceError(const char* fmt, ...) { + va_list ap; + va_start(ap, fmt); + VALog(PSV_ERROR, fmt, ap); + va_end(ap); +} + +const void* PSGetInterfaceImplementation(const char* interface_name) { + if (strcmp(interface_name, PPP_INSTANCE_INTERFACE_1_1) == 0) { + static struct PPP_Instance_1_1 interface = { + &Instance_DidCreate, + &Instance_DidDestroy, + &Instance_DidChangeView, + &Instance_DidChangeFocus, + &Instance_HandleDocumentLoad, + }; + return &interface; + } else if (strcmp(interface_name, PPP_MESSAGING_INTERFACE_1_0) == 0) { + static struct PPP_Messaging_1_0 interface = { + &Messaging_HandleMessage, + }; + return &interface; + } else if (strcmp(interface_name, PPP_INPUT_EVENT_INTERFACE_0_1) == 0) { + static struct PPP_InputEvent_0_1 interface = { + &InputEvent_HandleInputEvent, + }; + return &interface; + } else if (strcmp(interface_name, PPP_MOUSELOCK_INTERFACE_1_0) == 0) { + static struct PPP_MouseLock_1_0 interface = { + &MouseLock_MouseLockLost, + }; + return &interface; + } else if (strcmp(interface_name, PPP_GRAPHICS_3D_INTERFACE_1_0) == 0) { + static struct PPP_Graphics3D_1_0 interface = { + &Graphics3D_Graphics3DContextLost, + }; + return &interface; + } + + return NULL; +} diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_instance.cc b/native_client_sdk/src/libraries/ppapi_simple/ps_instance.cc deleted file mode 100644 index 63b8530..0000000 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_instance.cc +++ /dev/null @@ -1,612 +0,0 @@ -// 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. - -#include <errno.h> -#include <fcntl.h> -#include <pthread.h> -#include <stdio.h> -#include <stdlib.h> -#include <sys/ioctl.h> -#include <sys/types.h> -#include <sys/stat.h> -#include <termios.h> - -#include <algorithm> -#include <cstdlib> -#include <cstring> -#include <sstream> -#include <string> -#include <vector> - -#include "nacl_io/ioctl.h" -#include "nacl_io/kernel_wrap.h" -#include "nacl_io/log.h" -#include "nacl_io/nacl_io.h" - -#include "ppapi/c/ppb_var.h" - -#include "ppapi/cpp/input_event.h" -#include "ppapi/cpp/message_loop.h" -#include "ppapi/cpp/module.h" -#include "ppapi/cpp/rect.h" -#include "ppapi/cpp/size.h" -#include "ppapi/cpp/touch_point.h" -#include "ppapi/cpp/var.h" -#include "ppapi/cpp/var_array.h" -#include "ppapi/cpp/var_dictionary.h" - -#include "ppapi_simple/ps_event.h" -#include "ppapi_simple/ps_instance.h" -#include "ppapi_simple/ps_interface.h" -#include "ppapi_simple/ps_main.h" - -#if defined(WIN32) -#define open _open -#define dup2 _dup2 -#endif - -static PSInstance* s_InstanceObject = NULL; - -PSInstance* PSInstance::GetInstance() { - return s_InstanceObject; -} - -struct StartInfo { - PSInstance* inst_; - uint32_t argc_; - char** argv_; -}; - - -// The starting point for 'main'. We create this thread to hide the real -// main pepper thread which must never be blocked. -void* PSInstance::MainThreadThunk(void *info) { - s_InstanceObject->Trace("Got MainThreadThunk.\n"); - StartInfo* si = static_cast<StartInfo*>(info); - PSInstance* instance = si->inst_; - instance->main_loop_ = new pp::MessageLoop(si->inst_); - instance->main_loop_->AttachToCurrentThread(); - - int ret = instance->MainThread(si->argc_, si->argv_); - - // Clean up StartInfo. - for (uint32_t i = 0; i < si->argc_; i++) { - delete[] si->argv_[i]; - } - delete[] si->argv_; - delete si; - - // Exit the entire process once the 'main' thread returns. - // The error code will be available to javascript via - // the exitcode parameter of the crash event. -#ifdef __native_client__ - exit(ret); -#else - instance->ExitHandshake(ret); -#endif - return NULL; -} - -void PSInstance::ExitHandshake(int status) { - if (exit_message_ == NULL) - return; - - RegisterMessageHandler(exit_message_, MessageHandlerExitStatic, this); - - // Send the exit message to JavaScript. Then wait - // for the reply/confirmation. - std::stringstream ss; - ss << exit_message_ << ":" << status; - - pthread_mutex_lock(&exit_lock_); - PostMessage(ss.str()); - pthread_cond_wait(&exit_cond_, &exit_lock_); - pthread_mutex_unlock(&exit_lock_); -} - -// The default implementation supports running a 'C' main. -int PSInstance::MainThread(int argc, char* argv[]) { - if (!main_cb_) { - Error("No main defined.\n"); - return 0; - } - - Trace("Starting MAIN.\n"); - int ret = main_cb_(argc, argv); - Log("Main thread returned with %d.\n", ret); - - return ret; -} - -PSInstance::PSInstance(PP_Instance instance) - : pp::Instance(instance), - pp::MouseLock(this), - pp::Graphics3DClient(this), - main_loop_(NULL), - events_enabled_(PSE_NONE), - verbosity_(PSV_WARN), - tty_fd_(-1), - tty_prefix_(NULL), - exit_message_(NULL) { - - pthread_mutex_init(&exit_lock_, NULL); - pthread_cond_init(&exit_cond_, NULL); - - // Set the single Instance object - s_InstanceObject = this; - -#ifdef NACL_SDK_DEBUG - SetVerbosity(PSV_LOG); -#endif - - RequestInputEvents(PP_INPUTEVENT_CLASS_MOUSE | - PP_INPUTEVENT_CLASS_KEYBOARD | - PP_INPUTEVENT_CLASS_WHEEL | - PP_INPUTEVENT_CLASS_TOUCH); -} - -PSInstance::~PSInstance() { - s_InstanceObject = NULL; -} - -void PSInstance::SetMain(PSMainFunc_t main) { - main_cb_ = main; -} - -bool PSInstance::Init(uint32_t arg, - const char* argn[], - const char* argv[]) { - StartInfo* si = new StartInfo; - - si->inst_ = this; - si->argc_ = 0; - si->argv_ = new char *[arg+1]; - si->argv_[0] = NULL; - - // Process embed attributes into the environment. - // Converted the attribute names to uppercase as environment variables are - // case sensitive but are almost universally uppercase in practice. - for (uint32_t i = 0; i < arg; i++) { - std::string key = argn[i]; - std::transform(key.begin(), key.end(), key.begin(), toupper); - setenv(key.c_str(), argv[i], 1); - } - - // Set a default value for SRC. - setenv("SRC", "NMF?", 0); - // Use the src tag name if ARG0 is not explicitly specified. - setenv("ARG0", getenv("SRC"), 0); - - // Walk ARG0..ARGn populating argv until an argument is missing. - for (;;) { - std::ostringstream arg_stream; - arg_stream << "ARG" << si->argc_; - std::string arg_name = arg_stream.str(); - const char* next_arg = getenv(arg_name.c_str()); - if (NULL == next_arg) - break; - - char* value = new char[strlen(next_arg) + 1]; - strcpy(value, next_arg); - si->argv_[si->argc_++] = value; - } - - PSInterfaceInit(); - bool props_processed = ProcessProperties(); - - // Log arg values only once ProcessProperties has been - // called so that the ps_verbosity attribute will be in - // effect. - for (uint32_t i = 0; i < arg; i++) { - if (argv[i]) { - Trace("attribs[%d] '%s=%s'\n", i, argn[i], argv[i]); - } else { - Trace("attribs[%d] '%s'\n", i, argn[i]); - } - } - - for (uint32_t i = 0; i < si->argc_; i++) { - Trace("argv[%d] '%s'\n", i, si->argv_[i]); - } - - if (!props_processed) { - Warn("Skipping create thread.\n"); - return false; - } - - pthread_t main_thread; - int ret = pthread_create(&main_thread, NULL, MainThreadThunk, si); - Trace("Created thread: %d.\n", ret); - return ret == 0; -} - -// Processes the properties set at compile time via the -// initialization macro, or via dynamically set embed attributes -// through instance DidCreate. -bool PSInstance::ProcessProperties() { - // Reset verbosity if passed in - const char* verbosity = getenv("PS_VERBOSITY"); - if (verbosity) SetVerbosity(static_cast<Verbosity>(atoi(verbosity))); - - // Enable NaCl IO to map STDIN, STDOUT, and STDERR - nacl_io_init_ppapi(PSGetInstanceId(), PSGetInterface); - - tty_prefix_ = getenv("PS_TTY_PREFIX"); - if (tty_prefix_) { - tty_fd_ = open("/dev/tty", O_WRONLY); - if (tty_fd_ >= 0) { - RegisterMessageHandler(tty_prefix_, MessageHandlerInputStatic, this); - const char* tty_resize = getenv("PS_TTY_RESIZE"); - if (tty_resize) - RegisterMessageHandler(tty_resize, MessageHandlerResizeStatic, this); - - char* tty_rows = getenv("PS_TTY_ROWS"); - char* tty_cols = getenv("PS_TTY_COLS"); - if (tty_rows && tty_cols) { - char* end = tty_rows; - int rows = strtol(tty_rows, &end, 10); - if (*end != '\0' || rows < 0) { - Error("Invalid value for PS_TTY_ROWS: %s\n", tty_rows); - } else { - end = tty_cols; - int cols = strtol(tty_cols, &end, 10); - if (*end != '\0' || cols < 0) - Error("Invalid value for PS_TTY_COLS: %s\n", tty_cols); - else - HandleResize(cols, rows); - } - } - else if (tty_rows || tty_cols) { - Error("PS_TTY_ROWS and PS_TTY_COLS must be set together\n"); - } - - tioc_nacl_output handler; - handler.handler = TtyOutputHandlerStatic; - handler.user_data = this; - ioctl(tty_fd_, TIOCNACLOUTPUT, &handler); - } else { - Error("Failed to open /dev/tty.\n"); - } - } - - // Set default values - setenv("PS_STDIN", "/dev/stdin", 0); - setenv("PS_STDOUT", "/dev/stdout", 0); - setenv("PS_STDERR", "/dev/console3", 0); - - int fd0 = open(getenv("PS_STDIN"), O_RDONLY); - dup2(fd0, 0); - - int fd1 = open(getenv("PS_STDOUT"), O_WRONLY); - dup2(fd1, 1); - - int fd2 = open(getenv("PS_STDERR"), O_WRONLY); - dup2(fd2, 2); - - RegisterMessageHandler("jspipe1", MessageHandlerInputStatic, this); - RegisterMessageHandler("jspipe2", MessageHandlerInputStatic, this); - RegisterMessageHandler("jspipe3", MessageHandlerInputStatic, this); - - exit_message_ = getenv("PS_EXIT_MESSAGE"); - - // If PS_EXIT_MESSAGE is set in the environment then we perform a handshake - // with JavaScript when program exits. - if (exit_message_ != NULL) - nacl_io_set_exit_callback(HandleExitStatic, this); - - // Set line buffering on stdout and stderr -#if !defined(WIN32) - setvbuf(stderr, NULL, _IOLBF, 0); - setvbuf(stdout, NULL, _IOLBF, 0); -#endif - return true; -} - -void PSInstance::SetVerbosity(Verbosity verbosity) { - verbosity_ = verbosity; -} - -void PSInstance::VALog(Verbosity verbosity, const char *fmt, va_list args) { - if (verbosity <= verbosity_) { - fprintf(stderr, "ps: "); - vfprintf(stderr, fmt, args); - } -} - -void PSInstance::Trace(const char *fmt, ...) { - va_list ap; - va_start(ap, fmt); - VALog(PSV_TRACE, fmt, ap); - va_end(ap); -} - -void PSInstance::Log(const char *fmt, ...) { - va_list ap; - va_start(ap, fmt); - VALog(PSV_LOG, fmt, ap); - va_end(ap); -} - -void PSInstance::Warn(const char *fmt, ...) { - va_list ap; - va_start(ap, fmt); - VALog(PSV_WARN, fmt, ap); - va_end(ap); -} - -void PSInstance::Error(const char *fmt, ...) { - va_list ap; - va_start(ap, fmt); - VALog(PSV_ERROR, fmt, ap); - va_end(ap); -} - -void PSInstance::SetEnabledEvents(uint32_t mask) { - events_enabled_ = mask; - if (mask == 0) { - static bool warn_once = true; - if (warn_once) { - Warn("PSInstance::SetEnabledEvents(mask) where mask == 0 will block\n"); - Warn("all events. This can come from PSEventSetFilter(PSE_NONE);\n"); - warn_once = false; - } - } -} - -void PSInstance::PostEvent(PSEventType type) { - assert(PSE_GRAPHICS3D_GRAPHICS3DCONTEXTLOST == type || - PSE_MOUSELOCK_MOUSELOCKLOST == type); - - PSEvent *env = (PSEvent *) malloc(sizeof(PSEvent)); - memset(env, 0, sizeof(*env)); - env->type = type; - event_queue_.Enqueue(env); -} - -void PSInstance::PostEvent(PSEventType type, PP_Bool bool_value) { - assert(PSE_INSTANCE_DIDCHANGEFOCUS == type); - - PSEvent *env = (PSEvent *) malloc(sizeof(PSEvent)); - memset(env, 0, sizeof(*env)); - env->type = type; - env->as_bool = bool_value; - event_queue_.Enqueue(env); -} - -void PSInstance::PostEvent(PSEventType type, PP_Resource resource) { - assert(PSE_INSTANCE_HANDLEINPUT == type || - PSE_INSTANCE_DIDCHANGEVIEW == type); - - if (resource) { - PSInterfaceCore()->AddRefResource(resource); - } - PSEvent *env = (PSEvent *) malloc(sizeof(PSEvent)); - memset(env, 0, sizeof(*env)); - env->type = type; - env->as_resource = resource; - event_queue_.Enqueue(env); -} - -ssize_t PSInstance::TtyOutputHandler(const char* buf, size_t count) { - // We prepend the prefix_ to the data in buf, then package it up - // and post it as a message to javascript. - const char* data = static_cast<const char*>(buf); - std::string message = tty_prefix_; - message.append(data, count); - PostMessage(pp::Var(message)); - return count; -} - -void PSInstance::MessageHandlerExit(const pp::Var& message) { - assert(message.is_string()); - pthread_mutex_lock(&exit_lock_); - pthread_cond_signal(&exit_cond_); - pthread_mutex_unlock(&exit_lock_); -} - -void PSInstance::MessageHandlerInput(const pp::Var& key, - const pp::Var& message) { - std::string key_string = key.AsString(); - - const char* filename = NULL; - if (key_string == tty_prefix_) { - filename = "/dev/tty"; - } else if (key_string == "jspipe1") { - filename = "/dev/jspipe1"; - } else if (key_string == "jspipe2") { - filename = "/dev/jspipe2"; - } else if (key_string == "jspipe3") { - filename = "/dev/jspipe3"; - } else { - Error("unexpected input key: %s", key_string.c_str()); - return; - } - - int fd = open(filename, O_RDONLY); - if (fd < 0) { - Error("error opening file: %s (%s)", filename, strerror(errno)); - return; - } - - int ret = ioctl(fd, NACL_IOC_HANDLEMESSAGE, &message.pp_var()); - if (ret != 0) { - Error("ioctl on %s failed: %d.\n", filename, ret); - close(fd); - return; - } - - close(fd); -} - -void PSInstance::HandleExitStatic(int status, void* user_data) { - PSInstance* instance = static_cast<PSInstance*>(user_data); - instance->ExitHandshake(status); -} - -void PSInstance::HandleResize(int width, int height) { - struct winsize size; - memset(&size, 0, sizeof(size)); - size.ws_col = width; - size.ws_row = height; - ioctl(tty_fd_, TIOCSWINSZ, &size); -} - -void PSInstance::MessageHandlerResize(const pp::Var& message) { - assert(message.is_array()); - pp::VarArray array(message); - assert(array.GetLength() == 2); - - int width = array.Get(0).AsInt(); - int height = array.Get(1).AsInt(); - HandleResize(width, height); -} - -ssize_t PSInstance::TtyOutputHandlerStatic(const char* buf, - size_t count, - void* user_data) { - PSInstance* instance = static_cast<PSInstance*>(user_data); - return instance->TtyOutputHandler(buf, count); -} - -void PSInstance::MessageHandlerExitStatic(const pp::Var& key, - const pp::Var& value, - void* user_data) { - PSInstance* instance = static_cast<PSInstance*>(user_data); - instance->MessageHandlerExit(value); -} - -void PSInstance::MessageHandlerInputStatic(const pp::Var& key, - const pp::Var& value, - void* user_data) { - PSInstance* instance = static_cast<PSInstance*>(user_data); - instance->MessageHandlerInput(key, value); -} - -void PSInstance::MessageHandlerResizeStatic(const pp::Var& key, - const pp::Var& value, - void* user_data) { - PSInstance* instance = static_cast<PSInstance*>(user_data); - instance->MessageHandlerResize(value); -} - -void PSInstance::RegisterMessageHandler(std::string message_name, - MessageHandler_t handler, - void* user_data) { - Trace("registering msg handler: %s\n", message_name.c_str()); - if (handler == NULL) { - message_handlers_.erase(message_name); - return; - } - - MessageHandler message_handler = { handler, user_data }; - message_handlers_[message_name] = message_handler; -} - -void PSInstance::PostEvent(PSEventType type, const PP_Var& var) { - assert(PSE_INSTANCE_HANDLEMESSAGE == type); - - pp::Var event(var); - - // If the message is a dictionary then see if it matches one - // of the specific handlers, then call that handler rather than - // queuing an event. - if (event.is_dictionary()) { - pp::VarDictionary dictionary(var); - pp::VarArray keys = dictionary.GetKeys(); - if (keys.GetLength() == 1) { - pp::Var key = keys.Get(0); - Trace("calling handler for: %s\n", key.AsString().c_str()); - MessageHandlerMap::iterator iter = message_handlers_.find(key.AsString()); - if (iter != message_handlers_.end()) { - MessageHandler_t handler = iter->second.handler; - void* user_data = iter->second.user_data; - handler(key, dictionary.Get(key), user_data); - return; - } - } - } - - PSInterfaceVar()->AddRef(var); - PSEvent *env = (PSEvent *) malloc(sizeof(PSEvent)); - memset(env, 0, sizeof(*env)); - env->type = type; - env->as_var = var; - event_queue_.Enqueue(env); -} - -PSEvent* PSInstance::TryAcquireEvent() { - PSEvent* event; - while(true) { - event = event_queue_.Dequeue(false); - if (NULL == event) - break; - if (events_enabled_ & event->type) - break; - // Release filtered events & continue to acquire. - ReleaseEvent(event); - } - return event; -} - -PSEvent* PSInstance::WaitAcquireEvent() { - PSEvent* event; - while(true) { - event = event_queue_.Dequeue(true); - if (events_enabled_ & event->type) - break; - // Release filtered events & continue to acquire. - ReleaseEvent(event); - } - return event; -} - -void PSInstance::ReleaseEvent(PSEvent* event) { - if (event) { - switch(event->type) { - case PSE_INSTANCE_HANDLEMESSAGE: - PSInterfaceVar()->Release(event->as_var); - break; - case PSE_INSTANCE_HANDLEINPUT: - case PSE_INSTANCE_DIDCHANGEVIEW: - if (event->as_resource) { - PSInterfaceCore()->ReleaseResource(event->as_resource); - } - break; - default: - break; - } - free(event); - } -} - -void PSInstance::HandleMessage(const pp::Var& message) { - Trace("Got Message\n"); - PostEvent(PSE_INSTANCE_HANDLEMESSAGE, message.pp_var()); -} - -bool PSInstance::HandleInputEvent(const pp::InputEvent& event) { - PostEvent(PSE_INSTANCE_HANDLEINPUT, event.pp_resource()); - return true; -} - -void PSInstance::DidChangeView(const pp::View& view) { - pp::Size new_size = view.GetRect().size(); - Log("Got View change: %d,%d\n", new_size.width(), new_size.height()); - PostEvent(PSE_INSTANCE_DIDCHANGEVIEW, view.pp_resource()); -} - -void PSInstance::DidChangeFocus(bool focus) { - Log("Got Focus change: %s\n", focus ? "FOCUS ON" : "FOCUS OFF"); - PostEvent(PSE_INSTANCE_DIDCHANGEFOCUS, focus ? PP_TRUE : PP_FALSE); -} - -void PSInstance::Graphics3DContextLost() { - Log("Graphics3DContextLost\n"); - PostEvent(PSE_GRAPHICS3D_GRAPHICS3DCONTEXTLOST); -} - -void PSInstance::MouseLockLost() { - Log("MouseLockLost\n"); - PostEvent(PSE_MOUSELOCK_MOUSELOCKLOST); -} diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_instance.h b/native_client_sdk/src/libraries/ppapi_simple/ps_instance.h index 21209d1..0def929 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_instance.h +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_instance.h @@ -1,6 +1,6 @@ -// 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. +/* Copyright 2015 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. */ #ifndef PPAPI_SIMPLE_PS_INSTANCE_H_ #define PPAPI_SIMPLE_PS_INSTANCE_H_ @@ -9,209 +9,26 @@ #include "ppapi/c/pp_instance.h" #include "ppapi/c/pp_stdint.h" -#include "ppapi/c/ppb_core.h" #include "ppapi/c/ppb_var.h" -#include "ppapi/c/ppb_view.h" - -#include "ppapi/cpp/fullscreen.h" -#include "ppapi/cpp/graphics_3d_client.h" -#include "ppapi/cpp/instance.h" -#include "ppapi/cpp/message_loop.h" -#include "ppapi/cpp/mouse_lock.h" - -#include "ppapi/utility/completion_callback_factory.h" #include "ppapi_simple/ps_event.h" -#include "ppapi_simple/ps_main.h" - -#include "sdk_util/thread_safe_queue.h" -typedef void (*MessageHandler_t)(const pp::Var& key, - const pp::Var& value, - void* user_data); +EXTERN_C_BEGIN -struct MessageHandler { - MessageHandler_t handler; - void* user_data; +enum PSVerbosity { + PSV_SILENT = 0, + PSV_ERROR = 1, + PSV_WARN = 2, + PSV_LOG = 3, + PSV_TRACE = 4, }; -// The basic instance class which also inherits the MouseLock and -// Graphics3DClient interfaces. -class PSInstance : public pp::Instance, pp::MouseLock, pp::Graphics3DClient { - public: - // Verbosity levels, ecplicitly numbered since we pass these - // in from html attributes as numberic values. - enum Verbosity { - PSV_SILENT = 0, - PSV_ERROR = 1, - PSV_WARN = 2, - PSV_LOG = 3, - PSV_TRACE = 4, - }; - - // Returns a pointer to the global instance - static PSInstance* GetInstance(); - - PSInstance(PP_Instance inst); - virtual ~PSInstance(); - - // Set a function which will be called on a new thread once initialized. - // NOTE: This must be called by the Factory, once Init is called, this - // function will have no effect. - void SetMain(PSMainFunc_t func); - - // Started on Init, a thread which can be safely blocked. - virtual int MainThread(int argc, char* argv[]); - - // Logging Functions - void SetVerbosity(Verbosity verbosity); - void Trace(const char *fmt, ...); - void Log(const char *fmt, ...); - void Warn(const char *fmt, ...); - void Error(const char *fmt, ...); - - // Event Functions - void SetEnabledEvents(uint32_t mask); - void PostEvent(PSEventType type); - void PostEvent(PSEventType type, PP_Bool bool_value); - void PostEvent(PSEventType type, PP_Resource resource); - void PostEvent(PSEventType type, const PP_Var& var); - - PSEvent* TryAcquireEvent(); - PSEvent* WaitAcquireEvent(); - void ReleaseEvent(PSEvent* event); - - // Register a message handler for messages that arrive - // from JavaScript with a give names. Messages are of the - // form: { message_name : <value> }. - // - // PSInstance will then not generate events but instead - // cause the handler to be called upon message arrival. - // If handler is NULL then the current handler will be - // removed. Example usage: - // - // JavaScript: - // nacl_module.postMessage({'foo': 123}); - // - // C++: - // void MyMessageHandler(const pp::Var& key, - // const pp::Var& value, - // void* user_data) { - // assert(key.is_string()); - // assert(key.AsString() == "foo"); - // assert(value.is_int()); - // assert(value.AsInt() == 123); - // } - // ... - // instance_->RegisterMessageHandler("foo", &MyMessageHandler, NULL); - // - void RegisterMessageHandler(std::string message_name, - MessageHandler_t handler, - void* user_data); - - // Perform exit handshake with JavaScript. - // This is called by _exit before the process is terminated to ensure - // that all messages sent prior to _exit arrive at the JavaScript side. - void ExitHandshake(int status); - - protected: - typedef std::map<std::string, MessageHandler> MessageHandlerMap; - - // Callback functions triggered by Pepper - // - // These functions are called on the main pepper thread, so they must - // not block. - // - // Called by the browser when the NaCl module is loaded and all ready to go. - // This function will create a new thread which will run the pseudo main. - virtual bool Init(uint32_t argc, const char* argn[], const char* argv[]); - - // Output log message to stderr if the current verbosity is set - // at or above the given verbosity. - void VALog(Verbosity verbosity, const char *fmt, va_list args); - - // Called whenever the in-browser window changes size, it will pass a - // context change request to whichever thread is handling rendering. - virtual void DidChangeView(const pp::View& view); - - // Called by the browser when the NaCl canvas gets or loses focus. - virtual void DidChangeFocus(bool has_focus); - - // Called by the browser to handle the postMessage() call in Javascript. - virtual void HandleMessage(const pp::Var& message); +void PSInstanceSetVerbosity(enum PSVerbosity verbosity); +void PSInstanceTrace(const char *fmt, ...); +void PSInstanceLog(const char *fmt, ...); +void PSInstanceWarn(const char *fmt, ...); +void PSInstanceError(const char *fmt, ...); - // Called by the browser to handle incoming input events. Events are Q'd - // and can later be processed on a sperate processing thread. - virtual bool HandleInputEvent(const pp::InputEvent& event); - - // Called by the browser when the 3D context is lost. - virtual void Graphics3DContextLost(); - - // Called by the browser when the mouselock is lost. - virtual void MouseLockLost(); - - // Called by Init to processes default and embed tag arguments prior to - // launching the 'ppapi_main' thread. - virtual bool ProcessProperties(); - - private: - static void* MainThreadThunk(void *start_info); - ssize_t TtyOutputHandler(const char* buf, size_t count); - void MessageHandlerExit(const pp::Var& message); - void MessageHandlerInput(const pp::Var& key, const pp::Var& message); - void MessageHandlerResize(const pp::Var& message); - void HandleResize(int width, int height); - - static void HandleExitStatic(int status, void* user_data); - - static ssize_t TtyOutputHandlerStatic(const char* buf, size_t count, - void* user_data); - - /// Handle exit confirmation message from JavaScript. - static void MessageHandlerExitStatic(const pp::Var& key, - const pp::Var& message, - void* user_data); - - /// Handle input message from JavaScript. The value is - /// expected to be of type string. - static void MessageHandlerInputStatic(const pp::Var& key, - const pp::Var& message, - void* user_data); - - - /// Handle resizs message from JavaScript. The value is - /// expected to be an array of 2 integers representing the - /// number of columns and rows in the TTY. - static void MessageHandlerResizeStatic(const pp::Var& key, - const pp::Var& message, - void* user_data); - - protected: - pp::MessageLoop* main_loop_; - - sdk_util::ThreadSafeQueue<PSEvent> event_queue_; - uint32_t events_enabled_; - Verbosity verbosity_; - - // TTY handling - int tty_fd_; - const char* tty_prefix_; - MessageHandlerMap message_handlers_; - - PSMainFunc_t main_cb_; - - const PPB_Core* ppb_core_; - const PPB_Var* ppb_var_; - const PPB_View* ppb_view_; - - // Condition variable and lock used to wait for exit confirmation from - // JavaScript. - pthread_cond_t exit_cond_; - pthread_mutex_t exit_lock_; - - // A message to Post to JavaScript instead of exiting, or NULL if exit() - // should be called instead. - char* exit_message_; -}; +EXTERN_C_END -#endif // PPAPI_SIMPLE_PS_INSTANCE_H_ +#endif /* PPAPI_SIMPLE_PS_INSTANCE_H_ */ diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_interface.cc b/native_client_sdk/src/libraries/ppapi_simple/ps_interface.c index 43988e2..ee02557 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_interface.cc +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_interface.c @@ -1,12 +1,12 @@ -// Copyright 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. +/* Copyright 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. */ #include "ppapi_simple/ps.h" #include "ppapi_simple/ps_interface.h" -#define DEFINE_INTERFACE_FUNC(Name) \ - static const PPB_##Name* s_##Name; \ +#define DEFINE_INTERFACE_FUNC(Name) \ + static const PPB_##Name* s_##Name; \ const PPB_##Name* PSInterface##Name() { return s_##Name; } DEFINE_INTERFACE_FUNC(Audio) @@ -22,6 +22,7 @@ DEFINE_INTERFACE_FUNC(Graphics2D) DEFINE_INTERFACE_FUNC(Graphics3D) DEFINE_INTERFACE_FUNC(ImageData) DEFINE_INTERFACE_FUNC(Instance) +DEFINE_INTERFACE_FUNC(InputEvent) DEFINE_INTERFACE_FUNC(Messaging) DEFINE_INTERFACE_FUNC(MessageLoop) DEFINE_INTERFACE_FUNC(MouseCursor) @@ -29,13 +30,14 @@ DEFINE_INTERFACE_FUNC(URLLoader) DEFINE_INTERFACE_FUNC(URLRequestInfo) DEFINE_INTERFACE_FUNC(URLResponseInfo) DEFINE_INTERFACE_FUNC(Var) +DEFINE_INTERFACE_FUNC(VarArray) DEFINE_INTERFACE_FUNC(VarArrayBuffer) +DEFINE_INTERFACE_FUNC(VarDictionary) DEFINE_INTERFACE_FUNC(View) DEFINE_INTERFACE_FUNC(WebSocket) - -#define REQUEST_INTERFACE(x, y) \ - s_##x = static_cast<const PPB_##x*>(PSGetInterface(PPB_ ## y ##_INTERFACE)); +#define REQUEST_INTERFACE(x, y) \ + s_##x = (const PPB_##x*)(PSGetInterface(PPB_##y##_INTERFACE)); void PSInterfaceInit() { REQUEST_INTERFACE(Audio, AUDIO) @@ -51,6 +53,7 @@ void PSInterfaceInit() { REQUEST_INTERFACE(Graphics3D, GRAPHICS_3D) REQUEST_INTERFACE(ImageData, IMAGEDATA) REQUEST_INTERFACE(Instance, INSTANCE) + REQUEST_INTERFACE(InputEvent, INPUT_EVENT) REQUEST_INTERFACE(Messaging, MESSAGING) REQUEST_INTERFACE(MessageLoop, MESSAGELOOP) REQUEST_INTERFACE(MouseCursor, MOUSECURSOR) @@ -58,7 +61,9 @@ void PSInterfaceInit() { REQUEST_INTERFACE(URLRequestInfo, URLREQUESTINFO) REQUEST_INTERFACE(URLResponseInfo, URLRESPONSEINFO) REQUEST_INTERFACE(Var, VAR) + REQUEST_INTERFACE(VarArray, VAR_ARRAY) REQUEST_INTERFACE(VarArrayBuffer, VAR_ARRAY_BUFFER) + REQUEST_INTERFACE(VarDictionary, VAR_DICTIONARY) REQUEST_INTERFACE(View, VIEW) REQUEST_INTERFACE(WebSocket, WEBSOCKET) } diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_interface.h b/native_client_sdk/src/libraries/ppapi_simple/ps_interface.h index ad818f0..53ba836 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_interface.h +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_interface.h @@ -22,6 +22,7 @@ #include "ppapi/c/ppb_graphics_2d.h" #include "ppapi/c/ppb_graphics_3d.h" #include "ppapi/c/ppb_image_data.h" +#include "ppapi/c/ppb_input_event.h" #include "ppapi/c/ppb_instance.h" #include "ppapi/c/ppb_message_loop.h" #include "ppapi/c/ppb_messaging.h" @@ -31,7 +32,9 @@ #include "ppapi/c/ppb_url_request_info.h" #include "ppapi/c/ppb_url_response_info.h" #include "ppapi/c/ppb_var.h" +#include "ppapi/c/ppb_var_array.h" #include "ppapi/c/ppb_var_array_buffer.h" +#include "ppapi/c/ppb_var_dictionary.h" #include "ppapi/c/ppb_view.h" #include "ppapi/c/ppb_websocket.h" @@ -51,6 +54,7 @@ const PPB_Gamepad* PSInterfaceGamepad(); const PPB_Graphics2D* PSInterfaceGraphics2D(); const PPB_Graphics3D* PSInterfaceGraphics3D(); const PPB_ImageData* PSInterfaceImageData(); +const PPB_InputEvent* PSInterfaceInputEvent(); const PPB_Instance* PSInterfaceInstance(); const PPB_Messaging* PSInterfaceMessaging(); const PPB_MessageLoop* PSInterfaceMessageLoop(); @@ -59,7 +63,9 @@ const PPB_URLLoader* PSInterfaceURLLoader(); const PPB_URLRequestInfo* PSInterfaceURLRequestInfo(); const PPB_URLResponseInfo* PSInterfaceURLResponseInfo(); const PPB_Var* PSInterfaceVar(); +const PPB_VarArray* PSInterfaceVarArray(); const PPB_VarArrayBuffer* PSInterfaceVarArrayBuffer(); +const PPB_VarDictionary* PSInterfaceVarDictionary(); const PPB_View* PSInterfaceView(); const PPB_WebSocket* PSInterfaceWebSocket(); diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_main.cc b/native_client_sdk/src/libraries/ppapi_simple/ps_main.c index f9b8147..fd3602a 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_main.cc +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_main.c @@ -1,6 +1,8 @@ -// 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. +/* Copyright 2015 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. */ + +#include "ppapi_simple/ps_main.h" #ifdef __native_client__ #include <irt.h> @@ -10,18 +12,11 @@ #include <stdio.h> #include "nacl_io/nacl_io.h" -#include "ppapi/c/pp_instance.h" -#include "ppapi/c/pp_module.h" #include "ppapi_simple/ps_instance.h" -#include "ppapi_simple/ps_main.h" -extern "C" int PpapiPluginMain(); +FORCE_LINK_THIS(ps_main) -void* PSMainCreate(PP_Instance inst, PSMainFunc_t entry_point) { - PSInstance* pInst = new PSInstance(inst); - pInst->SetMain(entry_point); - return pInst; -} +int PpapiPluginMain(); /** * main entry point for ppapi_simple applications. This differs from the @@ -31,7 +26,7 @@ void* PSMainCreate(PP_Instance inst, PSMainFunc_t entry_point) { * and also under sel_ldr (no PPAPI). */ #ifdef __native_client__ -extern "C" int __nacl_main(int argc, char* argv[]) { +int __nacl_main(int argc, char* argv[]) { struct nacl_irt_ppapihook hooks; if (nacl_interface_query(NACL_IRT_PPAPIHOOK_v0_1, &hooks, sizeof(hooks)) == sizeof(hooks)) { diff --git a/native_client_sdk/src/libraries/ppapi_simple/ps_main.h b/native_client_sdk/src/libraries/ppapi_simple/ps_main.h index 2b42ac4..2ffcccd 100644 --- a/native_client_sdk/src/libraries/ppapi_simple/ps_main.h +++ b/native_client_sdk/src/libraries/ppapi_simple/ps_main.h @@ -1,4 +1,4 @@ -/* Copyright (c) 2012 The Chromium Authors. All rights reserved. +/* Copyright 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. */ @@ -13,14 +13,6 @@ EXTERN_C_BEGIN typedef int (*PSMainFunc_t)(int argc, char *argv[]); /** - * PSMainCreate - * - * Constructs an instance SimpleInstance and configures it to call into - * the provided "main" function. - */ -void* PSMainCreate(PP_Instance inst, PSMainFunc_t entry_point); - -/** * PSUserMainGet * * Prototype for the user provided function which retrieves the user's main @@ -34,14 +26,16 @@ PSMainFunc_t PSUserMainGet(); * * Constructs a PSInstance object and configures it to use call the provided * 'main' function on its own thread once initialization is complete. + * + * The ps_entrypoint_*.o and ps_main.o objects will not be linked by default, + * so we force them to be linked here. */ -#define PPAPI_SIMPLE_REGISTER_MAIN(main_func) \ - PSMainFunc_t PSUserMainGet() { \ - return main_func; \ - } \ - void* PSUserCreateInstance(PP_Instance inst) { \ - return PSMainCreate(inst, main_func); \ - } +#define PPAPI_SIMPLE_REGISTER_MAIN(main_func) \ + EXTERN_C_BEGIN \ + FORCE_LINK_THAT(ps_entry) \ + FORCE_LINK_THAT(ps_main) \ + EXTERN_C_END \ + PSMainFunc_t PSUserMainGet() { return main_func; } EXTERN_C_END diff --git a/native_client_sdk/src/libraries/ppapi_simple_cpp/library.dsc b/native_client_sdk/src/libraries/ppapi_simple_cpp/library.dsc new file mode 100644 index 0000000..196e700 --- /dev/null +++ b/native_client_sdk/src/libraries/ppapi_simple_cpp/library.dsc @@ -0,0 +1,24 @@ +{ + 'TOOLS': ['bionic', 'newlib', 'glibc', 'pnacl', 'linux', 'mac', 'clang-newlib'], + 'SEARCH': [ + '.', + '../ppapi_simple' + ], + 'TARGETS': [ + { + 'NAME' : 'ppapi_simple_cpp', + 'TYPE' : 'lib', + 'SOURCES' : [ + "ps.c", + "ps_context_2d.c", + "ps_event.c", + "ps_instance.c", + "ps_interface.c", + "ps_main.c", + "ps_entrypoints_cpp.cc" + ], + }, + ], + 'DEST': 'src', + 'NAME': 'ppapi_simple_cpp', +} diff --git a/native_client_sdk/src/libraries/ppapi_simple_cpp/ps_entrypoints_cpp.cc b/native_client_sdk/src/libraries/ppapi_simple_cpp/ps_entrypoints_cpp.cc new file mode 100644 index 0000000..3552b2d --- /dev/null +++ b/native_client_sdk/src/libraries/ppapi_simple_cpp/ps_entrypoints_cpp.cc @@ -0,0 +1,77 @@ +// Copyright 2015 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. + +#include <ppapi/c/pp_errors.h> +#include <ppapi/c/pp_module.h> +#include <ppapi/c/ppb.h> +#include <ppapi/c/ppp.h> +#include <ppapi/cpp/instance.h> +#include <ppapi/cpp/module.h> + +#include "ppapi_simple/ps_interface.h" + +class PSModule : public pp::Module { + public: + virtual pp::Instance* CreateInstance(PP_Instance instance) { + // Should not get here. + // This is only called by libppapi_cpp in Instance_DidCreate. That function + // is called by the PPP_Instance handler in libppapi_cpp, but we handle all + // plugin interfaces in ppapi_simple. + assert(0); + return NULL; + } +}; + +static PSModule* s_module; + +namespace pp { + +Module* Module::Get() { + return s_module; +} + +// This shouldn't be called (it is only referenced by PPP_InitialzeModule in +// ppapi_cpp, which we override), but is needed to successfully link. +Module* CreateModule() { + assert(0); + return NULL; +} + +} // namespace pp + +extern "C" { + +// Defined in ps_instance.c. +const void* PSGetInterfaceImplementation(const char*); +extern PPB_GetInterface g_ps_get_interface; + +// This is defined to allow an executable to force inclusion of this object +// file. Otherwise PPP_* functions won't be linked in (because they are not +// needed until -lppapi on the link-line, which is usually last. +FORCE_LINK_THIS(ps_entry) + +} // extern "C" + +int32_t PPP_InitializeModule(PP_Module module_id, + PPB_GetInterface get_interface) { + g_ps_get_interface = get_interface; + PSInterfaceInit(); + + PSModule* module = new PSModule(); + if (!module->InternalInit(module_id, get_interface)) { + delete s_module; + return PP_ERROR_FAILED; + } + s_module = module; + return PP_OK; +} + +const void* PPP_GetInterface(const char* interface_name) { + return PSGetInterfaceImplementation(interface_name); +} + +void PPP_ShutdownModule(void) { + delete s_module; + s_module = NULL; +} diff --git a/native_client_sdk/src/tests/nacl_io_socket_test/example.dsc b/native_client_sdk/src/tests/nacl_io_socket_test/example.dsc index 3afd3a6..8af5d73 100644 --- a/native_client_sdk/src/tests/nacl_io_socket_test/example.dsc +++ b/native_client_sdk/src/tests/nacl_io_socket_test/example.dsc @@ -13,7 +13,7 @@ 'DEPS': ['ppapi_simple', 'nacl_io'], # Order matters here: gtest has a "main" function that will be used if # referenced before ppapi. - 'LIBS': ['ppapi_simple', 'gmock', 'ppapi', 'gtest', 'nacl_io', 'ppapi_cpp', 'pthread'], + 'LIBS': ['ppapi_simple_cpp', 'ppapi_cpp', 'gmock', 'ppapi', 'gtest', 'nacl_io', 'pthread'], 'CXXFLAGS': ['-Wno-sign-compare'] } ], diff --git a/native_client_sdk/src/tests/nacl_io_test/example.dsc b/native_client_sdk/src/tests/nacl_io_test/example.dsc index f0a66924..d204111 100644 --- a/native_client_sdk/src/tests/nacl_io_test/example.dsc +++ b/native_client_sdk/src/tests/nacl_io_test/example.dsc @@ -64,7 +64,7 @@ 'DEPS': ['ppapi_simple', 'nacl_io'], # Order matters here: gtest has a "main" function that will be used if # referenced before ppapi. - 'LIBS': ['ppapi_simple', 'gmock', 'nacl_io', 'ppapi', 'gtest', 'ppapi_cpp', 'pthread'], + 'LIBS': ['ppapi_simple_cpp', 'ppapi_cpp', 'gmock', 'nacl_io', 'ppapi', 'gtest', 'pthread'], 'INCLUDES': ["."], 'CXXFLAGS': ['-Wno-sign-compare'], } diff --git a/native_client_sdk/src/tests/sdk_util_test/example.dsc b/native_client_sdk/src/tests/sdk_util_test/example.dsc index a9c09bb..6f22d3a 100644 --- a/native_client_sdk/src/tests/sdk_util_test/example.dsc +++ b/native_client_sdk/src/tests/sdk_util_test/example.dsc @@ -13,7 +13,7 @@ 'DEPS': ['ppapi_simple', 'sdk_util', 'nacl_io'], # Order matters here: gtest has a "main" function that will be used if # referenced before ppapi. - 'LIBS': ['ppapi_simple', 'sdk_util', 'ppapi', 'gtest', 'nacl_io', 'gmock', 'ppapi_cpp', 'pthread'], + 'LIBS': ['ppapi_simple_cpp', 'ppapi_cpp', 'gmock', 'nacl_io', 'ppapi', 'gtest', 'pthread'], 'CXXFLAGS': ['-Wno-sign-compare'] } ], |