Quick Seneca Summary

Projects:

Scripts:

Some Koji Scripts (The Push For Primary)

The push for ARM to become primary arch is not as easy as one might think. Everyone in the community is working hard to prove how ARM is as capable in most areas to that of the machines in primary architecture. Anyway, here are a couple of scripts one could use to help determine some basic stats about ones current build process.

To find out the current error counts and types (and unbuilt packages) of a given tag:

(could help to show how far off one is in keeping up with primary and where the errors are)

#!/bin/bash

tagname="f17"
tagnumb=`echo "${tagname}" | sed -e 's/[^0-9]//g'`

if [ ! -f pripkgs.txt -o "$1" == "f" ]
then
	koji --server=http://koji.fedoraproject.org/kojihub list-tagged ${tagname} --inherit --latest --quiet | awk '{ print $1 }' | sed -e 's/-[^-]*-[^-]*$//g' > pripkgs.txt
fi

if [ ! -f armpkgs.txt -o "$1" == "f" ]
then
	koji --server=http://arm.koji.fedoraproject.org/kojihub list-tagged ${tagname} --inherit --latest --quiet | awk '{ print $1 }' | sed -e 's/-[^-]*-[^-]*$//g' > armpkgs.txt
fi

builtnum=0; builtstr=""
archnumb=0; archstri=""
depsnumb=0; depsstri=""
reqsnumb=0; reqsstri=""
confnumb=0; confstri=""
buildnum=0; buildstr=""
makenumb=0; makestri=""
unknnumb=0; unknstri=""
ubuilnum=0; ubuilstr=""

outpstri=""

