All Data Structures Functions Variables Typedefs Enumerations Enumerator Groups Pages
CMT: Carrier Modulator Transmitter Driver

## Overview

The carrier modulator transmitter (CMT) module provides the means to generate the protocol timing and carrier signals for a side variety of encoding schemes. The CMT incorporates hardware to off-load the critical and/or lengthy timing requirements associated with signal generation from the CPU. The KSDK provides a driver for the CMT module of the Kinetis devices.

# Clock formulas

The CMT module has internal clock dividers. It was originally designed to be based on an 8 MHZ bus clock that could be divided by 1, 2, 4, or 8 according to the specification. To be compatible with higher bus frequency, the primary prescaler (PPS) was developed to receive a higher frequency and generate a clock enable signal called an intermediate frequency (IF). The IF must be approximately equal to 8MHz and works as a clock enable to the secondary prescaler. For the PPS, the prescaler is selected according to the bus clock to generate an intermediate clock approximately to 8 MHz and is selected as (bus_clock_hz/8000000). The secondary prescaler is the "cmtDivider". The clocks for the CMT module are listed below:

1. CMT clock frequency = bus_clock_Hz / (bus_clock_Hz / 8000000) / cmtDivider
2. CMT carrier and generator frequency = CMT clock frequency / (highCount1 + lowCount1)
   (In FSK mode, the second frequency = CMT clock frequency / (highCount2 + lowCount2))
3. CMT infrared output signal frequency
   a. In Time and Baseband mode
   CMT IRO signal mark time = (markCount + 1) / (CMT clock frequency / 8)
   CMT IRO signal space time = spaceCount / (CMT clock frequency / 8)
   b. In FSK mode
   CMT IRO signal mark time = (markCount + 1) / CMT carrier and generator frequency
   CMT IRO signal space time = spaceCount / CMT carrier and generator frequency

# Typical use case

This is an example code to initialize the data:

cmt_config_t config;
cmt_modulate_config_t modulateConfig;
uint32_t busClock;
// Gets the bus clock for the CMT module.
busClock = CLOCK_GetFreq(kCLOCK_BusClk);
CMT_GetDefaultConfig(&config);
// Interrupts is enabled to change the modulate mark and space count.
config.isInterruptEnabled = true;
CMT_Init(CMT, &config, busClock);
// Prepares the modulate configuration for a use case.
modulateConfig.highCount1 = ...;
modulateConfig.lowCount1 = ...;
modulateConfig.markCount = ...;
modulateConfig.spaceCount = ...;
// Sets the time mode.
CMT_SetMode(CMT, kCMT_TimeMode, &modulateConfig);

This is an example IRQ handler to change the mark and space count to complete the data modulation:

// The data length has been transmitted.
uint32_t g_CmtDataBitLen;
void CMT_IRQHandler(void)
{
if (CMT_GetStatusFlags(CMT))
{
if (g_CmtDataBitLen <= CMT_TEST_DATA_BITS)
{
// LSB.
if (data & ((uint32_t)0x01 << g_CmtDataBitLen))
{
CMT_SetModulateMarkSpace(CMT, g_CmtModDataOneMarkCount, g_CmtModDataOneSpaceCount);
}
else
{
CMT_SetModulateMarkSpace(CMT, g_CmtModDataZeroMarkCount, g_CmtModDataZeroSpaceCount);
}
}
}
}

## Data Structures

struct | cmt_modulate_config_t
| CMT carrier generator and modulator configuration structure. More...
struct | cmt_config_t
| CMT basic configuration structure. More...

## Enumerations

enum | cmt_mode_t { kCMT_DirectIROCtl = 0x00U, kCMT_TimeMode = 0x01U, kCMT_FSKMode = 0x05U, kCMT_BasebandMode = 0x09U }
| The modes of CMT. More...

enum

