Modified struct in some functions changes pointer and causes free() to fail - c

Pardon me for running multiple statements on one line, but this is what I don't understand. I have three functions named function1, function2 and function3 and each call makeblock, makeblock2, and makeblock3 respectively. See code below. I was trying to get them all to produce the same result on the screen. makeblock function works properly and the result after calling function1 is:
1 A
2 B
function2 and function3 do not work properly and produce a segmentation fault when attempting to free the memory pointer. I suspect it has to do with how the pointer is handled in makeblock2 and makeblock3 functions respectively.
So basically, I'm looking for a shortcut to making the data accessible without returning a modified address value back to the caller. Something shorter than block* dat=*datain;block** data=&dat; would be ideal provided it works yet my attempts in makeblock2 and makeblock3 have failed.
This is my code:
#include <stdio.h>
#include <stdlib.h>
typedef struct{int a;char b;} block;
void printdata(block* data){
while(data->a != 0){printf("%d %c\n",data->a,data->b);data++;}
}
void makeblock3(block** datain){
block** data=&(*datain);
(**data).a=1;(**data).b='A';(*data)++;
(**data).a=2;(**data).b='B';(*data)++;
}
void makeblock2(block** datain){
block** data=datain;
(**data).a=1;(**data).b='A';(*data)++;
(**data).a=2;(**data).b='B';(*data)++;
}
void makeblock(block** datain){
block* dat=*datain;block** data=&dat;
(**data).a=1;(**data).b='A';(*data)++;
(**data).a=2;(**data).b='B';(*data)++;
}
void function1(){block* data=calloc(1,100000);makeblock(&data);printdata(data);free(data);}
void function3(){block* data=calloc(1,100000);makeblock3(&data);printdata(data);free(data);}
void function2(){block* data=calloc(1,100000);makeblock2(&data);printdata(data);free(data);}
int main(){function3();return 0;}

Simple solution: don't pass by reference
void makeblock(block* data){
data->a=1; data->b='A'; data++;
data->a=2; data->b='B'; data++;
}
If you really want to pass by reference but don't want the referred object to change (which is contrary to the usual reason to pass by reference), then make a copy of the referred-to object:
void makeblock(block** data_p){
block* data = *data_p;
data->a=1; data->b='A'; data++;
data->a=2; data->b='B'; data++;
}

Related

How can I create a function object in C