while read pkgname
do
	pkgtagged=`cat armpkgs.txt | grep "${pkgname}"`
	
	if [ "${pkgtagged}" == "" ]
	then
		echo "[p] ${pkgname}" 1>&2
		
		pkgstat=`curl -Ls "http://arm.koji.fedoraproject.org/koji/search?match=glob&type=package&terms=${pkgname}" | tr -d '\t\r\n' | sed -e 's/<tr/\t<tr/g' | tr '\t' '\n' | grep -i "^<tr.*buildinfo.buildID" | sed -e 's/<a[^>]*buildinfo.buildID=\([0-9]*\)[^>]*>/ \1 /g' -e 's/<img[^>]*alt=.\([a-zA-Z]*\).[^>]*>/ \1 /g' -e 's/<[^>]*>/ /g' | grep -i "fc${tagnumb}" | sed -e 's/^[ \t]*//g' -e 's/[ \t]*$//g'`
		builtstat=`echo "${pkgstat}" | grep -i "complete$" | head -n 1`
		failstat=`echo "${pkgstat}" | grep -i "failed$" | head -n 1`
		
		if [ "${builtstat}" != "" ]
		then
			if [ "$2" == "p" ]
			then
				let builtnum="${builtnum} + 1"
				builtstr="${builtstr}${pkgname} http://arm.koji.fedoraproject.org/koji/search?match=glob&type=package&terms=${pkgname}\n"
			
			else
				outpstri="${outpstri}\n\"${pkgname}\":[\"complete\", \"\", 0]"
			fi
		
		elif [ "${failstat}" != "" ]
		then
			pkgnumb=`echo "${failstat}" | awk '{ print $1 }'`
			tasknumb=`curl -Ls "http://arm.koji.fedoraproject.org/koji/buildinfo?buildID=${pkgnumb}" | tr -d '\t\r\n' | sed -e 's/<a/\t<a/g' | tr '\t' '\n' | grep -i "^<a.*taskinfo.taskID" | sed -e 's/<a[^>]*taskinfo.taskID=\([0-9]*\)[^>]*>/ \1 /g' | awk '{ print $1 }' | head -n 1`
			failnumb=`curl -Ls "http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${tasknumb}" | tr -d '\t\r\n' | sed -e 's/<a/\t<a/g' | tr '\t' '\n' | grep -i "^<a.*taskinfo.taskID.*failed" | sed -e 's/<a[^>]*taskinfo.taskID=\([0-9]*\)[^>]*>/ \1 /g' | awk '{ print $1 }' | head -n 1`
			logsoutp=`koji --server=http://arm.koji.fedoraproject.org/kojihub watch-logs "${failnumb}"`
			
			archerro=`echo "${logsoutp}" | grep -i 'error: architecture is excluded' | head -n 1`
			depserro=`echo "${logsoutp}" | grep -i 'error: no package found for' | head -n 1`
			reqserro=`echo "${logsoutp}" | grep -i 'error: package' -A 1 | head -n 2 | tr -d '\t\r\n' | tr -s ' '`
			conferro=`echo "${logsoutp}" | grep -i 'error: bad exit status from' | head -n 1`
			builderr=`echo "${logsoutp}" | grep -i 'error: file not found' | head -n 1`
			makeerro=`echo "${logsoutp}" | grep -i 'make: .* error' | head -n 1`
			
			if [ "${archerro}" != "" ]
			then
				if [ "$2" == "p" ]
				then
					let archnumb="${archnumb} + 1"
					archstri="${archstri}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"arch-error\", \"${archerro}\", ${failnumb}]\n"
				fi
			
			elif [ "${depserro}" != "" ]
			then
				if [ "$2" == "p" ]
				then
					let depsnumb="${depsnumb} + 1"
					depsstri="${depsstri}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"dep-error\", \"${depserro}\", ${failnumb}]\n"
				fi
			
			elif [ "${reqserro}" != "" ]
			then
				if [ "$2" == "p" ]
				then
					let reqsnumb="${reqsnumb} + 1"
					reqsstri="${reqsstri}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"req-error\", \"${reqserro}\", ${failnumb}]\n"
				fi
			
			elif [ "${builderr}" != "" ]
			then
				if [ "$2" == "p" ]
				then
					let buildnum="${buildnum} + 1"
					buildstr="${buildstr}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"build-error\", \"${builderr}\", ${failnumb}]\n"
				fi
			
			elif [ "${makeerro}" != "" ]
			then
				if [ "$2" == "p" ]
				then
					let makenumb="${makenumb} + 1"
					makestri="${makestri}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"make-error\", \"${makeerro}\", ${failnumb}]\n"
				fi
			
			elif [ "${conferro}" != "" ]
			then
				if [ "$2" == "p" ]
				then
					let confnumb="${confnumb} + 1"
					confstri="${confstri}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"config-error\", \"${conferro}\", ${failnumb}]\n"
				fi
			
			else
				if [ "$2" == "p" ]
				then
					let unknnumb="${unknnumb} + 1"
					unknstri="${unknstri}${pkgname} http://arm.koji.fedoraproject.org/koji/taskinfo?taskID=${failnumb}\n"
				
				else
					outpstri="${outpstri}\"${pkgname}\":[\"unknown-error\", \"Error could not be interpreted.\", ${failnumb}]\n"
				fi
			fi
		
		else
			if [ "$2" == "p" ]
			then
				let ubuilnum="${ubuilnum} + 1"
				ubuilstr="${ubuilstr}${pkgname}\n"
			
			else
				outpstri="${outpstri}\"${pkgname}\":[\"unbuilt\", \"\", 0]\n"
			fi
		fi
	fi
done < pripkgs.txt

extranum=0; extrastr=""

while read pkgname
do
	pkgtagged=`cat pripkgs.txt | grep "${pkgname}"`
	
	if [ "${pkgtagged}" == "" ]
	then
		echo "[s] ${pkgname}" 1>&2
		
		if [ "$2" == "p" ]
		then
			let extranum="${extranum} + 1"
			extrastr="${extrastr}${pkgname}\n"
		
		else
			outpstri="${outpstri}\"${pkgname}\":[\"extra\", \"\", 0]\n"
		fi
	fi
