0

My goal is to instantiate a value in user space, install and run a kernel module (Ubuntu 20.04.1 if it matters) in which that value is changed/overwritten, and then print out the value in user space. I understand that copy_to/from_user() and/or get/put_user() are used to do things like this, but what I don't understand is this: How does the kernel module get the address to which it copies data? Does the user space program pass a pointer to it by calling the kernel module method that changes the value? Does the user program pass its PID to kernel module when installing/running it via bash and some how using the PID the kernel accesses the user program's memory space? Should I be tackling this a different way, such as having the kernel module instantiate the value and the user program access it and print it out?

If it matters, yes, this question is motivated by a homework assignment, however it is not the homework assignment, it is what I'm using to test my design of the homework assignment.

Sample user program:

// blah blah blah C stuff

int main(void)
{
    double val = 2.78;
    // call a bash script to insmod the kernel module
    while (val == 2.78);    // wait for the kernel module to change the value (yes, busy waiting sucks)
    printf("val = %f\n", val);    // print the changed value
    return 0;
}

Sample kernel module:

// more C stuff

static int mod_init(void)
{
    double kval = 3.14;
    copy_to_user(&val, &kval, sizeof(double));   // how do I do this?
    return 0;
}

I've read through other questions/answers on SO such as this and this, and I've read the relevant chapters of my text book (LDD3, ch 3, 6), and the sample code that it provides, but I'm still confused. Thanks in advance.

Edit: Thanks for your help SO. Haven't finished my homework assignment yet, but I think I'm now on the right track. For those with this question in the future: copy_to/from_user is (for lack of a better term) wrapped by an ioctl, which is essentially a cut rate system call. This helped me understand ioctls from the user perspective (warning: it's a really really gross website). LDD3 ch 3 helped flesh out the kernel side.

cstainer
  • 1
  • 1
  • 4
    Normally you read data from the kernel by calling a function, like `read` or `ioctl`. The pointer is one of the arguments to the function. The kernel doesn't just change data by itself. – user253751 Dec 03 '20 at 16:16
  • 3
    The addresses are passed as parameters in a relevant system call. – Ian Abbott Dec 03 '20 at 16:23
  • And how do you get a file descriptor for `read` or `ioctl`? You open a file in `/dev` which the driver creates. Unfortunately I don't know enough about it to write an answer. But this is how most drivers work. They create a `/dev` file for each device they know about (like a hard disk) - for drivers that don't actually have a device (like your test driver) they just create one for the whole driver. Then the program opens it and does reads and writes and ioctls – user253751 Dec 03 '20 at 17:27

0 Answers0