Servo outputs private mixing

This forum is dedicated to software development related to MultiWii.
It is not the right place to submit a setup problem.
Software download
Post Reply
mpnemo
Posts: 2
Joined: Sat Dec 21, 2013 3:19 am

Servo outputs private mixing

Post by mpnemo »

Hello everyone,

I am having some issues trying to get some of the rc channels routed to free outputs, A0 and A1. What I did is using the hexa X on my promini, and in the mainloop (I know, not nice) just overwriting the values for motor 4 and 5 with my own servo mixing, depending on aux2 as a switch, routing the yaw and - well just some mixing - , which can be output via A0 and A1 pins.

I have a laser scanner on the quad, which I have to turn through a servo command, but right now the 488Hz kills the modified servo in less than 2 minutes.. I need to get the frame rate down to 50 Hz.

I am really not into the timers, besides, I think the A0 and A1 pin are still software generated. Would be anyway good to have some outputs that can generate some standard servo signals for some optional equipment, like sound generators, rocket launchers...

Any ideas on what can be done?

mpnemo
Posts: 2
Joined: Sat Dec 21, 2013 3:19 am

Re: Servo outputs private mixing

Post by mpnemo »

Hello everyone,

Thanks for the great help and many answers. I actually solved the issue myself.
The software PWM generation is almost not documented, there are a lot of things that have to be assumed.
I got it down to 67Hz, which is fine. The software PWM relies on two ISRs that are called via a timer compare vector.
Its pretty hard to understand what it does without any comments. Anyway, all you got to do is to add additional states that just filling the low state time until you reach the desired frame rate.

#if (NUMBER_MOTOR == 6) && (!defined(SERVO) && !defined(HWPWM6))
#define SERVO_1K_US 250;
ISR(SOFT_PWM_ISR1) {
static uint8_t state = 0;
if(state == 0){
if (atomicPWM_PIN5_highState>0) SOFT_PWM_1_PIN_HIGH;
SOFT_PWM_CHANNEL1 += atomicPWM_PIN5_highState;
state = 1;
}else if(state == 1){
SOFT_PWM_CHANNEL1 += atomicPWM_PIN5_highState;
state = 2;
}else if(state == 2){
SOFT_PWM_1_PIN_LOW;
SOFT_PWM_CHANNEL1 += atomicPWM_PIN5_lowState;
state = 3;
}else if(state == 3){
SOFT_PWM_CHANNEL1 += atomicPWM_PIN5_lowState;
state = 4;
}else if(state >= 4 && !(state == 16) ){
SOFT_PWM_CHANNEL1 += SERVO_1K_US;
state+=1;
}else if(state == 16 ){
SOFT_PWM_CHANNEL1 += SERVO_1K_US;
state=0;
}

If you need to change the hardware pwm, you have to play with the prescaler, set it to 8, and in the write motor function you would have to do divide the values by 8, too.
I havent done that, because I dont need to do it, but I guess that you are loosing signal resolution if you use the prescaler on hw pwm. The software PWM surely will cause some jitter, unless you sort out that the interrupts are called evenly over time.

Post Reply