--- Urlader/urlader.c 2012/01/05 06:00:13 1.11 +++ Urlader/urlader.c 2012/01/17 18:38:37 1.13 @@ -1,3 +1,39 @@ +/* + * Copyright (c) 2012 Marc Alexander Lehmann + * + * Redistribution and use in source and binary forms, with or without modifica- + * tion, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MER- + * CHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO + * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPE- + * CIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, + * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; + * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, + * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTH- + * ERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + * Alternatively, the contents of this file may be used under the terms of + * the GNU General Public License ("GPL") version 2 or any later version, + * in which case the provisions of the GPL are applicable instead of + * the above. If you wish to allow the use of your version of this file + * only under the terms of the GPL and not to allow others to use your + * version of this file under the BSD license, indicate your decision + * by deleting the provisions above and replace them with the notice + * and other provisions required by the GPL. If you do not delete the + * provisions above, a recipient may use your version of this file under + * either the BSD or the GPL. + */ + #include "urlib.h" #include "urlib.c" @@ -16,9 +52,8 @@ static char tmppath[MAX_PATH]; static int exe_argc; -static const char *exe_argv[MAX_ARGC]; -static char exe_args[MAX_ARGS]; /* actual arguments strings copied here */ -static unsigned int exe_argo; +static u_dynbuf exe_argv; +static u_dynbuf exe_args; /* actual arguments strings copied here */ static void tmpdir (const char *dir) @@ -74,6 +109,7 @@ } static char *pack_base, *pack_end; +static struct u_pack_tail *pack_tail; static struct u_pack_hdr *pack_cur; static char *scratch; static unsigned int scratch_size; @@ -127,21 +163,22 @@ if (!addr) return 0; - pack_unmap (); + /*pack_unmap ();*/ pack_base = addr; pack_end = pack_base + size; - struct u_pack_tail *tail; + pack_tail = (void *)(pack_end - sizeof (*pack_tail)); - tail = (void *)(pack_end - sizeof (*tail)); - - if (memcmp (tail->magic, TAIL_MAGIC, sizeof (TAIL_MAGIC) - 1)) + if (memcmp (pack_tail->magic, TAIL_MAGIC, sizeof (TAIL_MAGIC) - 1)) return 0; - pack_cur = (struct u_pack_hdr *)(pack_end - u_32 (tail->size)); + pack_cur = (struct u_pack_hdr *)(pack_end - u_32 (pack_tail->size)); - scratch = u_malloc (scratch_size = u_32 (tail->max_uncompressed)); + if (pack_cur->type != T_META) + return 0; + + scratch = u_malloc (scratch_size = u_32 (pack_tail->max_uncompressed)); if (!scratch) return 0; @@ -149,20 +186,19 @@ } static void -exe_info (void) +add_arg (char *arg, unsigned int len) { - if (!pack_map ()) - u_fatal ("unable to locate packfile in executable - executable corrupted?"); - - if (pack_cur->type != T_META) - u_fatal ("unable to locate executable metadata - executable corrupted?"); - - strcpy (exe_id, PACK_NAME); + char *addr = u_dynbuf_append (&exe_args, arg, len); + u_dynbuf_append (&exe_argv, &addr, sizeof (addr)); } static void load (void) { + strcpy (exe_id , PACK_NAME); + strcpy (exe_ver, PACK_DATA); + u_set_exe_info (); + if (u_chdir (exe_dir)) u_fatal ("unable to change to application data directory"); @@ -171,21 +207,24 @@ { u_handle oh = pack_handle; + pack_unmap (); pack_handle = h; - if (pack_map ()) + + if (pack_map () + && strcmp (exe_id , PACK_NAME) == 0 + && strcmp (exe_ver, PACK_DATA) <= 0) u_setenv ("URLADER_OVERRIDE", "override"); else { + pack_unmap (); pack_handle = oh; oh = h; + pack_map (); } u_close (oh); } - if (pack_cur->type != T_META) - u_fatal ("unable to locate override metadata"); - strcpy (exe_ver, PACK_DATA); u_set_exe_info (); pack_next (); @@ -195,12 +234,7 @@ if (pack_cur->type == T_ENV) u_setenv (PACK_NAME, PACK_DATA); else if (pack_cur->type == T_ARG) - { - int len = u_16 (pack_cur->namelen) + 1; - exe_argv [exe_argc++] = exe_args + exe_argo; - memcpy (exe_args + exe_argo, PACK_NAME, len); - exe_argo += len; - } + add_arg (PACK_NAME, u_16 (pack_cur->namelen) + 1); else break; @@ -297,20 +331,33 @@ static void execute (void) { - exe_argv [exe_argc] = 0; - systemv (exe_argv); + char *null = 0; + u_dynbuf_append (&exe_argv, &null, sizeof (null)); + systemv ((const char *const *)exe_argv.addr); } +// this argc/argv is without argv [0] static void -doit (void) +doit (int argc, char *argv[]) { + int i; + + u_setenv ("URLADER_CURRDIR", currdir); + u_set_datadir (); u_mkdir (datadir); - exe_info (); - u_set_exe_info (); + if (!pack_map ()) + u_fatal ("unable to map pack file - executable corrupted?"); load (); + + while (argc--) + { + add_arg (*argv, strlen (*argv) + 1); + ++argv; + } + execute (); } @@ -322,6 +369,8 @@ if (!GetModuleFileName (hI, tmppath, sizeof (tmppath))) u_fatal ("unable to find executable pack"); + u_setenv ("URLADER_EXEPATH", tmppath); + pack_handle = u_open (tmppath); if (!u_valid (pack_handle)) u_fatal ("unable to open executable pack"); @@ -329,7 +378,7 @@ if (!GetCurrentDirectory (sizeof (currdir), currdir)) strcpy (currdir, "."); - doit (); + doit (1, &argv); return 0; } @@ -339,6 +388,8 @@ int main (int argc, char *argv[]) { + u_setenv ("URLADER_EXEPATH", argv [0]); + pack_handle = u_open (argv [0]); if (!u_valid (pack_handle)) u_fatal ("unable to open executable pack"); @@ -355,7 +406,7 @@ u_append (datadir, tmppath); #endif - doit (); + doit (argc - 1, argv + 1); return 0; }