439 lines
13 KiB
C
439 lines
13 KiB
C
/* USER CODE BEGIN Header */
|
|
/**
|
|
******************************************************************************
|
|
* @file usbpd_pwr_if.c
|
|
* @author MCD Application Team
|
|
* @brief This file contains power interface control functions.
|
|
******************************************************************************
|
|
* @attention
|
|
*
|
|
* <h2><center>© Copyright (c) 2020 STMicroelectronics.
|
|
* All rights reserved.</center></h2>
|
|
*
|
|
* This software component is licensed by ST under Ultimate Liberty license
|
|
* SLA0044, the "License"; You may not use this file except in compliance with
|
|
* the License. You may obtain a copy of the License at:
|
|
* www.st.com/SLA0044
|
|
*
|
|
******************************************************************************
|
|
*/
|
|
/* USER CODE END Header */
|
|
|
|
#define __USBPD_PWR_IF_C
|
|
|
|
/* Includes ------------------------------------------------------------------*/
|
|
#include "usbpd_pwr_if.h"
|
|
#include "usbpd_hw_if.h"
|
|
#include "usbpd_dpm_core.h"
|
|
#include "usbpd_dpm_conf.h"
|
|
#include "usbpd_pdo_defs.h"
|
|
#include "usbpd_core.h"
|
|
#if defined(_TRACE)
|
|
#include "usbpd_trace.h"
|
|
#endif /* _TRACE */
|
|
#include "string.h"
|
|
#include "gui_api.h"
|
|
/* USER CODE BEGIN Include */
|
|
|
|
/* USER CODE END Include */
|
|
|
|
/** @addtogroup STM32_USBPD_APPLICATION
|
|
* @{
|
|
*/
|
|
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF
|
|
* @{
|
|
*/
|
|
|
|
/* Private typedef -----------------------------------------------------------*/
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Private_TypeDef
|
|
* @{
|
|
*/
|
|
/* USER CODE BEGIN Private_Typedef */
|
|
|
|
/* USER CODE END Private_Typedef */
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/* Private define ------------------------------------------------------------*/
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Private_Defines
|
|
* @{
|
|
*/
|
|
/* USER CODE BEGIN Private_Define */
|
|
|
|
/* USER CODE END Private_Define */
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/* Private macros ------------------------------------------------------------*/
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Private_Macros
|
|
* @{
|
|
*/
|
|
#if defined(_TRACE)
|
|
#define PWR_IF_DEBUG_TRACE(_PORT_, __MESSAGE__) USBPD_TRACE_Add(USBPD_TRACE_DEBUG, (_PORT_), 0u, (uint8_t*)(__MESSAGE__), sizeof(__MESSAGE__) - 1u)
|
|
#else
|
|
#define PWR_IF_DEBUG_TRACE(_PORT_, __MESSAGE__)
|
|
#endif /* _TRACE */
|
|
/* USER CODE BEGIN Private_Macro */
|
|
|
|
/* USER CODE END Private_Macro */
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/* Private variables ---------------------------------------------------------*/
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Private_Variables
|
|
* @{
|
|
*/
|
|
/* USER CODE BEGIN Private_Variables */
|
|
/**
|
|
* @brief USBPD Port PDO Storage array declaration
|
|
*/
|
|
|
|
/**** PDO ****/
|
|
USBPD_PWR_Port_PDO_Storage_TypeDef PWR_Port_PDO_Storage[USBPD_PORT_COUNT];
|
|
/* USER CODE END Private_Variables */
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/* Private function prototypes -----------------------------------------------*/
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Private_Functions
|
|
* @{
|
|
*/
|
|
/* USER CODE BEGIN USBPD_USER_PRIVATE_FUNCTIONS_Prototypes */
|
|
|
|
/* USER CODE END USBPD_USER_PRIVATE_FUNCTIONS_Prototypes */
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Exported_Functions
|
|
* @{
|
|
*/
|
|
|
|
/**
|
|
* @brief Initialize structures and variables related to power board profiles
|
|
* used by Sink and Source, for all available ports.
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_Init(void)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_Init */
|
|
USBPD_StatusTypeDef _status = USBPD_OK;
|
|
|
|
/* Set links to PDO values and number for Port 0 (defined in PDO arrays in H file).
|
|
*/
|
|
PWR_Port_PDO_Storage[USBPD_PORT_0].SourcePDO.ListOfPDO = (uint32_t *) PORT0_PDO_ListSRC;
|
|
PWR_Port_PDO_Storage[USBPD_PORT_0].SourcePDO.NumberOfPDO = &USBPD_NbPDO[1];
|
|
|
|
return _status;
|
|
/* USER CODE END USBPD_PWR_IF_Init */
|
|
}
|
|
|
|
/**
|
|
* @brief Sets the required power profile, now it works only with Fixed ones
|
|
* @param PortNum Port number
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_SetProfile(uint8_t PortNum)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_SetProfile */
|
|
USBPD_StatusTypeDef _ret = USBPD_ERROR;
|
|
USBPD_PDO_TypeDef _pdo;
|
|
USBPD_SNKRDO_TypeDef _rdo;
|
|
|
|
_rdo.d32 = DPM_Ports[PortNum].DPM_RcvRequestDOMsg;
|
|
if (0 == PortNum)
|
|
_pdo.d32 = PORT0_PDO_ListSRC[0];
|
|
else
|
|
_pdo.d32 = PORT0_PDO_ListSRC[0];
|
|
|
|
if(PWR_OK == BSP_USBPD_PWR_VBUSSetVoltage_Fixed(PortNum, _pdo.SRCFixedPDO.VoltageIn50mVunits * 50,
|
|
(_rdo.FixedVariableRDO.OperatingCurrentIn10mAunits * 10),
|
|
(_rdo.FixedVariableRDO.MaxOperatingCurrent10mAunits * 10)))
|
|
{
|
|
_ret = USBPD_OK;
|
|
}
|
|
|
|
return _ret;
|
|
/* USER CODE END USBPD_PWR_IF_SetProfile */
|
|
}
|
|
|
|
/**
|
|
* @brief Checks if the power on a specified port is ready
|
|
* @param PortNum Port number
|
|
* @param Vsafe Vsafe status based on @ref USBPD_VSAFE_StatusTypeDef
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_SupplyReady(uint8_t PortNum, USBPD_VSAFE_StatusTypeDef Vsafe)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_SupplyReady */
|
|
return USBPD_ERROR;
|
|
/* USER CODE END USBPD_PWR_IF_SupplyReady */
|
|
}
|
|
|
|
/**
|
|
* @brief Enables VBUS power on a specified port
|
|
* @param PortNum Port number
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_VBUSEnable(uint8_t PortNum)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_VBUSEnable */
|
|
USBPD_StatusTypeDef _status = (USBPD_StatusTypeDef)HW_IF_PWR_Enable(PortNum, USBPD_ENABLE, CCNONE, USBPD_FALSE, USBPD_PORTPOWERROLE_SRC);
|
|
return _status;
|
|
/* USER CODE END USBPD_PWR_IF_VBUSEnable */
|
|
}
|
|
|
|
/**
|
|
* @brief Disable VBUS/VCONN the power on a specified port
|
|
* @param PortNum Port number
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_VBUSDisable(uint8_t PortNum)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_VBUSDisable */
|
|
USBPD_StatusTypeDef _status = (USBPD_StatusTypeDef)HW_IF_PWR_Enable(PortNum, USBPD_DISABLE, CCNONE, USBPD_FALSE, USBPD_PORTPOWERROLE_SRC);
|
|
return _status;
|
|
/* USER CODE END USBPD_PWR_IF_VBUSDisable */
|
|
}
|
|
|
|
/**
|
|
* @brief Checks if the power on a specified port is enabled
|
|
* @param PortNum Port number
|
|
* @retval USBPD_ENABLE or USBPD_DISABLE
|
|
*/
|
|
USBPD_FunctionalState USBPD_PWR_IF_VBUSIsEnabled(uint8_t PortNum)
|
|
{
|
|
/* Get the Status of the port */
|
|
return USBPD_PORT_IsValid(PortNum) ? (USBPD_FunctionalState)HW_IF_PWR_VBUSIsEnabled(PortNum) : USBPD_DISABLE;
|
|
}
|
|
|
|
/**
|
|
* @brief Reads the voltage and the current on a specified port
|
|
* @param PortNum Port number
|
|
* @param pVoltage: The Voltage in mV
|
|
* @param pCurrent: The Current in mA
|
|
* @retval USBPD_ERROR or USBPD_OK
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_ReadVA(uint8_t PortNum, uint16_t *pVoltage, uint16_t *pCurrent)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_ReadVA */
|
|
return USBPD_ERROR;
|
|
/* USER CODE END USBPD_PWR_IF_ReadVA */
|
|
}
|
|
|
|
/**
|
|
* @brief Enables the VConn on the port.
|
|
* @param PortNum Port number
|
|
* @param CC Specifies the CCx to be selected based on @ref CCxPin_TypeDef structure
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_Enable_VConn(uint8_t PortNum, CCxPin_TypeDef CC)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_Enable_VConn */
|
|
return USBPD_ERROR;
|
|
/* USER CODE END USBPD_PWR_IF_Enable_VConn */
|
|
}
|
|
|
|
/**
|
|
* @brief Disable the VConn on the port.
|
|
* @param PortNum Port number
|
|
* @param CC Specifies the CCx to be selected based on @ref CCxPin_TypeDef structure
|
|
* @retval USBPD status
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_Disable_VConn(uint8_t PortNum, CCxPin_TypeDef CC)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_Disable_VConn */
|
|
return USBPD_ERROR;
|
|
/* USER CODE END USBPD_PWR_IF_Disable_VConn */
|
|
}
|
|
|
|
/**
|
|
* @brief Allow PDO data reading from PWR_IF storage.
|
|
* @param PortNum Port number
|
|
* @param DataId Type of data to be read from PWR_IF
|
|
* This parameter can be one of the following values:
|
|
* @arg @ref USBPD_CORE_DATATYPE_SRC_PDO Source PDO reading requested
|
|
* @arg @ref USBPD_CORE_DATATYPE_SNK_PDO Sink PDO reading requested
|
|
* @param Ptr Pointer on address where PDO values should be written (u8 pointer)
|
|
* @param Size Pointer on nb of u32 written by PWR_IF (nb of PDOs)
|
|
* @retval None
|
|
*/
|
|
void USBPD_PWR_IF_GetPortPDOs(uint8_t PortNum, USBPD_CORE_DataInfoType_TypeDef DataId, uint8_t *Ptr, uint32_t *Size)
|
|
{
|
|
if (DataId == USBPD_CORE_DATATYPE_SRC_PDO)
|
|
{
|
|
*Size = USBPD_NbPDO[1];
|
|
memcpy(Ptr,PORT0_PDO_ListSRC, sizeof(uint32_t) * USBPD_NbPDO[1]);
|
|
}
|
|
/* USER CODE BEGIN USBPD_PWR_IF_GetPortPDOs */
|
|
uint32_t nbpdo, index, nb_valid_pdo = 0;
|
|
uint32_t *ptpdoarray = NULL;
|
|
USBPD_PDO_TypeDef pdo_first;
|
|
USBPD_PDO_TypeDef pdo;
|
|
|
|
/* Check if valid port */
|
|
if (USBPD_PORT_IsValid(PortNum))
|
|
{
|
|
/* According to type of PDO to be read, set pointer on values and nb of elements */
|
|
switch(DataId)
|
|
{
|
|
case USBPD_CORE_DATATYPE_SRC_PDO :
|
|
nbpdo = *PWR_Port_PDO_Storage[PortNum].SourcePDO.NumberOfPDO;
|
|
ptpdoarray = PWR_Port_PDO_Storage[PortNum].SourcePDO.ListOfPDO;
|
|
/* Save the 1st PDO */
|
|
pdo_first.d32 = *ptpdoarray;
|
|
/* Reset unchunked bit if current revision is PD2.0*/
|
|
if (USBPD_SPECIFICATION_REV2 == DPM_Params[PortNum].PE_SpecRevision)
|
|
{
|
|
pdo_first.SRCFixedPDO.UnchunkedExtendedMessage = USBPD_PDO_SRC_FIXED_UNCHUNK_NOT_SUPPORTED;
|
|
}
|
|
break;
|
|
default :
|
|
nbpdo = 0;
|
|
break;
|
|
}
|
|
|
|
/* Copy PDO data in output buffer */
|
|
for (index = 0; index < nbpdo; index++)
|
|
{
|
|
pdo.d32 = *ptpdoarray;
|
|
/* Copy only PDO (and not APDO in case of current revision is PD2.0) */
|
|
if ((USBPD_SPECIFICATION_REV2 == DPM_Params[PortNum].PE_SpecRevision)
|
|
&& (pdo.GenericPDO.PowerObject == USBPD_CORE_PDO_TYPE_APDO))
|
|
{
|
|
}
|
|
else
|
|
{
|
|
/* Copy 1st PDO as potentially FRS or UNCHUNKED bits have been reset */
|
|
if (0 == index)
|
|
{
|
|
(void)memcpy(Ptr, (uint8_t*)&pdo_first.d32, 4u);
|
|
}
|
|
else
|
|
{
|
|
(void)memcpy((Ptr + (nb_valid_pdo * 4u)), (uint8_t*)ptpdoarray, 4u);
|
|
}
|
|
nb_valid_pdo++;
|
|
}
|
|
ptpdoarray++;
|
|
}
|
|
/* Set nb of read PDO (nb of u32 elements); */
|
|
*Size = nb_valid_pdo;
|
|
}
|
|
/* USER CODE END USBPD_PWR_IF_GetPortPDOs */
|
|
}
|
|
|
|
/**
|
|
* @brief Find out SRC PDO pointed out by a position provided in a Request DO (from Sink).
|
|
* @param PortNum Port number
|
|
* @param RdoPosition RDO Position in list of provided PDO
|
|
* @param Pdo Pointer on PDO value pointed out by RDO position (u32 pointer)
|
|
* @retval Status of search
|
|
* USBPD_OK : Src PDO found for requested DO position (output Pdo parameter is set)
|
|
* USBPD_FAIL : Position is not compliant with current Src PDO for this port (no corresponding PDO value)
|
|
*/
|
|
USBPD_StatusTypeDef USBPD_PWR_IF_SearchRequestedPDO(uint8_t PortNum, uint32_t RdoPosition, uint32_t *Pdo)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_SearchRequestedPDO */
|
|
if((RdoPosition == 0) || (RdoPosition > *PWR_Port_PDO_Storage[PortNum].SourcePDO.NumberOfPDO))
|
|
{
|
|
/* Invalid PDO index */
|
|
return USBPD_FAIL;
|
|
}
|
|
|
|
*Pdo = PWR_Port_PDO_Storage[PortNum].SourcePDO.ListOfPDO[RdoPosition - 1];
|
|
return USBPD_OK;
|
|
/* USER CODE END USBPD_PWR_IF_SearchRequestedPDO */
|
|
}
|
|
|
|
/**
|
|
* @brief the function is called in case of critical issue is detected to switch in safety mode.
|
|
* @retval None
|
|
*/
|
|
void USBPD_PWR_IF_Alarm()
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_Alarm */
|
|
|
|
/* USER CODE END USBPD_PWR_IF_Alarm */
|
|
}
|
|
|
|
/**
|
|
* @brief Function is called to get VBUS power status.
|
|
* @param PortNum Port number
|
|
* @param PowerTypeStatus Power type status based on @ref USBPD_VBUSPOWER_STATUS
|
|
* @retval UBBPD_TRUE or USBPD_FALSE
|
|
*/
|
|
uint8_t USBPD_PWR_IF_GetVBUSStatus(uint8_t PortNum, USBPD_VBUSPOWER_STATUS PowerTypeStatus)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_GetVBUSStatus */
|
|
uint8_t _status = USBPD_FALSE;
|
|
uint32_t _vbus = HW_IF_PWR_GetVoltage(PortNum);
|
|
|
|
switch(PowerTypeStatus)
|
|
{
|
|
case USBPD_PWR_BELOWVSAFE0V :
|
|
if (_vbus < USBPD_PWR_LOW_VBUS_THRESHOLD) _status = USBPD_TRUE;
|
|
break;
|
|
case USBPD_PWR_VSAFE5V :
|
|
if (_vbus >= USBPD_PWR_HIGH_VBUS_THRESHOLD) _status = USBPD_TRUE;
|
|
break;
|
|
case USBPD_PWR_SNKDETACH:
|
|
if (_vbus < USBPD_PWR_HIGH_VBUS_THRESHOLD) _status = USBPD_TRUE;
|
|
break;
|
|
default :
|
|
break;
|
|
}
|
|
return _status;
|
|
/* USER CODE END USBPD_PWR_IF_GetVBUSStatus */
|
|
}
|
|
|
|
/**
|
|
* @brief Function is called to set the VBUS threshold when a request has been accepted.
|
|
* @param PortNum Port number
|
|
* @retval None
|
|
*/
|
|
void USBPD_PWR_IF_UpdateVbusThreshold(uint8_t PortNum)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_UpdateVbusThreshold */
|
|
/* USER CODE END USBPD_PWR_IF_UpdateVbusThreshold */
|
|
}
|
|
|
|
/**
|
|
* @brief Function is called to reset the VBUS threshold when there is a power reset.
|
|
* @param PortNum Port number
|
|
* @retval None
|
|
*/
|
|
void USBPD_PWR_IF_ResetVbusThreshold(uint8_t PortNum)
|
|
{
|
|
/* USER CODE BEGIN USBPD_PWR_IF_ResetVbusThreshold */
|
|
/* USER CODE END USBPD_PWR_IF_ResetVbusThreshold */
|
|
}
|
|
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/** @addtogroup STM32_USBPD_APPLICATION_POWER_IF_Private_Functions
|
|
* @{
|
|
*/
|
|
/* USER CODE BEGIN USBPD_USER_PRIVATE_FUNCTIONS_Definition */
|
|
|
|
/* USER CODE END USBPD_USER_PRIVATE_FUNCTIONS_Definition */
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/**
|
|
* @}
|
|
*/
|
|
|
|
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
|