#!/usr/bin/python -O
# Copyright 1999-2006 Gentoo Foundation
# Distributed under the terms of the GNU General Public License v2
# $Id$

import sys
# This block ensures that ^C interrupts are handled quietly.
try:
	import signal

	def exithandler(signum, frame):
		signal.signal(signal.SIGINT, signal.SIG_IGN)
		signal.signal(signal.SIGTERM, signal.SIG_IGN)
		sys.exit(1)

	signal.signal(signal.SIGINT, exithandler)
	signal.signal(signal.SIGTERM, exithandler)

except KeyboardInterrupt:
	sys.exit(1)

import os

import types

# Avoid sandbox violations after python upgrade.
pym_path = os.path.join(os.path.dirname(
	os.path.dirname(os.path.realpath(__file__))), "pym")
if os.environ.get("SANDBOX_ON") == "1":
	sandbox_write = os.environ.get("SANDBOX_WRITE", "").split(":")
	if pym_path not in sandbox_write:
		sandbox_write.append(pym_path)
		os.environ["SANDBOX_WRITE"] = \
			":".join(filter(None, sandbox_write))
	del sandbox_write

try:
	import portage
except ImportError:
	sys.path.insert(0, pym_path)
	import portage
del pym_path

from portage import os
from portage.util import writemsg, writemsg_stdout

#-----------------------------------------------------------------------------
#
# To add functionality to this tool, add a function below.
#
# The format for functions is:
#
#   def function(argv):
#       """<list of options for this function>
#       <description of the function>
#       """
#       <code>
#
# "argv" is an array of the command line parameters provided after the command.
#
# Make sure you document the function in the right format.  The documentation
# is used to display help on the function.
#
# You do not need to add the function to any lists, this tool is introspective,
# and will automaticly add a command by the same name as the function!
#

def has_version(argv):
	"""<root> <category/package>
	Return code 0 if it's available, 1 otherwise.
	"""
	if (len(argv) < 2):
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	if atom_validate_strict and not portage.isvalidatom(argv[1]):
		portage.writemsg("ERROR: Invalid atom: '%s'\n" % argv[1],
			noiselevel=-1)
		return 2
	try:
		mylist=portage.db[argv[0]]["vartree"].dbapi.match(argv[1])
		if mylist:
			sys.exit(0)
		else:
			sys.exit(1)
	except KeyError:
		sys.exit(1)
has_version.uses_root = True


def best_version(argv):
	"""<root> <category/package>
	Returns category/package-version (without .ebuild).
	"""
	if (len(argv) < 2):
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	if atom_validate_strict and not portage.isvalidatom(argv[1]):
		portage.writemsg("ERROR: Invalid atom: '%s'\n" % argv[1],
			noiselevel=-1)
		return 2
	try:
		mylist=portage.db[argv[0]]["vartree"].dbapi.match(argv[1])
		print portage.best(mylist)
	except KeyError:
		sys.exit(1)
best_version.uses_root = True


def mass_best_version(argv):
	"""<root> [<category/package>]+
	Returns category/package-version (without .ebuild).
	"""
	if (len(argv) < 2):
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	try:
		for pack in argv[1:]:
			mylist=portage.db[argv[0]]["vartree"].dbapi.match(pack)
			print pack+":"+portage.best(mylist)
	except KeyError:
		sys.exit(1)
mass_best_version.uses_root = True

def metadata(argv):
	"""<root> <pkgtype> <category/package> [<key>]+
	Returns metadata values for the specified package.
	"""
	if (len(argv) < 4):
		print >> sys.stderr, "ERROR: insufficient parameters!"
		sys.exit(2)

	root, pkgtype, pkgspec = argv[0:3]
	metakeys = argv[3:]
	type_map = {
		"ebuild":"porttree",
		"binary":"bintree",
		"installed":"vartree"}
	if pkgtype not in type_map:
		print >> sys.stderr, "Unrecognized package type: '%s'" % pkgtype
		sys.exit(1)
	trees = portage.db
	if os.path.realpath(root) == os.path.realpath(portage.settings["ROOT"]):
		root = portage.settings["ROOT"] # contains the normalized $ROOT
	try:
			values = trees[root][type_map[pkgtype]].dbapi.aux_get(
				pkgspec, metakeys)
			writemsg_stdout(''.join('%s\n' % x for x in values), noiselevel=-1)
	except KeyError:
		print >> sys.stderr, "Package not found: '%s'" % pkgspec
		sys.exit(1)

metadata.uses_root = True

