Exemplo n.º 1
0
	def _parse(paths, prepos, local_config, default_opts):
		"""Parse files in paths to load config"""
		parser = SafeConfigParser(defaults=default_opts)

		recursive_paths = []
		for p in paths:
			if isinstance(p, basestring):
				recursive_paths.extend(_recursive_file_list(p))
			else:
				recursive_paths.append(p)

		read_configs(parser, recursive_paths)

		prepos['DEFAULT'] = RepoConfig("DEFAULT",
			parser.defaults(), local_config=local_config)

		for sname in parser.sections():
			optdict = {}
			for oname in parser.options(sname):
				optdict[oname] = parser.get(sname, oname)

			repo = RepoConfig(sname, optdict, local_config=local_config)
			for o in portage.sync.module_specific_options(repo):
				if parser.has_option(sname, o):
					repo.set_module_specific_opt(o, parser.get(sname, o))

			# Perform repos.conf sync variable validation
			portage.sync.validate_config(repo, logging)

			# For backward compatibility with locations set via PORTDIR and
			# PORTDIR_OVERLAY, delay validation of the location and repo.name
			# until after PORTDIR and PORTDIR_OVERLAY have been processed.
			prepos[sname] = repo
Exemplo n.º 2
0
    def _parse(paths, prepos, local_config, default_opts):
        """Parse files in paths to load config"""
        parser = SafeConfigParser(defaults=default_opts)

        recursive_paths = []
        for p in paths:
            if isinstance(p, basestring):
                recursive_paths.extend(_recursive_file_list(p))
            else:
                recursive_paths.append(p)

        read_configs(parser, recursive_paths)

        prepos['DEFAULT'] = RepoConfig("DEFAULT",
                                       parser.defaults(),
                                       local_config=local_config)

        for sname in parser.sections():
            optdict = {}
            for oname in parser.options(sname):
                optdict[oname] = parser.get(sname, oname)

            repo = RepoConfig(sname, optdict, local_config=local_config)
            for o in portage.sync.module_specific_options(repo):
                if parser.has_option(sname, o):
                    repo.set_module_specific_opt(o, parser.get(sname, o))

            # Perform repos.conf sync variable validation
            portage.sync.validate_config(repo, logging)

            # For backward compatibility with locations set via PORTDIR and
            # PORTDIR_OVERLAY, delay validation of the location and repo.name
            # until after PORTDIR and PORTDIR_OVERLAY have been processed.
            prepos[sname] = repo
Exemplo n.º 3
0
    def __init__(self, settings, logger):
        self.settings = settings
        self.logger = logger
        # Similar to emerge, sync needs a default umask so that created
        # files have sane permissions.
        os.umask(0o22)

        self.module_controller = portage.sync.module_controller
        self.module_names = self.module_controller.module_names
        self.hooks = {}
        for _dir in ["repo.postsync.d", "postsync.d"]:
            postsync_dir = os.path.join(self.settings["PORTAGE_CONFIGROOT"],
                                        portage.USER_CONFIG_PATH, _dir)
            hooks = OrderedDict()
            for filepath in util._recursive_file_list(postsync_dir):
                name = filepath.split(postsync_dir)[1].lstrip(os.sep)
                if os.access(filepath, os.X_OK):
                    hooks[filepath] = name
                else:
                    writemsg_level(" %s %s hook: '%s' is not executable\n" % (
                        warn("*"),
                        _dir,
                        _unicode_decode(name),
                    ),
                                   level=logging.WARN,
                                   noiselevel=2)
            self.hooks[_dir] = hooks
Exemplo n.º 4
0
    def _parse(paths, defaults):
        parser = SafeConfigParser(defaults=defaults)
        recursive_paths = []
        for p in paths:
            if isinstance(p, str):
                recursive_paths.extend(_recursive_file_list(p))
            else:
                recursive_paths.append(p)

        read_configs(parser, recursive_paths)
        return parser
