diff --git a/src/pc/sys.c b/src/pc/sys.c
index 1c1fa97..aa92bc7 100644
--- a/src/pc/sys.c
+++ b/src/pc/sys.c
@@ -15,17 +15,32 @@ along with this program; see the file COPYING. If not, see
. */
#include
+#include
int
sys_launch_title(const char* title_id, char* args) {
printf("launch title: %s %s\n", title_id, args);
- return 0;
+ return -1;
}
int
sys_launch_homebrew(const char* path, char* args) {
- printf("launch homebrew: %s %s\n", path, args);
- return 0;
+ char cmd[255];
+ FILE *pf;
+
+ if(!args) {
+ args = "";
+ }
+
+ snprintf(cmd, sizeof(cmd), "%s %s", path, args);
+ printf("launch homebrew: %s\n", cmd);
+
+ if(!(pf=popen(cmd,"r"))) {
+ perror("popen");
+ return -1;
+ }
+
+ return fileno(pf);
}
diff --git a/src/ps5/hbldr.c b/src/ps5/hbldr.c
index b8476c2..cbc60f0 100644
--- a/src/ps5/hbldr.c
+++ b/src/ps5/hbldr.c
@@ -359,7 +359,7 @@ bigapp_set_procname(pid_t pid, const char* name) {
*
**/
static pid_t
-bigapp_replace(pid_t pid, uint8_t* elf, const char* progname) {
+bigapp_replace(pid_t pid, uint8_t* elf, const char* progname, int stdio) {
uint8_t int3instr = 0xcc;
intptr_t brkpoint;
uint8_t orginstr;
@@ -413,7 +413,7 @@ bigapp_replace(pid_t pid, uint8_t* elf, const char* progname) {
bigapp_set_procname(pid, basename(progname));
// Execute the ELF
- if(elfldr_exec(STDIN_FILENO, STDOUT_FILENO, STDERR_FILENO, pid, elf)) {
+ if(elfldr_exec(-1, stdio, stdio, pid, elf)) {
kill(pid, SIGKILL);
pt_detach(pid);
return -1;
@@ -423,8 +423,8 @@ bigapp_replace(pid_t pid, uint8_t* elf, const char* progname) {
}
-int
-hbldr_launch(const char* path, char** argv) {
+pid_t
+hbldr_launch(const char* path, char** argv, int stdio) {
uint32_t user_id;
uint8_t* elf;
int app_id;
@@ -463,10 +463,10 @@ hbldr_launch(const char* path, char** argv) {
kernel_set_proc_rootdir(pid, kernel_get_root_vnode());
kernel_set_proc_jaildir(pid, 0);
- if(bigapp_replace(pid, elf, path) < 0) {
+ if(bigapp_replace(pid, elf, path, stdio) < 0) {
return -1;
}
- return 0;
+ return pid;
}
diff --git a/src/ps5/hbldr.h b/src/ps5/hbldr.h
index 346caf1..58dcb69 100644
--- a/src/ps5/hbldr.h
+++ b/src/ps5/hbldr.h
@@ -16,6 +16,8 @@ along with this program; see the file COPYING. If not, see
#pragma once
+#include
-int hbldr_launch(const char* path, char** argv);
+
+pid_t hbldr_launch(const char* path, char** argv, int stdio);
diff --git a/src/ps5/sys.c b/src/ps5/sys.c
index b496fe0..a3f25db 100644
--- a/src/ps5/sys.c
+++ b/src/ps5/sys.c
@@ -95,39 +95,38 @@ ps5_find_pid(const char* name) {
int
sys_launch_homebrew(const char* path, const char* args) {
char* argv[255];
+ int fds[2];
char* buf;
pid_t pid;
-
printf("launch homebrew: %s %s\n", path, args);
-
+
if(!args) {
args = "";
}
+ if(pipe(fds)) {
+ perror("pipe");
+ return -1;
+ }
+
buf = strdup(args);
websrv_split_args(buf, argv, 255);
- if(hbldr_launch(path, argv) < 0) {
+ if((pid=hbldr_launch(path, argv, fds[1])) < 0) {
free(buf);
+ close(fds[0]);
+ close(fds[1]);
return -1;
}
free(buf);
-
- if((pid=ps5_find_pid("SceNKWebProcess")) > 0) {
- printf("exit %d\n", pid);
-
- pt_attach(pid);
- pt_syscall(pid, SYS_exit);
- pt_detach(pid);
- }
+ close(fds[1]);
- return 0;
+ return fds[0];
}
-
int
sys_launch_title(const char* title_id, const char* args) {
app_launch_ctx_t ctx = {0};
diff --git a/src/websrv.c b/src/websrv.c
index 1a47775..729a377 100644
--- a/src/websrv.c
+++ b/src/websrv.c
@@ -106,22 +106,28 @@ hbldr_request(struct MHD_Connection *conn, const char* url) {
const char* path;
const char *args;
int ret = MHD_NO;
- int status;
+ int fd;
path = MHD_lookup_connection_value(conn, MHD_GET_ARGUMENT_KIND, "path");
args = MHD_lookup_connection_value(conn, MHD_GET_ARGUMENT_KIND, "args");
if(!path) {
- status = MHD_HTTP_BAD_REQUEST;
- } else if(sys_launch_homebrew(path, args)) {
- status = MHD_HTTP_SERVICE_UNAVAILABLE;
- } else {
- status = MHD_HTTP_OK;
- }
+ if((resp=MHD_create_response_from_buffer(0, "", MHD_RESPMEM_PERSISTENT))) {
+ ret = websrv_queue_response(conn, MHD_HTTP_BAD_REQUEST, resp);
+ MHD_destroy_response(resp);
+ }
- if((resp=MHD_create_response_from_buffer(0, "", MHD_RESPMEM_PERSISTENT))) {
- ret = websrv_queue_response(conn, status, resp);
- MHD_destroy_response(resp);
+ } else if((fd=sys_launch_homebrew(path, args)) < 0) {
+ if((resp=MHD_create_response_from_buffer(0, "", MHD_RESPMEM_PERSISTENT))) {
+ ret = websrv_queue_response(conn, MHD_HTTP_SERVICE_UNAVAILABLE, resp);
+ MHD_destroy_response(resp);
+ }
+
+ } else {
+ if((resp=MHD_create_response_from_pipe(fd))) {
+ ret = websrv_queue_response(conn, MHD_HTTP_OK, resp);
+ MHD_destroy_response(resp);
+ }
}
return ret;