有四个相关的源文件。你可以找到他们作为附件。我添加了Makefile以及。Makefile配置µ你可以调整你的选择控制单元。
-
主。C(主回路和初始化)
-
主。H(所有的定义和设置)
-
中断。C(中断运行时)
-
功能。C(功能;)
的主要特点是外包给中断运行时节约能源。你可以把µC睡觉。
主要的C。
这是主回路。主。C配置端口,中断和接口,需要直接进入主循环。
// === LED timing diagram rear ===
//
// Time segments
// |00|01|02|03|04|05|06|07|08|09|10|11|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 01| | | | | | | | |##|##|##|##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 02| | | | | | | |##|##|##|##| |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// L 03| | | | | | |##|##|##|##| | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 04| | | | | |##|##|##|##| | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// E 05| | | | |##|##|##|##| | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 06| | | |##|##|##|##| | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// D 07| | |##|##|##|##| | | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 08| |##|##|##|##| | | | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// S 09|##|##|##|##| | | | | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 10|##|##|##| | | | | | | | |##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 11|##|##| | | | | | | | |##|##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 12|##| | | | | | | | |##|##|##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
#include "main.h" //Import all needed defines, makros, libraries, global variables
//=== Receiver ===
#define F_CPU 8000000UL
#include <avr/io.h>
#include <util/delay.h>
#include "rf12.c"
int main(void)
{
unsigned char chr = '1';
vTIMER0_ini(); //Initialize ans start timer 0 (overflow after 8*0.064ms), 8bit timer, prescaler 8, interrupt enable, no preload
vPORTS_ini(); //Initialize all ports for LED usage
vINT0_ini(); //Initialize external interrupt 0 (int0)
sei(); //Global interrupt enable on
rf12_init();
while(1) //Endless loop
{
rf12_rxdata(&chr, 1);
if (chr == '1')
{
switche_on = 1;
}
if (chr == '0')
{
switche_on = 0;
}
}
}#p#分页标题#e#
主回路(,(1))实际上可能是空的。这是源代码的最终版本。我添加了一个蓝牙模块的µC.驱动可以使用自行车显示开关灯打开和关闭无线。源文件“RF12。C”包含在附件。你可以使用它。如果有任何问题,随时问我吧。这个函数的基本目的是不必要的。
我用了两个中断。定时器中断是我精确的时钟,测量旋转时间。第二中断时激发的港口,而霍尔传感器连接,有一个上升沿。这将重置定时器和节省时间段。
主要的。
这是最主要的。它的主要头文件。
/ = = =引脚配置在高速单片机原理的项目= = =
/ / / / / /
VCC +
/ VCC _____ _____ |
/ + _____ | \ _ / | |
/ |复位O - 1 - | PA2 VCC | - 20-o --”
/。------ O ------。| | LED8
/ | | CS ----- RXD O - 2 - | PD0 PB7 | - 19-o ucsk / SCL / pcint7 ----- > | ---。
/ |。| | | LED7 |
/ | |哈尔|。—。SCK ----- TXD O--3-|PD1 PB6|-18-O MISO/DO/PCINT6 ------>|---o
// | | | | | 1.8k | | LED6 |
// | |1 2 3| | | SDI --- XTAL2 O--4-|PA1 PB5|-17-O MOSI/DI/PCINT5 ------>|---o
// | '-----' '-' | | LED5 |
// | | | | Q | SDO --- XTAL1 O--5-|PA0 PB4|-16-O OC1B/PCINT4 --------->|---o
// | | | | | | | LED4 |
// '---' | '-----o----------- CKOUT/XCK/INT0 O--6-|PD2 PB3|-15-O OC1A/PCINT3 --------->|---o
// | LED9 | | LED3 |
// | .----|<------------- INT1 O--7-|PD3 PB2|-14-O OC0A/PCINT2 --------->|---o
// | | LED10 | | LED2 |
// '---------o----|<--------------- T0 O--8-|PD4| PB1 - 13-o AIN1 / pcint1 --------- > |啊
/ | led11 | | LED1 |
/ / O ---- | < ---------- oc0b/T1 O - 9 - | PD5 PB0 | -氧AIN0 / pcint0 --------- > |啊
/ | | | led12 |
/ |。-- o-10 - | GND PD6 | - 11-氧ICP ----------------- > |啊
/ | | | _____________ | |
/ | | attiny 2313 |
/ | | |
/ / = = = = = = = = =
/接地接地接地
/ / = = = LED引脚= = = / /
#定义pin_led1 0
#定义pin_led2 1
#定义pin_leD3 2
#define PIN_LED4 3
#define PIN_LED5 4
#define PIN_LED6 5
#define PIN_LED7 6
#define PIN_LED8 7
#define PIN_LED9 3
#define PIN_LED10 4
#define PIN_LED11 5
#define PIN_LED12 6
// === LED Ports === //
#define PORT_LED1 PORTB
#define PORT_LED2 PORTB
#define PORT_LED3 PORTB
#define PORT_LED4 PORTB
#define PORT_LED5 PORTB
#define PORT_LED6 PORTB
#define PORT_LED7 PORTB
#define PORT_LED8 PORTB
#define PORT_LED9 PORTD
#define PORT_LED10 PORTD
#define PORT_LED11 PORTD
#define PORT_LED12 PORTD
// === LED Ports (ini) === //
#define PORT_INI_LED1 DDRB
#define PORT_INI_LED2 DDRB
#define PORT_INI_LED3 DDRB
#define PORT_INI_LED4 DDRB
#define PORT_INI_LED5 DDRB
#define PORT_INI_LED6 DDRB
#define PORT_INI_LED7 DDRB
#define PORT_INI_LED8 DDRB
#define PORT_INI_LED9 DDRD
#define PORT_INI_LED10 DDRD
#define PORT_INI_LED11 DDRD
#define PORT_INI_LED12 DDRD
// === LEDs off makros === //
#define mLED1_off(); PORT_LED1&=~(0x01<<PIN_LED1);
#define mLED2_off(); PORT_LED2&=~(0x01<<PIN_LED2);
#define mLED3_off(); PORT_LED3&=~(0x01<<PIN_LED3);
#define mLED4_off(); PORT_LED4&=~(0x01<<PIN_LED4);
#define mLED5_off(); PORT_LED5&=~(0x01<<PIN_LED5);
#define mLED6_off(); PORT_LED6&=~(0x01<<PIN_LED6);
#define mLED7_off(); PORT_LED7&=~(0x01<<PIN_LED7);
#define mLED8_off(); PORT_LED8&=~(0x01<<PIN_LED8);
#define mLED9_off(); PORT_LED9&=~(0x01<<PIN_LED9);
#define mLED10_off(); PORT_LED10&=~(0x01<<PIN_LED10);
#define mLED11_off(); PORT_LED11&=~(0x01<<PIN_LED11);
#define mLED12_off(); PORT_LED12&=~(0x01<<PIN_LED12);
// === LEDs on makros === //
#define mLED1_on(); PORT_LED1|=(0x01<<PIN_LED1);
#define mLED2_on(); PORT_LED2|=(0x01<<PIN_LED2);
#define mLED3_on(); PORT_LED3|=(0x01<<PIN_LED3);
#define mLED4_on(); PORT_LED4|=(0x01<<PIN_LED4);
#define mLED5_on(); PORT_LED5|=(0x01<<PIN_LED5);
#define mLED6_on(); PORT_LED6|=(0x01<<PIN_LED6);
#define mLED7_on(); PORT_LED7|=(0x01<<PIN_LED7);
#define mLED8_on(); PORT_LED8|=(0x01<<PIN_LED8);
#define mLED9_on(); PORT_LED9|=(0x01<<PIN_LED9);
#define mLED10_on(); PORT_LED10|=(0x01<<PIN_LED10);
#define mLED11_on(); PORT_LED11|=(0x01<<PIN_LED11);
#define mLED12_on(); PORT_LED12|=(0x01<<PIN_LED12);
// === LEDs off all makro === //
#define mLEDs_off(); PORT_LED1&=~(0x01<<PIN_LED1);PORT_LED2&=~(0x01<<PIN_LED2);PORT_LED3&=~(0x01<<PIN_LED3);PORT_LED4&=~(0x01<<PIN_LED4);PORT_LED5&=~(0x01<<PIN_LED5);PORT_LED6&=~(0x01<<PIN_LED6);PORT_LED7&=~(0x01<<PIN_LED7);PORT_LED8&=~(0x01<<PIN_LED8);PORT_LED9&=~(0x01<<PIN_LED9);PORT_LED10&=~(0x01<<PIN_LED10);PORT_LED11&=~(0x01<<PIN_LED11);PORT_LED12&=~(0x01<<PIN_LED12);
// === Global variables === //
volatile unsigned long ovrflw_cnt = 0;
volatile unsigned long segment_times = 1250;
//volatile unsigned char chr = '1';
volatile unsigned char switche_on = 1;
//volatile unsigned char chr = '1';
// === Libraries === //
#include <avr/interrupt.h>
#include "functions.c"
#include "interrupts.c"
//#include <avr/signal.h>
//#include <avr/io.h>
//#include <stdlib.h>
主,拥有所有的定义和库。如果你看到一个函数调用一样mled1_off()不要混淆。它不是函数调用实际上。它是一个文本的宏,可后来被定义在编译进步取代。这是一个典型的办法在嵌入式编程程序。它使阅读源代码的好得多,不浪费宝贵的记忆。
也有一些全局变量来跟踪段时间溢出计数。
C中断。
这是所有的中断例程。
// === LED timing diagram rear ===
//
// Time segments
// |00|01|02|03|04|05|06|07|08|09|10|11|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 01| | | | | | | | |##|##|##|##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 02| | | | | | | |##|##|##|##| |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// L 03| | | | | | |##|##|##|##| | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 04| | | | | |##|##|##|##| | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// E 05| | | | |##|##|##|##| | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 06| | | |##|##|##|##| | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// D 07| | |##|##|##|##| | | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 08| |##|##|##|##| | | | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// S 09|##|##|##|##| | | | | | | | |
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 10|##|##|##| | | | | | | | |##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 11|##|##| | | | | | | | |##|##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
// 12|##| | | | | | | | |##|##|##|
// --+--+--+--+--+--+--+--+--+--+--+--+--+
SIGNAL (INT0_vect)
{
if (ovrflw_cnt > 20) // Debouncing (~10,24ms)
{
//Calculate the time for one segment, 12 segments equal one revolution
segment_times = ovrflw_cnt / 12;
//Reset counter, time for the next revolution is measured
ovrflw_cnt = 0;
//Start of time segment 00
if (switche_on == 1)
{
mLEDs_off(); //Reset all LEDs to start fresh
mLED11_on();
mLED10_on();
mLED9_on();
mLED8_on();
}
}
}
SIGNAL (SIG_TIMER0_OVF) //8*0.064ms
{
ovrflw_cnt++;
if (switche_on == 1)
{
if (ovrflw_cnt == (segment_times * 1)) //Start of time segment 01
{
mLED12_on();
mLED8_off();
}
if (ovrflw_cnt == (segment_times * 2)) //Start of time segment 02
{
mLED1_on();
mLED9_off();
}
if (ovrflw_cnt == (segment_times * 3)) //Start of time segment 03
{
mLED2_on();
mLED10_off();
}
if (ovrflw_cnt == (segment_times * 4)) //Start of time segment 04
{
mLED3_on();
mLED11_off();
}
if (ovrflw_cnt == (segment_times * 5)) //Start of time segment 05
{
mLED4_on();
mLED12_off();
}
if (ovrflw_cnt == (segment_times * 6)) //Start of time segment 06
{
mLED5_on();
mLED1_off();
}
if (ovrflw_cnt == (segment_times * 7)) //Start of time segment 07
{
mLED6_on();
mLED2_off();
}
if (ovrflw_cnt == (segment_times * 8)) //Start of time segment 08
{
mLED7_on();
mLED3_off();
}
if (ovrflw_cnt == (segment_times * 9)) //Start of time segment 09
{
mLED8_on();
mLED4_off();
}
if (ovrflw_cnt == (segment_times * 10)) //Start of time segment 10
{
mLED9_on();
mLED5_off();
}
if (ovrflw_cnt == (segment_times * 11)) //Start of time segment 11
{
mLED10_on();
mLED6_off();
}
}
if (switche_on == 0)
{
mLEDs_off();
}
}
有两个中断。int0_vect负责霍尔传感器。它将被触发时,磁铁通过霍尔传感器。中断程序节省计算和节省时间段和重置定时器中断。
sig_timer0_ovf是定时器中断。时间使用定时器的溢出检测。在一个旋转的轮革命等于时间溢出的数量。因此,溢出除以12数等于一段时间。当定时器复位,它重新计数溢出和开关二极管和关闭相应的段在定时器。
C函数。
一些功能,谁能猜的:D
void vPORTS_ini (void);
void vTIMER0_ini (void);
void vINT0_ini (void);
//void vLED_on (char LED_number);
//void vLED_off (char LED_number);
//void vLED_off_all (void);
//void vUSART1_ini (void);
void vTIMER0_ini (void)
{
TCCR0A = 0x00 | (0 << COM0A1) | (0 << COM0A0) | (0 << COM0B1) | (0 << COM0B0) | (0 << WGM01) | (0 << WGM00);
// TCCR0A = 0x00
TCCR0B = 0x00 | (0 << FOC0A) | (0 << FOC0B) | (0 << WGM02) | (0 << CS02) | (1 << CS01) | (0 << CS00); //010 - 8 prescaler
// TCCR0B = 0x01
TCNT0 = 0x00;
// TCNT0 = 0
TIMSK |= (0 << OCIE0B) | (1 << TOIE0) | (0 << OCIE0A);
// TIMSK = 0x02
}
void vINT0_ini (void)
{
GIMSK |= (0x01 << 6);
//Interrupt enable INT0
MCUCR |= (0x01 << ISC01) | (0x00 << ISC00);
//ISC01 = 1, ISC00 = 0: Iterrupt flag on rising edge
}
void vPORTS_ini (void)
{
PORT_INI_LED1 |= (0x01 << PIN_LED1);
PORT_INI_LED2 |= (0x01 << PIN_LED2);
PORT_INI_LED3 |= (0x01 << PIN_LED3);
PORT_INI_LED4 |= (0x01 << PIN_LED4);
PORT_INI_LED5 |= (0x01 << PIN_LED5);
PORT_INI_LED6 |= (0x01 << PIN_LED6);
PORT_INI_LED7 |= (0x01 << PIN_LED7);
PORT_INI_LED8 |= (0x01 << PIN_LED8);
PORT_INI_LED9 |= (0x01 << PIN_LED9);
PORT_INI_LED10 |= (0x01 << PIN_LED10);
PORT_INI_LED11 |= (0x01 << PIN_LED11);
PORT_INI_LED12 |= (0x01 << PIN_LED12);
}
/*
void USART1_ini (void)
{
UBRR1H = (unsigned char) (BAUD>>8);
UBRR1L = (unsigned char) BAUD;
UCSR1C = (0 << UMSEL1) | //asynchronous
(0 << UPM10) | (0<<UPM01) | //Mode 00: no parity
(0 << USBS1) | //1 stop bit
(1 << UCSZ11) | (1 << UCSZ10); //Mode 011: 8 bit data
UCSR1B = (0 << RXCIE1) | (1 << TXCIE1) | (0 << RXEN1) | (1 << TXEN1) | (0 << UCSZ12);
UCSR1A = (0 << U2X1);
}
*/
这些都是建立µ我可以定义为…的功能,我不知道为什么我没有这么做其实并不重要:)。这也有同样的结果。
vports_ini配置端口作为输出。
vint0_ini配置中断看这个港口和等待一个上升沿(霍尔传感器看到磁铁)。
vtimer0_ini参数设置为定时器中断。跑多快等。
这里没有使用usart1_ini。它配置UART接口。类似的功能在RF12发现。C源文件。它是连接的蓝牙模块所需要的,这不过是一个无线串口(RS232)接口。