3 Copyright (C) 2002 Free Software Foundation, Inc.
5 Author: Richard Frith-Macdonald <richard@brainstorm.co.uk>
8 This file is part of the GNUstep Makefile Package.
10 This library is free software; you can redistribute it and/or
11 modify it under the terms of the GNU General Public License
12 as published by the Free Software Foundation; either version 2
13 of the License, or (at your option) any later version.
15 You should have received a copy of the GNU General Public
16 License along with this library; see the file COPYING.LIB.
17 If not, write to the Free Software Foundation,
18 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
34 #if defined(__MINGW__)
39 # include <sys/types.h>
58 #define lowlevelstringify(X) #X
59 #define stringify(X) lowlevelstringify(X)
64 * This tool is intended to produce a definitive form of the
65 * user specific root directories for a GNUstep user. It must
66 * remain consistent with the code in the GNUstep base library
67 * which provides path information for all GNUstep applications.
70 * How to run this tool ...
72 * 1. With no arguments ... the tool should print the home directory of
73 * the current user to stdout.
75 * 2. With a 'user' argument ... the tool should print the
76 * GNUSTEP_USER_ROOT directory to stdout.
78 * 3. With a 'defaults' argument ... the tool should print the
79 * GNUSTEP_DEFAULTS_ROOT directory to stdout.
81 * Any other arguments will be ignored.
82 * On success the tool will terminate with an exit status of zero
83 * On failure, the tool will terminate with an exit status of one
84 * and will print an error message to stderr.
87 /* NOTE FOR DEVELOPERS.
88 * If you change the behavior of this method you must also change
89 * NSUser.m in the base library package to match.
91 int main (int argc, char** argv)
97 enum { NONE, DEFS, USER } type = NONE;
98 #if defined(__MINGW__)
108 if (strcmp(argv[1], "defaults") == 0)
112 else if (strcmp(argv[1], "user") == 0)
120 #if defined(__WIN32__)
121 /* The GetUserName function returns the current user name */
124 len0 = GetEnvironmentVariable("LOGNAME", buf0, 1024);
125 if (len0 > 0 && len0 < 1024)
128 loginName[len0] = '\0';
130 else if (GetUserName(buf0, &n))
140 #endif /* HAVE_GETEUID */
141 struct passwd *pwent = getpwuid (uid);
142 loginName = pwent->pw_name;
143 #endif /* HAVE_GETPWUID */
147 fprintf(stderr, "Unable to determine current user name.\n");
152 #if !defined(__MINGW__)
153 pw = getpwnam (loginName);
156 fprintf(stderr, "Unable to locate home directory for '%s'\n", loginName);
159 strncpy(home, pw->pw_dir, sizeof(home));
163 * The environment variable HOMEPATH holds the home directory
164 * for the user on Windows NT; Win95 has no concept of home.
165 * For OPENSTEP compatibility (and because USERPROFILE is usually
166 * unusable because it contains spaces), we use HOMEPATH in
167 * preference to USERPROFILE.
169 len0 = GetEnvironmentVariable("HOMEPATH", buf0, 1024);
170 if (len0 > 0 && len0 < 1024)
174 * Only use HOMEDRIVE is HOMEPATH does not already contain drive.
176 if (len0 < 2 || buf0[1] != ':')
178 len1 = GetEnvironmentVariable("HOMEDRIVE", buf1, 128);
179 if (len1 > 0 && len1 < 128)
182 sprintf(home, "%s%s", buf1, buf0);
186 sprintf(home, "C:%s", buf0);
192 /* The environment variable USERPROFILE may hold the home directory
193 for the user on modern versions of windoze. */
194 len0 = GetEnvironmentVariable("USERPROFILE", buf0, 1024);
195 if (len0 > 0 && len0 < 1024)
205 for (i = 0; i < strlen(home); i++)
207 if (isspace((unsigned int)home[i]))
210 * GNU make doesn't handle spaces in paths.
211 * Broken, wrong and totally unfixable.
213 fprintf(stderr, "Make cannot handle spaces in paths so the " \
214 "home directory '%s' may cause problems!\n", home);
233 #if defined (__MINGW32__)
234 len0 = GetEnvironmentVariable("GNUSTEP_SYSTEM_ROOT", buf0, sizeof(buf0));
241 const char *gnustep_system_root = (const char*)getenv("GNUSTEP_SYSTEM_ROOT");
243 if (gnustep_system_root != 0)
245 strcpy(path, gnustep_system_root);
249 /* On my machine the strcpy was segfaulting when
250 * gnustep_system_root == 0. */
256 strcat(path, ".GNUsteprc");
257 fptr = fopen(path, "r");
260 while (fgets(buf0, sizeof(buf0), fptr) != 0)
262 char *pos = strchr(buf0, '=');
270 while (isspace((int)*key))
272 while (strlen(key) > 0 && isspace((int)key[strlen(key)-1]))
273 key[strlen(key)-1] = '\0';
274 while (isspace(*val))
276 while (strlen(val) > 0 && isspace((int)val[strlen(val)-1]))
277 val[strlen(val)-1] = '\0';
281 while (isspace((int)*key))
283 while (strlen(key) > 0 && isspace((int)key[strlen(key)-1]))
284 key[strlen(key)-1] = '\0';
288 if (strcmp(key, "GNUSTEP_USER_ROOT") == 0)
292 user = malloc(strlen(val) + strlen(home));
294 strcat(user, &val[1]);
298 user = malloc(strlen(val) + 1);
302 else if (strcmp(key, "GNUSTEP_DEFAULTS_ROOT") == 0)
306 defs = malloc(strlen(val) + strlen(home));
308 strcat(defs, &val[1]);
312 defs = malloc(strlen(val) + 1);
316 else if (strcmp(key, "FORCE_USER_ROOT") == 0)
320 else if (strcmp(key, "FORCE_DEFAULTS_ROOT") == 0)
328 if (*user == '\0' || forceU == 0 || *defs == '\0' || forceD == 0)
332 strcat(path, ".GNUsteprc");
333 fptr = fopen(path, "r");
336 while (fgets(buf0, sizeof(buf0), fptr) != 0)
338 char *pos = strchr(buf0, '=');
346 while (isspace((int)*key))
348 while (strlen(key) > 0
349 && isspace((int)key[strlen(key)-1]))
350 key[strlen(key)-1] = '\0';
351 while (isspace((int)*val))
353 while (strlen(val) > 0
354 && isspace((int)val[strlen(val)-1]))
355 val[strlen(val)-1] = '\0';
357 if (strcmp(key, "GNUSTEP_USER_ROOT") == 0)
359 if (*user == '\0' || forceU == 0)
363 user = malloc(strlen(val) + strlen(home));
365 strcat(user, &val[1]);
369 user = malloc(strlen(val) + 1);
374 else if (strcmp(key, "GNUSTEP_DEFAULTS_ROOT") == 0)
376 if (*defs == '\0' || forceD == 0)
380 defs = malloc(strlen(val) + strlen(home));
382 strcat(defs, &val[1]);
386 defs = malloc(strlen(val) + 1);
414 strcat(path, "GNUstep");
417 #if defined(__MINGW__)
419 * We always want to use unix style paths.
421 if (strlen(path) > 1 && path[1] == ':')
431 if (*ptr == '/' && ptr > path && ptr[-1] == '/')
433 memmove(ptr, &ptr[1], strlen(ptr)+1);
440 if (path[2] == '/' || path[2] == '\0')
446 memmove(&path[1], path, strlen(path)+1);