main.c revision 76015
1#ifndef lint 2static const char rcsid[] = 3 "$FreeBSD: head/usr.sbin/pkg_install/add/main.c 76015 2001-04-26 06:48:59Z ache $"; 4#endif 5 6/* 7 * 8 * FreeBSD install - a package for the installation and maintainance 9 * of non-core utilities. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 20 * Jordan K. Hubbard 21 * 18 July 1993 22 * 23 * This is the add module. 24 * 25 */ 26 27#include <err.h> 28#include <sys/param.h> 29#include <sys/utsname.h> 30#include "lib.h" 31#include "add.h" 32 33static char Options[] = "hvIRfnrp:SMt:"; 34 35char *Prefix = NULL; 36Boolean NoInstall = FALSE; 37Boolean NoRecord = FALSE; 38Boolean Remote = FALSE; 39 40char *Mode = NULL; 41char *Owner = NULL; 42char *Group = NULL; 43char *PkgName = NULL; 44char *Directory = NULL; 45char FirstPen[FILENAME_MAX]; 46add_mode_t AddMode = NORMAL; 47 48#define MAX_PKGS 20 49char pkgnames[MAX_PKGS][MAXPATHLEN]; 50char *pkgs[MAX_PKGS]; 51 52static char *getpackagesite(void); 53int getosreldate(void); 54 55static void usage __P((void)); 56 57int 58main(int argc, char **argv) 59{ 60 int ch, err; 61 char **start; 62 char *cp; 63 64 char *remotepkg = NULL, *ptr; 65 static char temppackageroot[MAXPATHLEN]; 66 67 start = argv; 68 while ((ch = getopt(argc, argv, Options)) != -1) { 69 switch(ch) { 70 case 'v': 71 Verbose = TRUE; 72 break; 73 74 case 'p': 75 Prefix = optarg; 76 break; 77 78 case 'I': 79 NoInstall = TRUE; 80 break; 81 82 case 'R': 83 NoRecord = TRUE; 84 break; 85 86 case 'f': 87 Force = TRUE; 88 break; 89 90 case 'n': 91 Fake = TRUE; 92 Verbose = TRUE; 93 break; 94 95 case 'r': 96 Remote = TRUE; 97 break; 98 99 case 't': 100 strcpy(FirstPen, optarg); 101 break; 102 103 case 'S': 104 AddMode = SLAVE; 105 break; 106 107 case 'M': 108 AddMode = MASTER; 109 break; 110 111 case 'h': 112 case '?': 113 default: 114 usage(); 115 break; 116 } 117 } 118 argc -= optind; 119 argv += optind; 120 121 if (argc > MAX_PKGS) { 122 warnx("too many packages (max %d)", MAX_PKGS); 123 return(1); 124 } 125 126 if (AddMode != SLAVE) { 127 for (ch = 0; ch < MAX_PKGS; pkgs[ch++] = NULL) ; 128 129 /* Get all the remaining package names, if any */ 130 for (ch = 0; *argv; ch++, argv++) { 131 if (Remote) { 132 strcpy(temppackageroot, getpackagesite()); 133 remotepkg = strcat(temppackageroot, *argv); 134 if (!((ptr = strrchr(remotepkg, '.')) && ptr[1] == 't' && 135 ptr[2] == 'g' && ptr[3] == 'z' && !ptr[4])) 136 strcat(remotepkg, ".tgz"); 137 } 138 if (!strcmp(*argv, "-")) /* stdin? */ 139 pkgs[ch] = "-"; 140 else if (isURL(*argv)) /* preserve URLs */ 141 pkgs[ch] = strcpy(pkgnames[ch], *argv); 142 else if ((Remote) && isURL(remotepkg)) 143 pkgs[ch] = strcpy(pkgnames[ch], remotepkg); 144 else { /* expand all pathnames to fullnames */ 145 if (fexists(*argv)) /* refers to a file directly */ 146 pkgs[ch] = realpath(*argv, pkgnames[ch]); 147 else { /* look for the file in the expected places */ 148 if (!(cp = fileFindByPath(NULL, *argv))) 149 warnx("can't find package '%s'", *argv); 150 else 151 pkgs[ch] = strcpy(pkgnames[ch], cp); 152 } 153 } 154 } 155 } 156 /* If no packages, yelp */ 157 else if (!ch) { 158 warnx("missing package name(s)"); 159 usage(); 160 } 161 else if (ch > 1 && AddMode == MASTER) { 162 warnx("only one package name may be specified with master mode"); 163 usage(); 164 } 165 /* Make sure the sub-execs we invoke get found */ 166 setenv("PATH", 167 "/sbin:/usr/sbin:/bin:/usr/bin:/usr/local/bin:/usr/X11R6/bin", 168 1); 169 170 /* Set a reasonable umask */ 171 umask(022); 172 173 if ((err = pkg_perform(pkgs)) != 0) { 174 if (Verbose) 175 warnx("%d package addition(s) failed", err); 176 return err; 177 } 178 else 179 return 0; 180} 181 182static char * 183getpackagesite(void) 184{ 185 int reldate; 186 static char sitepath[MAXPATHLEN]; 187 struct utsname u; 188 189 if (getenv("PACKAGESITE")) { 190 strcpy(sitepath, getenv("PACKAGESITE")); 191 return sitepath; 192 } 193 194 if (getenv("PACKAGEMIRROR")) 195 strcpy(sitepath, getenv("PACKAGEMIRROR")); 196 else 197 strcpy(sitepath, "ftp://ftp.FreeBSD.org"); 198 199 if (getenv("PACKAGEROOT")) 200 strcpy(sitepath, getenv("PACKAGEMIRRORROOT")); 201 else 202 strcat(sitepath, "/pub"); 203 204 strcat(sitepath, "/FreeBSD/ports/"); 205 206 uname(&u); 207 strcat(sitepath, u.machine); 208 209 reldate = getosreldate(); 210 if (reldate == 410000) 211 strcat(sitepath, "/packages-4.1-release"); 212 else if (reldate == 420000) 213 strcat(sitepath, "/packages-4.2-release"); 214 else if (reldate == 430000) 215 strcat(sitepath, "/packages-4.3-release"); 216 else if (reldate == 440000) 217 strcat(sitepath, "/packages-4.4-release"); 218 else if (reldate == 450000) 219 strcat(sitepath, "/packages-4.5-release"); 220 else if (300000 <= reldate && reldate <= 399000) 221 strcat(sitepath, "/packages-3-stable"); 222 else if (400000 <= reldate && reldate <= 499000) 223 strcat(sitepath, "/packages-4-stable"); 224 else if (510000 <= reldate && reldate <= 599000) /* get real values!! */ 225 strcat(sitepath, "/packages-5-stable"); 226 else 227 strcat(sitepath, "/packages-current"); 228 229 strcat(sitepath, "/Latest/"); 230 231 return sitepath; 232 233} 234 235static void 236usage() 237{ 238 fprintf(stderr, "%s\n%s\n", 239 "usage: pkg_add [-vInrfRMS] [-t template] [-p prefix]", 240 " pkg-name [pkg-name ...]"); 241 exit(1); 242} 243