Exemplo n.º 5
0
def get_hooks_from_dir(rel_directory, prefix="/"):
    directory = os.path.join(prefix, portage.USER_CONFIG_PATH, rel_directory)

    hooks = OrderedDict()
    for filepath in _recursive_file_list(directory):
        name = filepath.split(directory)[1].lstrip(portage.os.sep)
        if portage.os.access(filepath, portage.os.X_OK):
            hooks[filepath] = name
        else:
            writemsg_level(
                " %s %s hook: '%s' is not executable\n"
                % (
                    warn("*"),
                    directory,
                    portage._unicode_decode(name),
                ),
                level=logging.WARN,
                noiselevel=2,
            )

    return hooks
Exemplo n.º 6
0
	def __init__(self, settings, logger):
		self.settings = settings
		self.logger = logger
		# Similar to emerge, sync needs a default umask so that created
		# files have sane permissions.
		os.umask(0o22)

		self.module_controller = portage.sync.module_controller
		self.module_names = self.module_controller.module_names
		self.hooks = {}
		for _dir in ["repo.postsync.d", "postsync.d"]:
			postsync_dir = os.path.join(self.settings["PORTAGE_CONFIGROOT"],
				portage.USER_CONFIG_PATH, _dir)
			hooks = OrderedDict()
			for filepath in util._recursive_file_list(postsync_dir):
				name = filepath.split(postsync_dir)[1].lstrip(os.sep)
				if os.access(filepath, os.X_OK):
					hooks[filepath] = name
				else:
					writemsg_level(" %s %s hook: '%s' is not executable\n"
						% (warn("*"), _dir, _unicode_decode(name),),
						level=logging.WARN, noiselevel=2)
			self.hooks[_dir] = hooks