def contents(argv):
	"""<root> <category/package>
	List the files that are installed for a given package, with
	one file listed on each line. All file names will begin with
	<root>.
	"""
	if len(argv) != 2:
		print "ERROR: expected 2 parameters, got %d!" % len(argv)
		return 2

	root, cpv = argv
	vartree = portage.db[root]["vartree"]
	if not vartree.dbapi.cpv_exists(cpv):
		sys.stderr.write("Package not found: '%s'\n" % cpv)
		return 1
	cat, pkg = portage.catsplit(cpv)
	db = portage.dblink(cat, pkg, root, vartree.settings,
		treetype="vartree", vartree=vartree)
	writemsg_stdout(''.join('%s\n' % x for x in sorted(db.getcontents())),
		noiselevel=-1)
contents.uses_root = True

def owners(argv):
	"""<root> [<filename>]+
	Given a list of files, print the packages that own the files and which
	files belong to each package. Files owned by a package are listed on
	the lines below it, indented by a single tab character (\\t). All file
	paths must either start with <root> or be a basename alone.
	Returns 1 if no owners could be found, and 0 otherwise.
	"""
	if len(argv) < 2:
		sys.stderr.write("ERROR: insufficient parameters!\n")
		sys.stderr.flush()
		return 2

	from portage import catsplit, dblink
	settings = portage.settings
	root = settings["ROOT"]
	vardb = portage.db[root]["vartree"].dbapi

	cwd = None
	try:
		cwd = os.getcwd()
	except OSError:
		pass

	files = []
	for f in argv[1:]:
		f = portage.normalize_path(f)
		is_basename = os.sep not in f
		if not is_basename and f[:1] != os.sep:
			if cwd is None:
				sys.stderr.write("ERROR: cwd does not exist!\n")
				sys.stderr.flush()
				return 2
			f = os.path.join(cwd, f)
			f = portage.normalize_path(f)
		if not is_basename and not f.startswith(root):
			sys.stderr.write("ERROR: file paths must begin with <root>!\n")
			sys.stderr.flush()
			return 2
		if is_basename:
			files.append(f)
		else:
			files.append(f[len(root)-1:])

	owners = vardb._owners.get_owners(files)

	msg = []
	for pkg, owned_files in owners.iteritems():
		cpv = pkg.mycpv
		msg.append("%s\n" % cpv)
		for f in sorted(owned_files):
			msg.append("\t%s\n" % \
				os.path.join(root, f.lstrip(os.path.sep)))

	writemsg_stdout(''.join(msg), noiselevel=-1)

	if owners:
		return 0

	sys.stderr.write("None of the installed packages claim the file(s).\n")
	sys.stderr.flush()
	return 1

owners.uses_root = True

def is_protected(argv):
	"""<root> <filename>
	Given a single filename, return code 0 if it's protected, 1 otherwise.
	The filename must begin with <root>.
	"""
	if len(argv) != 2:
		sys.stderr.write("ERROR: expected 2 parameters, got %d!\n" % len(argv))
		sys.stderr.flush()
		return 2

	root, filename = argv

	err = sys.stderr
	cwd = None
	try:
		cwd = os.getcwd()
	except OSError:
		pass

	f = portage.normalize_path(filename)
	if not f.startswith(os.path.sep):
		if cwd is None:
			err.write("ERROR: cwd does not exist!\n")
			err.flush()
			return 2
		f = os.path.join(cwd, f)
		f = portage.normalize_path(f)

	if not f.startswith(root):
		err.write("ERROR: file paths must begin with <root>!\n")
		err.flush()
		return 2

	from portage.util import ConfigProtect

	settings = portage.settings
	protect = portage.util.shlex_split(settings.get("CONFIG_PROTECT", ""))
	protect_mask = portage.util.shlex_split(
		settings.get("CONFIG_PROTECT_MASK", ""))
	protect_obj = ConfigProtect(root, protect, protect_mask)

	if protect_obj.isprotected(f):
		return 0
	return 1

is_protected.uses_root = True

def filter_protected(argv):
	"""<root>
	Read filenames from stdin and write them to stdout if they are protected.
	All filenames are delimited by \\n and must begin with <root>.
	"""
	if len(argv) != 1:
		sys.stderr.write("ERROR: expected 1 parameter, got %d!\n" % len(argv))
		sys.stderr.flush()
		return 2

	root, = argv
	out = sys.stdout
	err = sys.stderr
	cwd = None
	try:
		cwd = os.getcwd()
	except OSError:
		pass

	from portage.util import ConfigProtect

	settings = portage.settings
	protect = portage.util.shlex_split(settings.get("CONFIG_PROTECT", ""))
	protect_mask = portage.util.shlex_split(
		settings.get("CONFIG_PROTECT_MASK", ""))
	protect_obj = ConfigProtect(root, protect, protect_mask)

	protected = 0
	errors = 0

	for line in sys.stdin:
		filename = line.rstrip("\n")
		f = portage.normalize_path(filename)
		if not f.startswith(os.path.sep):
			if cwd is None:
				err.write("ERROR: cwd does not exist!\n")
				err.flush()
				errors += 1
				continue
			f = os.path.join(cwd, f)
			f = portage.normalize_path(f)

		if not f.startswith(root):
			err.write("ERROR: file paths must begin with <root>!\n")
			err.flush()
			errors += 1
			continue

		if protect_obj.isprotected(f):
			protected += 1
			out.write("%s\n" % filename)
	out.flush()

	if errors:
		return 2

	return 0

