SlideShare a Scribd company logo
Lesson 17. Pattern 9. Mixed arithmetic
I hope you have already rested from the 13-th lesson and now are ready to study one more important
error pattern related to arithmetic expressions in which types of different capacities participate.

Mixed use of memsize-types and non-memsize types in expressions may lead to incorrect results on 64-
bit systems and concern changes of the range of the input values. Consider some examples:

size_t Count = BigValue;

for (unsigned Index = 0; Index != Count; ++Index)

{ ... }

This is an example of an eternal loop occurring if Count > UINT_MAX. Suppose that this code works well
on a 32-bit system with fewer iterations than UINT_MAX. But the 64-bit version of the program can
process more data and may need more iterations. Since the values of Index variable lie within the range
[0..UINT_MAX], the condition "Index != Count" will never be fulfilled and it leads to the eternal loop.

Note. Consider that this sample may work well at some particular settings of the compiler. Sometimes it
is a source of much confusion because the code seems to be correct. In one of the following lessons we
will tell you about phantom errors that reveal themselves only some time later. If you are already longing
to learn why the code behaves so strangely, see the article "A 64-bit horse that can count".

To correct the code you should use only memsize-types in the expressions. In our example we may
change the type of the variable Index from "unsigned" to size_t.

Another frequent error is using expressions of the following kind:

int x, y, z;

ptrdiff_t SizeValue = x * y * z;

We have already examined such examples with an arithmetic overflow that occurs when calculating
expressions using non-memsize types. The result was incorrect of course. The search and detection of
this code fragment was complicated by the fact that compilers usually do not generate any warnings on
it. From the viewpoint of C++ language it is an absolutely correct construct: several variables of "int"
type are multiplied together, after that the result is implicitly extended to the type ptrdiff_t and is
assigned to a variable.

Here is a small code sample that shows the danger of inaccurate expressions with mixed types (these
results were obtained in Microsoft Visual C++ 2005 in the 64-bit compilation mode):

int x = 100000;

int y = 100000;

int z = 100000;

ptrdiff_t size = 1;                                     // Result:

ptrdiff_t v1 = x * y * z;                               // -1530494976
ptrdiff_t v2 = ptrdiff_t (x) * y * z; // 1000000000000000

ptrdiff_t v3 = x * y * ptrdiff_t (z); // 141006540800000

ptrdiff_t v4 = size * x * y * z;                           // 1000000000000000

ptrdiff_t v5 = x * y * z * size;                           // -1530494976

ptrdiff_t v6 = size * (x * y * z);                         // -1530494976

ptrdiff_t v7 = size * (x * y) * z;                         // 141006540800000

ptrdiff_t v8 = ((size * x) * y) * z;                       // 1000000000000000

ptrdiff_t v9 = size * (x * (y * z));                       // -1530494976

All the operands in such expressions must be cast to a type of a larger capacity while performing the
calculations. Remember that an expression like

ptrdiff_t v2 = ptrdiff_t (x) + y * z;

does not guarantee a correct result at all. It guarantees only that the expression "ptrdiff_t (x) + y * z" will
have the type "ptrdiff_t".

So, if the expression's result must have a memsize-type, there must be only memsize-types in the
expression too. Here is the correct version:

ptrdiff_t v2 = ptrdiff_t (x) + ptrdiff_t (y) * ptrdiff_t (z); // OK!

However, it is not always necessary to convert all the arguments to a memsize-type. If an expression
consists of identical operators, you may convert only the first argument to the memsize-type. Consider
an example:

int c();

int d();

int a, b;

ptrdiff_t v2 = ptrdiff_t (a) * b * c() * d();

The order of calculating the expression with the operators of the same priority has not been defined.
More exactly, the compiler may choose any order of calculating the subexpressions (for example the
calls of the functions c() and d()) it considers the most efficient, even if the subexpressions may cause
side effects. The order of appearance of side effects has not been defined either. But since the
multiplication operation refers to left-associative operators, the procedure of calculation will be
performed in the following way:

ptrdiff_t v2 = ((ptrdiff_t (a) * b) * c()) * d();

As a result, each of the operators will be cast to the type "ptrdiff_t" before the multiplication and we
will get the correct result.

Note. If there are integer calculations in your program and they need the control over overflows, resort
to the class SafeInt - you may learn about its implementation and see its description in MSDN.
Mixed use of types may also result in the changes in program logic:

ptrdiff_t val_1 = -1;

unsigned int val_2 = 1;

if (val_1 > val_2)

  printf ("val_1 is greater than val_2n");

else

  printf ("val_1 is not greater than val_2n");

//Output on 32-bit system: "val_1 is greater than val_2"

//Output on 64-bit system: "val_1 is not greater than val_2"

According to C++ rules, the variable val_1 is extended to the type "unsigned int" and becomes the value
0xFFFFFFFFu on a 32-bit system - the condition "0xFFFFFFFFu > 1" is fulfilled. On a 64-bit system,
however, it is the variable val_2 that gets extended to the type "ptrdiff_t" - in this case it is the
expression "-1 > 1" which is checked. Figures 1 and 2 give the outlines of the transformations that take
place.




                Figure 1 - Transformations taking place in the 32-bit version of the code
Figure 2 - Transformations taking place in the 64-bit version of the code

If you need to make the code behave in the same way as before, you should change the type of the
variable val_2:

ptrdiff_t val_1 = -1;

size_t val_2 = 1;

if (val_1 > val_2)

    printf ("val_1 is greater than val_2n");

else

    printf ("val_1 is not greater than val_2n");