Exemplo n.º 7
0
def emirrordist_main(args):

	# The calling environment is ignored, so the program is
	# completely controlled by commandline arguments.
	env = {}

	if not sys.stdout.isatty():
		portage.output.nocolor()
		env['NOCOLOR'] = 'true'

	parser, options, args = parse_args(args)

	if options.version:
		sys.stdout.write("Portage %s\n" % portage.VERSION)
		return os.EX_OK

	config_root = options.config_root

	if options.repositories_configuration is not None:
		env['PORTAGE_REPOSITORIES'] = options.repositories_configuration

	settings = portage.config(config_root=config_root,
		local_config=False, env=env)

	default_opts = None
	if not options.ignore_default_opts:
		default_opts = settings.get('EMIRRORDIST_DEFAULT_OPTS', '').split()

	if default_opts:
		parser, options, args = parse_args(default_opts + args)

		settings = portage.config(config_root=config_root,
			local_config=False, env=env)

	if options.repo is None:
		if len(settings.repositories.prepos) == 2:
			for repo in settings.repositories:
				if repo.name != "DEFAULT":
					options.repo = repo.name
					break

		if options.repo is None:
			parser.error("--repo option is required")

	repo_path = settings.repositories.treemap.get(options.repo)
	if repo_path is None:
		parser.error("Unable to locate repository named '%s'" % (options.repo,))

	if options.jobs is not None:
		options.jobs = int(options.jobs)

	if options.load_average is not None:
		options.load_average = float(options.load_average)

	if options.failure_log is not None:
		options.failure_log = normalize_path(
			os.path.abspath(options.failure_log))

		parent_dir = os.path.dirname(options.failure_log)
		if not (os.path.isdir(parent_dir) and
			os.access(parent_dir, os.W_OK|os.X_OK)):
			parser.error(("--failure-log '%s' parent is not a "
				"writable directory") % options.failure_log)

	if options.success_log is not None:
		options.success_log = normalize_path(
			os.path.abspath(options.success_log))

		parent_dir = os.path.dirname(options.success_log)
		if not (os.path.isdir(parent_dir) and
			os.access(parent_dir, os.W_OK|os.X_OK)):
			parser.error(("--success-log '%s' parent is not a "
				"writable directory") % options.success_log)

	if options.scheduled_deletion_log is not None:
		options.scheduled_deletion_log = normalize_path(
			os.path.abspath(options.scheduled_deletion_log))

		parent_dir = os.path.dirname(options.scheduled_deletion_log)
		if not (os.path.isdir(parent_dir) and
			os.access(parent_dir, os.W_OK|os.X_OK)):
			parser.error(("--scheduled-deletion-log '%s' parent is not a "
				"writable directory") % options.scheduled_deletion_log)

		if options.deletion_db is None:
			parser.error("--scheduled-deletion-log requires --deletion-db")

	if options.deletion_delay is not None:
		options.deletion_delay = long(options.deletion_delay)
		if options.deletion_db is None:
			parser.error("--deletion-delay requires --deletion-db")

	if options.deletion_db is not None:
		if options.deletion_delay is None:
			parser.error("--deletion-db requires --deletion-delay")
		options.deletion_db = normalize_path(
			os.path.abspath(options.deletion_db))

	if options.temp_dir is not None:
		options.temp_dir = normalize_path(
			os.path.abspath(options.temp_dir))

		if not (os.path.isdir(options.temp_dir) and
			os.access(options.temp_dir, os.W_OK|os.X_OK)):
			parser.error(("--temp-dir '%s' is not a "
				"writable directory") % options.temp_dir)

	if options.distfiles is not None:
		options.distfiles = normalize_path(
			os.path.abspath(options.distfiles))

		if not (os.path.isdir(options.distfiles) and
			os.access(options.distfiles, os.W_OK|os.X_OK)):
			parser.error(("--distfiles '%s' is not a "
				"writable directory") % options.distfiles)
	else:
		parser.error("missing required --distfiles parameter")

	if options.mirror_overrides is not None:
		options.mirror_overrides = normalize_path(
			os.path.abspath(options.mirror_overrides))

		if not (os.access(options.mirror_overrides, os.R_OK) and
			os.path.isfile(options.mirror_overrides)):
			parser.error(
				"--mirror-overrides-file '%s' is not a readable file" %
				options.mirror_overrides)

	if options.distfiles_local is not None:
		options.distfiles_local = normalize_path(
			os.path.abspath(options.distfiles_local))

		if not (os.path.isdir(options.distfiles_local) and
			os.access(options.distfiles_local, os.W_OK|os.X_OK)):
			parser.error(("--distfiles-local '%s' is not a "
				"writable directory") % options.distfiles_local)

	if options.distfiles_db is not None:
		options.distfiles_db = normalize_path(
			os.path.abspath(options.distfiles_db))

	if options.tries is not None:
		options.tries = int(options.tries)

	if options.recycle_dir is not None:
		options.recycle_dir = normalize_path(
			os.path.abspath(options.recycle_dir))
		if not (os.path.isdir(options.recycle_dir) and
			os.access(options.recycle_dir, os.W_OK|os.X_OK)):
			parser.error(("--recycle-dir '%s' is not a "
				"writable directory") % options.recycle_dir)

	if options.recycle_db is not None:
		if options.recycle_dir is None:
			parser.error("--recycle-db requires "
				"--recycle-dir to be specified")
		options.recycle_db = normalize_path(
			os.path.abspath(options.recycle_db))

	if options.recycle_deletion_delay is not None:
		options.recycle_deletion_delay = \
			long(options.recycle_deletion_delay)

	if options.fetch_log_dir is not None:
		options.fetch_log_dir = normalize_path(
			os.path.abspath(options.fetch_log_dir))

		if not (os.path.isdir(options.fetch_log_dir) and
			os.access(options.fetch_log_dir, os.W_OK|os.X_OK)):
			parser.error(("--fetch-log-dir '%s' is not a "
				"writable directory") % options.fetch_log_dir)

	if options.whitelist_from:
		normalized_paths = []
		for x in options.whitelist_from:
			path = normalize_path(os.path.abspath(x))
			if not os.access(path, os.R_OK):
				parser.error("--whitelist-from '%s' is not readable" % x)
			if os.path.isfile(path):
				normalized_paths.append(path)
			elif os.path.isdir(path):
				for file in _recursive_file_list(path):
					if not os.access(file, os.R_OK):
						parser.error("--whitelist-from '%s' directory contains not readable file '%s'" % (x, file))
					normalized_paths.append(file)
			else:
				parser.error("--whitelist-from '%s' is not a regular file or a directory" % x)
		options.whitelist_from = normalized_paths

	if options.strict_manifests is not None:
		if options.strict_manifests == "y":
			settings.features.add("strict")
		else:
			settings.features.discard("strict")

	settings.lock()

	portdb = portage.portdbapi(mysettings=settings)

	# Limit ebuilds to the specified repo.
	portdb.porttrees = [repo_path]

	portage.util.initialize_logger()

	if options.verbose > 0:
		l = logging.getLogger()
		l.setLevel(l.getEffectiveLevel() - 10 * options.verbose)

	with Config(options, portdb,
		SchedulerInterface(global_event_loop())) as config:

		if not options.mirror:
			parser.error('No action specified')

		returncode = os.EX_OK

		if options.mirror:
			signum = run_main_scheduler(MirrorDistTask(config))
			if signum is not None:
				sys.exit(128 + signum)

	return returncode