filter_protected.uses_root = True

def best_visible(argv):
	"""<root> [<category/package>]+
	Returns category/package-version (without .ebuild).
	"""
	if (len(argv) < 2):
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	try:
		mylist=portage.db[argv[0]]["porttree"].dbapi.match(argv[1])
		visible=portage.best(mylist)
		if visible:
			print visible
			sys.exit(0)
		else:
			sys.exit(1)
	except KeyError:
		sys.exit(1)
best_visible.uses_root = True


def mass_best_visible(argv):
	"""<root> [<category/package>]+
	Returns category/package-version (without .ebuild).
	"""
	if (len(argv) < 2):
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	try:
		for pack in argv[1:]:
			mylist=portage.db[argv[0]]["porttree"].dbapi.match(pack)
			print pack+":"+portage.best(mylist)
	except KeyError:
		sys.exit(1)
mass_best_visible.uses_root = True


def all_best_visible(argv):
	"""<root>
	Returns all best_visible packages (without .ebuild).
	"""
	if (len(argv) < 1):
		print "ERROR: insufficient parameters!"
	
	#print portage.db[argv[0]]["porttree"].dbapi.cp_all()
	for pkg in portage.db[argv[0]]["porttree"].dbapi.cp_all():
		mybest=portage.best(portage.db[argv[0]]["porttree"].dbapi.match(pkg))
		if mybest:
			print mybest
all_best_visible.uses_root = True


def match(argv):
	"""<root> <atom>
	Returns a \\n separated list of category/package-version.
	When given an empty string, all installed packages will
	be listed.
	"""
	if len(argv) != 2:
		print "ERROR: expected 2 parameters, got %d!" % len(argv)
		sys.exit(2)
	root, atom = argv
	if atom:
		if atom_validate_strict and not portage.isvalidatom(atom):
			portage.writemsg("ERROR: Invalid atom: '%s'\n" % atom,
				noiselevel=-1)
			return 2
		results = portage.db[root]["vartree"].dbapi.match(atom)
	else:
		results = portage.db[root]["vartree"].dbapi.cpv_all()
		results.sort()
	for cpv in results:
		print cpv
match.uses_root = True


def vdb_path(argv):
	"""
	Returns the path used for the var(installed) package database for the
	set environment/configuration options.
	"""
	out = sys.stdout
	out.write(os.path.join(portage.settings["ROOT"], portage.VDB_PATH) + "\n")
	out.flush()
	return os.EX_OK

def gentoo_mirrors(argv):
	"""
	Returns the mirrors set to use in the portage configuration.
	"""
	print portage.settings["GENTOO_MIRRORS"]


def portdir(argv):
	"""
	Returns the PORTDIR path.
	"""
	print portage.settings["PORTDIR"]


def config_protect(argv):
	"""
	Returns the CONFIG_PROTECT paths.
	"""
	print portage.settings["CONFIG_PROTECT"]


def config_protect_mask(argv):
	"""
	Returns the CONFIG_PROTECT_MASK paths.
	"""
	print portage.settings["CONFIG_PROTECT_MASK"]


def portdir_overlay(argv):
	"""
	Returns the PORTDIR_OVERLAY path.
	"""
	print portage.settings["PORTDIR_OVERLAY"]


def pkgdir(argv):
	"""
	Returns the PKGDIR path.
	"""
	print portage.settings["PKGDIR"]


def distdir(argv):
	"""
	Returns the DISTDIR path.
	"""
	print portage.settings["DISTDIR"]


def envvar(argv):
	"""<variable>+
	Returns a specific environment variable as exists prior to ebuild.sh.
	Similar to: emerge --verbose --info | egrep '^<variable>='
	"""
	verbose = "-v" in argv
	if verbose:
		argv.pop(argv.index("-v"))

	if len(argv) == 0:
		print "ERROR: insufficient parameters!"
		sys.exit(2)

	for arg in argv:
		if verbose:
			print arg +"='"+ portage.settings[arg] +"'"
		else:
			print portage.settings[arg]

