Ср мар 21, 2018 15:46:38
Ср мар 21, 2018 19:43:52
Ср мар 21, 2018 23:09:31
Чт мар 22, 2018 11:50:24
Спасибочки, это стало понятноВывод - при использовании ISR_NAKED нужно самому позаботиться о сохранении контекста (или его части) в стек и о вычитывании его назад.
Вс апр 22, 2018 21:06:57
Ср июн 27, 2018 14:16:54
#define F_CPU 1000000L
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>
#define LED_1MIN 1
#define LED_2MIN 2
#define LED_3MIN 3
#define LED_4MIN 4
#define LED_5MIN 5
#define Buzzer 5
#define ButtonStart 3
#define ButtonSelect 2
#define ButtonStop 4
#define Selection 0
#define Running 1
#define SoundSignal 2
volatile int TimerTime;
volatile int ICR1_additional_value;
volatile int ProgramStatus;
//Timer1 initializing
void init_timer1 (void)
{
TIMSK1 = (1<<TOIE1); //Timer1 intrruption allow
TCCR1A = (0<<WGM11)|(0<<WGM10);
TCCR1B = (1<<WGM13)|(1<<WGM12);
//Clear Timer on Compare Match (CTC) mode
//TOP value - ICR1
}
void stop_timer1 (void)
{
TCCR1B = (1<<WGM13)|(1<<WGM12)|(0<<CS12)|(0<<CS11)|(0<<CS10);
TimerTime = 1;
}
void start_timer1 (void)
{
TCCR1B = (1<<WGM13)|(1<<WGM12)|(1<<CS12)|(0<<CS11)|(1<<CS10);
//Precaler 1024
}
void write_status (int TimerTime)
{
switch (TimerTime)
{
case LED_1MIN:
PORTC = 1<<LED_1MIN;
break;
case LED_2MIN:
PORTC = 1<<LED_2MIN;
break;
case LED_3MIN:
PORTC = 1<<LED_3MIN;
break;
case LED_4MIN:
PORTC = 1<<LED_4MIN;
break;
case LED_5MIN:
PORTC = 1<<LED_5MIN;
break;
}
}
void set_timer_top_value (int TimerTime)
{
switch (TimerTime)
{
case LED_1MIN:
ICR1_additional_value = 8593;
break;
case LED_2MIN:
ICR1_additional_value = 17187;
break;
case LED_3MIN:
ICR1_additional_value = 25781;
break;
case LED_4MIN:
ICR1_additional_value = 34375;
break;
case LED_5MIN:
ICR1_additional_value = 42968;
break;
}
}
void Sound_Out (void)
{
int i;
for (i = 1000; i > 0; i--)
{
PORTD = PORTD^(1<<Buzzer); //inverse bit
_delay_us (500);
PORTD = PORTD^(1<<Buzzer);
_delay_us (500);
}
}
//Timer/Counter1 Capture Event Handler
ISR (TIMER1_CAPT_vect)
{
//you can calculate final timer value in this formula:
//50000*TimerTime + ICR1_additional_value
if (ICR1 == ICR1_additional_value)
{
ProgramStatus = SoundSignal; //it means time is up, and indicate it with sound
}
else
{
TimerTime--;
if (TimerTime == 0)
{
ICR1 = ICR1_additional_value;
}
}
return;
}
int main(void)
{
init_timer1();
TimerTime = 1; //initial timer value is 1 minute
ProgramStatus = Selection;
//ports initializing
//PC5-PC1, PD5 - outputs, PD2 - input
DDRC = 1<<LED_1MIN|1<<LED_2MIN|1<<LED_3MIN|1<<LED_4MIN|1<<LED_5MIN;
PORTC = 1<<LED_1MIN; //initial timer indicator is 1min
DDRD = 1<<Buzzer|0<<ButtonSelect|0<<ButtonStart|0<<ButtonStop;
PORTD = 0<<Buzzer|1<<ButtonSelect|1<<ButtonStart|1<<ButtonStop;
sei(); //interrupts enable
//main infinite cycle
while (1)
{
switch (ProgramStatus)
{
case Running:
//Proccesing Stop Button
if ((PIND & (1<<ButtonStop)) == 0)
{
_delay_ms (50); //for button bounce reduce
if ((PIND & (1<<ButtonStop)) == 0)
{
ProgramStatus = Selection;
stop_timer1();
}
while ((PIND & (1<<ButtonStop)) == 0) //waiting for releasing the button
{
}
}
break;
case Selection:
//Proccesing Select Button
if ((PIND & (1<<ButtonSelect)) == 0)
{
_delay_ms (50); //for button bounce reduce
if ((PIND & (1<<ButtonSelect)) == 0)
{
TimerTime++; //change time
if (TimerTime == 6)
{
TimerTime = 1;
}
write_status(TimerTime); //indicate timers value
}
while ((PIND & (1<<ButtonSelect)) == 0) //waiting for releasing the button
{
}
}
//Proccesing Start Button
if ((PIND & (1<<ButtonStart)) == 0)
{
_delay_ms (50); //for button bounce reduce
if ((PIND & (1<<ButtonStart)) == 0)
{
ProgramStatus = Running;
ICR1 = 50000; //default top value
set_timer_top_value(TimerTime); //additional top value
start_timer1();
}
while ((PIND & (1<<ButtonStart)) == 0) //waiting for releasing the button
{
}
}
break;
case SoundSignal:
//stop timer and give sound signal to user
stop_timer1();
ProgramStatus = Selection;
Sound_Out();
break;
default:
break;
}
}
return 0;
}
Пн авг 13, 2018 16:37:52
uint64_t delit;
uint64_t delim;
uint64_t my_sf;
uint64_t any_podeli(uint64_t dalc){
delit=(my_sf*my_sf*395*dalc)/10;
delim= 1000000000000000000/delit;
return delim;
}
Вт авг 14, 2018 06:42:01
#include <avr/io.h>
#include <avr/interrupt.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
volatile uint64_t inductance;
uint64_t lcalc (uint32_t freq, uint32_t capacity)
{
uint64_t wrk; // рабочая переменная
wrk = 2533029591058444286; // (1e20 / (4 * pi * pi)), посчитано заранее на виндовом калькуляторе
wrk /= freq;
wrk /= freq;
wrk /= capacity;
return wrk;
}
int main(void)
{
inductance = lcalc ((uint32_t)24000, (uint32_t)16450);
}
Вт авг 14, 2018 06:59:56
Вт авг 14, 2018 13:32:19
Не-а! Не будет лучше. Да и что там такого бешеного? Посчитал в виндовом калькуляторе 1/(4пи квадрат), там же умножил это дело, не мелочась, на 1е24, скопипастил, компилирую - не лезет! Ладно, начинаю по циферке отбрасывать, 4 отбросил - влезло. Дальше оно только делится, так, что переполнений точно не будет. То есть, конечно, надо было подсчитать и сразу написать 1е20, но я поленился.WiseLord писал(а):Да, на 8бит МК лучше избегать использования форматов с плавающей точкой, но это может быть лучше расчётов с такими бешеными коэффициентами.
Вт авг 14, 2018 13:55:59
лучше будет с точки зрения простоты понимания выполняемых действий. для любых инженерных расчетов практически достаточно точности 3 знаков после запятой, поэтому емкость 100 мкФ записывать в с точностью до единиц пикофарад попросту глупо.afz писал(а):Не-а! Не будет лучше.
Вт авг 14, 2018 14:29:58
Вт авг 14, 2018 19:15:43
PC=0x2FFC. [AVR MEMORY] Writing to memory location 0x04DC outside of memory size 0x0460.
Вт авг 14, 2018 20:40:44
Вт авг 14, 2018 21:14:41
Ср авг 15, 2018 11:44:48
Так с ёмкостью 100 мкФ колебательных контуров и не бывает. Максимум 1-2 мкФ, и то, это при измерении больших индуктивностей (десятки Гн). А обычная для радиолюбителей практика - ёмкость в контуре - десятки-сотни-тысячи пикушек, редко когда десятки тысяч.ARV писал(а):поэтому емкость 100 мкФ записывать в с точностью до единиц пикофарад попросту глупо.
Не вижу разницы. Действия одни и те же, а что единицы измерения несколько странные, ну и что?ARV писал(а):лучше будет с точки зрения простоты понимания выполняемых действий.
Сб окт 13, 2018 14:02:51
Сб окт 13, 2018 14:25:34
MCU = atmega328p
AVRDUDE = avrdude
AD_MCU = -p $(MCU)
AD_PROG = -c stk500v2
AD_PORT = -P <порт>
AD_CMD = $(AD_MCU) $(AD_PROG) $(AD_PORT)
flash:
$(AVRDUDE) $(AD_CMD) -U flash:w:<прошивка>.hex:i
Сб окт 13, 2018 15:07:04
Сб окт 13, 2018 20:44:37