Typical errors of porting C++ code on the 64-bit platform

Serialization and data exchange

An important point during the port of a software solution on the new platform is succession to the existing data exchange protocol. It is necessary to provide the read of the existing projects formats, to carry out the data exchange between 32-bit and 64-bit processes etc.

Mostly the errors of this kind consist in the serialization of memsize types and data exchange operations using them.

1) size_t PixelCount;
   fread(&PixelCount, sizeof(PixelCount), 1, inFile);

 

2) __int32 value_1;
   SSIZE_T value_2;
   inputStream >> value_1 >> value_2;

 

3) time_t time;
   PackToBuffer(MemoryBuf, &time, sizeof(time));

In all the given examples there are errors of two kinds: the use of types of volatile size in binary interfaces and ignore of the byte order.

 

The use of types of volatile size.

It is unacceptably to use types which change their size depending on the development environment in binary interfaces of data exchange. In C++ language all the types don’t have distinct sizes and consequently it is not possible to use them all for these aims. That’s why the developers of the development means and programmers themselves develop data types which have an exact size such as __int8, __int16, INT32, word64 etc.

The use of such types provides data portability between programs on different platforms although it needs the use of odd ones. The three shown examples are written inaccurately and this will show up on the changing of the capacity of some data types from 32-bit to 64-bit. Taking into account the necessity to support old data formats the correction may look as follows.

1) size_t PixelCount;
   __uint32 tmp;
   fread(&tmp, sizeof(tmp), 1, inFile);
   PixelCount = static_cast<size_t>(tmp);

 

2) __int32 value_1;
   __int32 value_2;
   inputStream >> value_1 >> value_2;

 

3) time_t time;
   __uint32 tmp = static_cast<__uint32>(time);
   PackToBuffer(MemoryBuf, &tmp, sizeof(tmp));

But the given variant of correction cannot be the best. During the port on the 64-bit system the program may process a large number of data and the use of 32-bit types in the data may become a serious obstacle. In this case we may leave the old code for compatibility with the old data format having corrected the incorrect types, and fulfill the new binary data format taking into account the errors made. One more variant is to refuse binary formats and take text format or other formats provided by various libraries.

 

Ignoring of the byte order.

Even after the correction of volatile type sizes you may face the incompatibility of binary formats. The reason is a different data presentation. Most frequently it is related to a different byte order.

The byte order is a method of recording of bytes of multibyte numbers. The little-endian order means that the recording begins with the lowest byte and ends with the highest one. This record order was acceptable in the memory of PCs with x86-processors. The big-endian order – the recording begins with the highest byte and ends with the lowest one. This order is a standard for TCP/IP protocols. That’s why the big-endian byte order is often called the network byte order. This byte order is used by processors Motorola 68000, SPARC.

While developing the binary interface or data format you should remember about the byte order. If the 64-bit system on which you are porting a 32-bit application has a different byte order you’ll just have to take it into account in your code. For conversion between the big-endian byte order and the little-endian one you may use functions htonl(), htons(), bswap_64 etc.

You might also like...

Comments

Contribute

Why not write for us? Or you could submit an event or a user group in your area. Alternatively just tell us what you think!

Our tools

We've got automatic conversion tools to convert C# to VB.NET, VB.NET to C#. Also you can compress javascript and compress css and generate sql connection strings.

“Nine people can't make a baby in a month.” - Fred Brooks