Skip to content

Commit a3fd7f6

Browse files
saini-ranbirspathakraul
authored andcommitted
lib: Add Management Mode service group implementation
- Includes helper implementation for MM EFI service. Co-developed-by: Sunil V L <sunilvl@ventanamicro.com> Signed-off-by: Sunil V L <sunilvl@ventanamicro.com> Signed-off-by: Ranbir Singh <rsingh@ventanamicro.com>
1 parent 5ac80ce commit a3fd7f6

5 files changed

Lines changed: 1093 additions & 0 deletions

File tree

include/librpmi.h

Lines changed: 87 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -361,6 +361,14 @@ enum rpmi_volt_service_id {
361361
RPMI_VOLT_SRV_ID_MAX,
362362
};
363363

364+
/** RPMI Management Mode (MM) ServiceGroup Service IDs */
365+
enum rpmi_mm_service_id {
366+
RPMI_MM_SRV_ENABLE_NOTIFICATION = 0x01,
367+
RPMI_MM_SRV_GET_ATTRIBUTES = 0x02,
368+
RPMI_MM_SRV_COMMUNICATE = 0x03,
369+
RPMI_MM_SRV_ID_MAX
370+
};
371+
364372
/** @} */
365373

366374
/****************************************************************************/
@@ -2013,4 +2021,83 @@ void rpmi_service_group_voltage_destroy(struct rpmi_service_group *group);
20132021

20142022
/** @} */
20152023

2024+
/******************************************************************************/
2025+
2026+
/**
2027+
* \defgroup LIBRPMI_MMSRVGRP_INTERFACE RPMI MM Service Group Library Interface
2028+
* @brief Global functions and data structures implemented by the RPMI library
2029+
* for RPMI Management Mode service group.
2030+
* @{
2031+
*/
2032+
2033+
/** Structure used for MM Communication */
2034+
struct rpmi_mm_comm_req {
2035+
rpmi_uint32_t idata_off;
2036+
rpmi_uint32_t idata_len;
2037+
rpmi_uint32_t odata_off;
2038+
rpmi_uint32_t odata_len;
2039+
};
2040+
2041+
/** Basic data type definition introduced in UEFI */
2042+
struct rpmi_guid_t {
2043+
rpmi_uint32_t data1;
2044+
rpmi_uint16_t data2;
2045+
rpmi_uint16_t data3;
2046+
rpmi_uint8_t data4[8];
2047+
};
2048+
2049+
#define GUID_LENGTH 16 /* in bytes */
2050+
2051+
/**
2052+
* Prototype of callback function pointer associated with MM service unit for
2053+
* its active handling and cleanup (if required - to be called by the library
2054+
* when the linked group is being destroyed).
2055+
*/
2056+
typedef enum rpmi_error (*srvu_callback_fn_p)(struct rpmi_shmem *shmem,
2057+
rpmi_uint16_t req_datalen,
2058+
const rpmi_uint8_t *req_data,
2059+
rpmi_uint16_t *rsp_datalen,
2060+
rpmi_uint8_t *rsp_data,
2061+
void *priv_data);
2062+
2063+
/** Structure used for MM service unit (aka GUID) registration */
2064+
struct rpmi_mm_service {
2065+
struct rpmi_guid_t guid;
2066+
srvu_callback_fn_p active_cbfn_p;
2067+
srvu_callback_fn_p delete_cbfn_p;
2068+
void *priv_data;
2069+
};
2070+
2071+
/**
2072+
* @brief Create a management mode (MM) service group instance
2073+
*
2074+
* @param[in] shmem pointer to shared memory instance
2075+
*
2076+
* @return pointer to RPMI service group instance upon success and NULL upon failure
2077+
*/
2078+
struct rpmi_service_group *rpmi_service_group_mm_create(struct rpmi_shmem *shm);
2079+
2080+
/**
2081+
* @brief Destroy (or free) a management mode (MM) service group instance
2082+
*
2083+
* @param[in] group pointer to RPMI service group instance
2084+
*/
2085+
void rpmi_service_group_mm_destroy(struct rpmi_service_group *group);
2086+
2087+
/**
2088+
* @brief Register the list of MM service units with associated information
2089+
*
2090+
* @param[in] group pointer to RPMI service group instance
2091+
* @param[in] num_entries number of entries in the given input @iplist
2092+
* @param[in] iplist list containing @num_entries having MM service
2093+
* units to be registered with attached information
2094+
*
2095+
* @return enum rpmi_error
2096+
*/
2097+
enum rpmi_error rpmi_mm_service_register(struct rpmi_service_group *group,
2098+
rpmi_uint32_t num_entries,
2099+
struct rpmi_mm_service *iplist);
2100+
2101+
/** @} */
2102+
20162103
#endif /* __LIBRPMI_H__ */

