firmware/br-ext-chip-goke/board/gk7205v200/kernel/patches/00_drivers-tty-vt-selection...

101 lines
2.3 KiB
Diff

--- linux-4.9.37/drivers/tty/vt/selection.c 2017-07-12 16:42:41.000000000 +0300
+++ linux-4.9.y/drivers/tty/vt/selection.c 2021-06-07 13:01:34.000000000 +0300
@@ -13,6 +13,7 @@
#include <linux/tty.h>
#include <linux/sched.h>
#include <linux/mm.h>
+#include <linux/mutex.h>
#include <linux/slab.h>
#include <linux/types.h>
@@ -40,6 +41,7 @@
static int sel_end;
static int sel_buffer_lth;
static char *sel_buffer;
+static DEFINE_MUTEX(sel_lock);
/* clear_selection, highlight and highlight_pointer can be called
from interrupt (via scrollback/front) */
@@ -163,7 +165,7 @@
char *bp, *obp;
int i, ps, pe, multiplier;
u16 c;
- int mode;
+ int mode, ret = 0;
poke_blanked_console();
@@ -203,6 +205,7 @@
pe = tmp;
}
+ mutex_lock(&sel_lock);
if (sel_cons != vc_cons[fg_console].d) {
clear_selection();
sel_cons = vc_cons[fg_console].d;
@@ -248,9 +251,10 @@
break;
case TIOCL_SELPOINTER:
highlight_pointer(pe);
- return 0;
+ goto unlock;
default:
- return -EINVAL;
+ ret = -EINVAL;
+ goto unlock;
}
/* remove the pointer */
@@ -272,7 +276,7 @@
else if (new_sel_start == sel_start)
{
if (new_sel_end == sel_end) /* no action required */
- return 0;
+ goto unlock;
else if (new_sel_end > sel_end) /* extend to right */
highlight(sel_end + 2, new_sel_end);
else /* contract from right */
@@ -299,7 +303,8 @@
if (!bp) {
printk(KERN_WARNING "selection: kmalloc() failed\n");
clear_selection();
- return -ENOMEM;
+ ret = -ENOMEM;
+ goto unlock;
}
kfree(sel_buffer);
sel_buffer = bp;
@@ -324,7 +329,9 @@
}
}
sel_buffer_lth = bp - sel_buffer;
- return 0;
+unlock:
+ mutex_unlock(&sel_lock);
+ return ret;
}
/* Insert the contents of the selection buffer into the
@@ -352,10 +359,13 @@
tty_buffer_lock_exclusive(&vc->port);
add_wait_queue(&vc->paste_wait, &wait);
+ mutex_lock(&sel_lock);
while (sel_buffer && sel_buffer_lth > pasted) {
set_current_state(TASK_INTERRUPTIBLE);
if (tty_throttled(tty)) {
+ mutex_unlock(&sel_lock);
schedule();
+ mutex_lock(&sel_lock);
continue;
}
__set_current_state(TASK_RUNNING);
@@ -364,6 +374,7 @@
count);
pasted += count;
}
+ mutex_unlock(&sel_lock);
remove_wait_queue(&vc->paste_wait, &wait);
__set_current_state(TASK_RUNNING);