Access function member using it address - c

Trying to access/print function member using following snippet
void func()
{
int i=4;
}
int *k = func + 4;
int main()
{
printf("%x\n", func);
printf("%x\n", k);
printf("%d\n", *(int *)k);
return 0;
}
and looking to get value of i through last printf statement but wondering if it is possible this way ?
output of program is:
400526
40052a
83641799

First of all, no, it's not possible at all to do in any reliable way.
And this idea does not make sense either. The variable i will typically not be exist nearby the function code. Also, it will typically be created at different places on different calls.
However, something that's possible is this:
int *func()
{
static int i=4;
return &i;
}
int *k;
int main()
{
k = func();
That's perfectly valid, even if the usefulness could be discussed.
But you will never be able to access it via an offset to the function pointer. At least not in a legal way.

Related

Can hard-code address and manually assign it to a pointer?

When I compile this code :
int main() {
int a = 10;
int *p = &a;
printf("%p",p) // or printf("%p",&a);
return 0;
}
it prints 0022ff38.
Then this code :
int a=10;
int *p =(int *)0x22ff38;
printf("%d",*p); //does not output 10;
should print 10, but it output another thing(2293560).
But when I edit the code, and add a single line :
int main() {
int a = 10;
int *p =(int *)0x22ff38;
printf("%p",&a);
printf("%d",*p); // Now it prints correctly:10
return 0;
}
Every thing is ok!.
Questions:
Why my code does not output a value in first code?
What is usage of this way addressing pointers? is it useful?
Edit :
I have no problem in Linux, because in Linux every time that I run the code, the variable address changes and program output segmentation fault. but in windows address remains the same, and it is expected that manual addressing work in windows.
Compilers are smarter than you think. For example, given this code:
int main() {
int a=10;
int *p =(int *)0x22ff38;
printf("%d",*p);
}
The compiler is going to see that a is never even used. So it will never bother to actually allocate any memory for it.
If you add a printf("%d", a), the compiler might only put a in a register and never in memory.
Fundamentally, you can't assume that two programs will put variables in the same place in memory.

How to access local and global variable with same name in C

I had this assignment at school, wherein I had to find the output of the following C code, and also, to explain the output.
#include<stdio.h>
int i;
void fun1(void);
void fun2(void);
int main()
{
fun1();
fun2();
return 0;
}
void fun1(){
i=20;
printf("%d\t",i);
}
void fun2(){
int i=50;
printf("%d",i);
}
The output is 20 50
Because in fun1() the Global Variable 'i' is assigned to 20 and printed. And in fun2() the variable 'i' is a Local Variable, which is declared and initialized to 50, which is then printed.
I have this following question out of curiosity, how do I use the global variable 'i', in fun2()?
A simple solution would be to simply change the name and avoid the whole thing. But my curiosity is due to Java, where there is a keyword "this" to access class variable instead of a local variable.
so is there any way to do that in C?
The only way is to hide the declaration of the local variable in a code block.
For example
#include <stdio.h>
int i = 10;
void fun2( void )
{
int i = 20;
printf("local i = %d\n",i);
{
extern int i;
printf( "global i = %d\n",i);
}
}
int main(void)
{
fun2();
}
The program output is
local i = 20
global i = 10
There is no way to access a global parameter inside a function that has a local variable with the same name. It is usually bad practice to create such local variables in C though, as you saw, it is not prohibited.
In C++ you can solve it using namespaces but there is no equivalent in C.
The best way is to pass parameters to the function
void fun2(int fromExternalWorld){
int i=50;
printf("%d ",fromExternalWorld);
printf("%d\n",i);
}
int main(void)
{
fun2(i);
}
Otherwise is not possible to have two symbols with same name visible in the same scope.
You could cheat and create a pointer to the global i before declaring the local i:
void fun2( void )
{
int *ip = &i; // get address of global i
int i = 50; // local i ”shadows" global i
printf( "local i = %d, global i = %d\n", i, *ip );
}
EDIT
Seeing as this answer got accepted, I must emphasize that you should never write code like this. This is a band-aid around poor programming practice.
Avoid globals where possible, and where not possible use a naming convention that clearly marks them as global and is unlikely to be shadowed (such as prefixing with a g_ or something similar).
I can't tell you how many hours I've wasted chasing down issues that were due to a naming collision like this.

pointers for getting elements of an array in C [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
pointer arithmetic in C for getting a string
I am a newbie in C and I would like to get the elements of an array with a function, I have tried different options, but I still do not get the elements.
My function is:
void getelements(int *a, int cl)
{
int *p;
for (p=&a[0];p<&a[cl];p++)
{
printf("%d\n",*p);
}
}
I know that the solution should work like that, but it only prints the first element and then memory positions. I am calling my function with:
int v={10,12,20,34,45};
getelements(&v,5);
Any help? I need to use arithmetic of pointers.
Thanks
First, Please don't update code to fix bugs while a question is open. It makes most of the current answers meaningless, doesn't grant credit where it is due to the person(s) that solved one or more issues in your prior code, and makes the casual reader looking for a related problem to their own completely confused by both the question and the answers therein. If you want to amend an update do so in addition to the original problem, but if it an entirely different issue, then mark as answered, give credit where it is due, and open a new question with your new code and different problem(s) (ideally, anyway).
As written now, your function is fine. But your real issue is this:
// compile with -Wall -Werror and look at the warning here
int v={10,12,20,34,45}; // <== WRONG
getelements(&v,5); // <== Harmless, but bad form.
This should be like this instead, assuming you want to print all elements in the array:
int v[] = {10,12,20,34,45};
getelements(v, sizeof(v)/sizeof(v[0]));
Note the [] following your array. Without it, the &v was masking what would have been a big-fat warning or error from the compiler that int is being passed as an int *. Furthermore, if you compile your prior code with full warnings treated as errors (-Wall -Werror for gcc) you will get an error like the following on your v declaration line:
main.c:116:15: Excess elements in scalar initializer
In other words, everything past the first element was ignored, and thus your pointer was running off into undefined behavior land. Changing the declaration and invocation to what I have above will address this as well as ensure you don't make that mistake again, since sizeof(v[0]) won't even compile unless v is an array or pointer type. The latter can still cause headaches when you use a pointer rather than an array with such a calculation, but thats something you just have to discipline yourself against doing in C.
try this and let me know if that works.
void getelements(int *a)
{
int *p;
int l=5;
for (p=a;p<a+l;p++)
{
printf("%d\n",*p);
}
}
It's best to pass in the length of the array along with the array itself.
#include <stdlib.h>
#include <stdio.h>
void get_elements(int* values, int length)
{
int i;
for (i = 0; i < length; ++i)
{
printf("%d\n", values[i]);
}
}
int main(int argc, char** argv)
{
int vals[3];
vals[0] = 0;
vals[1] = 1;
vals[2] = 2;
get_elements(vals, 3);
getchar();
return 0;
}
Using the code similar to your original post (before the addition of the array length as a method parameter), you could do the follow (which is a bit convoluted if you ask me).
void get_elements(int* values, int length)
{
int *p;
for (p = &values[0]; p < &values[length]; p++)
{
printf("%d\n", *p);
}
}
Actually you are passing array address in
getelements(&v,5)
in function
getelements()
you are treating it like an array!!!
void getelements(int *a, int cl)
{
int *p;
for (p=a;p<a+cl;p++)
{
printf("%d\n",*p);
}
}
Let me know if you are cleared conceptually!!!
As per my knowledge and seeing your code.you have hardcoded the length of array to 5. I think you can also pass array length as a parameter to function; or you can use this function and see if it gives the desired result
void getelements(int *a)
{
int *p;
int i = 0;
int l=5;
p = a
for (i = 0;i<l;i++)
{
printf("%d\n",*(p + i));
}
}

What is wrong with this C code

I have a piece of code where I am trying to return the square of the value pointed to by *ptr.
int square(volatile int *ptr)
{
int a,b;
a = *ptr;
b = *ptr;
return a * b;
}
main()
{
int a=8,t;
t=square(&a);
printf("%d",t);
}
Its working fine for me but author of this code said it might not work because of following reason:
Because it's possible for the value of *ptr to change unexpectedly, it is possible for a and b to be different. Consequently, this code could return a number that is not a square!. The correct way to do is
long square(volatile int *ptr)
{
int a;
a = *ptr;
return a * a;
}
I really wanted to know why he said like that?
The idea of the volatile keyword is exactly to indicate to the compiler that a variable marked as such can change in unexpected ways during the program execution.
However, that does not make it a source of "random numbers" - it just advises the compiler - what is responsible for actually changing the variable contents should be another process, thread, some hardware interrupt - anything that would write to the process memory but not inlined in the function where the volatile declaration finds itself. In "older times" (compilers with less magic) everything it did was preventing the compiler from caching the variable value in one of the CPU registers. I have no idea on the optimisations/de-optimistions strategies triggered by it by modern compilers - but it will at least do that.
In the absense of any such external factor, a "volatile" variable is just like any other. Actually - it is just like any other variable - as variables not marked as volatile can also be changed by the same external causes (but the compiled C code would not be prepared for that in this case, which might lead to incorrect values being used).
Since the question has an accepted and correct answer, I will be brief: here is a short program that you can run to see the incorrect behavior happening for yourself.
#include <pthread.h>
#include <math.h>
#include <stdio.h>
int square(volatile int *p) {
int a = *p;
int b = *p;
return a*b;
}
volatile int done;
void* call_square(void* ptr) {
int *p = (int*)ptr;
int i = 0;
while (++i != 2000000000) {
int res = square(p);
int root = sqrt(res);
if (root*root != res) {
printf("square() returned %d after %d successful calls\n", res, i);
break;
}
}
done = 1;
}
int main() {
pthread_t thread;
int num = 0, i = 0;
done = 0;
int ret = pthread_create(&thread, NULL, call_square, (void*)&num);
while (!done) {
num = i++;
i %= 100;
}
return 0;
}
The main() function spawns a thread, and modifies the data being squared in a loop concurrently with another loop calling the square with a volatile pointer. Relatively speaking, it does not fail often, but it does so very reliably in less than a second:
square() returned 1353 after 5705 successful calls <<== 1353 = 33*41
square() returned 340 after 314 successful calls <<== 340 = 17*20
square() returned 1023 after 5566 successful calls <<== 1023 = 31*33
First understand what's volatile: Why is volatile needed in C?
and then, try to find answer by yourself.
It's a game of volatile and hardware world. :-)
Read answer given by Chris Jester-Young:
volatile tells the compiler that your variable may be changed by other means, than the code that is accessing it. e.g., it may be a I/O-mapped memory location. If this is not specified in such cases, some variable accesses can be optimised, e.g., its contents can be held in a register, and the memory location not read back in again.
If there is more than one thread, the value the pointer points to might change inbetween statement "a = *ptr" and statement "b = *ptr". Also: you want the square of a value, why put it into two variables?
In the code you present then there is no way for the variable a that is defined in your main to be modified whilst square is running.
However, consider a multi-threaded program. Suppose that another thread modified the value to your your pointer refers. And suppose that this modification took place after you had assigned a, but before you had assigned b, in the function sqaure.
int square(volatile int *ptr)
{
int a,b;
a = *ptr;
//the other thread writes to *ptr now
b = *ptr;
return a * b;
}
In this scenario, a and b would have different values.
The author is correct (if *ptr will be changed by other threads)
int square(volatile int *ptr)
{
int a,b;
a = *ptr;
//between this two assignments *ptr can change. So it is dangerous to do so. His way is safer
b = *ptr;
return a * b;
}
Because the value of the pointer *ptr might change between the first affection and the second one.
I don't think the value of *ptr can change in this code barring an extremely unusual (and non-standards-compliant) runtime environment.
We're looking at the entirety of main() here and it's not starting up other threads. The variable a, whose address we are taking, is a local in main(), and main() doesn't inform any other function of that variable's address.
If you added the line mysterious_external_function(&a); before the t=square(&a) line, then yes, mysterious_external_function could start a thread and diddle the a variable asynchronously. But there's no such line, so as written square() always returns a square.
(Was the OP a troll post, by the way?)
I see some answers with *ptr can be changed by other threads. But this cannot happen since *ptr is not a static data variable. Its a parameter variable and local and parameter variables being hold inside stack. Each thread has its own stack section and if *ptr has been changed by another thread, it should not effect the current thread's.
One reason why the result might not give the square can be an HW interrupt might happen before assigning b = *ptr; operation as indicated below:
int square(volatile int *ptr) {
int a,b;
a = *ptr; //assuming a is being kept inside CPU registers.
//an HW interrupt might occur here and change the value inside the register which keeps the value of integer "a"
b = *ptr;
return a * b;
}

How to return a value to the calling function without using return statement?

The function proto type like int xxxx(int) or void xxx(int)
You could use a global variable (or, a little better, you could use a static variable declared at file scope), or you could change your functions to take an output parameter, but ultimately you should just use a return statement, since that's really what it's for.
The two standard ways to return values out of functions in C are to either do it explicitly with the return statement, or to use a pointer parameter and assign into the object at the pointer.
There are other ways, but I'm not going into them for fear of increasing the amount of evil code in the world. You should use one of those two.
Use pass by reference:
void foo(int* x, int* y) {
int temp;
temp = *x;
x* = *y;
y* = temp;
}
void main(void) {
int x = 2, y=4;
foo(&x, &y);
printf("Swapped Nums: %d , %d",x,y);
}
You could have a global variable that you assign the value to.
You could pass an object that stores the integer, and if you change it in the function, it'll change elsewhere too, since objects are not value type.
It also depends on the programming language that you're using.
EDIT: Sorry I didn't see the C tag, so ignore my last statement
Typically you provide a reference to an external variable to your function.
void foo(int *value)
{
*value = 123;
}
int main(void)
{
int my_return_value = 0;
foo(&my_return_value);
printf("Value returned from foo is %d", my_return_value);
return 0;
}
The simple answer is given a prototype like the first one you must use the return statement as the int return value dictates it.
In principle it is possible to do something horrible like cast a pointer to an int and pass it in as a parameter, cast it back and modify it. As others have alluded to you must be sure you understand all the implications of doing this, and judging by your question I'd say you don't.
int wel();
int main()
{
int x;
x = wel();
printf("%d\n",x);
return 0;
}
int wel()
{
register int tvr asm ("ax");
tvr = 77;
}
Compiled with GCC compiler in ubuntu machine. In borland compiler, different way to return.
If you need to return more than one value, why not use a pointer to a new allocated struct?
typedef struct { int a, char b } mystruct;
mystruct * foo()
{
mystruct * s = (mystruct *) malloc(sizeof(mystruct));
return s;
}
Not tested, but should be valid.

Resources