the value of a pointer changes after the call to printf - c

The values of pointers of a struct change after each call to printf.
I have the following structs:
struct block_meta_data
{
size_t size;
struct block_meta_data * next;
int isFree;
};
typedef struct block_meta_data block_meta_data;
struct list
{
block_meta_data* base;
block_meta_data* end;
};
typedef struct list list;
I defined a global variable of type list called blocks_list:
list blocks_list = {NULL, NULL};
and the main function looks like :
int main(void)
{
char a[] = "hello";
printf("%s\n", a);
return 0;
}
Now, using a debugger, I observe the values of both fields of the 'blocks_list' variable before the call to printf and they both have the value NULL:
After the call to printf, the values of both fields change to:
I tried printing the values of both end and base (without using a compiler) and the issue still remains:
list blocks_list = {NULL, NULL};
int main(void)
{
char a[] = "hello";
printf("%s\n", a);
printf("base = %p | end = %p\n", blocks_list.base, blocks_list.end);
return 0;
}
output :
hello
base = 0x555eed65d000 | end = 0x555eed65d000
Can someone explain why this is happening?

Can someone explain why this is happening?
There are a few possible explanations:
you are not telling us the whole story (provide MCVE) -- this is the most likely one
this is a debugging artifact -- your debugger is confused and shows something that isn't actually happening
the compiler detected that blocks_list is not actually used, and didn't allocate any storage for it (usually the compiler would also set location of blocks_list to 0, which would prevent debugger from displaying it).
Since you appear to be using Linux, note that you can tell where the value is overwritten using GDB watch points:
(gdb) watch -l blocks_list.base
(gdb) continue
# GDB will stop when blocks_list.base changes its value

Related

Why will this code not print the list of items? I know its to do with return

I know it should return a value to the main function but do not know how to output the list without doing it in the main function.
I want to be able to call the menu function and it print the list of items to the screen
#include <stdio.h>
int main()
{
int menu;
return 0;
};
int Menu (const char *Items[3], int Price [], int NoItems )
{
int i;
//assigning values to arrays
Items[1] = "lamp";
Items[2] = "Toothbrush";
Items[3] = "Battery";
Price[1] = 4.5;
Price[2] = 3.68;
Price[3] = 0.99;
for(i=1; i<4; i++)
{
printf("1) %s: %d\n",Items[i], Price[i]);
}
return 0 ;
}
The reason you aren't getting any output...
The compiler makes the resulting executable so that it starts with main. Since main does not call the function with your output, Menu, it doesn't get called at all.
It appears from that you have Menu after main that you are trying to have it execute last. To do this, you could simply have it as the last call in main, or you could use atexit(Menu); to have it called upon exit (even if the program is terminated early, such as with a call to exit).
Also the people in the comments of your post are right - the indices ([...]) don't make much sense. They are technically valid but depending on your usage you may get a memory access violation due to buffer overflow (trying to access memory beyond what is allocated for the array will give you junk data or, more likely, will crash your application entirely, immediately if the OS or hardware detects that the program is trying to use memory it doesn't own, or later on if you broke the stack by writing something to it).
You can put the variable initializer int i = 0; in the for loop itself.
You are using ints for the Price values, but assigning them non-integers. They will be truncated (made into whole numbers) in this case. Instead, I recommend you use floats which retain the more precise values you put in them.
It's not necessary to return a value from Menu unless it provides something not constant. Since it's just returning 0, you are wasting 4 bytes of memory to have something that always equals 0.
Since Menu is declared after main, in which it is called, you must either 1. Provide a function prototype (which I have demonstrated below) or 2. Move the function itself to before any places where it is called.
I assume that where you have "1)" in your output you mean to show the number of each item in the list. If you want this to change as you step through your list, you need to not always have it "1)" but rather use an escape character and provide a variable.
To put this all together...
#include <stdio.h>
void Menu (const char**, float*); // Prototype
int main()
{
const char* Items [3];
float Price [3];
Menu(Items,Price);
return 0;
};
void Menu (const char *Items [3], float Price [3])
{
Items[0] = "Lamp";
Items[1] = "Toothbrush";
Items[2] = "Battery";
Price[0] = 4.5;
Price[1] = 3.68;
Price[2] = 0.99;
for(int i = 0; i < 3; i++) printf("%d) %s: %f\n", i + 1, Items[i], Price[i]);
};

Trying to structure with call by value and call by reference...code compiles without any error..but prints garbage value?