Actually, it would be more correct not to compare signed and unsigned types at all, but this issue lies
beyond the current topic.

We have considered only simple expressions. But the described issues may occur when using other C++
constructs too:

extern int Width, Height, Depth;

size_t GetIndex(int x, int y, int z) {

    return x + y * Width + z * Width * Height;

}

...

MyArray[GetIndex(x, y, z)] = 0.0f;

If there is a large array (containing more than INT_MAX items), this code will be incorrect and we will be
directed to the wrong items of the array MyArray. Although it is the value of "size_t" type which is
returned, the expression "x + y * Width + z * Width * Height" is calculated using the type "int". I think
you have already guessed what the corrected code will look like:

extern int Width, Height, Depth;

size_t GetIndex(int x, int y, int z) {

    return (size_t)(x) +

              (size_t)(y) * (size_t)(Width) +

              (size_t)(z) * (size_t)(Width) * (size_t)(Height);

}

Or a bit simpler:

extern int Width, Height, Depth;

size_t GetIndex(int x, int y, int z) {

    return (size_t)(x) +

              (size_t)(y) * Width +

              (size_t)(z) * Widt) * Height;

}

In the next example again we have a mixture of a memsize-type (the pointer) and a 32-bit "unsigned"
type:

extern char *begin, *end;

unsigned GetSize() {

    return end - begin;

}

The result of the expression "end - begin" has the type "ptrdiff_t". Since the function returns the type
"unsigned", there occurs an implicit type conversion that leads to a loss of the more significant bits of
the result. So, if the pointers begin and end refer to the beginning and the end of the array whose size is
more than UINT_MAX (4Gb), the function will return an incorrect result.

And one more example. Here we are going to consider not a returned value but a formal argument of a
function:

void foo(ptrdiff_t delta);

int i = -2;

unsigned k = 1;

foo(i + k);
This code resembles an example with incorrect pointer arithmetic discussed in the 13-th lesson, does
not it? Right, here we have the same. We get the incorrect result when the actual argument, equaling
0xFFFFFFFF and having the type "unsigned", is implicitly extended to the type "ptrdiff_t".


Diagnosis
Errors occurring in 64-bit systems when integer types and memsize-types are used together are
presented in many C++ syntactic constructs. To diagnose these errors several diagnostic warnings are
used. PVS-Studio analyzer warns the programmer about possible errors with the help of these warnings:
V101, V103, V104, V105, V106, V107, V109, V110, V121.

Let us return to the example we have considered earlier:

int c();

int d();

int a, b;

ptrdiff_t x = ptrdiff_t(a) * b * c() * d();

Although the expression itself multiplies together the arguments extending their types to "ptrdiff_t", an
error may hide in the procedure of calculating these arguments. That is why the analyzer still warns you
about the mixed types: "V104: Implicit type conversion to memsize type in an arithmetic expression".

PVS-Studio tool also allows you to find potentially unsafe expressions which hide behind explicit type
conversions. To enable this function you should enable the warnings V201 and V202. By default, the
analyzer does not generate warnings concerning explicit type conversions. For example:

TCHAR *begin, *end;

unsigned size = static_cast<unsigned>(end - begin);

The warnings V201 and V202 will help you detect such incorrect code fragments.

Still the analyzer will pay no attention to type conversions which are safe from the viewpoint of the 64-
bit code:

const int *constPtr;

int *ptr = const_cast<int>(constPtr);

float f = float(constPtr[0]);

char ch = static_cast<char>(sizeof(double));

The course authors: Andrey Karpov (karpov@viva64.com), Evgeniy Ryzhkov (evg@viva64.com).

The rightholder of the course "Lessons on development of 64-bit C/C++ applications" is OOO "Program
Verification Systems". The company develops software in the sphere of source program code analysis.
The company's site: http://www.viva64.com.

Contacts: e-mail: support@viva64.com, Tula, 300027, PO box 1800.

More Related Content

What's hot

Lecture 6- Intorduction to C Programming
Lecture 6- Intorduction to C ProgrammingLecture 6- Intorduction to C Programming
Lecture 6- Intorduction to C Programming
Md. Imran Hossain Showrov
 
C++11 and 64-bit Issues
C++11 and 64-bit IssuesC++11 and 64-bit Issues
C++11 and 64-bit Issues
Andrey Karpov
 
Type Conversion in C++ and C# Arithmetic Expressions
Type Conversion in C++ and C# Arithmetic ExpressionsType Conversion in C++ and C# Arithmetic Expressions
Type Conversion in C++ and C# Arithmetic Expressions
PVS-Studio
 
C Programming Assignment
C Programming AssignmentC Programming Assignment
C Programming Assignment
Vijayananda Mohire
 
Assignment c programming
Assignment c programmingAssignment c programming
Assignment c programming
Icaii Infotech
 
[ITP - Lecture 04] Variables and Constants in C/C++
[ITP - Lecture 04] Variables and Constants in C/C++[ITP - Lecture 04] Variables and Constants in C/C++
[ITP - Lecture 04] Variables and Constants in C/C++
Muhammad Hammad Waseem
 
Analyzing the Quake III Arena GPL project
Analyzing the Quake III Arena GPL projectAnalyzing the Quake III Arena GPL project
Analyzing the Quake III Arena GPL project
PVS-Studio
 
10 -bits_and_bytes
10  -bits_and_bytes10  -bits_and_bytes
10 -bits_and_bytes
Hector Garzo
 
Lecture 18 - Pointers
Lecture 18 - PointersLecture 18 - Pointers
Lecture 18 - Pointers
Md. Imran Hossain Showrov
 
