Reputation: 1778
I am using a 4.x linux kernel and have a kernel module where I receive socket information when opening up a socket.
if ((fd = socket(sai.sin_family, skt_type, skt_protocol)) < 0)
// ...
In this case, I am making use of UDP and before I transmit my first bit of data using sendto()
, I would like to be able to pass in a data structure from my client program into my kernel module. I could then add extra information into my protocol and relate this data to the file descriptor. This is not user data, rather, it's intended to control how my protocol will function.
The data structure I would like to pass in and relate to the socket is something like the following.
struct some_tag_info_t {
int field_t;
char field_a[MAX_A];
void *field_b;
};
I have a feeling ioctl might do something for me as it seems to be able to manipulate the underlying device parameters with a file descriptor.
In net/socket.c
, ioctl()
is:
static long sock_ioctl(struct file *file, unsigned cmd, unsigned long arg)
And after the function, I see this comment.
/*
* With an ioctl, arg may well be a user mode pointer, but we don't know
* what to do with it - that's up to the protocol still.
*/
It would appear I could use arg
to pass in my struct some_tag_info_t
above? Can anyone comment to this? Any thoughts?
Upvotes: 0
Views: 261
Reputation: 69367
Your understanding is correct, you could pass anything to your ioctl()
handler from userspace, it's then up to the kernel module to correctly handle whatever command and argument you pass. However, since you are working with sockets and writing your own protocol, it would be more appropriate to implement this functionality through getsockopt(2)
/setsockopt(2)
. The argument to setsockopt(2)
can be anything you want. From userspace you would do something like:
res = setsockopt(sock_fd, &your_struct, sizeof(your_struct));
Upvotes: 1