mirror of
https://github.com/eddyem/stm32samples.git
synced 2025-12-06 10:45:11 +03:00
some features added
This commit is contained in:
parent
7e9f81ca54
commit
29d62c26c7
144
F1-nolib/chronometer/Readme_rus.txt
Normal file
144
F1-nolib/chronometer/Readme_rus.txt
Normal file
@ -0,0 +1,144 @@
|
||||
****** Распиновка ******
|
||||
|
||||
=== Интерфейсы I/O ===
|
||||
- PA11/12 - USB
|
||||
- PA9(Tx), PA10(Rx) - USART1 - прокси RMC-сообщений GPS.
|
||||
- PA2(Tx), PA3(Rx) - USART2 - подключение GPS-приемника.
|
||||
- PB10(Tx), PB11(Rx) - USART3 - подключение лидара.
|
||||
|
||||
=== Остальные порты ===
|
||||
- PA1 - PPS сигнал от GPS; сюда можно подключать любой дополнительный высокоомный вход напрямую.
|
||||
- PA4 - TRIG2 - подключен к каналу 12В.
|
||||
- PA13 - TRIG0 - кнопка или створ, замыкающий контакты.
|
||||
- PA14 - TRIG1 - так же, как и вход TRIG0.
|
||||
- PA15 - подтяжка USB.
|
||||
- PB0 - TRIG4 - триггер по АЦП.
|
||||
- PB8, PB9 - индикаторные светодиоды.
|
||||
- PC13 - пищалка.
|
||||
|
||||
=== Светодиоды ===
|
||||
- LED0 (зеленый) - при отсутствии сигнала PPS просто горит, если PPS появляется - мигает (затухает на 0.25с на каждый сигнал).
|
||||
- LED1 (красный) - индикатор GPS: не горит, если приемник не обнаружен, горит, если неуверенный прием времени (буква "V" во второй позиции RMC-сообщения), мигает при уверенном приеме (буква "A" во второй позиции).
|
||||
Судя по эксперименту, даже через час после пропадания сигнала точность определения события - не хуже 1мс. Сам GPS-приемник выдает
|
||||
PPS даже при отсутствии спутников - лишь бы он успел "подхватить" точное время и начать генерировать pps. Начинать работу можно сразу,
|
||||
как только замигает зеленый светодиод после мигающего красного.
|
||||
|
||||
|
||||
****** Триггеры ******
|
||||
На прототипе распаяно два входа на триггеры: TRIG0 и TRIG2. К TRIG2 нужно подключать 12-вольтный сигнал, ток не меньше 10мА.
|
||||
Если створ имеет открытый коллектор, то выход створа подключается к минусу TRIG2, а к плюсу подключается 12В с источника питания.
|
||||
TRIG0 предназначен для подключения кнопки или концевика, просто замыкающего контакты. Никакого внешнего напряжения там быть не должно!
|
||||
|
||||
TRIG4 - аналоговый вход. Если будут ложные срабатывания на девбордах, порт PB0 нужно напрямую или через резистор до 10кОм посадить на землю.
|
||||
|
||||
Иногда бывают ложные срабатывания триггеров TRIG0..TRIG2, связанные с мощными источниками искр (зажигание, искрящиеся обмотки и т.п.).
|
||||
В случае таких ложных срабатываний рекомендуется заземлить катод источника питания хронометра.
|
||||
|
||||
При подключении внешней кнопки желательно, чтобы она имела нормально замкнутые контакты - это предотвратит ложные срабатывания из-за электромагнитных помех.
|
||||
|
||||
|
||||
****** Подключение ******
|
||||
Хронометр эмулирует "китайский" преобразователь PL2303. В линуксе нужно, чтобы был скомпилирован соответствующий модуль ядра.
|
||||
В андроиде работает "из коробки". В мастдайке новые драйвера PL2303 имеют защиту от подделок (те просто не работают с этими дровами),
|
||||
поэтому для нормальной работы необходимо найти и установить старые драйвера.
|
||||
|
||||
К выходам PA9/PA10 можно подключить преобразователь USART<>USB или накинуть их напрямую на ноги Rx/Tx "малинки" (не забыв соединить
|
||||
земли хронометра и малинки): PA9(Tx) соединить с Rx, PA10(Rx) - с Tx. Этот USART проксирует RMC-сообщения GPS-приемника (уже после
|
||||
обработки микроконтроллером, поэтому если МК выключен, а приемник включен, сигнала все равно не будет).
|
||||
|
||||
Для подключения PPS сигнала к "малинке" нужно напрямую соединить соответствующую ногу GPIO "малинки" с портом PA1 девборды.
|
||||
На прототипе нужно подпаяться к дорожке, выходящей с ноги PPS (отмечено маркером).
|
||||
|
||||
Подтяжка USB есть лишь на прототипе, на девбордах ее нет. Поэтому в случае перезагрузки микроконтроллера девборды для возобновления
|
||||
соединения необходимо переткнуть шнурок USB. В этом плане прототип надежней: сбросить МК можно независимо от питания GPS.
|
||||
|
||||
На прототипе и девбордах отсутствует подсоединение пищалки. На девбордах при желании можно накинуть на PC13 что-нибудь для индикации
|
||||
срабатывания створа (активный выход - "1" в течение 0.3с).
|
||||
|
||||
На девбордах не распаяны светодиодные индикаторы. Особого смысла в них нет, но если понадобится подключить, нагрузка должна висеть на
|
||||
PB8/PB9. Активный выход - низкий. Нога МК настроена в режиме open-drain, но внешняя подтяжка не должна быть выше +3.5В. И потребление
|
||||
не больше 5мА на ногу.
|
||||
|
||||
|
||||
****** Конфигурация ******
|
||||
Хронометр конфигурируется через USB. Ввод команд не сопровождается эхом (чтобы удобней было работать из внешних программ), поэтому
|
||||
для удобства можно тексты команд копировать из окна текстового редактора.
|
||||
Чтобы увидеть подсказку, достаточно отправить любую строку, начинающуюся с вопросительного знака. Появится справка:
|
||||
|
||||
adcmax - max ADC value treshold for trigger
|
||||
adcmin - min -//- (triggered when ADval>min & <max
|
||||
adcval - get ADC value
|
||||
buzzerS - turn buzzer ON/OFF
|
||||
distmin - min distance threshold (cm)
|
||||
distmax - max distance threshold (cm)
|
||||
gpsrestart - send Full Cold Restart to GPS
|
||||
gpsstring - current GPS data string
|
||||
ledsS - turn leds on/off (1/0)
|
||||
mcutemp - MCU temperature
|
||||
pullupNS - triggers pullups state (N - trigger No, S - 0/1 for off/on)
|
||||
showconf - show current configuration
|
||||
time - print time
|
||||
store - store new configuration in flash
|
||||
triglevelNS - working trigger N level S
|
||||
trigpauseNP - pause (P, ms) after trigger N shots
|
||||
trigtimeN - show last trigger N time
|
||||
vdd - Vdd value
|
||||
|
||||
Из нужного здесь:
|
||||
- gpsrestart - перезапуск GPS (если вдруг начнет глючить - у меня такого не случалось), делает "холодный" рестарт. Команда
|
||||
проверялась лишь на прототипе.
|
||||
- gpsstring - вывод очередного сообщения от GPS. Если все нормально, то появится строка RMC вроде
|
||||
$GPRMC,124001.000,A,4340.9369,N,04127.5034,E,0.00,33.26,150819,,,A*5C
|
||||
- pullupNS - включить или выключить внутренние верхние подтяжки для триггеров 0..3 (особо не нужно, т.к. подтяжки слабые, и если
|
||||
будет нужна подтяжка, лучше сделать сильную внешнюю).
|
||||
- showconf - отображение текущей конфигурации, например:
|
||||
CONFIG:
|
||||
DISTMIN=50
|
||||
DISTMAX=1000
|
||||
ADCMIN=1024
|
||||
ADCMAX=3072
|
||||
PULLUPS=255
|
||||
TRIGLVL=0
|
||||
TRIGPAUSE={400, 400, 400, 300, 300}
|
||||
ENDCONFIG
|
||||
|
||||
пункты конфигурации: DISTMIN/DISTMAX относятся к лидару, ADCMIN/ADCMAX ко входу АЦП, PULLUPS - состояние подтяжек
|
||||
(каждый бит, начиная с младшего - состояние соответствующей подтяжки; 0 - не активна, 1 - активна).
|
||||
TRIGLVL - конфигурация уровней срабатывания, каждый бит, начиная с младшего (всего три младших бита, как и в PULLUPS),
|
||||
равен нулю, если для соответствующего триггера срабатывание при перепаде 1->0, равен единице, если при
|
||||
перепаде 0->1.
|
||||
TRIGPAUSE - пауза между срабатываниями триггера: если после срабатывания произойдет следующее событие за интервал, меньший
|
||||
данного, это событие учитываться не будет.
|
||||
- time - отображает текущее время так, как оно бы отобразилось при срабатывании триггера, например,
|
||||
55725.961 (15:28:45)
|
||||
ВРЕМЯ ИЗМЕРЯЕТСЯ В UTC!!! Первое число - количество секунд и миллисекунд с начала суток по UTC, в скобках
|
||||
указывается человекочитаемое время.
|
||||
- store - сохранить новую конфигурацию во флеш-памяти МК.
|
||||
- triglevelNS - рабочий уровень триггера. Здесь N - номер триггера (0..2), S - уровень (0/1). Скажем, чтобы триггер 0 срабатывал
|
||||
при перепаде 1->0, нужно написать команду
|
||||
triglevel00
|
||||
а чтобы триггер 2 срабатывал при перепаде 0->1,
|
||||
triglevel21
|
||||
- trigpauseNP - задать паузу для триггера N, пауза в миллисекундах. Если написать 0, паузы не будет и каждое срабатывание
|
||||
будет вызывать соответствующее сообщение. Эта пауза нужнад для защиты от "звона" и нескольких срабатываний на "дырках"
|
||||
в объекте. Меньше 50мс лучше не делать.
|
||||
- trigtimeN - отображение последнего времени срабатывания триггера N, например, на запрос trigtime0, может быть выведено:
|
||||
TRIG0=45212.930 (12:33:32)
|
||||
Если срабатываний с момента включения не было, выведутся нули:
|
||||
TRIG4=0.000 (00:00:00)
|
||||
|
||||
После изменения конфигурации и ее сохранения необходимо нажатием на reset или отключением/включением питания перезагрузить МК,
|
||||
т.к. некоторые параметры активируются лишь при старте.
|
||||
|
||||
|
||||
****** Девборды и плата-прототип ******
|
||||
На платках из девборд два канала опторазвязок подключены к триггерам TRIG0 и TRIG1.
|
||||
Синий провод - земля, красные - +12В для каждого канала. Т.е. схема рассчитана на срабатывание по появлению плюса на одном из каналов.
|
||||
|
||||
В случае необходимости срабатывания по подтяжке к земле, нужно разорвать землю на входах опторазвязок и, наоборот, объединить плюсы.
|
||||
На плюсы подать +12В, минусы подключить к сигнальным выходам створов.
|
||||
|
||||
На прототипе распаяны развязки только на два канала: TRIG0 - для подключения чего-то, замыкающего контакты, и TRIG2 - для подключения
|
||||
чего-то, выдающего 12В. Я оставил такую конфигурацию: к TRIG0 можно подключить нормально замкнутую кнопку (triglevel01), а TRIG2
|
||||
сработает при поступлении туда 12В (triglevel21).
|
||||
|
||||
@ -71,18 +71,23 @@ uint32_t getVdd(){
|
||||
return vdd;
|
||||
}
|
||||
|
||||
void chkADCtrigger(){
|
||||
/**
|
||||
* @brief chkADCtrigger - check ADC trigger state
|
||||
* @return value of `triggered`
|
||||
*/
|
||||
uint8_t chkADCtrigger(){
|
||||
static uint8_t triggered = 0;
|
||||
savetrigtime();
|
||||
uint16_t val = getADCval(0);
|
||||
int16_t val = getADCval(0);
|
||||
if(triggered){ // check untriggered action
|
||||
if(val < the_conf.ADC_min || val > the_conf.ADC_max){
|
||||
if(val < (int16_t)the_conf.ADC_min - ADC_THRESHOLD || val > (int16_t)the_conf.ADC_max + ADC_THRESHOLD){
|
||||
triggered = 0;
|
||||
}
|
||||
}else{ // check if thigger shot
|
||||
if(val > the_conf.ADC_min && val < the_conf.ADC_max){
|
||||
if(val > (int16_t)the_conf.ADC_min + ADC_THRESHOLD && val < (int16_t)the_conf.ADC_max - ADC_THRESHOLD){
|
||||
triggered = 1;
|
||||
fillshotms(4);
|
||||
}
|
||||
}
|
||||
return triggered;
|
||||
}
|
||||
|
||||
@ -24,10 +24,12 @@
|
||||
// interval of trigger's shot (>min && <max), maybe negative
|
||||
#define ADC_MIN_VAL (1024)
|
||||
#define ADC_MAX_VAL (3072)
|
||||
// 2*ADC_THRESHOLD = hysteresis width
|
||||
#define ADC_THRESHOLD (50)
|
||||
|
||||
extern uint16_t ADC_array[];
|
||||
int32_t getMCUtemp();
|
||||
uint32_t getVdd();
|
||||
uint16_t getADCval(int nch);
|
||||
void chkADCtrigger();
|
||||
uint8_t chkADCtrigger();
|
||||
#endif // ADC_H
|
||||
|
||||
Binary file not shown.
@ -24,6 +24,8 @@
|
||||
#include "adc.h"
|
||||
#include "hardware.h"
|
||||
#include "flash.h"
|
||||
#include "lidar.h"
|
||||
#include "str.h"
|
||||
#include "time.h"
|
||||
#include "usart.h"
|
||||
|
||||
@ -41,10 +43,10 @@ static uint8_t trigstate[DIGTRIG_AMOUNT];
|
||||
trigtime shottime[TRIGGERS_AMOUNT];
|
||||
// Tms value when they shot
|
||||
static uint32_t shotms[TRIGGERS_AMOUNT];
|
||||
// trigger length (-1 if > MAX_TRIG_LEN)
|
||||
int16_t triglen[TRIGGERS_AMOUNT];
|
||||
// if trigger[N] shots, the bit N will be 1
|
||||
uint8_t trigger_shot = 0;
|
||||
// time when Buzzer was turned ON
|
||||
uint32_t BuzzerTime = 0;
|
||||
|
||||
static inline void gpio_setup(){
|
||||
BUZZER_OFF(); // turn off buzzer @start
|
||||
@ -78,7 +80,9 @@ static inline void gpio_setup(){
|
||||
uint16_t pin = trigpin[i];
|
||||
// fill trigstate array
|
||||
uint8_t trgs = (the_conf.trigstate & (1<<i)) ? 1 : 0;
|
||||
#ifdef EBUG
|
||||
trigstate[i] = trgs;
|
||||
#endif
|
||||
// turn on pullups
|
||||
if(the_conf.trig_pullups & (1<<i)) trigport[i]->ODR |= pin;
|
||||
EXTI->IMR |= pin;
|
||||
@ -147,17 +151,52 @@ void savetrigtime(){
|
||||
memcpy(&trgtm.Time, ¤t_time, sizeof(curtime));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief fillshotms - save trigger shot time
|
||||
* @param i - trigger number
|
||||
*/
|
||||
void fillshotms(int i){
|
||||
if(i < 0 || i > TRIGGERS_AMOUNT) return;
|
||||
if(i < 0 || i >= TRIGGERS_AMOUNT) return;
|
||||
if(Tms - shotms[i] > (uint32_t)the_conf.trigpause[i]){
|
||||
shotms[i] = Tms;
|
||||
memcpy(&shottime[i], &trgtm, sizeof(trigtime));
|
||||
shotms[i] = Tms;
|
||||
trigger_shot |= 1<<i;
|
||||
BuzzerTime = Tms;
|
||||
BUZZER_ON();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief fillunshotms - calculate trigger length time
|
||||
*/
|
||||
void fillunshotms(){
|
||||
if(!trigger_shot) return;
|
||||
uint8_t X = 1;
|
||||
for(int i = 0; i < TRIGGERS_AMOUNT; ++i, X<<=1){
|
||||
// check whether trigger is OFF but shot recently
|
||||
if(trigger_shot & X){
|
||||
uint32_t len = Tms - shotms[i];
|
||||
uint8_t rdy = 0;
|
||||
if(len > MAX_TRIG_LEN){
|
||||
triglen[i] = -1;
|
||||
rdy = 1;
|
||||
}else triglen[i] = (uint16_t) len;
|
||||
if(i == LIDAR_TRIGGER){
|
||||
if(!parse_lidar_data(NULL)) rdy = 1;
|
||||
}else if(i == ADC_TRIGGER){
|
||||
if(!chkADCtrigger()) rdy = 1;
|
||||
}else{
|
||||
uint8_t pinval = (trigport[i]->IDR & trigpin[i]) ? 1 : 0;
|
||||
if(pinval != trigstate[i]) rdy = 1; // trigger is OFF
|
||||
}
|
||||
if(rdy){
|
||||
shotms[i] = Tms;
|
||||
show_trigger_shot(X);
|
||||
trigger_shot &= ~X;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void exti4_isr(){ // PA4 - trigger[2]
|
||||
savetrigtime();
|
||||
fillshotms(2);
|
||||
@ -176,6 +215,7 @@ void exti15_10_isr(){ // PA13 - trigger[0], PA14 - trigger[1]
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef EBUG
|
||||
/**
|
||||
* @brief gettrig - get trigger state
|
||||
* @return 1 if trigger active or 0
|
||||
@ -186,3 +226,18 @@ uint8_t gettrig(uint8_t N){
|
||||
if(curval == trigstate[N]) return 1;
|
||||
else return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
void chk_buzzer(){
|
||||
if(!trigger_shot && BUZZER_GET()){ // should we turn off buzzer?
|
||||
uint8_t notrg = 1;
|
||||
for(int i = 0; i < DIGTRIG_AMOUNT; ++i){
|
||||
uint8_t curval = (trigport[i]->IDR & trigpin[i]) ? 1 : 0;
|
||||
if(curval == trigstate[i]){
|
||||
notrg = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if(notrg) BUZZER_OFF(); // turn off buzzer when there's no trigger events
|
||||
}
|
||||
}
|
||||
|
||||
@ -39,6 +39,7 @@ extern uint8_t buzzer_on;
|
||||
#define BUZZER_pin (1<<13)
|
||||
#define BUZZER_ON() do{if(buzzer_on)pin_set(BUZZER_port, BUZZER_pin);}while(0)
|
||||
#define BUZZER_OFF() pin_clear(BUZZER_port, BUZZER_pin)
|
||||
#define BUZZER_GET() (pin_read(BUZZER_port, BUZZER_pin))
|
||||
|
||||
// PPS pin - PA1
|
||||
#define PPS_port GPIOA
|
||||
@ -49,11 +50,18 @@ extern uint8_t buzzer_on;
|
||||
#define TRIGGERS_AMOUNT (5)
|
||||
// number of LIDAR trigger
|
||||
#define LIDAR_TRIGGER (3)
|
||||
// number of ADC trigger
|
||||
#define ADC_TRIGGER (4)
|
||||
// amount of digital triggers (on interrupts)
|
||||
#define DIGTRIG_AMOUNT (3)
|
||||
// max length of trigger event (ms)
|
||||
#define MAX_TRIG_LEN (1000)
|
||||
|
||||
#ifdef EBUG
|
||||
uint8_t gettrig(uint8_t N);
|
||||
#endif
|
||||
void fillshotms(int i);
|
||||
void fillunshotms();
|
||||
void savetrigtime();
|
||||
#define GET_PPS() ((GPIOA->IDR & (1<<1)) ? 1 : 0)
|
||||
|
||||
@ -83,11 +91,12 @@ typedef struct{
|
||||
extern uint8_t LEDSon;
|
||||
// time of triggers shot
|
||||
extern trigtime shottime[TRIGGERS_AMOUNT];
|
||||
// length (in ms) of trigger event (-1 if > MAX_TRIG_LEN
|
||||
extern int16_t triglen[TRIGGERS_AMOUNT];
|
||||
// if trigger[N] shots, the bit N will be 1
|
||||
extern uint8_t trigger_shot;
|
||||
// time when Buzzer was turned ON
|
||||
extern uint32_t BuzzerTime;
|
||||
|
||||
void chk_buzzer();
|
||||
void hw_setup();
|
||||
|
||||
#endif // __HARDWARE_H__
|
||||
|
||||
@ -24,14 +24,20 @@ uint16_t last_lidar_dist = 0;
|
||||
uint16_t last_lidar_stren = 0;
|
||||
uint16_t lidar_triggered_dist = 0;
|
||||
|
||||
void parse_lidar_data(char *txt){
|
||||
/**
|
||||
* @brief parse_lidar_data - parsing of string from lidar
|
||||
* @param txt - the string or NULL (if you want just check trigger state)
|
||||
* @return trigger state
|
||||
*/
|
||||
uint8_t parse_lidar_data(char *txt){
|
||||
static uint8_t triggered = 0;
|
||||
if(!txt) return triggered;
|
||||
last_lidar_dist = txt[2] | (txt[3] << 8);
|
||||
last_lidar_stren = txt[4] | (txt[5] << 8);
|
||||
if(last_lidar_stren < LIDAR_LOWER_STREN) return; // weak signal
|
||||
if(last_lidar_stren < LIDAR_LOWER_STREN) return 0; // weak signal
|
||||
if(!lidar_triggered_dist){ // first run
|
||||
lidar_triggered_dist = last_lidar_dist;
|
||||
return;
|
||||
return 0;
|
||||
}
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
if(triggered){ // check if body gone
|
||||
@ -60,4 +66,5 @@ void parse_lidar_data(char *txt){
|
||||
#endif
|
||||
}
|
||||
}
|
||||
return triggered;
|
||||
}
|
||||
|
||||
@ -34,6 +34,6 @@ extern uint16_t last_lidar_dist;
|
||||
extern uint16_t lidar_triggered_dist;
|
||||
extern uint16_t last_lidar_stren;
|
||||
|
||||
void parse_lidar_data(char *txt);
|
||||
uint8_t parse_lidar_data(char *txt);
|
||||
|
||||
#endif // LIDAR_H__
|
||||
|
||||
@ -158,23 +158,26 @@ char *parse_cmd(char *buf){
|
||||
}
|
||||
#endif
|
||||
|
||||
#define USBBUF 63
|
||||
// usb getline
|
||||
static char *get_USB(){
|
||||
static char tmpbuf[512], *curptr = tmpbuf;
|
||||
static int rest = 511;
|
||||
static char tmpbuf[USBBUF+1], *curptr = tmpbuf;
|
||||
static int rest = USBBUF;
|
||||
int x = USB_receive(curptr, rest);
|
||||
curptr[x] = 0;
|
||||
if(!x) return NULL;
|
||||
curptr[x] = 0;
|
||||
USB_send(curptr); // echo
|
||||
//if(x == 1 && *curptr < 32){USB_send("\n"); USB_send(u2str(*curptr)); USB_send("\n");}
|
||||
if(curptr[x-1] == '\n'){
|
||||
curptr = tmpbuf;
|
||||
rest = 511;
|
||||
rest = USBBUF;
|
||||
return tmpbuf;
|
||||
}
|
||||
curptr += x; rest -= x;
|
||||
if(rest <= 0){ // buffer overflow
|
||||
SEND("USB buffer overflow!\n");
|
||||
//SEND("USB buffer overflow!\n");
|
||||
curptr = tmpbuf;
|
||||
rest = 511;
|
||||
rest = USBBUF;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
@ -215,7 +218,6 @@ void break_handler(){ // client disconnected
|
||||
|
||||
#ifdef EBUG
|
||||
extern int32_t ticksdiff, timecntr, timerval, Tms1;
|
||||
extern uint32_t last_corr_time;
|
||||
#endif
|
||||
|
||||
int main(void){
|
||||
@ -245,10 +247,8 @@ int main(void){
|
||||
while (1){
|
||||
IWDG->KR = IWDG_REFRESH; // refresh watchdog
|
||||
if(Timer > 499) LED_on(); // turn ON LED0 over 0.25s after PPS pulse
|
||||
if(BuzzerTime && Tms - BuzzerTime > 249){
|
||||
BUZZER_OFF();
|
||||
BuzzerTime = 0;
|
||||
}
|
||||
// check if triggers that was recently shot are off now
|
||||
fillunshotms();
|
||||
if(lastT > Tms || Tms - lastT > 499){
|
||||
if(need2startseq) GPS_send_start_seq();
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
@ -301,8 +301,7 @@ int main(void){
|
||||
}
|
||||
#endif
|
||||
}
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
if(trigger_shot) show_trigger_shot(trigger_shot);
|
||||
//if(trigger_shot) show_trigger_shot(trigger_shot);
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
usb_proc();
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
@ -312,7 +311,7 @@ int main(void){
|
||||
DBG("Received data over USB:");
|
||||
DBG(txt);
|
||||
if(parse_USBCMD(txt))
|
||||
USB_send(txt); // echo back non-commands data
|
||||
USB_send("Bad command!");
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
}
|
||||
#if defined EBUG || defined USART1PROXY
|
||||
@ -352,7 +351,7 @@ int main(void){
|
||||
parse_lidar_data(txt);
|
||||
}
|
||||
}
|
||||
chkADCtrigger();
|
||||
chk_buzzer(); // should we turn off buzzer?
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -111,6 +111,7 @@ int parse_USBCMD(char *cmd){
|
||||
CMD_DISTMIN " - min distance threshold (cm)\n"
|
||||
CMD_DISTMAX " - max distance threshold (cm)\n"
|
||||
CMD_GPSRESTART " - send Full Cold Restart to GPS\n"
|
||||
CMD_GPSSTAT " - get GPS status\n"
|
||||
CMD_GPSSTR " - current GPS data string\n"
|
||||
CMD_LEDS "S - turn leds on/off (1/0)\n"
|
||||
CMD_GETMCUTEMP " - MCU temperature\n"
|
||||
@ -125,6 +126,7 @@ int parse_USBCMD(char *cmd){
|
||||
);
|
||||
}else if(CMP(cmd, CMD_PRINTTIME) == 0){
|
||||
USB_send(get_time(¤t_time, get_millis()));
|
||||
USB_send("\n");
|
||||
}else if(CMP(cmd, CMD_DISTMIN) == 0){ // set low limit
|
||||
DBG("CMD_DISTMIN");
|
||||
GETNUM(CMD_DISTMIN);
|
||||
@ -258,14 +260,34 @@ int parse_USBCMD(char *cmd){
|
||||
if(Nt > 1) goto bad_number;
|
||||
USB_send("BUZZER=");
|
||||
if(Nt){
|
||||
BuzzerTime = 0;
|
||||
buzzer_on = 1;
|
||||
USB_send("ON\n");
|
||||
}else{
|
||||
BuzzerTime = 0;
|
||||
buzzer_on = 0;
|
||||
USB_send("OFF\n");
|
||||
}
|
||||
}else if(CMP(cmd, CMD_GPSSTAT) == 0){
|
||||
USB_send("GPS status: ");
|
||||
const char *str = "unknown";
|
||||
switch(GPS_status){
|
||||
case GPS_NOTFOUND:
|
||||
str = "not found";
|
||||
break;
|
||||
case GPS_WAIT:
|
||||
str = "waiting";
|
||||
break;
|
||||
case GPS_NOT_VALID:
|
||||
str = "no satellites";
|
||||
break;
|
||||
case GPS_VALID:
|
||||
str = "valid time";
|
||||
break;
|
||||
}
|
||||
USB_send(str);
|
||||
if(Tms - last_corr_time < 1500)
|
||||
USB_send(", PPS working\n");
|
||||
else
|
||||
USB_send(", no PPS\n");
|
||||
}else return 1;
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
if(succeed) USB_send("Success!\n");
|
||||
@ -285,7 +307,7 @@ void show_trigger_shot(uint8_t tshot){
|
||||
IWDG->KR = IWDG_REFRESH;
|
||||
if(tshot & X) tshot &= ~X;
|
||||
else continue;
|
||||
if(trigger_shot & X) trigger_shot &= ~X;
|
||||
if(!triglen[i]) continue; // noice
|
||||
if(i == LIDAR_TRIGGER){
|
||||
USB_send("LIDAR, dist=");
|
||||
sendu(lidar_triggered_dist);
|
||||
@ -296,6 +318,9 @@ void show_trigger_shot(uint8_t tshot){
|
||||
}
|
||||
USB_send("=");
|
||||
USB_send(get_time(&shottime[i].Time, shottime[i].millis));
|
||||
USB_send(", len=");
|
||||
if(triglen[i] < 0) USB_send(">1s");
|
||||
else sendu((uint32_t) triglen[i]);
|
||||
USB_send("\n");
|
||||
}
|
||||
}
|
||||
|
||||
@ -42,6 +42,7 @@
|
||||
#define CMD_LEDS "leds"
|
||||
#define CMD_GPSRESTART "gpsrestart"
|
||||
#define CMD_BUZZER "buzzer"
|
||||
#define CMD_GPSSTAT "gpsstat"
|
||||
|
||||
extern uint8_t showGPSstr;
|
||||
|
||||
|
||||
@ -79,6 +79,26 @@ static char *puttwo(uint8_t N, char *buf){
|
||||
return buf;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief ms2str - fill buffer str with milliseconds ms
|
||||
* @param str (io) - pointer to buffer
|
||||
* @param T - milliseconds
|
||||
*/
|
||||
static void ms2str(char **str, uint32_t T){
|
||||
char *bptr = *str;
|
||||
*bptr++ = '.';
|
||||
if(T > 99){
|
||||
*bptr++ = T/100 + '0';
|
||||
T %= 100;
|
||||
}else *bptr++ = '0';
|
||||
if(T > 9){
|
||||
*bptr++ = T/10 + '0';
|
||||
T %= 10;
|
||||
}else *bptr++ = '0';
|
||||
*bptr++ = T + '0';
|
||||
*str = bptr;
|
||||
}
|
||||
|
||||
/**
|
||||
* print time: Tm - time structure, T - milliseconds
|
||||
*/
|
||||
@ -95,26 +115,18 @@ char *get_time(curtime *Tm, uint32_t T){
|
||||
S /= 10;
|
||||
}
|
||||
// now bstart is buffer starting index; bptr points to decimal point
|
||||
*bptr++ = '.';
|
||||
if(T > 99){
|
||||
*bptr++ = T/100 + '0';
|
||||
T %= 100;
|
||||
}else *bptr++ = '0';
|
||||
if(T > 9){
|
||||
*bptr++ = T/10 + '0';
|
||||
T %= 10;
|
||||
}else *bptr++ = '0';
|
||||
*bptr++ = T + '0';
|
||||
ms2str(&bptr, T);
|
||||
// put current time in HH:MM:SS format into buf
|
||||
*bptr++ = ' '; *bptr++ = '(';
|
||||
bptr = puttwo(Tm->H, bptr); *bptr++ = ':';
|
||||
bptr = puttwo(Tm->M, bptr); *bptr++ = ':';
|
||||
bptr = puttwo(Tm->S, bptr); *bptr++ = ')';
|
||||
bptr = puttwo(Tm->S, bptr);
|
||||
ms2str(&bptr, T);
|
||||
*bptr++ = ')';
|
||||
if(GPS_status == GPS_NOTFOUND){
|
||||
strcpy(bptr, " GPS not found");
|
||||
bptr += 14;
|
||||
}
|
||||
*bptr++ = '\n';
|
||||
*bptr = 0;
|
||||
return bstart;
|
||||
}
|
||||
|
||||
@ -46,6 +46,7 @@ typedef struct{
|
||||
extern volatile uint32_t Tms;
|
||||
extern volatile uint32_t Timer;
|
||||
extern curtime current_time;
|
||||
extern uint32_t last_corr_time;
|
||||
|
||||
extern curtime trigger_time[];
|
||||
extern uint32_t trigger_ms[];
|
||||
|
||||
@ -45,7 +45,7 @@
|
||||
#define usartrx(n) (linerdy[n])
|
||||
#define usartovr(n) (bufovr[n])
|
||||
|
||||
extern volatile int linerdy[4], bufovr[4], txrdy[4];
|
||||
extern volatile int linerdy[], bufovr[], txrdy[];
|
||||
|
||||
void transmit_tbuf(int n);
|
||||
void usarts_setup();
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user