I would like to create a wrapper for c functions, so that I can convert a function call of the form ret = function(arg1,arg2,arg3); into the form /*void*/ function_wrapper(/*void*/);. That is similar to function objects in C++ and boost bind.
Is this possible? how can I do it?
Update:
To explain in more details what I am looking for:
We start with this function:
int f(int i){
//do stuff
return somevalue;
}
Obvioulsy, it is called like this:
// do stuff
int x = 0;
ret = f(0);
// do more stuff.
I would like to do some magic that will wrap the function into void function(void)
struct function_object fo;
fo.function_pointer = &f;
fo.add_arg(x, int);
fo.set_ret_pointer(&ret);
fo.call();
Note: I saw that there was a vote for closing this question and marking it as unclear. Please do not do that. I have a legitimate need to get this question answered. If you need explanation, ask and I will be glad to elaborate.
I came up with a better code that might allow you to do what you want. First I'll explain how it works, show the code and explain why I still don't think it's a good idea to use it (though the code might open doors for improvements that addresses those issues).
Functionality:
Before you start using the "function objects", you have to call an initialization function (FUNCTIONOBJ_initialize();), which will initialize the mutexes on every data structure used in the library.
After initializing, every time you want to call one of those "function objects", without using the parameters, you will have to set it up first. This is done by creating a FUNCTIONOBJ_handler_t pointer and calling get_function_handler(). This will search for a free FUNCTIONOBJ_handler data structure that can be used at the moment.
If none is found (all FUNCTIONOBJ_handler data structures are busy, being used by some function call) NULL is returned.
If get_function_handler() does find a FUNCTIONOBJ_handler data structure it will try to lock the FUNCTIONOBJ_id_holder data structure, that holds the ID of the FUNCTIONOBJ_handler of the function about to be called.
If FUNCTIONOBJ_id_holder is locked already, get_function_handler() will hang until it's unlocked by the thread using it.
Once FUNCTIONOBJ_id_holder is locked, the ID of the grabbed FUNCTIONOBJ_handler is wrote on it and the FUNCTIONOBJ_handler pointer is returned by get_function_handler.
With the pointer in hand, the user can set the pointer to the arguments and the return variable with set_args_pointer and set_return_pointer, which both take a void * as arguments.
Finally, you can call the function you want. It has to:
1 - Grab the FUNCTIONOBJ_handler ID from the FUNCTIONOBJ_id_holder data structure and use it to get a pointer to the FUNCTIONOBJ_handler itself.
2 - Use the FUNCTIONOBJ_handler to access the arguments.
3 - Return by using one of the return function (on the example we have ret_int, which will return an integer and unlock the FUNCTIONOBJ_handler)
Below is a simplified mind map describing a bit of what is going on:
Finally, the code:
funcobj.h:
#include <stdio.h>
#include <pthread.h>
#define MAX_SIMULTANEOUS_CALLS 1024
typedef struct {
//Current ID about to be called
int current_id;
//Mutex
pthread_mutex_t id_holder_mutex;
} FUNCTIONOBJ_id_holder_t;
typedef struct {
//Attributes
void *arguments;
void *return_pointer;
//Mutex
pthread_mutex_t handler_mutex;
} FUNCTIONOBJ_handler_t;
FUNCTIONOBJ_handler_t FUNCTIONOBJ_handler[MAX_SIMULTANEOUS_CALLS];
FUNCTIONOBJ_id_holder_t FUNCTIONOBJ_id_holder;
void set_return_pointer(FUNCTIONOBJ_handler_t *this, void *pointer);
void set_args_pointer(FUNCTIONOBJ_handler_t *this, void *pointer);
void ret_int(FUNCTIONOBJ_handler_t *this, int return_value);
void FUNCTIONOBJ_initialize(void);
FUNCTIONOBJ_handler_t *get_function_handler(void);
funcobj.c:
#include "funcobj.h"
void set_return_pointer(FUNCTIONOBJ_handler_t *this, void *pointer){
this->return_pointer = pointer;
}
void set_args_pointer(FUNCTIONOBJ_handler_t *this, void *pointer){
this->arguments = pointer;
}
void ret_int(FUNCTIONOBJ_handler_t *this, int return_value){
if(this->return_pointer){
*((int *) (this->return_pointer)) = return_value;
}
pthread_mutex_unlock(&(this->handler_mutex));
}
void FUNCTIONOBJ_initialize(void){
for(int i = 0; i < MAX_SIMULTANEOUS_CALLS; ++i){
pthread_mutex_init(&FUNCTIONOBJ_handler[i].handler_mutex, NULL);
}
pthread_mutex_init(&FUNCTIONOBJ_id_holder.id_holder_mutex, NULL);
}
FUNCTIONOBJ_handler_t *get_function_handler(void){
int i = 0;
while((0 != pthread_mutex_trylock(&FUNCTIONOBJ_handler[i].handler_mutex)) && (i < MAX_SIMULTANEOUS_CALLS)){
++i;
}
if(i >= MAX_SIMULTANEOUS_CALLS){
return NULL;
}
//Sets the ID holder to hold this ID until the function is called
pthread_mutex_lock(&FUNCTIONOBJ_id_holder.id_holder_mutex);
FUNCTIONOBJ_id_holder.current_id = i;
return &FUNCTIONOBJ_handler[i];
}
main.c:
#include "funcobj.h"
#include <string.h>
//Function:
void print(void){
//First the function must grab the handler that contains all its attributes:
//The FUNCTIONOBJ_id_holder is mutex locked, so we can just access its value and
//then free the lock:
FUNCTIONOBJ_handler_t *this = &FUNCTIONOBJ_handler[FUNCTIONOBJ_id_holder.current_id];
//We dont need the id_holder anymore, free it!
pthread_mutex_unlock(&FUNCTIONOBJ_id_holder.id_holder_mutex);
//Do whatever the function has to do
printf("%s\n", (char *) this->arguments);
//Return the value to the pointed variable using the function that returns an int
ret_int(this, 0);
}
void *thread_entry_point(void *data){
int id = (int) data;
char string[100];
snprintf(string, 100, "Thread %u", id);
int return_val;
FUNCTIONOBJ_handler_t *this;
for(int i = 0; i < 200; ++i){
do {
this = get_function_handler();
} while(NULL == this);
set_args_pointer(this, string);
set_return_pointer(this, &return_val);
print();
}
return NULL;
}
int main(int argc, char **argv){
//Initialize global data strucutres (set up mutexes)
FUNCTIONOBJ_initialize();
//testing with 20 threads
pthread_t thread_id[20];
for(int i = 0; i < 20; ++i){
pthread_create(&thread_id[i], NULL, &thread_entry_point, (void *) i);
}
for(int i = 0; i < 20; ++i){
pthread_join(thread_id[i], NULL);
}
return 0;
}
To compile: gcc -o program main.c funcobj.c -lpthread
Reasons to avoid it:
By using this, you are limiting the number of "function objects" that can be running simultaneously. That's because we need to use global data structures to hold the information required by the functions (arguments and return pointer).
You will be seriously slowing down the program when using multiple threads if those use "function objects" frequently: Even though many functions can run at the same time, only a single function object can be set up at a time. So at least for that fraction of time it takes for the program to set up the function and actually call it, all other threads trying to run a function will be hanging waiting the the data structure to be unlocked.
You still have to write some non-intuitive code at the beginning and end of each function you want to work without arguments (grabbing the FUNCTIONOBJ_handler structure, unlocking the FUNCTIONOBJ_id_holder structure, accessing arguments through the pointer you grabbed and returning values with non-built-in functions). This increases the chances of bugs drastically if care is not taken, specially some nasty ones:
Increases the chances of deadlocks. If you forget to unlock one of the data structures in any point of your code, you might end up with a program that works fine at some moments, but randomly freeze completely at others (because all function calls without arguments will be hanging waiting for the lock to be freed). That is a risk that happens on multithreaded programs anyways, but by using this you are increasing the amount of code that requires locks unnecessarily (for style purposes).
Complicates the use of recursive functions: Every time you call the function object you'll have to go through the set up phrase (even when inside another function object). Also, if you call the recursive function enough times to fill all FUNCTIONOBJ_handler structures the program will deadlock.
Amongst other reasons I might not notice at the moment :p

