My name is Ambarish. I am a computer science engineering student. I am
interested in working under MINIX3 for GSoC'12. I am not exactly new
to MINIX. I have read alot about MINIX3 in context of microkernels
before. I've also read the paper on reliable operating systems [1].
I was going through the GSoC ideas page and the lwIP support idea
caught my eye. I have worked on lwIP before when I wrote a pcap driver
for lwIP. I really liked the design of lwIP. As far as I can see, the
way the port will work is that the lwIP server will interact with the
lwIP library using the raw API. The lwip driver will interface between
lwIP library and the nic driver using the data-link protocol as
mentioned on the wiki. The interface offered to the user application
will be the POSIX sockets API. These system calls, under the hood,
would be interacting with the lwIP server through messages. Is this
the overall picture or am I missing something?
So, what is the current state of the project? In the current src I see
that arch-dependant functions from sys_arch.c are "NOT_IMPLEMENTED".
The netif driver for lwIP is written. The lwIP server has also been
written, but I haven't gone through it completely yet. I am quite
familiar with lwIP codebase, so I was thinking of familiarizing myself
with MINIX3 further and going through the wiki. If there is something
that you suggest, please let me know.
Regards,
Ambarish
[1] - The Architecture of a Reliable Operating System
<www.minix3.org/docs/jorrit-herder/asci06.pdf>
> I was going through the GSoC ideas page and the lwIP support idea
> caught my eye. I have worked on lwIP before when I wrote a pcap driver
> for lwIP. I really liked the design of lwIP. As far as I can see, the
> way the port will work is that the lwIP server will interact with the
> lwIP library using the raw API. The lwip driver will interface between
> lwIP library and the nic driver using the data-link protocol as
> mentioned on the wiki. The interface offered to the user application
> will be the POSIX sockets API. These system calls, under the hood,
> would be interacting with the lwIP server through messages. Is this
> the overall picture or am I missing something?
Sounds good. Maybe one thing that's missing that the user applications
will not speak directly to LWIP. All requests have to go throught the
virtual file system server.
BTW: What exactly do you mean with raw API? You can have a look at
the current socket implementation at servers/lwip/{udp|tcp}.c.
> So, what is the current state of the project?
We have a basic lwip server (based on 1.4.0rc1) that has its
limitations, as no support for IPv6, only one raw socket, and it is
not too well integrated in the current system. Things that have to be
done are complete the integration into Minix, with all fancy feature
like IP forwarding and IPv6. Further we have a port of the NPF packet
filter which should has to be integrated into the system.
> In the current src I see
> that arch-dependant functions from sys_arch.c are "NOT_IMPLEMENTED".
As we are not using, and do not intent to user multi threading in the
lwip server, none of this functionality is needed currently.
> The netif driver for lwIP is written. The lwIP server has also been
> written, but I haven't gone through it completely yet. I am quite
> familiar with lwIP codebase, so I was thinking of familiarizing myself
> with MINIX3 further and going through the wiki.
Sounds good.
Cheers, Dirk
On Wed, Mar 14, 2012 at 5:58 PM, Dirk Vogt <colon...@googlemail.com> wrote:
> BTW: What exactly do you mean with raw API? You can have a look at
> the current socket implementation at servers/lwip/{udp|tcp}.c.
LwIP offers three levels of API. Raw API, netconn API, socket API.
RawAPI allows you to register callbacks for reads. Netconn API
requires multithreading support from the operating system. The socket
API internally uses the netconn API. As we don't support user
multithreading in MINIX3, we have to stick with Raw API and yeah, lwIP
server(servers/lwip/) from the trunk is using the rawAPI.
> We have a basic lwip server (based on 1.4.0rc1) that has its
> limitations, as no support for IPv6, only one raw socket, and it is
> not too well integrated in the current system. Things that have to be
> done are complete the integration into Minix, with all fancy feature
> like IP forwarding and IPv6. Further we have a port of the NPF packet
> filter which should has to be integrated into the system.
Some of these tasks may take a fair amount of work. I'll have to spend
some time analyzing them, to roughly sketch the time required for each
task. I'll come back to you soon on this.
Cheers
Ambarish
> I was going through the GSoC ideas page and the lwIP support idea
> caught my eye. I have worked on lwIP before when I wrote a pcap driver
> for lwIP. I really liked the design of lwIP. As far as I can see, the
> way the port will work is that the lwIP server will interact with the
> lwIP library using the raw API. The lwip driver will interface between
> lwIP library and the nic driver using the data-link protocol as
> mentioned on the wiki. The interface offered to the user application
> will be the POSIX sockets API. These system calls, under the hood,
> would be interacting with the lwIP server through messages. Is this
> the overall picture or am I missing something?
Exactly. Indeed, we use only the RAW API, the POSIX sockets are
provided by the VFS server and we only use LwIP to imlement the
protocols. The socket API in LwIP is meant to for applications where
the LwIP is linked together with the rest.
Cheers, T.
> > We have a basic lwip server (based on 1.4.0rc1) that has its
> > limitations, as no support for IPv6, only one raw socket, and it is
> > not too well integrated in the current system. Things that have to be
> > done are complete the integration into Minix, with all fancy feature
> > like IP forwarding and IPv6. Further we have a port of the NPF packet
> > filter which should has to be integrated into the system.
>
> Some of these tasks may take a fair amount of work. I'll have to spend
> some time analyzing them, to roughly sketch the time required for each
> task. I'll come back to you soon on this.
Basically, the first thing we need to do is to pull in the new 1.4.1
code from LwIP which should be released soon. Imo, that should be
fairly straight forward. Next, we need to make the lwip server a 100+%
substitute for the inet server. For instance, we need the DHCP to work
well. We have some quick fixes in our DHCP to work with the lwip
server which needs to be either polished or replaced, perhaps we could
you the DHCP from LwIP. We need routing and IP forwarding to work as
well. Minix has tools to setup routing, however, since Minix is mostly
used with a single network interfaceonly, they do not get tested and
do not work properly. Making LwIP the default stack is a good chance
to fix it. As Dirk already mentioned, we need to add hooks for the NPF
packet filter (again, imo, fairly straight forward task). These are
the primary goals.
We have some secondary goals as well. If you were interested in
working on the core LwIP, we have code for TCP segmentation offloading
which needs to be revised and perhaps upstreamed. Similarly, we would
be interested in adding features to LwIP like more advanced congestion
control algorithms or TCP windows scaling option.
Cheers, T.
Just for the record: AFAIU this change has been now fully applied to
-current, so you won't need it any more.
Antoine
thanks for the patch, good job. I just skimmed it, I have some
questions below.
> diff -ru minix-orig/lib/liblwip/core/tcp_in.c minix/lib/liblwip/core/tcp_in.c
> --- minix-orig/lib/liblwip/core/tcp_in.c 2012-03-12 01:55:37.000000000 +0530
> +++ minix/lib/liblwip/core/tcp_in.c 2012-04-09 23:36:56.069974599 +0530
> @@ -859,14 +867,28 @@
> /* Update window. */
> if (TCP_SEQ_LT(pcb->snd_wl1, seqno) ||
> (pcb->snd_wl1 == seqno && TCP_SEQ_LT(pcb->snd_wl2, ackno)) ||
> - (pcb->snd_wl2 == ackno && tcphdr->wnd > pcb->snd_wnd)) {
> + (pcb->snd_wl2 == ackno &&
> +#if LWIP_TCP_WINDOW_SCALE
> + tcphdr->wnd > (pcb->snd_wnd >> pcb->snd_shft_cnt)
Is the shift in the right direction?
> diff -ru minix-orig/lib/liblwip/include/lwip/opt.h minix/lib/liblwip/include/lwip/opt.h
> --- minix-orig/lib/liblwip/include/lwip/opt.h 2012-03-12 01:55:37.000000000 +0530
> +++ minix/lib/liblwip/include/lwip/opt.h 2012-04-10 04:25:49.349975567 +0530
> @@ -889,12 +889,39 @@
> #endif
>
> /**
> + * LWIP_TCP_WINDOW_SCALE == 1 Enable TCP window scaling option
> + * Recieve window will be scaled by a factor of 2**TCP_WND_SHFT
> + */
> +#ifndef LWIP_TCP_WINDOW_SCALE
> +#define LWIP_TCP_WINDOW_SCALE 1
> +#endif
> +
> +/**
> + * TCP_WND_SHFT : The scaling factor for TCP_WND when TCP
> + * Window Scaling option is set
> + */
> +#ifndef TCP_WND_SHFT
> +
> +#if LWIP_TCP_WINDOW_SCALE
> +#define TCP_WND_SHFT 6
> +#endif
> +
> +#endif /* TCP_WND_SHFT */
> +
> +/**
> * TCP_WND: The size of a TCP window. This must be at least
> * (2 * TCP_MSS) for things to work well
> */
> +
> #ifndef TCP_WND
> +
> +#if LWIP_TCP_WINDOW_SCALE
> +#define TCP_WND (4 * TCP_MSS) << TCP_WND_SHFT
Is it ok to set TCP_WND to a constant in this case?
> +#else
> #define TCP_WND (4 * TCP_MSS)
> -#endif
> +#endif /* LWIP_TCP_WINDOW_SCALE */
> +
> +#endif /* TCP_WND */
>
> /**
> * TCP_MAXRTX: Maximum number of retransmissions of data segments.
> diff -ru minix-orig/lib/liblwip/include/lwip/tcp.h minix/lib/liblwip/include/lwip/tcp.h
> --- minix-orig/lib/liblwip/include/lwip/tcp.h 2012-03-12 01:55:37.000000000 +0530
> +++ minix/lib/liblwip/include/lwip/tcp.h 2012-04-09 23:38:16.718327182 +0530
> @@ -189,8 +189,16 @@
> as we have to do some math with them */
> /* receiver variables */
> u32_t rcv_nxt; /* next seqno expected */
> - u16_t rcv_wnd; /* receiver window available */
> - u16_t rcv_ann_wnd; /* receiver window to announce */
> +
> +#if LWIP_TCP_WINDOW_SCALE
> + u32_t rcv_wnd;
> + u32_t rcv_ann_wnd; /* receiver window available */
> + u8_t rcv_shft_cnt; /* receiver window to announce */
Are the comments right?
One more minor thing in general. It is not good to leave whitespace at
the end of lines, but dont worry about that, just a friendly advice :)
Cheers, T.
On Tue, Apr 10, 2012 at 12:32 PM, Tomas Hruby <thr...@gmail.com> wrote:
>> + tcphdr->wnd > (pcb->snd_wnd >> pcb->snd_shft_cnt)
>
> Is the shift in the right direction?
Yeah, I think it is. Please explain why you think it should be otherwise.
>> +/**
>> * TCP_WND: The size of a TCP window. This must be at least
>> * (2 * TCP_MSS) for things to work well
>> */
>> +
>> #ifndef TCP_WND
>> +
>> +#if LWIP_TCP_WINDOW_SCALE
>> +#define TCP_WND (4 * TCP_MSS) << TCP_WND_SHFT
>
> Is it ok to set TCP_WND to a constant in this case?
I guess we will have a problem if the other end doesn't support window
scaling. Check the attached patch for changes.
>> + u32_t rcv_wnd;
>> + u32_t rcv_ann_wnd; /* receiver window available */
>> + u8_t rcv_shft_cnt; /* receiver window to announce */
>
> Are the comments right?
Of course they are not. Changed in the attached patch.
Please do let me know if any more improvements are required.
Cheers
Ambarish
Alright, on the second look I think it is correct. My bad.
>>> +/**
>>> * TCP_WND: The size of a TCP window. This must be at least
>>> * (2 * TCP_MSS) for things to work well
>>> */
>>> +
>>> #ifndef TCP_WND
>>> +
>>> +#if LWIP_TCP_WINDOW_SCALE
>>> +#define TCP_WND (4 * TCP_MSS) << TCP_WND_SHFT
>>
>> Is it ok to set TCP_WND to a constant in this case?
>
> I guess we will have a problem if the other end doesn't support window
> scaling. Check the attached patch for changes.
OK, it looks good to me. Great job! much appreciated.
Cheers, T.