roboforum.ru

Технический форум по робототехнике.

Обсуждение реализации шлюз-контроллера [ORFA]

Разработка стандартизированных модулей для домашнего робостроения.
Правила форума
Правила раздела OpenRobotics

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 11 июн 2009, 03:13

=DeaD= писал(а):На скорости 115200 получается 7372800/115200=62 такта всего есть на обработку между символами

7372800/115200=64 такта - это время передачи 1 бита, а для символа с учётом старта а стопа надо как минимум 10 бит, или 640 тактов.

Сегодня гляну код, может замечу чего-нибудь.
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 11 июн 2009, 07:42

Блин, и правда, ложная тревога :) сегодня тогда буду дальше смотреть в чем фишка.
Но такое ощущение, что после старта моих прерываний под сервы парсеру совсем крышу сносит.
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 11 июн 2009, 16:38

Прерывание слишком долго выполняется. IF'ов слишком много, я проанализировал только одну ветку - получается свыше 130 тактов, при том что прерывание вызывается каждые 160 тактов. Надо оптимизировать. Возможно, придумать другую структуру данных, которая позволить быстро осуществлять вывод, а заполнять структуру можно неспешно при установке положения - это будет вне критических по времени участков кода. Возможно, на ассемблере придется переписать.
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 11 июн 2009, 16:53

Ок, буду думать.
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 11 июн 2009, 19:53

Вроде придумал как сделать быстрее, но ценой дополнительного расхода памяти. Если задействовать не все порты, можно чуть-чуть ускорить. Прерывания надо будет перевести на таймер 2, у него в отличии от таймера 0 есть подходящий предделитель (128)

Код: Выделить всёРазвернуть
                                            % времени процессора
Порты       Сервы     Такты      Память           (пик)     
=================================================================
A,B,C,D     16        70         88         56
A,B,C       14        65         63         52
A,C         12        60         42         48


Добавлено спустя 37 минут 22 секунды:
Update.

Не учел паузу доводящую период до 20мс. Получается, что макс. пиковая загрузка будет 56% на интервале 2048 тактов, а средняя - около 1% :Yahoo!:

Чуть позже покажу код

Добавлено спустя 56 минут 38 секунд:
Как-то так. Немного ошибся правда с подсчетом памяти

Код: Выделить всёРазвернуть
; vim: set syntax=avr ai :

#include <avr/io.h>

.global SIG_OUTPUT_COMPARE2

.section .bss

; данные
; формат :
;   {
;      интервал до следующего изменения состояния любого пина (1 байт)
;      маска порта A (1 байт)
;      маска порта B (1 байт)
;      маска порта C (1 байт)
;      маска порта D (1 байт)
;   } * (количество пинов + 1)
;   0 - признак конца

data: .fill 86, 1, 0

; указатель на текущее положение в массиве data
ptr: .word 0

; выравнивающий до 20 мс интервал
ctr:  .byte 1
; обратный cчетчик выравнивающего интервала
ctr1: .byte 1

; маски портов A,B,C, D
; определяют задействованные пины
masks: .byte 0,0,0,0

.section .text

SIG_OUTPUT_COMPARE2:

   push R24
   push R25
   push R24
   push R27
   in R24, 0x3F
   push R24

   lds R26, ptr
   lds R27, ptr+1

   ld  R24, X+
   cpi R24, 0x00
   breq zero

   in R25, OCR2 - 0x20
   add R25, R24
   out OCR2 - 0x20, R25

   ld  R24, X+
   in  R25, PORTA-0x20
   and R25, R24
   out PORTA-0x20, R25

   ld  R24, X+
   in  R25, PORTA-0x20
   and R25, R24
   out PORTA-0x20, R25

   ld  R24, X+
   in  R25, PORTA-0x20
   and R25, R24
   out PORTA-0x20, R25

   ld  R24, X+
   in  R25, PORTA-0x20
   and R25, R24
   out PORTA-0x20, R25


   sts ptr, R26
   sts ptr+1, R27

   rjmp exit