Bad memory access while calling function

Actually i developing using unit test.
But i break down my code in other form to ask for the error that i faced.
I have these declaration in my header file
typedef struct
{
void *topOfStack;
}Stack;
typedef enum {NUMBER,OPERATOR,IDENTIFIER}Token;
int operatorEvaluate(Stack *numberStack , Stack *operatorStack);
void * pop(Stack *stack);
The following is the respective source file
#include "try.h"
void *pop(Stack *numberStack)
{
Token *newToken = NUMBER;
return newToken;
}
int operatorEvaluate(Stack *numberStack , Stack *operatorStack)
{
Token *first = (Token*)pop (numberStack);
if(numberStack != operatorStack)
{
if(*first == NUMBER)
return 1;
}
return 0;
}
This is the source file that i call the functions which is main
#include "try.h"
#include <stdio.h>
int main ()
{
Stack numberStack;
Stack operatorStack;
int num;
num = operatorEvaluate(&numberStack , &operatorStack);
printf("This is the returned value: %d",num);
return 0;
}
When i tried to compile, the unit test tell me that bad memory access.
So i try to use eclipse to compile these, and windows tells that the .exe had stop working.
Hope someone can help me, i stuck for a long time...
Enable compiler warnings.
In particular, this makes zero sense:
Token *newToken = NUMBER;
That's a pointer, and you're assigning a value.
I cannot propose a fix, as I have no idea what you're doing.
That pop() function isn't touching the stack, and is returning an enum converted to a pointer. If you try to access anything through that pointer, it's going to provoke undefined behavior.
Your pop function is wrong in a few ways. You probably want it to actually pop your stack, rather than return a constant (which it isn't doing either, by the way!)...something like this:
void *pop(Stack *numberStack)
{
return numberStack->topOfStack;
}
but if you do that it'll still crash, because you never initialize your stack OR fill the topOfStack pointer.

Generate two functions with C Preprocessor

I have a project, and a case where I have a few often-changed preprocessor #defines that control how it works--ex:
void myfunction(int num, mystruct* content) {
doSomethingTo(content);
//...
#ifdef FEATURE_X
feature_x(content);
#endif
}
This works fine, although it does have to be recompiled each time, so it's in the "stuff that has to be recompiled each time" file. I would like to push it into a [static] library instead. I'm ok with changing how it's called (already have a function pointer for picking myFunction), so I'd like that to turn into
void myfunction(int num, mystruct* content) {
doSomethingTo(content);
//...
}
void myfunction_featureX(int num, mystruct* content) {
doSomethingTo(content);
//...
feature_x(content);
}
I need to do this in a couple places, so using a separate library (one with and one without -D FEATURE_X) for each isn't an acceptable option. I could do it with copy/paste, but that results in code reuse that carries a risk of fixing a bug in one copy but not the other.
Have the featureX versions of functions call the mainline functions. In your example myfunction_featureX would call myfunction and then do its own thing.
Surely, this is the point at which you change the activation of Feature X from a compile time issue into a run-time issue:
void myfunction(int num, mystruct* content)
{
doSomethingTo(content);
//...
if (FeatureX_Enabled())
feature_x(content);
}
The FeatureX_Enabled() test might be a full function, or it might be simply test an appropriately scoped variable that is defined outside the function — a static variable in the file, or an external variable. This avoids having to futz with the function pointers; it's the same function called as now. Changing a table of function pointers is equivalent to changing a single variable — it involves changing the value of something stored outside the function to change the behaviour of the function.
Would it help if you put myfeature_x in a function table instead?
#include <stdio.h>
#include <string.h>
typedef struct {
int x,y;
} mystruct;
typedef void (*fn_ptr)(mystruct* content);
fn_ptr vtable[10];
#define FEATURE_X_INDEX 0
void feature_x(mystruct *content)
{
printf("y: %d\n", content->y);
}
void myfunction(int num, mystruct* content) {
printf("x: %d\n", content->x);
//...
if (vtable[FEATURE_X_INDEX]) {
vtable[FEATURE_X_INDEX](content);
}
}
int main(void)
{
bzero(vtable, sizeof(vtable));
mystruct s;
s.x = 1;
s.y = 2;
myfunction(0, &s);
if (1) {
//Of course you'd use a more sensible condition.
vtable[FEATURE_X_INDEX] = feature_x;
}
myfunction(0, &s);
return 0;
}
Output:
x: 1
x: 1
y: 2
Then all you need to do is populate the virtual function table with NULLs if that feature is not to be used, and with function pointers if it is to be used. This you can do from wherever you want - your static library for example.. or you can compile feature_x into a dynamic library, load it at runtime and if the loading succeeded populate the function table, and clear the table when the dynamically linked library is unloaded.
I think the only benefit this really gives you over Jonathan Leffler's method is that the code for feature_x doesn't actually need to be linked into the same binary as your other code. If all you need is a runtime switch to turn the feature on or off, a simple if statement should do the trick, as Jonathan Leffler suggested. (Incidentally, there's an if here, too - it checks the function table's content :) )

