about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/custommem.c2
-rwxr-xr-xsrc/elfs/elfloader.c2
-rwxr-xr-xsrc/emu/x64int3.c4
-rwxr-xr-xsrc/emu/x64syscall.c9
-rwxr-xr-xsrc/librarian/library.c2
-rwxr-xr-xsrc/library_list.h1
-rwxr-xr-xsrc/main.c17
-rw-r--r--src/steam.c93
-rw-r--r--src/wrapped/generated/functions_list.txt1
-rw-r--r--src/wrapped/generated/wrapper.c2
-rw-r--r--src/wrapped/generated/wrapper.h1
-rwxr-xr-xsrc/wrapped/wrappedlibrt_private.h2
12 files changed, 126 insertions, 10 deletions
diff --git a/src/custommem.c b/src/custommem.c
index c11e1557..b2b5d6a5 100644
--- a/src/custommem.c
+++ b/src/custommem.c
@@ -892,7 +892,7 @@ void addMapMem(uintptr_t begin, uintptr_t end)
         newm->end = end;
         m->next = newm;
     }
-    while(newm->next && (newm->next->begin-1)<=newm->end) {
+    while(newm && newm->next && (newm->next->begin-1)<=newm->end) {
         // fuse with next
         if(newm->next->end>newm->end)
             newm->end = newm->next->end;
diff --git a/src/elfs/elfloader.c b/src/elfs/elfloader.c
index fd869ddf..105a271b 100755
--- a/src/elfs/elfloader.c
+++ b/src/elfs/elfloader.c
@@ -1137,6 +1137,8 @@ int ElfCheckIfUseTCMallocMinimal(elfheader_t* h)
             char *needed = h->DynStrTab+h->delta+h->Dynamic[i].d_un.d_val;
             if(!strcmp(needed, "libtcmalloc_minimal.so.4")) // tcmalloc needs to be the 1st lib loaded
                 return 1;
+            else if(!strcmp(needed, "libtcmalloc_minimal.so.0")) // tcmalloc needs to be the 1st lib loaded
+                return 1;
             else
                 return 0;
         }
diff --git a/src/emu/x64int3.c b/src/emu/x64int3.c
index 2db1e6f7..c382734e 100755
--- a/src/emu/x64int3.c
+++ b/src/emu/x64int3.c
@@ -101,6 +101,10 @@ void x64Int3(x64emu_t* emu)
                     tmp = (char*)(R_RDI);
                     snprintf(buff, 255, "%04d|%p: Calling %s(\"%s\", %d (,%d))", tid, *(void**)(R_RSP), s, (tmp)?tmp:"(nil)", (int)(R_ESI), (int)(R_EDX));
                     perr = 1;
+                } else if (!strcmp(s, "shm_open")) {
+                    tmp = (char*)(R_RDI);
+                    snprintf(buff, 255, "%04d|%p: Calling %s(\"%s\", %d, %d)", tid, *(void**)(R_RSP), s, (tmp)?tmp:"(nil)", (int)(R_ESI), (int)(R_EDX));
+                    perr = 1;
                 } else if (!strcmp(s, "fopen") || !strcmp(s, "fopen64")) {
                     tmp = (char*)(R_RDI);
                     snprintf(buff, 255, "%04d|%p: Calling %s(\"%s\", \"%s\")", tid, *(void**)(R_RSP), s, (tmp)?tmp:"(nil)", (char*)(R_RSI));
diff --git a/src/emu/x64syscall.c b/src/emu/x64syscall.c
index d83cbaba..c9fa59dc 100755
--- a/src/emu/x64syscall.c
+++ b/src/emu/x64syscall.c
@@ -177,6 +177,9 @@ scwrap_t syscallwrap[] = {
     #ifdef __NR_fchmodat4
     { 434, __NR_fchmodat4, 4},
     #endif
+    #ifdef __NR_futex_waitv
+    { 449, __NR_futex_waitv, 5},
+    #endif
 };
 
 struct mmap_arg_struct {
@@ -483,6 +486,7 @@ void EXPORT x64Syscall(x64emu_t *emu)
 
 uintptr_t EXPORT my_syscall(x64emu_t *emu)
 {
+    static uint32_t warned = 0;
     uint32_t s = R_EDI;
     printf_dump(LOG_DEBUG, "%p: Calling libc syscall 0x%02X (%d) %p %p %p %p %p\n", (void*)R_RIP, s, s, (void*)R_RSI, (void*)R_RDX, (void*)R_RCX, (void*)R_R8, (void*)R_R9); 
     // check wrapper first
@@ -643,7 +647,10 @@ uintptr_t EXPORT my_syscall(x64emu_t *emu)
             return (int)fchmodat((int)R_ESI, (void*)R_RDX, (mode_t)R_RCX, (int)R_R8d);
         #endif
         default:
-            printf_log(LOG_INFO, "Warning: Unsupported libc Syscall 0x%02X (%d)\n", s, s);
+            if(!(warned&(1<<s))) {
+                printf_log(LOG_INFO, "Warning: Unsupported libc Syscall 0x%02X (%d)\n", s, s);
+                warned|=(1<<s);
+            }
             errno = ENOSYS;
             return -1;
     }
diff --git a/src/librarian/library.c b/src/librarian/library.c
index 46aead20..32a58311 100755
--- a/src/librarian/library.c
+++ b/src/librarian/library.c
@@ -342,6 +342,8 @@ library_t *NewLibrary(const char* path, box64context_t* context)
     }
     int notwrapped = FindInCollection(lib->name, &context->box64_emulated_libs);
     int precise = (path && path[0]=='/')?1:0;
+    if(!notwrapped && precise && strstr(path, "libtcmalloc_minimal.so"))
+        precise = 0;    // allow native version for tcmalloc_minimum
     // check if name is libSDL_sound-1.0.so.1 but with SDL2 loaded, then try emulated first...
     if(!notwrapped && !strcmp(lib->name, "libSDL_sound-1.0.so.1") && my_context->sdl2lib)
         notwrapped = 1;
diff --git a/src/library_list.h b/src/library_list.h
index 9f6203dc..04520348 100755
--- a/src/library_list.h
+++ b/src/library_list.h
@@ -144,6 +144,7 @@ GO("libtinfo.so.5", libtinfo)
 GO("libpanel.so.5", libpanel)
 GO("libncurses.so.6", libncurses6)
 GO("libtinfo.so.6", libtinfo6)
+GO("libtcmalloc_minimal.so.0", tcmallocminimal)
 GO("libtcmalloc_minimal.so.4", tcmallocminimal)
 GO("libmpg123.so.0", mpg123)
 GO("libgnutls.so.30", gnutls)
diff --git a/src/main.c b/src/main.c
index 772c1666..ae2c21b9 100755
--- a/src/main.c
+++ b/src/main.c
@@ -907,6 +907,7 @@ static void free_contextargv()
         free(my_context->argv[i]);
 }
 
