Давненько мы не говнокодили :(
- Войдите на сайт для отправки комментариев
Пнд, 10/05/2021 - 12:56
Берём Uno или Нано (или что угодно на 328P), подключаем светодиод на 9-ый пин и любуемся :-)
// // Uno / Nano и всё, что на ATmega328P // Нужен светодиод на 9-ом пине // #define _ (&ADC-42) void setup(void) { digitalWrite(9, *_=(_[50]=(_[46]=53<<6)<<1)>>10); } void loop(void) {}
Или вот ещё, тоже самое, но чуть покороче и поговнистее:
// // Uno / Nano и всё, что на ATmega328P // Нужен светодиод на 9-ом пине // #define _ (&ADC+4) void setup(void) { pinMode(9, _[4]=(*_=3392)*2); } void loop(void) {}
И не лень же вам :) &ADC+4+4 будет TCCR1A :)
И не лень же вам :) &ADC+4+4 будет TCCR1A :)
Да что Вы!? Не может быть!
На самом деле - это секретное, недокументированное значение второго параметра pinMode. которое вгоняет пин в секретный, недокументированный режим мигания! Во как!
А не то, что тут некоторые ... инсинуации ... панимаешь!
а так можно было )))
Нет, конечно!
На самом деле ваши загадки интересные, в процессе отгадки обязательно узнаётся что-то новое, так что давайте истчо :)
На самом деле ваши загадки интересные, в процессе отгадки обязательно узнаётся что-то новое, так что давайте истчо :)
присоединюсь, по ощущениям будто "кобылу на невольничьем рынке выбираешь" )))
Нет, у меня не такие ощущения :)
Женя! Прости старого пьяницу, но мне захотелось спросить тебя, вместо анализа стандарта. Почему xxx[4] прибавило 4, а не 8, когда xxx указатель на uint16_t? Пусть это будет считаться пробелом в моей эрудиции ;)))).
Ну, вот же второй скетч
_ = (&ADC+4) = 0x78 + 8 = 0x80 (TCCR1A)
Далее само выражение
_[4]=(*_=3392)*2
Первой выполняется жёлтая часть. Здесь по адресу 0x80 укладывается значение 3392 (0x0D40). При этом младший байт попадает в TCCR1A (0x80), а старший байт - в TCCR1B (0x81). Результат присваивания - как всегда то, что присвоилось - 3392.
В объемлющей части, это число умножается на 2 и попадает по адресу 0x80 + 8 = 0x88, а это 16-битный регистр OCR1A.
Вот и весь фокус.
Кстати, на 2 можно было и не умножать - было бы ещё короче. Частота вдвое больше - и нормально, она ещё вполне прилично мигает - не слишком часто.
В качестве извинений за то, что никак не мог совместить 4, 8 и 40° я "приговнокодил" мигание на встроенном диоде. ;))
Пришлось еще макрос и ISR добавить, но так даже поговнистие выглядит! Можно было не делать макрос с указателем на uint8_t, но тогда придется пренебречь искажением соседних регистров, хотя ради говнокода - можно. А прерывание придает значимости! ;))
Для "образности" можно вместо 13 написать LED_BUILTIN.
Граф, вот на самом деле сволочи гуры пудрят новичкам мозг какой-то тарабарщиной и птичьим языком типа digitalWrite и прочими никому непонятными HIGH и LOW.
А способы программировать просто - выдавая команды обычным текстом, почти по русски - скрывают.
Вот например, что понятнее
или простыми словами:
ну, ведь второе намного же понятнее!
Но ни один гура никогда такого новичку не покажет! Конкурентов будущих боятся.
Хотя, казалось бы, чего проще:
Как-нибудь очередной студент прибежит "срочно сдавать" - напишу ему пожалуй вот так, чтобы ему понятнее было. Пусть сдаёт. Доброта - она ведь нам зачтётся.
sbi pinb небось :)
Гура правильно делают, ведь им не хочется быть забитыми лопатой до полусмерти.
Ворота как-то какому-то такому "сдатчику", под обещание, что расскажет как сдал, написал готовый код (на брейнфаке). Так тот, сучка, исчез и так ничего и не рассказал.
sbi pinb небось :)
Ну, макрос-то один. Так что, от строки зависит
Лень опкоды смотреть, а историю эту я помню, не будут они такое сдавать, побоятся.
В объемлющей части, это число умножается на 2 и попадает по адресу 0x80 + 8 = 0x88, а это 16-битный регистр OCR1A.
на вавгаде не сработает видимо, так как OCR1A надо грузить как два восьмибитных
на вавгаде не сработает видимо, так как OCR1A надо грузить как два восьмибитных
Первая строка первого сапщения.
на вавгаде не сработает
На Fugaku - тоже :-(
OCR1A надо грузить как два восьмибитных
На Atmega тоже. И не только OCR1A, а и все 16-битные регистры (TCNT1, ADC и т.п.) - они именно так и грузятся - об этом заботится компилятор.
И все же Гарвардская архитектура не так много простора для говнокода дает, как родная и любимая фон Неймановская! Согласимся?
Как здорово и свободно говнокодится на ПиСюке! Мечта просто!
На Atmega тоже. И не только OCR1A, а и все 16-битные регистры (TCNT1, ADC и т.п.) - они именно так и грузятся - об этом заботится компилятор.
у меня видимо аддон вавгад был кривой, приходилось грузить указывая верхний и нижний регистр прямо
Хотя, казалось бы, чего проще:
Вам с Графом весело, а я дурак-дураком второй час этих "пляшущих человечков" пытаюсь расшифровать...
суровый пустой молчаливый пост :)
Вот это и печально)) Работает!
Пысы. Предидущий пост - мой бок))
ну а чего бы и не работать :)
перед компиляцией макрос разворачивается в 4-байтную функцию, ((void(*)(void))n)(); вызывает её. Функция, скорее всего, ставит/выключает бит в зависимости от < >. Вычислите значения этих четырех байт U-(, <+\ или >+\, 1-), 3+b да посмотрите по таблице опкодов 328p что за инструкции.
Говнокод чистой воды, потому что следующий, кто будет это поддерживать, захочет убить гуру лопатой, в продакшене так делать не стоит, но в качестве развлечения и демонстрации отличия архитектуры от типичной х86 - прикольно и даже в чём-то красиво.
Эти же два примера также отлично демонстрируют возможности си по стрелянию себе в ногу, вон, у мк прямой доступ ко всей памяти, порти что хочешь, всё на твоей ответственности :)
Забавный момент для Евгения Петровича, я избалованный тем самым х86, поначалу тупанул, думаю, какая там нафиг память с нуля, и только потом сообразил, а мля, codeseg-то не там, а отдельно :) Из полезного - узнал как маппинг i/o у 328 сделан, оказывается, в начале адресов перед оперативкой, мило. Ну а второй пример уже не тупил )) Может это вы так тренируете нас на архитектуры? ))
Вычислите значения этих четырех байт U-(, <+\ или >+\, 1-), 3+b
Если это понятно, то
перед компиляцией макрос разворачивается в 4-байтную функцию, ((void(*)(void))n)()
как это работает (массив в прогмем становится функцией) - понять не могу
Прогмем - секция флеша, кода, всё, что хранится в ней - код, его можно вызвать переходом по адресу, и он начнёт выполняться. Когда мы пишем строки F(***), мы на самом деле просто сохраняем данные в кодовый сегмент, просто потому, что он большой, а потом они оттуда читаются. Можете вызвать jmp *("xxx"); и строки как бы исполнятся, смотря какие там опкоды, это, видимо, Евгений Петрович приберёг для следующего примера.
Вот эта конструкция, с войдами :) - это такой сишный трюк, чтобы вызвать на исполнение код по адресу n в прогмем, а там находится соответственно эта строка опкодов, вычисленных перед компиляцией из s+символ.
Вот даже не знаю, верить или нет - мне эту историю рассказал парень - очень скромного/небольшого ранга дипломат. Он клялся, что правда ... Рутинная тусовка в ООН, никаких высоких лиц - обычная каждодневная рутинная встреча чиновником самого мелкого масштаба. Американец (А) наезжает на китайца (К) и тычет ему в нос спутниковые фото на которых видно, что с крейсера Ляонин взлетают самолёты:
К. И что Вас не устраивает? Зона закрыта для судоходства, опасности ни для кого нет.
А. Когда корабль покупался у Украины, Китай гарантировал, что судно будет использоваться как развлекательный центр и казино. Вот копия документа.
К. Оно именно так и используется. Развлекательный центр.
А. А почему же с него взлетают истребители?
К. (не моргнув глазом) Мы так развлекаемся.
вот-вот :)
вот-вот :)
Это как квайн - упражнение для ума.
У меня, к примеру, есть несколько сборников международных математических олимпиад школьников, от 60-х годов и далее. Я их, как пасьянсы, иногда решаю с ручкой и тетрадкой, штоп моск не заржавел! ;)))
Мне-то объяснять не нужно, сам такой же. Хотя чаще всё же стараюсь больше в непрофессиональной области развлекаться, типа как ваш кемпер. Демками в 90е немножко увлекался, можно было писать в регистры vga и трясти мониторы по-разному, воксели, родители нынешних шейдеров были прикольными :)
Если кому окромя меня интересно, что значит
тыц сюда. Интернет великая весчь, жаль будет, если запретят))
Остался последний вопрос "опкоды" - это куда?
http://academy.cba.mit.edu/classes/embedded_programming/doc0856.pdf
http://lyons42.com/AVR/Opcodes/AVRAllOpcodes.html
вот, кому-то пригодилось же :)
http://academy.cba.mit.edu/classes/embedded_programming/doc0856.pdf
http://lyons42.com/AVR/Opcodes/AVRAllOpcodes.html
вот, кому-то пригодилось же :)
(задумчиво, печально) -Ндааа.
Но, тем не менее спасибо, буду знать, что такое существует))
А как без этого писать компилятор, тот же gcc?
http://academy.cba.mit.edu/classes/embedded_programming/doc0856.pdf
http://lyons42.com/AVR/Opcodes/AVRAllOpcodes.html
вот, кому-то пригодилось же :)
неужели кто-то еще пишет в машинных кодах, повеяло далёкими 80 и интел 8080
(задумчиво, печально) -Ндааа.
Но, тем не менее спасибо, буду знать, что такое существует))
На самом деле всё проще. Чтобы пошутить, как пошутил я, вовсе необязательно изучать все коды. Достаточно написать на Си и посмотреть ассемблерный листинг (а AVR Studio он доступен сразу без всяких телодвижений, а в IDE надо дизассемблер запустить)
Красненькое - это оно и есть.
Как видите, разница между кодами только в одном байте: 9A и 98. И разница эта равна 2. А теперь смотрим на разницу в кодах '>' и '<' - тоже 2. Вот макрос единообразно куда надо и преобразует.
а это что значит?
0x05, 5- операнды команды. Точка с запятой - начало комментария. Всё, что после неё - комментарий.