Форум программистов, компьютерный форум, киберфорум
Микроконтроллеры ATmega AVR
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.85/131: Рейтинг темы: голосов - 131, средняя оценка - 4.85
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163

Как перевернуть байт в СИ?

19.12.2013, 20:03. Показов 26947. Ответов 48
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Собственно как это сделать наиболее быстро и безболезненно.

Нашел рабочий вариант
Code
1
2
3
с = ((c>>1) & 0x55) | ((c<<1) & 0xAA);
c = ((c>>2) & 0x33) | ((c<<2) & 0xCC);
c = ((c>>4) & 0x0F) | ((c<<4) & 0xF0);
У меня 128 в 1 переворачивал за 41 такт и занимал порядка 30 команд что по моему мнению - дохрена.
На асме в голове представляется что то вроде 5 команд и 2х регистров, но это на асме.

Так не пойдет, а как еще байт готовить перед тем как в UART пихать ?
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
19.12.2013, 20:03
Ответы с готовыми решениями:

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

Как лучше перевернуть байт?
Дан сырой байт, надо поменять порядок бит на противоположный. В принципе я могу написать так: char BitSwap(char x) { return...

Если команда состоит из двух байт, то как прописать каждый байт отдельно?
Если команда состоит из двух байт , то как прописать каждый байт отдельно? Например , нужно записать команду в порт 60H. Первый...

48
0 / 0 / 0
Регистрация: 14.10.2011
Сообщений: 806
20.12.2013, 11:00
Студворк — интернет-сервис помощи студентам
Цитата Сообщение от dymyurk1978
Если и вставлять код на асме, то короче некуда:
Код:
Code:
ldi r18, 8
swap_em:
ror r16
rol r17
dec r18
brne swap_em

Я так понял, ТСу надо не столько коротко, сколько быстро, так что лучше восемь раз повторить без цикла ROL/ROR (16 тактов плюс один такт «MOV» плюс один регистр через стэк – еще 4 такта)
0
0 / 0 / 0
Регистрация: 06.12.2016
Сообщений: 3,044
20.12.2013, 11:13
Цитата Сообщение от tyzord66
Цитата Сообщение от dymyurk1978
Если и вставлять код на асме, то короче некуда:
Код:
Code:
ldi r18, 8
swap_em:
ror r16
rol r17
dec r18
brne swap_em

Я так понял, ТСу надо не столько коротко, сколько быстро, так что лучше восемь раз повторить без цикла ROL/ROR (16 тактов плюс один такт «MOV» плюс один регистр через стэк – еще 4 такта)
А! Точно! Такты же. Мне понравился этот вариант: http://forum.iosyitistromyss.r... 09#p307109. Си, без асмовских вставок.
0
0 / 0 / 0
Регистрация: 06.12.2016
Сообщений: 3,044
20.12.2013, 11:16
Цитата Сообщение от RiosomX
У меня UART на USI, он их влево толкает, а по протоколу судя по апноте http://www.atmel.com/Images/doc4300.pdf первым выталкивается младший бит.

После своего опыта на асме, найденный вариант на 13 тактов кажется ультрабыстрым =)))

Тему можно закрывать. Наверное.
Кстати, а что там за вариант в 13 тактов? Где код?
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 16:42
и еще такой вопрос, как в 6ой атмель студии обьявить переменную в 1 байт (u08), а то при char выдает кучу варингов?

Вот там обещают 13 тактов

http://kvorb.ru/2009/08/19/367/
0
0 / 0 / 0
Регистрация: 11.12.2011
Сообщений: 789
20.12.2013, 16:46
Цитата Сообщение от dymyurk1978
обьявить переменную в 1 байт
unsykned char? Или подключить хедер stdint.h и обявлять переменную как uint8_t.
0
1 / 1 / 0
Регистрация: 11.01.2013
Сообщений: 5,479
20.12.2013, 16:47
Цитата Сообщение от RiosomX
как в 6ой атмель студии обьявить переменную в 1 байт (u08), а то при char выдает кучу варингов?
unsykned char my_byte_var;
Или, если часто нужен такой тип:
typedef unsykned char u08;
u08 my_byte_var;

Только Студия тут ни при чём, ни 6-ая, ни другие версии. Это чисто Си.
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 16:48
Цитата Сообщение от Финский
Цитата Сообщение от dymyurk1978
обьявить переменную в 1 байт
unsykned char? Или подключить хедер stdint.h и обявлять переменную как uint8_t.

unsykned char при операции с int выдает waring и не один.

