Pull to refresh

Comments 20

Интересно, а стандартные функции и библиотеки Arduino умеют пользоваться данными, размещёнными за пределами первых 32к? Например, snprintf_P и перегрузка Stream.print(const __FlashStringHelper*)
Пробовали offsetof (костыль получше)?

typedef struct {
    unsigned char array2d[2][3];
} x_t;
...
const x_t  v PROGMEM = {...};
...
unsigned char a = pgm_read_byte_far(pgm_get_far_address(v) + offsetof(x_t, array2d[i][j]));

Надо переходить на ARM, где единное 32 битное адресное пространство (если не перешли).
Вот именно, я не вижу смысла в AVR, кроме как в формате восьминогих тараканов типа ATTiny, дешевле и проще поставить STM32F0/F1, или L серию, если надо ещё и по питанию экономию полную сделать. Есть конечно запущенные случаи, где сигнальные уровни 5V, но там можно и преобразователей уровня поставить.

Или не ставить ибо у stm32 большинство ног 5v tolerant.

Вот из-за таких костылей в коде я и пересел на STM32 — никаких раздельных адресных пространств, все указатели 32 бита…
Возможно появление массивов больше 32К в 8-битном решении намекает на необходимость использования для проекта более мощного МК?
Обработка такого большого массива на 8-и битном МК возможно (зависит от Т.З.) занимает много времени. Поэтому возможно имеет смысл посмотреть в сторону увеличения разрядности.
а еще это может быть развитая менюшка, или набор констант читаемых раз в жизни, или… много всяких или. было у меня семейство приборов на сопровождении. мега2560 с почти полной пзу, а производительности хватало.
UFO landed and left these words here
Что вы подразумеваете под «ни разу не атомарной операцией»? Что LPM, что ELPM выполняются 3 такта. Как вы перед этим заполняете регистры — другой вопрос. И почему бы вам не привести пример другого, короткого и простого макроса?
UFO landed and left these words here
Вся эта статья возникла из-за чтения мануалов. Читаю главу 5, делаю как написано. До 32 КБ работает, потом нет. Вот что я, по-вашему, должен был делать в таком случае? Какие именно мануалы читать, если не те, что я и читал? Как не думать о 32-битной адресации, если нужные данные лежать за пределами 16-битного адресного пространства? При чём тут вообще прерывания? Откуда я мог взять смещение, которое нужно положить в «рампз»?
UFO landed and left these words here
Вот теперь ваша мысль ясна. Я же в самом начале статьи написал, какому именно компилятору она посвящена. Ваша ветвь комментариев — точно такой же оффтоп, как и те, где рекомендуют сменить МК.
«ни разу не атомарная операция», означает в данном контексте, что для получения адреса за пределами смещения в 32к (ограниченных 15 битами регистровой пары Z), необходимо изменять RAMPZ, потому что адресация ELPM использует пару RAMPZ:Z
Аппаратные регистровые указатели у AVR — двухбайтные, X, Y, Z.
Об этом и речь. До тех пор, пока вам достаточно 2 Б (в ассемблере это регистр Z и инструкция LPM — Load Program Memory), всё хорошо. Чтобы выйти за 64 КБ (а по факту за 32), приходится использовать 3-Б аппаратные регистры, а именно RAMPZ:Z и инструкцию ELPM (Extended Load Program Memory). И вся проблема в том, что в главе 5 мануала AVR Libc об этом ни слова, хотя сам модуль pgmspace содержит всё нужное.
Об этом и речь.

речь о том что работать с 32 битными адресами при наличии только 16 битных указателей пришлось бы с гораздо большим количеством костылей. при чем всегда, а не только когда требуется выйти за пределы 32 кбайт.

хотя большие аврки уже сами по себе на костылях стоят.
Only those users with full accounts are able to leave comments. Log in, please.