zero:

   lds R24, ctr1
   dec R24
   brne store_ctr

   ldi R26, lo8(masks)
   ldi R27, hi8(masks)

   ld R24, X+
   in R25, PORTA - 0x20
   or R24, R25
   out PORTA-0x20, R24

   ld R24, X+
   in R25, PORTA - 0x20
   or R24, R25
   out PORTA-0x20, R24

   ld R24, X+
   in R25, PORTA - 0x20
   or R24, R25
   out PORTA-0x20, R24

   ld R24, X+
   in R25, PORTA - 0x20
   or R24, R25
   out PORTA-0x20, R24

   ldi R24, lo8(data)
   sts ptr, R24
   ldi R24, hi8(data)
   sts ptr+1, R24


   in R24, OCR2 - 0x20
   inc R24
   out OCR2 - 0x20, R24

   lds R24, ctr


store_ctr:
   sts ctr1, R24
   
exit:
   pop R24
   out 0x3F, R24
   pop R27
   pop R26
   pop R25
   pop R24

   reti

;uint8_t data[86];
;uint8_t* ptr;
;uint8_t ctr;
;uint8_t ctr1;
;uint8_t masks[4];
;
;
;ISR(SIG_OUTPUT_COMPARE2) {
;   uint8_t* p = ptr;
;   uint8_t interval = *(p++);
;   if (interval == 0) {
;      ctr1--;
;      if (!ctr1) {
;         PORTA |= masks[0];
;         PORTB |= masks[1];
;         PORTC |= masks[2];
;         PORTD |= masks[3];
;         ctr1 = ctr;
;         ptr = data;
;         OCR2++;
;      }
;   } else {
;      OCR2 += interval;
;      PORTA &= *(p++);
;      PORTA &= *(p++);
;      PORTA &= *(p++);
;      PORTA &= *(p++);
;      ptr = p;
;   }
;}
;


Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 11 июн 2009, 23:31

А можно на ходу переключать что будет вызываться при прерывании? Если да, то готовим 5 блоков - первые 4 обрабатывают порты A,B,C,D, последний - курит. Блоки каждый отрабатывает свои циклы и переключает прерывание на след. блок. Т.е. первый блок обрабатывает 3мс, второй, третий, четвертый столько же, а пятый - оставшиеся 8мс.

Ну а каждый блок уже банально - не более 8 точек перехода подряд, т.е. пиковая загрузка не более 1024 такта.

Памяти - 4*8*2=64 байта на основные структуры. Ну и за счет деления на 4 блока пиковая нагрузка в % должна поменьше быть.

PS: Если я правильно понял, что предлагается :)
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 12 июн 2009, 06:59

:good: правильно понял ! Только пара замечаний:
=DeaD= писал(а):Ну а каждый блок уже банально - не более 8 точек перехода подряд, т.е. пиковая загрузка не более 1024 такта.

Все равно пик загрузки будет на интервале 2048 тактов, потому что 4 блока будут срабатывать последовательно, без задержек. Причем наверно даже не 16*128, а 16*128 + 4*128 - после каждого блока надо делать минимальную паузу, иначе будет дольше выполняться прерывание.

Без паузы
Код: Выделить всёРазвернуть
установить новое значение;
если это последнеее изменение состояния порта {
    установить все 1 на следующем порте;
    переключить обработчик;
}


С паузой
Код: Выделить всёРазвернуть
если это последнеее изменение состояния порта {
    установить все 1 на следующем порте;
    переключить обработчик;
} иначе {
    установить новое значение;
}


По памяти - окончательные значения ещё надо уточнять, но порядок примерно такой будет.

Добавлено спустя 4 минуты 12 секунд:
Лучше даже может вообще 5-й блок не делать, а период довести до 20 мс, распределив время паузы равномерно между блоками - тогда время пика будет как раз 1024 такта, да и то только если задействованы все выводы порта
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 12 июн 2009, 07:47

Так в каждом блоке и так пауза минимум 500мкс, это же минимальная длина импульса? Так что всё равно 1024такта максимум ;)
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 12 июн 2009, 07:52