cmt_primary_clkdiv_t {
kCMT_PrimaryClkDiv1 = 0U,
kCMT_PrimaryClkDiv2 = 1U,
kCMT_PrimaryClkDiv3 = 2U,
kCMT_PrimaryClkDiv4 = 3U,
kCMT_PrimaryClkDiv5 = 4U,
kCMT_PrimaryClkDiv6 = 5U,
kCMT_PrimaryClkDiv7 = 6U,
kCMT_PrimaryClkDiv8 = 7U,
kCMT_PrimaryClkDiv9 = 8U,
kCMT_PrimaryClkDiv10 = 9U,
kCMT_PrimaryClkDiv11 = 10U,
kCMT_PrimaryClkDiv12 = 11U,
kCMT_PrimaryClkDiv13 = 12U,
kCMT_PrimaryClkDiv14 = 13U,
kCMT_PrimaryClkDiv15 = 14U,
kCMT_PrimaryClkDiv16 = 15U
}

| The CMT clock divide primary prescaler. More...
enum | cmt_second_clkdiv_t { kCMT_SecondClkDiv1 = 0U, kCMT_SecondClkDiv2 = 1U, kCMT_SecondClkDiv4 = 2U, kCMT_SecondClkDiv8 = 3U }
| The CMT clock divide secondary prescaler. More...
enum | cmt_infrared_output_polarity_t { kCMT_IROActiveLow = 0U, kCMT_IROActiveHigh = 1U }
| The CMT infrared output polarity. More...
enum | cmt_infrared_output_state_t { kCMT_IROCtlLow = 0U, kCMT_IROCtlHigh = 1U }
| The CMT infrared output signal state control. More...
enum | _cmt_interrupt_enable { kCMT_EndOfCycleInterruptEnable = CMT_MSC_EOCIE_MASK }
| CMT interrupt configuration structure, default settings all disabled. More...

## Driver version

#define | FSL_CMT_DRIVER_VERSION (MAKE_VERSION(2, 0, 1))
| CMT driver version 2.0.1. More...

## Initialization and deinitialization

void | CMT_GetDefaultConfig (cmt_config_t *config)
| Gets the CMT default configuration structure. More...
void | CMT_Init (CMT_Type *base, const cmt_config_t *config, uint32_t busClock_Hz)
| Initializes the CMT module. More...
void | CMT_Deinit (CMT_Type *base)
| Disables the CMT module and gate control. More...

## Basic Control Operations

void | CMT_SetMode (CMT_Type *base, cmt_mode_t mode, cmt_modulate_config_t *modulateConfig)
| Selects the mode for CMT. More...
cmt_mode_t | CMT_GetMode (CMT_Type *base)
| Gets the mode of the CMT module. More...
uint32_t | CMT_GetCMTFrequency (CMT_Type *base, uint32_t busClock_Hz)
| Gets the actual CMT clock frequency. More...
static void | CMT_SetCarrirGenerateCountOne (CMT_Type *base, uint32_t highCount, uint32_t lowCount)
| Sets the primary data set for the CMT carrier generator counter. More...
static void | CMT_SetCarrirGenerateCountTwo (CMT_Type *base, uint32_t highCount, uint32_t lowCount)
| Sets the secondary data set for the CMT carrier generator counter. More...
void | CMT_SetModulateMarkSpace (CMT_Type *base, uint32_t markCount, uint32_t spaceCount)
| Sets the modulation mark and space time period for the CMT modulator. More...
static void | CMT_EnableExtendedSpace (CMT_Type *base, bool enable)
| Enables or disables the extended space operation. More...
void | CMT_SetIroState (CMT_Type *base, cmt_infrared_output_state_t state)
| Sets IRO - infrared output signal state. More...
static void | CMT_EnableInterrupts (CMT_Type *base, uint32_t mask)
| Enables the CMT interrupt. More...
static void | CMT_DisableInterrupts (CMT_Type *base, uint32_t mask)
| Disables the CMT interrupt. More...
static uint32_t | CMT_GetStatusFlags (CMT_Type *base)
| Gets the end of the cycle status flag. More...

## Data Structure Documentation

struct cmt_modulate_config_t

### Data Fields

