Skip to content

Commit f09e521

Browse files
committed
chore(ao_app): testing attestations and verification on GCP
1 parent 07544a8 commit f09e521

File tree

6 files changed

+595
-57
lines changed

6 files changed

+595
-57
lines changed
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
-----BEGIN CERTIFICATE-----
2+
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
37+
-----END CERTIFICATE-----
38+
-----BEGIN CERTIFICATE-----
39+
MIIGYzCCBBKgAwIBAgIDAQAAMEYGCSqGSIb3DQEBCjA5oA8wDQYJYIZIAWUDBAIC
40+
BQChHDAaBgkqhkiG9w0BAQgwDQYJYIZIAWUDBAICBQCiAwIBMKMDAgEBMHsxFDAS
41+
BgNVBAsMC0VuZ2luZWVyaW5nMQswCQYDVQQGEwJVUzEUMBIGA1UEBwwLU2FudGEg
42+
Q2xhcmExCzAJBgNVBAgMAkNBMR8wHQYDVQQKDBZBZHZhbmNlZCBNaWNybyBEZXZp
43+
Y2VzMRIwEAYDVQQDDAlBUkstTWlsYW4wHhcNMjAxMDIyMTcyMzA1WhcNNDUxMDIy
44+
MTcyMzA1WjB7MRQwEgYDVQQLDAtFbmdpbmVlcmluZzELMAkGA1UEBhMCVVMxFDAS
45+
BgNVBAcMC1NhbnRhIENsYXJhMQswCQYDVQQIDAJDQTEfMB0GA1UECgwWQWR2YW5j
46+
ZWQgTWljcm8gRGV2aWNlczESMBAGA1UEAwwJQVJLLU1pbGFuMIICIjANBgkqhkiG
47+
9w0BAQEFAAOCAg8AMIICCgKCAgEA0Ld52RJOdeiJlqK2JdsVmD7FktuotWwX1fNg
48+
W41XY9Xz1HEhSUmhLz9Cu9DHRlvgJSNxbeYYsnJfvyjx1MfU0V5tkKiU1EesNFta
49+
1kTA0szNisdYc9isqk7mXT5+KfGRbfc4V/9zRIcE8jlHN61S1ju8X93+6dxDUrG2
50+
SzxqJ4BhqyYmUDruPXJSX4vUc01P7j98MpqOS95rORdGHeI52Naz5m2B+O+vjsC0
51+
60d37jY9LFeuOP4Meri8qgfi2S5kKqg/aF6aPtuAZQVR7u3KFYXP59XmJgtcog05
52+
gmI0T/OitLhuzVvpZcLph0odh/1IPXqx3+MnjD97A7fXpqGd/y8KxX7jksTEzAOg
53+
bKAeam3lm+3yKIcTYMlsRMXPcjNbIvmsBykD//xSniusuHBkgnlENEWx1UcbQQrs
54+
+gVDkuVPhsnzIRNgYvM48Y+7LGiJYnrmE8xcrexekBxrva2V9TJQqnN3Q53kt5vi
55+
Qi3+gCfmkwC0F0tirIZbLkXPrPwzZ0M9eNxhIySb2npJfgnqz55I0u33wh4r0ZNQ
56+
eTGfw03MBUtyuzGesGkcw+loqMaq1qR4tjGbPYxCvpCq7+OgpCCoMNit2uLo9M18
57+
fHz10lOMT8nWAUvRZFzteXCm+7PHdYPlmQwUw3LvenJ/ILXoQPHfbkH0CyPfhl1j
58+
WhJFZasCAwEAAaN+MHwwDgYDVR0PAQH/BAQDAgEGMB0GA1UdDgQWBBSFrBrRQ/fI
59+
rFXUxR1BSKvVeErUUzAPBgNVHRMBAf8EBTADAQH/MDoGA1UdHwQzMDEwL6AtoCuG
60+
KWh0dHBzOi8va2RzaW50Zi5hbWQuY29tL3ZjZWsvdjEvTWlsYW4vY3JsMEYGCSqG
61+
SIb3DQEBCjA5oA8wDQYJYIZIAWUDBAICBQChHDAaBgkqhkiG9w0BAQgwDQYJYIZI
62+
AWUDBAICBQCiAwIBMKMDAgEBA4ICAQC6m0kDp6zv4Ojfgy+zleehsx6ol0ocgVel
63+
ETobpx+EuCsqVFRPK1jZ1sp/lyd9+0fQ0r66n7kagRk4Ca39g66WGTJMeJdqYriw
64+
STjjDCKVPSesWXYPVAyDhmP5n2v+BYipZWhpvqpaiO+EGK5IBP+578QeW/sSokrK
65+
dHaLAxG2LhZxj9aF73fqC7OAJZ5aPonw4RE299FVarh1Tx2eT3wSgkDgutCTB1Yq
66+
zT5DuwvAe+co2CIVIzMDamYuSFjPN0BCgojl7V+bTou7dMsqIu/TW/rPCX9/EUcp
67+
KGKqPQ3P+N9r1hjEFY1plBg93t53OOo49GNI+V1zvXPLI6xIFVsh+mto2RtgEX/e
68+
pmMKTNN6psW88qg7c1hTWtN6MbRuQ0vm+O+/2tKBF2h8THb94OvvHHoFDpbCELlq
69+
HnIYhxy0YKXGyaW1NjfULxrrmxVW4wcn5E8GddmvNa6yYm8scJagEi13mhGu4Jqh
70+
3QU3sf8iUSUr09xQDwHtOQUVIqx4maBZPBtSMf+qUDtjXSSq8lfWcd8bLr9mdsUn
71+
JZJ0+tuPMKmBnSH860llKk+VpVQsgqbzDIvOLvD6W1Umq25boxCYJ+TuBoa4s+HH
72+
CViAvgT9kf/rBq1d+ivj6skkHxuzcxbk1xv6ZGxrteJxVH7KlX7YRdZ6eARKwLe4
73+
AFZEAwoKCQ==
74+
-----END CERTIFICATE-----

