sprintf(current->comm, "liod");
unlock_kernel();
- /* declear we are ready */
- spin_lock(&iod->io_lock);
- iod->io_flag |= LIOD_FLAG_ALIVE;
+ /* declare we are ready */
+ set_bit(LIOD_FLAG_ALIVE, &iod->io_flag);
wake_up(&iod->io_waitq);
- spin_unlock(&iod->io_lock);
CDEBUG(D_NET, "liod(%d) started\n", current->pid);
while (1) {
int t;
/* check the stop command */
- if (iod->io_flag & LIOD_FLAG_STOP)
+ if (test_bit(LIOD_FLAG_STOP, &iod->io_flag))
break;
t = interruptible_sleep_on_timeout(&iod->io_sleepq,
(t ? "wakeup" : "timeout"));
}
- spin_lock(&iod->io_lock);
- iod->io_flag &= ~LIOD_FLAG_ALIVE;
- iod->io_flag |= LIOD_FLAG_STOPPED;
+ clear_bit(LIOD_FLAG_ALIVE, &iod->io_flag);
wake_up(&iod->io_waitq);
- spin_unlock(&iod->io_lock);
CDEBUG(D_NET, "liod(%d) exit\n", current->pid);
RETURN(0);
int liod_start(struct ll_io_daemon *iod)
{
- DECLARE_WAITQUEUE(queue, current);
int rc;
/* initialize */
iod->io_flag = 0;
- spin_lock_init(&iod->io_lock);
init_waitqueue_head(&iod->io_sleepq);
init_waitqueue_head(&iod->io_waitq);
- spin_lock(&iod->io_lock);
-
rc = kernel_thread(liod_main, (void *) iod,
CLONE_VM | CLONE_FS | CLONE_FILES);
if (rc < 0) {
CERROR("fail to start liod, error %d\n", rc);
- spin_unlock(&iod->io_lock);
return rc;
}
- set_current_state(TASK_UNINTERRUPTIBLE);
- add_wait_queue(&iod->io_waitq, &queue);
- spin_unlock(&iod->io_lock);
-
/* wait liod start */
- schedule();
-
- set_current_state(TASK_RUNNING);
- remove_wait_queue(&iod->io_waitq, &queue);
+ wait_event(iod->io_waitq, test_bit(LIOD_FLAG_ALIVE, &iod->io_flag));
- if (iod->io_flag & LIOD_FLAG_ALIVE)
- return 0;
- else
- return -ENOMEM;
+ return 0;
}
void liod_wakeup(struct ll_io_daemon *iod)
void liod_stop(struct ll_io_daemon *iod)
{
- DECLARE_WAITQUEUE(queue, current);
-
- spin_lock(&iod->io_lock);
+ if (!test_bit(LIOD_FLAG_ALIVE, &iod->io_flag)) {
+ CERROR("liod died unexpectedly!\n");
+ return;
+ }
/* send the kill command */
- iod->io_flag |= LIOD_FLAG_STOP;
+ set_bit(LIOD_FLAG_STOP, &iod->io_flag);
/* if wakeup daemon */
wake_up(&iod->io_sleepq);
- /* wait daemon's exit */
- set_current_state(TASK_UNINTERRUPTIBLE);
- add_wait_queue(&iod->io_waitq, &queue);
- spin_unlock(&iod->io_lock);
-
- schedule();
- /* must woken up by liod */
+ /* wait liod exit */
+ wait_event(iod->io_waitq, !test_bit(LIOD_FLAG_ALIVE, &iod->io_flag));
return;
}