Arduino / ATmega 328P fuse setting

透過 fuse setting 你可以設定以下功能

  • 選擇不同的時脈來源和決定晶片時脈速度
  • 在晶片開始運作之前設置最小電壓水平
  • 決定是否使用bootloader
  • 配置多少記憶體給bootloader
  • disable reset
  • disable serial programming
  • 在上傳新的 sketch 時停止 eeprom數據被刪除

總共分成3個bytes

  • low byte fuse
  • high byte fuse
  • extended fuse

ps.還有第四個byte用來lock bit,在此不討論。

fuse bit表示方式為二進位,數值1代表 not set / not programmed,數值0代表 set / programmed。當有一個byte表示成

B11111111時也可表示成 0xFF。

ATmega 328P 28PDIP diagram

LOW BYTE Fuses

主要用來處理時脈來源、決定晶片時脈速度、等待多久時間去start-up。

ATmega 晶片可運作在不同頻率下,時脈來源可以透過 CKSEL fuse bit 設定。

CKSEL (Clock Sources / Clock Selection)

時脈訊號可以透過內部的振盪器(oscillator)、外部的 crystal / resonator,Arduino 使用外部的16Mhz的 crystal 。

以上是16MHz的 crystal 被用來連接麵包板上的ATmega處理器,連接到 XTAL1 跟 XTAL2 腳位,要告訴處理去使用外部 crystal 時,要去設定 CKSEL fuse bits,最常犯的錯誤就是忘記去設定 fuse bits ,告訴處理器去使用

下列是對於 CKSEL 設定

Arduino 使用 "Low Power Crystal Oscillator" 選項,ATmega 內建兩個振盪器(oscillator),128kHz RC oscillator 跟 calibrated RC oscillator。"EXternal Clock" 選項,允許晶片使用外部方波時脈訊號,當電路上有自己本身的時脈訊號時,你想要去同步ATmega,或你想要使用單獨的時脈晶片時,都可以使用此選項,External clock 訊號必須連接到時脈接腳。

Crystal Oscillator Options

CKSEL[3:0] = 1111 ,代表選擇8.0Mhz ~ 16.0Mhz的crystal,為arduino 的 normal setting。假如你想要使用比較慢的 crystal 時,假設時脈為6MHz,則設定 CKSEL[3:0] = 1101。假如要使用內部的 RC oscillator 8MHz時,則設定 CKSEL[3:0] = 0010。

SUT1 / SUT0 (Start Up Time)

Crystals 跟 Oscillators 都需要足夠的工作電壓去運作正常,當電壓水平到最大值時需要一點時間,當電壓提升時,時脈可能沒辦法運作在正常速度,為了保持時脈可以運作在正常速度,可以設定 Start Up Time 去避免。

CKSEL0 根據 SUT1 / SUT0 的結果去設置。

BOD 為 Brown Out Detection, 我們稍後在討論。

arduino 使用了最大 startup delay of 14CK + 65ms (CKSEL0 = 1, SUT1 = 1, SUT0 = 1),這也是 ATmega 328 / 328P 晶片的預設值。

CKDIV8 (Clock Devide)

  • ATmega 328 / 328P 晶片有內建的 RC oscillator @ 8.0MHz ,新的晶片出廠時,CKDIV8已經被設置為0(programmed)了,所以時脈從 8MHz 變成了 1MHz。(CKSEL = 0010, SUT = 10, CKDIV8 = 0)此設定使得所有的使用者可以使用任何的 programming interface進行所需的時脈設置

  • 當時脈超出ATmega 晶片的最大值時,CKDIV8 應該被使用。

  • ATmega 晶片可以工作在非常低的電壓環境下,當在低電壓環境時,也需要較低的時脈,使用CKDIV8可以讓時脈變低,正常工作在低電壓環境。

CKOUT (Clock Output)

時脈訊號可以從PB0腳位輸出,當你需要時脈訊號去驅動其他電路時,你可以設置此數值為0(programmed),出廠預設值為1(not programmed)。

High Byte Fuses

有關於 watchdog timer、eeprom 操作以及 bootloader 相關設定。