Ch8 Arrays
Ch8 ArraysCh8 Arrays
Ch8 Arrays
SzeChingChen
 
C programming session8
C programming  session8C programming  session8
C programming session8
Keroles karam khalil
 
2.overview of c++ ________lecture2
2.overview of c++  ________lecture22.overview of c++  ________lecture2
2.overview of c++ ________lecture2
Warui Maina
 
Ch7 Basic Types
Ch7 Basic TypesCh7 Basic Types
Ch7 Basic Types
SzeChingChen
 
Pointers
PointersPointers
Pointers
PreethyJemima
 
Java căn bản - Chapter6
Java căn bản - Chapter6Java căn bản - Chapter6
Java căn bản - Chapter6
Vince Vo
 
What is c
What is cWhat is c
What is c
pacatarpit
 
Computer Programming- Lecture 3
Computer Programming- Lecture 3Computer Programming- Lecture 3
Computer Programming- Lecture 3
Dr. Md. Shohel Sayeed
 
C Programming Language
C Programming LanguageC Programming Language
C Programming Language
RTS Tech
 
Lecture 8- Data Input and Output
Lecture 8- Data Input and OutputLecture 8- Data Input and Output
Lecture 8- Data Input and Output
Md. Imran Hossain Showrov
 
Claguage 110226222227-phpapp02
Claguage 110226222227-phpapp02Claguage 110226222227-phpapp02
Claguage 110226222227-phpapp02
CIMAP
 

What's hot (20)

Lecture 6- Intorduction to C Programming
Lecture 6- Intorduction to C ProgrammingLecture 6- Intorduction to C Programming
Lecture 6- Intorduction to C Programming
 
C++11 and 64-bit Issues
C++11 and 64-bit IssuesC++11 and 64-bit Issues
C++11 and 64-bit Issues
 
Type Conversion in C++ and C# Arithmetic Expressions
Type Conversion in C++ and C# Arithmetic ExpressionsType Conversion in C++ and C# Arithmetic Expressions
Type Conversion in C++ and C# Arithmetic Expressions
 
C Programming Assignment
C Programming AssignmentC Programming Assignment
C Programming Assignment
 
Assignment c programming
Assignment c programmingAssignment c programming
Assignment c programming
 
[ITP - Lecture 04] Variables and Constants in C/C++
[ITP - Lecture 04] Variables and Constants in C/C++[ITP - Lecture 04] Variables and Constants in C/C++
[ITP - Lecture 04] Variables and Constants in C/C++
 
Analyzing the Quake III Arena GPL project
Analyzing the Quake III Arena GPL projectAnalyzing the Quake III Arena GPL project
Analyzing the Quake III Arena GPL project
 
10 -bits_and_bytes
10  -bits_and_bytes10  -bits_and_bytes
10 -bits_and_bytes
 
Lecture 18 - Pointers
Lecture 18 - PointersLecture 18 - Pointers
Lecture 18 - Pointers
 
Ch8 Arrays
Ch8 ArraysCh8 Arrays
Ch8 Arrays
 
C programming session8
C programming  session8C programming  session8
C programming session8
 
2.overview of c++ ________lecture2
2.overview of c++  ________lecture22.overview of c++  ________lecture2
2.overview of c++ ________lecture2
 
Ch7 Basic Types
Ch7 Basic TypesCh7 Basic Types
Ch7 Basic Types
 
Pointers
PointersPointers
Pointers
 
Java căn bản - Chapter6
Java căn bản - Chapter6Java căn bản - Chapter6
Java căn bản - Chapter6
 
What is c
What is cWhat is c
What is c
 
Computer Programming- Lecture 3
Computer Programming- Lecture 3Computer Programming- Lecture 3
Computer Programming- Lecture 3
 
C Programming Language
C Programming LanguageC Programming Language
C Programming Language
 
Lecture 8- Data Input and Output
Lecture 8- Data Input and OutputLecture 8- Data Input and Output
Lecture 8- Data Input and Output
 
Claguage 110226222227-phpapp02
Claguage 110226222227-phpapp02Claguage 110226222227-phpapp02
Claguage 110226222227-phpapp02
 

Viewers also liked

Difficulties of comparing code analyzers, or don't forget about usability
Difficulties of comparing code analyzers, or don't forget about usabilityDifficulties of comparing code analyzers, or don't forget about usability
Difficulties of comparing code analyzers, or don't forget about usability
PVS-Studio
 
Lesson 24. Phantom errors
Lesson 24. Phantom errorsLesson 24. Phantom errors
Lesson 24. Phantom errors
PVS-Studio
 
Viva64: working up of 64-bit applications
Viva64: working up of 64-bit applicationsViva64: working up of 64-bit applications
Viva64: working up of 64-bit applications
PVS-Studio
 
Development of a static code analyzer for detecting errors of porting program...
Development of a static code analyzer for detecting errors of porting program...Development of a static code analyzer for detecting errors of porting program...
Development of a static code analyzer for detecting errors of porting program...
PVS-Studio
 
64-bit Loki
64-bit Loki64-bit Loki
64-bit Loki
PVS-Studio
 
Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...
Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...
Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...
PVS-Studio
 
Comparing PVS-Studio with other code analyzers
Comparing PVS-Studio with other code analyzersComparing PVS-Studio with other code analyzers
Comparing PVS-Studio with other code analyzers
PVS-Studio
 
Lesson 11. Pattern 3. Shift operations
Lesson 11. Pattern 3. Shift operationsLesson 11. Pattern 3. Shift operations
Lesson 11. Pattern 3. Shift operations
PVS-Studio
 