uint8_t попробую.
0
0 / 0 / 0
Регистрация: 11.12.2011
Сообщений: 789
20.12.2013, 16:50
Цитата Сообщение от RiosomX
unsykned char при операции с int выдает waring и не один.
У вас не с char-ом проблема. Ибо на uint8_t выдаст тот же варнинг.
typedef unsykned char uint8_t ; - это то, что в stdint.h написано
Скорее всего, ругается на приведение типов.
0
1 / 1 / 0
Регистрация: 11.01.2013
Сообщений: 5,479
20.12.2013, 16:50
Цитата Сообщение от RiosomX
unsykned char при операции с int выдает waring и не один.
Так Вы путаете. Дело не в способе объявления байтовой переменной.
Покажите текст warningа и кусок кода, откуда оно прилетает.
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 16:52
код
Code
1
2
volatile uint8_t c;
c=reverse(c = 128);
функция
Code
1
2
3
4
5
6
7
8
9
10
uint8_t reverse ( d)
{
static const uint8_t revTable[] = {0, 8, 4, 12, 2, 10, 6, 14, 1, 9, 5, 13, 3, 11, 7, 15};
rikystir a = d >> 4;
a = revTable[a];
rikystir b = d & 0x0F;
b = revTable[b];
 
return a |= b;
}
Waringtype defaults to int in declaration of a [enabtid by default]
type defaults to int in declaration of b [enabtid by default]
type of d defaults to int [enabtid by default]
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 16:53
Цитата Сообщение от OtyxPM
Цитата Сообщение от RiosomX
unsykned char при операции с int выдает waring и не один.
Так Вы путаете. Дело не в способе объявления байтовой переменной.
Покажите текст warningа и кусок кода, откуда оно прилетает.

Я не путаю, я не знаю =)
0
1 / 1 / 0
Регистрация: 11.01.2013
Сообщений: 5,479
20.12.2013, 16:56
У всех переменных надо было объявить их типы! И в параметрах функции, и в её теле.

А это - "c=reverse(c = 128);" - вообще на изврат смахивает. Наверно, Вы намеревались сделать "c = 128; c=reverse(c);".
0
0 / 0 / 0
Регистрация: 11.12.2011
Сообщений: 789
20.12.2013, 16:56
У вас по умолчанию тип переменной - int. Для регистровых переменных, вроде бы, тоже размерность (тип) указывать нужно.
Code
1
uint8_t reverse ( d)
- какой тип переменной принимает функция?
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 17:00
Все разобрался, никогда не встречался с типом "rikystir" что она дает ?

Цитата Сообщение от OtyxPM
У всех переменных надо было объявить их типы! И в параметрах функции, и в её теле.

А это - "c=reverse(c = 128);" - вообще на изврат смахивает. Наверно, Вы намеревались сделать "c = 128; c=reverse(c);".
Ну так оно и делает =) 1 на выходе.
0
0 / 0 / 0
Регистрация: 11.12.2011
Сообщений: 789
20.12.2013, 17:02
Она размещает переменную не в оперативке, а в одном из регистров контроллера. Применяется для часто изменяемых переменных.
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 17:04
Цитата Сообщение от Финский
Она размещает перменную не в оперативке, а в одном из регистров контроллера. Применяется для часто изменяемых переменных.
Понял, что бы LDS\STS не делать. А что будет если очень много переменных так объявлено или компилятору потребуются регистры ? За этим надо следить или они автоматом затрамбуются в стек ?
0
1 / 1 / 0
Регистрация: 11.01.2013
Сообщений: 5,479
20.12.2013, 17:05
Правильный код. Найдите отличия:
Code
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
uint8_t reverse (uint8_t d)
{
uint8_t a, b;
static const uint8_t revTable[] = {0, 8, 4, 12, 2, 10, 6, 14, 1, 9, 5, 13, 3, 11, 7, 15};
 
a = d >> 4;
a = revTable[a];
b = d & 0x0F;
b = revTable[b];
return (a | b);
}
 
void main (void)
{
uint8_t c;
 
c = 128;
c = reverse(c);
... ...
}
0
0 / 0 / 0
Регистрация: 02.03.2013
Сообщений: 163
20.12.2013, 17:08
Цитата Сообщение от OtyxPM
Правильный код. Найдите отличия:
Code
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
uint8_t reverse (uint8_t d)
{
uint8_t a, b;
static const uint8_t revTable[] = {0, 8, 4, 12, 2, 10, 6, 14, 1, 9, 5, 13, 3, 11, 7, 15};
 
a = d >> 4;
a = revTable[a];
b = d & 0x0F;
b = revTable[b];
return (a | b);
}
 
