Სარჩევი:

AVR მიკროკონტროლერი. LED- ები ციმციმებს ტაიმერის გამოყენებით. ქრონომეტრები წყვეტს. ტაიმერი CTC რეჟიმი: 6 ნაბიჯი
AVR მიკროკონტროლერი. LED- ები ციმციმებს ტაიმერის გამოყენებით. ქრონომეტრები წყვეტს. ტაიმერი CTC რეჟიმი: 6 ნაბიჯი

ვიდეო: AVR მიკროკონტროლერი. LED- ები ციმციმებს ტაიმერის გამოყენებით. ქრონომეტრები წყვეტს. ტაიმერი CTC რეჟიმი: 6 ნაბიჯი

ვიდეო: AVR მიკროკონტროლერი. LED- ები ციმციმებს ტაიმერის გამოყენებით. ქრონომეტრები წყვეტს. ტაიმერი CTC რეჟიმი: 6 ნაბიჯი
ვიდეო: Мигающий светодиод. AVR.RU 2024, ნოემბერი
Anonim
Image
Image

Გამარჯობა ყველას!

ქრონომეტრები მნიშვნელოვანი კონცეფციაა ელექტრონიკის სფეროში. ყველა ელექტრონული კომპონენტი მუშაობს დროის ბაზაზე. ეს დროის ბაზა ხელს უწყობს ყველა სამუშაოს სინქრონიზაციას. ყველა მიკროკონტროლი მუშაობს საათის განსაზღვრული სიხშირით, მათ აქვთ ქრონომეტრების დაყენების დებულება. AVR გამოირჩევა ტაიმერით, რომელიც არის ძალიან ზუსტი, ზუსტი და საიმედო. ის გვთავაზობს უამრავ მახასიათებელს მასში, რაც მას ფართო თემად აქცევს. საუკეთესო ნაწილი ის არის, რომ ტაიმერი სრულიად დამოუკიდებელია CPU– სგან. ამრიგად, ის მუშაობს პროცესორის პარალელურად და არ არის პროცესორის ჩარევა, რაც ტაიმერს საკმაოდ ზუსტს ხდის. ამ ნაწილში მე ავხსნი AVR ქრონომეტრების ძირითად კონცეფციებს. მე ვწერ მარტივ პროგრამას C კოდში, რომ გავაკონტროლო LED განათება, ტაიმერების გამოყენებით.

ნაბიჯი 1: აღწერა

პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ
პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ

ATMega328– ში არის სამი ტიპის ტაიმერი:

ტაიმერი/მრიცხველი 0 (TC0) - არის ზოგადი დანიშნულების 8 ბიტიანი ტაიმერი/მრიცხველის მოდული, ორი დამოუკიდებელი გამომავალი შედარების ერთეულებით და PWM მხარდაჭერით;

ტაიმერი/მრიცხველი 1 (TC1) - 16 ბიტიანი ქრონომეტრი/მრიცხველი საშუალებას გაძლევთ ზუსტად შეასრულოთ პროგრამის დრო (ღონისძიებების მართვა), ტალღების წარმოქმნა და სიგნალის დროის გაზომვა;

ტაიმერი/მრიცხველი 2 (TC2) -არის ზოგადი დანიშნულების, არხის, 8 ბიტიანი ტაიმერის/მრიცხველის მოდული PWM და ასინქრონული ოპერაციით;

ნაბიჯი 2: პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ

პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ
პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ
პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ
პრობლემის განცხადება 1: მოდით აანთოთ პირველი LED (მწვანე) ყოველ 50 წთ

მეთოდოლოგია:

- Timer0 prescaler– ის გამოყენება, რათა შემცირდეს მაღალი სიხშირის ელექტრული სიგნალი ქვედა სიხშირეზე მთელი რიცხვის გაყოფით;

- შეწყვეტის გამოყენება ყოველ ჯერზე, როდესაც ტაიმერი 0 გადმოდის;