VivaMP, system of detecting errors in the code of parallel C++ programs using...
VivaMP, system of detecting errors in the code of parallel C++ programs using...VivaMP, system of detecting errors in the code of parallel C++ programs using...
VivaMP, system of detecting errors in the code of parallel C++ programs using...
PVS-Studio
 
Interview with Issam Lahlali, one of the CppDepend tool creators
Interview with Issam Lahlali, one of the CppDepend tool creatorsInterview with Issam Lahlali, one of the CppDepend tool creators
Interview with Issam Lahlali, one of the CppDepend tool creators
PVS-Studio
 
Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...
Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...
Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...
PVS-Studio
 
Driver Development for Windows 64-bit
Driver Development for Windows 64-bitDriver Development for Windows 64-bit
Driver Development for Windows 64-bit
PVS-Studio
 
Comparison of analyzers' diagnostic possibilities at checking 64-bit code
Comparison of analyzers' diagnostic possibilities at checking 64-bit codeComparison of analyzers' diagnostic possibilities at checking 64-bit code
Comparison of analyzers' diagnostic possibilities at checking 64-bit code
PVS-Studio
 
32 OpenMP Traps For C++ Developers
32 OpenMP Traps For C++ Developers32 OpenMP Traps For C++ Developers
32 OpenMP Traps For C++ Developers
PVS-Studio
 
Mobile CRM Webinar: 6 Steps to Mobile ROI for Government Agencies
Mobile CRM Webinar: 6 Steps to Mobile ROI for Government AgenciesMobile CRM Webinar: 6 Steps to Mobile ROI for Government Agencies
Mobile CRM Webinar: 6 Steps to Mobile ROI for Government Agencies
Waterfall Mobile
 
Lesson 21. Pattern 13. Data alignment
Lesson 21. Pattern 13. Data alignmentLesson 21. Pattern 13. Data alignment
Lesson 21. Pattern 13. Data alignment
PVS-Studio
 
VivaMP - a tool for OpenMP
VivaMP - a tool for OpenMPVivaMP - a tool for OpenMP
VivaMP - a tool for OpenMP
PVS-Studio
 
Viva64: What Is It, and Who Is It for?
Viva64: What Is It, and Who Is It for?Viva64: What Is It, and Who Is It for?
Viva64: What Is It, and Who Is It for?
PVS-Studio
 
Optimization in the world of 64-bit errors
Optimization  in the world of 64-bit errorsOptimization  in the world of 64-bit errors
Optimization in the world of 64-bit errors
PVS-Studio
 
How VivaCore library appeared
How VivaCore library appearedHow VivaCore library appeared
How VivaCore library appeared
PVS-Studio
 

Viewers also liked (20)

Difficulties of comparing code analyzers, or don't forget about usability
Difficulties of comparing code analyzers, or don't forget about usabilityDifficulties of comparing code analyzers, or don't forget about usability
Difficulties of comparing code analyzers, or don't forget about usability
 
Lesson 24. Phantom errors
Lesson 24. Phantom errorsLesson 24. Phantom errors
Lesson 24. Phantom errors
 
Viva64: working up of 64-bit applications
Viva64: working up of 64-bit applicationsViva64: working up of 64-bit applications
Viva64: working up of 64-bit applications
 
Development of a static code analyzer for detecting errors of porting program...
Development of a static code analyzer for detecting errors of porting program...Development of a static code analyzer for detecting errors of porting program...
Development of a static code analyzer for detecting errors of porting program...
 
64-bit Loki
64-bit Loki64-bit Loki
64-bit Loki
 
Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...
Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...
Case Study: Porting a set of point cloud and triangle mesh processing C++ lib...
 
Comparing PVS-Studio with other code analyzers
Comparing PVS-Studio with other code analyzersComparing PVS-Studio with other code analyzers
Comparing PVS-Studio with other code analyzers
 
Lesson 11. Pattern 3. Shift operations
Lesson 11. Pattern 3. Shift operationsLesson 11. Pattern 3. Shift operations
Lesson 11. Pattern 3. Shift operations
 
VivaMP, system of detecting errors in the code of parallel C++ programs using...
VivaMP, system of detecting errors in the code of parallel C++ programs using...VivaMP, system of detecting errors in the code of parallel C++ programs using...
VivaMP, system of detecting errors in the code of parallel C++ programs using...
 
Interview with Issam Lahlali, one of the CppDepend tool creators
Interview with Issam Lahlali, one of the CppDepend tool creatorsInterview with Issam Lahlali, one of the CppDepend tool creators
Interview with Issam Lahlali, one of the CppDepend tool creators
 
Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...
Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...
Comparing the general static analysis in Visual Studio 2010 and PVS-Studio by...
 
Driver Development for Windows 64-bit
Driver Development for Windows 64-bitDriver Development for Windows 64-bit
Driver Development for Windows 64-bit
 
Comparison of analyzers' diagnostic possibilities at checking 64-bit code
Comparison of analyzers' diagnostic possibilities at checking 64-bit codeComparison of analyzers' diagnostic possibilities at checking 64-bit code
Comparison of analyzers' diagnostic possibilities at checking 64-bit code
 
32 OpenMP Traps For C++ Developers
32 OpenMP Traps For C++ Developers32 OpenMP Traps For C++ Developers
32 OpenMP Traps For C++ Developers
 
