main.c revision 75981
1#ifndef lint 2static const char rcsid[] = 3 "$FreeBSD: head/usr.sbin/pkg_install/add/main.c 75981 2001-04-25 19:11:09Z obrien $"; 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", "/sbin:/usr/sbin:/bin:/usr/bin:/usr/local/bin:/usr/X11R6/bin" 167 1); 168 169 /* Set a reasonable umask */ 170 umask(022); 171 172 if ((err = pkg_perform(pkgs)) != 0) { 173 if (Verbose) 174 warnx("%d package addition(s) failed", err); 175 return err; 176 } 177 else 178 return 0; 179} 180 181static char * 182getpackagesite(void) 183{ 184 int reldate; 185 static char sitepath[MAXPATHLEN]; 186 struct utsname u; 187 188 if (getenv("PACKAGESITE")) { 189 strcpy(sitepath, getenv("PACKAGESITE")); 190 return sitepath; 191 } 192 193 if (getenv("PACKAGEMIRROR")) 194 strcpy(sitepath, getenv("PACKAGEMIRROR")); 195 else 196 strcpy(sitepath, "ftp://ftp.FreeBSD.org"); 197 198 if (getenv("PACKAGEROOT")) 199 strcpy(sitepath, getenv("PACKAGEMIRRORROOT")); 200 else 201 strcat(sitepath, "/pub"); 202 203 strcat(sitepath, "/FreeBSD/ports/"); 204 205 uname(&u); 206 strcat(sitepath, u.machine); 207 208 reldate = getosreldate(); 209 if (reldate == 410000) 210 strcat(sitepath, "/packages-4.1-release"); 211 else if (reldate == 420000) 212 strcat(sitepath, "/packages-4.2-release"); 213 else if (reldate == 430000) 214 strcat(sitepath, "/packages-4.3-release"); 215 else if (reldate == 440000) 216 strcat(sitepath, "/packages-4.4-release"); 217 else if (reldate == 450000) 218 strcat(sitepath, "/packages-4.5-release"); 219 else if (300000 <= reldate && reldate <= 399000) 220 strcat(sitepath, "/packages-3-stable"); 221 else if (400000 <= reldate && reldate <= 499000) 222 strcat(sitepath, "/packages-4-stable"); 223 else if (510000 <= reldate && reldate <= 599000) /* get real values!! */ 224 strcat(sitepath, "/packages-5-stable"); 225 else 226 strcat(sitepath, "/packages-current"); 227 228 strcat(sitepath, "/Latest/"); 229 230 return sitepath; 231 232} 233 234static void 235usage() 236{ 237 fprintf(stderr, "%s\n%s\n", 238 "usage: pkg_add [-vInrfRMS] [-t template] [-p prefix]", 239 " pkg-name [pkg-name ...]"); 240 exit(1); 241} 242