servo and sevopos ... a startup and shutdown problem.

Volhout

New Member
In a setup I am using digital servo's that are tested to hold position in absence of input signal.
The only thing I need is a clea way to start the servo pulse chain for 7 servo's, and to end it in a clean way.
But I have run into the following 2 problems.

using 28X2

Problem 1: starting the 20mSec servo frame correctly
A typical initialization of 7(8) servo signals would be

Code:
servo B.0,150
servo B.1,150
servo B.2,150
servo B.3,150
servo B.4,150
servo B.5,150
servo B.6,150
servo B.7,150
But this causes the first servo pulse to the B.0 servo to extend to 4.5mSec. I figured this was becuase the first pulse was started, and during this pulse B.1...B.7 where added. So I tried reverse order. Since the pulse of B.6 would be generated prior to B.7 we have almost a whole 20mSec frame to initialize the servo's.

Code:
servo B.7,150
servo B.6,150
servo B.5,150
servo B.4,150
servo B.3,150
servo B.2,150
servo B.1,150
servo B.0,150
This causes the first pulse on B.7 to be 15 mSec.....far worse.
Then I tried to use pause , to forse the init of the added servo channels to happen outside the active pulse of the first channel.

Code:
servo B.0,150
pause 3                        'first pulse is max 2 msec
servo B.1,150
pause 3                        'second pulse is max 2 msec
servo B.2,150
pause 3                        '3rd pulse is max 2 msec, and we definitely did not cover a 20msec frame
servo B.3,150
pause 3                        'not important anymore for the story, but it is in the code
servo B.4,150
pause 3
servo B.5,150
pause 3
servo B.6,150
pause 3
servo B.7,150
pause 3
This way I ended up with a first pulse on B.3 of 20mSec. I seem to (completely) miss the point. Is there anyone that can suggest a 7(8) servo startup sequence that guaranties a glitch free startup of the whole 20mSec frame ?? This feels a bit like "try and error" without any logic behind it.



Problem 2: terminating the 20mSec frame correctly.

shutting down servo pulses by a "low B.x" is an option but that is not synchronized with the 20mSec servo frame, so it potentially cuts an active servo pulse in half, causing the servo to move. Therefore I had all my hopes set in "servopos B.x,OFF". Hoping that command would stop the timer for servo B.x and terminate correctly. Tests have shown that is not the case. "servopos B.x.OFF" also cuts pulses in half.

Code:
servo B.0,150
pause 20
servopos B.0,OFF
Generates a 1.5mSec first pulse, and a 1 mSec second pulse because it shuts B.0 down.

Another (non documented) feature of servopos ...

Code:
servo B.0,150
... code
servopos B.0,OFF
.... all kind of code 
servopos B.0,150
Does not start the sero pulses anymore. You need to use the "servo" command to start again. Bit awkward, using servopos to stop, and servo to start again. But that is just part of the learning curve I guess.

The idea I have now is to generate a 8'th servo pulse on B7 (I don't need that, 7 servo's is enough, but it will become part of the servo frame), and poll the B.7 line. When it is high, other servo's will be low, and I can (staring with B.0 who is the next in time) put all the lines low with fast "low B.x" commands.

When I solved the puzzles, I will let you know, but I welcome any suggestions....
 
Last edited:

Volhout

New Member
hi hippy,

Yes, that might be a suggestion.

I am currently just evaluating the picaxe for this applications, but changes like that are absolutely possible. And I like the picaxe development environment a lot.
But I am beginning to realize that it allows very fast development (If these, and the serrxd-, problems would not have existed, the project would be done in 1 day) as long as the commands do exactly what you need (or as long as you have no problems with a first and last pulse being somewhat different).

I haven't given up yet ...!! It would have taken me 2 days to write this in assembly for a PIC16F84 alike, and 2 more to test the heck out of it, so I am still on schedule....

Volhout
 

Goeytex

Senior Member
Things to try...

1. Make sure there is a 100nf Bypass capacitor across the Picaxe Power pins.

2. Use separate power sources for the Picaxe and Servos.

3. Operating 8 servos at the same time can draw considerable current. Make sure that your power source
is adequate.

4. Use some kind of noise suppression on the servos. 8 servos motors running at the same time can generate
quite a bit of electrical noise.

5. Try operating the Picaxe at 32Mhz to reduce command overhead time. (Setfreq m32)

6. Start small. Try 2 servos first, then add servos to see what happens.

Good Luck
 

hippy

Ex-Staff (retired)
The idea I have now is to generate a 8'th servo pulse on B7 (I don't need that, 7 servo's is enough, but it will become part of the servo frame), and poll the B.7 line. When it is high, other servo's will be low, and I can (staring with B.0 who is the next in time) put all the lines low with fast "low B.x" commands.
For ensuring only full servo pulses are passed to the servos, it would be possible to use some simple logic to either pass the servo signals or output zeroes. It should be simple enough to get that to switch from zeroes to pass-through once all servo signals have been set, and switch to zeroes only when there are no servo pulses.