ტაიმერი 0 (8 ბიტიანი) ის ითვლის 0 -დან 255 -მდე ამის შემდეგ, ისინი გადმოდიან, ეს მნიშვნელობა იცვლება ყოველ საათის პულსის დროს.

F_CPU = 16 MHz: საათის დროის პერიოდი = 1000ms / 16000000Hz = 0.0000625ms

ტაიმერის რაოდენობა = (საჭირო გადადება / საათის დრო) -1 = (50ms / 0.0000625ms) = 799999

საათი უკვე 799999 -ჯერ დარეკილია, რაც მხოლოდ 50 ms დაგვიანებას იძლევა!

ჩვენ შეგვიძლია გამოვიყენოთ სიხშირის გაყოფის ტექნიკა, რომელსაც ეწოდება წინასწარ გადიდება ტაიმერის რაოდენობის შესამცირებლად. AVR გვთავაზობს prescaler– ის შემდეგ მნიშვნელობებს არჩევანისგან: 8, 64, 256 და 1024. იხილეთ ცხრილი აჯამებს სხვადასხვა წინასწარი შემფასებლების გამოყენების შედეგებს.

მრიცხველი ყოველთვის უნდა იყოს მთელი რიცხვი. ავირჩიოთ წინასწარ გამყიდველი 256!

უმეტეს მიკროკონტროლერებში არის რაღაც, რასაც ჰქვია შეფერხება. ეს შეფერხება შეიძლება გათავისუფლდეს, როდესაც დაკმაყოფილებულია გარკვეული პირობები. ახლა, როდესაც შეფერხება გათავისუფლდება, AVR აჩერებს და ზოგავს ძირითად რუტინას, ასრულებს შეწყვეტის ზარს (სპეციალური რუტინის შესრულებით, რომელსაც ეწოდება Interrupt Service Routine, ISR) და მას შემდეგ რაც ეს კეთდება, ბრუნდება მთავარი რუტინა და აგრძელებს მის შესრულებას.

ვინაიდან საჭირო შეფერხება (50 ms) აღემატება მაქსიმალურ შესაძლო შეფერხებას: 4, 096ms = 1000ms / 62500Hz * 256, ცხადია, ტაიმერი გადავსდება. და როდესაც ტაიმერი გადმოდის, შუალედი იხსნება.

რამდენჯერ უნდა გათავისუფლდეს შეფერხება?

50ms / 4.096ms = 3125 /256 = 12.207 თუ ტაიმერი 12 -ჯერ გადაფრინდა, 12 * 4.096ms = 49.152ms გავიდოდა. მე -13 გამეორებისას, ჩვენ გვჭირდება 50ms დაგვიანებით - 49.152ms = 0.848ms.

62500 ჰც სიხშირით (წინასწარგამრიცხველი = 256), თითოეულ ტკიპს სჭირდება 0.016 მ. ამრიგად, 0.848 წმ დაგვიანების მისაღწევად, ამას დასჭირდება 0.848 მ / 0.016 მ = 53 ტკიპა. ამრიგად, მე -13 გამეორებისას, ჩვენ ვაძლევთ ტაიმერს მხოლოდ 53 -მდე დათვლის საშუალებას, შემდეგ კი გადატვირთავთ მას.

ტაიმერის ინიციალიზაცია 0/მრიცხველი (იხ. სურათი):

TCCR0B | = (1 << CS02] // დააყენეთ ტაიმერი წინასწარგამრიცხველით = 256 TCNT0 = 0 // ინიციალიზაციის მრიცხველი TIMSK0 | = (1 << TOIE0] // ჩართეთ overflow interrupt sei () // ჩართეთ გლობალური შეფერხებები tot_overflow = 0 // ინიციალიზაცია overflow counter ცვლადი

ნაბიჯი 3: პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში

პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში
პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში
პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში
პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში
პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში
პრობლემის განცხადება 2: მოდით აანთოთ მეორე LED (ლურჯი) ყოველ 1 წამში

