summaryrefslogtreecommitdiff
path: root/src/pr-tools
diff options
context:
space:
mode:
authorNicolás Reynolds <apoyosis@correo.inta.gob.ar>2012-11-07 15:06:55 -0300
committerNicolás Reynolds <apoyosis@correo.inta.gob.ar>2012-11-07 15:06:55 -0300
commit73b813613aa08646515f4e06c71503b18125cec3 (patch)
tree5b98b01f1c331692e2dcae4fd4f6fb4e4a7064df /src/pr-tools
parent6c14fad1750b4342b5b283e0851c00e3c074a15c (diff)
parent040111e9d8419456255816600784a496febd57b0 (diff)
Merge branch 'master' of git://gitorious.org/parabola/libretools
Diffstat (limited to 'src/pr-tools')
-rwxr-xr-xsrc/pr-tools/prfullpkg398
-rwxr-xr-xsrc/pr-tools/prmipsrelease98
-rw-r--r--src/pr-tools/prtools.conf4
-rwxr-xr-xsrc/pr-tools/prtoru173
4 files changed, 673 insertions, 0 deletions
diff --git a/src/pr-tools/prfullpkg b/src/pr-tools/prfullpkg
new file mode 100755
index 0000000..bbb8d73
--- /dev/null
+++ b/src/pr-tools/prfullpkg
@@ -0,0 +1,398 @@
+#!/bin/bash
+
+source /etc/makepkg.conf
+source /etc/abs.conf
+source /etc/libretools.conf
+source /etc/libretools.d/prtools.conf
+
+if [ -z $XDG_CONFIG_HOME ]; then # Avoid /libretools dir doesn't exist errors
+
+ error "There's no XDG_CONFIG_HOME var set"; exit 1
+
+elif [ -e $XDG_CONFIG_HOME/libretools/libretools.conf ]; then
+
+ source $XDG_CONFIG_HOME/libretools/libretools.conf
+
+fi
+
+
+function usage {
+
+ echo "cd to a dir containing a PKGBUILD and run:"
+ echo "$0 [options]"
+ printf "This script will check dependencies, build them if possible "
+ printf "and stage the packages on it's repo."
+ echo
+ echo "OPTIONS:"
+ echo " -h : this message."
+ echo " -a absdir : set absdir as ABSROOT."
+ echo " -b build_dir : use a fullpkg build_dir and only build."
+ echo " -c : check deps only, do not build."
+ echo " -d build_dir : use this dir to build. Defaults to mktemp."
+ echo " -n : don't update pacman db."
+ echo " -m max_level : check deps until this level"
+ echo " -r \"command\" : use this instead of \"$FULLBUILDCMD\""
+ echo
+ exit 1
+
+}
+
+function remove_buildorder { # Removes a package from the buildorder
+# $1 package name
+# $2 buildorder file
+
+ grep -Evw "${1}" ${2} > ${2}2
+ mv -f ${2}2 ${2}
+
+}
+
+function guess_repo { # Get repo name. Asumes ${ABSROOT}/package/repo/PKGBUILD
+
+ basename $(pwd)
+
+}
+
+function get_fullver { # return : full version spec, including epoch (if necessary), pkgver, pkgrel
+
+# usage : get_fullver( ${epoch:-0}, $pkgver, $pkgrel )
+
+ if [[ $1 -eq 0 ]]; then
+ # zero epoch case, don't include it in version
+ echo $2-$3
+ else
+ echo $1:$2-$3
+ fi
+
+}
+
+function cleanup { # Cleans the build_dir.
+
+ [ ! -d "${build_dir}" -o "${build_only}" = 'y' ] && return 0 # Do nothing or already cleaned.
+
+
+ if [ $level -eq 0 ]; then # Only do cleanup on level 0.
+ msg "Cleaning up ${build_dir}"
+ rm -rf "$build_dir/*"
+ fi
+}
+
+function find_deps { # Checks ABSROOT and look for target pkg deps. Adds them if not built or outdated.
+
+ source PKGBUILD ## Check this level.
+
+ local repo=${repo:-$(guess_repo)}
+ local pkgbase=${pkgbase:-${pkgname[0]}}
+ local epoch=${epoch:-0}
+ local fullver=$(get_fullver ${epoch} ${pkgver} ${pkgrel})
+
+ if is_built "${pkgbase}" "${fullver}"; then
+ exit 0 # pkg is built and updated
+ fi
+
+ echo "${level}:${pkgbase}" >> "${build_dir}/BUILDORDER" # greater levels are built first
+
+ if [ -d "${build_dir}/${pkgbase}" ]; then # PKGBUILD is already there
+
+ exit 0
+
+ else # Copy dir to build_dir
+
+ mkdir ${build_dir}/${pkgbase}
+ cp -r $(pwd)/* ${build_dir}/${pkgbase}
+
+ echo "repo=$repo" > "${build_dir}/${pkgbase}/.INFO" # to identify repo later
+ fi
+
+ msg2 "%${level}s${pkgbase}-${fullver}" # current package plus a space for every level
+
+ declare -i next_level=$level+1 ## Check next deps level.
+
+ deps=$(echo "${depends[@]} ${makedepends[@]}" | \
+ sed "s/[=<>]\+[^ ]\+//g" | \
+ tr ' ' "\n" | \
+ sort -u) # All deps in separate line, only once, without version.
+
+ for _dep in ${deps[@]}; do
+
+ local found=false
+
+ if [ -d "${ABSROOT}/${_dep}" ]; then # ABSROOT/package/repo
+
+ for _repo in ${REPOS[@]}; do # Use PKGBUILD from repo in REPOS array order
+
+ if [ -e "${ABSROOT}/${_dep}/${_repo}/PKGBUILD" ]; then
+
+ pushd "${ABSROOT}/${_dep}/${_repo}" > /dev/null
+ $0 -c -d ${build_dir} -l ${next_level} # run this cmd on dep's PKGBUILD dir
+ [ $? -eq 20 ] && return 20 # probable circular deps
+ popd > /dev/null
+ local found=true
+ break 1 # found, go to next dep
+ fi
+
+ done
+
+ else # pkgsplit, needs guess
+
+ for _repo in ${REPOS[@]}; do
+
+ if _dir=($(find "$ABSROOT/" -type f \
+ -wholename "*/${_repo}/PKGBUILD" -print0 2>/dev/null | \
+ "xargs" -0 -e grep -HEw "pkgname=|pkgbase=|provides=" | \
+ grep -w "$_dep" 2>&1)) ;
+
+ then
+
+ _dir=$(dirname $(echo $_dir | cut -d: -f1))
+ plain "guess for $_dep -> $_dir"
+
+ pushd "$_dir" > /dev/null
+ $0 -c -d ${build_dir} -l ${next_level} # run this cmd on dep's PKGBUILD dir
+ [ $? -eq 20 ] && return 20 # probable circular dep
+ popd > /dev/null
+ local found=true
+ break 1 # found, go to next dep
+ fi
+
+ done
+
+ fi
+
+ if ( ${found} ); then
+ continue 1 # go to next dep
+ else
+ echo "dep_not_found:$_dep" >> $build_dir/log
+ fi
+
+ done
+
+ unset next_level dir
+ # unset PKGBUILD variables
+ unset pkgbase pkgname pkgver pkgrel epoch pkgdesc arch url license groups depends \
+ makedepens checkdepends optdepends provides conflicts replaces backup \
+ options install changelog source noextract md5sums build check package
+}
+
+function __build () {
+ pushd ${build_dir} > /dev/null
+
+ build_packages=($(sort -gr $buildorder | cut -d: -f2)) # greater levels must be built first
+
+ while [ ${#build_packages[@]} -ge 1 ]; do
+ pushd $build_dir/${build_packages[0]} > /dev/null
+ source PKGBUILD
+
+ msg2 "${pkgbase:-${pkgname[0]}} $pkgver-$pkgrel"
+
+ msg2 "Checking for non free deps"
+ pkgbuild-check-nonfree || {
+ if [ $? -eq 15 ]; then # this error means nonfree others means fail.
+
+ echo "nonfree:$(basename $PWD)" >> $build_dir/log
+
+ remove_buildorder "$(basename $PWD)" $buildorder # take out package from $buildorder
+
+ continue # build next package
+ fi
+ }
+
+ msg2 "Building $(basename $PWD)"
+
+ $FULLBUILDCMD; r=$? # this buildcmd is on libretools.conf
+
+ case $r in
+
+ 0) ## Succesfull build
+
+ plain "The build was succesful."
+ if source .INFO && [ -n $repo ]; then
+
+ if [ ! -z $HOOKLOCALRELEASE ]; then # Calls a local release script if it's used
+ find -name "*.pkg.tar.?z" -print0 | xargs -0 $HOOKLOCALRELEASE $repo
+ fi
+
+ librestage $repo || echo "unstaged:$(basename $PWD)" >> $build_dir/log
+
+ msg "Updating pacman db and packages"
+ sudo pacman -Sy || true
+
+ fi
+
+ echo "built:$(basename $PWD)" >> $build_dir/log
+ ;;
+
+ *) ## Build failed
+ error "There were errors while trying to build the package."
+ echo "failed:$(basename $PWD)" >> $build_dir/log
+ ;;
+ esac
+
+ remove_buildorder "${build_packages[0]}" $buildorder || true
+
+ build_packages=($(sort -gr $buildorder | cut -d: -f2)) # which is next package?
+ popd > /dev/null
+ done
+
+ pkgs=($(grep "nonfree:" $build_dir/log)) && {
+ error "Those packages contain nonfree deps:"
+ echo ${pkgs[@]} | tr " " "\n" | cut -d: -f2
+ }
+
+ pkgs=($(grep "built:" $build_dir/log)) && {
+ msg "Those packages were built and staged:"
+ echo ${pkgs[@]} | tr " " "\n" | cut -d: -f2
+ }
+
+ pkgs=($(grep "failed:" $build_dir/log)) && {
+ error "Those packages failed to build:"
+ echo ${pkgs[@]} | tr " " "\n" | cut -d: -f2
+ }
+
+ pkgs=($(grep "unstaged:" $build_dir/log)) && {
+ error "Those packages couldn't be staged because of missing reponame:"
+ echo ${pkgs[@]} | tr " " "\n" | cut -d: -f2
+ }
+
+ popd > /dev/null
+}
+
+function trap_exit { # End inmediately but print a useful message
+
+ error "$@"
+ warning "Leftover files left on $build_dir"
+
+ exit 1
+}
+
+# Trap signals from makepkg
+set -E
+trap 'trap_exit "(prfullpkg:${level}) TERM signal caught. Exiting..."' TERM HUP QUIT
+trap 'trap_exit "(prfullpkg:${level}) Aborted by user! Exiting..."' INT
+trap 'trap_exit "(prfullpkg:${level}) An unknown error has occurred. Exiting..."' ERR
+
+ban_file=$XDG_CONFIG_HOME/libretools/ban
+force_build=""
+level=0
+noupdate='n'
+build_only='n'
+check_deps_only='n'
+max_level=21
+
+while getopts 'ha:b:cd:l:nm:r:' arg; do
+ case $arg in
+ h) usage ;;
+ a) ABSROOT="$OPTARG" ;;
+ b) build_only='y'
+ build_dir="$OPTARG"
+ if [ -z ${build_dir} ]; then
+ usage
+ fi
+ if [ ! -r ${build_dir}/BUILDORDER ] ; then
+ error "${build_dir}/BUILDORDER doesn't exist."
+ exit 1
+ fi;;
+ c) check_deps_only='y' ;;
+ d) build_dir="$OPTARG" ;;
+ l) level=$OPTARG ;; # hidden option to know dep level.
+ n) noupdate='y';;
+ m) max_level=$OPTARG ;;
+ r) FULLBUILDCMD="$OPTARG" ;;
+ esac
+done
+
+if [ ${build_only} == 'n' ]; then
+
+ [ ! -r PKGBUILD ] && { # Check if we are actually on a build directory. Do this early.
+ error "This isn't a build directory"
+ usage
+ }
+
+ if [ ! -z "$HOOKPKGBUILDMOD" ]; then
+ "$HOOKPKGBUILDMOD"
+ fi
+
+fi
+
+if [ $level -eq 0 ]; then
+
+ if [ ! -d ${build_dir} ]; then # in case of custom -d option
+ mkdir -p ${build_dir}
+ else
+ cleanup # files already there can screw find_deps
+ fi
+
+ build_dir=${build_dir:-$(mktemp -d /tmp/fullpkg.XXXXXX)} # use -d option or else mktemp
+
+ touch ${build_dir}/{log,BUILDORDER} ${ban_file} # make files for log and buildorder
+ buildorder=${build_dir}/BUILDORDER
+
+ if [ ${noupdate} = 'n' ]; then
+
+ msg "Updating pacman db and packages"
+ sudo pacman -Syu --noconfirm || true
+
+ fi
+
+ if [ ${build_only} == 'y' ]; then
+
+ msg "Build Packages"
+
+ __build
+
+ exit 0
+
+ fi
+
+ msg "Checking dependencies"
+fi
+
+[ $level -ge $max_level ] && exit 20 # Probable circular deps
+
+find_deps || {
+
+ if [ $? -eq 20 ]; then # Probable circular deps
+
+ if [ $level -eq 0 ]; then # Show error only on level 0
+ error "Check for circular deps on $build_dir/BUILDORDER";
+ fi
+
+ fi
+ exit 20 # Pass message 20
+}
+
+[ $check_deps_only = 'y' -o $level -gt 0 ] && exit 0 # only build on level 0
+
+if [ $level -eq 0 -a -d $build_dir ]; then # Sanity check
+
+ if [ ! -w $ban_file -o ! -r $ban_file ]; then # Check ban_file permisions
+
+ chmod a+rw $ban_file || error "Ban file is not readable/writable ($ban_file)"
+
+ else
+
+ rsync -e ssh -aq $PARABOLAHOST:mips64el/ban >/dev/null 2>&1 || {
+
+ warning "Failed to get ban list" && [ -r ${ban_file} ] && { # use local copy if it exist
+
+ search=$(cat ${ban_file} | tr "\n" "|")
+
+ egrep -w "$search" ${buildorder} >> ${build_dir}/banned # Keep track of banned files
+
+ egrep -vw "$search" ${buildorder} > ${buildorder}2 # Take banned packages out of buildorder
+
+ mv -f ${buildorder}2 ${buildorder}
+
+ unset search
+ }
+ }
+ fi
+fi
+
+msg "Building packages:"
+
+__build # Build the packages
+
+echo
+msg2 "Check if your system works fine and librerelease if it does"
+
+exit 0
diff --git a/src/pr-tools/prmipsrelease b/src/pr-tools/prmipsrelease
new file mode 100755
index 0000000..1fbd696
--- /dev/null
+++ b/src/pr-tools/prmipsrelease
@@ -0,0 +1,98 @@
+#!/bin/bash
+# Lic: GPLv3+
+# Author: Nicolas Reynolds <fauno@kiwwwi.com.ar>
+# Local release of mips64el packages + clean ABS sync
+# Called by HOOKLOCALRELEASE
+
+# $1 repo
+# $2+ packages
+
+ source /etc/makepkg.conf
+ source /etc/libretools.conf
+ source /etc/libretools.d/prtools.conf
+
+ usage() {
+ echo "$0 repo package1 [ package2 ... packageN ]"
+ echo
+ echo " release packages locally on ${PKGDEST}/stage3."
+ echo " and make a clean ABS sync "
+ }
+
+##
+# usage : get_full_version( $epoch, $pkgver, $pkgrel )
+# return : full version spec, including epoch (if necessary), pkgver, pkgrel
+##
+ get_full_version() {
+ if [[ $1 -eq 0 ]]; then
+ # zero epoch case, don't include it in version
+ echo $2-$3
+ else
+ echo $1:$2-$3
+ fi
+ }
+
+ repo=$1; shift
+ repo-add "${PKGDEST}/stage3.db.tar.gz" $@
+
+# Get all needed sources
+ source PKGBUILD
+ fullver=$(get_full_version ${epoch:-0} ${pkgver} ${pkgrel})
+ pkgbase=${pkgbase:-$pkgname}
+
+ msg "Adding packages to [stage3]..."
+ repo-add $@
+ for name in ${pkgname[@]}; do
+ msg2 "${name} ${fullver}"
+ repo-add ${PKGDEST}/stage3.db.tar.gz ${PKGDEST}/${name}-${fullver}-*.pkg.tar.*
+ done
+
+# Copy PKGBUILD and sources
+
+ msg "Adding clean source to $WORKDIR/abs/${CARCH}/$repo/$pkgbase"
+ dest_dir="$WORKDIR/abs/${CARCH}/$repo/$pkgbase"
+ mkdir -p ${dest_dir} >/dev/null
+ rm -rf ${dest_dir}/* # if package existed already there
+
+ eval $(grep '^CARCH=' "$copydir/etc/makepkg.conf") # CARCH might be used in PKGBUILD to select sources.
+ export CARCH
+ source=($(. "PKGBUILD"; echo ${source[@]}))
+ cp --remove-destination "PKGBUILD" "${dest_dir}" || echo "copy 1"
+ for f in ${source[@]}; do
+ basef=$(echo $f | sed 's|::.*||' | sed 's|^.*://.*/||g')
+ if [ -f "$basef" ]; then
+ cp --remove-destination "$basef" "${dest_dir}"
+ fi
+ done
+
+ ( . PKGBUILD
+ for i in 'changelog' 'install'; do
+ filelist=$(sed -n "s/^[[:space:]]*$i=//p" PKGBUILD)
+ for file in $filelist; do
+ # evaluate any bash variables used
+ eval file=${file}
+ if [ -f "$file" ]; then
+ cp --remove-destination "$file" "${dest_dir}"
+ fi
+ done
+ done
+ )
+# END add clean abs
+
+# Commit the changes
+
+ pushd "$dest_dir" >/dev/null
+
+ source "${dest_dir}/PKGBUILD"
+ epoch=${epoch:-0}
+ fullver=$(get_full_version ${epoch} ${pkgver} ${pkgrel})
+ pkgbase=${pkgbase:-${pkgname[0]}}
+
+ git add "${dest_dir}/." # add using .gitignore
+
+ git commit -m "${pkgbase}-${fullver} ${repo}" >/dev/null && msg2 "${pkgbase} ${fullver} ${repo}"
+
+ popd >/dev/null
+
+# END commit
+
+ exit $?
diff --git a/src/pr-tools/prtools.conf b/src/pr-tools/prtools.conf
new file mode 100644
index 0000000..5b41216
--- /dev/null
+++ b/src/pr-tools/prtools.conf
@@ -0,0 +1,4 @@
+
+# Absroot for libretools-pr
+ABSROOT=$WORKDIR/prabs
+HOOKLOCALRELEASE="prmipsrelease" \ No newline at end of file
diff --git a/src/pr-tools/prtoru b/src/pr-tools/prtoru
new file mode 100755
index 0000000..2898b66
--- /dev/null
+++ b/src/pr-tools/prtoru
@@ -0,0 +1,173 @@
+#!/bin/bash
+# Queries the ABS
+# License: GPL3
+
+## TODO
+# * Add license text
+# * Create symlinks from pkgbase to pkgname[@] for easy package finding
+# * Use lastsync to store processed packages
+
+## GOALS
+# * Have a searchable database of PKGBUILD metadata
+# * Have an interface for source-only builds
+# * Possibility to hook up ABS dirs besides ABSROOT (low priority)
+# * Tell updates and non available binary packages (working on this)
+
+source /etc/abs.conf
+source /etc/libretools.conf
+source /etc/libretools.d/prtools.conf
+
+# Stores the lastsync date
+lastsync() {
+ [ -e ${lastsyncfile} -a ! -w ${lastsyncfile} ] && {
+ error "The sync date can't be saved. ${lastsyncfile} isn't writable."
+ return 1
+ }
+
+ date +%s > "$lastsyncfile"
+ touch "$lastsyncfile"
+}
+
+##
+# usage : get_full_version( $epoch, $pkgver, $pkgrel )
+# return : full version spec, including epoch (if necessary), pkgver, pkgrel
+##
+get_full_version() {
+ if [[ $1 -eq 0 ]]; then
+ # zero epoch case, don't include it in version
+ echo $2-$3
+ else
+ echo $1:$2-$3
+ fi
+}
+
+# Outputs an ordered package-fullpkgver array
+print_package_array() {
+ echo "$@" | tr " " "\n" | sort -V -u
+}
+
+
+# Gets repo.db contents
+# $1 repo
+get_db_contents() {
+ [ ! -r /var/lib/pacman/sync/$1.db ] && return 0
+
+ bsdtar -tf /var/lib/pacman/sync/$1.db | \
+ cut -d'/' -f1 | \
+ sort -V -u
+}
+
+
+extract_pkgname() {
+ echo "$@" | tr " " "\n" | sed "s/^\(.\+\)-[^-]\+-[^-]\+$/\1/"
+}
+
+extract_fullpkgver() {
+ echo "$@" | tr " " "\n" | sed "s/^.\+-\([^-]\+-[^-]\+\)$/\1/"
+}
+
+
+# Updates the database by finding all PKGBUILDS
+# Workflow:
+# * Find all PKGBUILDs on the ABS repo specified
+# * Get all packages already on package repos
+# * Compare them
+# Args:
+update() {
+# The PKGBUILDs found
+ local pkgbuilds=()
+# The list of pkgname-fullpkgver
+ local packages_to_sync=()
+ local packages_in_sync=()
+ local needed_updates=()
+ local old_versions=()
+
+# Find all the PKGBUILDs newer than the last update
+# Update newer, otherwise everything
+ if [ $force ] || [ ! -e ${lastsyncfile} ]; then
+ $quiet || msg "Forcing upgrade"
+ pkgbuilds=($(find ${@} -maxdepth 2 -type f -name 'PKGBUILD'))
+ else
+ pkgbuilds=($(find ${@} -maxdepth 2 -type f -name 'PKGBUILD' -newer ${lastsyncfile}))
+ fi
+
+# Inform how many PKGBUILDS were found and quit immediately if none
+ $quiet || msg "Found $((${#pkgbuilds[*]}-1)) packages to update"
+ [ ${#pkgbuilds[*]} -eq 1 ] && {
+ $quiet || msg2 "There's nothing to be done. Phew!"
+ exit 0
+ }
+
+ for _pkgbuild in ${pkgbuilds[@]}; do
+
+# The repo name is guessed
+# You *must* use repo/pkgbase structure
+ _pkgpath=$(dirname "${_pkgbuild}")
+ _pkgbase=$(basename "${_pkgpath}")
+ _pkgrepo=$(basename $(dirname "${_pkgpath}"))
+
+ source ${_pkgbuild}
+
+ for _pkg in ${pkgname[@]}; do
+# Fill the list of packages to find
+ packages_to_sync+=($_pkg-$(get_full_version ${epoch:-0} $pkgver $pkgrel))
+ done
+
+ unset pkgbase pkgname pkgver pkgrel source epoch
+ done
+
+# Get repo database contents
+ packages_in_sync=($(get_db_contents ${_pkgrepo}))
+ print_package_array "${packages_to_sync[@]}" > ${TMPDIR}/packages_to_sync
+ print_package_array "${packages_in_sync[@]}" > ${TMPDIR}/packages_in_sync
+
+# We've orderer the files!
+ needed_updates=($(comm --nocheck-order -32 ${TMPDIR}/packages_to_sync ${TMPDIR}/packages_in_sync))
+ old_versions=($(comm --nocheck-order -31 ${TMPDIR}/packages_to_sync ${TMPDIR}/packages_in_sync))
+
+ $quiet || msg "This packages are available to update"
+ for _update in ${needed_updates[@]}; do
+ pkg=$(extract_pkgname $_update)
+
+ $quiet && echo $pkg
+ $quiet || {
+ ver=$(extract_fullpkgver $_update)
+ oldver=$(extract_fullpkgver $(grep -w $pkg ${TMPDIR}/packages_in_sync))
+
+ msg2 "$pkg $oldver => $ver"
+ }
+
+ done
+
+# lastsync
+
+}
+
+## MAIN
+commands=()
+repos=()
+quiet=false
+force=false
+while getopts 'hqfu' arg; do
+ case $arg in
+ h) usage; exit 0 ;;
+ q) quiet=true ;;
+ f) force=true ;;
+ u) commands+=(update);;
+ esac
+
+ shift $((OPTIND-1))
+done
+
+# This is the syncfile, stores the last date as content and mtime
+lastsyncfile=${ABSROOT}/toru.lastsync
+
+TMPDIR=$(mktemp -d)
+
+[[ -z ${TMPDIR} ]] && exit 1
+
+${commands[0]} ${@}
+
+rm -rf ${TMPDIR}
+
+exit $?