'PORTDIR_OVERLAY', 'PORTAGE_BUNZIP2_COMMAND',
'PORTAGE_BZIP2_COMMAND',
'USE', 'CHOST', 'CFLAGS', 'CXXFLAGS',
- 'ACCEPT_KEYWORDS', 'ACCEPT_LICENSE', 'SYNC', 'FEATURES',
+ 'ACCEPT_KEYWORDS', 'ACCEPT_LICENSE', 'FEATURES',
'EMERGE_DEFAULT_OPTS']
myvars.extend(portage.util.grabfile(settings["PORTDIR"]+"/profiles/info_vars"))
sys.exit(1)
searchinstance.output()
-def action_sync(settings, trees, mtimedb, myopts, myaction):
- enter_invalid = '--ask-enter-invalid' in myopts
+def action_sync(settings, trees, myopts):
xterm_titles = "notitles" not in settings.features
emergelog(xterm_titles, " === sync")
+
+ for repo in settings.repositories:
+ if repo.sync_type is not None:
+ returncode = _sync_repo(repo, settings, trees, myopts)
+ if returncode != os.EX_OK:
+ return returncode
+
+ # Reload the whole config from scratch.
+ portage._sync_disabled_warnings = False
+ settings, trees, mtimedb = load_emerge_config(trees=trees)
+ adjust_configs(myopts, trees)
portdb = trees[settings['EROOT']]['porttree'].dbapi
- myportdir = portdb.porttree_root
- if not myportdir:
- myportdir = settings.get('PORTDIR', '')
- if myportdir and myportdir.strip():
- myportdir = os.path.realpath(myportdir)
- else:
- myportdir = None
+ root_config = trees[settings['EROOT']]['root_config']
+
+ if myopts.get('--package-moves') != 'n' and _global_updates(trees, mtimedb["updates"], quiet=("--quiet" in myopts)):
+ mtimedb.commit()
+ # Reload the whole config from scratch.
+ settings, trees, mtimedb = load_emerge_config(trees=trees)
+ adjust_configs(myopts, trees)
+ portdb = trees[settings['EROOT']]['porttree'].dbapi
+ root_config = trees[settings['EROOT']]['root_config']
+
+ mybestpv = portdb.xmatch("bestmatch-visible", portage.const.PORTAGE_PACKAGE_ATOM)
+ mypvs = portage.best(trees[settings['EROOT']]['vartree'].dbapi.match(portage.const.PORTAGE_PACKAGE_ATOM))
+
+ chk_updated_cfg_files(settings["EROOT"], portage.util.shlex_split(settings.get("CONFIG_PROTECT", "")))
+
+ if mybestpv != mypvs and "--quiet" not in myopts:
+ print()
+ print(warn(" * ")+bold("An update to portage is available.")+" It is _highly_ recommended")
+ print(warn(" * ")+"that you update portage now, before any other packages are updated.")
+ print()
+ print(warn(" * ")+"To update portage, run 'emerge --oneshot portage' now.")
+ print()
+
+ display_news_notification(root_config, myopts)
+ return os.EX_OK
+
+def _sync_repo(repo, settings, trees, myopts):
+ enter_invalid = '--ask-enter-invalid' in myopts
+ xterm_titles = "notitles" not in settings.features
+ msg = ">>> Synchronization of repository '%s' located in '%s'..." % (repo.name, repo.location)
+ emergelog(xterm_titles, msg)
+ writemsg_level(msg + "\n")
out = portage.output.EOutput()
- global_config_path = GLOBAL_CONFIG_PATH
- if portage.const.EPREFIX:
- global_config_path = os.path.join(portage.const.EPREFIX,
- GLOBAL_CONFIG_PATH.lstrip(os.sep))
- if not myportdir:
- sys.stderr.write("!!! PORTDIR is undefined. " + \
- "Is %s/make.globals missing?\n" % global_config_path)
- sys.exit(1)
- if myportdir[-1]=="/":
- myportdir=myportdir[:-1]
try:
- st = os.stat(myportdir)
+ st = os.stat(repo.location)
except OSError:
st = None
if st is None:
- print(">>>",myportdir,"not found, creating it.")
- portage.util.ensure_dirs(myportdir, mode=0o755)
- st = os.stat(myportdir)
+ print(">>> '%s' not found, creating it." % repo.location)
+ portage.util.ensure_dirs(repo.location, mode=0o755)
+ st = os.stat(repo.location)
usersync_uid = None
spawn_kwargs = {}
if rval != os.EX_OK:
return rval
- syncuri = settings.get("SYNC", "").strip()
- if not syncuri:
- writemsg_level("!!! SYNC is undefined. " + \
- "Is %s/make.globals missing?\n" % global_config_path,
- noiselevel=-1, level=logging.ERROR)
- return 1
+ syncuri = repo.sync_uri
vcs_dirs = frozenset(VCS_DIRS)
- vcs_dirs = vcs_dirs.intersection(os.listdir(myportdir))
+ vcs_dirs = vcs_dirs.intersection(os.listdir(repo.location))
os.umask(0o022)
dosyncuri = syncuri
updatecache_flg = False
- git = False
- if myaction == "metadata":
- print("skipping sync")
- updatecache_flg = True
- elif ".git" in vcs_dirs:
+ if repo.sync_type == "git":
# Update existing git repository, and ignore the syncuri. We are
# going to trust the user and assume that the user is in the branch
# that he/she wants updated. We'll let the user manage branches with
writemsg_level("!!! %s\n" % l,
level=logging.ERROR, noiselevel=-1)
return 1
- msg = ">>> Starting git pull in %s..." % myportdir
+ msg = ">>> Starting git pull in %s..." % repo.location
emergelog(xterm_titles, msg )
writemsg_level(msg + "\n")
exitcode = portage.process.spawn_bash("cd %s ; git pull" % \
- (portage._shell_quote(myportdir),),
+ (portage._shell_quote(repo.location),),
**portage._native_kwargs(spawn_kwargs))
if exitcode != os.EX_OK:
- msg = "!!! git pull error in %s." % myportdir
+ msg = "!!! git pull error in %s." % repo.location
emergelog(xterm_titles, msg)
writemsg_level(msg + "\n", level=logging.ERROR, noiselevel=-1)
return exitcode
- msg = ">>> Git pull in %s successful" % myportdir
+ msg = ">>> Git pull in %s successful" % repo.location
emergelog(xterm_titles, msg)
writemsg_level(msg + "\n")
- git = True
- elif syncuri[:8]=="rsync://" or syncuri[:6]=="ssh://":
+ elif repo.sync_type == "rsync":
for vcs_dir in vcs_dirs:
writemsg_level(("!!! %s appears to be under revision " + \
"control (contains %s).\n!!! Aborting rsync sync.\n") % \
- (myportdir, vcs_dir), level=logging.ERROR, noiselevel=-1)
+ (repo.location, vcs_dir), level=logging.ERROR, noiselevel=-1)
return 1
rsync_binary = portage.process.find_binary("rsync")
if rsync_binary is None:
print("!!! /usr/bin/rsync does not exist, so rsync support is disabled.")
print("!!! Type \"emerge net-misc/rsync\" to enable rsync support.")
- sys.exit(1)
+ return os.EX_UNAVAILABLE
mytimeout=180
rsync_opts = []
# Real local timestamp file.
servertimestampfile = os.path.join(
- myportdir, "metadata", "timestamp.chk")
+ repo.location, "metadata", "timestamp.chk")
content = portage.util.grabfile(servertimestampfile)
mytimestamp = 0
r"(rsync|ssh)://([^:/]+@)?(\[[:\da-fA-F]*\]|[^:/]*)(:[0-9]+)?",
syncuri, maxsplit=4)[1:5]
except ValueError:
- writemsg_level("!!! SYNC is invalid: %s\n" % syncuri,
+ writemsg_level("!!! sync-uri is invalid: %s\n" % syncuri,
noiselevel=-1, level=logging.ERROR)
return 1
print(">>> In order to force sync, remove '%s'." % servertimestampfile)
print(">>>")
print()
- sys.exit(0)
+ return os.EX_OK
elif (servertimestamp != 0) and (servertimestamp < mytimestamp):
emergelog(xterm_titles,
">>> Server out of date: %s" % dosyncuri)
exitcode = SERVER_OUT_OF_DATE
elif (servertimestamp == 0) or (servertimestamp > mytimestamp):
# actual sync
- mycommand = rsynccommand + [dosyncuri+"/", myportdir]
+ mycommand = rsynccommand + [dosyncuri+"/", repo.location]
exitcode = portage.process.spawn(mycommand,
**portage._native_kwargs(spawn_kwargs))
if exitcode in [0,1,3,4,11,14,20,21]:
if (exitcode==0):
emergelog(xterm_titles, "=== Sync completed with %s" % dosyncuri)
elif exitcode == SERVER_OUT_OF_DATE:
- sys.exit(1)
+ return 1
elif exitcode == EXCEEDED_MAX_RETRIES:
sys.stderr.write(
">>> Exceeded PORTAGE_RSYNC_RETRIES: %s\n" % maxretries)
- sys.exit(1)
+ return 1
elif (exitcode>0):
msg = []
if exitcode==1:
msg.append("Rsync has reported that there is a syntax error. Please ensure")
- msg.append("that your SYNC statement is proper.")
- msg.append("SYNC=" + settings["SYNC"])
+ msg.append("that sync-uri attribute for repository '%s' is proper." % repo.name)
+ msg.append("sync-uri: '%s'" % repo.sync_uri)
elif exitcode==11:
msg.append("Rsync has reported that there is a File IO error. Normally")
msg.append("this means your disk is full, but can be caused by corruption")
- msg.append("on the filesystem that contains PORTDIR. Please investigate")
+ msg.append("on the filesystem that contains repository '%s'. Please investigate" % repo.name)
msg.append("and try again after the problem has been fixed.")
- msg.append("PORTDIR=" + settings["PORTDIR"])
+ msg.append("Location of repository: '%s'" % repo.location)
elif exitcode==20:
msg.append("Rsync was killed before it finished.")
else:
msg.append("(and possibly your system's filesystem) configuration.")
for line in msg:
out.eerror(line)
- sys.exit(exitcode)
- elif syncuri[:6]=="cvs://":
+ return exitcode
+ elif repo.sync_type == "cvs":
if not os.path.exists("/usr/bin/cvs"):
print("!!! /usr/bin/cvs does not exist, so CVS support is disabled.")
print("!!! Type \"emerge dev-vcs/cvs\" to enable CVS support.")
- sys.exit(1)
- cvsroot=syncuri[6:]
- cvsdir=os.path.dirname(myportdir)
- if not os.path.exists(myportdir+"/CVS"):
+ return os.EX_UNAVAILABLE
+ cvs_root = syncuri
+ if cvs_root.startswith("cvs://"):
+ cvs_root = cvs_root[6:]
+ if not os.path.exists(os.path.join(repo.location, "CVS")):
#initial checkout
print(">>> Starting initial cvs checkout with "+syncuri+"...")
- if os.path.exists(cvsdir+"/gentoo-x86"):
- print("!!! existing",cvsdir+"/gentoo-x86 directory; exiting.")
- sys.exit(1)
try:
- os.rmdir(myportdir)
+ os.rmdir(repo.location)
except OSError as e:
if e.errno != errno.ENOENT:
sys.stderr.write(
- "!!! existing '%s' directory; exiting.\n" % myportdir)
- sys.exit(1)
+ "!!! existing '%s' directory; exiting.\n" % repo.location)
+ return 1
del e
if portage.process.spawn_bash(
- "cd %s; exec cvs -z0 -d %s co -P gentoo-x86" % \
- (portage._shell_quote(cvsdir), portage._shell_quote(cvsroot)),
+ "cd %s; exec cvs -z0 -d %s co -P -d %s %s" %
+ (portage._shell_quote(os.path.dirname(repo.location)), portage._shell_quote(cvs_root),
+ portage._shell_quote(os.path.basename(repo.location)), portage._shell_quote(repo.sync_cvs_repo)),
**portage._native_kwargs(spawn_kwargs)) != os.EX_OK:
print("!!! cvs checkout error; exiting.")
- sys.exit(1)
- os.rename(os.path.join(cvsdir, "gentoo-x86"), myportdir)
+ return 1
else:
#cvs update
print(">>> Starting cvs update with "+syncuri+"...")
retval = portage.process.spawn_bash(
"cd %s; exec cvs -z0 -q update -dP" % \
- (portage._shell_quote(myportdir),),
+ (portage._shell_quote(repo.location),),
**portage._native_kwargs(spawn_kwargs))
if retval != os.EX_OK:
writemsg_level("!!! cvs update error; exiting.\n",
noiselevel=-1, level=logging.ERROR)
- sys.exit(retval)
+ return retval
dosyncuri = syncuri
- else:
- writemsg_level("!!! Unrecognized protocol: SYNC='%s'\n" % (syncuri,),
- noiselevel=-1, level=logging.ERROR)
- return 1
# Reload the whole config from scratch.
- portage._sync_disabled_warnings = False
settings, trees, mtimedb = load_emerge_config(trees=trees)
adjust_configs(myopts, trees)
- root_config = trees[settings['EROOT']]['root_config']
portdb = trees[settings['EROOT']]['porttree'].dbapi
- if git:
+ if repo.sync_type == "git":
# NOTE: Do this after reloading the config, in case
# it did not exist prior to sync, so that the config
# and portdb properly account for its existence.
- exitcode = git_sync_timestamps(portdb, myportdir)
+ exitcode = git_sync_timestamps(portdb, repo.location)
if exitcode == os.EX_OK:
updatecache_flg = True
- if updatecache_flg and \
- myaction != "metadata" and \
- "metadata-transfer" not in settings.features:
+ if updatecache_flg and "metadata-transfer" not in settings.features:
updatecache_flg = False
if updatecache_flg and \
- os.path.exists(os.path.join(myportdir, 'metadata', 'cache')):
+ os.path.exists(os.path.join(repo.location, 'metadata', 'cache')):
- # Only update cache for myportdir since that's
+ # Only update cache for repo.location since that's
# the only one that's been synced here.
- action_metadata(settings, portdb, myopts, porttrees=[myportdir])
-
- if myopts.get('--package-moves') != 'n' and \
- _global_updates(trees, mtimedb["updates"], quiet=("--quiet" in myopts)):
- mtimedb.commit()
- # Reload the whole config from scratch.
- settings, trees, mtimedb = load_emerge_config(trees=trees)
- adjust_configs(myopts, trees)
- portdb = trees[settings['EROOT']]['porttree'].dbapi
- root_config = trees[settings['EROOT']]['root_config']
+ action_metadata(settings, portdb, myopts, porttrees=[repo.location])
- mybestpv = portdb.xmatch("bestmatch-visible",
- portage.const.PORTAGE_PACKAGE_ATOM)
- mypvs = portage.best(
- trees[settings['EROOT']]['vartree'].dbapi.match(
- portage.const.PORTAGE_PACKAGE_ATOM))
-
- chk_updated_cfg_files(settings["EROOT"],
- portage.util.shlex_split(settings.get("CONFIG_PROTECT", "")))
-
- if myaction != "metadata":
- postsync = os.path.join(settings["PORTAGE_CONFIGROOT"],
- portage.USER_CONFIG_PATH, "bin", "post_sync")
- if os.access(postsync, os.X_OK):
- retval = portage.process.spawn(
- [postsync, dosyncuri], env=settings.environ())
- if retval != os.EX_OK:
- writemsg_level(
- " %s spawn failed of %s\n" % (bad("*"), postsync,),
- level=logging.ERROR, noiselevel=-1)
-
- if(mybestpv != mypvs) and not "--quiet" in myopts:
- print()
- print(warn(" * ")+bold("An update to portage is available.")+" It is _highly_ recommended")
- print(warn(" * ")+"that you update portage now, before any other packages are updated.")
- print()
- print(warn(" * ")+"To update portage, run 'emerge --oneshot portage' now.")
- print()
+ postsync = os.path.join(settings["PORTAGE_CONFIGROOT"], portage.USER_CONFIG_PATH, "bin", "post_sync")
+ if os.access(postsync, os.X_OK):
+ retval = portage.process.spawn([postsync, dosyncuri], env=settings.environ())
+ if retval != os.EX_OK:
+ writemsg_level(" %s spawn failed of %s\n" % (bad("*"), postsync,),
+ level=logging.ERROR, noiselevel=-1)
- display_news_notification(root_config, myopts)
return os.EX_OK
def action_uninstall(settings, trees, ldpath_mtimes,
if "sync" == emerge_config.action:
return action_sync(emerge_config.target_config.settings,
- emerge_config.trees, emerge_config.target_config.mtimedb,
- emerge_config.opts, emerge_config.action)
+ emerge_config.trees, emerge_config.opts)
elif "metadata" == emerge_config.action:
action_metadata(emerge_config.target_config.settings,
emerge_config.target_config.trees['porttree'].dbapi,
'find_invalid_path_char', 'format', 'local_config', 'location',
'main_repo', 'manifest_hashes', 'masters', 'missing_repo_name',
'name', 'portage1_profiles', 'portage1_profiles_compat', 'priority',
- 'profile_formats', 'sign_commit', 'sign_manifest', 'sync',
- 'thin_manifest', 'update_changelog', 'user_location',
- '_eapis_banned', '_eapis_deprecated')
+ 'profile_formats', 'sign_commit', 'sign_manifest', 'sync_cvs_repo',
+ 'sync_type', 'sync_uri', 'thin_manifest', 'update_changelog',
+ 'user_location', '_eapis_banned', '_eapis_deprecated')
def __init__(self, name, repo_opts, local_config=True):
"""Build a RepoConfig with options in repo_opts
priority = None
self.priority = priority
- # Not implemented.
- sync = repo_opts.get('sync')
- if sync is not None:
- sync = sync.strip()
- self.sync = sync
+ sync_cvs_repo = repo_opts.get('sync-cvs-repo')
+ if sync_cvs_repo is not None:
+ sync_cvs_repo = sync_cvs_repo.strip()
+ self.sync_cvs_repo = sync_cvs_repo or None
+
+ sync_type = repo_opts.get('sync-type')
+ if sync_type is not None:
+ sync_type = sync_type.strip()
+ self.sync_type = sync_type or None
+
+ sync_uri = repo_opts.get('sync-uri')
+ if sync_uri is not None:
+ sync_uri = sync_uri.strip()
+ self.sync_uri = sync_uri or None
# Not implemented.
format = repo_opts.get('format')
location = repo_opts.get('location')
self.user_location = location
if location is not None and location.strip():
- if os.path.isdir(location):
+ if os.path.isdir(location) or portage._sync_disabled_warnings:
location = os.path.realpath(location)
else:
location = None
missing = True
self.name = name
if self.location is not None:
- eapi = read_corresponding_eapi_file(os.path.join(self.location, REPO_NAME_LOC))
- self.name, missing = self._read_valid_repo_name(self.location)
- elif name == "DEFAULT":
+ if os.path.isdir(location):
+ eapi = read_corresponding_eapi_file(os.path.join(self.location, REPO_NAME_LOC))
+ self.name, missing = self._read_valid_repo_name(self.location)
+ else:
+ missing = not portage._sync_disabled_warnings
+ elif name == "DEFAULT":
missing = False
self.eapi = eapi
repo_msg.append(indent + "format: " + self.format)
if self.user_location:
repo_msg.append(indent + "location: " + self.user_location)
- if self.sync:
- repo_msg.append(indent + "sync: " + self.sync)
+ if self.sync_cvs_repo:
+ repo_msg.append(indent + "sync-cvs-repo: " + self.sync_cvs_repo)
+ if self.sync_type:
+ repo_msg.append(indent + "sync-type: " + self.sync_type)
+ if self.sync_uri:
+ repo_msg.append(indent + "sync-uri: " + self.sync_uri)
if self.masters:
repo_msg.append(indent + "masters: " + " ".join(master.name for master in self.masters))
if self.priority is not None:
if self.aliases:
repo_msg.append(indent + "aliases: " + " ".join(self.aliases))
if self.eclass_overrides:
- repo_msg.append(indent + "eclass_overrides: " + \
+ repo_msg.append(indent + "eclass-overrides: " + \
" ".join(self.eclass_overrides))
repo_msg.append("")
return "\n".join(repo_msg)
optdict[oname] = parser.get(sname, oname)
repo = RepoConfig(sname, optdict, local_config=local_config)
- if repo.name != sname:
- writemsg_level("!!! %s\n" %
- _("Section name '%s' set in repos.conf differs from name '%s' set inside repository") %
+
+ if repo.name != sname and not portage._sync_disabled_warnings:
+ writemsg_level("!!! %s\n" % _("Section name '%s' set in repos.conf differs from name '%s' set inside repository") %
(sname, repo.name), level=logging.ERROR, noiselevel=-1)
continue
- if repo.location and not exists_raise_eaccess(repo.location):
- writemsg(_("!!! Invalid repos.conf entry '%s'"
- " (not a dir): '%s'\n") % (sname, repo.location), noiselevel=-1)
+ if repo.location and not exists_raise_eaccess(repo.location) and not portage._sync_disabled_warnings:
+ writemsg_level("!!! %s\n" % _("Repository '%s' has location attribute set to nonexistent directory: '%s'") %
+ (sname, repo.location), level=logging.ERROR, noiselevel=-1)
+ continue
+
+ if repo.sync_type is not None and repo.sync_uri is None:
+ writemsg_level("!!! %s\n" % _("Repository '%s' has sync-type attribute, but is missing sync-uri attribute") %
+ sname, level=logging.ERROR, noiselevel=-1)
+ continue
+
+ if repo.sync_uri is not None and repo.sync_type is None:
+ writemsg_level("!!! %s\n" % _("Repository '%s' has sync-uri attribute, but is missing sync-type attribute") %
+ sname, level=logging.ERROR, noiselevel=-1)
+ continue
+
+ if repo.sync_type not in (None, "cvs", "git", "rsync"):
+ writemsg_level("!!! %s\n" % _("Repository '%s' has sync-type attribute set to unsupported value: '%s'") %
+ (sname, repo.sync_type), level=logging.ERROR, noiselevel=-1)
+ continue
+
+ if repo.sync_type == "cvs" and repo.sync_cvs_repo is None:
+ writemsg_level("!!! %s\n" % _("Repository '%s' has sync-type=cvs, but is missing sync-cvs-repo attribute") %
+ sname, level=logging.ERROR, noiselevel=-1)
continue
if repo.name in prepos:
if r.location is None:
writemsg(_("!!! Location not set for repository %s\n") % name, noiselevel=-1)
else:
- if not isdir_raise_eaccess(r.location):
+ if not isdir_raise_eaccess(r.location) and not portage._sync_disabled_warnings:
self.prepos_order.remove(name)
writemsg(_("!!! Invalid Repository Location"
" (not a dir): '%s'\n") % r.location, noiselevel=-1)
return repo_name in self.prepos
def config_string(self):
- str_or_int_keys = ("format", "location", "main_repo", "priority", "sync")
+ str_or_int_keys = ("format", "location", "main_repo", "priority", "sync_cvs_repo", "sync_type", "sync_uri")
str_tuple_keys = ("aliases", "eclass_overrides")
repo_config_tuple_keys = ("masters",)
keys = str_or_int_keys + str_tuple_keys + repo_config_tuple_keys