diff options
author | Jack Sangdahl <[email protected]> | 2024-04-02 23:08:19 -0600 |
---|---|---|
committer | Jack Sangdahl <[email protected]> | 2024-04-02 23:08:19 -0600 |
commit | 4b0d366a6665a70921dedb26c9ed5bdc7cd5c948 (patch) | |
tree | b10db80f6dc3ef49a79a1bff83725d4b31f3b2da | |
download | csci3753-4b0d366a6665a70921dedb26c9ed5bdc7cd5c948.tar.gz csci3753-4b0d366a6665a70921dedb26c9ed5bdc7cd5c948.zip |
pa1
-rw-r--r-- | .gitignore | 9 | ||||
-rw-r--r-- | pa1_syscalls_lkms/csci3753_mult.c | 12 | ||||
-rw-r--r-- | pa1_syscalls_lkms/csci3753_mult_test.c | 13 | ||||
-rw-r--r-- | pa1_syscalls_lkms/helloworld.c | 8 | ||||
-rw-r--r-- | pa1_syscalls_lkms/helloworld_test.c | 8 | ||||
-rw-r--r-- | pa1_syscalls_lkms/modules/Makefile | 4 | ||||
-rw-r--r-- | pa1_syscalls_lkms/modules/hellomodule.c | 20 | ||||
-rw-r--r-- | pa1_syscalls_lkms/readme.md | 58 |
8 files changed, 132 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..f1ed751 --- /dev/null +++ b/.gitignore @@ -0,0 +1,9 @@ +*.pdf +*.o +*.ko +*/.gdb_history +pa2_file_tester/pa2test +pa4_shared_array/shared_array +pa5_dns_resolver/lookup +pa6_threaded_resolver/multi-lookup +pa7_lru/test* diff --git a/pa1_syscalls_lkms/csci3753_mult.c b/pa1_syscalls_lkms/csci3753_mult.c new file mode 100644 index 0000000..cfe9458 --- /dev/null +++ b/pa1_syscalls_lkms/csci3753_mult.c @@ -0,0 +1,12 @@ +#include <linux/kernel.h> +#include <linux/linkage.h> +#include <linux/syscalls.h> + +SYSCALL_DEFINE3(csci3753_mult, int, number1, int, number2, long *, result) { + printk("Numbers being multiplied:\n"); + printk("Number 1: %d\n", number1); + printk("Number 2: %d\n", number2); + long product = number1 * number2; + printk("Result: %ld\n", product); + return copy_to_user(result, &product, sizeof(long)) ? -EFAULT : 0; +} diff --git a/pa1_syscalls_lkms/csci3753_mult_test.c b/pa1_syscalls_lkms/csci3753_mult_test.c new file mode 100644 index 0000000..116737a --- /dev/null +++ b/pa1_syscalls_lkms/csci3753_mult_test.c @@ -0,0 +1,13 @@ +#include <unistd.h> +#include <stdio.h> +#include <stdlib.h> +#define SYS_CALL_NUM 463 + +int main(int argc, char **argv) { + if (argc < 3) + exit(-1); + int a = atoi(argv[1]), b = atoi(argv[2]); + long c, res = syscall(SYS_CALL_NUM, a, b, &c); + printf("%d * %d = %ld\n", a, b, c); + exit(res); +} diff --git a/pa1_syscalls_lkms/helloworld.c b/pa1_syscalls_lkms/helloworld.c new file mode 100644 index 0000000..b712465 --- /dev/null +++ b/pa1_syscalls_lkms/helloworld.c @@ -0,0 +1,8 @@ +#include <linux/kernel.h> +#include <linux/linkage.h> +#include <linux/syscalls.h> + +SYSCALL_DEFINE0(helloworld) { + printk(KERN_ALERT "hello world\n"); + return 0; +} diff --git a/pa1_syscalls_lkms/helloworld_test.c b/pa1_syscalls_lkms/helloworld_test.c new file mode 100644 index 0000000..ddb9037 --- /dev/null +++ b/pa1_syscalls_lkms/helloworld_test.c @@ -0,0 +1,8 @@ +#include <unistd.h> +#include <stdlib.h> +#define SYS_CALL_NUM 462 + +int main() { + long res = syscall(SYS_CALL_NUM); + exit(res); +} diff --git a/pa1_syscalls_lkms/modules/Makefile b/pa1_syscalls_lkms/modules/Makefile new file mode 100644 index 0000000..34b0157 --- /dev/null +++ b/pa1_syscalls_lkms/modules/Makefile @@ -0,0 +1,4 @@ +obj-m += hellomodule.o + +all: + make -C /lib/modules/`uname -r`/build M=`pwd` diff --git a/pa1_syscalls_lkms/modules/hellomodule.c b/pa1_syscalls_lkms/modules/hellomodule.c new file mode 100644 index 0000000..0d92e22 --- /dev/null +++ b/pa1_syscalls_lkms/modules/hellomodule.c @@ -0,0 +1,20 @@ +#include <linux/init.h> +#include <linux/module.h> + +MODULE_AUTHOR("jasa7131"); +MODULE_LICENSE("GPL"); + +int hello_init(void); +void hello_exit(void); + +int hello_init(void) { + printk(KERN_ALERT "inside %s function\n", __FUNCTION__); + return 0; +} + +void hello_exit(void) { + printk(KERN_ALERT "inside %s function\n", __FUNCTION__); +} + +module_init(hello_init); +module_exit(hello_exit); diff --git a/pa1_syscalls_lkms/readme.md b/pa1_syscalls_lkms/readme.md new file mode 100644 index 0000000..86855f9 --- /dev/null +++ b/pa1_syscalls_lkms/readme.md @@ -0,0 +1,58 @@ +## PA1 - Syscalls & LKMs +### Adding a system call (6.6.11) +create file `arch/x86/kernel/helloworld.c` and note the following +* `kernel.h` header contains many constants and functions in kernel programming +* `linkage.h` header defines macros used to keep stack safe & orderly +* `syscalls.h` header contains `SYSCALL_DEFINEn` macros where `n` is the number of parameters being passed to system call +* `printk()` is used to print kernel messages (eg. dmesg) + +add `obj-y+=helloworld.o` to `arch/x86/kernel/Makefile` to link object +file of our system call. next, add system call to table. edit +`arch/x86/entry/syscalls/syscall_64.tbl` with +`454 common helloworld sys_helloworld`. a prototype for our system call +is needed. add `asmlinkage long sys_helloworld(void);` to +`include/linux/syscalls.h`. all system calls are prefixed with `sys_` +by convention. `asmlinkage` keyword tells the compiler that the function +should not expect to find any of its arguments in registers, but only +on the cpu's stack (see `linkage.h` file) + +### Writing a test program +an additional userspace program is needed to test the new system call. +the first argument to `syscall()` function is our system call number, +and any additional arguments would be passed system call function. +returns 0 on success, and -1 otherwise. , then compile and test program +and view the output of `dmesg` and look for our `print()` contents +```sh +cc hellotest.c +./a.out +echo $? +0 # no error +``` + +### Writing a second system call +create file `arch/x86/kernel/csci3753_mult.c` and write system call number +455 named `csci3753_mult()` and define two integer arguments: `num1, num2` +and a pointer to the integer integer result (long). the system call must +do the following: +* use `printk()` to log the numbers being multiplied +* multiply those two numbers +* use `printk()` to log the result +* store the result in userspace via the return pointer + * account for the fact that kernel cannot directly write to userspace memory +* return appropriate status (0 for success, non-zero for failure) + +again, a userspace program will be needed to test the system call's +functionality. see `csci3753_mult_test.c` file and use above steps. + +### Loadable Kernel Modules (LKMs) +allow for code to be loaded into kernel at runtime without the need to +recompile and reboot kernel. `CONFIG_MODULES` must be built and +configured. note the following about `modules/hellomodule.c`: +* `linux/{init.h, module.h}` contain library headers for module initialisation +* `module_init()` and `module_exit()` bind two functions, `hello_init()` +and `hello_exit()` to be executed when the module is loaded/unloaded + +after compilation (see `modules/Makefile`), the new `*.ko` moddule file +can be loaded with `insmod hellomodule.ko`, and unloaded using +`rmmod hellomodule.ko`. now, view output of dmesg to see what's been +printed. |