hi,
Emios_Pwm_Ip_SetDutyCycle does the abstraction for you. The duty cycle enter there is always 0....channelperiod.
The issue is with the following line when duty cycle = 1 (from Emios_Pwm_Ip_SetDutyCycleOpwmcb which is called by Emios_Pwm_Ip_SetDutyCycle)
Emios_Pwm_Ip_SetUCRegA(Base, Channel, (Emios_Pwm_Ip_PeriodType)(ChPeriod - (NewDutyCycle >> 1U)));
--> shift (NewDutyCycle >> 1U) = 0 --> Reg A = ChPeriod which causes the issue.
But i do not see any point discussing this further. The work around not setting dutycycle to 1 works. So this is just an FYI.
static inline Emios_Pwm_Ip_StatusType Emios_Pwm_Ip_SetDutyCycleOpwmcb(uint8 Instance,
uint8 Channel,
Emios_Pwm_Ip_DutyType NewDutyCycle
)
{
#if (EMIOS_PWM_IP_DEV_ERROR_DETECT == STD_ON)
DevAssert(EMIOS_PWM_IP_INSTANCE_COUNT > Instance);
DevAssert(EMIOS_PWM_IP_CHANNEL_COUNT > Channel);
#endif
Emios_Pwm_Ip_HwAddrType *const Base = Emios_Pwm_Ip_aBasePtr[Instance];
Emios_Pwm_Ip_StatusType Ret = EMIOS_PWM_IP_STATUS_SUCCESS;
Emios_Pwm_Ip_PeriodType ChPeriod = Emios_Pwm_Ip_GetCounterBusPeriod(Instance, Channel, Emios_Pwm_Ip_GetCounterBus(Base, Channel));
/* Get the value of channel Index */
uint8 ChannelIdx = Emios_Pwm_Ip_GetChannelIndex(Instance, Channel);
if (ChannelIdx < EMIOS_PWM_IP_NUM_OF_CHANNELS_USED_U8)
{
/* OPWMCB Mode */
if(NewDutyCycle > ((ChPeriod * 2U) - 2U))
{ /* Duty cycle value should not be greater than the Channel Period. */
Ret = EMIOS_PWM_IP_STATUS_ERROR;
}
else if(0U == NewDutyCycle)
{
/* Disable and clear interrupt flag */
Emios_Pwm_Ip_SetInterruptRequest(Base, Channel, FALSE);
Emios_Pwm_Ip_ClearFlagEvent(Base, Channel);
Emios_Pwm_Ip_SetUCRegA(Base, Channel, ChPeriod + 1U);
Emios_Pwm_Ip_aNotif[ChannelIdx] = (uint8)1U;
/* This statement is required to avoid limitation of 0% duty cycle (if call 100% to 0%) */
if(1U == Emios_Pwm_Ip_GetUCRegA(Base, Channel))
{
if((Emios_Pwm_Ip_aInitialModes[ChannelIdx] == EMIOS_PWM_IP_MODE_OPWMCB_TRAIL_EDGE_FLAG) ||
(Emios_Pwm_Ip_aInitialModes[ChannelIdx] == EMIOS_PWM_IP_MODE_OPWMCB_TRAIL_EDGE_FLAG_BOTH))
{
Emios_Pwm_Ip_SetForceMatchB(Base, Channel, TRUE);
}
else
{
Emios_Pwm_Ip_SetForceMatchA(Base, Channel, TRUE);
}
}
}
else if(NewDutyCycle == ((ChPeriod * 2U) - 2U))
{
/* Disable and clear interrupt flag */
Emios_Pwm_Ip_SetInterruptRequest(Base, Channel, FALSE);
Emios_Pwm_Ip_ClearFlagEvent(Base, Channel);
Emios_Pwm_Ip_SetUCRegA(Base, Channel, 1U);
Emios_Pwm_Ip_aNotif[ChannelIdx] = (uint8)1U;
}
else
{
Emios_Pwm_Ip_SetUCRegA(Base, Channel, (Emios_Pwm_Ip_PeriodType)(ChPeriod - (NewDutyCycle >> 1U)));
Emios_Pwm_Ip_aNotif[ChannelIdx] = (uint8)0U;
Emios_Pwm_Ip_SetInterruptRequest(Base, Channel, (Emios_Pwm_Ip_aCheckEnableNotif[ChannelIdx] == 0U)? FALSE : TRUE);
}
/* Stores the new duty cycle in ticks */
Emios_Pwm_Ip_aDutyCycle[ChannelIdx] = NewDutyCycle;
}
else