Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to interpret hex number byte array from left shift binary sum?

My android application is receiving an array of data bytes that is sent from a C# application. I need to interpret those bytes.

In C# application, there are 16 check boxes (Bit0 to Bit15) in form and the code shows processing of those checkbox result.

ushort flag = (ushort)(
                (Bit0.Checked ? (1 << 0) : (0)) +
                (Bit1.Checked ? (1 << 1) : (0)) +
                (Bit2.Checked ? (1 << 2) : (0)) +
                (Bit3.Checked ? (1 << 3) : (0)) +
                (Bit4.Checked ? (1 << 4) : (0)) +
                (Bit5.Checked ? (1 << 5) : (0)) +
                (Bit6.Checked ? (1 << 6) : (0)) +
                (Bit7.Checked ? (1 << 7) : (0)) +
                (Bit8.Checked ? (1 << 8) : (0)) +
                (Bit9.Checked ? (1 << 9) : (0)) +
                (Bit10.Checked ? (1 << 10) : (0)) +
                (Bit11.Checked ? (1 << 11) : (0)) +
                (Bit12.Checked ? (1 << 12) : (0)) +
                (Bit13.Checked ? (1 << 13) : (0)) +
                (Bit14.Checked ? (1 << 14) : (0)) +
                (Bit15.Checked ? (1 << 15) : (0)));

flag is passed to the function described below and then it is sent to my Android application.

    public static void setFlag(List<Byte> data, ushort flag)
    {
        for (int i = 0; i < 2; i++)
        {
            int t = flag >> (i * 8);
            data.Add((byte)(t & 0x00FF));
        }
    }

In Android application, the data is received as an array of 4 bytes and then it is converted to decimal

public String bytesToAscii(byte[] data) {
    String str = new String(data);
    return str.trim();
}

// This returns the decimal
Integer.parseInt(bytesToAscii(flag), 16)

Let's say for example, when Bit13 was checked in the C# application; the Andriod app receives an array of 4 bytes which represents hex numbers:

flag[0] = 0x30;
flag[1] = 0x30;
flag[2] = 0x32;
flag[3] = 0x30;

It is converted to 0020 and it is then converted to decimal:

Integer.parseInt(bytesToAscii(flag), 16); // 32

I need to parse 32 to figure out Bit13 was selected. Bit13 is just an example for 32. I need to figure out which one or more Bit (0 to 15) are selected.

like image 489
Sithu Avatar asked Mar 31 '26 08:03

Sithu


1 Answers

To check if a bit is set, you can do a bitwise AND with that bit. Then check if the result is equal to 0. If it isn't, the bit was set.

e.g.

00100110
00000010     // checks the second bit
-------- &
00000010     // result != 0, so the bit was set

A char is unsigned 16 bits, so you could use that to store the result.

0020 is almost right, but the bytes are reversed (00 20, should be 20 00 for Bit13).

byte[] flag = new byte[4];      
flag[0] = 0x30;
flag[1] = 0x30;
flag[2] = 0x32;
flag[3] = 0x30;

// Bytes to char, using the 'oversized' short so the numbers won't be out of range
short b1 = Short.parseShort(new String(new byte[]{flag[0], flag[1]}), 16);
short b2 = Short.parseShort(new String(new byte[]{flag[2], flag[3]}), 16);
char i = (char) (b1 | (b2 << 8));

// Print contents as binary string
System.out.println(String.format("%16s", Integer.toBinaryString(i)).replace(' ', '0'));

// Output: 0010000000000000

// Check if 14'th bit is set (at index 13)
boolean isSet = ((i & (1 << 13)) != 0);

System.out.println(isSet); // true

You can use that method to check each bit. Just replace the 13 with the index you want to check.


I'm using a char here since that will print a little nicer. You could use a short, but whenever you convert that to an int (which can happen implicitly), the value gets padded with 1's if the most significant bit was set, because it's a signed type. char is unsigned however, so it doesn't have that behaviour.

like image 104
Jorn Vernee Avatar answered Apr 02 '26 20:04

Jorn Vernee



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!