Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Boolean is two bytes in .NET?

This question originates from here. I tried this statement in VS to see what happens:

Len(Name <= 3)

According to this answer and also this one, Boolean should consume 4 bytes. According to MSDN, Len Function in VB

Returns an integer containing either the number of characters in a string or the nominal number of bytes required to store a variable.

Name <= 3 should convert 3 to String and perform string comparison, returning a boolean value, so Len should evaluate number of bytes in it, which should be 4. For some reason, above code returns 2, regardless of the second parameter. In other words, Len(True) also returns 2. Tried for different platform targets (32 and 64) - same thing.

Why does Len(Boolean) return 2 instead of 4?

like image 998
Neolisk Avatar asked Jan 20 '13 15:01

Neolisk


2 Answers

According to MSDN's Data Type Summary (VS2012) the size of Boolean is dependent on the implementing platform. However if you look at the same page for VS2003 it does say that Boolean is 2 bytes.

ECMA-335 section III.1.1.1 states:

The evaluation stack only holds 4- or 8-byte integers, but other locations (arguments, local variables, statics, array elements, fields) can hold 1 - or 2-byte integers. For the purpose of stack operations the bool (§III.1.1.2) and char types are treated as unsigned 1-byte and 2-byte integers respectively. Loading from these locations onto the stack converts them to 4-byte values

And section III.1.1.2 states:

A CLI Boolean type occupies 1 byte in memory. A bit pattern of all zeroes denotes a value of false. A bit pattern with any one or more bits set (analogous to a non-zero integer) denotes a value of true. For the purpose of stack operations boolean values are treated as unsigned 1-byte integers


So given that, I feel only more confused as to why you get 2 and not 1

like image 22
CodingWithSpike Avatar answered Sep 21 '22 15:09

CodingWithSpike


With user-defined types and Object variables, the Len function returns the size as it will be written to the file by the FilePut function. If an Object contains a String, it will return the length of the string. If an Object contains any other type, it will return the size of the object as it will be written to the file by the FilePut function.

Len() is a legacy function, it should only be used in code that was ported from previous generation Visual Basic projects. Where it would typically appear in code that involved binary serialization of VB values. Sizes of basic types were different in those old versions. Integer was 16 bits for example, explaining the great number of bad pinvoke declarations you find in the web that use Long. And Boolean was a VARIANT_BOOL under the hood, a 16-bit value. Furthermore quirky by having its True value convert to -1 instead 1.

Clearly adopting the .NET sizes would have been a heavily breaking change to a lot of data that exists in files written by a VB6 program. Or binary data sent across a TCP connection. Etcetera. Accordingly, the Len() function returns the legacy sizes.

like image 53
Hans Passant Avatar answered Sep 18 '22 15:09

Hans Passant