Hi all. When looking thru the code (and manpage) in libalias i could see that proxy_rules support udp packets. This is nice.. The only problem is that in the udpPacketIn/out functions proxy rules is not checked. I wrote a small patch that implements this and I've done some basic testing..
Patch is attached to this mail. I couldn't see any maintainer for libalias and decided to write to -net. I hope this is the right list :) Comments ? --- Nicolai Petri catpipe Systems ApS Copenhagen / Denmark Ps. A volunteering commiter would be nice if the patch looks sane.
--- alias.c.orig Fri Nov 8 14:45:08 2002 +++ alias.c Mon Nov 11 11:38:46 2002 @@ -257,7 +257,7 @@ static int ProtoAliasIn(struct ip *); static int ProtoAliasOut(struct ip *); -static int UdpAliasOut(struct ip *); +static int UdpAliasOut(struct ip *, int); static int UdpAliasIn (struct ip *); static int TcpAliasOut(struct ip *, int); @@ -744,28 +744,28 @@ struct udphdr *ud; struct alias_link *link; -/* Return if proxy-only mode is enabled */ - if (packetAliasMode & PKT_ALIAS_PROXY_ONLY) - return PKT_ALIAS_OK; - ud = (struct udphdr *) ((char *) pip + (pip->ip_hl << 2)); link = FindUdpTcpIn(pip->ip_src, pip->ip_dst, ud->uh_sport, ud->uh_dport, - IPPROTO_UDP, 1); + IPPROTO_UDP, !(packetAliasMode & PKT_ALIAS_PROXY_ONLY)); if (link != NULL) { struct in_addr alias_address; struct in_addr original_address; + struct in_addr proxy_address; u_short alias_port; + u_short proxy_port; int accumulate; u_short *sptr; - int r = 0; + int r = 0; alias_address = GetAliasAddress(link); original_address = GetOriginalAddress(link); + proxy_address = GetProxyAddress(link); alias_port = ud->uh_dport; ud->uh_dport = GetOriginalPort(link); + proxy_port = GetProxyPort(link); /* Special processing for IP encoding protocols */ if (ntohs(ud->uh_dport) == CUSEEME_PORT_NUMBER) @@ -791,14 +791,48 @@ sptr = (u_short *) &original_address; accumulate -= *sptr++; accumulate -= *sptr; + +/* If this is a proxy packet, modify checksum because of source change.*/ + if (proxy_port != 0) + { + accumulate += ud->uh_sport; + accumulate -= proxy_port; + } + + if (proxy_address.s_addr != 0) + { + sptr = (u_short *) &pip->ip_src; + accumulate += *sptr++; + accumulate += *sptr; + sptr = (u_short *) &proxy_address; + accumulate -= *sptr++; + accumulate -= *sptr; + } + ADJUST_CHECKSUM(accumulate, ud->uh_sum); + } +/* XXX: Could the two if's below be concatenated to one ? */ +/* Restore source port and/or address in case of proxying*/ + + if (proxy_port != 0) + ud->uh_sport = proxy_port; + + if (proxy_address.s_addr != 0) + { + DifferentialChecksum(&pip->ip_sum, + (u_short *) &proxy_address, + (u_short *) &pip->ip_src, + 2); + pip->ip_src = proxy_address; + } + /* Restore original IP address */ DifferentialChecksum(&pip->ip_sum, - (u_short *) &original_address, - (u_short *) &pip->ip_dst, - 2); + (u_short *) &original_address, + (u_short *) &pip->ip_dst, + 2); pip->ip_dst = original_address; /* @@ -813,16 +847,57 @@ } static int -UdpAliasOut(struct ip *pip) +UdpAliasOut(struct ip *pip, int maxpacketsize) { struct udphdr *ud; struct alias_link *link; + int proxy_type; + u_short dest_port; + u_short proxy_server_port; + struct in_addr dest_address; + struct in_addr proxy_server_address; -/* Return if proxy-only mode is enabled */ - if (packetAliasMode & PKT_ALIAS_PROXY_ONLY) +/* Return if proxy-only mode is enabled and not proxyrule found.*/ + ud = (struct udphdr *) ((char *) pip + (pip->ip_hl << 2)); + + proxy_type = ProxyCheck(pip, &proxy_server_address, &proxy_server_port); + + if (proxy_type == 0 && (packetAliasMode & PKT_ALIAS_PROXY_ONLY)) return PKT_ALIAS_OK; - ud = (struct udphdr *) ((char *) pip + (pip->ip_hl << 2)); +/* If this is a transparent proxy, save original destination, + then alter the destination and adjust checksums */ + dest_port = ud->uh_dport; + dest_address = pip->ip_dst; + + if (proxy_type != 0) + { + int accumulate; + u_short *sptr; + + accumulate = ud->uh_dport; + ud->uh_dport = proxy_server_port; + accumulate -= ud->uh_dport; + + sptr = (u_short *) &(pip->ip_dst); + accumulate += *sptr++; + accumulate += *sptr; + sptr = (u_short *) &proxy_server_address; + accumulate -= *sptr++; + accumulate -= *sptr; + + ADJUST_CHECKSUM(accumulate, ud->uh_sum); + + sptr = (u_short *) &(pip->ip_dst); + accumulate = *sptr++; + accumulate += *sptr; + pip->ip_dst = proxy_server_address; + sptr = (u_short *) &(pip->ip_dst); + accumulate -= *sptr++; + accumulate -= *sptr; + + ADJUST_CHECKSUM(accumulate, pip->ip_sum); + } link = FindUdpTcpOut(pip->ip_src, pip->ip_dst, ud->uh_sport, ud->uh_dport, @@ -832,6 +907,17 @@ u_short alias_port; struct in_addr alias_address; +/* Save original destination address, if this is a proxy packet. + Also modify packet to include destination encoding. This may + change the size of IP header. */ + if (proxy_type != 0) + { + SetProxyPort(link, dest_port); + SetProxyAddress(link, dest_address); + ProxyModify(link, pip, maxpacketsize, proxy_type); + ud = (struct udphdr *) ((char *) pip + (pip->ip_hl << 2)); + } + alias_address = GetAliasAddress(link); alias_port = GetAliasPort(link); @@ -1092,7 +1178,7 @@ else if (ntohs(tc->th_dport) == RTSP_CONTROL_PORT_NUMBER_1 || ntohs(tc->th_sport) == RTSP_CONTROL_PORT_NUMBER_1 || ntohs(tc->th_dport) == RTSP_CONTROL_PORT_NUMBER_2 - || ntohs(tc->th_sport) == RTSP_CONTROL_PORT_NUMBER_2) + || ntohs(tc->th_sport) == RTSP_CONTROL_PORT_NUMBER_2) AliasHandleRtspOut(pip, link, maxpacketsize); else if (ntohs(tc->th_dport) == PPTP_CONTROL_PORT_NUMBER || ntohs(tc->th_sport) == PPTP_CONTROL_PORT_NUMBER) @@ -1434,7 +1520,7 @@ iresult = IcmpAliasOut(pip); break; case IPPROTO_UDP: - iresult = UdpAliasOut(pip); + iresult = UdpAliasOut(pip, maxpacketsize); break; case IPPROTO_TCP: iresult = TcpAliasOut(pip, maxpacketsize);