RSTDISBL (External reset disable)

  • 腳位PC6 是 reset pin,保持低電位,晶片將執行 rest 指令,在 arduino 上,當你按壓開關後,實際上PC6會被接地,然後 reset 晶片。

  • 腳位PC6 也可以被當作一般IO使用,如果當作一般IO使用後,代表 reset 功能不能被使用,而 inline programming 需要 reset ,則導致不能再對晶片 inline programming了。

  • RSTDISBL 是基於安全措施所實施的功能,用來停止重新編程晶片。

  • 當 RSTDISBL 被 programmed(被設定成0)時,Startup time(SUT1 SUT0)會被設定成14CK + 4.1ms 以確保可以進入programming 模式。

  • RSTDISBL 預設值為 not programmed。

DWEN (debugWire enable)

  • ATmega 晶片有內建的 debugging tools ,預設值為關閉。DWEN fuse 被使用來使用此工具。

  • DWEN使用跟 reset 一樣的腳位(PC6),當DWEN 被啟用後(lock bits not set),reset 腳位會變成 communication 腳位,正常的 reset功能則不能再使用,舉個例子,當你啟用 DWEN 在 arduino上,reset 功能則不能被使用了。

  • 為了去使用 on-chip debugging 你需要可相容的 programmer,像是AVR Dragon。更多相關資訊:http://www.hilltop-cottage.info/blogs/adam/debugging-arduino-using-debugwire-atmel-studio-and-an-avr-dragon/

  • 假如你啟用了 DWEN 但也啟用 lock bits 你不能再以正常方式燒錄晶片了。

  • 如果你只是初學者,就把他設定成 not set,甚麼都不用管,畢竟 reset 還是非常有用的。

SPIEN (Enable Serial programming and Data Downloading)

  • ATmega 晶片可以透過使用 serial programming 去 programmed。 Serial programming 被使用在 board programming 透過 serial protocol 藉由 ISP(inline serial programmer) 或 UART。

  • 正常方法去 programming ATmega 晶片 是透過藉由 SPI 介面使用 SCK(clock)、MOSI(input)、MISO(output)腳位。假如你停用 serial programming 你將不能再使用 SPI 介面去 program,你也可以透過 lock bits 去停用 serial programming。

  • 為了去正常使用,就把 SPIEN 設定成啟用就行,除非你的裝置已無需再 programming 的時候,你可以停用此功能,防止有人從 serial communication 存取你的裝置。

  • SPIEN 預設為0(programmed)。

  • RSTDISBL、SPIEN、DWEN fuses 都有可能會造成 ATmega 晶片鎖死,很難再度去使用此晶片。對於一般用途,如果你是剛開始 programming 此晶片,你更不應該更改這些 fuse setting,你也應該檢查這些 fuse setting 有沒有被更改過。

WDTON( Watchdog Timer Always on)

  • watchdog 基本上是一個 timer ,當它沒有接收到 ok 訊號時,它會 reset 晶片。
  • 當你寫了一個不穩定的 code 或者系統可能沒有被允許永久鎖死時,它非常的有用。
  • 當 watchdog 啟用時,有個 sketch 導致崩潰或凍結,使得 watchdog 計時結束還沒有收到 ok 訊號時,它會 reset 晶片,就像arduino上的 reset 按鈕功能差不多。
  • watchdog timer 可以透過軟體啟用,所以 fuse setting 不怎麼需要被使用,預設值為1(not programmed)。

  • 這裡有個迷你教學關於watchdog timer:https://forum.arduino.cc/index.php?topic=63651.0

EESAVE (Preserve EEPROM memory)

  • 當ATmega 晶片被 programming 的時候,eeprom memory 會在新的 code 上傳前,被抹除之前的儲存的資訊,EESAVE fuse 可以被用來告訴晶片不要抹除,當你想要更新你的 code 但是也想保留留在eeprom上的使用者的設定,這非常有用。
  • EESAVE預設值為1(not programmed),當 programming 時,eeprom memory會被抹除。
  • 當你有使用到eeprom儲存資料時,當programming時,記得設置此fuse以保存資料。