def get_repos(argv):
	"""<root>
	Returns all repos with names (repo_name file) argv[0] = $ROOT
	"""
	if len(argv) < 1:
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	print " ".join(portage.db[argv[0]]["porttree"].dbapi.getRepositories())

def get_repo_path(argv):
	"""<root> <repo_id>+
	Returns the path to the repo named argv[1], argv[0] = $ROOT
	"""
	if len(argv) < 2:
		print "ERROR: insufficient parameters!"
		sys.exit(2)
	for arg in argv[1:]:
		print portage.db[argv[0]]["porttree"].dbapi.getRepositoryPath(arg)

def list_preserved_libs(argv):
	"""<root>
	Print a list of libraries preserved during a package update in the form
	package: path. Returns 0 if no preserved libraries could be found, 
	1 otherwise.
	"""

	if len(argv) != 1:
		print "ERROR: wrong number of arguments"
		sys.exit(2)
	mylibs = portage.db[argv[0]]["vartree"].dbapi.plib_registry.getPreservedLibs()
	rValue = 0
	msg = []
	for cpv in sorted(mylibs):
		msg.append(cpv)
		for path in mylibs[cpv]:
			msg.append(' ' + path)
			rValue = 1
		msg.append('\n')
	writemsg_stdout(''.join(msg), noiselevel=-1)
	return rValue
list_preserved_libs.uses_root = True

#-----------------------------------------------------------------------------
#
# DO NOT CHANGE CODE BEYOND THIS POINT - IT'S NOT NEEDED!
#

def usage(argv):
	print ">>> Portage information query tool"
	print ">>> $Id$"
	print ">>> Usage: portageq <command> [<option> ...]"
	print ""
	print "Available commands:"

	#
	# Show our commands -- we do this by scanning the functions in this
	# file, and formatting each functions documentation.
	#
	non_commands = frozenset(['exithandler', 'main',
		'usage', 'writemsg', 'writemsg_stdout'])
	commands = sorted(k for k, v in globals().iteritems() \
		if type(v) is types.FunctionType and k not in non_commands)

	for name in commands:
		# Drop non-functions
		obj = globals()[name]

		doc = obj.__doc__
		if (doc == None):
			print "   "+name
			print "      MISSING DOCUMENTATION!"
			print ""
			continue

		lines = doc.split("\n")
		print "   "+name+" "+lines[0].strip()
		if (len(sys.argv) > 1):
			if ("--help" not in sys.argv):
				lines = lines[:-1]
			for line in lines[1:]:
				print "      "+line.strip()
	if (len(sys.argv) == 1):
		print "\nRun portageq with --help for info"

atom_validate_strict = "EBUILD_PHASE" in os.environ

def main():
	if "-h" in sys.argv or "--help" in sys.argv:
		usage(sys.argv)
		sys.exit(os.EX_OK)
	elif len(sys.argv) < 2:
		usage(sys.argv)
		sys.exit(os.EX_USAGE)

	cmd = sys.argv[1]
	function = globals().get(cmd)
	if function is None:
		usage(sys.argv)
		sys.exit(os.EX_USAGE)
	function = globals()[cmd]
	uses_root = getattr(function, "uses_root", False) and len(sys.argv) > 2
	if uses_root:
		if not os.path.isdir(sys.argv[2]):
			sys.stderr.write("Not a directory: '%s'\n" % sys.argv[2])
			sys.stderr.write("Run portageq with --help for info\n")
			sys.stderr.flush()
			sys.exit(os.EX_USAGE)
		os.environ["ROOT"] = sys.argv[2]

	args = sys.argv[2:]
	if args and not isinstance(args[0], unicode):
		for i in xrange(len(args)):
			args[i] = portage._unicode_decode(args[i])

	try:
		if uses_root:
			args[0] = portage.settings["ROOT"]
		retval = function(args)
		if retval:
			sys.exit(retval)
	except portage.exception.PermissionDenied, e:
		sys.stderr.write("Permission denied: '%s'\n" % str(e))
		sys.exit(e.errno)
	except portage.exception.ParseError, e:
		sys.stderr.write("%s\n" % str(e))
		sys.exit(1)
	except ValueError, e:
		if not e.args or \
			not hasattr(e.args[0], "__len__") or \
			len(e.args[0]) < 2:
			raise
		# Multiple matches thrown from cpv_expand
		pkgs = e.args[0]
		# An error has occurred so we writemsg to stderr and exit nonzero.
		portage.writemsg("You specified an unqualified atom that matched multiple packages:\n", noiselevel=-1)
		for pkg in pkgs:
			portage.writemsg("* %s\n" % pkg, noiselevel=-1)
		portage.writemsg("\nPlease use a more specific atom.\n", noiselevel=-1)
		sys.exit(1)

main()

#-----------------------------------------------------------------------------
