--- bin/makepkg	2011-08-10 19:37:37.000000000 +0300
+++ local/bin/makepkg4	2011-08-10 19:41:15.000000000 +0300
@@ -44,7 +44,7 @@
 srcdir="$startdir/src"
 pkgdir="$startdir/pkg"
 
-packaging_options=('strip' 'docs' 'libtool' 'emptydirs' 'zipman' 'purge')
+packaging_options=('strip' 'splitdbg' 'docs' 'libtool' 'emptydirs' 'zipman' 'purge')
 other_options=('ccache' 'distcc' 'buildflags' 'makeflags')
 splitpkg_overrides=('pkgver' 'pkgrel' 'pkgdesc' 'arch' 'license' 'groups' \
                     'depends' 'optdepends' 'provides' 'conflicts' 'replaces' \
@@ -74,6 +74,8 @@
 CHECKFUNC=0
 PKGFUNC=0
 SPLITPKG=0
+SPLIT_DBG=0
+SKIP_DEBUG_PACKAGE=0
 PKGLIST=()
 
 # Forces the pkgver of the current PKGBUILD. Used by the fakeroot call
@@ -902,21 +904,49 @@
 		done
 	fi
 
+	local is_splitdbg
+	[ "$(check_option splitdbg)" = "y" ] || (( SPLIT_DBG )) && is_splitdbg=1
+	(( is_splitdbg )) && backup_package_variables "dbg"
+
+	local dbgdir="$pkgdir-dbg"
 	if [[ $(check_option strip) = y ]]; then
 		msg2 "$(gettext "Stripping unneeded symbols from binaries and libraries...")"
 		# make sure library stripping variables are defined to prevent excess stripping
 		[[ -z ${STRIP_SHARED+x} ]] && STRIP_SHARED="-S"
 		[[ -z ${STRIP_STATIC+x} ]] && STRIP_STATIC="-S"
-		local binary
+		local binary hardlink strip_opt
 		find . -type f -perm -u+w 2>/dev/null | while read binary ; do
 			case "$(file -bi "$binary")" in
 				*application/x-sharedlib*)  # Libraries (.so)
-					/usr/bin/strip $STRIP_SHARED "$binary";;
+					strip_opt=$STRIP_SHARED;;
 				*application/x-archive*)    # Libraries (.a)
-					/usr/bin/strip $STRIP_STATIC "$binary";;
+					strip_opt=$STRIP_STATIC;;
 				*application/x-executable*) # Binaries
-					/usr/bin/strip $STRIP_BINARIES "$binary";;
+					strip_opt=$STRIP_BINARIES;;
+				*) continue ;;
 			esac
+			# Strip symbols
+			if (( is_splitdbg )); then
+				# Create directory for the symbol file
+				mkdir -p "${dbgdir}/usr/lib/debug/${binary%/*}"
+				if readelf -S $binary | grep "\.gnu_debuglink" &>/dev/null; then
+					# An already stripped binary is a hard link
+					find ${STRIP_DIRS[@]} -samefile "$binary" 2>/dev/null | while read hardlink ; do
+						# Is the symbol file for the hardlink in the right dir ?
+						[ -e "${dbgdir}/usr/lib/debug/${hardlink#/}.debug" ] && \
+						[ "${hardlink%/*}" != "${binary%/*}" ] && \
+							ln "${dbgdir}/usr/lib/debug/${hardlink#/}.debug" "${dbgdir}/usr/lib/debug/${binary%/*}" && break
+					done
+				else
+					# Strip the file
+					/usr/bin/objcopy --only-keep-debug "$binary" "${dbgdir}/usr/lib/debug/${binary#/}.debug"
+					/usr/bin/strip $strip_opts "$binary"
+					/usr/bin/objcopy --add-gnu-debuglink="${dbgdir}/usr/lib/debug/${binary#/}.debug" "$binary"
+					chmod 644 "${dbgdir}/usr/lib/debug/${binary#/}.debug"
+				fi
+			else
+				/usr/bin/strip $strip_opts "$binary"
+			fi
 		done
 	fi
 
@@ -1008,6 +1038,12 @@
 }
 
 create_package() {
+	if (( SKIP_DEBUG_PACKAGE )); then
+		warning "$(gettext "No .debug files for debug package found, skipping...")"
+		SKIP_DEBUG_PACKAGE=0
+		return
+	fi
+
 	if [[ ! -d $pkgdir ]]; then
 		error "$(gettext "Missing pkg/ directory.")"
 		plain "$(gettext "Aborting...")"
@@ -1096,6 +1132,38 @@
 	fi
 }
 
