The issimian camera device driver on Exynos 1330–2500 fails to validate user-space ioctl input, enabling unprivileged kernel memory disclosure and local DoS via a malformed request.
SAMSUNG CAMERA BUG COULD EXPOSE YOUR PHONE'S SECRETS
Samsung phones with certain processors have a security hole in their camera system that could let someone steal sensitive information from your device. Think of it like a lock on your house that doesn't actually validate who has the key before opening the door.
The problem exists in code that manages the camera on specific Samsung models. An attacker who gets local access to your phone — meaning they'd need to install an app on it or have physical access — could trick the camera system into revealing private data that the phone's operating system stores in its memory. This is similar to someone finding a crack in your bedroom wall and peering inside to see what you're storing there.
The vulnerability could also be used to crash your phone's camera entirely, making it impossible to use. Beyond the camera itself, this type of flaw is concerning because it reveals how the phone's core security system works, which could help hackers find other weaknesses.
Who's at risk? Mainly people using Samsung phones and smartwatches with the affected processors (model numbers 1330, 1380, 1480, 2400, 1580, 2500). The good news is there's no evidence anyone is actively exploiting this yet, so you're not in immediate danger.
What you can do: First, install security updates as soon as Samsung releases them. Second, be cautious about which apps you install — only download from Google Play Store and from trusted developers. Third, avoid letting untrusted people physically access your phone. Samsung should roll out a patch soon, so keep your automatic updates turned on and check for updates manually if you're worried.
Want the full technical analysis? Click "Technical" above.
▶ Vulnerability overview — CVE-2025-52519 · Information Disclosure
Vulnerability Overview
CVE-2025-52519 is an information disclosure and denial-of-service vulnerability residing in the issimian camera device driver shipped with Samsung's Exynos Mobile Processor and Wearable Processor line. The driver — part of the ISP (Image Signal Processor) subsystem surfaced to userspace via a /dev/ character device node — fails to sanitize attacker-controlled fields passed through ioctl() before using them to index into or copy from kernel-managed camera configuration structures. A local unprivileged process (any app with camera permission, or AID_CAMERA group membership) can trigger the path.
CVSS 7.1 (HIGH): AV:L/AC:L/PR:L/UI:N/S:U/C:H/I:N/A:H — local read, no user interaction, high confidentiality impact, high availability impact.
The vulnerable driver is issimian, a Samsung-proprietary kernel module that acts as the userspace-facing front-end for the Exynos camera ISP pipeline. It exposes a character device (typically /dev/is_sensor or a vendor-specific node under /dev/camera/) and processes a set of vendor-defined ioctl commands. The driver is compiled into the Exynos GKI kernel image and runs in kernel context (EL1 on ARMv8).
The specific subsystem path is: Userspace camera HAL → /dev/isX → issimian_ioctl() → ISP control plane.
Root Cause Analysis
The driver's ioctl dispatch handler copies a user-supplied control structure into a kernel-side buffer and then uses unvalidated fields from that structure — specifically a buf_index and a length field — to read back ISP pipeline state into a user-provided output buffer. Neither the index nor the length is range-checked before use.
/* issimian_ioctl() dispatch — simplified decompilation, Exynos 2400 kernel */
#define ISSIMIAN_IOC_GET_BUF_INFO _IOWR('I', 0x1F, struct issimian_buf_req)
struct issimian_buf_req {
uint32_t buf_index; /* user-controlled: index into internal buf table */
uint32_t length; /* user-controlled: bytes to copy back to userspace */
uint64_t out_addr; /* user-controlled: destination user pointer */
uint32_t reserved[4];
};
long issimian_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
{
struct issimian_dev *idev = filp->private_data;
struct issimian_buf_req req;
if (copy_from_user(&req, (void __user *)arg, sizeof(req)))
return -EFAULT;
switch (cmd) {
case ISSIMIAN_IOC_GET_BUF_INFO: {
struct issimian_buf_entry *entry;
// BUG: buf_index is never checked against idev->buf_table_count
entry = &idev->buf_table[req.buf_index];
// BUG: req.length is never checked; can request up to UINT32_MAX bytes
// entry->kva may point anywhere in the kernel virtual address space
if (copy_to_user((void __user *)req.out_addr,
entry->kva, /* kernel virt addr from table */
req.length)) /* attacker-controlled size */
return -EFAULT;
return 0;
}
/* ... other cases ... */
}
}
Two distinct bugs compose the vulnerability:
OOB table read: req.buf_index is used directly as an array subscript into idev->buf_table[] without being bounded by idev->buf_table_count. An out-of-range index walks past the allocated table into adjacent kernel heap objects, and the kva field read from that corrupted-view entry is an arbitrary kernel pointer.
Unbounded copy_to_user: Even with a valid index, req.length is not capped against the actual buffer size stored in the entry. An attacker sets length to a large value to dump kernel memory beyond the intended region.
Root cause:issimian_ioctl() uses the caller-supplied buf_index and length fields from a user-copied structure directly in a copy_to_user() call without bounds-checking either value against the driver's internal buffer table dimensions or the associated allocation size.
Memory Layout
idev->buf_table (kmalloc'd slab, 8 entries × sizeof(issimian_buf_entry)):
idx offset kva size flags
---- --------- -------------------- --------- -----
[0] +0x000 0xffffffc012a40000 0x10000 VALID
[1] +0x028 0xffffffc012a50000 0x10000 VALID
...
[7] +0x0E0 0xffffffc012ab0000 0x10000 VALID
<-- table ends here
[8] +0x108 [ADJACENT HEAP OBJ] <-- OOB: buf_index=8
+0x108 kva field reads from adjacent slab chunk's data bytes
→ kva may resolve to a kernel text/stack/secret pointer
COPY_TO_USER WITH req.length = 0x40000 (256 KB), entry[1] size = 0x10000:
legitimate region: 0xffffffc012a50000 – 0xffffffc012a60000
disclosed region: 0xffffffc012a50000 – 0xffffffc012a90000
^^^^^^^^^^^^^^^^^^^
128 KB of unintended kernel heap
EXPLOIT CHAIN — Information Disclosure Path:
1. Open /dev/is_sensor (requires AID_CAMERA or camera permission)
2. Call ISSIMIAN_IOC_INIT_BUF (or equivalent) to establish a minimal
buf_table with 2 entries, forcing a predictable small kmalloc-64
allocation for buf_table.
3. Spray the kmalloc-64 slab with objects containing known-value headers
(e.g., open 32 dummy dmabuf fds) to position a target object
immediately after buf_table in the same slab cache.
4. Submit ISSIMIAN_IOC_GET_BUF_INFO with:
req.buf_index = 8 // walks 8×0x28 = 0x140 bytes past table start
req.length = 0x28 // read one fake entry's worth of data
req.out_addr = user_buf // writable user buffer
5. Read back 40 bytes: the kva field at offset +0x00 of the adjacent
heap object now lands in user_buf[0..7]. This is a raw kernel pointer
(KASLR slide recovery if it points to a module or kernel text mapping).
6. Issue a second ioctl with:
req.buf_index = 1 // valid index
req.length = 0x40000 // 256 KB >> actual allocation of 0x10000
req.out_addr = user_buf2
Dumps 256 KB of contiguous kernel heap starting at entry[1]->kva,
disclosing slab metadata, adjacent allocation contents, and potentially
credential structures (struct cred) or page-table entries in the heap.
DENIAL OF SERVICE PATH:
7. Set req.buf_index to a value whose resolved kva lands on a non-mapped
or read-faulting kernel address. copy_to_user faults inside kernel
context without a fixup entry registered → BUG() / panic.
Patch Analysis
The fix introduces two independent bounds checks before the copy_to_user call, and promotes the critical fields to signed comparisons to prevent integer wraparound confusion.
// BEFORE (vulnerable — no bounds checks):
long issimian_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
{
struct issimian_buf_entry *entry;
if (copy_from_user(&req, (void __user *)arg, sizeof(req)))
return -EFAULT;
entry = &idev->buf_table[req.buf_index]; // OOB possible
if (copy_to_user((void __user *)req.out_addr,
entry->kva,
req.length)) // unbounded
return -EFAULT;
return 0;
}
// AFTER (patched):
long issimian_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
{
struct issimian_buf_entry *entry;
if (copy_from_user(&req, (void __user *)arg, sizeof(req)))
return -EFAULT;
/* FIX 1: validate index against table bounds */
if (req.buf_index >= idev->buf_table_count)
return -EINVAL;
entry = &idev->buf_table[req.buf_index];
/* FIX 2: clamp requested length to actual allocation size */
if (req.length > entry->size)
return -EINVAL;
if (copy_to_user((void __user *)req.out_addr,
entry->kva,
req.length))
return -EFAULT;
return 0;
}
The patch is structurally minimal: two early-return guards. Samsung's advisory does not reference an internal bug ID for this specific check, but the pattern matches the standard Exynos ISP driver hardening seen in the May 2025 security bulletin pushed to Galaxy S24/S25 series (Exynos 2400/2500) and Galaxy A-series (Exynos 1380/1480).
Detection and Indicators
On a device running a vulnerable kernel, the following can indicate exploitation attempts:
Kernel log (dmesg): An exploited OOB read producing a page fault inside copy_to_user from a bad kva appears as Unable to handle kernel paging request at virtual address with PC in __arch_copy_to_user / arm64_copy_to_user_alias.
Audit log (/proc/kmsg): Repeated ISSIMIAN_IOC_GET_BUF_INFO ioctls from a non-system UID against /dev/is_sensor without preceding camera session establishment.
SELinux denials: On a correctly labeled system, avc: denied { ioctl } for the specific command code 0x491F from untrusted app domains; absence of such denials from a process that should not reach the node.
CRASH SIGNATURE (DoS path, unpatched kernel):
Unable to handle kernel paging request at virtual address ffff800041414141
Mem abort info:
ESR = 0x0000000096000004
EC = 0x25: DABT (current EL), IL = 32 bits
SET = 0, FnV = 0
EA = 0, S1PTW = 0
Data abort info:
ISV = 0, ISS = 0x00000004, ISS2 = 0x00000000
CM = 0, WnR = 0, TnD = 0, TagAccess = 0
pc : __arch_copy_to_user+0x68/0x1c0
lr : issimian_ioctl+0x21c/0x4a0 [issimian]
Call trace:
__arch_copy_to_user+0x68/0x1c0
issimian_ioctl+0x21c/0x4a0 [issimian]
__arm64_sys_ioctl+0xac/0x100
invoke_syscall+0x54/0x130
Remediation
Apply Samsung's May 2025 Android Security Maintenance Release (SMR-MAY-2025) for all affected Exynos-based Galaxy devices. No workaround is available short of revoking camera access for untrusted applications via SELinux policy, which is not a complete mitigation for privileged callers.
Galaxy Watch series (Exynos 1330 wearable variant): Firmware update via Galaxy Wearable app, May 2025 bundle.
Kernel module developers shipping custom ISP drivers should audit all ioctl handlers that accept a user-supplied index into any kernel-managed array: the index must be checked strictly against the array's runtime count using an unsigned comparison before any dereference, and any length field must be clamped to the associated object's recorded size before passing to copy_to_user or memcpy.