perform.c revision 8084
1#ifndef lint
2static const char *rcsid = "$Id: perform.c,v 1.24 1995/04/26 12:37:46 jkh Exp $";
3#endif
4
5/*
6 * FreeBSD install - a package for the installation and maintainance
7 * of non-core utilities.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 *    notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 *    notice, this list of conditions and the following disclaimer in the
16 *    documentation and/or other materials provided with the distribution.
17 *
18 * Jordan K. Hubbard
19 * 18 July 1993
20 *
21 * This is the main body of the create module.
22 *
23 */
24
25#include "lib.h"
26#include "create.h"
27
28#include <signal.h>
29#include <sys/syslimits.h>
30
31static void sanity_check(void);
32static void make_dist(char *, char *, char *, Package *);
33
34int
35pkg_perform(char **pkgs)
36{
37    char *pkg = *pkgs;		/* Only one arg to create */
38    char *home, *cp;
39    FILE *pkg_in, *fp;
40    Package plist;
41    char *suffix;  /* What we tack on to the end of the finished package */
42
43    /* Preliminary setup */
44    sanity_check();
45    if (Verbose && !PlistOnly)
46	printf("Creating package %s\n", pkg);
47    get_dash_string(&Comment);
48    get_dash_string(&Desc);
49    if (!strcmp(Contents, "-"))
50	pkg_in = stdin;
51    else {
52	pkg_in = fopen(Contents, "r");
53	if (!pkg_in)
54	    barf("Unable to open contents file '%s' for input.", Contents);
55    }
56    plist.head = plist.tail = NULL;
57
58    /* Break the package name into base and desired suffix (if any) */
59    if ((cp = rindex(pkg, '.')) != NULL) {
60	suffix = cp + 1;
61	*cp = '\0';
62    }
63    else
64	suffix = "tgz";
65
66    /* Stick the dependencies, if any, at the top */
67    if (Pkgdeps) {
68	if (Verbose && !PlistOnly)
69	    printf("Registering depends:");
70	while (Pkgdeps) {
71	    cp = strsep(&Pkgdeps, " \t\n");
72	    if (*cp) {
73		add_plist(&plist, PLIST_PKGDEP, cp);
74		if (Verbose && !PlistOnly)
75		    printf(" %s", cp);
76	    }
77	}
78	if (Verbose && !PlistOnly)
79	    printf(".\n");
80    }
81    /* Slurp in the packing list */
82    read_plist(&plist, pkg_in);
83
84    /* Prefix should override the packing list */
85    if (Prefix) {
86	delete_plist(&plist, FALSE, PLIST_CWD, NULL);
87	add_plist_top(&plist, PLIST_CWD, Prefix);
88    }
89    /*
90     * Run down the list and see if we've named it, if not stick in a name
91     * at the top.
92     */
93    if (find_plist(&plist, PLIST_NAME) == NULL)
94	add_plist_top(&plist, PLIST_NAME, basename_of(pkg));
95
96    /*
97     * We're just here for to dump out a revised plist for the FreeBSD ports
98     * hack.  It's not a real create in progress.
99     */
100    if (PlistOnly) {
101	write_plist(&plist, stdout);
102	exit(0);
103    }
104
105    /* Make a directory to stomp around in */
106    home = make_playpen(PlayPen, 0);
107    signal(SIGINT, cleanup);
108    signal(SIGHUP, cleanup);
109
110    /* Make first "real contents" pass over it */
111    check_list(home, &plist);
112    (void) umask(022);	/* make sure gen'ed directories, files don't have
113			   group or other write bits. */
114    /* copy_plist(home, &plist); */
115    /* mark_plist(&plist); */
116
117    /* Now put the release specific items in */
118    add_plist(&plist, PLIST_CWD, ".");
119    write_file(COMMENT_FNAME, Comment);
120    add_plist(&plist, PLIST_IGNORE, NULL);
121    add_plist(&plist, PLIST_FILE, COMMENT_FNAME);
122    write_file(DESC_FNAME, Desc);
123    add_plist(&plist, PLIST_IGNORE, NULL);
124    add_plist(&plist, PLIST_FILE, DESC_FNAME);
125
126    if (Install) {
127	copy_file(home, Install, INSTALL_FNAME);
128	add_plist(&plist, PLIST_IGNORE, NULL);
129	add_plist(&plist, PLIST_FILE, INSTALL_FNAME);
130    }
131    if (DeInstall) {
132	copy_file(home, DeInstall, DEINSTALL_FNAME);
133	add_plist(&plist, PLIST_IGNORE, NULL);
134	add_plist(&plist, PLIST_FILE, DEINSTALL_FNAME);
135    }
136    if (Require) {
137	copy_file(home, Require, REQUIRE_FNAME);
138	add_plist(&plist, PLIST_IGNORE, NULL);
139	add_plist(&plist, PLIST_FILE, REQUIRE_FNAME);
140    }
141    if (Display) {
142	copy_file(home, Display, DISPLAY_FNAME);
143	add_plist(&plist, PLIST_IGNORE, NULL);
144	add_plist(&plist, PLIST_FILE, DISPLAY_FNAME);
145	add_plist(&plist, PLIST_DISPLAY, DISPLAY_FNAME);
146    }
147    if (Mtree) {
148	copy_file(home, Mtree, MTREE_FNAME);
149	add_plist(&plist, PLIST_IGNORE, NULL);
150	add_plist(&plist, PLIST_FILE, MTREE_FNAME);
151	add_plist(&plist, PLIST_MTREE, MTREE_FNAME);
152    }
153
154    /* Run through the list again, picking up extra "local" items */
155    /* check_list(".", &plist); */
156    /* copy_plist(".", &plist); */
157    /* mark_plist(&plist); */
158
159    /* Finally, write out the packing list */
160    fp = fopen(CONTENTS_FNAME, "w");
161    if (!fp)
162	barf("Can't open file %s for writing.", CONTENTS_FNAME);
163    write_plist(&plist, fp);
164    if (fclose(fp))
165	barf("Error while closing %s.", CONTENTS_FNAME);
166
167    /* And stick it into a tar ball */
168    make_dist(home, pkg, suffix, &plist);
169
170    /* Cleanup */
171    free(Comment);
172    free(Desc);
173    free_plist(&plist);
174    cleanup(0);
175    return TRUE;	/* Success */
176}
177
178static void
179make_dist(char *home, char *pkg, char *suffix, Package *plist)
180{
181    char tball[FILENAME_MAX];
182    char *cmd;
183    int ret, max, len;
184    PackingList p;
185
186    max = sysconf(_SC_ARG_MAX);
187    cmd = alloca(max);
188    if (!cmd)
189	barf("Couldn't allocate temporary storage for dist name!");
190    strcpy(cmd, "tar ");
191    if (*pkg == '/')
192	snprintf(tball, max, "%s.%s", pkg, suffix);
193    else
194	snprintf(tball, max, "%s/%s.%s", home, pkg, suffix);
195    if (index(suffix, 'z'))	/* Compress/gzip? */
196	strncat(cmd, "-z", max - strlen(cmd));
197    if (Dereference)
198	strncat(cmd, "h", max - strlen(cmd));
199    if (Verbose)
200	printf("Creating gzip'd tar ball in '%s'\n", tball);
201    strncat(cmd, "cf ", max - strlen(cmd));
202    strncat(cmd, tball, max - strlen(cmd));
203    if (ExcludeFrom) {
204	len = strlen(cmd);
205	snprintf(&cmd[len], max -= len, " -X %s", ExcludeFrom);
206    }
207    len = strlen(cmd);
208    snprintf(&cmd[len], max -= len, " %s %s %s", CONTENTS_FNAME,
209	     COMMENT_FNAME, DESC_FNAME);
210    if (Install) {
211	len = strlen(cmd);
212	snprintf(&cmd[len], max -= len, " %s", INSTALL_FNAME);
213    }
214    if (DeInstall) {
215	len = strlen(cmd);
216	snprintf(&cmd[len], max -= len, " %s", DEINSTALL_FNAME);
217    }
218    if (Require) {
219	len = strlen(cmd);
220	snprintf(&cmd[len], max -= len, " %s", REQUIRE_FNAME);
221    }
222    if (Display) {
223	len = strlen(cmd);
224	snprintf(&cmd[len], max -= len, " %s", DISPLAY_FNAME);
225    }
226    if (Mtree) {
227	len = strlen(cmd);
228	snprintf(&cmd[len], max -= len, " %s", MTREE_FNAME);
229    }
230    for (p = plist->head; p; p = p->next) {
231	if (p->type == PLIST_FILE) {
232	    len = strlen(cmd);
233	    snprintf(&cmd[len], max -= len, " %s", p->name);
234	}
235	else if (p->type == PLIST_CWD) {
236	    len = strlen(cmd);
237	    snprintf(&cmd[len], max -= len, " -C %s", p->name);
238	}
239	else if (p->type == PLIST_SRC) {
240	    len = strlen(cmd);
241	    snprintf(&cmd[len], max -= len, " -C %s", p->name);
242	}
243	else if (p->type == PLIST_IGNORE)
244	     p = p->next;
245    }
246    ret = vsystem(cmd);
247    if (ret)
248	barf("tar command `%s' failed with code %d", cmd, ret);
249}
250
251static void
252sanity_check()
253{
254    if (!Comment)
255	barf("Required package comment string is missing (-c comment).");
256    if (!Desc)
257	barf("Required package description string is missing (-d desc).");
258    if (!Contents)
259	barf("Required package contents list is missing (-f [-]file).");
260}
261
262
263/* Clean up those things that would otherwise hang around */
264void
265cleanup(int sig)
266{
267    leave_playpen();
268}
269