# HG changeset patch # User Christopher Rogers # Date 1290655816 0 # Node ID 6d654d523ac88937ffbc629a476cdde976c66695 first release diff -r 000000000000 -r 6d654d523ac8 .hgignore --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/.hgignore Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,2 @@ +syntax: glob +working/** \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 config --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/config Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,2 @@ +MODULES="a.000.base a.001.justx a.002.core-basic a.003.mesa a.004.xorg-xf86-video a.005.firefox a.006.libs a.007.apps a.008.mercurial a.009.pentest" +COPY_HG="yes" \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 initramfs/init --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/initramfs/init Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,151 @@ +#!/bin/sh + +launch_init() +{ + echo -e "\\033[70G[ \\033[1;33mOK\\033[0;39m ]" + exec /sbin/switch_root mnt /sbin/init +} + +launch_init_modular() +{ + echo -e "\\033[70G[ \\033[1;33mOK\\033[0;39m ]" + exec /sbin/switch_root mnt /linuxrc +} + +failed() +{ + echo -e "\\033[70G[ \\033[1;31mFailed\\033[0;39m ]" +} + +try_init() +{ + if [ ! -d /mnt/etc ] && grep -q cryptoroot= /proc/cmdline; then + modprobe dm-mod + modprobe dm-crypt + modprobe aes-i586 + root="$(sed 's/.*cryptoroot=\([^ ]*\).*/\1/' < /proc/cmdline)" + dev=${root#/dev/} + dmlabel=crypto-$dev + if cryptsetup isLuks $root 2> /dev/null; then + cryptsetup luksOpen $root $dmlabel + else + read -s -t 60 -p "Pass phrase : " passphrase + key=$(echo $passphrase | hashalot -x -n 32 sha512) + blocks=$(cat $(find /sys/block | grep /$dev/size)) + echo 0 $blocks crypt aes-plain $key 0 $root 0 | \ + dmsetup create $dmlabel + fi + mount /dev/mapper/$dmlabel /mnt + fi + if [ -d /mnt/etc ]; then + umount /sys + [ -n "$1" ] && for i in $@ ; do + cp -a $i /mnt$(dirname $i) + done + umount /proc + launch_init + fi + failed +} + +mount_mapper() +{ + mount $root /mnt + try_init /dev/mapper $@ +} + +lvmsetup() +{ +if grep -q lvmroot= /proc/cmdline; then + modprobe dm-mod + vgscan --ignorelockingfailure + vgchange -ay --ignorelockingfailure + root="/dev/mapper/$(sed 's/.*lvmroot=\([^ ]*\).*/\1/' < /proc/cmdline)" + return 0 +fi +return 1 +} + +load_raid() +{ +while read line; do + case "$line" in + *raid10*) modprobe raid10 ;; + *raid0*) modprobe raid0 ;; + *raid1*) modprobe raid1 ;; + *raid[456]*) modprobe raid456 ;; + esac +done +} + +mount -t proc proc /proc +mount -t sysfs sysfs /sys +if grep -q dmraid= /proc/cmdline; then + root="$(sed 's/.*dmraid=\([^ ]*\).*/\1/' < /proc/cmdline)" + echo -n "Switching / to dmraid $root..." + dmraid -s | grep ^type | awk '{ print $3 }' | load_raid + case "$root" in + /dev/*);; + *) root=/dev/mapper/$(dmraid -s|grep ^name|awk '{print $3}')p${root#p};; + esac + dmraid -ay + lvmsetup + mount_mapper +fi +if grep -q softraid= /proc/cmdline; then + root="$(sed 's/.*softraid=\([^ ]*\).*/\1/' < /proc/cmdline)" + echo -n "Switching / to softraid $root..." + mdadm --examine --scan --config=partitions > /etc/mdadm.conf + grep level=raid /etc/mdadm.conf | load_raid + mdadm --assemble --scan + lvmsetup + mount_mapper /etc/mdadm.conf +fi +if lvmsetup; then + echo -n "Switching / to lvm $root..." + mount_mapper +fi +if grep -q loopfs= /proc/cmdline; then + loopfs="$(sed 's/.*loopfs=\([^ ]*\).*/\1/' < /proc/cmdline)" + dev=${loopfs%,*} + loopfs=${loopfs#*,} + echo -n "Switching / to loop $loopfs on $dev..." + if ! mount $dev /mnt; then + if echo $dev | grep -q "/dev/sd"; then + delay=`cat /sys/module/usb_storage/parameters/delay_use` + delay=$((1+$delay)) + echo -n "sleep for $delay seconds..." + sleep $delay + fi + mount $dev /mnt || loopfs="" + fi + if [ -n "$loopfs" ]; then + losetup /dev/loop0 /mnt/$loopfs + mount /dev/loop0 /mnt 2> /dev/null + fi + try_init +fi +grep -q cryptoroot= /proc/cmdline && try_init +umount /sys +echo -n "Switching / to tmpfs..." +size="$(grep rootfssize= < /proc/cmdline | \ + sed 's/.*rootfssize=\([0-9]*[kmg%]\).*/-o size=\1/')" +free=$(busybox free | busybox awk '/Mem:/ { print int(($4*100)/$3) }') +umount /proc +[ -n "$size" ] || size="-o size=90%" +if [ $free -lt 100 ] || ! mount -t tmpfs $size tmpfs /mnt; then + echo -e "\\033[70G[ \\033[1;33mSkipped\\033[0;39m]" + exec /sbin/init +fi +for i in $(ls -a /); do + case "$i" in + .|..) ;; + mnt) mkdir /mnt/mnt;; + *) if ! cp -a /$i /mnt 2> /dev/null; then + failed + umount /mnt + exec /sbin/init + fi;; + esac +done +launch_init_modular diff -r 000000000000 -r 6d654d523ac8 initramfs/liblinuxlive --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/initramfs/liblinuxlive Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,1128 @@ +#!/bin/bash + +# Functions library :: for Linux Live scripts 6 +# Author: Tomas M. +# + +# =========================================================== +# GLOBAL variables +# =========================================================== + +# linux live flag to fstab, if fstab line doesn't contain it, +# never remove it from fstab automatically (user added it) +FSTABLLFLAG="# AutoUpdate" + +# We have to set these variables very carefully +UNION=union +MEMORY=memory +MOUNTDIR=mnt +CHANGES=$MEMORY/changes +XINO=$MEMORY/xino +COPY2RAM=$MEMORY/copy2ram +IMAGES=$MEMORY/images +INITRAMDISK=$MOUNTDIR/live +LOOPMOUNT=$MOUNTDIR/tmp +FINDISOMNT=$MOUNTDIR/findiso + +# this will be replaced by build script, so never change the following line! +LIVECDNAME="slitaz" + +# ================================================================= +# debug and output functions +# ================================================================= + +# global variable +DEBUG_IS_ENABLED=$(cat /proc/cmdline 2>/dev/null | grep debug) + +debug_log() +{ + if [ "$DEBUG_IS_ENABLED" ]; then + echo "- debug: $*" >&2 + log "- debug: $*" + fi +} + +# echogreen will echo $@ in green color +# $1 = text +# +echogreen() +{ + echo -ne " ""$@""" +} + +# echolog +# $1 = text to show and to write to /var/log/messages +# +echolog() +{ + if [ "$1" != "" ]; then + echogreen "* " + log "LIVECD:" "$@" + echo "$@" + fi +} + +# log +# store given text in /var/log/livedbg +log() +{ + echo "$@" 2>/dev/null >>/var/log/livedbg +} + +# show information about the debug shell +show_debug_banner() +{ + echo + echo "=====" + echo ": Debugging started. Here is the root shell for you." + echo ": Type your desired commands or hit Ctrl+D to continue booting." + echo +} + +# debug_shell +# executed when debug boot parameter is present +# +debug_shell() +{ + if [ "$DEBUG_IS_ENABLED" ]; then + show_debug_banner + ash < /dev/console + echo + fi +} + +# header +# $1 = text to show +# +header() +{ + echo """$@""" +} + +fatal() +{ + echolog + header "Fatal error occured - $1" + echolog "Something went wrong and we can't continue. This should never happen." + echolog "Please reboot your computer with Ctrl+Alt+Delete ..." + echolog + ash < /dev/console +} + +allow_only_root() +{ + # test if the script is started by root user. If not, exit + if [ "0$UID" -ne 0 ]; then + echo "Only root can run $(basename $0)"; exit 1 + fi +} + +# =========================================================== +# text processing functions +# =========================================================== + +# look into cmdline and echo $1 back if $1 is set +# $1 = value name, case sensitive, for example 'debug' +# +cmdline_parameter() +{ + debug_log "cmdline_parameter" "$*" + log "searching for bootparam: $1" + egrep -o "(^|[[:space:]])$1([[:space:]]|\$)" /proc/cmdline | tr -d " " | tail -n 1 +} + +# look into cmdline and echo value of $1 option +# $1 = value name, case sensitive, for example 'changes' +# +cmdline_value() +{ + debug_log "cmdline_value" "$*" + log "searching for bootparam value: $1" + egrep -o "(^|[[:space:]])$1=[^[:space:]]+" /proc/cmdline | cut -d "=" -f 2- | tail -n 1 +} + +# Make sure the part of a script after 'mutex_lock' call is atomic, +# that means the 'locked' part of the script can never be execuetd +# from several processes at the same time, in parallel. +# Every script waits until it gathers the lock. +# The lock directory is saved in /dev instead of /tmp, because /tmp may be +# readonly at the time when the lock is needed (eg. when udev is starting) +# $1 = name of the lock +# +mutex_lock() +{ + debug_log "mutex_lock" "$*" + while ! mkdir "/dev/ll-mutex-lock-$1" 2>/dev/null; do + usleep 100000; + done +} + +# Unlock the lock so another waiting process can reusse it and continue +# $1 = name of the lock +# +mutex_unlock() +{ + debug_log "mutex_unlock" "$*" + rmdir "/dev/ll-mutex-lock-$1" 2>/dev/null +} + +# =========================================================== +# system functions +# =========================================================== + +# setup /usr from /usr.lzm inside initrd +mount_initrd_loops() +{ + debug_log "mount_initrd_loops" "$*" + if [ -e /usr.lzm ]; then + mount_device /usr.lzm /usr loop,ro squashfs + fi + if [ -e /drivers.lzm ]; then + mount_device /drivers.lzm /lib/modules/*/kernel/drivers loop,ro squashfs + fi +} + +# modprobe module $1, including all dependencies, suppress all messages +# This was own function, because modprobe in busybox didn't support +# neither gzipped modules nor dependencies. Seems to be fixed now, though. +# $1 = module name, eg. ehci-hcd +# $* = optional arguments +# +modprobe_module() +{ + debug_log "modprobe_module" "$*" + local MODULE + + MODULE="$1" + shift + + if [ ! "$MODULE" ]; then return 1; fi + modprobe "$MODULE" $* 2>/dev/null +} + +cdname() +{ + if [ "$(cmdline_value cdname)" != "" ]; then + LIVECDNAME="$(cmdline_value cdname)" + else + LIVECDNAME="${LIVECDNAME}" + fi +} + +cdname + +# mknod next loop device +# - find biggest loop device in /dev/loop/, assume it to be used +# - preallocate (mknod) 20 more loop devices in one round +mknod_next_loop_dev() +{ + debug_log "mknod_next_loop_dev" "$*" + local i NR END PFX + + mutex_lock mknod_next_loop_dev + + if [ -d /dev/loop ]; then + NR=$(find /dev/loop/ -maxdepth 1 | sed -r 's/[^0-9]+//' | sort -n | tail -n 1) + PFX="/" + else + NR=$(find /dev/ -maxdepth 1 | grep loop | sed -r 's/[^0-9]+//' | sort -n | tail -n 1) + PFX="" + fi + NR=$(expr 0$NR + 1) + END=$(expr 0$NR + 20) + for i in $(seq $NR $END); do + mknod /dev/loop$PFX$i b 7 $i 2>/dev/null + done + echo /dev/loop$PFX$NR + + mutex_unlock mknod_next_loop_dev +} + +# =========================================================== +# Filesystem functions +# =========================================================== + +# Find out what locale is requested +# If no locale is given, use the firts one available (if any) +# $1 = locale (optional argument, if exists, no autodetection is made) +locale_id() +{ + debug_log "locale_id" "$*" + local LOCALE i + + # first try to find out locale from boot parameters + LOCALE="$1" + if [ "$LOCALE" = "" ]; then LOCALE=$(cmdline_value locale); fi + if [ "$LOCALE" = "" ]; then LOCALE=$(cmdline_value language); fi + if [ "$LOCALE" = "" ]; then LOCALE=$(cmdline_value lang); fi + + # if not found, set it to locale from usr/lib/locale, + # but only if there is just ONE directory, nothing more + # (so we are sure which one to use) + if [ "$LOCALE" = "" ]; then + for LOCALE in $(ls -A1p /usr/lib/locale 2>/dev/null | grep / | sed -r "s:[/]|[.].*::"); do + i="1$i" + done + if [ "$i" != "1" ]; then LOCALE=""; fi + fi + + if [ "$LOCALE" != "" -a -e /usr/share ]; then + cat /usr/share/locale/locale.alias | sed -r "s/#.*//" | egrep "$LOCALE|$LOCALE""_" | tail -n 1 | tr -s "[[:space:]]" " " | cut -d " " -f 2- | tr -d " " + fi +} + +# Find out what iocharset to use +iocharset() +{ + debug_log "iocharset" "$*" + local CHARSET IOCHARSET + + # if iocharset is explicitly set at the boot prompt, + # return it regardless the locale settings + IOCHARSET=$(cmdline_value iocharset) + if [ "$IOCHARSET" != "" ]; then + echo $IOCHARSET + return 0; + fi + + # else find out the iocharset from locale_id output, it should match + # some kernel module (after stripping out few of the dashes) + IOCHARSET=$(locale_id | cut -d . -f 2- | tr "[[:upper:]]" "[[:lower:]]" | tr -d -) + if [ "$IOCHARSET" = "" ]; then return 0; fi + + find /lib/modules -name "nls_*" | sed -r 's:^.*/|[.]ko$::g' | cut -b 5- | while read CHARSET; do + if [ "$(echo $CHARSET | tr "[[:upper:]]" "[[:lower:]]" | tr -d -)" = "$IOCHARSET" ]; then + echo "$CHARSET" + return 0 + fi + done + return 1 +} + +# Get filesystem options +# $1 = filesystem +# $2 = 'fstab' or 'mount' ... 'auto'/'noauto' string is enabled (fstab) or disabled (mount) +# + +fs_options() +{ + debug_log "fs_options" "$*" + local NOAUTO IOCHARSET + + NOAUTO=$(cmdline_parameter noauto) + if [ "$NOAUTO" = "" ]; then NOAUTO="auto"; fi + if [ "$2" = "fstab" ]; then echo -n "$NOAUTO," ; fi + if [ "$1" = "swap" ]; then echo "defaults,pri=1"; return 0; fi + echo -n "noatime,users,suid,dev,exec" + + IOCHARSET=$(iocharset) + + if [ "$1" = "vfat" ]; then + echo -n ",quiet,umask=0,check=s,shortname=mixed" + if [ "$IOCHARSET" ]; then + echo ",iocharset=$IOCHARSET" + fi + fi + + if [ "$1" = "iso9660" -o "$1" = "iso9660,udf" ]; then + echo -n ",ro" + if [ "$IOCHARSET" ]; then + echo ",iocharset=$IOCHARSET" + fi + fi + + if [ "$1" = "ntfs" ]; then + echo -n ",ro" + if [ "$IOCHARSET" ]; then + echo ",nls=$IOCHARSET" + fi + fi + + if [ "$1" = "ntfs-3g" ]; then + echo ",locale=$(locale_id)" + fi + + if [ "$1" = "ext3" -o "$1" = "ext4" ]; then + echo ",barrier=1,data=ordered" + fi + +} + +# discover filesystem used on the given device +# Use vfat for msdos filesystem. Use ntfs-3g for ntfs if ntfs-3g exists. +# $1 = device, eg. /dev/hda1 +# +device_filesystem() +{ + debug_log "device_filesystem" "$*" + local NTFS + + if [ -e /bin/ntfs-3g ]; then NTFS="ntfs-3g"; else NTFS="ntfs"; fi + blkid -s TYPE "$1" -o value | sed "s/msdos/vfat/" | sed "s/ntfs/$NTFS/" +} + +# tell us if the given filesystem is supported +# (eg. it's in /proc/filesystems or we know it) +# $1 = filesystem name +# +is_supported_filesystem() +{ + debug_log "is_supported_filesystem" "$*" + + if [ -e /bin/ntfs-3g -a "$1" = "ntfs-3g" ]; then + return 0 + fi + + # the following command will set the return value + egrep -q "[[:space:]]$1\$" /proc/filesystems +} + +# Mount device $1 to $2 +# If the device is using vfat or ntfs filesystem, use iocharset as a mount option +# $1 = /dev device to mount, eg. /dev/hda1, or loop file, or directory +# $2 = mountpoint, eg. /mnt/hda1 +# $3 = optional mount options, for example "ro", or "remount,rw" +# $4 = optional filesystem name, in order to skip autodetection +# +mount_device() +{ + debug_log "mount_device" "$*" + local FS DEV LOOPDEV OPTIONS FILESYSTEM ERR + + # make sure we have enough arguments + if [ "$2" = "" ]; then return 1; fi + if [ "$1" = "" ]; then rmdir "$2" 2>/dev/null; return 1; fi + mkdir -p "$2" + + DEV="$1" + if [ "$4" != "" ]; then FS="$4"; else FS=$(device_filesystem "$1"); fi + if [ "$FS" ]; then OPTIONS=$(fs_options $FS mount); FS="-t $FS"; fi + if [ "$OPTIONS" ]; then OPTIONS="$OPTIONS"; else OPTIONS=""; fi + if [ -f "$DEV" ]; then OPTIONS="$OPTIONS,loop"; fi + if [ -d "$DEV" ]; then OPTIONS="$OPTIONS,rbind"; fi + if [ "$3" ]; then OPTIONS="$OPTIONS,$3"; fi + OPTIONS=$(echo "$OPTIONS" | sed -r "s/^,+//") + + if [ "$FS" = "-t ntfs-3g" ]; then + ntfs-3g "$DEV" "$2" -o $OPTIONS >/dev/null 2>&1 + ERR=$? + else + mount -n -o $OPTIONS $FS "$DEV" "$2" >/dev/null 2>&1 + ERR=$? + fi + + # not enough loop devices? try to create one. + if [ $ERR -eq 2 ]; then + LOOPDEV=$(mknod_next_loop_dev) + OPTIONS=$(echo "$OPTIONS" | sed -r "s/,loop//g") + losetup "$LOOPDEV" "$DEV" 2>/dev/null # busybox's losetup doesn't support -r + if [ $? -ne 0 ]; then + losetup -r "$LOOPDEV" "$DEV" 2>/dev/null # force read-only in case of error + fi + mount -n -o $OPTIONS $FS "$LOOPDEV" "$2" >/dev/null 2>&1 + ERR=$? + fi + + # if nothing works, try to force read-only mount + if [ $ERR -ne 0 ]; then + mount -n -r -o $OPTIONS $FS "$DEV" "$2" >/dev/null 2>&1 + ERR=$? + fi + + if [ $ERR -ne 0 ]; then rmdir $2 2>/dev/null; fi + return $ERR +} + +# unmount all parameters. If the parameter is not mountpoint but +# it's a file or directory, umount the device where the file/dir is stored. +# +# First try normal umount, if that fails then remount read-only +# If -l parameter is specified, do lazy-umount when normal umount fails +# $1..$n = files/directories/devices to be unmounted +# +fumount() +{ + debug_log "fumount" "$*" + local TARGET LAZY + + while [ "$1" ]; do + if [ "$1" = "-l" ]; then LAZY="yes"; shift; fi + TARGET=$(readlink -f "$1") + if ! ismountpoint "$TARGET"; then + if [ -f "$TARGET" -o -d "$TARGET" ]; then + TARGET=$(df "$TARGET" | tail -n 1 | tr -s " " | cut -d " " -f 6) + fi + fi + + if [ "$TARGET" != "" ]; then + umount -n "$TARGET" >/dev/null 2>&1 + if [ $? -ne 0 ]; then + mount -n -o remount,ro -t ignored ignored "$TARGET" >/dev/null 2>&1 + if [ "$LAZY" ]; then umount -n -l "$TARGET" >/dev/null 2>&1; fi + fi + fi + shift + done +} + +# =========================================================== +# live module functions +# =========================================================== + +# Create module +# call mksquashfs with apropriate arguments +# $1 = directory which will be compressed to squashfs module +# $2 = output filesystem module file +# $3..$9 = optional arguments like -keep-as-directory or -b 123456789 +# +create_module() +{ + debug_log "create_module" "$*" + rm -f "$2" # overwrite, never append to existing file + mksquashfs "$1" "$2" -b 256K $3 $4 $5 $6 $7 $8 $9>/dev/null + if [ $? -ne 0 ]; then return 1; fi + chmod a-wx "$2" # remove execute and write attrib + chmod a+r "$2" # add read for everyone +} + +# ismountpoint exits with 0 if $1 is mountpoint, else exits with 1 +# $1 = directory or loop_file +# +ismountpoint() +{ + debug_log "ismountpoint" "$*" + local MDIR + + MDIR=$(readlink -f "$1") + cat /proc/mounts | cut -d " " -f 2 | egrep "^$MDIR\$" >/dev/null 2>&1 +} + +# Mount filesystem module to destination directory +# $1 = path to the compressed module +# $2 = destination folder +# +mount_module() +{ + debug_log "mount_module" "$*" + mount_device "$1" "$2" loop,ro squashfs +} + +# Insert a directory tree $2 to an union specified by $1 +# Top-level read-write branch is specified by it's index 0 +# Using =rr enables aufs to optimize real readonly branches +# $1 = union absolute path (starting with /) +# $2 = path to data directory +# +union_insert_dir() +{ + debug_log "union_insert_dir" "$*" + mount -n -o remount,add:1:$2=rr aufs $1 +} + +# Find LZM modules in given dir +# $1 = root directory of mounted DATAdir +# +find_modules() +{ + debug_log "find_modules" "$*" + if [ "$(cmdline_parameter baseonly)" ]; then + find "$1/base" "$1/optional" -name "*.sqfs" 2>/dev/null | sort + find "$1/base" "$1/optional" -name "*.lzm" 2>/dev/null | sort + else + find "$1/base" "$1/modules" "$1/optional" "$1/tmp" -name "*.sqfs" 2>/dev/null | sort + find "$1/base" "$1/modules" "$1/optional" "$1/tmp" -name "*.lzm" 2>/dev/null | sort + fi +} + +# List all modules in all directories (base, modules, optional) +# and filter out unneeded optional modules (not specified by load= kernel parameter) +# separator for load and noload arguments is "," or ";" +# $1 = root directory of mounted DATAdir +# +list_modules() +{ + debug_log "list_modules" "$*" + local LOAD NOLOAD + + LOAD=$(cmdline_value load | sed -r 's/\*/.\*/g' | sed -r 's/,|;/|/g') + NOLOAD=$(cmdline_value noload | sed -r 's/\*/.\*/g' | sed -r 's/,|;/|/g') + find_modules "$1" | while read LINE; do + MODNAME=$(echo $LINE | cut -b ${#1}- | cut -b 2-) + if [ "$(echo $LINE | grep /optional/)" ]; then + if [ ! "$LOAD" -o ! "$(echo $MODNAME | egrep -i "$LOAD")" ]; then continue; fi + fi + if [ "$NOLOAD" -a "$(echo $MODNAME | egrep -i "$NOLOAD")" ]; then continue; fi + echo $LINE + done +} + +# Insert one single filesystem module to the union +# $1 = union absolute path +# $2 = module full path +# $3 = destination folder, where images will be mounted to +# $4 = preffix length strip (number of characters) +# +union_insert_module() +{ + debug_log "union_insert_module" "$*" + local TARGET + + TARGET="$3/$(basename $2)" + if ismountpoint $TARGET; then return 1; fi # skip already used modules + mkdir -p $TARGET + mount_module $2 $TARGET + if [ $? -ne 0 ]; then echo "Cannot read module data. corrupted download?" >&2; return 1; fi + union_insert_dir $1 $TARGET + if [ $? -ne 0 ]; then echo "can't insert module to union" >&2; return 2; fi + echo "$2" | cut -b $(($4+1))- + echolog "$2" >/dev/null + return 0 +} + +# Insert all filesystem modules from $2 directory and subdirectories, to the union +# $1 = union absolute path (starting with /) +# $2 = LiveCD data dir (with directories /base, /modules, etc.) +# $3 = destination folder, where images will be mounted to +# +union_insert_modules() +{ + debug_log "union_insert_modules" "$*" + local INSERTED + + list_modules $2 | while read MODULE; do + INSERTED=$(union_insert_module $1 $MODULE $3 ${#2}) + if [ "$INSERTED" != "" ]; then echolog " -> $(echo $INSERTED | sed -r s:^/::)"; fi + done +} + +# Copy LiveCD modules to RAM directory +# will copy only /boot, and module files from $1 +# $1 = data directory +# $2 = target directory in RAM +# +copy_to_ram() +{ + debug_log "copy_to_ram" "$*" + cp -a "$1/rootcopy" "$2" 2>/dev/null # could be empty + list_modules "$1" | while read MODULE; do + TARGET=$(dirname "$MODULE" | cut -b ${#1}- | cut -b 2-) + mkdir -p "$2/$TARGET" + cp "$MODULE" "$2/$TARGET" + if [ $? -ne 0 ]; then fatal "Not enough memory. Using ramsize=$RAMSIZE"; fi + done +} + +# =========================================================== +# discovery functions +# =========================================================== + +# List all supported network drivers +# +list_network_drivers() +{ + debug_log "list_network_drivers" "$*" + + # these drivers are probed in Slackware's initrd + # (see initrd.img/scripts/network.sh). + # I don't have personal experiences with most of these drivers + # so I'll be happy if you report any particular one to be not working + # (eg. causing hangups) in order to remove it from this list. + + echo 3c59x acenic atl1 de4x5 dgrs eepro100 e1000 epic100 hp100 ne2k-pci \ + olympic pcnet32 r8169 rcpci 8139too 8139cp sktr skge sky2 tulip via-rhine \ + yellowfin tg3 dl2k ns83820 depca ibmtr 3c501 3c503 3c505 3c507 3c509 3c515 \ + ac3200 acenic at1700 cosa cs89x0 de4x5 de600 de620 e2100 eepro eexpress \ + es3210 eth16i ewrk3 fmv18x forcedeth hostess_sv11 hp-plus hp lne390 ne3210 \ + ni5010 ni52 ni65 sb1000 sealevel smc-ultra sis900 smc-ultra32 smc9194 wd \ + | tr " " "\n" +} + +# List all CD-ROMs +# by using /proc entries +# +list_cdrom_devices() +{ + debug_log "list_cdrom_devices" "$*" + local CDDEVICE + + for CDDEVICE in $(cat /proc/sys/dev/cdrom/info 2>/dev/null | head -n 3 | tail -n 1 | cut -d ":" -f 2); do + echo "/dev/$CDDEVICE" + done +} + +# List all mounted directories +# +list_mounted_directories() +{ + debug_log "list_mounted_directories" "$*" + if [ "$MOUNTDIR" ]; then + ls -1 $MOUNTDIR | while read DIR; do + if ismountpoint $MOUNTDIR/$DIR; then echo $DIR; fi + done + fi +} + +# List all devices with filesystems +# Return empty result when nohd parameter was given. +# +list_partition_devices() +{ + debug_log "list_partition_devices" "$*" + if [ "$(cmdline_parameter nohd)" != "" ]; then return 1; fi + cat /proc/partitions | grep -v loop | grep -v major | grep -v '^$' | sed -r "s:^[0-9 ]+:/dev/:" + if [ -e /dev/mapper/control ]; then # list LVM partitions if available + ls -1 /dev/mapper/ | grep -v "^control\$" | sed -r "s:^:/dev/mapper/:" + fi +} + +# List all disk devices +# +list_disk_devices() +{ + debug_log "list_disk_devices" "$*" + list_partition_devices | egrep -v "[0-9]" +} + +# List all partitions marked as Linux Swap +# +list_swap_devices() +{ + debug_log "list_swap_devices" "$*" + if [ "$(cmdline_parameter nohd)" != "" -o "$(cmdline_parameter noswap)" != "" ]; then return 1; fi + blkid -t TYPE="swap" -o device +} + +# List all block devices +# +list_block_devices() +{ + debug_log "list_block_devices" "$*" + if [ "$(cmdline_parameter nocd)" = "" ]; then + list_cdrom_devices + fi + list_partition_devices +} + +# Format mountdir for device. This function used to append _cdrom or _removable +# suffix to the directory name so KDE was able to assign a nice icon for evey +# device, but this should be done using HAL in KDE nowadays, so we do not +# support these stupid suffixes anymore. Many people will be happy :) +# $1 = device full path, eg. /dev/hda1 +# +device_mountdir() +{ + debug_log "device_mountdir" "$*" + echo "/$MOUNTDIR/$(basename "$1")" | tr -s / +} + +# Find file-path on given device +# First it mounts the device read-only. If then the 'path' is found, +# then remount without RO flag (causes it to be mounted read-write if possible) +# and return the path, else unmount and exit. +# If the device/dev_directory is already mounted, preserve it mounted +# $1 = device +# $2 = path/filename +# +find_filepath() +{ + debug_log "find_filepath" "$*" + local DIR FOUND PRESERVE + + DIR=$(device_mountdir $1) + ismountpoint $DIR + if [ $? -eq 0 ]; then + PRESERVE="true" + else + mount_device $1 $DIR ro + if [ $? -ne 0 ]; then rmdir $DIR 2>/dev/null; return 1; fi + PRESERVE="" + fi + + FOUND=$(ls -A1d $DIR/$2 2>/dev/null | head -n 1 | tr -s '/') + + if [ "$FOUND" = "" ]; then + if [ "$PRESERVE" != "true" ]; then + fumount $DIR + rmdir $DIR 2>/dev/null + fi + return 1 + else + # remount without the 'ro' option now, so use rw or defaults + # Only in the case it was not mounted already before. + if [ "$PRESERVE" != "true" ]; then + fumount $DIR + mount_device $1 $DIR + if [ $? -ne 0 ]; then + rmdir $DIR 2>/dev/null + return 2 + fi + fi + echo "$FOUND" + return 0 + fi +} + +# Find file in computer by mounting disks or other storage devices +# and searching for $1 in the mounted directory +# $1 = filename or device-path or devicepath/filename +# +find_file() +{ + debug_log "find_file" "$*" + local FIND DEVICE DEVPART PATHPART + + # allow using /mnt/... as well as /dev/... + FIND=$(echo "$1" | sed -r "s:^/mnt/:/dev/:") + + # if parameter is just a device, echo it and exit + if [ -b "$FIND" -o -c "$FIND" -o "$FIND" = "" ]; then echo "$FIND"; return; fi + + # If path doesn't start with /dev/, try to find the exact path on all devices + # First, split DEV/PATH parts + DEVPART=$(echo "$FIND" | egrep -o "^/dev/[^/]+") + + if [ "$DEVPART" = "" ]; then + # no device is specified. Search all devices for filename $FIND + PATHPART="$FIND"; + for DEVICE in $(list_mounted_directories) $(list_block_devices); do + if ! grep -q ":$DEVICE@$PATHPART:" /tmp/_findfile 2>/dev/null; then + find_filepath "$DEVICE" "$PATHPART" + if [ $? -eq 0 ]; then return 0; fi + echo ":$DEVICE@$PATHPART:" >>/tmp/_findfile + fi + done + else + # try to find PATHPART only on the given device + PATHPART=$(echo "$FIND" | sed -r 's:^/dev/[^/]+(.*):\1:') + find_filepath $DEVPART $PATHPART + fi +} + +# Find In Computer +# use 'find_file' function to find the given file/dir +# if nothing found, sleep for a while to allow devices to settle and try again. +# (is there any way to find out if there are devices queued through /sys?) +# $1 = file or directory to find +# +find_in_computer() +{ + debug_log "find_in_computer" "$*" + local TIMEOUT RESULT + + TIMEOUT=$(cmdline_value scantimeout | sed -r 's/[^0-9]*([0-9]+).*/\1/') + if [ "$TIMEOUT" = "" ]; then TIMEOUT=10; fi + + RESULT=$(find_file "$1") + + while [ $TIMEOUT -gt 0 -a "$RESULT" = "" ]; do + echo -ne "- wait a while\r" >&2 + sleep 1 + TIMEOUT=$((TIMEOUT-1)) + RESULT=$(find_file "$1") + done + + echo $RESULT +} + +# Find and run all scripts from the given module +# This function is used by the activate and deactivate script when the distro +# is already started, not during live setup +# $1 = mounted module full path +# $2..$n = optional arguments for the scripts, eg. 'start' +# +find_n_run_scripts() +{ + debug_log "find_n_run_scripts" "$*" + local MOD + + MOD="$1" + shift + + if [ -d $MOD/etc/rc.d -o -d $MOD/etc/rc.d/init.d -o -d $MOD/etc/init.d ]; then + ( find $MOD/etc/rc.d -type f -maxdepth 1 2>/dev/null ; \ + find $MOD/etc/init.d -type f -maxdepth 1 2>/dev/null ; \ + find $MOD/etc/rc.d/init.d -type f -maxdepth 1 2>/dev/null \ + ) | cut -b ${#MOD}- | cut -b 2- | xargs -n 1 -r readlink -f | sort -u | while read SCRIPT; do + if [ "$SCRIPT" != "" -a -x "$SCRIPT" -a ! -d "$SCRIPT" ]; then + # call the script by real path, not from the module + log "starting '$SCRIPT $@'" + ${SCRIPT} "$@" + fi + done + fi +} + +# =========================================================== +# hardware preparation functions +# =========================================================== + +# Create block devices to /dev described by /sys entries +# +mdev_start_hotplug() +{ + debug_log "mdev_start_hotplug" "$*" + echolog "Creating /dev entries for block devices" + mdev -s + #rm /dev/pty??* /dev/tty??* # remove unneeded pty and tty devices + echo /bin/mdev > /proc/sys/kernel/hotplug # use mdev as a hotplug handler +} + +# Modprobe kernel modules needed for the LiveCD +# +modprobe_essential_modules() +{ + debug_log "modprobe_essential_modules" "$*" + + echolog "Loading filesystems modules ..." + modprobe_module loop + modprobe_module isofs + #modprobe_module sqlzma + modprobe_module squashfs + #modprobe_module unlzma + modprobe_module aufs brs=1 + modprobe_module ext2 + modprobe_module ext3 + modprobe_module ext4 + modprobe_module btrfs + modprobe_module reiserfs + modprobe_module xfs + modprobe_module vfat + modprobe_module fuse # for ntfs-3g + modprobe_module ntfs # for ro driver +} + +# Modprobe kernel modules needed for USB masstorage devices +# +modprobe_usb_modules() +{ + debug_log "modprobe_usb_modules" "$*" + local LSPCI + + # skip module loading if nohotplug bootparam is present + if [ "$(cmdline_parameter nohotplug)" ]; then return 0; fi + + LSPCI=$(lspci -v | grep -i prog-if) + if [ "$(echo $LSPCI | egrep -i [eou]hci)" = "" ]; then + return 0 + fi + + echolog "Loading USB modules ..." + if [ "$(echo $LSPCI | grep -i ehci)" != "" ]; then + modprobe_module ehci-hcd + fi + if [ "$(echo $LSPCI | grep -i ohci)" != "" ]; then + modprobe_module ohci-hcd + fi + if [ "$(echo $LSPCI | grep -i uhci)" != "" ]; then + modprobe_module uhci-hcd + fi + modprobe_module usb-storage +} + +# Load drivers for PCMCIA CardBus devices +# +modprobe_pcmcia_modules() +{ + debug_log "modprobe_pcmcia_modules" "$*" + + # skip module loading if nohotplug bootparam is present + if [ "$(cmdline_parameter nohotplug)" ]; then return 0; fi + + echolog "Loading PCMCIA CardBus modules ..." + modprobe_module pcmcia_core + modprobe_module pcmcia + modprobe_module rsrc_nonstatic + modprobe_module yenta_socket +} + +# Load network drivers unless eth[0-9] is found +# +modprobe_network_modules() +{ + debug_log "modprobe_network_modules" "$*" + local ETH + + # skip module loading if nohotplug bootparam is present + if [ "$(cmdline_parameter nohotplug)" ]; then return 0; fi + + # probe all drivers. Start by the ones mentioned in pcimodules' output + for module in $(list_network_drivers | egrep "$(pcimodules | tr "\n" "|")!") $(list_network_drivers); do + modprobe_module $module + ETH=$(cat /proc/net/dev | grep : | grep -v lo: | cut -d : -f 1 | tr -d " ") + if [ "$ETH" != "" ]; then + echo $ETH + return 0 + fi + rmmod $module 2>/dev/null + done +} + +# Start udhcpc to get IP address from DHCP server +# $1 = interface to use (optional) +# +init_dhcp() +{ + debug_log "start_dhcp_client" "$*" + + if [ "$1" != "" ]; then + ifconfig $1 up + udhcpc -i $1 -q + else + ifconfig eth0 up + udhcpc -q + fi +} + +# Mount http filesystem from the given server +# $1 = server +# $2 = mountdir +# +mount_httpfs() +{ + debug_log "mount_httpfs" "$*" + + mkdir -p $2 + httpfs $1 $2 +} + + +# Unload modules loaded to kernel which are not used +# This function used to unload more modules, but it may cause +# problems to auto-remove some of them (eg. a network module +# can seem unneeded even if network is to be used very soon. +# +rmmod_unused_modules() +{ + debug_log "rmmod_unused_modules" "$*" + rmmod usb-storage uhci-hcd ohci-hcd ehci-hcd 2>/dev/null + rmmod yenta_socket rsrc_nonstatic pcmcia pcmcia_core 2>/dev/null +} + +# kill all unneeded processes, which have bigger PID then the PID of +# current shell. We can't use killall5, as it would kill some processes +# which may be currently needed, for example ntfs-3g. +# $1 = maximum pid (kill all lower) +# +killall_unneeded() +{ + debug_log "killall_unneeded" "$*" + local LIST PID + + PID=$1 + for pid in $(ps | grep -v "PID" | egrep -v "\[.*\]" | fgrep -v mount | fgrep -v posixovl | fgrep -v ntfs | sed -r "s/^[[:space:]]*([0-9]+).*/\\1/"); do + if [ $pid -lt $PID ]; then + LIST="$LIST $pid" + fi + done + + kill -SIGTERM $LIST 2>/dev/null # SIGTERM + sleep 2 + kill -SIGKILL $LIST 2>/dev/null # SIGKILL +} + +# enable/disable CD autoejecting when unmounted +# $1 = 1|0 ... enable|disable +# +cd_autoeject() +{ + debug_log "cd_autoeject" "$*" + echo $1 >/proc/sys/dev/cdrom/autoeject +} + +# =========================================================== +# FSTAB functions +# =========================================================== + +# $1 = fstab file +# $2 = device name +dev_is_in_fstab() +{ + debug_log "dev_is_in_fstab" "$*" + cat "$1" | sed -r "s/#.*//" | egrep -q "^[[:space:]]*$2[[:space:]]" +} + +# update given line in fstab, add new values only if the device is not found +# $1 = fstab file to parse +# $2 = device name +# $3 = mountpoint +# $4 = filesystem +# $5 = mount options +# +fstab_add_line() +{ + debug_log "fstab_add_line" "$*" + local DIR + + if [ "$4" != "swap" ]; then DIR="$3"; else DIR="none"; fi + if ! dev_is_in_fstab "$1" "$2"; then + echo "$2" "$DIR" "$4" "$5" 0 0 "$FSTABLLFLAG" >>$1 + fi +} + +# create correct fstab file in $1/etc/fstab and create apropriate +# mount directories in $1/mnt. This function is only calld once, +# during liveCD startup (even before init from the distro is started). +# $1 = root directory (union) +# +fstab_update() +{ + debug_log "fstab_update" "$*" + local FSTAB FSTABTMP + + FSTAB="$1/etc/fstab" + FSTABTMP=$FSTAB$$ + mkdir -p $1/etc $1/mnt + cat $FSTAB 2>/dev/null | grep -v "$FSTABLLFLAG" >$FSTABTMP + + fstab_add_line $FSTABTMP none / unionfs defaults + fstab_add_line $FSTABTMP none /proc proc defaults + fstab_add_line $FSTABTMP none /sys sysfs defaults + fstab_add_line $FSTABTMP none /dev/pts devpts gid=5,mode=620 + fstab_add_line $FSTABTMP tmpfs /dev/shm tmpfs defaults + + list_cdrom_devices | while read DEVICE; do + MNT=$(device_mountdir $DEVICE) + FS=$(device_filesystem $DEVICE) + if [ "$FS" = "" ]; then FS=iso9660,udf; fi + mkdir -p "$1/$MNT" + fstab_add_line $FSTABTMP $DEVICE $MNT $FS $(fs_options $FS fstab) + done + list_partition_devices | while read DEVICE; do + MNT=$(device_mountdir $DEVICE) + FS=$(device_filesystem $DEVICE) + OPT=$(fs_options $FS fstab) + + if [ "$FS" = "swap" ]; then + fstab_add_line $FSTABTMP $DEVICE $MNT $FS $OPT + fi + + # If the partition has a valid filesystem, add it to fstab + if is_supported_filesystem "$FS"; then + fstab_add_line $FSTABTMP $DEVICE $MNT $FS $OPT + mkdir -p "$1/$MNT" + fi + done + + mv -f $FSTABTMP $FSTAB +} + +# create correct fstab file in $1/etc/fstab only with aufs,proc,sysfs and devpts +# No partition will be mounted and mount point created +# HAL is going to manage mount points and medias +fstab_clean() +{ + debug_log "fstab_update" "$*" + local FSTAB FSTABTMP + + FSTAB="$1/etc/fstab" + FSTABTMP=$FSTAB$$ + mkdir -p $1/etc $1/mnt + cat $FSTAB 2>/dev/null | grep -v "$FSTABLLFLAG" >$FSTABTMP + + fstab_add_line $FSTABTMP aufs / aufs defaults + fstab_add_line $FSTABTMP proc /proc proc defaults + fstab_add_line $FSTABTMP sysfs /sys sysfs defaults + fstab_add_line $FSTABTMP devpts /dev/pts devpts gid=5,mode=620 + fstab_add_line $FSTABTMP tmpfs /dev/shm tmpfs defaults + mv -f $FSTABTMP $FSTAB +} diff -r 000000000000 -r 6d654d523ac8 initramfs/linuxrc --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/initramfs/linuxrc Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,351 @@ +#!/bin/ash +# Initial script for Linux Live operating system +# Author: Tomas M + +export PATH=.:/:/usr/sbin:/usr/bin:/sbin:/bin + +mount -n -t proc proc /proc +mount -n -t sysfs sysfs /sys +#mount -n -o remount,rw / # for the case we forgot rw boot option +ln -sf /proc/mounts /etc/mtab # this allows us to use umount -a + +. /liblinuxlive # it requires proc to be mounted + +# Don't print kernel messages to konsole now. +# Syslog will reset printk settings, no need to remember it here anymore. +echo "0" >/proc/sys/kernel/printk + +# Load essential drivers, like CDROM drivers, aufs/squashfs etc, +# use mdev to create /dev/ devices and setup it as a hotplug-handler +modprobe_essential_modules + +# /usr and some drivers are compressed in initrd +# so it must be mounted from .lzm files +#mount_initrd_loops + +# start hotplugging before hw drivers load +#mdev_start_hotplug + +# Then load drivers for data storage and input devices +modprobe_usb_modules +modprobe_pcmcia_modules + +debug_shell + +# make sure ext3 partitions are not mounted using ext2 driver, +# and vfat partitions are not mounted using msdos driver +echo -e "ext4\next3\next2\nvfat\n*" >/etc/filesystems + +mkdir -p $UNION +mkdir -p $MEMORY + +debug_shell + +# Find livecd data directory by searching for livecd.sgn file +SGN=$(cmdline_value sgnfile) +if [ "$SGN" = "" ]; then SGN=livecd.sgn; fi +echolog "looking for '$LIVECDNAME' data directory (searching for $SGN file)" + +# First, try from= boot argument, if given +DATAFROM=$(cmdline_value from) + +# Boot directly from iso +FINDISOVAR=$(cmdline_value findiso) + +# If ip= parameter is present, assume we're booted over PXE +# In that case, we have to initialize network very soon (now) +# ip=::: +# Nevertheless, from= parameter won't be overwritten by this +IP=$(cmdline_value ip) +if [ "$IP" != "" -a "$DATAFROM" = "" ]; then + DATAFROM="http://"$(echo $IP | cut -d : -f 2) +fi + +if [ "$FINDISOVAR" != "" -a "$DATAFROM" = "" ]; then + FINDISO=$(find_in_computer $FINDISOVAR) + DATAFROM="$FINDISO" + echolog "$FINDISO found." +fi + +if [ "$DATAFROM" ]; then + if [ "$(echo $DATAFROM | cut -b 1-7 | tr "[:upper:]" "[:lower:]")" = "http://" ]; then + init_dhcp $(modprobe_network_modules) + mount_httpfs $DATAFROM $MOUNTDIR/httpfs + # if mountdir/httpfs/livecdname is found, set DATA=, else umount httpfs + # - currently this part works even without the above mentioned, but livecd.sgn is required now untill it's uncommented + elif [ "$FINDISO" ]; then + mount_device $DATAFROM $FINDISOMNT + echolog "$FINDISO mounted." + else + DATAFROM=$(find_in_computer $DATAFROM) + if [ "$DATAFROM" ]; then + mount_device $DATAFROM $LOOPMOUNT # mount again, it may be loop device + if [ $? -eq 0 -a "$(find_modules $LOOPMOUNT/$LIVECDNAME)" != "" ]; then + echolog "found in $DATAFROM" + DATA=$LOOPMOUNT/$LIVECDNAME + else + fumount $LOOPMOUNT + fumount $MOUNTDIR/* + fi + fi + fi +fi + +if [ "$DATA" = "" ]; then + # from= is not used or it didn't contain valid data + DATA=$(find_in_computer $LIVECDNAME/$SGN) + DATA=$(dirname $DATA 2>/dev/null) +fi + +if [ "$DATA" = "" ]; then fatal \ +"$LIVECDNAME data not found. +You are maybe using an unsupported boot device (eg. SCSI or old PCMCIA). +Workaround: Copy the directory $LIVECDNAME from your boot device to an IDE/SATA +disk, eg. to /mnt/hda1/$LIVECDNAME or C:\\$LIVECDNAME. Then try to boot again." +fi + +echolog "Using $LIVECDNAME data from $DATA" + +debug_shell + +echolog "Setting up directory for changes ..." +CHANGESVAL=$(cmdline_value changes) + +if [ "$CHANGESVAL" ]; then + CHANGESMNT=$(find_in_computer $CHANGESVAL) + echolog $CHANGESMNT +fi + +debug_shell + +mount_device "$CHANGESMNT" $MEMORY # removes $MEMORY if CHANGESMNT is wrong + +# test if the filesystem is writable so changes can be stored to it +touch $MEMORY/empty 2>/dev/null && \ +rm -f $MEMORY/empty 2>/dev/null + +# if changes can't be mounted or the filesystem is not writable, +# fallback to the default: tmpfs +if [ $? -ne 0 ]; then + echolog "Changes not used or not writable, using memory only" + fumount $MEMORY + mkdir -p $MEMORY # mount_device might removed it + + RAMSIZE=$(cmdline_value ramsize) + if [ "$RAMSIZE" = "" ]; then RAMSIZE="60%"; fi + mount -t tmpfs -o "size=$RAMSIZE" tmpfs $MEMORY + XINO=$MEMORY +else + # So it is writable, we will keep the filesystem mounted. + # Check if it supports links and chmod. + # If not, overmount CHANGES using posixovl + echolog "Testing the filesystem for posix compatibility ..." + touch $MEMORY/.empty1 && \ + ln -sf $MEMORY/.empty1 $MEMORY/.empty2 2>/dev/null && \ + chmod +x $MEMORY/.empty1 2>/dev/null && \ + test -x $MEMORY/.empty1 && \ + chmod -x $MEMORY/.empty1 2>/dev/null && \ + test ! -x $MEMORY/.empty1 && \ + rm $MEMORY/.empty1 $MEMORY/.empty2 2>/dev/null + + if [ $? -ne 0 ]; then + echolog "Not compatible - starting posixovl" + rm $MEMORY/.empty1 $MEMORY/.empty2 2>/dev/null + mkdir -p $CHANGES + posixovl -F $CHANGES -- -o attr_timeout=300,entry_timeout=300,negative_timeout=300,kernel_cache,allow_other + find $CHANGES >/dev/null 2>&1 # cache everything now + fi +fi + +# $UNION will be used as a root directory, livecd modules will be added soon +echolog "Setup union directory (using aufs)" + +mkdir -p $CHANGES +mkdir -p $IMAGES +mount -n -t tmpfs tmpfs $IMAGES + +debug_shell + +# store the xino file in memory in all cases, it's faster and safer +if [ "$XINO" != "$MEMORY" ]; then + mkdir -p $XINO + mount -n -t tmpfs tmpfs $XINO +fi + +# mount aufs using the writable branch as the first one (leftmost/topmost) +mount -t aufs -o nowarn_perm,xino=$XINO/.aufs.xino,br:$CHANGES=rw aufs $UNION +if [ $? -ne 0 ]; then dmesg | tail -n 1; fatal "can't setup union (aufs)"; fi + +debug_shell + +# If toram or copy2ram boot parameter is present, copy all fs modules to RAM. +# (skip modules from /optional/ which are not listed in load= boot option) +# Finaly modify DATA variable so it will point to correct directory +if [ "$(cmdline_parameter toram)" != "" -o "$(cmdline_parameter copy2ram)" != "" ]; then + echolog "copying $LIVECDNAME data to RAM, this may take some time..." + mkdir -p $COPY2RAM + + # make sure it's in RAM even with changes= parameter + if [ "$CHANGESMNT" ]; then mount -t tmpfs -o "size=$RAMSIZE" tmpfs $COPY2RAM; fi + copy_to_ram $DATA $COPY2RAM + + cd_autoeject 1 + fumount $DATA + fumount $MOUNTDIR/* + rmdir $MOUNTDIR/* 2>/dev/null # mounted device names are empty, remove them + DATA=$COPY2RAM + cd_autoeject 0 +fi + +debug_shell + +MODPATH=$(cmdline_value modpath) +if [ "$MODPATH" != "" ]; then + MODPATH=$(find_in_computer $MODPATH) + if [ $FINDISOVAR ]; then + mount_device $MODPATH $FINDISOMNT/$LIVECDNAME/tmp rbind + else + mount_device $MODPATH $DATA/tmp rbind + fi +fi + +debug_shell + +#if [ $(cmdline_parameter copy) ]; then +# echolog "Copying initramfs to union. Please wait..." +# # copy busybox to union +# for i in $(ls -a /); do +# case "$i" in +# .|..) ;; +# memory|union) ;; +# mnt) mkdir -p $UNION/mnt ;; +# sys) mkdir -p $UNION/sys ;; +# proc) mkdir -p $UNION/proc ;; +# dev) ;; +# *) if ! cp -af /$i $UNION 2> /dev/null; then +# debug_shell +# fi ;; +# esac +# done +#fi + +#debug_shell + +# DATA contains path to the base directory of all fs modules which need +# to be mounted and inserted into live filesystem. Do it now. +echolog "Loading modules:" +union_insert_modules $UNION $DATA $IMAGES + +# the $MEMORY directory can contain $MEMORY/modules too +# in the case if changes= boot argument is used. If not, it doesn't hurt +union_insert_modules $UNION $MEMORY $IMAGES + +debug_shell + +ROOTCOPY=$(cmdline_value rootcopy) +if [ $(cmdline_parameter norootcopy) ]; then + echolog "Not using rootcopy" +elif [ "$ROOTCOPY" ]; then + echolog "Mounting content of rootcopy directory" + ROOTCOPY=$(find_in_computer $ROOTCOPY) + mount_device $ROOTCOPY $DATA/rootcopy rbind + echolog "Copying content of rootcopy directory" + cp -af $DATA/rootcopy/* $UNION 2>/dev/null # may be empty +else + echolog "Copying content of rootcopy directory" + cp -af $DATA/rootcopy/* $UNION 2>/dev/null # may be empty +fi + +# TODO: if copy2ram is used, there is no need to preserve the original in memory anymore +#if [ "$DATA" = "$COPY2RAM" ]; then +# rm from memory once ?? +#fi + +echolog "Copying liblinuxlive library to union" +cp -af /liblinuxlive $UNION/usr/lib/ + +debug_shell + +echolog "Recreating /etc/fstab and /mnt directories" +touch $UNION/etc/fstab +rmdir $UNION/mnt/* 2>/dev/null +fstab_update $UNION +#fstab_clean $UNION + +# everything is ready now, so we may unload unused kernel modules +# and do some cleanup, unmount few things which are no longer needed. +#rmmod_unused_modules +#fumount /usr +#fumount /sys + +# More likely these directories aren't there. +# Even if they are, this won't hurt. +mkdir -p $UNION/boot +mkdir -p $UNION/proc +mkdir -p $UNION/sys +mkdir -p $UNION/dev +mkdir -p $UNION/tmp +chmod 1777 $UNION/tmp + +# Boot will contain whatever was in ./boot directory in the bootable media +# Error output goes to null, as nothing is mounted with copy2ram +#mount -n -o rbind $(dirname $DATA)/boot $UNION/boot 2>/dev/null + +# Union contains all the files and directories unioned from all modules. +# Change root directory to it, and move initrd's root to /mnt/live/initramdisk +# Finaly execute /sbin/init to start the distribution. +echolog "changing root directory..." + +cd $UNION +mkdir -p $INITRAMDISK + +# Copy all dev files (found by mdev) to unioned dev directory +# so at least disk devices exist (your Linux may need them). +# Two exceptions, do not copy pty* and tty* devs. +if [ "$(cmdline_parameter nohotplug)" ]; then + cp -fdR /dev . 2>/dev/null +#else + #mount -n -o move /dev dev +fi + +#mount -n -o move /proc proc +#mount -n -o move /sys sys +fumount /sys + +if [ ! -e /dev/console ]; then mknod /dev/console c 5 1; fi + +# find chroot and init +if [ -x bin/chroot ]; then CHROOT=bin/chroot; fi +if [ -x sbin/chroot ]; then CHROOT=sbin/chroot; fi +if [ -x usr/bin/chroot ]; then CHROOT=usr/bin/chroot; fi +if [ -x usr/sbin/chroot ]; then CHROOT=usr/sbin/chroot; fi +if [ "$CHROOT" = "" ]; then fatal "Can't find executable chroot command"; fi + +if [ -x bin/init ]; then INIT=bin/init; fi +if [ -x sbin/init ]; then INIT=sbin/init; fi +if [ "$INIT" = "" ]; then fatal "Can't find executable init command"; fi + +# time to end Linux Live scripts and start the distribution itself, +# using /sbin/init or whatever was found. + +debug_shell + +fumount /proc + +mount -n -o remount,ro aufs . + +# We will copy init from the distro to initrd (there should be 2MB free) +# This allows us to use the cleanup script during reboot, as init will be +# started from memory and not from the union and /union will not be busy. + +cp -af $INIT /bin >/dev/null 2>&1 +if [ $? -eq 0 ]; then + pivot_root . $INITRAMDISK + exec $CHROOT . $INITRAMDISK/bin/init dev/console 2>&1 +else # If copying fails, start init directly. + pivot_root . $INITRAMDISK + exec $CHROOT . $INIT dev/console 2>&1 +fi + +header "!!ERROR!!" +fatal "You are not supposed to be here, something went wrong!" diff -r 000000000000 -r 6d654d523ac8 list/a.000.base.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.000.base.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,36 @@ +busybox +bzlib +dialog +dropbear +e2fsprogs +gcc-lib-base +glibc-base +gpxe +grub4dos-linux +isapnptools +kbd-busybox +libcap +linux +linux-drm +linux-firmware +lzlib +lzma +pcmciautils +ppp +rp-pppoe +slitaz-base-files +slitaz-boot-scripts +slitaz-tools +sysfsutils +syslinux +syslinux-extra +tazlito +tazpkg +tazusb +tazwok +udev +zlib +ncurses-common +aufs-utils +squashfs +htop \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.001.justx.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.001.justx.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,96 @@ +busybox +bzlib +cairo +cdrkit +dbus +dbus-glib +dialog +dropbear +e2fsprogs +expat +fontconfig +freetype +gcc-lib-base +glib +glibc-base +gpxe +grub4dos-linux +hal +isapnptools +jpeg +kbd-busybox +libcap +libcomerr +libcrypto +libgcrypt +libgio +libpng +libxml2 +linux +locale-de +locale-es +locale-fr +locale-pt +lzlib +lzma +nano +ncurses +openbox +pango +pciutils +pcmciautils +pcre +pixman +popt +ppp +rp-pppoe +slim +slitaz-base-files +slitaz-boot-scripts +slitaz-doc +slitaz-polar-cursors +slitaz-tools +sqlite +startup-notification +sysfsutils +syslinux +syslinux-extra +tazlito +tazpkg +tazusb +tazwok +tiff +ttf-dejavu +udev +xorg-base-fonts +xorg-libfontenc +xorg-libICE +xorg-libSM +xorg-libX11 +xorg-libXau +xorg-libXaw +xorg-libXcomposite +xorg-libXcursor +xorg-libXdamage +xorg-libXdmcp +xorg-libXext +xorg-libXfixes +xorg-libXfont +xorg-libXft +xorg-libXi +xorg-libXinerama +xorg-libXmu +xorg-libXpm +xorg-libXrandr +xorg-libXrender +xorg-libXt +xorg-libXtst +xorg-rgb +xorg-server +xorg-setxkbmap +xorg-xauth +xorg-xf86-input-evdev +xorg-xf86-video-vesa +xorg-xsetroot +xterm +zlib diff -r 000000000000 -r 6d654d523ac8 list/a.002.core-basic.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.002.core-basic.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,151 @@ +atk +busybox +bzlib +cairo +cdrkit +clearlooks +dbus +dbus-glib +dialog +dropbear +e2fsprogs +expat +fontconfig +freetype +gamin +gcc-lib-base +get-wifi-firmware +glib +glibc-base +gpxe +grub4dos-linux +gtk+ +gtkdialog +hal +hardinfo +hicolor-icon-theme +isapnptools +jpeg +kbd-busybox +leafpad +libcap +libcomerr +libgio +libglade +libpng +libxml2 +linux +linux-wireless +linux-sound +locale-de +locale-es +locale-fr +locale-pt +lxappearance +lxpanel +lxtask +lzlib +lzma +nano +nanochess +ncurses +ncursesw +obconf +openbox +pango +pciutils +pcmanfm +pcmciautils +pcre +pixman +popt +ppp +rp-pppoe +shared-mime-info +slim +slitaz-base-files +slitaz-boot-scripts +slitaz-configs +slitaz-doc +slitaz-icon +slitaz-menus +slitaz-polar-cursors +slitaz-tools +slitaz-tools-boxes +sqlite +startup-notification +sysfsutils +syslinux +syslinux-extra +tazlito +tazpkg +tazusb +tazwikiss +tazwok +tiff +transset-df +ttf-dejavu +udev +xorg +xorg-base-fonts +xorg-libfontenc +xorg-libICE +xorg-libSM +xorg-libX11 +xorg-libXau +xorg-libXaw +xorg-libXcomposite +xorg-libXcursor +xorg-libXdamage +xorg-libXdmcp +xorg-libXext +xorg-libXfixes +xorg-libXfont +xorg-libXft +xorg-libXi +xorg-libXinerama +xorg-libXmu +xorg-libXpm +xorg-libXrandr +xorg-libXrender +xorg-libXt +xorg-libXtst +xorg-rgb +xorg-xauth +xorg-xcompmgr +xterm +zlib +libcrypto +wireless_tools +wpa_supplicant +mtpaint +libnotify +transmission +alsa-lib +alsaplayer +alsa-utils +asunder +galculator +ntfs-3g +ntfsprogs +web-applications +viewnior +sudoku-savant +desktop-file-utils +xorg-server +xorg-xf86-input-evdev +xorg-xf86-video-vesa +xorg-setxkbmap +mhwaveedit +isomaster +gcolor2 +lostirc +gparted +beaver +lua +epdfview +915resolution +libunique +libwebkit +midori +gettext-base diff -r 000000000000 -r 6d654d523ac8 list/a.003.mesa.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.003.mesa.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,3 @@ +mesa +mesa-dri +#mesa-demos \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.004.xorg-xf86-video.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.004.xorg-xf86-video.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,13 @@ +xorg-xf86-video-ati +xorg-xf86-video-i740 +xorg-xf86-video-intel +#xorg-xf86-video-mga +xorg-xf86-video-neomagic +xorg-xf86-video-nv +xorg-xf86-video-openchrome +xorg-xf86-video-s3 +xorg-xf86-video-savage +xorg-xf86-video-sis +xorg-xf86-video-trident +xorg-xf86-video-v4l +xorg-xf86-video-vmware \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.005.firefox.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.005.firefox.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,1 @@ +firefox \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.006.libs.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.006.libs.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,37 @@ +abiword +gnumeric +mplayer +devede +gtkpod +pidgin +uget +geany +deluge +mixxx +lmms +hydrogen +gimp +gimp-plug-ins +gimp-console +inkscape +xarchiver +comix +zsnes +stella +pcsxr-svn +visualboyadvance-gtk +virtualbox-ose +vlc +#libs-only +python +patch +openssl +openssh +zip +unzip +bzip2 +xz +libarchive +get-rar +perl +get-flash-plugin \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.006.libs.removelist --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.006.libs.removelist Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,24 @@ +abiword +gnumeric +mplayer +devede +gtkpod +pidgin +uget +geany +deluge +mixxx +lmms +hydrogen +gimp +gimp-plug-ins +gimp-console +inkscape +xarchiver +comix +zsnes +stella +pcsxr-svn +visualboyadvance-gtk +virtualbox-ose +vlc \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.007.apps.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.007.apps.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,24 @@ +abiword +gnumeric +mplayer +devede +gtkpod +pidgin +uget +geany +deluge +mixxx +lmms +hydrogen +gimp +gimp-plug-ins +gimp-console +inkscape +xarchiver +comix +zsnes +stella +pcsxr-svn +visualboyadvance-gtk +virtualbox-ose +vlc \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.008.mercurial.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.008.mercurial.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,1 @@ +mercurial \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/a.009.pentest.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/a.009.pentest.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,16 @@ +aircrack-ng +airpwn +airsnort +aaphoto +nmap +snort +nfs-utils +wipe +tor +tinyproxy +testdisk +scanssh +sshfs +dd_rescue +sleuthkit +secure-delete \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 list/initramfs.list --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/list/initramfs.list Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,31 @@ +busybox +bzlib +dialog +e2fsprogs +gcc-lib-base +glibc-base +gpxe +grub +isapnptools +kbd-busybox +libcap +libcomerr +linux +lzlib +lzma +ncurses +pciutils +pcmciautils +slitaz-base-files +slitaz-boot-scripts +sysfsutils +syslinux +syslinux-extra +udev +zlib +linux-squashfs +aufs +aufs-utils +squashfs +module-init-tools +util-linux-ng-blkid \ No newline at end of file diff -r 000000000000 -r 6d654d523ac8 mkiso.sh --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/mkiso.sh Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,355 @@ +#!/bin/sh + +if [ -f "./tazwok.conf" ]; then + . ./tazwok.conf +elif [ -f "/etc/tazwok.conf" ]; then + . /etc/tazwok.conf +else + echo -e "\nUnable to find tazwok configuration file : /etc/tazwok.conf" + exit 1 +fi + +QUIET="y" +FORCE="y" +export LABEL="slitaz_$(date +%Y%m)" +PUBLISHER="Slitaz" +APPLICATION="Slitaz" +CREATE_DEFAULT="n" +PROFILE="$(pwd)" +ver="" +CDNAME="slitaz" +RMSTUFF=n +MVSTUFF=n +UNGZIP=n +EXT="sqfs" +COMPRESSION="gzip" +MKOPTION="-b 256k" +MODULES="" +WORKING="$PROFILE/working" +INITRAMFS="$WORKING/initramfs" +UNION="$WORKING/union" +LOG="$WORKING/log" +ISODIR="$WORKING/iso" +IMGNAME="$PROFILE/$CDNAME-$(date +%F).iso" +IMGMD5NAME="$IMGNAME.md5" +LASTBR="$WORKING/empty" +SGNFILE="$ISODIR/$CDNAME/livecd.sgn" +MODULES_DIR="$WORKING/modules" +HG_DIR="$WORKING/hg" +COPY_HG="no" +UPDATE_HG="no" +BACKUP_SOURCES="no" +BACKUP_PACKAGES="no" +CLEAN_MODULES_DIR="no" +HG_LIST="flavors flavors-stable slitaz-base-files slitaz-boot-scripts slitaz-configs slitaz-doc slitaz-pizza slitaz-tools tank tazlito tazpkg tazusb tazwok website wok" + +error () { echo -e "\033[1;31;40m!!! \033[1;37;40m$@\033[1;0m"; } +warn () { echo -e "\033[1;33;40m*** \033[1;37;40m$@\033[1;0m"; } +info () { echo -e "\033[1;32;40m>>> \033[1;37;40m$@\033[1;0m"; } + +# do UID checking here so someone can at least get usage instructions +#if [ "$EUID" != "0" ]; then +# error "error: This script must be run as root." +# exit 1 +#fi + +if [ -f ${PROFILE}/config ]; then + source ${PROFILE}/config +fi + +_overlay() +{ + if [ -d ${MODULES_DIR}/overlay ]; then + rm -rf ${MODULES_DIR}/overlay + cp -rf ${PROFILE}/overlay ${MODULES_DIR} + else + cp -rf ${PROFILE}/overlay ${MODULES_DIR} + fi + + if [ "${QUIET}" = "y" ]; then + mksquashfs "${MODULES_DIR}/overlay" "${ISODIR}/${CDNAME}/modules/zzz.overlay.${EXT}" -comp ${COMPRESSION} -noappend ${MKOPTION} >/dev/null + else + mksquashfs "${MODULES_DIR}/overlay" "${ISODIR}/${CDNAME}/modules/zzz.overlay.${EXT}" -comp ${COMPRESSION} -noappend ${MKOPTION} + fi +} + +lzma_switches() +{ + echo "-d$(echo 24) -mt$(grep ^processor < /proc/cpuinfo | wc -l)" +} + +# Pack rootfs +pack_rootfs() +{ + ( cd $1 ; find . -print | cpio -o -H newc ) | \ + if [ -x /usr/bin/lzma ]; then + info "Generating lzma'ed initramfs... " + lzma e -si -so $(lzma_switches $1) > $2 + else + info "Generating gziped initramfs... " + gzip -9 > $2 + fi + echo 1 > /tmp/rootfs +} + +initramfs () { + + if [ ! -e "$PROFILE/list/initramfs.list" ]; then + error "error: $PROFILE/list/initramfs.list doesn't exist, aborting." + exit 1 + fi + + info "Making bootable image" + cat "$PROFILE/list/initramfs.list" | grep -v "^#" | while read pkgname; do + if [ ! -d ${INITRAMFS}/var/lib/tazpkg/installed/${pkgname} ]; then + tazpkg get-install $pkgname --root=$INITRAMFS | tee -a $LOG/initramfs.log + sleep 1 + else + info "${pkgname} installed" + fi + done + + if [ ! -d $ISODIR/boot ]; then + mkdir -p $ISODIR/boot + fi + + if [ ! -f $ISODIR/boot/bzImage ]; then + cp -f $INITRAMFS/boot/vmlinuz* $ISODIR/boot/bzImage + rm -f $INITRAMFS/boot/vmlinuz* + fi + + info "Copying isolinux files..." + if [ -d $INITRAMFS/boot/isolinux ]; then + cp -a $INITRAMFS/boot/isolinux $ISODIR/boot + fi + + if [ -d $PROFILE/initramfs ]; then + cp -af $PROFILE/initramfs/* $INITRAMFS + fi + + info "Creating rootfs.gz" + pack_rootfs $INITRAMFS $ISODIR/boot/rootfs.gz +} + +copy_hg() { + if [ ! -d ${HG_DIR}/hg-${1}/home/slitaz/hg/$1 ]; then + info "Cloning $1 repo ..." + hg clone http://hg.slitaz.org/$1 ${HG_DIR}/hg-${1}/home/slitaz/hg/$1 + elif [ -d ${HG_DIR}/hg-${1}/home/slitaz/hg/$1 -a ${UPDATE_HG} = "yes" ]; then + info "Updating $1 repo ..." + cd ${HG_DIR}/hg-${1}/home/slitaz/hg/$1 && + hg pull && hg update + cd $PROFILE + fi +} + +squashfs_hg() { + if [ ! -d "$ISODIR/$CDNAME/modules/hg" ]; then + mkdir -p "$ISODIR/$CDNAME/modules/hg" + fi + if [ -d ${HG_DIR}/hg-${1}/home/slitaz/hg/$1 ]; then + _mksquash ${HG_DIR}/hg-${1} "$ISODIR/$CDNAME/modules/hg" /home/slitaz/hg/$1 + fi +} + +slitaz_union () { + + if [ -d ${MODULES_DIR}/${mod}/var/lib/tazpkg/installed ]; then + echo "${mod} module exist. Moving on." + elif [ ! -d ${MODULES_DIR}/${mod}/var/lib/tazpkg/installed ]; then + if [ -f "$PROFILE/list/${mod}.list" ]; then + cat "$PROFILE/list/${mod}.list" | grep -v "^#" | while read pkgname; do + if [ ! -d ${UNION}/var/lib/tazpkg/installed/${pkgname} ]; then + tazpkg get-install $pkgname --root=${UNION} | tee -a ${LOG}/${mod}-current.log + sleep 1 + else + info "${pkgname} installed" + fi + done + fi + + if [ -f $PROFILE/list/${mod}.removelist ]; then + cat "$PROFILE/list/${mod}.removelist" | grep -v "^#" | while read pkgname; do + if [ -d ${UNION}/var/lib/tazpkg/installed/${pkgname} ]; then + echo "y" | tazpkg remove ${pkgname} --root=${UNION} | tee -a ${LOG}/${mod}-current.log + sleep 1 + else + info "${pkgname} removed" + fi + done + fi + fi +} + +union () { + mkdir -p $WORKING + mkdir -p $UNION + mkdir -p $LOG + mkdir -p $INITRAMFS + mkdir -p $ISODIR/${CDNAME}/base + mkdir -p $ISODIR/${CDNAME}/modules + mkdir -p $ISODIR/${CDNAME}/optional + mkdir -p $ISODIR/${CDNAME}/rootcopy + mkdir -p $ISODIR/${CDNAME}/tmp + mkdir -p $LASTBR + touch $SGNFILE + + modprobe aufs + if [ $? -ne 0 ]; then + error "Error loading Union filesystem module. (aufs)" + exit 1 + fi + + mount -t aufs -o br:${LASTBR}=rw aufs ${UNION} + if [ $? -ne 0 ]; then + error "Error mounting $union." + exit 1 + fi + + info "====> Installing packages to '$UNION'" + for mod in $MODULES; do + + if [ "$CLEAN_MODULES_DIR" = "yes" ]; then + if [ -d $MODULES_DIR/$mod ]; then + rm -Rf $MODULES_DIR/$mod + fi + fi + + if [ ! -d $MODULES_DIR/$mod ]; then + mkdir -p $MODULES_DIR/$mod + fi + info "Adding $MODULES_DIR/$mod as top branch of union." + mount -t aufs -o remount,add:0:${MODULES_DIR}/${mod}=rw aufs $UNION + info "Adding $LASTBR as lower branch of union." + mount -t aufs -o remount,mod:${LASTBR}=rr+wh aufs $UNION + LASTBR="$MODULES_DIR/${mod}" + + slitaz_union + done + + info "Unmounting union" + umount -l "${UNION}" + + info "Removing unionfs .wh. files." + find ${MODULES_DIR} -type f -name ".wh.*" -exec rm {} \; + find ${MODULES_DIR} -type d -name ".wh.*" -exec rm -rf {} \; +} + + +# _mksquash dirname +_mksquash () { + if [ ! -d "$1" ]; then + error "Error: '$1' is not a directory" + return 1 + fi + + if [ ! -d "$2" ]; then + error "Error: '$2' is not a directory" + return 1 + fi + + if [ ! -d "${1}${3}" ]; then + error "Error: '${1}${3}' is not a directory" + return 1 + fi + + time_dir="${3}" + sqimg="${2}/$(basename ${1}).${EXT}" + info "====> Generating SquashFS image for '${1}'" + if [ -e "${sqimg}" ]; then + dirhaschanged=$(find ${1}${time_dir} -newer ${sqimg}) + if [ "${dirhaschanged}" != "" ]; then + info "SquashFS image '${sqimg}' is not up to date, rebuilding..." + rm "${sqimg}" + else + info "SquashFS image '${sqimg}' is up to date, skipping." + return + fi + fi + + info "Creating SquashFS image. This may take some time..." + start=$(date +%s) + if [ "${QUIET}" = "y" ]; then + mksquashfs "${1}" "${sqimg}" -noappend ${MKOPTION} -comp ${COMPRESSION} >/dev/null + else + mksquashfs "${1}" "${sqimg}" -noappend ${MKOPTION} -comp ${COMPRESSION} + fi + minutes=$(echo $start $(date +%s) | awk '{ printf "%0.2f",($2-$1)/60 }') + info "Image creation done in $minutes minutes." +} + +imgcommon () { + if [ "${MODULES}" != "" ]; then + for MOD in ${MODULES}; do + if [ -d "${MODULES_DIR}/${MOD}" ]; then + _mksquash "${MODULES_DIR}/${MOD}" "$ISODIR/$CDNAME/base" /var/lib/tazpkg/installed + fi + done + fi + + if [ "$HG_LIST" != "" ]; then + if [ "$COPY_HG" = "yes" ]; then + for hg in $HG_LIST; do + copy_hg $hg + squashfs_hg $hg + done + fi + fi + + if [ "${HG_LIST}" != "" ]; then + for hg in ${HG_LIST}; do + if [ -d "${MODULES_DIR}/hg-${hg}" ]; then + squashfs_hg $hg + fi + done + fi + + info "====> Making bootable image" + + # Sanity checks + if [ ! -d "${ISODIR}" ]; then + error "Error: '${ISODIR}' doesn't exist. What did you do?!" + exit 1 + fi + + if [ ! -f "${SGNFILE}" ]; then + error "Error: the ${SGNFILE} file doesn't exist. This image won't do anything" + error " Protecting you from yourself and erroring out here..." + exit 1 + fi + + + if [ -e "${IMGNAME}" ]; then + if [ "${FORCE}" = "y" ]; then + info "Removing existing bootable image..." + rm -rf "${IMGNAME}" + else + error "Error: Image '${IMGNAME}' already exists, aborting." + exit 1 + fi + fi + +} + +make_iso () { + imgcommon + initramfs + + if [ -d ${PROFILE}/overlay ]; then + _overlay + fi + + info "Creating ISO image..." + genisoimage -R -o $IMGNAME -b boot/isolinux/isolinux.bin \ + -c boot/isolinux/boot.cat -no-emul-boot -boot-load-size 4 \ + -V "SliTaz" -input-charset iso8859-1 -boot-info-table $ISODIR + if [ -x /usr/bin/isohybrid ]; then + info "Creating hybrid ISO..." + isohybrid "${IMGNAME}" + fi + md5sum "${IMGNAME}" > $IMGMD5NAME +} + + +union +make_iso diff -r 000000000000 -r 6d654d523ac8 overlay/etc/fstab --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/overlay/etc/fstab Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,9 @@ +# /etc/fstab: Information about static filesystems. +# +proc /proc proc defaults 0 0 +sysfs /sys sysfs defaults 0 0 +devpts /dev/pts devpts defaults 0 0 +tmpfs /dev/shm tmpfs defaults 0 0 +tmpfs /tmp tmpfs defaults 0 0 +#/dev/hda3 /home ext3 defaults 0 2 +#/dev/hdb1 /mnt/data ext3 defaults 0 2 diff -r 000000000000 -r 6d654d523ac8 overlay/usr/bin/tazpkg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/overlay/usr/bin/tazpkg Thu Nov 25 03:30:16 2010 +0000 @@ -0,0 +1,2787 @@ +#!/bin/sh +# Tazpkg - Tiny autonomous 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 lets you +# list, install, remove, download or get information about a package. You can +# use 'tazpkg usage' to get a list of commands with short descriptions. Tazpkg +# also resolves dependencies and can upgrade packages from a mirror. I18n is +# done with gettext and eval_gettext, ex: +# gettext "displayed text"; echo +# eval_gettext "display \$VARIABLE"; echo +# echo -e "BOLD `gettext \"i18n message\"`" +# +# (C) 2007-2010 SliTaz - GNU General Public License v3. +# +# Authors : Christophe Lincoln +# Pascal Bellard +# Eric Joseph-Alexandre +# Paul Issott +# Rohit Joshi +# +VERSION=4.0 + +#################### +# Script variables # +#################### + +. /etc/slitaz/tazpkg.conf + +# Include gettext helper script. +. /usr/bin/gettext.sh + +# Export package name for gettext. +TEXTDOMAIN='tazpkg' +export TEXTDOMAIN + +# 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` +INSTALL_LIST="" + +# Path to tazpkg used dir and configuration files +INSTALLED=$LOCALSTATE/installed +MIRROR=$LOCALSTATE/mirror +BLOCKED=$LOCALSTATE/blocked-packages.list +DEFAULT_MIRROR="http://mirror.slitaz.org/packages/`cat /etc/slitaz-release`/" + +# Check if the directories and files used by Tazpkg +# exist. 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 package 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. + bugs Show known bugs in packages. + list List installed packages on the system by category or all. + xhtml-list Create a xHTML list of installed packages. + list-mirror List all available packages on the mirror (--diff for new). + info Print information about a package. + desc Print description of a package (if it exists). + list-files List the files installed with a package. + list-config List the configuration files. + search Search for a package by pattern or name (options: -i|-l|-m). + search-pkgname Search on mirror for package having a particular file. + 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 Create a package archive from an installed package. + repack-config Create a package archive with configuration files. + recompress Rebuild a package with the better compression ratio. + upgrade Upgrade one or all installed/listed package(s) on the mirror. + upgradeable Build upgradeable packages list quickly. + 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 consistency of installed packages. + 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. + depends Display dependencies tree. + rdepends Display reverse dependencies tree. + convert Convert a deb/rpm/tgz/arch package to a slitaz (.tazpkg). + link Link a package from another slitaz installation. + setup-mirror Change the mirror url configuration. + list-undigest List undigest mirrors. + remove-undigest Remove an undigest mirror. + add-undigest Add an undigest mirror. + setup-undigest Update an undigest mirror. + 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 + gettext \ +"You must be root to run tazpkg with this option. Please use the command: +su followed by the root password to become super-user."; echo + echo "" && exit 0 + fi +} + +# Check for a package name on cmdline. +check_for_package_on_cmdline() +{ + if [ -z "$PACKAGE" ]; then + echo "" + gettext "Please specify a package name on the command line."; echo + echo "" + exit 0 + fi +} + +# Check if the package (*.tazpkg) exist before installing or extracting. +check_for_package_file() +{ + if [ ! -f "$PACKAGE_FILE" ]; then + echo "" + eval_gettext "Unable to find: \$PACKAGE_FILE"; echo + echo "" && exit 0 + fi +} + +# Check for the receipt of an installed package. +check_for_receipt() +{ + if [ ! -f "$1$INSTALLED/$PACKAGE/receipt" ]; then + FS=$1 + echo "" + eval_gettext "Unable to find the receipt: \$FS\$INSTALLED/\$PACKAGE/receipt"; echo + echo "" && 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 "" + eval_gettext "\$PACKAGE package is already installed. You can +use the --forced option to force installation or remove it and reinstall."; echo + echo "" && 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 "" + eval_gettext "Unable to find the list: \$LOCALSTATE/packages.list"; echo + gettext \ +"You must probably run 'tazpkg recharge' as root to get the latest list of +packages available on the mirror."; echo + echo "" && exit 0 + fi + fi +} + +# get an already installed package from packages.equiv +equivalent_pkg() +{ + for i in $(grep -hs "^$1=" $LOCALSTATE/packages.equiv \ + $LOCALSTATE/undigest/*/packages.equiv | sed "s/^$1=//"); do + if echo $i | grep -q : ; then + # format 'alternative:newname' + # if alternative is installed then substitute newname + if [ -f $2$INSTALLED/${i%:*}/receipt ]; then + # substitute package dependancy + echo ${i#*:} + return + fi + else + # if alternative is installed then nothing to install + if [ -f $2$INSTALLED/$i/receipt ]; then + # substitute installed package + echo $i + return + fi + fi + done + # if not found in packages.equiv then no substitution + echo $1 +} + +# get a virtual package from packages.equiv +virtual_pkg() +{ + for i in $(grep -hs "^$1=" $LOCALSTATE/packages.equiv \ + $LOCALSTATE/undigest/*/packages.equiv | sed "s/^$1=//"); do + if echo $i | grep -q : ; then + # format 'alternative:newname' + # if alternative is installed then substitute newname + if [ -f $2$INSTALLED/${i%:*}/receipt ]; then + # substitute package dependancy + echo ${i#*:} + return + fi + else + # unconditional substitution + echo $i + return + fi + done +} + +# Get package filename available on the mirror +get_package_filename() +{ + local pkg + pkg=$(grep -A 1 -sh "^$1$" $LOCALSTATE/packages.txt \ + $LOCALSTATE/undigest/*/packages.txt | tail -1) + pkg=$(echo $pkg) + [ -n "$pkg" ] && pkg=$(grep -sh "^$1-$pkg" \ + $LOCALSTATE/packages.list \ + $LOCALSTATE/undigest/*/packages.list | head -1) + [ -n "$pkg" ] || pkg=$(grep -sh "^$1-[0-9]" \ + $LOCALSTATE/packages.list \ + $LOCALSTATE/undigest/*/packages.list | head -1) + [ -n "$pkg" ] || pkg=$(grep -sh "^$1-.[\.0-9]" \ + $LOCALSTATE/packages.list \ + $LOCALSTATE/undigest/*/packages.list | head -1) + if [ -z "$pkg" ]; then + # Check for vitual package + local equiv + equiv=$(virtual_pkg $1) + if [ "$equiv" != "$1" ]; then + PACKAGE=$equiv + get_package_filename $PACKAGE + return + fi + fi + echo $pkg +} + +# Check for a package in packages.list. Used by get and get-install to grep +# package basename. +check_for_package_in_list() +{ + local filename + local check_only + check_only="$1" + filename=$(get_package_filename $PACKAGE) + if [ -n "$filename" ]; then + PACKAGE=$filename + else + echo "" + eval_gettext "Unable to find: \$PACKAGE in the mirrored packages list."; echo + echo "" + [ -n "$check_only" ] && return 1 + exit 0 + fi +} + +# Log this activity +log() +{ + local extra + [ "$1" = "Installed" ] && \ + extra=" - $(grep $PACKAGE-$VERSION $LOCALSTATE/installed.md5 | awk '{ print $1 }')" + [ -e $LOG ] || touch $LOG + DATE=`date +'%F %T'` + [ -w $LOG ] && + echo "$DATE - $1 - $PACKAGE ($VERSION$EXTRAVERSION)$extra" >> $LOG +} + +# Download a file from this mirror +download_from() +{ + local i + local mirrors + mirrors="$1" + shift + for i in $mirrors; do + case "$i" in + http://*|ftp://*) wget -c $i$@ && break;; + *) cp $i/$1 . && break;; + esac + done +} + +# Download a file trying all mirrors +download() +{ + local i + case "$1" in + *.tazpkg) + for i in $LOCALSTATE $LOCALSTATE/undigest/* ; do + grep "^${1%.tazpkg}$" $i/packages.list || continue + download_from "$(cat $i/mirror)" "$@" && return + done + esac + for i in $(cat $MIRROR $LOCALSTATE/undigest/*/mirror 2> /dev/null); do + download_from "$i" "$@" && break + done +} + +# Extract a package with cpio and gzip/lzma. +extract_package() +{ + gettext "Extracting $PACKAGE... " + cpio -idm < $PACKAGE.tazpkg && rm -f $PACKAGE.tazpkg + if [ -f fs.cpio.lzma ]; then + gettext "Extracting the pseudo fs... " + echo -n "(lzma) " + unlzma -c fs.cpio.lzma | cpio -idm && rm fs.cpio.lzma + elif [ -f fs.cpio.gz ]; then + gettext "Extracting the pseudo fs... " + zcat fs.cpio.gz | cpio -idm && rm fs.cpio.gz + fi +} + +remove_with_path() +{ + local dir + rm -f $1 2>/dev/null + dir="$1" + while [ "$dir" != "/" ]; do + dir="$(dirname $dir)" + rmdir $dir 2> /dev/null || break + done +} + +grepesc() +{ + sed 's/\[/\\[/g' +} + +# This function installs 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 dependencies loop + mkdir -p $TMP_DIR + ( cd $TMP_DIR ; cpio --quiet -i receipt > /dev/null 2>&1) < $PACKAGE_FILE + . $TMP_DIR/receipt + if grep -q ^pre_depends $TMP_DIR/receipt; then + pre_depends $ROOT + fi + # keep modifers and file list on upgrade + cp $ROOT$INSTALLED/$PACKAGE/modifiers \ + $ROOT$INSTALLED/$PACKAGE/files.list $TMP_DIR 2> /dev/null + rm -rf $ROOT$INSTALLED/$PACKAGE 2> /dev/null + # Make the installed package data dir to store + # the receipt and the files list. + mkdir -p $ROOT$INSTALLED/$PACKAGE + cp $TMP_DIR/modifiers $ROOT$INSTALLED/$PACKAGE 2> /dev/null + cp $TMP_DIR/files.list $ROOT$INSTALLED/$PACKAGE 2> /dev/null + rm -rf $TMP_DIR 2> /dev/null + sed -i "/ $(basename $PACKAGE_FILE)$/d" \ + $ROOT$LOCALSTATE/installed.md5 2> /dev/null + cd $(dirname $PACKAGE_FILE) + md5sum $(basename $PACKAGE_FILE) >> $ROOT$LOCALSTATE/installed.md5 + ) + # Resolve 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[1m`gettext \"Installation of :\"`\033[0m $PACKAGE" + echo "================================================================================" + eval_gettext "Copying \$PACKAGE... " + cp $PACKAGE_FILE $TMP_DIR + status + cd $TMP_DIR + extract_package + SELF_INSTALL=0 + EXTRAVERSION="" + CONFIG_FILES="" + # Include temporary receipt to get the right variables. + . $PWD/receipt + cd $ROOT$INSTALLED + if [ $SELF_INSTALL -ne 0 -a -n "$ROOT" ]; then + gettext "Checking post install dependencies... " + [ -f $INSTALLED/$PACKAGE/receipt ] + if ! status; then + eval_gettext "Please run 'tazpkg install \$PACKAGE_FILE' in / and retry."; echo + rm -rf $TMP_DIR + exit 1 + fi + fi + # Get files to remove if upgrading + if [ -f $PACKAGE/files.list ]; then + while read file; do + grep -q "^$(echo $file | grepesc)$" $TMP_DIR/files.list && continue + for i in $(cat $PACKAGE/modifiers 2> /dev/null ; + grep -sl $PACKAGE */modifiers | cut -d/ -f1 ); do + grep -qs "^$(echo $file | grepesc)$" $i/files.list && continue 2 + done + echo $file + done < $PACKAGE/files.list > $TMP_DIR/files2remove.list + fi + # Remember modified packages + { check=false + for i in $(grep -v '\[' $TMP_DIR/files.list); do + [ -e "$ROOT$i" ] || continue + [ -d "$ROOT$i" ] && continue + echo "- $i" + check=true + done ; + $check && for i in *; do + [ "$i" == "$PACKAGE" ] && continue + [ -s $i/files.list ] || continue + awk "{ printf \"$i %s\\n\",\$1 }" < $i/files.list + done } | awk ' +{ + if ($1 == "-" || file[$2] != "") { + file[$2] = file[$2] " " $1 + if ($1 != "-") { + if (pkg[$1] == "") all = all " " $1 + pkg[$1] = pkg[$1] " " $2 + } + } +} +END { + for (i = split(all, p, " "); i > 0; i--) + for (j = split(pkg[p[i]], f, " "); j > 0; j--) + printf "%s %s\n",p[i],f[j]; +} + ' | while read dir file; do + if grep -qs ^$dir$ $PACKAGE/modifiers; then + # Do not overload an overloaded file ! + rm $TMP_DIR$file 2> /dev/null + continue + fi + grep -qs ^$PACKAGE$ $dir/modifiers && continue + if [ -s "$dir/volatile.cpio.gz" ]; then + # We can modify backed up files without notice + zcat $dir/volatile.cpio.gz | cpio -t 2> /dev/null | \ + grep -q "^${file#/}$" && continue + fi + echo "$PACKAGE" >> $dir/modifiers + done + + cd $TMP_DIR + cp receipt files.list $ROOT$INSTALLED/$PACKAGE + # Copy the description if found. + if [ -f "description.txt" ]; then + cp description.txt $ROOT$INSTALLED/$PACKAGE + fi + # Copy the md5sum if found. + if [ -f "md5sum" ]; then + cp md5sum $ROOT$INSTALLED/$PACKAGE + fi + # Pre install commands. + if grep -q ^pre_install $ROOT$INSTALLED/$PACKAGE/receipt; then + pre_install $ROOT + fi + if [ -n "$CONFIG_FILES" ]; then + # save 'official' configuration files + eval_gettext "Saving configuration files for \$PACKAGE... " + for i in $CONFIG_FILES; do + ( cd fs ; find ${i#/} -type f ) + done | ( cd fs ; cpio -o -H newc | gzip -9 ) > \ + $ROOT$INSTALLED/$PACKAGE/volatile.cpio.gz + # keep user configuration files + for i in $CONFIG_FILES; do + ( cd fs ; find ${i#/} -type f ) + done | while read i; do + [ -e $ROOT/$i ] || continue + cp -a $ROOT/$i fs/$i + done + status + fi + eval_gettext "Installing \$PACKAGE... " + cp -a fs/* $ROOT/ + status + if [ -s files2remove.list ]; then + eval_gettext "Removing old \$PACKAGE... " + while read file; do + remove_with_path $ROOT$file + done < files2remove.list + true + status + fi + # Remove the temporary random directory. + gettext "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 + # Update-desktop-database if needed. + if [ "$(grep .desktop $ROOT$INSTALLED/$PACKAGE/files.list | grep /usr/share/applications/)" ]; then + updatedesktopdb=yes + fi + # Update-mime-database if needed. + if [ "$(grep /usr/share/mime $ROOT$INSTALLED/$PACKAGE/files.list)" ]; then + updatemimedb=yes + fi + cd $TOP_DIR + echo "================================================================================" + eval_gettext "\$PACKAGE (\$VERSION\$EXTRAVERSION) is installed."; echo + echo "" + # Log this activity + [ -n "$ROOT" ] || log Installed +} + +# 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 --quiet -i receipt > /dev/null 2>&1) < $PACKAGE_FILE + . $TMP_DIR/receipt + PACKAGE=$saved + rm -rf $TMP_DIR + for pkgorg in $DEPENDS + do + i=$(equivalent_pkg $pkgorg $1) + if [ ! -d "$1$INSTALLED/$i" ]; then + MISSING_PACKAGE=$i + deps=$(($deps+1)) + elif [ ! -f "$1$INSTALLED/$i/receipt" ]; then + eval_gettext "WARNING Dependency loop between \$PACKAGE and \$i."; echo + fi + done + if [ ! "$MISSING_PACKAGE" = "" ]; then + echo -e "\033[1m`gettext \"Tracking dependencies for :\"`\033[0m $PACKAGE" + echo "================================================================================" + for pkgorg in $DEPENDS + do + i=$(equivalent_pkg $pkgorg $1) + if [ ! -d "$1$INSTALLED/$i" ]; then + MISSING_PACKAGE=$i + eval_gettext "Missing: \$MISSING_PACKAGE"; echo + fi + done + echo "================================================================================" + eval_gettext "\$deps missing package(s) to install."; echo + fi +} + +# Install all missing deps. Auto install or 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" + if [ "$AUTO_INSTALL_DEPS" == "yes" ]; then + anser="y" + else + echo "" + gettext "Install all missing dependencies (y/N) ? "; read anser + echo "" + fi + if [ "$anser" == "y" ]; then + for pkgorg in $DEPENDS + do + pkg=$(equivalent_pkg $pkgorg $1) + 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. + found=0 + if [ -f "$list" ]; then + eval_gettext "Checking if \$pkg exists in local list... "; echo + mkdir $TMP_DIR + for i in $pkg-*.tazpkg; do + [ -f $i ] || continue + ( cd $TMP_DIR ; cpio --quiet -i receipt > /dev/null 2>&1) < $i + [ "$(. $TMP_DIR/receipt; echo $PACKAGE)" = "$pkg" ] || continue + if grep -q ^$(package_fullname_in_dir $TMP_DIR).tazpkg$ $list + then + found=1 + tazpkg install $i $root --list=$list + break + fi + done + rm -rf $TMP_DIR + fi + # Install deps from the mirror. + if [ $found -eq 0 ]; then + if [ ! -f "$LOCALSTATE/packages.list" ]; then + tazpkg recharge + fi + tazpkg get-install $pkg $root + fi + fi + done + else + echo "" + eval_gettext \ +"Leaving dependencies for \$PACKAGE unsolved. The package is installed but +will probably not work."; echo + echo "" + fi +} + +# xHTML packages list header. +xhtml_header() +{ + cat > $XHTML_LIST << _EOT_ + + + + Installed packages list + + + + + + + +
+ +
+ +

