Skip to content

Commit 1a53ced

Browse files
authored
Merge pull request #2212 from jepler/nrf-audio-issue2203
nrf: PWMAudioOut: deactivate PWM when deinitting self
2 parents 0ccab50 + fae6e29 commit 1a53ced

File tree

1 file changed

+30
-26
lines changed

1 file changed

+30
-26
lines changed

ports/nrf/common-hal/audiopwmio/PWMAudioOut.c

Lines changed: 30 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -64,23 +64,25 @@ STATIC uint32_t calculate_pwm_parameters(uint32_t sample_rate, uint32_t *top_out
6464
}
6565

6666
STATIC void activate_audiopwmout_obj(audiopwmio_pwmaudioout_obj_t *self) {
67-
for(size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
68-
if(!active_audio[i]) {
67+
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
68+
if (!active_audio[i]) {
6969
active_audio[i] = self;
7070
break;
7171
}
7272
}
7373
}
7474
STATIC void deactivate_audiopwmout_obj(audiopwmio_pwmaudioout_obj_t *self) {
75-
for(size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
76-
if(active_audio[i] == self)
75+
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
76+
if (active_audio[i] == self) {
7777
active_audio[i] = NULL;
78+
}
7879
}
7980
}
8081

8182
void audiopwmout_reset() {
82-
for(size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++)
83+
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
8384
active_audio[i] = NULL;
85+
}
8486
}
8587

