@@ -378,7 +378,127 @@ TEST_F(enclave, unclobbered_vdso_oversubscribed)
378
378
EXPECT_EQ (get_op .value , MAGIC );
379
379
EXPECT_EEXIT (& self -> run );
380
380
EXPECT_EQ (self -> run .user_data , 0 );
381
+ }
382
+
383
+ TEST_F_TIMEOUT (enclave , unclobbered_vdso_oversubscribed_remove , 900 )
384
+ {
385
+ struct sgx_enclave_remove_pages remove_ioc ;
386
+ struct sgx_enclave_modify_types modt_ioc ;
387
+ struct encl_op_get_from_buf get_op ;
388
+ struct encl_op_eaccept eaccept_op ;
389
+ struct encl_op_put_to_buf put_op ;
390
+ struct encl_segment * heap ;
391
+ unsigned long total_mem ;
392
+ int ret , errno_save ;
393
+ unsigned long addr ;
394
+ unsigned long i ;
395
+
396
+ /*
397
+ * Create enclave with additional heap that is as big as all
398
+ * available physical SGX memory.
399
+ */
400
+ total_mem = get_total_epc_mem ();
401
+ ASSERT_NE (total_mem , 0 );
402
+ TH_LOG ("Creating an enclave with %lu bytes heap may take a while ..." ,
403
+ total_mem );
404
+ ASSERT_TRUE (setup_test_encl (total_mem , & self -> encl , _metadata ));
405
+
406
+ /*
407
+ * Hardware (SGX2) and kernel support is needed for this test. Start
408
+ * with check that test has a chance of succeeding.
409
+ */
410
+ memset (& modt_ioc , 0 , sizeof (modt_ioc ));
411
+ ret = ioctl (self -> encl .fd , SGX_IOC_ENCLAVE_MODIFY_TYPES , & modt_ioc );
412
+
413
+ if (ret == -1 ) {
414
+ if (errno == ENOTTY )
415
+ SKIP (return ,
416
+ "Kernel does not support SGX_IOC_ENCLAVE_MODIFY_TYPES ioctl()" );
417
+ else if (errno == ENODEV )
418
+ SKIP (return , "System does not support SGX2" );
419
+ }
420
+
421
+ /*
422
+ * Invalid parameters were provided during sanity check,
423
+ * expect command to fail.
424
+ */
425
+ EXPECT_EQ (ret , -1 );
426
+
427
+ /* SGX2 is supported by kernel and hardware, test can proceed. */
428
+ memset (& self -> run , 0 , sizeof (self -> run ));
429
+ self -> run .tcs = self -> encl .encl_base ;
430
+
431
+ heap = & self -> encl .segment_tbl [self -> encl .nr_segments - 1 ];
432
+
433
+ put_op .header .type = ENCL_OP_PUT_TO_BUFFER ;
434
+ put_op .value = MAGIC ;
435
+
436
+ EXPECT_EQ (ENCL_CALL (& put_op , & self -> run , false), 0 );
437
+
438
+ EXPECT_EEXIT (& self -> run );
439
+ EXPECT_EQ (self -> run .user_data , 0 );
440
+
441
+ get_op .header .type = ENCL_OP_GET_FROM_BUFFER ;
442
+ get_op .value = 0 ;
443
+
444
+ EXPECT_EQ (ENCL_CALL (& get_op , & self -> run , false), 0 );
445
+
446
+ EXPECT_EQ (get_op .value , MAGIC );
447
+ EXPECT_EEXIT (& self -> run );
448
+ EXPECT_EQ (self -> run .user_data , 0 );
381
449
450
+ /* Trim entire heap. */
451
+ memset (& modt_ioc , 0 , sizeof (modt_ioc ));
452
+
453
+ modt_ioc .offset = heap -> offset ;
454
+ modt_ioc .length = heap -> size ;
455
+ modt_ioc .page_type = SGX_PAGE_TYPE_TRIM ;
456
+
457
+ TH_LOG ("Changing type of %zd bytes to trimmed may take a while ..." ,
458
+ heap -> size );
459
+ ret = ioctl (self -> encl .fd , SGX_IOC_ENCLAVE_MODIFY_TYPES , & modt_ioc );
460
+ errno_save = ret == -1 ? errno : 0 ;
461
+
462
+ EXPECT_EQ (ret , 0 );
463
+ EXPECT_EQ (errno_save , 0 );
464
+ EXPECT_EQ (modt_ioc .result , 0 );
465
+ EXPECT_EQ (modt_ioc .count , heap -> size );
466
+
467
+ /* EACCEPT all removed pages. */
468
+ addr = self -> encl .encl_base + heap -> offset ;
469
+
470
+ eaccept_op .flags = SGX_SECINFO_TRIM | SGX_SECINFO_MODIFIED ;
471
+ eaccept_op .header .type = ENCL_OP_EACCEPT ;
472
+
473
+ TH_LOG ("Entering enclave to run EACCEPT for each page of %zd bytes may take a while ..." ,
474
+ heap -> size );
475
+ for (i = 0 ; i < heap -> size ; i += 4096 ) {
476
+ eaccept_op .epc_addr = addr + i ;
477
+ eaccept_op .ret = 0 ;
478
+
479
+ EXPECT_EQ (ENCL_CALL (& eaccept_op , & self -> run , true), 0 );
480
+
481
+ EXPECT_EQ (self -> run .exception_vector , 0 );
482
+ EXPECT_EQ (self -> run .exception_error_code , 0 );
483
+ EXPECT_EQ (self -> run .exception_addr , 0 );
484
+ ASSERT_EQ (eaccept_op .ret , 0 );
485
+ ASSERT_EQ (self -> run .function , EEXIT );
486
+ }
487
+
488
+ /* Complete page removal. */
489
+ memset (& remove_ioc , 0 , sizeof (remove_ioc ));
490
+
491
+ remove_ioc .offset = heap -> offset ;
492
+ remove_ioc .length = heap -> size ;
493
+
494
+ TH_LOG ("Removing %zd bytes from enclave may take a while ..." ,
495
+ heap -> size );
496
+ ret = ioctl (self -> encl .fd , SGX_IOC_ENCLAVE_REMOVE_PAGES , & remove_ioc );
497
+ errno_save = ret == -1 ? errno : 0 ;
498
+
499
+ EXPECT_EQ (ret , 0 );
500
+ EXPECT_EQ (errno_save , 0 );
501
+ EXPECT_EQ (remove_ioc .count , heap -> size );
382
502
}
383
503
384
504
TEST_F (enclave , clobbered_vdso )
0 commit comments