მეთოდოლოგია:

- Timer1 prescaler– ის გამოყენება, რათა შემცირდეს მაღალი სიხშირის ელექტრული სიგნალი ქვედა სიხშირეზე მთელი რიცხვის გაყოფით;

- Clear Timer on Compare (CTC) რეჟიმის გამოყენება;

- შეწყვეტის გამოყენება CTC რეჟიმში;

ქრონომეტრი 1 (16 ბიტიანი) ის ითვლის 0 -დან 65534 -მდე ამის შემდეგ, ისინი ივსება. ეს მნიშვნელობა იცვლება ყოველი საათის იმპულსზე.

F_CPU = 16MHz: საათის დროის მონაკვეთი = 1000ms / 16000000Hz = 0.0000625ms ქრონომეტრის რაოდენობა = (საჭირო დაგვიანება / საათის დრო პერიოდი) -1 = (1000ms / 0.0000625ms) = 15999999

საათი უკვე 15999999 -ჯერ აჩქარდა 1 წამის დაგვიანებით!

ჩვენ შეგვიძლია გამოვიყენოთ სიხშირის გაყოფის ტექნიკა, რომელსაც ეწოდება წინასწარ გადიდება ტაიმერის რაოდენობის შესამცირებლად. AVR გვთავაზობს prescaler– ის შემდეგ მნიშვნელობებს: 8, 64, 256 და 1024. იხილეთ ცხრილი აჯამებს სხვადასხვა წინასწარი შემფასებლების გამოყენების შედეგებს. მრიცხველი ყოველთვის უნდა იყოს მთელი რიცხვი. ავირჩიოთ წინასწარ გამყიდველი 256!

შეადარეთ ქრონომეტრი შედარებისას (CTC) რეჟიმში, OCR1A ან ICR1 რეგისტრი გამოიყენება მრიცხველის გარჩევადობის მანიპულირებისთვის. CTC რეჟიმში მრიცხველი გაწმენდილია ნულამდე, როდესაც მრიცხველის მნიშვნელობა (TCNT1) ემთხვევა OCR1A- ს ან ICR1- ს. OCR1A ან ICR1 განსაზღვრავს მრიცხველის ზედა მნიშვნელობას და, შესაბამისად, მის გარჩევადობასაც. ეს რეჟიმი საშუალებას იძლევა უფრო მეტად აკონტროლოთ შედარების მატჩის გამომავალი სიხშირე იგი ასევე ამარტივებს გარე მოვლენების დათვლის მუშაობას. ჩვენ უნდა ვუთხრათ AVR- ს, გადატვირთოს ტაიმერი 1/მრიცხველი, როგორც კი მისი მნიშვნელობა მიაღწევს 62500 მნიშვნელობას, რითაც მიაღწევს 1 წამიან დაგვიანებას.

ტაიმერის ინიციალიზაცია 1/მთვლელი (იხ. სურათი):

TCCR1B | = (1 << WGM12] | (1 << CS12] // ტაიმერის დაყენება წინასწარგამრიცხველით = 256 და CTC რეჟიმში TCNT1 = 0 // ინიციალიზაციის მრიცხველი TIMSK1 | = (1 << OCIE1A] // ჩართვა შედარების შეწყვეტის OCR1A = 62500 // ინიციალიზაცია შედარების მნიშვნელობა

ნაბიჯი 4: პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms

პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms
პრობლემის განცხადება 3: მოდით აანთოთ მესამე LED (წითელი) ყოველ 16 ms

მეთოდოლოგია:

- Timer2 prescaler– ის გამოყენება, რათა შემცირდეს მაღალი სიხშირის ელექტრული სიგნალი ქვედა სიხშირეზე მთელი რიცხვის გაყოფით;

- Clear Timer on Compare (CTC) რეჟიმის გამოყენება;