uint8_t | highCount1
| The high time for carrier generator first register. More...
uint8_t | lowCount1
| The low time for carrier generator first register. More...
uint8_t | highCount2
| The high time for carrier generator second register for FSK mode. More...
uint8_t | lowCount2
| The low time for carrier generator second register for FSK mode. More...
uint16_t | markCount
| The mark time for the modulator gate. More...
uint16_t | spaceCount
| The space time for the modulator gate. More...

#### Field Documentation

uint8_t cmt_modulate_config_t::highCount1

uint8_t cmt_modulate_config_t::lowCount1

uint8_t cmt_modulate_config_t::highCount2

uint8_t cmt_modulate_config_t::lowCount2

uint16_t cmt_modulate_config_t::markCount

uint16_t cmt_modulate_config_t::spaceCount

struct cmt_config_t

### Data Fields

bool | isInterruptEnabled
| Timer interrupt 0-disable, 1-enable. More...
bool | isIroEnabled
| The IRO output 0-disabled, 1-enabled. More...
cmt_infrared_output_polarity_t | iroPolarity
| The IRO polarity. More...
cmt_second_clkdiv_t | divider
| The CMT clock divide prescaler. More...

#### Field Documentation

bool cmt_config_t::isInterruptEnabled

bool cmt_config_t::isIroEnabled

cmt_infrared_output_polarity_t cmt_config_t::iroPolarity

cmt_second_clkdiv_t cmt_config_t::divider

## Macro Definition Documentation

#define FSL_CMT_DRIVER_VERSION (MAKE_VERSION(2, 0, 1))

## Enumeration Type Documentation

enum cmt_mode_t

Enumerator
kCMT_DirectIROCtl | Carrier modulator is disabled and the IRO signal is directly in software control.
kCMT_TimeMode | Carrier modulator is enabled in time mode.
kCMT_FSKMode | Carrier modulator is enabled in FSK mode.
kCMT_BasebandMode | Carrier modulator is enabled in baseband mode.

enum cmt_primary_clkdiv_t

The primary clock divider is used to divider the bus clock to get the intermediate frequency to approximately equal to 8 MHZ. When the bus clock is 8 MHZ, set primary prescaler to "kCMT_PrimaryClkDiv1".

Enumerator
kCMT_PrimaryClkDiv1 | The intermediate frequency is the bus clock divided by 1.
kCMT_PrimaryClkDiv2 | The intermediate frequency is the bus clock divided by 2.
kCMT_PrimaryClkDiv3 | The intermediate frequency is the bus clock divided by 3.
kCMT_PrimaryClkDiv4 | The intermediate frequency is the bus clock divided by 4.
kCMT_PrimaryClkDiv5 | The intermediate frequency is the bus clock divided by 5.
kCMT_PrimaryClkDiv6 | The intermediate frequency is the bus clock divided by 6.
kCMT_PrimaryClkDiv7 | The intermediate frequency is the bus clock divided by 7.
kCMT_PrimaryClkDiv8 | The intermediate frequency is the bus clock divided by 8.
kCMT_PrimaryClkDiv9 | The intermediate frequency is the bus clock divided by 9.
kCMT_PrimaryClkDiv10 | The intermediate frequency is the bus clock divided by 10.
kCMT_PrimaryClkDiv11 | The intermediate frequency is the bus clock divided by 11.
kCMT_PrimaryClkDiv12 | The intermediate frequency is the bus clock divided by 12.
kCMT_PrimaryClkDiv13 | The intermediate frequency is the bus clock divided by 13.
kCMT_PrimaryClkDiv14 | The intermediate frequency is the bus clock divided by 14.
kCMT_PrimaryClkDiv15 | The intermediate frequency is the bus clock divided by 15.
kCMT_PrimaryClkDiv16 | The intermediate frequency is the bus clock divided by 16.

enum cmt_second_clkdiv_t

The second prescaler can be used to divide the 8 MHZ CMT clock by 1, 2, 4, or 8 according to the specification.

