First, here's the Smalltalk code, the method processServo in class PICServoInterface:
processServos "Process the servo. Basically, servos work using pulse-width modulation, where the frequency is about 50 Hz, and the duty cycle determines the servo position. The duty cycle should be between approximately 1000 and 2000 micro-seconds, although different servos may require different duty cylces. These ones in particular have a duty cycle between about 690 and 1690 us." "Turn on the port to start with, and wait the initial 1 ms." ServoPort setBit: Servo1Pin. self servoDelay: 195. "Now count down, doing a comparison on each interation. When the count is equal to the servo's position, turn off the port." servoCounter := 250. [ self clearWatchdogTimer. servoCounter = servoOnePosition ifTrue: [ServoPort clearBit: Servo1Pin]] repeatWhile: [servoCounter decrementSkipIfZero]. ServoPort clearBit: Servo1Pin
And now, the PIC assembler produced:
; ========================================== ; = processServos ; ========================================== processServos equ * bsf ServoPort, Servo1Pin ; Generating call to 'servoDelay:' movlw 195 ; Pushing WReg (next two instructions)... decf indirectAddressLatch movwf indirect call servoDelay ; Popping (and ignoring) 1 variable from the stack... incf indirectAddressLatch movlw 250 movwf servoCounter Label_00 equ * clrwdt movfw servoOnePosition, w xorwf servoCounter, w btfsc status, Zero bcf ServoPort, Servo1Pin decfsz servoCounter goto Label_00 bcf ServoPort, Servo1Pin return
Go back to my PIC/Smalltalk page...