<meter id="pryje"><nav id="pryje"><delect id="pryje"></delect></nav></meter>
          <label id="pryje"></label>

          新聞中心

          EEPW首頁 > 嵌入式系統(tǒng) > 設計應用 > Avr單片機編程---延遲函數

          Avr單片機編程---延遲函數

          作者: 時間:2016-11-23 來源:網絡 收藏
          avr-gcc提供了兩個延遲函數,可以在用戶的程序中使用,前提--加入avr/delay.h這個頭文件:

          _delay_us(double __us)
          _delay_ms(double __ms)
          而這兩個延遲函數在實際工作的時候,調用了另兩個函數,位于delay_basic.h中:
          a, _delay_loop_1(uint8_t __count)
          b,_delay_loop_2(uint16_t __count)
          a 函數可以看出,_count的最大值是256,b 函數中_count的最大值是65536。在delay_basic.h中有說明,也可以結合a,b兩個函數的具體定義看,a 函數執(zhí)行一次的時間是3個指令周期,b 執(zhí)行一次的時間是4個指令周期,一個指令周期 T = 1 / F_CPU。
          (測試:可以試著計算下當F_CPU取值1M時,_count取1,_delay_loop_1和_delay_loop_2分別延遲時間
          是多 少,如果F_CPU取2M呢,延遲又是多少?)
          *********************************************
          F_CPU在avr-gcc中有定義,這個值是在編譯的時候傳遞給編譯器的,說明用戶程序的晶振頻率,編譯器為了保證編譯過程中防止因用戶為定義這個 F_CPU的值,設定一個初值F_CPU=100 0000UL,即默認用戶使用的是1M的晶振。當然,在實際程序設計時一定要根據實際用到的晶振設定這個值,否則,延遲肯定不準??梢栽诙x加載頭文件前這樣:如
          #include
          #define F_CPU 1000000UL
          #include
          #include
          ***********************************************
          _delay_us(double __us), _delay_ms(double __ms)中又有這樣的定義:
          double __tmp = ((F_CPU) / 4e3) * __ms
          __ticks = (uint16_t)__tmp;
          _delay_loop_2(__ticks);
          --------------------------------------------
          double __tmp = ((F_CPU) / 3e6) * __us;
          __ticks = (uint8_t)__tmp;
          _delay_loop_1(__ticks);
          ---------------------------------------------
          所以根據a,b兩個函數中_count(實際參數)的最大值描述就應該是:
          ((F_CPU) / 3e6) * __us最大值是256
          ((F_CPU) / 4e3) * __ms的最大值是65536
          即我們在自己程序中調用 _delay_us(double __us),_delay_ms(double __ms)這兩個函數時參數的選擇與所取的F_CPU(也就是實際用到的晶振頻率)是有關系的。
          當F_CPU取值為1M時,__us的最大取值是768,__ms的最大取值是65536*4
          當F_CPU取值為2M時,__us的最大取值是768/2,__ms的最大取值是65536*4/2
          ......
          當F_CPU取值為8M時,__us的最大取值是768/8,__ms的最大取值是65536*4/8
          所以,延遲函數的參數取值是不能一概而論的。
          //*************************************************************************************************************************
          現在再來看究竟延遲了多久?
          _delay_us(double __us)的延遲時間因為調用了_delay_loop_1(),而_delay_loop_1()是執(zhí)行3個指令周期,所以延遲時間就是:
          ((F_CPU) / 3e6) * __us*3*T (T = 1 / F_CPU 單位MHz)
          _delay_ms(double __ms)的延遲時間因為調用了_delay_loop_2(),而_delay_loop_2()是執(zhí)行4個指令周期,所以延遲時間就是:
          ((F_CPU) / 4e3) * __ms*4*T (T = 1 / F_CPU 單位MHz)
          可以試著計算下,當F_CPU取值為1M時,_delay_us(X)就是延遲X us,_delay_ms(X)就是延遲X ms
          補充:
          其實,如果自己查看新的源代碼可以發(fā)現,現在的定時的時間并不像有的舊的文章上說的那樣,限制在一定的范圍內。因為代碼更新過了,嘎嘎。

          本文引用地址:http://www.ex-cimer.com/article/201611/320341.htm


          評論


          技術專區(qū)

          關閉
          看屁屁www成人影院,亚洲人妻成人图片,亚洲精品成人午夜在线,日韩在线 欧美成人 (function(){ var bp = document.createElement('script'); var curProtocol = window.location.protocol.split(':')[0]; if (curProtocol === 'https') { bp.src = 'https://zz.bdstatic.com/linksubmit/push.js'; } else { bp.src = 'http://push.zhanzhang.baidu.com/push.js'; } var s = document.getElementsByTagName("script")[0]; s.parentNode.insertBefore(bp, s); })();