github.com/epfl-dcsl/gotee@v0.0.0-20200909122901-014b35f5e5e9/src/gosec/signature.go (about) 1 package gosec 2 3 import ( 4 "bytes" 5 "crypto/sha256" 6 "encoding/binary" 7 "encoding/gob" 8 "io/ioutil" 9 "os" 10 "os/exec" 11 "time" 12 "unsafe" 13 ) 14 15 const ( 16 target = "/tmp/gobdump.dat" 17 _enclaveCssSize = uintptr(1808) 18 _miscselectSize = uintptr(4) 19 _attribSize = uintptr(16) 20 _measurementSize = uintptr(SGX_HASH_SIZE) 21 _tcs_t_size = uintptr(0x1000) 22 ) 23 24 var data2hash []byte = nil 25 var meta *metadata_t 26 27 func checkStructSize() { 28 if unsafe.Sizeof(enclave_css_t{}) != _enclaveCssSize { 29 panic("Wrong size for the enclave css.") 30 } 31 32 if unsafe.Sizeof(miscselect_t{}) != _miscselectSize { 33 panic("Wrong size for the miscseclect") 34 } 35 36 if unsafe.Sizeof(sgx_attributes_t{}) != _attribSize { 37 panic("Wrong size for the sgx_attributes.") 38 } 39 40 if unsafe.Sizeof(sgx_measurement_t{}) != _measurementSize { 41 panic("Wrong size for the sgx_measurement") 42 } 43 44 if unsafe.Sizeof(tcs_t{}) != _tcs_t_size { 45 panic("Wrong size for the tcs_t") 46 } 47 } 48 49 func sgxHashInit() { 50 checkStructSize() 51 data2hash = make([]byte, 0) 52 meta = &metadata_t{} 53 setHeader(&meta.Enclave_css) 54 setBody(&meta.Enclave_css) 55 meta.Magic_num = METADATA_MAGIC 56 meta.Version = METADATA_VERSION 57 meta.Tcs_policy = 1 58 meta.Max_save_buffer_size = 2632 59 meta.Desired_misc_select = 0 60 meta.Tcs_min_pool = 1 61 62 } 63 64 func setHeader(e *enclave_css_t) { 65 e.Header = [12]uint8{6, 0, 0, 0, 0xE1, 0, 0, 0, 0, 0, 1, 0} 66 e.Header2 = [16]uint8{1, 1, 0, 0, 0x60, 0, 0, 0, 0x60, 0, 0, 0, 1, 0, 0, 0} 67 //TODO trying to see if dbg works. 68 e.Tpe = 0 //uint32(TPE_DBG) 69 e.Module_vendor = 0 70 year, month, day := time.Now().Date() 71 e.Date = uint32(day + (int(month) << 8) + (year % 100 << 16) + (year / 100 << 24)) 72 e.Hw_version = 0 73 for i := range e.Reserved { 74 e.Reserved[i] = 0 75 } 76 } 77 78 func setBody(e *enclave_css_t) { 79 e.Misc_mask.Value = 0xff 80 for i := range e.Misc_mask.Reversed2 { 81 e.Misc_mask.Reversed2[i] = 0xff 82 } 83 e.Isv_prod_id = 0 84 e.Isv_svn = 42 85 } 86 87 func sgxHashEcreate(secs *secs_t) { 88 meta.Enclave_size = secs.size 89 meta.Attributes.Flags = secs.attributes 90 meta.Attributes.Xfrm = secs.xfrm 91 92 tmp := make([]byte, 64) 93 offset := 0 94 95 eheader := []byte("ECREATE\000") 96 if len(eheader) != 8 { 97 panic("header has incorrect size.") 98 } 99 memcpy_s(tmp, eheader, offset, 8) 100 offset += 8 101 102 //ssaFS := make([]byte, 8) 103 //binary.LittleEndian.PutUint64(ssaFS, uint64(secs.ssaFrameSize)) 104 //memcpy_s(tmp, ssaFS, offset, 8) 105 //offset += 8 106 ssaFS := make([]byte, 4) 107 binary.LittleEndian.PutUint32(ssaFS, secs.ssaFrameSize) 108 memcpy_s(tmp, ssaFS, offset, 4) 109 offset += 4 110 111 secSize := make([]byte, 8) 112 binary.LittleEndian.PutUint64(secSize, secs.size) 113 memcpy_s(tmp, secSize, offset, 8) 114 offset += 8 115 for i := offset; i < len(tmp); i++ { 116 tmp[i] = byte(0) 117 } 118 119 // Append it to the hash. 120 data2hash = append(data2hash, tmp...) 121 } 122 123 func sgxHashEadd(secs *secs_t, secinfo *isgx_secinfo, daddr uintptr) { 124 if daddr < uintptr(secs.baseAddr) { 125 panic("gosec: invalid daddr out of range.") 126 } 127 tmp := make([]byte, 64) 128 offset := 0 129 130 eheader := []byte("EADD\000\000\000\000") 131 if len(eheader) != 8 { 132 panic("EADD hash has not the correct size.") 133 } 134 memcpy_s(tmp, eheader, offset, 8) 135 offset += 8 136 137 off := uint64(daddr) - secs.baseAddr 138 encloff := make([]byte, 8) 139 binary.LittleEndian.PutUint64(encloff, off) 140 memcpy_s(tmp, encloff, offset, 8) 141 offset += 8 142 143 flags := make([]byte, 8) 144 binary.LittleEndian.PutUint64(flags, secinfo.flags) 145 memcpy_s(tmp, flags, offset, 8) 146 offset += 8 147 148 base := unsafe.Pointer(&secinfo.reserved) 149 for i := offset; i < len(tmp); i++ { 150 val := (*byte)(unsafe.Pointer(uintptr(base) + uintptr(i-offset))) 151 tmp[i] = *val 152 } 153 // Add it to the signature. 154 data2hash = append(data2hash, tmp...) 155 156 if secinfo.flags&SGX_SECINFO_W == 0 || secinfo.flags&SGX_SECINFO_TCS != 0 { 157 sgxHashEExtendRegion(secs, daddr) 158 } 159 160 } 161 162 func sgxHashEExtend(secs *secs_t, daddr uintptr) { 163 if daddr < uintptr(secs.baseAddr) || daddr > uintptr(secs.baseAddr)+uintptr(secs.size) { 164 panic("gosec: invalid daddr out of range.") 165 } 166 tmp := make([]byte, 320) 167 offset := 0 168 169 eheader := []byte("EEXTEND\000") 170 if len(eheader) != 8 { 171 panic("EEXTEND has not the correct size.") 172 } 173 memcpy_s(tmp, eheader, offset, 8) 174 offset += 8 175 176 off := uint64(uint64(daddr) - secs.baseAddr) 177 encloff := make([]byte, 8) 178 binary.LittleEndian.PutUint64(encloff, off) 179 memcpy_s(tmp, encloff, offset, 8) 180 offset += 8 181 182 // TODO 48 0 bytes. 183 offset += 48 184 base := transposeOut(daddr) 185 for i := uintptr(0); i < uintptr(256); i++ { 186 val := (*byte)(unsafe.Pointer(base + i)) 187 tmp[int(i)+offset] = *val 188 } 189 data2hash = append(data2hash, tmp...) 190 } 191 192 // Adds a full page to the eextend 193 func sgxHashEExtendRegion(secs *secs_t, daddr uintptr) { 194 for i := uintptr(0); i < PSIZE; i += uintptr(256) { 195 sgxHashEExtend(secs, daddr+i) 196 } 197 } 198 199 func sgxHashFinalize() { 200 sig := sha256.Sum256(data2hash) 201 for i := 0; i < SGX_HASH_SIZE; i++ { 202 meta.Enclave_css.Enclave_hash.M[i] = sig[i] 203 } 204 205 //Do a dump of the measurement here. 206 err := ioutil.WriteFile("/tmp/gosec_measurement.dat", data2hash, 0644) 207 check(err) 208 } 209 210 func sgxTokenGetRequest(secs *secs_t) *LaunchTokenRequest { 211 tokenreq := &LaunchTokenRequest{} 212 tokenreq.MrSigner = []byte("trying") // key modulus. 213 tokenreq.MrEnclave = meta.Enclave_css.Enclave_hash.M[:] 214 215 seattrib := make([]byte, 0) 216 217 attrib := make([]byte, 8) 218 binary.LittleEndian.PutUint64(attrib, secs.attributes) 219 seattrib = append(seattrib, attrib...) 220 221 xflags := make([]byte, 8) 222 binary.LittleEndian.PutUint64(xflags, secs.xfrm) 223 seattrib = append(seattrib, xflags...) 224 225 tokenreq.SeAttributes = seattrib 226 return tokenreq 227 } 228 229 func sgxTokenGetAesm(secs *secs_t) TokenGob { 230 request := sgxTokenGetRequest(secs) 231 232 f, err := os.Create("/tmp/gobdump_meta.dat") 233 check(err) 234 235 enc := gob.NewEncoder(f) 236 err = enc.Encode(meta) 237 check(err) 238 239 f2, err := os.Create("/tmp/gobdump_req.dat") 240 check(err) 241 enc = gob.NewEncoder(f2) 242 err = enc.Encode(request) 243 check(err) 244 245 cmd := exec.Command("serializer", "") 246 err = cmd.Run() 247 check(err) 248 249 // Read the token. 250 b, err := ioutil.ReadFile("/tmp/go_enclave.token") 251 check(err) 252 253 dec := gob.NewDecoder(bytes.NewReader(b)) 254 var token TokenGob 255 err = dec.Decode(&token) 256 check(err) 257 return token 258 } 259 260 func memcpy_s(dst, src []byte, off, s int) { 261 for i := 0; i < s; i++ { 262 dst[off+i] = src[i] 263 } 264 }