Skip to content

Commit

Permalink
Assert fp is not None
Browse files Browse the repository at this point in the history
  • Loading branch information
radarhere committed Dec 22, 2024
1 parent 0e3f51d commit ab708da
Show file tree
Hide file tree
Showing 41 changed files with 77 additions and 4 deletions.
1 change: 1 addition & 0 deletions Tests/test_file_bufrstub.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ def open(self, im: ImageFile.StubImageFile) -> None:

def load(self, im: ImageFile.StubImageFile) -> Image.Image:
self.loaded = True
assert im.fp is not None
im.fp.close()
return Image.new("RGB", (1, 1))

Expand Down
1 change: 1 addition & 0 deletions Tests/test_file_cur.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ def test_invalid_file() -> None:
no_cursors_file = "Tests/images/no_cursors.cur"

cur = CurImagePlugin.CurImageFile(TEST_FILE)
assert cur.fp is not None
cur.fp.close()
with open(no_cursors_file, "rb") as cur.fp:
with pytest.raises(TypeError):
Expand Down
1 change: 1 addition & 0 deletions Tests/test_file_gribstub.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ def open(self, im: Image.Image) -> None:

def load(self, im: Image.Image) -> Image.Image:
self.loaded = True
assert im.fp is not None
im.fp.close()
return Image.new("RGB", (1, 1))

Expand Down
1 change: 1 addition & 0 deletions Tests/test_file_hdf5stub.py
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@ def open(self, im: Image.Image) -> None:

def load(self, im: Image.Image) -> Image.Image:
self.loaded = True
assert im.fp is not None
im.fp.close()
return Image.new("RGB", (1, 1))

Expand Down
3 changes: 2 additions & 1 deletion Tests/test_file_jpeg.py
Original file line number Diff line number Diff line change
Expand Up @@ -1085,8 +1085,9 @@ def test_fd_leak(self, tmp_path: Path) -> None:
im.save(tmpfile)

im = Image.open(tmpfile)
assert im.fp is not None
assert not im.fp.closed
fp = im.fp
assert not fp.closed
with pytest.raises(OSError):
os.remove(tmpfile)
im.load()
Expand Down
13 changes: 11 additions & 2 deletions Tests/test_file_libtiff.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,15 @@

import pytest

from PIL import Image, ImageFilter, ImageOps, TiffImagePlugin, TiffTags, features
from PIL import (
Image,
ImageFile,
ImageFilter,
ImageOps,
TiffImagePlugin,
TiffTags,
features,
)
from PIL.TiffImagePlugin import OSUBFILETYPE, SAMPLEFORMAT, STRIPOFFSETS, SUBIFD

