Here's part of the bug.
https://github.com/freebsd/freebsd-src/blob/main/usr.bin/grep/file.c#L210
There's no handling of EOF if it occurs as the very first read() of the file.
A zero-length regular file and /dev/null will also result in two read()s returning 0 before grep then exits.
This code was introduced in commit 3ed1008b891eb34df96a6ae4f87e5a3270be759c in 2010.
#OpenBSD's version of this code is older and uses the normal C stdio library routines and getline(3) rather than rolling its own layer over read().