+add_split_debug_packages(){
+	[ ${#pkgname[@]} = 1 ] && eval "function package_${pkgname}() { package;}"
+
+	local pkg pkgname_dbg
+	for pkg in ${pkgname[@]}
+	do
+		pkgname_dbg=( ${pkgname_dbg[@]} ${pkg} ${pkg/%/-dbg} )
+		eval "function package_${pkg}-dbg() { package_dbg; }"
+	done
+	pkgname=( ${pkgname_dbg[@]} )
+}
+
+package_dbg(){
+	check_dbg_files=`find $pkgdir/ -name "*.debug"`
+	if [ -z "$check_dbg_files" ]; then
+		SKIP_DEBUG_PACKAGE=1
+		return
+	fi
+
+	restore_package_variables "dbg"
+	pkgdesc="$pkgdesc (debugging symbols)"
+	depends=("${pkgname%-dbg}=$pkgver-$pkgrel")
+	groups=('debug' ${groups[@]/%/-debug})
+	optdepends=()
+	replaces=()
+	provides=()
+	conflicts=()
+	backup=()
+	options=(!strip !splitdbg docs !zipman !purge libtool !emptydirs)
+	unset install
+}
+
 create_srcpackage() {
 	cd "$startdir"
 
@@ -1423,17 +1491,19 @@
 }
 
 backup_package_variables() {
-	local var
+	local var suffix
+	suffix=$1
 	for var in ${splitpkg_overrides[@]}; do
-		local indirect="${var}_backup"
+		local indirect="${var}_backup${suffix}"
 		eval "${indirect}=(\"\${$var[@]}\")"
 	done
 }
 
 restore_package_variables() {
-	local var
+	local var suffix
+	suffix=$1
 	for var in ${splitpkg_overrides[@]}; do
-		local indirect="${var}_backup"
+		local indirect="${var}_backup${suffix}"
 		if [[ -n ${!indirect} ]]; then
 			eval "${var}=(\"\${$indirect[@]}\")"
 		else
@@ -1582,6 +1652,7 @@
 	echo "$(gettext "  -r, --rmdeps     Remove installed dependencies after a successful build")"
 	echo "$(gettext "  -R, --repackage  Repackage contents of the package without rebuilding")"
 	echo "$(gettext "  -s, --syncdeps   Install missing dependencies with pacman")"
+	echo "$(gettext "  -t, --splitdbg   Split debugging symbols into separate package")"
 	echo "$(gettext "  --allsource      Generate a source-only tarball including downloaded sources")"
 	echo "$(gettext "  --asroot         Allow makepkg to run as root user")"
 	printf "$(gettext "  --check          Run the check() function in the %s")\n" "$BUILDSCRIPT"
@@ -1622,11 +1693,11 @@
 ARGLIST=("$@")
 
 # Parse Command Line Options.
-OPT_SHORT="AcCdefFghiLmop:rRsV"
+OPT_SHORT="AcCdefFghiLmop:rRstV"
 OPT_LONG="allsource,asroot,ignorearch,check,clean,cleancache,nodeps"
 OPT_LONG+=",noextract,force,forcever:,geninteg,help,holdver"
 OPT_LONG+=",install,log,nocolor,nobuild,nocheck,pkg:,rmdeps"
-OPT_LONG+=",repackage,skipinteg,source,syncdeps,version,config:"
+OPT_LONG+=",repackage,skipinteg,source,syncdeps,splitdbg,version,config:"
 # Pacman Options
 OPT_LONG+=",noconfirm,noprogressbar"
 OPT_TEMP="$(parse_options $OPT_SHORT $OPT_LONG "$@" || echo 'PARSE_OPTIONS FAILED')"
@@ -1671,6 +1742,7 @@
 		--skipinteg)      SKIPINTEG=1 ;;
 		--source)         SOURCEONLY=1 ;;
 		-s|--syncdeps)    DEP_BIN=1 ;;
+		-t|--splitdbg)    SPLIT_DBG=1 ;;
 
 		-h|--help)        usage; exit 0 ;; # E_OK
 		-V|--version)     version; exit 0 ;; # E_OK
@@ -1874,6 +1946,8 @@
 devel_check
 devel_update
 
+[ "$(check_option splitdbg)" = "y" ] || (( SPLIT_DBG )) && add_split_debug_packages
+
 if (( ${#pkgname[@]} > 1 )); then
 	SPLITPKG=1
 fi