- აპარატურის CTC რეჟიმის გამოყენება შეფერხებების გარეშე;

ტაიმერი 2 (8 ბიტიანი) ის ითვლის 0 -დან 255 -მდე ამის შემდეგ, ისინი ივსება. ეს მნიშვნელობა იცვლება ყოველი საათის იმპულსზე.

F_CPU = 16 MHz: საათის დროის პერიოდი = 1000ms / 16000000Hz = 0.0000625ms

ტაიმერის რაოდენობა = (საჭირო დაგვიანება / საათის დრო) -1 = (16ms / 0.0000625ms) = 255999

საათი უკვე 255999 -ჯერ აჩქარდა, რაც 16 წამის დაგვიანებით აძლევდა!

იხილეთ ცხრილი აჯამებს სხვადასხვა წინასწარი შემფასებლების გამოყენების შედეგებს. მრიცხველი ყოველთვის უნდა იყოს მთელი რიცხვი. ავირჩიოთ წინასწარ გამყიდველი 1024!

CTC რეჟიმში მრიცხველი ნულის ტოლდება, როდესაც მრიცხველის მნიშვნელობა (TCNT2) ემთხვევა OCR2A- ს ან ICR2- ს. Pin PB3 ასევე არის TIMER2 - OC2A გამომავალი შედარების პინი (იხ. დიაგრამა).

ქრონომეტრი/Counter2 საკონტროლო რეგისტრი A - TCCR2A ბიტი 7: 6 - COM2A1: 0 - შეადარეთ გამოთვლის რეჟიმი შეადარეთ ერთეულს A. ვინაიდან ჩვენ გვჭირდება LED- ის გადართვა, ჩვენ ვირჩევთ ვარიანტს: გადართვა OC2A შედარების მატჩზე, როდესაც შედარების მატჩი ხდება, OC2A პინი ავტომატურად გადართულია. არ არის საჭირო დროშის ნაწილის შემოწმება, არ არის საჭირო რაიმე შეფერხების დაკვირვება.

ტაიმერის ინიციალიზაცია 2/მრიცხველი

TCCR2A | = (1 << COM2A0] | (1 << WGM21) // დააყენეთ ტაიმერის OC2A პინი გადართვის რეჟიმში და CTC რეჟიმში TCCR2B | = (1 << CS22] | (1 << CS21) | (1 << CS20) // დააყენეთ ტაიმერი წინასწარგამრიცხველით = 1024 TCNT2 = 0 // ინიციალიზაციის მრიცხველი OCR2A = 250 // ინიციალიზაცია შედარების მნიშვნელობა

ნაბიჯი 5: პროგრამის კოდის წერა C. ატვირთეთ HEX ფაილი მიკროკონტროლერის ფლეშ მეხსიერებაში

პროგრამის კოდის წერა C. HEX ფაილის ატვირთვა მიკროკონტროლერის ფლეშ მეხსიერებაში
პროგრამის კოდის წერა C. HEX ფაილის ატვირთვა მიკროკონტროლერის ფლეშ მეხსიერებაში
პროგრამის კოდის წერა C. HEX ფაილის ატვირთვა მიკროკონტროლერის ფლეშ მეხსიერებაში
პროგრამის კოდის წერა C. HEX ფაილის ატვირთვა მიკროკონტროლერის ფლეშ მეხსიერებაში

AVR მიკროკონტროლერის პროგრამის წერა და შექმნა C კოდში ინტეგრირებული განვითარების პლატფორმის - Atmel Studio გამოყენებით.

F_CPU განსაზღვრავს საათის სიხშირეს ჰერცში და ხშირია პროგრამებში, avr-libc ბიბლიოთეკის გამოყენებით. ამ შემთხვევაში იგი გამოიყენება დაგვიანების რუტინით, რათა დადგინდეს როგორ გამოვთვალოთ დროის შეფერხებები.

#ifndef F_CPU