Exemplo n.º 8
0
	def _parse(paths, prepos, ignored_map, ignored_location_map, local_config, portdir):
		"""Parse files in paths to load config"""
		parser = SafeConfigParser()

		# use read_file/readfp in order to control decoding of unicode
		try:
			# Python >=3.2
			read_file = parser.read_file
			source_kwarg = 'source'
		except AttributeError:
			read_file = parser.readfp
			source_kwarg = 'filename'

		recursive_paths = []
		for p in paths:
			if isinstance(p, basestring):
				recursive_paths.extend(_recursive_file_list(p))
			else:
				recursive_paths.append(p)

		for p in recursive_paths:
			if isinstance(p, basestring):
				f = None
				try:
					f = io.open(_unicode_encode(p,
						encoding=_encodings['fs'], errors='strict'),
						mode='r', encoding=_encodings['repo.content'],
						errors='replace')
				except EnvironmentError:
					pass
				else:
					# The 'source' keyword argument is needed since otherwise
					# ConfigParser in Python <3.3.3 may throw a TypeError
					# because it assumes that f.name is a native string rather
					# than binary when constructing error messages.
					kwargs = {source_kwarg: p}
					read_file(f, **portage._native_kwargs(kwargs))
				finally:
					if f is not None:
						f.close()
			elif isinstance(p, io.StringIO):
				kwargs = {source_kwarg: "<io.StringIO>"}
				read_file(p, **portage._native_kwargs(kwargs))
			else:
				raise TypeError("Unsupported type %r of element %r of 'paths' argument" % (type(p), p))

		prepos['DEFAULT'] = RepoConfig("DEFAULT",
			parser.defaults(), local_config=local_config)

		for sname in parser.sections():
			optdict = {}
			for oname in parser.options(sname):
				optdict[oname] = parser.get(sname, oname)

			repo = RepoConfig(sname, optdict, local_config=local_config)

			# Perform repos.conf sync variable validation
			portage.sync.validate_config(repo, logging)

			# For backward compatibility with locations set via PORTDIR and
			# PORTDIR_OVERLAY, delay validation of the location and repo.name
			# until after PORTDIR and PORTDIR_OVERLAY have been processed.
			prepos[sname] = repo
Exemplo n.º 9
0
	def _parse(paths, prepos, ignored_map, ignored_location_map, local_config, portdir):
		"""Parse files in paths to load config"""
		parser = SafeConfigParser()

		# use read_file/readfp in order to control decoding of unicode
		try:
			# Python >=3.2
			read_file = parser.read_file
			source_kwarg = 'source'
		except AttributeError:
			read_file = parser.readfp
			source_kwarg = 'filename'

		recursive_paths = []
		for p in paths:
			if isinstance(p, basestring):
				recursive_paths.extend(_recursive_file_list(p))
			else:
				recursive_paths.append(p)

		for p in recursive_paths:
			if isinstance(p, basestring):
				f = None
				try:
					f = io.open(_unicode_encode(p,
						encoding=_encodings['fs'], errors='strict'),
						mode='r', encoding=_encodings['repo.content'],
						errors='replace')
				except EnvironmentError:
					pass
				else:
					# The 'source' keyword argument is needed since otherwise
					# ConfigParser in Python <3.3.3 may throw a TypeError
					# because it assumes that f.name is a native string rather
					# than binary when constructing error messages.
					kwargs = {source_kwarg: p}
					read_file(f, **portage._native_kwargs(kwargs))
				finally:
					if f is not None:
						f.close()
			elif isinstance(p, io.StringIO):
				kwargs = {source_kwarg: "<io.StringIO>"}
				read_file(p, **portage._native_kwargs(kwargs))
			else:
				raise TypeError("Unsupported type %r of element %r of 'paths' argument" % (type(p), p))

		prepos['DEFAULT'] = RepoConfig("DEFAULT",
			parser.defaults(), local_config=local_config)

		for sname in parser.sections():
			optdict = {}
			for oname in parser.options(sname):
				optdict[oname] = parser.get(sname, oname)

			repo = RepoConfig(sname, optdict, local_config=local_config)

			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

			# For backward compatibility with locations set via PORTDIR and
			# PORTDIR_OVERLAY, delay validation of the location and repo.name
			# until after PORTDIR and PORTDIR_OVERLAY have been processed.
			prepos[sname] = repo