+_packages_ packages installed - List generated on : $DATE +

+ +_EOT_ +} + +# xHTML content with packages info. +xhtml_pkg_info() +{ + cat >> $XHTML_LIST << _EOT_ +

$PACKAGE

+
+Version    : $VERSION$EXTRAVERSION
+Short desc : $SHORT_DESC
+Web site   : $WEB_SITE
+
+ +_EOT_ +} + +# xHTML packages list footer. +xhtml_footer() +{ + cat >> $XHTML_LIST << _EOT_ +
+ + + +
+ + +_EOT_ +} + +# Search pattern in installed packages. +search_in_installed_packages() +{ + gettext "Installed packages"; echo + 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 + eval_gettext "0 installed packages found for : \$PATTERN"; echo + echo "" + else + echo "================================================================================" + eval_gettext "\$packages installed package(s) found for : \$PATTERN"; echo + echo "" + fi +} + +# Search in packages.list for available pkgs. +search_in_packages_list() +{ + gettext "Available packages name-version"; echo + echo "================================================================================" + packages=0 + for i in $LOCALSTATE/packages.list $LOCALSTATE/undigest/*/packages.list; do + grep -is "$PATTERN" $i + packages=$(($packages + `grep -is "$PATTERN" $i | wc -l`)) + done + if [ ! -f "$LOCALSTATE/packages.list" ]; then + echo "" + gettext \ +"No 'packages.list' found to check for mirrored packages. For more results, +please run 'tazpkg recharge' once as root before searching."; echo + echo "" + fi + if [ "$packages" = "0" ]; then + eval_gettext "0 available packages found for : \$PATTERN"; echo + echo "" + else + echo "================================================================================" + eval_gettext "\$packages available package(s) found for : \$PATTERN"; echo + echo "" + fi +} + +# search --mirror: Search in packages.txt for available pkgs and give more +# info than --list or default. +search_in_packages_txt() +{ + gettext "Matching packages name with version and desc"; echo + echo "================================================================================" + packages=0 + for i in $LOCALSTATE/packages.txt $LOCALSTATE/undigest/*/packages.txt; do + grep -is -A 2 "^$PATTERN" $i + packages=$(($packages + `grep -is "^$PATTERN" $i | wc -l`)) + done + if [ ! -f "$LOCALSTATE/packages.txt" ]; then + echo "" + gettext \ +"No 'packages.txt' found to check for mirrored packages. For more results, +please run 'tazpkg recharge' once as root before searching."; echo + echo "" + fi + if [ "$packages" = "0" ]; then + eval_gettext "0 available packages found for : \$PATTERN"; echo + echo "" + else + echo "================================================================================" + eval_gettext "\$packages available package(s) found for : \$PATTERN"; echo + 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 >/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 + eval_gettext "Can't find flavor \$FLAVOR. Aborting."; echo + fi + cd $TOP_DIR + rm -rf $TMP_DIR +} + +# Update mirror urls +setup_mirror() +{ + # Backup old list. + if [ -f "$1/mirror" ]; then + cp -f $1/mirror $1/mirror.bak + fi + echo "" + echo -e "\033[1m`gettext \"Current mirror(s)\"`\033[0m" + echo "================================================================================" + echo " `cat $1/mirror 2> /dev/null`" + gettext \ +"Please enter URL of the new mirror (http, ftp or local path). You must specify +the complete address to the directory of the packages and packages.list file."; echo + echo "" + gettext "New mirror(s) URL : " + NEW_MIRROR_URL=$2 + if [ -n "$NEW_MIRROR_URL" ]; then + echo $NEW_MIRROR_URL + else + read NEW_MIRROR_URL + fi + if [ "$NEW_MIRROR_URL" = "" ]; then + gettext "Nothing has been changed."; echo + else + eval_gettext "Setting mirror(s) to : $NEW_MIRROR_URL"; echo + rm -f $1/mirror + for i in $NEW_MIRROR_URL; do + echo "$i" >> $1/mirror + done + fi + echo "" +} + +# recursive dependencies scan +dep_scan() +{ +for i in $1; do + case " $ALL_DEPS " in + *\ $i\ *) continue;; + esac + ALL_DEPS="$ALL_DEPS $i" + [ -n "$2" ] && echo "$2$i ($(grep -A 3 $i $LOCALSTATE/packages.txt \ + | tail -1 | sed 's/.*(\([^ ]*\).*/\1/'))" + [ -f $i/receipt ] || continue + DEPENDS="" + . $i/receipt + [ -n "$DEPENDS" ] && dep_scan "$DEPENDS" "$2 " +done +} + +# recursive reverse dependencies scan +rdep_scan() +{ +SEARCH=$1 + +for i in * ; do + DEPENDS="" + . $i/receipt + echo "$i $(echo $DEPENDS)" +done | awk -v search=$SEARCH ' +function show_deps(deps, all_deps, pkg, space) +{ + if (all_deps[pkg] == 1) return + all_deps[pkg] = 1 + if (space != "") printf "%s %s\n",space,pkg + for (i = 1, n = split(deps[pkg], mydeps, " "); i <= n; i++) { + show_deps(deps, all_deps, mydeps[i],"==" space) + } +} + +{ + all_deps[$1] = 0 + for (i = 2; i <= NF; i++) + deps[$i] = deps[$i] " " $1 +} + +END { + show_deps(deps, all_deps, search, "") +} +' | while read spc pkg; do + echo -n $spc | sed 's/=/ /g' + echo -n $pkg + echo -n ' (' + grep -A 3 $pkg $LOCALSTATE/packages.txt | tail -1 | \ + sed 's/.*(\([^ ]*\).*/\1)/' +done +} + +# Check for ELF file +is_elf() +{ + [ "$(dd if=$1 bs=1 skip=1 count=3 2> /dev/null)" = "ELF" ] +} + +# Print shared library dependencies +ldd() +{ + LD_TRACE_LOADED_OBJECTS=1 /lib/ld*.so $1 2> /dev/null +} + +# search dependencies for files in $TMP_DIR/$file/fs +find_depends() +{ + DEFAULT_DEPENDS="glibc-base gcc-lib-base" + + [ -f /var/lib/tazpkg/files.list.lzma ] || tazpkg recharge > /dev/null + for i in /var/lib/tazpkg/files.list.lzma \ + /var/lib/tazpkg/undigest/*/files.list.lzma ; do + [ -f $i ] && lzma d $i -so >> $TMP_DIR/files.list + done + find $TMP_DIR/$file/fs -type f | while read chkfile ; do + is_elf $chkfile || continue + case "$chkfile" in + *.o|*.ko|*.ko.gz) continue;; + esac + ldd $chkfile | while read lib rem; do + case "$lib" in + statically|linux-gate.so*|ld-*.so|*/ld-*.so) + continue;; + esac + find $TMP_DIR/$file/fs | grep -q /$lib$ && continue + for dep in $(grep $lib files.list | cut -d: -f1); do + case " $DEFAULT_DEPENDS " in + *\ $dep\ *) continue 2;; + esac + grep -qs "^$dep$" $TMP_DIR/depends && continue 2 + done + if [ -n "$dep" ]; then + echo "$dep" >> $TMP_DIR/depends + else + grep -qs ^$lib$ $TMP_DIR/unresolved || + echo "$lib" >> $TMP_DIR/unresolved + fi + done + done + spc="" + cat $TMP_DIR/depends | sort | uniq | while read file; do + echo -n "$spc$file" + spc=" " + done +} + +show_unresolved_lib() +{ + if [ -s $TMP_DIR/unresolved ]; then + echo "BUGS=\"No dependency for" >> $1 + cat $TMP_DIR/unresolved | sort | uniq | while read file; do + echo -e "$WARNING: unknown dependency for $lib" + echo -n " $file" >> $1 + done + echo "\"" >> $1 + fi +} + +# convert a .ipk package to .tazpkg +convert_ipk() +{ + mkdir -p $TMP_DIR + tar xOzf $PACKAGE_FILE ./control.tar.gz | tar xzf - -C $TMP_DIR + package="$(grep ^Package $TMP_DIR/control | sed 's/.*: //')" + version="$(grep ^Version $TMP_DIR/control | sed 's/.*: //')" + maintainer="$(grep ^Maintainer $TMP_DIR/control | sed 's/.*: //')" + target="$(grep ^Architecture $TMP_DIR/control | sed 's/.*: //')" + descrip="$(grep ^Description $TMP_DIR/control | sed 's/.*: //')" + url="http://openwrt.org/" + case "$target" in + i386|all) + file=$package-$version + mkdir -p $TMP_DIR/$file/fs + tar xOzf $PACKAGE_FILE ./data.tar.gz | \ + tar xzf - -C $TMP_DIR/$file/fs + cd $TMP_DIR + cat > $file/receipt <> $file/receipt <> $file/receipt < $file/description.txt + sed -i 's/^\.$//' $file/description.txt + [ -s $file/description.txt ] || rm -f $file/description.txt + tazpkg pack $file + cd $TOP_DIR + mv $TMP_DIR/$file.tazpkg . + ;; + *) + gettext "Invalid target: $target (expected i386)"; echo + ;; + esac + rm -rf $TMP_DIR +} + +# convert a .pkg.tar.gz package to .tazpkg +convert_arch() +{ + mkdir -p $TMP_DIR/fs + tar xzf $PACKAGE_FILE -C $TMP_DIR/fs + if [ -f $TMP_DIR/fs/.PKGINFO ]; then + cd $TMP_DIR + package="$(grep ^pkgname fs/.PKGINFO | sed 's/.*= //')" + version="$(grep ^pkgver fs/.PKGINFO | sed 's/.*= //')" + descrip="$(grep ^pkgdesc fs/.PKGINFO | sed 's/.*= //')" + url="$(grep ^url fs/.PKGINFO | sed 's/.*= //')" + maintainer="$(grep ^packager fs/.PKGINFO | sed 's/.*= //')" + file=$package-$version + mkdir $file + mv fs $file + cat > $file/receipt < $file/receipt <> $file/receipt < $file/description.txt + [ -s $file/description.txt ] || rm -f $file/description.txt + rm -rf $file/fs/install + tazpkg pack $file + mv $file.tazpkg $TOP_DIR + else + eval_gettext "\$PACKAGE_FILE does not look like a Slackware package !"; echo + fi + cd $TOP_DIR + rm -rf $TMP_DIR +} + +# convert a .deb package to .tazpkg +convert_deb() +{ + mkdir -p $TMP_DIR + dpkg-deb -e $PACKAGE_FILE $TMP_DIR + package=$(grep '^ *Package' $TMP_DIR/control) + package=$(echo ${package##*:}) + version=$(grep '^ *Version' $TMP_DIR/control) + version=$(echo ${version##*:}) + descrip=$(grep '^ *Description' $TMP_DIR/control) + descrip=$(echo ${descrip##*:}) + target="$(grep ^Architecture $TMP_DIR/control | sed 's/.*: //')" + case "$target" in + i386|all) + file="$package-$version" + mkdir -p $TMP_DIR/$file/fs/ + dpkg-deb -x $PACKAGE_FILE $TMP_DIR/$file/fs + cd $TMP_DIR + cat > $file/receipt <> $file/receipt < $file/description.txt + sed -i 's/^\.$//' $file/description.txt + [ -s $file/description.txt ] || rm -f $file/description.txt + tazpkg pack $file + mv $file.tazpkg $TOP_DIR + ;; + *) + gettext "Invalid target: $target (expected i386)"; echo + ;; + esac + cd $TOP_DIR + rm -rf $TMP_DIR +} + +# convert a .rpm package to .tazpkg +convert_rpm() +{ + mkdir -p $TMP_DIR + cp $PACKAGE_FILE $TMP_DIR + PACKAGE_FILE=$TMP_DIR/$(basename $PACKAGE_FILE) + rpm -qip $PACKAGE_FILE | awk -v pkg=$(basename $PACKAGE_FILE) ' +BEGIN { + goturl=0; + printf "# Taz package receipt.\n"; + printf "# generated by tazpkg from rpm package %s\n",pkg; +} +{ + if (/^Name/) { name=$3; printf "PACKAGE=\"%s\"\n",$3; } + if (/^Version/) printf "VERSION=\"%s-",$3; + if (/^Release/) printf "%s\"\n",$3; + if (/^Summary/) printf "SHORT_DESC=\"%s\"\n",substr($0,15); + if (/^URL/) { goturl=1; printf "WEB_SITE=\"%s\"\n",$3; } +} +END { + if (goturl == 0) + printf "WEB_SITE=\"http://rpmfind.net/linux/rpm2html/search.php?query=%s\"\n",name; + printf "CATEGORY=\"misc\"\n"; + printf "MAINTAINER=\"nobody@slitaz.org\"\n"; +} +' > $TMP_DIR/receipt + . $TMP_DIR/receipt + file=$PACKAGE-$VERSION + mkdir -p $TMP_DIR/$file/fs/ + mv $TMP_DIR/receipt $TMP_DIR/$file + rpm -qip $PACKAGE_FILE | awk ' +DEGIN { show=0 } +{ + if (show) print; + if (/^Description/) show=1; +} +' > $TMP_DIR/$file/description.txt + cd $TMP_DIR/$file/fs/ + rpm2cpio $PACKAGE_FILE | cpio -idm + cd ../.. + echo "DEPENDS=\"$(find_depends)\"" >> $TMP_DIR/$file/receipt + show_unresolved_lib $TMP_DIR/$file/receipt + tazpkg pack $file + mv $file.tazpkg $TOP_DIR + cd $TOP_DIR + rm -rf $TMP_DIR +} + +update_desktop_database() +{ + if [ -f /usr/bin/update-desktop-database ] && [ -n "$updatedesktopdb" ]; then + update-desktop-database $1/usr/share/applications + fi +} + +update_mime_database() +{ + if [ -f /usr/bin/update-desktop-database ] && [ -n "$updatemimedb" ]; then + update-mime-database $1/usr/share/mime + fi +} + +################### +# Tazpkg commands # +################### + +case "$COMMAND" in + list) + # List all installed packages or a specific category. + # + if [ "$2" = "blocked" ]; then + echo "" + echo -e "\033[1m`gettext \"Blocked packages\"`\033[0m" + echo "================================================================================" + if [ -s "$BLOCKED" ];then + cat $BLOCKED + else + gettext "No blocked packages found." + fi + echo "" && exit 0 + fi + # Display the list of categories. + if [ "$2" = "cat" -o "$2" = "categories" ]; then + echo "" + echo -e "\033[1m`gettext \"Packages 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[1m`gettext \"Installed 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 "================================================================================" + eval_gettext "\$packages packages installed of category \$ASKED_CATEGORY."; echo + echo "" + else + # By default list all packages and versions. + echo "" + echo -e "\033[1m`gettext \"List 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 "================================================================================" + eval_gettext "\$packages packages installed."; echo + echo "" + fi ;; + xhtml-list) + # Get info 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[1m`gettext \"Creating xHTML list of installed packages\"`\033[0m" + echo "================================================================================" + gettext "Generating xHTML header..." + xhtml_header + status + # Packages + gettext "Creating packages information..." + for pkg in $INSTALLED/* + do + [ -f $pkg/receipt ] || continue + EXTRAVERSION="" + . $pkg/receipt + xhtml_pkg_info + packages=$(($packages+1)) + done + status + gettext "Generating xHTML footer..." + xhtml_footer + status + # sed pkgs nb in header. + sed -i s/'_packages_'/"$packages"/ $XHTML_LIST + echo "================================================================================" + eval_gettext "\$XHTML_LIST created - $packages packages."; echo + echo "" ;; + list-mirror) + # List all available packages on the mirror. Option --diff displays + # last mirrored packages diff (see recharge). + check_for_packages_list + case $2 in + --diff) + if [ -f "$LOCALSTATE/packages.diff" ]; then + echo "" + echo -e "\033[1m`gettext \"Mirrored packages diff\"`\033[0m" + echo "================================================================================" + cat $LOCALSTATE/packages.diff + echo "================================================================================" + pkgs=`cat $LOCALSTATE/packages.diff | wc -l` + eval_gettext "\$pkgs new packages listed on the mirror."; echo + echo "" + else + echo "" + gettext "Unable to list anything, no packages.diff found."; echo + gettext "Recharge your current list to create a first diff."; echo + echo "" + fi && exit 0 ;; + --text|--txt) + echo "" + echo -e "\033[1m`gettext \"List of available packages on the mirror\"`\033[0m" + echo "================================================================================" + cat $LOCALSTATE/packages.txt ;; + --raw|*) + echo "" + echo -e "\033[1m`gettext \"List of available packages on the mirror\"`\033[0m" + echo "================================================================================" + cat $LOCALSTATE/packages.list ;; + esac + echo "================================================================================" + pkgs=`cat $LOCALSTATE/packages.list | wc -l` + eval_gettext "\$pkgs packages in the last recharged list."; echo + echo "" ;; + list-files) + # List files installed with the package. + # + check_for_package_on_cmdline + check_for_receipt + echo "" + echo -e "\033[1m`gettext \"Installed 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[1m`gettext \"Tazpkg information\"`\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[1m`gettext \"Description of:\"`\033[0m $PACKAGE" + echo "================================================================================" + cat $INSTALLED/$PACKAGE/description.txt + echo "================================================================================" + echo "" + else + echo "" + gettext "Sorry, no description available for this package."; echo + echo "" + fi ;; + search) + # Search for a package by pattern or name. + # + PATTERN="$2" + if [ -z "$PATTERN" ]; then + echo "" + gettext "Please specify a pattern or package name to search for."; echo + gettext "Example : 'tazpkg search paint'"; echo + echo "" + exit 0 + fi + echo "" + echo -e "\033[1m`gettext \"Search 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 "" + gettext "Please specify a pattern or file name to search for."; echo + gettext "Example : 'tazpkg search-file libnss'"; echo + echo "" + exit 0 + fi + echo "" + echo -e "\033[1m`gettext \"Search result for file\"`\033[0m $2" + echo "================================================================================" + + if [ "$3" == "--mirror" ]; then + + match=0 + for i in $LOCALSTATE/files.list.lzma \ + $LOCALSTATE/undigest/*/files.list.lzma; do + [ -f $i ] || continue + unlzma -c $i | 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=$(($match + `unlzma -c $i | grep -- ".*:.*$2" | wc -l`)) + done + + 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[1m`gettext \"Package\"` $PACKAGE:\033[0m" + grep "$2" $pkg/files.list + files=`grep $2 $pkg/files.list | wc -l` + match=$(($match+$files)) + fi + done + + fi + pkg=$2 + if [ "$match" = "" ]; then + eval_gettext "0 file found for: \$pkg"; echo + echo "" + else + echo "" + echo "================================================================================" + eval_gettext "\$match file(s) found for: \$pkg"; echo + echo "" + fi ;; + search-pkgname) + # Search for a package name + if [ -z "$2" ]; then + echo "" + gettext "Please specify a pattern or file name to search for."; echo + gettext "Example : 'tazpkg search-pkgname libnss'"; echo + echo "" + exit 0 + fi + echo "" + echo -e "\033[1m`gettext \"Search result for file\"`\033[0m $2" + echo "================================================================================" + + # Search for a file on mirror and output only the package name + match=0 + for i in $LOCALSTATE/files.list.lzma \ + $LOCALSTATE/undigest/*/files.list.lzma; do + [ -f $i ] || continue + unlzma -c $i | grep -- ".*:.*$2" | cut -d: -f1 | uniq | awk '{ print $1 }' + match=$(($match + `unlzma -c $i | grep -- ".*:.*$2" | cut -d: -f1 | uniq | wc -l`)) + done + file=$2 + if [ "$match" = "" ]; then + eval_gettext "0 file found for : \$file"; echo + echo "" + else + echo "" + echo "================================================================================" + eval_gettext "$match pkg(s) found with file: \$file"; echo + 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 + update_desktop_database $ROOT + update_mime_database $ROOT ;; + install-list|get-install-list) + # Install a set of packages from a list. + # + check_root + if [ -z "$2" ]; then + echo "" + gettext \ +"Please change directory (cd) to the packages repository and specify the +list of packages to install. Example : tazpkg install-list packages.list" + echo "" && exit 0 + fi + # Check if the packages list exist. + list_file=$2 + if [ ! -f "$list_file" ]; then + gettext "Unable to find : $list_file"; echo + 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 + + # Upgrade tazpkg first. It may handle new features/formats... + # then upgrade essential packages early + for pkg in busybox-pam busybox gcc-lib-base glibc-base \ + slitaz-base-files tazpkg ; do + pkg=$(egrep $pkg-[0-9] $INSTALL_LIST) + [ -n "$pkg" ] || continue + echo "Adding implicit depends $pkg ..." + LIST="$pkg +$LIST" + done + + 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 "" + gettext "Please specify the release you want on the command line."; echo + gettext "Example: tazpkg set-release cooking"; echo + echo "" + exit 0 + fi + rm /var/lib/tazpkg/mirror + echo "$RELEASE" > /etc/slitaz-release + tazpkg recharge && tazpkg upgrade + + # Install missing depends + cd $INSTALLED + for i in * ; do + DEPENDS="" + . $i/receipt + for j in $DEPENDS ; do + [ -d $j ] || tazpkg get-install $j + done + done ;; + remove) + # Remove packages. + # + check_root + check_for_package_on_cmdline + ROOT="" + while [ -n "$3" ]; do + case "$3" in + --root=*) + ROOT="${3#--root=}" + if [ "$ROOT" ]; then + ROOTOPTS="--root=$ROOT" + else + ROOTOPTS="" + fi + ;; + *) shift 2 + echo -e "\nUnknown option $*.\n" + exit 1 + ;; + esac + shift + done + if [ ! -f "$ROOT$INSTALLED/$PACKAGE/receipt" ]; then + echo "" + eval_gettext "\$PACKAGE is not installed."; echo + exit 0 + else + ALTERED="" + THE_PACKAGE=$PACKAGE # altered by receipt + for i in $(cd $ROOT$INSTALLED ; ls); do + [ -f $ROOT$INSTALLED/$i/receipt ] || continue + DEPENDS="" + . $ROOT$INSTALLED/$i/receipt + case " $(echo $DEPENDS) " in + *\ $THE_PACKAGE\ *) ALTERED="$ALTERED $i";; + esac + done + EXTRAVERSION="" + . $ROOT$INSTALLED/$THE_PACKAGE/receipt + fi + echo "" + if [ -n "$ALTERED" ]; then + eval_gettext "The following packages depend on \$PACKAGE:"; echo + for i in $ALTERED; do + echo " $i" + done + fi + REFRESH=$(cd $ROOT$INSTALLED ; grep -sl ^$PACKAGE$ */modifiers) + if [ -n "$REFRESH" ]; then + eval_gettext "The following packages have been modified by \$PACKAGE:"; echo + for i in $REFRESH; do + echo " ${i%/modifiers}" + done + fi + eval_gettext "Remove \$PACKAGE (\$VERSION\$EXTRAVERSION) ?"; echo + gettext "Please confirm uninstallation (y/N) : "; read anser + if [ "$anser" = "y" ]; then + echo "" + echo -e "\033[1m`gettext \"Removing:\"`\033[0m $PACKAGE" + echo "================================================================================" + # Pre remove commands. + if grep -q ^pre_remove $ROOT$INSTALLED/$PACKAGE/receipt; then + pre_remove + fi + gettext "Removing all files installed..." + if [ -f $ROOT$INSTALLED/$PACKAGE/modifiers ]; then + for mod in `cat $ROOT$INSTALLED/$PACKAGE/modifiers` + do + for file in `cat $ROOT$INSTALLED/$PACKAGE/files.list` + do + [ $(grep "^$(echo $file | grepesc)$" $ROOT$INSTALLED/$mod/files.list | wc -l) -gt 1 ] && continue + remove_with_path $ROOT$file + done + done + else + for file in `cat $ROOT$INSTALLED/$PACKAGE/files.list` + do + remove_with_path $ROOT$file + done + fi + status + if grep -q ^post_remove $ROOT$INSTALLED/$PACKAGE/receipt; then + post_remove + fi + # Remove package receipt. + gettext "Removing package receipt..." + rm -rf $ROOT$INSTALLED/$PACKAGE + status + sed -i "/ $PACKAGE-$VERSION$EXTRAVERSION$/d" \ + $LOCALSTATE/installed.md5 2> /dev/null + # Log this activity + log Removed + if [ -n "$ALTERED" ]; then + eval_gettext "Remove packages depending on \$PACKAGE" + echo -n " (y/N) ? "; read anser + if [ "$anser" = "y" ]; then + for i in $ALTERED; do + if [ -d "$ROOT$INSTALLED/$i" ]; then + tazpkg remove $i $ROOTOPTS + fi + done + fi + fi + if [ -n "$REFRESH" ]; then + eval_gettext "Reinstall packages modified by \$PACKAGE" + echo -n " (y/N) ? "; read anser + if [ "$anser" = "y" ]; then + for i in $REFRESH; do + if [ $(wc -l < $ROOT$INSTALLED/$i) -gt 1 ]; then + eval_gettext "Check \$INSTALLED/\$i for reinstallation"; echo + continue + fi + rm -r $ROOT$INSTALLED/$i + tazpkg get-install ${i%/modifiers} $ROOTOPTS --forced + done + fi + fi + else + echo "" + eval_gettext "Uninstallation of \$PACKAGE cancelled."; echo + fi + echo "" ;; + extract) + # Extract .tazpkg cpio archive into a directory. + # + check_for_package_on_cmdline + check_for_package_file + echo "" + echo -e "\033[1m`gettext \"Extracting:\"`\033[0m $PACKAGE" + echo "================================================================================" + # If no directory destination is found on the cmdline + # we create 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 + gettext "Copying original package..." + cp $PACKAGE_FILE $DESTDIR + status + cd $DESTDIR + extract_package + echo "================================================================================" + eval_gettext "\$PACKAGE is extracted to: \$DESTDIR"; echo + echo "" ;; + recompress) + # Recompress .tazpkg cpio archive with lzma. + # + check_for_package_on_cmdline + check_for_package_file + echo "" + echo -e "\033[1m`gettext \"Recompressing:\"`\033[0m $PACKAGE" + echo "================================================================================" + mkdir -p $TMP_DIR + gettext "Copying original package..." + cp $PACKAGE_FILE $TMP_DIR + status + cd $TMP_DIR + extract_package + gettext "Recompressing the fs... " + find fs | cpio -o -H newc 2> /dev/null | lzma e fs.cpio.lzma -si + rm -rf fs + status + gettext "Creating new package... " + find . -print | cpio -o -H newc > \ + $TOP_DIR/$(basename $PACKAGE_FILE).$$ && mv -f \ + $TOP_DIR/$(basename $PACKAGE_FILE).$$ \ + $TOP_DIR/$(basename $PACKAGE_FILE) + status + cd $TOP_DIR + rm -rf $TMP_DIR ;; + list-config) + # List configuration files installed. + # + if [ "$2" = "--box" ]; then + mkdir -p $TMP_DIR && cd $TMP_DIR + FILES="$INSTALLED/*/volatile.cpio.gz" + [ -n "$3" ] && FILES="$INSTALLED/$3/volatile.cpio.gz" + for i in $FILES; do + zcat $i | cpio -idm > /dev/null + find * -type f 2>/dev/null | while read file; do + if [ ! -e /$file ]; then + echo -n "|--|--|--|File lost" + else + echo -n "$(stat -c "%A|%U|%G|%s|" /$file)" + cmp $file /$file > /dev/null 2>&1 || \ + echo -n "$(stat -c "%.16y" /$file)" + fi + echo "|/$file" + done + rm -rf * + done + cd $TOP_DIR + rm -rf $TMP_DIR + else + echo "" + echo -e "\033[1m`gettext \"Configuration files\"`" + echo "================================================================================" + for i in $INSTALLED/*/volatile.cpio.gz; do + [ -n "$2" -a "$i" != "$INSTALLED/$2/volatile.cpio.gz" ] && continue + [ -f "$i" ] || continue + zcat $i | cpio -t | grep -v "[0-9]* blocks" + done | sed 's|^|/|' | sort + echo "================================================================================" + echo "" + fi ;; + repack-config) + # Create SliTaz package archive from configuration files. + # + mkdir -p $TMP_DIR && cd $TMP_DIR + CONFIG_VERSION=1.0 + mkdir config-$CONFIG_VERSION + cd config-$CONFIG_VERSION + for i in $INSTALLED/*/volatile.cpio.gz; do + zcat $i | cpio -t | grep -v "[0-9]* blocks" + done > files.list + mkdir fs + cd fs + ( cd / ; cpio -o -H newc ) < ../files.list | cpio -idm > /dev/null + mkdir -p etc/tazlito + for i in $INSTALLED/*/receipt; do + EXTRAVERSION="" + . $i + echo "$PACKAGE-$VERSION$EXTRAVERSION" + done > etc/tazlito/config-packages.list + cd .. + echo "etc/tazlito/config-packages.list" >> files.list + cat > receipt </dev/null |\ + ( cd tmp ; cpio -idm >/dev/null ) + mv tmp/rootfs fs + if [ -f $INSTALLED/$PACKAGE/volatile.cpio.gz ]; then + zcat $INSTALLED/$PACKAGE/volatile.cpio.gz | \ + ( cd fs; cpio -idm ) + fi + 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 | \ + md5sum -s -c || { + echo "Can't repack, md5sum error." + cd $TOP_DIR + rm -rf $TMP_DIR + exit 1 + } + fi + find fs | cpio -o -H newc 2> /dev/null | lzma e fs.cpio.lzma -si + echo -e "$FILES" | cpio -o -H newc 2> /dev/null > \ + $TOP_DIR/$PACKAGE-$VERSION$EXTRAVERSION.tazpkg + cd $TOP_DIR + \rm -R $TMP_DIR + eval_gettext "Package \$PACKAGE repacked successfully."; echo + echo "Size : `du -sh $PACKAGE-$VERSION$EXTRAVERSION.tazpkg`" + echo "" ;; + pack) + # Create SliTaz package archive using cpio and gzip. + # + check_for_package_on_cmdline + cd $PACKAGE + if [ ! -f "receipt" ]; then + gettext "Receipt is missing. Please read the documentation."; echo + exit 0 + else + echo "" + echo -e "\033[1mPacking :\033[0m $PACKAGE" + echo "================================================================================" + # Create files.list with redirecting find outpout. + gettext "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 + gettext "Creating md5sum of files..." + while read file; do + [ -L "fs$file" ] && continue + [ -f "fs$file" ] || continue + case "$file" in + /lib/modules/*/modules.*|*.pyc) continue;; + esac + md5sum "fs$file" | sed 's/ fs/ /' + done < files.list > md5sum + status + UNPACKED_SIZE=$(du -chs fs receipt files.list md5sum \ + description.txt 2> /dev/null | awk \ + '{ sz=$1 } END { print sz }') + # Build cpio archives. + gettext "Compressing the fs... " + find fs | cpio -o -H newc | lzma e fs.cpio.lzma -si + rm -rf fs + status + PACKED_SIZE=$(du -chs fs.cpio.lzma receipt files.list \ + md5sum description.txt 2> /dev/null | awk \ + '{ sz=$1 } END { print sz }') + gettext "Updating receipt sizes..." + sed -i s/^PACKED_SIZE.*$// receipt + sed -i s/^UNPACKED_SIZE.*$// receipt + sed -i "s/^PACKAGE=/PACKED_SIZE=\"$PACKED_SIZE\"\nUNPACKED_SIZE=\"$UNPACKED_SIZE\"\nPACKAGE=/" receipt + status + gettext "Creating full cpio archive... " + find . -print | cpio -o -H newc > ../$PACKAGE.tazpkg + status + gettext "Restoring original package tree... " + unlzma -c fs.cpio.lzma | cpio -idm + status + rm fs.cpio.lzma && cd .. + echo "================================================================================" + eval_gettext "Package \$PACKAGE compressed successfully."; echo + echo "Size : `du -sh $PACKAGE.tazpkg`" + echo "" + fi ;; + recharge) + # Recharge packages.list from a mirror. + # + check_root + for path in $LOCALSTATE $LOCALSTATE/undigest/*; do + [ -f $path/mirror ] || continue + echo "" + if [ "$path" != "$LOCALSTATE" ]; then + echo "Recharging undigest $(basename $path):" + fi + cd $path + if [ -f "packages.list" ]; then + gettext "Creating backup of the last packages list..." + mv -f packages.desc packages.desc.bak 2>/dev/null + mv -f packages.md5 packages.md5.txt 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 packages.equiv packages.equiv.bak 2>/dev/null + mv -f files.list.lzma files.list.lzma.bak 2> /dev/null + mv -f mirrors mirrors.bak 2> /dev/null + status + fi + download_from "$(cat mirror)" packages.desc + download_from "$(cat mirror)" packages.md5 + download_from "$(cat mirror)" packages.txt + download_from "$(cat mirror)" packages.list + download_from "$(cat mirror)" packages.equiv + download_from "$(cat mirror)" files.list.lzma + download_from "$(sed 's|packages/.*||' < mirror)" mirrors + [ -f mirrors ] || mv mirrors.bak mirrors 2> /dev/null + suffix=$(head -1 mirror) + suffix=packages${suffix#*/packages} + for i in $(cat mirrors 2> /dev/null); do + grep -qs $i mirror || echo $i$suffix >> mirror + done + if [ -f "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[1m`gettext \"Mirrored packages diff\"`\033[0m" + echo "================================================================================" + cat packages.diff + new_pkgs=`cat packages.diff | wc -l` + if [ "$new_pkgs" != 0 ]; then + echo "================================================================================" + eval_gettext "\$new_pkgs new packages on the mirror."; echo + echo "" + else + gettext "No new packages on the mirror."; echo + echo "" + fi + else + echo -e " +================================================================================" + gettext \ +"Last packages.list is ready to use. Note that next time you recharge the +list, a list of differences will be displayed to show new and upgradeable +packages." + echo "" + fi + done ;; + upgradeable) + # Build upgradeable-packages.list quickly. + # + check_root + cd $LOCALSTATE + while read md5 file ; do + grep -qs "$md5 $file" packages.md5 && continue + for i in 1 2 3 4 5; do + file=${file%-*} + [ -d installed/$file ] || continue + echo $file + break + done + done < installed.md5 > upgradeable-packages.list ;; + 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 upgradeable-packages.list + echo "" + echo -e "\033[1m`gettext \"Available upgrades\"`\033[0m" + echo "================================================================================" + echo "" + # Some packages must be installed first + FIRST_CLASS_PACKAGE=" glibc-base slitaz-base-files slitaz-boot-scripts " + if [ -n "$PACKAGE_FILE" -a -d "$INSTALLED/$PACKAGE_FILE" ]; then + ALL=$INSTALLED/$PACKAGE_FILE + else + ALL="$(ls -d $INSTALLED/*)" + fi + for pkg in $ALL + do + [ -f $pkg/receipt ] || continue + EXTRAVERSION="" + . $pkg/receipt + # Display 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 -qs "^$PACKAGE" $BLOCKED; then + blocked=$(($blocked+1)) + else + # Check if the installed package is in the current list (other + # mirror or local). + NEW_PACKAGE=$(get_package_filename $PACKAGE) + + if [ -n "$NEW_PACKAGE" ]; then + # Set new pkg and version for future comparison + 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. Upgrades are only available for official + # packages, so we control the mirror and it should be ok if + # we just check for equality. + RELEASE="" + if [ -f installed.md5 -a -f packages.md5 ]; then + current_md5=$(grep -s " $PACKAGE-$VERSION" installed.md5 | awk '{ print $1 }') + new_md5=$(grep -hs " $PACKAGE-$VERSION" packages.md5 undigest/*/packages.md5 | head -1 | awk '{ print $1 }') + [ -n "$current_md5" ] && [ -n "$new_md5" ] && + [ "$current_md5" != "$new_md5" ] && RELEASE=build + fi + if [ "$VERSION" != "$NEW_VERSION" -o -n "$RELEASE" ]; 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" ] 2> /dev/null; then + RELEASE=minor + fi + if [ "$NEW_MINOR" -lt "$PKG_MINOR" ] 2> /dev/null; then + RELEASE=$WARNING + FIXE=yes + fi + # Major + if [ "$NEW_MAJOR" -gt "$PKG_MAJOR" ] 2> /dev/null; then + RELEASE=major + FIXE="" + fi + if [ "$NEW_MAJOR" -lt "$PKG_MAJOR" ] 2> /dev/null; 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" >> upgradeable-packages.list + case "$FIRST_CLASS_PACKAGE" in + *\ $PACKAGE\ *) echo "$PACKAGE" >> upgradeable-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 "================================================================================" + eval_gettext "\$packages installed and listed packages to consider, \$up to upgrade, \$blocked blocked."; echo + echo "" + else + echo -e "\\033[0G`gettext \"System is up-to-date.\"` " + echo "" + echo "================================================================================" + eval_gettext "\$packages installed and listed packages to consider, 0 to upgrade, \$blocked blocked."; echo + echo "" + exit 0 + fi + # What to do if major or minor version is smaller. + if [ "$FIXE" == "yes" ]; then + gettext \ +"WARNING ---> Installed package seems more recent than the mirrored +one. You can block packages using the command : 'tazpkg block package'. +Or upgrade packages at your own risk." + echo "" + fi + # Ask for upgrade, it can be done another time. + echo -n "Upgrade now (y/N) ? "; read anser + if [ ! "$anser" = "y" ]; then + echo "" + gettext "Exiting. No package upgraded."; echo + echo "" + exit 0 + fi + # If anser is yes (y). Install all new versions. + cat upgradeable-packages.list >> upgradeable-packages.list$$ + mv -f upgradeable-packages.list$$ upgradeable-packages.list + yes y | tazpkg get-install-list upgradeable-packages.list --forced + rm -f upgradeable-packages.list + ;; + bugs) + # Show known bugs in package(s) + # + cd $INSTALLED + shift + LIST=$@ + [ -n "$LIST" ] || LIST=`ls` + MSG=`gettext "No known bugs."` + for PACKAGE in $LIST; do + BUGS="" + EXTRAVERSION="" + . $PACKAGE/receipt + if [ -n "$BUGS" ]; then + MSG=`gettext "Bug list completed"` + echo "" + eval_gettext "Bugs in package \$PACKAGE version \$VERSION\$EXTRAVERSION:"; echo + cat < /dev/null | \ + grep -v OK$ | sed 's/FAILED$/MD5SUM MISMATCH/' + done + FILES=" " + for file in $(cat */files.list); do + [ -d "$file" ] && continue + case "$FILES" in *\ $file\ *) continue;; esac + [ $(grep "^$(echo $file | grepesc)$" */files.list 2> /dev/null | \ + wc -l) -gt 1 ] || continue + FILES="$FILES$file " + echo "The following packages provide $file :" + grep -l "^$(echo $file | grepesc)$" */files.list | while read f + do + pkg=${f%/files.list} + echo -n " $pkg" + if [ -f $pkg/modifiers ]; then + echo -n " (overridden by $(echo "$(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 2> /dev/null | while read file; do + case "$file" in *\[*) continue;; esac + grep -q "^$(echo $file | grepesc)$" */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 -qs "^$PACKAGE" $BLOCKED; then + eval_gettext "\$PACKAGE is already in the blocked packages list."; echo + echo "" + exit 0 + else + eval_gettext "Add \$PACKAGE to : \$BLOCKED..." + echo $PACKAGE >> $BLOCKED + status + # Log this activity + . $INSTALLED/$PACKAGE/receipt + log Blocked + fi + echo "" ;; + unblock) + # Remove a pkg name from the list of blocked packages. + # + check_root + check_for_package_on_cmdline + echo "" + if grep -qs "^$PACKAGE" $BLOCKED; then + eval_gettext "Removing \$PACKAGE from : \$BLOCKED..." + sed -i s/$PACKAGE/''/ $BLOCKED + sed -i '/^$/d' $BLOCKED + status + # Log this activity + . $INSTALLED/$PACKAGE/receipt + log Unblocked + else + eval_gettext "\$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 + 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 + AUTOEXEC="no" + if ! check_for_package_in_list check; then + PACKAGE=get-$PACKAGE + AUTOEXEC=$PACKAGE + check_for_package_in_list + if [ -n "$(get_installed_package_pathname $PACKAGE $ROOT)" ]; then + $AUTOEXEC $ROOT + exit 0 + fi + fi + # 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 || { + eval_gettext "Continuing \$PACKAGE download"; echo + download $PACKAGE.tazpkg + } + if [ "$(md5sum $PACKAGE.tazpkg)" != "$(grep " $PACKAGE.tazpkg$" /var/lib/tazpkg/packages.md5)" ]; then + rm -f $PACKAGE.tazpkg + download $PACKAGE.tazpkg + fi + else + echo "" + download $PACKAGE.tazpkg + fi + PACKAGE_FILE=$CACHE_DIR/$PACKAGE.tazpkg + install_package $ROOT + [ "$AUTOEXEC" != "no" ] && $PACKAGE $ROOT + update_desktop_database $ROOT + update_mime_database $ROOT ;; + clean-cache) + # Remove all downloaded packages. + # + check_root + files=`ls -1 $CACHE_DIR | wc -l` + echo "" + echo -e "\033[1m`gettext \"Clean cache:\"`\033[0m $CACHE_DIR" + echo "================================================================================" + gettext "Cleaning cache directory..." + rm -rf $CACHE_DIR/* + status + echo "================================================================================" + eval_gettext "\$files file(s) removed from cache."; echo + echo "" ;; + list-undigest) + # list undigest URLs. + # + if [ "$2" = "--box" ]; then + for i in $LOCALSTATE/undigest/*/mirror; do + [ -f $i ] || continue + echo "$(basename $(dirname $i))|$(cat $i)" + done + else + echo "" + echo -e "\033[1m`gettext \"Current undigest(s)\"`\033[0m" + echo "================================================================================" + for i in $LOCALSTATE/undigest/*/mirror; do + if [ ! -f $i ]; then + gettext "No undigest mirror found."; echo + exit 1 + fi + echo "$(basename $(dirname $i)) $(cat $i)" + done + echo "" + fi ;; + remove-undigest) + # remove undigest URL. + # + check_root + if [ -d $LOCALSTATE/undigest/$2 ]; then + echo -n "Remove $2 undigest (y/N) ? "; read anser + if [ "$anser" = "y" ]; then + echo -n "Removing $2 undigest..." + rm -rf $LOCALSTATE/undigest/$2 + status + rmdir $LOCALSTATE/undigest 2> /dev/null + fi + else + echo "Undigest $2 not found" + fi ;; + add-undigest|setup-undigest) + # Add undigest URL. + # + check_root + undigest=$2 + [ -d $LOCALSTATE/undigest ] || mkdir $LOCALSTATE/undigest + if [ -z "$undigest" ]; then + i=1 + while [ -d $LOCALSTATE/undigest/$i ]; do + i=$(($i+1)) + done + undigest=$i + fi + if [ ! -d $LOCALSTATE/undigest/$undigest ]; then + eval_gettext "Creating new undigest \$undigest."; echo + mkdir $LOCALSTATE/undigest/$undigest + fi + setup_mirror $LOCALSTATE/undigest/$undigest $3 ;; + setup-mirror) + # Change mirror URL. + # + check_root + setup_mirror $LOCALSTATE $2 ;; + reconfigure) + # Replay post_install from receipt + # + check_for_package_on_cmdline + check_root + ROOT="" + while [ -n "$3" ]; do + case "$3" in + --root=*) + ROOT="${3#--root=}/" ;; + *) shift 2 + echo -e "\nUnknown option $*.\n" + exit 1 ;; + esac + shift + done + if [ -d "$ROOT$INSTALLED/$PACKAGE" ]; then + check_for_receipt $ROOT + # Check for post_install + if grep -q ^post_install $ROOT$INSTALLED/$PACKAGE/receipt; then + . $ROOT$INSTALLED/$PACKAGE/receipt + post_install $ROOT + # Log this activity + [ -n "$ROOT" ] || log Reconfigured + else + echo "" + eval_gettext "Nothing to do for \$PACKAGE."; echo + fi + else + echo "" + eval_gettext "Package \$PACKAGE is not installed."; echo + gettext "Install package with 'tazpkg install' or 'tazpkg get-install'"; echo + echo "" + 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 "================================================================================" + gettext "Type 'usage' to list all available commands or 'quit' or 'q' to exit."; echo + echo "" + fi + while true + do + echo -en "$PROMPT"; read cmd + case $cmd in + q|quit) + break ;; + shell) + gettext "You are already running a Tazpkg SHell."; echo ;; + su) + su -c 'exec tazpkg shell --noheader' && break ;; + "") + continue ;; + *) + tazpkg $cmd ;; + esac + done ;; + depends) + # Display dependencies tree + cd $INSTALLED + ALL_DEPS="" + if [ -f $2/receipt ]; then + dep_scan $2 "" + fi ;; + rdepends) + # Display reverse dependencies tree + cd $INSTALLED + ALL_DEPS="" + if [ -f $2/receipt ]; then + rdep_scan $2 + fi ;; + convert) + # convert misc package format to .tazpkg + check_for_package_file + case "$PACKAGE_FILE" in + *.deb|*.udeb) + convert_deb;; + *.rpm) + convert_rpm;; + *.tgz) + convert_tgz;; + *.pkg.tar.gz) + convert_arch;; + *.ipk|*.opk) + convert_ipk;; + *) + gettext "Unsupported format"; echo ;; + esac ;; + link) + # link a package from another slitaz installation + PACKAGE=$2 + if [ ! -d "$TARGET_DIR" -o \ + ! -d "$TARGET_DIR$INSTALLED/$PACKAGE" ]; then + cat <