aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/misc
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2014-04-01 19:13:21 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2014-04-01 19:13:21 -0400
commit675c354a95d5375153b8bb80a0448cab916c7991 (patch)
tree88cbc5a5a31dd1c1016271006a8d56cfe0abf7bd /drivers/misc
parentc70929147a10fa4538886cb23b934b509c4c0e49 (diff)
parent1b3fa22e0234d613df967445cd34807e10fa54fa (diff)
Merge tag 'char-misc-3.15-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc
Pull char/misc driver patches from Greg KH: "Here's the big char/misc driver updates for 3.15-rc1. Lots of various things here, including the new mcb driver subsystem. All of these have been in linux-next for a while" * tag 'char-misc-3.15-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc: (118 commits) extcon: Move OF helper function to extcon core and change function name extcon: of: Remove unnecessary function call by using the name of device_node extcon: gpio: Use SIMPLE_DEV_PM_OPS macro extcon: palmas: Use SIMPLE_DEV_PM_OPS macro mei: don't use deprecated DEFINE_PCI_DEVICE_TABLE macro mei: amthif: fix checkpatch error mei: client.h fix checkpatch errors mei: use cl_dbg where appropriate mei: fix Unnecessary space after function pointer name mei: report consistently copy_from/to_user failures mei: drop pr_fmt macros mei: make me hw headers private to me hw. mei: fix memory leak of pending write cb objects mei: me: do not reset when less than expected data is received drivers: mcb: Fix build error discovered by 0-day bot cs5535-mfgpt: Simplify dependencies spmi: pm: drop bus-level PM suspend/resume routines spmi: pmic_arb: make selectable on ARCH_QCOM Drivers: hv: vmbus: Increase the limit on the number of pfns we can handle pch_phub: Report error writing MAC back to user ...
Diffstat (limited to 'drivers/misc')
-rw-r--r--drivers/misc/Kconfig2
-rw-r--r--drivers/misc/ad525x_dpot.c1
-rw-r--r--drivers/misc/apds9802als.c1
-rw-r--r--drivers/misc/bmp085.c1
-rw-r--r--drivers/misc/carma/carma-fpga.c1
-rw-r--r--drivers/misc/ds1682.c1
-rw-r--r--drivers/misc/eeprom/at25.c1
-rw-r--r--drivers/misc/eeprom/eeprom.c1
-rw-r--r--drivers/misc/eeprom/eeprom_93xx46.c1
-rw-r--r--drivers/misc/eeprom/max6875.c1
-rw-r--r--drivers/misc/eeprom/sunxi_sid.c3
-rw-r--r--drivers/misc/genwqe/card_debugfs.c1
-rw-r--r--drivers/misc/hmc6352.c1
-rw-r--r--drivers/misc/isl29003.c1
-rw-r--r--drivers/misc/isl29020.c1
-rw-r--r--drivers/misc/lattice-ecp3-config.c1
-rw-r--r--drivers/misc/lis3lv02d/lis3lv02d.c1
-rw-r--r--drivers/misc/lis3lv02d/lis3lv02d_i2c.c1
-rw-r--r--drivers/misc/lis3lv02d/lis3lv02d_spi.c1
-rw-r--r--drivers/misc/lkdtm.c74
-rw-r--r--drivers/misc/mei/Kconfig9
-rw-r--r--drivers/misc/mei/Makefile6
-rw-r--r--drivers/misc/mei/amthif.c72
-rw-r--r--drivers/misc/mei/bus.c21
-rw-r--r--drivers/misc/mei/client.c300
-rw-r--r--drivers/misc/mei/client.h30
-rw-r--r--drivers/misc/mei/debugfs.c54
-rw-r--r--drivers/misc/mei/hbm.c281
-rw-r--r--drivers/misc/mei/hbm.h1
-rw-r--r--drivers/misc/mei/hw-me.c30
-rw-r--r--drivers/misc/mei/hw-txe-regs.h294
-rw-r--r--drivers/misc/mei/hw-txe.c1107
-rw-r--r--drivers/misc/mei/hw-txe.h74
-rw-r--r--drivers/misc/mei/hw.h20
-rw-r--r--drivers/misc/mei/init.c43
-rw-r--r--drivers/misc/mei/interrupt.c159
-rw-r--r--drivers/misc/mei/main.c23
-rw-r--r--drivers/misc/mei/mei_dev.h54
-rw-r--r--drivers/misc/mei/nfc.c14
-rw-r--r--drivers/misc/mei/pci-me.c14
-rw-r--r--drivers/misc/mei/pci-txe.c293
-rw-r--r--drivers/misc/mei/wd.c136
-rw-r--r--drivers/misc/mic/host/mic_intr.c2
-rw-r--r--drivers/misc/pch_phub.c5
-rw-r--r--drivers/misc/sram.c127
-rw-r--r--drivers/misc/ti-st/st_core.c1
-rw-r--r--drivers/misc/ti_dac7512.c1
-rw-r--r--drivers/misc/tsl2550.c1
-rw-r--r--drivers/misc/vmw_vmci/vmci_guest.c7
49 files changed, 2671 insertions, 604 deletions
diff --git a/drivers/misc/Kconfig b/drivers/misc/Kconfig
index 6cb388e8fb7d..809afebe0dad 100644
--- a/drivers/misc/Kconfig
+++ b/drivers/misc/Kconfig
@@ -235,7 +235,7 @@ config SGI_XP
235 235
236config CS5535_MFGPT 236config CS5535_MFGPT
237 tristate "CS5535/CS5536 Geode Multi-Function General Purpose Timer (MFGPT) support" 237 tristate "CS5535/CS5536 Geode Multi-Function General Purpose Timer (MFGPT) support"
238 depends on PCI && X86 && MFD_CS5535 238 depends on MFD_CS5535
239 default n 239 default n
240 help 240 help
241 This driver provides access to MFGPT functionality for other 241 This driver provides access to MFGPT functionality for other
diff --git a/drivers/misc/ad525x_dpot.c b/drivers/misc/ad525x_dpot.c
index d3eee113baeb..a43053daad0e 100644
--- a/drivers/misc/ad525x_dpot.c
+++ b/drivers/misc/ad525x_dpot.c
@@ -72,7 +72,6 @@
72#include <linux/module.h> 72#include <linux/module.h>
73#include <linux/device.h> 73#include <linux/device.h>
74#include <linux/kernel.h> 74#include <linux/kernel.h>
75#include <linux/init.h>
76#include <linux/delay.h> 75#include <linux/delay.h>
77#include <linux/slab.h> 76#include <linux/slab.h>
78 77
diff --git a/drivers/misc/apds9802als.c b/drivers/misc/apds9802als.c
index 0c6e037153d2..c6cc3dc8ae1f 100644
--- a/drivers/misc/apds9802als.c
+++ b/drivers/misc/apds9802als.c
@@ -22,7 +22,6 @@
22 */ 22 */
23 23
24#include <linux/module.h> 24#include <linux/module.h>
25#include <linux/init.h>
26#include <linux/slab.h> 25#include <linux/slab.h>
27#include <linux/i2c.h> 26#include <linux/i2c.h>
28#include <linux/err.h> 27#include <linux/err.h>
diff --git a/drivers/misc/bmp085.c b/drivers/misc/bmp085.c
index 820e53d0048f..9b313f7810f5 100644
--- a/drivers/misc/bmp085.c
+++ b/drivers/misc/bmp085.c
@@ -47,7 +47,6 @@
47 47
48#include <linux/module.h> 48#include <linux/module.h>
49#include <linux/device.h> 49#include <linux/device.h>
50#include <linux/init.h>
51#include <linux/slab.h> 50#include <linux/slab.h>
52#include <linux/of.h> 51#include <linux/of.h>
53#include "bmp085.h" 52#include "bmp085.h"
diff --git a/drivers/misc/carma/carma-fpga.c b/drivers/misc/carma/carma-fpga.c
index 9e2b985293fc..14d90eae605b 100644
--- a/drivers/misc/carma/carma-fpga.c
+++ b/drivers/misc/carma/carma-fpga.c
@@ -101,7 +101,6 @@
101#include <linux/kernel.h> 101#include <linux/kernel.h>
102#include <linux/module.h> 102#include <linux/module.h>
103#include <linux/poll.h> 103#include <linux/poll.h>
104#include <linux/init.h>
105#include <linux/slab.h> 104#include <linux/slab.h>
106#include <linux/kref.h> 105#include <linux/kref.h>
107#include <linux/io.h> 106#include <linux/io.h>
diff --git a/drivers/misc/ds1682.c b/drivers/misc/ds1682.c
index 154b02e5094f..6a672f9ef522 100644
--- a/drivers/misc/ds1682.c
+++ b/drivers/misc/ds1682.c
@@ -32,7 +32,6 @@
32 */ 32 */
33 33
34#include <linux/module.h> 34#include <linux/module.h>
35#include <linux/init.h>
36#include <linux/i2c.h> 35#include <linux/i2c.h>
37#include <linux/string.h> 36#include <linux/string.h>
38#include <linux/list.h> 37#include <linux/list.h>
diff --git a/drivers/misc/eeprom/at25.c b/drivers/misc/eeprom/at25.c
index 4f3bca1003a1..634f72929e12 100644
--- a/drivers/misc/eeprom/at25.c
+++ b/drivers/misc/eeprom/at25.c
@@ -10,7 +10,6 @@
10 */ 10 */
11 11
12#include <linux/kernel.h> 12#include <linux/kernel.h>
13#include <linux/init.h>
14#include <linux/module.h> 13#include <linux/module.h>
15#include <linux/slab.h> 14#include <linux/slab.h>
16#include <linux/delay.h> 15#include <linux/delay.h>
diff --git a/drivers/misc/eeprom/eeprom.c b/drivers/misc/eeprom/eeprom.c
index f0fa4e8ca124..33f8673d23a6 100644
--- a/drivers/misc/eeprom/eeprom.c
+++ b/drivers/misc/eeprom/eeprom.c
@@ -17,7 +17,6 @@
17 */ 17 */
18 18
19#include <linux/kernel.h> 19#include <linux/kernel.h>
20#include <linux/init.h>
21#include <linux/module.h> 20#include <linux/module.h>
22#include <linux/slab.h> 21#include <linux/slab.h>
23#include <linux/jiffies.h> 22#include <linux/jiffies.h>
diff --git a/drivers/misc/eeprom/eeprom_93xx46.c b/drivers/misc/eeprom/eeprom_93xx46.c
index 78e55b501c94..9ebeacdb8ec4 100644
--- a/drivers/misc/eeprom/eeprom_93xx46.c
+++ b/drivers/misc/eeprom/eeprom_93xx46.c
@@ -11,7 +11,6 @@
11#include <linux/delay.h> 11#include <linux/delay.h>
12#include <linux/device.h> 12#include <linux/device.h>
13#include <linux/kernel.h> 13#include <linux/kernel.h>
14#include <linux/init.h>
15#include <linux/module.h> 14#include <linux/module.h>
16#include <linux/mutex.h> 15#include <linux/mutex.h>
17#include <linux/slab.h> 16#include <linux/slab.h>
diff --git a/drivers/misc/eeprom/max6875.c b/drivers/misc/eeprom/max6875.c
index e36157d5d3ab..580ff9df5529 100644
--- a/drivers/misc/eeprom/max6875.c
+++ b/drivers/misc/eeprom/max6875.c
@@ -27,7 +27,6 @@
27 */ 27 */
28 28
29#include <linux/kernel.h> 29#include <linux/kernel.h>
30#include <linux/init.h>
31#include <linux/module.h> 30#include <linux/module.h>
32#include <linux/slab.h> 31#include <linux/slab.h>
33#include <linux/i2c.h> 32#include <linux/i2c.h>
diff --git a/drivers/misc/eeprom/sunxi_sid.c b/drivers/misc/eeprom/sunxi_sid.c
index 9c34e5704304..3f2b625b2032 100644
--- a/drivers/misc/eeprom/sunxi_sid.c
+++ b/drivers/misc/eeprom/sunxi_sid.c
@@ -21,7 +21,6 @@
21#include <linux/err.h> 21#include <linux/err.h>
22#include <linux/export.h> 22#include <linux/export.h>
23#include <linux/fs.h> 23#include <linux/fs.h>
24#include <linux/init.h>
25#include <linux/io.h> 24#include <linux/io.h>
26#include <linux/kernel.h> 25#include <linux/kernel.h>
27#include <linux/kobject.h> 26#include <linux/kobject.h>
@@ -96,7 +95,7 @@ static int sunxi_sid_remove(struct platform_device *pdev)
96} 95}
97 96
98static const struct of_device_id sunxi_sid_of_match[] = { 97static const struct of_device_id sunxi_sid_of_match[] = {
99 { .compatible = "allwinner,sun4i-sid", .data = (void *)16}, 98 { .compatible = "allwinner,sun4i-a10-sid", .data = (void *)16},
100 { .compatible = "allwinner,sun7i-a20-sid", .data = (void *)512}, 99 { .compatible = "allwinner,sun7i-a20-sid", .data = (void *)512},
101 {/* sentinel */}, 100 {/* sentinel */},
102}; 101};
diff --git a/drivers/misc/genwqe/card_debugfs.c b/drivers/misc/genwqe/card_debugfs.c
index 3bfdc07a7248..50d2096ea1c7 100644
--- a/drivers/misc/genwqe/card_debugfs.c
+++ b/drivers/misc/genwqe/card_debugfs.c
@@ -26,7 +26,6 @@
26 26
27#include <linux/module.h> 27#include <linux/module.h>
28#include <linux/kernel.h> 28#include <linux/kernel.h>
29#include <linux/init.h>
30#include <linux/debugfs.h> 29#include <linux/debugfs.h>
31#include <linux/seq_file.h> 30#include <linux/seq_file.h>
32#include <linux/uaccess.h> 31#include <linux/uaccess.h>
diff --git a/drivers/misc/hmc6352.c b/drivers/misc/hmc6352.c
index 170bd3daf336..90520d76633f 100644
--- a/drivers/misc/hmc6352.c
+++ b/drivers/misc/hmc6352.c
@@ -22,7 +22,6 @@
22 */ 22 */
23 23
24#include <linux/module.h> 24#include <linux/module.h>
25#include <linux/init.h>
26#include <linux/slab.h> 25#include <linux/slab.h>
27#include <linux/i2c.h> 26#include <linux/i2c.h>
28#include <linux/err.h> 27#include <linux/err.h>
diff --git a/drivers/misc/isl29003.c b/drivers/misc/isl29003.c
index e3183f26216b..12c30b486b27 100644
--- a/drivers/misc/isl29003.c
+++ b/drivers/misc/isl29003.c
@@ -26,7 +26,6 @@
26 */ 26 */
27 27
28#include <linux/module.h> 28#include <linux/module.h>
29#include <linux/init.h>
30#include <linux/slab.h> 29#include <linux/slab.h>
31#include <linux/i2c.h> 30#include <linux/i2c.h>
32#include <linux/mutex.h> 31#include <linux/mutex.h>
diff --git a/drivers/misc/isl29020.c b/drivers/misc/isl29020.c
index b7f84dacf822..4a9c50a43afb 100644
--- a/drivers/misc/isl29020.c
+++ b/drivers/misc/isl29020.c
@@ -23,7 +23,6 @@
23 */ 23 */
24 24
25#include <linux/module.h> 25#include <linux/module.h>
26#include <linux/init.h>
27#include <linux/slab.h> 26#include <linux/slab.h>
28#include <linux/i2c.h> 27#include <linux/i2c.h>
29#include <linux/err.h> 28#include <linux/err.h>
diff --git a/drivers/misc/lattice-ecp3-config.c b/drivers/misc/lattice-ecp3-config.c
index 61fbe6acabef..0a1565e63c71 100644
--- a/drivers/misc/lattice-ecp3-config.c
+++ b/drivers/misc/lattice-ecp3-config.c
@@ -12,7 +12,6 @@
12#include <linux/module.h> 12#include <linux/module.h>
13#include <linux/errno.h> 13#include <linux/errno.h>
14#include <linux/kernel.h> 14#include <linux/kernel.h>
15#include <linux/init.h>
16#include <linux/spi/spi.h> 15#include <linux/spi/spi.h>
17#include <linux/platform_device.h> 16#include <linux/platform_device.h>
18#include <linux/delay.h> 17#include <linux/delay.h>
diff --git a/drivers/misc/lis3lv02d/lis3lv02d.c b/drivers/misc/lis3lv02d/lis3lv02d.c
index 036effe9a795..3ef4627f9cb1 100644
--- a/drivers/misc/lis3lv02d/lis3lv02d.c
+++ b/drivers/misc/lis3lv02d/lis3lv02d.c
@@ -23,7 +23,6 @@
23#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 23#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
24 24
25#include <linux/kernel.h> 25#include <linux/kernel.h>
26#include <linux/init.h>
27#include <linux/dmi.h> 26#include <linux/dmi.h>
28#include <linux/module.h> 27#include <linux/module.h>
29#include <linux/types.h> 28#include <linux/types.h>
diff --git a/drivers/misc/lis3lv02d/lis3lv02d_i2c.c b/drivers/misc/lis3lv02d/lis3lv02d_i2c.c
index 7c97550240f1..d324f8a97b88 100644
--- a/drivers/misc/lis3lv02d/lis3lv02d_i2c.c
+++ b/drivers/misc/lis3lv02d/lis3lv02d_i2c.c
@@ -26,7 +26,6 @@
26 26
27#include <linux/module.h> 27#include <linux/module.h>
28#include <linux/kernel.h> 28#include <linux/kernel.h>
29#include <linux/init.h>
30#include <linux/err.h> 29#include <linux/err.h>
31#include <linux/i2c.h> 30#include <linux/i2c.h>
32#include <linux/pm_runtime.h> 31#include <linux/pm_runtime.h>
diff --git a/drivers/misc/lis3lv02d/lis3lv02d_spi.c b/drivers/misc/lis3lv02d/lis3lv02d_spi.c
index 9aa2bd2a71ae..bd06d0cfac45 100644
--- a/drivers/misc/lis3lv02d/lis3lv02d_spi.c
+++ b/drivers/misc/lis3lv02d/lis3lv02d_spi.c
@@ -10,7 +10,6 @@
10 10
11#include <linux/module.h> 11#include <linux/module.h>
12#include <linux/kernel.h> 12#include <linux/kernel.h>
13#include <linux/init.h>
14#include <linux/err.h> 13#include <linux/err.h>
15#include <linux/input.h> 14#include <linux/input.h>
16#include <linux/interrupt.h> 15#include <linux/interrupt.h>
diff --git a/drivers/misc/lkdtm.c b/drivers/misc/lkdtm.c
index 49c7a23f02fc..d66a2f24f6b3 100644
--- a/drivers/misc/lkdtm.c
+++ b/drivers/misc/lkdtm.c
@@ -30,6 +30,7 @@
30 * 30 *
31 * See Documentation/fault-injection/provoke-crashes.txt for instructions 31 * See Documentation/fault-injection/provoke-crashes.txt for instructions
32 */ 32 */
33#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
33 34
34#include <linux/kernel.h> 35#include <linux/kernel.h>
35#include <linux/fs.h> 36#include <linux/fs.h>
@@ -45,6 +46,7 @@
45#include <linux/debugfs.h> 46#include <linux/debugfs.h>
46#include <linux/vmalloc.h> 47#include <linux/vmalloc.h>
47#include <linux/mman.h> 48#include <linux/mman.h>
49#include <asm/cacheflush.h>
48 50
49#ifdef CONFIG_IDE 51#ifdef CONFIG_IDE
50#include <linux/ide.h> 52#include <linux/ide.h>
@@ -101,6 +103,7 @@ enum ctype {
101 CT_EXEC_USERSPACE, 103 CT_EXEC_USERSPACE,
102 CT_ACCESS_USERSPACE, 104 CT_ACCESS_USERSPACE,
103 CT_WRITE_RO, 105 CT_WRITE_RO,
106 CT_WRITE_KERN,
104}; 107};
105 108
106static char* cp_name[] = { 109static char* cp_name[] = {
@@ -137,6 +140,7 @@ static char* cp_type[] = {
137 "EXEC_USERSPACE", 140 "EXEC_USERSPACE",
138 "ACCESS_USERSPACE", 141 "ACCESS_USERSPACE",
139 "WRITE_RO", 142 "WRITE_RO",
143 "WRITE_KERN",
140}; 144};
141 145
142static struct jprobe lkdtm; 146static struct jprobe lkdtm;
@@ -316,6 +320,13 @@ static void do_nothing(void)
316 return; 320 return;
317} 321}
318 322
323/* Must immediately follow do_nothing for size calculuations to work out. */
324static void do_overwritten(void)
325{
326 pr_info("do_overwritten wasn't overwritten!\n");
327 return;
328}
329
319static noinline void corrupt_stack(void) 330static noinline void corrupt_stack(void)
320{ 331{
321 /* Use default char array length that triggers stack protection. */ 332 /* Use default char array length that triggers stack protection. */
@@ -328,7 +339,12 @@ static void execute_location(void *dst)
328{ 339{
329 void (*func)(void) = dst; 340 void (*func)(void) = dst;
330 341
342 pr_info("attempting ok execution at %p\n", do_nothing);
343 do_nothing();
344
331 memcpy(dst, do_nothing, EXEC_SIZE); 345 memcpy(dst, do_nothing, EXEC_SIZE);
346 flush_icache_range((unsigned long)dst, (unsigned long)dst + EXEC_SIZE);
347 pr_info("attempting bad execution at %p\n", func);
332 func(); 348 func();
333} 349}
334 350
@@ -337,8 +353,13 @@ static void execute_user_location(void *dst)
337 /* Intentionally crossing kernel/user memory boundary. */ 353 /* Intentionally crossing kernel/user memory boundary. */
338 void (*func)(void) = dst; 354 void (*func)(void) = dst;
339 355
356 pr_info("attempting ok execution at %p\n", do_nothing);
357 do_nothing();
358
340 if (copy_to_user((void __user *)dst, do_nothing, EXEC_SIZE)) 359 if (copy_to_user((void __user *)dst, do_nothing, EXEC_SIZE))
341 return; 360 return;
361 flush_icache_range((unsigned long)dst, (unsigned long)dst + EXEC_SIZE);
362 pr_info("attempting bad execution at %p\n", func);
342 func(); 363 func();
343} 364}
344 365
@@ -463,8 +484,12 @@ static void lkdtm_do_action(enum ctype which)
463 } 484 }
464 485
465 ptr = (unsigned long *)user_addr; 486 ptr = (unsigned long *)user_addr;
487
488 pr_info("attempting bad read at %p\n", ptr);
466 tmp = *ptr; 489 tmp = *ptr;
467 tmp += 0xc0dec0de; 490 tmp += 0xc0dec0de;
491
492 pr_info("attempting bad write at %p\n", ptr);
468 *ptr = tmp; 493 *ptr = tmp;
469 494
470 vm_munmap(user_addr, PAGE_SIZE); 495 vm_munmap(user_addr, PAGE_SIZE);
@@ -475,10 +500,28 @@ static void lkdtm_do_action(enum ctype which)
475 unsigned long *ptr; 500 unsigned long *ptr;
476 501
477 ptr = (unsigned long *)&rodata; 502 ptr = (unsigned long *)&rodata;
503
504 pr_info("attempting bad write at %p\n", ptr);
478 *ptr ^= 0xabcd1234; 505 *ptr ^= 0xabcd1234;
479 506
480 break; 507 break;
481 } 508 }
509 case CT_WRITE_KERN: {
510 size_t size;
511 unsigned char *ptr;
512
513 size = (unsigned long)do_overwritten -
514 (unsigned long)do_nothing;
515 ptr = (unsigned char *)do_overwritten;
516
517 pr_info("attempting bad %zu byte write at %p\n", size, ptr);
518 memcpy(ptr, (unsigned char *)do_nothing, size);
519 flush_icache_range((unsigned long)ptr,
520 (unsigned long)(ptr + size));
521
522 do_overwritten();
523 break;
524 }
482 case CT_NONE: 525 case CT_NONE:
483 default: 526 default:
484 break; 527 break;
@@ -493,8 +536,8 @@ static void lkdtm_handler(void)
493 536
494 spin_lock_irqsave(&count_lock, flags); 537 spin_lock_irqsave(&count_lock, flags);
495 count--; 538 count--;
496 printk(KERN_INFO "lkdtm: Crash point %s of type %s hit, trigger in %d rounds\n", 539 pr_info("Crash point %s of type %s hit, trigger in %d rounds\n",
497 cp_name_to_str(cpoint), cp_type_to_str(cptype), count); 540 cp_name_to_str(cpoint), cp_type_to_str(cptype), count);
498 541
499 if (count == 0) { 542 if (count == 0) {
500 do_it = true; 543 do_it = true;
@@ -551,18 +594,18 @@ static int lkdtm_register_cpoint(enum cname which)
551 lkdtm.kp.symbol_name = "generic_ide_ioctl"; 594 lkdtm.kp.symbol_name = "generic_ide_ioctl";
552 lkdtm.entry = (kprobe_opcode_t*) jp_generic_ide_ioctl; 595 lkdtm.entry = (kprobe_opcode_t*) jp_generic_ide_ioctl;
553#else 596#else
554 printk(KERN_INFO "lkdtm: Crash point not available\n"); 597 pr_info("Crash point not available\n");
555 return -EINVAL; 598 return -EINVAL;
556#endif 599#endif
557 break; 600 break;
558 default: 601 default:
559 printk(KERN_INFO "lkdtm: Invalid Crash Point\n"); 602 pr_info("Invalid Crash Point\n");
560 return -EINVAL; 603 return -EINVAL;
561 } 604 }
562 605
563 cpoint = which; 606 cpoint = which;
564 if ((ret = register_jprobe(&lkdtm)) < 0) { 607 if ((ret = register_jprobe(&lkdtm)) < 0) {
565 printk(KERN_INFO "lkdtm: Couldn't register jprobe\n"); 608 pr_info("Couldn't register jprobe\n");
566 cpoint = CN_INVALID; 609 cpoint = CN_INVALID;
567 } 610 }
568 611
@@ -709,8 +752,7 @@ static ssize_t direct_entry(struct file *f, const char __user *user_buf,
709 if (type == CT_NONE) 752 if (type == CT_NONE)
710 return -EINVAL; 753 return -EINVAL;
711 754
712 printk(KERN_INFO "lkdtm: Performing direct entry %s\n", 755 pr_info("Performing direct entry %s\n", cp_type_to_str(type));
713 cp_type_to_str(type));
714 lkdtm_do_action(type); 756 lkdtm_do_action(type);
715 *off += count; 757 *off += count;
716 758
@@ -772,7 +814,7 @@ static int __init lkdtm_module_init(void)
772 /* Register debugfs interface */ 814 /* Register debugfs interface */
773 lkdtm_debugfs_root = debugfs_create_dir("provoke-crash", NULL); 815 lkdtm_debugfs_root = debugfs_create_dir("provoke-crash", NULL);
774 if (!lkdtm_debugfs_root) { 816 if (!lkdtm_debugfs_root) {
775 printk(KERN_ERR "lkdtm: creating root dir failed\n"); 817 pr_err("creating root dir failed\n");
776 return -ENODEV; 818 return -ENODEV;
777 } 819 }
778 820
@@ -787,28 +829,26 @@ static int __init lkdtm_module_init(void)
787 de = debugfs_create_file(cur->name, 0644, lkdtm_debugfs_root, 829 de = debugfs_create_file(cur->name, 0644, lkdtm_debugfs_root,
788 NULL, &cur->fops); 830 NULL, &cur->fops);
789 if (de == NULL) { 831 if (de == NULL) {
790 printk(KERN_ERR "lkdtm: could not create %s\n", 832 pr_err("could not create %s\n", cur->name);
791 cur->name);
792 goto out_err; 833 goto out_err;
793 } 834 }
794 } 835 }
795 836
796 if (lkdtm_parse_commandline() == -EINVAL) { 837 if (lkdtm_parse_commandline() == -EINVAL) {
797 printk(KERN_INFO "lkdtm: Invalid command\n"); 838 pr_info("Invalid command\n");
798 goto out_err; 839 goto out_err;
799 } 840 }
800 841
801 if (cpoint != CN_INVALID && cptype != CT_NONE) { 842 if (cpoint != CN_INVALID && cptype != CT_NONE) {
802 ret = lkdtm_register_cpoint(cpoint); 843 ret = lkdtm_register_cpoint(cpoint);
803 if (ret < 0) { 844 if (ret < 0) {
804 printk(KERN_INFO "lkdtm: Invalid crash point %d\n", 845 pr_info("Invalid crash point %d\n", cpoint);
805 cpoint);
806 goto out_err; 846 goto out_err;
807 } 847 }
808 printk(KERN_INFO "lkdtm: Crash point %s of type %s registered\n", 848 pr_info("Crash point %s of type %s registered\n",
809 cpoint_name, cpoint_type); 849 cpoint_name, cpoint_type);
810 } else { 850 } else {
811 printk(KERN_INFO "lkdtm: No crash points registered, enable through debugfs\n"); 851 pr_info("No crash points registered, enable through debugfs\n");
812 } 852 }
813 853
814 return 0; 854 return 0;
@@ -823,7 +863,7 @@ static void __exit lkdtm_module_exit(void)
823 debugfs_remove_recursive(lkdtm_debugfs_root); 863 debugfs_remove_recursive(lkdtm_debugfs_root);
824 864
825 unregister_jprobe(&lkdtm); 865 unregister_jprobe(&lkdtm);
826 printk(KERN_INFO "lkdtm: Crash point unregistered\n"); 866 pr_info("Crash point unregistered\n");
827} 867}
828 868
829module_init(lkdtm_module_init); 869module_init(lkdtm_module_init);
diff --git a/drivers/misc/mei/Kconfig b/drivers/misc/mei/Kconfig
index c76fa31e9bf6..d23384dde73b 100644
--- a/drivers/misc/mei/Kconfig
+++ b/drivers/misc/mei/Kconfig
@@ -34,3 +34,12 @@ config INTEL_MEI_ME
34 82Q33 Express 34 82Q33 Express
35 82X38/X48 Express 35 82X38/X48 Express
36 36
37config INTEL_MEI_TXE
38 tristate "Intel Trusted Execution Environment with ME Interface"
39 select INTEL_MEI
40 depends on X86 && PCI && WATCHDOG_CORE
41 help
42 MEI Support for Trusted Execution Environment device on Intel SoCs
43
44 Supported SoCs:
45 Intel Bay Trail
diff --git a/drivers/misc/mei/Makefile b/drivers/misc/mei/Makefile
index 08698a466268..8ebc6cda1373 100644
--- a/drivers/misc/mei/Makefile
+++ b/drivers/misc/mei/Makefile
@@ -1,6 +1,6 @@
1# 1#
2# Makefile - Intel Management Engine Interface (Intel MEI) Linux driver 2# Makefile - Intel Management Engine Interface (Intel MEI) Linux driver
3# Copyright (c) 2010-2011, Intel Corporation. 3# Copyright (c) 2010-2014, Intel Corporation.
4# 4#
5obj-$(CONFIG_INTEL_MEI) += mei.o 5obj-$(CONFIG_INTEL_MEI) += mei.o
6mei-objs := init.o 6mei-objs := init.o
@@ -17,3 +17,7 @@ mei-$(CONFIG_DEBUG_FS) += debugfs.o
17obj-$(CONFIG_INTEL_MEI_ME) += mei-me.o 17obj-$(CONFIG_INTEL_MEI_ME) += mei-me.o
18mei-me-objs := pci-me.o 18mei-me-objs := pci-me.o
19mei-me-objs += hw-me.o 19mei-me-objs += hw-me.o
20
21obj-$(CONFIG_INTEL_MEI_TXE) += mei-txe.o
22mei-txe-objs := pci-txe.o
23mei-txe-objs += hw-txe.o
diff --git a/drivers/misc/mei/amthif.c b/drivers/misc/mei/amthif.c
index 2fad84432829..b8deb3455480 100644
--- a/drivers/misc/mei/amthif.c
+++ b/drivers/misc/mei/amthif.c
@@ -21,7 +21,6 @@
21#include <linux/fcntl.h> 21#include <linux/fcntl.h>
22#include <linux/aio.h> 22#include <linux/aio.h>
23#include <linux/pci.h> 23#include <linux/pci.h>
24#include <linux/init.h>
25#include <linux/ioctl.h> 24#include <linux/ioctl.h>
26#include <linux/cdev.h> 25#include <linux/cdev.h>
27#include <linux/list.h> 26#include <linux/list.h>
@@ -35,7 +34,6 @@
35 34
36#include "mei_dev.h" 35#include "mei_dev.h"
37#include "hbm.h" 36#include "hbm.h"
38#include "hw-me.h"
39#include "client.h" 37#include "client.h"
40 38
41const uuid_le mei_amthif_guid = UUID_LE(0x12f80028, 0xb4b7, 0x4b2d, 39const uuid_le mei_amthif_guid = UUID_LE(0x12f80028, 0xb4b7, 0x4b2d,
@@ -79,10 +77,9 @@ int mei_amthif_host_init(struct mei_device *dev)
79 77
80 i = mei_me_cl_by_uuid(dev, &mei_amthif_guid); 78 i = mei_me_cl_by_uuid(dev, &mei_amthif_guid);
81 if (i < 0) { 79 if (i < 0) {
82 ret = i;
83 dev_info(&dev->pdev->dev, 80 dev_info(&dev->pdev->dev,
84 "amthif: failed to find the client %d\n", ret); 81 "amthif: failed to find the client %d\n", i);
85 return ret; 82 return -ENOTTY;
86 } 83 }
87 84
88 cl->me_client_id = dev->me_clients[i].client_id; 85 cl->me_client_id = dev->me_clients[i].client_id;
@@ -116,14 +113,11 @@ int mei_amthif_host_init(struct mei_device *dev)
116 113
117 cl->state = MEI_FILE_CONNECTING; 114 cl->state = MEI_FILE_CONNECTING;
118 115
119 if (mei_hbm_cl_connect_req(dev, cl)) { 116 ret = mei_cl_connect(cl, NULL);
120 dev_dbg(&dev->pdev->dev, "amthif: Failed to connect to ME client\n"); 117
121 cl->state = MEI_FILE_DISCONNECTED; 118 dev->iamthif_state = MEI_IAMTHIF_IDLE;
122 cl->host_client_id = 0; 119
123 } else { 120 return ret;
124 cl->timer_count = MEI_CONNECT_TIMEOUT;
125 }
126 return 0;
127} 121}
128 122
129/** 123/**
@@ -137,14 +131,12 @@ int mei_amthif_host_init(struct mei_device *dev)
137struct mei_cl_cb *mei_amthif_find_read_list_entry(struct mei_device *dev, 131struct mei_cl_cb *mei_amthif_find_read_list_entry(struct mei_device *dev,
138 struct file *file) 132 struct file *file)
139{ 133{
140 struct mei_cl_cb *pos = NULL; 134 struct mei_cl_cb *cb;
141 struct mei_cl_cb *next = NULL;
142 135
143 list_for_each_entry_safe(pos, next, 136 list_for_each_entry(cb, &dev->amthif_rd_complete_list.list, list) {
144 &dev->amthif_rd_complete_list.list, list) { 137 if (cb->cl && cb->cl == &dev->iamthif_cl &&
145 if (pos->cl && pos->cl == &dev->iamthif_cl && 138 cb->file_object == file)
146 pos->file_object == file) 139 return cb;
147 return pos;
148 } 140 }
149 return NULL; 141 return NULL;
150} 142}
@@ -180,14 +172,13 @@ int mei_amthif_read(struct mei_device *dev, struct file *file,
180 /* Only possible if we are in timeout */ 172 /* Only possible if we are in timeout */
181 if (!cl || cl != &dev->iamthif_cl) { 173 if (!cl || cl != &dev->iamthif_cl) {
182 dev_dbg(&dev->pdev->dev, "bad file ext.\n"); 174 dev_dbg(&dev->pdev->dev, "bad file ext.\n");
183 return -ETIMEDOUT; 175 return -ETIME;
184 } 176 }
185 177
186 i = mei_me_cl_by_id(dev, dev->iamthif_cl.me_client_id); 178 i = mei_me_cl_by_id(dev, dev->iamthif_cl.me_client_id);
187
188 if (i < 0) { 179 if (i < 0) {
189 dev_dbg(&dev->pdev->dev, "amthif client not found.\n"); 180 dev_dbg(&dev->pdev->dev, "amthif client not found.\n");
190 return -ENODEV; 181 return -ENOTTY;
191 } 182 }
192 dev_dbg(&dev->pdev->dev, "checking amthif data\n"); 183 dev_dbg(&dev->pdev->dev, "checking amthif data\n");
193 cb = mei_amthif_find_read_list_entry(dev, file); 184 cb = mei_amthif_find_read_list_entry(dev, file);
@@ -228,7 +219,7 @@ int mei_amthif_read(struct mei_device *dev, struct file *file,
228 dev_dbg(&dev->pdev->dev, "amthif Time out\n"); 219 dev_dbg(&dev->pdev->dev, "amthif Time out\n");
229 /* 15 sec for the message has expired */ 220 /* 15 sec for the message has expired */
230 list_del(&cb->list); 221 list_del(&cb->list);
231 rets = -ETIMEDOUT; 222 rets = -ETIME;
232 goto free; 223 goto free;
233 } 224 }
234 } 225 }
@@ -253,9 +244,10 @@ int mei_amthif_read(struct mei_device *dev, struct file *file,
253 * the buf_idx may point beyond */ 244 * the buf_idx may point beyond */
254 length = min_t(size_t, length, (cb->buf_idx - *offset)); 245 length = min_t(size_t, length, (cb->buf_idx - *offset));
255 246
256 if (copy_to_user(ubuf, cb->response_buffer.data + *offset, length)) 247 if (copy_to_user(ubuf, cb->response_buffer.data + *offset, length)) {
248 dev_dbg(&dev->pdev->dev, "failed to copy data to userland\n");
257 rets = -EFAULT; 249 rets = -EFAULT;
258 else { 250 } else {
259 rets = length; 251 rets = length;
260 if ((*offset + length) < cb->buf_idx) { 252 if ((*offset + length) < cb->buf_idx) {
261 *offset += length; 253 *offset += length;
@@ -302,9 +294,8 @@ static int mei_amthif_send_cmd(struct mei_device *dev, struct mei_cl_cb *cb)
302 if (ret < 0) 294 if (ret < 0)
303 return ret; 295 return ret;
304 296
305 if (ret && dev->hbuf_is_ready) { 297 if (ret && mei_hbuf_acquire(dev)) {
306 ret = 0; 298 ret = 0;
307 dev->hbuf_is_ready = false;
308 if (cb->request_buffer.size > mei_hbuf_max_len(dev)) { 299 if (cb->request_buffer.size > mei_hbuf_max_len(dev)) {
309 mei_hdr.length = mei_hbuf_max_len(dev); 300 mei_hdr.length = mei_hbuf_max_len(dev);
310 mei_hdr.msg_complete = 0; 301 mei_hdr.msg_complete = 0;
@@ -336,10 +327,6 @@ static int mei_amthif_send_cmd(struct mei_device *dev, struct mei_cl_cb *cb)
336 list_add_tail(&cb->list, &dev->write_list.list); 327 list_add_tail(&cb->list, &dev->write_list.list);
337 } 328 }
338 } else { 329 } else {
339 if (!dev->hbuf_is_ready)
340 dev_dbg(&dev->pdev->dev, "host buffer is not empty");
341
342 dev_dbg(&dev->pdev->dev, "No flow control credentials, so add iamthif cb to write list.\n");
343 list_add_tail(&cb->list, &dev->write_list.list); 330 list_add_tail(&cb->list, &dev->write_list.list);
344 } 331 }
345 return 0; 332 return 0;
@@ -365,7 +352,7 @@ int mei_amthif_write(struct mei_device *dev, struct mei_cl_cb *cb)
365 if (ret) 352 if (ret)
366 return ret; 353 return ret;
367 354
368 cb->fop_type = MEI_FOP_IOCTL; 355 cb->fop_type = MEI_FOP_WRITE;
369 356
370 if (!list_empty(&dev->amthif_cmd_list.list) || 357 if (!list_empty(&dev->amthif_cmd_list.list) ||
371 dev->iamthif_state != MEI_IAMTHIF_IDLE) { 358 dev->iamthif_state != MEI_IAMTHIF_IDLE) {
@@ -447,23 +434,23 @@ unsigned int mei_amthif_poll(struct mei_device *dev,
447 434
448 435
449/** 436/**
450 * mei_amthif_irq_write_completed - processes completed iamthif operation. 437 * mei_amthif_irq_write - write iamthif command in irq thread context.
451 * 438 *
452 * @dev: the device structure. 439 * @dev: the device structure.
453 * @slots: free slots.
454 * @cb_pos: callback block. 440 * @cb_pos: callback block.
455 * @cl: private data of the file object. 441 * @cl: private data of the file object.
456 * @cmpl_list: complete list. 442 * @cmpl_list: complete list.
457 * 443 *
458 * returns 0, OK; otherwise, error. 444 * returns 0, OK; otherwise, error.
459 */ 445 */
460int mei_amthif_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb, 446int mei_amthif_irq_write(struct mei_cl *cl, struct mei_cl_cb *cb,
461 s32 *slots, struct mei_cl_cb *cmpl_list) 447 struct mei_cl_cb *cmpl_list)
462{ 448{
463 struct mei_device *dev = cl->dev; 449 struct mei_device *dev = cl->dev;
464 struct mei_msg_hdr mei_hdr; 450 struct mei_msg_hdr mei_hdr;
465 size_t len = dev->iamthif_msg_buf_size - dev->iamthif_msg_buf_index; 451 size_t len = dev->iamthif_msg_buf_size - dev->iamthif_msg_buf_index;
466 u32 msg_slots = mei_data2slots(len); 452 u32 msg_slots = mei_data2slots(len);
453 int slots;
467 int rets; 454 int rets;
468 455
469 rets = mei_cl_flow_ctrl_creds(cl); 456 rets = mei_cl_flow_ctrl_creds(cl);
@@ -480,13 +467,15 @@ int mei_amthif_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb,
480 mei_hdr.reserved = 0; 467 mei_hdr.reserved = 0;
481 mei_hdr.internal = 0; 468 mei_hdr.internal = 0;
482 469
483 if (*slots >= msg_slots) { 470 slots = mei_hbuf_empty_slots(dev);
471
472 if (slots >= msg_slots) {
484 mei_hdr.length = len; 473 mei_hdr.length = len;
485 mei_hdr.msg_complete = 1; 474 mei_hdr.msg_complete = 1;
486 /* Split the message only if we can write the whole host buffer */ 475 /* Split the message only if we can write the whole host buffer */
487 } else if (*slots == dev->hbuf_depth) { 476 } else if (slots == dev->hbuf_depth) {
488 msg_slots = *slots; 477 msg_slots = slots;
489 len = (*slots * sizeof(u32)) - sizeof(struct mei_msg_hdr); 478 len = (slots * sizeof(u32)) - sizeof(struct mei_msg_hdr);
490 mei_hdr.length = len; 479 mei_hdr.length = len;
491 mei_hdr.msg_complete = 0; 480 mei_hdr.msg_complete = 0;
492 } else { 481 } else {
@@ -496,7 +485,6 @@ int mei_amthif_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb,
496 485
497 dev_dbg(&dev->pdev->dev, MEI_HDR_FMT, MEI_HDR_PRM(&mei_hdr)); 486 dev_dbg(&dev->pdev->dev, MEI_HDR_FMT, MEI_HDR_PRM(&mei_hdr));
498 487
499 *slots -= msg_slots;
500 rets = mei_write_message(dev, &mei_hdr, 488 rets = mei_write_message(dev, &mei_hdr,
501 dev->iamthif_msg_buf + dev->iamthif_msg_buf_index); 489 dev->iamthif_msg_buf + dev->iamthif_msg_buf_index);
502 if (rets) { 490 if (rets) {
diff --git a/drivers/misc/mei/bus.c b/drivers/misc/mei/bus.c
index 4bc7d620d695..ddc5ac92a200 100644
--- a/drivers/misc/mei/bus.c
+++ b/drivers/misc/mei/bus.c
@@ -26,7 +26,6 @@
26#include <linux/mei_cl_bus.h> 26#include <linux/mei_cl_bus.h>
27 27
28#include "mei_dev.h" 28#include "mei_dev.h"
29#include "hw-me.h"
30#include "client.h" 29#include "client.h"
31 30
32#define to_mei_cl_driver(d) container_of(d, struct mei_cl_driver, driver) 31#define to_mei_cl_driver(d) container_of(d, struct mei_cl_driver, driver)
@@ -145,9 +144,9 @@ static struct device_type mei_cl_device_type = {
145static struct mei_cl *mei_bus_find_mei_cl_by_uuid(struct mei_device *dev, 144static struct mei_cl *mei_bus_find_mei_cl_by_uuid(struct mei_device *dev,
146 uuid_le uuid) 145 uuid_le uuid)
147{ 146{
148 struct mei_cl *cl, *next; 147 struct mei_cl *cl;
149 148
150 list_for_each_entry_safe(cl, next, &dev->device_list, device_link) { 149 list_for_each_entry(cl, &dev->device_list, device_link) {
151 if (!uuid_le_cmp(uuid, cl->device_uuid)) 150 if (!uuid_le_cmp(uuid, cl->device_uuid))
152 return cl; 151 return cl;
153 } 152 }
@@ -524,6 +523,22 @@ void mei_cl_bus_rx_event(struct mei_cl *cl)
524 schedule_work(&device->event_work); 523 schedule_work(&device->event_work);
525} 524}
526 525
526void mei_cl_bus_remove_devices(struct mei_device *dev)
527{
528 struct mei_cl *cl, *next;
529
530 mutex_lock(&dev->device_lock);
531 list_for_each_entry_safe(cl, next, &dev->device_list, device_link) {
532 if (cl->device)
533 mei_cl_remove_device(cl->device);
534
535 list_del(&cl->device_link);
536 mei_cl_unlink(cl);
537 kfree(cl);
538 }
539 mutex_unlock(&dev->device_lock);
540}
541
527int __init mei_cl_bus_init(void) 542int __init mei_cl_bus_init(void)
528{ 543{
529 return bus_register(&mei_cl_bus_type); 544 return bus_register(&mei_cl_bus_type);
diff --git a/drivers/misc/mei/client.c b/drivers/misc/mei/client.c
index 89a557972d1b..8c078b808cd3 100644
--- a/drivers/misc/mei/client.c
+++ b/drivers/misc/mei/client.c
@@ -29,20 +29,21 @@
29 * mei_me_cl_by_uuid - locate index of me client 29 * mei_me_cl_by_uuid - locate index of me client
30 * 30 *
31 * @dev: mei device 31 * @dev: mei device
32 *
33 * Locking: called under "dev->device_lock" lock
34 *
32 * returns me client index or -ENOENT if not found 35 * returns me client index or -ENOENT if not found
33 */ 36 */
34int mei_me_cl_by_uuid(const struct mei_device *dev, const uuid_le *uuid) 37int mei_me_cl_by_uuid(const struct mei_device *dev, const uuid_le *uuid)
35{ 38{
36 int i, res = -ENOENT; 39 int i;
37 40
38 for (i = 0; i < dev->me_clients_num; ++i) 41 for (i = 0; i < dev->me_clients_num; ++i)
39 if (uuid_le_cmp(*uuid, 42 if (uuid_le_cmp(*uuid,
40 dev->me_clients[i].props.protocol_name) == 0) { 43 dev->me_clients[i].props.protocol_name) == 0)
41 res = i; 44 return i;
42 break;
43 }
44 45
45 return res; 46 return -ENOENT;
46} 47}
47 48
48 49
@@ -60,37 +61,79 @@ int mei_me_cl_by_uuid(const struct mei_device *dev, const uuid_le *uuid)
60int mei_me_cl_by_id(struct mei_device *dev, u8 client_id) 61int mei_me_cl_by_id(struct mei_device *dev, u8 client_id)
61{ 62{
62 int i; 63 int i;
64
63 for (i = 0; i < dev->me_clients_num; i++) 65 for (i = 0; i < dev->me_clients_num; i++)
64 if (dev->me_clients[i].client_id == client_id) 66 if (dev->me_clients[i].client_id == client_id)
65 break; 67 return i;
66 if (WARN_ON(dev->me_clients[i].client_id != client_id))
67 return -ENOENT;
68 68
69 if (i == dev->me_clients_num) 69 return -ENOENT;
70 return -ENOENT;
71
72 return i;
73} 70}
74 71
75 72
76/** 73/**
77 * mei_io_list_flush - removes list entry belonging to cl. 74 * mei_cl_cmp_id - tells if the clients are the same
78 * 75 *
79 * @list: An instance of our list structure 76 * @cl1: host client 1
80 * @cl: host client 77 * @cl2: host client 2
78 *
79 * returns true - if the clients has same host and me ids
80 * false - otherwise
81 */
82static inline bool mei_cl_cmp_id(const struct mei_cl *cl1,
83 const struct mei_cl *cl2)
84{
85 return cl1 && cl2 &&
86 (cl1->host_client_id == cl2->host_client_id) &&
87 (cl1->me_client_id == cl2->me_client_id);
88}
89
90/**
91 * mei_io_list_flush - removes cbs belonging to cl.
92 *
93 * @list: an instance of our list structure
94 * @cl: host client, can be NULL for flushing the whole list
95 * @free: whether to free the cbs
81 */ 96 */
82void mei_io_list_flush(struct mei_cl_cb *list, struct mei_cl *cl) 97static void __mei_io_list_flush(struct mei_cl_cb *list,
98 struct mei_cl *cl, bool free)
83{ 99{
84 struct mei_cl_cb *cb; 100 struct mei_cl_cb *cb;
85 struct mei_cl_cb *next; 101 struct mei_cl_cb *next;
86 102
103 /* enable removing everything if no cl is specified */
87 list_for_each_entry_safe(cb, next, &list->list, list) { 104 list_for_each_entry_safe(cb, next, &list->list, list) {
88 if (cb->cl && mei_cl_cmp_id(cl, cb->cl)) 105 if (!cl || (cb->cl && mei_cl_cmp_id(cl, cb->cl))) {
89 list_del(&cb->list); 106 list_del(&cb->list);
107 if (free)
108 mei_io_cb_free(cb);
109 }
90 } 110 }
91} 111}
92 112
93/** 113/**
114 * mei_io_list_flush - removes list entry belonging to cl.
115 *
116 * @list: An instance of our list structure
117 * @cl: host client
118 */
119static inline void mei_io_list_flush(struct mei_cl_cb *list, struct mei_cl *cl)
120{
121 __mei_io_list_flush(list, cl, false);
122}
123
124
125/**
126 * mei_io_list_free - removes cb belonging to cl and free them
127 *
128 * @list: An instance of our list structure
129 * @cl: host client
130 */
131static inline void mei_io_list_free(struct mei_cl_cb *list, struct mei_cl *cl)
132{
133 __mei_io_list_flush(list, cl, true);
134}
135
136/**
94 * mei_io_cb_free - free mei_cb_private related memory 137 * mei_io_cb_free - free mei_cb_private related memory
95 * 138 *
96 * @cb: mei callback struct 139 * @cb: mei callback struct
@@ -196,8 +239,8 @@ int mei_cl_flush_queues(struct mei_cl *cl)
196 239
197 cl_dbg(dev, cl, "remove list entry belonging to cl\n"); 240 cl_dbg(dev, cl, "remove list entry belonging to cl\n");
198 mei_io_list_flush(&cl->dev->read_list, cl); 241 mei_io_list_flush(&cl->dev->read_list, cl);
199 mei_io_list_flush(&cl->dev->write_list, cl); 242 mei_io_list_free(&cl->dev->write_list, cl);
200 mei_io_list_flush(&cl->dev->write_waiting_list, cl); 243 mei_io_list_free(&cl->dev->write_waiting_list, cl);
201 mei_io_list_flush(&cl->dev->ctrl_wr_list, cl); 244 mei_io_list_flush(&cl->dev->ctrl_wr_list, cl);
202 mei_io_list_flush(&cl->dev->ctrl_rd_list, cl); 245 mei_io_list_flush(&cl->dev->ctrl_rd_list, cl);
203 mei_io_list_flush(&cl->dev->amthif_cmd_list, cl); 246 mei_io_list_flush(&cl->dev->amthif_cmd_list, cl);
@@ -254,10 +297,9 @@ struct mei_cl *mei_cl_allocate(struct mei_device *dev)
254struct mei_cl_cb *mei_cl_find_read_cb(struct mei_cl *cl) 297struct mei_cl_cb *mei_cl_find_read_cb(struct mei_cl *cl)
255{ 298{
256 struct mei_device *dev = cl->dev; 299 struct mei_device *dev = cl->dev;
257 struct mei_cl_cb *cb = NULL; 300 struct mei_cl_cb *cb;
258 struct mei_cl_cb *next = NULL;
259 301
260 list_for_each_entry_safe(cb, next, &dev->read_list.list, list) 302 list_for_each_entry(cb, &dev->read_list.list, list)
261 if (mei_cl_cmp_id(cl, cb->cl)) 303 if (mei_cl_cmp_id(cl, cb->cl))
262 return cb; 304 return cb;
263 return NULL; 305 return NULL;
@@ -375,6 +417,23 @@ void mei_host_client_init(struct work_struct *work)
375 mutex_unlock(&dev->device_lock); 417 mutex_unlock(&dev->device_lock);
376} 418}
377 419
420/**
421 * mei_hbuf_acquire: try to acquire host buffer
422 *
423 * @dev: the device structure
424 * returns true if host buffer was acquired
425 */
426bool mei_hbuf_acquire(struct mei_device *dev)
427{
428 if (!dev->hbuf_is_ready) {
429 dev_dbg(&dev->pdev->dev, "hbuf is not ready\n");
430 return false;
431 }
432
433 dev->hbuf_is_ready = false;
434
435 return true;
436}
378 437
379/** 438/**
380 * mei_cl_disconnect - disconnect host client from the me one 439 * mei_cl_disconnect - disconnect host client from the me one
@@ -406,8 +465,7 @@ int mei_cl_disconnect(struct mei_cl *cl)
406 return -ENOMEM; 465 return -ENOMEM;
407 466
408 cb->fop_type = MEI_FOP_CLOSE; 467 cb->fop_type = MEI_FOP_CLOSE;
409 if (dev->hbuf_is_ready) { 468 if (mei_hbuf_acquire(dev)) {
410 dev->hbuf_is_ready = false;
411 if (mei_hbm_cl_disconnect_req(dev, cl)) { 469 if (mei_hbm_cl_disconnect_req(dev, cl)) {
412 rets = -ENODEV; 470 rets = -ENODEV;
413 cl_err(dev, cl, "failed to disconnect.\n"); 471 cl_err(dev, cl, "failed to disconnect.\n");
@@ -461,17 +519,17 @@ free:
461bool mei_cl_is_other_connecting(struct mei_cl *cl) 519bool mei_cl_is_other_connecting(struct mei_cl *cl)
462{ 520{
463 struct mei_device *dev; 521 struct mei_device *dev;
464 struct mei_cl *pos; 522 struct mei_cl *ocl; /* the other client */
465 struct mei_cl *next;
466 523
467 if (WARN_ON(!cl || !cl->dev)) 524 if (WARN_ON(!cl || !cl->dev))
468 return false; 525 return false;
469 526
470 dev = cl->dev; 527 dev = cl->dev;
471 528
472 list_for_each_entry_safe(pos, next, &dev->file_list, link) { 529 list_for_each_entry(ocl, &dev->file_list, link) {
473 if ((pos->state == MEI_FILE_CONNECTING) && 530 if (ocl->state == MEI_FILE_CONNECTING &&
474 (pos != cl) && cl->me_client_id == pos->me_client_id) 531 ocl != cl &&
532 cl->me_client_id == ocl->me_client_id)
475 return true; 533 return true;
476 534
477 } 535 }
@@ -505,11 +563,10 @@ int mei_cl_connect(struct mei_cl *cl, struct file *file)
505 goto out; 563 goto out;
506 } 564 }
507 565
508 cb->fop_type = MEI_FOP_IOCTL; 566 cb->fop_type = MEI_FOP_CONNECT;
509
510 if (dev->hbuf_is_ready && !mei_cl_is_other_connecting(cl)) {
511 dev->hbuf_is_ready = false;
512 567
568 /* run hbuf acquire last so we don't have to undo */
569 if (!mei_cl_is_other_connecting(cl) && mei_hbuf_acquire(dev)) {
513 if (mei_hbm_cl_connect_req(dev, cl)) { 570 if (mei_hbm_cl_connect_req(dev, cl)) {
514 rets = -ENODEV; 571 rets = -ENODEV;
515 goto out; 572 goto out;
@@ -521,18 +578,19 @@ int mei_cl_connect(struct mei_cl *cl, struct file *file)
521 } 578 }
522 579
523 mutex_unlock(&dev->device_lock); 580 mutex_unlock(&dev->device_lock);
524 rets = wait_event_timeout(dev->wait_recvd_msg, 581 wait_event_timeout(dev->wait_recvd_msg,
525 (cl->state == MEI_FILE_CONNECTED || 582 (cl->state == MEI_FILE_CONNECTED ||
526 cl->state == MEI_FILE_DISCONNECTED), 583 cl->state == MEI_FILE_DISCONNECTED),
527 mei_secs_to_jiffies(MEI_CL_CONNECT_TIMEOUT)); 584 mei_secs_to_jiffies(MEI_CL_CONNECT_TIMEOUT));
528 mutex_lock(&dev->device_lock); 585 mutex_lock(&dev->device_lock);
529 586
530 if (cl->state != MEI_FILE_CONNECTED) { 587 if (cl->state != MEI_FILE_CONNECTED) {
531 rets = -EFAULT; 588 /* something went really wrong */
589 if (!cl->status)
590 cl->status = -EFAULT;
532 591
533 mei_io_list_flush(&dev->ctrl_rd_list, cl); 592 mei_io_list_flush(&dev->ctrl_rd_list, cl);
534 mei_io_list_flush(&dev->ctrl_wr_list, cl); 593 mei_io_list_flush(&dev->ctrl_wr_list, cl);
535 goto out;
536 } 594 }
537 595
538 rets = cl->status; 596 rets = cl->status;
@@ -554,7 +612,8 @@ out:
554int mei_cl_flow_ctrl_creds(struct mei_cl *cl) 612int mei_cl_flow_ctrl_creds(struct mei_cl *cl)
555{ 613{
556 struct mei_device *dev; 614 struct mei_device *dev;
557 int i; 615 struct mei_me_client *me_cl;
616 int id;
558 617
559 if (WARN_ON(!cl || !cl->dev)) 618 if (WARN_ON(!cl || !cl->dev))
560 return -EINVAL; 619 return -EINVAL;
@@ -567,19 +626,19 @@ int mei_cl_flow_ctrl_creds(struct mei_cl *cl)
567 if (cl->mei_flow_ctrl_creds > 0) 626 if (cl->mei_flow_ctrl_creds > 0)
568 return 1; 627 return 1;
569 628
570 for (i = 0; i < dev->me_clients_num; i++) { 629 id = mei_me_cl_by_id(dev, cl->me_client_id);
571 struct mei_me_client *me_cl = &dev->me_clients[i]; 630 if (id < 0) {
572 if (me_cl->client_id == cl->me_client_id) { 631 cl_err(dev, cl, "no such me client %d\n", cl->me_client_id);
573 if (me_cl->mei_flow_ctrl_creds) { 632 return id;
574 if (WARN_ON(me_cl->props.single_recv_buf == 0))
575 return -EINVAL;
576 return 1;
577 } else {
578 return 0;
579 }
580 }
581 } 633 }
582 return -ENOENT; 634
635 me_cl = &dev->me_clients[id];
636 if (me_cl->mei_flow_ctrl_creds) {
637 if (WARN_ON(me_cl->props.single_recv_buf == 0))
638 return -EINVAL;
639 return 1;
640 }
641 return 0;
583} 642}
584 643
585/** 644/**
@@ -595,32 +654,31 @@ int mei_cl_flow_ctrl_creds(struct mei_cl *cl)
595int mei_cl_flow_ctrl_reduce(struct mei_cl *cl) 654int mei_cl_flow_ctrl_reduce(struct mei_cl *cl)
596{ 655{
597 struct mei_device *dev; 656 struct mei_device *dev;
598 int i; 657 struct mei_me_client *me_cl;
658 int id;
599 659
600 if (WARN_ON(!cl || !cl->dev)) 660 if (WARN_ON(!cl || !cl->dev))
601 return -EINVAL; 661 return -EINVAL;
602 662
603 dev = cl->dev; 663 dev = cl->dev;
604 664
605 if (!dev->me_clients_num) 665 id = mei_me_cl_by_id(dev, cl->me_client_id);
606 return -ENOENT; 666 if (id < 0) {
667 cl_err(dev, cl, "no such me client %d\n", cl->me_client_id);
668 return id;
669 }
607 670
608 for (i = 0; i < dev->me_clients_num; i++) { 671 me_cl = &dev->me_clients[id];
609 struct mei_me_client *me_cl = &dev->me_clients[i]; 672 if (me_cl->props.single_recv_buf != 0) {
610 if (me_cl->client_id == cl->me_client_id) { 673 if (WARN_ON(me_cl->mei_flow_ctrl_creds <= 0))
611 if (me_cl->props.single_recv_buf != 0) { 674 return -EINVAL;
612 if (WARN_ON(me_cl->mei_flow_ctrl_creds <= 0)) 675 me_cl->mei_flow_ctrl_creds--;
613 return -EINVAL; 676 } else {
614 dev->me_clients[i].mei_flow_ctrl_creds--; 677 if (WARN_ON(cl->mei_flow_ctrl_creds <= 0))
615 } else { 678 return -EINVAL;
616 if (WARN_ON(cl->mei_flow_ctrl_creds <= 0)) 679 cl->mei_flow_ctrl_creds--;
617 return -EINVAL;
618 cl->mei_flow_ctrl_creds--;
619 }
620 return 0;
621 }
622 } 680 }
623 return -ENOENT; 681 return 0;
624} 682}
625 683
626/** 684/**
@@ -652,7 +710,7 @@ int mei_cl_read_start(struct mei_cl *cl, size_t length)
652 i = mei_me_cl_by_id(dev, cl->me_client_id); 710 i = mei_me_cl_by_id(dev, cl->me_client_id);
653 if (i < 0) { 711 if (i < 0) {
654 cl_err(dev, cl, "no such me client %d\n", cl->me_client_id); 712 cl_err(dev, cl, "no such me client %d\n", cl->me_client_id);
655 return -ENODEV; 713 return -ENOTTY;
656 } 714 }
657 715
658 cb = mei_io_cb_init(cl, NULL); 716 cb = mei_io_cb_init(cl, NULL);
@@ -666,8 +724,7 @@ int mei_cl_read_start(struct mei_cl *cl, size_t length)
666 goto err; 724 goto err;
667 725
668 cb->fop_type = MEI_FOP_READ; 726 cb->fop_type = MEI_FOP_READ;
669 if (dev->hbuf_is_ready) { 727 if (mei_hbuf_acquire(dev)) {
670 dev->hbuf_is_ready = false;
671 if (mei_hbm_cl_flow_control_req(dev, cl)) { 728 if (mei_hbm_cl_flow_control_req(dev, cl)) {
672 cl_err(dev, cl, "flow control send failed\n"); 729 cl_err(dev, cl, "flow control send failed\n");
673 rets = -ENODEV; 730 rets = -ENODEV;
@@ -687,27 +744,26 @@ err:
687} 744}
688 745
689/** 746/**
690 * mei_cl_irq_write_complete - write a message to device 747 * mei_cl_irq_write - write a message to device
691 * from the interrupt thread context 748 * from the interrupt thread context
692 * 749 *
693 * @cl: client 750 * @cl: client
694 * @cb: callback block. 751 * @cb: callback block.
695 * @slots: free slots.
696 * @cmpl_list: complete list. 752 * @cmpl_list: complete list.
697 * 753 *
698 * returns 0, OK; otherwise error. 754 * returns 0, OK; otherwise error.
699 */ 755 */
700int mei_cl_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb, 756int mei_cl_irq_write(struct mei_cl *cl, struct mei_cl_cb *cb,
701 s32 *slots, struct mei_cl_cb *cmpl_list) 757 struct mei_cl_cb *cmpl_list)
702{ 758{
703 struct mei_device *dev; 759 struct mei_device *dev;
704 struct mei_msg_data *buf; 760 struct mei_msg_data *buf;
705 struct mei_msg_hdr mei_hdr; 761 struct mei_msg_hdr mei_hdr;
706 size_t len; 762 size_t len;
707 u32 msg_slots; 763 u32 msg_slots;
764 int slots;
708 int rets; 765 int rets;
709 766
710
711 if (WARN_ON(!cl || !cl->dev)) 767 if (WARN_ON(!cl || !cl->dev))
712 return -ENODEV; 768 return -ENODEV;
713 769
@@ -724,6 +780,7 @@ int mei_cl_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb,
724 return 0; 780 return 0;
725 } 781 }
726 782
783 slots = mei_hbuf_empty_slots(dev);
727 len = buf->size - cb->buf_idx; 784 len = buf->size - cb->buf_idx;
728 msg_slots = mei_data2slots(len); 785 msg_slots = mei_data2slots(len);
729 786
@@ -732,13 +789,13 @@ int mei_cl_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb,
732 mei_hdr.reserved = 0; 789 mei_hdr.reserved = 0;
733 mei_hdr.internal = cb->internal; 790 mei_hdr.internal = cb->internal;
734 791
735 if (*slots >= msg_slots) { 792 if (slots >= msg_slots) {
736 mei_hdr.length = len; 793 mei_hdr.length = len;
737 mei_hdr.msg_complete = 1; 794 mei_hdr.msg_complete = 1;
738 /* Split the message only if we can write the whole host buffer */ 795 /* Split the message only if we can write the whole host buffer */
739 } else if (*slots == dev->hbuf_depth) { 796 } else if (slots == dev->hbuf_depth) {
740 msg_slots = *slots; 797 msg_slots = slots;
741 len = (*slots * sizeof(u32)) - sizeof(struct mei_msg_hdr); 798 len = (slots * sizeof(u32)) - sizeof(struct mei_msg_hdr);
742 mei_hdr.length = len; 799 mei_hdr.length = len;
743 mei_hdr.msg_complete = 0; 800 mei_hdr.msg_complete = 0;
744 } else { 801 } else {
@@ -749,7 +806,6 @@ int mei_cl_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb,
749 cl_dbg(dev, cl, "buf: size = %d idx = %lu\n", 806 cl_dbg(dev, cl, "buf: size = %d idx = %lu\n",
750 cb->request_buffer.size, cb->buf_idx); 807 cb->request_buffer.size, cb->buf_idx);
751 808
752 *slots -= msg_slots;
753 rets = mei_write_message(dev, &mei_hdr, buf->data + cb->buf_idx); 809 rets = mei_write_message(dev, &mei_hdr, buf->data + cb->buf_idx);
754 if (rets) { 810 if (rets) {
755 cl->status = rets; 811 cl->status = rets;
@@ -802,21 +858,29 @@ int mei_cl_write(struct mei_cl *cl, struct mei_cl_cb *cb, bool blocking)
802 858
803 859
804 cb->fop_type = MEI_FOP_WRITE; 860 cb->fop_type = MEI_FOP_WRITE;
861 cb->buf_idx = 0;
862 cl->writing_state = MEI_IDLE;
863
864 mei_hdr.host_addr = cl->host_client_id;
865 mei_hdr.me_addr = cl->me_client_id;
866 mei_hdr.reserved = 0;
867 mei_hdr.msg_complete = 0;
868 mei_hdr.internal = cb->internal;
805 869
806 rets = mei_cl_flow_ctrl_creds(cl); 870 rets = mei_cl_flow_ctrl_creds(cl);
807 if (rets < 0) 871 if (rets < 0)
808 goto err; 872 goto err;
809 873
810 /* Host buffer is not ready, we queue the request */ 874 if (rets == 0) {
811 if (rets == 0 || !dev->hbuf_is_ready) { 875 cl_dbg(dev, cl, "No flow control credentials: not sending.\n");
812 cb->buf_idx = 0; 876 rets = buf->size;
813 /* unseting complete will enqueue the cb for write */ 877 goto out;
814 mei_hdr.msg_complete = 0; 878 }
879 if (!mei_hbuf_acquire(dev)) {
880 cl_dbg(dev, cl, "Cannot acquire the host buffer: not sending.\n");
815 rets = buf->size; 881 rets = buf->size;
816 goto out; 882 goto out;
817 } 883 }
818
819 dev->hbuf_is_ready = false;
820 884
821 /* Check for a maximum length */ 885 /* Check for a maximum length */
822 if (buf->size > mei_hbuf_max_len(dev)) { 886 if (buf->size > mei_hbuf_max_len(dev)) {
@@ -827,12 +891,6 @@ int mei_cl_write(struct mei_cl *cl, struct mei_cl_cb *cb, bool blocking)
827 mei_hdr.msg_complete = 1; 891 mei_hdr.msg_complete = 1;
828 } 892 }
829 893
830 mei_hdr.host_addr = cl->host_client_id;
831 mei_hdr.me_addr = cl->me_client_id;
832 mei_hdr.reserved = 0;
833 mei_hdr.internal = cb->internal;
834
835
836 rets = mei_write_message(dev, &mei_hdr, buf->data); 894 rets = mei_write_message(dev, &mei_hdr, buf->data);
837 if (rets) 895 if (rets)
838 goto err; 896 goto err;
@@ -840,13 +898,12 @@ int mei_cl_write(struct mei_cl *cl, struct mei_cl_cb *cb, bool blocking)
840 cl->writing_state = MEI_WRITING; 898 cl->writing_state = MEI_WRITING;
841 cb->buf_idx = mei_hdr.length; 899 cb->buf_idx = mei_hdr.length;
842 900
843 rets = buf->size;
844out: 901out:
845 if (mei_hdr.msg_complete) { 902 if (mei_hdr.msg_complete) {
846 if (mei_cl_flow_ctrl_reduce(cl)) { 903 rets = mei_cl_flow_ctrl_reduce(cl);
847 rets = -ENODEV; 904 if (rets < 0)
848 goto err; 905 goto err;
849 } 906
850 list_add_tail(&cb->list, &dev->write_waiting_list.list); 907 list_add_tail(&cb->list, &dev->write_waiting_list.list);
851 } else { 908 } else {
852 list_add_tail(&cb->list, &dev->write_list.list); 909 list_add_tail(&cb->list, &dev->write_list.list);
@@ -856,15 +913,18 @@ out:
856 if (blocking && cl->writing_state != MEI_WRITE_COMPLETE) { 913 if (blocking && cl->writing_state != MEI_WRITE_COMPLETE) {
857 914
858 mutex_unlock(&dev->device_lock); 915 mutex_unlock(&dev->device_lock);
859 if (wait_event_interruptible(cl->tx_wait, 916 rets = wait_event_interruptible(cl->tx_wait,
860 cl->writing_state == MEI_WRITE_COMPLETE)) { 917 cl->writing_state == MEI_WRITE_COMPLETE);
861 if (signal_pending(current))
862 rets = -EINTR;
863 else
864 rets = -ERESTARTSYS;
865 }
866 mutex_lock(&dev->device_lock); 918 mutex_lock(&dev->device_lock);
919 /* wait_event_interruptible returns -ERESTARTSYS */
920 if (rets) {
921 if (signal_pending(current))
922 rets = -EINTR;
923 goto err;
924 }
867 } 925 }
926
927 rets = buf->size;
868err: 928err:
869 return rets; 929 return rets;
870} 930}
@@ -905,9 +965,9 @@ void mei_cl_complete(struct mei_cl *cl, struct mei_cl_cb *cb)
905 965
906void mei_cl_all_disconnect(struct mei_device *dev) 966void mei_cl_all_disconnect(struct mei_device *dev)
907{ 967{
908 struct mei_cl *cl, *next; 968 struct mei_cl *cl;
909 969
910 list_for_each_entry_safe(cl, next, &dev->file_list, link) { 970 list_for_each_entry(cl, &dev->file_list, link) {
911 cl->state = MEI_FILE_DISCONNECTED; 971 cl->state = MEI_FILE_DISCONNECTED;
912 cl->mei_flow_ctrl_creds = 0; 972 cl->mei_flow_ctrl_creds = 0;
913 cl->timer_count = 0; 973 cl->timer_count = 0;
@@ -922,8 +982,8 @@ void mei_cl_all_disconnect(struct mei_device *dev)
922 */ 982 */
923void mei_cl_all_wakeup(struct mei_device *dev) 983void mei_cl_all_wakeup(struct mei_device *dev)
924{ 984{
925 struct mei_cl *cl, *next; 985 struct mei_cl *cl;
926 list_for_each_entry_safe(cl, next, &dev->file_list, link) { 986 list_for_each_entry(cl, &dev->file_list, link) {
927 if (waitqueue_active(&cl->rx_wait)) { 987 if (waitqueue_active(&cl->rx_wait)) {
928 cl_dbg(dev, cl, "Waking up reading client!\n"); 988 cl_dbg(dev, cl, "Waking up reading client!\n");
929 wake_up_interruptible(&cl->rx_wait); 989 wake_up_interruptible(&cl->rx_wait);
@@ -942,20 +1002,8 @@ void mei_cl_all_wakeup(struct mei_device *dev)
942 */ 1002 */
943void mei_cl_all_write_clear(struct mei_device *dev) 1003void mei_cl_all_write_clear(struct mei_device *dev)
944{ 1004{
945 struct mei_cl_cb *cb, *next; 1005 mei_io_list_free(&dev->write_list, NULL);
946 struct list_head *list; 1006 mei_io_list_free(&dev->write_waiting_list, NULL);
947
948 list = &dev->write_list.list;
949 list_for_each_entry_safe(cb, next, list, list) {
950 list_del(&cb->list);
951 mei_io_cb_free(cb);
952 }
953
954 list = &dev->write_waiting_list.list;
955 list_for_each_entry_safe(cb, next, list, list) {
956 list_del(&cb->list);
957 mei_io_cb_free(cb);
958 }
959} 1007}
960 1008
961 1009
diff --git a/drivers/misc/mei/client.h b/drivers/misc/mei/client.h
index c8396e582f1c..96d5de0389f9 100644
--- a/drivers/misc/mei/client.h
+++ b/drivers/misc/mei/client.h
@@ -45,8 +45,6 @@ static inline void mei_io_list_init(struct mei_cl_cb *list)
45{ 45{
46 INIT_LIST_HEAD(&list->list); 46 INIT_LIST_HEAD(&list->list);
47} 47}
48void mei_io_list_flush(struct mei_cl_cb *list, struct mei_cl *cl);
49
50/* 48/*
51 * MEI Host Client Functions 49 * MEI Host Client Functions
52 */ 50 */
@@ -61,22 +59,6 @@ int mei_cl_unlink(struct mei_cl *cl);
61int mei_cl_flush_queues(struct mei_cl *cl); 59int mei_cl_flush_queues(struct mei_cl *cl);
62struct mei_cl_cb *mei_cl_find_read_cb(struct mei_cl *cl); 60struct mei_cl_cb *mei_cl_find_read_cb(struct mei_cl *cl);
63 61
64/**
65 * mei_cl_cmp_id - tells if file private data have same id
66 *
67 * @fe1: private data of 1. file object
68 * @fe2: private data of 2. file object
69 *
70 * returns true - if ids are the same and not NULL
71 */
72static inline bool mei_cl_cmp_id(const struct mei_cl *cl1,
73 const struct mei_cl *cl2)
74{
75 return cl1 && cl2 &&
76 (cl1->host_client_id == cl2->host_client_id) &&
77 (cl1->me_client_id == cl2->me_client_id);
78}
79
80 62
81int mei_cl_flow_ctrl_creds(struct mei_cl *cl); 63int mei_cl_flow_ctrl_creds(struct mei_cl *cl);
82 64
@@ -86,15 +68,15 @@ int mei_cl_flow_ctrl_reduce(struct mei_cl *cl);
86 */ 68 */
87static inline bool mei_cl_is_connected(struct mei_cl *cl) 69static inline bool mei_cl_is_connected(struct mei_cl *cl)
88{ 70{
89 return (cl->dev && 71 return cl->dev &&
90 cl->dev->dev_state == MEI_DEV_ENABLED && 72 cl->dev->dev_state == MEI_DEV_ENABLED &&
91 cl->state == MEI_FILE_CONNECTED); 73 cl->state == MEI_FILE_CONNECTED;
92} 74}
93static inline bool mei_cl_is_transitioning(struct mei_cl *cl) 75static inline bool mei_cl_is_transitioning(struct mei_cl *cl)
94{ 76{
95 return (MEI_FILE_INITIALIZING == cl->state || 77 return MEI_FILE_INITIALIZING == cl->state ||
96 MEI_FILE_DISCONNECTED == cl->state || 78 MEI_FILE_DISCONNECTED == cl->state ||
97 MEI_FILE_DISCONNECTING == cl->state); 79 MEI_FILE_DISCONNECTING == cl->state;
98} 80}
99 81
100bool mei_cl_is_other_connecting(struct mei_cl *cl); 82bool mei_cl_is_other_connecting(struct mei_cl *cl);
@@ -102,8 +84,8 @@ int mei_cl_disconnect(struct mei_cl *cl);
102int mei_cl_connect(struct mei_cl *cl, struct file *file); 84int mei_cl_connect(struct mei_cl *cl, struct file *file);
103int mei_cl_read_start(struct mei_cl *cl, size_t length); 85int mei_cl_read_start(struct mei_cl *cl, size_t length);
104int mei_cl_write(struct mei_cl *cl, struct mei_cl_cb *cb, bool blocking); 86int mei_cl_write(struct mei_cl *cl, struct mei_cl_cb *cb, bool blocking);
105int mei_cl_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb, 87int mei_cl_irq_write(struct mei_cl *cl, struct mei_cl_cb *cb,
106 s32 *slots, struct mei_cl_cb *cmpl_list); 88 struct mei_cl_cb *cmpl_list);
107 89
108void mei_cl_complete(struct mei_cl *cl, struct mei_cl_cb *cb); 90void mei_cl_complete(struct mei_cl *cl, struct mei_cl_cb *cb);
109 91
diff --git a/drivers/misc/mei/debugfs.c b/drivers/misc/mei/debugfs.c
index a3ae154444b2..ced5b777c70f 100644
--- a/drivers/misc/mei/debugfs.c
+++ b/drivers/misc/mei/debugfs.c
@@ -75,6 +75,54 @@ static const struct file_operations mei_dbgfs_fops_meclients = {
75 .llseek = generic_file_llseek, 75 .llseek = generic_file_llseek,
76}; 76};
77 77
78static ssize_t mei_dbgfs_read_active(struct file *fp, char __user *ubuf,
79 size_t cnt, loff_t *ppos)
80{
81 struct mei_device *dev = fp->private_data;
82 struct mei_cl *cl;
83 const size_t bufsz = 1024;
84 char *buf;
85 int i = 0;
86 int pos = 0;
87 int ret;
88
89 if (!dev)
90 return -ENODEV;
91
92 buf = kzalloc(bufsz, GFP_KERNEL);
93 if (!buf)
94 return -ENOMEM;
95
96 pos += scnprintf(buf + pos, bufsz - pos,
97 " |me|host|state|rd|wr|\n");
98
99 mutex_lock(&dev->device_lock);
100
101 /* if the driver is not enabled the list won't b consitent */
102 if (dev->dev_state != MEI_DEV_ENABLED)
103 goto out;
104
105 list_for_each_entry(cl, &dev->file_list, link) {
106
107 pos += scnprintf(buf + pos, bufsz - pos,
108 "%2d|%2d|%4d|%5d|%2d|%2d|\n",
109 i, cl->me_client_id, cl->host_client_id, cl->state,
110 cl->reading_state, cl->writing_state);
111 i++;
112 }
113out:
114 mutex_unlock(&dev->device_lock);
115 ret = simple_read_from_buffer(ubuf, cnt, ppos, buf, pos);
116 kfree(buf);
117 return ret;
118}
119
120static const struct file_operations mei_dbgfs_fops_active = {
121 .open = simple_open,
122 .read = mei_dbgfs_read_active,
123 .llseek = generic_file_llseek,
124};
125
78static ssize_t mei_dbgfs_read_devstate(struct file *fp, char __user *ubuf, 126static ssize_t mei_dbgfs_read_devstate(struct file *fp, char __user *ubuf,
79 size_t cnt, loff_t *ppos) 127 size_t cnt, loff_t *ppos)
80{ 128{
@@ -128,6 +176,12 @@ int mei_dbgfs_register(struct mei_device *dev, const char *name)
128 dev_err(&dev->pdev->dev, "meclients: registration failed\n"); 176 dev_err(&dev->pdev->dev, "meclients: registration failed\n");
129 goto err; 177 goto err;
130 } 178 }
179 f = debugfs_create_file("active", S_IRUSR, dir,
180 dev, &mei_dbgfs_fops_active);
181 if (!f) {
182 dev_err(&dev->pdev->dev, "meclients: registration failed\n");
183 goto err;
184 }
131 f = debugfs_create_file("devstate", S_IRUSR, dir, 185 f = debugfs_create_file("devstate", S_IRUSR, dir,
132 dev, &mei_dbgfs_fops_devstate); 186 dev, &mei_dbgfs_fops_devstate);
133 if (!f) { 187 if (!f) {
diff --git a/drivers/misc/mei/hbm.c b/drivers/misc/mei/hbm.c
index 28cd74c073b9..4960288e543a 100644
--- a/drivers/misc/mei/hbm.c
+++ b/drivers/misc/mei/hbm.c
@@ -21,7 +21,41 @@
21 21
22#include "mei_dev.h" 22#include "mei_dev.h"
23#include "hbm.h" 23#include "hbm.h"
24#include "hw-me.h" 24#include "client.h"
25
26static const char *mei_cl_conn_status_str(enum mei_cl_connect_status status)
27{
28#define MEI_CL_CS(status) case MEI_CL_CONN_##status: return #status
29 switch (status) {
30 MEI_CL_CS(SUCCESS);
31 MEI_CL_CS(NOT_FOUND);
32 MEI_CL_CS(ALREADY_STARTED);
33 MEI_CL_CS(OUT_OF_RESOURCES);
34 MEI_CL_CS(MESSAGE_SMALL);
35 default: return "unknown";
36 }
37#undef MEI_CL_CCS
38}
39
40/**
41 * mei_cl_conn_status_to_errno - convert client connect response
42 * status to error code
43 *
44 * @status: client connect response status
45 *
46 * returns corresponding error code
47 */
48static int mei_cl_conn_status_to_errno(enum mei_cl_connect_status status)
49{
50 switch (status) {
51 case MEI_CL_CONN_SUCCESS: return 0;
52 case MEI_CL_CONN_NOT_FOUND: return -ENOTTY;
53 case MEI_CL_CONN_ALREADY_STARTED: return -EBUSY;
54 case MEI_CL_CONN_OUT_OF_RESOURCES: return -EBUSY;
55 case MEI_CL_CONN_MESSAGE_SMALL: return -EINVAL;
56 default: return -EINVAL;
57 }
58}
25 59
26/** 60/**
27 * mei_hbm_me_cl_allocate - allocates storage for me clients 61 * mei_hbm_me_cl_allocate - allocates storage for me clients
@@ -100,33 +134,6 @@ bool mei_hbm_cl_addr_equal(struct mei_cl *cl, void *buf)
100 134
101 135
102/** 136/**
103 * is_treat_specially_client - checks if the message belongs
104 * to the file private data.
105 *
106 * @cl: private data of the file object
107 * @rs: connect response bus message
108 *
109 */
110static bool is_treat_specially_client(struct mei_cl *cl,
111 struct hbm_client_connect_response *rs)
112{
113 if (mei_hbm_cl_addr_equal(cl, rs)) {
114 if (!rs->status) {
115 cl->state = MEI_FILE_CONNECTED;
116 cl->status = 0;
117
118 } else {
119 cl->state = MEI_FILE_DISCONNECTED;
120 cl->status = -ENODEV;
121 }
122 cl->timer_count = 0;
123
124 return true;
125 }
126 return false;
127}
128
129/**
130 * mei_hbm_idle - set hbm to idle state 137 * mei_hbm_idle - set hbm to idle state
131 * 138 *
132 * @dev: the device structure 139 * @dev: the device structure
@@ -147,13 +154,13 @@ int mei_hbm_start_wait(struct mei_device *dev)
147 ret = wait_event_interruptible_timeout(dev->wait_recvd_msg, 154 ret = wait_event_interruptible_timeout(dev->wait_recvd_msg,
148 dev->hbm_state == MEI_HBM_IDLE || 155 dev->hbm_state == MEI_HBM_IDLE ||
149 dev->hbm_state >= MEI_HBM_STARTED, 156 dev->hbm_state >= MEI_HBM_STARTED,
150 mei_secs_to_jiffies(MEI_INTEROP_TIMEOUT)); 157 mei_secs_to_jiffies(MEI_HBM_TIMEOUT));
151 mutex_lock(&dev->device_lock); 158 mutex_lock(&dev->device_lock);
152 159
153 if (ret <= 0 && (dev->hbm_state <= MEI_HBM_START)) { 160 if (ret <= 0 && (dev->hbm_state <= MEI_HBM_START)) {
154 dev->hbm_state = MEI_HBM_IDLE; 161 dev->hbm_state = MEI_HBM_IDLE;
155 dev_err(&dev->pdev->dev, "waiting for mei start failed\n"); 162 dev_err(&dev->pdev->dev, "waiting for mei start failed\n");
156 return -ETIMEDOUT; 163 return -ETIME;
157 } 164 }
158 return 0; 165 return 0;
159} 166}
@@ -283,17 +290,18 @@ static int mei_hbm_prop_req(struct mei_device *dev)
283} 290}
284 291
285/** 292/**
286 * mei_hbm_stop_req_prepare - prepare stop request message 293 * mei_hbm_stop_req - send stop request message
287 * 294 *
288 * @dev - mei device 295 * @dev - mei device
289 * @mei_hdr - mei message header 296 * @cl: client info
290 * @data - hbm message body buffer 297 *
298 * This function returns -EIO on write failure
291 */ 299 */
292static void mei_hbm_stop_req_prepare(struct mei_device *dev, 300static int mei_hbm_stop_req(struct mei_device *dev)
293 struct mei_msg_hdr *mei_hdr, unsigned char *data)
294{ 301{
302 struct mei_msg_hdr *mei_hdr = &dev->wr_msg.hdr;
295 struct hbm_host_stop_request *req = 303 struct hbm_host_stop_request *req =
296 (struct hbm_host_stop_request *)data; 304 (struct hbm_host_stop_request *)dev->wr_msg.data;
297 const size_t len = sizeof(struct hbm_host_stop_request); 305 const size_t len = sizeof(struct hbm_host_stop_request);
298 306
299 mei_hbm_hdr(mei_hdr, len); 307 mei_hbm_hdr(mei_hdr, len);
@@ -301,6 +309,8 @@ static void mei_hbm_stop_req_prepare(struct mei_device *dev,
301 memset(req, 0, len); 309 memset(req, 0, len);
302 req->hbm_cmd = HOST_STOP_REQ_CMD; 310 req->hbm_cmd = HOST_STOP_REQ_CMD;
303 req->reason = DRIVER_STOP_REQUEST; 311 req->reason = DRIVER_STOP_REQUEST;
312
313 return mei_write_message(dev, mei_hdr, dev->wr_msg.data);
304} 314}
305 315
306/** 316/**
@@ -319,8 +329,7 @@ int mei_hbm_cl_flow_control_req(struct mei_device *dev, struct mei_cl *cl)
319 mei_hbm_hdr(mei_hdr, len); 329 mei_hbm_hdr(mei_hdr, len);
320 mei_hbm_cl_hdr(cl, MEI_FLOW_CONTROL_CMD, dev->wr_msg.data, len); 330 mei_hbm_cl_hdr(cl, MEI_FLOW_CONTROL_CMD, dev->wr_msg.data, len);
321 331
322 dev_dbg(&dev->pdev->dev, "sending flow control host client = %d, ME client = %d\n", 332 cl_dbg(dev, cl, "sending flow control\n");
323 cl->host_client_id, cl->me_client_id);
324 333
325 return mei_write_message(dev, mei_hdr, dev->wr_msg.data); 334 return mei_write_message(dev, mei_hdr, dev->wr_msg.data);
326} 335}
@@ -330,27 +339,34 @@ int mei_hbm_cl_flow_control_req(struct mei_device *dev, struct mei_cl *cl)
330 * 339 *
331 * @dev: the device structure 340 * @dev: the device structure
332 * @flow: flow control. 341 * @flow: flow control.
342 *
343 * return 0 on success, < 0 otherwise
333 */ 344 */
334static void mei_hbm_add_single_flow_creds(struct mei_device *dev, 345static int mei_hbm_add_single_flow_creds(struct mei_device *dev,
335 struct hbm_flow_control *flow) 346 struct hbm_flow_control *flow)
336{ 347{
337 struct mei_me_client *client; 348 struct mei_me_client *me_cl;
338 int i; 349 int id;
339 350
340 for (i = 0; i < dev->me_clients_num; i++) { 351 id = mei_me_cl_by_id(dev, flow->me_addr);
341 client = &dev->me_clients[i]; 352 if (id < 0) {
342 if (client && flow->me_addr == client->client_id) { 353 dev_err(&dev->pdev->dev, "no such me client %d\n",
343 if (client->props.single_recv_buf) { 354 flow->me_addr);
344 client->mei_flow_ctrl_creds++; 355 return id;
345 dev_dbg(&dev->pdev->dev, "recv flow ctrl msg ME %d (single).\n",
346 flow->me_addr);
347 dev_dbg(&dev->pdev->dev, "flow control credentials =%d.\n",
348 client->mei_flow_ctrl_creds);
349 } else {
350 BUG(); /* error in flow control */
351 }
352 }
353 } 356 }
357
358 me_cl = &dev->me_clients[id];
359 if (me_cl->props.single_recv_buf) {
360 me_cl->mei_flow_ctrl_creds++;
361 dev_dbg(&dev->pdev->dev, "recv flow ctrl msg ME %d (single).\n",
362 flow->me_addr);
363 dev_dbg(&dev->pdev->dev, "flow control credentials =%d.\n",
364 me_cl->mei_flow_ctrl_creds);
365 } else {
366 BUG(); /* error in flow control */
367 }
368
369 return 0;
354} 370}
355 371
356/** 372/**
@@ -362,8 +378,7 @@ static void mei_hbm_add_single_flow_creds(struct mei_device *dev,
362static void mei_hbm_cl_flow_control_res(struct mei_device *dev, 378static void mei_hbm_cl_flow_control_res(struct mei_device *dev,
363 struct hbm_flow_control *flow_control) 379 struct hbm_flow_control *flow_control)
364{ 380{
365 struct mei_cl *cl = NULL; 381 struct mei_cl *cl;
366 struct mei_cl *next = NULL;
367 382
368 if (!flow_control->host_addr) { 383 if (!flow_control->host_addr) {
369 /* single receive buffer */ 384 /* single receive buffer */
@@ -372,7 +387,7 @@ static void mei_hbm_cl_flow_control_res(struct mei_device *dev,
372 } 387 }
373 388
374 /* normal connection */ 389 /* normal connection */
375 list_for_each_entry_safe(cl, next, &dev->file_list, link) { 390 list_for_each_entry(cl, &dev->file_list, link) {
376 if (mei_hbm_cl_addr_equal(cl, flow_control)) { 391 if (mei_hbm_cl_addr_equal(cl, flow_control)) {
377 cl->mei_flow_ctrl_creds++; 392 cl->mei_flow_ctrl_creds++;
378 dev_dbg(&dev->pdev->dev, "flow ctrl msg for host %d ME %d.\n", 393 dev_dbg(&dev->pdev->dev, "flow ctrl msg for host %d ME %d.\n",
@@ -405,6 +420,25 @@ int mei_hbm_cl_disconnect_req(struct mei_device *dev, struct mei_cl *cl)
405} 420}
406 421
407/** 422/**
423 * mei_hbm_cl_disconnect_rsp - sends disconnect respose to the FW
424 *
425 * @dev: the device structure
426 * @cl: a client to disconnect from
427 *
428 * This function returns -EIO on write failure
429 */
430int mei_hbm_cl_disconnect_rsp(struct mei_device *dev, struct mei_cl *cl)
431{
432 struct mei_msg_hdr *mei_hdr = &dev->wr_msg.hdr;
433 const size_t len = sizeof(struct hbm_client_connect_response);
434
435 mei_hbm_hdr(mei_hdr, len);
436 mei_hbm_cl_hdr(cl, CLIENT_DISCONNECT_RES_CMD, dev->wr_msg.data, len);
437
438 return mei_write_message(dev, mei_hdr, dev->wr_msg.data);
439}
440
441/**
408 * mei_hbm_cl_disconnect_res - disconnect response from ME 442 * mei_hbm_cl_disconnect_res - disconnect response from ME
409 * 443 *
410 * @dev: the device structure 444 * @dev: the device structure
@@ -414,29 +448,23 @@ static void mei_hbm_cl_disconnect_res(struct mei_device *dev,
414 struct hbm_client_connect_response *rs) 448 struct hbm_client_connect_response *rs)
415{ 449{
416 struct mei_cl *cl; 450 struct mei_cl *cl;
417 struct mei_cl_cb *pos = NULL, *next = NULL; 451 struct mei_cl_cb *cb, *next;
418 452
419 dev_dbg(&dev->pdev->dev, 453 dev_dbg(&dev->pdev->dev, "hbm: disconnect response cl:host=%02d me=%02d status=%d\n",
420 "disconnect_response:\n" 454 rs->me_addr, rs->host_addr, rs->status);
421 "ME Client = %d\n" 455
422 "Host Client = %d\n" 456 list_for_each_entry_safe(cb, next, &dev->ctrl_rd_list.list, list) {
423 "Status = %d\n", 457 cl = cb->cl;
424 rs->me_addr, 458
425 rs->host_addr, 459 /* this should not happen */
426 rs->status); 460 if (WARN_ON(!cl)) {
427 461 list_del(&cb->list);
428 list_for_each_entry_safe(pos, next, &dev->ctrl_rd_list.list, list) {
429 cl = pos->cl;
430
431 if (!cl) {
432 list_del(&pos->list);
433 return; 462 return;
434 } 463 }
435 464
436 dev_dbg(&dev->pdev->dev, "list_for_each_entry_safe in ctrl_rd_list.\n");
437 if (mei_hbm_cl_addr_equal(cl, rs)) { 465 if (mei_hbm_cl_addr_equal(cl, rs)) {
438 list_del(&pos->list); 466 list_del(&cb->list);
439 if (!rs->status) 467 if (rs->status == MEI_CL_DISCONN_SUCCESS)
440 cl->state = MEI_FILE_DISCONNECTED; 468 cl->state = MEI_FILE_DISCONNECTED;
441 469
442 cl->status = 0; 470 cl->status = 0;
@@ -476,46 +504,41 @@ static void mei_hbm_cl_connect_res(struct mei_device *dev,
476{ 504{
477 505
478 struct mei_cl *cl; 506 struct mei_cl *cl;
479 struct mei_cl_cb *pos = NULL, *next = NULL; 507 struct mei_cl_cb *cb, *next;
480 508
481 dev_dbg(&dev->pdev->dev, 509 dev_dbg(&dev->pdev->dev, "hbm: connect response cl:host=%02d me=%02d status=%s\n",
482 "connect_response:\n" 510 rs->me_addr, rs->host_addr,
483 "ME Client = %d\n" 511 mei_cl_conn_status_str(rs->status));
484 "Host Client = %d\n"
485 "Status = %d\n",
486 rs->me_addr,
487 rs->host_addr,
488 rs->status);
489 512
490 /* if WD or iamthif client treat specially */ 513 cl = NULL;
491 514
492 if (is_treat_specially_client(&dev->wd_cl, rs)) { 515 list_for_each_entry_safe(cb, next, &dev->ctrl_rd_list.list, list) {
493 dev_dbg(&dev->pdev->dev, "successfully connected to WD client.\n");
494 mei_watchdog_register(dev);
495 516
496 return; 517 cl = cb->cl;
497 } 518 /* this should not happen */
519 if (WARN_ON(!cl)) {
520 list_del_init(&cb->list);
521 continue;
522 }
498 523
499 if (is_treat_specially_client(&dev->iamthif_cl, rs)) { 524 if (cb->fop_type != MEI_FOP_CONNECT)
500 dev->iamthif_state = MEI_IAMTHIF_IDLE; 525 continue;
501 return;
502 }
503 list_for_each_entry_safe(pos, next, &dev->ctrl_rd_list.list, list) {
504 526
505 cl = pos->cl; 527 if (mei_hbm_cl_addr_equal(cl, rs)) {
506 if (!cl) { 528 list_del(&cb->list);
507 list_del(&pos->list); 529 break;
508 return;
509 }
510 if (pos->fop_type == MEI_FOP_IOCTL) {
511 if (is_treat_specially_client(cl, rs)) {
512 list_del(&pos->list);
513 cl->status = 0;
514 cl->timer_count = 0;
515 break;
516 }
517 } 530 }
518 } 531 }
532
533 if (!cl)
534 return;
535
536 cl->timer_count = 0;
537 if (rs->status == MEI_CL_CONN_SUCCESS)
538 cl->state = MEI_FILE_CONNECTED;
539 else
540 cl->state = MEI_FILE_DISCONNECTED;
541 cl->status = mei_cl_conn_status_to_errno(rs->status);
519} 542}
520 543
521 544
@@ -525,32 +548,34 @@ static void mei_hbm_cl_connect_res(struct mei_device *dev,
525 * 548 *
526 * @dev: the device structure. 549 * @dev: the device structure.
527 * @disconnect_req: disconnect request bus message from the me 550 * @disconnect_req: disconnect request bus message from the me
551 *
552 * returns -ENOMEM on allocation failure
528 */ 553 */
529static void mei_hbm_fw_disconnect_req(struct mei_device *dev, 554static int mei_hbm_fw_disconnect_req(struct mei_device *dev,
530 struct hbm_client_connect_request *disconnect_req) 555 struct hbm_client_connect_request *disconnect_req)
531{ 556{
532 struct mei_cl *cl, *next; 557 struct mei_cl *cl;
533 const size_t len = sizeof(struct hbm_client_connect_response); 558 struct mei_cl_cb *cb;
534 559
535 list_for_each_entry_safe(cl, next, &dev->file_list, link) { 560 list_for_each_entry(cl, &dev->file_list, link) {
536 if (mei_hbm_cl_addr_equal(cl, disconnect_req)) { 561 if (mei_hbm_cl_addr_equal(cl, disconnect_req)) {
537 dev_dbg(&dev->pdev->dev, "disconnect request host client %d ME client %d.\n", 562 dev_dbg(&dev->pdev->dev, "disconnect request host client %d ME client %d.\n",
538 disconnect_req->host_addr, 563 disconnect_req->host_addr,
539 disconnect_req->me_addr); 564 disconnect_req->me_addr);
540 cl->state = MEI_FILE_DISCONNECTED; 565 cl->state = MEI_FILE_DISCONNECTED;
541 cl->timer_count = 0; 566 cl->timer_count = 0;
542 if (cl == &dev->wd_cl) 567
543 dev->wd_pending = false; 568 cb = mei_io_cb_init(cl, NULL);
544 else if (cl == &dev->iamthif_cl) 569 if (!cb)
545 dev->iamthif_timer = 0; 570 return -ENOMEM;
546 571 cb->fop_type = MEI_FOP_DISCONNECT_RSP;
547 /* prepare disconnect response */ 572 cl_dbg(dev, cl, "add disconnect response as first\n");
548 mei_hbm_hdr(&dev->wr_ext_msg.hdr, len); 573 list_add(&cb->list, &dev->ctrl_wr_list.list);
549 mei_hbm_cl_hdr(cl, CLIENT_DISCONNECT_RES_CMD, 574
550 dev->wr_ext_msg.data, len);
551 break; 575 break;
552 } 576 }
553 } 577 }
578 return 0;
554} 579}
555 580
556 581
@@ -629,10 +654,7 @@ int mei_hbm_dispatch(struct mei_device *dev, struct mei_msg_hdr *hdr)
629 dev_warn(&dev->pdev->dev, "hbm: start: version mismatch - stopping the driver.\n"); 654 dev_warn(&dev->pdev->dev, "hbm: start: version mismatch - stopping the driver.\n");
630 655
631 dev->hbm_state = MEI_HBM_STOPPED; 656 dev->hbm_state = MEI_HBM_STOPPED;
632 mei_hbm_stop_req_prepare(dev, &dev->wr_msg.hdr, 657 if (mei_hbm_stop_req(dev)) {
633 dev->wr_msg.data);
634 if (mei_write_message(dev, &dev->wr_msg.hdr,
635 dev->wr_msg.data)) {
636 dev_err(&dev->pdev->dev, "hbm: start: failed to send stop request\n"); 658 dev_err(&dev->pdev->dev, "hbm: start: failed to send stop request\n");
637 return -EIO; 659 return -EIO;
638 } 660 }
@@ -778,10 +800,11 @@ int mei_hbm_dispatch(struct mei_device *dev, struct mei_msg_hdr *hdr)
778 800
779 case ME_STOP_REQ_CMD: 801 case ME_STOP_REQ_CMD:
780 dev_dbg(&dev->pdev->dev, "hbm: stop request: message received\n"); 802 dev_dbg(&dev->pdev->dev, "hbm: stop request: message received\n");
781
782 dev->hbm_state = MEI_HBM_STOPPED; 803 dev->hbm_state = MEI_HBM_STOPPED;
783 mei_hbm_stop_req_prepare(dev, &dev->wr_ext_msg.hdr, 804 if (mei_hbm_stop_req(dev)) {
784 dev->wr_ext_msg.data); 805 dev_err(&dev->pdev->dev, "hbm: start: failed to send stop request\n");
806 return -EIO;
807 }
785 break; 808 break;
786 default: 809 default:
787 BUG(); 810 BUG();
diff --git a/drivers/misc/mei/hbm.h b/drivers/misc/mei/hbm.h
index 5f92188a5cd7..20e8782711c0 100644
--- a/drivers/misc/mei/hbm.h
+++ b/drivers/misc/mei/hbm.h
@@ -54,6 +54,7 @@ int mei_hbm_start_req(struct mei_device *dev);
54int mei_hbm_start_wait(struct mei_device *dev); 54int mei_hbm_start_wait(struct mei_device *dev);
55int mei_hbm_cl_flow_control_req(struct mei_device *dev, struct mei_cl *cl); 55int mei_hbm_cl_flow_control_req(struct mei_device *dev, struct mei_cl *cl);
56int mei_hbm_cl_disconnect_req(struct mei_device *dev, struct mei_cl *cl); 56int mei_hbm_cl_disconnect_req(struct mei_device *dev, struct mei_cl *cl);
57int mei_hbm_cl_disconnect_rsp(struct mei_device *dev, struct mei_cl *cl);
57int mei_hbm_cl_connect_req(struct mei_device *dev, struct mei_cl *cl); 58int mei_hbm_cl_connect_req(struct mei_device *dev, struct mei_cl *cl);
58bool mei_hbm_version_is_supported(struct mei_device *dev); 59bool mei_hbm_version_is_supported(struct mei_device *dev);
59 60
diff --git a/drivers/misc/mei/hw-me.c b/drivers/misc/mei/hw-me.c
index 6f656c053b14..8dbdaaef1af5 100644
--- a/drivers/misc/mei/hw-me.c
+++ b/drivers/misc/mei/hw-me.c
@@ -20,10 +20,10 @@
20#include <linux/interrupt.h> 20#include <linux/interrupt.h>
21 21
22#include "mei_dev.h" 22#include "mei_dev.h"
23#include "hw-me.h"
24
25#include "hbm.h" 23#include "hbm.h"
26 24
25#include "hw-me.h"
26#include "hw-me-regs.h"
27 27
28/** 28/**
29 * mei_me_reg_read - Reads 32bit data from the mei device 29 * mei_me_reg_read - Reads 32bit data from the mei device
@@ -240,11 +240,11 @@ static int mei_me_hw_ready_wait(struct mei_device *dev)
240 mutex_unlock(&dev->device_lock); 240 mutex_unlock(&dev->device_lock);
241 err = wait_event_interruptible_timeout(dev->wait_hw_ready, 241 err = wait_event_interruptible_timeout(dev->wait_hw_ready,
242 dev->recvd_hw_ready, 242 dev->recvd_hw_ready,
243 mei_secs_to_jiffies(MEI_INTEROP_TIMEOUT)); 243 mei_secs_to_jiffies(MEI_HW_READY_TIMEOUT));
244 mutex_lock(&dev->device_lock); 244 mutex_lock(&dev->device_lock);
245 if (!err && !dev->recvd_hw_ready) { 245 if (!err && !dev->recvd_hw_ready) {
246 if (!err) 246 if (!err)
247 err = -ETIMEDOUT; 247 err = -ETIME;
248 dev_err(&dev->pdev->dev, 248 dev_err(&dev->pdev->dev,
249 "wait hw ready failed. status = %d\n", err); 249 "wait hw ready failed. status = %d\n", err);
250 return err; 250 return err;
@@ -303,7 +303,7 @@ static bool mei_me_hbuf_is_empty(struct mei_device *dev)
303 * 303 *
304 * @dev: the device structure 304 * @dev: the device structure
305 * 305 *
306 * returns -1(ESLOTS_OVERFLOW) if overflow, otherwise empty slots count 306 * returns -EOVERFLOW if overflow, otherwise empty slots count
307 */ 307 */
308static int mei_me_hbuf_empty_slots(struct mei_device *dev) 308static int mei_me_hbuf_empty_slots(struct mei_device *dev)
309{ 309{
@@ -326,7 +326,7 @@ static size_t mei_me_hbuf_max_len(const struct mei_device *dev)
326 326
327 327
328/** 328/**
329 * mei_write_message - writes a message to mei device. 329 * mei_me_write_message - writes a message to mei device.
330 * 330 *
331 * @dev: the device structure 331 * @dev: the device structure
332 * @header: mei HECI header of message 332 * @header: mei HECI header of message
@@ -354,7 +354,7 @@ static int mei_me_write_message(struct mei_device *dev,
354 354
355 dw_cnt = mei_data2slots(length); 355 dw_cnt = mei_data2slots(length);
356 if (empty_slots < 0 || dw_cnt > empty_slots) 356 if (empty_slots < 0 || dw_cnt > empty_slots)
357 return -EIO; 357 return -EMSGSIZE;
358 358
359 mei_me_reg_write(hw, H_CB_WW, *((u32 *) header)); 359 mei_me_reg_write(hw, H_CB_WW, *((u32 *) header));
360 360
@@ -381,7 +381,7 @@ static int mei_me_write_message(struct mei_device *dev,
381 * 381 *
382 * @dev: the device structure 382 * @dev: the device structure
383 * 383 *
384 * returns -1(ESLOTS_OVERFLOW) if overflow, otherwise filled slots count 384 * returns -EOVERFLOW if overflow, otherwise filled slots count
385 */ 385 */
386static int mei_me_count_full_read_slots(struct mei_device *dev) 386static int mei_me_count_full_read_slots(struct mei_device *dev)
387{ 387{
@@ -505,17 +505,25 @@ irqreturn_t mei_me_irq_thread_handler(int irq, void *dev_id)
505 /* check slots available for reading */ 505 /* check slots available for reading */
506 slots = mei_count_full_read_slots(dev); 506 slots = mei_count_full_read_slots(dev);
507 while (slots > 0) { 507 while (slots > 0) {
508 /* we have urgent data to send so break the read */
509 if (dev->wr_ext_msg.hdr.length)
510 break;
511 dev_dbg(&dev->pdev->dev, "slots to read = %08x\n", slots); 508 dev_dbg(&dev->pdev->dev, "slots to read = %08x\n", slots);
512 rets = mei_irq_read_handler(dev, &complete_list, &slots); 509 rets = mei_irq_read_handler(dev, &complete_list, &slots);
510 /* There is a race between ME write and interrupt delivery:
511 * Not all data is always available immediately after the
512 * interrupt, so try to read again on the next interrupt.
513 */
514 if (rets == -ENODATA)
515 break;
516
513 if (rets && dev->dev_state != MEI_DEV_RESETTING) { 517 if (rets && dev->dev_state != MEI_DEV_RESETTING) {
518 dev_err(&dev->pdev->dev, "mei_irq_read_handler ret = %d.\n",
519 rets);
514 schedule_work(&dev->reset_work); 520 schedule_work(&dev->reset_work);
515 goto end; 521 goto end;
516 } 522 }
517 } 523 }
518 524
525 dev->hbuf_is_ready = mei_hbuf_is_ready(dev);
526
519 rets = mei_irq_write_handler(dev, &complete_list); 527 rets = mei_irq_write_handler(dev, &complete_list);
520 528
521 dev->hbuf_is_ready = mei_hbuf_is_ready(dev); 529 dev->hbuf_is_ready = mei_hbuf_is_ready(dev);
diff --git a/drivers/misc/mei/hw-txe-regs.h b/drivers/misc/mei/hw-txe-regs.h
new file mode 100644
index 000000000000..7283c24c1af1
--- /dev/null
+++ b/drivers/misc/mei/hw-txe-regs.h
@@ -0,0 +1,294 @@
1/******************************************************************************
2 * Intel Management Engine Interface (Intel MEI) Linux driver
3 * Intel MEI Interface Header
4 *
5 * This file is provided under a dual BSD/GPLv2 license. When using or
6 * redistributing this file, you may do so under either license.
7 *
8 * GPL LICENSE SUMMARY
9 *
10 * Copyright(c) 2013 - 2014 Intel Corporation. All rights reserved.
11 *
12 * This program is free software; you can redistribute it and/or modify
13 * it under the terms of version 2 of the GNU General Public License as
14 * published by the Free Software Foundation.
15 *
16 * This program is distributed in the hope that it will be useful, but
17 * WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 * General Public License for more details.
20 *
21 * The full GNU General Public License is included in this distribution
22 * in the file called COPYING
23 *
24 * Contact Information:
25 * Intel Corporation.
26 * linux-mei@linux.intel.com
27 * http://www.intel.com
28 *
29 * BSD LICENSE
30 *
31 * Copyright(c) 2013 - 2014 Intel Corporation. All rights reserved.
32 * All rights reserved.
33 *
34 * Redistribution and use in source and binary forms, with or without
35 * modification, are permitted provided that the following conditions
36 * are met:
37 *
38 * * Redistributions of source code must retain the above copyright
39 * notice, this list of conditions and the following disclaimer.
40 * * Redistributions in binary form must reproduce the above copyright
41 * notice, this list of conditions and the following disclaimer in
42 * the documentation and/or other materials provided with the
43 * distribution.
44 * * Neither the name Intel Corporation nor the names of its
45 * contributors may be used to endorse or promote products derived
46 * from this software without specific prior written permission.
47 *
48 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
49 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
50 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
51 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
52 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
53 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
54 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
55 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
56 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
57 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
58 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
59 *
60 *****************************************************************************/
61#ifndef _MEI_HW_TXE_REGS_H_
62#define _MEI_HW_TXE_REGS_H_
63
64#include "hw.h"
65
66#define SEC_ALIVENESS_TIMER_TIMEOUT (5 * MSEC_PER_SEC)
67#define SEC_ALIVENESS_WAIT_TIMEOUT (1 * MSEC_PER_SEC)
68#define SEC_RESET_WAIT_TIMEOUT (1 * MSEC_PER_SEC)
69#define SEC_READY_WAIT_TIMEOUT (5 * MSEC_PER_SEC)
70#define START_MESSAGE_RESPONSE_WAIT_TIMEOUT (5 * MSEC_PER_SEC)
71#define RESET_CANCEL_WAIT_TIMEOUT (1 * MSEC_PER_SEC)
72
73enum {
74 SEC_BAR,
75 BRIDGE_BAR,
76
77 NUM_OF_MEM_BARS
78};
79
80/* SeC FW Status Register
81 *
82 * FW uses this register in order to report its status to host.
83 * This register resides in PCI-E config space.
84 */
85#define PCI_CFG_TXE_FW_STS0 0x40
86# define PCI_CFG_TXE_FW_STS0_WRK_ST_MSK 0x0000000F
87# define PCI_CFG_TXE_FW_STS0_OP_ST_MSK 0x000001C0
88# define PCI_CFG_TXE_FW_STS0_FW_INIT_CMPLT 0x00000200
89# define PCI_CFG_TXE_FW_STS0_ERR_CODE_MSK 0x0000F000
90# define PCI_CFG_TXE_FW_STS0_OP_MODE_MSK 0x000F0000
91# define PCI_CFG_TXE_FW_STS0_RST_CNT_MSK 0x00F00000
92
93
94#define IPC_BASE_ADDR 0x80400 /* SeC IPC Base Address */
95
96/* IPC Input Doorbell Register */
97#define SEC_IPC_INPUT_DOORBELL_REG (0x0000 + IPC_BASE_ADDR)
98
99/* IPC Input Status Register
100 * This register indicates whether or not processing of
101 * the most recent command has been completed by the SEC
102 * New commands and payloads should not be written by the Host
103 * until this indicates that the previous command has been processed.
104 */
105#define SEC_IPC_INPUT_STATUS_REG (0x0008 + IPC_BASE_ADDR)
106# define SEC_IPC_INPUT_STATUS_RDY BIT(0)
107
108/* IPC Host Interrupt Status Register */
109#define SEC_IPC_HOST_INT_STATUS_REG (0x0010 + IPC_BASE_ADDR)
110#define SEC_IPC_HOST_INT_STATUS_OUT_DB BIT(0)
111#define SEC_IPC_HOST_INT_STATUS_IN_RDY BIT(1)
112#define SEC_IPC_HOST_INT_STATUS_HDCP_M0_RCVD BIT(5)
113#define SEC_IPC_HOST_INT_STATUS_ILL_MEM_ACCESS BIT(17)
114#define SEC_IPC_HOST_INT_STATUS_AES_HKEY_ERR BIT(18)
115#define SEC_IPC_HOST_INT_STATUS_DES_HKEY_ERR BIT(19)
116#define SEC_IPC_HOST_INT_STATUS_TMRMTB_OVERFLOW BIT(21)
117
118/* Convenient mask for pending interrupts */
119#define SEC_IPC_HOST_INT_STATUS_PENDING \
120 (SEC_IPC_HOST_INT_STATUS_OUT_DB| \
121 SEC_IPC_HOST_INT_STATUS_IN_RDY)
122
123/* IPC Host Interrupt Mask Register */
124#define SEC_IPC_HOST_INT_MASK_REG (0x0014 + IPC_BASE_ADDR)
125
126# define SEC_IPC_HOST_INT_MASK_OUT_DB BIT(0) /* Output Doorbell Int Mask */
127# define SEC_IPC_HOST_INT_MASK_IN_RDY BIT(1) /* Input Ready Int Mask */
128
129/* IPC Input Payload RAM */
130#define SEC_IPC_INPUT_PAYLOAD_REG (0x0100 + IPC_BASE_ADDR)
131/* IPC Shared Payload RAM */
132#define IPC_SHARED_PAYLOAD_REG (0x0200 + IPC_BASE_ADDR)
133
134/* SeC Address Translation Table Entry 2 - Ctrl
135 *
136 * This register resides also in SeC's PCI-E Memory space.
137 */
138#define SATT2_CTRL_REG 0x1040
139# define SATT2_CTRL_VALID_MSK BIT(0)
140# define SATT2_CTRL_BR_BASE_ADDR_REG_SHIFT 8
141# define SATT2_CTRL_BRIDGE_HOST_EN_MSK BIT(12)
142
143/* SATT Table Entry 2 SAP Base Address Register */
144#define SATT2_SAP_BA_REG 0x1044
145/* SATT Table Entry 2 SAP Size Register. */
146#define SATT2_SAP_SIZE_REG 0x1048
147 /* SATT Table Entry 2 SAP Bridge Address - LSB Register */
148#define SATT2_BRG_BA_LSB_REG 0x104C
149
150/* Host High-level Interrupt Status Register */
151#define HHISR_REG 0x2020
152/* Host High-level Interrupt Enable Register
153 *
154 * Resides in PCI memory space. This is the top hierarchy for
155 * interrupts from SeC to host, aggregating both interrupts that
156 * arrive through HICR registers as well as interrupts
157 * that arrive via IPC.
158 */
159#define HHIER_REG 0x2024
160#define IPC_HHIER_SEC BIT(0)
161#define IPC_HHIER_BRIDGE BIT(1)
162#define IPC_HHIER_MSK (IPC_HHIER_SEC | IPC_HHIER_BRIDGE)
163
164/* Host High-level Interrupt Mask Register.
165 *
166 * Resides in PCI memory space.
167 * This is the top hierarchy for masking interrupts from SeC to host.
168 */
169#define HHIMR_REG 0x2028
170#define IPC_HHIMR_SEC BIT(0)
171#define IPC_HHIMR_BRIDGE BIT(1)
172
173/* Host High-level IRQ Status Register */
174#define HHIRQSR_REG 0x202C
175
176/* Host Interrupt Cause Register 0 - SeC IPC Readiness
177 *
178 * This register is both an ICR to Host from PCI Memory Space
179 * and it is also exposed in the SeC memory space.
180 * This register is used by SeC's IPC driver in order
181 * to synchronize with host about IPC interface state.
182 */
183#define HICR_SEC_IPC_READINESS_REG 0x2040
184#define HICR_SEC_IPC_READINESS_HOST_RDY BIT(0)
185#define HICR_SEC_IPC_READINESS_SEC_RDY BIT(1)
186#define HICR_SEC_IPC_READINESS_SYS_RDY \
187 (HICR_SEC_IPC_READINESS_HOST_RDY | \
188 HICR_SEC_IPC_READINESS_SEC_RDY)
189#define HICR_SEC_IPC_READINESS_RDY_CLR BIT(2)
190
191/* Host Interrupt Cause Register 1 - Aliveness Response */
192/* This register is both an ICR to Host from PCI Memory Space
193 * and it is also exposed in the SeC memory space.
194 * The register may be used by SeC to ACK a host request for aliveness.
195 */
196#define HICR_HOST_ALIVENESS_RESP_REG 0x2044
197#define HICR_HOST_ALIVENESS_RESP_ACK BIT(0)
198
199/* Host Interrupt Cause Register 2 - SeC IPC Output Doorbell */
200#define HICR_SEC_IPC_OUTPUT_DOORBELL_REG 0x2048
201
202/* Host Interrupt Status Register.
203 *
204 * Resides in PCI memory space.
205 * This is the main register involved in generating interrupts
206 * from SeC to host via HICRs.
207 * The interrupt generation rules are as follows:
208 * An interrupt will be generated whenever for any i,
209 * there is a transition from a state where at least one of
210 * the following conditions did not hold, to a state where
211 * ALL the following conditions hold:
212 * A) HISR.INT[i]_STS == 1.
213 * B) HIER.INT[i]_EN == 1.
214 */
215#define HISR_REG 0x2060
216#define HISR_INT_0_STS BIT(0)
217#define HISR_INT_1_STS BIT(1)
218#define HISR_INT_2_STS BIT(2)
219#define HISR_INT_3_STS BIT(3)
220#define HISR_INT_4_STS BIT(4)
221#define HISR_INT_5_STS BIT(5)
222#define HISR_INT_6_STS BIT(6)
223#define HISR_INT_7_STS BIT(7)
224#define HISR_INT_STS_MSK \
225 (HISR_INT_0_STS | HISR_INT_1_STS | HISR_INT_2_STS)
226
227/* Host Interrupt Enable Register. Resides in PCI memory space. */
228#define HIER_REG 0x2064
229#define HIER_INT_0_EN BIT(0)
230#define HIER_INT_1_EN BIT(1)
231#define HIER_INT_2_EN BIT(2)
232#define HIER_INT_3_EN BIT(3)
233#define HIER_INT_4_EN BIT(4)
234#define HIER_INT_5_EN BIT(5)
235#define HIER_INT_6_EN BIT(6)
236#define HIER_INT_7_EN BIT(7)
237
238#define HIER_INT_EN_MSK \
239 (HIER_INT_0_EN | HIER_INT_1_EN | HIER_INT_2_EN)
240
241
242/* SEC Memory Space IPC output payload.
243 *
244 * This register is part of the output payload which SEC provides to host.
245 */
246#define BRIDGE_IPC_OUTPUT_PAYLOAD_REG 0x20C0
247
248/* SeC Interrupt Cause Register - Host Aliveness Request
249 * This register is both an ICR to SeC and it is also exposed
250 * in the host-visible PCI memory space.
251 * The register is used by host to request SeC aliveness.
252 */
253#define SICR_HOST_ALIVENESS_REQ_REG 0x214C
254#define SICR_HOST_ALIVENESS_REQ_REQUESTED BIT(0)
255
256
257/* SeC Interrupt Cause Register - Host IPC Readiness
258 *
259 * This register is both an ICR to SeC and it is also exposed
260 * in the host-visible PCI memory space.
261 * This register is used by the host's SeC driver uses in order
262 * to synchronize with SeC about IPC interface state.
263 */
264#define SICR_HOST_IPC_READINESS_REQ_REG 0x2150
265
266
267#define SICR_HOST_IPC_READINESS_HOST_RDY BIT(0)
268#define SICR_HOST_IPC_READINESS_SEC_RDY BIT(1)
269#define SICR_HOST_IPC_READINESS_SYS_RDY \
270 (SICR_HOST_IPC_READINESS_HOST_RDY | \
271 SICR_HOST_IPC_READINESS_SEC_RDY)
272#define SICR_HOST_IPC_READINESS_RDY_CLR BIT(2)
273
274/* SeC Interrupt Cause Register - SeC IPC Output Status
275 *
276 * This register indicates whether or not processing of the most recent
277 * command has been completed by the Host.
278 * New commands and payloads should not be written by SeC until this
279 * register indicates that the previous command has been processed.
280 */
281#define SICR_SEC_IPC_OUTPUT_STATUS_REG 0x2154
282# define SEC_IPC_OUTPUT_STATUS_RDY BIT(0)
283
284
285
286/* MEI IPC Message payload size 64 bytes */
287#define PAYLOAD_SIZE 64
288
289/* MAX size for SATT range 32MB */
290#define SATT_RANGE_MAX (32 << 20)
291
292
293#endif /* _MEI_HW_TXE_REGS_H_ */
294
diff --git a/drivers/misc/mei/hw-txe.c b/drivers/misc/mei/hw-txe.c
new file mode 100644
index 000000000000..f60182a52f96
--- /dev/null
+++ b/drivers/misc/mei/hw-txe.c
@@ -0,0 +1,1107 @@
1/*
2 *
3 * Intel Management Engine Interface (Intel MEI) Linux driver
4 * Copyright (c) 2013-2014, Intel Corporation.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
14 *
15 */
16
17#include <linux/pci.h>
18#include <linux/jiffies.h>
19#include <linux/delay.h>
20#include <linux/kthread.h>
21#include <linux/irqreturn.h>
22
23#include <linux/mei.h>
24
25#include "mei_dev.h"
26#include "hw-txe.h"
27#include "client.h"
28#include "hbm.h"
29
30/**
31 * mei_txe_reg_read - Reads 32bit data from the device
32 *
33 * @base_addr: registers base address
34 * @offset: register offset
35 *
36 */
37static inline u32 mei_txe_reg_read(void __iomem *base_addr,
38 unsigned long offset)
39{
40 return ioread32(base_addr + offset);
41}
42
43/**
44 * mei_txe_reg_write - Writes 32bit data to the device
45 *
46 * @base_addr: registers base address
47 * @offset: register offset
48 * @value: the value to write
49 */
50static inline void mei_txe_reg_write(void __iomem *base_addr,
51 unsigned long offset, u32 value)
52{
53 iowrite32(value, base_addr + offset);
54}
55
56/**
57 * mei_txe_sec_reg_read_silent - Reads 32bit data from the SeC BAR
58 *
59 * @dev: the device structure
60 * @offset: register offset
61 *
62 * Doesn't check for aliveness while Reads 32bit data from the SeC BAR
63 */
64static inline u32 mei_txe_sec_reg_read_silent(struct mei_txe_hw *hw,
65 unsigned long offset)
66{
67 return mei_txe_reg_read(hw->mem_addr[SEC_BAR], offset);
68}
69
70/**
71 * mei_txe_sec_reg_read - Reads 32bit data from the SeC BAR
72 *
73 * @dev: the device structure
74 * @offset: register offset
75 *
76 * Reads 32bit data from the SeC BAR and shout loud if aliveness is not set
77 */
78static inline u32 mei_txe_sec_reg_read(struct mei_txe_hw *hw,
79 unsigned long offset)
80{
81 WARN(!hw->aliveness, "sec read: aliveness not asserted\n");
82 return mei_txe_sec_reg_read_silent(hw, offset);
83}
84/**
85 * mei_txe_sec_reg_write_silent - Writes 32bit data to the SeC BAR
86 * doesn't check for aliveness
87 *
88 * @dev: the device structure
89 * @offset: register offset
90 * @value: value to write
91 *
92 * Doesn't check for aliveness while writes 32bit data from to the SeC BAR
93 */
94static inline void mei_txe_sec_reg_write_silent(struct mei_txe_hw *hw,
95 unsigned long offset, u32 value)
96{
97 mei_txe_reg_write(hw->mem_addr[SEC_BAR], offset, value);
98}
99
100/**
101 * mei_txe_sec_reg_write - Writes 32bit data to the SeC BAR
102 *
103 * @dev: the device structure
104 * @offset: register offset
105 * @value: value to write
106 *
107 * Writes 32bit data from the SeC BAR and shout loud if aliveness is not set
108 */
109static inline void mei_txe_sec_reg_write(struct mei_txe_hw *hw,
110 unsigned long offset, u32 value)
111{
112 WARN(!hw->aliveness, "sec write: aliveness not asserted\n");
113 mei_txe_sec_reg_write_silent(hw, offset, value);
114}
115/**
116 * mei_txe_br_reg_read - Reads 32bit data from the Bridge BAR
117 *
118 * @hw: the device structure
119 * @offset: offset from which to read the data
120 *
121 */
122static inline u32 mei_txe_br_reg_read(struct mei_txe_hw *hw,
123 unsigned long offset)
124{
125 return mei_txe_reg_read(hw->mem_addr[BRIDGE_BAR], offset);
126}
127
128/**
129 * mei_txe_br_reg_write - Writes 32bit data to the Bridge BAR
130 *
131 * @hw: the device structure
132 * @offset: offset from which to write the data
133 * @value: the byte to write
134 */
135static inline void mei_txe_br_reg_write(struct mei_txe_hw *hw,
136 unsigned long offset, u32 value)
137{
138 mei_txe_reg_write(hw->mem_addr[BRIDGE_BAR], offset, value);
139}
140
141/**
142 * mei_txe_aliveness_set - request for aliveness change
143 *
144 * @dev: the device structure
145 * @req: requested aliveness value
146 *
147 * Request for aliveness change and returns true if the change is
148 * really needed and false if aliveness is already
149 * in the requested state
150 * Requires device lock to be held
151 */
152static bool mei_txe_aliveness_set(struct mei_device *dev, u32 req)
153{
154
155 struct mei_txe_hw *hw = to_txe_hw(dev);
156 bool do_req = hw->aliveness != req;
157
158 dev_dbg(&dev->pdev->dev, "Aliveness current=%d request=%d\n",
159 hw->aliveness, req);
160 if (do_req) {
161 hw->recvd_aliveness = false;
162 mei_txe_br_reg_write(hw, SICR_HOST_ALIVENESS_REQ_REG, req);
163 }
164 return do_req;
165}
166
167
168/**
169 * mei_txe_aliveness_req_get - get aliveness requested register value
170 *
171 * @dev: the device structure
172 *
173 * Extract HICR_HOST_ALIVENESS_RESP_ACK bit from
174 * from HICR_HOST_ALIVENESS_REQ register value
175 */
176static u32 mei_txe_aliveness_req_get(struct mei_device *dev)
177{
178 struct mei_txe_hw *hw = to_txe_hw(dev);
179 u32 reg;
180 reg = mei_txe_br_reg_read(hw, SICR_HOST_ALIVENESS_REQ_REG);
181 return reg & SICR_HOST_ALIVENESS_REQ_REQUESTED;
182}
183
184/**
185 * mei_txe_aliveness_get - get aliveness response register value
186 * @dev: the device structure
187 *
188 * Extract HICR_HOST_ALIVENESS_RESP_ACK bit
189 * from HICR_HOST_ALIVENESS_RESP register value
190 */
191static u32 mei_txe_aliveness_get(struct mei_device *dev)
192{
193 struct mei_txe_hw *hw = to_txe_hw(dev);
194 u32 reg;
195 reg = mei_txe_br_reg_read(hw, HICR_HOST_ALIVENESS_RESP_REG);
196 return reg & HICR_HOST_ALIVENESS_RESP_ACK;
197}
198
199/**
200 * mei_txe_aliveness_poll - waits for aliveness to settle
201 *
202 * @dev: the device structure
203 * @expected: expected aliveness value
204 *
205 * Polls for HICR_HOST_ALIVENESS_RESP.ALIVENESS_RESP to be set
206 * returns > 0 if the expected value was received, -ETIME otherwise
207 */
208static int mei_txe_aliveness_poll(struct mei_device *dev, u32 expected)
209{
210 struct mei_txe_hw *hw = to_txe_hw(dev);
211 int t = 0;
212
213 do {
214 hw->aliveness = mei_txe_aliveness_get(dev);
215 if (hw->aliveness == expected) {
216 dev_dbg(&dev->pdev->dev,
217 "aliveness settled after %d msecs\n", t);
218 return t;
219 }
220 mutex_unlock(&dev->device_lock);
221 msleep(MSEC_PER_SEC / 5);
222 mutex_lock(&dev->device_lock);
223 t += MSEC_PER_SEC / 5;
224 } while (t < SEC_ALIVENESS_WAIT_TIMEOUT);
225
226 dev_err(&dev->pdev->dev, "aliveness timed out\n");
227 return -ETIME;
228}
229
230/**
231 * mei_txe_aliveness_wait - waits for aliveness to settle
232 *
233 * @dev: the device structure
234 * @expected: expected aliveness value
235 *
236 * Waits for HICR_HOST_ALIVENESS_RESP.ALIVENESS_RESP to be set
237 * returns returns 0 on success and < 0 otherwise
238 */
239static int mei_txe_aliveness_wait(struct mei_device *dev, u32 expected)
240{
241 struct mei_txe_hw *hw = to_txe_hw(dev);
242 const unsigned long timeout =
243 msecs_to_jiffies(SEC_ALIVENESS_WAIT_TIMEOUT);
244 long err;
245 int ret;
246
247 hw->aliveness = mei_txe_aliveness_get(dev);
248 if (hw->aliveness == expected)
249 return 0;
250
251 mutex_unlock(&dev->device_lock);
252 err = wait_event_timeout(hw->wait_aliveness,
253 hw->recvd_aliveness, timeout);
254 mutex_lock(&dev->device_lock);
255
256 hw->aliveness = mei_txe_aliveness_get(dev);
257 ret = hw->aliveness == expected ? 0 : -ETIME;
258
259 if (ret)
260 dev_err(&dev->pdev->dev, "aliveness timed out");
261 else
262 dev_dbg(&dev->pdev->dev, "aliveness settled after %d msecs\n",
263 jiffies_to_msecs(timeout - err));
264 hw->recvd_aliveness = false;
265 return ret;
266}
267
268/**
269 * mei_txe_aliveness_set_sync - sets an wait for aliveness to complete
270 *
271 * @dev: the device structure
272 *
273 * returns returns 0 on success and < 0 otherwise
274 */
275int mei_txe_aliveness_set_sync(struct mei_device *dev, u32 req)
276{
277 if (mei_txe_aliveness_set(dev, req))
278 return mei_txe_aliveness_wait(dev, req);
279 return 0;
280}
281
282/**
283 * mei_txe_input_ready_interrupt_enable - sets the Input Ready Interrupt
284 *
285 * @dev: the device structure
286 */
287static void mei_txe_input_ready_interrupt_enable(struct mei_device *dev)
288{
289 struct mei_txe_hw *hw = to_txe_hw(dev);
290 u32 hintmsk;
291 /* Enable the SEC_IPC_HOST_INT_MASK_IN_RDY interrupt */
292 hintmsk = mei_txe_sec_reg_read(hw, SEC_IPC_HOST_INT_MASK_REG);
293 hintmsk |= SEC_IPC_HOST_INT_MASK_IN_RDY;
294 mei_txe_sec_reg_write(hw, SEC_IPC_HOST_INT_MASK_REG, hintmsk);
295}
296
297/**
298 * mei_txe_input_doorbell_set
299 * - Sets bit 0 in SEC_IPC_INPUT_DOORBELL.IPC_INPUT_DOORBELL.
300 * @dev: the device structure
301 */
302static void mei_txe_input_doorbell_set(struct mei_txe_hw *hw)
303{
304 /* Clear the interrupt cause */
305 clear_bit(TXE_INTR_IN_READY_BIT, &hw->intr_cause);
306 mei_txe_sec_reg_write(hw, SEC_IPC_INPUT_DOORBELL_REG, 1);
307}
308
309/**
310 * mei_txe_output_ready_set - Sets the SICR_SEC_IPC_OUTPUT_STATUS bit to 1
311 *
312 * @dev: the device structure
313 */
314static void mei_txe_output_ready_set(struct mei_txe_hw *hw)
315{
316 mei_txe_br_reg_write(hw,
317 SICR_SEC_IPC_OUTPUT_STATUS_REG,
318 SEC_IPC_OUTPUT_STATUS_RDY);
319}
320
321/**
322 * mei_txe_is_input_ready - check if TXE is ready for receiving data
323 *
324 * @dev: the device structure
325 */
326static bool mei_txe_is_input_ready(struct mei_device *dev)
327{
328 struct mei_txe_hw *hw = to_txe_hw(dev);
329 u32 status;
330 status = mei_txe_sec_reg_read(hw, SEC_IPC_INPUT_STATUS_REG);
331 return !!(SEC_IPC_INPUT_STATUS_RDY & status);
332}
333
334/**
335 * mei_txe_intr_clear - clear all interrupts
336 *
337 * @dev: the device structure
338 */
339static inline void mei_txe_intr_clear(struct mei_device *dev)
340{
341 struct mei_txe_hw *hw = to_txe_hw(dev);
342 mei_txe_sec_reg_write_silent(hw, SEC_IPC_HOST_INT_STATUS_REG,
343 SEC_IPC_HOST_INT_STATUS_PENDING);
344 mei_txe_br_reg_write(hw, HISR_REG, HISR_INT_STS_MSK);
345 mei_txe_br_reg_write(hw, HHISR_REG, IPC_HHIER_MSK);
346}
347
348/**
349 * mei_txe_intr_disable - disable all interrupts
350 *
351 * @dev: the device structure
352 */
353static void mei_txe_intr_disable(struct mei_device *dev)
354{
355 struct mei_txe_hw *hw = to_txe_hw(dev);
356 mei_txe_br_reg_write(hw, HHIER_REG, 0);
357 mei_txe_br_reg_write(hw, HIER_REG, 0);
358}
359/**
360 * mei_txe_intr_disable - enable all interrupts
361 *
362 * @dev: the device structure
363 */
364static void mei_txe_intr_enable(struct mei_device *dev)
365{
366 struct mei_txe_hw *hw = to_txe_hw(dev);
367 mei_txe_br_reg_write(hw, HHIER_REG, IPC_HHIER_MSK);
368 mei_txe_br_reg_write(hw, HIER_REG, HIER_INT_EN_MSK);
369}
370
371/**
372 * mei_txe_pending_interrupts - check if there are pending interrupts
373 * only Aliveness, Input ready, and output doorbell are of relevance
374 *
375 * @dev: the device structure
376 *
377 * Checks if there are pending interrupts
378 * only Aliveness, Readiness, Input ready, and Output doorbell are relevant
379 */
380static bool mei_txe_pending_interrupts(struct mei_device *dev)
381{
382
383 struct mei_txe_hw *hw = to_txe_hw(dev);
384 bool ret = (hw->intr_cause & (TXE_INTR_READINESS |
385 TXE_INTR_ALIVENESS |
386 TXE_INTR_IN_READY |
387 TXE_INTR_OUT_DB));
388
389 if (ret) {
390 dev_dbg(&dev->pdev->dev,
391 "Pending Interrupts InReady=%01d Readiness=%01d, Aliveness=%01d, OutDoor=%01d\n",
392 !!(hw->intr_cause & TXE_INTR_IN_READY),
393 !!(hw->intr_cause & TXE_INTR_READINESS),
394 !!(hw->intr_cause & TXE_INTR_ALIVENESS),
395 !!(hw->intr_cause & TXE_INTR_OUT_DB));
396 }
397 return ret;
398}
399
400/**
401 * mei_txe_input_payload_write - write a dword to the host buffer
402 * at offset idx
403 *
404 * @dev: the device structure
405 * @idx: index in the host buffer
406 * @value: value
407 */
408static void mei_txe_input_payload_write(struct mei_device *dev,
409 unsigned long idx, u32 value)
410{
411 struct mei_txe_hw *hw = to_txe_hw(dev);
412 mei_txe_sec_reg_write(hw, SEC_IPC_INPUT_PAYLOAD_REG +
413 (idx * sizeof(u32)), value);
414}
415
416/**
417 * mei_txe_out_data_read - read dword from the device buffer
418 * at offset idx
419 *
420 * @dev: the device structure
421 * @idx: index in the device buffer
422 *
423 * returns register value at index
424 */
425static u32 mei_txe_out_data_read(const struct mei_device *dev,
426 unsigned long idx)
427{
428 struct mei_txe_hw *hw = to_txe_hw(dev);
429 return mei_txe_br_reg_read(hw,
430 BRIDGE_IPC_OUTPUT_PAYLOAD_REG + (idx * sizeof(u32)));
431}
432
433/* Readiness */
434
435/**
436 * mei_txe_readiness_set_host_rdy
437 *
438 * @dev: the device structure
439 */
440static void mei_txe_readiness_set_host_rdy(struct mei_device *dev)
441{
442 struct mei_txe_hw *hw = to_txe_hw(dev);
443 mei_txe_br_reg_write(hw,
444 SICR_HOST_IPC_READINESS_REQ_REG,
445 SICR_HOST_IPC_READINESS_HOST_RDY);
446}
447
448/**
449 * mei_txe_readiness_clear
450 *
451 * @dev: the device structure
452 */
453static void mei_txe_readiness_clear(struct mei_device *dev)
454{
455 struct mei_txe_hw *hw = to_txe_hw(dev);
456 mei_txe_br_reg_write(hw, SICR_HOST_IPC_READINESS_REQ_REG,
457 SICR_HOST_IPC_READINESS_RDY_CLR);
458}
459/**
460 * mei_txe_readiness_get - Reads and returns
461 * the HICR_SEC_IPC_READINESS register value
462 *
463 * @dev: the device structure
464 */
465static u32 mei_txe_readiness_get(struct mei_device *dev)
466{
467 struct mei_txe_hw *hw = to_txe_hw(dev);
468 return mei_txe_br_reg_read(hw, HICR_SEC_IPC_READINESS_REG);
469}
470
471
472/**
473 * mei_txe_readiness_is_sec_rdy - check readiness
474 * for HICR_SEC_IPC_READINESS_SEC_RDY
475 *
476 * @readiness - cached readiness state
477 */
478static inline bool mei_txe_readiness_is_sec_rdy(u32 readiness)
479{
480 return !!(readiness & HICR_SEC_IPC_READINESS_SEC_RDY);
481}
482
483/**
484 * mei_txe_hw_is_ready - check if the hw is ready
485 *
486 * @dev: the device structure
487 */
488static bool mei_txe_hw_is_ready(struct mei_device *dev)
489{
490 u32 readiness = mei_txe_readiness_get(dev);
491 return mei_txe_readiness_is_sec_rdy(readiness);
492}
493
494/**
495 * mei_txe_host_is_ready - check if the host is ready
496 *
497 * @dev: the device structure
498 */
499static inline bool mei_txe_host_is_ready(struct mei_device *dev)
500{
501 struct mei_txe_hw *hw = to_txe_hw(dev);
502 u32 reg = mei_txe_br_reg_read(hw, HICR_SEC_IPC_READINESS_REG);
503 return !!(reg & HICR_SEC_IPC_READINESS_HOST_RDY);
504}
505
506/**
507 * mei_txe_readiness_wait - wait till readiness settles
508 *
509 * @dev: the device structure
510 *
511 * returns 0 on success and -ETIME on timeout
512 */
513static int mei_txe_readiness_wait(struct mei_device *dev)
514{
515 if (mei_txe_hw_is_ready(dev))
516 return 0;
517
518 mutex_unlock(&dev->device_lock);
519 wait_event_timeout(dev->wait_hw_ready, dev->recvd_hw_ready,
520 msecs_to_jiffies(SEC_RESET_WAIT_TIMEOUT));
521 mutex_lock(&dev->device_lock);
522 if (!dev->recvd_hw_ready) {
523 dev_err(&dev->pdev->dev, "wait for readiness failed\n");
524 return -ETIME;
525 }
526
527 dev->recvd_hw_ready = false;
528 return 0;
529}
530
531/**
532 * mei_txe_hw_config - configure hardware at the start of the devices
533 *
534 * @dev: the device structure
535 *
536 * Configure hardware at the start of the device should be done only
537 * once at the device probe time
538 */
539static void mei_txe_hw_config(struct mei_device *dev)
540{
541
542 struct mei_txe_hw *hw = to_txe_hw(dev);
543 /* Doesn't change in runtime */
544 dev->hbuf_depth = PAYLOAD_SIZE / 4;
545
546 hw->aliveness = mei_txe_aliveness_get(dev);
547 hw->readiness = mei_txe_readiness_get(dev);
548
549 dev_dbg(&dev->pdev->dev, "aliveness_resp = 0x%08x, readiness = 0x%08x.\n",
550 hw->aliveness, hw->readiness);
551}
552
553
554/**
555 * mei_txe_write - writes a message to device.
556 *
557 * @dev: the device structure
558 * @header: header of message
559 * @buf: message buffer will be written
560 * returns 1 if success, 0 - otherwise.
561 */
562
563static int mei_txe_write(struct mei_device *dev,
564 struct mei_msg_hdr *header, unsigned char *buf)
565{
566 struct mei_txe_hw *hw = to_txe_hw(dev);
567 unsigned long rem;
568 unsigned long length;
569 int slots = dev->hbuf_depth;
570 u32 *reg_buf = (u32 *)buf;
571 u32 dw_cnt;
572 int i;
573
574 if (WARN_ON(!header || !buf))
575 return -EINVAL;
576
577 length = header->length;
578
579 dev_dbg(&dev->pdev->dev, MEI_HDR_FMT, MEI_HDR_PRM(header));
580
581 dw_cnt = mei_data2slots(length);
582 if (dw_cnt > slots)
583 return -EMSGSIZE;
584
585 if (WARN(!hw->aliveness, "txe write: aliveness not asserted\n"))
586 return -EAGAIN;
587
588 /* Enable Input Ready Interrupt. */
589 mei_txe_input_ready_interrupt_enable(dev);
590
591 if (!mei_txe_is_input_ready(dev)) {
592 dev_err(&dev->pdev->dev, "Input is not ready");
593 return -EAGAIN;
594 }
595
596 mei_txe_input_payload_write(dev, 0, *((u32 *)header));
597
598 for (i = 0; i < length / 4; i++)
599 mei_txe_input_payload_write(dev, i + 1, reg_buf[i]);
600
601 rem = length & 0x3;
602 if (rem > 0) {
603 u32 reg = 0;
604 memcpy(&reg, &buf[length - rem], rem);
605 mei_txe_input_payload_write(dev, i + 1, reg);
606 }
607
608 /* after each write the whole buffer is consumed */
609 hw->slots = 0;
610
611 /* Set Input-Doorbell */
612 mei_txe_input_doorbell_set(hw);
613
614 return 0;
615}
616
617/**
618 * mei_txe_hbuf_max_len - mimics the me hbuf circular buffer
619 *
620 * @dev: the device structure
621 *
622 * returns the PAYLOAD_SIZE - 4
623 */
624static size_t mei_txe_hbuf_max_len(const struct mei_device *dev)
625{
626 return PAYLOAD_SIZE - sizeof(struct mei_msg_hdr);
627}
628
629/**
630 * mei_txe_hbuf_empty_slots - mimics the me hbuf circular buffer
631 *
632 * @dev: the device structure
633 *
634 * returns always hbuf_depth
635 */
636static int mei_txe_hbuf_empty_slots(struct mei_device *dev)
637{
638 struct mei_txe_hw *hw = to_txe_hw(dev);
639 return hw->slots;
640}
641
642/**
643 * mei_txe_count_full_read_slots - mimics the me device circular buffer
644 *
645 * @dev: the device structure
646 *
647 * returns always buffer size in dwords count
648 */
649static int mei_txe_count_full_read_slots(struct mei_device *dev)
650{
651 /* read buffers has static size */
652 return PAYLOAD_SIZE / 4;
653}
654
655/**
656 * mei_txe_read_hdr - read message header which is always in 4 first bytes
657 *
658 * @dev: the device structure
659 *
660 * returns mei message header
661 */
662
663static u32 mei_txe_read_hdr(const struct mei_device *dev)
664{
665 return mei_txe_out_data_read(dev, 0);
666}
667/**
668 * mei_txe_read - reads a message from the txe device.
669 *
670 * @dev: the device structure
671 * @buf: message buffer will be written
672 * @len: message size will be read
673 *
674 * returns -EINVAL on error wrong argument and 0 on success
675 */
676static int mei_txe_read(struct mei_device *dev,
677 unsigned char *buf, unsigned long len)
678{
679
680 struct mei_txe_hw *hw = to_txe_hw(dev);
681 u32 i;
682 u32 *reg_buf = (u32 *)buf;
683 u32 rem = len & 0x3;
684
685 if (WARN_ON(!buf || !len))
686 return -EINVAL;
687
688 dev_dbg(&dev->pdev->dev,
689 "buffer-length = %lu buf[0]0x%08X\n",
690 len, mei_txe_out_data_read(dev, 0));
691
692 for (i = 0; i < len / 4; i++) {
693 /* skip header: index starts from 1 */
694 u32 reg = mei_txe_out_data_read(dev, i + 1);
695 dev_dbg(&dev->pdev->dev, "buf[%d] = 0x%08X\n", i, reg);
696 *reg_buf++ = reg;
697 }
698
699 if (rem) {
700 u32 reg = mei_txe_out_data_read(dev, i + 1);
701 memcpy(reg_buf, &reg, rem);
702 }
703
704 mei_txe_output_ready_set(hw);
705 return 0;
706}
707
708/**
709 * mei_txe_hw_reset - resets host and fw.
710 *
711 * @dev: the device structure
712 * @intr_enable: if interrupt should be enabled after reset.
713 *
714 * returns 0 on success and < 0 in case of error
715 */
716static int mei_txe_hw_reset(struct mei_device *dev, bool intr_enable)
717{
718 struct mei_txe_hw *hw = to_txe_hw(dev);
719
720 u32 aliveness_req;
721 /*
722 * read input doorbell to ensure consistency between Bridge and SeC
723 * return value might be garbage return
724 */
725 (void)mei_txe_sec_reg_read_silent(hw, SEC_IPC_INPUT_DOORBELL_REG);
726
727 aliveness_req = mei_txe_aliveness_req_get(dev);
728 hw->aliveness = mei_txe_aliveness_get(dev);
729
730 /* Disable interrupts in this stage we will poll */
731 mei_txe_intr_disable(dev);
732
733 /*
734 * If Aliveness Request and Aliveness Response are not equal then
735 * wait for them to be equal
736 * Since we might have interrupts disabled - poll for it
737 */
738 if (aliveness_req != hw->aliveness)
739 if (mei_txe_aliveness_poll(dev, aliveness_req) < 0) {
740 dev_err(&dev->pdev->dev,
741 "wait for aliveness settle failed ... bailing out\n");
742 return -EIO;
743 }
744
745 /*
746 * If Aliveness Request and Aliveness Response are set then clear them
747 */
748 if (aliveness_req) {
749 mei_txe_aliveness_set(dev, 0);
750 if (mei_txe_aliveness_poll(dev, 0) < 0) {
751 dev_err(&dev->pdev->dev,
752 "wait for aliveness failed ... bailing out\n");
753 return -EIO;
754 }
755 }
756
757 /*
758 * Set rediness RDY_CLR bit
759 */
760 mei_txe_readiness_clear(dev);
761
762 return 0;
763}
764
765/**
766 * mei_txe_hw_start - start the hardware after reset
767 *
768 * @dev: the device structure
769 *
770 * returns 0 on success and < 0 in case of error
771 */
772static int mei_txe_hw_start(struct mei_device *dev)
773{
774 struct mei_txe_hw *hw = to_txe_hw(dev);
775 int ret;
776
777 u32 hisr;
778
779 /* bring back interrupts */
780 mei_txe_intr_enable(dev);
781
782 ret = mei_txe_readiness_wait(dev);
783 if (ret < 0) {
784 dev_err(&dev->pdev->dev, "wating for readiness failed\n");
785 return ret;
786 }
787
788 /*
789 * If HISR.INT2_STS interrupt status bit is set then clear it.
790 */
791 hisr = mei_txe_br_reg_read(hw, HISR_REG);
792 if (hisr & HISR_INT_2_STS)
793 mei_txe_br_reg_write(hw, HISR_REG, HISR_INT_2_STS);
794
795 /* Clear the interrupt cause of OutputDoorbell */
796 clear_bit(TXE_INTR_OUT_DB_BIT, &hw->intr_cause);
797
798 ret = mei_txe_aliveness_set_sync(dev, 1);
799 if (ret < 0) {
800 dev_err(&dev->pdev->dev, "wait for aliveness failed ... bailing out\n");
801 return ret;
802 }
803
804 /* enable input ready interrupts:
805 * SEC_IPC_HOST_INT_MASK.IPC_INPUT_READY_INT_MASK
806 */
807 mei_txe_input_ready_interrupt_enable(dev);
808
809
810 /* Set the SICR_SEC_IPC_OUTPUT_STATUS.IPC_OUTPUT_READY bit */
811 mei_txe_output_ready_set(hw);
812
813 /* Set bit SICR_HOST_IPC_READINESS.HOST_RDY
814 */
815 mei_txe_readiness_set_host_rdy(dev);
816
817 return 0;
818}
819
820/**
821 * mei_txe_check_and_ack_intrs - translate multi BAR interrupt into
822 * single bit mask and acknowledge the interrupts
823 *
824 * @dev: the device structure
825 * @do_ack: acknowledge interrupts
826 */
827static bool mei_txe_check_and_ack_intrs(struct mei_device *dev, bool do_ack)
828{
829 struct mei_txe_hw *hw = to_txe_hw(dev);
830 u32 hisr;
831 u32 hhisr;
832 u32 ipc_isr;
833 u32 aliveness;
834 bool generated;
835
836 /* read interrupt registers */
837 hhisr = mei_txe_br_reg_read(hw, HHISR_REG);
838 generated = (hhisr & IPC_HHIER_MSK);
839 if (!generated)
840 goto out;
841
842 hisr = mei_txe_br_reg_read(hw, HISR_REG);
843
844 aliveness = mei_txe_aliveness_get(dev);
845 if (hhisr & IPC_HHIER_SEC && aliveness)
846 ipc_isr = mei_txe_sec_reg_read_silent(hw,
847 SEC_IPC_HOST_INT_STATUS_REG);
848 else
849 ipc_isr = 0;
850
851 generated = generated ||
852 (hisr & HISR_INT_STS_MSK) ||
853 (ipc_isr & SEC_IPC_HOST_INT_STATUS_PENDING);
854
855 if (generated && do_ack) {
856 /* Save the interrupt causes */
857 hw->intr_cause |= hisr & HISR_INT_STS_MSK;
858 if (ipc_isr & SEC_IPC_HOST_INT_STATUS_IN_RDY)
859 hw->intr_cause |= TXE_INTR_IN_READY;
860
861
862 mei_txe_intr_disable(dev);
863 /* Clear the interrupts in hierarchy:
864 * IPC and Bridge, than the High Level */
865 mei_txe_sec_reg_write_silent(hw,
866 SEC_IPC_HOST_INT_STATUS_REG, ipc_isr);
867 mei_txe_br_reg_write(hw, HISR_REG, hisr);
868 mei_txe_br_reg_write(hw, HHISR_REG, hhisr);
869 }
870
871out:
872 return generated;
873}
874
875/**
876 * mei_txe_irq_quick_handler - The ISR of the MEI device
877 *
878 * @irq: The irq number
879 * @dev_id: pointer to the device structure
880 *
881 * returns irqreturn_t
882 */
883irqreturn_t mei_txe_irq_quick_handler(int irq, void *dev_id)
884{
885 struct mei_device *dev = dev_id;
886
887 if (mei_txe_check_and_ack_intrs(dev, true))
888 return IRQ_WAKE_THREAD;
889 return IRQ_NONE;
890}
891
892
893/**
894 * mei_txe_irq_thread_handler - txe interrupt thread
895 *
896 * @irq: The irq number
897 * @dev_id: pointer to the device structure
898 *
899 * returns irqreturn_t
900 *
901 */
902irqreturn_t mei_txe_irq_thread_handler(int irq, void *dev_id)
903{
904 struct mei_device *dev = (struct mei_device *) dev_id;
905 struct mei_txe_hw *hw = to_txe_hw(dev);
906 struct mei_cl_cb complete_list;
907 s32 slots;
908 int rets = 0;
909
910 dev_dbg(&dev->pdev->dev, "irq thread: Interrupt Registers HHISR|HISR|SEC=%02X|%04X|%02X\n",
911 mei_txe_br_reg_read(hw, HHISR_REG),
912 mei_txe_br_reg_read(hw, HISR_REG),
913 mei_txe_sec_reg_read_silent(hw, SEC_IPC_HOST_INT_STATUS_REG));
914
915
916 /* initialize our complete list */
917 mutex_lock(&dev->device_lock);
918 mei_io_list_init(&complete_list);
919
920 if (pci_dev_msi_enabled(dev->pdev))
921 mei_txe_check_and_ack_intrs(dev, true);
922
923 /* show irq events */
924 mei_txe_pending_interrupts(dev);
925
926 hw->aliveness = mei_txe_aliveness_get(dev);
927 hw->readiness = mei_txe_readiness_get(dev);
928
929 /* Readiness:
930 * Detection of TXE driver going through reset
931 * or TXE driver resetting the HECI interface.
932 */
933 if (test_and_clear_bit(TXE_INTR_READINESS_BIT, &hw->intr_cause)) {
934 dev_dbg(&dev->pdev->dev, "Readiness Interrupt was received...\n");
935
936 /* Check if SeC is going through reset */
937 if (mei_txe_readiness_is_sec_rdy(hw->readiness)) {
938 dev_dbg(&dev->pdev->dev, "we need to start the dev.\n");
939 dev->recvd_hw_ready = true;
940 } else {
941 dev->recvd_hw_ready = false;
942 if (dev->dev_state != MEI_DEV_RESETTING) {
943
944 dev_warn(&dev->pdev->dev, "FW not ready: resetting.\n");
945 schedule_work(&dev->reset_work);
946 goto end;
947
948 }
949 }
950 wake_up(&dev->wait_hw_ready);
951 }
952
953 /************************************************************/
954 /* Check interrupt cause:
955 * Aliveness: Detection of SeC acknowledge of host request that
956 * it remain alive or host cancellation of that request.
957 */
958
959 if (test_and_clear_bit(TXE_INTR_ALIVENESS_BIT, &hw->intr_cause)) {
960 /* Clear the interrupt cause */
961 dev_dbg(&dev->pdev->dev,
962 "Aliveness Interrupt: Status: %d\n", hw->aliveness);
963 hw->recvd_aliveness = true;
964 if (waitqueue_active(&hw->wait_aliveness))
965 wake_up(&hw->wait_aliveness);
966 }
967
968
969 /* Output Doorbell:
970 * Detection of SeC having sent output to host
971 */
972 slots = mei_count_full_read_slots(dev);
973 if (test_and_clear_bit(TXE_INTR_OUT_DB_BIT, &hw->intr_cause)) {
974 /* Read from TXE */
975 rets = mei_irq_read_handler(dev, &complete_list, &slots);
976 if (rets && dev->dev_state != MEI_DEV_RESETTING) {
977 dev_err(&dev->pdev->dev,
978 "mei_irq_read_handler ret = %d.\n", rets);
979
980 schedule_work(&dev->reset_work);
981 goto end;
982 }
983 }
984 /* Input Ready: Detection if host can write to SeC */
985 if (test_and_clear_bit(TXE_INTR_IN_READY_BIT, &hw->intr_cause)) {
986 dev->hbuf_is_ready = true;
987 hw->slots = dev->hbuf_depth;
988 }
989
990 if (hw->aliveness && dev->hbuf_is_ready) {
991 /* get the real register value */
992 dev->hbuf_is_ready = mei_hbuf_is_ready(dev);
993 rets = mei_irq_write_handler(dev, &complete_list);
994 if (rets && rets != -EMSGSIZE)
995 dev_err(&dev->pdev->dev, "mei_irq_write_handler ret = %d.\n",
996 rets);
997 dev->hbuf_is_ready = mei_hbuf_is_ready(dev);
998 }
999
1000 mei_irq_compl_handler(dev, &complete_list);
1001
1002end:
1003 dev_dbg(&dev->pdev->dev, "interrupt thread end ret = %d\n", rets);
1004
1005 mutex_unlock(&dev->device_lock);
1006
1007 mei_enable_interrupts(dev);
1008 return IRQ_HANDLED;
1009}
1010
1011static const struct mei_hw_ops mei_txe_hw_ops = {
1012
1013 .host_is_ready = mei_txe_host_is_ready,
1014
1015 .hw_is_ready = mei_txe_hw_is_ready,
1016 .hw_reset = mei_txe_hw_reset,
1017 .hw_config = mei_txe_hw_config,
1018 .hw_start = mei_txe_hw_start,
1019
1020 .intr_clear = mei_txe_intr_clear,
1021 .intr_enable = mei_txe_intr_enable,
1022 .intr_disable = mei_txe_intr_disable,
1023
1024 .hbuf_free_slots = mei_txe_hbuf_empty_slots,
1025 .hbuf_is_ready = mei_txe_is_input_ready,
1026 .hbuf_max_len = mei_txe_hbuf_max_len,
1027
1028 .write = mei_txe_write,
1029
1030 .rdbuf_full_slots = mei_txe_count_full_read_slots,
1031 .read_hdr = mei_txe_read_hdr,
1032
1033 .read = mei_txe_read,
1034
1035};
1036
1037/**
1038 * mei_txe_dev_init - allocates and initializes txe hardware specific structure
1039 *
1040 * @pdev - pci device
1041 * returns struct mei_device * on success or NULL;
1042 *
1043 */
1044struct mei_device *mei_txe_dev_init(struct pci_dev *pdev)
1045{
1046 struct mei_device *dev;
1047 struct mei_txe_hw *hw;
1048
1049 dev = kzalloc(sizeof(struct mei_device) +
1050 sizeof(struct mei_txe_hw), GFP_KERNEL);
1051 if (!dev)
1052 return NULL;
1053
1054 mei_device_init(dev);
1055
1056 hw = to_txe_hw(dev);
1057
1058 init_waitqueue_head(&hw->wait_aliveness);
1059
1060 dev->ops = &mei_txe_hw_ops;
1061
1062 dev->pdev = pdev;
1063 return dev;
1064}
1065
1066/**
1067 * mei_txe_setup_satt2 - SATT2 configuration for DMA support.
1068 *
1069 * @dev: the device structure
1070 * @addr: physical address start of the range
1071 * @range: physical range size
1072 */
1073int mei_txe_setup_satt2(struct mei_device *dev, phys_addr_t addr, u32 range)
1074{
1075 struct mei_txe_hw *hw = to_txe_hw(dev);
1076
1077 u32 lo32 = lower_32_bits(addr);
1078 u32 hi32 = upper_32_bits(addr);
1079 u32 ctrl;
1080
1081 /* SATT is limited to 36 Bits */
1082 if (hi32 & ~0xF)
1083 return -EINVAL;
1084
1085 /* SATT has to be 16Byte aligned */
1086 if (lo32 & 0xF)
1087 return -EINVAL;
1088
1089 /* SATT range has to be 4Bytes aligned */
1090 if (range & 0x4)
1091 return -EINVAL;
1092
1093 /* SATT is limited to 32 MB range*/
1094 if (range > SATT_RANGE_MAX)
1095 return -EINVAL;
1096
1097 ctrl = SATT2_CTRL_VALID_MSK;
1098 ctrl |= hi32 << SATT2_CTRL_BR_BASE_ADDR_REG_SHIFT;
1099
1100 mei_txe_br_reg_write(hw, SATT2_SAP_SIZE_REG, range);
1101 mei_txe_br_reg_write(hw, SATT2_BRG_BA_LSB_REG, lo32);
1102 mei_txe_br_reg_write(hw, SATT2_CTRL_REG, ctrl);
1103 dev_dbg(&dev->pdev->dev, "SATT2: SAP_SIZE_OFFSET=0x%08X, BRG_BA_LSB_OFFSET=0x%08X, CTRL_OFFSET=0x%08X\n",
1104 range, lo32, ctrl);
1105
1106 return 0;
1107}
diff --git a/drivers/misc/mei/hw-txe.h b/drivers/misc/mei/hw-txe.h
new file mode 100644
index 000000000000..0812d98633a4
--- /dev/null
+++ b/drivers/misc/mei/hw-txe.h
@@ -0,0 +1,74 @@
1/*
2 *
3 * Intel Management Engine Interface (Intel MEI) Linux driver
4 * Copyright (c) 2013-2014, Intel Corporation.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
14 *
15 */
16
17#ifndef _MEI_HW_TXE_H_
18#define _MEI_HW_TXE_H_
19
20#include <linux/irqreturn.h>
21
22#include "hw.h"
23#include "hw-txe-regs.h"
24
25/* Flatten Hierarchy interrupt cause */
26#define TXE_INTR_READINESS_BIT 0 /* HISR_INT_0_STS */
27#define TXE_INTR_READINESS HISR_INT_0_STS
28#define TXE_INTR_ALIVENESS_BIT 1 /* HISR_INT_1_STS */
29#define TXE_INTR_ALIVENESS HISR_INT_1_STS
30#define TXE_INTR_OUT_DB_BIT 2 /* HISR_INT_2_STS */
31#define TXE_INTR_OUT_DB HISR_INT_2_STS
32#define TXE_INTR_IN_READY_BIT 8 /* beyond HISR */
33#define TXE_INTR_IN_READY BIT(8)
34
35/**
36 * struct mei_txe_hw - txe hardware specifics
37 *
38 * @mem_addr: SeC and BRIDGE bars
39 * @aliveness: aliveness (power gating) state of the hardware
40 * @readiness: readiness state of the hardware
41 * @wait_aliveness: aliveness wait queue
42 * @recvd_aliveness: aliveness interrupt was recived
43 * @intr_cause: translated interrupt cause
44 */
45struct mei_txe_hw {
46 void __iomem *mem_addr[NUM_OF_MEM_BARS];
47 u32 aliveness;
48 u32 readiness;
49 u32 slots;
50
51 wait_queue_head_t wait_aliveness;
52 bool recvd_aliveness;
53
54 unsigned long intr_cause;
55};
56
57#define to_txe_hw(dev) (struct mei_txe_hw *)((dev)->hw)
58
59static inline struct mei_device *hw_txe_to_mei(struct mei_txe_hw *hw)
60{
61 return container_of((void *)hw, struct mei_device, hw);
62}
63
64struct mei_device *mei_txe_dev_init(struct pci_dev *pdev);
65
66irqreturn_t mei_txe_irq_quick_handler(int irq, void *dev_id);
67irqreturn_t mei_txe_irq_thread_handler(int irq, void *dev_id);
68
69int mei_txe_aliveness_set_sync(struct mei_device *dev, u32 req);
70
71int mei_txe_setup_satt2(struct mei_device *dev, phys_addr_t addr, u32 range);
72
73
74#endif /* _MEI_HW_TXE_H_ */
diff --git a/drivers/misc/mei/hw.h b/drivers/misc/mei/hw.h
index dd44e33ad2b6..6b476ab49b2e 100644
--- a/drivers/misc/mei/hw.h
+++ b/drivers/misc/mei/hw.h
@@ -22,7 +22,7 @@
22/* 22/*
23 * Timeouts in Seconds 23 * Timeouts in Seconds
24 */ 24 */
25#define MEI_INTEROP_TIMEOUT 7 /* Timeout on ready message */ 25#define MEI_HW_READY_TIMEOUT 2 /* Timeout on ready message */
26#define MEI_CONNECT_TIMEOUT 3 /* HPS: at least 2 seconds */ 26#define MEI_CONNECT_TIMEOUT 3 /* HPS: at least 2 seconds */
27 27
28#define MEI_CL_CONNECT_TIMEOUT 15 /* HPS: Client Connect Timeout */ 28#define MEI_CL_CONNECT_TIMEOUT 15 /* HPS: Client Connect Timeout */
@@ -31,13 +31,13 @@
31#define MEI_IAMTHIF_STALL_TIMER 12 /* HPS */ 31#define MEI_IAMTHIF_STALL_TIMER 12 /* HPS */
32#define MEI_IAMTHIF_READ_TIMER 10 /* HPS */ 32#define MEI_IAMTHIF_READ_TIMER 10 /* HPS */
33 33
34#define MEI_HBM_TIMEOUT 1 /* 1 second */
34 35
35/* 36/*
36 * MEI Version 37 * MEI Version
37 */ 38 */
38#define HBM_MINOR_VERSION 0 39#define HBM_MINOR_VERSION 0
39#define HBM_MAJOR_VERSION 1 40#define HBM_MAJOR_VERSION 1
40#define HBM_TIMEOUT 1 /* 1 second */
41 41
42/* Host bus message command opcode */ 42/* Host bus message command opcode */
43#define MEI_HBM_CMD_OP_MSK 0x7f 43#define MEI_HBM_CMD_OP_MSK 0x7f
@@ -89,19 +89,19 @@ enum mei_stop_reason_types {
89 * Client Connect Status 89 * Client Connect Status
90 * used by hbm_client_connect_response.status 90 * used by hbm_client_connect_response.status
91 */ 91 */
92enum client_connect_status_types { 92enum mei_cl_connect_status {
93 CCS_SUCCESS = 0x00, 93 MEI_CL_CONN_SUCCESS = 0x00,
94 CCS_NOT_FOUND = 0x01, 94 MEI_CL_CONN_NOT_FOUND = 0x01,
95 CCS_ALREADY_STARTED = 0x02, 95 MEI_CL_CONN_ALREADY_STARTED = 0x02,
96 CCS_OUT_OF_RESOURCES = 0x03, 96 MEI_CL_CONN_OUT_OF_RESOURCES = 0x03,
97 CCS_MESSAGE_SMALL = 0x04 97 MEI_CL_CONN_MESSAGE_SMALL = 0x04
98}; 98};
99 99
100/* 100/*
101 * Client Disconnect Status 101 * Client Disconnect Status
102 */ 102 */
103enum client_disconnect_status_types { 103enum mei_cl_disconnect_status {
104 CDS_SUCCESS = 0x00 104 MEI_CL_DISCONN_SUCCESS = 0x00
105}; 105};
106 106
107/* 107/*
diff --git a/drivers/misc/mei/init.c b/drivers/misc/mei/init.c
index cdd31c2a2a2b..4460975c0eef 100644
--- a/drivers/misc/mei/init.c
+++ b/drivers/misc/mei/init.c
@@ -116,7 +116,6 @@ int mei_reset(struct mei_device *dev)
116 mei_cl_unlink(&dev->wd_cl); 116 mei_cl_unlink(&dev->wd_cl);
117 mei_cl_unlink(&dev->iamthif_cl); 117 mei_cl_unlink(&dev->iamthif_cl);
118 mei_amthif_reset_params(dev); 118 mei_amthif_reset_params(dev);
119 memset(&dev->wr_ext_msg, 0, sizeof(dev->wr_ext_msg));
120 } 119 }
121 120
122 121
@@ -126,7 +125,6 @@ int mei_reset(struct mei_device *dev)
126 125
127 if (ret) { 126 if (ret) {
128 dev_err(&dev->pdev->dev, "hw_reset failed ret = %d\n", ret); 127 dev_err(&dev->pdev->dev, "hw_reset failed ret = %d\n", ret);
129 dev->dev_state = MEI_DEV_DISABLED;
130 return ret; 128 return ret;
131 } 129 }
132 130
@@ -139,7 +137,6 @@ int mei_reset(struct mei_device *dev)
139 ret = mei_hw_start(dev); 137 ret = mei_hw_start(dev);
140 if (ret) { 138 if (ret) {
141 dev_err(&dev->pdev->dev, "hw_start failed ret = %d\n", ret); 139 dev_err(&dev->pdev->dev, "hw_start failed ret = %d\n", ret);
142 dev->dev_state = MEI_DEV_DISABLED;
143 return ret; 140 return ret;
144 } 141 }
145 142
@@ -149,7 +146,7 @@ int mei_reset(struct mei_device *dev)
149 ret = mei_hbm_start_req(dev); 146 ret = mei_hbm_start_req(dev);
150 if (ret) { 147 if (ret) {
151 dev_err(&dev->pdev->dev, "hbm_start failed ret = %d\n", ret); 148 dev_err(&dev->pdev->dev, "hbm_start failed ret = %d\n", ret);
152 dev->dev_state = MEI_DEV_DISABLED; 149 dev->dev_state = MEI_DEV_RESETTING;
153 return ret; 150 return ret;
154 } 151 }
155 152
@@ -166,6 +163,7 @@ EXPORT_SYMBOL_GPL(mei_reset);
166 */ 163 */
167int mei_start(struct mei_device *dev) 164int mei_start(struct mei_device *dev)
168{ 165{
166 int ret;
169 mutex_lock(&dev->device_lock); 167 mutex_lock(&dev->device_lock);
170 168
171 /* acknowledge interrupt and stop interrupts */ 169 /* acknowledge interrupt and stop interrupts */
@@ -175,10 +173,18 @@ int mei_start(struct mei_device *dev)
175 173
176 dev_dbg(&dev->pdev->dev, "reset in start the mei device.\n"); 174 dev_dbg(&dev->pdev->dev, "reset in start the mei device.\n");
177 175
178 dev->dev_state = MEI_DEV_INITIALIZING;
179 dev->reset_count = 0; 176 dev->reset_count = 0;
180 mei_reset(dev); 177 do {
178 dev->dev_state = MEI_DEV_INITIALIZING;
179 ret = mei_reset(dev);
180
181 if (ret == -ENODEV || dev->dev_state == MEI_DEV_DISABLED) {
182 dev_err(&dev->pdev->dev, "reset failed ret = %d", ret);
183 goto err;
184 }
185 } while (ret);
181 186
187 /* we cannot start the device w/o hbm start message completed */
182 if (dev->dev_state == MEI_DEV_DISABLED) { 188 if (dev->dev_state == MEI_DEV_DISABLED) {
183 dev_err(&dev->pdev->dev, "reset failed"); 189 dev_err(&dev->pdev->dev, "reset failed");
184 goto err; 190 goto err;
@@ -238,27 +244,40 @@ int mei_restart(struct mei_device *dev)
238 244
239 mutex_unlock(&dev->device_lock); 245 mutex_unlock(&dev->device_lock);
240 246
241 if (err || dev->dev_state == MEI_DEV_DISABLED) 247 if (err == -ENODEV || dev->dev_state == MEI_DEV_DISABLED) {
248 dev_err(&dev->pdev->dev, "device disabled = %d\n", err);
242 return -ENODEV; 249 return -ENODEV;
250 }
251
252 /* try to start again */
253 if (err)
254 schedule_work(&dev->reset_work);
255
243 256
244 return 0; 257 return 0;
245} 258}
246EXPORT_SYMBOL_GPL(mei_restart); 259EXPORT_SYMBOL_GPL(mei_restart);
247 260
248
249static void mei_reset_work(struct work_struct *work) 261static void mei_reset_work(struct work_struct *work)
250{ 262{
251 struct mei_device *dev = 263 struct mei_device *dev =
252 container_of(work, struct mei_device, reset_work); 264 container_of(work, struct mei_device, reset_work);
265 int ret;
253 266
254 mutex_lock(&dev->device_lock); 267 mutex_lock(&dev->device_lock);
255 268
256 mei_reset(dev); 269 ret = mei_reset(dev);
257 270
258 mutex_unlock(&dev->device_lock); 271 mutex_unlock(&dev->device_lock);
259 272
260 if (dev->dev_state == MEI_DEV_DISABLED) 273 if (dev->dev_state == MEI_DEV_DISABLED) {
261 dev_err(&dev->pdev->dev, "reset failed"); 274 dev_err(&dev->pdev->dev, "device disabled = %d\n", ret);
275 return;
276 }
277
278 /* retry reset in case of failure */
279 if (ret)
280 schedule_work(&dev->reset_work);
262} 281}
263 282
264void mei_stop(struct mei_device *dev) 283void mei_stop(struct mei_device *dev)
@@ -269,6 +288,8 @@ void mei_stop(struct mei_device *dev)
269 288
270 mei_nfc_host_exit(dev); 289 mei_nfc_host_exit(dev);
271 290
291 mei_cl_bus_remove_devices(dev);
292
272 mutex_lock(&dev->device_lock); 293 mutex_lock(&dev->device_lock);
273 294
274 mei_wd_stop(dev); 295 mei_wd_stop(dev);
diff --git a/drivers/misc/mei/interrupt.c b/drivers/misc/mei/interrupt.c
index f0fbb5179f80..29b5af8efb71 100644
--- a/drivers/misc/mei/interrupt.c
+++ b/drivers/misc/mei/interrupt.c
@@ -26,7 +26,6 @@
26 26
27#include "mei_dev.h" 27#include "mei_dev.h"
28#include "hbm.h" 28#include "hbm.h"
29#include "hw-me.h"
30#include "client.h" 29#include "client.h"
31 30
32 31
@@ -161,29 +160,63 @@ static int mei_cl_irq_read_msg(struct mei_device *dev,
161} 160}
162 161
163/** 162/**
163 * mei_cl_irq_disconnect_rsp - send disconnection response message
164 *
165 * @cl: client
166 * @cb: callback block.
167 * @cmpl_list: complete list.
168 *
169 * returns 0, OK; otherwise, error.
170 */
171static int mei_cl_irq_disconnect_rsp(struct mei_cl *cl, struct mei_cl_cb *cb,
172 struct mei_cl_cb *cmpl_list)
173{
174 struct mei_device *dev = cl->dev;
175 u32 msg_slots;
176 int slots;
177 int ret;
178
179 slots = mei_hbuf_empty_slots(dev);
180 msg_slots = mei_data2slots(sizeof(struct hbm_client_connect_response));
181
182 if (slots < msg_slots)
183 return -EMSGSIZE;
184
185 ret = mei_hbm_cl_disconnect_rsp(dev, cl);
186
187 cl->state = MEI_FILE_DISCONNECTED;
188 cl->status = 0;
189 list_del(&cb->list);
190 mei_io_cb_free(cb);
191
192 return ret;
193}
194
195
196
197/**
164 * mei_cl_irq_close - processes close related operation from 198 * mei_cl_irq_close - processes close related operation from
165 * interrupt thread context - send disconnect request 199 * interrupt thread context - send disconnect request
166 * 200 *
167 * @cl: client 201 * @cl: client
168 * @cb: callback block. 202 * @cb: callback block.
169 * @slots: free slots.
170 * @cmpl_list: complete list. 203 * @cmpl_list: complete list.
171 * 204 *
172 * returns 0, OK; otherwise, error. 205 * returns 0, OK; otherwise, error.
173 */ 206 */
174static int mei_cl_irq_close(struct mei_cl *cl, struct mei_cl_cb *cb, 207static int mei_cl_irq_close(struct mei_cl *cl, struct mei_cl_cb *cb,
175 s32 *slots, struct mei_cl_cb *cmpl_list) 208 struct mei_cl_cb *cmpl_list)
176{ 209{
177 struct mei_device *dev = cl->dev; 210 struct mei_device *dev = cl->dev;
211 u32 msg_slots;
212 int slots;
178 213
179 u32 msg_slots = 214 msg_slots = mei_data2slots(sizeof(struct hbm_client_connect_request));
180 mei_data2slots(sizeof(struct hbm_client_connect_request)); 215 slots = mei_hbuf_empty_slots(dev);
181 216
182 if (*slots < msg_slots) 217 if (slots < msg_slots)
183 return -EMSGSIZE; 218 return -EMSGSIZE;
184 219
185 *slots -= msg_slots;
186
187 if (mei_hbm_cl_disconnect_req(dev, cl)) { 220 if (mei_hbm_cl_disconnect_req(dev, cl)) {
188 cl->status = 0; 221 cl->status = 0;
189 cb->buf_idx = 0; 222 cb->buf_idx = 0;
@@ -207,27 +240,23 @@ static int mei_cl_irq_close(struct mei_cl *cl, struct mei_cl_cb *cb,
207 * 240 *
208 * @cl: client 241 * @cl: client
209 * @cb: callback block. 242 * @cb: callback block.
210 * @slots: free slots.
211 * @cmpl_list: complete list. 243 * @cmpl_list: complete list.
212 * 244 *
213 * returns 0, OK; otherwise, error. 245 * returns 0, OK; otherwise, error.
214 */ 246 */
215static int mei_cl_irq_read(struct mei_cl *cl, struct mei_cl_cb *cb, 247static int mei_cl_irq_read(struct mei_cl *cl, struct mei_cl_cb *cb,
216 s32 *slots, struct mei_cl_cb *cmpl_list) 248 struct mei_cl_cb *cmpl_list)
217{ 249{
218 struct mei_device *dev = cl->dev; 250 struct mei_device *dev = cl->dev;
219 u32 msg_slots = mei_data2slots(sizeof(struct hbm_flow_control)); 251 u32 msg_slots;
220 252 int slots;
221 int ret; 253 int ret;
222 254
255 msg_slots = mei_data2slots(sizeof(struct hbm_flow_control));
256 slots = mei_hbuf_empty_slots(dev);
223 257
224 if (*slots < msg_slots) { 258 if (slots < msg_slots)
225 /* return the cancel routine */
226 list_del(&cb->list);
227 return -EMSGSIZE; 259 return -EMSGSIZE;
228 }
229
230 *slots -= msg_slots;
231 260
232 ret = mei_hbm_cl_flow_control_req(dev, cl); 261 ret = mei_hbm_cl_flow_control_req(dev, cl);
233 if (ret) { 262 if (ret) {
@@ -244,32 +273,30 @@ static int mei_cl_irq_read(struct mei_cl *cl, struct mei_cl_cb *cb,
244 273
245 274
246/** 275/**
247 * mei_cl_irq_ioctl - processes client ioctl related operation from the 276 * mei_cl_irq_connect - send connect request in irq_thread context
248 * interrupt thread context - send connection request
249 * 277 *
250 * @cl: client 278 * @cl: client
251 * @cb: callback block. 279 * @cb: callback block.
252 * @slots: free slots.
253 * @cmpl_list: complete list. 280 * @cmpl_list: complete list.
254 * 281 *
255 * returns 0, OK; otherwise, error. 282 * returns 0, OK; otherwise, error.
256 */ 283 */
257static int mei_cl_irq_ioctl(struct mei_cl *cl, struct mei_cl_cb *cb, 284static int mei_cl_irq_connect(struct mei_cl *cl, struct mei_cl_cb *cb,
258 s32 *slots, struct mei_cl_cb *cmpl_list) 285 struct mei_cl_cb *cmpl_list)
259{ 286{
260 struct mei_device *dev = cl->dev; 287 struct mei_device *dev = cl->dev;
288 u32 msg_slots;
289 int slots;
261 int ret; 290 int ret;
262 291
263 u32 msg_slots = 292 msg_slots = mei_data2slots(sizeof(struct hbm_client_connect_request));
264 mei_data2slots(sizeof(struct hbm_client_connect_request)); 293 slots = mei_hbuf_empty_slots(dev);
265 294
266 if (*slots < msg_slots) { 295 if (mei_cl_is_other_connecting(cl))
267 /* return the cancel routine */ 296 return 0;
268 list_del(&cb->list);
269 return -EMSGSIZE;
270 }
271 297
272 *slots -= msg_slots; 298 if (slots < msg_slots)
299 return -EMSGSIZE;
273 300
274 cl->state = MEI_FILE_CONNECTING; 301 cl->state = MEI_FILE_CONNECTING;
275 302
@@ -323,7 +350,7 @@ int mei_irq_read_handler(struct mei_device *dev,
323 dev_err(&dev->pdev->dev, "less data available than length=%08x.\n", 350 dev_err(&dev->pdev->dev, "less data available than length=%08x.\n",
324 *slots); 351 *slots);
325 /* we can't read the message */ 352 /* we can't read the message */
326 ret = -ERANGE; 353 ret = -ENODATA;
327 goto end; 354 goto end;
328 } 355 }
329 356
@@ -409,10 +436,10 @@ int mei_irq_write_handler(struct mei_device *dev, struct mei_cl_cb *cmpl_list)
409 s32 slots; 436 s32 slots;
410 int ret; 437 int ret;
411 438
412 if (!mei_hbuf_is_ready(dev)) { 439
413 dev_dbg(&dev->pdev->dev, "host buffer is not empty.\n"); 440 if (!mei_hbuf_acquire(dev))
414 return 0; 441 return 0;
415 } 442
416 slots = mei_hbuf_empty_slots(dev); 443 slots = mei_hbuf_empty_slots(dev);
417 if (slots <= 0) 444 if (slots <= 0)
418 return -EMSGSIZE; 445 return -EMSGSIZE;
@@ -447,29 +474,16 @@ int mei_irq_write_handler(struct mei_device *dev, struct mei_cl_cb *cmpl_list)
447 474
448 if (dev->wd_state == MEI_WD_STOPPING) { 475 if (dev->wd_state == MEI_WD_STOPPING) {
449 dev->wd_state = MEI_WD_IDLE; 476 dev->wd_state = MEI_WD_IDLE;
450 wake_up_interruptible(&dev->wait_stop_wd); 477 wake_up(&dev->wait_stop_wd);
451 } 478 }
452 479
453 if (dev->wr_ext_msg.hdr.length) { 480 if (mei_cl_is_connected(&dev->wd_cl)) {
454 mei_write_message(dev, &dev->wr_ext_msg.hdr,
455 dev->wr_ext_msg.data);
456 slots -= mei_data2slots(dev->wr_ext_msg.hdr.length);
457 dev->wr_ext_msg.hdr.length = 0;
458 }
459 if (dev->dev_state == MEI_DEV_ENABLED) {
460 if (dev->wd_pending && 481 if (dev->wd_pending &&
461 mei_cl_flow_ctrl_creds(&dev->wd_cl) > 0) { 482 mei_cl_flow_ctrl_creds(&dev->wd_cl) > 0) {
462 if (mei_wd_send(dev)) 483 ret = mei_wd_send(dev);
463 dev_dbg(&dev->pdev->dev, "wd send failed.\n"); 484 if (ret)
464 else if (mei_cl_flow_ctrl_reduce(&dev->wd_cl)) 485 return ret;
465 return -ENODEV;
466
467 dev->wd_pending = false; 486 dev->wd_pending = false;
468
469 if (dev->wd_state == MEI_WD_RUNNING)
470 slots -= mei_data2slots(MEI_WD_START_MSG_SIZE);
471 else
472 slots -= mei_data2slots(MEI_WD_STOP_MSG_SIZE);
473 } 487 }
474 } 488 }
475 489
@@ -484,28 +498,31 @@ int mei_irq_write_handler(struct mei_device *dev, struct mei_cl_cb *cmpl_list)
484 switch (cb->fop_type) { 498 switch (cb->fop_type) {
485 case MEI_FOP_CLOSE: 499 case MEI_FOP_CLOSE:
486 /* send disconnect message */ 500 /* send disconnect message */
487 ret = mei_cl_irq_close(cl, cb, &slots, cmpl_list); 501 ret = mei_cl_irq_close(cl, cb, cmpl_list);
488 if (ret) 502 if (ret)
489 return ret; 503 return ret;
490 504
491 break; 505 break;
492 case MEI_FOP_READ: 506 case MEI_FOP_READ:
493 /* send flow control message */ 507 /* send flow control message */
494 ret = mei_cl_irq_read(cl, cb, &slots, cmpl_list); 508 ret = mei_cl_irq_read(cl, cb, cmpl_list);
495 if (ret) 509 if (ret)
496 return ret; 510 return ret;
497 511
498 break; 512 break;
499 case MEI_FOP_IOCTL: 513 case MEI_FOP_CONNECT:
500 /* connect message */ 514 /* connect message */
501 if (mei_cl_is_other_connecting(cl)) 515 ret = mei_cl_irq_connect(cl, cb, cmpl_list);
502 continue;
503 ret = mei_cl_irq_ioctl(cl, cb, &slots, cmpl_list);
504 if (ret) 516 if (ret)
505 return ret; 517 return ret;
506 518
507 break; 519 break;
508 520 case MEI_FOP_DISCONNECT_RSP:
521 /* send disconnect resp */
522 ret = mei_cl_irq_disconnect_rsp(cl, cb, cmpl_list);
523 if (ret)
524 return ret;
525 break;
509 default: 526 default:
510 BUG(); 527 BUG();
511 } 528 }
@@ -518,11 +535,9 @@ int mei_irq_write_handler(struct mei_device *dev, struct mei_cl_cb *cmpl_list)
518 if (cl == NULL) 535 if (cl == NULL)
519 continue; 536 continue;
520 if (cl == &dev->iamthif_cl) 537 if (cl == &dev->iamthif_cl)
521 ret = mei_amthif_irq_write_complete(cl, cb, 538 ret = mei_amthif_irq_write(cl, cb, cmpl_list);
522 &slots, cmpl_list);
523 else 539 else
524 ret = mei_cl_irq_write_complete(cl, cb, 540 ret = mei_cl_irq_write(cl, cb, cmpl_list);
525 &slots, cmpl_list);
526 if (ret) 541 if (ret)
527 return ret; 542 return ret;
528 } 543 }
@@ -541,8 +556,7 @@ EXPORT_SYMBOL_GPL(mei_irq_write_handler);
541void mei_timer(struct work_struct *work) 556void mei_timer(struct work_struct *work)
542{ 557{
543 unsigned long timeout; 558 unsigned long timeout;
544 struct mei_cl *cl_pos = NULL; 559 struct mei_cl *cl;
545 struct mei_cl *cl_next = NULL;
546 struct mei_cl_cb *cb_pos = NULL; 560 struct mei_cl_cb *cb_pos = NULL;
547 struct mei_cl_cb *cb_next = NULL; 561 struct mei_cl_cb *cb_next = NULL;
548 562
@@ -570,9 +584,9 @@ void mei_timer(struct work_struct *work)
570 goto out; 584 goto out;
571 585
572 /*** connect/disconnect timeouts ***/ 586 /*** connect/disconnect timeouts ***/
573 list_for_each_entry_safe(cl_pos, cl_next, &dev->file_list, link) { 587 list_for_each_entry(cl, &dev->file_list, link) {
574 if (cl_pos->timer_count) { 588 if (cl->timer_count) {
575 if (--cl_pos->timer_count == 0) { 589 if (--cl->timer_count == 0) {
576 dev_err(&dev->pdev->dev, "timer: connect/disconnect timeout.\n"); 590 dev_err(&dev->pdev->dev, "timer: connect/disconnect timeout.\n");
577 mei_reset(dev); 591 mei_reset(dev);
578 goto out; 592 goto out;
@@ -580,6 +594,9 @@ void mei_timer(struct work_struct *work)
580 } 594 }
581 } 595 }
582 596
597 if (!mei_cl_is_connected(&dev->iamthif_cl))
598 goto out;
599
583 if (dev->iamthif_stall_timer) { 600 if (dev->iamthif_stall_timer) {
584 if (--dev->iamthif_stall_timer == 0) { 601 if (--dev->iamthif_stall_timer == 0) {
585 dev_err(&dev->pdev->dev, "timer: amthif hanged.\n"); 602 dev_err(&dev->pdev->dev, "timer: amthif hanged.\n");
@@ -619,10 +636,10 @@ void mei_timer(struct work_struct *work)
619 list_for_each_entry_safe(cb_pos, cb_next, 636 list_for_each_entry_safe(cb_pos, cb_next,
620 &dev->amthif_rd_complete_list.list, list) { 637 &dev->amthif_rd_complete_list.list, list) {
621 638
622 cl_pos = cb_pos->file_object->private_data; 639 cl = cb_pos->file_object->private_data;
623 640
624 /* Finding the AMTHI entry. */ 641 /* Finding the AMTHI entry. */
625 if (cl_pos == &dev->iamthif_cl) 642 if (cl == &dev->iamthif_cl)
626 list_del(&cb_pos->list); 643 list_del(&cb_pos->list);
627 } 644 }
628 mei_io_cb_free(dev->iamthif_current_cb); 645 mei_io_cb_free(dev->iamthif_current_cb);
diff --git a/drivers/misc/mei/main.c b/drivers/misc/mei/main.c
index 5424f8ff3f7f..b35594dbf52f 100644
--- a/drivers/misc/mei/main.c
+++ b/drivers/misc/mei/main.c
@@ -13,9 +13,6 @@
13 * more details. 13 * more details.
14 * 14 *
15 */ 15 */
16
17#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
18
19#include <linux/module.h> 16#include <linux/module.h>
20#include <linux/moduleparam.h> 17#include <linux/moduleparam.h>
21#include <linux/kernel.h> 18#include <linux/kernel.h>
@@ -40,7 +37,6 @@
40#include <linux/mei.h> 37#include <linux/mei.h>
41 38
42#include "mei_dev.h" 39#include "mei_dev.h"
43#include "hw-me.h"
44#include "client.h" 40#include "client.h"
45 41
46/** 42/**
@@ -129,17 +125,11 @@ static int mei_release(struct inode *inode, struct file *file)
129 } 125 }
130 if (cl->state == MEI_FILE_CONNECTED) { 126 if (cl->state == MEI_FILE_CONNECTED) {
131 cl->state = MEI_FILE_DISCONNECTING; 127 cl->state = MEI_FILE_DISCONNECTING;
132 dev_dbg(&dev->pdev->dev, 128 cl_dbg(dev, cl, "disconnecting\n");
133 "disconnecting client host client = %d, "
134 "ME client = %d\n",
135 cl->host_client_id,
136 cl->me_client_id);
137 rets = mei_cl_disconnect(cl); 129 rets = mei_cl_disconnect(cl);
138 } 130 }
139 mei_cl_flush_queues(cl); 131 mei_cl_flush_queues(cl);
140 dev_dbg(&dev->pdev->dev, "remove client host client = %d, ME client = %d\n", 132 cl_dbg(dev, cl, "removing\n");
141 cl->host_client_id,
142 cl->me_client_id);
143 133
144 mei_cl_unlink(cl); 134 mei_cl_unlink(cl);
145 135
@@ -284,6 +274,7 @@ copy_buffer:
284 length = min_t(size_t, length, cb->buf_idx - *offset); 274 length = min_t(size_t, length, cb->buf_idx - *offset);
285 275
286 if (copy_to_user(ubuf, cb->response_buffer.data + *offset, length)) { 276 if (copy_to_user(ubuf, cb->response_buffer.data + *offset, length)) {
277 dev_dbg(&dev->pdev->dev, "failed to copy data to userland\n");
287 rets = -EFAULT; 278 rets = -EFAULT;
288 goto free; 279 goto free;
289 } 280 }
@@ -340,7 +331,7 @@ static ssize_t mei_write(struct file *file, const char __user *ubuf,
340 331
341 id = mei_me_cl_by_id(dev, cl->me_client_id); 332 id = mei_me_cl_by_id(dev, cl->me_client_id);
342 if (id < 0) { 333 if (id < 0) {
343 rets = -ENODEV; 334 rets = -ENOTTY;
344 goto out; 335 goto out;
345 } 336 }
346 337
@@ -404,7 +395,7 @@ static ssize_t mei_write(struct file *file, const char __user *ubuf,
404 395
405 rets = copy_from_user(write_cb->request_buffer.data, ubuf, length); 396 rets = copy_from_user(write_cb->request_buffer.data, ubuf, length);
406 if (rets) { 397 if (rets) {
407 dev_err(&dev->pdev->dev, "failed to copy data from userland\n"); 398 dev_dbg(&dev->pdev->dev, "failed to copy data from userland\n");
408 rets = -EFAULT; 399 rets = -EFAULT;
409 goto out; 400 goto out;
410 } 401 }
@@ -471,7 +462,7 @@ static int mei_ioctl_connect_client(struct file *file,
471 if (i < 0 || dev->me_clients[i].props.fixed_address) { 462 if (i < 0 || dev->me_clients[i].props.fixed_address) {
472 dev_dbg(&dev->pdev->dev, "Cannot connect to FW Client UUID = %pUl\n", 463 dev_dbg(&dev->pdev->dev, "Cannot connect to FW Client UUID = %pUl\n",
473 &data->in_client_uuid); 464 &data->in_client_uuid);
474 rets = -ENODEV; 465 rets = -ENOTTY;
475 goto end; 466 goto end;
476 } 467 }
477 468
@@ -569,7 +560,7 @@ static long mei_ioctl(struct file *file, unsigned int cmd, unsigned long data)
569 dev_dbg(&dev->pdev->dev, "copy connect data from user\n"); 560 dev_dbg(&dev->pdev->dev, "copy connect data from user\n");
570 if (copy_from_user(connect_data, (char __user *)data, 561 if (copy_from_user(connect_data, (char __user *)data,
571 sizeof(struct mei_connect_client_data))) { 562 sizeof(struct mei_connect_client_data))) {
572 dev_err(&dev->pdev->dev, "failed to copy data from userland\n"); 563 dev_dbg(&dev->pdev->dev, "failed to copy data from userland\n");
573 rets = -EFAULT; 564 rets = -EFAULT;
574 goto out; 565 goto out;
575 } 566 }
diff --git a/drivers/misc/mei/mei_dev.h b/drivers/misc/mei/mei_dev.h
index f7de95b4cdd9..94a516716d22 100644
--- a/drivers/misc/mei/mei_dev.h
+++ b/drivers/misc/mei/mei_dev.h
@@ -24,7 +24,6 @@
24#include <linux/mei_cl_bus.h> 24#include <linux/mei_cl_bus.h>
25 25
26#include "hw.h" 26#include "hw.h"
27#include "hw-me-regs.h"
28#include "hbm.h" 27#include "hbm.h"
29 28
30/* 29/*
@@ -130,16 +129,18 @@ enum mei_wd_states {
130 129
131/** 130/**
132 * enum mei_cb_file_ops - file operation associated with the callback 131 * enum mei_cb_file_ops - file operation associated with the callback
133 * @MEI_FOP_READ - read 132 * @MEI_FOP_READ - read
134 * @MEI_FOP_WRITE - write 133 * @MEI_FOP_WRITE - write
135 * @MEI_FOP_IOCTL - ioctl 134 * @MEI_FOP_CONNECT - connect
136 * @MEI_FOP_OPEN - open 135 * @MEI_FOP_DISCONNECT_RSP - disconnect response
137 * @MEI_FOP_CLOSE - close 136 * @MEI_FOP_OPEN - open
137 * @MEI_FOP_CLOSE - close
138 */ 138 */
139enum mei_cb_file_ops { 139enum mei_cb_file_ops {
140 MEI_FOP_READ = 0, 140 MEI_FOP_READ = 0,
141 MEI_FOP_WRITE, 141 MEI_FOP_WRITE,
142 MEI_FOP_IOCTL, 142 MEI_FOP_CONNECT,
143 MEI_FOP_DISCONNECT_RSP,
143 MEI_FOP_OPEN, 144 MEI_FOP_OPEN,
144 MEI_FOP_CLOSE 145 MEI_FOP_CLOSE
145}; 146};
@@ -236,20 +237,20 @@ struct mei_cl {
236 */ 237 */
237struct mei_hw_ops { 238struct mei_hw_ops {
238 239
239 bool (*host_is_ready) (struct mei_device *dev); 240 bool (*host_is_ready)(struct mei_device *dev);
240 241
241 bool (*hw_is_ready) (struct mei_device *dev); 242 bool (*hw_is_ready)(struct mei_device *dev);
242 int (*hw_reset) (struct mei_device *dev, bool enable); 243 int (*hw_reset)(struct mei_device *dev, bool enable);
243 int (*hw_start) (struct mei_device *dev); 244 int (*hw_start)(struct mei_device *dev);
244 void (*hw_config) (struct mei_device *dev); 245 void (*hw_config)(struct mei_device *dev);
245 246
246 void (*intr_clear) (struct mei_device *dev); 247 void (*intr_clear)(struct mei_device *dev);
247 void (*intr_enable) (struct mei_device *dev); 248 void (*intr_enable)(struct mei_device *dev);
248 void (*intr_disable) (struct mei_device *dev); 249 void (*intr_disable)(struct mei_device *dev);
249 250
250 int (*hbuf_free_slots) (struct mei_device *dev); 251 int (*hbuf_free_slots)(struct mei_device *dev);
251 bool (*hbuf_is_ready) (struct mei_device *dev); 252 bool (*hbuf_is_ready)(struct mei_device *dev);
252 size_t (*hbuf_max_len) (const struct mei_device *dev); 253 size_t (*hbuf_max_len)(const struct mei_device *dev);
253 254
254 int (*write)(struct mei_device *dev, 255 int (*write)(struct mei_device *dev,
255 struct mei_msg_hdr *hdr, 256 struct mei_msg_hdr *hdr,
@@ -258,7 +259,7 @@ struct mei_hw_ops {
258 int (*rdbuf_full_slots)(struct mei_device *dev); 259 int (*rdbuf_full_slots)(struct mei_device *dev);
259 260
260 u32 (*read_hdr)(const struct mei_device *dev); 261 u32 (*read_hdr)(const struct mei_device *dev);
261 int (*read) (struct mei_device *dev, 262 int (*read)(struct mei_device *dev,
262 unsigned char *buf, unsigned long len); 263 unsigned char *buf, unsigned long len);
263}; 264};
264 265
@@ -294,6 +295,7 @@ int __mei_cl_async_send(struct mei_cl *cl, u8 *buf, size_t length);
294int __mei_cl_send(struct mei_cl *cl, u8 *buf, size_t length); 295int __mei_cl_send(struct mei_cl *cl, u8 *buf, size_t length);
295int __mei_cl_recv(struct mei_cl *cl, u8 *buf, size_t length); 296int __mei_cl_recv(struct mei_cl *cl, u8 *buf, size_t length);
296void mei_cl_bus_rx_event(struct mei_cl *cl); 297void mei_cl_bus_rx_event(struct mei_cl *cl);
298void mei_cl_bus_remove_devices(struct mei_device *dev);
297int mei_cl_bus_init(void); 299int mei_cl_bus_init(void);
298void mei_cl_bus_exit(void); 300void mei_cl_bus_exit(void);
299 301
@@ -339,7 +341,6 @@ struct mei_cl_device {
339 * @hbuf_depth - depth of hardware host/write buffer is slots 341 * @hbuf_depth - depth of hardware host/write buffer is slots
340 * @hbuf_is_ready - query if the host host/write buffer is ready 342 * @hbuf_is_ready - query if the host host/write buffer is ready
341 * @wr_msg - the buffer for hbm control messages 343 * @wr_msg - the buffer for hbm control messages
342 * @wr_ext_msg - the buffer for hbm control responses (set in read cycle)
343 */ 344 */
344struct mei_device { 345struct mei_device {
345 struct pci_dev *pdev; /* pointer to pci device struct */ 346 struct pci_dev *pdev; /* pointer to pci device struct */
@@ -394,11 +395,6 @@ struct mei_device {
394 unsigned char data[128]; 395 unsigned char data[128];
395 } wr_msg; 396 } wr_msg;
396 397
397 struct {
398 struct mei_msg_hdr hdr;
399 unsigned char data[4]; /* All HBM messages are 4 bytes */
400 } wr_ext_msg; /* for control responses */
401
402 struct hbm_version version; 398 struct hbm_version version;
403 399
404 struct mei_me_client *me_clients; /* Note: memory has to be allocated */ 400 struct mei_me_client *me_clients; /* Note: memory has to be allocated */
@@ -518,8 +514,8 @@ struct mei_cl_cb *mei_amthif_find_read_list_entry(struct mei_device *dev,
518 514
519void mei_amthif_run_next_cmd(struct mei_device *dev); 515void mei_amthif_run_next_cmd(struct mei_device *dev);
520 516
521int mei_amthif_irq_write_complete(struct mei_cl *cl, struct mei_cl_cb *cb, 517int mei_amthif_irq_write(struct mei_cl *cl, struct mei_cl_cb *cb,
522 s32 *slots, struct mei_cl_cb *cmpl_list); 518 struct mei_cl_cb *cmpl_list);
523 519
524void mei_amthif_complete(struct mei_device *dev, struct mei_cl_cb *cb); 520void mei_amthif_complete(struct mei_device *dev, struct mei_cl_cb *cb);
525int mei_amthif_irq_read_msg(struct mei_device *dev, 521int mei_amthif_irq_read_msg(struct mei_device *dev,
@@ -546,7 +542,7 @@ int mei_wd_host_init(struct mei_device *dev);
546 * once we got connection to the WD Client 542 * once we got connection to the WD Client
547 * @dev - mei device 543 * @dev - mei device
548 */ 544 */
549void mei_watchdog_register(struct mei_device *dev); 545int mei_watchdog_register(struct mei_device *dev);
550/* 546/*
551 * mei_watchdog_unregister - Unregistering watchdog interface 547 * mei_watchdog_unregister - Unregistering watchdog interface
552 * @dev - mei device 548 * @dev - mei device
@@ -633,6 +629,8 @@ static inline int mei_count_full_read_slots(struct mei_device *dev)
633 return dev->ops->rdbuf_full_slots(dev); 629 return dev->ops->rdbuf_full_slots(dev);
634} 630}
635 631
632bool mei_hbuf_acquire(struct mei_device *dev);
633
636#if IS_ENABLED(CONFIG_DEBUG_FS) 634#if IS_ENABLED(CONFIG_DEBUG_FS)
637int mei_dbgfs_register(struct mei_device *dev, const char *name); 635int mei_dbgfs_register(struct mei_device *dev, const char *name);
638void mei_dbgfs_deregister(struct mei_device *dev); 636void mei_dbgfs_deregister(struct mei_device *dev);
diff --git a/drivers/misc/mei/nfc.c b/drivers/misc/mei/nfc.c
index a58320c0c049..3095fc514a65 100644
--- a/drivers/misc/mei/nfc.c
+++ b/drivers/misc/mei/nfc.c
@@ -364,7 +364,7 @@ static int mei_nfc_send(struct mei_cl_device *cldev, u8 *buf, size_t length)
364 if (!wait_event_interruptible_timeout(ndev->send_wq, 364 if (!wait_event_interruptible_timeout(ndev->send_wq,
365 ndev->recv_req_id == ndev->req_id, HZ)) { 365 ndev->recv_req_id == ndev->req_id, HZ)) {
366 dev_err(&dev->pdev->dev, "NFC MEI command timeout\n"); 366 dev_err(&dev->pdev->dev, "NFC MEI command timeout\n");
367 err = -ETIMEDOUT; 367 err = -ETIME;
368 } else { 368 } else {
369 ndev->req_id++; 369 ndev->req_id++;
370 } 370 }
@@ -502,7 +502,7 @@ int mei_nfc_host_init(struct mei_device *dev)
502 i = mei_me_cl_by_uuid(dev, &mei_nfc_info_guid); 502 i = mei_me_cl_by_uuid(dev, &mei_nfc_info_guid);
503 if (i < 0) { 503 if (i < 0) {
504 dev_info(&dev->pdev->dev, "nfc: failed to find the client\n"); 504 dev_info(&dev->pdev->dev, "nfc: failed to find the client\n");
505 ret = -ENOENT; 505 ret = -ENOTTY;
506 goto err; 506 goto err;
507 } 507 }
508 508
@@ -520,7 +520,7 @@ int mei_nfc_host_init(struct mei_device *dev)
520 i = mei_me_cl_by_uuid(dev, &mei_nfc_guid); 520 i = mei_me_cl_by_uuid(dev, &mei_nfc_guid);
521 if (i < 0) { 521 if (i < 0) {
522 dev_info(&dev->pdev->dev, "nfc: failed to find the client\n"); 522 dev_info(&dev->pdev->dev, "nfc: failed to find the client\n");
523 ret = -ENOENT; 523 ret = -ENOTTY;
524 goto err; 524 goto err;
525 } 525 }
526 526
@@ -552,13 +552,7 @@ err:
552void mei_nfc_host_exit(struct mei_device *dev) 552void mei_nfc_host_exit(struct mei_device *dev)
553{ 553{
554 struct mei_nfc_dev *ndev = &nfc_dev; 554 struct mei_nfc_dev *ndev = &nfc_dev;
555
556 cancel_work_sync(&ndev->init_work); 555 cancel_work_sync(&ndev->init_work);
556}
557 557
558 mutex_lock(&dev->device_lock);
559 if (ndev->cl && ndev->cl->device)
560 mei_cl_remove_device(ndev->cl->device);
561 558
562 mei_nfc_free(ndev);
563 mutex_unlock(&dev->device_lock);
564}
diff --git a/drivers/misc/mei/pci-me.c b/drivers/misc/mei/pci-me.c
index ddadd08956f4..1c8fd3a3e135 100644
--- a/drivers/misc/mei/pci-me.c
+++ b/drivers/misc/mei/pci-me.c
@@ -13,9 +13,6 @@
13 * more details. 13 * more details.
14 * 14 *
15 */ 15 */
16
17#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
18
19#include <linux/module.h> 16#include <linux/module.h>
20#include <linux/moduleparam.h> 17#include <linux/moduleparam.h>
21#include <linux/kernel.h> 18#include <linux/kernel.h>
@@ -27,7 +24,6 @@
27#include <linux/aio.h> 24#include <linux/aio.h>
28#include <linux/pci.h> 25#include <linux/pci.h>
29#include <linux/poll.h> 26#include <linux/poll.h>
30#include <linux/init.h>
31#include <linux/ioctl.h> 27#include <linux/ioctl.h>
32#include <linux/cdev.h> 28#include <linux/cdev.h>
33#include <linux/sched.h> 29#include <linux/sched.h>
@@ -40,11 +36,12 @@
40#include <linux/mei.h> 36#include <linux/mei.h>
41 37
42#include "mei_dev.h" 38#include "mei_dev.h"
43#include "hw-me.h"
44#include "client.h" 39#include "client.h"
40#include "hw-me-regs.h"
41#include "hw-me.h"
45 42
46/* mei_pci_tbl - PCI Device ID Table */ 43/* mei_pci_tbl - PCI Device ID Table */
47static DEFINE_PCI_DEVICE_TABLE(mei_me_pci_tbl) = { 44static const struct pci_device_id mei_me_pci_tbl[] = {
48 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, MEI_DEV_ID_82946GZ)}, 45 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, MEI_DEV_ID_82946GZ)},
49 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, MEI_DEV_ID_82G35)}, 46 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, MEI_DEV_ID_82G35)},
50 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, MEI_DEV_ID_82Q965)}, 47 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, MEI_DEV_ID_82Q965)},
@@ -270,7 +267,7 @@ static void mei_me_remove(struct pci_dev *pdev)
270 267
271 268
272} 269}
273#ifdef CONFIG_PM 270#ifdef CONFIG_PM_SLEEP
274static int mei_me_pci_suspend(struct device *device) 271static int mei_me_pci_suspend(struct device *device)
275{ 272{
276 struct pci_dev *pdev = to_pci_dev(device); 273 struct pci_dev *pdev = to_pci_dev(device);
@@ -330,11 +327,12 @@ static int mei_me_pci_resume(struct device *device)
330 327
331 return 0; 328 return 0;
332} 329}
330
333static SIMPLE_DEV_PM_OPS(mei_me_pm_ops, mei_me_pci_suspend, mei_me_pci_resume); 331static SIMPLE_DEV_PM_OPS(mei_me_pm_ops, mei_me_pci_suspend, mei_me_pci_resume);
334#define MEI_ME_PM_OPS (&mei_me_pm_ops) 332#define MEI_ME_PM_OPS (&mei_me_pm_ops)
335#else 333#else
336#define MEI_ME_PM_OPS NULL 334#define MEI_ME_PM_OPS NULL
337#endif /* CONFIG_PM */ 335#endif /* CONFIG_PM_SLEEP */
338/* 336/*
339 * PCI driver structure 337 * PCI driver structure
340 */ 338 */
diff --git a/drivers/misc/mei/pci-txe.c b/drivers/misc/mei/pci-txe.c
new file mode 100644
index 000000000000..ad3adb009a1e
--- /dev/null
+++ b/drivers/misc/mei/pci-txe.c
@@ -0,0 +1,293 @@
1/*
2 *
3 * Intel Management Engine Interface (Intel MEI) Linux driver
4 * Copyright (c) 2013-2014, Intel Corporation.
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
14 *
15 */
16
17#include <linux/module.h>
18#include <linux/kernel.h>
19#include <linux/device.h>
20#include <linux/fs.h>
21#include <linux/errno.h>
22#include <linux/types.h>
23#include <linux/pci.h>
24#include <linux/init.h>
25#include <linux/sched.h>
26#include <linux/uuid.h>
27#include <linux/jiffies.h>
28#include <linux/interrupt.h>
29#include <linux/workqueue.h>
30
31#include <linux/mei.h>
32
33
34#include "mei_dev.h"
35#include "hw-txe.h"
36
37static const struct pci_device_id mei_txe_pci_tbl[] = {
38 {PCI_DEVICE(PCI_VENDOR_ID_INTEL, 0x0F18)}, /* Baytrail */
39 {0, }
40};
41MODULE_DEVICE_TABLE(pci, mei_txe_pci_tbl);
42
43
44static void mei_txe_pci_iounmap(struct pci_dev *pdev, struct mei_txe_hw *hw)
45{
46 int i;
47 for (i = SEC_BAR; i < NUM_OF_MEM_BARS; i++) {
48 if (hw->mem_addr[i]) {
49 pci_iounmap(pdev, hw->mem_addr[i]);
50 hw->mem_addr[i] = NULL;
51 }
52 }
53}
54/**
55 * mei_probe - Device Initialization Routine
56 *
57 * @pdev: PCI device structure
58 * @ent: entry in mei_txe_pci_tbl
59 *
60 * returns 0 on success, <0 on failure.
61 */
62static int mei_txe_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
63{
64 struct mei_device *dev;
65 struct mei_txe_hw *hw;
66 int err;
67 int i;
68
69 /* enable pci dev */
70 err = pci_enable_device(pdev);
71 if (err) {
72 dev_err(&pdev->dev, "failed to enable pci device.\n");
73 goto end;
74 }
75 /* set PCI host mastering */
76 pci_set_master(pdev);
77 /* pci request regions for mei driver */
78 err = pci_request_regions(pdev, KBUILD_MODNAME);
79 if (err) {
80 dev_err(&pdev->dev, "failed to get pci regions.\n");
81 goto disable_device;
82 }
83
84 err = pci_set_dma_mask(pdev, DMA_BIT_MASK(36));
85 if (err) {
86 err = pci_set_dma_mask(pdev, DMA_BIT_MASK(32));
87 if (err) {
88 dev_err(&pdev->dev, "No suitable DMA available.\n");
89 goto release_regions;
90 }
91 }
92
93 /* allocates and initializes the mei dev structure */
94 dev = mei_txe_dev_init(pdev);
95 if (!dev) {
96 err = -ENOMEM;
97 goto release_regions;
98 }
99 hw = to_txe_hw(dev);
100
101 /* mapping IO device memory */
102 for (i = SEC_BAR; i < NUM_OF_MEM_BARS; i++) {
103 hw->mem_addr[i] = pci_iomap(pdev, i, 0);
104 if (!hw->mem_addr[i]) {
105 dev_err(&pdev->dev, "mapping I/O device memory failure.\n");
106 err = -ENOMEM;
107 goto free_device;
108 }
109 }
110
111
112 pci_enable_msi(pdev);
113
114 /* clear spurious interrupts */
115 mei_clear_interrupts(dev);
116
117 /* request and enable interrupt */
118 if (pci_dev_msi_enabled(pdev))
119 err = request_threaded_irq(pdev->irq,
120 NULL,
121 mei_txe_irq_thread_handler,
122 IRQF_ONESHOT, KBUILD_MODNAME, dev);
123 else
124 err = request_threaded_irq(pdev->irq,
125 mei_txe_irq_quick_handler,
126 mei_txe_irq_thread_handler,
127 IRQF_SHARED, KBUILD_MODNAME, dev);
128 if (err) {
129 dev_err(&pdev->dev, "mei: request_threaded_irq failure. irq = %d\n",
130 pdev->irq);
131 goto free_device;
132 }
133
134 if (mei_start(dev)) {
135 dev_err(&pdev->dev, "init hw failure.\n");
136 err = -ENODEV;
137 goto release_irq;
138 }
139
140 err = mei_register(dev);
141 if (err)
142 goto release_irq;
143
144 pci_set_drvdata(pdev, dev);
145
146 return 0;
147
148release_irq:
149
150 mei_cancel_work(dev);
151
152 /* disable interrupts */
153 mei_disable_interrupts(dev);
154
155 free_irq(pdev->irq, dev);
156 pci_disable_msi(pdev);
157
158free_device:
159 mei_txe_pci_iounmap(pdev, hw);
160
161 kfree(dev);
162release_regions:
163 pci_release_regions(pdev);
164disable_device:
165 pci_disable_device(pdev);
166end:
167 dev_err(&pdev->dev, "initialization failed.\n");
168 return err;
169}
170
171/**
172 * mei_remove - Device Removal Routine
173 *
174 * @pdev: PCI device structure
175 *
176 * mei_remove is called by the PCI subsystem to alert the driver
177 * that it should release a PCI device.
178 */
179static void mei_txe_remove(struct pci_dev *pdev)
180{
181 struct mei_device *dev;
182 struct mei_txe_hw *hw;
183
184 dev = pci_get_drvdata(pdev);
185 if (!dev) {
186 dev_err(&pdev->dev, "mei: dev =NULL\n");
187 return;
188 }
189
190 hw = to_txe_hw(dev);
191
192 mei_stop(dev);
193
194 /* disable interrupts */
195 mei_disable_interrupts(dev);
196 free_irq(pdev->irq, dev);
197 pci_disable_msi(pdev);
198
199 pci_set_drvdata(pdev, NULL);
200
201 mei_txe_pci_iounmap(pdev, hw);
202
203 mei_deregister(dev);
204
205 kfree(dev);
206
207 pci_release_regions(pdev);
208 pci_disable_device(pdev);
209}
210
211
212#ifdef CONFIG_PM_SLEEP
213static int mei_txe_pci_suspend(struct device *device)
214{
215 struct pci_dev *pdev = to_pci_dev(device);
216 struct mei_device *dev = pci_get_drvdata(pdev);
217
218 if (!dev)
219 return -ENODEV;
220
221 dev_dbg(&pdev->dev, "suspend\n");
222
223 mei_stop(dev);
224
225 mei_disable_interrupts(dev);
226
227 free_irq(pdev->irq, dev);
228 pci_disable_msi(pdev);
229
230 return 0;
231}
232
233static int mei_txe_pci_resume(struct device *device)
234{
235 struct pci_dev *pdev = to_pci_dev(device);
236 struct mei_device *dev;
237 int err;
238
239 dev = pci_get_drvdata(pdev);
240 if (!dev)
241 return -ENODEV;
242
243 pci_enable_msi(pdev);
244
245 mei_clear_interrupts(dev);
246
247 /* request and enable interrupt */
248 if (pci_dev_msi_enabled(pdev))
249 err = request_threaded_irq(pdev->irq,
250 NULL,
251 mei_txe_irq_thread_handler,
252 IRQF_ONESHOT, KBUILD_MODNAME, dev);
253 else
254 err = request_threaded_irq(pdev->irq,
255 mei_txe_irq_quick_handler,
256 mei_txe_irq_thread_handler,
257 IRQF_SHARED, KBUILD_MODNAME, dev);
258 if (err) {
259 dev_err(&pdev->dev, "request_threaded_irq failed: irq = %d.\n",
260 pdev->irq);
261 return err;
262 }
263
264 err = mei_restart(dev);
265
266 return err;
267}
268
269static SIMPLE_DEV_PM_OPS(mei_txe_pm_ops,
270 mei_txe_pci_suspend,
271 mei_txe_pci_resume);
272
273#define MEI_TXE_PM_OPS (&mei_txe_pm_ops)
274#else
275#define MEI_TXE_PM_OPS NULL
276#endif /* CONFIG_PM_SLEEP */
277/*
278 * PCI driver structure
279 */
280static struct pci_driver mei_txe_driver = {
281 .name = KBUILD_MODNAME,
282 .id_table = mei_txe_pci_tbl,
283 .probe = mei_txe_probe,
284 .remove = mei_txe_remove,
285 .shutdown = mei_txe_remove,
286 .driver.pm = MEI_TXE_PM_OPS,
287};
288
289module_pci_driver(mei_txe_driver);
290
291MODULE_AUTHOR("Intel Corporation");
292MODULE_DESCRIPTION("Intel(R) Trusted Execution Environment Interface");
293MODULE_LICENSE("GPL v2");
diff --git a/drivers/misc/mei/wd.c b/drivers/misc/mei/wd.c
index f70945ed96f6..ebf1cbc198fd 100644
--- a/drivers/misc/mei/wd.c
+++ b/drivers/misc/mei/wd.c
@@ -25,7 +25,6 @@
25 25
26#include "mei_dev.h" 26#include "mei_dev.h"
27#include "hbm.h" 27#include "hbm.h"
28#include "hw-me.h"
29#include "client.h" 28#include "client.h"
30 29
31static const u8 mei_start_wd_params[] = { 0x02, 0x12, 0x13, 0x10 }; 30static const u8 mei_start_wd_params[] = { 0x02, 0x12, 0x13, 0x10 };
@@ -53,7 +52,7 @@ static void mei_wd_set_start_timeout(struct mei_device *dev, u16 timeout)
53 * 52 *
54 * @dev: the device structure 53 * @dev: the device structure
55 * 54 *
56 * returns -ENENT if wd client cannot be found 55 * returns -ENOTTY if wd client cannot be found
57 * -EIO if write has failed 56 * -EIO if write has failed
58 * 0 on success 57 * 0 on success
59 */ 58 */
@@ -73,7 +72,7 @@ int mei_wd_host_init(struct mei_device *dev)
73 id = mei_me_cl_by_uuid(dev, &mei_wd_guid); 72 id = mei_me_cl_by_uuid(dev, &mei_wd_guid);
74 if (id < 0) { 73 if (id < 0) {
75 dev_info(&dev->pdev->dev, "wd: failed to find the client\n"); 74 dev_info(&dev->pdev->dev, "wd: failed to find the client\n");
76 return id; 75 return -ENOTTY;
77 } 76 }
78 77
79 cl->me_client_id = dev->me_clients[id].client_id; 78 cl->me_client_id = dev->me_clients[id].client_id;
@@ -87,15 +86,20 @@ int mei_wd_host_init(struct mei_device *dev)
87 86
88 cl->state = MEI_FILE_CONNECTING; 87 cl->state = MEI_FILE_CONNECTING;
89 88
90 if (mei_hbm_cl_connect_req(dev, cl)) { 89 ret = mei_cl_connect(cl, NULL);
91 dev_err(&dev->pdev->dev, "wd: failed to connect to the client\n"); 90
92 cl->state = MEI_FILE_DISCONNECTED; 91 if (ret) {
93 cl->host_client_id = 0; 92 dev_err(&dev->pdev->dev, "wd: failed to connect = %d\n", ret);
94 return -EIO; 93 mei_cl_unlink(cl);
94 return ret;
95 } 95 }
96 cl->timer_count = MEI_CONNECT_TIMEOUT;
97 96
98 return 0; 97 ret = mei_watchdog_register(dev);
98 if (ret) {
99 mei_cl_disconnect(cl);
100 mei_cl_unlink(cl);
101 }
102 return ret;
99} 103}
100 104
101/** 105/**
@@ -106,13 +110,16 @@ int mei_wd_host_init(struct mei_device *dev)
106 * returns 0 if success, 110 * returns 0 if success,
107 * -EIO when message send fails 111 * -EIO when message send fails
108 * -EINVAL when invalid message is to be sent 112 * -EINVAL when invalid message is to be sent
113 * -ENODEV on flow control failure
109 */ 114 */
110int mei_wd_send(struct mei_device *dev) 115int mei_wd_send(struct mei_device *dev)
111{ 116{
117 struct mei_cl *cl = &dev->wd_cl;
112 struct mei_msg_hdr hdr; 118 struct mei_msg_hdr hdr;
119 int ret;
113 120
114 hdr.host_addr = dev->wd_cl.host_client_id; 121 hdr.host_addr = cl->host_client_id;
115 hdr.me_addr = dev->wd_cl.me_client_id; 122 hdr.me_addr = cl->me_client_id;
116 hdr.msg_complete = 1; 123 hdr.msg_complete = 1;
117 hdr.reserved = 0; 124 hdr.reserved = 0;
118 hdr.internal = 0; 125 hdr.internal = 0;
@@ -121,10 +128,24 @@ int mei_wd_send(struct mei_device *dev)
121 hdr.length = MEI_WD_START_MSG_SIZE; 128 hdr.length = MEI_WD_START_MSG_SIZE;
122 else if (!memcmp(dev->wd_data, mei_stop_wd_params, MEI_WD_HDR_SIZE)) 129 else if (!memcmp(dev->wd_data, mei_stop_wd_params, MEI_WD_HDR_SIZE))
123 hdr.length = MEI_WD_STOP_MSG_SIZE; 130 hdr.length = MEI_WD_STOP_MSG_SIZE;
124 else 131 else {
132 dev_err(&dev->pdev->dev, "wd: invalid message is to be sent, aborting\n");
125 return -EINVAL; 133 return -EINVAL;
134 }
126 135
127 return mei_write_message(dev, &hdr, dev->wd_data); 136 ret = mei_write_message(dev, &hdr, dev->wd_data);
137 if (ret) {
138 dev_err(&dev->pdev->dev, "wd: write message failed\n");
139 return ret;
140 }
141
142 ret = mei_cl_flow_ctrl_reduce(cl);
143 if (ret) {
144 dev_err(&dev->pdev->dev, "wd: flow_ctrl_reduce failed.\n");
145 return ret;
146 }
147
148 return 0;
128} 149}
129 150
130/** 151/**
@@ -133,9 +154,11 @@ int mei_wd_send(struct mei_device *dev)
133 * @dev: the device structure 154 * @dev: the device structure
134 * @preserve: indicate if to keep the timeout value 155 * @preserve: indicate if to keep the timeout value
135 * 156 *
136 * returns 0 if success, 157 * returns 0 if success
137 * -EIO when message send fails 158 * on error:
159 * -EIO when message send fails
138 * -EINVAL when invalid message is to be sent 160 * -EINVAL when invalid message is to be sent
161 * -ETIME on message timeout
139 */ 162 */
140int mei_wd_stop(struct mei_device *dev) 163int mei_wd_stop(struct mei_device *dev)
141{ 164{
@@ -151,20 +174,12 @@ int mei_wd_stop(struct mei_device *dev)
151 174
152 ret = mei_cl_flow_ctrl_creds(&dev->wd_cl); 175 ret = mei_cl_flow_ctrl_creds(&dev->wd_cl);
153 if (ret < 0) 176 if (ret < 0)
154 goto out; 177 goto err;
155
156 if (ret && dev->hbuf_is_ready) {
157 ret = 0;
158 dev->hbuf_is_ready = false;
159
160 if (!mei_wd_send(dev)) {
161 ret = mei_cl_flow_ctrl_reduce(&dev->wd_cl);
162 if (ret)
163 goto out;
164 } else {
165 dev_err(&dev->pdev->dev, "wd: send stop failed\n");
166 }
167 178
179 if (ret && mei_hbuf_acquire(dev)) {
180 ret = mei_wd_send(dev);
181 if (ret)
182 goto err;
168 dev->wd_pending = false; 183 dev->wd_pending = false;
169 } else { 184 } else {
170 dev->wd_pending = true; 185 dev->wd_pending = true;
@@ -172,21 +187,21 @@ int mei_wd_stop(struct mei_device *dev)
172 187
173 mutex_unlock(&dev->device_lock); 188 mutex_unlock(&dev->device_lock);
174 189
175 ret = wait_event_interruptible_timeout(dev->wait_stop_wd, 190 ret = wait_event_timeout(dev->wait_stop_wd,
176 dev->wd_state == MEI_WD_IDLE, 191 dev->wd_state == MEI_WD_IDLE,
177 msecs_to_jiffies(MEI_WD_STOP_TIMEOUT)); 192 msecs_to_jiffies(MEI_WD_STOP_TIMEOUT));
178 mutex_lock(&dev->device_lock); 193 mutex_lock(&dev->device_lock);
179 if (dev->wd_state == MEI_WD_IDLE) { 194 if (dev->wd_state != MEI_WD_IDLE) {
180 dev_dbg(&dev->pdev->dev, "wd: stop completed ret=%d.\n", ret); 195 /* timeout */
181 ret = 0; 196 ret = -ETIME;
182 } else {
183 if (!ret)
184 ret = -ETIMEDOUT;
185 dev_warn(&dev->pdev->dev, 197 dev_warn(&dev->pdev->dev,
186 "wd: stop failed to complete ret=%d.\n", ret); 198 "wd: stop failed to complete ret=%d.\n", ret);
199 goto err;
187 } 200 }
188 201 dev_dbg(&dev->pdev->dev, "wd: stop completed after %u msec\n",
189out: 202 MEI_WD_STOP_TIMEOUT - jiffies_to_msecs(ret));
203 return 0;
204err:
190 return ret; 205 return ret;
191} 206}
192 207
@@ -260,8 +275,8 @@ static int mei_wd_ops_stop(struct watchdog_device *wd_dev)
260 */ 275 */
261static int mei_wd_ops_ping(struct watchdog_device *wd_dev) 276static int mei_wd_ops_ping(struct watchdog_device *wd_dev)
262{ 277{
263 int ret = 0;
264 struct mei_device *dev; 278 struct mei_device *dev;
279 int ret;
265 280
266 dev = watchdog_get_drvdata(wd_dev); 281 dev = watchdog_get_drvdata(wd_dev);
267 if (!dev) 282 if (!dev)
@@ -277,25 +292,18 @@ static int mei_wd_ops_ping(struct watchdog_device *wd_dev)
277 292
278 dev->wd_state = MEI_WD_RUNNING; 293 dev->wd_state = MEI_WD_RUNNING;
279 294
295 ret = mei_cl_flow_ctrl_creds(&dev->wd_cl);
296 if (ret < 0)
297 goto end;
280 /* Check if we can send the ping to HW*/ 298 /* Check if we can send the ping to HW*/
281 if (dev->hbuf_is_ready && mei_cl_flow_ctrl_creds(&dev->wd_cl) > 0) { 299 if (ret && mei_hbuf_acquire(dev)) {
282 300
283 dev->hbuf_is_ready = false;
284 dev_dbg(&dev->pdev->dev, "wd: sending ping\n"); 301 dev_dbg(&dev->pdev->dev, "wd: sending ping\n");
285 302
286 if (mei_wd_send(dev)) { 303 ret = mei_wd_send(dev);
287 dev_err(&dev->pdev->dev, "wd: send failed.\n"); 304 if (ret)
288 ret = -EIO;
289 goto end; 305 goto end;
290 } 306 dev->wd_pending = false;
291
292 if (mei_cl_flow_ctrl_reduce(&dev->wd_cl)) {
293 dev_err(&dev->pdev->dev,
294 "wd: mei_cl_flow_ctrl_reduce() failed.\n");
295 ret = -EIO;
296 goto end;
297 }
298
299 } else { 307 } else {
300 dev->wd_pending = true; 308 dev->wd_pending = true;
301 } 309 }
@@ -363,17 +371,25 @@ static struct watchdog_device amt_wd_dev = {
363}; 371};
364 372
365 373
366void mei_watchdog_register(struct mei_device *dev) 374int mei_watchdog_register(struct mei_device *dev)
367{ 375{
368 if (watchdog_register_device(&amt_wd_dev)) { 376
369 dev_err(&dev->pdev->dev, 377 int ret;
370 "wd: unable to register watchdog device.\n"); 378
371 return; 379 /* unlock to perserve correct locking order */
380 mutex_unlock(&dev->device_lock);
381 ret = watchdog_register_device(&amt_wd_dev);
382 mutex_lock(&dev->device_lock);
383 if (ret) {
384 dev_err(&dev->pdev->dev, "wd: unable to register watchdog device = %d.\n",
385 ret);
386 return ret;
372 } 387 }
373 388
374 dev_dbg(&dev->pdev->dev, 389 dev_dbg(&dev->pdev->dev,
375 "wd: successfully register watchdog interface.\n"); 390 "wd: successfully register watchdog interface.\n");
376 watchdog_set_drvdata(&amt_wd_dev, dev); 391 watchdog_set_drvdata(&amt_wd_dev, dev);
392 return 0;
377} 393}
378 394
379void mei_watchdog_unregister(struct mei_device *dev) 395void mei_watchdog_unregister(struct mei_device *dev)
diff --git a/drivers/misc/mic/host/mic_intr.c b/drivers/misc/mic/host/mic_intr.c
index f9c29bc918bc..dbc5afde1392 100644
--- a/drivers/misc/mic/host/mic_intr.c
+++ b/drivers/misc/mic/host/mic_intr.c
@@ -194,7 +194,7 @@ static int mic_setup_msix(struct mic_device *mdev, struct pci_dev *pdev)
194 for (i = 0; i < MIC_MIN_MSIX; i++) 194 for (i = 0; i < MIC_MIN_MSIX; i++)
195 mdev->irq_info.msix_entries[i].entry = i; 195 mdev->irq_info.msix_entries[i].entry = i;
196 196
197 rc = pci_enable_msix(pdev, mdev->irq_info.msix_entries, 197 rc = pci_enable_msix_exact(pdev, mdev->irq_info.msix_entries,
198 MIC_MIN_MSIX); 198 MIC_MIN_MSIX);
199 if (rc) { 199 if (rc) {
200 dev_dbg(&pdev->dev, "Error enabling MSIx. rc = %d\n", rc); 200 dev_dbg(&pdev->dev, "Error enabling MSIx. rc = %d\n", rc);
diff --git a/drivers/misc/pch_phub.c b/drivers/misc/pch_phub.c
index a5925f7f17f6..956597321d2a 100644
--- a/drivers/misc/pch_phub.c
+++ b/drivers/misc/pch_phub.c
@@ -636,6 +636,7 @@ static ssize_t store_pch_mac(struct device *dev, struct device_attribute *attr,
636 u8 mac[ETH_ALEN]; 636 u8 mac[ETH_ALEN];
637 ssize_t rom_size; 637 ssize_t rom_size;
638 struct pch_phub_reg *chip = dev_get_drvdata(dev); 638 struct pch_phub_reg *chip = dev_get_drvdata(dev);
639 int ret;
639 640
640 if (!mac_pton(buf, mac)) 641 if (!mac_pton(buf, mac))
641 return -EINVAL; 642 return -EINVAL;
@@ -644,8 +645,10 @@ static ssize_t store_pch_mac(struct device *dev, struct device_attribute *attr,
644 if (!chip->pch_phub_extrom_base_address) 645 if (!chip->pch_phub_extrom_base_address)
645 return -ENOMEM; 646 return -ENOMEM;
646 647
647 pch_phub_write_gbe_mac_addr(chip, mac); 648 ret = pch_phub_write_gbe_mac_addr(chip, mac);
648 pci_unmap_rom(chip->pdev, chip->pch_phub_extrom_base_address); 649 pci_unmap_rom(chip->pdev, chip->pch_phub_extrom_base_address);
650 if (ret)
651 return ret;
649 652
650 return count; 653 return count;
651} 654}
diff --git a/drivers/misc/sram.c b/drivers/misc/sram.c
index afe66571ce0b..21181fa243df 100644
--- a/drivers/misc/sram.c
+++ b/drivers/misc/sram.c
@@ -24,6 +24,9 @@
24#include <linux/err.h> 24#include <linux/err.h>
25#include <linux/io.h> 25#include <linux/io.h>
26#include <linux/of.h> 26#include <linux/of.h>
27#include <linux/of_address.h>
28#include <linux/list.h>
29#include <linux/list_sort.h>
27#include <linux/platform_device.h> 30#include <linux/platform_device.h>
28#include <linux/slab.h> 31#include <linux/slab.h>
29#include <linux/spinlock.h> 32#include <linux/spinlock.h>
@@ -36,14 +39,35 @@ struct sram_dev {
36 struct clk *clk; 39 struct clk *clk;
37}; 40};
38 41
42struct sram_reserve {
43 struct list_head list;
44 u32 start;
45 u32 size;
46};
47
48static int sram_reserve_cmp(void *priv, struct list_head *a,
49 struct list_head *b)
50{
51 struct sram_reserve *ra = list_entry(a, struct sram_reserve, list);
52 struct sram_reserve *rb = list_entry(b, struct sram_reserve, list);
53
54 return ra->start - rb->start;
55}
56
39static int sram_probe(struct platform_device *pdev) 57static int sram_probe(struct platform_device *pdev)
40{ 58{
41 void __iomem *virt_base; 59 void __iomem *virt_base;
42 struct sram_dev *sram; 60 struct sram_dev *sram;
43 struct resource *res; 61 struct resource *res;
44 unsigned long size; 62 struct device_node *np = pdev->dev.of_node, *child;
63 unsigned long size, cur_start, cur_size;
64 struct sram_reserve *rblocks, *block;
65 struct list_head reserve_list;
66 unsigned int nblocks;
45 int ret; 67 int ret;
46 68
69 INIT_LIST_HEAD(&reserve_list);
70
47 res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 71 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
48 virt_base = devm_ioremap_resource(&pdev->dev, res); 72 virt_base = devm_ioremap_resource(&pdev->dev, res);
49 if (IS_ERR(virt_base)) 73 if (IS_ERR(virt_base))
@@ -65,19 +89,106 @@ static int sram_probe(struct platform_device *pdev)
65 if (!sram->pool) 89 if (!sram->pool)
66 return -ENOMEM; 90 return -ENOMEM;
67 91
68 ret = gen_pool_add_virt(sram->pool, (unsigned long)virt_base, 92 /*
69 res->start, size, -1); 93 * We need an additional block to mark the end of the memory region
70 if (ret < 0) { 94 * after the reserved blocks from the dt are processed.
71 if (sram->clk) 95 */
72 clk_disable_unprepare(sram->clk); 96 nblocks = (np) ? of_get_available_child_count(np) + 1 : 1;
73 return ret; 97 rblocks = kmalloc((nblocks) * sizeof(*rblocks), GFP_KERNEL);
98 if (!rblocks) {
99 ret = -ENOMEM;
100 goto err_alloc;
101 }
102
103 block = &rblocks[0];
104 for_each_available_child_of_node(np, child) {
105 struct resource child_res;
106
107 ret = of_address_to_resource(child, 0, &child_res);
108 if (ret < 0) {
109 dev_err(&pdev->dev,
110 "could not get address for node %s\n",
111 child->full_name);
112 goto err_chunks;
113 }
114
115 if (child_res.start < res->start || child_res.end > res->end) {
116 dev_err(&pdev->dev,
117 "reserved block %s outside the sram area\n",
118 child->full_name);
119 ret = -EINVAL;
120 goto err_chunks;
121 }
122
123 block->start = child_res.start - res->start;
124 block->size = resource_size(&child_res);
125 list_add_tail(&block->list, &reserve_list);
126
127 dev_dbg(&pdev->dev, "found reserved block 0x%x-0x%x\n",
128 block->start,
129 block->start + block->size);
130
131 block++;
132 }
133
134 /* the last chunk marks the end of the region */
135 rblocks[nblocks - 1].start = size;
136 rblocks[nblocks - 1].size = 0;
137 list_add_tail(&rblocks[nblocks - 1].list, &reserve_list);
138
139 list_sort(NULL, &reserve_list, sram_reserve_cmp);
140
141 cur_start = 0;
142
143 list_for_each_entry(block, &reserve_list, list) {
144 /* can only happen if sections overlap */
145 if (block->start < cur_start) {
146 dev_err(&pdev->dev,
147 "block at 0x%x starts after current offset 0x%lx\n",
148 block->start, cur_start);
149 ret = -EINVAL;
150 goto err_chunks;
151 }
152
153 /* current start is in a reserved block, so continue after it */
154 if (block->start == cur_start) {
155 cur_start = block->start + block->size;
156 continue;
157 }
158
159 /*
160 * allocate the space between the current starting
161 * address and the following reserved block, or the
162 * end of the region.
163 */
164 cur_size = block->start - cur_start;
165
166 dev_dbg(&pdev->dev, "adding chunk 0x%lx-0x%lx\n",
167 cur_start, cur_start + cur_size);
168 ret = gen_pool_add_virt(sram->pool,
169 (unsigned long)virt_base + cur_start,
170 res->start + cur_start, cur_size, -1);
171 if (ret < 0)
172 goto err_chunks;
173
174 /* next allocation after this reserved block */
175 cur_start = block->start + block->size;
74 } 176 }
75 177
178 kfree(rblocks);
179
76 platform_set_drvdata(pdev, sram); 180 platform_set_drvdata(pdev, sram);
77 181
78 dev_dbg(&pdev->dev, "SRAM pool: %ld KiB @ 0x%p\n", size / 1024, virt_base); 182 dev_dbg(&pdev->dev, "SRAM pool: %ld KiB @ 0x%p\n", size / 1024, virt_base);
79 183
80 return 0; 184 return 0;
185
186err_chunks:
187 kfree(rblocks);
188err_alloc:
189 if (sram->clk)
190 clk_disable_unprepare(sram->clk);
191 return ret;
81} 192}
82 193
83static int sram_remove(struct platform_device *pdev) 194static int sram_remove(struct platform_device *pdev)
@@ -87,8 +198,6 @@ static int sram_remove(struct platform_device *pdev)
87 if (gen_pool_avail(sram->pool) < gen_pool_size(sram->pool)) 198 if (gen_pool_avail(sram->pool) < gen_pool_size(sram->pool))
88 dev_dbg(&pdev->dev, "removed while SRAM allocated\n"); 199 dev_dbg(&pdev->dev, "removed while SRAM allocated\n");
89 200
90 gen_pool_destroy(sram->pool);
91
92 if (sram->clk) 201 if (sram->clk)
93 clk_disable_unprepare(sram->clk); 202 clk_disable_unprepare(sram->clk);
94 203
diff --git a/drivers/misc/ti-st/st_core.c b/drivers/misc/ti-st/st_core.c
index 3aed525e55b4..1972d57aadb3 100644
--- a/drivers/misc/ti-st/st_core.c
+++ b/drivers/misc/ti-st/st_core.c
@@ -22,7 +22,6 @@
22#define pr_fmt(fmt) "(stc): " fmt 22#define pr_fmt(fmt) "(stc): " fmt
23#include <linux/module.h> 23#include <linux/module.h>
24#include <linux/kernel.h> 24#include <linux/kernel.h>
25#include <linux/init.h>
26#include <linux/tty.h> 25#include <linux/tty.h>
27 26
28#include <linux/seq_file.h> 27#include <linux/seq_file.h>
diff --git a/drivers/misc/ti_dac7512.c b/drivers/misc/ti_dac7512.c
index 83da711ce9f1..cb0289b44a17 100644
--- a/drivers/misc/ti_dac7512.c
+++ b/drivers/misc/ti_dac7512.c
@@ -20,7 +20,6 @@
20 */ 20 */
21 21
22#include <linux/module.h> 22#include <linux/module.h>
23#include <linux/init.h>
24#include <linux/spi/spi.h> 23#include <linux/spi/spi.h>
25#include <linux/of.h> 24#include <linux/of.h>
26 25
diff --git a/drivers/misc/tsl2550.c b/drivers/misc/tsl2550.c
index 5bc10fa193de..b00335652e52 100644
--- a/drivers/misc/tsl2550.c
+++ b/drivers/misc/tsl2550.c
@@ -20,7 +20,6 @@
20 */ 20 */
21 21
22#include <linux/module.h> 22#include <linux/module.h>
23#include <linux/init.h>
24#include <linux/slab.h> 23#include <linux/slab.h>
25#include <linux/i2c.h> 24#include <linux/i2c.h>
26#include <linux/mutex.h> 25#include <linux/mutex.h>
diff --git a/drivers/misc/vmw_vmci/vmci_guest.c b/drivers/misc/vmw_vmci/vmci_guest.c
index d35cda06b5e8..e0d5017785e5 100644
--- a/drivers/misc/vmw_vmci/vmci_guest.c
+++ b/drivers/misc/vmw_vmci/vmci_guest.c
@@ -383,11 +383,12 @@ static int vmci_enable_msix(struct pci_dev *pdev,
383 vmci_dev->msix_entries[i].vector = i; 383 vmci_dev->msix_entries[i].vector = i;
384 } 384 }
385 385
386 result = pci_enable_msix(pdev, vmci_dev->msix_entries, VMCI_MAX_INTRS); 386 result = pci_enable_msix_exact(pdev,
387 vmci_dev->msix_entries, VMCI_MAX_INTRS);
387 if (result == 0) 388 if (result == 0)
388 vmci_dev->exclusive_vectors = true; 389 vmci_dev->exclusive_vectors = true;
389 else if (result > 0) 390 else if (result == -ENOSPC)
390 result = pci_enable_msix(pdev, vmci_dev->msix_entries, 1); 391 result = pci_enable_msix_exact(pdev, vmci_dev->msix_entries, 1);
391 392
392 return result; 393 return result;
393} 394}