2026-02-04 11:47 AM - last edited on 2026-02-06 5:09 AM by FBL
Following this thread Solved: USBPD EPR Source - STMicroelectronics Community
Do you have a similar guide on how to do EPR as a Sink?
2026-02-06 5:14 AM
Hi @xGloooM
I will provide a guideline as FAQ to enter EPR mode as sink.
However, as EPR voltages are not supported on our hardware, VBUS value management will be kept on 5V value for this demonstration purpose package (whatever the contract negotiated between SRC and SNK sides). This limitation does not prevent from exercising the complete USBPD EPR stack for reaching either SPR or EPR contract negotiation. This limitation could be disabled (in case management of higher voltages is managed on application side and supported by hardware), but you have to manage your power management at your own risk.
To give better visibility on the answered topics, please click on Accept as Solution on the reply which solved your issue or answered your question.
2026-02-07 3:57 AM - edited 2026-02-07 3:59 AM
I've also found strange behaviour in the stack.
After receiving PDOs in EPR mode, it calls USBPD_DPM_SetDataInfo with USBPD_CORE_DATATYPE_RCV_SRC_PDO with the Size of SPR + EPR PDOs, but empty last PDOs, which corresponds to EPR ones.
Is it a bug?
2026-02-10 6:58 AM
Hi @xGloooM
I assume you this is an implementation issue. You may need to differentiate between DPM_ListOfRcvSRCEPRPDO and DPM_ListOfRcvSRCPDO. You need to store SPR and EPR PDOs in two separate arrays.
case USBPD_CORE_DATATYPE_RCV_SRC_PDO_EPR :
if (*Size <= (USBPD_MAX_NB_PDO * 4U))
{
uint8_t* pdo;
DPM_Ports[PortNum].DPM_NumberOfRcvSRCEPRPDO = (*Size / 4U);
/* Copy EPR PDO data in DPM Handle field */
for (uint32_t index = 0; index < (*Size / 4U); index++)
{
pdo = (uint8_t*)&DPM_Ports[PortNum].DPM_ListOfRcvSRCEPRPDO[index];
(void)memcpy(pdo, (Ptr + (index * 4U)), (4U * sizeof(uint8_t)));
}
}
break;
To give better visibility on the answered topics, please click on Accept as Solution on the reply which solved your issue or answered your question.
2026-02-11 1:06 AM - edited 2026-02-11 1:09 AM
Yes, case USBPD_CORE_DATATYPE_RCV_SRC_PDO_EPR is handled separately. But the problem is inside USBPD_CORE_DATATYPE_RCV_SRC_PDO (non-EPR), where
DPM_Ports[PortNum].DPM_NumberOfRcvSRCPDO = (*Size / 4U);can't work properly after entering EPR_Mode, as the stack returns Size = 28, 28/4=7; however, SPR has only 6 PDOs and 1 EPR PDO.
I've workaround it as
uint32_t pdos_cnt = 0;
for (uint32_t index = 0; index < (Size / 4); index++)
{
rdo = (uint8_t*)&DPM_Ports[PortNum].DPM_ListOfRcvSRCPDO[index];
(void)memcpy(rdo, (Ptr + (index * 4u)), (4u * sizeof(uint8_t)));
if (*rdo != 0) {
pdos_cnt++;
}
}
DPM_Ports[PortNum].DPM_NumberOfRcvSRCPDO = pdos_cnt;