delorie.com/archives/browse.cgi   search  
Mail Archives: djgpp-workers/2000/08/21/07:53:44

Message-ID: <39A1181F.C25823B3@softhome.net>
Date: Mon, 21 Aug 2000 13:53:03 +0200
From: Laurynas Biveinis <lauras AT softhome DOT net>
X-Mailer: Mozilla 4.74 [en] (Win98; U)
X-Accept-Language: lt,en
MIME-Version: 1.0
To: DJGPP Workers <djgpp-workers AT delorie DOT com>
Subject: Patch: symlinks to programs
Reply-To: djgpp-workers AT delorie DOT com

Here are changes for dosexec.c to DTRT with symlinks.
This code was probably the hardest piece of symlink support
to implement, so there might be few stupid stupidities laying
around in this patch, although my testsuite suggests that it
even works.

This is (If I haven't skipped anything else) the last non-trivial
patch for symlinks. All upcoming patches will be mostly

if (!__solve_symlinks(path, real_path))
  return -1;
...
/* Change 'path' to 'real_path' everywhere... */

Feedback is very welcome for this patch.
Laurynas

Index: djgpp/src/libc/dos/process/dosexec.c
===================================================================
RCS file: /cvs/djgpp/djgpp/src/libc/dos/process/dosexec.c,v
retrieving revision 1.9
diff -u -r1.9 dosexec.c
--- dosexec.c	2000/08/03 12:21:17	1.9
+++ dosexec.c	2000/08/21 11:41:51
@@ -22,6 +22,7 @@
 #include <libc/unconst.h>
 #include <libc/dosio.h>
 #include <libc/farptrgs.h>
+#include <libc/symlink.h>
 
 /* FIXME: this is not LFN-clean.  Win95 has a way to
    pass long command lines, but we don't support it here.  */
@@ -519,6 +520,7 @@
   int i;
   char *go32, *sip=0;
   char rpath[FILENAME_MAX];
+  char real_program[FILENAME_MAX];
   int argc=0;
 
   int si_la=0, si_off=0, rm_off, argv_off;
@@ -527,8 +529,11 @@
   int retval;
   int lfn = 2;	/* means don't know yet */
 
-  type = _check_v2_prog (program, -1);
+  if (!__solve_symlinks(program, real_program))
+     return -1;
 
+  type = _check_v2_prog (real_program, -1);
+
   /* Because this function is called only, when program
      exists, I can skip the check for type->valid */
 
@@ -539,16 +544,16 @@
 
   if (type->exec_format == _V2_EXEC_FORMAT_UNIXSCRIPT)
   {
-    return script_exec(program, argv, envp);
+    return script_exec(real_program, argv, envp);
   }
 
   /* Non-DJGPP programs cannot be run by !proxy.  */
   if (!is_coff)
   {
     if (type->exec_format == _V2_EXEC_FORMAT_EXE)
-      return direct_exec(program, argv, envp);
+      return direct_exec(real_program, argv, envp);
     else
-      return __dosexec_command_exec (program, argv, envp);
+      return __dosexec_command_exec (real_program, argv, envp);
   }
 
   if (found_si)
@@ -560,7 +565,7 @@
 
   if (v2_0 && is_stubbed)
   {
-    strcpy(rpath, program);
+    strcpy(rpath, real_program);
   }
   else
   {
@@ -568,7 +573,7 @@
     if (!__dosexec_find_on_path(go32, envp, rpath))
     {
       errno = e;
-      return direct_exec(program, argv, envp); /* give up and just run it */
+      return direct_exec(real_program, argv, envp); /* give up and just run it */
     }
 
     if (found_si)
@@ -586,7 +591,7 @@
      usual DOS command line and the !proxy one (which will be put
      into the environment).  Sigh...  */
   save_argv0 = argv[0];
-  argv[0] = unconst(program, char *); /* since that's where we really found it */
+  argv[0] = unconst(program, char *);
   /* Construct the DOS command tail */
   for (argc=0; argv[argc]; argc++);
 
@@ -704,9 +709,13 @@
   int cmdlen;
   int i;
   int was_quoted = 0;	/* was the program name quoted? */
+  char real_program[FILENAME_MAX];
+
+  if (!__solve_symlinks(program, real_program))
+     return -1;
 
   /* Add spare space for possible quote characters.  */
-  cmdlen = strlen(program) + 4 + 2;
+  cmdlen = strlen(real_program) + 4 + 2;
   for (i=0; argv[i]; i++)
     cmdlen += 2*strlen(argv[i]) + 1;
   cmdline = (char *)alloca(cmdlen);
@@ -714,21 +723,21 @@
   /* FIXME: is this LFN-clean?  What special characters can
      the program name have and how should they be quoted?  */
   strcpy(cmdline, "/c ");
-  if (strchr(program, ' ') || strchr(program, '\t'))
+  if (strchr(real_program, ' ') || strchr(real_program, '\t'))
   {
     was_quoted = 1;
     cmdline[3] = '"';
   }
-  for (i = 0; program[i] > ' '; i++)
+  for (i = 0; real_program[i] > ' '; i++)
   {
     /* COMMAND.COM cannot grok program names with forward slashes.  */
     if (program[i] == '/')
       cmdline[i+3+was_quoted] = '\\';
     else
-      cmdline[i+3+was_quoted] = program[i];
+      cmdline[i+3+was_quoted] = real_program[i];
   }
-  for (; program[i]; i++)
-    cmdline[i+3+was_quoted] = program[i];
+  for (; real_program[i]; i++)
+    cmdline[i+3+was_quoted] = real_program[i];
   if (was_quoted)
   {
     cmdline[i+3+was_quoted] = '"';
Index: djgpp/tests/libc/dos/process/args.c
===================================================================
RCS file: args.c
diff -N args.c
--- /dev/null	Tue May  5 16:32:27 1998
+++ args.c	Mon Aug 21 07:42:04 2000
@@ -0,0 +1,9 @@
+#include <stdio.h>
+
+int main(int argc, char *argv[])
+{
+   int i;
+   for (i = 0; i < argc; i++)
+      printf("argv[%d] = %s\n", i, argv[i]);
+   return 0;
+}
Index: djgpp/tests/libc/dos/process/makefile
===================================================================
RCS file: /cvs/djgpp/djgpp/tests/libc/dos/process/makefile,v
retrieving revision 1.1
diff -u -r1.1 makefile
--- makefile	1995/11/13 03:14:50	1.1
+++ makefile	2000/08/21 11:42:04
@@ -1,5 +1,7 @@
 TOP=../..
 
+SRC += args.c
 SRC += spawnvp.c
+SRC += symlinks.c
 
 include $(TOP)/../makefile.inc
Index: djgpp/tests/libc/dos/process/symlinks.c
===================================================================
RCS file: symlinks.c
diff -N symlinks.c
--- /dev/null	Tue May  5 16:32:27 1998
+++ symlinks.c	Mon Aug 21 07:42:04 2000
@@ -0,0 +1,28 @@
+/* Testsuite for symlink handling aspect in launching program. 
+ * This is by no means a regression testsuite, you have to decide 
+ * if bad stuff happens from output. 
+ *
+ * Shell script handling will be checked only if you have bash installed.
+ */
+#include <process.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+
+int main(void)
+{
+   symlink("args.exe", "linkargs.exe");
+   system("args.exe 1 2 3");
+   system("linkargs.exe 4 5 6");
+   spawnl(P_WAIT, "args.exe", "args.exe", "what", NULL);
+   spawnl(P_WAIT, "linkargs.exe", "linkargs.exe", "where", "why", NULL);
+   remove("linkargs.exe");
+   symlink("C:/command.com", "linkcom.com");
+   system("linkcom.com");
+   remove("linkcom.com");
+   symlink("test.sh", "linksh.sh");
+   system("test.sh");
+   system("linksh.sh");
+   remove("linksh.sh");
+   return 0;
+}
Index: djgpp/tests/libc/dos/process/test.sh
===================================================================
RCS file: test.sh
diff -N test.sh
--- /dev/null	Tue May  5 16:32:27 1998
+++ test.sh	Mon Aug 21 07:42:04 2000
@@ -0,0 +1,3 @@
+#!/bin/sh
+echo Just checking...
+

- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019