fix on rt-tests of backfire kernel module

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi all,
I'm new in this mailing list. I start to work/test PREEPT_RT and
making some test I seee that there is a bug on backfire module in
rt-tests repository.

I'm attaching my patch.

best regards.
Michele
From cd94ede8cf9eb8c26a196ea0111220969451cbb2 Mon Sep 17 00:00:00 2001
From: Michele Dionisio <michele.dionisio@xxxxxxxxxxxx>
Date: Tue, 26 Sep 2017 14:32:51 +0200
Subject: [FIX] fix copy data to and from userspace


diff --git a/src/backfire/backfire.c b/src/backfire/backfire.c
index aaf9c4a..b38651b 100644
--- a/src/backfire/backfire.c
+++ b/src/backfire/backfire.c
@@ -20,11 +20,9 @@
  */
 
 #include <linux/module.h>
-
 #include <linux/sched.h>
 #include <linux/cpumask.h>
 #include <linux/time.h>
-#include <linux/smp_lock.h>
 #include <linux/types.h>
 #include <linux/errno.h>
 #include <linux/miscdevice.h>
@@ -32,25 +30,33 @@
 #include <linux/spinlock.h>
 
 #include <asm/uaccess.h>
-#include <asm/system.h>
 
 #define BACKFIRE_MINOR MISC_DYNAMIC_MINOR
 
-static spinlock_t backfire_state_lock = SPIN_LOCK_UNLOCKED;
+static DEFINE_SPINLOCK(backfire_state_lock);
 static int backfire_open_cnt; /* #times opened */
 static int backfire_open_mode; /* special open modes */
 static struct timeval sendtime; /* when the most recent signal was sent */
 #define BACKFIRE_WRITE 1 /* opened for writing (exclusive) */
 #define BACKFIRE_EXCL 2 /* opened with O_EXCL */
 
+#define MAX_SIZE_DATA_RW 512
+
 /*
  * These are the file operation function for user access to /dev/backfire
  */
 static ssize_t
 backfire_read(struct file *file, char *buf, size_t count, loff_t *ppos)
 {
-	return snprintf(buf, count, "%d,%d\n", (int) sendtime.tv_sec,
+    char kbuf[MAX_SIZE_DATA_RW];
+    ssize_t res;
+    if (count > MAX_SIZE_DATA_RW) {
+        count = MAX_SIZE_DATA_RW;
+    }
+	res = snprintf(kbuf, count, "%d,%d\n", (int) sendtime.tv_sec,
 		(int) sendtime.tv_usec);
+    copy_to_user(buf, kbuf, res+1);
+    return res;
 }
 
 static ssize_t
@@ -58,16 +64,28 @@ backfire_write(struct file *file, const char *buf, size_t count, loff_t *ppos)
 {
 	int signo;
 	struct pid *pid;
-
-	if (sscanf(buf, "%d", &signo) >= 1) {
+    char kbuf[MAX_SIZE_DATA_RW+1];
+    ssize_t retval = 0;
+    
+    if (count == 0) {
+        return 0;
+    }
+    if (count > MAX_SIZE_DATA_RW) {
+        count = MAX_SIZE_DATA_RW;
+    }
+    copy_from_user(kbuf, buf, count);
+    kbuf[count] = '\0';
+
+	if (sscanf(kbuf, "%d", &signo) >= 1) {
 		if (signo > 0 && signo < 32) {
 			pid = get_pid(task_pid(current));
 			do_gettimeofday(&sendtime);
 			kill_pid(pid, signo, 1);
+            retval = strlen(kbuf);
 		} else
 			printk(KERN_ERR "Invalid signal no. %d\n", signo);
 	}
-	return strlen(buf);
+	return retval;
 }
 
 static int

[Index of Archives]     [RT Stable]     [Kernel Newbies]     [IDE]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux ATA RAID]     [Samba]     [Video 4 Linux]     [Device Mapper]

  Powered by Linux