Re: ip_dynaddr broken in 2.4.0-test1 ?

From: Malware (Michael.Mueller4@post.rwth-aachen.de)
Date: Tue Jun 06 2000 - 11:56:57 EST


Hi Christian,

you wrote on linux-kernel:
> if (rt == NULL) {
> int err;
>
> u32 daddr = sk->daddr;
>
> if(sk->protinfo.af_inet.opt &&
> sk->protinfo.af_inet.opt->srr)
> daddr = sk->protinfo.af_inet.opt->faddr;
>
> err = ip_route_output(&rt, daddr, sk->saddr,
> RT_TOS(sk->protinfo.af_inet.tos) |
> RTO_CON
> N | sk->localroute,
> sk->bound_dev_if);
> >> printk(KERN_INFO "error: %d\n", err);
> if (err) {
> sk->err_soft=-err;
> sk->error_report(sk);
> return -1;
> }
[...]
> Jun 5 23:58:37 beastieboys kernel: rt_new: 00000000, old: 00000000
> Jun 5 23:58:37 beastieboys kernel: want rewrite 1
> Jun 5 23:58:37 beastieboys kernel: error: -22

Looks like it is something bad to call ip_route_output with the original
source address of the socket (before it is rewritten) since the function
ip_route_output_slow sitting behind does contain following lines:

if (saddr) {
        if (MULTICAST(saddr) || BADCLASS(saddr) || ZERONET(saddr))
                return -EINVAL;

        /* It is equivalent to inet_addr_type(saddr) == RTN_LOCAL */
        dev_out = ip_dev_find(saddr);
        if (dev_out == NULL)
            return -EINVAL;
...

So since a source address is specified it will try finding an interface
this one is associated with which might fail.

There should be a userspace work-arround as following:

On system startup and disconnect (ip-down script) configure the PPP
interface to have the address of an permanent interface as the ethernet
or dummy interface. So packets generated while the line is down will get
the address of this interface assigned and a route will be generated by
ip_route_output - hopefully I did not miss a hook to netfilter there
since it could block the packet. Since the next step in
tcpv4_rebuild_header is the rewrite already it should work.

If it should be fixed within the kernel I would apply:

--- tcp_ipv4.c.orig Wed May 3 10:48:03 2000
+++ tcp_ipv4.c Tue Jun 6 18:52:24 2000
@@ -1744,7 +1744,7 @@
                if(sk->protinfo.af_inet.opt &&
sk->protinfo.af_inet.opt->srr)
                        daddr = sk->protinfo.af_inet.opt->faddr;
 
- err = ip_route_output(&rt, daddr, sk->saddr,
+ err = ip_route_output(&rt, daddr, (want_rewrite ? 0 :
sk->saddr),
                                      RT_TOS(sk->protinfo.af_inet.tos) |
RTO_CONN | sk->localroute,
                                      sk->bound_dev_if);
                if (err) {

But as I am not familiar with most details I do not swear on that being
an solution and not causing other problems.

Malware

PS: Copies of this message are going to the netdev list and Christian
Nautze.

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/



This archive was generated by hypermail 2b29 : Wed Jun 07 2000 - 21:00:25 EST