Layers: Lock cache file, bomb out after 30 seconds

This commit is contained in:
Mike Auty
2021-02-05 01:11:50 +00:00
parent d66357c64c
commit 4aba8a0c7a
2 changed files with 34 additions and 17 deletions
@@ -76,6 +76,9 @@ BUG_URL = "https://github.com/volatilityfoundation/volatility3/issues"
ProgressCallback = Optional[Callable[[float, str], None]]
"""Type information for ProgressCallback objects"""
URLOPEN_LOCK_TIMEOUT = 30000
"""Number of miliseconds to wait before timing-out on file locks"""
class Parallelism(enum.IntEnum):
"""An enumeration listing the different types of parallelism applied to
+31 -17
View File
@@ -10,6 +10,7 @@ import logging
import lzma
import os
import ssl
import time
import urllib.parse
import urllib.request
import zipfile
@@ -121,26 +122,39 @@ class ResourceAccessor(object):
constants.CACHE_PATH,
"data_" + hashlib.sha512(bytes(url, 'raw_unicode_escape')).hexdigest() + ".cache")
if not os.path.exists(temp_filename):
vollog.debug("Caching file at: {}".format(temp_filename))
with open(temp_filename + '.lock', 'w'):
if not os.path.exists(temp_filename):
vollog.debug("Caching file at: {}".format(temp_filename))
try:
content_length = fp.info().get('Content-Length', -1)
except AttributeError:
# If our fp doesn't have an info member, carry on gracefully
content_length = -1
cache_file = open(temp_filename, "wb")
try:
content_length = fp.info().get('Content-Length', -1)
except AttributeError:
# If our fp doesn't have an info member, carry on gracefully
content_length = -1
cache_file = open(temp_filename, "wb")
count = 0
block = fp.read(block_size)
while block:
count += len(block)
if self._progress_callback:
self._progress_callback(count * 100 / max(count, int(content_length)),
"Reading file {}".format(url))
cache_file.write(block)
count = 0
block = fp.read(block_size)
cache_file.close()
while block:
count += len(block)
if self._progress_callback:
self._progress_callback(count * 100 / max(count, int(content_length)),
"Reading file {}".format(url))
cache_file.write(block)
block = fp.read(block_size)
cache_file.close()
else:
count = 0
while os.path.exists(temp_filename + '.lock'):
count += 1
if self._progress_callback:
self._progress_callback(0, "Waiting on lock to retrieve {}".format(url))
time.sleep(0.1)
if count >= constants.URLOPEN_LOCK_TIMEOUT // 1000:
break
if not os.path.exists(temp_filename):
raise error.URLError("Unable to lock the cache for {}".format(url))
# Re-open the cache with a different mode
# Since we don't want people thinking they're able to save to the cache file,
# open it in read mode only and allow breakages to happen if they wanted to write