Skip to content

Commit e43709e

Browse files
malmond77m-blaha
authored andcommitted
Use libdnf.utils.checksum_{check,value}
libdnf has the canonical implementation of checksum handling. We aim to replace all use of dnf.yum.misc.checksum() with this. In doing so, this fixes installing previously downloaded and transcoded rpms to support rpm-software-management/librepo#222 This also has some minor performance benefits: librepo's checksum handling employs caching of previously downloaded files via extended attributes. This works for ordinary rpms in the dnf cache, but does not work (yet) for rpm paths specified on the command line due to rpm-software-management/librepo#233. That issue is pretty minor, and the fix ends up in libdnf later. The previous implementation maps all runtime errors to MiscError. We do this still by taking the libdnf.error.Error class (defined in SWIG) and map it directly back to the Python exception as before.
1 parent ed06bbf commit e43709e

File tree

2 files changed

+10
-121
lines changed

2 files changed

+10
-121
lines changed

dnf/package.py

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@
3030
import dnf.rpm
3131
import dnf.yum.misc
3232
import hawkey
33+
import libdnf.error
34+
import libdnf.utils
3335
import logging
3436
import os
3537
import rpm
@@ -56,7 +58,10 @@ def _chksum(self):
5658
return self._priv_chksum
5759
if self._from_cmdline:
5860
chksum_type = dnf.yum.misc.get_default_chksum_type()
59-
chksum_val = dnf.yum.misc.checksum(chksum_type, self.location)
61+
try:
62+
chksum_val = libdnf.utils.checksum_value(chksum_type, self.location)
63+
except libdnf.error.Error as e:
64+
raise dnf.exceptions.MiscError(str(e))
6065
return (hawkey.chksum_type(chksum_type),
6166
binascii.unhexlify(chksum_val))
6267
return super(Package, self).chksum
@@ -330,10 +335,7 @@ def verifyLocalPkg(self):
330335
if self._from_cmdline:
331336
return True # local package always verifies against itself
332337
(chksum_type, chksum) = self.returnIdSum()
333-
real_sum = dnf.yum.misc.checksum(chksum_type, self.localPkg(),
334-
datasize=self._size)
335-
if real_sum != chksum:
336-
logger.debug(_('%s: %s check failed: %s vs %s'),
337-
self, chksum_type, real_sum, chksum)
338-
return False
339-
return True
338+
try:
339+
return libdnf.utils.checksum_check(chksum_type, self.localPkg(), chksum)
340+
except libdnf.error.Error as e:
341+
raise dnf.exceptions.MiscError(str(e))

dnf/yum/misc.py

Lines changed: 0 additions & 113 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,6 @@
2222

2323
from __future__ import print_function, absolute_import
2424
from __future__ import unicode_literals
25-
from dnf.exceptions import MiscError
2625
from dnf.pycomp import base64_decodebytes, basestring, unicode
2726
from stat import *
2827
import libdnf.utils
@@ -32,7 +31,6 @@
3231
import dnf.i18n
3332
import errno
3433
import glob
35-
import hashlib
3634
import io
3735
import os
3836
import os.path
@@ -41,7 +39,6 @@
4139
import shutil
4240
import tempfile
4341

44-
_available_checksums = set(['md5', 'sha1', 'sha256', 'sha384', 'sha512'])
4542
_default_checksums = ['sha256']
4643

4744

@@ -68,119 +65,9 @@ def re_full_search_needed(s):
6865
return True
6966
return False
7067

71-
72-
class Checksums(object):
73-
""" Generate checksum(s), on given pieces of data. Producing the
74-
Length and the result(s) when complete. """
75-
76-
def __init__(self, checksums=None, ignore_missing=False, ignore_none=False):
77-
if checksums is None:
78-
checksums = _default_checksums
79-
self._sumalgos = []
80-
self._sumtypes = []
81-
self._len = 0
82-
83-
done = set()
84-
for sumtype in checksums:
85-
if sumtype == 'sha':
86-
sumtype = 'sha1'
87-
if sumtype in done:
88-
continue
89-
90-
if sumtype in _available_checksums:
91-
sumalgo = hashlib.new(sumtype)
92-
elif ignore_missing:
93-
continue
94-
else:
95-
raise MiscError('Error Checksumming, bad checksum type %s' %
96-
sumtype)
97-
done.add(sumtype)
98-
self._sumtypes.append(sumtype)
99-
self._sumalgos.append(sumalgo)
100-
if not done and not ignore_none:
101-
raise MiscError('Error Checksumming, no valid checksum type')
102-
103-
def __len__(self):
104-
return self._len
105-
106-
# Note that len(x) is assert limited to INT_MAX, which is 2GB on i686.
107-
length = property(fget=lambda self: self._len)
108-
109-
def update(self, data):
110-
self._len += len(data)
111-
for sumalgo in self._sumalgos:
112-
data = data.encode('utf-8') if isinstance(data, unicode) else data
113-
sumalgo.update(data)
114-
115-
def read(self, fo, size=2**16):
116-
data = fo.read(size)
117-
self.update(data)
118-
return data
119-
120-
def hexdigests(self):
121-
ret = {}
122-
for sumtype, sumdata in zip(self._sumtypes, self._sumalgos):
123-
ret[sumtype] = sumdata.hexdigest()
124-
return ret
125-
126-
def hexdigest(self, checksum=None):
127-
if checksum is None:
128-
if not self._sumtypes:
129-
return None
130-
checksum = self._sumtypes[0]
131-
if checksum == 'sha':
132-
checksum = 'sha1'
133-
return self.hexdigests()[checksum]
134-
135-
def digests(self):
136-
ret = {}
137-
for sumtype, sumdata in zip(self._sumtypes, self._sumalgos):
138-
ret[sumtype] = sumdata.digest()
139-
return ret
140-
141-
def digest(self, checksum=None):
142-
if checksum is None:
143-
if not self._sumtypes:
144-
return None
145-
checksum = self._sumtypes[0]
146-
if checksum == 'sha':
147-
checksum = 'sha1'
148-
return self.digests()[checksum]
149-
15068
def get_default_chksum_type():
15169
return _default_checksums[0]
15270

153-
def checksum(sumtype, file, CHUNK=2**16, datasize=None):
154-
"""takes filename, hand back Checksum of it
155-
sumtype = md5 or sha/sha1/sha256/sha512 (note sha == sha1)
156-
filename = /path/to/file
157-
CHUNK=65536 by default"""
158-
159-
# chunking brazenly lifted from Ryan Tomayko
160-
161-
if isinstance(file, basestring):
162-
try:
163-
with open(file, 'rb', CHUNK) as fo:
164-
return checksum(sumtype, fo, CHUNK, datasize)
165-
except (IOError, OSError):
166-
raise MiscError('Error opening file for checksum: %s' % file)
167-
168-
try:
169-
# assumes file is a file-like-object
170-
data = Checksums([sumtype])
171-
while data.read(file, CHUNK):
172-
if datasize is not None and data.length > datasize:
173-
break
174-
175-
# This screws up the length, but that shouldn't matter. We only care
176-
# if this checksum == what we expect.
177-
if datasize is not None and datasize != data.length:
178-
return '!%u!%s' % (datasize, data.hexdigest(sumtype))
179-
180-
return data.hexdigest(sumtype)
181-
except (IOError, OSError) as e:
182-
raise MiscError('Error reading file for checksum: %s' % file)
183-
18471
class GenericHolder(object):
18572
"""Generic Holder class used to hold other objects of known types
18673
It exists purely to be able to do object.somestuff, object.someotherstuff

0 commit comments

Comments
 (0)