done < armpkgs.txt

if [ "$2" == "p" ]
then
	printf '%10s|%10s|%10s|%10s|%10s|%10s|%10s\n' "Arch" "Deps" "Reqs" "Config" "Build" "Make" "Unknown"
	for i in `seq 1 80` ; do printf '-' ; done ; printf '\n'
	printf '%10s|%10s|%10s|%10s|%10s|%10s|%10s\n' "${archnumb}" "${depsnumb}" "${reqsnumb}" "${confnumb}" "${buildnum}" "${makenumb}" "${unknnumb}"
	echo
	if [ "${archstri}" != "" ] ; then echo -e "Arch-Errors:" ; echo -e "${archstri}" ; fi
	if [ "${depsstri}" != "" ] ; then echo -e "Dep-Errors:" ; echo -e "${depsstri}" ; fi
	if [ "${reqsstri}" != "" ] ; then echo -e "Require-Errors:" ; echo -e "${reqsstri}" ; fi
	if [ "${confstri}" != "" ] ; then echo -e "Config-Errors:" ; echo -e "${confstri}" ; fi
	if [ "${buildstr}" != "" ] ; then echo -e "Build-Errors:" ; echo -e "${buildstr}" ; fi
	if [ "${makestri}" != "" ] ; then echo -e "Make-Errors:" ; echo -e "${makestri}" ; fi
	if [ "${unknstri}" != "" ] ; then echo -e "Unknown-Errors:" ; echo -e "${unknstri}" ; fi
	if [ "${builtstr}" != "" ] ; then echo -e "Built but un-tagged/blocked pkgs = ${builtnum}" ; echo -e "${builtstr}" ; fi
	echo -e "Number of unbuilt/cancelled/building pkgs = ${ubuilnum}\n"
	if [ "${extrastr}" != "" ] ; then echo -e "Pkgs tagged in arm and not primary = ${extranum}" ; echo -e "${extrastr}" ; fi
	echo

else
	echo -e "${outpstri}"
	echo
fi

This script can help to compare build times between your various machines and primary:

(could help to compare how quickly ones build farm could keep up with primaries)

#!/bin/bash

function taskinfo
{
	roottask=`koji --server="$1/kojihub" buildinfo "$2" | grep -i '^task:' | awk '{ print $2 }'`
	curl -Ls "$1/koji/taskinfo?taskID=${roottask}" | tr -d '\t\r\n' | sed -e 's/<a/\t<a/g' | tr '\t' '\n' | grep -i 'taskinfo.taskID=.*buildArch' | sed -e 's/^.*taskinfo.taskID=\([0-9]*\).*$/ \1 /g' > /tmp/koji.task.$4.txt
	
	while read tasknumb
	do
		taskinfo=`curl -Ls "$1/koji/taskinfo?taskID=${tasknumb}" | tr -d '\t\r\n' | sed -e 's/<tr/\t<tr/g' | tr '\t' '\n'`
		begtime=`echo "${taskinfo}" | grep -i '^<tr>.*<th>.*Started.*</th>' | sed -e 's/^.*<td>//g' -e 's/<[^>]*>/ /g' -e 's/^[ \t]*//g' -e 's/[ \t]*$//g'`
		endtime=`echo "${taskinfo}" | grep -i '^<tr>.*<th>.*Completed.*</th>' | sed -e 's/^.*<td>//g' -e 's/<[^>]*>/ /g' -e 's/^[ \t]*//g' -e 's/[ \t]*$//g'`
		archname=`echo "${taskinfo}" | grep -i "^<tr>.*<th>.*Arch.*</th>" | sed -e 's/^.*<td>//g' -e 's/<[^>]*>/ /g' -e 's/^[ \t]*//g' -e 's/[ \t]*$//g'`
		hostname=`echo "${taskinfo}" | grep -i "^<tr>.*<th>.*Host.*</th>.*<td>.*$3.*</td>" | sed -e 's/^.*<td>//g' -e 's/<[^>]*>/ /g' -e 's/^[ \t]*//g' -e 's/[ \t]*$//g'`
		
		if [ "${begtime}" != "" -a "${endtime}" != "" -a "${archname}" != "" -a "${hostname}" != "" ]
		then
			begepoch=`date --date="${begtime}" '+%s'`
			endepoch=`date --date="${endtime}" '+%s'`
			
			hourdiff=`echo "(${endepoch} - ${begepoch}) / 3600" | bc`
			if [ ${hourdiff} -lt 10 ] ; then hourdiff="0${hourdiff}" ; fi
			
			mindiff=`echo "((${endepoch} - ${begepoch}) / 60) % 60" | bc`
			if [ ${mindiff} -lt 10 ] ; then mindiff="0${mindiff}" ; fi
			
			echo "${archname} ${hourdiff}:${mindiff}"
		fi
	done < /tmp/koji.task.$4.txt
}