#განსაზღვრეთ F_CPU 16000000UL // ეუბნება კონტროლერს ბროლის სიხშირე (16 MHz AVR ATMega328P) #endif

#include // header მონაცემების ნაკადის კონტროლის გასააქტიურებლად ქინძისთავებზე. განსაზღვრავს ქინძისთავებს, პორტებს და ა.

პირველი ფაილი არის avr-libc- ის ნაწილი და გამოყენებული იქნება თითქმის ნებისმიერ AVR პროექტში, რომელზეც მუშაობთ. io.h განსაზღვრავს თქვენს მიერ გამოყენებულ CPU- ს (რის გამოც თქვენ მიუთითებთ ნაწილს შედგენისას) და თავის მხრივ მოიცავს ჩიპს, რომელსაც ჩვენ ვიყენებთ, შესაბამისი IO განსაზღვრის სათაურში. ის უბრალოდ განსაზღვრავს მუდმივობას თქვენი ყველა ქინძისთავისთვის, პორტისთვის, სპეციალური რეგისტრაციისთვის და ა.

#include // header შეწყვეტის გასააქტიურებლად

არასტაბილური uint8_t tot_overflow; // გლობალური ცვლადი, რათა დაითვალოს გადავსების რაოდენობა

პრობლემის შექმნის მეთოდოლოგია: Flash პირველი (მწვანე) LED ყოველ 50 ms

- Timer0 prescaler– ის გამოყენება, რათა შემცირდეს მაღალი სიხშირის ელექტრული სიგნალი ქვედა სიხშირეზე მთელი რიცხვის გაყოფით;

- შეწყვეტის გამოყენება ყოველ ჯერზე, როდესაც ტაიმერი 0 გადმოდის;

void timer0_init () // ტაიმერის ინიციალიზაცია 0, შეწყვეტა და ცვლადი