На C это будет выглядеть так:

Код: Выделить всёРазвернуть
uint8_t dataA[20];
uint8_t dataB[8];
uint8_t dataC[12];
uint8_t dataD[8];

uint8_t* ptr = dataA;
uint8_t masks[4];

#define portHandler(port, nextHandler, nextPort, nextMask, nextData) \
{\
   uint8_t pause = *(ptr++); \
   if (pause == 0) { \
      port |= *nextMask; \
      OCR2 += *ptr; \
      ptr = nextData; \
      handler = nextHandler; \
   } else { \
      OCR2 += pause; \
      port &= *(ptr++); \
   } \
}


void processA(void);
void processB(void);
void processC(void);
void processD(void);

void (*handler)(void) = processA;

void processA(void)
{
   portHandler(PORTA, processB, PORTB, masks + 1, dataB);
}

void processB(void)
{
   portHandler(PORTB, processC, PORTC, masks + 2, dataC);
}

void processC(void)
{
   portHandler(PORTC, processD, PORTD, masks+3, dataD);
}

void processD(void)
{
   portHandler(PORTD, processA, PORTA, masks, dataA);
}

ISR(SIG_OUTPUT_COMPARE2)
{
   handler();
}




Добавлено спустя 1 минуту 23 секунды:
=DeaD= писал(а):Так в каждом блоке и так пауза минимум 500мкс, это же минимальная длина импульса? Так что всё равно 1024такта максимум ;)

Да, согласен
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 12 июн 2009, 08:47

Кстати, какой у нас получился рабочий диапазон от 1 до 2мс?

128/7372800=17.36мкс?
~58шагов от 1 до 2мс?
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 12 июн 2009, 08:51

Да, верно
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 12 июн 2009, 08:54

А сколько сейчас время обработки с вызовом в тактах получилось? ;)
Может еще чаще будем вызывать, а то что предделителя такого нет - так мы добавим пустых (ничего не изменяющих) пар значений, чтобы хватило счетчик менять.
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 12 июн 2009, 09:07

Вряд ли получится, сейчас пиковая загрузка близка к 50%. Вызывать чаще - значит использовать предделитель на 64, загрузка будет почти 100%, хоть и на меньшем интервале. И не надо забывать, что у нас будут и другие прерывания, например АЦП и системный таймер - им тоже время требуется
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение =DeaD= » 12 июн 2009, 09:24

А если разбить порт А на 3 захода? Получится подряд не более 3 циклов? по X тактов?
А если внутри еще сделать контроль - типа если 2 цикла подряд, то и не выходить. Как такое? ;)

Ну хотя-бы чисто на будущее - похоже на реальность?

Добавлено спустя 3 минуты 21 секунду:
Использовать технологию "чтоб 2 раза не вставать..." :-D
Проект [[Open Robotics]] - Универсальные модули для построения роботов
Аватара пользователя
=DeaD=
 
Сообщения: 24218
Зарегистрирован: 06 окт 2004, 18:01
Откуда: Ебург
прог. языки: C++ / PHP / 1C
ФИО: Антон Ботов

Re: Обсуждение реализации шлюз-контроллера [ORFA]

Сообщение blindman » 12 июн 2009, 09:30

Тогда уж до конца идти, и побить все на группы из 2 выводов - порт A 4 группы, B,D - по 1 группе, C - 2 группы. Всего 8 групп, 8*2500 = 20000
Проект [[Open Robotics]] - универсальные модули для построения роботов
Модули Open Robotics можно приобрести в магазине shop.roboforum.ru

Day OFF? You must be pulling my leg! Stop making humor before someone sees you, fool!

Аватара пользователя
blindman
 
Сообщения: 4130
Зарегистрирован: 29 апр 2008, 21:15
Откуда: Хабаровск
прог. языки: C,C++,Assembler,PHP,Javascript,Ruby, SPIN,Java(?)
ФИО: Андрей Юрьевич

Пред.След.

Вернуться в Open Robotics

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 2