#!/bin/sh
# Tazpkg - Tiny autonomus zone packages manager.
#
# This is a lightwight packages manager for *.tazpkg files, all written in
# SHell script. It works well with Busybox ash shell and bash. Tazpkg let you
# list, install, remove, download or get information about a package, you can
# use 'tazpkg usage' to get a list of commands with a short description. Tazpkg
# also resolves dependencies and can upgrade packages from a mirror.
#
# (C) 2007-2008 SliTaz - GNU General Public License v3.
#
# Authors : Christophe Lincoln <pankso@slitaz.org>
#           Pascal Bellard <pascal.bellard@slitaz.org>
#           Eric Joseph-Alexandre <erjo@slitaz.org>
#
VERSION=2.3

####################
# Script variables #
####################

# Packages categories.
CATEGORIES="
base-system
utilities
network
graphics
multimedia
office
development
system-tools
security
games
misc
meta
non-free"

# Initialize some variables to use words
# rather than numbers for functions and actions.
COMMAND=$1
if [ -f "$2" ]; then
	# Set pkg basename for install, extract
	PACKAGE=$(basename ${2%.tazpkg} 2>/dev/null)
else
	# Pkg name for remove, search and all other cmds
	PACKAGE=${2%.tazpkg}
fi
PACKAGE_FILE=$2
TARGET_DIR=$3
TOP_DIR=`pwd`
TMP_DIR=/tmp/tazpkg-$$-$RANDOM

# Path to tazpkg used dir and configuration files
LOCALSTATE=/var/lib/tazpkg
INSTALLED=$LOCALSTATE/installed
CACHE_DIR=/var/cache/tazpkg
MIRROR=$LOCALSTATE/mirror
PACKAGES_LIST=$LOCALSTATE/packages.list
BLOCKED=$LOCALSTATE/blocked-packages.list
DEFAULT_MIRROR="http://mirror.slitaz.org/packages/`cat /etc/slitaz-release`/"
INSTALL_LIST=""

# Bold red warning for upgrade.
WARNING="\\033[1;31mWARNING\\033[0;39m"

# Check if the directories and files used by Tazpkg
# exists. If not and user is root we create them.
if test $(id -u) = 0 ; then
	if [ ! -d "$CACHE_DIR" ]; then
		mkdir -p $CACHE_DIR
	fi
	if [ ! -d "$INSTALLED" ]; then
		mkdir -p $INSTALLED
	fi
	if [ ! -f "$LOCALSTATE/mirror" ]; then
		echo "$DEFAULT_MIRROR" > $LOCALSTATE/mirror
	fi
fi

####################
# Script functions #
####################

