Виж темите без отговор | Виж активните теми
Дата и час: Пет Апр 19, 2024 1:59 am
Zilog - Z8 Encore! F083A Series
Автор |
Съобщение |
Metyyy
Ранг: Минаващ
Регистриран на: Съб Ное 22, 2014 6:23 pm Мнения: 48
|
Zilog - Z8 Encore! F083A Series
Здравейте, В момента разучавам таймера на горе посоченият микроконтролер. Искам да го конфигурирам в one-shot mode. Според спецификацията: One-Shot Mode Time-Out Period (s) = (Reload Value – Start Value) * Prescale / System Clock Frequency (Hz) След заместване: (65535 - 0) * 128 / 20MHz = 420ms (приблизително). "От горните изчисления излиза, че максималното време на препълване на таймера е 419424μs или приблизително 420ms, т.е.. периодът на правоъгълните импулси ще бъде 420ms * 2 = 840ms (1.2Hz)." Не разбирам, защо трябва да умножаваме 420ms * 2 ? Ако приемем, че T (период) = 420ms =>, че f = 1 / T => 1 / 0,42s (420ms) = 2,4Hz, но ако умножим 420ms * 2 = 840ms =>, че f = 1 / T => 1 / 0,84s (840ms) = 1,2Hz. Явно бъркам максималното време за препълване на таймера със периода? Наясно съм, че питам елементарни и глупави неща, но много бих се радвал, ако някой ми разясни как точно се случват нещата. Ами, ако искам да направя диода да свети на 5 или 10s ? Мисля, че няма да стане, тъй като максималния делител е 128? Благодаря, предварително!
|
Вто Юни 05, 2018 2:53 pm |
|
|
miro_atc
Ранг: Форумен бог
Регистриран на: Нед Фев 26, 2006 5:52 pm Мнения: 10368 Местоположение: Добрич
|
Re: Zilog - Z8 Encore! F083A Series
Не познавам въпросния таймер, но това си е обща болест... При едно извъртане на таймера имаш 1 събитие. Ако искаш второ събитие се налага още веднъж да извъртиш или таймер с повече compare регистри. От друга страна за да генерираш правоъгълен импулс ти трябват две събития (по едното правиш преден фронт, по другото заден). И те така, първия път таймера като каже "щрак" имаш единия фронт. Втория път като каже "щрак" имаш и другия фронт. Както и да ги броим това са 2 щракания за един период Когато надскочиш възможностите на хардуера се налага да пишеш софтуер. Демек софтуерно си правиш един брояч колко пъти е казал "щрак" таймера. За удобство може таймера да го настроиш на по-кръгло число, да кажем 100ms. И така като софтуерния брояч стане 25, палиш диода, след още 25 щракания гасиш. Ето ти ги 5s. За 10s ще се сетиш сам
|
Вто Юни 05, 2018 3:22 pm |
|
|
itso.t
Ранг: Форумен бог
Регистриран на: Чет Фев 03, 2005 1:21 am Мнения: 10610 Местоположение: София
|
Re: Zilog - Z8 Encore! F083A Series
Виж тая тема - http://www.mcu-bg.com/mcu_site/viewtopi ... =2&t=15883Там са обсъждани различни начини да си мигаш и светкаш.
|
Вто Юни 05, 2018 5:25 pm |
|
|
ike
Ранг: Форумен бог
Регистриран на: Пет Фев 04, 2005 8:59 pm Мнения: 6019 Местоположение: София
|
Re: Zilog - Z8 Encore! F083A Series
Онази тема само ще го обърка още повече, особено ако сега почва.
_________________ Warriors of the Night, ASSEMBLER!!!
|
Вто Юни 05, 2018 10:41 pm |
|
|
slav4o.com
Ранг: Форумен бог
Регистриран на: Нед Яну 01, 2012 7:04 pm Мнения: 2586 Местоположение: Велико Търново / София
|
Re: Zilog - Z8 Encore! F083A Series
Ами на 420ms ти се променя (обръща) изходното ниво (състояние). 420ms лог.1 420ms лог.0 . Получава се период на честотата 840ms или 1.19Hz. Повечето системи където има делене на честотата работят така. Всъщност това нещо което обръща изхода е примерно един JK тригер, който реално дели на две. Предимството както се вижда е, че при какъвто и да е коефициент на делене на брояча, се получава 50/50 коефициент на запълване, нещо което няма как да стане иначе при произволен коефициент.
|
Вто Юни 05, 2018 11:02 pm |
|
|
Metyyy
Ранг: Минаващ
Регистриран на: Съб Ное 22, 2014 6:23 pm Мнения: 48
|
Re: Zilog - Z8 Encore! F083A Series
Благодаря на всички ! Може би, отговора на miro_atc е най-близко разбираем за моите възможности в момента Опитах се да направя delay 5s, но честно да си призная софтуерната част (Delay_Counter_5s == 11) с избора на числово 11 беше чисто и просто налучкване. Не мога да разбера, как получих 5s delay, при положение, че имам първоначално 0.82s и после 11? Съжалявам, ако отговора е очевиден. Откровено казано, темата пратена от itso.t, наистина ме обърка и все пак благодаря ! #include<ez8.h> /* Този хедър позволява да достъпваме вътрешните регистри като всички останали, чрез имената им. */ #define DD0_OFFSET (0) #define IRQE_OFFSET (7) #define TENH_OFFSET (5) #define TENL_OFFSET (5) #define TH_OFFSET (0) #define TL_OFFSET (0) #define TRH_VALUE (65535) #define TRL_VALUE (65535) #define TEN_BIT (7) #define TPOL_BIT (6) #define PRES_BIT_5 (5) #define PRES_BIT_4 (4) #define PRES_BIT_3 (3) #define TMODE_BIT_2 (2) #define TMODE_BIT_1 (1) #define TMODE_BIT_0 (0) #define TMODEHI_BIT (0) #define TCTL1_VALUE ((1<<TEN_BIT) | (0<<TPOL_BIT) | (1<<PRES_BIT_5) | (1<<PRES_BIT_4) | (1<<PRES_BIT_3) | (0<<TMODE_BIT_2) | (0<<TMODE_BIT_1) | (0<<TMODE_BIT_0)) #define POUT0_VALUE (0) typedef unsigned char u08; int main(void) { PADD &= ~(1<<DD0_OFFSET); /* За да конфигурираме извод PA0 като изход, трябва да нулираме бит 0 на регистър PADD */ IRQCTL |= 1<<IRQE_OFFSET; /* Прекъсванията се разрешават с глобалния бит IRQE в регистър IRQCTL. Бит IRQE се установява в 1 */ IRQ0ENL |= 1<<TENL_OFFSET; /* Достатъчно е да установим единия от двата или и двата бита. Младши бит 5 e за разрешаване на прекъсване от Таймер0. Всеки източник на прекъсване има локален механизъм за разрешаване. Този механизъм също се използва за задаване и на софтуерен приоритет на прекъсванията. Тъй като имаме само един източник на прекъсване в програмата, е без значение какво ниво на приоритет ще изберем. */ IRQ0ENH |= 1<<TENH_OFFSET; /* Достатъчно е да установим единия от двата или и двата бита. Младши бит 5 e за разрешаване на прекъсване от Таймер0. Всеки източник на прекъсване има локален механизъм за разрешаване. Този механизъм също се използва за задаване и на софтуерен приоритет на прекъсванията. Тъй като имаме само един източник на прекъсване в програмата, е без значение какво ниво на приоритет ще изберем. */ T0H = TH_OFFSET; /* Записваме начална стойност на таймера в броячните регистри TxH и TxL, т.е. ги нулираме */ T0L = TL_OFFSET; /* Записваме начална стойност на таймера в броячните регистри TxH и TxL, т.е. ги нулираме */ T0RH = TRH_VALUE; /* Регистрите съдържат макс. 16-битова броячна стойност до която брои таймера и тя е 65535 */ T0RL = TRL_VALUE; /* Регистрите съдържат макс. 16-битова броячна стойност до която брои таймера и тя е 65535 */ /* One-shot mode: T = (65535 - 0) * 128 / 20MHz = 419424 микросекунди = 420ms (приблизително) За да генерираме правоъгълен импулс ни трябват две събития (по едното правим преден фронт, по другото заден), затова и трябва да умножим 420ms * 2 = 840ms = 0.84s; T = 1 / 0,84 = 1.2Hz */ T0CTL0 = TMODEHI_BIT; /* Еднократен режим */ T0CTL1 = TCTL1_VALUE; /* Коефициент на деление 128 и стартиране на таймера */ while(1); } void interrupt Timer0_ISR(void) _At TIMER0 { static u08 Delay_Counter_5s = 0; if (Delay_Counter_5s == 11) { PAOUT ^= 1<<POUT0_VALUE; /* Превключване на нивото на извод PA0 */ Delay_Counter_5s=0; } else { Delay_Counter_5s++; } T0CTL1 |= 1<<TEN_BIT; /* Стартиране на таймера отново */ }
|
Сря Юни 06, 2018 12:23 am |
|
|
ike
Ранг: Форумен бог
Регистриран на: Пет Фев 04, 2005 8:59 pm Мнения: 6019 Местоположение: София
|
Re: Zilog - Z8 Encore! F083A Series
420ms * 11 = 4620ms = 4.62s
_________________ Warriors of the Night, ASSEMBLER!!!
|
Сря Юни 06, 2018 6:48 pm |
|
|
Metyyy
Ранг: Минаващ
Регистриран на: Съб Ное 22, 2014 6:23 pm Мнения: 48
|
Re: Zilog - Z8 Encore! F083A Series
По скоро 420 * 10 = 4200ms = 4.2s
|
Сря Юни 06, 2018 7:21 pm |
|
|
slav4o.com
Ранг: Форумен бог
Регистриран на: Нед Яну 01, 2012 7:04 pm Мнения: 2586 Местоположение: Велико Търново / София
|
Re: Zilog - Z8 Encore! F083A Series
Не знам какво си направил. По принцип като изтече периода 420ms се вдига някакъв флаг. Ти или трябва да го проверяваш достатъчно често, или да викаш прекъсване. Когато видиш че е вдигнат флага, го изчистваш и правиш нещо, каквото ти е необходимо. Ако обръщаш изхода на всяко вдигане на флага ще имаш 420ms ниско и 420ms високо ниво. Реално честотата е двойно по-ниска от тази на вдигането на флага. От там идва това 2. Ако броиш 10 пъти вдигане на флага, да 10х420мс и си правиш там нещо като изброиш до 10, т.е. като мине закъснението от 4.2ms. Ако искаш може да броиш до 10 и да обръщаш изхода, така ще поучиш период 8.4s или 0.119Hz, което всъщност няма почти никакво смислено приложение.
|
Сря Юни 06, 2018 7:27 pm |
|
|
miro_atc
Ранг: Форумен бог
Регистриран на: Нед Фев 26, 2006 5:52 pm Мнения: 10368 Местоположение: Добрич
|
Re: Zilog - Z8 Encore! F083A Series
Не знам, не съм гледал и не искам да гледам документацията на твоя чеп...
Но съм видял стотици други и навсякъде таймер се прави с един брояч и един компаратор, които клокваш с някакъв клок. Когато компараторът види еднакви стойности броячът се презарежда и имаш прекъсване. Елементарно е, само че сметките са малко по-различни от тия дето си дал. Ако приемем че броячът брои от 0 и се ресетва до 0, то най-малката стойност дето може да сложиш в компаратора е също нула. При това на всеки такт ще имаш прекъсване и броячът ще брои 0, 0, 0, 0, 0... Изходната честота ще ти е точно 2 пъти по-ниска. Ако сложиш 1 в компаратора, броячът ще брои 0,1,0,1,0,1.... демек ще имаш прекъсване на всеки два такта или с други думи изходната честота е 4 пъти по-ниска.
Така че формулата би трябвало да е нещо от сорта: One-Shot Mode Time-Out Period (s) = (Reload Value +1 – Start Value) * 2* Prescale / System Clock Frequency (Hz)
Нека да приемем prescale=1 и системен клок 1MHz Тогава в първия пример когато reload value=0 и start value=0 имаш X = (0+1-0)*2*1/1000000 = 2/1000000 = 2us
Сега в твоя случай ако брои от 0 до 11, това са си 12 стойности или 12 клока за едно прекъсване или по друг начин казано 12 * 420ms =5.04s
толкова получаваш нали?
|
Пет Юни 08, 2018 8:27 am |
|
|
Metyyy
Ранг: Минаващ
Регистриран на: Съб Ное 22, 2014 6:23 pm Мнения: 48
|
Re: Zilog - Z8 Encore! F083A Series
Сигурен съм, че моите сметки са правилни, точно до графиката с прекъсванията. Така, искам 5 секунди, в случая съм сложил 100 ms, но тогава ще имам 50 прекъсвания, а за да ги намаля, трябва да избера максималното число, кратно на 5 и по малко от 420 ms (0.42s) и то е 200 =>, че графиката се променя и там вместо 100 ms, ще имаме 200 ms. Тук ми е 1-ят въпрос (10 прекъсвания ли ще имам или 11 или 12), макар, че като го сметна е едно и също, тъй като при всички случаи се получава, че за 1 секунда ще имам 5 прекъсвания т.е. за 5 секунди ще имам 25 прекъсвания. А, 2-ят ми въпрос е, колко трябва да бъде началната стойност, от която таймера брои - 65335 т.е. (65535 - 200)? Мисля, че нещата са доста по прости от това което смятам и правя, ама айде де, не мога да го измисля и това е.
Сега, по-случайност избрах за начална стойност на таймера 64753 =>, че 782 * 0.0000064 = 5.0048 секунди.
Предполагам, че досаждам вече, но не виждам друг изход.
Благодаря!
|
Пет Юни 08, 2018 2:56 pm |
|
|
slav4o.com
Ранг: Форумен бог
Регистриран на: Нед Яну 01, 2012 7:04 pm Мнения: 2586 Местоположение: Велико Търново / София
|
Re: Zilog - Z8 Encore! F083A Series
Хм аз пък си мисля, че 250ms x 20 = 5s. Тааака избрал си все пак 200ms. Първо трябва да разбереш откъде взема тактов сигнал този таймер. Имаш прескалер, което значи че входната честота се дели. В случая тя се дели на 128 : 20MHz/128 = 156,25kHz. Периода е 1/156,25 = 6,4uS. Така. За да получиш заветните 200ms, брояча трябва да изброи: 200 000 / 6,4 = 31 250пъти (периода). Това ти е коефициента на брояча. Сега. Процесора ти не знам какъв е , но на PIC-овете първо се настройва таймера и се пуска да си цъка прекъсвания постоянно. Тук ако е така пускаш си го и ще ти генерира прекъсванията. Дотук добре. Ти си харесел период 200ms, което значи че трябва да изброиш 25 пъти докато направиш 5 секунди. Значи във прекъсването трябва да инкрементираш един брояч, който ще ти брои до 25. Да го кръстим unsigned char intcnt; Сега идва ключовият момент. Искаш да кажеш старт на хронометъра и да почнеш да отчиташ заветните 5 секунди. Понеже не знаеш какво число държи брояча на прекъсвания и какво брояча на таймера (понеже си вървят свободно) трябва да ги нулираш. Първо нулираш брояча на таймера , после брояча на прекъсвания, после пак брояча на таймера. Умишлено го нулирам два пъти, първият път може брояча да е на 31 249. Това ми гарантира, че докато нулирам intcnt няма да се извика прекъсването (и да го инкрементира). След това нулирам отново брояча и забележи нулирам последно младшия байт. Така се получава минимално натрупване, докато почнеш да изпълняваш чакането на 5те сек. т.е. максимално точно да е. Така вече имаш функция с която стартираш хронометъра. Остава и да разбереш кога ти е изтекло времето. Има и други начини, със стартиране и спиране на таймера. Аз обаче в моите програми не ги ползвам, тъй като таймера дава тайминги и на други процеси. Освен това не ми са критични толкова времената. Има и други варианти PICовете имат постскалери, постскалера е това което е intcnt. Само, че може да се настрои автоматично да брои примерно до 16 и тогава да ти се генерира прекъсване. Този процесор обаче е друг и не зная дали има. Пък и за теб е важно да знаеш принципно как се прави, а към съответния процесор ще се нагодиш лесно. Ако не ти трябва точност, може да се нулира само intcnt, т.е. софтуерният ти постскалер.
|
Пет Юни 08, 2018 11:25 pm |
|
|
slav4o.com
Ранг: Форумен бог
Регистриран на: Нед Яну 01, 2012 7:04 pm Мнения: 2586 Местоположение: Велико Търново / София
|
Re: Zilog - Z8 Encore! F083A Series
Всъщност те подведох, intcnt ще се инкрементира винаги и след като се превърти, ще ще вика IztekloWreme(); затова ще използваме семафор BOOL timeout = true; с който ще указваме кога да се работи когато влезеш в IztekloWreme(); "светваш" семафора и в прекъсванията ти няма да се броят пакетите от 200ms. Така докато не стартираш отново хронометъра.
|
Съб Юни 09, 2018 12:02 am |
|
|
Metyyy
Ранг: Минаващ
Регистриран на: Съб Ное 22, 2014 6:23 pm Мнения: 48
|
Re: Zilog - Z8 Encore! F083A Series
Благодаря ти за отговора ! Това е което аз направих: Имам системна честота - 20MHz => Честота на таймера - 20MHz / 128 (prescaler) = 156250Hz => Периода на таймера - 1 / 156250 = 0.0000064s или 6.4us => Таймера се увеличава с 1 на всеки 6.4us. "За да получиш заветните 200ms, брояча трябва да изброи: 200 000 / 6,4 = 31 250 пъти (периода). Това ти е коефициента на брояча." - Благодаря ти за това изречение ! Точно това исках да разбера. Също така си абсолютно прав, че трябва да избера 250ms, а не 200ms, защото за 5s при 200ms, ще имам 25 прекъсвания, а за 5s при 250ms, ще имам 20 прекъсвания, което са си 5 по-малко => началната стойност на таймера ще е 250 00 / 6.4 = 39062.5 пъти (периода) => ще брои от 39062.5 до 65535 => прекъсване и следния код: void interrupt Timer0_ISR(void) _At TIMER0 { static u08 Delay_Counter_5s = 1; if (Delay_Counter_5s == 11) { PAOUT ^= 1<<POUT0_VALUE; /* Превключване на нивото на извод PA0 */ Delay_Counter_5s=0; } else { Delay_Counter_5s++; } T0CTL1 |= 1<<TEN_BIT; /* Стартиране на таймера отново (One-shot mode) */ } Логиката ми е: Таймера почва да брои до 65535 => прекъсване - 1=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 2=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 3=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 4=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 5=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 6=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 7=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 8=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 9=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 10=11 (false) - брояча се увеличава => Таймера почва да брои до 65535 => прекъсване - 11=11 (true) - светва диода и нулираме брояча Така, имаме 10 прекъсвания на таймера и 10 на софтуерния броят, демек общо 20 прекъсвания. Това ли трябва да ми е логиката ? Надявам се да, защото уж на пръв поглед един прост таймер ми отне толкова време за разбиране, че ужас Сега, като засека с хронометъра уж са 5s, но все пак не мога да съм абсолютно сигурен.
|
Нед Юни 10, 2018 11:23 am |
|
|
palavrov
Ранг: Форумен бог
Регистриран на: Вто Окт 11, 2011 10:53 pm Мнения: 4194 Местоположение: Brussels / Пловдив
|
Re: Zilog - Z8 Encore! F083A Series
Вземи си един евтин логически анализатор за няма и $10 и ще може да го измериш достатъчно точно + ще ти е в полза и в бъдеще.
_________________ Мразя да мразя ...
|
Нед Юни 10, 2018 1:15 pm |
|
|
Кой е на линия |
Потребители разглеждащи този форум: 0 регистрирани и 6 госта |
|
Вие не можете да пускате нови теми Вие не можете да отговаряте на теми Вие не можете да променяте собственото си мнение Вие не можете да изтривате собствените си мнения Вие не можете да прикачвате файл
|
|