Mobile CRM Webinar: 6 Steps to Mobile ROI for Government Agencies
Mobile CRM Webinar: 6 Steps to Mobile ROI for Government AgenciesMobile CRM Webinar: 6 Steps to Mobile ROI for Government Agencies
Mobile CRM Webinar: 6 Steps to Mobile ROI for Government Agencies
 
Lesson 21. Pattern 13. Data alignment
Lesson 21. Pattern 13. Data alignmentLesson 21. Pattern 13. Data alignment
Lesson 21. Pattern 13. Data alignment
 
VivaMP - a tool for OpenMP
VivaMP - a tool for OpenMPVivaMP - a tool for OpenMP
VivaMP - a tool for OpenMP
 
Viva64: What Is It, and Who Is It for?
Viva64: What Is It, and Who Is It for?Viva64: What Is It, and Who Is It for?
Viva64: What Is It, and Who Is It for?
 
Optimization in the world of 64-bit errors
Optimization  in the world of 64-bit errorsOptimization  in the world of 64-bit errors
Optimization in the world of 64-bit errors
 
How VivaCore library appeared
How VivaCore library appearedHow VivaCore library appeared
How VivaCore library appeared
 

Similar to Lesson 17. Pattern 9. Mixed arithmetic

Lesson 13. Pattern 5. Address arithmetic
Lesson 13. Pattern 5. Address arithmeticLesson 13. Pattern 5. Address arithmetic
Lesson 13. Pattern 5. Address arithmetic
PVS-Studio
 
About size_t and ptrdiff_t
About size_t and ptrdiff_tAbout size_t and ptrdiff_t
About size_t and ptrdiff_t
PVS-Studio
 
the refernce of programming C notes ppt.pptx
the refernce of programming C notes ppt.pptxthe refernce of programming C notes ppt.pptx
the refernce of programming C notes ppt.pptx
AnkitaVerma776806
 
L03vars
L03varsL03vars
Monitoring a program that monitors computer networks
Monitoring a program that monitors computer networksMonitoring a program that monitors computer networks
Monitoring a program that monitors computer networks
Andrey Karpov
 
Analysis of Microsoft Code Contracts
Analysis of Microsoft Code ContractsAnalysis of Microsoft Code Contracts
Analysis of Microsoft Code Contracts
PVS-Studio
 
A collection of examples of 64 bit errors in real programs
A collection of examples of 64 bit errors in real programsA collection of examples of 64 bit errors in real programs
A collection of examples of 64 bit errors in real programs
Michael Scovetta
 
C important questions
C important questionsC important questions
C important questions
JYOTI RANJAN PAL
 
keyword
keywordkeyword
keyword
teach4uin
 
keyword
keywordkeyword
keyword
teach4uin
 
CPP Homework Help
CPP Homework HelpCPP Homework Help
CPP Homework Help
C++ Homework Help
 
Tesseract. Recognizing Errors in Recognition Software
Tesseract. Recognizing Errors in Recognition SoftwareTesseract. Recognizing Errors in Recognition Software
Tesseract. Recognizing Errors in Recognition Software
Andrey Karpov
 
unit 1 (1).pptx
unit 1 (1).pptxunit 1 (1).pptx
unit 1 (1).pptx
PriyadarshiniS28
 
C tutorial
C tutorialC tutorial
C tutorial
Khan Rahimeen
 
C tutorial
C tutorialC tutorial
C tutorial
Anuja Lad
 
C tutorial
C tutorialC tutorial
C tutorial
tuncay123
 
C++ Homework Help
C++ Homework HelpC++ Homework Help
C++ Homework Help
C++ Homework Help
 
How to make fewer errors at the stage of code writing. Part N1.
How to make fewer errors at the stage of code writing. Part N1.How to make fewer errors at the stage of code writing. Part N1.
How to make fewer errors at the stage of code writing. Part N1.
PVS-Studio
 
A Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real ProgramsA Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real Programs
Andrey Karpov
 
A Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real ProgramsA Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real Programs
PVS-Studio
 

Similar to Lesson 17. Pattern 9. Mixed arithmetic (20)

Lesson 13. Pattern 5. Address arithmetic
Lesson 13. Pattern 5. Address arithmeticLesson 13. Pattern 5. Address arithmetic
Lesson 13. Pattern 5. Address arithmetic
 
About size_t and ptrdiff_t
About size_t and ptrdiff_tAbout size_t and ptrdiff_t
About size_t and ptrdiff_t
 
the refernce of programming C notes ppt.pptx
the refernce of programming C notes ppt.pptxthe refernce of programming C notes ppt.pptx
the refernce of programming C notes ppt.pptx
 
L03vars
L03varsL03vars
L03vars
 
Monitoring a program that monitors computer networks
Monitoring a program that monitors computer networksMonitoring a program that monitors computer networks
Monitoring a program that monitors computer networks
 
Analysis of Microsoft Code Contracts
Analysis of Microsoft Code ContractsAnalysis of Microsoft Code Contracts
Analysis of Microsoft Code Contracts
 
A collection of examples of 64 bit errors in real programs
A collection of examples of 64 bit errors in real programsA collection of examples of 64 bit errors in real programs
A collection of examples of 64 bit errors in real programs
 
C important questions
C important questionsC important questions
C important questions
 
keyword
keywordkeyword
keyword
 
keyword
keywordkeyword
keyword
 
CPP Homework Help
CPP Homework HelpCPP Homework Help
CPP Homework Help
 
Tesseract. Recognizing Errors in Recognition Software
Tesseract. Recognizing Errors in Recognition SoftwareTesseract. Recognizing Errors in Recognition Software
Tesseract. Recognizing Errors in Recognition Software
 
