From 60db1604bf4f33d1e5384d1f523e02dc97604fcf Mon Sep 17 00:00:00 2001 From: jkh Date: Tue, 4 Oct 1994 16:07:50 +0000 Subject: Add the ability to verify that a package won't extract in the space available. Thanks to Michael Elbel for pushing me in the right direction. --- usr.sbin/pkg_install/add/perform.c | 18 ++++++++++++++---- usr.sbin/pkg_install/info/perform.c | 15 +++++++++++++-- usr.sbin/pkg_install/lib/lib.h | 4 ++-- usr.sbin/pkg_install/lib/pen.c | 35 ++++++++++++++++++++++++++++++----- 4 files changed, 59 insertions(+), 13 deletions(-) (limited to 'usr.sbin') diff --git a/usr.sbin/pkg_install/add/perform.c b/usr.sbin/pkg_install/add/perform.c index 88719cd..45b4c11 100644 --- a/usr.sbin/pkg_install/add/perform.c +++ b/usr.sbin/pkg_install/add/perform.c @@ -1,5 +1,5 @@ #ifndef lint -static const char *rcsid = "$Id: perform.c,v 1.7 1994/05/25 06:24:18 jkh Exp $"; +static const char *rcsid = "$Id: perform.c,v 1.8 1994/05/25 17:59:54 asami Exp $"; #endif /* @@ -60,6 +60,7 @@ pkg_do(char *pkg) char *home; int code = 0; PackingList p; + struct stat sb; /* Reset some state */ if (Plist.head) @@ -77,16 +78,25 @@ pkg_do(char *pkg) read_plist(&Plist, stdin); } else { - home = make_playpen(PlayPen); if (pkg[0] == '/') /* full pathname? */ strcpy(pkg_fullname, pkg); else sprintf(pkg_fullname, "%s/%s", home, pkg); if (!fexists(pkg_fullname)) { - whinge("Can't open package '%s'.", pkg_fullname); + whinge("Can't find package '%s'.", pkg_fullname); return 1; } - + /* + * Apply a crude heuristic to see how much space the package will + * take up once it's unpacked. I've noticed that most packages + * compress an average of 65%. + */ + if (stat(pkg_fullname, &sb) == FAIL) { + whinge("Can't stat package file '%s'.", pkg_fullname); + return 1; + } + sb.st_size *= 1.65; + home = make_playpen(PlayPen, sb.st_size); if (unpack(pkg_fullname, NULL)) return 1; diff --git a/usr.sbin/pkg_install/info/perform.c b/usr.sbin/pkg_install/info/perform.c index 53a2135..9fac45d 100644 --- a/usr.sbin/pkg_install/info/perform.c +++ b/usr.sbin/pkg_install/info/perform.c @@ -1,5 +1,5 @@ #ifndef lint -static const char *rcsid = "$Id: perform.c,v 1.4 1993/09/04 05:06:43 jkh Exp $"; +static const char *rcsid = "$Id: perform.c,v 1.6 1993/09/08 01:46:57 jkh Exp $"; #endif /* @@ -78,12 +78,23 @@ pkg_do(char *pkg) if (fexists(pkg)) { char fname[FILENAME_MAX]; + struct stat sb; - home = make_playpen(PlayPen); if (pkg[0] == '/') strcpy(fname, pkg); else sprintf(fname, "%s/%s", home, pkg); + /* + * Apply a crude heuristic to see how much space the package will + * take up once it's unpacked. I've noticed that most packages + * compress an average of 65%. + */ + if (stat(fname, &sb) == FAIL) { + whinge("Can't stat package file '%s'.", fname); + return 1; + } + sb.st_size *= 1.65; + home = make_playpen(PlayPen, sb.st_size); if (unpack(fname, "+*")) { whinge("Error during unpacking, no info for '%s' available.", pkg); return 1; diff --git a/usr.sbin/pkg_install/lib/lib.h b/usr.sbin/pkg_install/lib/lib.h index 08de0be..31bd696 100644 --- a/usr.sbin/pkg_install/lib/lib.h +++ b/usr.sbin/pkg_install/lib/lib.h @@ -1,4 +1,4 @@ -/* $Id: lib.h,v 1.8 1994/08/28 14:15:29 jkh Exp $ */ +/* $Id: lib.h,v 1.9 1994/09/29 13:19:42 jkh Exp $ */ /* * FreeBSD install - a package for the installation and maintainance @@ -99,7 +99,7 @@ typedef struct _pack Package; /* Misc */ int vsystem(const char *, ...); void cleanup(int); -char *make_playpen(char *); +char *make_playpen(char *, size_t); void leave_playpen(void); char *where_playpen(void); diff --git a/usr.sbin/pkg_install/lib/pen.c b/usr.sbin/pkg_install/lib/pen.c index 1872d82..a3cfcdf 100644 --- a/usr.sbin/pkg_install/lib/pen.c +++ b/usr.sbin/pkg_install/lib/pen.c @@ -1,5 +1,5 @@ #ifndef lint -static const char *rcsid = "$Id: pen.c,v 1.2 1993/09/04 05:06:51 jkh Exp $"; +static const char *rcsid = "$Id: pen.c,v 1.3 1993/09/05 04:54:23 jkh Exp $"; #endif /* @@ -23,28 +23,42 @@ static const char *rcsid = "$Id: pen.c,v 1.2 1993/09/04 05:06:51 jkh Exp $"; */ #include "lib.h" +#include +#include /* For keeping track of where we are */ static char Cwd[FILENAME_MAX]; static char Pen[FILENAME_MAX]; +static long min_free(char *); /* * Make a temporary directory to play in and chdir() to it, returning * pathname of previous working directory. */ char * -make_playpen(char *pen) +make_playpen(char *pen, size_t sz) { - if (!pen) - pen = "/tmp/instmp.XXXXXX"; + if (!pen) { + char *cp; + + if ((cp = getenv("TMPDIR")) != NULL) + sprintf(Pen, "%s/instmp.XXXXXX", cp); + else + strcpy(Pen, "/tmp/instmp.XXXXXX"); + } + else + strcpy(Pen, pen); if (!getcwd(Cwd, FILENAME_MAX)) upchuck("getcwd"); - strcpy(Pen, pen); if (!mktemp(Pen)) barf("Can't mktemp '%s'.", Pen); if (mkdir(Pen, 0755) == FAIL) barf("Can't mkdir '%s'.", Pen); + if (min_free(Pen) < sz) { + rmdir(Pen); + barf("%s doesn't have enough free space. Please set your TMPDIR\nenvironment variable to a location with more space and\ntry the command again.", Pen); + } if (chdir(Pen) == FAIL) barf("Can't chdir to '%s'.", Pen); return Cwd; @@ -72,3 +86,14 @@ where_playpen(void) else return NULL; } + +static long min_free(char *tmpdir) +{ + struct statfs buf; + + if (statfs(tmpdir, &buf) != 0) { + perror("Error in statfs"); + return -1; + } + return buf.f_bavail * buf.f_bsize; +} -- cgit v1.1