19a19fea43616066561e221359596ce532e631395Patrick Mochel/*
29a19fea43616066561e221359596ce532e631395Patrick Mochel *	klist.h - Some generic list helpers, extending struct list_head a bit.
39a19fea43616066561e221359596ce532e631395Patrick Mochel *
49a19fea43616066561e221359596ce532e631395Patrick Mochel *	Implementations are found in lib/klist.c
59a19fea43616066561e221359596ce532e631395Patrick Mochel *
69a19fea43616066561e221359596ce532e631395Patrick Mochel *
79a19fea43616066561e221359596ce532e631395Patrick Mochel *	Copyright (C) 2005 Patrick Mochel
89a19fea43616066561e221359596ce532e631395Patrick Mochel *
99a19fea43616066561e221359596ce532e631395Patrick Mochel *	This file is rleased under the GPL v2.
109a19fea43616066561e221359596ce532e631395Patrick Mochel */
119a19fea43616066561e221359596ce532e631395Patrick Mochel
12d856f1e337782326c638c70c0b4df2b909350decJames Bottomley#ifndef _LINUX_KLIST_H
13d856f1e337782326c638c70c0b4df2b909350decJames Bottomley#define _LINUX_KLIST_H
14d856f1e337782326c638c70c0b4df2b909350decJames Bottomley
159a19fea43616066561e221359596ce532e631395Patrick Mochel#include <linux/spinlock.h>
169a19fea43616066561e221359596ce532e631395Patrick Mochel#include <linux/kref.h>
179a19fea43616066561e221359596ce532e631395Patrick Mochel#include <linux/list.h>
189a19fea43616066561e221359596ce532e631395Patrick Mochel
1934bb61f9ddabd7a7f909cbfb05592eb775f6662aJames Bottomleystruct klist_node;
209a19fea43616066561e221359596ce532e631395Patrick Mochelstruct klist {
219a19fea43616066561e221359596ce532e631395Patrick Mochel	spinlock_t		k_lock;
229a19fea43616066561e221359596ce532e631395Patrick Mochel	struct list_head	k_list;
2334bb61f9ddabd7a7f909cbfb05592eb775f6662aJames Bottomley	void			(*get)(struct klist_node *);
2434bb61f9ddabd7a7f909cbfb05592eb775f6662aJames Bottomley	void			(*put)(struct klist_node *);
25795abaf1e4e188c4171e3cd3dbb11a9fcacaf505David Miller} __attribute__ ((aligned (sizeof(void *))));
269a19fea43616066561e221359596ce532e631395Patrick Mochel
271da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo#define KLIST_INIT(_name, _get, _put)					\
281da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo	{ .k_lock	= __SPIN_LOCK_UNLOCKED(_name.k_lock),		\
291da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo	  .k_list	= LIST_HEAD_INIT(_name.k_list),			\
301da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo	  .get		= _get,						\
311da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo	  .put		= _put, }
321da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo
331da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo#define DEFINE_KLIST(_name, _get, _put)					\
341da43e4a9ee942c9c967dbe8839476571df0c3edTejun Heo	struct klist _name = KLIST_INIT(_name, _get, _put)
359a19fea43616066561e221359596ce532e631395Patrick Mochel
36c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_init(struct klist *k, void (*get)(struct klist_node *),
3734bb61f9ddabd7a7f909cbfb05592eb775f6662aJames Bottomley		       void (*put)(struct klist_node *));
389a19fea43616066561e221359596ce532e631395Patrick Mochel
399a19fea43616066561e221359596ce532e631395Patrick Mochelstruct klist_node {
40a1ed5b0cffe4b16a93a6a3390e8cee0fbef94f86Tejun Heo	void			*n_klist;	/* never access directly */
419a19fea43616066561e221359596ce532e631395Patrick Mochel	struct list_head	n_node;
429a19fea43616066561e221359596ce532e631395Patrick Mochel	struct kref		n_ref;
439a19fea43616066561e221359596ce532e631395Patrick Mochel};
449a19fea43616066561e221359596ce532e631395Patrick Mochel
45c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_add_tail(struct klist_node *n, struct klist *k);
46c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_add_head(struct klist_node *n, struct klist *k);
4793dd40013f4f7f4b18d19d0d77855f025bcc57c3Tejun Heoextern void klist_add_after(struct klist_node *n, struct klist_node *pos);
4893dd40013f4f7f4b18d19d0d77855f025bcc57c3Tejun Heoextern void klist_add_before(struct klist_node *n, struct klist_node *pos);
499a19fea43616066561e221359596ce532e631395Patrick Mochel
50c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_del(struct klist_node *n);
51c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_remove(struct klist_node *n);
529a19fea43616066561e221359596ce532e631395Patrick Mochel
53c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern int klist_node_attached(struct klist_node *n);
548b0c250be489dcbf1a3a33bb4ec4c7f33735a365Patrick Mochel
559a19fea43616066561e221359596ce532e631395Patrick Mochel
569a19fea43616066561e221359596ce532e631395Patrick Mochelstruct klist_iter {
57c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartman	struct klist		*i_klist;
58c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartman	struct klist_node	*i_cur;
599a19fea43616066561e221359596ce532e631395Patrick Mochel};
609a19fea43616066561e221359596ce532e631395Patrick Mochel
619a19fea43616066561e221359596ce532e631395Patrick Mochel
62c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_iter_init(struct klist *k, struct klist_iter *i);
63c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_iter_init_node(struct klist *k, struct klist_iter *i,
64c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartman				 struct klist_node *n);
65c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern void klist_iter_exit(struct klist_iter *i);
66c3bb7fadaf52de3637b834002dac27f6250b4b49Greg Kroah-Hartmanextern struct klist_node *klist_next(struct klist_iter *i);
679a19fea43616066561e221359596ce532e631395Patrick Mochel
68d856f1e337782326c638c70c0b4df2b909350decJames Bottomley#endif
69