unit 1 (1).pptx
unit 1 (1).pptxunit 1 (1).pptx
unit 1 (1).pptx
 
C tutorial
C tutorialC tutorial
C tutorial
 
C tutorial
C tutorialC tutorial
C tutorial
 
C tutorial
C tutorialC tutorial
C tutorial
 
C++ Homework Help
C++ Homework HelpC++ Homework Help
C++ Homework Help
 
How to make fewer errors at the stage of code writing. Part N1.
How to make fewer errors at the stage of code writing. Part N1.How to make fewer errors at the stage of code writing. Part N1.
How to make fewer errors at the stage of code writing. Part N1.
 
A Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real ProgramsA Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real Programs
 
A Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real ProgramsA Collection of Examples of 64-bit Errors in Real Programs
A Collection of Examples of 64-bit Errors in Real Programs
 

Recently uploaded

National Security Agency - NSA mobile device best practices
National Security Agency - NSA mobile device best practicesNational Security Agency - NSA mobile device best practices
National Security Agency - NSA mobile device best practices
Quotidiano Piemontese
 
Serial Arm Control in Real Time Presentation
Serial Arm Control in Real Time PresentationSerial Arm Control in Real Time Presentation
Serial Arm Control in Real Time Presentation
tolgahangng
 
GraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracyGraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracy
Tomaz Bratanic
 
Webinar: Designing a schema for a Data Warehouse
Webinar: Designing a schema for a Data WarehouseWebinar: Designing a schema for a Data Warehouse
Webinar: Designing a schema for a Data Warehouse
Federico Razzoli
 
Your One-Stop Shop for Python Success: Top 10 US Python Development Providers
Your One-Stop Shop for Python Success: Top 10 US Python Development ProvidersYour One-Stop Shop for Python Success: Top 10 US Python Development Providers
Your One-Stop Shop for Python Success: Top 10 US Python Development Providers
akankshawande
 
Driving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success StoryDriving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success Story
Safe Software
 
Programming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup SlidesProgramming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup Slides
Zilliz
 
Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...
Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...
Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...
saastr
 
Artificial Intelligence for XMLDevelopment
Artificial Intelligence for XMLDevelopmentArtificial Intelligence for XMLDevelopment
Artificial Intelligence for XMLDevelopment
Octavian Nadolu
 
Taking AI to the Next Level in Manufacturing.pdf
Taking AI to the Next Level in Manufacturing.pdfTaking AI to the Next Level in Manufacturing.pdf
Taking AI to the Next Level in Manufacturing.pdf
ssuserfac0301
 
GenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizationsGenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizations
kumardaparthi1024
 
Recommendation System using RAG Architecture
Recommendation System using RAG ArchitectureRecommendation System using RAG Architecture
Recommendation System using RAG Architecture
fredae14
 
20240609 QFM020 Irresponsible AI Reading List May 2024
20240609 QFM020 Irresponsible AI Reading List May 202420240609 QFM020 Irresponsible AI Reading List May 2024
20240609 QFM020 Irresponsible AI Reading List May 2024
Matthew Sinclair
 
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Jeffrey Haguewood
 
Monitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdfMonitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdf
Tosin Akinosho
 
Choosing The Best AWS Service For Your Website + API.pptx
Choosing The Best AWS Service For Your Website + API.pptxChoosing The Best AWS Service For Your Website + API.pptx
Choosing The Best AWS Service For Your Website + API.pptx
Brandon Minnick, MBA
 
June Patch Tuesday
June Patch TuesdayJune Patch Tuesday
June Patch Tuesday
Ivanti
 
Cosa hanno in comune un mattoncino Lego e la backdoor XZ?
Cosa hanno in comune un mattoncino Lego e la backdoor XZ?Cosa hanno in comune un mattoncino Lego e la backdoor XZ?
Cosa hanno in comune un mattoncino Lego e la backdoor XZ?
Speck&Tech
 
Nordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptxNordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptx
MichaelKnudsen27
 
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdfHow to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
Chart Kalyan
 

Recently uploaded (20)

National Security Agency - NSA mobile device best practices
National Security Agency - NSA mobile device best practicesNational Security Agency - NSA mobile device best practices
National Security Agency - NSA mobile device best practices
 
Serial Arm Control in Real Time Presentation
Serial Arm Control in Real Time PresentationSerial Arm Control in Real Time Presentation
Serial Arm Control in Real Time Presentation
 
GraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracyGraphRAG for Life Science to increase LLM accuracy
GraphRAG for Life Science to increase LLM accuracy
 
Webinar: Designing a schema for a Data Warehouse
Webinar: Designing a schema for a Data WarehouseWebinar: Designing a schema for a Data Warehouse
Webinar: Designing a schema for a Data Warehouse
 
Your One-Stop Shop for Python Success: Top 10 US Python Development Providers
Your One-Stop Shop for Python Success: Top 10 US Python Development ProvidersYour One-Stop Shop for Python Success: Top 10 US Python Development Providers
Your One-Stop Shop for Python Success: Top 10 US Python Development Providers
 
Driving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success StoryDriving Business Innovation: Latest Generative AI Advancements & Success Story
Driving Business Innovation: Latest Generative AI Advancements & Success Story
 
Programming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup SlidesProgramming Foundation Models with DSPy - Meetup Slides
Programming Foundation Models with DSPy - Meetup Slides
 
Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...
Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...
Deep Dive: AI-Powered Marketing to Get More Leads and Customers with HyperGro...
 
Artificial Intelligence for XMLDevelopment
Artificial Intelligence for XMLDevelopmentArtificial Intelligence for XMLDevelopment
Artificial Intelligence for XMLDevelopment
 
