Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions Documentation/userspace-api/ioctl/ioctl-number.rst
Original file line number Diff line number Diff line change
Expand Up @@ -412,4 +412,5 @@ Code Seq# Include File Comments
<mailto:naveenkrishna.chatradhi@amd.com>
0xFD all linux/dm-ioctl.h
0xFE all linux/isst_if.h
0xFF 00-0F uapi/linux/ocp_svsm.h
==== ===== ========================================================= ================================================================
9 changes: 9 additions & 0 deletions arch/x86/coco/sev/core.c
Original file line number Diff line number Diff line change
Expand Up @@ -1395,6 +1395,11 @@ static struct platform_device tpm_svsm_device = {
.id = -1,
};

static struct platform_device ocp_svsm_device = {
.name = "ocp-svsm",
.id = -1,
};

static int __init snp_init_platform_device(void)
{
if (!cc_platform_has(CC_ATTR_GUEST_SEV_SNP))
Expand All @@ -1407,6 +1412,10 @@ static int __init snp_init_platform_device(void)
platform_device_register(&tpm_svsm_device))
return -ENODEV;

// TODO: add probe like above
if (platform_device_register(&ocp_svsm_device))
return -ENODEV;

pr_info("SNP guest platform devices initialized.\n");
return 0;
}
Expand Down
96 changes: 96 additions & 0 deletions arch/x86/coco/sev/svsm.c
Original file line number Diff line number Diff line change
Expand Up @@ -360,3 +360,99 @@ bool snp_svsm_vtpm_probe(void)
/* Check platform commands contains TPM_SEND_COMMAND - platform command 8 */
return call.rcx_out & BIT_ULL(8);
}

int snp_svsm_ocp_list_objects(u8 *buffer, u64 first_entry, u64 num_entries,
u32 *entries_returned)
{
struct svsm_call call = {};
int ret;

call.caa = svsm_get_caa();
call.rax = SVSM_OCP_CALL(SVSM_OCP_LIST_OBJECTS);
call.rcx = first_entry;
call.rdx = __pa(buffer);
call.r8 = num_entries;

ret = svsm_perform_call_protocol(&call);

if (ret < 0) {
return ret;
}

*entries_returned = call.rcx_out;
return 0;
}
EXPORT_SYMBOL_GPL(snp_svsm_ocp_list_objects);

int snp_svsm_ocp_list_object_sources(u8 *buffer, u32 object_entry,
u32 first_entry, u64 num_entries,
u32 *entries_returned)
{
struct svsm_call call = {};
int ret;

call.caa = svsm_get_caa();
call.rax = SVSM_OCP_CALL(SVSM_OCP_LIST_OBJECT_SOURCES);
call.rcx = ((u64)object_entry << 32) | first_entry;
call.rdx = __pa(buffer);
call.r8 = num_entries;

ret = svsm_perform_call_protocol(&call);

if (ret < 0) {
return ret;
}

*entries_returned = call.rcx_out;
return 0;
}
EXPORT_SYMBOL_GPL(snp_svsm_ocp_list_object_sources);

int snp_svsm_ocp_read_source(u8 *buffer, u32 object_entry, u32 source_idx,
u64 bytes_to_read, u64 offset, u32 *bytes_read)
{
struct svsm_call call = {};
int ret;

call.caa = svsm_get_caa();
call.rax = SVSM_OCP_CALL(SVSM_OCP_READ);
call.rcx = ((u64)object_entry << 32) | source_idx;
call.rdx = __pa(buffer);
call.r8 = bytes_to_read;
call.r9 = offset;

ret = svsm_perform_call_protocol(&call);

if (ret < 0) {
return ret;
}

*bytes_read = call.r8_out;
return 0;
}
EXPORT_SYMBOL_GPL(snp_svsm_ocp_read_source);

