user16310948
user16310948

Reputation:

C++ bool gets random/wrong value?

While debugging my code I have noticed that something strange is going on, So I have added more lines and got confused even more:

#include <iostream>
#include <memory>

struct Node
{
    size_t size = 0;
};

class MallocMetadata {
public:
    size_t size; /** Effective allocation - requested size **/
    bool is_free;
    MallocMetadata *next;
    MallocMetadata *prev;
    MallocMetadata *next_free;
    MallocMetadata *prev_free;
};

int main()
{
    size_t size = 0;
    auto node = std::make_shared<Node>();
    int tmp_res=node->size - size - sizeof(MallocMetadata);
    bool test=(node->size - size - sizeof(MallocMetadata)) < 128;
    bool test1=tmp_res<128;
    std::cout << tmp_res << "\n";
    std::cout << test << "\n";
    std::cout << test1 << "\n";
}

After running these 3 lines I saw:

tmp_res=-48
test = false
test1 = true

How is this even possible! why test is false, -48 is smaller than 128

Here's a proof:

enter image description here

Upvotes: 0

Views: 325

Answers (2)

Staz
Staz

Reputation: 358

I believe whenever there is an unsigned value in an expression, the result tends to be unsigned aswell.

size_t size = 0;
auto val = 1 + 100 + (-100) + size;
std::cout << typeid(val).name();

'val' will be a size_t aswell. So in your case, you're trying to store a negative value in size_t which causes overflow. You can explicitly typecast it to a signed integer and that should be enough if I'm not mistaken.Like so:

bool test=int(node->size - size - sizeof(MallocMetadata)) < 128;

Upvotes: 0

MikeCAT
MikeCAT

Reputation: 75062

It looks like the part node->size - size - sizeof(MallocMetadata) is calculated in unsigned integer.

When calculation of unsigned integer is going to be negative, the maximum number of the type plus one is added and the result wraparounds.

Therefore, the value looks like being big value (128 or more), making the expression (node->size - size - sizeof(MallocMetadata)) < 128 false.

In the other hands, int tmp_res=node->size - size - sizeof(MallocMetadata); will convert the big value to int. int is signed and it may give different value than the expression above that doesn't perform convertion to int.

Upvotes: 7

Related Questions