Exemplo n.º 10
0
	def _parse(paths, prepos, ignored_map, ignored_location_map, local_config, portdir, default_opts):
		"""Parse files in paths to load config"""
		parser = SafeConfigParser(defaults=default_opts)

		# use read_file/readfp in order to control decoding of unicode
		try:
			# Python >=3.2
			read_file = parser.read_file
			source_kwarg = 'source'
		except AttributeError:
			read_file = parser.readfp
			source_kwarg = 'filename'

		recursive_paths = []
		for p in paths:
			if isinstance(p, basestring):
				recursive_paths.extend(_recursive_file_list(p))
			else:
				recursive_paths.append(p)

		for p in recursive_paths:
			if isinstance(p, basestring):
				f = None
				try:
					f = io.open(_unicode_encode(p,
						encoding=_encodings['fs'], errors='strict'),
						mode='r', encoding=_encodings['repo.content'],
						errors='replace')
				except EnvironmentError:
					pass
				else:
					# The 'source' keyword argument is needed since otherwise
					# ConfigParser in Python <3.3.3 may throw a TypeError
					# because it assumes that f.name is a native string rather
					# than binary when constructing error messages.
					kwargs = {source_kwarg: p}
					read_file(f, **portage._native_kwargs(kwargs))
				finally:
					if f is not None:
						f.close()
			elif isinstance(p, io.StringIO):
				kwargs = {source_kwarg: "<io.StringIO>"}
				read_file(p, **portage._native_kwargs(kwargs))
			else:
				raise TypeError("Unsupported type %r of element %r of 'paths' argument" % (type(p), p))

		prepos['DEFAULT'] = RepoConfig("DEFAULT",
			parser.defaults(), local_config=local_config)

		for sname in parser.sections():
			optdict = {}
			for oname in parser.options(sname):
				optdict[oname] = parser.get(sname, oname)

			repo = RepoConfig(sname, optdict, local_config=local_config)
			for o in portage.sync.module_specific_options(repo):
				repo.set_module_specific_opt(o, parser.get(sname, o))

			# Perform repos.conf sync variable validation
			portage.sync.validate_config(repo, logging)

			# For backward compatibility with locations set via PORTDIR and
			# PORTDIR_OVERLAY, delay validation of the location and repo.name
			# until after PORTDIR and PORTDIR_OVERLAY have been processed.
			prepos[sname] = repo
Exemplo n.º 11
0
    def _parse(paths, prepos, ignored_map, ignored_location_map, local_config,
               portdir):
        """Parse files in paths to load config"""
        parser = SafeConfigParser()

        # use read_file/readfp in order to control decoding of unicode
        try:
            # Python >=3.2
            read_file = parser.read_file
            source_kwarg = 'source'
        except AttributeError:
            read_file = parser.readfp
            source_kwarg = 'filename'

        recursive_paths = []
        for p in paths:
            if isinstance(p, basestring):
                recursive_paths.extend(_recursive_file_list(p))
            else:
                recursive_paths.append(p)

        for p in recursive_paths:
            if isinstance(p, basestring):
                f = None
                try:
                    f = io.open(_unicode_encode(p,
                                                encoding=_encodings['fs'],
                                                errors='strict'),
                                mode='r',
                                encoding=_encodings['repo.content'],
                                errors='replace')
                except EnvironmentError:
                    pass
                else:
                    # The 'source' keyword argument is needed since otherwise
                    # ConfigParser in Python <3.3.3 may throw a TypeError
                    # because it assumes that f.name is a native string rather
                    # than binary when constructing error messages.
                    kwargs = {source_kwarg: p}
                    read_file(f, **portage._native_kwargs(kwargs))
                finally:
                    if f is not None:
                        f.close()
            elif isinstance(p, io.StringIO):
                kwargs = {source_kwarg: "<io.StringIO>"}
                read_file(p, **portage._native_kwargs(kwargs))
            else:
                raise TypeError(
                    "Unsupported type %r of element %r of 'paths' argument" %
                    (type(p), p))

        prepos['DEFAULT'] = RepoConfig("DEFAULT",
                                       parser.defaults(),
                                       local_config=local_config)

        for sname in parser.sections():
            optdict = {}
            for oname in parser.options(sname):
                optdict[oname] = parser.get(sname, oname)

            repo = RepoConfig(sname, optdict, local_config=local_config)

            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

            # For backward compatibility with locations set via PORTDIR and
            # PORTDIR_OVERLAY, delay validation of the location and repo.name
            # until after PORTDIR and PORTDIR_OVERLAY have been processed.
            prepos[sname] = repo
