diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 73c82cd..5b3dccf 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -6,7 +6,7 @@ jobs: build: runs-on: ubuntu-22.04 env: - SDK_VERSION: 3.1.46.bi + SDK_VERSION: 3.1.46.1bi SYS_PYTHON: /usr/bin/python3 PACKAGES: emsdk hpy pygame BUILD_STATIC: emsdk hpy diff --git a/packages.d/pygame/pygame.sh b/packages.d/pygame/pygame.sh index a9427ac..e63533f 100755 --- a/packages.d/pygame/pygame.sh +++ b/packages.d/pygame/pygame.sh @@ -201,6 +201,10 @@ TAG=${PYMAJOR}${PYMINOR} echo "FIXME: build wheel" +SDL2="-sUSE_ZLIB=1 -sUSE_BZIP2=1 -sUSE_LIBPNG -sUSE_SDL=2 -sUSE_SDL_MIXER=2 -lSDL2 -L/opt/python-wasm-sdk/devices/emsdk/usr/lib -lSDL2_image -lSDL2_gfx -lSDL2_mixer -lSDL2_mixer_ogg -lSDL2_ttf -lvorbis -logg -lwebp -ljpeg -lpng -lharfbuzz -lfreetype" +SDL2="$SDL2 -lssl -lcrypto -lffi -lbz2 -lz -ldl -lm" + + if [ -d testing/pygame_static-1.0-cp${TAG}-cp${TAG}-wasm32_mvp_emscripten ] then TARGET_FOLDER=$(pwd)/testing/pygame_static-1.0-cp${TAG}-cp${TAG}-wasm32_${WASM_FLAVOUR}_emscripten @@ -210,7 +214,7 @@ then [ -f ${TARGET_FILE} ] && rm ${TARGET_FILE} ${TARGET_FILE}.map - emcc -shared -Os -g0 -fpic -o ${TARGET_FILE} $SDKROOT/prebuilt/emsdk/libpygame${PYMAJOR}.${PYMINOR}.a + emcc -shared -Os -g0 -fpic -o ${TARGET_FILE} $SDKROOT/prebuilt/emsdk/libpygame${PYMAJOR}.${PYMINOR}.a $SDL2 # github CI does not build wheel for now. if [ -d /data/git/archives/repo/pkg ] diff --git a/pygbag/support/cross/aio/pep0723.py b/pygbag/support/cross/aio/pep0723.py index 2c826f2..754f582 100644 --- a/pygbag/support/cross/aio/pep0723.py +++ b/pygbag/support/cross/aio/pep0723.py @@ -1,6 +1,8 @@ # https://peps.python.org/pep-0722/ – Dependency specification for single-file scripts # https://peps.python.org/pep-0508/ – Dependency specification for Python Software Packages +# https://setuptools.pypa.io/en/latest/userguide/ext_modules.html + import sys import os from pathlib import Path @@ -172,6 +174,37 @@ async def install_pkg(sysconf, wheel_url, wheel_pkg): install(target_filename, sysconf) +async def pip_install(pkg, sconf={}): + print("searching", pkg) + if not sconf: + sconf = __import__("sysconfig").get_paths() + + wheel_url = "" + try: + async with fopen(f"https://pypi.org/simple/{pkg}/") as html: + if html: + for line in html.readlines(): + if line.find("href=") > 0: + if line.find("-py3-none-any.whl") > 0: + wheel_url = line.split('"', 2)[1] + else: + print("270: ERROR: cannot find package :", pkg) + except FileNotFoundError: + print("190: ERROR: cannot find package :", pkg) + continue + + except: + print("194: ERROR: cannot find package :", pkg) + return + + try: + wheel_pkg, wheel_hash = wheel_url.rsplit("/", 1)[-1].split("#", 1) + await install_pkg(sconf, wheel_url, wheel_pkg) + except: + print("ERROR", wheel_url) + + + async def check_list(code=None, filename=None): print() print("-" * 11, "computing required packages", "-" * 10) @@ -258,31 +291,7 @@ async def check_list(code=None, filename=None): if (env / pkg).is_dir(): print("found in env :", pkg) continue - print("searching", pkg) - wheel_url = "" - try: - async with fopen(f"https://pypi.org/simple/{pkg}/") as html: - if html: - for line in html.readlines(): - if line.find("href=") > 0: - if line.find("-py3-none-any.whl") > 0: - wheel_url = line.split('"', 2)[1] - else: - print("270: ERROR: cannot find package :", pkg) - except FileNotFoundError: - print("272: ERROR: cannot find package :", pkg) - continue - - except: - print("277: ERROR: cannot find package :", pkg) - continue - - try: - wheel_pkg, wheel_hash = wheel_url.rsplit("/", 1)[-1].split("#", 1) - await install_pkg(sconf, wheel_url, wheel_pkg) - except: - print("ERROR", wheel_url) - continue + await pip_install(pkg) print("-" * 40) print() diff --git a/pygbag/support/cross/aio/toplevel.py b/pygbag/support/cross/aio/toplevel.py index 2904d47..5a5a818 100644 --- a/pygbag/support/cross/aio/toplevel.py +++ b/pygbag/support/cross/aio/toplevel.py @@ -65,7 +65,6 @@ async def get_repo_pkg(pkg_file, pkg, resume, ex): # sconf["platlib"] = os.environ.get("HOME","/tmp") platlib = sconf["platlib"] Path(platlib).mkdir(exist_ok=True) - # print(f"{platlib=}") if platlib not in sys.path: sys.path.append(platlib) @@ -91,7 +90,7 @@ async def get_repo_pkg(pkg_file, pkg, resume, ex): print(f"84: {pkg_file} already installed") if pkg in platform.patches: - print("88:", pkg, "requires patch") + print("88:", pkg, "requires patching") platform.patches.pop(pkg)() if resume and ex: @@ -105,8 +104,6 @@ async def get_repo_pkg(pkg_file, pkg, resume, ex): return asyncio.sleep(0) except Exception as resume_ex: sys.print_exception(ex, limit=-1) - # finally: - # print("-"*40) return None diff --git a/pygbag/support/pythonrc.py b/pygbag/support/pythonrc.py index 124520c..ea04337 100644 --- a/pygbag/support/pythonrc.py +++ b/pygbag/support/pythonrc.py @@ -1384,7 +1384,12 @@ async def async_repos(cls): apitag = apitag.replace('-','_') for repo in PyConfig.pkg_indexes: - async with platform.fopen(f"{repo}index-bi.json", "r") as index: + if apitag.find('mvp')>0: + idx = f"{repo}index.json" + else: + idx = f"{repo}index-bi.json" + + async with platform.fopen(idx, "r") as index: try: data = index.read() if isinstance(data, bytes): diff --git a/scripts/build-loader.sh b/scripts/build-loader.sh index fdcb06c..9a70e9e 100755 --- a/scripts/build-loader.sh +++ b/scripts/build-loader.sh @@ -54,14 +54,6 @@ echo " EMPIC=/opt/python-wasm-sdk/emsdk/upstream/emscripten/cache/sysroot/lib/wasm32-emscripten/pic -CF_SDL="-I${SDKROOT}/devices/emsdk/usr/include/SDL2" -#LD_SDL2="-lSDL2_gfx -lSDL2_mixer -lSDL2_ttf" - -LD_SDL2="$EMPIC/libSDL2.a" -LD_SDL2="$LD_SDL2 $EMPIC/libSDL2_gfx.a $EMPIC/libogg.a $EMPIC/libvorbis.a" -LD_SDL2="$LD_SDL2 $EMPIC/libSDL2_mixer_ogg.a $EMPIC/libSDL2_ttf.a" -LD_SDL2="-L${SDKROOT}/devices/emsdk/usr/lib $LD_SDL2 -lSDL2_image -lwebp -ljpeg -lpng -lharfbuzz -lfreetype" - SUPPORT_FS="" @@ -233,11 +225,24 @@ then # TODO: test -sWEBGL2_BACKWARDS_COMPATIBILITY_EMULATION -# -# -sWEBGL2_BACKWARDS_COMPATIBILITY_EMULATION - LDFLAGS="$LD_VENDOR -sUSE_GLFW=3 -sUSE_WEBGL2 -sMIN_WEBGL_VERSION=2 -sOFFSCREENCANVAS_SUPPORT=1 -sFULL_ES2 -sFULL_ES3" -# LDFLAGS="$LD_VENDOR -sUSE_GLFW=3 -sUSE_WEBGL2 -sMIN_WEBGL_VERSION=2 -sMAX_WEBGL_VERSION=2 -sFULL_ES2" + + +# /opt/python-wasm-sdk/emsdk/upstream/emscripten/cache/sysroot/lib/wasm32-emscripten/pic/libSDL2.a + + CF_SDL="-I${SDKROOT}/devices/emsdk/usr/include/SDL2" + #LD_SDL2="-lSDL2_gfx -lSDL2_mixer -lSDL2_ttf" + + LD_SDL2="$EMPIC/libSDL2.a" + LD_SDL2="$LD_SDL2 $EMPIC/libSDL2_gfx.a $EMPIC/libogg.a $EMPIC/libvorbis.a" + LD_SDL2="$LD_SDL2 $EMPIC/libSDL2_mixer_ogg.a $EMPIC/libSDL2_ttf.a" + LD_SDL2="$LD_SDL2 -lSDL2_image -lwebp -ljpeg -lpng -lharfbuzz -lfreetype" + + + #LDFLAGS="$LD_VENDOR -sUSE_GLFW=3 -sUSE_WEBGL2 -sMIN_WEBGL_VERSION=2 -sOFFSCREENCANVAS_SUPPORT=1 -sFULL_ES2 -sFULL_ES3" + LDFLAGS="$LD_SDL2" +LDFLAGS="" + if echo ${PYBUILD}|grep -q 10$ then @@ -246,8 +251,9 @@ then LDFLAGS="$LDFLAGS -lsqlite3" fi -# LDFLAGS="$LDFLAGS $LD_SDL2 -lffi -lbz2 -lz -ldl -lm" - LDFLAGS="$LDFLAGS $LD_SDL2 -lssl -lcrypto -lffi -lbz2 -lz -ldl -lm" + + + LDFLAGS="-L${SDKROOT}/devices/emsdk/usr/lib $LDFLAGS -lssl -lcrypto -lffi -lbz2 -lz -ldl -lm" LINKPYTHON="python mpdec expat" diff --git a/scripts/vendoring.sh b/scripts/vendoring.sh index f9fca54..d3c992e 100755 --- a/scripts/vendoring.sh +++ b/scripts/vendoring.sh @@ -5,8 +5,8 @@ export VENDOR=${VENDOR:-pygbag} export PACKAGES=${PACKAGES:-emsdk hpy pygame} export SDKROOT=${SDKROOT:-/opt/python-wasm-sdk} -export SDK_VERSION=${SDK_VERSION:-3.1.22.0} -export CYTHON=${CYTHON:-Cython-3.0.0-py2.py3-none-any.whl} +export SDK_VERSION=${SDK_VERSION:-3.1.46.1bi} +export CYTHON=${CYTHON:-Cython-3.0.1-py2.py3-none-any.whl} export PYBUILD=${PYBUILD:-3.11} export LC_ALL=C diff --git a/static/pythons.js b/static/pythons.js index ca1616f..b7a82d7 100644 --- a/static/pythons.js +++ b/static/pythons.js @@ -270,7 +270,7 @@ function prerun(VM) { if (window.BrowserFS) { - vm.BFS = new BrowserFS.EmscriptenFS() + VM.BFS = new BrowserFS.EmscriptenFS() VM.BFS.Buffer = BrowserFS.BFSRequire('buffer').Buffer } else { console.error("VM.prefun","BrowserFS not found") @@ -1085,49 +1085,123 @@ window.MM = { tracks : 0, UME : true, download : download, camera : {} } async function media_prepare(trackid) { const track = MM[trackid] + await _until(defined)("avail", track) if (track.type === "audio") { //console.log(`audio ${trackid}:${track.url} ready`) + return } if (track.type === "fs") { console.log(`fs ${trackid}:${track.url} => ${track.path} ready`) + return } + if (track.type === "mount") { + + if (!vm.BFS) { + // how is passed the FS object ??? + vm.BFS = new BrowserFS.EmscriptenFS() // {FS:vm.FS} + + vm.BFS.Buffer = BrowserFS.BFSRequire('buffer').Buffer + } + // async - MM[trackid].media = vm.BFS.Buffer.from( MM[trackid].data ) + MM[trackid].media = await vm.BFS.Buffer.from( MM[trackid].data ) track.mount.path = track.mount.path || '/' //??= const hint = `${track.mount.path}@${track.mount.point}:${trackid}` - function apk_cb(e, apkfs){ - console.log(__FILE__, "930 mounting", hint, "onto", track.mount.point) - - BrowserFS.FileSystem.InMemory.Create( - function(e, memfs) { - BrowserFS.FileSystem.OverlayFS.Create({"writable" : memfs, "readable" : apkfs }, - function(e, ovfs) { - BrowserFS.FileSystem.MountableFileSystem.Create({ - '/' : ovfs - }, async function(e, mfs) { - await BrowserFS.initialize(mfs); - await vm.FS.mount(vm.BFS, {root: track.mount.path}, track.mount.point ); - setTimeout(()=>{track.ready=true}, 0) - }) - } - ); - } - ); + var track_media + + if (!vm) { + vm={} + + // how is passed the FS object ??? + vm.BFS = new BrowserFS.EmscriptenFS() // {FS:vm.FS} + + vm.BFS.Buffer = BrowserFS.BFSRequire('buffer').Buffer + const data = await (await fetch('test.apk')).arrayBuffer() + track_media = await vm.BFS.Buffer.from(data) + } else { + track_media = MM[trackid].media } - await BrowserFS.FileSystem.ZipFS.Create( - {"zipData" : track.media, "name": hint}, - apk_cb - ) - } + var bfs2 = false + if (!BrowserFS.InMemory) { + console.warn(" ==================== BFS1 ===============") + BrowserFS.InMemory = BrowserFS.FileSystem.InMemory + BrowserFS.OverlayFS = BrowserFS.FileSystem.OverlayFS + BrowserFS.MountableFileSystem = BrowserFS.FileSystem.MountableFileSystem + BrowserFS.ZipFS = BrowserFS.FileSystem.ZipFS + } else { + console.warn(" ==================== BFS2 ===============") + bfs2 = true + } + + if (bfs2) { + const zipfs = await BrowserFS.ZipFS.Create({ + zipData: track_media, + "name": hint + }) + await BrowserFS.initialize( zipfs ) + + + const memfs = await BrowserFS.InMemory.Create(); + await BrowserFS.initialize( memfs) + + + const ovfs = await BrowserFS.OverlayFS.Create({ + writable : memfs, + readable: zipfs + }) + + await BrowserFS.initialize( ovfs) + + // this alone does not work ? why ?? + // const mfs = await BrowserFS.MountableFileSystem.Create({"/" : ovfs}) + // console.log( mfs ) + + const mfs = await BrowserFS.initialize( await BrowserFS.MountableFileSystem.Create({"/" : ovfs}) ) + + // where is the link beetween (BFSEmscriptenFS)vm.BFS and MountableFileSystem(mfs) ? + // vm.BFS.mount( ???????? ) + + const emfs = await vm.FS.mount(vm.BFS, {root: "/"}, "/data/data/test" ); + + setTimeout(()=>{track.ready=true}, 0) + + } else { + function apk_cb(e, apkfs){ + console.log(__FILE__, "930 mounting", hint, "onto", track.mount.point) + + BrowserFS.InMemory.Create( + function(e, memfs) { + BrowserFS.OverlayFS.Create({"writable" : memfs, "readable" : apkfs }, + function(e, ovfs) { + BrowserFS.MountableFileSystem.Create({ + '/' : ovfs + }, async function(e, mfs) { + await BrowserFS.initialize(mfs); + await vm.FS.mount(vm.BFS, {root: track.mount.path}, track.mount.point); + setTimeout(()=>{track.ready=true}, 0) + }) + } + ); + } + ); + } + + //await BrowserFS.FileSystem.ZipFS.Create( + await BrowserFS.ZipFS.Create( + {"zipData" : track_media, "name": hint}, + apk_cb + ) + } // bfs2 + } // track type mount } diff --git a/support/__EMSCRIPTEN__.c b/support/__EMSCRIPTEN__.c index 8fe234a..ac0bf82 100644 --- a/support/__EMSCRIPTEN__.c +++ b/support/__EMSCRIPTEN__.c @@ -55,8 +55,11 @@ self hosting: #include #include #include "emscripten.h" + /* + #define SDL2 #include #include + */ // #include // SDL_HINT_EMSCRIPTEN_KEYBOARD_ELEMENT #define SDL_HINT_EMSCRIPTEN_KEYBOARD_ELEMENT "SDL_EMSCRIPTEN_KEYBOARD_ELEMENT" @@ -295,7 +298,7 @@ embed_isatty(PyObject *self, PyObject *argv) { return Py_BuildValue("i", isatty(fd) ); } - +#if SDL2 static PyObject * embed_get_sdl_version(PyObject *self, PyObject *_null) { @@ -304,7 +307,7 @@ embed_get_sdl_version(PyObject *self, PyObject *_null) SDL_GetVersion(&v); return Py_BuildValue("iii", v.major, v.minor, v.patch); } - +#endif static PyMethodDef mod_embed_methods[] = { {"run", (PyCFunction)embed_run, METH_VARARGS | METH_KEYWORDS, "start aio stepping"}, @@ -333,9 +336,9 @@ static PyMethodDef mod_embed_methods[] = { {"prompt", (PyCFunction)embed_prompt, METH_NOARGS, "output the prompt"}, {"isatty", (PyCFunction)embed_isatty, METH_VARARGS, "isatty(int fd)"}, - +#if SDL2 {"get_sdl_version", embed_get_sdl_version, METH_NOARGS, "get_sdl_version"}, - +#endif {"test", (PyCFunction)embed_test, METH_VARARGS | METH_KEYWORDS, "test"}, {"webgl", (PyCFunction)embed_webgl, METH_VARARGS | METH_KEYWORDS, "test"}, @@ -868,7 +871,7 @@ EM_ASM({ PyRun_SimpleString("import sys, os, json, builtins, shutil, time"); //PyRun_SimpleString("import universal;print('HPy init done')"); - +#if SDL2 // SDL2 basic init { if (TTF_Init()) @@ -877,7 +880,7 @@ EM_ASM({ const char *target = "1"; SDL_SetHint(SDL_HINT_EMSCRIPTEN_KEYBOARD_ELEMENT, target); } - +#endif emscripten_set_main_loop( (em_callback_func)main_iteration, 0, 1); return 0;