tagname="f17"
tagnumb=`echo "${tagname}" | sed -e 's/[^0-9]//g'`

if [ ! -f primary.built.txt ]
then
	koji --server=http://koji.fedoraproject.org/kojihub list-tagged ${tagname} --inherit --latest --quiet | awk '{ print $1 }' > primary.built.txt
fi

tempfile="$1"
uniqname=`head -c 1024 /dev/urandom | md5sum | awk '{ print $1 }'`

if [ "${tempfile}" == "" ]
then
	koji --server=http://arm.koji.fedoraproject.org/kojihub list-tagged ${tagname} --inherit --latest --quiet | awk '{ print $1 }' > arm.built.txt
	tempfile="arm.built.txt"
fi

builder="$2"

if [ "${builder}" == "" ]
then
	builder="cdot.trimslice"
fi

printf '%-40s | %10s | %10s | %10s | %10s | %20s\n' "Package Name" "x86" "x64" "ARMvSFP" "ARMvHFP" "(Time = HH:MM)"
for i in `seq 1 95` ; do printf '-' ; done ; printf '\n'

while read srpmname
do
	pkgname=`echo "${srpmname}" | sed -e 's/-[^-]*-[^-]*$//g'`
	primpkg=`cat primary.built.txt | grep "^${pkgname}-[0-9\.][0-9\.]*-" | head -n 1`
	
	arminfo=`taskinfo "http://arm.koji.fedoraproject.org" "${srpmname}" "${builder}" "${uniqname}"`
	
	if [ "${arminfo}" != "" ]
	then
		priminfo=`taskinfo "http://koji.fedoraproject.org" "${primpkg}" ".*" "${uniqname}"`
		
		tttime=`echo "${priminfo}" | grep -i '^i386 ' | awk '{ print $2 }' | head -n 1`
		sftime=`echo "${priminfo}" | grep -i '^x86_64 ' | awk '{ print $2 }' | head -n 1`
		astime=`echo "${arminfo}" | grep -i '^arm ' | awk '{ print $2 }' | head -n 1`
		ahtime=`echo "${arminfo}" | grep -i '^armhfp ' | awk '{ print $2 }' | head -n 1`
		
		printf '%-40s | %10s | %10s | %10s | %10s |\n' "${pkgname}" "${tttime}" "${sftime}" "${astime}" "${ahtime}"
	fi
done < ${tempfile}

[really off topic] I also really like colorful circles moving around randomly!

If my server is still up -> Liquid Particles

liquid-particles.js

/**
*   Liquid particles canvas experiment
*   ©2010 spielzeugz.de 
*/

var PI_2        = Math.PI * 2;

var canvasW     = 8;
var canvasH     = 8;
var numMovers   = 1024;
var friction    = 0.96;
var movers      = [];

var canvas = null;
var ctx = null;

var mouseX;
var mouseY;
var mouseVX;
var mouseVY;
var prevMouseX;
var prevMouseY;
var isMouseDown;

function init(){
	canvas = document.getElementById("mainCanvas");
	
	canvasW = canvas.width;
	canvasH = canvas.height;
	numMovers = (canvasW + canvasH);
	
	if ( canvas.getContext ){
		setup();
		setInterval( run , 33 );
		trace("interact with the mouse, occasionally click or hold down the mousebutton");
	}
	else{
		trace("Sorry, needs a recent version of Chrome, Firefox, Opera, Safari, or Internet Explorer 9.");
	}
}
   
function setup(){
	ctx       = canvas.getContext("2d");
	
	var i = numMovers;
	while ( i-- ){
		var m = new Mover();
		m.x   = canvasW * 0.5;
		m.y   = canvasH * 0.5;
		m.vX  = Math.cos(i) * Math.random() * 34;
		m.vY  = Math.sin(i) * Math.random() * 34;
		movers[i] = m;
	}
	
	mouseX = prevMouseX = canvasW * 0.5;
	mouseY = prevMouseY = canvasH * 0.5;
}

function run(){
	ctx.globalCompositeOperation = "source-over";
	ctx.fillStyle = "rgba(8,8,12,0.65)";
	ctx.fillRect( 0 , 0 , canvasW , canvasH );
	ctx.globalCompositeOperation = "lighter";
	
	mouseVX    = mouseX - prevMouseX;
	mouseVY    = mouseY - prevMouseY;
	prevMouseX = mouseX;
	prevMouseY = mouseY;
	
	var toDist   = canvasW * 0.86;
	var stirDist = canvasW * 0.125;
	var blowDist = canvasW * 0.5;
	
	var Mrnd = Math.random;
	var Mabs = Math.abs;
	
	var i = numMovers;
	while ( i-- ){
		var m  = movers[i];
		var x  = m.x;
		var y  = m.y;
		var vX = m.vX;
		var vY = m.vY;
		
		var dX = x - mouseX;
		var dY = y - mouseY; 
		var d  = Math.sqrt( dX * dX + dY * dY ) || 0.001;
		dX /= d;
		dY /= d;
		
		if ( isMouseDown ){
			if ( d < blowDist ){
				var blowAcc = ( 1 - ( d / blowDist ) ) * 14;
				vX += dX * blowAcc + 0.5 - Mrnd();
				vY += dY * blowAcc + 0.5 - Mrnd();
			}
		}
		
		if ( d < toDist ){
			var toAcc = ( 1 - ( d / toDist ) ) * canvasW * 0.0014;
			vX -= dX * toAcc;
			vY -= dY * toAcc;			
		}
		
		if ( d < stirDist ){
			var mAcc = ( 1 - ( d / stirDist ) ) * canvasW * 0.00026;
			vX += mouseVX * mAcc;
			vY += mouseVY * mAcc;			
		}
		
		vX *= friction;
		vY *= friction;
		
		var avgVX = Mabs( vX );
		var avgVY = Mabs( vY );
		var avgV  = ( avgVX + avgVY ) * 0.5;
		
		if( avgVX < .1 ) vX *= Mrnd() * 3;
		if( avgVY < .1 ) vY *= Mrnd() * 3;
		
		var sc = avgV * 0.45;
		sc = Math.max( Math.min( sc , 3.5 ) , 0.4 );
		
		var nextX = x + vX;
		var nextY = y + vY;
		
		if ( nextX > canvasW ){
			nextX = canvasW;
			vX *= -1;
		}
		else if ( nextX < 0 ){
			nextX = 0;
			vX *= -1;
		}
		
		if ( nextY > canvasH ){
			nextY = canvasH;
			vY *= -1;
		}
		else if ( nextY < 0 ){
			nextY = 0;
			vY *= -1;
		}
		
		m.vX = vX;
		m.vY = vY;
		m.x  = nextX;
		m.y  = nextY;
		
		ctx.fillStyle = m.color;
		ctx.beginPath();
		ctx.arc( nextX , nextY , sc , 0 , PI_2 , true );
		ctx.closePath();
		ctx.fill();		
	}
}

