Home > database >  How to mathemathically invert a StringToHex function
How to mathemathically invert a StringToHex function

Time:11-04

The (wireless) mBus standard uses a number as equivalent to a manufacturer-string. Some examples are shown here: https://www.m-bus.de/man.html

Turning a manufacturer string like "IST" to the correct number 0x2674 is explained on the website for javascript, I turned it successfully into a c# function:

public static bool TryMANtoHEX(string man_str, out uint man_hex)
        {
            man_hex = 0;
            if (man_str.Length != 3) return false;
            if (!Regex.IsMatch(man_str, @"^[a-zA-Z] $")) return false;
            man_str = man_str.ToUpper();

            try
            {   
                man_hex  = ((uint)man_str[2] - 64);
                man_hex  = ((uint)man_str[1] - 64) * 32;
                man_hex  = ((uint)man_str[0] - 64) * 32 * 32;
            } catch
            {
                return false;
            }

            return true;
        }

But I am struggling to revert this function, so turning an number back to a string.

I tried the following code an it works for character 1 and 3 - but not for char 2:

public static bool TryHEXtoMAN(uint man_hex, out string man_str)
        {
            man_str = string.Empty;

            char c1 = (char)((man_hex / 1024)   64);
            char c2 = (char)((man_hex / 32)   64);
            char c3 = (char)((man_hex % 32)   64); 

            char[] cs = { c1, c2, c3 };

            man_str = new(cs);

            return true;
        }

For 0x2674 I would expect "IST", but get "IųT".

Any Ideas?

CodePudding user response:

Just use easier to read bit-masking:

    char c1 = (char)(((man_hex & 0b111110000000000) >>10)   64);  
    char c2 = (char)(((man_hex & 0b000001111100000) >> 5)   64); 
    char c3 = (char)(((man_hex & 0b000000000011111) >> 0)   64); 

    char[] cs = { c1, c2, c3 };

The particular error in your code is in computing c2 as you are not masking higher bits (15-10). If you want to keep math instead bitwise:

 char c2 = (char)((man_hex % 1024 / 32)   64);
  •  Tags:  
  • c#
  • Related