Casting int to void pointer - c++

Good day,
I just started to learn void pointers in c++ and now I'm writing binary tree where value stored in each node is void pointer to a value.
struct TreeNode
{
int count;
void* data;
TreeNode *left;
TreeNode *right;
};
The problem occurred in very first method-add method.
my method now takes int a a parameter and return nothing
At the very beginning i create new node.
To do that I need to cast integer into void.
Program compiles and first element adds to root correctly-however then when i send another number to method it stores in root again.
so if in main i have something like
tree.addToTree(12);
tree.addToTree(13);
than it would store 12 first and than right after else statement(code below)how that root->data i 13.
void Tree::addToTree(int num)
{
if(root==NULL){
root= new TreeNode();
root->data=#
//((int *)(root->data)) = num;//i tried to convert to void* in this way but it give me segmentation fault
root->left=NULL;
root->right=NULL;
}
else{
//here root value is already changed
int *intPtr = static_cast<int*>(root->data);
cout << "key2" << *intPtrT << endl;
//TreeNode* current= insert(num,root);
}
}
as i understood thats because i use &num so my parameter always tore in one place and a root is "connected" to &num it change as well.
I tried to find solution but was unsuccessful.
Is there a way to cat int to void pointer?

First of all, there are very very few reasons to store something as a void* instead of using a strongly typed method (e.g. template). Your entire problem goes away fairly quickly when you change your code to
template<typename T>
TreeNode
{
TreeNode<T>* left;
TreeNode<T>* right;
T data;
};
That said, the problem you have is that you are storing the address of a copy that will go away once the function goes out of scope:
if(root==NULL)
{
root= new TreeNode();
root->data=&num; // PROBLEM!!!
root->left=NULL;
root->right=NULL;
}
The problem line should be:
root->data = new int(num);
And you will have to properly delete the memory when you are done with it (e.g. when your tree is being destructed).
Alternatively, if you happen to be on a system where sizeof(void*) == sizeof(int), you can do this
root->data = (void*)num;
Which will simply treat the void* member as an integer. This does not work on systems where int is larger than void*.

First of all you should decide if you want to store data by value or by a pointer to it.
In first case having a pointer is just useless, you could use a template like:
template <typename T>
struct TreeNode
{
T data;
..
}
TreeNode<int> node;
This will work even with pointers (like T *data ... data = new int()).
In case you want to store a pointer to data you can also use a template with a type parameter or use a common ancestor class and then subclass it with the required types, eg:
class TreeData {
}
class TreeDataInt {
int value;
}
struct TreeNode
{
TreeData *data;
..
}
Lastly storying an int inside a void* pointer is something not so encouraged, using void* in C++ to achieve polymorphism is discouraged in general since you have many other tools which are safer and more reliable.
If you really want to store an int inside a void* then you should use the intptr_t type which is an integer that is convertible to a pointer. Eg:
#include <cstdint>
intptr_t value = 50;
node->data = static_cast<void*>(value);
intptr_t value2 = static_cast<intptr_t>(node->data);
This will save the value of the integer directly as an address inside the void*. This means that you can't dereference the pointer itself.
By the way root->data=&num is wrong since you are assigning to data the address of an automatic allocated variable which will become invalid when exiting its scope.

