5

I'm just getting started with PIC processors, driven mainly by a shortage of the simpler PICAXE from my local retailer. My question is, how do I read the length of a PWM pulse on a certain input pin (analogous to the PULSIN command on PICAXEs). I'm using the MPLab IDE, and the specific PIC in question is the 12F683. Secondly, (sorry to combine two questions into one), are there libraries out there that contain 'common' functions (PWM output, i2c support and the like)? Google's turning up dry-ish, but it seems to me that such libraries have to be out there, somewhere.... Thanks for any help!

EDIT: the language is C, and the PWM signal is the output from a RC reciever intended for a servo, so, it is a 1-2 ms high pulse every 20 ms (if I understand that correctly)

Chris
  • 617
  • 9
  • 15
  • 1
    You forgot to mention the language that you are using. Assembler, C, Jal, maybe Pascal? – Wouter van Ooijen Jul 08 '12 at 10:06
  • or COBOL perhaps? :-) – stevenvh Jul 08 '12 at 11:09
  • Also the PWM's frequency – stevenvh Jul 08 '12 at 11:09
  • Apparently the 12F683 chip has a "capture/compare/PWM" module that let's you time the duration of an event on a given pin. Now the trick is finding the code that runs this, M'chip has example code, but only for the PIC18Fxx, I'll give it a try when I get the chips... – Chris Jul 08 '12 at 14:11
  • See the options part in my [question](http://electronics.stackexchange.com/q/35050/5035) to have some idea of how things work. – abdullah kahraman Jul 09 '12 at 09:52
  • It's a link only (don't have time now to summarize it, so I don't post it as an answer), but it may help you: http://www.bobblick.com/techref/projects/sv2hb/sv2hb2/sv2hb2.html – Axeman Jul 10 '12 at 12:32

3 Answers3

5

There are various ways to measure the width of incoming pulses. Which is most appropriate depends on the width of the pulses, what accuracy you need, and which peripherals your PIC has. Some possibilities are:

  1. Use two CCP modules in capture mode. This is not possible for your particular PIC since it has only one CCP module, I'll mention it anyway for others or in case you change the PIC. A CCP module in capture mode grabs a snapshot of the free running 16 bit timer 1 on the edge of a I/O pin. With two of these captures, one for each edge, you subtract them to get the pulse duration.

    This method allows for the shortest duration pulses and has the most accuracy, but takes two CCP modules.

  2. Use a single CCP module and flip the edge it captures on in a interrupt triggered by the first capture. This has the same accuracy and resolution as #1 and uses only a single CCP module, but requires the pulse to be some minimum width so that the interrupt routine has time to grab the captured value switch the capture edge polarity.

  3. Capture the free running timer 1 in firmware every edge, then do the subtraction as in #1 and #2. This requires no CCP module at all, but there must be some minimum time between edges for the interrupt routine to do its job. It also has a bit more error due to some uncertainty in the interrupt response, and possibly in variable number of instructions from the interrupt routine if not coded carefully.

  4. Gate timer 1 from the pulse. Have the trailing edge cause a interrupt, which then reads the timer 1 value and possibly resets it ready for the next pulse. This has good accuracy and resolution, but requires some minimum time between pulses for the interrupt to grab the timer 1 value and set up for the next pulse.

There are other methods too, but without knowing more about the characteristics of your pulses it's not worth spending time on them. Given that your PIC has a single CCP module and timer 1 with gating option, methods 2 and 4 are worth considering. Again, it would help to know more about the pulse characteristics.

One thing I didn't metion is overflow handling for long pulses, but if your pulses are known to be short enough this is not a issue.

Olin Lathrop
  • 310,974
  • 36
  • 428
  • 915
  • Method #4. I know one can get "automatically" counted pulse width (in timer increments) in single-pulse gate mode. You can also have full period length in single+toggle mode. What is the right way to calculate pulse as % if you can only go either for pulse or for period (one at a time)? Thanks a lot! – hypers Jan 30 '18 at 13:17
1

Microchip provides a Tips'n'trick collection, containing many useful (small) solutions for many problems. Part 3.4 provides a solution for measuring a pulse width (with the capture/compare functionality, as @Chris mentioned correctly). It explains what you do, but doesn't provide any source code (but together with the 12F683 data sheet it should be fairly easy to code this in C).

To your second question: Microchip provides such libraries only for their PIC18 series and upwards, so you are out of luck with the PIC12. But there are some other repositories of example code, which you can use a basis for your work.

hli
  • 2,336
  • 15
  • 17
1

As for the libraries, you could use mikroC C compiler for PIC from MikroElektronika. The free version they provide limits the output binary size to 2KB (it's not an issue with PIC12F683 as its program memory is also 2KB). Compiler comes with a lot of useful libraries like Pwm, Eeprom, Uart, Manchester etc. I've been using this IDE to play with PIC12F683 for a while, It's pretty easy to get used to.