Создание собственной системы стабилизации
рабочий код вижу. расскажите, пожалуйста, в двух словах суть самого процесса считывания ШИМа, чтобы лучше код осмыслить…
У обычного таймера СТМ32 всего один вектор прерываний, но события, с которыми он в этот вектор выпадает, могут быть разными или набором событий. У таймера есть 4 входа захвата ШИМ, используем их соответственно для каждого канала РУ.
Алгоритм для одного канала такой:
-
Проверяем наличие флага захвата канала, если нет переходим к следующему каналу п4.
-
Если порт в “1”,
то перенастраиваем канал на приём спада,
сохраняем значение из регистра захвата в буфере. -
Если порт “0”,
перенастраиваем канал на приём фронта,
делаем беззнаковое вычитание буфера из регистра захвата (получаем длительность в тактах таймера),
обнуляем счётчик пропусков. -
… здесь аналогично остальные каналы …
-
Если установлен флаг переполнения, то увеличиваем счётчики пропусков всех каналов.
-
сбрасываем все флаги.
Но это для СТМ32 (я для oleg70 писал), для АВР по другому (я бы сказал намного хуже).
это 3D (акро) режим, который есть почти во всех полетных контроллерах…
я не делал отдельный режим, у меня все режимы влияют только на вращение управляющего кватерниона, задаётся либо наклон, либо скорость вращения вокруг соответствующей оси. АП просто пытается привести текущее положение к заданому.
аж башка трешит - мысли через уши лезут, этож блин пол кодятника перелопатил
Вот поэтому я и пишу своё, только иногда иногда что то заимствую. В вий и пират мне страшно заглядывать ( да и не нужно уже 😃).
Как вариант измерения ШИМ: на каждую (желаемую) входную ногу “вешаем” отдельную однотипную функцию прерывания по обоим фронтам в которой:
1.если порт/бит =1 стартуем счетчик.
2.если порт/бит=0 останавливаем счет, пишем в переменную, обнуляем счетчик.
Плюсы (мое мнение):
1.однозначно определен номер канала
2.не нужно ничего вычитать
3.как следствие, лаконичней код обработчика прерывания.
Интересно Ваше мнение на этот счет ? (пока я не начал ковыряться с реализацией).
Интересно Ваше мнение на этот счет ?
Работать будет, но сколько Вам потребуется счетчиков и входов прерываний? В п.2 сколько времени нужно для в хода в прерывание если оно не самое преоритетное, такты не пропустите?
пока я не начал ковыряться с реализацией
А Вы попробуйте! Возможно появится стимул изучить подробней возможности перифирии, а она у СТМ32 зело способная 😃
Оптимальный вариант, использовать ICP пины, по одному на каждый канал. Естественно, если процессор это позволяет. В большинстве случаев, приходится извращаться, т.к. доступен бывает только один таймер и что хуже всего, при изменении одного из 8 пинов, приходит одинаковое прерывание. Но это все фигня и вполне, даже AVR вполне с этим справляется.
В сети можно найти кучу реализаций обработки PPM или PWM. Начиная от multiwii и пирата, потом PPM Encoder у Ардукоптера. Ну хватает опенсорсных проектов под STM32… Зачем изобретать велосипед???
Зачем изобретать велосипед???
Мыж тут о “собственной системе стабилизации” размышляем, потому и пост…
Если велосипед едет лучше мотоцикла, почему не попробовать изобрести,
а так то конечно “все давно придумано”.
Думаю так: готовых проектов много, общие принципы ясны, разница только в подходах к реализации (как раз в этих мелочах типа приоритетов и методов) и результаты у разных систем особенные… что собственно и интересно…
Подскажите, пожалуйста проекты на STM32F103 и на STM32F4 с открытым исходным кодом, чтобы не изобретать велосипед.
Я нашел:
OpenPilot вроде под STM32F103 - хорош, но специфический набор датчиков (у меня их нет) и структура такая, как будто они винду пишут на МК.
Afroflight - вроде ничего, под какой именно МК не знаю
APM32 (Flymaple, если я ничего не напутал)- ардуино-подобная мешанина в коде под F4
MultiPilot32?
У меня есть комплект сенсоров L3G4200D, HMC5883L, BMP085, ADXL345. А также у друга лежит ITG3200+ADXL345. Вот под них и хочу код надергать.
У меня есть комплект сенсоров L3G4200D, HMC5883L, BMP085, ADXL345. А также у друга лежит ITG3200+ADXL345. Вот под них и хочу код надергать.
Naze32 на F103 все эти датчики поддерживает сразу, мультипилот есть под 103 есть под407 - но под ваши датчики всё переписывать надо, как в принципе и ОпенПилот СС, СС3D - 103, Revo -405 и BMP выкиньте сразу…
Весна уже на дворе, какие разработки? уже летать надоооо 😃
Мультипилот, на мой взгляд не совсем хорошее решение, копаюсь в PWM и таймерах - бррр…
Afroflight - вроде ничего, под какой именно МК не знаю
F103
Подскажите, пожалуйста проекты на STM32F103 и на STM32F4
Посмотрите еще ArduCopter. Последние исходники уже написаны под разные платформы, в том числе и F4 (плата называется PX4). Правда это усложняет структуру кода, т.к. они пишут свой HAL под каждую платформу.
Multipilot32 вроде тот же ArduCopter портированный под железо VRBrain…
Весна уже на дворе, какие разработки? уже летать надоооо
Мы в разных странах живем? У меня за окном сугробы по пояс 😃
Подскажите, пожалуйста проекты на STM32F103 и на STM32F4 с открытым исходным кодом, чтобы не изобретать велосипед.
Мультипилот, на мой взгляд не совсем хорошее решение, копаюсь в PWM и таймерах - бррр…
Вот неплохой проект code.google.com/p/gluonpilot/, aka Drinker подсказал, весь проект не смотрел, но ИМУ у него (то что на кватернионах) правильное. Именно АХРС советую, математика быстрая, горизонт устойчивый , думаю в свой пролект встроить.
Подскажите, пожалуйста, как завести таймер на Atmega128 на 0,5мкс для подсчета ШИМа??? У меня ниже 5мкс он виснуть начинает(((( может нужно как то специально его регистры конфигурить и еще чего?? подскажите, пожалуйста, кто знает как…
У меня за окном сугробы по пояс
ага наверно, у меня недавно пошел, а уже тоже по колено, с утра всё чисто было даже подсохло всё …
Naze32 на F103 все эти датчики поддерживает сразу, мультипилот есть под 103 есть под407 - но под ваши датчики всё переписывать надо, как в принципе и ОпенПилот СС, СС3D - 103, Revo -405 и BMP выкиньте сразу…
Весна уже на дворе, какие разработки? уже летать надоооо 😃
Мультипилот, на мой взгляд не совсем хорошее решение, копаюсь в PWM и таймерах - бррр…
BMP выкинуть не могу - платка 10DOF, максимум что можно - не использовать его 😃 Чем заменить?
Naze32 - это Afrodevices? Я в них запутался уже.
Multipilot это порт MultiWii под STM32 с эмуляцией ардуино (на хрена- непонятно), верно?
Меня не пугает переписать, потому что доделывать чужое сложнее чем написать свое, скорее всего. Особенно когда проект вида OpenPilot. Тем более у меня пока нет задачи превзойти, мне нужна хорошая расширяемость и удаленная управляемость. Ну и разобраться что к чему.
Летать уже летал, но сейчас продал ESC Turnigy AE-25A и заказал моторчики NX4005-650 хочу проверить их эффективность на 10х4.5 как пишут в табличках на 3S. Под мой вес коптера их тяги должно хватить и ESC BlueSeries 20A.
В качестве “просто полетать” валяется платка Crius MultiWii SE и висит на стене еще не облетанный Clouds Fly. Но это не особо интересно.
Все равно я сейчас в команде по разработке коптера, так что от разработки никуда не деться )
Naze32 - это Afrodevices? Я в них запутался уже.
да - это порт MultiWii
Multipilot это порт MultiWii под STM32 с эмуляцией ардуино (на хрена- непонятно), верно?
ArduPilot - STM32
BMP выкинуть не могу - платка 10DOF, максимум что можно - не использовать его Чем заменить?
я у себя на мелкоплате выкинул и повесил на проводках MS5611 - небо и земля…
Посмотрите еще ArduCopter. Последние исходники уже написаны под разные платформы, в том числе и F4 (плата называется PX4). Правда это усложняет структуру кода, т.к. они пишут свой HAL под каждую платформу.
Multipilot32 вроде тот же ArduCopter портированный под железо VRBrain…
PX4 уже на заметке, да, спасибо. Вместе с AfroDevices. У меня такой список получился:
Naze32
AfroFlight32 (MultiWii STM32 - AfroFlight)
OpenPilot
STM32VLDiscovery (aeroquad.com/attachment.php?attachmentid=3632&d=1306798120)
Flymaple
MultiPilot32
AeroQuad32
Вместе с AfroDevices
code.google.com/p/afrodevices/source/browse/#svn%2… интересней чем просто WII
Посмотрите еще ArduCopter. Последние исходники уже написаны под разные платформы, в том числе и F4 (плата называется PX4). Правда это усложняет структуру кода, т.к. они пишут свой HAL под каждую платформу.
Multipilot32 вроде тот же ArduCopter портированный под железо VRBrain…
чёт я ничего не увидел, в мультипилоте точно есть порт Арду на PX4, о надо ещё в нём поковырятся…
Алексей, вы со снегом накаркали - за окном метель вообще началась ничерта не видно, а я расчитывал мелкоплату потестить, все лучшие моменты жизни блин на работе, пол дня на улице в одной кофте провозился с таксометром, а тут на тебе 😃
мелкоплату потестить
Сергей, Вы не работали с Atmega-ми? Не поможете с таймером разобраться?..
с Wii не пойдёт?
/**************************************************************************************/
/*************** Standard RX Pins reading ********************/
/**************************************************************************************/
#if defined(STANDARD_RX)
// predefined PC pin block (thanks to lianj)
#define RX_PIN_CHECK(pin_pos, rc_value_pos) \
if (mask & PCInt_RX_Pins[pin_pos]) { \
if (!(pin & PCInt_RX_Pins[pin_pos])) { \
dTime = cTime-edgeTime[pin_pos]; if (900<dTime && dTime<2200) rcValue[rc_value_pos] = dTime; \
} else edgeTime[pin_pos] = cTime; \
}
// port change Interrupt
ISR(RX_PC_INTERRUPT) { //this ISR is common to every receiver channel, it is call everytime a change state occurs on a RX input pin
uint8_t mask;
uint8_t pin;
uint16_t cTime,dTime;
static uint16_t edgeTime[8];
static uint8_t PCintLast;
pin = RX_PCINT_PIN_PORT; // RX_PCINT_PIN_PORT indicates the state of each PIN for the arduino port dealing with Ports digital pins
mask = pin ^ PCintLast; // doing a ^ between the current interruption and the last one indicates wich pin changed
sei(); // re enable other interrupts at this point, the rest of this interrupt is not so time critical and can be interrupted safely
PCintLast = pin; // we memorize the current state of all PINs [D0-D7]
cTime = micros(); // micros() return a uint32_t, but it is not usefull to keep the whole bits => we keep only 16 bits
#if (PCINT_PIN_COUNT > 0)
RX_PIN_CHECK(0,2);
#endif
#if (PCINT_PIN_COUNT > 1)
RX_PIN_CHECK(1,4);
#endif
#if (PCINT_PIN_COUNT > 2)
RX_PIN_CHECK(2,5);
#endif
#if (PCINT_PIN_COUNT > 3)
RX_PIN_CHECK(3,6);
#endif
#if (PCINT_PIN_COUNT > 4)
RX_PIN_CHECK(4,7);
#endif
#if (PCINT_PIN_COUNT > 5)
RX_PIN_CHECK(5,0);
#endif
#if (PCINT_PIN_COUNT > 6)
RX_PIN_CHECK(6,1);
#endif
#if (PCINT_PIN_COUNT > 7)
RX_PIN_CHECK(7,3);
#endif
#if defined(FAILSAFE) && !defined(PROMICRO)
if (mask & 1<<THROTTLEPIN) { // If pulse present on THROTTLE pin (independent from ardu version), clear FailSafe counter - added by MIS
if(failsafeCnt > 20) failsafeCnt -= 20; else failsafeCnt = 0; }
#endif
}
с Wii не пойдёт?
этот код с атмеги? и что такое Wii?
328мега , атмега2560 ну и там всякие производные
вот настройка портов
/**************************************************************************************/
/*************** RX Pin Setup ********************/
/**************************************************************************************/
void configureReceiver() {
/****************** Configure each rc pin for PCINT ***************************/
#if defined(STANDARD_RX)
#if defined(MEGA)
DDRK = 0; // defined PORTK as a digital port ([A8-A15] are consired as digital PINs and not analogical)
#endif
// PCINT activation
for(uint8_t i = 0; i < PCINT_PIN_COUNT; i++){ // i think a for loop is ok for the init.
PCINT_RX_PORT |= PCInt_RX_Pins[i];
PCINT_RX_MASK |= PCInt_RX_Pins[i];
}
PCICR = PCIR_PORT_BIT;
/************* atmega328P's Specific Aux2 Pin Setup *********************/
#if defined(PROMINI)
#if defined(RCAUXPIN)
PCICR |= (1 << 0) ; // PCINT activated also for PINS [D8-D13] on port B
#if defined(RCAUXPIN8)
PCMSK0 = (1 << 0);
#endif
#if defined(RCAUXPIN12)
PCMSK0 = (1 << 4);
#endif
#endif
#endif
/*************** atmega32u4's Specific RX Pin Setup **********************/
#if defined(PROMICRO)
//Trottle on pin 7
DDRE &= ~(1 << 6); // pin 7 to input
PORTE |= (1 << 6); // enable pullups
EIMSK |= (1 << INT6); // enable interuppt
EICRB |= (1 << ISC60);
// Aux2 pin on PBO (D17/RXLED)
#if defined(RCAUX2PIND17)
DDRB &= ~(1 << 0); // set D17 to input
#endif
// Aux2 pin on PD2 (RX0)
#if defined(RCAUX2PINRXO)
DDRD &= ~(1 << 2); // RX to input
PORTD |= (1 << 2); // enable pullups
EIMSK |= (1 << INT2); // enable interuppt
EICRA |= (1 << ISC20);
#endif
#endif
а вот ещё веточка есть rcopen.com/forum/f123/topic221574
328мега , атмега2560 ну и там всякие производные
вот настройка портов Код:
о_0. Вы разбираетесь в этом коде??
есть маленький проблем, это ардуино со своими библиотеками и всеми вытекающими, но есть такой контроллер - КУК kkmulticopter.com/index.php?option=com_content&vie… там исходники чисто под AVRStudio есть на си, есть на ассеме, когда-то баловался переписывал порты, давно…
// pin change interrupt enables
PCICR |= (1 << PCIE0); // PCINT0..7
PCICR |= (1 << PCIE2); // PCINT16..23
// pin change masks
PCMSK0 |= (1 << PCINT7); // PB7
PCMSK2 |= (1 << PCINT17); // PD1
// external interrupts
EICRA = (1 << ISC00) | (1 << ISC10); // Any change INT0, INT1
EIMSK = (1 << INT0) | (1 << INT1); // External Interrupt Mask Register
EIFR |= (1 << INTF0) | (1 << INTF1);
// timer0 (8bit) - run @ 8MHz
// used to control ESC/servo pulse length
TCCR0A = 0; // normal operation
TCCR0B = (1 << CS00); // clk/0
TIMSK0 = 0; // no interrupts
// timer1 (16bit) - run @ 1Mhz
// used to measure Rx Signals & control ESC/servo output rate
TCCR1A = 0;
TCCR1B = (1 << CS11);
// timer2 8bit - run @ 8MHz / 1024 = 7812.5KHz
// and Stick-Arming
TCCR2A = 0;
TCCR2B = (1 << CS22) | (1 << CS21) | (1 << CS20); // /1024
TIMSK2 = 0;
TIFR2 = 0;
TCNT2 = 0; // reset counter