One problem I see is this (not the answer, just a problem)... in the function
void Tree::addToTree(int num)
{
if(root==NULL){
root= new TreeNode();
root->data=&num;
You are assigning the address of an automatic variable to data. The trouble is that as soon as the function exits, this variable will no longer exist (it is said to go out of scope) and so you have what's known as a dangling pointer, i.e., a pointer that points to an area of memory that is no longer used or is no longer used for the original purpose that the pointer expects.
You could fix this in three ways.
If you only want to store ints or any data type whose width is le that sizeof(void *), you could do root->data = (void *)num (note I cast the value of the variable to a void* and not the address of the variable). Or you could, as I see Zac has suggested too,
Create a copy of the variable and store the copies address. root->data = new int(num);. In this case you must make sure to delete the memory when you destroy the tree
Use templates as others have suggested (this is the better way) - I'll leave this point as others have covered it.
The other bit of you question where you have the comment
//((int *)(root->data)) = num;//i tried to convert to void* in this way but it give me segmentation fault
The reason this fails is because root->data at this point is just a pointer... it doesn't point anywhere (meaningful) yet. Thus when you try to dereference it, you are trying to access some memory that does "exist" yet (either pointer is NULL or has an invalid address), and so you seg fault.
When using a pointer in this way you need to create some memory and then make the pointer point to that memory, e.g. root->data = new int;. Once you have done that, you can then assign a value to that location in memory, e.g., *(root->data) = 1234;

Related

deleting object pointed to by two differnet pointers

I have created one Node object and the pointer named head is pointing to it. Then another pointer named newHead is created which points to the same object. Then I delete the memory by doing delete head and reassign head to a nullptr. However, this change is not reflected by the newHead pointer. From the attached code it is evident that newHead is not a nullptr and accessing the member value returns garbage value.
To understand this problem, I have already gone through this post which states that
Also note that you can delete the memory from any pointer that points to it
which is evidently not the case for the attached code below. Further I know that using smart pointers will definitely one way to resolve the issue, but in my application, I do need to use a raw pointer.
Any help in giving me an understanding of why is this happening and how to resolve it will be appreciated. Thank you.
#include <iostream>
using namespace std;
class Node {
public:
Node(int value) {this->value = value;}
int value;
Node* next = nullptr;
};
int main(int argc, char** argv) {
// create a node object
Node* head = new Node(5);
// another pointer pointing to head
Node* newHead = head;
// delete the object pointed to by head
delete head;
head = nullptr;
// check if newHead is nullptr
if (newHead == nullptr) {
std::cout << "newHead is a nullptr" << std::endl;
}
else {
std::cout << "Head is not a nullptr" << std::endl;
std::cout << "Node value is: " << newHead->value << std::endl;
}
return 0;
}
The two pointers were pointing to the same memory, the nullptr is not put in there instead of the deleted object.
head = nullptr; // this is not putting nullptr where the deleted object was!
This is why, newHead is not pointing to nullptr but to a released memory.
What you want is a Reference to pointer
// CPP program to demonstrate references to pointers.
#include <iostream>
using namespace std;
int main()
{
int x = 10;
// ptr1 holds address of x
int* ptr1 = &x;
// Now ptr2 also holds address of x.
// But note that pt2 is an alias of ptr1.
// So if we change any of these two to
// hold some other address, the other
// pointer will also change.
int*& ptr2 = ptr1;
int y = 20;
ptr1 = &y;
// Below line prints 20, 20, 10, 20
// Note that ptr1 also starts pointing
// to y.
cout << *ptr1 << " " << *ptr2 << " "
<< x << " " << y;
return 0;
}
Output:
20 20 10 20
Credit to geeksforgeeks
In contrast, having
int* ptr2 = ptr1;
int y = 20;
ptr1 = &y;
Gives
20 10 10 20
If you delete the memory pointed by one or more pointers, the pointer values don't change. You can test this by checking the value pointer before and after the execution of the delete statement.
There's no way to (without saving some meta information somewhere) to know how many or what pointers are still pointing to some memory buffer.
The approach followed by this class of objects (that get pointed to from different places) is to have a count of the number of pointers you still have pointing to the buffer. When you assing a new reference, you increment the pointer, and when you delete one reference, you decrement it, and, only when the count of reference pointers is about to reach 0, then you actually delete it.
It's not complicated to use this technique to implement dynamic classes like trees or more abstract. I used it to implement a string type, years ago, with a copy on write semantics that allowed you to save copying string contents on mostly readonly strings.
I have created one Node object and the pointer named head is pointing to it. Then another pointer named newHead is created which points to the same object. Then I delete the memory by doing delete head and reassign head to a nullptr. However, this change is not reflected by the newHead pointer. From the attached code it is evident that newHead is not a nullptr and accessing the member value returns garbage value.
Right. Nowhere in your code in your code to you change newHeads value, so it still has the same value it had before. Of course, it is an error to access the member value because the object no longer exists.
To understand this problem, I have already gone through this post which states that
Also note that you can delete the memory from any pointer that points to it
which is evidently not the case for the attached code below.
Why do you say that? That's exactly what happened in your code. You had two pointers that point to the same block of memory and you could have used either to free it. You used one of them, and it was freed.
Any help in giving me an understanding of why is this happening and how to resolve it will be appreciated. Thank you.
You never change the value of newHead, so it contains the same value it had before you called free. Only after you call free, that object no longer exists, so it's a useless garbage value.
It's not clear what you don't understand. After you free a block of memory, it is an error to access it. The solution is simple -- don't do that. After you do delete head;, both head and newHead point to memory that is no longer allocated. You set head to nullptr, but you don't change newHead's value, so it still points to where the memory used to be.
If you are going to use malloc or new, it is your responsibility to track the lifetimes of objects and not access them outside their lifetimes.

How to to set/get the low bits of a pointer to a struct? [duplicate]

I am trying to use tagged pointers for handling the lock free operations on a list, in order to block the compare-and-swap (CAS) from going through if some other thread operated on the list during this transaction. My node struct and CAS look like this:
struct node {
unsigned long key;
unsigned long val;
struct node * next;
};
static inline bool CAS(std::atomic<node*> node, struct node* oldNode, struct node* newNode)
{
node.compare_exchange_strong(oldNode, newNode, std::memory_order_seq_cst);
}
I found some methods for setting and checking these pointers but it is unclear to me how they work, these are the methods for setting the mask and verifying it.
__inline struct node* setTagMask(struct node* p, int MASK_BIT)
{
return (struct node*) ((uintptr_t)p | MASK_BIT);
}
__inline bool isMaskFlagSet(struct node* p)
{
return ((uintptr_t)p & MASK_BIT) != 0;
}
So what is unclear to me is for example in the setTagMask, if I use it on my list than it will delete all its references to its value and next element as well.
Can anyone explain to me how can I properly set these bits so the other elements of the list remain the same?
The setTagMask function returns a modified version of the pointer p. If you store this modified pointer in your linked-list, then the list gets broken because the modified pointer does not point to a node anymore.
The pointer is modified as follows. The pointer p is converted to an unsigned integer which is capable to store a pointer: uintptr_t.
Then one or more bits are set according to MASK_BIT. Finally, the result is converted back to a pointer and returned.
The function isMaskFlagSet checks whether the mask bits are still set.
The only use case, I can image is: you have to call isMaskFlagSet every time, before you use the pointer. If the mask bits are set, then it is prohibited to actually use the pointer.

Why pointer to pointer?

A very general question: I was wondering why we use pointer to pointer?
A pointer to pointer will hold the address of a pointer which in turn will point to another pointer. But, this could be achieved even by using a single pointer.
Consider the following example:
{
int number = 10;
int *a = NULL;
a = &number;
int *b = a;
int *pointer1 = NULL;
pointer1 = b; //pointer1 points to the address of number which has value 10
int **pointer2 = NULL;
pointer2 = &b; //pointer2 points to the address of b which in turn points to the address of number which has value 10. Why **pointer2??
return 0;
}
I think you answered your own question, the code is correct, what you commented isn't.
int number = 10; is the value
int *pointer1 = b; points to the address where int number is kept
int **pointer2 = &b; points to the address where address of int number is kept
Do you see the pattern here??
address = * (single indirection)
address of address = ** (double indirection)
The following expressions are true:
*pointer2 == b
**pointer2 == 10
The following is not!
*pointer2 == 10
Pointer to pointer can be useful when you want to change to what a pointer points to outside of a function. For example
void func(int** ptr)
{
*ptr = new int;
**ptr = 1337;
}
int main()
{
int* p = NULL;
func(&p);
std::cout << *p << std::endl; // writes 1337 to console
delete p;
}
A stupid example to show what can be achieved :) With just a pointer this can not be done.
First of all, a pointer doesn't point to a value. It point to a memory location (that is it contains a memory address) which in turn contains a value. So when you write
pointer1 = b;
pointer1 points to the same memory location as b which is the variable number. Now after that is you execute
pointer2 = &b;
Then pointer2 point to the memory location of b which doesn't contains 10 but the address of the variable number
Your assumption is incorrect. pointer2 does not point to the value 10, but to the (address of the) pointer b. Dereferencing pointer2 with the * operator produces an int *, not an int.
You need pointers to pointers for the same reasons you need pointers in the first place: to implement pass-by-reference parameters in function calls, to effect sharing of data between data structures, and so on.
In c such construction made sense, with bigger data structures. The OOP in C, because of lack of possibility to implement methods withing structures, the methods had c++ this parameter passed explicitly. Also some structures were defined by a pointer to one specially selected element, which was held in the scope global to the methods.
So when you wanted to pass whole stucture, E.g. a tree, and needed to change the root, or 1st element of a list, you passes a pointer-to-a-pointer to this special root/head element, so you could change it.
Note: This is c-style implementation using c++ syntax for convienience.
void add_element_to_list(List** list, Data element){
Data new_el = new Data(element); // this would be malloc and struct copy
*list = new_el; //move the address of list, so it begins at new element
}
In c++ there is reference mechanismm and you generally you can implement nearly anything with it. It basically makes usage of pointers at all obsolete it c++, at least in many, many cases. You also design objects and work on them, and everything is hidden under the hood those two.
There was also a nice question lately "Why do we use pointers in c++?" or something like that.
A simple example is an implementation of a matrix (it's an example, it's not the best way to implement matrices in C++).
int nrows = 10;
int ncols = 15;
double** M = new double*[nrows];
for(unsigned long int i = 0; i < nrows; ++i)
M[i] = new double[ncols];
M[3][7] = 3.1416;
You'll rarely see this construct in normal C++ code, since C++ has references. It's useful in C for "passing by reference:"
int allocate_something(void **p)
{
*p = malloc(whatever);
if (*p)
return 1;
else
return 0;
}
The equivalent C++ code would use void *&p for the parameter.
Still, you could imagine e.g. a resource monitor like this:
struct Resource;
struct Holder
{
Resource *res;
};
struct Monitor
{
Resource **res;
void monitor(const Holder &h) { res = &h.res; }
Resource& getResource() const { return **res; }
}
Yes, it's contrived, but the idea's there - it will keep a pointer to the pointer stored in a holder, and correctly return that resource even when the holder's res pointer changes.
Of course, it's a dangling dereference waiting to happen - normally, you'd avoid code like this.

Why would a change in a function header cause a Pointer assignment to not function?

When I change the last parameter in the function header from char Findthis[64] to char * Findthis when debugging the Testthis=&*Look_in; assignment breaks. Look_in has a memory address and member values but Testthis is not being assigned that pointer location. Why is this happening?
struct Node * ProbableMatch(struct Node * Look_in, int MaxNodes,
char Findthis[64])
{
char Findit[64];
strcpy_s(Findit,64,Findthis);
struct Node * CurrentHighProb;
CurrentHighProb=new(Node);
struct Node * Testthis;
Testthis=new(Node);
Testthis=&*Look_in;
while((Testthis) || (i!=(ccounter-1)))
{ //This Testthis does not cause exception
string str1;
string str2;
n1=sizeof(Testthis->NAME);
n2=sizeof(Findit);
n=0;
while((Testthis->NAME[n]!='\0') && (n<=n1)){
//While Testthis->NAME here causes the exception
if(Testthis->NAME[n]=='-'){Testthis->NAME[n]=' ';}
n++;
}//end of while
//_DIFFERENT PART OF PROGRAM____
std::string Findme;
cout<<"Enter varible to find. Type quit to quit, case sensative."<<endl;
cin>>Findme;
char * writable = new char[Findme.size()+1];
std::copy(Findme.begin(),Findme.end(),writable);
writable[Findme.size()] = '\0';
if((Findme.compare("quit")!=0) ^ (Findme.compare("Quit")!=0) ^ (Findme.compare("QUIT")!=0)){
ProbableMatch(head,ccounter,writable);
}
delete [] writable;
//_ NODE____
struct Node
{ public:
int VARID,counter,prob;
char NAME[64];
char DESCRIPTION[1024];
struct Node* next;
}node, *pNode=&node;
Looks more like C code. Why are you using C-strings and std strings? In any case, it looks like your error is unrelated. The assignment before Testthis = &*Look_in is useless (not to mention the new call leaks memory). In this case, there is no reason to first dereference your Look_in node and then take the address. You should be able to simply change that statement to Testthis = Look_in.
However, if this is a runtime error, be certain that Look_in != NULL or is not deleted somewhere else.
It looks like you have small confusion on pointers overall; so here is a quick run-down.
Pointers point to a memory location at which some value is stored. So when you declare a pointer and assign it some memory location, you are telling that pointer where in memory to look for some item. When you dereference a valid, non-null pointer, you can get the value which that memory location holds. For instance,
Node x[64]; // An array of 64 nodes
Node * t = x; // t points to element 0 of x. Therefore, changing values of x changes values of t and changing values of t changes values of x
Furthermore, memory allocation/deallocation is a different story. Stack memory (as declared above for both of those declarations) is managed by the operating system. However, heap allocation is up to you (i.e. new/delete).
Node * x = new Node;
// Do stuff with your node - it is on the heap, so it is persistent until you explicitly remove it
delete x;
The biggest difference between the stack and the heap is that heap memory exceeds the life of the function. For example, each function gets its own stack-frame to declare variables on. However, when the function exits, then the stack-frame is freed. Heap memory, however, can hold values which are not exclusive to a single function lifetime.
A simple example is this:
int* giveMeAnInt()
{
int x;
return &x;
}
In the function above, we declare a local variable, and try to return its address as a pointer to that value. However, after we return, that value is popped off the stack anyway since the function has ended. To do this properly you would have to:
int* giveMeAnInt()
{
int* x = new int;
return x;
}
The second example declares a variable on the heap and returns its address. But do not forget, if you use new, you must delete it later. Another quick example (using the working version of the code above i.e. example 2)
...
int * z = giveMeAnInt();
cout<< *z << endl;
delete z; // Free the memory allocated by the giveMeAnInt() function
...
That is a lot of quick information, but good luck.
EDIT
Perhaps if you are crashing at ...->NAME[n], then NAME[n] does not exist. Notice that you are effectively dereferencing Testthis at sizeof(Testthis->NAME) so the problem is not with the pointer. If you are looking for the number of characters in the string for a pointer, then you must use strlen() and not sizeof().
Here is the problem we are facing: the difference between an array and a pointer. If you declare char someArray[64], then sizeof(someArray) == 64. However, if you declare char* someArray, then sizeof(someArray) == 4 (since sizeof(char*) == 4, assuming 32-bit machine. But for now, the constant doesn't matter) and not the actual number of characters. To be safe, you should instead simply use strlen(someArray) which will work as expected for both declarations.
Ok looks like the std::string to char * conversion was causing leaks.
Switched to a vector option as suggested here: How to convert a std::string to const char* or char*?
Problem went away. I'll have to trace the actual memory later but I find it odd that that string memory was placed right next to the begining of the linked-list.

using Pointers to a series of integers in C++

I am trying to make a c++ program with a class which holds integers on the "heap" and has only one method, pop() which returns the first item in the class and removes it. This is my code so far:
#include <iostream>
using namespace std;
class LinkList {
int *values; //pointer to integers stored in linklist
int number; // number of values stored in linklist
public:
LinkList(const int*, int); // Constructor (method declaration)
int pop(); // typically remove item from data structure (method declaration)
};
LinkList::LinkList(const int *v, int n){
number = n;
*values = *v;
int mypointer = 1;
while (mypointer<n) {
*(values+mypointer) = *(v+mypointer);
mypointer++;
}
}
int LinkList::pop() {
if (number>0) {
int returnme = *values; //get the first integer in the linklist
number--;
values++; //move values to next address
return returnme;
}
else {return -1;}
}
int main() {
int test[] = {1,2,3,4,5};
LinkList l1(test,5);
cout << l1.pop() << endl;
LinkList l2(test,5);
cout << l2.pop() << endl;
return 0;
}
The issue is that its failing at the line *values = *v, if i remove the 4th and 5th lines from the main method, I no longer get this issue, so its go to be a memory management thing.
What I want to do is to get values to point to a continuous bit of memory with integers in. I have tried to use arrays for this but keep just getting random memory addresses returned by pop()
Background: normal I programming in java, I've only be using C/C++ for 2 months, I'm using eclipse IDE in ubuntu, I can make very basic use of the debugger but currently I dont have functioning scroll bars in eclipse so I can't do somethings if they dont fit on my screen.
You are dereferencing an uninitialized pointer (values) at the line *values = *v; which is undefined behavior (UB). What this line says is "get the integer that values points to and assign to it the value pointed by v". The problem with this logic is that values doesn't yet point to anything. The result of this UB is the crash that you receive.
There are many other problems with this code, such as passing a const int* to the constructor with the intent of modifying those values. The biggest problem is that this is not an actual linked list.
*values = *v;
You dereference the values pointer in this line before initializing it. This is the source of the later errors, and the non-errors in the first three lines of main are simply due to luck. You have to allocate space via values = new int[n] and deallocate it in the destructor via delete[] values. std::vector does this work in a clean and exception-safe way for you.
Perhaps the problem is that you're incrementing an integer - mypointer, rather than a a pointer. If the integer requires more than one byte of space, then this might lead to errors. Could you try declaring a pointer and incrementing that instead?
The values member variable is a pointer to uninitialized memory. Before you start copying numbers into it you have to point it to valid memory. For example:
LinkList::LinkList(const int *v, int n){
number = n;
values = new int[n]; // allocate memory
int mypointer = 0;
while (mypointer<n) {
*(values+mypointer) = *(v+mypointer);
mypointer++;
}
}
LinkList::~LinkList() {
delete values; // release memory
}
Also, why do you call this a linked list while in fact you are using a memory array to store your numbers?