from .helper import (
Expand Down Expand Up @@ -556,8 +564,9 @@ def test_bw_compression_w_rgb(self, compression: str, tmp_path: Path) -> None:
im.save(out, compression=compression)

def test_fp_leak(self) -> None:
im: Image.Image | None = Image.open("Tests/images/hopper_g4_500.tif")
im: ImageFile.ImageFile | None = Image.open("Tests/images/hopper_g4_500.tif")
assert im is not None
assert im.fp is not None
fn = im.fp.fileno()

os.fstat(fn)
Expand Down
5 changes: 4 additions & 1 deletion Tests/test_file_tiff.py
Original file line number Diff line number Diff line change
Expand Up @@ -861,6 +861,7 @@ def test_close_on_load_exclusive(self, tmp_path: Path) -> None:

im = Image.open(tmpfile)
fp = im.fp
assert fp is not None
assert not fp.closed
im.load()
assert fp.closed
Expand All @@ -874,6 +875,7 @@ def test_close_on_load_nonexclusive(self, tmp_path: Path) -> None:
with open(tmpfile, "rb") as f:
im = Image.open(f)
fp = im.fp
assert fp is not None
assert not fp.closed
im.load()
assert not fp.closed
Expand Down Expand Up @@ -925,8 +927,9 @@ def test_fd_leak(self, tmp_path: Path) -> None:
im.save(tmpfile)

im = Image.open(tmpfile)
assert im.fp is not None
assert not im.fp.closed
fp = im.fp
assert not fp.closed
with pytest.raises(OSError):
os.remove(tmpfile)
im.load()
Expand Down
1 change: 1 addition & 0 deletions Tests/test_image_load.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ def test_close_after_load(caplog: pytest.LogCaptureFixture) -> None:
def test_contextmanager() -> None:
fn = None
with Image.open("Tests/images/hopper.gif") as im:
assert im.fp is not None
fn = im.fp.fileno()
os.fstat(fn)

Expand Down
1 change: 1 addition & 0 deletions docs/example/DdsImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -213,6 +213,7 @@ class DdsImageFile(ImageFile.ImageFile):
format_description = "DirectDraw Surface"

def _open(self) -> None:
assert self.fp is not None
if not _accept(self.fp.read(4)):
msg = "not a DDS file"
raise SyntaxError(msg)
Expand Down
1 change: 1 addition & 0 deletions src/PIL/BlpImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -258,6 +258,7 @@ class BlpImageFile(ImageFile.ImageFile):
format_description = "Blizzard Mipmap Format"

def _open(self) -> None:
assert self.fp is not None
self.magic = self.fp.read(4)

self.fp.seek(5, os.SEEK_CUR)
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/BmpImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ class BmpImageFile(ImageFile.ImageFile):

def _bitmap(self, header: int = 0, offset: int = 0) -> None:
"""Read relevant info about the BMP"""
assert self.fp is not None
read, seek = self.fp.read, self.fp.seek
if header:
seek(header)
Expand Down Expand Up @@ -307,6 +308,7 @@ def _bitmap(self, header: int = 0, offset: int = 0) -> None:
def _open(self) -> None:
"""Open file, check magic number and read header"""
# read 14 bytes: magic number, filesize, reserved, header final offset
assert self.fp is not None
head_data = self.fp.read(14)
# choke if the file does not have the required magic bytes
if not _accept(head_data):
Expand Down
1 change: 1 addition & 0 deletions src/PIL/BufrStubImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ class BufrStubImageFile(ImageFile.StubImageFile):
format_description = "BUFR"

def _open(self) -> None:
assert self.fp is not None
offset = self.fp.tell()

if not _accept(self.fp.read(4)):
Expand Down
1 change: 1 addition & 0 deletions src/PIL/CurImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ class CurImageFile(BmpImagePlugin.BmpImageFile):
format_description = "Windows Cursor"

def _open(self) -> None:
assert self.fp is not None
offset = self.fp.tell()

# check magic
Expand Down
1 change: 1 addition & 0 deletions src/PIL/DcxImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ class DcxImageFile(PcxImageFile):

def _open(self) -> None:
# Header
assert self.fp is not None
s = self.fp.read(4)
if not _accept(s):
msg = "not a DCX file"
Expand Down
1 change: 1 addition & 0 deletions src/PIL/DdsImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -333,6 +333,7 @@ class DdsImageFile(ImageFile.ImageFile):
format_description = "DirectDraw Surface"

def _open(self) -> None:
assert self.fp is not None
if not _accept(self.fp.read(4)):
msg = "not a DDS file"
raise SyntaxError(msg)
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/EpsImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,7 @@ class EpsImageFile(ImageFile.ImageFile):
mode_map = {1: "L", 2: "LAB", 3: "RGB", 4: "CMYK"}

def _open(self) -> None:
assert self.fp is not None
(length, offset) = self._find_offset(self.fp)

# go to offset - start of "%!PS"
Expand Down Expand Up @@ -398,6 +399,7 @@ def load(
) -> Image.core.PixelAccess | None:
# Load EPS via Ghostscript
if self.tile:
assert self.fp is not None
self.im = Ghostscript(self.tile, self.size, self.fp, scale, transparency)
self._mode = self.im.mode
self._size = self.im.size
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/FliImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ class FliImageFile(ImageFile.ImageFile):

def _open(self) -> None:
# HEAD
assert self.fp is not None
s = self.fp.read(128)
if not (_accept(s) and s[20:22] == b"\x00\x00"):
msg = "not an FLI/FLC file"
Expand Down Expand Up @@ -110,6 +111,7 @@ def _palette(self, palette: list[tuple[int, int, int]], shift: int) -> None:
# load palette

i = 0
assert self.fp is not None
for e in range(i16(self.fp.read(2))):
s = self.fp.read(2)
i = i + s[0]
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/FpxImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ def _open(self) -> None:
# read the OLE directory and see if this is a likely
# to be a FlashPix file

assert self.fp is not None
try:
self.ole = olefile.OleFileIO(self.fp)
except OSError as e:
Expand Down Expand Up @@ -229,6 +230,7 @@ def _open_subimage(self, index: int = 1, subimage: int = 0) -> None:
if y >= ysize:
break # isn't really required

assert self.fp is not None
self.stream = stream
self._fp = self.fp
self.fp = None
Expand Down
1 change: 1 addition & 0 deletions src/PIL/FtexImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@ class FtexImageFile(ImageFile.ImageFile):
format_description = "Texture File Format (IW2:EOC)"

def _open(self) -> None:
assert self.fp is not None
if not _accept(self.fp.read(4)):
msg = "not an FTEX file"
raise SyntaxError(msg)
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/GbrImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ class GbrImageFile(ImageFile.ImageFile):
format_description = "GIMP brush file"

def _open(self) -> None:
assert self.fp is not None
header_size = i32(self.fp.read(4))
if header_size < 20:
msg = "not a GIMP brush"
Expand Down Expand Up @@ -90,6 +91,7 @@ def _open(self) -> None:

def load(self) -> Image.core.PixelAccess | None:
if self._im is None:
assert self.fp is not None
self.im = Image.core.new(self.mode, self.size)
self.frombytes(self.fp.read(self._data_size))
return Image.Image.load(self)
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/GifImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -83,6 +83,7 @@ class GifImageFile(ImageFile.ImageFile):
global_palette = None

def data(self) -> bytes | None:
assert self.fp is not None
s = self.fp.read(1)
if s and s[0]:
return self.fp.read(s[0])
Expand All @@ -96,6 +97,7 @@ def _is_palette_needed(self, p: bytes) -> bool:

def _open(self) -> None:
# Screen
assert self.fp is not None
s = self.fp.read(13)
if not _accept(s):
msg = "not a GIF file"
Expand Down
1 change: 1 addition & 0 deletions src/PIL/GribStubImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ class GribStubImageFile(ImageFile.StubImageFile):
format_description = "GRIB"

def _open(self) -> None:
assert self.fp is not None
offset = self.fp.tell()

if not _accept(self.fp.read(8)):
Expand Down
1 change: 1 addition & 0 deletions src/PIL/Hdf5StubImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ class HDF5StubImageFile(ImageFile.StubImageFile):
format_description = "HDF5"

def _open(self) -> None:
assert self.fp is not None
offset = self.fp.tell()

if not _accept(self.fp.read(8)):
Expand Down
1 change: 1 addition & 0 deletions src/PIL/IcnsImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -267,6 +267,7 @@ class IcnsImageFile(ImageFile.ImageFile):
format_description = "Mac OS icns resource"

def _open(self) -> None:
assert self.fp is not None
self.icns = IcnsFile(self.fp)
self._mode = "RGBA"
self.info["sizes"] = self.icns.itersizes()
Expand Down
1 change: 1 addition & 0 deletions src/PIL/IcoImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,7 @@ class IcoImageFile(ImageFile.ImageFile):
format_description = "Windows Icon"

def _open(self) -> None:
assert self.fp is not None
self.ico = IcoFile(self.fp)
self.info["sizes"] = self.ico.sizes()
self.size = self.ico.entry[0].dim
Expand Down
1 change: 1 addition & 0 deletions src/PIL/ImImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,7 @@ def _open(self) -> None:
# Quick rejection: if there's not an LF among the first
# 100 bytes, this is (probably) not a text header.

assert self.fp is not None
if b"\n" not in self.fp.read(100):
msg = "not an IM file"
raise SyntaxError(msg)
Expand Down
1 change: 1 addition & 0 deletions src/PIL/ImageFile.py
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,7 @@ def load(self) -> Image.core.PixelAccess | None:
# As of pypy 2.1.0, memory mapping was failing here.
use_mmap = use_mmap and not hasattr(sys, "pypy_version_info")

assert self.fp is not None
readonly = 0

# look for read/seek overrides
Expand Down
3 changes: 3 additions & 0 deletions src/PIL/IptcImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ def getint(self, key: tuple[int, int]) -> int:
def field(self) -> tuple[tuple[int, int] | None, int]:
#
# get a IPTC field header
assert self.fp is not None
s = self.fp.read(5)
if not s.strip(b"\x00"):
return None, 0
Expand Down Expand Up @@ -104,6 +105,7 @@ def field(self) -> tuple[tuple[int, int] | None, int]:

def _open(self) -> None:
# load descriptive fields
assert self.fp is not None
while True:
offset = self.fp.tell()
tag, size = self.field()
Expand Down Expand Up @@ -157,6 +159,7 @@ def load(self) -> Image.core.PixelAccess | None:

offset, compression = self.tile[0][2:]

assert self.fp is not None
self.fp.seek(offset)

# Copy image data to temporary file
Expand Down
2 changes: 2 additions & 0 deletions src/PIL/Jpeg2KImagePlugin.py
Original file line number Diff line number Diff line change
Expand Up @@ -248,6 +248,7 @@ class Jpeg2KImageFile(ImageFile.ImageFile):
format_description = "JPEG 2000 (ISO 15444)"

def _open(self) -> None:
assert self.fp is not None
sig = self.fp.read(4)
if sig == b"\xff\x4f\xff\x51":
self.codec = "j2k"
Expand Down Expand Up @@ -296,6 +297,7 @@ def _open(self) -> None:
]

def _parse_comment(self) -> None:
assert self.fp is not None
hdr = self.fp.read(2)
length = _binary.i16be(hdr)
self.fp.seek(length - 2, os.SEEK_CUR)
Expand Down
Loading

0 comments on commit ab708da

Please sign in to comment.