diff options
author | Christoph Hellwig <hch@lst.de> | 2007-08-14 19:17:15 -0400 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@suse.de> | 2007-10-12 18:03:15 -0400 |
commit | fa007d8bebc5d812a445c48664b5bcad81f1351c (patch) | |
tree | 84b65bf601a5bd37511a738e8f2eed0136417f90 /drivers | |
parent | 2d100fe8f6ebe5e4335b26f3749bb0b7f706d1f9 (diff) |
pci: hotplug: cpqphp: convert to kthread infrastructure
Signed-off-by: Christoph Hellwig <hch@lst.de>
Signed-off-by: Kristen Carlson Accardi <kristen.c.accardi@intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/pci/hotplug/cpqphp_ctrl.c | 69 |
1 files changed, 21 insertions, 48 deletions
diff --git a/drivers/pci/hotplug/cpqphp_ctrl.c b/drivers/pci/hotplug/cpqphp_ctrl.c index dcafa2aaef8a..3ef0a4875a62 100644 --- a/drivers/pci/hotplug/cpqphp_ctrl.c +++ b/drivers/pci/hotplug/cpqphp_ctrl.c | |||
@@ -37,6 +37,7 @@ | |||
37 | #include <linux/smp_lock.h> | 37 | #include <linux/smp_lock.h> |
38 | #include <linux/pci.h> | 38 | #include <linux/pci.h> |
39 | #include <linux/pci_hotplug.h> | 39 | #include <linux/pci_hotplug.h> |
40 | #include <linux/kthread.h> | ||
40 | #include "cpqphp.h" | 41 | #include "cpqphp.h" |
41 | 42 | ||
42 | static u32 configure_new_device(struct controller* ctrl, struct pci_func *func, | 43 | static u32 configure_new_device(struct controller* ctrl, struct pci_func *func, |
@@ -45,34 +46,20 @@ static int configure_new_function(struct controller* ctrl, struct pci_func *func | |||
45 | u8 behind_bridge, struct resource_lists *resources); | 46 | u8 behind_bridge, struct resource_lists *resources); |
46 | static void interrupt_event_handler(struct controller *ctrl); | 47 | static void interrupt_event_handler(struct controller *ctrl); |
47 | 48 | ||
48 | static struct semaphore event_semaphore; /* mutex for process loop (up if something to process) */ | ||
49 | static struct semaphore event_exit; /* guard ensure thread has exited before calling it quits */ | ||
50 | static int event_finished; | ||
51 | static unsigned long pushbutton_pending; /* = 0 */ | ||
52 | 49 | ||
53 | /* things needed for the long_delay function */ | 50 | static struct task_struct *cpqhp_event_thread; |
54 | static struct semaphore delay_sem; | 51 | static unsigned long pushbutton_pending; /* = 0 */ |
55 | static wait_queue_head_t delay_wait; | ||
56 | 52 | ||
57 | /* delay is in jiffies to wait for */ | 53 | /* delay is in jiffies to wait for */ |
58 | static void long_delay(int delay) | 54 | static void long_delay(int delay) |
59 | { | 55 | { |
60 | DECLARE_WAITQUEUE(wait, current); | 56 | /* |
61 | 57 | * XXX(hch): if someone is bored please convert all callers | |
62 | /* only allow 1 customer into the delay queue at once | 58 | * to call msleep_interruptible directly. They really want |
63 | * yes this makes some people wait even longer, but who really cares? | 59 | * to specify timeouts in natural units and spend a lot of |
64 | * this is for _huge_ delays to make the hardware happy as the | 60 | * effort converting them to jiffies.. |
65 | * signals bounce around | ||
66 | */ | 61 | */ |
67 | down (&delay_sem); | ||
68 | |||
69 | init_waitqueue_head(&delay_wait); | ||
70 | |||
71 | add_wait_queue(&delay_wait, &wait); | ||
72 | msleep_interruptible(jiffies_to_msecs(delay)); | 62 | msleep_interruptible(jiffies_to_msecs(delay)); |
73 | remove_wait_queue(&delay_wait, &wait); | ||
74 | |||
75 | up(&delay_sem); | ||
76 | } | 63 | } |
77 | 64 | ||
78 | 65 | ||
@@ -955,8 +942,8 @@ irqreturn_t cpqhp_ctrl_intr(int IRQ, void *data) | |||
955 | } | 942 | } |
956 | 943 | ||
957 | if (schedule_flag) { | 944 | if (schedule_flag) { |
958 | up(&event_semaphore); | 945 | wake_up_process(cpqhp_event_thread); |
959 | dbg("Signal event_semaphore\n"); | 946 | dbg("Waking even thread"); |
960 | } | 947 | } |
961 | return IRQ_HANDLED; | 948 | return IRQ_HANDLED; |
962 | } | 949 | } |
@@ -1735,7 +1722,7 @@ static u32 remove_board(struct pci_func * func, u32 replace_flag, struct control | |||
1735 | static void pushbutton_helper_thread(unsigned long data) | 1722 | static void pushbutton_helper_thread(unsigned long data) |
1736 | { | 1723 | { |
1737 | pushbutton_pending = data; | 1724 | pushbutton_pending = data; |
1738 | up(&event_semaphore); | 1725 | wake_up_process(cpqhp_event_thread); |
1739 | } | 1726 | } |
1740 | 1727 | ||
1741 | 1728 | ||
@@ -1744,13 +1731,13 @@ static int event_thread(void* data) | |||
1744 | { | 1731 | { |
1745 | struct controller *ctrl; | 1732 | struct controller *ctrl; |
1746 | 1733 | ||
1747 | daemonize("phpd_event"); | ||
1748 | |||
1749 | while (1) { | 1734 | while (1) { |
1750 | dbg("!!!!event_thread sleeping\n"); | 1735 | dbg("!!!!event_thread sleeping\n"); |
1751 | down_interruptible (&event_semaphore); | 1736 | set_current_state(TASK_INTERRUPTIBLE); |
1752 | dbg("event_thread woken finished = %d\n", event_finished); | 1737 | schedule(); |
1753 | if (event_finished) break; | 1738 | |
1739 | if (kthread_should_stop()) | ||
1740 | break; | ||
1754 | /* Do stuff here */ | 1741 | /* Do stuff here */ |
1755 | if (pushbutton_pending) | 1742 | if (pushbutton_pending) |
1756 | cpqhp_pushbutton_thread(pushbutton_pending); | 1743 | cpqhp_pushbutton_thread(pushbutton_pending); |
@@ -1759,38 +1746,24 @@ static int event_thread(void* data) | |||
1759 | interrupt_event_handler(ctrl); | 1746 | interrupt_event_handler(ctrl); |
1760 | } | 1747 | } |
1761 | dbg("event_thread signals exit\n"); | 1748 | dbg("event_thread signals exit\n"); |
1762 | up(&event_exit); | ||
1763 | return 0; | 1749 | return 0; |
1764 | } | 1750 | } |
1765 | 1751 | ||
1766 | |||
1767 | int cpqhp_event_start_thread(void) | 1752 | int cpqhp_event_start_thread(void) |
1768 | { | 1753 | { |
1769 | int pid; | 1754 | cpqhp_event_thread = kthread_run(event_thread, NULL, "phpd_event"); |
1770 | 1755 | if (IS_ERR(cpqhp_event_thread)) { | |
1771 | /* initialize our semaphores */ | ||
1772 | init_MUTEX(&delay_sem); | ||
1773 | init_MUTEX_LOCKED(&event_semaphore); | ||
1774 | init_MUTEX_LOCKED(&event_exit); | ||
1775 | event_finished=0; | ||
1776 | |||
1777 | pid = kernel_thread(event_thread, NULL, 0); | ||
1778 | if (pid < 0) { | ||
1779 | err ("Can't start up our event thread\n"); | 1756 | err ("Can't start up our event thread\n"); |
1780 | return -1; | 1757 | return PTR_ERR(cpqhp_event_thread); |
1781 | } | 1758 | } |
1782 | dbg("Our event thread pid = %d\n", pid); | 1759 | |
1783 | return 0; | 1760 | return 0; |
1784 | } | 1761 | } |
1785 | 1762 | ||
1786 | 1763 | ||
1787 | void cpqhp_event_stop_thread(void) | 1764 | void cpqhp_event_stop_thread(void) |
1788 | { | 1765 | { |
1789 | event_finished = 1; | 1766 | kthread_stop(cpqhp_event_thread); |
1790 | dbg("event_thread finish command given\n"); | ||
1791 | up(&event_semaphore); | ||
1792 | dbg("wait for event_thread to exit\n"); | ||
1793 | down(&event_exit); | ||
1794 | } | 1767 | } |
1795 | 1768 | ||
1796 | 1769 | ||