applied patch to rename .AppInfo directory
[wmaker-crm.git] / util / wmsetup.c
blobb01e6f0e846e7b93d8bb8abee0e18db54a3e9436
1 /* wmsetup.c- create wmaker config file dir structure and copy default
2 * config files.
4 * Copyright (c) 2000-2003 Alfredo K. Kojima
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 #if 1
21 int
22 main()
25 #else
26 #define PROG_VERSION "wmsetup 0.0 (Window Maker)"
28 #include <stdlib.h>
29 #include <stdio.h>
30 #include <unistd.h>
32 #include <sys/stat.h>
33 #include <sys/types.h>
34 #include <sys/stat.h>
36 #include <WINGs/WINGs.h>
38 #include "../src/config.h"
42 char *RequiredDirectories[] = {
43 "/Defaults",
44 "/Library",
45 "/Library/Icons",
46 "/Library/WindowMaker",
47 "/Library/WindowMaker/Backgrounds",
48 "/Library/WindowMaker/IconSets",
49 "/Library/WindowMaker/Pixmaps",
50 "/Library/WindowMaker/CachedPixmaps",
51 "/Library/WindowMaker/SoundSets",
52 "/Library/WindowMaker/Sounds",
53 "/Library/WindowMaker/Styles",
54 "/Library/WindowMaker/Themes",
55 "/Library/WindowMaker/WPrefs",
56 NULL
60 char *RequiredFiles[] = {
61 "/Defaults/WindowMaker",
62 "/Defaults/WMWindowAttributes",
63 NULL
68 WMScreen *scr;
72 #define wlog wwarning
75 #if 0
76 void
77 wlog(const char *msg, ...)
79 va_list args;
80 char buf[MAXLINE];
82 va_start(args, msg);
84 vsprintf(buf, msg, args);
85 puts(buf);
87 va_end(args);
89 #endif
92 void
93 alert(const char *msg, ...)
95 va_list args;
96 char buffer[2048];
98 va_start(args, msg);
100 vsprintf(buf, msg, args);
102 WMRunAlertPanel(scr, NULL, _("Error"),
103 buffer, _("OK"), NULL, NULL);
105 va_end(args);
109 Bool
110 ask(char *title, char *yes, char *no, const char *msg, ...)
112 va_list args;
113 char buffer[2048];
115 va_start(args, msg);
117 vsprintf(buf, msg, args);
119 WMRunAlertPanel(scr, NULL, title,
120 buffer, yes, no, NULL);
122 va_end(args);
126 char*
127 renameName(char *path)
129 char *buf = wmalloc(strlen(path)+8);
130 int i;
132 sprintf(buf, "%s~", path);
134 if (access(buf, F_OK) < 0) {
135 return buf;
138 for (i = 0; i < 10; i++) {
139 sprintf(buf, "%s~%i", path, i);
141 if (access(buf, F_OK) < 0) {
142 return buf;
146 sprintf(buf, "%s~", path);
148 return buf;
153 void
154 showFileError(int error, Bool directory, char *path)
156 switch (error) {
157 case EACCESS:
158 if (directory) {
159 alert(_("The directory %s needs to be fully accessible, but is\n"
160 "not. Make sure all of it's parent directories have\n"
161 "read and execute permissions set."), path);
162 } else {
163 alert(_("The file %s needs to be fully accessible, but is not.\n"
164 "Make sure it has read and write permissions set and\n"
165 "all of it's parent directories have read and execute\n"
166 "permissions."), path);
168 break;
170 case EROFS:
171 alert(_("The %s %s is in a read-only file system, but it needs to be\n"
172 "writable. Start wmaker with the --static command line option."),
173 directory ? _("directory") : _("file"), path);
174 break;
176 default:
177 alert(_("An error occurred while accessing the %s %s. Please make sure\n"
178 "it exists and is accessible.\n%s"),
179 directory ? _("directory") : _("file"), path,
180 wstrerror(error));
181 break;
187 Bool
188 checkDir(char *path, Bool fatal)
190 if (access(path, F_OK) < 0) {
191 if (mkdir(path, 0775) < 0) {
192 alert(_("could not create directory %s\n%s"), path,
193 wstrerror(errno));
194 return False;
195 } else {
196 wlog(_("created directory %s"), path);
200 if (access(path, R_OK|W_OK|X_OK) == 0) {
201 return True;
203 wsyserror("bad access to directory %s", path);
205 if (!fatal) {
206 struct stat buf;
208 if (stat(path, &buf) < 0) {
209 alert(_("The directory %s could not be stat()ed. Please make sure\n"
210 "it exists and is accessible."), path);
211 return False;
214 if (!S_ISDIR(buf)) {
215 char *newName = renameName(path);
217 if (ask(_("Rename"), _("OK"), _("Cancel"),
218 _("A directory named %s needs to be created but a file with\n"
219 "the same name already exists. The file will be renamed to\n"
220 "%s and the directory will be created."),
221 path, newName)) {
223 if (rename(path, newName) < 0) {
224 alert(_("Could not rename %s to %s:%s"),
225 path, newName, wstrerror(errno));
228 wfree(newName);
230 return False;
232 if (!(buf.st_mode & S_IRWXU)) {
233 if (chmod(path, (buf.st_mode & 00077)|7) < 0) {
234 return False;
238 return checkDir(path, True);
241 showFileError(errno, True, path);
243 return False;
249 Bool
250 checkFile(char *path)
252 if (access(path, F_OK|R_OK|W_OK) == 0) {
253 return True;
256 showFileError(errno, False, path);
258 return False;
263 Bool
264 checkCurrentSetup(char *home)
266 char path[1024];
267 char *p;
269 if (!checkDir(home, False)) {
270 wlog("couldnt make directory %s", home);
271 return False;
274 for (p = RequiredDirectories; p != NULL; p++) {
275 sprintf(path, "%s%s", home, p);
276 if (!checkDir(p, False)) {
277 wlog("couldnt make directory %s", p);
278 return False;
282 for (p = RequiredFiles; p != NULL; p++) {
283 sprintf(path, "%s%s", home, p);
284 if (!checkFile(p, False)) {
285 return False;
289 return True;
294 Bool
295 copyAllFiles(char *gsdir)
297 FILE *f;
298 char path[2048];
299 char file[256];
300 char target[2048];
302 /* copy misc data files */
304 sprintf(path, "%s/USER_FILES", DATADIR);
306 f = fopen(path, "rb");
307 while (!feof(f)) {
308 if (!fgets(file, 255, f)) {
309 break;
311 sprintf(path, "%s/%s", DATADIR, file);
312 sprintf(target, "%s/Library/WindowMaker/%s", gsdir, file);
313 if (!copyFile(path, target)) {
314 return False;
317 fclose(f);
319 /* copy auto{start,finish} scripts */
322 /* select and copy menu */
325 /* copy Defaults stuff */
327 sprintf(path, "%s/USER_FILES", ETCDIR);
329 f = fopen(path, "rb");
330 while (!feof(f)) {
331 if (!fgets(path, 255, f)) {
332 break;
334 sprintf(path, "%s/%s", ETCDIR, file);
335 sprintf(target, "%s/Defaults/%s", gsdir, file);
336 if (!copyFile(path, target)) {
337 return False;
340 fclose(f);
342 /* setup .xinitrc */
348 void
349 showFinishSplash(char *gsdir)
351 #if 0
352 WMWindow *win;
354 win = WMCreateWindow(scr, "finished");
355 #endif
360 main(int argc, char **argv)
362 Display *dpy;
363 char *gsdir;
364 int i;
366 for (i=1; i<argc; i++) {
367 if (strcmp(argv[i], "-display")==0) {
368 i++;
369 if (i>=argc) {
370 wwarning(_("too few arguments for %s"), argv[i-1]);
371 exit(0);
373 DisplayName = argv[i];
374 } else if (strcmp(argv[i], "-version")==0
375 || strcmp(argv[i], "--version")==0) {
376 puts(PROG_VERSION);
377 exit(0);
381 WMInitializeApplication("WMSetup", &argc, argv);
383 dpy = XOpenDisplay("");
384 if (!dpy) {
385 printf("could not open display\n");
386 exit(1);
389 scr = WMCreateScreen(dpy, DefaultScreen(dpy));
391 gsdir = wusergnusteppath();
393 /* check directory structure and copy files */
394 if (access(gsdir, F_OK) != 0) {
395 if (!ask(_("Window Maker"), _("OK"), _("Cancel"),
396 _("Window Maker will create a directory named %s, where\n"
397 "it will store it's configuration files and other data."),
398 gsdir)) {
399 alert(_("Window Maker will be started in 'static' mode, where\n"
400 "it will use default configuration and will not write\n"
401 "any information to disk."));
402 return 1;
406 if (checkCurrentSetup(gsdir)) {
407 printf(_("%s: wmaker configuration files already installed\n"),
408 argv[0]);
409 return 0;
412 if (!copyAllFiles(gsdir)) {
413 alert(_("An error occurred while doing user specific setup of\n"
414 "Window Maker. It will be started in 'static' mode, where\n"
415 "the default configuration will be used and it will not write\n"
416 "any information to disk."));
417 return 1;
420 showFinishSplash(gsdir);
422 return 0;
424 #endif