How to implement high and low bit exchange in embedded programming?

Follow the + star public account and never miss exciting content

e45d3fd23ee88a63735ed3be30221ac8.gif

Transfer from | Technology makes dreams bigger

In the recent agreement, I encountered the problem of high-low byte conversion, so I was lazy to check it online. When I encountered a similar problem, I also knew a new name, called butterfly exchange.

The protocol requires that the low bit of the byte is on the left and the high bit is on the right. Each byte is converted and its high and low bits are exchanged one by one. For example, 11010001after 0->7,1->6,2->5,3->4the corresponding bits are exchanged, it becomes 10001011.

Here you need to have knowledge of bit operations. Please refer to  What are the tricks of bit operations? (Source code attached)

Here we take the conversion of high and low bits of 8-bit data as an example:

1#include <stdio.h>
 2
 3unsigned char highAndLowShiftHEX(unsigned char data);
 4void printBin(int n);
 5
 6int main () {
 7
 8    highAndLowShiftHEX(209);
 9    return 0;
10}
11
12unsigned char highAndLowShiftHEX(unsigned char data)  
13{  
14   unsigned char i;  
15   unsigned char tmp=0x00;  
16   for(i=0;i<8;i++)  
17   {  
18       tmp=((data>>i)&0x01)|tmp;  
19       //printBin(tmp);
20       if(i<7)  
21           tmp=tmp<<1;  
22   }  
23   printf("\nafter shift data:");  
24   printBin(tmp);
25   return tmp;    
26}
27
28//由于二进制直观,故写了一个打印二进制的函数
29void printBin(int n)
30{
31    int len = sizeof(n)*8;//总位数。
32    int i;
33    if(i == 0)
34    {
35         printf("0");
36         return;
37    }
38    for(i = len-1; i >= 0; i --)//略去高位0.
39    {
40        if(n&(1<<i)) break;
41    }
42
43    for(;i>=0; i --)
44        printf("%d", (n&(1<<i)) != 0);
45}

If you are familiar with bit operations, the above code is relatively simple to implement. In embedded development, this type of problem is usually implemented using the butterfly exchange method and the look-up table method.

High-level implementation?

The lookup table method is to store some values ​​in the memory and look up the table when calculation is needed, but this method will occupy additional storage space.

So here we mainly introduce the butterfly exchange method. We take 8-bit data conversion as an example.

  • Assume the original sequence is:1 2 3 4 5 6 7 8

  • The target sequence is:8 7 6 5 4 3 2 1

Then the flow chart is as follows:

8dd840d631854ce589bb4a0e2d8248c1.png

This completes the reverse order conversion of the entire bit. Taking the same 11010001example, the following is the specific implementation code:

1#include <stdio.h>
 2
 3unsigned char highAndLowShiftHEX(unsigned char );
 4void printBin(int );
 5
 6int main () {
 7
 8    highAndLowShiftHEX(209);
 9    return 0;
10}
11
12unsigned char highAndLowShiftHEX(unsigned char data)  
13{  
14   data=(data<<4)|(data>>4);  
15   data=((data<<2)&0xcc)|((data>>2)&0x33);  
16   data=((data<<1)&0xaa)|((data>>1)&0x55);  
17   printf("  after shift data=%x \n",data);  
18   printBin(data);
19   return data;  
20}
21
22//由于二进制直观,故写了一个打印二进制的函数
23void printBin(int n)
24{
25    int len = sizeof(n)*8;//总位数。
26    int i;
27    if(i == 0)
28    {
29         printf("0");
30         return;
31    }
32    for(i = len-1; i >= 0; i --)//略去高位0.
33    {
34        if(n&(1<<i)) break;
35    }
36
37    for(;i>=0; i --)
38        printf("%d", (n&(1<<i)) != 0);
39}

Swapping the high and low bits of bytes is not a very common problem. When encountering this problem, careful analysis and proficiency in C language bit operations are required to solve this type of problem.

Expand

Then we extend it to the high and low bit conversion of 16-bit halfword data.

