@@ -231,7 +231,9 @@ static int __pwm_write_waveform(struct pwm_chip *chip, struct pwm_device *pwm, c
231
231
*
232
232
* Usually all values passed in @wf are rounded down to the nearest possible
233
233
* value (in the order period_length_ns, duty_length_ns and then
234
- * duty_offset_ns). Only if this isn't possible, a value might grow.
234
+ * duty_offset_ns). Only if this isn't possible, a value might grow. See the
235
+ * documentation for pwm_set_waveform_might_sleep() for a more formal
236
+ * description.
235
237
*
236
238
* Returns: 0 on success, 1 if at least one value had to be rounded up or a
237
239
* negative errno.
@@ -411,6 +413,26 @@ static int __pwm_set_waveform(struct pwm_device *pwm,
411
413
* possible/needed. In the above example requesting .period_length_ns = 94 and
412
414
* @exact = true, you get the hardware configured with period = 93.5 ns.
413
415
*
416
+ * Let C be the set of possible hardware configurations for a given PWM device,
417
+ * consisting of tuples (p, d, o) where p is the period length, d is the duty
418
+ * length and o the duty offset.
419
+ *
420
+ * The following algorithm is implemented to pick the hardware setting
421
+ * (p, d, o) ∈ C for a given request (p', d', o') with @exact = false::
422
+ *
423
+ * p = max( { ṗ | ∃ ḋ, ȯ : (ṗ, ḋ, ȯ) ∈ C ∧ ṗ ≤ p' } ∪ { min({ ṗ | ∃ ḋ, ȯ : (ṗ, ḋ, ȯ) ∈ C }) })
424
+ * d = max( { ḋ | ∃ ȯ : (p, ḋ, ȯ) ∈ C ∧ ḋ ≤ d' } ∪ { min({ ḋ | ∃ ȯ : (p, ḋ, ȯ) ∈ C }) })
425
+ * o = max( { ȯ | (p, d, ȯ) ∈ C ∧ ȯ ≤ o' } ∪ { min({ ȯ | (p, d, ȯ) ∈ C }) })
426
+ *
427
+ * In words: The chosen period length is the maximal possible period length not
428
+ * bigger than the requested period length and if that doesn't exist, the
429
+ * minimal period length. The chosen duty length is the maximal possible duty
430
+ * length that is compatible with the chosen period length and isn't bigger than
431
+ * the requested duty length. Again if such a value doesn't exist, the minimal
432
+ * duty length compatible with the chosen period is picked. After that the duty
433
+ * offset compatible with the chosen period and duty length is chosen in the
434
+ * same way.
435
+ *
414
436
* Returns: 0 on success, -EDOM if setting failed due to the exact waveform not
415
437
* being possible (if @exact), or a different negative errno on failure.
416
438
* Context: May sleep.
0 commit comments