2 #define _POSIX_C_SOURCE 199309L
16 static char * ReadAll (FILE * f
, int offset
)
26 while (iRead
< sizeof buf
)
28 nRead
= fread (buf
+iRead
, 1, (sizeof buf
)-iRead
, f
) ;
29 if (nRead
<= 0) break ;
35 assert (iRead
== sizeof buf
) ;
36 ret
= ReadAll (f
, offset
+iRead
) ;
41 error ("read file: %s", strerror (errno
)) ;
46 ret
= malloc (offset
+iRead
+1) ;
47 if (ret
== NULL
) error ("failed to allocate memory") ;
48 ret
[offset
+iRead
] = EOS
;
50 memcpy (ret
+offset
, buf
, iRead
) ;
55 extern char * File_ReadAll (FILE * f
)
58 return ReadAll (f
, 0) ;
61 static const char * getHome (void)
63 static char homeDir
[80] = "" ;
64 static int initialized
= 0 ;
68 env
= getenv ("HOME") ;
69 if (env
!= NULL
&& env
[0] != EOS
)
71 sprintf (homeDir
, "%.*s", (int)(sizeof homeDir
)-1, env
) ;
75 return homeDir
[0] != EOS
? homeDir
: NULL
;
78 extern bool File_FindInPath (char * out
, int outSz
,
79 const char * path
, const char * basename
)
81 char name
[FILENAME_MAX
] ;
84 assert (path
!= NULL
) ;
85 assert (basename
!= NULL
) ;
86 assert (out
!= NULL
) ;
89 if (access (basename
, F_OK
) == 0)
91 sprintf (out
, "%.*s", outSz
-1, basename
) ;
95 /* relative to home directory */
96 if (strncmp (basename
, "~/", 2) == 0 && getHome () != NULL
)
98 sprintf (name
, "%s%s", getHome (), basename
+1) ;
99 if (access (name
, F_OK
) == 0)
101 sprintf (out
, "%.*s", outSz
-1, name
) ;
110 /* forbid relative to PATH just like shell */
111 /* NB: absolute non-existent files also drop here */
112 if (strchr (basename
, '/') != NULL
)
120 len
= strcspn (path
, ":") ;
122 if (strncmp (path
, "~/", 2) == 0)
124 sprintf (name
, "%s%.*s/%s",
125 getHome (), len
-1, path
+1, basename
) ;
129 sprintf (name
, "%.*s/%s", len
, path
, basename
) ;
132 if (access (name
, F_OK
) == 0)
134 sprintf (out
, "%.*s", outSz
-1, name
) ;
139 while (*path
== ':') path
++ ;
146 extern char * File_ReadOutputFromCommand (const char * cmd
)
151 if ((out
= popen (cmd
, "r")) == NULL
)
153 error ("when calling command: %s, error: ",
154 cmd
, strerror (errno
)) ;
159 ret
= File_ReadAll (out
) ;
162 /* if return value is correct, remove trailing whitespace */
165 char *lastNotWhite
, *cursor
;
168 cursor
= lastNotWhite
= ret
;
170 while ((c
= *cursor
++) != EOS
)
172 if (strchr (" \t\n", c
) == NULL
)
174 lastNotWhite
= cursor
;
178 *lastNotWhite
= EOS
;