Fork of Erik Olieman's FastPWM library created to add the targets I need.
Fork of FastPWM by
FastPWM.h@4:a7b9f778c4b4, 2013-08-13 (annotated)
- Committer:
- Sissors
- Date:
- Tue Aug 13 16:54:06 2013 +0000
- Revision:
- 4:a7b9f778c4b4
- Parent:
- 3:3094d3806cfc
- Child:
- 6:0f57969697b6
v2.0
; Added KL25Z/LPC11u24 support
; Added prescalers
; Direct tick changes
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
Sissors | 1:1aed61747ed6 | 1 | /* |
Sissors | 1:1aed61747ed6 | 2 | .---. _....._ |
Sissors | 1:1aed61747ed6 | 3 | / p `\ .-""`: :`"-. |
Sissors | 1:1aed61747ed6 | 4 | |__ - | ,' . ' ', |
Sissors | 1:1aed61747ed6 | 5 | ._> \ /: : ; :, |
Sissors | 1:1aed61747ed6 | 6 | '-. '\`. . : ' \ |
Sissors | 1:1aed61747ed6 | 7 | `. | .'._.' '._.' '._.'. | |
Sissors | 1:1aed61747ed6 | 8 | `;-\. : : ' '/,__, |
Sissors | 1:1aed61747ed6 | 9 | .-'`'._ ' . : _.'.__.' |
Sissors | 1:1aed61747ed6 | 10 | ((((-'/ `";--..:..--;"` \ |
Sissors | 1:1aed61747ed6 | 11 | .' / \ \ |
Sissors | 1:1aed61747ed6 | 12 | jgs ((((-' ((((-' |
Sissors | 1:1aed61747ed6 | 13 | |
Sissors | 1:1aed61747ed6 | 14 | Yeah ASCII art turtle more fun than copyright stuff |
Sissors | 1:1aed61747ed6 | 15 | */ |
Sissors | 1:1aed61747ed6 | 16 | |
Sissors | 1:1aed61747ed6 | 17 | |
Sissors | 0:f8c1b0ad5371 | 18 | #include "mbed.h" |
Sissors | 0:f8c1b0ad5371 | 19 | |
Sissors | 0:f8c1b0ad5371 | 20 | #ifndef FASTPWM_H |
Sissors | 0:f8c1b0ad5371 | 21 | #define FASTPWM_H |
Sissors | 0:f8c1b0ad5371 | 22 | |
Sissors | 0:f8c1b0ad5371 | 23 | /** Library that allows faster and/or higher resolution PWM output |
Sissors | 0:f8c1b0ad5371 | 24 | * |
Sissors | 0:f8c1b0ad5371 | 25 | * Library can directly replace standard mbed PWM library. Only limitation is that the maximum PWM period is four times shorter |
Sissors | 0:f8c1b0ad5371 | 26 | * The maximum achievable period is roughly 40 seconds, I dont think that should be a problem. |
Sissors | 0:f8c1b0ad5371 | 27 | * Do take into account all PWM objects will run four times faster than default. |
Sissors | 0:f8c1b0ad5371 | 28 | * |
Sissors | 0:f8c1b0ad5371 | 29 | * Contrary to the default mbed library, this library takes doubles instead of floats. The compiler will autocast if needed, |
Sissors | 0:f8c1b0ad5371 | 30 | * but do take into account it is done for a reason, your accuracy will otherwise be limitted by the floating point precision. |
Sissors | 0:f8c1b0ad5371 | 31 | */ |
Sissors | 4:a7b9f778c4b4 | 32 | class FastPWM : public PwmOut { |
Sissors | 0:f8c1b0ad5371 | 33 | public: |
Sissors | 0:f8c1b0ad5371 | 34 | /** |
Sissors | 0:f8c1b0ad5371 | 35 | * Create a FastPWM object connected to the specified pin |
Sissors | 0:f8c1b0ad5371 | 36 | * |
Sissors | 0:f8c1b0ad5371 | 37 | * @param pin - PWM pin to connect to |
Sissors | 4:a7b9f778c4b4 | 38 | * @param prescaler - Clock prescaler, -1 is dynamic (default), 0 is bit random, everything else normal |
Sissors | 0:f8c1b0ad5371 | 39 | */ |
Sissors | 4:a7b9f778c4b4 | 40 | FastPWM(PinName pin, int prescaler = -1); |
Sissors | 0:f8c1b0ad5371 | 41 | |
Sissors | 0:f8c1b0ad5371 | 42 | /** |
Sissors | 0:f8c1b0ad5371 | 43 | * Set the PWM period, specified in seconds (double), keeping the duty cycle the same. |
Sissors | 0:f8c1b0ad5371 | 44 | */ |
Sissors | 0:f8c1b0ad5371 | 45 | void period(double seconds); |
Sissors | 0:f8c1b0ad5371 | 46 | |
Sissors | 0:f8c1b0ad5371 | 47 | /** |
Sissors | 0:f8c1b0ad5371 | 48 | * Set the PWM period, specified in milli-seconds (int), keeping the duty cycle the same. |
Sissors | 0:f8c1b0ad5371 | 49 | */ |
Sissors | 0:f8c1b0ad5371 | 50 | void period_ms(int ms); |
Sissors | 0:f8c1b0ad5371 | 51 | |
Sissors | 0:f8c1b0ad5371 | 52 | /** |
Sissors | 0:f8c1b0ad5371 | 53 | * Set the PWM period, specified in micro-seconds (int), keeping the duty cycle the same. |
Sissors | 0:f8c1b0ad5371 | 54 | */ |
Sissors | 0:f8c1b0ad5371 | 55 | void period_us(int us); |
Sissors | 0:f8c1b0ad5371 | 56 | |
Sissors | 0:f8c1b0ad5371 | 57 | /** |
Sissors | 0:f8c1b0ad5371 | 58 | * Set the PWM period, specified in micro-seconds (double), keeping the duty cycle the same. |
Sissors | 0:f8c1b0ad5371 | 59 | */ |
Sissors | 0:f8c1b0ad5371 | 60 | void period_us(double us); |
Sissors | 0:f8c1b0ad5371 | 61 | |
Sissors | 0:f8c1b0ad5371 | 62 | /** |
Sissors | 4:a7b9f778c4b4 | 63 | * Set the PWM period, specified in clock ticks, keeping _pulse width_ the same. |
Sissors | 4:a7b9f778c4b4 | 64 | * |
Sissors | 4:a7b9f778c4b4 | 65 | * This function can be used if low overhead is required. Do take into account the result is |
Sissors | 4:a7b9f778c4b4 | 66 | * board (clock frequency) dependent, and this does not keep an equal duty cycle! |
Sissors | 4:a7b9f778c4b4 | 67 | */ |
Sissors | 4:a7b9f778c4b4 | 68 | void period_ticks(uint32_t ticks); |
Sissors | 4:a7b9f778c4b4 | 69 | |
Sissors | 4:a7b9f778c4b4 | 70 | /** |
Sissors | 0:f8c1b0ad5371 | 71 | * Set the PWM pulsewidth, specified in seconds (double), keeping the period the same. |
Sissors | 0:f8c1b0ad5371 | 72 | */ |
Sissors | 0:f8c1b0ad5371 | 73 | void pulsewidth(double seconds); |
Sissors | 0:f8c1b0ad5371 | 74 | |
Sissors | 0:f8c1b0ad5371 | 75 | /** |
Sissors | 0:f8c1b0ad5371 | 76 | * Set the PWM pulsewidth, specified in milli-seconds (int), keeping the period the same. |
Sissors | 0:f8c1b0ad5371 | 77 | */ |
Sissors | 0:f8c1b0ad5371 | 78 | void pulsewidth_ms(int ms); |
Sissors | 0:f8c1b0ad5371 | 79 | |
Sissors | 0:f8c1b0ad5371 | 80 | /** |
Sissors | 0:f8c1b0ad5371 | 81 | * Set the PWM pulsewidth, specified in micro-seconds (int), keeping the period the same. |
Sissors | 0:f8c1b0ad5371 | 82 | */ |
Sissors | 0:f8c1b0ad5371 | 83 | void pulsewidth_us(int us); |
Sissors | 0:f8c1b0ad5371 | 84 | |
Sissors | 0:f8c1b0ad5371 | 85 | /** |
Sissors | 0:f8c1b0ad5371 | 86 | * Set the PWM pulsewidth, specified in micro-seconds (double), keeping the period the same. |
Sissors | 0:f8c1b0ad5371 | 87 | */ |
Sissors | 0:f8c1b0ad5371 | 88 | void pulsewidth_us(double us); |
Sissors | 0:f8c1b0ad5371 | 89 | |
Sissors | 0:f8c1b0ad5371 | 90 | /** |
Sissors | 4:a7b9f778c4b4 | 91 | * Set the PWM period, specified in clock ticks, keeping the period the same. |
Sissors | 4:a7b9f778c4b4 | 92 | * |
Sissors | 4:a7b9f778c4b4 | 93 | * This function can be used if low overhead is required. Do take into account the result is |
Sissors | 4:a7b9f778c4b4 | 94 | * board (clock frequency) dependent! |
Sissors | 4:a7b9f778c4b4 | 95 | */ |
Sissors | 4:a7b9f778c4b4 | 96 | void pulsewidth_ticks(uint32_t ticks); |
Sissors | 4:a7b9f778c4b4 | 97 | |
Sissors | 4:a7b9f778c4b4 | 98 | /** |
Sissors | 0:f8c1b0ad5371 | 99 | * Set the ouput duty-cycle, specified as a percentage (double) |
Sissors | 0:f8c1b0ad5371 | 100 | * |
Sissors | 0:f8c1b0ad5371 | 101 | * @param duty - A double value representing the output duty-cycle, specified as a percentage. The value should lie between 0.0 (representing on 0%) and 1.0 (representing on 100%). |
Sissors | 0:f8c1b0ad5371 | 102 | */ |
Sissors | 0:f8c1b0ad5371 | 103 | void write(double duty); |
Sissors | 0:f8c1b0ad5371 | 104 | |
Sissors | 0:f8c1b0ad5371 | 105 | /** |
Sissors | 0:f8c1b0ad5371 | 106 | * Return the ouput duty-cycle, specified as a percentage (double) |
Sissors | 0:f8c1b0ad5371 | 107 | * |
Sissors | 0:f8c1b0ad5371 | 108 | * @param return - A double value representing the output duty-cycle, specified as a percentage. |
Sissors | 0:f8c1b0ad5371 | 109 | */ |
Sissors | 0:f8c1b0ad5371 | 110 | double read( void ); |
Sissors | 0:f8c1b0ad5371 | 111 | |
Sissors | 0:f8c1b0ad5371 | 112 | /** |
Sissors | 0:f8c1b0ad5371 | 113 | * An operator shorthand for write() |
Sissors | 0:f8c1b0ad5371 | 114 | */ |
Sissors | 0:f8c1b0ad5371 | 115 | FastPWM& operator= (double value); |
Sissors | 0:f8c1b0ad5371 | 116 | |
Sissors | 0:f8c1b0ad5371 | 117 | /** |
Sissors | 0:f8c1b0ad5371 | 118 | * An operator shorthand for read() |
Sissors | 0:f8c1b0ad5371 | 119 | */ |
Sissors | 0:f8c1b0ad5371 | 120 | operator double(); |
Sissors | 0:f8c1b0ad5371 | 121 | |
Sissors | 4:a7b9f778c4b4 | 122 | /** |
Sissors | 4:a7b9f778c4b4 | 123 | * Set the PWM prescaler |
Sissors | 4:a7b9f778c4b4 | 124 | * |
Sissors | 4:a7b9f778c4b4 | 125 | * The period of all PWM pins on the same PWM unit have to be reset after using this! |
Sissors | 4:a7b9f778c4b4 | 126 | * |
Sissors | 4:a7b9f778c4b4 | 127 | * @param value - The required prescaler. Special values: 0 = lock current prescaler, -1 = use dynamic prescaler |
Sissors | 4:a7b9f778c4b4 | 128 | * @param return - The prescaler which was set (can differ from requested prescaler if not possible) |
Sissors | 4:a7b9f778c4b4 | 129 | */ |
Sissors | 4:a7b9f778c4b4 | 130 | int prescaler(int value); |
Sissors | 4:a7b9f778c4b4 | 131 | |
Sissors | 0:f8c1b0ad5371 | 132 | private: |
Sissors | 4:a7b9f778c4b4 | 133 | void initFastPWM(void); |
Sissors | 4:a7b9f778c4b4 | 134 | |
Sissors | 4:a7b9f778c4b4 | 135 | uint32_t setPrescaler( uint32_t reqScale ); |
Sissors | 4:a7b9f778c4b4 | 136 | int calcPrescaler(uint64_t clocks); |
Sissors | 4:a7b9f778c4b4 | 137 | uint32_t getPeriod( void ); |
Sissors | 4:a7b9f778c4b4 | 138 | |
Sissors | 4:a7b9f778c4b4 | 139 | void updateTicks( uint32_t prescaler ); |
Sissors | 4:a7b9f778c4b4 | 140 | uint32_t bits; |
Sissors | 4:a7b9f778c4b4 | 141 | |
Sissors | 0:f8c1b0ad5371 | 142 | double _duty; |
Sissors | 0:f8c1b0ad5371 | 143 | |
Sissors | 4:a7b9f778c4b4 | 144 | double dticks, dticks_us; |
Sissors | 4:a7b9f778c4b4 | 145 | int iticks_ms, iticks_us; |
Sissors | 4:a7b9f778c4b4 | 146 | |
Sissors | 4:a7b9f778c4b4 | 147 | bool dynamicPrescaler; |
Sissors | 4:a7b9f778c4b4 | 148 | |
Sissors | 0:f8c1b0ad5371 | 149 | |
Sissors | 0:f8c1b0ad5371 | 150 | }; |
Sissors | 0:f8c1b0ad5371 | 151 | #endif |