src/hb_app.erl

Lines changed: 0 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -8,72 +8,15 @@
88
-behaviour(application).
99

1010
-export([start/2, stop/1]).
11-
-export([attest_key/0]).
1211

1312
-include("include/hb.hrl").
1413

1514
start(_StartType, _StartArgs) ->
1615
hb:init(),
17-
attest_key(),
1816
hb_sup:start_link(),
1917
ok = dev_scheduler_registry:start(),
2018
_TimestampServer = ar_timestamp:start(),
2119
{ok, _} = hb_http_router:start().
2220

2321
stop(_State) ->
2422
ok.
25-
26-
attest_key() ->
27-
W = hb:wallet(),
28-
Addr = ar_wallet:to_address(W),
29-
30-
% Pad the address to 32 bytes (64 hex characters) for the TPM nonce
31-
Nonce = pad_to_size(Addr, 32),
32-
33-
% Pad the address to 64 bytes (128 hex characters) for the TEE nonce
34-
TeeNonce = pad_to_size(Addr, 64),
35-
36-
% Determine tee-technology based on the existence of TEE devices
37-
TeeTech = case os:cmd("test -e /dev/tdx_guest && echo tdx || (test -e /dev/sev_guest && echo sev-snp)") of
38-
"tdx\n" -> "tdx";
39-
"sev-snp\n" -> "sev-snp";
40-
_ -> {error, "No TEE device found"}
41-
end,
42-
43-
% Proceed if a valid TEE technology is found
44-
case TeeTech of
45-
{error, _} -> {error, "Required TEE device not found"};
46-
_ ->
47-
Cmd = lists:flatten(io_lib:format("sudo gotpm attest --key AK --nonce ~s --tee-nonce ~s --tee-technology ~s", [Nonce, TeeNonce, TeeTech])),
48-
CommandResult = os:cmd(Cmd),
49-
case is_list(CommandResult) of
50-
true ->
51-
% If CommandResult is a list of integers, convert it to binary
52-
BinaryResult = list_to_binary(CommandResult),
53-
?event(BinaryResult),
54-
Signed = ar_bundles:sign_item(
55-
#tx{
56-
tags = [
57-
{<<"Type">>, <<"TEE-Attestation">>},
58-
{<<"Address">>, hb_util:id(Addr)}
59-
],
60-
data = BinaryResult
61-
},
62-
W
63-
),
64-
?event(Signed),
65-
hb_client:upload(Signed),
66-
ok;
67-
false ->
68-
{error, "Unexpected output format from gotpm attest command"}
69-
end
70-
end.
71-
72-
% Pads an address to the specified byte size (in hex characters)
73-
pad_to_size(Addr, SizeInBytes) ->
74-
HexAddr = binary:encode_hex(Addr),
75-
RequiredLength = SizeInBytes * 2, % Convert bytes to hex characters
76-
Padding = RequiredLength - byte_size(HexAddr),
77-
lists:duplicate(Padding, $0) ++ HexAddr.
78-
79-
%% internal functions

