produces a pulse by inverting the state of the specified pin for a period of 1 to 65,535 units of 10 instruction cycles.
Pulsout can produce brief clock pulses to blip the enable lines of LCD modules and logic devices, or wide-range pulses to drive positioning servos. It differs from the Pwm command in two ways: it produces only one pulse each time it is called, and duty cycle is controlled by the ratio of the pulse width to the interval between pulses (if it is called repeatedly).
To use Pulsout, you must set the desired pin to output and supply three arguments: the desired length of the pulse in 10-instruction cycle units in the 16-bit variable consisting of hiB and lowB, the pin number (0 to 7) in pin, and the port number (0 = RA, 1 = RB, etc.) in w.
The type of pulse generated by Pulsout depends on the state of the pin's output latch when the routine is called. If pin is initially 1, Pulsout will invert it to 0 for the specified period of time, then restore it to 1. If it's initially 0, it will be set to 1 for the specified time, then cleared to 0.
Upon return, the contents of hiB and lowB will have been cleared, so keep copies of these values if they are required elsewhere in your program.
Half of Pulsout's 10-cycle delay is produced with nop instructions. If you want a 5-cycle version of Pulsout, remove the nops.
Pulsout, like the other routines that accept pin and port arguments, requires the short table Pinz. Remember that tables must be located in the first 256 words of a 512-word program memory page. One hint on using Pulsout: always assign the port number to w immediately before calling the routine. If you don't, some other instruction that uses w may change its contents, causing an error.
To see Pulsout in operation, either run the program with the PSIM simulator,
or connect the circuit below to an erasable PIC or PIC emulator, such as
the Parallax downloader. Assemble and run PULSOUT.SRC. The 'scope will show
a series of 100-µs pulses (assuming a 4-MHz clock for the PIC).
; PULSOUT port, pin, time ; Generates an output pulse in 10-cycle (10 us at 4 MHz) units, ; based on a 16-bit (1 to 65,535) value. The pulse is the reverse ; of the pin's state when pulsout is called. For instance, if the ; specified pin is initially 1, Pulsout will invert it to make a ; negative-going pulse. org 8 hiB ds 1 ; MSB of time. lowB ds 1 ; LSB of time. pin ds 1 ; Pin number to pulse (0-7). temp ds 1 ; Temporary variables for time delay temp2 ds 1 ; between pulses ; Device data and reset vector device pic16c55,xt_osc,wdt_off,protect_off reset start org 0 ; Table to convert pin number (0-7) into bit mask (00000001b to 10000000b). Pinz jmp pc+w retw 1,2,4,8,16,32,64,128 start mov !ra, #0 ; All outputs. clr ra ; Start with 0s. mov lowB,#10 ; 10 x 10-cycle pulse clr hiB mov pin,#2 ; Pin 2. mov w,#0 ; of port ra. call Pulsout ; Pulse pin high for 100 cycles. call delay ; Wait a while between pulses. jmp start ; Do it again. ; Upon entry, the desired pin must already be set up as an output. ; The w register contains a number representing the output port (0-2) for ; RA through RC. Variable "pin" contains the pin number (0-7). The variables ; hiB and lowB are the MSB and LSB of the time argument. Pulsout mov fsr,w ; Point to the port number. add fsr,#RA ; Add offset for port RA. mov w,pin call Pinz ; Get bit mask from the table. mov pin,w ; Put the mask into pin NOT hiB ; Take twos complement NEG lowB ; of the 16-bit counter snz ; If zero, lowB overflowed, inc hiB ; so carry into hiB. XOR indirect,pin ; Invert the selected pin. ; The main timing loop. Remove the nops for 5-cycle resolution. :loop jmp $+1 ; Two-cycle "nop." jmp $+1 ; Two-cycle "nop." nop inc lowB ; lowB = lowB+1. snz ; Overflow in lowB? incsz hiB ; Yes: hiB=hiB+1, watch for overflow. jmp :loop ; If not overflow, do it again. XOR indirect,pin ; Invert pin (back to initial state). ret ; Delay routine for demonstration. Not required by Pulsout. delay djnz temp,delay ; Time delay to provide spacing djnz temp2,delay ; between pulses. ret