; ------------------------------------------------------------------------
;
; Title:
;
;   PD02 -- PIC "4-pin" 10^2 frequency divider (10 MHz to 100 kHz)
;
; Function:
;
;   This PIC program implements a digital frequency divider: the external
;   input clock is divided by a factor of 100. For example, if the input
;   clock is 10 MHz then the output clock will be 100 kHz.
;
;                               ---o---
;              (Vdd) +5 V  ++++|1     8|====  ground (Vss)
;             input clock  >---|2 12F 7|--->  output clock
;                             -|3 6xx 6|-
;                             -|4     5|-
;                               -------
; Notes:
;
;   Only 4 pins are required: power (2-5V), ground, input and output.
;   Output frequency accuracy is the same as clock input accuracy.
;   Output duty cycle is 40% (not 50% perfect square wave).
;   Note: For added flexibility GP1(pin6) and GP4(pin3) match GP0(pin7).
;   Output drive current is 25 mA maximum per pin.
;   Coded for Microchip 12F675 but any '609 '615 '629 '635 '675 '683 works.
;
; Version:
;
;   26-Jan-2013  Tom Van Baak (tvb)  www.LeapSecond.com/pic
;
; ------------------------------------------------------------------------

; Microchip MPLAB IDE assembler code (mpasm).

        list        p=pic12f675
        include     p12f675.inc
        __config    _EC_OSC & _MCLRE_OFF & _WDT_OFF

; Register definitions.

        cblock  0x20            ; define register base
        endc

; One-time PIC 12F675 initialization.

        org     0               ; power-on entry here
        bcf     STATUS,RP0      ; bank 0
        clrf    GPIO            ; set all pins low
        movlw   07h             ; set mode to turn
        movwf   CMCON           ;   comparator off
        bsf     STATUS,RP0      ; bank 1
        clrf    ANSEL-0x80      ; set digital IO (no analog A/D)
        movlw   b'101100'       ; set GP0,GP1,GP4 as output(0) and
        movwf   TRISIO-0x80     ;   other pins are input(1)
        bcf     STATUS,RP0      ; bank 0

; With an external 10 MHz PIC clock the (4:1) execution rate is 2.5 MIPS.
; A 25 instruction (400 ns each) loop takes exactly 10 microseconds.
; Output pins are toggled twice per loop to create a 100 kHz signal.
; Note that because 25 is odd, a perfect square wave is not possible.
; Use 40% duty cycle: 10 cycles on (4 us) and 15 cycles off (6 us).

rise:   movlw   0xFF            ; (      1) all on
        movwf   GPIO            ; (      1) W -> output pin(s)
        call    Delay6          ; (      6)
        goto    fall            ; (      2)

fall:   movlw   0x00            ; (      1) all off
        movwf   GPIO            ; (      1) W -> output pin(s)
        call    Delay10         ; (     10)
        nop                     ; (      1)
        goto    rise            ; (      2)

        include delayw.asm      ; precise delay functions
        end