src/sec.erl

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,105 @@
1+
%%%---------------------------------------------------------------------
2+
%%% Module: sec
3+
%%%---------------------------------------------------------------------
4+
%%% Purpose:
5+
%%% This module handles the generation and verification of attestation
6+
%%% reports using both TPM and SEV-SNP. It combines attestation reports
7+
%%% from both technologies into a single binary and provides functionality
8+
%%% to verify the combined reports.
9+
%%%
10+
%%% It uses the `sec_tpm` and `sec_tee` modules to interact with the TPM
11+
%%% hardware and SEV-SNP for generating and verifying attestation reports.
12+
%%%---------------------------------------------------------------------
13+
%%% Exports
14+
%%%---------------------------------------------------------------------
15+
%%% generate_attestation(Nonce)
16+
%%% Generates a combined attestation report using the provided nonce.
17+
%%% It generates attestation reports from both TPM and SEV-SNP, calculates
18+
%%% their sizes, creates a header containing the sizes, and combines them
19+
%%% into a single binary.
20+
%%%
21+
%%% verify_attestation(AttestationBinary)
22+
%%% Verifies the provided attestation binary by extracting the TPM and
23+
%%% SEV-SNP reports, verifying them using their respective verification
24+
%%% methods, and then combining the results into a single binary.
25+
%%%---------------------------------------------------------------------
26+
27+
-module(sec).
28+
-export([generate_attestation/1, verify_attestation/1]).
29+
30+
-include("include/ao.hrl").
31+
32+
-ao_debug(print).
33+
34+
%% Generate attestation based on the provided nonce (both TPM and SEV-SNP)
35+
generate_attestation(Nonce) ->
36+
?c({"Generating TPM attestation..."}),
37+
38+
case sec_tpm:generate_attestation(Nonce) of
39+
{ok, TPMAttestation} ->
40+
?c({"TPM attestation generated, size:", byte_size(TPMAttestation)}),
41+
42+
?c({"Generating SEV-SNP attestation..."}),
43+
44+
case sec_tee:generate_attestation(Nonce) of
45+
{ok, TEEAttestation} ->
46+
?c({"SEV-SNP attestation generated, size:", byte_size(TEEAttestation)}),
47+
48+
%% Calculate sizes of the two attestation binaries
49+
TPMSize = byte_size(TPMAttestation),
50+
TEESize = byte_size(TEEAttestation),
51+
52+
%% Create the header containing the sizes
53+
Header = <<TPMSize:32/unit:8, TEESize:32/unit:8>>,
54+
?c({"Header created, TPMSize:", TPMSize, "TEESize:", TEESize}),
55+
56+
%% Combine the header with the two attestation binaries
57+
CombinedAttestation = <<Header/binary, TPMAttestation/binary, TEEAttestation/binary>>,
58+
?c({"Combined attestation binary created, total size:", byte_size(CombinedAttestation)}),
59+
60+
{ok, CombinedAttestation};
61+
62+
{error, Reason} ->
63+
?c({"Error generating SEV-SNP attestation:", Reason}),
64+
{error, Reason}
65+
end;
66+
67+
{error, Reason} ->
68+
?c({"Error generating TPM attestation:", Reason}),
69+
{error, Reason}
70+
end.
71+
72+
%% Verify attestation report based on the provided binary (both TPM and SEV-SNP)
73+
verify_attestation(AttestationBinary) ->
74+
?c("Verifying attestation..."),
75+
76+
%% Extract the header (size info) and the attestation binaries
77+
<<TPMSize:32/unit:8, TEESize:32/unit:8, Rest/binary>> = AttestationBinary,
78+
?c({"Header extracted, TPMSize:", TPMSize, "TEESize:", TEESize}),
79+
80+
%% Extract the TPM and SEV-SNP attestation binaries based on their sizes
81+
<<TPMAttestation:TPMSize/binary, TEEAttestation:TEESize/binary>> = Rest,
82+
?c({"Extracted TPM and SEV-SNP attestation binaries"}),
83+
84+
%% Verify TPM attestation
85+
case sec_tpm:verify_attestation(TPMAttestation) of
86+
{ok, _TPMVerification} ->
87+
?c({"TPM attestation verification completed"}),
88+
89+
%% Verify SEV-SNP attestation
90+
case sec_tee:verify_attestation(TEEAttestation) of
91+
{ok, _TEEVerification} ->
92+
?c({"SEV-SNP attestation verification completed"}),
93+
94+
%% Return success if both verifications succeeded
95+
{ok, "Verified"};
96+
97+
{error, Reason} ->
98+
?c({"Error verifying SEV-SNP attestation:", Reason}),
99+
{error, Reason}
100+
end;
101+
102+
{error, Reason} ->
103+
?c({"Error verifying TPM attestation:", Reason}),
104+
{error, Reason}
105+
end.

src/sec_helpers.erl

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
-module(sec_helpers).
2+
-export([write_to_file/2, read_file/1, run_command/1]).
3+
4+
-include("include/ao.hrl").
5+
-ao_debug(print).
6+
7+
%% Helper function to write data to a file
8+
write_to_file(FilePath, Data) ->
9+
case file:write_file(FilePath, Data) of
10+
ok -> ?c({"Written data to file", FilePath});
11+
{error, Reason} -> ?c({"Failed to write to file", FilePath, Reason})
12+
end.
13+
14+
%% Helper function to read a file
15+
read_file(FilePath) ->
16+
?c({"Reading file", FilePath}),
17+
case file:read_file(FilePath) of
18+
{ok, Data} -> {FilePath, binary:bin_to_list(Data)};
19+
{error, Reason} -> {error, Reason}
20+
end.
21+
22+
%% Generalized function to run a shell command and optionally apply a success function
23+
%% When SuccessFun is provided, it is called upon successful execution
24+
run_command(Command) ->
25+
?c({"Executing command", Command}),
26+
Output = os:cmd(Command ++ " 2>&1"),
27+
case Output of
28+
"" -> {ok, []}; % Empty output interpreted as success if no output is expected
29+
_ -> {ok, Output} % Return output for further inspection
30+
end.

0 commit comments

Comments
 (0)