function onDocMouseMove( e ){
	var ev = e ? e : window.event;
	mouseX = ev.clientX - canvas.offsetLeft;
	mouseY = ev.clientY - canvas.offsetTop;
}

function onDocMouseDown( e ){
	isMouseDown = true;
	return false;
}

function onDocMouseUp( e ){
	isMouseDown = false;
	return false;
}

function Mover(){
	this.color = "rgb(" + Math.floor( Math.random()*255 ) + "," + Math.floor( Math.random()*255 ) + "," + Math.floor( Math.random()*255 ) + ")";
	this.y     = 0;
	this.x     = 0;
	this.vX    = 0;
	this.vY    = 0;
	this.size  = 1; 
}

function rect( context , x , y , w , h ){
	context.beginPath();
	context.rect( x , y , w , h );
	context.closePath();
	context.fill();
}

function trace( str ){
	console.log(str);
}

lp.html

<html>
	<head>
		<title>Automatic Liquid Particles</title>
		
		<style>
			body
			{
				background-color: black;
			}
			
			canvas
			{
				border: 1px dotted white;
			}
		</style>
		
		<script src="liquid-particles.js"></script>
		<script>
			var mousepos = [0, 0, 1, 1];
			var lasttime = 0;
			
			function fakemove()
			{
				var dateobjc = new Date();
				var prestime = (dateobjc.getTime() / 1000);
				
				if ((canvasW > 8) && (canvasH > 8) && (canvas != null))
				{
					onDocMouseDown(null);
					
					if ((prestime - lasttime) >= 1)
					{
						mousepos[2] = parseInt(Math.random() * 2);
						mousepos[3] = parseInt(Math.random() * 2);
						
						if (mousepos[2] == 0) { mousepos[2] = -1; }
						if (mousepos[3] == 0) { mousepos[3] = -1; }
						
						lasttime = prestime;
					}
					
					mousepos[0] = Math.min(canvasW, Math.max(0, mousepos[0] + (16 * mousepos[2])));
					mousepos[1] = Math.min(canvasH, Math.max(0, mousepos[1] + (16 * mousepos[3])));
					
					var mouseeve = {"clientX":(mousepos[0] + canvas.offsetLeft), "clientY":(mousepos[1] + canvas.offsetTop)};
					
					onDocMouseMove(mouseeve);
				}
				
				setTimeout("fakemove();", 32);
			}
			
			function prepinit()
			{
				document.body.innerHTML = ("<center><canvas id='mainCanvas' width='" + (document.body.offsetWidth - 32) + "' height='" + (document.body.offsetHeight - 32) + "'></canvas></center>");
				init();
				fakemove();
			}
		</script>
	</head>
	
	<body onload="prepinit();"></body>
</html>

[off topic] I like the horoscopes from thestar…

Ok so I was bored again and I was randomly reading my scopes from the star and I liked them so here’s an overly complicated bash command to get them for you!

u=`curl -s "http://www.thestar.com/horoscopes" | tr -d '\t\r\n' | sed -e 's/<a /\t<a /g' | tr '\t' '\n' | grep -i '/horoscopes/article/.*--' | sed -e 's/^.*<a href="//g' -e 's/">.*$//g' | head -n 1` ; h=`curl -s "http://www.thestar.com/${u}" | tr -d '\t\r\n' | sed -e 's/<b>/\t/g' | tr '\t' '\n' | sed -e 's/<[^>]*>/ /g' | tr -s ' ' | grep -i "^aqua"` ; echo "$u" ; echo ; echo "$h" ; echo

Just change the grep -i "^aqua" part near the end of the command to the start of your own horoscope name. Also note, if the star decides to change the structure of their html web pages even just a little, this script is likely to break!

johnny stoops