You could probably use a flip-flop ...

servo_pulse AND enable_servos --> SET ( pass-through )

( NOT servo_pulse ) AND ( NOT enable_servos ) --> RESET ( zeroes )

Or something like that. Once you have a hardware solution you'll have a lot less worry what the software may be doing when initialising or turning on or off.
 

erco

Senior Member
You're not referring to initial servo glitch on powerup, are you? Not sure if digital servos do that.

You might try pulsouts in place of the servo commands. That seems to help in some situations, but you have to program the loops & delays yourself. Not as tidy as the servo/servopos commands.
 

Volhout

New Member
Things to try...

5. Try operating the Picaxe at 32Mhz to reduce command overhead time. (Setfreq m32)

Good Luck
I have tried this. The 4.5mSec changed down to 2.8mSec, so still not usable, but I found another nice fix... I need 7 channels, and can open 8 servo channels. I planned to use B.0-B.6, but why not skip the first one ? Only B.0 has the longer pulse at the start.
So I will only use B.1-B.7 for the 7 servo's , and not use B.0. Issue solved.

hippy: thanks for the tip on the hardware disable, and as it is simple to construct, and leads to the target. But I will try to fix it in software first. That is my primary challenge now.
 
Last edited:

Volhout

New Member
If anyone is interested, this solution works.

1/ dummy channel B.0 prevents irregular first pulse
2/ terminate by polling dummy channel, and when high (others are low) shutting down the output.

in code
Code:
setfreq em32			'not really needed, it also works without


'start the 7 servo channels
servo B.0,150			'dummy channel 0
servo B.1,150			'channel 1
servo B.2,150
servo B.3,150
servo B.4,150
servo B.5,150
servo B.6,150
servo B.7,150			'channel 7

'put your code here
pause 1000
'end of user code


'terminate the servo outputs just before shutdown/re-program
do
loop until pinB.0 = 1		'wait here until dummy servo channel B.0 is active

low outpinsB			'now the others are inactive (low), turn them off		
low B.0				'for some reason B.0 is not low (changed to input ?)
				'force it low.
				'this also kills the servo frame. Not sure how, 
				'but no pulses show anymore.

end
The behaviour at the end was not what I expected (I did not have to kill the servo channels with servopos x.x,OFF) so if I ever get a firmware update in the picaxe 28x2, I need to check this again. But anyway...it works.
Only need a few lines to convert hser input data output to servopos. That is a no-brainer....
 

hippy

Ex-Staff (retired)
low outpinsB

That's probably not doing what you hope it would; it likely only sets one output low. It's more likely the END is what actually stops the servo pulses. You can probably get by with just -

Do : Loop Until pinB.0 = 1
End
 

Volhout

New Member
Confirmed !

Do : Loop Until pinB.0 = 1
End

Does work also. Only B.0 remains hig, but that is not connected to a servo anymore, so I don't care.
 

Goeytex

Senior Member
Only need a few lines to convert hser input data output to servopos. That is a no-brainer....

When hardware serial is enabled with "hsersetup".....you may find that the servos will glitch from time to time.
 

Volhout

New Member
Goeytex,

I hope you are wrong. I will see this monday (have a day off today). If that is the case, then interrupt priority is wrong.
And that is a software architecture fault.
A serial port is bi-directional and can therefore (with appropriate code) correct faults via the return channel (closed loop).
A servo signal is, per design,a control (has no feedback) so it completely depends on accuracy of the timing.
It's priority should always be higher than the serial port, especially since the serial port is hardware (buffered), so timing only becomes critical at very high speeds.

Volhout
 

papaof2

Senior Member
Goeytex,

I hope you are wrong. I will see this monday (have a day off today). If that is the case, then interrupt priority is wrong.
And that is a software architecture fault.
A serial port is bi-directional and can therefore (with appropriate code) correct faults via the return channel (closed loop).
A servo signal is, per design,a control (has no feedback) so it completely depends on accuracy of the timing.
It's priority should always be higher than the serial port, especially since the serial port is hardware (buffered), so timing only becomes critical at very high speeds.

Volhout
I wrote some code that used a servo and serial to an LCD display, among other things. If the serial out string was long enough, the servo would glitch.

Think about the PICAXE's intended audience: not professional designers but school children. The purpose of the chips is to introduce programming microprocessors, not build moon-shot-reliability products. Some of the chips use bit-banging serial, so they are heavy users of a timer without a servo being involved.

If you want perfect serial and perfect servo control, you probably can't use a single microprocessor that runs an interpreter (PICAXE). That means either running two PICAXE chips or learning a new language and learning how to set the microprocessor's parameters yourself. A PICAXE with a single byte of background serial receive could probably run a servo by getting its occasional servo update from a single serial byte: actual value for position, some low value for off.
 
Top