Enumerator
kCMT_SecondClkDiv1 | The CMT clock is the intermediate frequency frequency divided by 1.
kCMT_SecondClkDiv2 | The CMT clock is the intermediate frequency frequency divided by 2.
kCMT_SecondClkDiv4 | The CMT clock is the intermediate frequency frequency divided by 4.
kCMT_SecondClkDiv8 | The CMT clock is the intermediate frequency frequency divided by 8.

enum cmt_infrared_output_polarity_t

Enumerator
kCMT_IROActiveLow | The CMT infrared output signal polarity is active-low.
kCMT_IROActiveHigh | The CMT infrared output signal polarity is active-high.

enum cmt_infrared_output_state_t

Enumerator
kCMT_IROCtlLow | The CMT Infrared output signal state is controlled to low.
kCMT_IROCtlHigh | The CMT Infrared output signal state is controlled to high.

enum _cmt_interrupt_enable

This structure contains the settings for all of the CMT interrupt configurations.

Enumerator
kCMT_EndOfCycleInterruptEnable | CMT end of cycle interrupt.

## Function Documentation

void CMT_GetDefaultConfig | ( | cmt_config_t * | config | ) |

The purpose of this API is to get the default configuration structure for the CMT_Init(). Use the initialized structure unchanged in CMT_Init(), or modify some fields of the structure before calling the CMT_Init().

Parameters

  config | The CMT configuration structure pointer.

void CMT_Init | ( | CMT_Type * | base,
|  | const cmt_config_t * | config,
|  | uint32_t | busClock_Hz
| ) |  |

This function ungates the module clock and sets the CMT internal clock, interrupt, and infrared output signal for the CMT module.

Parameters

  base | CMT peripheral base address.
  config | The CMT basic configuration structure.
  busClock_Hz | The CMT module input clock - bus clock frequency.

void CMT_Deinit | ( | CMT_Type * | base | ) |

This function disables CMT modulator, interrupts, and gates the CMT clock control. CMT_Init must be called to use the CMT again.

Parameters

  base | CMT peripheral base address.

void CMT_SetMode | ( | CMT_Type * | base,
|  | cmt_mode_t | mode,
|  | cmt_modulate_config_t * | modulateConfig
| ) |  |

Parameters

  base | CMT peripheral base address.
  mode | The CMT feature mode enumeration. See "cmt_mode_t".
  modulateConfig | The carrier generation and modulator configuration.

cmt_mode_t CMT_GetMode | ( | CMT_Type * | base | ) |

Parameters

  base | CMT peripheral base address.

Returns
  The CMT mode. kCMT_DirectIROCtl Carrier modulator is disabled, the IRO signal is directly in software control. kCMT_TimeMode Carrier modulator is enabled in time mode. kCMT_FSKMode Carrier modulator is enabled in FSK mode. kCMT_BasebandMode Carrier modulator is enabled in baseband mode.

uint32_t CMT_GetCMTFrequency | ( | CMT_Type * | base,
|  | uint32_t | busClock_Hz
| ) |  |

Parameters

  base | CMT peripheral base address.
  busClock_Hz | CMT module input clock - bus clock frequency.

Returns
  The CMT clock frequency.

static void CMT_SetCarrirGenerateCountOne | ( | CMT_Type * | base,
|  | uint32_t | highCount,
|  | uint32_t | lowCount
| ) |  |

inlinestatic

This function sets the high time and low time of the primary data set for the CMT carrier generator counter to control the period and the duty cycle of the output carrier signal. If the CMT clock period is Tcmt, The period of the carrier generator signal equals (highCount + lowCount) * Tcmt. The duty cycle equals highCount / (highCount + lowCount).

Parameters

  base | CMT peripheral base address.
  highCount | The number of CMT clocks for carrier generator signal high time, integer in the range of 1 ~ 0xFF.
  lowCount | The number of CMT clocks for carrier generator signal low time, integer in the range of 1 ~ 0xFF.

static void CMT_SetCarrirGenerateCountTwo | ( | CMT_Type * | base,
|  | uint32_t | highCount,
|  | uint32_t | lowCount
| ) |  |

