source: git/omalloc/omFindExec.c @ d011a2

spielwiese
Last change on this file since d011a2 was 13fe1b, checked in by Hans Schönemann <hannes@…>, 23 years ago
*hannes: DecAlpha-ccc-port git-svn-id: file:///usr/local/Singular/svn/trunk@5409 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 5.9 KB
Line 
1/*******************************************************************
2 *  File:    omFindExec.c
3 *  Purpose: routine which determines absolute pathname of executable
4 *  Author:  obachman (Olaf Bachmann)
5 *  Created: 11/99
6 *  Version: $Id: omFindExec.c,v 1.10 2001-04-30 09:02:06 Singular Exp $
7 *******************************************************************/
8
9#ifdef HAVE_CONFIG_H
10#include "omConfig.h"
11#endif
12
13#if ! defined(__MWERKS__) && defined(HAVE_UNISTD_H) && defined(STDC_HEADERS)
14
15#ifdef HAVE_UNISTD_H
16#include <unistd.h> /* always defiend */
17#endif
18#include <stdlib.h>
19#include <string.h>
20
21#include "omFindExec.h"
22
23#ifndef MAXPATHLEN
24#define MAXPATHLEN 1024
25#endif
26
27#ifdef WINNT
28#include "om_Alloc.h"
29#endif
30
31/* ABSOLUTE_FILENAME_P (fname): True if fname is an absolute filename */
32#ifdef atarist
33#define ABSOLUTE_FILENAME_P(fname)        ((fname[0] == '/') || \
34        (fname[0] && (fname[1] == ':')))
35#else
36#define ABSOLUTE_FILENAME_P(fname)        (fname[0] == '/')
37#endif /* atarist */
38
39/* Return the absolute name of the program named NAME.  This function
40   searches the directories in the PATH environment variable if PROG
41   has no directory components. */
42#ifndef HAVE_READLINK
43char * omFindExec (const char *name, char* executable)
44#else
45static char * omFindExec_link (const char *name, char* executable)
46#endif
47{
48  char *search;
49  char *p;
50#ifdef WINNT
51  char *extra = NULL;
52#endif
53  char tbuf[MAXPATHLEN];
54
55  if (ABSOLUTE_FILENAME_P(name))
56  {
57      /* If we can execute the named file then return it. */
58      if (! access (name, X_OK))
59      {
60        strcpy(executable, name);
61        return executable;
62      }
63  }
64  else
65  {
66    if (((name[0] == '.') && (name[1] == '/')) ||
67        ((name[0] == '.') && (name[1] == '.') && (name[2] == '/')) ||
68        strchr(name, '/') != NULL)
69    {
70
71#ifdef HAVE_GETCWD
72      getcwd (tbuf, MAXPATHLEN);
73#else
74# ifdef HAVE_GETWD
75      getwd (tbuf);
76# endif
77#endif
78      strcat (tbuf, "/");
79      strcat (tbuf, name);
80      if (! access(tbuf, X_OK))
81      {
82        strcpy(executable, tbuf);
83        return executable;
84      }
85    }
86
87
88    search = getenv("PATH");
89/* for winnt under msdos, cwd is implictly in the path */
90#ifdef WINNT
91    p = getenv("SHELL");
92    if (p == NULL || strlen(p) < 2)
93    {
94      char *extra = NULL;
95      /* we are under msdos display */
96      extra = (char*) omAlloc((search != NULL ? strlen(search) : 0) + 3);
97      strcpy(extra, ".:");
98      if (search != NULL) strcat(extra, search);
99      search = extra;
100    }
101#endif
102    p = search;
103
104    if (p != NULL)
105    {
106      while (1)
107      {
108        char *next;
109        next = tbuf;
110
111        /* Copy directory name into [tbuf]. */
112        /* This is somewhat tricky: empty names mean cwd, w.r.t. some
113           shell spec */
114        while (*p && *p != ':')
115          *next ++ = *p ++;
116        *next = '\0';
117
118        if ((tbuf[0] == '.' && tbuf[1] == '\0') || tbuf[0] == '\0') {
119#ifdef HAVE_GETCWD
120          getcwd (tbuf, MAXPATHLEN);
121#else
122# ifdef HAVE_GETWD
123          getwd (tbuf);
124# endif
125#endif
126        }
127
128        if (tbuf[strlen(tbuf)-1] != '/') strcat(tbuf, "/");
129        strcat (tbuf, name);
130
131        /* If we can execute the named file, then return it. */
132        if (! access (tbuf, X_OK))
133        {
134#ifdef WINNT
135          if (extra != NULL)
136            omFree(extra);
137#endif
138          strcpy(executable, tbuf);
139          return executable;
140        }
141
142        if (*p != '\0')
143        {
144          p ++;
145        }
146        else
147        {
148          break;
149        }
150      }
151    }
152  }
153  return NULL;
154}
155
156#ifdef HAVE_READLINK
157/* similar to readlink, but dont' mess up absolute pathnames */
158static int my_readlink(const char* name, char* buf, size_t bufsize)
159{
160  char buf2[MAXPATHLEN];
161  int ret;
162
163  if ((ret = readlink(name, buf2, bufsize)) > 0)
164  {
165    buf2[ret] = 0;
166    if (*name == '/' && *buf2 != '/')
167    {
168      char* last = strrchr(name, '/');
169      int i = 0;
170      while (&(name[i]) != last)
171      {
172        buf[i] = name[i];
173        i++;
174      }
175      buf[i] = '/';
176      i++;
177      strcpy(&(buf[i]), buf2);
178      return i + ret;
179    }
180    else
181    {
182      strcpy(buf, buf2);
183    }
184  }
185  return ret;
186}
187
188#define MAX_LINK_LEVEL 10
189/* similar to readlink (cf. man readlink), except that symbolic links are
190   followed up to MAX_LINK_LEVEL
191*/
192static int full_readlink(const char* name, char* buf, size_t bufsize)
193{
194  int ret;
195
196  if ((ret=my_readlink(name, buf, bufsize)) > 0)
197  {
198    char buf2[MAXPATHLEN];
199    int ret2, i = 0;
200
201    do
202    {
203      buf[ret] = '\0';
204      if ((ret2 = my_readlink(buf, buf2, MAXPATHLEN)) > 0)
205      {
206        i++;
207        buf2[ret2] = '\0';
208        strcpy(buf, buf2);
209        ret = ret2;
210      }
211      else
212      {
213        return ret;
214      }
215    }
216    while (i<MAX_LINK_LEVEL);
217  }
218  return -1;
219}
220
221#ifdef WINNT
222char * _omFindExec (const char *name, char* exec);
223/* for windows, serch first for .exe */
224char* omFindExec(const char *name, char* exec)
225{
226
227  if (strstr(name, ".exe") == NULL)
228  {
229    char buf[MAXPATHLEN];
230    char* ret;
231    strcpy(buf, name);
232    strcat(buf, ".exe");
233    ret = _omFindExec(buf, exec);
234    if (ret != NULL) return ret;
235  }
236  return _omFindExec(name, exec);
237}
238#else
239#define _omFindExec omFindExec
240#endif
241
242char * _omFindExec (const char *name, char* exec)
243{
244  char * link = omFindExec_link(name, exec);
245  char buf[MAXPATHLEN];
246  int ret;
247
248  if (link == NULL && (ret=full_readlink(name, buf, MAXPATHLEN)) > 0)
249  {
250    buf[ret] ='\0';
251    link = omFindExec_link(buf, exec);
252  }
253  if (link != NULL && (ret=full_readlink(link, buf, MAXPATHLEN)) > 0)
254  {
255    char *p = strrchr(link, '/');
256
257
258    if(p!=NULL) *(p+1)='\0';
259    buf[ret]='\0';
260
261    if (buf[0] != '/')
262    {
263      strcpy(exec, link);
264      strcat(exec, buf);
265    }
266    else
267    {
268      strcpy(exec, buf);
269    }
270
271    return exec;
272  }
273  return link;
274}
275#endif /* HAVE_READLINK */
276
277#else
278
279char* omFindExec (const char *name, char* exec)
280{
281  return name;
282}
283
284#endif /* ! defined(__MWERKS__) && defined(HAVE_UNISTD_H) && defined(STDC_HEADERS) */
Note: See TracBrowser for help on using the repository browser.