Using Windows slim read/write lock

/*language C code*/
#include "windows.h"
typedef struct object_s
{
SRWLOCK lock;
int data;
} object_t, *object_p; /*own and pointer type*/
void thread(object_p x)
{
AcquireSRWLockExclusive(&x->lock);
//...do something that could probably change x->data value to 0
if(x->data==0)
free(x);
else
ReleaseSRWLockExclusive(&x->lock);
}
void main()
{
int i;
object_p object=(object_p)malloc(sizeof(object_t));
InitializeSRWLock(&object->lock);
for(i=0;i<3;i++)
CreateThread(0,0,thread,object,0);
}
As you can figure out in the codes above, what I have to accomplish is to let one thread conditionally free the object on which the other two may block. Codes above are obviously flawed because if object is set free along with the lock, all blocking threads give us nowhere but wrong.
A solution below
/*language C code*/
#include "windows.h"
typedef struct object_s
{
/*change: move lock to stack in main()*/
int data;
} object_t, *object_p; /*own and pointer type*/
void thread(void * x)
{
struct {
PSRWLOCK l;
object_p o;
} * _x=x;
AcquireSRWLockExclusive(_x->l);
//...do something that could probably change x->data value to 0
if(_x->o->data==0)
free(_x->o);
ReleaseSRWLockExclusive(&x->lock);
}
void main()
{
int i;
SRWLOCK lock; /*lock over here*/
object_p object=(object_p)malloc(sizeof(object_t));
InitializeSRWLock(&lock);
/*pack for thread context*/
struct
{
PSRWLOCK l;
object_p o;
} context={&lock, object};
for(i=0;i<3;i++)
CreateThread(0,0,thread,&context,0);
}
works in this case but not applicable however, in my final project because there is actually a dynamic linked list of objects. By applying this solution it means that there must be a list of locks accordingly, each lock for an object and moreover, when a certain object is set free, its lock must be set free at the same time. There is nothing new compared with the first code section.
Now I wonder if there is an alternative solution to this. Thank you very much!
The solution is to not allocate the lock together with the data. I would suggest that you move the data out of that struct and replace it with a pointer to the data. Your linked list can then free the data first, and then the node, without any problems. Here's some pseudo code:
typedef struct
{
lock_t lock;
int* data_ptr;
} something_t;
void init_something (something_t* thing, ...)
{
thing->lock = init_lock();
thing->data_ptr = malloc(...); // whatever the data is supposed to be
}
void free_something (somthing_t* thing)
{
lock(thing->lock);
free(thing->data_ptr);
thing->data_ptr = NULL;
unlock(thing->lock);
}
...
void linked_list_delete_node (...)
{
free_something(node_to_delete->thing);
free(node_to_delete);
}
...
void thread (void* x)
{
lock(x->lock);
//...do something that could probably change x->data_ptr->data... to 0
if(x->data_ptr->data == 0)
{
free_something(x->data_ptr->data);
}
unlock(x->lock);
}
AcquireSRWLockExclusive(lock);
if(_x->o->data==0)
free(_x);
ReleaseSRWLockExclusive(lock);
As a sidenote, a C program for Windows can never return void. A hosted C program must always return int. Your program will not compile on a C compiler.
Also, CreateThread() expects a function pointer to a function returning a 32-bit value and taking a void pointer as parameter. You pass a different kind of function pointer, function pointer casts aren't allowed in C, nor am I sure what sort of madness Windows will execute if it gets a different function pointer than what it expects. You invoke undefined behavior. This can cause your program to crash or behave in unexpected or random ways.
You need to change your thread function to DWORD WINAPI thread (LPVOID param);

