This post is older than 2 years and might not be relevant anymore
More Info: Consider searching for newer posts

PWM SEQ[1].REFRESH is ignored if the samples size is equal to one!

Hello,

I use a nRF52832 device, and I have some strange behavior when I use PWM. You can see my test program listed below.

Thank for your reply, Thierry!

/*
 * Test_PWM.c
 *
 *  Created on: 13 déc. 2017
 *      Author: Thierry
 */    
#include <system.h>

#include <nrf_drv_pwm.h>
#include <nrf_drv_gpiote.h>
#include <nrf_drv_ppi.h>

/* BUG : PWM
 *
 * SEQ[1].REFRESH is ignored if the samples size is equal to one.
 *
 * The PWM should generate a signal waveform described as following.
 * It's composed of 4 samples with one pulse each and 4 samples with zero level.
 *    __      __      __      __
 * __|  |____|  |____|  |____|  |___________________________________....
 * <---------- seq0 -------------->
 *                                 <---------- seq1 --------------->
 *
 * and the result is wrong !
 *    __      __      __      __
 * __|  |____|  |____|  |____|  |__________....
 * <---------- seq0 -------------->
 *                                 <-seq1->
 *
 * But, if I add more than one sample on the SEQ1 ( pwm1_seq1_values[] ), the problem doesn't occur
 * and the number of repeats is corresponding to pwm1_seq1.repeats value.
 */

#ifndef PWM1_ENABLED
	#error "PWM1 should be enable in sdk_config.h!"
#else
	static nrf_drv_pwm_t pwm1 = NRF_DRV_PWM_INSTANCE(1);
#endif


#define GPIO_OUTPUT_TEST_PIN	(3)	// P0.03

#define FREQ_PWM				(125E3)
#define PWM_TOP					(FREQ_PWM*0.25)		// 31250 (maxi 15 bits)
#define PWM_CH0 				(FREQ_PWM*0.15) 	// DEBUG


/* RAM location */
static nrf_pwm_values_common_t pwm1_seq0_values[] = {
	(PWM_CH0)
};


static const nrf_pwm_sequence_t pwm1_seq0 =
{
	.values.p_common	= pwm1_seq0_values,
	.length         = NRF_PWM_VALUES_LENGTH(pwm1_seq0_values),
	.repeats        = 3,	// < -- 4 samples for sequence 0
	.end_delay      = 0
};

/* RAM location */
static nrf_pwm_values_common_t pwm1_seq1_values[] = {
	(PWM_TOP),
//	(PWM_TOP),	// < -- workaround!
//	(PWM_TOP),
//	(PWM_TOP),
};


static const nrf_pwm_sequence_t pwm1_seq1 =
{
	.values.p_common	= pwm1_seq1_values,
	.length         = NRF_PWM_VALUES_LENGTH(pwm1_seq1_values),
	.repeats        = 3,	// < -- 4 samples for sequence 1 : ignored if samples size is one
	.end_delay      = 0
};

static const nrf_drv_pwm_config_t pwm1_config =
{
	.output_pins =
	{
		GPIO_OUTPUT_TEST_PIN | NRF_DRV_PWM_PIN_INVERTED, // channel 0
		NRF_DRV_PWM_PIN_NOT_USED,
		NRF_DRV_PWM_PIN_NOT_USED,
		NRF_DRV_PWM_PIN_NOT_USED
	},
	.irq_priority = APP_IRQ_PRIORITY_LOWEST,
	.base_clock   = NRF_PWM_CLK_125kHz,
	.count_mode   = NRF_PWM_MODE_UP_AND_DOWN,
	.top_value    = PWM_TOP,
	.load_mode    = NRF_PWM_LOAD_COMMON,
	.step_mode    = NRF_PWM_STEP_AUTO
};

static void test_pwm_init(void) {
	ret_code_t error;

	// Init PWM without irq handler
	error = nrf_drv_pwm_init(&pwm1, &pwm1_config, NULL); // NULL : don't use pwm_handler
    APP_ERROR_CHECK(error);

    error = nrf_drv_pwm_complex_playback(&pwm1, &pwm1_seq0, &pwm1_seq1, 1, NRF_DRV_PWM_FLAG_LOOP);
    APP_ERROR_CHECK(error);
}


void Test_PWM(void) {
	test_pwm_init();
}
Related