+void pressure_vessel(int argc, const char** argv, int nextarg);
 extern char** environ;
 int main(int argc, const char **argv, char **env) {
 
@@ -969,16 +970,12 @@ int main(int argc, const char **argv, char **env) {
             //wine_preloaded = 1;
         }
     }
-    #if 0
+    #if 1
     // pre-check for pressure-vessel-wrap
     if(strstr(prog, "pressure-vessel-wrap")==(prog+strlen(prog)-strlen("pressure-vessel-wrap"))) {
         // pressure-vessel-wrap detecter, skipping it and all -- args until "--" if needed
-        ++nextarg;
-        if(argv[nextarg][0]=='-' && argv[nextarg][1]=='-')
-            while(argv[nextarg][0]=='-' && argv[nextarg][1]=='-')
-                ++nextarg;
-        prog = argv[nextarg];
-        printf_log(LOG_INFO, "BOX64: pressure-vessel-wrap detected, loading \"%s\" directly\n", prog);
+        printf_log(LOG_INFO, "BOX64: pressure-vessel-wrap detected\n");
+        pressure_vessel(argc, argv, nextarg+1);
     }
     #endif
     // check if this is wine
@@ -1002,6 +999,10 @@ int main(int argc, const char **argv, char **env) {
     if(!strcmp(prog, "wineserver") || !strcmp(prog, "wineserver64") || (strlen(prog)>9 && !strcmp(prog+strlen(prog)-strlen("/wineserver"), "/wineserver"))) {
         box64_wine = 1;
     }
+    if(box64_wine) {
+        // disabling the use of futex_waitv for now
+        setenv("WINEFSYNC", "0", 1);
+    }
     // Create a new context
     my_context = NewBox64Context(argc - nextarg);
 
@@ -1033,6 +1034,8 @@ int main(int argc, const char **argv, char **env) {
     } else {
         if(getenv("LD_PRELOAD")) {
             char* p = getenv("LD_PRELOAD");
+            if(strstr(p, "libtcmalloc_minimal.so.0"))
+                box64_tcmalloc_minimal = 1;
             if(strstr(p, "libtcmalloc_minimal.so.4"))
                 box64_tcmalloc_minimal = 1;
             if(strstr(p, "libtcmalloc_minimal_debug.so.4"))
diff --git a/src/steam.c b/src/steam.c
new file mode 100644
index 00000000..ddbb7c6a
--- /dev/null
+++ b/src/steam.c
@@ -0,0 +1,93 @@
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <sys/wait.h>
+#include <unistd.h>
+#include <errno.h>
+
+#include "debug.h"
+#include "box64context.h"
+#include "fileutils.h"
+
+void pressure_vessel(int argc, const char** argv, int nextarg)
+{
+    // skip all the parameter, but parse some of them
+    if(argv[nextarg][0]=='-' && argv[nextarg][1]=='-')
+        while(argv[nextarg][0]=='-' && argv[nextarg][1]=='-') {
+            if(strstr(argv[nextarg], "--env-if-host=PRESSURE_VESSEL_APP_LD_LIBRARY_PATH=")==argv[nextarg]) {
+                // transform RESSURE_VESSEL_APP_LD_LIBRARY_PATH to BOX86_ / BOX64_ LD_LIBRARY_PATH
+                char tmp[strlen(argv[nextarg])];
+                strcpy(tmp, "");
+                strcat(tmp, argv[nextarg]+strlen("--env-if-host=PRESSURE_VESSEL_APP_"));
+                char *p = strchr(tmp, '=');
+                *p ='\0'; ++p;
+                setenv(tmp, p, 1);
+                printf_log(/*LOG_DEBUG*/LOG_INFO, "setenv(%s, %s, 1)\n", tmp, p);
+            } else if(strstr(argv[nextarg], "--env-if-host=STEAM_RUNTIME_LIBRARY_PATH=")==argv[nextarg]) {
+                // transform RESSURE_VESSEL_APP_LD_LIBRARY_PATH to BOX86_ / BOX64_ LD_LIBRARY_PATH
+                char tmp[strlen(argv[nextarg])];
+                strcpy(tmp, "BOX86_LD_");
+                strcat(tmp, argv[nextarg]+strlen("--env-if-host=STEAM_RUNTIME_"));
+                char *p = strchr(tmp, '=');
+                *p ='\0'; ++p;
+                setenv(tmp, p, 1);
+                printf_log(/*LOG_DEBUG*/LOG_INFO, "setenv(%s, %s, 1)\n", tmp, p);
+                tmp[3] = '6';
+                tmp[4] = '4';
+                setenv(tmp, p, 1);
+                printf_log(/*LOG_DEBUG*/LOG_INFO, "setenv(%s, %s, 1)\n", tmp, p);
+            } else if(!strcmp(argv[nextarg], "--")) {
+                printf_log(/*LOG_DEBUG*/LOG_INFO, "End of pressure-vessel-wrap parameters\n");
+            }else {
+                printf_log(/*LOG_DEBUG*/LOG_INFO, "Ignored parameter: \"%s\"\n", argv[nextarg]);
+            }
+            ++nextarg;
+        }
+    printf_log(/*LOG_DEBUG*/LOG_INFO, "Ready to launch \"%s\", nextarg=%d, argc=%d\n", argv[nextarg], nextarg, argc);
+    const char* prog = argv[nextarg];
+    my_context = NewBox64Context(argc - nextarg);
+    int x86 = my_context->box86path?FileIsX86ELF(argv[nextarg]):0;
+    int x64 = my_context->box64path?FileIsX64ELF(argv[nextarg]):0;
+    // create the new argv array
+    const char** newargv = (const char**)calloc((argc-nextarg)+1+((x86 || x64)?1:0), sizeof(char*));
+    if(x86 || x64) {
+        newargv[0] = x64?my_context->box64path:my_context->box86path;
+        printf_log(/*LOG_DEBUG*/LOG_INFO, "argv[%d]=\"%s\"\n", 0, newargv[0]);    
+        for(int i=nextarg; i<argc; ++i) {
+            printf_log(/*LOG_DEBUG*/LOG_INFO, "argv[%d]=\"%s\"\n", 1+i-nextarg, argv[i]);    
+            newargv[1+i-nextarg] = argv[i];
+        }
+    } else {
+        for(int i=nextarg; i<argc; ++i) {
+            printf_log(/*LOG_DEBUG*/LOG_INFO, "argv[%d]=\"%s\"\n", i-nextarg, argv[i]);    
+            newargv[i-nextarg] = argv[i];
+        }
+    }
+
+//setenv("BOX64_TRACE_FILE", "/home/seb/trace64-%pid.txt", 1);
+//setenv("BOX86_TRACE_FILE", "/home/seb/trace86-%pid.txt", 1);
+//setenv("BOX86_LOG", "1", 1);
+//setenv("BOX64_LOG", "1", 1);
+//setenv("BOX86_SHOWSEGV", "1", 1);
+//setenv("BOX64_SHOWSEGV", "1", 1);
+
+    printf_log(/*LOG_DEBUG*/LOG_INFO, "Run %s %s and wait\n", x86?"i386":(x64?"x86_64":""), argv[nextarg]);
+    pid_t v = vfork();
+    if(v==-1) {
+        printf_log(LOG_NONE, "vfork failed!\n");
+        FreeBox64Context(&my_context);
+        return;
+    }
+    if(!v) {
+        // child process, exec the program...
+        int ret = execvp(newargv[0], (char * const*)newargv);
+        printf_log(/*LOG_DEBUG*/LOG_INFO, "Error launching program: %d (%s)\n", ret, strerror(errno));
+        exit(0);
+    } else {
+        // parent process, wait the end of child
+        FreeBox64Context(&my_context);
+        int wstatus;
+        waitpid(v, &wstatus, 0);
+        exit(0);
+    }
+}
\ No newline at end of file
diff --git a/src/wrapped/generated/functions_list.txt b/src/wrapped/generated/functions_list.txt
index c05b8830..fa0faa29 100644
--- a/src/wrapped/generated/functions_list.txt
+++ b/src/wrapped/generated/functions_list.txt
@@ -404,6 +404,7 @@
 #() iFppl
 #() iFppL
 #() iFppp
+#() iFpOu
 #() iFpOM
 #() iFSpL
 #() IFiIi
diff --git a/src/wrapped/generated/wrapper.c b/src/wrapped/generated/wrapper.c
index 738e1395..a95b9938 100644
--- a/src/wrapped/generated/wrapper.c
+++ b/src/wrapped/generated/wrapper.c
@@ -438,6 +438,7 @@ typedef int64_t (*iFppd_t)(void*, void*, double);
 typedef int64_t (*iFppl_t)(void*, void*, intptr_t);
 typedef int64_t (*iFppL_t)(void*, void*, uintptr_t);
 typedef int64_t (*iFppp_t)(void*, void*, void*);
+typedef int64_t (*iFpOu_t)(void*, int32_t, uint64_t);
 typedef int64_t (*iFpOM_t)(void*, int32_t, ...);
 typedef int64_t (*iFSpL_t)(void*, void*, uintptr_t);
 typedef int64_t (*IFiIi_t)(int64_t, int64_t, int64_t);
@@ -2496,6 +2497,7 @@ void iFppd(x64emu_t *emu, uintptr_t fcn) { iFppd_t fn = (iFppd_t)fcn; R_RAX=(int
 void iFppl(x64emu_t *emu, uintptr_t fcn) { iFppl_t fn = (iFppl_t)fcn; R_RAX=(int64_t)fn((void*)R_RDI, (void*)R_RSI, (intptr_t)R_RDX); }
 void iFppL(x64emu_t *emu, uintptr_t fcn) { iFppL_t fn = (iFppL_t)fcn; R_RAX=(int64_t)fn((void*)R_RDI, (void*)R_RSI, (uintptr_t)R_RDX); }
 void iFppp(x64emu_t *emu, uintptr_t fcn) { iFppp_t fn = (iFppp_t)fcn; R_RAX=(int64_t)fn((void*)R_RDI, (void*)R_RSI, (void*)R_RDX); }
+void iFpOu(x64emu_t *emu, uintptr_t fcn) { iFpOu_t fn = (iFpOu_t)fcn; R_RAX=(int64_t)fn((void*)R_RDI, of_convert((int32_t)R_RSI), (uint64_t)R_RDX); }
 void iFpOM(x64emu_t *emu, uintptr_t fcn) { iFpOM_t fn = (iFpOM_t)fcn; R_RAX=(int64_t)fn((void*)R_RDI, of_convert((int32_t)R_RSI), (void*)R_RDX, (void*)R_RCX); }
 void iFSpL(x64emu_t *emu, uintptr_t fcn) { iFSpL_t fn = (iFSpL_t)fcn; R_RAX=(int64_t)fn(io_convert((void*)R_RDI), (void*)R_RSI, (uintptr_t)R_RDX); }
 void IFiIi(x64emu_t *emu, uintptr_t fcn) { IFiIi_t fn = (IFiIi_t)fcn; R_RAX=(int64_t)fn((int64_t)R_RDI, (int64_t)R_RSI, (int64_t)R_RDX); }
diff --git a/src/wrapped/generated/wrapper.h b/src/wrapped/generated/wrapper.h
index 85134c1f..d28be157 100644
--- a/src/wrapped/generated/wrapper.h
+++ b/src/wrapped/generated/wrapper.h
@@ -437,6 +437,7 @@ void iFppd(x64emu_t *emu, uintptr_t fnc);
 void iFppl(x64emu_t *emu, uintptr_t fnc);
 void iFppL(x64emu_t *emu, uintptr_t fnc);
 void iFppp(x64emu_t *emu, uintptr_t fnc);
+void iFpOu(x64emu_t *emu, uintptr_t fnc);
 void iFpOM(x64emu_t *emu, uintptr_t fnc);
 void iFSpL(x64emu_t *emu, uintptr_t fnc);
 void IFiIi(x64emu_t *emu, uintptr_t fnc);
diff --git a/src/wrapped/wrappedlibrt_private.h b/src/wrapped/wrappedlibrt_private.h
index 20dc6288..75eb3faa 100755
--- a/src/wrapped/wrappedlibrt_private.h
+++ b/src/wrapped/wrappedlibrt_private.h
@@ -40,7 +40,7 @@ GO(mq_setattr, iFipp)
 GO(mq_timedreceive, lFipLpp)
 GO(mq_timedsend, iFipLup)
 GO(mq_unlink, iFp)
-GO(shm_open, iFpiu)
+GO(shm_open, iFpOu)
 GO(shm_unlink, iFp)
 GOM(timer_create, iFEupp)
 GO(timer_delete, iFu)