aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/misc
diff options
context:
space:
mode:
authorTomas Winkler <tomas.winkler@intel.com>2013-09-16 16:44:47 -0400
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2013-10-03 19:01:16 -0400
commit22f96a0eb6c62b570621d77dacbf2589a6de2997 (patch)
treec81ff5bc3b2899721514fdbccc7d5c9bc22b504b /drivers/misc
parente036cc5727eb6d471442d2a9218990aa11215400 (diff)
mei: revamp open handler counts
Make open counter to be incremented and decremented from mei_cl_link and mei_cl_unlik function respectively Nfc was assuming symmetric linking API and thus open handler count was never decreased. This patch fixes that. We need to add separate open hander count for amthif which is handled out of link/unlink functions and doesn't break the symmetric API. Last we do not waste clients slots if amthif or wd are not present in the device. we don't need to allocates slots ahead it is all covered by link/unlink before the devices is responding to user space connection and thus not racing on allocation Signed-off-by: Tomas Winkler <tomas.winkler@intel.com> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/misc')
-rw-r--r--drivers/misc/mei/amthif.c5
-rw-r--r--drivers/misc/mei/client.c19
-rw-r--r--drivers/misc/mei/init.c5
-rw-r--r--drivers/misc/mei/main.c6
-rw-r--r--drivers/misc/mei/mei_dev.h1
5 files changed, 20 insertions, 16 deletions
diff --git a/drivers/misc/mei/amthif.c b/drivers/misc/mei/amthif.c
index 226c3f3cd3e8..4f259d411a2c 100644
--- a/drivers/misc/mei/amthif.c
+++ b/drivers/misc/mei/amthif.c
@@ -58,6 +58,7 @@ void mei_amthif_reset_params(struct mei_device *dev)
58 dev->iamthif_state = MEI_IAMTHIF_IDLE; 58 dev->iamthif_state = MEI_IAMTHIF_IDLE;
59 dev->iamthif_timer = 0; 59 dev->iamthif_timer = 0;
60 dev->iamthif_stall_timer = 0; 60 dev->iamthif_stall_timer = 0;
61 dev->iamthif_open_count = 0;
61} 62}
62 63
63/** 64/**
@@ -731,8 +732,8 @@ static bool mei_clear_lists(struct mei_device *dev, struct file *file)
731*/ 732*/
732int mei_amthif_release(struct mei_device *dev, struct file *file) 733int mei_amthif_release(struct mei_device *dev, struct file *file)
733{ 734{
734 if (dev->open_handle_count > 0) 735 if (dev->iamthif_open_count > 0)
735 dev->open_handle_count--; 736 dev->iamthif_open_count--;
736 737
737 if (dev->iamthif_file_object == file && 738 if (dev->iamthif_file_object == file &&
738 dev->iamthif_state != MEI_IAMTHIF_IDLE) { 739 dev->iamthif_state != MEI_IAMTHIF_IDLE) {
diff --git a/drivers/misc/mei/client.c b/drivers/misc/mei/client.c
index 88770e040dd1..a48c0e71e69d 100644
--- a/drivers/misc/mei/client.c
+++ b/drivers/misc/mei/client.c
@@ -275,6 +275,7 @@ struct mei_cl_cb *mei_cl_find_read_cb(struct mei_cl *cl)
275int mei_cl_link(struct mei_cl *cl, int id) 275int mei_cl_link(struct mei_cl *cl, int id)
276{ 276{
277 struct mei_device *dev; 277 struct mei_device *dev;
278 long open_handle_count;
278 279
279 if (WARN_ON(!cl || !cl->dev)) 280 if (WARN_ON(!cl || !cl->dev))
280 return -EINVAL; 281 return -EINVAL;
@@ -291,7 +292,8 @@ int mei_cl_link(struct mei_cl *cl, int id)
291 return -EMFILE; 292 return -EMFILE;
292 } 293 }
293 294
294 if (dev->open_handle_count >= MEI_MAX_OPEN_HANDLE_COUNT) { 295 open_handle_count = dev->open_handle_count + dev->iamthif_open_count;
296 if (open_handle_count >= MEI_MAX_OPEN_HANDLE_COUNT) {
295 dev_err(&dev->pdev->dev, "open_handle_count exceded %d", 297 dev_err(&dev->pdev->dev, "open_handle_count exceded %d",
296 MEI_MAX_OPEN_HANDLE_COUNT); 298 MEI_MAX_OPEN_HANDLE_COUNT);
297 return -EMFILE; 299 return -EMFILE;
@@ -337,6 +339,17 @@ int mei_cl_unlink(struct mei_cl *cl)
337 339
338 cl_dbg(dev, cl, "unlink client"); 340 cl_dbg(dev, cl, "unlink client");
339 341
342 if (dev->open_handle_count > 0)
343 dev->open_handle_count--;
344
345 /* never clear the 0 bit */
346 if (cl->host_client_id)
347 clear_bit(cl->host_client_id, dev->host_clients_map);
348
349 list_del_init(&cl->link);
350
351 cl->state = MEI_FILE_INITIALIZING;
352
340 list_del_init(&cl->link); 353 list_del_init(&cl->link);
341 354
342 return 0; 355 return 0;
@@ -358,10 +371,8 @@ void mei_host_client_init(struct work_struct *work)
358 /* 371 /*
359 * Reserving the first three client IDs 372 * Reserving the first three client IDs
360 * 0: Reserved for MEI Bus Message communications 373 * 0: Reserved for MEI Bus Message communications
361 * 1: Reserved for Watchdog
362 * 2: Reserved for AMTHI
363 */ 374 */
364 bitmap_set(dev->host_clients_map, 0, 3); 375 bitmap_set(dev->host_clients_map, 0, 1);
365 376
366 for (i = 0; i < dev->me_clients_num; i++) { 377 for (i = 0; i < dev->me_clients_num; i++) {
367 client_props = &dev->me_clients[i].props; 378 client_props = &dev->me_clients[i].props;
diff --git a/drivers/misc/mei/init.c b/drivers/misc/mei/init.c
index 6197018e2f16..a7d29a7dcab2 100644
--- a/drivers/misc/mei/init.c
+++ b/drivers/misc/mei/init.c
@@ -165,12 +165,7 @@ void mei_reset(struct mei_device *dev, int interrupts_enabled)
165 /* remove entry if already in list */ 165 /* remove entry if already in list */
166 dev_dbg(&dev->pdev->dev, "remove iamthif and wd from the file list.\n"); 166 dev_dbg(&dev->pdev->dev, "remove iamthif and wd from the file list.\n");
167 mei_cl_unlink(&dev->wd_cl); 167 mei_cl_unlink(&dev->wd_cl);
168 if (dev->open_handle_count > 0)
169 dev->open_handle_count--;
170 mei_cl_unlink(&dev->iamthif_cl); 168 mei_cl_unlink(&dev->iamthif_cl);
171 if (dev->open_handle_count > 0)
172 dev->open_handle_count--;
173
174 mei_amthif_reset_params(dev); 169 mei_amthif_reset_params(dev);
175 memset(&dev->wr_ext_msg, 0, sizeof(dev->wr_ext_msg)); 170 memset(&dev->wr_ext_msg, 0, sizeof(dev->wr_ext_msg));
176 } 171 }
diff --git a/drivers/misc/mei/main.c b/drivers/misc/mei/main.c
index 87ab5ca1d633..9661a812f550 100644
--- a/drivers/misc/mei/main.c
+++ b/drivers/misc/mei/main.c
@@ -141,10 +141,6 @@ static int mei_release(struct inode *inode, struct file *file)
141 cl->host_client_id, 141 cl->host_client_id,
142 cl->me_client_id); 142 cl->me_client_id);
143 143
144 if (dev->open_handle_count > 0) {
145 clear_bit(cl->host_client_id, dev->host_clients_map);
146 dev->open_handle_count--;
147 }
148 mei_cl_unlink(cl); 144 mei_cl_unlink(cl);
149 145
150 146
@@ -498,11 +494,11 @@ static int mei_ioctl_connect_client(struct file *file,
498 rets = -ENODEV; 494 rets = -ENODEV;
499 goto end; 495 goto end;
500 } 496 }
501 clear_bit(cl->host_client_id, dev->host_clients_map);
502 mei_cl_unlink(cl); 497 mei_cl_unlink(cl);
503 498
504 kfree(cl); 499 kfree(cl);
505 cl = NULL; 500 cl = NULL;
501 dev->iamthif_open_count++;
506 file->private_data = &dev->iamthif_cl; 502 file->private_data = &dev->iamthif_cl;
507 503
508 client = &data->out_client_properties; 504 client = &data->out_client_properties;
diff --git a/drivers/misc/mei/mei_dev.h b/drivers/misc/mei/mei_dev.h
index 456b322013e2..406f68e05b4e 100644
--- a/drivers/misc/mei/mei_dev.h
+++ b/drivers/misc/mei/mei_dev.h
@@ -414,6 +414,7 @@ struct mei_device {
414 struct file *iamthif_file_object; 414 struct file *iamthif_file_object;
415 struct mei_cl iamthif_cl; 415 struct mei_cl iamthif_cl;
416 struct mei_cl_cb *iamthif_current_cb; 416 struct mei_cl_cb *iamthif_current_cb;
417 long iamthif_open_count;
417 int iamthif_mtu; 418 int iamthif_mtu;
418 unsigned long iamthif_timer; 419 unsigned long iamthif_timer;
419 u32 iamthif_stall_timer; 420 u32 iamthif_stall_timer;