Hi friends as I am new to C practising hard to understand all nitygrity things in C. While trying Structure I manage to write a piece of code where I am trying to pass structure to a function by value and reference. But I think I am doing something wrong...please help friends...it would be a great help if you guys can guide me to a proper in depth tutorial on Structures...thanks
#include <stdio.h>
#include <stdlib.h>
struct foo{
char arr[200];
int x_val;
int y_val;
float result;
};
struct foo my_foo;
int foo_fun(struct foo var); //proto declearation
int foo_fun1(struct foo *var1); //proto declearation
int main()
{
//As I was not getting prover string printed by using function foo_fun1
// I have tried to print directrly calling another ptr here
int i = 0;
struct foo *ptr;
ptr = (struct foo *)malloc(sizeof(struct foo)*10);
ptr->arr[0] = "calculator";
printf("Ptr zero contains a string %s\n",ptr->arr[0]); //even here prints wrong value
i = foo_fun(my_foo);
printf("Result from foo_fun is %d\n",i);
//Expecting this function to print string ....but getting some unexpected result
foo_fun1(&my_foo);
system("pause");
return 0;
}
// pass by value
int foo_fun(struct foo var)
{
int i;
int total = 0;
for(i=0;i<sizeof(var.arr); i++)
{ var.arr[i] = i;
total = total+var.arr[i];
}
var.x_val = 230;
var.y_val = 120;
return total;
}
// pass by reference
int foo_fun1(struct foo *var1)
{
int i = 0;
var1 = (struct foo *)malloc(sizeof(struct foo)*20);
var1->arr[0] = "A";
printf("%s\n",var1->arr);
return 0;
}
The following is wrong:
ptr->arr[0] = "calculator";
(BTW, your compiler should have warned you about this.)
You should use strcpy() instead.
The same goes for the other place where you're using a similar construct.
Finally, the malloc() in foo_fun1() is unnecessary. Not only you're overwriting the value of the function argument (why?), you are also leaking memory.
The line
ptr->arr[0] = "calculator";
is wrong, you cannot assign a string to a single character, that's what ptr->arr[0] represents.
ptr->arr = "calculator";
would be wrong too, since you cannot assing a string to a char array in that way, you have to use strcpy().
printf("Ptr zero contains a string %s\n",ptr->arr[0]);
should also be
printf("Ptr zero contains a string %s\n",ptr->arr);
since you are printing an array not a single char
Three problems in your code:
You must not cast return value from malloc() -
you are trying to assign a constant string to an indexed array - so it should be
strcpy(ptr->arr, "calculator"); and strcpy(var1->arr,"A");
Also - there is a massive memory leak in your code. No call to free() anywhere.

Struct argument passed in pthread create gets mangled

I have a structure named command that looks like this. The first value in the enum is AND_COMMAND
struct command
{
enum command_type type;
int status;
char *input;
char *output;
union
{
struct command *command[2];
char **word;
struct command *subshell_command;
} u;
};
When I call pthread_create I pass it a command in the form of a command_t (that is cast to (void *)).
typedef struct command *command_t;
My thread takes this (void *) command_t, casts it back (command_t) and tries to use the structure.
void execute_thread(void *c) {
command_t command = (command_t) c;
However when I pass a struct in to execute_thread the first values are zeroed out. If I have a command_type of SIMPLE_COMMAND and status of -1, when it's passed in to the thread the command_type is AND_COMMAND and status of 0. None of the other values in the struct are changed however. What's more curious is when this data mangling occurs. I was able to capture the phenomenon in gdb:
445 command_t command = (command_t) c;
(gdb) p *((command_t) c)
$6 = {type = SIMPLE_COMMAND, status = -1, input = 0x605370 "abc", output = 0x605390 "def", u = {
command = {0x6052e0, 0x0}, word = 0x6052e0, subshell_command = 0x6052e0}}
(gdb) n
(gdb) p *((command_t) c)
$7 = {type = AND_COMMAND, status = 0, input = 0x605370 "abc", output = 0x605390 "def", u = {command = {
0x6052e0, 0x0}, word = 0x6052e0, subshell_command = 0x6052e0}}
It appears that the structure pointed to by c doesn't change until casting it with (command_t) c; I am entirely confounded by this behavior. I didn't think that casting a pointer could change the values it pointed to. Could someone please point out, ha ha, what could be going on here? I would appreciate that very much.
What's more curious is when this data mangling occurs. I was able to capture the phenomenon in gdb:
The wording here leads me to believe that the problem isn't deterministic; ie., sometimes it doesn't happen, or it doesn't happen at the moment you happened to capture in gdb in the question.
If that's the case (and maybe even if it isn't), I suspect that you problem is that you're trashing the memory allocated to the struct command in the main thread (or whatever thread is creating the execute_thread() thread). You didn't show us the thread creation code, but if you use a local variable and pass the address of that to the created thread, then it can be tricky to make sure the local variable's lifetime doesn't expire before the the second thread gets around to using it. You might want to pass in a struct command that has been allocated on the heap:
struct command* thread_data = malloc(sizeof(struct command));
struct_command_init(thread_data);
pthread_create(/* ... */, thread_data);
// ...
and in the execute_command() thread:
void* execute_command(void* p)
{
struct command cmd = *(struct command*)p;
free(p);
// use cmd to get at the structure data passed in...
}
Keep in mind that the data referred to by various pointers insode the struct command also need to have their lifetime and ownership clearly managed, too.

Modifying struct members through a pointer passed to a function

for instance this code:
struct test{
int ID;
bool start;
};
struct test * sTest;
void changePointer(struct test * t)
{
t->ID = 3;
t->start = false;
}
int main(void)
{
sTest->ID = 5;
sTest->start = true;
changePointer(sTest);
return 0;
}
If I was to execute this code, then what would the output be? (i.e. if I pass a pointer like this, does it change the reference or is it just a copy?)
Thanks in advance!
Your program doesn't have any output, so there would be none.
It also never initializes the sTest pointer to point at some valid memory, so the results are totally undefined. This program invokes undefined behavior, and should/might/could crash when run.
IF the pointer had been initialized to point at a valid object of type struct test, the fields of that structure would have been changed so that at the end of main(), ID would be 3. The changes done inside changePointer() are done on the same memory as the changes done in main().
An easy fix would be:
int main(void)
{
struct test aTest;
sTest = &aTest; /* Notice the ampersand! */
sTest->start = true;
changePointer(sTest);
return 0;
}
Also note that C before C99 doesn't have a true keyword.
The only question is why do you need a test pointer in a global name space? Second is that you do not have any memory allocation operations. And you have a pointer as an input parameter of your function. Therefore structure where it points to will be changed in "changePointer".
1) First thing your code will crash since you are not allocating memory for saving structure.. you might need to add
sText = malloc(sizeof(struct test));
2) After correcting the crash, you can pass structure pointer and the changes you make in changePointer function will reflect in main and vizeversa..
3) But since you are not printing anything, there wont be any output to your program..

Returning local data from functions in C and C++ via pointer

I have argument with my friend. He says that I can return a pointer to local data from a function. This is not what I have learned but I can't find a counterargument for him to prove my knowledge.
Here is illustrated case:
char *name() {
char n[10] = "bodacydo!";
return n;
}
And it's used as:
int main() {
char *n = name();
printf("%s\n", n);
}
He says this is perfectly OK because after a program calls name, it returns a pointer to n, and right after that it just prints it. Nothing else happens in the program meanwhile, because it's single threaded and execution is serial.
I can't find a counter-argument. I would never write code like that, but he's stubborn and says this is completely ok. If I was his boss, I would fire him for being a stubborn idiot, but I can't find a counter argument.
Another example:
int *number() {
int n = 5;
return &n;
}
int main() {
int *a = number();
int b = 9;
int c = *a * b;
printf("%d\n", c);
}
I will send him this link after I get some good answers, so he at least learns something.
Your friend is wrong.
name is returning a pointer to the call stack. Once you invoke printf, there's no telling how that stack will be overwritten before the data at the pointer is accessed. It may work on his compiler and machine, but it won't work on all of them.
Your friend claims that after name returns, "nothing happens except printing it". printf is itself another function call, with who knows how much complexity inside it. A great deal is happening before the data is printed.
Also, code is never finished, it will be amended and added to. Code the "does nothing" now will do something once it's changed, and your closely-reasoned trick will fall apart.
Returning a pointer to local data is a recipe for disaster.
you will get a problem, when you call another function between name() and printf(), which itself uses the stack
char *fun(char *what) {
char res[10];
strncpy(res, what, 9);
return res;
}
main() {
char *r1 = fun("bla");
char *r2 = fun("blubber");
printf("'%s' is bla and '%s' is blubber", r1, r2);
}
As soon as the scope of the function ends i.e after the closing brace } of function, memory allocated(on stack) for all the local variables will be left. So, returning pointer to some memory which is no longer valid invokes undefined behavior.
Also you can say that local variable lifetime is ended when the function finished execution.
Also more details you can read HERE.
My counter-arguments would be:
it's never OK to write code with undefined behavior,
how long before somebody else uses that function in different context,
the language provides facilities to do the same thing legally (and possibly more efficiently)
It's undefined behavior and the value could easily be destroyed before it is actually printed. printf(), which is just a normal function, could use some local variables or call other functions before the string is actually printed. Since these actions use the stack they could easily corrupt the value.
If the code happens to print the correct value depends on the implementation of printf() and how function calls work on the compiler/platform you are using (which parameters/addresses/variables are put where on the stack,...). Even if the code happens to "work" on your machine with certain compiler settings it's far from sure that it will work anywhere else or under slightly different border conditions.
You are correct - n lives on the stack and so could go away as soon as the function returns.
Your friend's code might work only because the memory location that n is pointing to has not been corrupted (yet!).
As the others have already pointed out it is not illegal to do this, but a bad idea because the returned data resides on the non-used part of the stack and may get overridden at any time by other function calls.
Here is a counter-example that crashes on my system if compiled with optimizations turned on:
char * name ()
{
char n[] = "Hello World";
return n;
}
void test (char * arg)
{
// msg and arg will reside roughly at the same memory location.
// so changing msg will change arg as well:
char msg[100];
// this will override whatever arg points to.
strcpy (msg, "Logging: ");
// here we access the overridden data. A bad idea!
strcat (msg, arg);
strcat (msg, "\n");
printf (msg);
}
int main ()
{
char * n = name();
test (n);
return 0;
}
gcc : main.c: In function ‘name’:
main.c:4: warning: function returns address of local variable
Wherever it could been done like that (but it's not sexy code :p) :
char *name()
{
static char n[10] = "bodacydo!";
return n;
}
int main()
{
char *n = name();
printf("%s\n", n);
}
Warning it's not thread safe.
You're right, your friend is wrong. Here's a simple counterexample:
char *n = name();
printf("(%d): %s\n", 1, n);
Returning pointer to local variable is aways wrong, even if it appears to work in some rare situation.
A local (automatic) variable can be allocated either from stack or from registers.
If it is allocated from stack, it will be overwritten as soon as next function call (such as printf) is executed or if an interrupt occurs.
If the variable is allocated from a register, it is not even possible to have a pointer pointing to it.
Even if the application is "single threaded", the interrupts may use the stack. In order to be relatively safe, you should disable the interrupts. But it is not possible to disable the NMI (Non Maskable Interrupt), so you can never be safe.
While it is true that you cannot return pointers to local stack variables declared inside a function, you can however allocate memory inside a function using malloc and then return a pointer to that block. Maybe this is what your friend meant?
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
char* getstr(){
char* ret=malloc(sizeof(char)*15);
strcpy(ret,"Hello World");
return ret;
}
int main(){
char* answer=getstr();
printf("%s\n", answer);
free(answer);
return 0;
}
The way I see it you have three main options because this one is dangerous and utilizes undefined behavior:
replace: char n[10] = "bodacydo!"
with: static char n[10] = "bodacydo!"
This will give undesirable results if you use the same function more than once in row while trying to maintain the values contained therein.
replace:
char n[10] = "bodacydo!"
with:
char *n = new char[10];
*n = "bodacydo!"
With will fix the aforementioned problem, but you will then need to delete the heap memory or start incurring memory leaks.
Or finally:
replace: char n[10] = "bodacydo!";
with: shared_ptr<char> n(new char[10]) = "bodacydo!";
Which relieves you from having to delete the heap memory, but you will then have change the return type and the char *n in main to a shared_prt as well in order to hand off the management of the pointer. If you don't hand it off, the scope of the shared_ptr will end and the value stored in the pointer gets set to NULL.
If we take the code segment u gave....
char *name() {
char n[10] = "bodacydo!";
return n;
}
int main() {
char *n = name();
printf("%s\n", n);
}
Its okay to use that local var in printf() in main 'coz here we are using a string literal which again isn't something local to name().
But now lets look at a slightly different code
class SomeClass {
int *i;
public:
SomeClass() {
i = new int();
*i = 23;
}
~SomeClass() {
delete i;
i = NULL;
}
void print() {
printf("%d", *i);
}
};
SomeClass *name() {
SomeClass s;
return &s;
}
int main() {
SomeClass *n = name();
n->print();
}
In this case when the name() function returns SomeClass destructor would be called and the member var i would have be deallocated and set to NULL.
So when we call print() in main even though since the mem pointed by n isn't overwritten (i am assuming that) the print call will crash when it tried to de-reference a NULL pointer.
So in a way ur code segment will most likely not fail but will most likely fail if the objects deconstructor is doing some resource deinitialization and we are using it afterwards.
Hope it helps

Resources