# Print the usage.
usage ()
{
	echo -e "SliTaz packages manager - Version: $VERSION\n
\033[1mUsage:\033[0m tazpkg [command] [package|dir|pattern|list|cat|--opt] [dir|--opt]
       tazpkg shell\n
\033[1mCommands: \033[0m
  usage            Print this short usage.
  list             List installed packages on the system by category or all.
  xhtml-list       Creates a xHTML list of installed packges.
  list-mirror      List all available packages on the mirror (--diff for new).
  info             Print informations about the package.
  desc             Print description of a package (if it exist).
  list-files       List of files installed with the package.
  search           Search for a package by pattern or name (options: -i|-l|-m).
  search-file	   Search for file(s) in all installed packages files.
  install          Install a local (*.tazpkg) package (--forced to force).
  install-list     Install all packages from a list of packages.
  remove           Remove the specified package and all installed files.
  extract          Extract a (*.tazpkg) package into a directory.
  pack             Pack an unpacked or prepared package tree.
  recharge         Recharge your packages.list from the mirror.
  repack           Creates a package archive from an installed package.
  upgrade          Upgrade all installed and listed packages on the mirror.
  block|unblock    Block an installed package version or unblock it for upgrade.
  get              Download a package into the current directory.
  get-install      Download and install a package from the mirror.
  get-install-list Download and install a list of packages from the mirror.
  check            Verify installed packages concistancy.
  add-flavor       Install the flavor list of packages.
  install-flavor   Install the flavor list of packages and remove other ones.
  set-release      Change release and update packages
  clean-cache      Clean all packages downloaded in cache directory.
  setup-mirror     Change the mirror url configuration.
  reconfigure	   Replay post install script from package."
}

# Status function with color (supported by Ash).
status()
{
	local CHECK=$?
	echo -en "\\033[70G[ "
	if [ $CHECK = 0 ]; then
		echo -en "\\033[1;33mOK"
	else
		echo -en "\\033[1;31mFailed"
	fi
	echo -e "\\033[0;39m ]"
	return $CHECK
}

# Check if user is root to install, or remove packages.
check_root()
{
	if test $(id -u) != 0 ; then
		echo -e "\nYou must be root to run `basename $0` with this option."
		echo -e "Please use 'su' and root password to become super-user.\n"
		exit 0
	fi
}

# Check for a package name on cmdline.
check_for_package_on_cmdline()
{
	if [ -z "$PACKAGE" ]; then
		echo -e "\nPlease specify a package name on the command line.\n"
		exit 0
	fi
}

# Check if the package (*.tazpkg) exist before installing or extracting.
check_for_package_file()
{
	if [ ! -f "$PACKAGE_FILE" ]; then
		echo -e "
Unable to find : $PACKAGE_FILE\n"
		exit 0
	fi
}

# Check for the receipt of an installed package.
check_for_receipt()
{
	if [ ! -f "$INSTALLED/$PACKAGE/receipt" ]; then
		echo -e "\nUnable to find the receipt : $INSTALLED/$PACKAGE/receipt\n"
		exit 0
	fi
}

# Get package name in a directory
package_fullname_in_dir()
{
	[ -f $2$1/receipt ] || return
	EXTRAVERSION=""
	. $2$1/receipt
	echo $PACKAGE-$VERSION$EXTRAVERSION
}

# Get package name that is already installed.
get_installed_package_pathname()
{
	for i in $2$INSTALLED/${1%%-*}*; do
		[ -d $i ] || continue
		if [ "$1" = "$(package_fullname_in_dir $i $2)" ]; then
			echo $i
			return
		fi
	done
}

# Check if a package is already installed.
check_for_installed_package()
{
	if [ -n "$(get_installed_package_pathname $PACKAGE $1)" ]; then
		echo -e "
$PACKAGE is already installed. You can use the --forced option to force
installation or remove it and reinstall.\n"
		exit 0
	fi
}

# Check for packages.list to download and install packages.
check_for_packages_list()
{
	if [ ! -f "$LOCALSTATE/packages.list" ]; then
		if test $(id -u) = 0 ; then
			tazpkg recharge
		else
			echo -e "
Unable to find the list : $LOCALSTATE/packages.list\n
You must probably run 'tazpkg recharge' as root to get the last list of 
packages avalaible on the mirror.\n"
			exit 0
		fi
	fi
}

# Check for a package in packages.list. Used by get and get-install to grep
# package basename.
check_for_package_in_list()
{
	local pkg
	pkg=$(grep "^$PACKAGE-[0-9]" $LOCALSTATE/packages.list | head -1)
	[ -n "$pkg" ] || pkg=$(grep "^$PACKAGE-.[\.0-9]" $LOCALSTATE/packages.list | head -1)
	if [ -n "$pkg" ]; then
		PACKAGE=$pkg
	else
		echo -e "\nUnable to find : $PACKAGE in the mirrored packages list.\n"
		exit 0
	fi
}

# Download a file trying all mirrors
download()
{
	for i in $(cat $MIRROR); do
		wget -c $i$@ && break
	done
}

# Extract a package with cpio and gzip.
extract_package()
{
	echo -n "Extracting $PACKAGE... "
	cpio -id < $PACKAGE.tazpkg && rm -f $PACKAGE.tazpkg
	gzip -d fs.cpio.gz
	echo -n "Extracting the pseudo fs... "
	cpio -id < fs.cpio && rm fs.cpio
}

# This function install a package in the rootfs.
install_package()
{
	ROOT=$1
	if [ -n "$ROOT" ]; then
		 # get absolute path
		 ROOT=$(cd $ROOT; pwd)
	fi
	(
		# Create package path early to avoid dependancies loop
		mkdir -p $TMP_DIR
		( cd $TMP_DIR ; cpio -i receipt > /dev/null) < $PACKAGE_FILE
		. $TMP_DIR/receipt
		rm -rf $TMP_DIR
		# Make the installed package data dir to store
		# the receipt and the files list.
		mkdir -p $ROOT$INSTALLED/$PACKAGE
	)
	# Resolv package deps.
	check_for_deps $ROOT
	if [ ! "$MISSING_PACKAGE" = "" ]; then
		install_deps $ROOT
	fi
	mkdir -p $TMP_DIR
	[ -n "$INSTALL_LIST" ] && echo "$PACKAGE_FILE" >> $INSTALL_LIST-processed
	echo ""
	echo -e "\033[1mInstallation of :\033[0m $PACKAGE"
	echo "================================================================================"
	echo -n "Copying $PACKAGE... "
	cp $PACKAGE_FILE $TMP_DIR
	status
	cd $TMP_DIR
	extract_package
	SELF_INSTALL=0
	EXTRAVERSION=""
	# Include temporary receipt to get the right variables.
	. $PWD/receipt
	if [ $SELF_INSTALL -ne 0 -a -n "$ROOT" ]; then
		echo -n "Checking post install dependencies... "
		[ -f $INSTALLED/$PACKAGE/receipt ]
		if ! status; then
			echo "Please run 'tazpkg install $PACKAGE_FILE' in / and retry."
			cd .. && rm -rf $TMP_DIR
			exit 1
		fi
	fi
	# Remember modified packages
	for i in $(grep -v '\[' files.list); do
		[ -e "$ROOT$i" ] || continue
		[ -d "$ROOT$i" ] && continue
		for j in $(grep -l "^$i$" $ROOT$INSTALLED/*/files.list); do
			[ "$j" = "$ROOT$INSTALLED/$PACKAGE/files.list" ] && continue
			grep -qs ^$PACKAGE$ $(dirname $j)/modifiers && continue
			echo "$PACKAGE" >> $(dirname $j)/modifiers
		done
	done
	cp receipt files.list $ROOT$INSTALLED/$PACKAGE
	# Copy the description if found.
	if [ -f "description.txt" ]; then
		cp description.txt $ROOT$INSTALLED/$PACKAGE
	fi
	# Pre install commands.
	if grep -q ^pre_install $ROOT$INSTALLED/$PACKAGE/receipt; then
		pre_install $ROOT
	fi
	echo -n "Installing $PACKAGE... "
	cp -a fs/* $ROOT/
	status
	# Remove the temporary random directory.
	echo -n "Removing all tmp files... "
	cd .. && rm -rf $TMP_DIR
	status
	# Post install commands.
	if grep -q ^post_install $ROOT$INSTALLED/$PACKAGE/receipt; then
		post_install $ROOT
	fi
	cd $TOP_DIR
	echo "================================================================================"
	echo "$PACKAGE ($VERSION$EXTRAVERSION) is installed."
	echo ""
}

# Check for loop in deps tree.
check_for_deps_loop()
{
	local list
	local pkg
	local deps
	pkg=$1
	shift
	[ -n "$1" ] || return
	list=""
	# Filter out already processed deps
	for i in $@; do
		case " $ALL_DEPS" in
		*\ $i\ *);;
		*) list="$list $i";;
		esac
	done
	ALL_DEPS="$ALL_DEPS$list "
	for i in $list; do
		[ -f $i/receipt ] || continue
		deps="$(DEPENDS=""; . $i/receipt; echo $DEPENDS)"
		case " $deps " in
		*\ $pkg\ *) echo -e "$MSG  $i"; MSG="";;
		*) check_for_deps_loop $pkg $deps;;
		esac
	done
}

# Check for missing deps listed in a receipt packages.
check_for_deps()
{
	local saved;
	saved=$PACKAGE
	mkdir -p $TMP_DIR
	( cd $TMP_DIR ; cpio -i receipt > /dev/null ) < $PACKAGE_FILE
	. $TMP_DIR/receipt
	PACKAGE=$saved
	rm -rf $TMP_DIR
	for i in $DEPENDS
	do
		if [ ! -d "$1$INSTALLED/$i" ]; then
			MISSING_PACKAGE=$i
			deps=$(($deps+1))
		elif [ ! -f "$1$INSTALLED/$i/receipt" ]; then
			echo -e "$WARNING Dependancy loop between $PACKAGE and $i."
		fi
	done
	if [ ! "$MISSING_PACKAGE" = "" ]; then
		echo -e "\033[1mTracking dependencies for :\033[0m $PACKAGE"
		echo "================================================================================"
		for i in $DEPENDS
		do
			if [ ! -d "$1$INSTALLED/$i" ]; then
				MISSING_PACKAGE=$i
				echo "Missing : $MISSING_PACKAGE"
			fi
		done
		echo "================================================================================"
		echo "$deps missing package(s) to install."
	fi
}

# Install all missing deps. First ask user then install all missing deps
# from local dir, cdrom, media or from the mirror. In case we want to
# install packages from local, we need a packages.list to find the version.
install_deps()
{
	local root
	root=""
	[ -n "$1" ] && root="--root=$1"
	echo ""
	echo -n "Install all missing dependencies (y/N) ? "; read anser
	echo ""
	if [ "$anser" = "y" ]; then
		for pkg in $DEPENDS
		do
			if [ ! -d "$1$INSTALLED/$pkg" ]; then
				local list
				list="$INSTALL_LIST"
				[ -n "$list" ] || list="$TOP_DIR/packages.list"
				# We can install packages from a local dir by greping
				# the TAZPKG_BASENAME in the local packages.list.
				if [ -f "$list" ]; then
					echo "Checking if $pkg exist in local list... "
					mkdir $TMP_DIR
					for i in $pkg-*.tazpkg; do
						[ -f $i ] || continue
						( cd $TMP_DIR ; cpio -i receipt > /dev/null) < $i
						if grep -q ^$(package_fullname_in_dir $TMP_DIR).tazpkg$ $list
						then
							tazpkg install $i $root --list=$list
							break
						fi
					done
					rm -rf $TMP_DIR
				# Install deps from the mirror.
				else
					if [ ! -f "$LOCALSTATE/packages.list" ]; then
						tazpkg recharge
					fi
					tazpkg get-install $pkg $root
				fi
			fi
		done
	else
		echo -e "\nLeaving dependencies for $PACKAGE unsolved."
		echo -e "The package is installed but will probably not work.\n"
	fi
}

# xHTML packages list header.
xhtml_header()
{
	cat > $XHTML_LIST << _EOT_
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
	"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
	<title>Installed packages list</title>
	<meta http-equiv="content-type" content="text/html; charset=ISO-8859-1" />
	<meta name="modified" content="$DATE" />
	<meta name="generator" content="Tazpkg" />
	<style type="text/css"><!--
	body { font: 12px sans-serif, vernada, arial; margin: 0; }
	#header { background: #f0ba08; color: black; height: 50px;
		border-top: 1px solid black; border-bottom: 1px solid black; }
	#content { margin: 0px 50px 26px 50px; }
	#footer { border-top: 1px solid black; padding-top: 10px;}
	h1 { margin: 14px 0px 0px 16px; }
	pre { padding-left: 5px; }
	hr { color: white; background: white; height: 1px; border: 0; }
	--></style>
</head>
<body bgcolor="#ffffff">
<div id="header">
<h1><font color="#3e1220">Installed packages list</font></h1>
</div>
<hr />
<!-- Start content -->
<div id="content">

<p>
_packages_ packages installed - List generated on : $DATE
<p>

_EOT_
}

# xHTML content with packages infos.
xhtml_pkg_info()
{
	cat >> $XHTML_LIST << _EOT_
<h3>$PACKAGE</h3>
<pre>
Version    : $VERSION$EXTRAVERSION
Short desc : $SHORT_DESC
Web site   : <a href="$WEB_SITE">$WEB_SITE</a>
</pre>

_EOT_
}

# xHTML packages list footer.
xhtml_footer()
{
	cat >> $XHTML_LIST << _EOT_
<hr />
<p id="footer">
$packages packages installed - List generated on : $DATE
</p>

<!-- End content -->
</div>
</body>
</html>
_EOT_
}

# Search pattern in installed packages.		
search_in_installed_packages()
{
	echo "Installed packages"
	echo "================================================================================"
	list=`ls -1 $INSTALLED | grep -i "$PATTERN"`
	for pkg in $list
	do
		EXTRAVERSION=""
		[ -f $INSTALLED/$pkg/receipt ] || continue
		. $INSTALLED/$pkg/receipt
		echo -n "$PACKAGE "
		echo -en "\033[24G $VERSION$EXTRAVERSION"
		echo -e "\033[42G $CATEGORY"
		packages=$(($packages+1))
	done
	# Set correct ending messages.
	if [ "$packages" = "" ]; then
		echo "0 installed packages found for : $PATTERN"
		echo ""
	else
		echo "================================================================================"
		echo "$packages installed package(s) found for : $PATTERN"
		echo ""
	fi
}

# Search in packages.list for avalaible pkgs.	
search_in_packages_list()
{
	echo "Available packages name-version"
	echo "================================================================================"
	if [ -f "$LOCALSTATE/packages.list" ]; then
		cat $LOCALSTATE/packages.list | grep -i "$PATTERN"
		packages=`cat $LOCALSTATE/packages.list | grep "$PATTERN" | wc -l`
	else
		echo -e "
No 'packages.list' found to check for mirrored packages. For more results,
please run once 'tazpkg recharge' as root before searching.\n"
	fi
	if [ "$packages" = "0" ]; then
		echo "0 available packages found for : $PATTERN"
		echo ""
	else
		echo "================================================================================"
		echo "$packages available package(s) found for : $PATTERN"
		echo ""
	fi
}

# search --mirror: Search in packages.txt for avalaible pkgs and give more 
# infos than --list or default.	
search_in_packages_txt()
{
	echo "Matching packages name with version and desc"
	echo "================================================================================"
	if [ -f "$LOCALSTATE/packages.txt" ]; then
		cat $LOCALSTATE/packages.txt | grep -A 2 "^$PATTERN"
		packages=`cat $LOCALSTATE/packages.txt | grep -i "^$PATTERN" | wc -l`
	else
		echo -e "
No 'packages.txt' found to check for mirrored packages. For more results,
please run once 'tazpkg recharge' as root before searching.\n"
	fi
	if [ "$packages" = "0" ]; then
		echo "0 available packages found for : $PATTERN"
		echo ""
	else
		echo "================================================================================"
		echo "$packages available package(s) found for : $PATTERN"
		echo ""
	fi
}

# Install package-list from a flavor
install_flavor()
{
	check_root
	FLAVOR=$1
	ARG=$2
	mkdir -p $TMP_DIR
	[ -f $FLAVOR.flavor ] && cp $FLAVOR.flavor $TMP_DIR
	cd $TMP_DIR
	if [ -f $FLAVOR.flavor ] || download $FLAVOR.flavor; then
		zcat $FLAVOR.flavor | cpio -i 2>/dev/null
		while read file; do
			for pkg in $(ls -d $INSTALLED/${file%%-*}*); do
				[ -f $pkg/receipt ] || continue
				EXTRAVERSION=""
				. $pkg/receipt
				[ "$PACKAGE-$VERSION$EXTRAVERSION" = "$file" ] && break
			done
			[ "$PACKAGE-$VERSION$EXTRAVERSION" = "$file" ] && continue
			cd $CACHE_DIR
			download $file.tazpkg
			cd $TMP_DIR
		        tazpkg install $CACHE_DIR/$file.tazpkg --forced
		done < $FLAVOR.pkglist
		[ -f $FLAVOR.nonfree ] && while read pkg; do
			[ -d $INSTALLED/$pkg ] || continue
			[ -d $INSTALLED/get-$pkg ] && tazpkg get-install get-$pkg
			get-$pkg
		done < $FLAVOR.nonfree
		[ "$ARG" == "--purge" ] && for pkg in $(ls $INSTALLED); do
			[ -f $INSTALLED/$pkg/receipt ] || continue
			EXTRAVERSION=""
			. $INSTALLED/$pkg/receipt
			grep -q ^$PACKAGE-$VERSION$EXTRAVERSION$ $FLAVOR.pkglist && continue
			grep -qs ^$PACKAGE$ $FLAVOR.nonfree && continue
			tazpkg remove $PACKAGE
		done
	else
		echo "Can't find flavor $FLAVOR Abort."
	fi
	cd $TOP_DIR
	rm -rf $TMP_DIR
}

###################
# Tazpkg commands #
###################

case "$COMMAND" in
	list)
		# List all installed packages or a specific category.
		#
		if [ "$2" = "blocked" ]; then
			if [ -f $BLOCKED ]; then
				LIST=`cat $BLOCKED`
			fi
			echo ""
			echo -e "\033[1mBlocked packages\033[0m"
			echo "================================================================================"
			if [ -n $LIST ];then
				echo $LIST
				echo ""
			else
				echo -e "No blocked packages found.\n"
			fi
			exit 0
		fi
		# Display the list of categories.
		if [ "$2" = "cat" -o "$2" = "categories" ]; then
			echo ""
			echo -e "\033[1mPackages categories :\033[0m"
			echo "================================================================================"
			for i in $CATEGORIES
			do
				echo $i
				categories=$(($categories+1))
			done
			echo "================================================================================"
			echo "$categories categories"
			echo ""
			exit 0
		fi
		# Check for an asked category.
		if [ -n "$2" ]; then
			ASKED_CATEGORY=$2
			echo ""
			echo -e "\033[1mInstalled packages of category :\033[0m $ASKED_CATEGORY"
			echo "================================================================================"
			for pkg in $INSTALLED/*
			do
				[ -f $pkg/receipt ] || continue
				EXTRAVERSION=""
				. $pkg/receipt
				if [ "$CATEGORY" == "$ASKED_CATEGORY" ]; then
					echo -n "$PACKAGE"
					echo -e "\033[24G $VERSION$EXTRAVERSION"
					packages=$(($packages+1))
				fi
			done
			echo "================================================================================"
			echo -e "$packages packages installed of category $ASKED_CATEGORY."
			echo ""
		else
			# By default list all packages and version.
			echo ""
			echo -e "\033[1mList of all installed packages\033[0m"
			echo "================================================================================"
			for pkg in $INSTALLED/*
			do
				[ -f $pkg/receipt ] || continue
				EXTRAVERSION=""
				. $pkg/receipt
				echo -n "$PACKAGE"
				echo -en "\033[24G $VERSION$EXTRAVERSION"
				echo -e "\033[42G $CATEGORY"
				packages=$(($packages+1))
			done
			echo "================================================================================"
			echo "$packages packages installed."
			echo ""
		fi
		;;
	xhtml-list)
		# Get infos in receipts and build list.
		DATE=`date +%Y-%m-%d\ \%H:%M:%S`
		if [ -n "$2" ]; then
			XHTML_LIST=$2
		else
			XHTML_LIST=installed-packages.html
		fi
		echo ""
		echo -e "\033[1mCreating xHTML list of installed packages\033[0m"
		echo "================================================================================"
		echo -n "Generating xHTML header..."
		xhtml_header
		status
		# Packages
		echo -n "Creating packages informations..."
		for pkg in $INSTALLED/*
		do
			[ -f $pkg/receipt ] || continue
			EXTRAVERSION=""
			. $pkg/receipt
			xhtml_pkg_info
			packages=$(($packages+1))
		done
		status
		echo -n "Generating xHTML footer..."
		xhtml_footer
		status
		# sed pkgs nb in header.
		sed -i s/'_packages_'/"$packages"/ $XHTML_LIST
		echo "================================================================================"
		echo "$XHTML_LIST created - $packages packages."
		echo ""
		;;
	list-mirror)
		# List all available packages on the mirror. Option --diff display
		# last mirrored packages diff (see recharge).
		check_for_packages_list
		case $2 in
			--diff)
				if [ -f "$LOCALSTATE/packages.diff" ]; then
					echo ""
					echo -e "\033[1mMirrored packages diff\033[0m"
					echo "================================================================================"
					cat $LOCALSTATE/packages.diff
					echo "================================================================================"
					pkgs=`cat $LOCALSTATE/packages.diff | wc -l`
					echo "$pkgs new packages listed on the mirror."
					echo ""
				else
					 echo -e "\nUnable to list anything, no packages.diff found."
					 echo -e "Recharge your current list to creat a first diff.\n"
				fi && exit 0 ;;
			--text|--txt)
				echo ""
				echo -e "\033[1mList of available packages on the mirror\033[0m"
				echo "================================================================================"
				cat $LOCALSTATE/packages.txt ;;
			--raw|*)
				echo ""
				echo -e "\033[1mList of available packages on the mirror\033[0m"
				echo "================================================================================"
				cat $LOCALSTATE/packages.list ;;
		esac
		echo "================================================================================"
		pkgs=`cat $LOCALSTATE/packages.list | wc -l`
		echo "$pkgs packages in the last recharged list."
		echo "" 
		;;
	list-files)
		# List files installed with the package.
		#
		check_for_package_on_cmdline
		check_for_receipt
		echo ""
		echo -e "\033[1mInstalled files with :\033[0m $PACKAGE"
		echo "================================================================================"
		cat $INSTALLED/$PACKAGE/files.list | sort
		echo "================================================================================"
		files=`cat $INSTALLED/$PACKAGE/files.list | wc -l`
		echo "$files files installed with $PACKAGE."
		echo ""
		;;
	info)
		# Information about package.
		#
		check_for_package_on_cmdline
		check_for_receipt
		EXTRAVERSION=""
		. $INSTALLED/$PACKAGE/receipt
		echo ""
		echo -e "\033[1mTazpkg informations\033[0m
================================================================================
Package    : $PACKAGE
Version    : $VERSION$EXTRAVERSION
Category   : $CATEGORY
Short desc : $SHORT_DESC
Maintainer : $MAINTAINER"
		if [ ! "$DEPENDS" = "" ]; then
			echo -e "Depends    : $DEPENDS"
		fi
		if [ ! "$SUGGESTED" = "" ]; then
			echo -e "Suggested  : $SUGGESTED"
		fi
		if [ ! "$BUILD_DEPENDS" = "" ]; then
			echo -e "Build deps : $BUILD_DEPENDS"
		fi
		if [ ! "$WANTED" = "" ]; then
			echo -e "Wanted src : $WANTED"
		fi
		if [ ! "$WEB_SITE" = "" ]; then
			echo -e "Web site   : $WEB_SITE"
		fi
		echo "================================================================================"
		echo ""
		;;
	desc)
		# Display package description.txt if available.
		if [ -f "$INSTALLED/$PACKAGE/description.txt" ]; then
			echo ""
			echo -e "\033[1mDescription of :\033[0m $PACKAGE"
			echo "================================================================================"
			cat $INSTALLED/$PACKAGE/description.txt
			echo "================================================================================"
			echo ""
		else
			echo -e "\nSorry, no description available for this package.\n"
		fi
		;;
	search)
		# Search for a package by pattern or name.
		#
		PATTERN="$2"
		if [ -z "$PATTERN" ]; then
			echo -e "\nPlease specify a pattern or a package name to search."
			echo -e "Example : 'tazpkg search paint'.\n"
			exit 0
		fi
		echo ""
		echo -e "\033[1mSearch result for :\033[0m $PATTERN"
		echo ""
		# Default is to search in installed pkgs and the raw list.
		case $3 in
			-i|--installed)
				search_in_installed_packages ;;
			-l|--list)
				search_in_packages_list ;;
			-m|--mirror)
				search_in_packages_txt ;;
			*)
				search_in_installed_packages
				search_in_packages_list ;;
		esac
		;;
	search-file)
		# Search for a file by pattern or name in all files.list.
		#
		if [ -z "$2" ]; then
			echo -e "\nPlease specify a pattern or a file name to search."
			echo -e "Example : 'tazpkg search-file libnss'. \n"
			exit 0
		fi
		echo ""
		echo -e "\033[1mSearch result for file :\033[0m $2"
		echo "================================================================================"

		if [ "$3" == "--mirror" ]; then
		
		unlzma -c $LOCALSTATE/files.list.lzma | grep -- ".*:.*$2" | awk '
                            BEGIN { last="" }
                            {
			    	pkg=substr($0,0,index($0,":")-1);
			    	file=substr($0,index($0,":")+2);
                                if (last != pkg) {
				    last = pkg;
				    printf("\n%c[1mPackage %s :%c[0m\n",27,pkg,27);
				}
                                printf("%s\n",file);
                            }'
		match=`unlzma -c $LOCALSTATE/files.list.lzma | \
			grep -- ".*:.*$2" | wc -l`

		else

		# Check all pkg files.list in search match with specify the package
		# name and the full path to the file(s).
		for pkg in $INSTALLED/*
		do
			if grep -qs "$2" $pkg/files.list; then
				. $pkg/receipt
				echo ""
				echo -e "\033[1mPackage $PACKAGE :\033[0m"
				grep "$2" $pkg/files.list
				files=`grep $2 $pkg/files.list | wc -l`
				match=$(($match+$files))
			fi
		done

		fi

		if [ "$match" = "" ]; then
			echo "0 file found for : $2"
			echo ""
		else
			echo ""
			echo "================================================================================"
			echo "$match file(s) found for : $2"
			echo ""
		fi
		;;
	install)
		# Install .tazpkg packages.
		#
		check_root
		check_for_package_on_cmdline
		check_for_package_file
		# Check if forced install.
		DO_CHECK="yes"
		ROOT=""
		while [ -n "$3" ]; do
			case "$3" in
			--forced)
				DO_CHECK="no"
				;;
			--root=*)
				ROOT="${3#--root=}"
				;;
			--list=*)
				INSTALL_LIST="${3#--list=}"
				;;
			*)	shift 2
				echo -e "\nUnknown option $*.\n"
				exit 1
				;;
			esac
			shift
		done
		if [ "$DO_CHECK" = "yes" ]; then
			check_for_installed_package $ROOT
		fi
		install_package $ROOT
		;;
	install-list|get-install-list)
		# Install a set of packages from a list.
		#
		check_root
		if [ -z "$2" ]; then
			echo -e "
Please change directory (cd) to the packages repository, and specify the
list of packages to install. Example : tazpkg install-list packages.list\n"
			exit 0
		fi
		# Check if the packages list exist.
		if [ ! -f "$2" ]; then
			echo "Unable to find : $2"
			exit 0
		else
			LIST=`cat $2`
		fi
		
		# Remember processed list
		export INSTALL_LIST="$2"

		# Set $COMMAND and install all packages.
		if [ "$1" = "get-install-list" ]; then
			COMMAND=get-install
		else
			COMMAND=install
		fi
		touch $2-processed
		for pkg in $LIST
		do
			grep -qs ^$pkg$ $2-processed && continue
			tazpkg $COMMAND $pkg --list=$2 "$3" "$4" "$5"
		done
		rm -f $2-processed
		;;
	add-flavor)
		# Install a set of packages from a flavor.
		#
		install_flavor $2
		;;
	install-flavor)
		# Install a set of packages from a flavor and purge other ones.
		#
		install_flavor $2 --purge
		;;
	set-release)
		# Change curent release and upgrade packages.
		#
		RELEASE=$2
		if [ -z "$RELEASE" ]; then
			echo -e "\nPlease specify the release you want on the command line."
			echo -e "Example: tazpkg set-release cooking\n"
			exit 0
		fi
		rm /var/lib/tazpkg/mirror
		echo "$RELEASE" > /etc/slitaz-release
		tazpkg recharge && tazpkg upgrade
		;;
	remove)
		# Remove packages.
		#
		check_root
		check_for_package_on_cmdline
		if [ ! -f "$INSTALLED/$PACKAGE/receipt" ]; then
			echo -e "\n$PACKAGE is not installed.\n"
			exit 0
		else
			ALTERED=""
			THE_PACKAGE=$PACKAGE	# altered by receipt
			for i in $(cd $INSTALLED ; ls); do
				DEPENDS=""
				. $INSTALLED/$i/receipt
				case " $(echo $DEPENDS) " in
				*\ $THE_PACKAGE\ *) ALTERED="$ALTERED $i";;
				esac
			done
			EXTRAVERSION=""
			. $INSTALLED/$THE_PACKAGE/receipt
		fi
		echo ""
		if [ -n "$ALTERED" ]; then
			echo "The following packages depend on $PACKAGE :"
			for i in $ALTERED; do
				echo "  $i"
			done
		fi
		echo "Remove $PACKAGE ($VERSION$EXTRAVERSION) ?"
		echo -n "Please confirm uninstallation (y/N) : "; read anser
		if [ "$anser" = "y" ]; then
			echo ""
			echo -e "\033[1mRemoving :\033[0m $PACKAGE"
			echo "================================================================================"
			# Pre remove commands.
			if grep -q ^pre_remove $INSTALLED/$PACKAGE/receipt; then
				pre_remove
			fi
			echo -n "Removing all files installed..."
			for file in `cat $INSTALLED/$PACKAGE/files.list`
			do
				[ $(grep ^$file$ $INSTALLED/*/files.list | wc -l) -gt 1 ] && continue
				rm -f $file 2>/dev/null
			done
			status
			if grep -q ^post_remove $INSTALLED/$PACKAGE/receipt; then
				post_remove
			fi
			# Remove package receipt.
			echo -n "Removing package receipt..."
			rm -rf $INSTALLED/$PACKAGE
			status
			if [ -n "$ALTERED" ]; then
				echo -n "Remove packages depending on $PACKAGE"
				echo -n " (y/N) ? "; read anser
				if [ "$anser" = "y" ]; then
					for i in $ALTERED; do
						if [ -d "$INSTALLED/$i" ]; then
							tazpkg remove $i
						fi
					done
				fi
			fi
		else
			echo ""
			echo "Uninstallation of $PACKAGE cancelled."
		fi
		echo ""
		;;
	extract)
		# Extract .tazpkg cpio archive into a directory.
		#
		check_for_package_on_cmdline
		check_for_package_file
		echo ""
		echo -e "\033[1mExtracting :\033[0m $PACKAGE"
		echo "================================================================================"
		# If any directory destination is found on the cmdline
		# we creat one in the current dir using the package name.
		if [ -n "$TARGET_DIR" ]; then
			DESTDIR=$TARGET_DIR/$PACKAGE
		else
			DESTDIR=$PACKAGE
		fi
		mkdir -p $DESTDIR
		echo -n "Copying original package..."
		cp $PACKAGE_FILE $DESTDIR
		status
		cd $DESTDIR
		extract_package
		echo "================================================================================"
		echo "$PACKAGE is extracted to : $DESTDIR"
		echo ""
		;;
	repack)
		# Creat SliTaz package archive from an installed package.
		#
		check_for_package_on_cmdline
		check_for_receipt
		EXTRAVERSION=""
		. $INSTALLED/$PACKAGE/receipt
		echo ""
		echo -e "\033[1mRepacking :\033[0m $PACKAGE-$VERSION$EXTRAVERSION.tazpkg"
		echo "================================================================================"
		if grep -qs ^NO_REPACK= $INSTALLED/$PACKAGE/receipt; then
			echo "Can't repack $PACKAGE"
			exit 1
		fi
		if [ -s $INSTALLED/$PACKAGE/modifiers ]; then
			echo "Can't repack, $PACKAGE files have been modified by:"
			for i in $(cat $INSTALLED/$PACKAGE/modifiers); do
				echo "  $i"
			done
			exit 1
		fi
		MISSING=""
		while read i; do
			[ -e "$i" ] && continue
			[ -L "$i" ] || MISSING="$MISSING\n  $i"
		done < $INSTALLED/$PACKAGE/files.list
		if [ -n "$MISSING" ]; then
			echo -n "Can't repack, the following files are lost:"
			echo -e "$MISSING"
			exit 1
		fi
		mkdir -p $TMP_DIR && cd $TMP_DIR
		FILES="fs.cpio.gz\n"
		for i in $(ls $INSTALLED/$PACKAGE) ; do
			cp $INSTALLED/$PACKAGE/$i . && FILES="$FILES$i\n"
		done
		ln -s / rootfs
		mkdir tmp
		sed 's/^/rootfs/' < files.list | cpio -o -H newc 2>/dev/null |\
		      ( cd tmp ; cpio -id 2>/dev/null )
		mv tmp/rootfs fs
		if grep -q repack_cleanup $INSTALLED/$PACKAGE/receipt; then
			. $INSTALLED/$PACKAGE/receipt
			repack_cleanup fs
		fi
		if [ -f $INSTALLED/$PACKAGE/md5sum ]; then
			sed 's,  ,  fs,' < $INSTALLED/$PACKAGE/md5sum | \
			if ! md5sum -s -c; then
				echo -n "Can't repack, md5sum error."
				cd $TOP_DIR
				\rm -R $TMP_DIR
				exit 1
			fi
		fi
		find fs | cpio -o -H newc 2> /dev/null | gzip -9 > fs.cpio.gz
		echo -e "$FILES" | cpio -o -H newc 2> /dev/null > \
			$TOP_DIR/$PACKAGE-$VERSION$EXTRAVERSION.tazpkg
		cd $TOP_DIR
		\rm -R $TMP_DIR
		echo "Package $PACKAGE repacked successfully."
		echo "Size : `du -sh $PACKAGE-$VERSION$EXTRAVERSION.tazpkg`"
		echo ""
		;;
	pack)
		# Creat SliTaz package archive using cpio and gzip.
		#
		check_for_package_on_cmdline
		cd $PACKAGE
		if [ ! -f "receipt" ]; then
			echo "Receipt is missing. Please read the documentation."
			exit 0
		else
			echo ""
			echo -e "\033[1mPacking :\033[0m $PACKAGE"
			echo "================================================================================"
			# Creat files.list with redirecting find outpout.
			echo -n "Creating the list of files..." && cd fs
			find . -type f -print > ../files.list
			find . -type l -print >> ../files.list
			cd .. && sed -i s/'^.'/''/ files.list
			status
			# Build cpio archives.
			echo -n "Compressing the fs... "
			find fs -print | cpio -o -H newc > fs.cpio
			gzip fs.cpio && rm -rf fs
			echo -n "Creating full cpio archive... "
			find . -print | cpio -o -H newc > ../$PACKAGE.tazpkg
			echo -n "Restoring original package tree... "
			gzip -d fs.cpio.gz && cpio -id < fs.cpio
			rm fs.cpio && cd ..
			echo "================================================================================"
			echo "Package $PACKAGE compressed successfully."
			echo "Size : `du -sh $PACKAGE.tazpkg`"
			echo ""
		fi
		;;
	recharge)
		# Recharge packages.list from a mirror.
		#
		check_root
		cd $LOCALSTATE
		echo ""
		if [ -f "$LOCALSTATE/packages.list" ]; then
			echo -n "Creating backup of the last packages list..."
			mv -f packages.desc packages.desc.bak 2>/dev/null
			mv -f packages.txt packages.txt.bak 2>/dev/null
			mv -f packages.list packages.list.bak 2>/dev/null
			mv -f files.list.lzma files.list.lzma.bak 2> /dev/nul
			status
		fi
		download packages.desc
		download packages.txt
		download packages.list
		download files.list.lzma
		if [ -f "$LOCALSTATE/packages.list.bak" ]; then
			diff -u packages.list.bak packages.list | grep ^+[a-z] > packages.diff
			sed -i s/+// packages.diff
			echo ""
			echo -e "\033[1mMirrored packages diff\033[0m"
			echo "================================================================================"
			cat packages.diff
			if [ ! "`cat packages.diff | wc -l`" = 0 ]; then
				echo "================================================================================"
				echo "`cat packages.diff | wc -l` new packages on the mirror."
				echo ""
			else
				echo "`cat packages.diff | wc -l` new packages on the mirror."
				echo ""
			fi
		else
			echo -e "