Taking AI to the Next Level in Manufacturing.pdf
Taking AI to the Next Level in Manufacturing.pdfTaking AI to the Next Level in Manufacturing.pdf
Taking AI to the Next Level in Manufacturing.pdf
 
GenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizationsGenAI Pilot Implementation in the organizations
GenAI Pilot Implementation in the organizations
 
Recommendation System using RAG Architecture
Recommendation System using RAG ArchitectureRecommendation System using RAG Architecture
Recommendation System using RAG Architecture
 
20240609 QFM020 Irresponsible AI Reading List May 2024
20240609 QFM020 Irresponsible AI Reading List May 202420240609 QFM020 Irresponsible AI Reading List May 2024
20240609 QFM020 Irresponsible AI Reading List May 2024
 
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
Salesforce Integration for Bonterra Impact Management (fka Social Solutions A...
 
Monitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdfMonitoring and Managing Anomaly Detection on OpenShift.pdf
Monitoring and Managing Anomaly Detection on OpenShift.pdf
 
Choosing The Best AWS Service For Your Website + API.pptx
Choosing The Best AWS Service For Your Website + API.pptxChoosing The Best AWS Service For Your Website + API.pptx
Choosing The Best AWS Service For Your Website + API.pptx
 
June Patch Tuesday
June Patch TuesdayJune Patch Tuesday
June Patch Tuesday
 
Cosa hanno in comune un mattoncino Lego e la backdoor XZ?
Cosa hanno in comune un mattoncino Lego e la backdoor XZ?Cosa hanno in comune un mattoncino Lego e la backdoor XZ?
Cosa hanno in comune un mattoncino Lego e la backdoor XZ?
 
Nordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptxNordic Marketo Engage User Group_June 13_ 2024.pptx
Nordic Marketo Engage User Group_June 13_ 2024.pptx
 
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdfHow to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
How to Interpret Trends in the Kalyan Rajdhani Mix Chart.pdf
 

Lesson 17. Pattern 9. Mixed arithmetic

  • 1. Lesson 17. Pattern 9. Mixed arithmetic I hope you have already rested from the 13-th lesson and now are ready to study one more important error pattern related to arithmetic expressions in which types of different capacities participate. Mixed use of memsize-types and non-memsize types in expressions may lead to incorrect results on 64- bit systems and concern changes of the range of the input values. Consider some examples: size_t Count = BigValue; for (unsigned Index = 0; Index != Count; ++Index) { ... } This is an example of an eternal loop occurring if Count > UINT_MAX. Suppose that this code works well on a 32-bit system with fewer iterations than UINT_MAX. But the 64-bit version of the program can process more data and may need more iterations. Since the values of Index variable lie within the range [0..UINT_MAX], the condition "Index != Count" will never be fulfilled and it leads to the eternal loop. Note. Consider that this sample may work well at some particular settings of the compiler. Sometimes it is a source of much confusion because the code seems to be correct. In one of the following lessons we will tell you about phantom errors that reveal themselves only some time later. If you are already longing to learn why the code behaves so strangely, see the article "A 64-bit horse that can count". To correct the code you should use only memsize-types in the expressions. In our example we may change the type of the variable Index from "unsigned" to size_t. Another frequent error is using expressions of the following kind: int x, y, z; ptrdiff_t SizeValue = x * y * z; We have already examined such examples with an arithmetic overflow that occurs when calculating expressions using non-memsize types. The result was incorrect of course. The search and detection of this code fragment was complicated by the fact that compilers usually do not generate any warnings on it. From the viewpoint of C++ language it is an absolutely correct construct: several variables of "int" type are multiplied together, after that the result is implicitly extended to the type ptrdiff_t and is assigned to a variable. Here is a small code sample that shows the danger of inaccurate expressions with mixed types (these results were obtained in Microsoft Visual C++ 2005 in the 64-bit compilation mode): int x = 100000; int y = 100000; int z = 100000; ptrdiff_t size = 1; // Result: ptrdiff_t v1 = x * y * z; // -1530494976
  • 2. ptrdiff_t v2 = ptrdiff_t (x) * y * z; // 1000000000000000 ptrdiff_t v3 = x * y * ptrdiff_t (z); // 141006540800000 ptrdiff_t v4 = size * x * y * z; // 1000000000000000 ptrdiff_t v5 = x * y * z * size; // -1530494976 ptrdiff_t v6 = size * (x * y * z); // -1530494976 ptrdiff_t v7 = size * (x * y) * z; // 141006540800000 ptrdiff_t v8 = ((size * x) * y) * z; // 1000000000000000 ptrdiff_t v9 = size * (x * (y * z)); // -1530494976 All the operands in such expressions must be cast to a type of a larger capacity while performing the calculations. Remember that an expression like ptrdiff_t v2 = ptrdiff_t (x) + y * z; does not guarantee a correct result at all. It guarantees only that the expression "ptrdiff_t (x) + y * z" will have the type "ptrdiff_t". So, if the expression's result must have a memsize-type, there must be only memsize-types in the expression too. Here is the correct version: ptrdiff_t v2 = ptrdiff_t (x) + ptrdiff_t (y) * ptrdiff_t (z); // OK! However, it is not always necessary to convert all the arguments to a memsize-type. If an expression consists of identical operators, you may convert only the first argument to the memsize-type. Consider an example: int c(); int d(); int a, b; ptrdiff_t v2 = ptrdiff_t (a) * b * c() * d(); The order of calculating the expression with the operators of the same priority has not been defined. More exactly, the compiler may choose any order of calculating the subexpressions (for example the calls of the functions c() and d()) it considers the most efficient, even if the subexpressions may cause side effects. The order of appearance of side effects has not been defined either. But since the multiplication operation refers to left-associative operators, the procedure of calculation will be performed in the following way: ptrdiff_t v2 = ((ptrdiff_t (a) * b) * c()) * d(); As a result, each of the operators will be cast to the type "ptrdiff_t" before the multiplication and we will get the correct result. Note. If there are integer calculations in your program and they need the control over overflows, resort to the class SafeInt - you may learn about its implementation and see its description in MSDN.
  • 3. Mixed use of types may also result in the changes in program logic: ptrdiff_t val_1 = -1; unsigned int val_2 = 1; if (val_1 > val_2) printf ("val_1 is greater than val_2n"); else printf ("val_1 is not greater than val_2n"); //Output on 32-bit system: "val_1 is greater than val_2" //Output on 64-bit system: "val_1 is not greater than val_2" According to C++ rules, the variable val_1 is extended to the type "unsigned int" and becomes the value 0xFFFFFFFFu on a 32-bit system - the condition "0xFFFFFFFFu > 1" is fulfilled. On a 64-bit system, however, it is the variable val_2 that gets extended to the type "ptrdiff_t" - in this case it is the expression "-1 > 1" which is checked. Figures 1 and 2 give the outlines of the transformations that take place. Figure 1 - Transformations taking place in the 32-bit version of the code
  • 4. Figure 2 - Transformations taking place in the 64-bit version of the code If you need to make the code behave in the same way as before, you should change the type of the variable val_2: ptrdiff_t val_1 = -1; size_t val_2 = 1; if (val_1 > val_2) printf ("val_1 is greater than val_2n"); else printf ("val_1 is not greater than val_2n"); Actually, it would be more correct not to compare signed and unsigned types at all, but this issue lies beyond the current topic. We have considered only simple expressions. But the described issues may occur when using other C++ constructs too: extern int Width, Height, Depth; size_t GetIndex(int x, int y, int z) { return x + y * Width + z * Width * Height; } ... MyArray[GetIndex(x, y, z)] = 0.0f; If there is a large array (containing more than INT_MAX items), this code will be incorrect and we will be directed to the wrong items of the array MyArray. Although it is the value of "size_t" type which is
  • 5. returned, the expression "x + y * Width + z * Width * Height" is calculated using the type "int". I think you have already guessed what the corrected code will look like: extern int Width, Height, Depth; size_t GetIndex(int x, int y, int z) { return (size_t)(x) + (size_t)(y) * (size_t)(Width) + (size_t)(z) * (size_t)(Width) * (size_t)(Height); } Or a bit simpler: extern int Width, Height, Depth; size_t GetIndex(int x, int y, int z) { return (size_t)(x) + (size_t)(y) * Width + (size_t)(z) * Widt) * Height; } In the next example again we have a mixture of a memsize-type (the pointer) and a 32-bit "unsigned" type: extern char *begin, *end; unsigned GetSize() { return end - begin; } The result of the expression "end - begin" has the type "ptrdiff_t". Since the function returns the type "unsigned", there occurs an implicit type conversion that leads to a loss of the more significant bits of the result. So, if the pointers begin and end refer to the beginning and the end of the array whose size is more than UINT_MAX (4Gb), the function will return an incorrect result. And one more example. Here we are going to consider not a returned value but a formal argument of a function: void foo(ptrdiff_t delta); int i = -2; unsigned k = 1; foo(i + k);
  • 6. This code resembles an example with incorrect pointer arithmetic discussed in the 13-th lesson, does not it? Right, here we have the same. We get the incorrect result when the actual argument, equaling 0xFFFFFFFF and having the type "unsigned", is implicitly extended to the type "ptrdiff_t". Diagnosis Errors occurring in 64-bit systems when integer types and memsize-types are used together are presented in many C++ syntactic constructs. To diagnose these errors several diagnostic warnings are used. PVS-Studio analyzer warns the programmer about possible errors with the help of these warnings: V101, V103, V104, V105, V106, V107, V109, V110, V121. Let us return to the example we have considered earlier: int c(); int d(); int a, b; ptrdiff_t x = ptrdiff_t(a) * b * c() * d(); Although the expression itself multiplies together the arguments extending their types to "ptrdiff_t", an error may hide in the procedure of calculating these arguments. That is why the analyzer still warns you about the mixed types: "V104: Implicit type conversion to memsize type in an arithmetic expression". PVS-Studio tool also allows you to find potentially unsafe expressions which hide behind explicit type conversions. To enable this function you should enable the warnings V201 and V202. By default, the analyzer does not generate warnings concerning explicit type conversions. For example: TCHAR *begin, *end; unsigned size = static_cast<unsigned>(end - begin); The warnings V201 and V202 will help you detect such incorrect code fragments. Still the analyzer will pay no attention to type conversions which are safe from the viewpoint of the 64- bit code: const int *constPtr; int *ptr = const_cast<int>(constPtr); float f = float(constPtr[0]); char ch = static_cast<char>(sizeof(double)); The course authors: Andrey Karpov (karpov@viva64.com), Evgeniy Ryzhkov (evg@viva64.com). The rightholder of the course "Lessons on development of 64-bit C/C++ applications" is OOO "Program Verification Systems". The company develops software in the sphere of source program code analysis. The company's site: http://www.viva64.com. Contacts: e-mail: support@viva64.com, Tula, 300027, PO box 1800.