Hi All, I need to borrow your collective wisdom and experience. I have developed differential motor controls for everything from steppers to PWM dc motor controllers with PID but have only recently gotten around to discovering servos. Finding them pretty cool I built a quick wandering bot from a 12F629 and a couple of servos, with sonar to boot (not bad for an 8 pin cpu, you gotta love pics heheh). Having run out of I/O pins I wanted to move on to a 16F876 to take advantage of the dual CPP PWM. I built up a nice pcb and only after building it and doing the math did I discover like so many others that you can't directly get the period down lower than about 1.2 khz. I found an interesting snippet that did use the capture instead to measure only the ON duration and accurately turn it off after the 0.5-2.5 ms pulse but that's still not as good as a total HW solution. I already have a pretty nice SW PWM snippet that I wrote that basically increments on and off counters at 50us intervals so I can get the resolution I want but it still wasted cpu time, especially in an ISR. I was thinking about rewriting my pwm driving to use a single timer instead, resetting the 16 bit timer to just get tapped on the shoulder at each of the next stages in the pwm generation (turn on and time the on time, turn off and time the off time) and somehow intermix this idea to run two servos independantly, keeping the interrupts down to 4 per total periods (motor 1 on, motor 1 off/motor 2 on, motor 2 off/delay until next refresh of servos). What are the best solutions you have found for driving servos from pics, without relying on external pwm chips? Can the CCP PWM somehow be useful or is there a better sw solution? Thanks in advance for the advice, Trent |
|
SW vs HW PWM
I have no idea where I have seen it but it must have been on one of the popular pic sites that there was a project with 8 servo controls from a pic. Maybe google for it or it would probably be on one of the rings.
From: Trent
[mailto:s...@yahoo.com]
Hi
All, |
|
Yeah I have seen a lot of variations including 8 and even more, but I was disappointed that the two PWM generators in the PIC weren't being used in them. I was hoping several people had tried several methods and had a favorite, preferably one that used the hardware and not as much "turn the bit on, delay 1500 us, turn the bit off" type stuff that blocks all other operations. Cheers, Trent --- In , "martin de lange" <martin_de_lange@x> wrote: > I have no idea where I have seen it but it must have been on one of the > popular pic sites that there was a project with 8 servo controls from a pic. > Maybe google for it or it would probably be on one of the rings. > |
--- In , "martin de lange" <martin_de_lange@x> wrote: > I have no idea where I have seen it but it must have been on one of the > popular pic sites that there was a project with 8 servo controls from a pic. > Maybe google for it or it would probably be on one of the rings. > Al Williams offers PAC co-processors I think it is the PAC-V you are referring to. http://www.al-williams.com/pak5.htm Dave > _____ > > From: Trent [mailto:scoobytw@y...] > Sent: Sunday, 15 August 2004 17:01 > To: > Subject: [piclist] SW vs HW PWM > > Hi All, > > I need to borrow your collective wisdom and experience. I have > developed differential motor controls for everything from steppers to > PWM dc motor controllers with PID but have only recently gotten around > to discovering servos. Finding them pretty cool I built a quick > wandering bot from a 12F629 and a couple of servos, with sonar to boot > (not bad for an 8 pin cpu, you gotta love pics heheh). Having run out > of I/O pins I wanted to move on to a 16F876 to take advantage of the > dual CPP PWM. I built up a nice pcb and only after building it and > doing the math did I discover like so many others that you can't > directly get the period down lower than about 1.2 khz. I found an > interesting snippet that did use the capture instead to measure only > the ON duration and accurately turn it off after the 0.5-2.5 ms pulse > but that's still not as good as a total HW solution. I already have a > pretty nice SW PWM snippet that I wrote that basically increments on > and off counters at 50us intervals so I can get the resolution I want > but it still wasted cpu time, especially in an ISR. > > I was thinking about rewriting my pwm driving to use a single timer > instead, resetting the 16 bit timer to just get tapped on the shoulder > at each of the next stages in the pwm generation (turn on and time the > on time, turn off and time the off time) and somehow intermix this > idea to run two servos independantly, keeping the interrupts down to > 4 per total periods (motor 1 on, motor 1 off/motor 2 on, motor 2 > off/delay until next refresh of servos). > > What are the best solutions you have found for driving servos from > pics, without relying on external pwm chips? Can the CCP PWM somehow > be useful or is there a better sw solution? > > Thanks in advance for the advice, > Trent > > to unsubscribe, go to http://www.yahoogroups.com and follow the instructions <http://us.ard.yahoo.com/SIG9l50kpv/M)8184.5285298.6392945.300117 6/D=gr > oups/S06554205:HM/EXP92632454/A!64331/R=0/SIGeaelai9/*http: /www.n > etflix.com/Default?mqso`183351> click here > <http://us.adserver.yahoo.com/l? M)8184.5285298.6392945.3001176/D=groups/S= > :HM/A!64331/randd6932683> > > _____ > > > . |
|
Still cannot remember what the site was but it was a different one that had open source with it
From: Dave Mucha
[mailto:d...@yahoo.com]
--- In
p...@yahoogroups.com,
"martin de lange" <martin_de_lange@x> |
|
This has been done using TMR0 interrupts - join the MiniSumo Mark III Group and search on 'timer0'. There is a thread where the technique is discussed. The basic idea was to use 10 kHz as the interrupt rate and start all pulses every 200 interrupts. Resolution is 0.1 mS per interrupt and the pulses should be 1 to 2 mS wide with a center value of 1.5 mS or 15 interrupts. This resolution has steps of 20% in each direction, no exactly precise but for the application it is probably good enough. Somehow we figured that 3% of the processor cycles were being used but I haven't verified that. |
It sounds like you've already figured out a good solution. I, too, was dissapointed to discover that PIC PWMs dont get down that low but its really OK. Here's how I do it (might sound familiar): For a dual servo system, I use tmr0 to generate 50 uS ticks. In the ISR, I count down for 20 mS (servo period). At the start of the period, I load both PWM counters, set the servo pins high and start decrementing per tick. When a counter gets to 0, set the servo pin low. It works nicely and the per tick overhead is very small. The main loop simply sets the PWM counter load values and the ISR does the rest. I figured I could go all the way down to about 20 uS clock period @ 20mhz and still have enough cycles for my main loop. At 50 uS, the ISR only takes about 5% of the CPU but you do have to calculate worst case ISR execution time. This solution is fully generalizable to many more servos. Since the cost per servo in the ISR is, iirc, 5 instructions. --- In , "Trent" <scoobytw@y...> wrote: > Hi All, > > I need to borrow your collective wisdom and experience. I have > developed differential motor controls for everything from steppers to > PWM dc motor controllers with PID but have only recently gotten around > to discovering servos. Finding them pretty cool I built a quick > wandering bot from a 12F629 and a couple of servos, with sonar to boot > (not bad for an 8 pin cpu, you gotta love pics heheh). Having run out > of I/O pins I wanted to move on to a 16F876 to take advantage of the > dual CPP PWM. I built up a nice pcb and only after building it and > doing the math did I discover like so many others that you can't > directly get the period down lower than about 1.2 khz. I found an > interesting snippet that did use the capture instead to measure only > the ON duration and accurately turn it off after the 0.5-2.5 ms pulse > but that's still not as good as a total HW solution. I already have a > pretty nice SW PWM snippet that I wrote that basically increments on > and off counters at 50us intervals so I can get the resolution I want > but it still wasted cpu time, especially in an ISR. > > I was thinking about rewriting my pwm driving to use a single timer > instead, resetting the 16 bit timer to just get tapped on the shoulder > at each of the next stages in the pwm generation (turn on and time the > on time, turn off and time the off time) and somehow intermix this > idea to run two servos independantly, keeping the interrupts down to > 4 per total periods (motor 1 on, motor 1 off/motor 2 on, motor 2 > off/delay until next refresh of servos). > > What are the best solutions you have found for driving servos from > pics, without relying on external pwm chips? Can the CCP PWM somehow > be useful or is there a better sw solution? > > Thanks in advance for the advice, > Trent |
|
That is pretty much what I was wanting to hear. Low impact on the ISR while leaving the hardware to help out as much as it can. The numbers you are getting sound good too in case I want to try to get a little tighter resolution. Like all motors types I am finding that even after calibrating to find the center of each servos unique deadband area that they still run at _slightly_ different speeds so like all other bot projects it looks like there is going to be the need for encoders in this one too or the long term odometry goes out the window. Since the solution may end up being entirely timer based I may go back to using a 12F629 programmed as a dual PWM controller with encoder feedbacks and leave the main decision making in the '876. Another question on servos, I have read that your refresh period should be around 50ms and if it is faster, maybe every 20ms that they start to use more current and doing this isn't really worth any smoothness you might get. Any truth to this? I know they can eat a nine volt battery in a weekend and have also come to the conclusion that I'll probably run them off of a separate supply just to get rid of all the noise on the logic and power rails. And is there a need for any diodes on the servo connections to keep the inductance kicks away from the power supply or signal line from the pic like you have on other DC motors driven by pwm? Thanks again for the advice, Trent --- In , "Phil" <phil1960us@y...> wrote: > It sounds like you've already figured out a good solution. I, too, > was dissapointed to discover that PIC PWMs dont get down that low but > its really OK. > > Here's how I do it (might sound familiar): For a dual servo system, > I use tmr0 to generate 50 uS ticks. In the ISR, I count down for 20 > mS (servo period). At the start of the period, I load both PWM > counters, set the servo pins high and start decrementing per tick. > When a counter gets to 0, set the servo pin low. It works nicely and > the per tick overhead is very small. The main loop simply sets the > PWM counter load values and the ISR does the rest. > > I figured I could go all the way down to about 20 uS clock period @ > 20mhz and still have enough cycles for my main loop. At 50 uS, the > ISR only takes about 5% of the CPU but you do have to calculate worst > case ISR execution time. > > This solution is fully generalizable to many more servos. Since the > cost per servo in the ISR is, iirc, 5 instructions. > |
|
On the MiniSumo Mark III a set of 4 AA batteries powers the servos. A separate 9V battery powers the processor. 9V battery life is about 1 hour. The AAs may go a little more. The motors are brush type so I would expect a certain amount of noise although it doesn't seem to bother the servo electronics. FWIW, I kind of like the embedded Secret L293D driver that fits inside the servo and allows true all-hardware PWM control. Check out http://info.hobbyengineering.com/specs/Solorbotics-kit10.pdf I have two MiniSumos, identical except for the servo drives, and the one with the L293D wins almost every time. I haven't spent enough time to understand why. --- In , "Trent" <scoobytw@y...> wrote: > That is pretty much what I was wanting to hear. Low impact on the ISR > while leaving the hardware to help out as much as it can. The numbers > you are getting sound good too in case I want to try to get a little > tighter resolution. Like all motors types I am finding that even after > calibrating to find the center of each servos unique deadband area > that they still run at _slightly_ different speeds so like all other > bot projects it looks like there is going to be the need for encoders > in this one too or the long term odometry goes out the window. Since > the solution may end up being entirely timer based I may go back to > using a 12F629 programmed as a dual PWM controller with encoder > feedbacks and leave the main decision making in the '876. > > Another question on servos, I have read that your refresh period > should be around 50ms and if it is faster, maybe every 20ms that they > start to use more current and doing this isn't really worth any > smoothness you might get. Any truth to this? I know they can eat a > nine volt battery in a weekend and have also come to the conclusion > that I'll probably run them off of a separate supply just to get rid > of all the noise on the logic and power rails. > > And is there a need for any diodes on the servo connections to keep > the inductance kicks away from the power supply or signal line from > the pic like you have on other DC motors driven by pwm? > > Thanks again for the advice, > > Trent > > --- In , "Phil" <phil1960us@y...> wrote: > > It sounds like you've already figured out a good solution. I, too, > > was dissapointed to discover that PIC PWMs dont get down that low > but > > its really OK. > > > > Here's how I do it (might sound familiar): For a dual servo > system, > > I use tmr0 to generate 50 uS ticks. In the ISR, I count down for > 20 > > mS (servo period). At the start of the period, I load both PWM > > counters, set the servo pins high and start decrementing per tick. > > When a counter gets to 0, set the servo pin low. It works nicely > and > > the per tick overhead is very small. The main loop simply sets the > > PWM counter load values and the ISR does the rest. > > > > I figured I could go all the way down to about 20 uS clock period @ > > 20mhz and still have enough cycles for my main loop. At 50 uS, the > > ISR only takes about 5% of the CPU but you do have to calculate > worst > > case ISR execution time. > > > > This solution is fully generalizable to many more servos. Since > the > > cost per servo in the ISR is, iirc, 5 instructions. > > |
|
interesting questions (and answers). First, a question: on the secret L298 driver. Is the L298 mkIII faster than the stock servo one? Or does it appear to have more torque/pushing power? I have 2 stock servo mkIIIs and it looks to me like the faster one is able to get around the slower one (usually due to battery state) and push it. Once a minisumo is flanked, its usually over (and yes, I know there are experts that say its all about traction). Do yours wind up head-to-head or flanking? By the way, one of my mkIIIs is slightly better at head-to-head so it could be other factors (though I doubt it). some answers: I don't know on the servo update period. I've always seen 20 mS as the preferred target but with no explanation why. I'm pretty sure there is a fair amount of leeway in this since they are made for radio control devices and it makes sense not to go haywire if there's a missed pulse or two. It's not obvious to me why a faster update period would cause more draw - the internal controller is PWMing the motor and that's the vast majority of the current draw. If the PWM duty cycle is the same in both cases, wouldn't the current draw be the same? I'm pretty sure the servo controller has diodes. otherwise, they would get toasted a lot more often. A good robot design pays very close attention to isolating motor and logic supplies. Even if there is enough capacity to drive both, the motors will pull a lot of current and cause nasty fluctions as well as all that dirty noise. Dropouts from the motor pulling a lot of current will wreak havoc. Just try running mkIII electronics and motors on the AA pack for a rather stark lesson! Seperate batteries at first seems kind of ugly but when it eliminates a somewhat complex power subsystem, it looks pretty smart to me. I wouldn't run servos off of a 9V battery. Not enough capacity, at least for driving wheels for much time at all. I've also heard anechdotes that many brands of servos don't like much above 6-7ish VDC. I know the servos I have in my minisumos don't mind 7.2 VDC. I get the same battery life as rick. On differential speed. Yeah, I have this too on both bots but it doesn't matter since I update course/targeting data every couple hundred mS. If it sees an opponent, it tracks it. If it doesn't, it executes a turn within a few seconds. I guess you could put encoders into the servo - there's an article on the PARTS site, iirc, on that topic. I'm still a bit unsure of the value of encoders in small robots - there are so many other factors that will introduce errors. phil --- In , "rtstofer" <rstofer@p...> wrote: > > On the MiniSumo Mark III a set of 4 AA batteries powers the servos. > A separate 9V battery powers the processor. 9V battery life is > about 1 hour. The AAs may go a little more. > > The motors are brush type so I would expect a certain amount of > noise although it doesn't seem to bother the servo electronics. > > FWIW, I kind of like the embedded Secret L293D driver that fits > inside the servo and allows true all-hardware PWM control. Check > out http://info.hobbyengineering.com/specs/Solorbotics-kit10.pdf > > I have two MiniSumos, identical except for the servo drives, and the > one with the L293D wins almost every time. I haven't spent enough > time to understand why. > --- In , "Trent" <scoobytw@y...> wrote: > > That is pretty much what I was wanting to hear. Low impact on the > ISR > > while leaving the hardware to help out as much as it can. The > numbers > > you are getting sound good too in case I want to try to get a > little > > tighter resolution. Like all motors types I am finding that even > after > > calibrating to find the center of each servos unique deadband area > > that they still run at _slightly_ different speeds so like all > other > > bot projects it looks like there is going to be the need for > encoders > > in this one too or the long term odometry goes out the window. > Since > > the solution may end up being entirely timer based I may go back to > > using a 12F629 programmed as a dual PWM controller with encoder > > feedbacks and leave the main decision making in the '876. > > > > Another question on servos, I have read that your refresh period > > should be around 50ms and if it is faster, maybe every 20ms that > they > > start to use more current and doing this isn't really worth any > > smoothness you might get. Any truth to this? I know they can eat > a > > nine volt battery in a weekend and have also come to the conclusion > > that I'll probably run them off of a separate supply just to get > rid > > of all the noise on the logic and power rails. > > > > And is there a need for any diodes on the servo connections to keep > > the inductance kicks away from the power supply or signal line from > > the pic like you have on other DC motors driven by pwm? > > > > Thanks again for the advice, > > > > Trent > > > > --- In , "Phil" <phil1960us@y...> wrote: > > > It sounds like you've already figured out a good solution. I, > too, > > > was dissapointed to discover that PIC PWMs dont get down that low > > but > > > its really OK. > > > > > > Here's how I do it (might sound familiar): For a dual servo > > system, > > > I use tmr0 to generate 50 uS ticks. In the ISR, I count down for > > 20 > > > mS (servo period). At the start of the period, I load both PWM > > > counters, set the servo pins high and start decrementing per > tick. > > > When a counter gets to 0, set the servo pin low. It works nicely > > and > > > the per tick overhead is very small. The main loop simply sets > the > > > PWM counter load values and the ISR does the rest. > > > > > > I figured I could go all the way down to about 20 uS clock > period @ > > > 20mhz and still have enough cycles for my main loop. At 50 uS, > the > > > ISR only takes about 5% of the CPU but you do have to calculate > > worst > > > case ISR execution time. > > > > > > This solution is fully generalizable to many more servos. Since > > the > > > cost per servo in the ISR is, iirc, 5 instructions. > > > |
|