================================================================================
Last packages.list is ready to use. Note that next time you recharge the list,
a list of differencies will be displayed to show new and upgradable packages.\n"
		fi
		;;
	upgrade)
		# Upgrade all installed packages with the new version from the mirror.
		#
		check_root
		check_for_packages_list
		cd $LOCALSTATE
		# Touch the blocked pkgs list to avoid errors and remove any old
		# upgrade list.
		touch blocked-packages.list
		rm -f upradable-packages.list
		echo ""
		echo -e "\033[1mAvalaible upgrade\033[0m"
		echo "================================================================================"
		echo ""
		# Some packages must be installed first
		FIRST_CLASS_PACKAGE=" glibc-base slitaz-base-files slitaz-boot-scripts "
		for pkg in $INSTALLED/*
		do 
			[ -f $pkg/receipt ] || continue
			EXTRAVERSION=""
			. $pkg/receipt
			# Diplay package name to show that Tazpkg is working...
			echo -en "\\033[0G                                         "
			echo -en "\\033[0G$PACKAGE"
			# Skip specified pkgs listed in $LOCALSTATE/blocked-packages.list
			if grep -q "^$PACKAGE" $BLOCKED; then
				blocked=$(($blocked+1))
			else
				# Check if the installed package is in the current list (other
				# mirror or local).
				NEW_PACKAGE=$(grep "^$PACKAGE-[0-9]" packages.list | head -1)
				[ -n "$NEW_PACKAGE" ] || NEW_PACKAGE=$(grep "^$PACKAGE-.[\.0-9]" packages.list | head -1)

				if [ -n "$NEW_PACKAGE" ]; then
					# Set new pkg and version for futur comparaison
					NEW_VERSION=`echo $NEW_PACKAGE | sed s/$PACKAGE-/''/`
					# Change '-' and 'pre' to points.
					NEW_VERSION=`echo $NEW_VERSION | sed s/'-'/'.'/`
					VERSION=`echo $VERSION | sed s/'-'/'.'/`$EXTRAVERSION
					NEW_VERSION=`echo $NEW_VERSION | sed s/'pre'/'.'/`
					VERSION=`echo $VERSION | sed s/'pre'/'.'/`
					NEW_VERSION=`echo $NEW_VERSION | sed 's/[A-Z]\.//'`
					VERSION=`echo $VERSION | sed 's/[A-Z]\.//'`
					# Compare version. Upgrade are only avalaible for official
					# packages, so we control de mirror and it should be ok if
					# we just check for egality.
					if [ "$VERSION" != "$NEW_VERSION" ]; then
						# Version seems different. Check for major, minor or 
						# revision
						PKG_MAJOR=`echo ${VERSION%_*} | cut -f1 -d"."`
						NEW_MAJOR=`echo ${NEW_VERSION%_*} | cut -f1 -d"."`
						PKG_MINOR=`echo ${VERSION%_*} | cut -f2 -d"."`
						NEW_MINOR=`echo ${NEW_VERSION%_*} | cut -f2 -d"."`
						# Minor
						if [ "$NEW_MINOR" -gt "$PKG_MINOR" ]; then
							RELEASE=minor
						fi
						if [ "$NEW_MINOR" -lt "$PKG_MINOR" ]; then
							RELEASE=$WARNING
							FIXE=yes
						fi
						# Major
						if [ "$NEW_MAJOR" -gt "$PKG_MAJOR" ]; then
							RELEASE=major
							FIXE=""
						fi
						if [ "$NEW_MAJOR" -lt "$PKG_MAJOR" ]; then
							RELEASE=$WARNING
							FIXE=yes
						fi
						# Default to revision.
						if [ -z $RELEASE ]; then
							RELEASE=revision
						fi
						# Pkg name is already displayed by the check process.
						echo -en "\033[24G $VERSION"
						echo -en "\033[38G --->"
						echo -en "\033[43G $NEW_VERSION"
						echo -en "\033[58G $CATEGORY"
						echo -e "\033[72G $RELEASE"
						up=$(($up+1))
						echo "$PACKAGE" >> upradable-packages.list
						case "$FIRST_CLASS_PACKAGE" in
						*\ $PACKAGE\ *) echo "$PACKAGE" >> upradable-packages.list$$;;
						esac
						unset RELEASE
					fi
					packages=$(($packages+1))
				fi
			fi
		done
		if [ -z $blocked ]; then
			blocked=0
		fi
		# Clean last checked package and display summary.
		if [ ! "$up" = "" ]; then
			echo -e "\\033[0G                                         "
			echo "================================================================================"
			echo "$packages installed and listed packages to consider, $up to upgrade, $blocked blocked."
			echo ""
		else
			echo -e "\\033[0GSystem is up to date.                    "
			echo ""
			echo "================================================================================"
			echo "$packages installed and listed packages to consider, 0 to upgrade, $blocked blocked."
			echo ""
			exit 0
		fi
		# What to do if major or minor version is smaller.
		if [ "$FIXE" == "yes" ]; then
			echo -e "$WARNING ---> Installed package seems more recent than the mirrored one."
			echo "You can block packages using the command : 'tazpkg block package'"
			echo "Or upgrade package at you own risks."
			echo ""
		fi
		# Ask for upgrade, it can be done an other time.
		echo -n "Upgrade now (y/N) ? "; read anser
		if [ ! "$anser" = "y" ]; then
			echo -e "\nExiting. No package upgraded.\n"
			exit 0
		fi
		# If anser is yes (y). Install all new version.
		cat upradable-packages.list >> upradable-packages.list$$
		mv -f upradable-packages.list$$ upradable-packages.list
		yes y | tazpkg get-install-list upradable-packages.list
		#rm -f upradable-packages.list
		;;
	check)
		# check installed packages set.
		#
		check_root
		cd $INSTALLED
		for PACKAGE in `ls`; do
			if [ ! -f $PACKAGE/receipt ]; then
				echo "The package $PACKAGE installation is not completed"
				continue
			fi
			DEPENDS=""
			EXTRAVERSION=""
			. $PACKAGE/receipt
			if [ -s $PACKAGE/modifiers ]; then
				echo "The package $PACKAGE $VERSION$EXTRAVERSION has been modified by :"
				for i in $(cat $PACKAGE/modifiers); do
					echo "  $i"
				done
			fi
			MSG="Files lost from $PACKAGE $VERSION$EXTRAVERSION :\n"
			while read file; do
				[ -e "$file" ] && continue
				if [ -L "$file" ]; then
					MSG="$MSG  target of symlink"
				fi
				echo -e "$MSG  $file"
				MSG=""
			done < $PACKAGE/files.list
			MSG="Missing dependencies for $PACKAGE $VERSION$EXTRAVERSION :\n"
			for i in $DEPENDS; do
				[ -d $i ] && continue
				echo -e "$MSG  $i"
				MSG=""
			done
			MSG="Dependencies loop between $PACKAGE and :\n"
			ALL_DEPS=""
			check_for_deps_loop $PACKAGE $DEPENDS
		done
		if [ "$PACKAGE_FILE" = "--full" ]; then
			for file in */md5sum; do
				[ -s "$file" ] || continue
				md5sum -c "$file" 2> /dev/null | grep -v OK$
			done
			FILES=" "
			for file in $(cat */files.list); do
				[ -d "$file" ] && continue
				case "$FILES" in *\ $file\ *) continue;; esac
				[ $(grep "^$file$" */files.list 2> /dev/null | \
					wc -l) -gt 1 ] || continue
				FILES="$FILES$file "
				echo "The following packages provide $file :"
				grep -l "^$file$" */files.list | while read f
				do
					pkg=${f%/files.list}
					echo -n "  $pkg"
					if [ -f $pkg/modifiers ]; then
						echo -n " (known as overridden by $(cat $pkg/modifiers))"
					fi
					echo ""
				done
			done
			MSG="No package has installed the following files:\n"
			find /etc /bin /sbin /lib /usr /var/www -not -type d | while read file; do
				case "$file" in *\[*) continue;; esac
				grep -q "^$file$" */files.list && continue
				echo -e "$MSG  $file"
				MSG=""
			done
		fi
		echo "Check completed."
		;;
	block)
		# Add a pkg name to the list of blocked packages.
		#
		check_root
		check_for_package_on_cmdline
		echo ""
		if grep -q "^$PACKAGE" $BLOCKED; then
			echo "$PACKAGE is already in the blocked packages list."
			echo ""
			exit 0
		else
			echo -n "Add $PACKAGE to : $BLOCKED..."
			echo $PACKAGE >> $BLOCKED
			status
		fi
		echo ""
		;;
	unblock)
		# Remove a pkg name to the list of blocked packages.
		#
		check_root
		check_for_package_on_cmdline
		echo ""
		if grep -q "^$PACKAGE" $BLOCKED; then
			echo -n "Removing $PACKAGE from : $BLOCKED..."
			sed -i s/$PACKAGE/''/ $BLOCKED
			sed -i '/^$/d' $BLOCKED
			status
		else
			echo "$PACKAGE is not in the blocked packages list."
			echo ""
			exit 0
		fi
		echo ""
		;;
	get)
		# Downlowd a package with wget.
		#
		check_for_package_on_cmdline
		check_for_packages_list
		check_for_package_in_list
		echo ""
		download $PACKAGE.tazpkg
		echo ""
		;;
	get-install)
		# Download and install a package.
		#
		check_root
		check_for_package_on_cmdline
		check_for_packages_list
		check_for_package_in_list
		DO_CHECK=""
		while [ -n "$3" ]; do
			case "$3" in
			--forced)
				DO_CHECK="no"
				;;
			--root=*)
				ROOT="${3#--root=}"
				;;
			--list=*)
				INSTALL_LIST="${3#--list=}"
				;;
			*)	shift 2
				echo -e "\nUnknown option $*.\n"
				exit 1
				;;
			esac
			shift
		done
		# Check if forced install.
		if [ "$DO_CHECK" = "no" ]; then
			rm -f $CACHE_DIR/$PACKAGE.tazpkg
		else
			check_for_installed_package $ROOT
		fi
		cd $CACHE_DIR
		if [ -f "$PACKAGE.tazpkg" ]; then
			echo "$PACKAGE already in the cache : $CACHE_DIR"
			# check package download was finished
			tail -c 2k $PACKAGE.tazpkg | grep -q 00000000TRAILER || {
				echo "Continue $PACKAGE download"
				download $PACKAGE.tazpkg
			}
		else
			echo ""
			download $PACKAGE.tazpkg
		fi
		PACKAGE_FILE=$CACHE_DIR/$PACKAGE.tazpkg
		install_package $ROOT
		;;
	clean-cache)
		# Remove all downloaded packages.
		#
		check_root
		files=`ls -1 $CACHE_DIR | wc -l`
		echo ""
		echo -e "\033[1mClean cache :\033[0m $CACHE_DIR"
		echo "================================================================================"
		echo -n "Cleaning cache directory..."
		rm -rf $CACHE_DIR/*
		status
		echo "================================================================================"
		echo "$files file(s) removed from cache."
		echo ""
		;;
	setup-mirror)
		# Change mirror URL.
		#
		check_root
		# Backup old list.
		if [ -f "$LOCALSTATE/mirror" ]; then
			cp -f $LOCALSTATE/mirror $LOCALSTATE/mirror.bak
		fi
		echo ""
		echo -e "\033[1mCurrent mirror(s)\033[0m"
		echo "================================================================================"
		echo "  `cat $MIRROR`"
		echo "
Please enter URL of the new mirror (http or ftp). You must specify the complet
address to the directory of the packages and packages.list file."
		echo ""
		echo -n "New mirror URL : "
		read NEW_MIRROR_URL
		if [ "$NEW_MIRROR_URL" = "" ]; then
			echo "Nothing as been change."
		else
			echo "Setting mirror(s) to : $NEW_MIRROR_URL"
			echo "$NEW_MIRROR_URL" > $LOCALSTATE/mirror
		fi
		echo ""
		;;
	reconfigure)
		# Replay post_install from receipt
		#
		check_for_package_on_cmdline
		check_root
		if [ -d "$INSTALLED/$PACKAGE" ]; then
			check_for_receipt
			# Check for post_install
			if grep -q ^post_install $INSTALLED/$PACKAGE/receipt; then
				. $INSTALLED/$PACKAGE/receipt
				post_install
			else 
				echo -e "\nNothing to do for $PACKAGE."
			fi
		else
			echo -e "\npackage $PACKAGE is not installed."
			echo -e "Install package with 'tazpkg install' or 'tazpkg get-install'\n"
		fi
		;;
	shell)
		# Tazpkg SHell
		#
		if test $(id -u) = 0 ; then
			PROMPT="\\033[1;33mtazpkg\\033[0;39m# "
		else
			PROMPT="\\033[1;33mtazpkg\\033[0;39m> "
		fi
		if [ ! "$2" = "--noheader" ]; then
			clear
			echo ""
			echo -e "\033[1mTazpkg SHell.\033[0m"
			echo "================================================================================"
			echo "Type 'usage' to list all avalaible commands and 'quit' or 'q' to exit."
			echo ""
		fi
		while true
		do
			echo -en "$PROMPT"; read cmd
			case $cmd in
				q|quit)
					break ;;
				shell)
					echo "You are already running a Tazpkg SHell." ;;
				su)
					su -c 'exec tazpkg shell --noheader' && break ;;
				"")
					continue ;;
				*)
					tazpkg $cmd ;;
			esac
		done
		;;
	usage|*)
		# Print a short help or give usage for an unknown or empty command.
		#
		usage
		;;
esac

exit 0