{TCCR0B | = (1 << CS02); // დააყენეთ ტაიმერი წინასწარგამრიცხველით = 256 TCNT0 = 0; // მრიცხველის ინიციალიზაცია TIMSK0 | = (1 << TOIE0]; // ჩართვა overflow nterrupt sei (); // გლობალური შეფერხებების ჩართვა tot_overflow = 0; // ინიციალიზაცია overflow counter ცვლადი}

პრობლემის შექმნის მეთოდოლოგია: Flash მეორე LED (ლურჯი) ყოველ 1 წმ

- Timer1 prescaler– ის გამოყენება, რათა შემცირდეს მაღალი სიხშირის ელექტრული სიგნალი ქვედა სიხშირეზე მთელი რიცხვის გაყოფით;

- Clear Timer on Compare (CTC) რეჟიმის გამოყენება;

- შეწყვეტის გამოყენება CTC რეჟიმში;

void timer1_init () // ტაიმერის ინიციალიზაცია 1, შეწყვეტა და ცვლადი {TCCR1B | = (1 << WGM12] | (1 << CS12); // დააყენეთ ტაიმერი წინასწარგამრიცხველი = 256 და CTC რეჟიმში TCNT1 = 0; // მრიცხველის ინიციალიზაცია OCR1A = 62500; // ინიციალიზაცია შედარების მნიშვნელობა TIMSK1 | = (1 << OCIE1A); // შეადარეთ შეწყვეტის ჩართვა}

პრობლემის შექმნის მეთოდოლოგია: მესამე მესამე LED (წითელი) ყოველ 16 ms

- Timer2 prescaler– ის გამოყენება, რათა შემცირდეს მაღალი სიხშირის ელექტრული სიგნალი ქვედა სიხშირეზე მთელი რიცხვის გაყოფით;

- Clear Timer on Compare (CTC) რეჟიმის გამოყენება;

- აპარატურის CTC რეჟიმის გამოყენება შეფერხებების გარეშე;

void timer2_init () // ტაიმერის ინიციალიზაცია 2 {TCCR2A | = (1 << COM2A0] | (1 << WGM21); // დააყენეთ ტაიმერის OC2A პინი გადართვის რეჟიმში და CTC რეჟიმში TCCR2B | = (1 << CS22] | (1 << CS21) | (1 << CS20); // დააყენეთ ტაიმერი წინასწარგამრიცხველით = 1024 TCNT2 = 0; // მრიცხველის ინიციალიზაცია OCR2A = 250; // შეადარეთ მნიშვნელობის ინიციალიზაცია}

TIMER0 overflow შეწყვეტის სერვისის რუტინა, როდესაც TCNT0 გადმოდის:

ISR (TIMER0_OVF_vect)

{tot_overflow ++; // თვალყური ადევნეთ გადავსების რაოდენობას}

ეს ISR იხსნება ყოველთვის, როდესაც მატჩი ხდება, გადართვა ხდება თავად აქ:

ISR (TIMER1_COMPA_vect) {PORTC ^= (1 << 1); // გადართვა led აქ}

მთავარი (ბათილია)

{DDRB | = (1 << 0]; // დაკავშირება 1 (მწვანე) led pin PB0 DDRC | = (1 << 1); // დაკავშირება 2 (ლურჯი) გამოიწვია pin PC1 DDRB | = (1 << 3); // დაკავშირება 3 (წითელი) led pin PB3 (OC2A) timer0_init (); // ინიციალიზაცია timer0 timer1_init (); // ინიციალიზაცია timer1 timer2_init (); // ტაიმერის ინიციალიზაცია 2 ხოლო (1) // მარყუჟი სამუდამოდ {

თუ ტაიმერი 0 12 -ჯერ გადაფრინდა, 12 * 4.096 მმ = 49.152 წამი გავიდოდა. მე -13 გამეორებისას ჩვენ გვჭირდება 50ms დაგვიანებით - 49.152ms = 0.848ms. ამრიგად, მე -13 გამეორებისას, ჩვენ ვაძლევთ ტაიმერს მხოლოდ 53 -მდე დათვლის საშუალებას, შემდეგ კი გადატვირთავთ მას.

თუ (tot_overflow> = 12) // შეამოწმეთ თუ არა of overflows = 12 შენიშვნა: '> =' გამოიყენება

{if (TCNT0> = 53) // შეამოწმეთ აღწევს თუ არა ტაიმერის რაოდენობა 53 -ს {PORTB ^= (1 << 0]; // გადააქვს led TCNT0 = 0; // მრიცხველის გადატვირთვა tot_overflow = 0; // გადატვირთვის მრიცხველის გადატვირთვა}}}}

მიკროკონტროლერის ფლეშ მეხსიერებაში HEX ფაილის ატვირთვა:

ჩაწერეთ DOS მოთხოვნის ფანჯარაში ბრძანება:

avrdude –c [პროგრამისტის სახელი] –p m328p –u –U flash: w: [თქვენი hex ფაილის სახელი] ჩემს შემთხვევაში ეს არის: avrdude –c ISPProgv1 –p m328p –u –U flash: w: Timers.hex

ეს ბრძანება წერს ექვსკუთხა ფაილს მიკროკონტროლის მეხსიერებაში. ნახეთ ვიდეო მიკროკონტროლერის ფლეშ მეხსიერების დაწვის დეტალური აღწერით:

მიკროკონტროლერის ფლეშ მეხსიერების დაწვა…

Კარგი! ახლა, მიკროკონტროლი მუშაობს ჩვენი პროგრამის ინსტრუქციის შესაბამისად. მოდით შევამოწმოთ!

ნაბიჯი 6: ელექტრული წრის გაკეთება

ელექტრული წრის გაკეთება
ელექტრული წრის გაკეთება
ელექტრული წრის გაკეთება
ელექტრული წრის გაკეთება
ელექტრული წრის გაკეთება
ელექტრული წრის გაკეთება

შეაერთეთ კომპონენტები სქემატური დიაგრამის შესაბამისად.

გირჩევთ: