From 648e30e3ee07722b62b5ca5a9c111ee081cd7b36 Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Sun, 5 Jan 2025 09:47:56 +0000 Subject: [PATCH 1/7] lttle guest manager device mmio + test triggers --- fs/read_write.c | 8 ++++++ include/lttle/trigger.h | 16 ++++++++++++ kernel/Makefile | 3 ++- kernel/lttle.c | 56 +++++++++++++++++++++++++++++++++++++++++ net/socket.c | 6 +++++ 5 files changed, 88 insertions(+), 1 deletion(-) create mode 100644 include/lttle/trigger.h create mode 100644 kernel/lttle.c diff --git a/fs/read_write.c b/fs/read_write.c index 24b9668d63770f..938f0eaebe7cd7 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -25,6 +25,8 @@ #include #include +#include + const struct file_operations generic_ro_fops = { .llseek = generic_file_llseek, .read_iter = generic_file_read_iter, @@ -625,6 +627,12 @@ SYSCALL_DEFINE3(read, unsigned int, fd, char __user *, buf, size_t, count) ssize_t ksys_write(unsigned int fd, const char __user *buf, size_t count) { + // @TODO(laurci): this is just a temporary test + if (fd == 100) { + lttle_sys_trigger(LTTLE_SYS_WRITE, NULL); + return 0; + } + struct fd f = fdget_pos(fd); ssize_t ret = -EBADF; diff --git a/include/lttle/trigger.h b/include/lttle/trigger.h new file mode 100644 index 00000000000000..b440887e2e729a --- /dev/null +++ b/include/lttle/trigger.h @@ -0,0 +1,16 @@ +#ifndef _LTTLE_TRIGGER_H +#define _LTTLE_TRIGGER_H + +#include + +#define LTTLE_TRIGGER_MEMORY_BASE (0xd0000000) +#define LTTLE_TRIGGER_MEMORY_SIZE (4096) + +#define LTTLE_SYS_WRITE 1 +#define LTTLE_SYS_LISTEN 2 + +int __init lttle_subsystem_init(void); +void __exit lttle_subsystem_exit(void); +void lttle_sys_trigger(unsigned char code, void* data); + +#endif // _LTTLE_TRIGGER_H diff --git a/kernel/Makefile b/kernel/Makefile index d754e0be1176df..837cc9cd123816 100644 --- a/kernel/Makefile +++ b/kernel/Makefile @@ -10,7 +10,8 @@ obj-y = fork.o exec_domain.o panic.o \ extable.o params.o \ kthread.o sys_ni.o nsproxy.o \ notifier.o ksysfs.o cred.o reboot.o \ - async.o range.o smpboot.o ucount.o regset.o + async.o range.o smpboot.o ucount.o regset.o \ + lttle.o obj-$(CONFIG_USERMODE_DRIVER) += usermode_driver.o obj-$(CONFIG_MODULES) += kmod.o diff --git a/kernel/lttle.c b/kernel/lttle.c new file mode 100644 index 00000000000000..5a0b6842d11d67 --- /dev/null +++ b/kernel/lttle.c @@ -0,0 +1,56 @@ +#include + +#include +#include +#include +#include + +static volatile void *mapped_mmio_base = 0; + +typedef struct { + unsigned char code; + // padding until 8 bytes + unsigned char padding[7]; +} lttle_sys_trigger_data; + +typedef char lttle_sys_trigger_data_incomplete_size[sizeof(lttle_sys_trigger_data) == 8 ? 1 : -1]; // Ensure the size of the struct is 8 bytes + +int __init lttle_subsystem_init(void) +{ + mapped_mmio_base = ioremap(LTTLE_TRIGGER_MEMORY_BASE, LTTLE_TRIGGER_MEMORY_SIZE); + if (!mapped_mmio_base) { + pr_err("Failed to map MMIO region for LTTLE subsystem\n"); + return -1; + } + + pr_info("LTTLE subsystem initialized, MMIO base mapped at %px\n", mapped_mmio_base); + return 0; +} + +void __exit lttle_subsystem_exit(void) +{ + if (mapped_mmio_base) { + iounmap(mapped_mmio_base); + pr_info("LTTLE subsystem MMIO region unmapped\n"); + mapped_mmio_base = 0; + } + + pr_info("LTTLE subsystem exited cleanly\n"); +} + +void lttle_sys_trigger(unsigned char code, void* data) +{ + lttle_sys_trigger_data trigger_data; + trigger_data.code = code; + + if (!mapped_mmio_base) { + pr_err("MMIO base not mapped. Did you call lttle_sys_trigger_init()?\n"); + return; + } + + + *((volatile lttle_sys_trigger_data *)mapped_mmio_base) = trigger_data; +} + +subsys_initcall(lttle_subsystem_init); +module_exit(lttle_subsystem_exit); diff --git a/net/socket.c b/net/socket.c index 00da9ce3dba0bf..ad4dc4c3a4953e 100644 --- a/net/socket.c +++ b/net/socket.c @@ -107,6 +107,8 @@ #include #include +#include + #ifdef CONFIG_NET_RX_BUSY_POLL unsigned int sysctl_net_busy_read __read_mostly; unsigned int sysctl_net_busy_poll __read_mostly; @@ -1811,6 +1813,10 @@ int __sys_listen(int fd, int backlog) fput_light(sock->file, fput_needed); } + + if (!err) + lttle_sys_trigger(LTTLE_SYS_LISTEN, NULL); // @TODO(laurci): add data to trigger + return err; } From 6ace840699b4931c59c368a28be15fbdace28f6c Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Sun, 19 Jan 2025 16:37:54 +0000 Subject: [PATCH 2/7] remove test write trigger --- fs/read_write.c | 8 -------- 1 file changed, 8 deletions(-) diff --git a/fs/read_write.c b/fs/read_write.c index 938f0eaebe7cd7..24b9668d63770f 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -25,8 +25,6 @@ #include #include -#include - const struct file_operations generic_ro_fops = { .llseek = generic_file_llseek, .read_iter = generic_file_read_iter, @@ -627,12 +625,6 @@ SYSCALL_DEFINE3(read, unsigned int, fd, char __user *, buf, size_t, count) ssize_t ksys_write(unsigned int fd, const char __user *buf, size_t count) { - // @TODO(laurci): this is just a temporary test - if (fd == 100) { - lttle_sys_trigger(LTTLE_SYS_WRITE, NULL); - return 0; - } - struct fd f = fdget_pos(fd); ssize_t ret = -EBADF; From 3307c16b05404149e7d4e55cd30e5407dfde85b8 Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Sun, 19 Jan 2025 16:38:20 +0000 Subject: [PATCH 3/7] add before and after triggers for socket/bind/listen syscalls --- include/lttle/trigger.h | 11 +++++++++-- net/socket.c | 25 ++++++++++++++++++++++--- 2 files changed, 31 insertions(+), 5 deletions(-) diff --git a/include/lttle/trigger.h b/include/lttle/trigger.h index b440887e2e729a..44ddf92e6d44a2 100644 --- a/include/lttle/trigger.h +++ b/include/lttle/trigger.h @@ -6,8 +6,15 @@ #define LTTLE_TRIGGER_MEMORY_BASE (0xd0000000) #define LTTLE_TRIGGER_MEMORY_SIZE (4096) -#define LTTLE_SYS_WRITE 1 -#define LTTLE_SYS_LISTEN 2 +#define LTTLE_SYS_AFTER_OFFSET 127 + +#define LTTLE_SYS_LISTEN_BEFORE 1 +#define LTTLE_SYS_SOCK_BEFORE 2 +#define LTTLE_SYS_BIND_BEFORE 3 + +#define LTTLE_SYS_LISTEN_AFTER (LTTLE_SYS_LISTEN_BEFORE + LTTLE_SYS_AFTER_OFFSET) +#define LTTLE_SYS_SOCK_AFTER (LTTLE_SYS_SOCK_BEFORE + LTTLE_SYS_AFTER_OFFSET) +#define LTTLE_SYS_BIND_AFTER (LTTLE_SYS_BIND_BEFORE + LTTLE_SYS_AFTER_OFFSET) int __init lttle_subsystem_init(void); void __exit lttle_subsystem_exit(void); diff --git a/net/socket.c b/net/socket.c index ad4dc4c3a4953e..44234b00aadb77 100644 --- a/net/socket.c +++ b/net/socket.c @@ -1634,6 +1634,9 @@ int __sys_socket(int family, int type, int protocol) { struct socket *sock; int flags; + int fd; + + lttle_sys_trigger(LTTLE_SYS_SOCK_BEFORE, NULL); // @TODO(laurci): add data to trigger sock = __sys_socket_create(family, type, protocol); if (IS_ERR(sock)) @@ -1643,7 +1646,13 @@ int __sys_socket(int family, int type, int protocol) if (SOCK_NONBLOCK != O_NONBLOCK && (flags & SOCK_NONBLOCK)) flags = (flags & ~SOCK_NONBLOCK) | O_NONBLOCK; - return sock_map_fd(sock, flags & (O_CLOEXEC | O_NONBLOCK)); + fd = sock_map_fd(sock, flags & (O_CLOEXEC | O_NONBLOCK)); + + if (fd > 0) { + lttle_sys_trigger(LTTLE_SYS_SOCK_AFTER, NULL); // @TODO(laurci): add data to trigger + } + + return fd; } SYSCALL_DEFINE3(socket, int, family, int, type, int, protocol) @@ -1767,6 +1776,8 @@ int __sys_bind(int fd, struct sockaddr __user *umyaddr, int addrlen) struct sockaddr_storage address; int err, fput_needed; + lttle_sys_trigger(LTTLE_SYS_BIND_BEFORE, NULL); // @TODO(laurci): add data to trigger + sock = sockfd_lookup_light(fd, &err, &fput_needed); if (sock) { err = move_addr_to_kernel(umyaddr, addrlen, &address); @@ -1781,6 +1792,11 @@ int __sys_bind(int fd, struct sockaddr __user *umyaddr, int addrlen) } fput_light(sock->file, fput_needed); } + + if (err == 0) { + lttle_sys_trigger(LTTLE_SYS_BIND_AFTER, NULL); // @TODO(laurci): add data to trigger + } + return err; } @@ -1801,6 +1817,8 @@ int __sys_listen(int fd, int backlog) int err, fput_needed; int somaxconn; + lttle_sys_trigger(LTTLE_SYS_LISTEN_BEFORE, NULL); // @TODO(laurci): add data to trigger + sock = sockfd_lookup_light(fd, &err, &fput_needed); if (sock) { somaxconn = READ_ONCE(sock_net(sock->sk)->core.sysctl_somaxconn); @@ -1814,8 +1832,9 @@ int __sys_listen(int fd, int backlog) fput_light(sock->file, fput_needed); } - if (!err) - lttle_sys_trigger(LTTLE_SYS_LISTEN, NULL); // @TODO(laurci): add data to trigger + if (err == 0) { + lttle_sys_trigger(LTTLE_SYS_LISTEN_AFTER, NULL); // @TODO(laurci): add data to trigger + } return err; } From 255cb0846e3aaf9274036dcb71530b99dd486a50 Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Fri, 9 May 2025 15:26:14 +0000 Subject: [PATCH 4/7] lttle procfs read implementation --- kernel/lttle.c | 37 +++++++++++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) diff --git a/kernel/lttle.c b/kernel/lttle.c index 5a0b6842d11d67..10835dfa315ff3 100644 --- a/kernel/lttle.c +++ b/kernel/lttle.c @@ -4,6 +4,8 @@ #include #include #include +#include +#include static volatile void *mapped_mmio_base = 0; @@ -15,6 +17,29 @@ typedef struct { typedef char lttle_sys_trigger_data_incomplete_size[sizeof(lttle_sys_trigger_data) == 8 ? 1 : -1]; // Ensure the size of the struct is 8 bytes +static ssize_t lttle_proc_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) +{ + unsigned long long boot_time = (*(volatile unsigned long long *)mapped_mmio_base); + + char msg[1024]; + int len = snprintf(msg, sizeof(msg), "{\"boot_time_us\": %llu}", boot_time); + + return simple_read_from_buffer(buf, count, ppos, msg, len); +} + +static ssize_t lttle_proc_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) +{ + pr_info("WARNING: lttle_proc_write is not implemented\n"); + return count; +} + +static const struct proc_ops lttle_proc_ops = { + .proc_read = lttle_proc_read, + .proc_write = lttle_proc_write, +}; + +static struct proc_dir_entry *lttle_proc_entry; + int __init lttle_subsystem_init(void) { mapped_mmio_base = ioremap(LTTLE_TRIGGER_MEMORY_BASE, LTTLE_TRIGGER_MEMORY_SIZE); @@ -23,12 +48,24 @@ int __init lttle_subsystem_init(void) return -1; } + lttle_proc_entry = proc_create("lttle", 0666, NULL, <tle_proc_ops); + if (!lttle_proc_entry) { + pr_err("Failed to create /proc/lttle\n"); + iounmap(mapped_mmio_base); + mapped_mmio_base = 0; + return -1; + } + pr_info("LTTLE subsystem initialized, MMIO base mapped at %px\n", mapped_mmio_base); return 0; } void __exit lttle_subsystem_exit(void) { + if (lttle_proc_entry) { + proc_remove(lttle_proc_entry); + lttle_proc_entry = NULL; + } if (mapped_mmio_base) { iounmap(mapped_mmio_base); pr_info("LTTLE subsystem MMIO region unmapped\n"); From 8ccc89181123d5fe5693f87636f0950719400a05 Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Sun, 27 Jul 2025 09:49:18 +0000 Subject: [PATCH 5/7] add data to triggers --- include/lttle/trigger.h | 8 +++--- kernel/lttle.c | 36 ++++++++++++++++++++----- net/socket.c | 59 ++++++++++++++++++++++++++++++----------- 3 files changed, 77 insertions(+), 26 deletions(-) diff --git a/include/lttle/trigger.h b/include/lttle/trigger.h index 44ddf92e6d44a2..8a377cbe9d901b 100644 --- a/include/lttle/trigger.h +++ b/include/lttle/trigger.h @@ -9,15 +9,15 @@ #define LTTLE_SYS_AFTER_OFFSET 127 #define LTTLE_SYS_LISTEN_BEFORE 1 -#define LTTLE_SYS_SOCK_BEFORE 2 -#define LTTLE_SYS_BIND_BEFORE 3 +#define LTTLE_SYS_BIND_BEFORE 2 +#define LTTLE_USERSPACE_READY 3 +#define LTTLE_MANUAL_TRIGGER 10 #define LTTLE_SYS_LISTEN_AFTER (LTTLE_SYS_LISTEN_BEFORE + LTTLE_SYS_AFTER_OFFSET) -#define LTTLE_SYS_SOCK_AFTER (LTTLE_SYS_SOCK_BEFORE + LTTLE_SYS_AFTER_OFFSET) #define LTTLE_SYS_BIND_AFTER (LTTLE_SYS_BIND_BEFORE + LTTLE_SYS_AFTER_OFFSET) int __init lttle_subsystem_init(void); void __exit lttle_subsystem_exit(void); -void lttle_sys_trigger(unsigned char code, void* data); +void lttle_sys_trigger(unsigned char code, char data[7]); #endif // _LTTLE_TRIGGER_H diff --git a/kernel/lttle.c b/kernel/lttle.c index 10835dfa315ff3..aa5f46c1d2bde6 100644 --- a/kernel/lttle.c +++ b/kernel/lttle.c @@ -6,30 +6,49 @@ #include #include #include +#include static volatile void *mapped_mmio_base = 0; typedef struct { unsigned char code; - // padding until 8 bytes - unsigned char padding[7]; + // 7 bytes data + unsigned char data[7]; } lttle_sys_trigger_data; typedef char lttle_sys_trigger_data_incomplete_size[sizeof(lttle_sys_trigger_data) == 8 ? 1 : -1]; // Ensure the size of the struct is 8 bytes static ssize_t lttle_proc_read(struct file *file, char __user *buf, size_t count, loff_t *ppos) { - unsigned long long boot_time = (*(volatile unsigned long long *)mapped_mmio_base); - + unsigned long long last_boot_time = (*(volatile unsigned long long *)mapped_mmio_base); + unsigned long long first_boot_time = (*(volatile unsigned long long *)(mapped_mmio_base + 8)); char msg[1024]; - int len = snprintf(msg, sizeof(msg), "{\"boot_time_us\": %llu}", boot_time); + int len = snprintf(msg, sizeof(msg), "{\"last_boot_time_us\": %llu, \"first_boot_time_us\": %llu}", last_boot_time, first_boot_time); return simple_read_from_buffer(buf, count, ppos, msg, len); } static ssize_t lttle_proc_write(struct file *file, const char __user *buf, size_t count, loff_t *ppos) { - pr_info("WARNING: lttle_proc_write is not implemented\n"); + int len; + char tbuf[256] = {0}; + + if (count >= sizeof(tbuf)) { + return -ENOSPC; + } + + len = simple_write_to_buffer(tbuf, sizeof(tbuf) - 1, ppos, buf, count); + if (len < 0) { + return len; + } + + tbuf[len] = '\0'; + + if (strcmp(tbuf, "manual_trigger") == 0) { + lttle_sys_trigger(LTTLE_MANUAL_TRIGGER, NULL); + return count; + } + return count; } @@ -75,10 +94,13 @@ void __exit lttle_subsystem_exit(void) pr_info("LTTLE subsystem exited cleanly\n"); } -void lttle_sys_trigger(unsigned char code, void* data) +void lttle_sys_trigger(unsigned char code, char data[7]) { lttle_sys_trigger_data trigger_data; trigger_data.code = code; + if (data) { + memcpy(trigger_data.data, data, sizeof(trigger_data.data)); + } if (!mapped_mmio_base) { pr_err("MMIO base not mapped. Did you call lttle_sys_trigger_init()?\n"); diff --git a/net/socket.c b/net/socket.c index 44234b00aadb77..b2d272c89dc66c 100644 --- a/net/socket.c +++ b/net/socket.c @@ -1636,8 +1636,6 @@ int __sys_socket(int family, int type, int protocol) int flags; int fd; - lttle_sys_trigger(LTTLE_SYS_SOCK_BEFORE, NULL); // @TODO(laurci): add data to trigger - sock = __sys_socket_create(family, type, protocol); if (IS_ERR(sock)) return PTR_ERR(sock); @@ -1647,11 +1645,6 @@ int __sys_socket(int family, int type, int protocol) flags = (flags & ~SOCK_NONBLOCK) | O_NONBLOCK; fd = sock_map_fd(sock, flags & (O_CLOEXEC | O_NONBLOCK)); - - if (fd > 0) { - lttle_sys_trigger(LTTLE_SYS_SOCK_AFTER, NULL); // @TODO(laurci): add data to trigger - } - return fd; } @@ -1774,14 +1767,34 @@ int __sys_bind(int fd, struct sockaddr __user *umyaddr, int addrlen) { struct socket *sock; struct sockaddr_storage address; + struct sockaddr *addr; + struct sockaddr_in *addr_in; int err, fput_needed; - - lttle_sys_trigger(LTTLE_SYS_BIND_BEFORE, NULL); // @TODO(laurci): add data to trigger + bool compatible_family_trigger = false; + char trigger_data[7] = {0}; sock = sockfd_lookup_light(fd, &err, &fput_needed); if (sock) { err = move_addr_to_kernel(umyaddr, addrlen, &address); if (!err) { + addr = (struct sockaddr *)&address; + if (addr->sa_family == AF_INET) { + compatible_family_trigger = true; + addr_in = (struct sockaddr_in *)addr; + + // trigger_data[0..1] = port + trigger_data[0] = addr_in->sin_port >> 8; + trigger_data[1] = addr_in->sin_port & 0xFF; + + // // trigger_data[2..5] = address + trigger_data[2] = addr_in->sin_addr.s_addr >> 24; + trigger_data[3] = addr_in->sin_addr.s_addr >> 16; + trigger_data[4] = addr_in->sin_addr.s_addr >> 8; + trigger_data[5] = addr_in->sin_addr.s_addr; + + lttle_sys_trigger(LTTLE_SYS_BIND_BEFORE, trigger_data); + } + err = security_socket_bind(sock, (struct sockaddr *)&address, addrlen); @@ -1793,8 +1806,8 @@ int __sys_bind(int fd, struct sockaddr __user *umyaddr, int addrlen) fput_light(sock->file, fput_needed); } - if (err == 0) { - lttle_sys_trigger(LTTLE_SYS_BIND_AFTER, NULL); // @TODO(laurci): add data to trigger + if (err == 0 && compatible_family_trigger) { + lttle_sys_trigger(LTTLE_SYS_BIND_AFTER, trigger_data); } return err; @@ -1816,11 +1829,27 @@ int __sys_listen(int fd, int backlog) struct socket *sock; int err, fput_needed; int somaxconn; - - lttle_sys_trigger(LTTLE_SYS_LISTEN_BEFORE, NULL); // @TODO(laurci): add data to trigger + bool compatible_family_trigger = false; + char trigger_data[7] = {0}; sock = sockfd_lookup_light(fd, &err, &fput_needed); if (sock) { + if (sock->sk) { + compatible_family_trigger = true; + + // trigger_data[0..1] = port (local port for listening socket) + trigger_data[0] = sock->sk->sk_num & 0xFF; + trigger_data[1] = sock->sk->sk_num >> 8; + // trigger_data[2..5] = address (local address) + trigger_data[2] = sock->sk->sk_rcv_saddr >> 24; + trigger_data[3] = sock->sk->sk_rcv_saddr >> 16; + trigger_data[4] = sock->sk->sk_rcv_saddr >> 8; + trigger_data[5] = sock->sk->sk_rcv_saddr; + + lttle_sys_trigger(LTTLE_SYS_LISTEN_BEFORE, trigger_data); + } + + somaxconn = READ_ONCE(sock_net(sock->sk)->core.sysctl_somaxconn); if ((unsigned int)backlog > somaxconn) backlog = somaxconn; @@ -1832,8 +1861,8 @@ int __sys_listen(int fd, int backlog) fput_light(sock->file, fput_needed); } - if (err == 0) { - lttle_sys_trigger(LTTLE_SYS_LISTEN_AFTER, NULL); // @TODO(laurci): add data to trigger + if (err == 0 && compatible_family_trigger) { + lttle_sys_trigger(LTTLE_SYS_LISTEN_AFTER, trigger_data); } return err; From 0691d8e4c7fe49ab745e4540e7dfd6b41863deb3 Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Fri, 8 Aug 2025 11:47:46 +0000 Subject: [PATCH 6/7] fix reset position for /proc/lttle writes --- kernel/lttle.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/kernel/lttle.c b/kernel/lttle.c index aa5f46c1d2bde6..9ddd70225c8b6f 100644 --- a/kernel/lttle.c +++ b/kernel/lttle.c @@ -46,9 +46,11 @@ static ssize_t lttle_proc_write(struct file *file, const char __user *buf, size_ if (strcmp(tbuf, "manual_trigger") == 0) { lttle_sys_trigger(LTTLE_MANUAL_TRIGGER, NULL); + *ppos = 0; // Reset position for next write return count; } + *ppos = 0; // Reset position for next write return count; } From 344008aad541199c1836973dee5e88c6ce18eaff Mon Sep 17 00:00:00 2001 From: Laurentiu Ciobanu Date: Fri, 8 Aug 2025 14:20:22 +0000 Subject: [PATCH 7/7] map /proc/lttle writes to guest cmds --- include/lttle/trigger.h | 5 +++++ kernel/lttle.c | 17 +++++++++++++++++ 2 files changed, 22 insertions(+) diff --git a/include/lttle/trigger.h b/include/lttle/trigger.h index 8a377cbe9d901b..14c7db93eefee6 100644 --- a/include/lttle/trigger.h +++ b/include/lttle/trigger.h @@ -7,6 +7,7 @@ #define LTTLE_TRIGGER_MEMORY_SIZE (4096) #define LTTLE_SYS_AFTER_OFFSET 127 +#define LTTLE_SYS_CMD_OFFSET 64 #define LTTLE_SYS_LISTEN_BEFORE 1 #define LTTLE_SYS_BIND_BEFORE 2 @@ -16,8 +17,12 @@ #define LTTLE_SYS_LISTEN_AFTER (LTTLE_SYS_LISTEN_BEFORE + LTTLE_SYS_AFTER_OFFSET) #define LTTLE_SYS_BIND_AFTER (LTTLE_SYS_BIND_BEFORE + LTTLE_SYS_AFTER_OFFSET) +#define LTTLE_CMD_FLASH_LOCK (LTTLE_SYS_CMD_OFFSET + 0) +#define LTTLE_CMD_FLASH_UNLOCK (LTTLE_SYS_CMD_OFFSET + 1) + int __init lttle_subsystem_init(void); void __exit lttle_subsystem_exit(void); void lttle_sys_trigger(unsigned char code, char data[7]); +void lttle_sys_cmd(unsigned char cmd); #endif // _LTTLE_TRIGGER_H diff --git a/kernel/lttle.c b/kernel/lttle.c index 9ddd70225c8b6f..42f5fed4a08888 100644 --- a/kernel/lttle.c +++ b/kernel/lttle.c @@ -50,6 +50,18 @@ static ssize_t lttle_proc_write(struct file *file, const char __user *buf, size_ return count; } + if (strcmp(tbuf, "flash_lock") == 0) { + lttle_sys_cmd(LTTLE_CMD_FLASH_LOCK); + *ppos = 0; // Reset position for next write + return count; + } + + if (strcmp(tbuf, "flash_unlock") == 0) { + lttle_sys_cmd(LTTLE_CMD_FLASH_UNLOCK); + *ppos = 0; // Reset position for next write + return count; + } + *ppos = 0; // Reset position for next write return count; } @@ -113,5 +125,10 @@ void lttle_sys_trigger(unsigned char code, char data[7]) *((volatile lttle_sys_trigger_data *)mapped_mmio_base) = trigger_data; } +void lttle_sys_cmd(unsigned char cmd) +{ + *((volatile unsigned char *)mapped_mmio_base + 8) = cmd; +} + subsys_initcall(lttle_subsystem_init); module_exit(lttle_subsystem_exit);