inlinestatic

This function is used for FSK mode setting the high time and low time of the secondary data set CMT carrier generator counter to control the period and the duty cycle of the output carrier signal. If the CMT clock period is Tcmt, The period of the carrier generator signal equals (highCount + lowCount) * Tcmt. The duty cycle equals highCount / (highCount + lowCount).

Parameters

  base | CMT peripheral base address.
  highCount | The number of CMT clocks for carrier generator signal high time, integer in the range of 1 ~ 0xFF.
  lowCount | The number of CMT clocks for carrier generator signal low time, integer in the range of 1 ~ 0xFF.

void CMT_SetModulateMarkSpace | ( | CMT_Type * | base,
|  | uint32_t | markCount,
|  | uint32_t | spaceCount
| ) |  |

This function sets the mark time period of the CMT modulator counter to control the mark time of the output modulated signal from the carrier generator output signal. If the CMT clock frequency is Fcmt and the carrier out signal frequency is fcg:

- In Time and Baseband mode: The mark period of the generated signal equals (markCount + 1) / (Fcmt/8). The space period of the generated signal equals spaceCount / (Fcmt/8).
- In FSK mode: The mark period of the generated signal equals (markCount + 1)/fcg. The space period of the generated signal equals spaceCount / fcg.

Parameters

  base | Base address for current CMT instance.
  markCount | The number of clock period for CMT modulator signal mark period, in the range of 0 ~ 0xFFFF.
  spaceCount | The number of clock period for CMT modulator signal space period, in the range of the 0 ~ 0xFFFF.

static void CMT_EnableExtendedSpace | ( | CMT_Type * | base,
|  | bool | enable
| ) |  |

inlinestatic

This function is used to make the space period longer for time, baseband, and FSK modes.

Parameters

  base | CMT peripheral base address.
  enable | True enable the extended space, false disable the extended space.

void CMT_SetIroState | ( | CMT_Type * | base,
|  | cmt_infrared_output_state_t | state
| ) |  |

Changes the states of the IRO signal when the kCMT_DirectIROMode mode is set and the IRO signal is enabled.

Parameters

  base | CMT peripheral base address.
  state | The control of the IRO signal. See "cmt_infrared_output_state_t"

static void CMT_EnableInterrupts | ( | CMT_Type * | base,
|  | uint32_t | mask
| ) |  |

inlinestatic

This function enables the CMT interrupts according to the provided maskIf enabled. The CMT only has the end of the cycle interrupt - an interrupt occurs at the end of the modulator cycle. This interrupt provides a means for the user to reload the new mark/space values into the CMT modulator data registers and verify the modulator mark and space. For example, to enable the end of cycle, do the following:

* CMT_EnableInterrupts(CMT, kCMT_EndOfCycleInterruptEnable);
*

Parameters

  base | CMT peripheral base address.
  mask | The interrupts to enable. Logical OR of _cmt_interrupt_enable.

static void CMT_DisableInterrupts | ( | CMT_Type * | base,
|  | uint32_t | mask
| ) |  |

inlinestatic

This function disables the CMT interrupts according to the provided maskIf enabled. The CMT only has the end of the cycle interrupt. For example, to disable the end of cycle, do the following:

* CMT_DisableInterrupts(CMT, kCMT_EndOfCycleInterruptEnable);
*

Parameters

  base | CMT peripheral base address.
  mask | The interrupts to enable. Logical OR of _cmt_interrupt_enable.

static uint32_t CMT_GetStatusFlags | ( | CMT_Type * | base | ) |

inlinestatic

The flag is set:

- When the modulator is not currently active and carrier and modulator are set to start the initial CMT transmission.
- At the end of each modulation cycle when the counter is reloaded and the carrier and modulator are enabled.
  Parameters

    base | CMT peripheral base address.

  Returns
    Current status of the end of cycle status flag
    - non-zero: End-of-cycle has occurred.
    - zero: End-of-cycle has not yet occurred since the flag last cleared.