In fact, the principle is the same as that of 8-bit, using a simple shift method to convert the high and low bits of the data. The code is relatively simple if you are familiar with bit operations.

The following is the specific implementation of this idea.

1#include <stdio.h>
 2
 3void expandPrintBin(int val2);
 4unsigned short HighAndLowSwitchHEX(unsigned short data);
 5
 6int main () {
 7
 8    HighAndLowSwitchHEX(38491);
 9    return 0;
10}
11
12
13//由于二进制直观,故写了一个扩展的打印二进制的函数
14void expandPrintBin(int val2)
15{
16    int i,k;
17    unsigned char *p = (unsigned char*)&val2 + 3; //从低位到高位,低端字节计算机
18    for( k = 0; k <= 3; k++)
19    {
20        int val2 = *(p-k);
21        for (i = 7; i >= 0; i--)
22        {
23            if(val2 & (1 << i))
24                printf("1");
25            else
26                printf("0");
27        }
28        printf(" ");
29    }
30}
31unsigned short HighAndLowSwitchHEX(unsigned short data)
32{
33    unsigned char i = 0;
34    unsigned short temp = 0x0000;
35
36    for(i = 0; i < 16; i++)
37    {
38        temp = ((data >> i) & 0x0001) | temp;
39        if(i < 15)
40        {
41            temp = temp << 1;
42        }
43    }
44    printf("temp:%x\n\n",temp);
45    expandPrintBin(temp);
46    return temp;
47}

For the same so-called butterfly exchange method, I quoted the example of byte exchange method. We can calculate it:

  • Assume the original sequence is:a b c d e f g h i j k l m n o p

  • The target sequence is:p o n m l k j i h g f e d c b a

Then the flow chart is as follows:

c02fdba9cbb62835124d42d96f3510e2.png

This completes the reverse order conversion of the entire bit and completes the expansion of the algorithm. Taking as 1001011001011011an example, the following is the specific implementation code:

1#include <stdio.h>
 2
 3unsigned short highAndLowShiftHEX(unsigned short data);
 4void expandPrintBin(int val2);
 5
 6int main () {
 7
 8    highAndLowShiftHEX(38491);
 9    return 0;
10}
11
12unsigned short highAndLowShiftHEX(unsigned short data)
13{
14  data = (data << 8) | (data >> 8);   //0101101110010110
15  data = ((data << 4) & 0xF0FF) | ((data >> 4) & 0xFF0F); //1011010101101001
16  data = ((data << 2) & 0xCCCC) | ((data >> 2) & 0x3333); //1110010110010110
17  data = ((data << 1) & 0xAAAA) | ((data >>1 ) & 0x5555); //1101101001101001
18  printf("  after shift data=%x \n",data);  
19  expandPrintBin(data);
20  return data;  
21}
22
23//由于二进制直观,故写了一个扩展的打印二进制的函数
24void expandPrintBin(int val2)
25{
26    int i,k;
27    unsigned char *p = (unsigned char*)&val2 + 3; //从低位到高位,低端字节计算机
28    for( k = 0; k <= 3; k++)
29    {
30        int val2 = *(p-k);
31        for (i = 7; i >= 0; i--)
32        {
33            if(val2 & (1 << i))
34                printf("1");
35            else
36                printf("0");
37        }
38        printf(" ");
39    }
40}

This kind of bit swapping problem is often encountered in embedded development. It is important to be familiar with bit operations and debugging methods. If you skillfully use the shift operation of C language, you can quickly solve such problems.

Summarize

The key to the above problem is the flexible and wonderful use of bit operations. Secondly, I wrote two functions for printing binary, which are convenient to use. The code can be used directly, and debugging is not easy. Welcome to like it, watch it, and forward it as well. See you in the next issue. !

------------ END ------------



●专栏《嵌入式工具》●专栏《嵌入式开发》●专栏《Keil教程》●嵌入式专栏精选教程


关注公众号回复“加群”按规则加入技术交流群,回复“1024”查看更多内容。











点击“阅读原文”查看更多分享。

Guess you like

Origin blog.csdn.net/ybhuangfugui/article/details/132550732