public inbox for gentoo-portage-dev@lists.gentoo.org
 help / color / mirror / Atom feed
From: Marius Mauch <genone@gentoo.org>
To: gentoo-portage-dev@lists.gentoo.org
Subject: [gentoo-portage-dev] [PATCH] elog-base
Date: Sat, 22 Oct 2005 17:08:38 +0200	[thread overview]
Message-ID: <20051022170838.0043deb4@sven.genone.homeip.net> (raw)


[-- Attachment #1.1: Type: text/plain, Size: 865 bytes --]

First patch for elog integration in 2.0.x adding the basic elog
framework without the actual modules, config samples or other docs. The
code is mostly unchanged from the 2.1 branch and only lightly tested
on 2.0. Known issues with this patch:
- needs better integration of isolated-functions.sh, probably should be
a separate patch (Brian?)
- module loader should be improved somehow (low priority)
- logging currenty only occurs after successful merges
- probably more that I can't remember atm

Later patches will add the actual logging modules and make.*
enhancements, maybe also python logging (for einfo style messages) and
support tools.

Marius

-- 
Public Key at http://www.genone.de/info/gpg-key.pub

In the beginning, there was nothing. And God said, 'Let there be
Light.' And there was still nothing, but you could see a bit better.

[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.2: portage-2.0.53-elog-base.patch --]
[-- Type: text/x-patch; name=portage-2.0.53-elog-base.patch, Size: 8553 bytes --]

Index: pym/portage.py
===================================================================
--- pym/portage.py	(revision 2155)
+++ pym/portage.py	(working copy)
@@ -454,6 +454,57 @@
 			mygraph.okeys=self.okeys[:]
 		return mygraph
 
+def elog_process(cpv, mysettings):
+	mylogfiles = listdir(mysettings["T"]+"/logging/")
+	# shortcut for packages without any messages
+	if len(mylogfiles) == 0:
+		return
+	# exploit listdir() file order so we process log entries in cronological order
+	mylogfiles.reverse()
+	mylogentries = {}
+	for f in mylogfiles:
+		msgfunction, msgtype = f.split(".")
+		if not msgtype.upper() in mysettings["PORTAGE_ELOG_CLASSES"].split() \
+				and not msgtype.lower() in mysettings["PORTAGE_ELOG_CLASSES"].split():
+			continue
+		if msgfunction not in portage_const.EBUILD_PHASES.split():
+			print "!!! can't process invalid log file: %s" % f
+			continue
+		if not msgfunction in mylogentries:
+			mylogentries[msgfunction] = []
+		msgcontent = open(mysettings["T"]+"/logging/"+f, "r").readlines()
+		mylogentries[msgfunction].append((msgtype, msgcontent))
+
+	# in case the filters matched all messages
+	if len(mylogentries) == 0:
+		return
+
+	# generate a single string with all log messages
+	fulllog = ""
+	for phase in portage_const.EBUILD_PHASES.split():
+		if not phase in mylogentries:
+			continue
+		for msgtype,msgcontent in mylogentries[phase]:
+			fulllog += "%s: %s\n" % (msgtype, phase)
+			for line in msgcontent:
+				fulllog += line
+			fulllog += "\n"
+
+	# pass the processing to the individual modules
+	logsystems = mysettings["PORTAGE_ELOG_SYSTEM"].split()
+	for s in logsystems:
+		try:
+			# FIXME: ugly ad.hoc import code
+			# TODO:  implement a common portage module loader
+			logmodule = __import__("elog_modules.mod_"+s)
+			m = getattr(logmodule, "mod_"+s)
+			m.process(mysettings, cpv, mylogentries, fulllog)
+		except (ImportError, AttributeError), e:
+			print "!!! Error while importing logging modules:"
+			print e
+		except portage_exception.PortageException, e:
+			print e
+
 # valid end of version components; integers specify offset from release version
 # pre=prerelease, p=patchlevel (should always be followed by an int), rc=release candidate
 # all but _p (where it is required) can be followed by an optional trailing integer
@@ -2505,6 +2556,12 @@
 			os.chown(mysettings["T"],portage_uid,portage_gid)
 			os.chmod(mysettings["T"],02770)
 
+		logdir = mysettings["T"]+"/logging"
+		if not os.path.exists(logdir):
+			os.makedirs(logdir)
+		os.chown(logdir, portage_uid, portage_gid)
+		os.chmod(logdir, 0770)
+
 		try: # XXX: negative RESTRICT
 			if not (("nouserpriv" in string.split(mysettings["PORTAGE_RESTRICT"])) or \
 			   ("userpriv" in string.split(mysettings["PORTAGE_RESTRICT"]))):
@@ -6679,6 +6736,10 @@
 		if dircache.has_key(self.dbcatdir):
 			del dircache[self.dbcatdir]
 		print ">>>",self.mycpv,"merged."
+
+		# Process ebuild logfiles
+		elog_process(self.mycpv, self.settings)
+		
 		return 0
 
 	def mergeme(self,srcroot,destroot,outfile,secondhand,stufftomerge,cfgfiledict,thismtime):
Index: pym/portage_const.py
===================================================================
--- pym/portage_const.py	(revision 2155)
+++ pym/portage_const.py	(working copy)
@@ -40,6 +40,8 @@
 SANDBOX_PIDS_FILE       = "/tmp/sandboxpids.tmp"
 CONFIG_MEMORY_FILE      = PRIVATE_PATH + "/config"
 
+EBUILD_PHASES			= "setup unpack compile test install preinst postinst prerm postrm"
+
 INCREMENTALS=["USE","FEATURES","ACCEPT_KEYWORDS","ACCEPT_LICENSE","CONFIG_PROTECT_MASK","CONFIG_PROTECT","PRELINK_PATH","PRELINK_PATH_MASK"]
 STICKIES=["KEYWORDS_ACCEPT","USE","CFLAGS","CXXFLAGS","MAKEOPTS","EXTRA_ECONF","EXTRA_EINSTALL","EXTRA_EMAKE"]
 
Index: bin/isolated-functions.sh
===================================================================
--- bin/isolated-functions.sh	(revision 0)
+++ bin/isolated-functions.sh	(revision 0)
@@ -0,0 +1,204 @@
+# Copyright 1999-2004 Gentoo Technologies, Inc.
+# Distributed under the terms of the GNU General Public License v2
+# $Header$
+
+# Internal logging function, don't use this in ebuilds
+elog_base() {
+	local messagetype
+	[ -z "${1}" -o -z "${T}" -o ! -d "${T}/logging" ] && return 1
+	case "${1}" in
+		INFO|WARN|ERROR|LOG)
+			messagetype="${1}"
+			shift
+			;;
+		*)
+			echo -e " ${BAD}*${NORMAL} Invalid use of internal function elog_base(), next message will not be logged"
+			return 1
+			;;
+	esac
+	echo ${*} >> ${T}/logging/${EBUILD_PHASE}.${messagetype}
+	return 0
+}
+
+elog() {
+	elog_base LOG ${*}
+	echo -e " ${GOOD}*${NORMAL} ${*}"
+	return 0
+}
+
+esyslog() {
+	local pri=
+	local tag=
+	
+	if [ -x /usr/bin/logger ]
+	then
+		pri="$1"
+		tag="$2"
+		
+		shift 2
+		[ -z "$*" ] && return 0
+		
+		/usr/bin/logger -p "${pri}" -t "${tag}" -- "$*"
+	fi
+
+	return 0
+}
+
+einfo() {
+	einfon ${*}
+	echo
+	return 0
+}
+
+einfon() {
+	elog_base INFO ${*}
+	echo -ne " ${GOOD}*${NORMAL} ${*}"
+	return 0
+}
+
+ewarn() {
+	elog_base WARN ${*}
+	echo -e " ${WARN}*${NORMAL} ${*}"
+	return 0
+}
+
+eerror() {
+	elog_base ERROR ${*}
+	echo -e " ${BAD}*${NORMAL} ${*}"
+	return 0
+}
+
+ebegin() {
+	if [ -z "${NOCOLOR}" ]; then
+		echo -ne " ${GOOD}*${NORMAL} ${*}..."
+	else
+		echo -e " ${GOOD}*${NORMAL} ${*}..."
+	fi
+	return 0
+}
+
+eend() {
+	local retval=
+	if [ "$#" -eq 0 ] || [ "${1:-1}" -eq  0 ]; then
+		echo -e "${ENDCOL}  ${BRACKET}[ ${GOOD}ok${BRACKET} ]${NORMAL}"
+	else
+		retval="$1"
+		
+		if [ "$#" -ge 2 ]
+		then
+			shift
+			eerror "${*}"
+		fi
+		echo -e "${ENDCOL}  ${BRACKET}[ ${BAD}!!${BRACKET} ]${NORMAL}"
+		# extra spacing makes it easier to read
+		echo
+		return ${retval}
+	fi
+	return 0
+}
+
+KV_major() {
+	local KV=
+	
+	[ -z "$1" ] && return 1
+
+	KV="$(echo "$1" | \
+		awk '{ tmp = $0; gsub(/^[0-9\.]*/, "", tmp); sub(tmp, ""); print }')"
+	echo "${KV}" | awk -- 'BEGIN { FS = "." } { print $1 }'
+
+	return 0
+}
+
+KV_minor() {
+	local KV=
+	
+	[ -z "$1" ] && return 1
+
+	KV="$(echo "$1" | \
+		awk '{ tmp = $0; gsub(/^[0-9\.]*/, "", tmp); sub(tmp, ""); print }')"
+	echo "${KV}" | awk -- 'BEGIN { FS = "." } { print $2 }'
+
+	return 0
+}
+
+KV_micro() {
+	local KV=
+	
+	[ -z "$1" ] && return 1
+
+	KV="$(echo "$1" | \
+		awk '{ tmp = $0; gsub(/^[0-9\.]*/, "", tmp); sub(tmp, ""); print }')"
+	echo "${KV}" | awk -- 'BEGIN { FS = "." } { print $3 }'
+
+	return 0
+}
+
+KV_to_int() {
+	local KV_MAJOR=
+	local KV_MINOR=
+	local KV_MICRO=
+	local KV_int=
+	
+	[ -z "$1" ] && return 1
+    
+	KV_MAJOR="$(KV_major "$1")"
+	KV_MINOR="$(KV_minor "$1")"
+	KV_MICRO="$(KV_micro "$1")"
+	KV_int="$((KV_MAJOR * 65536 + KV_MINOR * 256 + KV_MICRO))"
+    
+	# We make version 2.2.0 the minimum version we will handle as
+	# a sanity check ... if its less, we fail ...
+	if [ "${KV_int}" -ge 131584 ]
+	then 
+		echo "${KV_int}"
+
+		return 0
+	fi
+
+	return 1
+}   
+
+get_KV() {
+	local KV="$(uname -r)"
+
+	echo "$(KV_to_int "${KV}")"
+
+	return $?
+}
+
+getcols() {
+	echo "$2"
+}
+
+unset_colors() {
+	COLS="25 80"
+	ENDCOL=
+	
+	GOOD=
+	WARN=
+	BAD=
+	NORMAL=
+	HILITE=
+	BRACKET=
+	
+	if [ -n "${EBUILD}" ] && [ "${*/depend}" = "$*" ]; then
+		stty cols 80 &>/dev/null
+		stty rows 25 &>/dev/null
+	fi
+}
+
+set_colors() {
+	COLS="`stty size 2> /dev/null`"
+	COLS="`getcols ${COLS}`"
+	COLS=$((${COLS} - 7))
+	ENDCOL=$'\e[A\e['${COLS}'G'    # Now, ${ENDCOL} will move us to the end of the
+	                               # column;  irregardless of character width
+	
+	GOOD=$'\e[32;01m'
+	WARN=$'\e[33;01m'
+	BAD=$'\e[31;01m'
+	NORMAL=$'\e[0m'
+	HILITE=$'\e[36;01m'
+	BRACKET=$'\e[34;01m'
+}
+true
Index: bin/ebuild.sh
===================================================================
--- bin/ebuild.sh	(revision 2155)
+++ bin/ebuild.sh	(working copy)
@@ -50,8 +50,9 @@
 export PATH="/sbin:/usr/sbin:/usr/lib/portage/bin:/bin:/usr/bin:${ROOTPATH}"
 [ ! -z "$PREROOTPATH" ] && export PATH="${PREROOTPATH%%:}:$PATH"
 
-if [ -e /etc/init.d/functions.sh ]; then
-	source /etc/init.d/functions.sh  &>/dev/null
+if [ -e /usr/lib/portage/bin/isolated-functions.sh ]; then
+	source /usr/lib/portage/bin/isolated-functions.sh  &>/dev/null
+	set_colors
 elif [ -e /etc/rc.d/config/functions ];	then
 	source /etc/rc.d/config/functions &>/dev/null
 else

[-- Attachment #2: Type: application/pgp-signature, Size: 189 bytes --]

             reply	other threads:[~2005-10-22 15:08 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2005-10-22 15:08 Marius Mauch [this message]
2005-10-23  2:54 ` [gentoo-portage-dev] [PATCH] elog-base Jason Stubbs
2005-10-23  9:35   ` Marius Mauch
2005-10-26 14:24   ` Thomas de Grenier de Latour
2005-10-26 14:38     ` Jason Stubbs
2005-10-26 15:07     ` Marius Mauch

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20051022170838.0043deb4@sven.genone.homeip.net \
    --to=genone@gentoo.org \
    --cc=gentoo-portage-dev@lists.gentoo.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox