From 4f989950d14deee9e0532aeb633536d1a2025f8d Mon Sep 17 00:00:00 2001 From: "leon.bohnwagner" <leon.bohnwagner@informatik.hs-fulda.de> Date: Wed, 12 Feb 2025 23:07:15 +0100 Subject: [PATCH] =?UTF-8?q?feat:=20add=20bit=20banging=20raw=20dogging=20(?= =?UTF-8?q?=C2=AC=E2=80=BF=C2=AC)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- kernel/kmod.c | 58 ++++++++++++++++++++++++++++++++++++++++++--------- 1 file changed, 48 insertions(+), 10 deletions(-) diff --git a/kernel/kmod.c b/kernel/kmod.c index d8dd08c..882a939 100644 --- a/kernel/kmod.c +++ b/kernel/kmod.c @@ -6,6 +6,8 @@ #include <linux/uaccess.h> #include <linux/hrtimer.h> #include <linux/kthread.h> +#include <linux/gpio.h> +#include <linux/delay.h> #include "../common/include/message.h" #define DEVICE_NAME "amogus" @@ -14,6 +16,8 @@ #define SLOTS 4 #define SLOT_INTERVAL_NS 250000 +#define GPIO_PIN 12 + static int major_number; static struct class* class = NULL; static struct cdev mycdev; @@ -44,7 +48,7 @@ static ssize_t device_write(struct file *filp, const char *input, size_t length, loff_t *offset) { if(length != sizeof(message_t)) { - printk(KERN_ALERT "lkm: Tried to to write more bytes than allowed\n"); + printk(KERN_ALERT "lkm: Tried to write more bytes than allowed\n"); return -EFAULT; } @@ -52,7 +56,7 @@ static ssize_t device_write(struct file *filp, const char *input, return -EFAULT; } - printk(KERN_INFO "lkm: received write of size %zu\n",length); + printk(KERN_INFO "lkm: received write of size %zu\n", length); return length; } @@ -71,12 +75,31 @@ static enum hrtimer_restart timer_callback(struct hrtimer *timer) { return HRTIMER_RESTART; } +static void send_byte(uint8_t byte) { + for (int i = 0; i < 8; i++) { + int bit = (byte >> (7 - i)) & 1; + + gpio_set_value(GPIO_PIN, bit); + udelay(1); + } +} + +static void send_data(void *data, size_t length) { + uint8_t *bytes = (uint8_t*)data; + + for (size_t i = 0; i < length; i++) { + send_byte(bytes[i]); + } +} + static int timed_thread_fn(void *args) { while (!kthread_should_stop()) { wait_event_interruptible(wq, atomic_read(&wake_counter) > 0); atomic_dec(&wake_counter); - if (slot == 0) {} + if (slot == 0) { + send_data(&message, sizeof(message)); + } slot = (slot + 1) % SLOTS; } @@ -130,10 +153,16 @@ static int __init lkm_init(void) printk(KERN_INFO "lkm: device created successfully\n"); - interval = ktime_set(0, SLOT_INTERVAL_NS); - hrtimer_init(&timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); - timer.function = timer_callback; - hrtimer_start(&timer, interval, HRTIMER_MODE_REL); + if (gpio_request(GPIO_PIN, "GPIO_PIN") < 0) { + vfree(message); + cdev_del(&mycdev); + device_destroy(class, MKDEV(major_number, 0)); + class_destroy(class); + unregister_chrdev_region(MKDEV(major_number, 0), 1); + printk(KERN_ALERT "Failed to request GPIO pin\n"); + return -1; + } + gpio_direction_output(GPIO_PIN, 0); timed_thread = kthread_run(timed_thread_fn, NULL, "timed_thread"); if (IS_ERR(timed_thread)) { @@ -142,13 +171,15 @@ static int __init lkm_init(void) device_destroy(class, MKDEV(major_number, 0)); class_destroy(class); unregister_chrdev_region(MKDEV(major_number, 0), 1); - - hrtimer_cancel(&timer); - printk(KERN_ALERT "Failed to create timed thread\n"); return -1; } + interval = ktime_set(0, SLOT_INTERVAL_NS); + hrtimer_init(&timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); + timer.function = timer_callback; + hrtimer_start(&timer, interval, HRTIMER_MODE_REL); + return 0; } @@ -161,6 +192,13 @@ static void __exit lkm_exit(void) unregister_chrdev_region(MKDEV(major_number, 0), 1); printk(KERN_INFO "lkm: device removed successfully\n"); + gpio_set_value(GPIO_PIN, 0); + gpio_free(GPIO_PIN); + + if(timed_thread) { + kthread_stop(timed_thread); + } + hrtimer_cancel(&timer); } -- GitLab