Many people would like to use PAKs that use SHIFTIN/SHIFTOUT with Pic Basic from MELabs. You can do this, but there are a few things you need to know.

The problem is that the ShiftIn/ShiftOut command is too fast on some versions of PIC Basic. This will depend, too, on the speed of the PIC you are using.

One answer is to use the "roll your own" approach, and write your own substitutes for ShiftIn/ShiftOut as shown in the PAK manuals (for the Stamp I). Make sure you have enough time between pulses (the value depends on the type of PAK -- read PAK Interfacing for more details.

You might think that you could use DEFINE SHIFT_PAUSEUS, however that is broken in some versions of PIC Basic. If it is ever fixed, this should work fine. However, the current workaround suggested by MELabs is to open up PBPPIC14.LIB and find the line that reads:

goto $ + 1 ; Slow down transfer

Add some more lines of "goto $+1" just below that. Each line will add 2uS at 4MHz (scale for your clock rate). So:

goto $ + 1
goto $ + 1
goto $ + 1
goto $ + 1

Would add 8uS to the already 2uS that is there for a total of 10uS. However, recent versions (version 2.40, at least) account for your clock speed correctly, so there is no need to worry about it. Typically, you'll need to make the following changes to our Basic Stamp libraries:

Change the I/O pin definitions to match what you are using
Change any nibble variables to bytes
Add any specific defines you need for PBP
If you are running a fast PIC you may need to add some delay into the FReset command, and perhaps other commands that might need a little time to execute. However, PAKs that have functions take a long time to execute usually handle that by indicating when they are done (for example, math functions on a PAK I, II, or IX).
Include modedefs.bas (part of PBP) to define things like MSBFIRST, etc.

For the maximum control, you can "roll your own" SHIFTIN and SHIFTOUT commands. Here's an example:

pakclock con 3 ' 6us @ 20MHz (adjust for your clock)
pakclocklow con 3 ' 3uS low 6uS + 3uS + 1uS hold = 10uS = 100kbps

shiftoutput: ' sends iobyte
output datapin
for i=0 to 7
' Set data pin to 0 or 1
low datapin
if (iobyte & $80) <> $80 then goto so0
high datapin
so0:
iobyte=iobyte<<1 ' shift byte left
pauseus pakclocklow
pulsout clk,pakclock
pauseus 1 
next
pauseus 50 ' give it some time to process
return

shiftinput:
input datapin
iobyte=0
for i=0 to 7
iobyte=iobyte<<1 ' shift left
iobyte=iobyte | datap
pauseus pakclocklow
pulsout clk,pakclock
pauseus 1 ' hold data a tick
next
return

You need to adjust the pakclock and pakclocklow constants to match your processor speed and the speed of the PAK. The code above works for a 50MHz PAK.

As an example, here is the PAK-VIII library converted to PIC Basic Pro (this library appears on the product disk since April 25, 2002). You can also find a PAK-VII library that uses "roll your own" SHIFTIN and SHIFTOUT commands on this page. There is also a PAK-I library that would be easy to adapt to the PAK-II or IX (since the PAK-II and IX are based on the PAK-I).

' These are some starter routines
' that will help you use the PAK-8
' Coprocessor from AWC
' For PIC Basic Pro V2.40

Include "modedefs.bas"
define LOADER_USED 1 ' comment this out if not using a boot loader
Define OSC 20        ' change to suit your speed


' Change these to suit your setup
datap var portc.2 ' Data pin (I/O)
datapin var portc.2
clk var portc.3 ' Clk pin (output)

' Register names
DURLOW con %000
DURHIGH con %001
HIGHDUR con %010
LOWDUR con %011
PSCALE con %100
PSBASE con %101
N con %110
CTRL con %111


output clk
output datap

fpx var word ' Integer used by some routines
fpb var byte ' byte
' parameters for FCommand
chan var byte
register var byte


gosub freset ' always reset!

' TEST CODE -- REPLACE WITH YOUR OWN
' This program blinks an LED on the PAK's port 0 at 1Hz
t:
gosub FTotalReset ' hard reset


top:

chan=0
register=1
fpx=50000 ' 500 ms on and off = 500ms period = 1Hz
gosub FCommand
register=2 ' no need to set register again
gosub FCommand
' turn on pulse operation of channel 0
fpb=3
gosub FJam

stopit:
goto stopit

' End of your code -- everything from here down is library code

' Reset the Pak8 I/O
FReset:
LOW DATAP
LOW CLK
pauseus 50 ' might be able to reduce these pauses if necessary
HIGH CLK
pauseus 50
HIGH DATAP
pauseus 50
LOW CLK 
pauseus 50
return

' 0 is 0, 1 is 1, 2 is hi-z, 3 is normal
' note: 3 enables channel to run!
FJam:
fpb=chan + (fpb<<3)+%01000000
goto FSendByte

FCommand:
' inputs chan = channel, register = register
fpb=(register<<3) + chan
gosub FSendByte
fpb=fpx.lowbyte
gosub FSendByte
fpb=fpx.highbyte
goto FSendByte


FReadReg:
fpb=(register<<3) + chan + %10000000
gosub FSendByte
' fall into FReadWord


FReadWord:
Shiftin datap,clk,MSBPRE,[fpx.lowbyte,fpx.highbyte]
return

FTotalReset:
fpb=$FF
FSendByte:
Shiftout datap,clk,MSBFIRST,[fpb]
return

FReadByte:
shiftin datap,clk,MSBPRE,[fpb]
return

FPrescale:
' set fpb to the prescale constant
fpb = fpb + $C0
goto FSendByte


Site contents © 1997-2014 by AWC, 310 Ivy Glen, League City, TX 77573    (281) 334-4341