From 8037cdcd9ab4f8e62ceabdded0f43afb2a11df0f Mon Sep 17 00:00:00 2001 From: Brooks Davis Date: Tue, 13 Mar 2018 19:56:10 +0000 Subject: [PATCH] Fix ISP_FC_LIP and ISP_RESCAN on big-endian 64-bit systems. For _IO() ioctls, addr is a pointer to uap->data which is a caddr_t. When the caddr_t stores an int, dereferencing addr as an (int *) results in truncation on little-endian 64-bit systems and corruption (owing to extracting top bits) on big-endian 64-bit systems. In practice the value of chan was probably always zero on systems of the latter type as all such FreeBSD platforms use a register-based calling convention. Reviewed by: mav Obtained from: CheriBSD MFC after: 1 week Sponsored by: DARPA, AFRL Differential Revision: https://reviews.freebsd.org/D14673 --- sys/dev/isp/isp_freebsd.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/sys/dev/isp/isp_freebsd.c b/sys/dev/isp/isp_freebsd.c index 464c80584c0..3f7850829b9 100644 --- a/sys/dev/isp/isp_freebsd.c +++ b/sys/dev/isp/isp_freebsd.c @@ -444,7 +444,7 @@ ispioctl(struct cdev *dev, u_long c, caddr_t addr, int flags, struct thread *td) case ISP_RESCAN: if (IS_FC(isp)) { - chan = *(int *)addr; + chan = *(intptr_t *)addr; if (chan < 0 || chan >= isp->isp_nchan) { retval = -ENXIO; break; @@ -461,7 +461,7 @@ ispioctl(struct cdev *dev, u_long c, caddr_t addr, int flags, struct thread *td) case ISP_FC_LIP: if (IS_FC(isp)) { - chan = *(int *)addr; + chan = *(intptr_t *)addr; if (chan < 0 || chan >= isp->isp_nchan) { retval = -ENXIO; break;