How can I invoke buffer overflow?

I got a homework assignment asking me to invoke a function without explicitly calling it, using buffer overflow. The code is basically this:
#include <stdio.h>
#include <stdlib.h>
void g()
{
printf("now inside g()!\n");
}
void f()
{
printf("now inside f()!\n");
// can only modify this section
// cant call g(), maybe use g (pointer to function)
}
int main (int argc, char *argv[])
{
f();
return 0;
}
Though I'm not sure how to proceed. I thought about changing the return address for the program counter so that it'll proceed directly to the address of g(), but I'm not sure how to access it. Anyway, tips will be great.
The basic idea is to alter the function's return address so that when the function returns is continues to execute at a new hacked address. As done by Nils in one of the answers, you can declare a piece of memory (usually array) and overflow it in such a way that the return address is overwritten as well.
I would suggest you to not blindly take any of the programs given here without actually understanding how they work. This article is very well written and you'll find it very useful:
A step-by-step on the buffer overflow vulnerablity
That is compiler dependent, so no single answer can be given.
The following code will do what you want for gcc 4.4.1. Compile with optimizations disabled (important!)
#include <stdio.h>
#include <stdlib.h>
void g()
{
printf("now inside g()!\n");
}
void f()
{
int i;
void * buffer[1];
printf("now inside f()!\n");
// can only modify this section
// cant call g(), maybe use g (pointer to function)
// place the address of g all over the stack:
for (i=0; i<10; i++)
buffer[i] = (void*) g;
// and goodbye..
}
int main (int argc, char *argv[])
{
f();
return 0;
}
Output:
nils#doofnase:~$ gcc overflow.c
nils#doofnase:~$ ./a.out
now inside f()!
now inside g()!
now inside g()!
now inside g()!
now inside g()!
now inside g()!
now inside g()!
Segmentation fault
Since this is homework, I would like to echo codeaddict's suggestion of understanding how a buffer overflow actually works.
I learned the technique by reading the excellent (if a bit dated) article/tutorial on exploiting buffer overflow vulnerabilities Smashing The Stack For Fun And Profit.
Try this one:
void f()
{
void *x[1];
printf("now inside f()!\n");
// can only modify this section
// cant call g(), maybe use g (pointer to function)
x[-1]=&g;
}
or this one:
void f()
{
void *x[1];
printf("now inside f()!\n");
// can only modify this section
// cant call g(), maybe use g (pointer to function)
x[1]=&g;
}
While this solution doesn't use an overflow technique to overwrite the function's return address on the stack, it still causes g() to get called from f() on its way back to main() by only modifying f() and not calling g() directly.
Function epilogue-like inline assembly is added to f() to modify the value of the return address on the stack so that f() will return through g().
#include <stdio.h>
void g()
{
printf("now inside g()!\n");
}
void f()
{
printf("now inside f()!\n");
// can only modify this section
// cant call g(), maybe use g (pointer to function)
/* x86 function epilogue-like inline assembly */
/* Causes f() to return to g() on its way back to main() */
asm(
"mov %%ebp,%%esp;"
"pop %%ebp;"
"push %0;"
"ret"
: /* no output registers */
: "r" (&g)
: "%ebp", "%esp"
);
}
int main (int argc, char *argv[])
{
f();
return 0;
}
Understanding how this code works can lead to a better understanding of how a function's stack frame is setup for a particular architecture which forms the basis of buffer overflow techniques.

Resources