<br><br><div class="gmail_quote">On Tue, Mar 19, 2013 at 3:53 PM, Dave Hylands <span dir="ltr">&lt;<a href="mailto:dhylands@gmail.com" target="_blank">dhylands@gmail.com</a>&gt;</span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">

<div dir="ltr"><div><div><div><div><div><div><div><div>Hi Arlie,<div><div class="h5"><br><br><br>On Tue, Mar 19, 2013 at 8:34 AM, Arlie Stephens &lt;<a href="mailto:arlie@worldash.org" target="_blank">arlie@worldash.org</a>&gt; wrote:<br>

&gt;<br>&gt; Hi Folks,<br>
&gt;<br>&gt; I&#39;m trying to understand the linux way of doing things, so as to write<br>&gt; code which will be easier for experienced linux kernel people to<br>&gt; understand. Yesterday I wound up in a 3 engineer discussion about<br>


&gt; something conceptually simple, that just didn&#39;t want to be done with<br>&gt; the tools at hand; what&#39;s worse, the only ways I could see to do it<br>&gt; were (a) do my own linked lists or (b) write some routines that relied<br>


&gt; kind of heavily on the never-mentioned-in-documentation details of<br>&gt; linux/list.h   I&#39;ll probably go with option (b), as that seems less<br>&gt; insane, but I thought I might as well ask here as well.<br>&gt;<br>


&gt; Here&#39;s the problem. I have a collection of resources. Call them<br>&gt; A,B,C,D but note that resources get added at run time, so I don&#39;t know<br>&gt; how many to expect. I want to go through them in a round robin<br>


&gt; fashion, but not all at once. On the first request, I use A. On a<br>&gt; later request I use B, etc. This seems to me to map naturally to a<br>&gt; circular linked list, with a &quot;cursor&quot; - a pointer of some kind to the<br>


&gt; next one I want to use. To make my specific situation more<br>&gt; interesting, I actually have multiple cursors - that may or may not<br>&gt; happen to point to the same node at any given time, but usually will<br>

&gt; not.<br>
&gt;<br>&gt; This is where I wish I could draw pictures in ascii emails ;-)<br>&gt; Perhaps the following will come through halfway sanely:<br>&gt;<br>&gt; C1 C2 C3<br>&gt; V /    V<br>&gt; A&lt;-&gt;B&lt;-&gt;C-&lt;-&gt;D<br>


&gt; ^------------^<br>&gt;<br>&gt; list.h implements a circular linked list - see for example<br>&gt; <a href="http://www.makelinux.net/books/lkd2/app01lev1sec2" target="_blank">http://www.makelinux.net/books/lkd2/app01lev1sec2</a> - so I thought this<br>


&gt; would be easy and natural. But then I discovered there was no such<br>&gt; thing as a list_next(). OK, I can write it - Something like:<br>&gt; cursor-&gt;resource = list_entry(cursor-&gt;resource-&gt;link.next, struct resource, link);<br>


&gt; But the fact there was no interface made me ask advice from colleagues.<br>&gt; And that&#39;s when the debate erupted.<br>&gt;<br>&gt; First of all, it&#39;s unclear whether that would even work. If the list<br>&gt; is initialized following the standard pardigm, there may be a &quot;head&quot;<br>


&gt; element embedded in the list, which all the existing interfaces know<br>&gt; to ignore. I.e.<br><br></div></div></div>So the real secret is that it&#39;s a circular list with a dummy node. This dummy node just has head/tail pointers and nothing else.<br>


<br></div>So when you&#39;re advancing through the list, instead of testing list-&gt;next for NULL you check to see if list-&gt;next is equal to the list head.<br><br></div>So if you want your cursor object to be self-contained, then it should include both a list head and a list current.<br>


<br></div>If you want your cursor to be generic, then it should probably look something like:<br><br></div>struct list_cursor {<br></div>    struct list_head *list;<br></div>    struct list_head *curr;<br>};<br><br></div>


<div>I think you&#39;ll find that the cursor operations make a lot more sense if you keep the cursor generic and try not to include the type information about the list node.<br></div><div><br></div><div>To initialize the cursor:<br>


<br></div><div>cursor-&gt;list = somelist<br></div><div>cursor-&gt;curr = somelist<br><br></div><div>To advance to the first node (remember the list has a dummy head node)<br><br></div><div>cursor-&gt;curr = cursor-&gt;curr-&gt;next<br>


<br></div><div>If the result is == cursor-&gt;head then there aren&#39;t any nodes except for the dummy node (i.e. list is empty)<br><br></div><div>To get at the actual entry, use list_entry as per usual.<br><br></div><div>


I see RPDay has posted the link to his little tutorial, and I was going to do the same, but I didn&#39;t have it saved anywhere. I highly recommend reading through that.<br></div><div><br></div></div></blockquote><div>Besides the Robert&#39;s link you can also have a look at FAQ on kernel newbies<br>

<a href="http://kernelnewbies.org/FAQ/LinkedLists">http://kernelnewbies.org/FAQ/LinkedLists</a><br><br>LDD also covers it<br><a href="http://www.makelinux.net/ldd3/chp-11-sect-5">http://www.makelinux.net/ldd3/chp-11-sect-5</a><br>

<br>There is a good explanation of kernel linked list in Robert Love&#39;s book as well.<br><br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex"><div dir="ltr"><div>

</div><div><div><div><div><div><div>
<div><div>--<br>Dave Hylands<br>Shuswap, BC, Canada<br><a href="http://www.davehylands.com" target="_blank">http://www.davehylands.com</a></div></div></div></div></div></div></div></div></div>
<br>_______________________________________________<br>
Kernelnewbies mailing list<br>
<a href="mailto:Kernelnewbies@kernelnewbies.org">Kernelnewbies@kernelnewbies.org</a><br>
<a href="http://lists.kernelnewbies.org/mailman/listinfo/kernelnewbies" target="_blank">http://lists.kernelnewbies.org/mailman/listinfo/kernelnewbies</a><br>
<br></blockquote></div><br><br clear="all"><br>-- <br>Thank you <br>Warm Regards<br>Anuz<br>