Exemplo n.º 12
0
def emirrordist_main(args):

	# The calling environment is ignored, so the program is
	# completely controlled by commandline arguments.
	env = {}

	if not sys.stdout.isatty():
		portage.output.nocolor()
		env['NOCOLOR'] = 'true'

	parser, options, args = parse_args(args)

	if options.version:
		sys.stdout.write("Portage[mgorny] %s\n" % portage.VERSION)
		return os.EX_OK

	config_root = options.config_root

	if options.repositories_configuration is not None:
		env['PORTAGE_REPOSITORIES'] = options.repositories_configuration

	settings = portage.config(config_root=config_root,
		local_config=False, env=env)

	default_opts = None
	if not options.ignore_default_opts:
		default_opts = settings.get('EMIRRORDIST_DEFAULT_OPTS', '').split()

	if default_opts:
		parser, options, args = parse_args(default_opts + args)

		settings = portage.config(config_root=config_root,
			local_config=False, env=env)

	if options.repo is None:
		if len(settings.repositories.prepos) == 2:
			for repo in settings.repositories:
				if repo.name != "DEFAULT":
					options.repo = repo.name
					break

		if options.repo is None:
			parser.error("--repo option is required")

	repo_path = settings.repositories.treemap.get(options.repo)
	if repo_path is None:
		parser.error("Unable to locate repository named '%s'" % (options.repo,))

	if options.jobs is not None:
		options.jobs = int(options.jobs)

	if options.load_average is not None:
		options.load_average = float(options.load_average)

	if options.failure_log is not None:
		options.failure_log = normalize_path(
			os.path.abspath(options.failure_log))

		parent_dir = os.path.dirname(options.failure_log)
		if not (os.path.isdir(parent_dir) and
			os.access(parent_dir, os.W_OK|os.X_OK)):
			parser.error(("--failure-log '%s' parent is not a "
				"writable directory") % options.failure_log)

	if options.success_log is not None:
		options.success_log = normalize_path(
			os.path.abspath(options.success_log))

		parent_dir = os.path.dirname(options.success_log)
		if not (os.path.isdir(parent_dir) and
			os.access(parent_dir, os.W_OK|os.X_OK)):
			parser.error(("--success-log '%s' parent is not a "
				"writable directory") % options.success_log)

	if options.scheduled_deletion_log is not None:
		options.scheduled_deletion_log = normalize_path(
			os.path.abspath(options.scheduled_deletion_log))

		parent_dir = os.path.dirname(options.scheduled_deletion_log)
		if not (os.path.isdir(parent_dir) and
			os.access(parent_dir, os.W_OK|os.X_OK)):
			parser.error(("--scheduled-deletion-log '%s' parent is not a "
				"writable directory") % options.scheduled_deletion_log)

		if options.deletion_db is None:
			parser.error("--scheduled-deletion-log requires --deletion-db")

	if options.deletion_delay is not None:
		options.deletion_delay = long(options.deletion_delay)
		if options.deletion_db is None:
			parser.error("--deletion-delay requires --deletion-db")

	if options.deletion_db is not None:
		if options.deletion_delay is None:
			parser.error("--deletion-db requires --deletion-delay")
		options.deletion_db = normalize_path(
			os.path.abspath(options.deletion_db))

	if options.temp_dir is not None:
		options.temp_dir = normalize_path(
			os.path.abspath(options.temp_dir))

		if not (os.path.isdir(options.temp_dir) and
			os.access(options.temp_dir, os.W_OK|os.X_OK)):
			parser.error(("--temp-dir '%s' is not a "
				"writable directory") % options.temp_dir)

	if options.distfiles is not None:
		options.distfiles = normalize_path(
			os.path.abspath(options.distfiles))

		if not (os.path.isdir(options.distfiles) and
			os.access(options.distfiles, os.W_OK|os.X_OK)):
			parser.error(("--distfiles '%s' is not a "
				"writable directory") % options.distfiles)
	else:
		parser.error("missing required --distfiles parameter")

	if options.mirror_overrides is not None:
		options.mirror_overrides = normalize_path(
			os.path.abspath(options.mirror_overrides))

		if not (os.access(options.mirror_overrides, os.R_OK) and
			os.path.isfile(options.mirror_overrides)):
			parser.error(
				"--mirror-overrides-file '%s' is not a readable file" %
				options.mirror_overrides)

	if options.distfiles_local is not None:
		options.distfiles_local = normalize_path(
			os.path.abspath(options.distfiles_local))

		if not (os.path.isdir(options.distfiles_local) and
			os.access(options.distfiles_local, os.W_OK|os.X_OK)):
			parser.error(("--distfiles-local '%s' is not a "
				"writable directory") % options.distfiles_local)

	if options.distfiles_db is not None:
		options.distfiles_db = normalize_path(
			os.path.abspath(options.distfiles_db))

	if options.tries is not None:
		options.tries = int(options.tries)

	if options.recycle_dir is not None:
		options.recycle_dir = normalize_path(
			os.path.abspath(options.recycle_dir))
		if not (os.path.isdir(options.recycle_dir) and
			os.access(options.recycle_dir, os.W_OK|os.X_OK)):
			parser.error(("--recycle-dir '%s' is not a "
				"writable directory") % options.recycle_dir)

	if options.recycle_db is not None:
		if options.recycle_dir is None:
			parser.error("--recycle-db requires "
				"--recycle-dir to be specified")
		options.recycle_db = normalize_path(
			os.path.abspath(options.recycle_db))

	if options.recycle_deletion_delay is not None:
		options.recycle_deletion_delay = \
			long(options.recycle_deletion_delay)

	if options.fetch_log_dir is not None:
		options.fetch_log_dir = normalize_path(
			os.path.abspath(options.fetch_log_dir))

		if not (os.path.isdir(options.fetch_log_dir) and
			os.access(options.fetch_log_dir, os.W_OK|os.X_OK)):
			parser.error(("--fetch-log-dir '%s' is not a "
				"writable directory") % options.fetch_log_dir)

	if options.whitelist_from:
		normalized_paths = []
		for x in options.whitelist_from:
			path = normalize_path(os.path.abspath(x))
			if not os.access(path, os.R_OK):
				parser.error("--whitelist-from '%s' is not readable" % x)
			if os.path.isfile(path):
				normalized_paths.append(path)
			elif os.path.isdir(path):
				for file in _recursive_file_list(path):
					if not os.access(file, os.R_OK):
						parser.error("--whitelist-from '%s' directory contains not readable file '%s'" % (x, file))
					normalized_paths.append(file)
			else:
				parser.error("--whitelist-from '%s' is not a regular file or a directory" % x)
		options.whitelist_from = normalized_paths

	if options.strict_manifests is not None:
		if options.strict_manifests == "y":
			settings.features.add("strict")
		else:
			settings.features.discard("strict")

	settings.lock()

	portdb = portage.portdbapi(mysettings=settings)

	# Limit ebuilds to the specified repo.
	portdb.porttrees = [repo_path]

	portage.util.initialize_logger()

	if options.verbose > 0:
		l = logging.getLogger()
		l.setLevel(l.getEffectiveLevel() - 10 * options.verbose)

	with Config(options, portdb,
		SchedulerInterface(global_event_loop())) as config:

		if not options.mirror:
			parser.error('No action specified')

		returncode = os.EX_OK

		if options.mirror:
			signum = run_main_scheduler(MirrorDistTask(config))
			if signum is not None:
				sys.exit(128 + signum)

	return returncode