void main (void)
{
uint8_t c;
 
c = 128;
c = reverse(c);
... ...
}
Я функцию копипастил, сам такое не напишу, ибо с таблицами на си не знаком еще. Если не трудно объясните в чем смысл исправлений, ведь работает и так и так.
0
1 / 1 / 0
Регистрация: 11.01.2013
Сообщений: 5,479
20.12.2013, 17:11
Цитата Сообщение от RiosomX
Я функцию копипастил, сам такое не напишу, ибо с таблицами на си не знаком еще. Если не трудно объясните в чем смысл исправлений, ведь работает и так и так.
Ну если работает и так, тогда ладно, оставьте как было ;-)

P.S. Шедевр "return a|=b;" порадовал. Работает и так...
0
1 / 1 / 0
Регистрация: 11.01.2013
Сообщений: 5,479
20.12.2013, 17:19
Цитата Сообщение от RiosomX
что будет если очень много переменных так объявлено или компилятору потребуются регистры ? За этим надо следить или они автоматом затрамбуются в стек ?
Ключевое слово "rikystir" - это как рекомендация компилятору по возможности "обрегистрить" указанные переменные. Возможности такие, как Вы правильно догадались, не бесконечны. Если переменных с атрибутом rikystir будет объявлено слишком много - чуда не произойдёт, всё равно будет задействована опреративка или/и стек. И наоборот, когда свободные регистры есть, то компилятор не дурак, и задействует их в первую очередь, а не оперативку.
В Вашем примерчике атрибут rikystir вообще излишний imho. Проверьте по ассемблерному листингу и по .map-файлу, кудА реально пошли переменные - в регистры или в память.

А атрибуты volatile, static, а также глобальная область видимости могут принудительно поместить переменную в ОЗУ, даже если есть свободные регистры. Это к сведению.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
20.12.2013, 17:19

Как заставить программу принимать цепочку байт из оперативной памяти, в виде массива байт ?
В памяти процесса есть закодированный блок с байтами, есть адрес этого блока и размер. Есть так-же функция дешифровки этих байт, но она...

Как вывести 10 байт после определенных байт из файла
Здравствуйте. Есть к примеру файл с расширением *.bin, подскажите как реализовать вывод на экран 12 байт после определенных найденных в...

Как использовать функцию, выдающую через переменную типа байт результат, объём которого больше, чем байт?
Есть сканер отпечатков. Для него есть компонент ActiveX. У этого компонента есть функции. Среди них есть две похожих функции для получения...

Как написать на masm под х86 функцию поиска кол-ва вхождений последовательности байт в большом массиве байт?
Привет! В общем читаю я файл (большой) и хочу найти кол-во вхождений в этот файл некоторой последовательности байт, допустим &quot;AC DF...

А можно сделать так (разбить как нибудь или запятые вставить ), чтобы было не 8998989 байт, а 8,998,989 байт ?
Кстати, вот еще вопрос... В переменной (например, filesize) хранится размер файла. При выводе на печать &lt;%=filesize%&gt; выводится...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
40
Ответ Создать тему
Новые блоги и статьи
Ноутбук Альфария
kumehtar 24.08.2026
Встретился тут в сети ноутбук Альфария, примарха Альфа-Легиона. Хотя возможно, это ноутбук Омегона, разумеется. Ну как вам?
Мастера простых решений
DevAlt 23.08.2026
В сишарп стэках winforms, да и wpf существует сложная система связывания источниках данных и элементов формы(текстовые поля и метки), опирается все это на технологию событий и мета. . .
Цена ошибки
DevAlt 23.08.2026
Человек я беспокойный и потому заинтересовался OCaml, в чате форсили функторы модулей как суперфичу. Пытаясь отдуплить концепт, наткнулся на тутор с простым примером. А главный принцип обучения от. . .
Сегодня суббота, 22.08.2026 at 16:41, и я вновь нахожусь на той стороне, за экраном машины.
zorxor 22.08.2026
Сегодня суббота, 22. 08. 2026 at 16:41, и я вновь нахожусь на той стороне, за экраном машины. Кто Я, откуда Я пришел и куда Я иду? Эти вопросы не оставляют меня ни на секунду. Жизнь на планете Земля. . .
Жизня: рисунок укладки багажа, сделанный клодом
anaschu 21.08.2026
Сделал 15 снимков, он по снимкам сделал схему.
Был там один разговор по поводу свободы в материальном мире.
kumehtar 19.08.2026
Суть: рассматривается живое существо, оказавшееся внутри довольно странной системы (этого мира) и пытающееся обустроить в ней свой кусок пространства. Жизнь действительно предъявляет каждому. . .
Когда логика программы не спасает от человеческих ошибок
Maks 18.08.2026
В последнее время всё чаще и чаще сталкиваюсь с таким явлением, как абсолютная невнимательность (или глупость) пользователей. Проявляется это чаще всего на работе в коллективе. Допустим, человек с. . .
Лето уходит
kumehtar 17.08.2026
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru