--- Begin Message ---
- To: Debian Bug Tracking System <submit@bugs.debian.org>
- Subject: python-apt: segfault on bad usage of ParseTagFile
- From: Alastair McKinstry <mckinstry@debian.org>
- Date: Sun, 10 Oct 2004 18:00:52 +0100
- Message-id: <20041010170052.714CE235C0@coll>
Package: python-apt
Version: 0.5.10
Severity: normal
If you fail to use parse.step() on parsing a tag file,
instead of getting an exception, the .so segfaults.
Attached is an example program that does this.
-- System Information:
Debian Release: 3.1
APT prefers experimental
APT policy: (990, 'experimental')
Architecture: i386 (i686)
Kernel: Linux 2.6.7-1-686
Locale: LANG=C, LC_CTYPE=C (ignored: LC_ALL set to ga_IE.UTF-8)
Versions of packages python-apt depends on:
ii apt [libapt-pkg-libc6.3-5-3 0.5.27 Advanced front-end for dpkg
ii apt-utils [libapt-inst-libc 0.5.27 APT utility programs
ii libc6 2.3.2.ds1-17 GNU C Library: Shared libraries an
ii python 2.3.4-4 An interactive high-level object-o
-- no debconf information
#!/usr/bin/python
# -*- coding: UTF-8 -*-
__author__ = 'Alastair McKinstry'
__author_email__ = 'mckinstry@debian.org'
__copyright__ = 'Copyright © 2004 Alastair McKinstry <mckinstry@debian.org>'
__license__ = 'GPL'
__version__ = '$Id$'
import apt_pkg, os, unittest, errno
# from errno import *
__all__ = [ 'Archive', 'Distribution' ]
class BadDistribution(Exception):
pass
class Archive:
"""Class for Debian Archive management"""
__archives = {}
def __init__(self, path):
"""Create an archive object listing the archives, as necessary """
if self.__archives.has_key(path):
a = self.__archives[path]
self.__dict__ = a.__dict__
self.__class__ = a.__class__
else:
self.path = path
self.dists = {}
self.Distributions = os.listdir('%s/dists' % path)
self.__archives[path] = self
self._dists_fetched = False
def fetchDistributions(self):
"""Fetch all the distribution details, and eliminate aliases"""
for d in self.Distributions:
try:
di = Distribution(self, d)
except BadDistribution, e:
# Remove d from list
pass
class Distribution:
"""Class for Distribution within Debian Archive"""
__distributions = {}
# Tags that may be in a release file.
# Not interested in MD5Sum for the moment.
_tags = ['Origin', 'Label', 'Suite', 'Codename', 'Date',
'Architectures', 'Components', 'Description', 'Version']
def __init__(self, archive, name):
"""Create a Distribution object, from an archive"""
if self.__distributions.has_key((archive, name)):
a = self.__distributions[archive, name]
self.__dict__ = a.__dict__
self.__class__ = a.__class__
else:
self.archive = archive
self.name = name
try:
path = '%s/dists/%s/Release' % (archive.path, name)
f = open(path, 'r')
except IOError, e:
print e.__dict__
if e.errno == errno.ENOENT or e.errno == errno.ENOTDIR:
raise BadDistribution, '%s is not a distibution name' % name
raise IOError, e
try:
parse = apt_pkg.ParseTagFile(open(path,'r'))
except:
raise SystemError, "Failed to parse file %s" % path
for tag in self._tags:
val = parse.Section.get(tag)
if val != '':
setattr(self, tag, val)
class ArchiveTestCase(unittest.TestCase):
"""Unit tests for Debian Archive class"""
def testArchive(self):
"""Test Creation"""
a = Archive('/srv/debian.org/debian')
def testSingleton(self):
"""Check that archives are cached."""
a = Archive('/srv/debian.org/debian')
b = Archive('/srv/debian.org/debian')
assert id(a.__dict__) == id(b.__dict__), "Archive objects not cached"
def testDistributions(self):
"""Check we get the correct distributions"""
a = Archive('/srv/debian.org/debian')
a.fetchDistributions()
class DistributionTestCase(unittest.TestCase):
"""Unit Tests for Debian Distribution class"""
def testDistribution(self):
"""Create a distribution object"""
archive = Archive('/srv/debian.org/debian')
dist = Distribution(archive, 'woody')
if __name__ == '__main__':
unittest.main()
--- End Message ---