[Mono-dev] Mono's BitConverter.

Miguel de Icaza miguel at ximian.com
Fri Mar 16 18:28:51 EDT 2007


Hello folks,

    We have recently been made aware of problems in BitConverter's
implementation.   The .NET bit converter implementation in 1.1 would not
do much, it would basically just return the in-memory representation as
a byte array or it would turn a byte array into a larger data type with
no conversions of any kind done.

    This limits the usefulness of this class, but also in 2.0 a mild and
broken attempt was done to provide support for translating the code to
LittleEndian.   This is botched so badly, that Vista pales in
comparison.

    So we have decided to implement an actually useful set of Bit
conversion class and request developers to use this instead.

    What we need are:

* Raw conversions (byte [] to datatype and back).

* LittleEndian to native (byte [] contains LE encoded data
  and must be converted into a proper data type, as well
  as routines for converting a datatype into a little-endian
  encoded byte array).

* BigEndian to native (byte [] contains BE encoded data and
  must be converted into native data type, as well as routines
  for converting a datatype into a big-endian encoded byte
  array).

    A few additional request have been made in addition: to provide
methods for writing this to streams (it seems sensible).

    Paolo has also suggested Pack and Unpack methods:

byte [] Pack (string template, params object [] arguments)

ArrayList Unpack (string template, byte [] arguments)

    We would add in addition to that, Try versions that throw no
exceptions on errors:

bool TryPack (string template, out byte [] result, params ...);
bool TryUnpack (string template, out ArrayList result, ...);

    The template would be a string that has instructions about how to
encode each argument, similar to Perl, for example:

Pack ("iii", 1, 2, 3);

* Naming Questions:

    Am struggling between having methods like this:

    class Mono.BitConverter {
	double ToDouble (byte [] data)
	double LEToDouble (byte [] data)
	double BEToDouble (byte [] data)
	byte [] FromDouble (double d)
	byte [] FromDoubleToLE (double d)
	byte [] FromDoubleToBE (double d)
    }

    Or having separate classes:

    class Mono.RawConverter {
	double ToDouble (..)
	byte [] FromDouble (..)
	byte [] Pack (...);
    }

    class Mono.LEConverter {
	double ToDoule (...);
	...
    }

    class Mono.BEConverter {
	...
    }

Using nested classes perhaps?

	public class Conveter {
		public class Raw {
		}
		public class BE {
		}
		public class LE {
		}
	}

Also, although it feels like I should use LittleEndian and BigEndian for
the classes, am not sure people will like typing those.

So usage would be a choice between:

	Converter.FromDoubleLE (..)
	Converter.FromDoubleLittleEndian (..)
	LEConverter.FromDouble (..)
	LittleEndianConveter.FromDouble (..)
	Converter.LE.FromDouble (..)
	Conveter.LittleEndian.FromDouble (..)

Also, I wonder what does Python and Java offer in this space for this,
is there a lesson or pattern that we could learn from Python, or should
we go with the Perl pattern?

Am interested in input from those that are familiar with the .NET Design
Guidelines.

Miguel.




More information about the Mono-devel-list mailing list