PWM Overview
As part of the MCAL layer, learn how you can use the PWM module in Autosar for your projects that require PWM modulation
Recently, we have been covering all the MCAL modules. We started with the SPI, on SPI Overview (opens in a new tab) and went through DIO and port, on DIO and Port Overview (opens in a new tab). Today, we'll continue on this journey, this time with our eyes turned into the PWM (Pulse Width Modulation) module.
The PWM module is part of the MCAL in the Autosar layered architecture, and its purpose is to provide indirection on the hardware (i.e. no matter what microcontroller you're using, the interface will never change). It enables you to create and control the duty cycle and frequency of PWM signals. The flow is simple. Such as with SPI, you configure the port pins you want to use (in the Port module), configure the PWM signals within the PWM module, where you can specify the relevant parameters:
- Default value for period
- Default value for duty cycle
- Polarity (high or low)
- Idle state (high or low)
- Channel class, where you have 3 options: fixed period, fixed period - shifted (if your underlying hardware supports such functionality) and variable period (can be changed in runtime)
- Edge notifications (get notified if the PWM edge has changed)
Optionally, you can have some more parameters, if supported by your hardware:
- Channel phase shift
- Reference channel for phase shift
- Microcontroller-specific channel properties
Some considerations when using the PWM module is that you need to know the underlying time unit in ticks, as that is the unit expected to control the period of your PWM signal. This is usually not a big deal, as you're supposed to interact with a PWM signal (and other MCAL modules, in fact) through a component in the IO Hardware Abstraction Layer (IOHwAbs), which converts the value in ticks into a period in an intuitive unit. Another is that some PWM drivers offers some operation modes with lower power consumption, at the cost of a slower reaction time. This is optional and might not be present in your PWM driver, but if you have it, that's something that will reduce overhead for your system, due to asynchronous operation (at the cost of speed). We'll see this in action in a second.
Now, let's explore the APIs available to the user:
-
void Pwm_Init(const Pwm_ConfigType* ConfigPtr) - Initialize the PWM driver's internals, with the provided default values. You can also de-initialize the driver with Pwm_DeInit
-
void Pwm_SetDutyCycle(Pwm_ChannelType ChannelNumber, uint16 DutyCycle) - Sets the duty cycle for a PWM channel, from 0% to 100%
-
void Pwm_SetPeriodAndDuty(Pwm_ChannelType ChannelNumber, Pwm_PeriodType Period, uint16 DutyCycle) - Set the duty cycle and period (remember, in ticks) of the PWM signal. This API is only allowed in the variable period PWM signals
-
void Pwm_SetOutputToIdle(Pwm_ChannelType ChannelNumber) - Sets the PWM signal state to idle, aka, deactivates the PWM signal
-
Pwm_OutputStateType Pwm_GetOutputState(Pwm_ChannelType ChannelNumber) - Get the current PWM state. The possible values are PWM_HIGH or PWM_LOW
-
void Pwm_EnableNotification(Pwm_ChannelType ChannelNumber, Pwm_EdgeNotificationType Notification) - Enable PWM signal notification for rising, falling or both edges. It can also be disabled, through Pwm_DisableNotification
-
Std_ReturnType Pwm_SetPowerState(Pwm_PowerStateRequestResultType* Result) - Configures the PWM hardware to enter a specific power state. All necessary actions that need to be taken care of before entering the requested power stage must take place before this point. For example, if the power state requires all PWM signals to be in the idle state, this should be handled by an IOHwAbs component beforehand. If not, the power stage change will not take place and you will get an error. For this purpose, you might want to enable the Development Error Tracer (DET) module, which is quite useful in development. You can read more about it in our article DET Overview (opens in a new tab). To prepare a power state, you can call the API Pwm_PreparePowerState. Lastly, you can read the current power state through the API Pwm_GetCurrentPowerState, or read the currently requested power state in Pwm_GetTargetPowerState
-
void Pwm_Main_PowerTransitionManager(void) - As you can see, the power state management for PWM is asynchronous, as opposed to the synchronous nature of all other APIs. To handle the power state transitions, this cyclic call is scheduled to manage the state transition
Aside from the aforementioned APIs, there are also Pwm_Notification_<Channel> and IoHwAb_Pwm_NotifyReadyForPowerState<Mode>, which serve as callbacks for PWM signals edge changes and a callback for when a specific power state is ready
Alright, that's about all you need to know, regarding PWM in the Autosar Layered Architecture! We hope this article provided you with enough knowledge to enable you to configure the PWM module. And, with the exception of the underlying ticking source for the PWM, which is heavily microcontroller-dependent, everything is in here. See you soon, remember to subscribe to our mailing list and share this article with your coworkers, so that you all can evolve your Autosar knowledge together!
Author: Micael Coutinho (opens in a new tab)
References:
© AutosarToday —@LinkedIn