8688
STATIC void fill_buffers(audiopwmio_pwmaudioout_obj_t *self, int buf) {
@@ -97,25 +99,25 @@ STATIC void fill_buffers(audiopwmio_pwmaudioout_obj_t *self, int buf) {
9799
}
98100
uint32_t num_samples = buffer_length / self->bytes_per_sample / self->spacing;
99101

100-
if(self->bytes_per_sample == 1) {
102+
if (self->bytes_per_sample == 1) {
101103
uint8_t offset = self->signed_to_unsigned ? 0x80 : 0;
102104
uint16_t scale = self->scale;
103-
for(uint32_t i=0; i<buffer_length/self->spacing; i++) {
105+
for (uint32_t i=0; i<buffer_length/self->spacing; i++) {
104106
uint8_t rawval = (*buffer++ + offset);
105107
uint16_t val = (uint16_t)(((uint32_t)rawval * (uint32_t)scale) >> 8);
106108
*dev_buffer++ = val;
107-
if(self->spacing == 1)
109+
if (self->spacing == 1)
108110
*dev_buffer++ = val;
109111
}
110112
} else {
111113
uint16_t offset = self->signed_to_unsigned ? 0x8000 : 0;
112114
uint16_t scale = self->scale;
113115
uint16_t *buffer16 = (uint16_t*)buffer;
114-
for(uint32_t i=0; i<buffer_length/2/self->spacing; i++) {
116+
for (uint32_t i=0; i<buffer_length/2/self->spacing; i++) {
115117
uint16_t rawval = (*buffer16++ + offset);
116118
uint16_t val = (uint16_t)((rawval * (uint32_t)scale) >> 16);
117119
*dev_buffer++ = val;
118-
if(self->spacing == 1)
120+
if (self->spacing == 1)
119121
*dev_buffer++ = val;
120122
}
121123
}
@@ -124,30 +126,30 @@ STATIC void fill_buffers(audiopwmio_pwmaudioout_obj_t *self, int buf) {
124126

125127
if (self->loop && get_buffer_result == GET_BUFFER_DONE) {
126128
audiosample_reset_buffer(self->sample, false, 0);
127-
} else if(get_buffer_result == GET_BUFFER_DONE) {
129+
} else if (get_buffer_result == GET_BUFFER_DONE) {
128130
self->pwm->SHORTS = NRF_PWM_SHORT_SEQEND0_STOP_MASK | NRF_PWM_SHORT_SEQEND1_STOP_MASK;
129131
self->stopping = true;
130132
}
131133
}
132134

133135
STATIC void audiopwmout_background_obj(audiopwmio_pwmaudioout_obj_t *self) {
134-
if(!common_hal_audiopwmio_pwmaudioout_get_playing(self))
136+
if (!common_hal_audiopwmio_pwmaudioout_get_playing(self))
135137
return;
136-
if(self->stopping) {
138+
if (self->stopping) {
137139
bool stopped =
138140
(self->pwm->EVENTS_SEQEND[0] || !self->pwm->EVENTS_SEQSTARTED[0]) &&
139141
(self->pwm->EVENTS_SEQEND[1] || !self->pwm->EVENTS_SEQSTARTED[1]);
140-
if(stopped)
142+
if (stopped)
141143
self->pwm->TASKS_STOP = 1;
142-
} else if(!self->paused && !self->single_buffer) {
143-
if(self->pwm->EVENTS_SEQSTARTED[0]) fill_buffers(self, 1);
144-
if(self->pwm->EVENTS_SEQSTARTED[1]) fill_buffers(self, 0);
144+
} else if (!self->paused && !self->single_buffer) {
145+
if (self->pwm->EVENTS_SEQSTARTED[0]) fill_buffers(self, 1);
146+
if (self->pwm->EVENTS_SEQSTARTED[1]) fill_buffers(self, 0);
145147
}
146148
}
147149

148150
void audiopwmout_background() {
149-
for(size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
150-
if(!active_audio[i]) continue;
151+
for (size_t i=0; i < MP_ARRAY_SIZE(active_audio); i++) {
152+
if (!active_audio[i]) continue;
151153
audiopwmout_background_obj(active_audio[i]);
152154
}
153155
}
@@ -157,7 +159,7 @@ void common_hal_audiopwmio_pwmaudioout_construct(audiopwmio_pwmaudioout_obj_t* s
157159
assert_pin_free(left_channel);
158160
assert_pin_free(right_channel);
159161
self->pwm = pwmout_allocate(256, PWM_PRESCALER_PRESCALER_DIV_1, true, NULL, NULL);
160-
if(!self->pwm) {
162+
if (!self->pwm) {
161163
mp_raise_RuntimeError(translate("All timers in use"));
162164
}
163165

@@ -172,7 +174,7 @@ void common_hal_audiopwmio_pwmaudioout_construct(audiopwmio_pwmaudioout_obj_t* s
172174
self->pwm->PSEL.OUT[0] = self->left_channel_number = left_channel->number;
173175
claim_pin(left_channel);
174176

175-
if(right_channel)
177+
if (right_channel)
176178
{
177179
self->pwm->PSEL.OUT[2] = self->right_channel_number = right_channel->number;
178180
claim_pin(right_channel);
@@ -192,12 +194,14 @@ void common_hal_audiopwmio_pwmaudioout_deinit(audiopwmio_pwmaudioout_obj_t* self
192194
if (common_hal_audiopwmio_pwmaudioout_deinited(self)) {
193195
return;
194196
}
197+
deactivate_audiopwmout_obj(self);
198+
195199
// TODO: ramp the pwm down from quiescent value to 0
196200
self->pwm->ENABLE = 0;
197201

198-
if(self->left_channel_number)
202+
if (self->left_channel_number)
199203
reset_pin_number(self->left_channel_number);
200-
if(self->right_channel_number)
204+
if (self->right_channel_number)
201205
reset_pin_number(self->right_channel_number);
202206

203207
pwmout_free_channel(self->pwm, 0);
@@ -230,12 +234,12 @@ void common_hal_audiopwmio_pwmaudioout_play(audiopwmio_pwmaudioout_obj_t* self,
230234
audiosample_get_buffer_structure(sample, /* single channel */ false,
231235
&self->single_buffer, &self->signed_to_unsigned, &max_buffer_length,
232236
&self->spacing);
233-
if(max_buffer_length > UINT16_MAX) {
237+
if (max_buffer_length > UINT16_MAX) {
234238
mp_raise_ValueError_varg(translate("Buffer length %d too big. It must be less than %d"), max_buffer_length, UINT16_MAX);
235239
}
236240
self->buffer_length = (uint16_t)max_buffer_length;
237241
self->buffers[0] = m_malloc(self->buffer_length * 2 * sizeof(uint16_t), false);
238-
if(!self->single_buffer)
242+
if (!self->single_buffer)
239243
self->buffers[1] = m_malloc(self->buffer_length * 2 * sizeof(uint16_t), false);
240244

241245

@@ -274,7 +278,7 @@ void common_hal_audiopwmio_pwmaudioout_stop(audiopwmio_pwmaudioout_obj_t* self)
274278
}
275279

276280
bool common_hal_audiopwmio_pwmaudioout_get_playing(audiopwmio_pwmaudioout_obj_t* self) {
277-
if(!self->paused && self->pwm->EVENTS_STOPPED) {
281+
if (!self->paused && self->pwm->EVENTS_STOPPED) {
278282
self->playing = false;
279283
self->pwm->EVENTS_STOPPED = 0;
280284
}

0 commit comments

Comments
 (0)