int snp_svsm_ocp_write_source(u8 *buffer, u32 object_entry, u32 source_idx,
u64 bytes_to_write, u64 offset,
u32 *bytes_written)
{
struct svsm_call call = {};
int ret;

call.caa = svsm_get_caa();
call.rax = SVSM_OCP_CALL(SVSM_OCP_WRITE);
call.rcx = ((u64)object_entry << 32) | source_idx;
call.rdx = __pa(buffer);
call.r8 = bytes_to_write;
call.r9 = offset;

ret = svsm_perform_call_protocol(&call);

if (ret < 0) {
return ret;
}

*bytes_written = call.r8_out;
return 0;
}
EXPORT_SYMBOL_GPL(snp_svsm_ocp_write_source);
39 changes: 39 additions & 0 deletions arch/x86/include/asm/sev.h
Original file line number Diff line number Diff line change
Expand Up @@ -435,6 +435,12 @@ struct svsm_call {
#define SVSM_VTPM_QUERY 0
#define SVSM_VTPM_CMD 1

#define SVSM_OCP_CALL(x) ((5ULL << 32) | (x))
#define SVSM_OCP_LIST_OBJECTS 0
#define SVSM_OCP_LIST_OBJECT_SOURCES 1
#define SVSM_OCP_READ 2
#define SVSM_OCP_WRITE 3

#ifdef CONFIG_AMD_MEM_ENCRYPT

extern u8 snp_vmpl;
Expand Down Expand Up @@ -528,6 +534,16 @@ void snp_msg_free(struct snp_msg_desc *mdesc);
int snp_send_guest_request(struct snp_msg_desc *mdesc, struct snp_guest_req *req);

int snp_svsm_vtpm_send_command(u8 *buffer);
int snp_svsm_ocp_list_objects(u8 *buffer, u64 first_entry, u64 num_entries,
u32 *entries_returned);
int snp_svsm_ocp_list_object_sources(u8 *buffer, u32 object_entry,
u32 first_entry, u64 num_entries,
u32 *entries_returned);
int snp_svsm_ocp_read_source(u8 *buffer, u32 object_entry, u32 source_idx,
u64 bytes_to_read, u64 offset, u32 *bytes_read);
int snp_svsm_ocp_write_source(u8 *buffer, u32 object_entry, u32 source_idx,
u64 bytes_to_write, u64 offset,
u32 *bytes_written);

void __init snp_secure_tsc_prepare(void);
void __init snp_secure_tsc_init(void);
Expand Down Expand Up @@ -636,6 +652,29 @@ static inline void snp_msg_free(struct snp_msg_desc *mdesc) { }
static inline int snp_send_guest_request(struct snp_msg_desc *mdesc,
struct snp_guest_req *req) { return -ENODEV; }
static inline int snp_svsm_vtpm_send_command(u8 *buffer) { return -ENODEV; }
static int snp_svsm_ocp_list_objects(u8 *buffer, u64 first_entry,
u64 num_entries, u32 *entries_returned)
{
return -ENODEV;
}
static int snp_svsm_ocp_list_object_sources(u8 *buffer, u32 object_entry,
u32 first_entry, u64 num_entries,
u32 *entries_returned)
{
return -ENODEV;
}
static int snp_svsm_ocp_read_source(u8 *buffer, u32 object_entry,
u32 source_idx, u64 bytes_to_read,
u64 offset, u32 *bytes_read)
{
return -ENODEV;
}
static int snp_svsm_ocp_write_source(u8 *buffer, u32 object_entry,
u32 source_idx, u64 bytes_to_write,
u64 offset, u32 *bytes_written)
{
return -ENODEV;
}
static inline void __init snp_secure_tsc_prepare(void) { }
static inline void __init snp_secure_tsc_init(void) { }
static inline void sev_evict_cache(void *va, int npages) {}
Expand Down
10 changes: 10 additions & 0 deletions drivers/char/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -397,4 +397,14 @@ config ADI
and SSM (Silicon Secured Memory). Intended consumers of this
driver include crash and makedumpfile.

config OCP_SVSM
tristate "SNP SVSM OCP interface"
depends on AMD_MEM_ENCRYPT
default m
help
This is a driver for the AMD SVSM OCP protocol that a SEV-SNP guest
OS can use to retrieve or configure state information of the Secure
VM Service Module (SVSM) in the guest context. To compile this
driver, choose M here.

endmenu
2 changes: 2 additions & 0 deletions drivers/char/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -43,3 +43,5 @@ obj-$(CONFIG_PS3_FLASH) += ps3flash.o
obj-$(CONFIG_XILLYBUS_CLASS) += xillybus/
obj-$(CONFIG_POWERNV_OP_PANEL) += powernv-op-panel.o
obj-$(CONFIG_ADI) += adi.o

obj-$(CONFIG_OCP_SVSM) += ocp_svsm.o
Loading