4

I'm trying to pass a pointer to an array of struct. This code should create an array of struct, writes to the vars in struct, and then prints them out (which works). Then I want to pass a pointer of that array of struct to another function and print out the array of struts.

#define PORT_NUMBER 5100
#define MAX_CLIENTS 5

#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <string.h>
#include <pthread.h>

typedef struct thread_args
 {
    int client_number;
    int connected;
    char client_name[1024];
} client;

void pass_func(client* clients[])

int main()
{
  struct thread_args clients[MAX_CLIENTS];
  int i;

  for(i =0; i < MAX_CLIENTS; i++)
  {
  clients[i].client_number=i;
  strcpy(clients[i].client_name, "BOBBY");
  }

    for(i =0; i < MAX_CLIENTS; i++)
  {
     printf("%d | %s\n", clients[i].client_number=i, clients[i].client_name);
  }

  printf("\n\n");
  pass_func(&clients);
}

void pass_func(client* clients[])
{
  int i;
  for(i =0; i < MAX_CLIENTS; i++)
  {
     printf("%d | %s\n", clients[i]->client_number=i, clients[i]->client_name);
  }
}

And this is the output:

$ gcc TEST.c -lpthread -o TEST.out
TEST.c: In function ‘main’:
TEST.c:41:3: warning: passing argument 1 of ‘pass_func’ from incompatible pointer type [enabled by default]
TEST.c:22:6: note: expected ‘struct thread_args **’ but argument is of type ‘struct thread_args (*)[5]’

$ ./TEST.out 
0 | BOBBY
1 | BOBBY
2 | BOBBY
3 | BOBBY
4 | BOBBY


Segmentation fault

I've done about an hour of research and can't figure out why this is not working. Most of the examples I find are for C++, but not C. (And yes I know many of the header files I've included are not necessary for this code; this is just a segment of my original code.)

2
  • How about pass_func(&clients[0]) Commented Apr 21, 2012 at 1:05
  • @TJD - That gives me the same behavior. Commented Apr 21, 2012 at 1:17

3 Answers 3

14

pass_func expects an array of pointers to client

void pass_func(client* clients[]);

but you pass it

pass_func(&clients);

a pointer to an array of clients. So the client clients[i] is interpreted as a pointer to client in pass_func, but of course the bit-pattern is not a valid pointer to client, hence you're trying to access memory you shouldn't and get a segfault.

Either pass an array of pointers, or declare pass_func

void pass_func(client *clients);

(and then pass pass_func(clients) without the address-operator in main).

Your compiler warned you about passing an incompatible pointer type, though.

Sign up to request clarification or add additional context in comments.

5 Comments

It did warn: "TEST.c:41:3: warning: passing argument 1 of ‘pass_func’ from incompatible pointer type"
Oh, right. Completely missed that. Raises the question, why don't people heed the compiler warnings.
I agree, they are very useful. (Although the warnings can be fairly abstruse if you don't have much experience, especially for GCC.)
I did note the warning, hence why I included the gcc output, but I could not understand what I was overlooking. I originally had tried passing without [] - which is what I thought should have been correct, however I kept overlooking that I was passing an address (so called) of an address. Thanks.
@faction918 Ah, trying to figure out what a warning means by temporarily ignoring it is a legitimate strategy. Not necessarily the best, though, since it will often just result in segfaults or working code. You can also ask here "What does this warning mean for this code:...", that should get you a good explanation.
2
void pass_func(client* clients[])
{
  int i;
  for(i =0; i < MAX_CLIENTS; i++)
  {
     printf("%d | %s\n", (*clients)[i].client_number=i, (*clients)[i].client_name);
  }
}

this will be fine.

Comments

1

You need to get the basics right...

You need to first understand how arrays are passed to a function first: better go through this

1 Comment

The link is broken. I'm trying to dereference pointers to 2 nested structs. The main struct has a pointer to another struct. *((uint8_t)th0->(*(tsk+0))->args_cnts) = 0; where tsk is a pointer to multiple objects of the same type but don't know how to dereference it right.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.