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