include/librpmi_mm_efi.h

Lines changed: 172 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,172 @@
1+
/* SPDX-License-Identifier: BSD-2-Clause */
2+
/*
3+
* Copyright (c) 2025 Ventana Micro Systems Inc.
4+
*/
5+
6+
#ifndef __LIBRPMI_MM_EFI_H__
7+
#define __LIBRPMI_MM_EFI_H__
8+
9+
#include <librpmi.h>
10+
11+
enum mm_efi_header_guid {
12+
MM_EFI_VAR_PROTOCOL_GUID,
13+
MM_EFI_VAR_POLICY_GUID,
14+
MM_EFI_END_OF_DXE_GUID,
15+
MM_EFI_READY_TO_BOOT_GUID,
16+
MM_EFI_EXIT_BOOT_SVC_GUID,
17+
MM_EFI_HDR_GUID_UNSUPPORTED,
18+
};
19+
20+
#define MM_EFI_VAR_PROTOCOL_GUID_DATA \
21+
{ 0xed32d533, 0x99e6, 0x4209, \
22+
{ 0x9c, 0xc0, 0x2d, 0x72, 0xcd, 0xd9, 0x98, 0xa7 } }
23+
24+
#define MM_EFI_VAR_POLICY_GUID_DATA \
25+
{ 0xda1b0d11, 0xd1a7, 0x46c4, \
26+
{ 0x9d, 0xc9, 0xf3, 0x71, 0x48, 0x75, 0xc6, 0xeb } }
27+
28+
#define MM_EFI_END_OF_DXE_GUID_DATA \
29+
{ 0x2ce967a, 0xdd7e, 0x4ffc, \
30+
{ 0x9e, 0xe7, 0x81, 0x0c, 0xf0, 0x47, 0x08, 0x80 } }
31+
32+
#define MM_EFI_READY_TO_BOOT_GUID_DATA \
33+
{ 0x7ce88fb3, 0x4bd7, 0x4679, \
34+
{ 0x87, 0xa8, 0xa8, 0xd8, 0xde, 0xe5, 0x0d, 0x2b } }
35+
36+
#define MM_EFI_EXIT_BOOT_SVC_GUID_DATA \
37+
{ 0x27abf055, 0xb1b8, 0x4c26, \
38+
{ 0x80, 0x48, 0x74, 0x8f, 0x37, 0xba, 0xa2, 0xdf } }
39+
40+
/** Basic EFI error defines */
41+
#define MAX_BIT (0x8000000000000000ULL)
42+
43+
#define ENCODE_ERROR(code) ((rpmi_uint64_t)(MAX_BIT | code))
44+
#define RETURN_ERROR(code) (((rpmi_int64_t)(rpmi_uint64_t)(code)) < 0)
45+
46+
#define EFI_SUCCESS ((rpmi_uint64_t)0)
47+
#define EFI_INVALID_PARAMETER ENCODE_ERROR(2)
48+
#define EFI_UNSUPPORTED ENCODE_ERROR(3)
49+
#define EFI_BUFFER_TOO_SMALL ENCODE_ERROR(5)
50+
#define EFI_OUT_OF_RESOURCES ENCODE_ERROR(9)
51+
#define EFI_NOT_FOUND ENCODE_ERROR(14)
52+
#define EFI_ACCESS_DENIED ENCODE_ERROR(15)
53+
54+
#define EFI_ERROR(n) RETURN_ERROR(n)
55+
56+
/**
57+
* struct mm_efi_comm_header - Header used for MM EFI communication
58+
*
59+
* @hdr_guid: guid used for disambiguation of message format
60+
* @msg_len: size of data (in bytes) - excluding size of the header
61+
* @data: an array of bytes that is msg_len in size
62+
*
63+
* To avoid confusion in interpreting frames, the communication buffer should
64+
* always begin with struct mm_efi_comm_header.
65+
*/
66+
struct mm_efi_comm_header {
67+
struct rpmi_guid_t hdr_guid;
68+
rpmi_uint64_t msg_len;
69+
rpmi_uint8_t data[];
70+
};
71+
72+
struct efi_var_policy_comm_header {
73+
rpmi_uint32_t signature;
74+
rpmi_uint32_t revision;
75+
rpmi_uint32_t command;
76+
rpmi_uint64_t result;
77+
};
78+
79+
/** The payload for this function is struct mm_var_comm_access_variable */
80+
#define EFI_VAR_FN_GET_VARIABLE 1
81+
82+
/** The payload for this function is struct mm_var_comm_get_next_var_name */
83+
#define EFI_VAR_FN_GET_NEXT_VARIABLE_NAME 2
84+
85+
/** The payload for this function is struct mm_var_comm_access_variable */
86+
#define EFI_VAR_FN_SET_VARIABLE 3
87+
88+
#define EFI_VAR_FN_QUERY_VARIABLE_INFO 4
89+
#define EFI_VAR_FN_READY_TO_BOOT 5
90+
#define EFI_VAR_FN_EXIT_BOOT_SERVICE 6
91+
#define EFI_VAR_FN_GET_STATISTICS 7
92+
#define EFI_VAR_FN_LOCK_VARIABLE 8
93+
#define EFI_VAR_FN_VAR_CHECK_VARIABLE_PROPERTY_SET 9
94+
#define EFI_VAR_FN_VAR_CHECK_VARIABLE_PROPERTY_GET 10
95+
96+
/** The payload for this function is struct efi_var_comm_get_payload_size */
97+
#define EFI_VAR_FN_GET_PAYLOAD_SIZE 11
98+
99+
#define EFI_VAR_FN_INIT_RUNTIME_VARIABLE_CACHE_CONTEXT 12
100+
#define EFI_VAR_FN_SYNC_RUNTIME_CACHE 13
101+
#define EFI_VAR_FN_GET_RUNTIME_CACHE_INFO 14
102+
103+
/** Size of MM EFI communicate header, without including the payload */
104+
#define MM_EFI_COMM_HEADER_SIZE (sizeof(struct mm_efi_comm_header) - 1)
105+
106+
/** Size of EFI variable communicate header, without including the payload */
107+
#define EFI_VAR_COMM_HEADER_SIZE (sizeof(struct efi_var_comm_header) - 1)
108+
109+
/* Max information size per MM variable: 1 KB (including header) */
110+
#define MAX_VARINFO_SIZE 1024
111+
#define MAX_PAYLOAD_SIZE (MAX_VARINFO_SIZE - EFI_VAR_COMM_HEADER_SIZE)
112+
113+
/**
114+
* This structure is used for MM variable. The communication buffer should be:
115+
* struct mm_efi_comm_header + struct efi_var_comm_header + payload
116+
*/
117+
struct efi_var_comm_header {
118+
rpmi_uint64_t function;
119+
rpmi_uint64_t return_status;
120+
rpmi_uint8_t data[];
121+
};
122+
123+
struct efi_var_get_payload_size {
124+
rpmi_uint64_t var_payload_size;
125+
};
126+
127+
/** Structure used to communicate with MM EFI via SetVariable/ GetVariable */
128+
struct efi_var_access_variable {
129+
struct rpmi_guid_t guid;
130+
rpmi_uint64_t datasize;
131+
rpmi_uint64_t namesize;
132+
rpmi_uint32_t attr;
133+
rpmi_uint16_t name[];
134+
};
135+
136+
/** Structure used to communicate with MM EFI via GetNextVariableName */
137+
struct efi_var_get_next_var_name {
138+
struct rpmi_guid_t guid;
139+
rpmi_uint64_t namesize;
140+
rpmi_uint16_t name[];
141+
};
142+
143+
/** MM EFI specific platform operations */
144+
struct rpmi_mm_efi_platform_ops {
145+
rpmi_uint64_t (*get_variable)(void *priv, const rpmi_uint8_t *data,
146+
rpmi_uint32_t datasize);
147+
148+
rpmi_uint64_t (*get_next_variable_name)(void *priv,
149+
const rpmi_uint8_t *data,
150+
rpmi_uint32_t datasize);
151+
152+
rpmi_uint64_t (*set_variable)(void *priv, const rpmi_uint8_t *data,
153+
rpmi_uint32_t datasize);
154+
};
155+
156+
/** Details required for MM EFI platform operations */
157+
struct rpmi_mm_efi {
158+
/** MM EFI platform operations */
159+
const struct rpmi_mm_efi_platform_ops *ops;
160+
161+
/** Private data of MM EFI platform operations */
162+
void *ops_priv;
163+
};
164+
165+
/**
166+
* Function to register MM EFI service units and the platform operations that
167+
* are to be attached with the MM EFI helper
168+
*/
169+
enum rpmi_error rpmi_mm_efi_register_service(struct rpmi_service_group *group,
170+
struct rpmi_mm_efi *efi);
171+
172+
#endif /* __LIBRPMI_MM_EFI_H__ */

lib/objects.mk

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66

77
lib-objs-y += rpmi_context.o
88
lib-objs-y += rpmi_hsm.o
9+
lib-objs-y += rpmi_mm_efi.o
910
lib-objs-y += rpmi_service_group_hsm.o
11+
lib-objs-y += rpmi_service_group_mm.o
1012
lib-objs-y += rpmi_service_group_sysmsi.o
1113
lib-objs-y += rpmi_service_group_sysreset.o
1214
lib-objs-y += rpmi_service_group_syssusp.o

0 commit comments

Comments
 (0)