BOOTSZ1 & BOOTSZ0 (Boot loader Size)

  • ATmega 晶片可以使用bootloader,當晶片啟動或 reset 時,它是第一個被執行的小型程式,它通常被用來初始化裝置跟檢查外部通訊。arduino 使用bootloader 去跟電腦通訊,並檢查是否有新 code 要被上傳,那也就是為什麼arduino要在你上傳新的 code時,reset 晶片,透過 reset 此動作,它會再次執行 bootloader 檢查是否有新 code 要上傳。
  • bootloader 儲存在 program memory(flash),bootloader 因為有不同 size,而可以告訴晶片有多少空間我需要儲存。較舊的 arduino bootloader 需要2KB,但是新的 Optiboot (used on the UNO)只需要0.5KB,但如果需要更大的 program memory 的話,可以把 bootloader給刪掉,騰出更多 program memory(flash)。

  • bootloader 被儲存在 program memory(flash) 的頂端。
  • 假如你有一個 bootloader ,那麼 BOOTSZ 跟 BOOTRST 必須一起結合使用,BOOTRST 告訴 晶片 bootloader 的記憶體位址,如果 BOOTRST 沒有設置時,不論 BOOTSZ 的設定如何,uer application 都可以使用整個 program memory。
  • Boot Size Configuration for the 328 / 328P

注意以上的 Boot Size 單位為 words,而一個 words 等同於兩個 bytes,所以 256 words 就是 512 bytes 。

  • BOOTSZ1 跟 BOOTSZ0 的預設值都是0,也就是說有 4KB 的空間保留給 bootloader。

BOOTRST (Select reset vector)

  • ATmega 晶片可以使用 bootloader ,它就像是小型程式,當晶片 reset 時,它是第一支被執行的程式,假如你有使用 bootloader的話,你必須要設置此 BOOTRST ,當 BOOTRST 被設置時,假如晶片被 reset 時,它會跳到 bootloader 的記憶體位址,開始運行 bootloader ,假如沒有設置,則晶片 reset 後,會直接從記憶體位址為0x0000開始執行。
  • BOOTRST 的預設值為1(not programmed)。
  • 假如 BOOTRST 沒有被設置時,則可以忽略 BOOTSZ 的 fuse setting。

Extended Fuse Bits

  • extended fuse 只有被用來設定 brown-out detection level (BOD)。
  • 當電壓不足時,ATmega 晶片會很不穩聽,舉例來說,328 / 328P 可以運行在 16MHz ,但條件是電壓水平至少需要 4V,只要電壓不足 4V,晶片都可能會不穩定,當你的裝置被用來連接感測器去測量或需要準確時間時,這將會產生很大的問題。

  • 為了確保晶片運行在最小電壓水平之上,假設晶片上的電壓下降到最小電壓水平以下時,晶片將會自己 reset,這種方式稱為 brown-out detector,基本上,只要供應電壓低於 BOD 所設定的電壓,晶片將會一直把 reset 設定為低電位(保持 reset )。

  • BODLEVEL[2:0]預設值為111,代表為 BOD disabled。

Default Fuse Settings

  • New ATmega 328P Chip 設定如下

    Low fuse = 0x62 (B01100010)

    High fuse = 0xD9 (B11011001)

    Extended fuse = 0XFF (B11111111)

  • Arduino Duemilanove or Nano w/ ATmega328 Default Fuse Settings

    Low fuse = 0xFF (B11111111)

    High fuse = 0xDA (B11011110)

    Extended fuse = 0x05 (B00000101)

  • Optiboot Boot Loader

    假如你使用 Optiboot bootloader的話,要把 BOOTSZ1 跟 BOOTSZ0 都設置成1,使得bootloader size 為256個 words(512bytes),差別在使用的 bootloader 比較小。

如果你想要看 arduino 所有開發板的預設 fuse settings,請參照:http://www.codingwithcody.com/2011/06/25/arduino-default-fuse-settings/

Lock Bits

  • lock bits 用來限制記憶體的存取, boot section 跟 application 都有他們自己的 lock bits。
  • 當你啟用 lock bits 時,有可能會把晶片給鎖死(brick),所以最好不要更改。

results matching ""

    No results matching ""