main.go raw

   1  package main
   2  
   3  import (
   4  	"bytes"
   5  	"os"
   6  	"strconv"
   7  	"unsafe"
   8  )
   9  
  10  // Milestone-4 verification: memfd_secret(2) upgrade path.
  11  //
  12  // On Linux ≥5.14 secureMap attempts to replace the anonymous data pages of a
  13  // secure arena with pages backed by memfd_secret(2). This test observes the
  14  // outcome by parsing /proc/self/maps: each mapping line starts with the VA
  15  // range (hex-hex) followed by protection, offset, device, inode, and the
  16  // pathname. memfd_secret mappings show as "/memfd:secretmem (deleted)" in
  17  // the pathname — deleted because we close the fd right after mmap to keep
  18  // the mapping alive without retaining an fd table entry.
  19  //
  20  // Expected outcomes:
  21  //   - Kernel ≥5.14 with secretmem enabled: SECRETMEM_OK on stdout.
  22  //   - Older kernel or Darwin: ANONYMOUS_FALLBACK on stdout. (Still secure via
  23  //     mlock + guard pages.)
  24  //
  25  // The test runner decides which outcome to assert based on the host kernel.
  26  
  27  func main() {
  28  	secret := []byte{:32, secure}
  29  	copy(secret, []byte("MOXIE_M4_SECRETMEM_PROBE_BYTES_A"))
  30  
  31  	addr := uintptr(unsafe.Pointer(&secret[0]))
  32  	os.Stdout.Write([]byte("ADDR="))
  33  	os.Stdout.Write([]byte(strconv.FormatUint(uint64(addr), 16)))
  34  	os.Stdout.Write([]byte("\n"))
  35  
  36  	maps, err := os.ReadFile("/proc/self/maps")
  37  	if err != nil {
  38  		os.Stderr.Write([]byte("FAIL: could not read /proc/self/maps: "))
  39  		os.Stderr.Write([]byte(err.Error()))
  40  		os.Stderr.Write([]byte("\n"))
  41  		os.Exit(1)
  42  	}
  43  
  44  	var matched []byte
  45  	for _, line := range bytes.Split(maps, []byte("\n")) {
  46  		dash := bytes.IndexByte(line, '-')
  47  		if dash <= 0 {
  48  			continue
  49  		}
  50  		space := bytes.IndexByte(line, ' ')
  51  		if space <= dash+1 {
  52  			continue
  53  		}
  54  		start, errS := strconv.ParseUint(string(line[:dash]), 16, 64)
  55  		if errS != nil {
  56  			continue
  57  		}
  58  		end, errE := strconv.ParseUint(string(line[dash+1:space]), 16, 64)
  59  		if errE != nil {
  60  			continue
  61  		}
  62  		if uint64(addr) >= start && uint64(addr) < end {
  63  			matched = line
  64  			break
  65  		}
  66  	}
  67  
  68  	if matched == nil {
  69  		os.Stderr.Write([]byte("FAIL: arena VA not found in /proc/self/maps\n"))
  70  		os.Exit(1)
  71  	}
  72  
  73  	os.Stdout.Write([]byte("MATCH="))
  74  	os.Stdout.Write(matched)
  75  	os.Stdout.Write([]byte("\n"))
  76  
  77  	if bytes.Contains(matched, []byte("secretmem")) {
  78  		os.Stdout.Write([]byte("SECRETMEM_OK\n"))
  79  	} else {
  80  		os.Stdout.Write([]byte("ANONYMOUS_FALLBACK\n"))
  81  	}
  82  }
  83