diff options
| -rw-r--r-- | doc/pacman.conf.5.txt | 6 | ||||
| -rwxr-xr-x | pactest/pmtest.py | 3 | ||||
| -rw-r--r-- | pactest/tests/sync301.py | 4 | ||||
| -rw-r--r-- | src/pacman/conf.c | 2 | ||||
| -rw-r--r-- | src/pacman/conf.h | 1 | ||||
| -rw-r--r-- | src/pacman/pacman.c | 7 | ||||
| -rw-r--r-- | src/pacman/sync.c | 77 | 
7 files changed, 62 insertions, 38 deletions
| diff --git a/doc/pacman.conf.5.txt b/doc/pacman.conf.5.txt index 5514e2c0..eb9285c3 100644 --- a/doc/pacman.conf.5.txt +++ b/doc/pacman.conf.5.txt @@ -82,6 +82,12 @@ Options  	Instructs pacman to ignore any upgrades for this package when performing  	a '\--sysupgrade'. +*SyncFirst =* package ...:: +	Instructs pacman to check for newer version of these packages before any +	sync operation. The user will have the choice to either cancel the current +	operation and upgrade these packages first or go on with the current operation. +	This option is typically used with the 'pacman' package. +  *IgnoreGroup =* group ...::  	Instructs pacman to ignore any upgrades for all packages in this  	group when performing a '\--sysupgrade'. diff --git a/pactest/pmtest.py b/pactest/pmtest.py index 0c4ba847..267eeb2e 100755 --- a/pactest/pmtest.py +++ b/pactest/pmtest.py @@ -83,7 +83,8 @@ class pmtest:              "noupgrade": [],              "ignorepkg": [],              "ignoregroup": [], -            "noextract": [] +            "noextract": [], +            "syncfirst": []          }          # Test rules diff --git a/pactest/tests/sync301.py b/pactest/tests/sync301.py index e8526b93..96402fc3 100644 --- a/pactest/tests/sync301.py +++ b/pactest/tests/sync301.py @@ -16,10 +16,12 @@ self.addpkg2db("local", lp)  lp1 = pmpkg("pkg1", "1.0-1")  self.addpkg2db("local", lp1) +self.option["SyncFirst"] = ["pacman"] +  self.args = "-Su"  self.addrule("PACMAN_RETCODE=0")  self.addrule("PKG_EXIST=pacman")  self.addrule("PKG_VERSION=pacman|1.0-2") +self.addrule("PKG_VERSION=pkg1|1.0-1")  self.addrule("PKG_EXIST=dep") -self.addrule("PKG_REQUIREDBY=dep|pacman") diff --git a/src/pacman/conf.c b/src/pacman/conf.c index 27c254b5..48c927bf 100644 --- a/src/pacman/conf.c +++ b/src/pacman/conf.c @@ -47,6 +47,7 @@ config_t *config_new(void)  	newconfig->rootdir = NULL;  	newconfig->dbpath = NULL;  	newconfig->logfile = NULL; +	newconfig->syncfirst = NULL;  	return(newconfig);  } @@ -57,6 +58,7 @@ int config_free(config_t *oldconfig)  		return(-1);  	} +	FREELIST(oldconfig->syncfirst);  	free(oldconfig->configfile);  	free(oldconfig->rootdir);  	free(oldconfig->dbpath); diff --git a/src/pacman/conf.h b/src/pacman/conf.h index 28ac4b96..874ce708 100644 --- a/src/pacman/conf.h +++ b/src/pacman/conf.h @@ -69,6 +69,7 @@ typedef struct __config_t {  	 * downloaded of the total download list */  	unsigned short totaldownload;  	unsigned short cleanmethod; /* select -Sc behavior */ +	alpm_list_t *syncfirst;  } config_t;  /* Operations */ diff --git a/src/pacman/pacman.c b/src/pacman/pacman.c index 5cb3c784..7ae023b2 100644 --- a/src/pacman/pacman.c +++ b/src/pacman/pacman.c @@ -515,6 +515,11 @@ static int parseargs(int argc, char *argv[])  	return(0);  } +/* helper for being used with setrepeatingoption */ +static void option_add_syncfirst(const char *name) { +	config->syncfirst = alpm_list_add(config->syncfirst, strdup(name)); +} +  /** Add repeating options such as NoExtract, NoUpgrade, etc to libalpm   * settings. Refactored out of the parseconfig code since all of them did   * the exact same thing and duplicated code. @@ -666,6 +671,8 @@ static int _parseconfig(const char *file, const char *givensection,  						setrepeatingoption(ptr, "IgnoreGroup", alpm_option_add_ignoregrp);  					} else if(strcmp(key, "HoldPkg") == 0) {  						setrepeatingoption(ptr, "HoldPkg", alpm_option_add_holdpkg); +					} else if(strcmp(key, "SyncFirst") == 0) { +						setrepeatingoption(ptr, "SyncFirst", option_add_syncfirst);  					} else if(strcmp(key, "DBPath") == 0) {  						/* don't overwrite a path specified on the command line */  						if(!config->dbpath) { diff --git a/src/pacman/sync.c b/src/pacman/sync.c index 78235c54..134d4db3 100644 --- a/src/pacman/sync.c +++ b/src/pacman/sync.c @@ -527,6 +527,24 @@ static int sync_list(alpm_list_t *syncs, alpm_list_t *targets)  	return(0);  } +static alpm_list_t *syncfirst() { +	alpm_list_t *i, *res = NULL; + +	for(i = config->syncfirst; i; i = alpm_list_next(i)) { +		char *pkgname = alpm_list_getdata(i); +		pmpkg_t *pkg = alpm_db_get_pkg(alpm_option_get_localdb(), pkgname); +		if(pkg == NULL) { +			continue; +		} + +		if(alpm_sync_newversion(pkg, alpm_option_get_syncdbs())) { +			res = alpm_list_add(res, strdup(pkgname)); +		} +	} + +	return(res); +} +  static int sync_trans(alpm_list_t *targets)  {  	int retval = 0; @@ -539,7 +557,6 @@ static int sync_trans(alpm_list_t *targets)  	}  	if(config->op_s_upgrade) { -		alpm_list_t *pkgs, *i;  		printf(_(":: Starting full system upgrade...\n"));  		alpm_logaction("starting full system upgrade\n");  		if(alpm_trans_sysupgrade() == -1) { @@ -547,40 +564,6 @@ static int sync_trans(alpm_list_t *targets)  			retval = 1;  			goto cleanup;  		} - -		if(!(alpm_trans_get_flags() & (PM_TRANS_FLAG_DOWNLOADONLY | PM_TRANS_FLAG_PRINTURIS))) { -			/* check if pacman itself is one of the packages to upgrade. -			 * this can prevent some of the "syntax error" problems users can have -			 * when sysupgrade'ing with an older version of pacman. -			 */ -			pkgs = alpm_trans_get_pkgs(); -			for(i = pkgs; i; i = alpm_list_next(i)) { -				pmsyncpkg_t *sync = alpm_list_getdata(i); -				pmpkg_t *spkg = alpm_sync_get_pkg(sync); -				/* TODO pacman name should probably not be hardcoded. In addition, we -				 * have problems on an -Syu if pacman has to pull in deps, so recommend -				 * an '-S pacman' operation */ -				if(strcmp("pacman", alpm_pkg_get_name(spkg)) == 0) { -					printf("\n"); -					printf(_(":: pacman has detected a newer version of itself.\n")); -					if(yesno(1, _(":: Do you want to cancel the current operation\n" -					           ":: and install the new pacman version now?"))) { -						if(trans_release() == -1) { -							return(1); -						} -						if(trans_init(PM_TRANS_TYPE_SYNC, 0) == -1) { -							return(1); -						} -						if(alpm_trans_addtarget("pacman") == -1) { -							pm_fprintf(stderr, PM_LOG_ERROR, _("pacman: %s\n"), -								alpm_strerrorlast()); -							return(1); -						} -						break; -					} -				} -			} -		}  	} else {  		alpm_list_t *i; @@ -831,7 +814,29 @@ int pacman_sync(alpm_list_t *targets)  	}  	if(needs_transaction()) { -		if(sync_trans(targets) == 1) { +		alpm_list_t *targs = alpm_list_strdup(targets); +		if(!(config->flags & (PM_TRANS_FLAG_DOWNLOADONLY | PM_TRANS_FLAG_PRINTURIS))) { +			/* check for newer versions of packages to be upgraded first */ +			alpm_list_t *packages = syncfirst(); +			if(packages) { +				printf(_(":: The following packages should be upgraded first :\n")); +				list_display("   ", packages); +				if(yesno(1, _(":: Do you want to cancel the current operation\n" +								":: and upgrade these packages now?"))) { +					FREELIST(targs); +					targs = packages; +					config->flags = 0; +					config->op_s_upgrade = 0; +				} else { +					FREELIST(packages); +				} +				printf("\n"); +			} +		} + +		int ret = sync_trans(targs); +		FREELIST(targs); +		if(ret == 1) {  			return(1);  		}  	} | 
