Чтение фьюзов на ATmega328P
- Войдите на сайт для отправки комментариев
Чт, 20/12/2018 - 01:12
Не знаю, кому и зачем это может нафиг понадобиться, но на Амперке кому-то приспичило, решил сдублировать здесь. Вдруг и нашим кому пригодится.
Собственно, читаем из программы фьюзы и локбиты. Все пояснения в даташите на 328P, раздел 26.2.2. Если после это нужно с этими фьюзами работать, можно использовать константы (битовые маски), которые определены в файле iom328p.h. Включать его не надо, он у Вас уже включён.
#define LFUSE 0 #define HFUSE 3 #define EFUSE 2 #define LOCKB 1 uint8_t readFuse(const uint8_t fuse = 0) { uint8_t retval = 0; __asm__ __volatile__ ( "mov zl, %[param] \n" "ldi zh, 0 \n" "in r25, %[reg] \n" "ori r25, %[mask] \n" "out %[reg], r25 \n" "lpm %[retval], Z \n" : [retval] "=r" (retval) : [reg] "I" (_SFR_IO_ADDR(SPMCSR)), [mask] "I" (bit(BLBSET) | bit(SPMEN)), [param] "r" (fuse) : "r25", "r30", "r31" ); return retval; } void setup(void) { Serial.begin(115200); Serial.print("Low fuse="); Serial.println(readFuse(LFUSE), HEX); Serial.print("High fuse="); Serial.println(readFuse(HFUSE), HEX); Serial.print("Extended fuse="); Serial.println(readFuse(EFUSE), HEX); Serial.print("Lock bits="); Serial.println(readFuse(LOCKB), HEX); } void loop(void) {}
Нада было там тока ссылку дать. Пусть сюда ходят.
Как всё накручено... Любит у нас народ изобретать.
Вот так и думал, что такая функция уже есть где-то готовая :)
Ну, тогда будем считать, что я просто показал как она внутри делается :)
Кстати, там она сделана в виде макроса, а не функции и использует "sts" вместо моей комбинации "in - ori - out". Т.е. они не только взводят в единицы нужные биты, но и заодно обнуляют все остальные. Я так побоялся делать, но, наверное, можно :)
Иногда нужно заказчику запудрить мозги... Увидев такой код, лох просто цепенеет.)
А вот искал и, тут решение, в закладочку добавлю
SysInfo кроме фьюзов ещё и сигнатуры читает, и по сигнатурам определяет контроллер (#74):
http://arduino.ru/forum/programmirovanie/sysinfo-arduino?page=1#comment-...
Я вот знаете о чём думаю. Вот, что в моём решении, что в решении из boot.h (пост #3) нет никаких cli, а ведь если между записью битов в регистр и командой lpm произойдёт прерывание, то потом lpm бред считает.
Я вот не поставил умышленно, типа мол если есть опасность прерываний ставь снаружи, а лишний раз прерывания закрывать не дело. Но так тввёрдо и не уверен, что прав. Может лучше было поставить. Они там (авторы boot.h) тоже из таких соображений не стали ставить? На самом деле - это ведь залёт, при определённых условиях.
При чтении серийника я ставлю запрет. Читал где-то дискуссию давно уже, с тех пор и ставлю...
Это уже по ситуации. Обычно использую save_interrupt()/restore_interrupt() - макросы сохраняющие и восстанавливающие SREG и запрещаю прерывания на время чтения фьюзов/локов.
SysInfo кроме фьюзов ещё и сигнатуры читает, и по сигнатурам определяет контроллер (#74):
http://arduino.ru/forum/programmirovanie/sysinfo-arduino?page=1#comment-...
Ага, только какие то школьные ошибки в сообщениях: "Unrecogized signature".))
SysInfo кроме фьюзов ещё и сигнатуры читает, и по сигнатурам определяет контроллер (#74):
http://arduino.ru/forum/programmirovanie/sysinfo-arduino?page=1#comment-...
Ага, только какие то школьные ошибки в сообщениях: "Unrecogized signature".))
Вот глаз-алмаз - за целый год никто эту опечатку не заметил. Спасибо, исправлю.
Иногда нужно заказчику запудрить мозги... Увидев такой код, лох просто цепенеет.)
и зачем вы обижаете 99% участников форума)))))
Зато правда.)
Вот глаз-алмаз - за целый год никто эту опечатку не заметил. Спасибо, исправлю.
Я бы вообще советовал писать по русски. Тогда у людей не будет никаких вопросов.)