コード例 #1
0
static int kthread(void *_create)
{
	struct kthread_create_info *create = _create;
	int (*threadfn)(void *data);
	void *data;
	int ret = -EINTR;

	/* Copy data: it's on kthread's stack */
	threadfn = create->threadfn;
	data = create->data;

	/* OK, tell user we're spawned, wait for stop or wakeup */
	__set_current_state(TASK_UNINTERRUPTIBLE);
	complete(&create->started);
	schedule();

	if (!kthread_should_stop())
		ret = threadfn(data);

	/* It might have exited on its own, w/o kthread_stop.  Check. */
	if (kthread_should_stop()) {
		kthread_stop_info.err = ret;
		complete(&kthread_stop_info.done);
	}
	return 0;
}
コード例 #2
0
ファイル: kthread.c プロジェクト: 454053205/linux
static int kthread(void *_create)
{
	/* Copy data: it's on kthread's stack */
	struct kthread_create_info *create = _create;
	int (*threadfn)(void *data) = create->threadfn;
	void *data = create->data;
	struct kthread self;
	int ret;

	self.should_stop = 0;
	self.data = data;
	init_completion(&self.exited);
	current->vfork_done = &self.exited;

	/* OK, tell user we're spawned, wait for stop or wakeup */
	__set_current_state(TASK_UNINTERRUPTIBLE);
	create->result = current;
	complete(&create->done);
	schedule();

	ret = -EINTR;
	if (!self.should_stop)
		ret = threadfn(data);

	/* we can't just return, we must preserve "self" on stack */
	do_exit(ret);
}
コード例 #3
0
static int kthread(void *_create)
{
	/*                                    */
	struct kthread_create_info *create = _create;
	int (*threadfn)(void *data) = create->threadfn;
	void *data = create->data;
	struct kthread self;
	int ret;

	self.should_stop = 0;
	self.data = data;
	init_completion(&self.exited);
	current->vfork_done = &self.exited;

	/*                                                      */
	__set_current_state(TASK_UNINTERRUPTIBLE);
	create->result = current;
	complete(&create->done);
	schedule();

	ret = -EINTR;
	if (!self.should_stop)
		ret = threadfn(data);

	/*                                                        */
	do_exit(ret);
}
コード例 #4
0
ファイル: kthread.c プロジェクト: FrozenCow/FIRE-ICE
static int kthread(void *_create)
{
	/* Copy data: it's on kthread's stack */
	struct kthread_create_info *create = _create;
	int (*threadfn)(void *data) = create->threadfn;
	void *data = create->data;
	struct kthread self;
	int ret;

	self.flags = 0;
	self.data = data;
	init_completion(&self.exited);
	init_completion(&self.parked);
	current->vfork_done = &self.exited;

	/* OK, tell user we're spawned, wait for stop or wakeup */
	__set_current_state(TASK_UNINTERRUPTIBLE);
	create->result = current;

	/*
	 * Disable preemption so we enter TASK_UNINTERRUPTIBLE after
	 * complete() instead of possibly being preempted. This speeds
	 * up clients that do a kthread_bind() directly after
	 * creation.
	 */
	preempt_disable();
	complete(&create->done);
	preempt_enable_no_resched();

	schedule();

	ret = -EINTR;

	if (!test_bit(KTHREAD_SHOULD_STOP, &self.flags)) {
		__kthread_parkme(&self);
		ret = threadfn(data);
	}
	/* we can't just return, we must preserve "self" on stack */
	do_exit(ret);
}
コード例 #5
0
ファイル: kthread.c プロジェクト: OpenHMR/Open-HMR600
static int kthread(void *_create)
{
	struct kthread_create_info *create = _create;
	int (*threadfn)(void *data);
	void *data;
	sigset_t blocked;
	int ret = -EINTR;

	kthread_exit_files();

	/* Copy data: it's on keventd's stack */
	threadfn = create->threadfn;
	data = create->data;

	/* Block and flush all signals (in case we're not from keventd). */
	sigfillset(&blocked);
	sigprocmask(SIG_BLOCK, &blocked, NULL);
	flush_signals(current);

	/* By default we can run anywhere, unlike keventd. */
	set_cpus_allowed(current, CPU_MASK_ALL);

	/* OK, tell user we're spawned, wait for stop or wakeup */
	__set_current_state(TASK_INTERRUPTIBLE);
	complete(&create->started);
	schedule();

	if (!kthread_should_stop())
		ret = threadfn(data);

	/* It might have exited on its own, w/o kthread_stop.  Check. */
	if (kthread_should_stop()) {
		kthread_stop_info.err = ret;
		complete(&kthread_stop_info.done);
	}
	return 0;
}
コード例 #6
0
static int kthread(void *_create)
{
	/* Copy data: it's on kthread's stack */
	struct kthread_create_info *create = _create;
	int (*threadfn)(void *data) = create->threadfn;
	void *data = create->data;
	struct completion *done;
	struct kthread self;
	int ret;

	self.flags = 0;
	self.data = data;
	init_completion(&self.exited);
	init_completion(&self.parked);
	current->vfork_done = &self.exited;

	/* If user was SIGKILLed, I release the structure. */
	done = xchg(&create->done, NULL);
	if (!done) {
		kfree(create);
		do_exit(-EINTR);
	}
	/* OK, tell user we're spawned, wait for stop or wakeup */
	__set_current_state(TASK_UNINTERRUPTIBLE);
	create->result = current;
	complete(done);
	schedule();

	ret = -EINTR;

	if (!test_bit(KTHREAD_SHOULD_STOP, &self.flags)) {
		__kthread_parkme(&self);
		ret = threadfn(data);
	}
	/* we can't just return, we must preserve "self" on stack */
	do_exit(ret);
}
コード例 #7
0
static int
kthread(void *_create)
{
    struct kthread_create_info *create = _create;
    int (*threadfn)(void *data);
    void *data;

//    printk("kthread: create %p\n", create);

    threadfn = create->threadfn;
    data = create->data;
//    printk("kthread: threadfn %p data %p\n", threadfn, data);

    lock_kernel();
    daemonize();
    reparent_to_init();
    spin_lock_irq(&current->sigmask_lock);
    sigfillset(&current->blocked);
    recalc_sigpending(current);
    spin_unlock_irq(&current->sigmask_lock);
    unlock_kernel();

    set_current_state(TASK_INTERRUPTIBLE);
    complete(&create->started);

//    printk("kthread: about to call thread function\n");

    if (!kthread_should_stop())
	threadfn(data);

//    printk("kthread: thread function done\n");

    if (kthread_should_stop())
	complete(&kthread_stop_complete);

    return 0;
}