diff -r -N -c libalias.org/Makefile libalias/Makefile *** libalias.org/Makefile Fri Jan 14 16:57:13 2000 --- libalias/Makefile Sun May 21 00:42:36 2000 *************** *** 5,11 **** SHLIB_MINOR= 0 CFLAGS+= -Wall -I${.CURDIR} SRCS= alias.c alias_cuseeme.c alias_db.c alias_ftp.c alias_irc.c \ ! alias_nbt.c alias_proxy.c alias_util.c INCS= alias.h MAN3= libalias.3 --- 5,11 ---- SHLIB_MINOR= 0 CFLAGS+= -Wall -I${.CURDIR} SRCS= alias.c alias_cuseeme.c alias_db.c alias_ftp.c alias_irc.c \ ! alias_nbt.c alias_proxy.c alias_util.c alias_real.c INCS= alias.h MAN3= libalias.3 diff -r -N -c libalias.org/alias.c libalias/alias.c *** libalias.org/alias.c Sat Sep 11 00:27:34 1999 --- libalias/alias.c Sun May 28 23:50:25 2000 *************** *** 109,114 **** --- 109,116 ---- #define IRC_CONTROL_PORT_NUMBER_1 6667 #define IRC_CONTROL_PORT_NUMBER_2 6668 #define CUSEEME_PORT_NUMBER 7648 + #define REAL_CONTROL_PORT_NUMBER_1 554 + #define REAL_CONTROL_PORT_NUMBER_2 7070 *************** *** 982,987 **** --- 984,992 ---- if (ntohs(tc->th_dport) == IRC_CONTROL_PORT_NUMBER_1 || ntohs(tc->th_dport) == IRC_CONTROL_PORT_NUMBER_2) AliasHandleIrcOut(pip, link, maxpacketsize); + if (ntohs(tc->th_dport) == REAL_CONTROL_PORT_NUMBER_1 + || ntohs(tc->th_dport) == REAL_CONTROL_PORT_NUMBER_2) + AliasHandleRealOut(pip, link, maxpacketsize); /* Adjust TCP checksum since source port is being aliased */ /* and source address is being altered */ diff -r -N -c libalias.org/alias_local.h libalias/alias_local.h *** libalias.org/alias_local.h Mon Aug 30 08:17:04 1999 --- libalias/alias_local.h Sun Jun 4 13:59:32 2000 *************** *** 160,165 **** --- 160,167 ---- int ProxyCheck(struct ip *, struct in_addr *, u_short *); void ProxyModify(struct alias_link *, struct ip *, int, int); + /* Real routines */ + void AliasHandleRealOut(struct ip *, struct alias_link *, int); enum alias_tcp_state { ALIAS_TCP_STATE_NOT_CONNECTED, diff -r -N -c libalias.org/alias_real.c libalias/alias_real.c *** libalias.org/alias_real.c Thu Jan 1 09:00:00 1970 --- libalias/alias_real.c Sun Jun 4 14:01:32 2000 *************** *** 0 **** --- 1,279 ---- + /*- + * Copyright (c) 2000 Junichi SATOH + * + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $FreeBSD: $ + */ + + #include + #include + #include + #include + #include + #include + #include + #include + + #include "alias_local.h" + + #define ISDIGIT(a) (((a) >= '0') && ((a) <= '9')) + + int search_string(char *data, int dlen, char *search_str) + { + int i, j, k; + int search_str_len; + + search_str_len = strlen(search_str); + for (i = 0; i < dlen - search_str_len; i++) { + for (j = i, k = 0; j < dlen - search_str_len; j++, k++) { + if (data[j] != search_str[k] && + data[j] != search_str[k] - ('a' - 'A')) { + break; + } + if (k == search_str_len - 1) { + return j + 1; + } + } + } + return -1; + } + + int alias_rtsp_out(struct ip *pip, + struct alias_link *link, + char *data) + { + int hlen, tlen, dlen; + struct tcphdr *tc; + + int i, pos, state, port_dlen, new_dlen, delta; + char *transport_str = "transport:"; + char *client_port_str = "client_port"; + u_short p[2], alias_port, new_len, sport, eport; + char newdata[2048], *port_data, *port_newdata, stemp[80]; + struct alias_link *rtsp_link; + + /* Calculate data length of TCP packet */ + tc = (struct tcphdr *) ((char *) pip + (pip->ip_hl << 2)); + hlen = (pip->ip_hl + tc->th_off) << 2; + tlen = ntohs(pip->ip_len); + dlen = tlen - hlen; + + /* Find keyword, "Transport: " */ + pos = search_string(data, dlen, transport_str); + if (pos < 0) { + return -1; + } + port_data = data + pos; + port_dlen = dlen - pos; + + memcpy(newdata, data, pos); + port_newdata = newdata + pos; + + while (port_dlen > strlen(client_port_str)) { + /* Find keyword, "client_port" */ + pos = search_string(port_data, port_dlen, client_port_str); + if (pos < 0) { + break; + } + + memcpy (port_newdata, port_data, pos + 1); + port_newdata += (pos + 1); + + p[0] = p[1] = 0; + sport = eport = 0; + state = 0; + for (i = pos; i < port_dlen; i++) { + switch(state) { + case 0: + if (port_data[i] == '=') { + state++; + } + break; + case 1: + if (ISDIGIT(port_data[i])) { + p[0] = p[0] * 10 + port_data[i] - '0'; + } else { + if (port_data[i] == ';') { + state = 3; + } + if (port_data[i] == '-') { + state++; + } + } + break; + case 2: + if (ISDIGIT(port_data[i])) { + p[1] = p[1] * 10 + port_data[i] - '0'; + } else { + state++; + } + break; + case 3: + sport = htons(p[0]); + eport = htons(p[1]); + rtsp_link = FindUdpTcpOut(pip->ip_src, GetDestAddress(link), + sport, 0, IPPROTO_UDP); + if (rtsp_link != NULL) { + #ifndef NO_FW_PUNCH + /* Puhch hole in firewall */ + PunchFWHole(rtsp_link); + #endif + alias_port = GetAliasPort(rtsp_link); + + /* Copy into IP packet */ + sprintf(stemp, "%d", ntohs(alias_port)); + memcpy(port_newdata, stemp, strlen(stemp)); + port_newdata += strlen(stemp); + } + if (eport != 0) { + *port_newdata = '-'; + port_newdata++; + rtsp_link = FindUdpTcpOut(pip->ip_src, + GetDestAddress(link), + eport, 0, IPPROTO_UDP); + if (rtsp_link != NULL) { + #ifndef NO_FW_PUNCH + /* Puhch hole in firewall */ + PunchFWHole(rtsp_link); + #endif + alias_port = GetAliasPort(rtsp_link); + + /* Copy into IP packet */ + sprintf(stemp, "%d", ntohs(alias_port)); + memcpy(port_newdata, stemp, strlen(stemp)); + port_newdata += strlen(stemp); + } + } + *port_newdata = ';'; + port_newdata++; + state++; + break; + } + if (state > 3) { + break; + } + } + port_data += i; + port_dlen -= i; + } + + memcpy (port_newdata, port_data, port_dlen); + port_newdata += port_dlen; + *port_newdata = '\0'; + + /* Create new packet */ + new_dlen = port_newdata - newdata; + memcpy (data, newdata, new_dlen); + + SetAckModified(link); + delta = GetDeltaSeqOut(pip, link); + AddSeq(pip, link, delta + new_dlen - dlen); + + new_len = htons(hlen + new_dlen); + DifferentialChecksum(&pip->ip_sum, + &new_len, + &pip->ip_len, + 1); + pip->ip_len = new_len; + + tc->th_sum = 0; + tc->th_sum = TcpChecksum(pip); + + return 0; + } + + int alias_pna_out(struct ip *pip, + struct alias_link *link, + char *data, + int dlen) + { + struct alias_link *pna_links; + u_short msg_id, msg_len; + char *work; + u_short alias_port, port; + struct tcphdr *tc; + + work = data; + work += 5; + while (work + 4 < data + dlen) { + memcpy(&msg_id, work, 2); + work += 2; + memcpy(&msg_len, work, 2); + work += 2; + if (ntohs(msg_id) == 0) { + /* end of options */ + return 0; + } + if ((ntohs(msg_id) == 1) || (ntohs(msg_id) == 7)) { + memcpy((char*)&port, (char*)work, 2); + pna_links = FindUdpTcpOut(pip->ip_src, GetDestAddress(link), + port, 0, IPPROTO_UDP); + if (pna_links != NULL) { + #ifndef NO_FW_PUNCH + /* Puhch hole in firewall */ + PunchFWHole(pna_links); + #endif + tc = (struct tcphdr *) ((char *) pip + (pip->ip_hl << 2)); + alias_port = GetAliasPort(pna_links); + memcpy((char*)work, (char*)&alias_port, 2); + + /* Compute TCP checksum for revised packet */ + tc->th_sum = 0; + tc->th_sum = TcpChecksum(pip); + } + } + work += ntohs(msg_len); + } + + return 0; + } + + void + AliasHandleRealOut(struct ip *pip, struct alias_link *link, int maxpacketsize) + { + int hlen, tlen, dlen; + struct tcphdr *tc; + char *data, *setup = "SETUP", *pna = "PNA"; + + tc = (struct tcphdr *)((char *)pip + (pip->ip_hl << 2)); + hlen = (pip->ip_hl + tc->th_off) << 2; + tlen = ntohs(pip->ip_len); + dlen = tlen - hlen; + + data = (char*)pip; + data += hlen; + + if (dlen >= strlen(setup)) { + if (memcmp(data, setup, strlen(setup)) == 0) { + alias_rtsp_out(pip, link, data); + return; + } + } + if (dlen >= strlen(pna)) { + if (memcmp(data, pna, strlen(pna)) == 0) { + alias_pna_out(pip, link, data, dlen); + } + } + }