Перейти к содержанию
    

vvppvv

Участник
  • Постов

    70
  • Зарегистрирован

  • Посещение

Весь контент vvppvv


  1. Добрый день! Есть узкая длинная плата, на ней 16 одинаковых схем фотоприемников + питание + обслуживание. Подскажите, где можно почитать, или найти пример, как всё это корректно сделать, начиная с принципиальной схемы, и кончая печатной платой? Чтоб можно было составить перечень элементов, прогнать всякие DRC, т.е. по-человечески, без извратов. В схеме легко нарисовать один модуль M1, а остальные скрыть за пунктирами, М2, М3 и пр. А как быть с разводкой печатной платы? Ctrl-C, Ctrl-V, так Пикад начнёт ругаться, мол, повторяющиеся цепи. Вобщем, прошу направить в нужном направлении. Можно даже дать ускоряющего пендаля. :))) Или в PCAD2006 такое невозможно в принципе?
  2. Да, в случае с AVR тут два байта но одно машинное слово. Содержащее и саму операцию, и источник, и получатель - всё в одном, и за 1 такт. )) Спасибо! ))
  3. Ну, вроде как да. )) Аутомотив чуть попроще. Во всяком случае, википедия пишет следующее: ============= Most devices are manufactured in several temperature grades. Broadly accepted grades are: Commercial: 0 ° to 70 °C Industrial: −40 ° to 85 °C Military: −55 ° to 125 °C Nevertheless, each manufacturer defines its own temperature grades so designers must pay close attention to actual datasheet specifications. For example, Maxim Integrated uses five temperature grades for its products: Full Military: −55 °C to 125 °C Automotive: −40 °C to 125 °C AEC-Q100 Level 2: −40 °C to 105 °C Extended Industrial: −40 °C to 85 °C Industrial: −20 °C to 85 °C ================ Что касаемо морозостойкости AVR, конкретно лет 10 назад морозили один моторедуктор на 24В для УРАЛа, вкупе с нашим блочком управления. Прецизионных термокамер у нас не было, брали пенопластовый ящик, куб сухого льда, и самый точный термометр, какой был (87-ой Флюк со штатной выносной термопарой, засунутой внутрь блочка и расположеной рядом с Атмегой48 :)). Оставляли на ночь, оно всё промораживалось вусмерть, утром открывали... Вначале термопара в ящике показывала около -74С, после открывания, как лёд начинал испаряться, доходило почти до -80С! После испарения льда, температура плавно начинала расти. Короче, до -65С не работало вобще ничего. Труп 100%. В районе -60...-55 блочок оживал и вполне себе шевелил выходами, в зависимости от входов. Питание Vcc, правда, было в районе 4,5В (электролиты сильно теряют емкость на морозе), где-то в районе -45С и питание в норму приходило. +5,05В. За точностью цифр мы не гнались (нечем было обеспечить, да и незачем), нас самих такой результат вполне удовлетворил, и мы сами себе дали "добро" для использования AVR. :)))
  4. А главное, после того, как машина всю ночь простоит на морозе, ЭБУ вобще фиолетово, в какой части автомобиля он находится. ))) P.S. Кстати, поискал доку на свой ЭСУД М75, который в моём автомобильчике, там стоИт камень SAK-XC2060M-104F80L. Поискал на него даташит, указано: the temperature range: – SAF-…: -40°C to 85°C – SAH-…: -40°C to 110°C – SAK-…: -40°C to 125°C Т.е. вверх диапазон задвинут аж до Аутомотив, а снизу так и ограничено -40С.
  5. Нашёл! Свою старую демо-программку (это я в 95 году учился для х86 программировать, почти 30 лет назад :)). Это как демонстрация той самой моей идеи. Работает под MS-DOS, сейчас запустил на Win7-64, просто кинув файл Fox-pg.exe на иконку DOSBox. Левым Ctrl поочищать окно, а правым Shift останавливать-пускать поток. Вот что-то такое я имел ввиду. На экране монитора, разумеется, всё можно подсветить разными цветами, для наглядности. Китайский анализатор, клон Sealogic (или как там его) у меня есть, работает, но вот UART порты на нем не смотрел, как-то было без надобности. Fox-pg.zip
  6. Не могу найти названий тех коробочек и программ, которыми пользовался 25 - 30 лет назад. )) Но смысл такой, поясню по воспоминаниям анализатора протокола SINEC L1 для MS-DOS. Я бы сделал так. По экрану бегут 2 строки символов, параллельно. Верхняя - одно устройство (У№1), нижняя - второе (У№2). Если никто ничего не посылает, то строки замирают на месте. Послал байт У№1. он отобразился в верхней строке, а в нижней - ничего. Если оба У№1 и У№2 посылают байты, то они отображаются в соответствующих строках. Плюсы такого "монитора" очевидны - виден "нахлёст", т.е. про софтварном Xon-Xoff, когда У№1 шлёт посылку, а У№2 шлёт код DC3, чтоб её затормозить, видно, сколько байт "хвоста" следуют от У№1, пока он не остановится. Нужен промежуточный микроконтроллер с 2-мя последовательными портами (входами) и 2-мя буферами. Заполнились 2 буфера - выдать. Порт выдачи, понятное дело, должен иметь скорость как минимум в 2 раза выше наблюдаемых (какой-нибудь USB-UART на 500кбит).
  7. Тому, как выглядит AVR на фоне других (скажем так, дешёвых бытовых) МК. AVR обязан работать и работает при -55С. А STM8Sххх, на который предплагалось перейти - только до -40С. И STM32 тоже только до -40С. Да, но всё-таки, это заявлено как operating температура, а не просто storage. Что косвенно свидетельствует о некотором запасе прочности при эксплуатации в районе -45С. Разумеется, ресурсные испытания на термоциклирование мы не проводили, да и зачем? Тот же самый атомобиль УРАЛ 4320, кстати, разрешается эксплуатировать до -45С и (цитата) "кратковременно до -50". P.S. чтоб два раза не вставать - разумеется, такие фривольные рассуждения о морозоустойчивости AVR идут в контексте применения данных МК сугубо в продукции "гражданского назначения", в частности, об УРАЛах дивизиона НХ (народное хозяйство).
  8. Вот то и значит, что реально. В документации прописано "Operating Temperature..... -55°C to +125°C" и оно реально так работает! И АЦП достаточно точно работает (я обычно усредняю 4 отсчёта), без всяких внешних опор, в диапазоне рабочих температур, при "гулянии" питания 4...5В. И это плюс AVR. Гибкость работы с портами ввода-вывода AVR меня вполне устраивает, потому, что гибче некуда - от высокого импеданса до +\- 40мА на вывод. Скажите мне, как поведут себя платки Raspberry Pi Pico, скажем, где-нибудь в сибирской глуши, на автомобиле Урал-4320, ясной морозной ночью при -45? Вот и я про то же. Задачи-то бывают разные.
  9. AVR при низких температурах

    Выделил от этого сообщения (прошу там не обсуждать низкие температуры): И не только вычислительной способности. AVR реально работают при -50 градусов Цельсия. У AVR прекрасная, термостабильная внутренняя опора, в самых мелких камнях. У AVR все входы-выходы ОДИНАКОВЫЕ, а не так, что тут мощно, тут полумощно, здесь открытый коллектор, там не пойми чего. Это я про собственный опыт попытки пересадки с AVR на STM8S00x )))) Да и вобще, пока по планете бодро шагают армии ардуинщиков, с похоронами AVR придётся повременить. Я держу до сих пор AVR Studio 4.19 как эмулятор, для _софтовой_ отладки критичных кусков. По тактам (по времени), по логике и пр. Пробовал IAR'овский UBROF загрузить в последнюю студию Майкрочипа (сейчас версия 7.0.2542), но что-то никак не получается. Вот чтобы было окно с регистрами, памятью, всеми битами/портами, сишным исходником, дизассемблером и пр., как это было в AVR студии.
  10. Я с либами тоже дел не имел, но, так думаю, если в исходнике есть прямые команды, чего куда положить, значит, они обязательны для дальнейшего использования. В доке IAR'а есть глава "Controlling data and function placement in memory", там всё подробно расписано. Данные можно расположить по конкретным адресам, областям, либо использовать свои, пользовательские сегменты. То же самое относится и к функциям. ==== #pragma location=0xFF2002 __no_init const int beta; /* OK */ const int gamma @ 0xFF2004 = 3; /* OK */ __no_init int alpha @ "MY_NOINIT"; /* OK */ #pragma location="MY_CONSTANTS" const int beta = 42; /* OK */ const int gamma @ "MY_CONSTANTS" = 17;/* OK */ int theta @ "MY_ZEROS"; /* OK */ int phi @ "MY_INITED" = 4711; /* OK */ void f(void) @ "MY_FUNCTIONS"; void g(void) @ "MY_FUNCTIONS" { } #pragma location="MY_FUNCTIONS" void h(void); Да, забыл добавить - это дока для AVR, но, я думаю, для ARM всё будет очень похожее.
  11. Что-то специфическая конфетка получилась. ))) Не под изначальную задачу. Я, конечно, не большой специалист в теории языка Си, но зачем выходной результат вычислений функции (байт четности) передавать ей вначале, как аргумент? Туда что писать, ноль? Изначально задача была взять байт 0...0х7F и установить в нём старший бит таким образом, чтобы количество единиц в байте было чётным. Предыдущая "конфетка" - самое то. А вобще, была когда-то такая микросхема, 74LS280, которая это сама делала. Вот её и пришлось программно эмулировать. :)) P.S. нашёл даже её функциональную диаграму:
  12. Тогда уж, для универсальности и кросс-платформенности, придётся какие-нибудь ifdef'ы дописать, сколько бит в байте (7 или 8), и куда совать бит четности, на позицию 7-го бита, или в отдельный байт. Чтоб выполнялось: Тогда конфетка точно будет. 🙂
  13. Да, это была просто перестраховка, в начале опытов. На самом деле входные символы используют только первую половину ASCII-кодов, так что седьмой (старший) бит теоретически на входе должен быть всегда 0. А на выходе должен дополнять байт до чётного количества битов. Алгоритм уже опробован на реальном железе (старые системы ЧПУ типа FANUC-6, FANUC-0mc) и показал полную работоспособность! )) Поэтому я эту команду обнуления убрал, как ненужную.
  14. Конкретно в том месте, компилятор просто решил использовать R16 как ctemp и R17 как cin. )) Ну, для понятия алгоритма (для, так сказать, визуализации) - да, корректней было бы написать сложение. Переписал. Это у же в кодах, по факту, будет SUBI. )) 398 char cSetParity (char cin) \ cSetParity: 399 { 400 char ctemp; 401 ctemp = cin; \ 00000000 2F10 MOV R17, R16 402 ctemp += cin; \ 00000002 0F10 ADD R17, R16 403 ctemp ^= cin; \ 00000004 2710 EOR R17, R16 404 ctemp &= 0xAA; \ 00000006 7A1A ANDI R17, 0xAA 405 ctemp += 0x66; \ 00000008 591A SUBI R17, 154 406 ctemp &= 0x88; \ 0000000A 7818 ANDI R17, 0x88 407 ctemp += 0x78; \ 0000000C 5818 SUBI R17, 136 408 ctemp &= 0x80; \ 0000000E 7810 ANDI R17, 0x80 409 cin |= ctemp; \ 00000010 2B01 OR R16, R17 410 return cin; \ 00000012 9508 RET 411 }
  15. Добрый день! Проверил. Не знаю как, но тоже работает. )) Компилятор, увидев сложение самое с собой ("ADD R17,R16"), вставил "LSL R16" 🙂 Инструкция SWAP в ассемблерах мне встречалась часто, но вот чтобы её использовать в Си для AVR, приходится подключать и применять intrinsic-функции, что привязано к конкретному железу и компилятору, т.е. неуниверсально. Потому без SWAP, конечно же, будет корректнее, на чистом Си: char cSetParity (char cin) { char ctemp; ctemp = cin; ctemp += cin; ctemp ^= cin; ctemp &= 0xAA; ctemp -= 0x9A; ctemp &= 0x88; ctemp -= 0x88; ctemp &= 0x80; cin |= ctemp; return cin; } Как говорится, "Ну вот, теперь можно в рамочку, и на стену". )) Спасибо!
  16. Это выглядит элегантнее на Си, а вот код будет раздут (считывается весь порт, потом в отдельный регистр пишется единичный бит, потом эта маска накладывается по XOR на содержимое порта и пр.) Старые Меги тогглить выводами не умеют. :))
  17. :-)) Спасибо! Ну, что тут скажешь. Поторопился. Посыпаю голову пеплом. Как всегда, компиллятор оказался не при чём, "дело было не в бобине..". При получении грамотных команд, компилятор выдал то, что хотелось. Причём, результат (генерируемый код) не меняется от настроек и уровня оптимизации. Теперь никакого инлайн-ассемблера не потребуется, и костылей к нему тоже. 377 char cSetParity (char cin) \ cSetParity: 378 { 379 char ctemp; 380 cin &= 0x7F; // сбросить 7-ой бит чётности в 0 \ 00000000 770F ANDI R16, 0x7F 381 ctemp = cin; \ 00000002 2F10 MOV R17, R16 382 ctemp = __swap_nibbles(ctemp); \ 00000004 9512 SWAP R17 383 ctemp ^= cin; \ 00000006 2710 EOR R17, R16 384 ctemp &= 0xC3; \ 00000008 7C13 ANDI R17, 0xC3 385 ctemp += 0x41; \ 0000000A 5B1F SUBI R17, 191 386 ctemp |= 0x7C; \ 0000000C 671C ORI R17, 0x7C 387 ctemp += 0x02; \ 0000000E 5F1E SUBI R17, 254 388 ctemp &= 0x80; \ 00000010 7810 ANDI R17, 0x80 389 cin |= ctemp; \ 00000012 2B01 OR R16, R17 390 return cin; \ 00000014 9508 RET 391 } Спасибо большое всем за алгоритмы и подсказки!
  18. Понятно. Раз никак, значит, никак. )) Я попытался переписать асемблер на Си. Все по алгоритму выше. точь в точь. Вместо R17 добавить локальный "ctemp". Но IAR почему-то зачудил. При оптимизации вобще все выкинул, кроме andi 0x7F. Если оптимизацию отключить совсем, получается почти хорошо: \ cSetParity: 380 { 381 char ctemp; 382 cin &= 0x7F; // сбросить 7-ой бит чётности в 0 \ 00000000 770F ANDI R16, 0x7F 383 ctemp = cin; \ 00000002 2F10 MOV R17, R16 384 __swap_nibbles(ctemp); \ 00000004 2F21 MOV R18, R17 \ 00000006 9522 SWAP R18 385 ctemp ^= cin; \ 00000008 2710 EOR R17, R16 386 ctemp &= 0xC3; \ 0000000A 7C13 ANDI R17, 0xC3 387 ctemp += 0x41; \ 0000000C 5B1F SUBI R17, 191 388 ctemp |= 0x7C; \ 0000000E 671C ORI R17, 0x7C 389 ctemp += 0x02; \ 00000010 5F1E SUBI R17, 254 390 ctemp &= 0x80; \ 00000012 7810 ANDI R17, 0x80 391 cin |= ctemp; \ 00000014 2B01 OR R16, R17 392 return cin; \ 00000016 9508 RET 393 } Почему "почти"? См. свап ниблов. Откуда-то вылез R18, который после нигде не фигурирует. Играясь "оптимизЭйшын левелами", я добился нужного результата в листинге, но меня это не устраивает. Когда результат зависит от настроения конкретного релиза компилятора. Так что останется инлайн ассемблер. Вопрос, к чему все мои извраты, ради каких-то 5 тактов? Просто это используется с большой скоростью, для передачи данных. Для массива 1 мегабайт, 5 тактов на 1 байт дадут общий выигрыш 5 миллионов тактов. Переходить на GCC... не уверен, что оно того стОит. Уж больно много лет я сижу в IAR. Да и оптимизирует он код по размеру просто чудовищно эффективно. А у меня часто быват проектики для самых мелких камешков, не влезло - следующий чип, а его или нет, или рублей на 50 дороже. 1000 изделий сразу тянут плюсом 50 тыщ рублей, на ровном месте, и пошло, поехало... ((
  19. Спасибо! )) Ну, я как бы в курсе. Потому и написАл про "костыль", из-за которого функция якобы возвращает 2 байта. Из которых нужен один, а второй просто указывает компилятору, что где-то внутри функции он испорчен. Если есть цивилизованый способ как-то "обволятилить" R17, то подскажите? ))
  20. В общем, погонял я в симуляторе этот алгоритм: #pragma inline = forced unsigned int cSetParityBitNew (char cin) { // в R16 - исходный байт asm (" ANDI R16,0x7F \n" // сбросить 7-ой бит чётности в 0 " MOV R17,R16 \n" " SWAP R17 \n" " EOR R17,R16 \n" " ANDI R17,0xC3 \n" " SUBI R17,0xBF \n" " ORI R17,0x7C \n" " SUBI R17,0xFE \n" " ANDI R17,0x80 \n" " OR R16,R17 \n"); return (unsigned int) cin; // возврат R16 с результатом (R17...?) } Работает. 10 тактов, против изначально моих 15-ти. Логика мне непонятна, но считает этот Шайтан-алгоритм всё верно. Спасибо за подсказку! :-))) Теперь вопрос, как сказать компилятору, что в моей функции портится регистр R17? Я прилепил костыль, на сколько хватило моих познаний и фантазии, попрошу сильно не смеяться. Обозначил в прототипе возврат 16-ти битного целого (а это значит R17:R16). Надеюсь, так IAR AVR поймёт, что значение R17 поменялось. Э не-е-ет, так не пойдёт. Иначе придётся распрощаться с оптимизацией IAR! Много лет назад я эти грабли уже проходил, "Странно, почему, когда включаешь оптимизацию, то программа перестаёт нормально работать?" Компилятор пасёт состояния всех регистров и переменных. Если он когда-то в R17 положил ноль, и больше его не трогал, то когда в следующий раз ему понадобится ноль в каком-нибудь порту, то он его с R17 и дёрнет. А там уже кака.
  21. Можно. 8-ми битный индекс просто помещать в младший регистр указателя. Но как сказать компилятору, что регистр Z портится в моей функции? Он же ж, гат, за всем следит и всё оптимизирует. ))) Можно выбрать регистровую пару, скажем, R10:R9, и туда сохранять ZH:ZL, после восстанавливать. Тогда выигрыш потеряется. Хорошо, но портятся 2 регистра, R17 и R18. Хм... Очень лаконично. Спасибо! Портится всего один регистр R17. Какой хитрый алгоритм, надо будет попробовать. ))
  22. Да, "High" "Speed". Я вот как раз и думал, что наверняка есть какой-то алгоритм со свапом в байте... Но в результате, то на то и получается. Видимо, теоретически достижимый предел (4+2=6 тактов), это использовать табличный метод, причем пожертвовав ОЗУ (из флеша дольше выковыривать) 355 PORTB = cCrc8Table [PINA]; \ 00000000 B100 IN R16, 0x00 \ 00000002 E0F0 LDI R31, 0 \ 00000004 2FE0 MOV R30, R16 \ 00000006 .... SUBI R30, LOW((-(cCrc8Table) & 0xFFFF)) \ 00000008 .... SBCI R31, (-(cCrc8Table) & 0xFFFF) >> 8 \ 0000000A 8100 LD R16, Z \ 0000000C B905 OUT 0x05, R16
  23. 334 char isEven(char inbyte) \ isEven: 335 { 336 inbyte ^= inbyte << 4; \ 00000000 2F10 MOV R17, R16 \ 00000002 9512 SWAP R17 \ 00000004 7F10 ANDI R17, 0xF0 \ 00000006 2701 EOR R16, R17 337 inbyte ^= inbyte << 2; \ 00000008 2F10 MOV R17, R16 \ 0000000A 0F11 LSL R17 \ 0000000C 0F11 LSL R17 \ 0000000E 2701 EOR R16, R17 338 inbyte ^= inbyte << 1; 339 340 return inbyte >> 7 ^ 1; \ 00000010 FB07 BST R16, 7 \ 00000012 E010 LDI R17, 0 \ 00000014 F910 BLD R17, 0 \ 00000016 FB06 BST R16, 6 \ 00000018 E020 LDI R18, 0 \ 0000001A F920 BLD R18, 0 \ 0000001C 2712 EOR R17, R18 \ 0000001E E001 LDI R16, 1 \ 00000020 2701 EOR R16, R17 \ 00000022 9508 RET 341 } Спасибо! На Си смотрится короче. Результат получается длиннее и дольше :))
  24. С размером кода проблем нет, камень на 128к или 256к флеш. Просто если таблица, то используется больше регистров. Сначала надо сохранить регистры указателя, после загрузить в них начало таблицы, вычислить смещение (прибавить входной байт), получить ответ, восстановить испорченные регистры... А тут портится только регистр флагов. А я подсел. :)) Аккурат, с 1997 года. Нравится то, что разрабатывалась она "в обратную", от Си к ассемблеру. Многое нравится, а вот паритета нет. В древнем MCS-51 в регистре флагов (PSW) есть бит четности, а тут украли... :((
  25. Доброго дня! Возникла необходимость подсчитать паритет битов в байте, четность. Как в последовательном порту. Но там это делается само, а тут надо, чтобы старший 7-ой бит дополнял весть байт до четности. Т.е. 0х21 -> 0x21, 0x20 -> 0xA0 (в битах: 0010.0001 -> 0010.0001, а 0010.0000 -> 1010.0000). Пока реализовал ассемблерную вставку как инлайн-функцию, где побитно перебираю все 7 бит в байте. Компилятор IAR AVR. #pragma inline = forced char cSetParityBit (char cin) { // в R16 - исходный байт asm (" andi R16, 0x7F \n" // сбросить 7-ой бит чётности в 0 " sbrc R16,6 \n" " subi R16,128 \n" " sbrc R16,5 \n" " subi R16,128 \n" " sbrc R16,4 \n" " subi R16,128 \n" " sbrc R16,3 \n" " subi R16,128 \n" " sbrc R16,2 \n" " subi R16,128 \n" " sbrc R16,1 \n" " subi R16,128 \n" " sbrc R16,0 \n" " subi R16,128 \n"); return cin; // возврат R16 с результатом } Всё работает, но на вид реализация выглядит слишком "в лоб", как-то неспортивно. :)) Можно, конечно, ещё организовать таблицу во флеш, забить 127 паттернов с уже готовой чётностью. Но что-то тоже неэстетично. Может есть какие другие, более лаконичные алгоритмы для чётности в байте?
×
×
  • Создать...