Bug#577226: [apt] improve Dpkg::Chroot-Directory for installation of packages in chroot
Package: apt
Version: 0.7.25.3
Severity: wishlist
Tags: patch
Hi,
Here is a python program which bootstraps a sid system, then attempts to
install a package in the chroot:
---
#!/usr/bin/python
import apt.cache
import apt_pkg
import os
import subprocess
import sys
subprocess.call('debootstrap --variant=minbase sid /tmp/crap http://localhost:9999/debian/'.split())
apt_pkg.init()
apt_pkg.config.set('Dpkg::Chroot-Directory', '/tmp/crap')
cache = apt.cache.Cache(rootdir='/tmp/crap')
apt_pkg.Config.clear("DPkg::Pre-Install-Pkgs")
cache.update()
cache.open()
cache['hello'].mark_install()
cache.commit()
---
It fails, because after chroot('/tmp/crap') the later dpkg process gets given
a filename argument which begins with the pathname to chroot itself and is
not accessible:
---
Reading package lists... Done
Building dependency tree... Done
Building data structures... Done
Reading package lists... Done
Building dependency tree... Done
Building data structures... Done
Chrooting into /tmp/crap/
dpkg: error processing /tmp/crap/var/cache/apt/archives/hello_2.5-1_amd64.deb (--unpack):
cannot access archive: No such file or directory
Errors were encountered while processing:
/tmp/crap/var/cache/apt/archives/hello_2.5-1_amd64.deb
Traceback (most recent call last):
File "./test_apt.py", line 17, in <module>
cache.commit()
File "/usr/lib/python2.5/site-packages/apt/deprecation.py", line 98, in deprecated_function
return func(*args, **kwds)
File "/usr/lib/python2.5/site-packages/apt/cache.py", line 381, in commit
raise SystemError("installArchives() failed")
SystemError: installArchives() failed
---
The following patch adds some logic to check each File, when
DPkg::Chroot-Directory != '/', to see if it begins with the pathname
of the chroot. If it does, it returns a substring of File without the
chroot pathname. It is careful not to strip the leading / from any File.
---
--- a/apt-pkg/deb/dpkgpm.cc
+++ b/apt-pkg/deb/dpkgpm.cc
@@ -124,6 +124,18 @@ bool pkgDPkgPM::Install(PkgIterator Pkg,
if (File.empty() == true || Pkg.end() == true)
return _error->Error("Internal Error, No file name for %s",Pkg.Name());
+ // If the filename string begins with DPkg::Chroot-Directory, return the
+ // substr that is within the chroot so dpkg can access it.
+ string chrootdir = _config->FindDir("DPkg::Chroot-Directory","/");
+ if (chrootdir.compare("/") != 0 && File.find(chrootdir) == 0)
+ {
+ size_t len = chrootdir.length();
+ if (chrootdir.at(len - 1) == '/')
+ len--;
+ List.push_back(Item(Item::Install,Pkg,File.substr(len)));
+ return true;
+ }
+
List.push_back(Item(Item::Install,Pkg,File));
return true;
}
---
Can you please consider applying it?
Thanks, Kel.
--- System information. ---
Architecture: amd64
Kernel: Linux 2.6.33-2.slh.3-sidux-amd64
Debian Release: squeeze/sid
500 unstable localhost
1 experimental localhost
--- Package information. ---
Depends (Version) | Installed
=======================================-+-=============
libc6 (>= 2.3.4) | 2.10.2-6
libgcc1 (>= 1:4.1.1) | 1:4.4.3-7
libstdc++6 (>= 4.4.0) | 4.4.3-7
debian-archive-keyring | 2009.01.31
Package's Recommends field is empty.
Suggests (Version) | Installed
=========================-+-===========
aptitude |
OR synaptic |
OR wajig |
dpkg-dev | 1.15.5.6
apt-doc |
bzip2 | 1.0.5-4
lzma | 4.43-14
python-apt | 0.7.94.2
Reply to: