nat_cmd.c revision 37191
1/*- 2 * The code in this file was written by Eivind Eklund <perhaps@yes.no>, 3 * who places it in the public domain without restriction. 4 * 5 * $Id: alias_cmd.c,v 1.14 1998/06/15 19:05:59 brian Exp $ 6 */ 7 8#include <sys/types.h> 9#include <netinet/in.h> 10#include <arpa/inet.h> 11#include <netdb.h> 12#include <netinet/in_systm.h> 13#include <netinet/in.h> 14#include <netinet/tcp.h> 15#include <netinet/ip.h> 16#include <sys/un.h> 17 18#include <alias.h> 19#include <stdio.h> 20#include <stdlib.h> 21#include <string.h> 22#include <termios.h> 23 24#include "defs.h" 25#include "command.h" 26#include "log.h" 27#include "alias_cmd.h" 28#include "descriptor.h" 29#include "prompt.h" 30#include "timer.h" 31#include "fsm.h" 32#include "slcompress.h" 33#include "throughput.h" 34#include "iplist.h" 35#include "ipcp.h" 36#include "lqr.h" 37#include "hdlc.h" 38#include "mbuf.h" 39#include "lcp.h" 40#include "ccp.h" 41#include "link.h" 42#include "mp.h" 43#include "filter.h" 44#include "bundle.h" 45 46 47static int StrToAddr(const char *, struct in_addr *); 48static int StrToPort(const char *, u_short *, const char *); 49static int StrToAddrAndPort(const char *, struct in_addr *, u_short *, const char *); 50 51 52int 53alias_RedirectPort(struct cmdargs const *arg) 54{ 55 if (!arg->bundle->AliasEnabled) { 56 prompt_Printf(arg->prompt, "Alias not enabled\n"); 57 return 1; 58 } else if (arg->argc == arg->argn+3) { 59 char proto_constant; 60 const char *proto; 61 u_short local_port; 62 u_short alias_port; 63 int error; 64 struct in_addr local_addr; 65 struct in_addr null_addr; 66 struct alias_link *link; 67 68 proto = arg->argv[arg->argn]; 69 if (strcmp(proto, "tcp") == 0) { 70 proto_constant = IPPROTO_TCP; 71 } else if (strcmp(proto, "udp") == 0) { 72 proto_constant = IPPROTO_UDP; 73 } else { 74 prompt_Printf(arg->prompt, "port redirect: protocol must be" 75 " tcp or udp\n"); 76 prompt_Printf(arg->prompt, "Usage: alias %s %s\n", arg->cmd->name, 77 arg->cmd->syntax); 78 return 1; 79 } 80 81 error = StrToAddrAndPort(arg->argv[arg->argn+1], &local_addr, &local_port, 82 proto); 83 if (error) { 84 prompt_Printf(arg->prompt, "port redirect: error reading" 85 " local addr:port\n"); 86 prompt_Printf(arg->prompt, "Usage: alias %s %s\n", arg->cmd->name, 87 arg->cmd->syntax); 88 return 1; 89 } 90 error = StrToPort(arg->argv[arg->argn+2], &alias_port, proto); 91 if (error) { 92 prompt_Printf(arg->prompt, "port redirect: error reading alias port\n"); 93 prompt_Printf(arg->prompt, "Usage: alias %s %s\n", arg->cmd->name, 94 arg->cmd->syntax); 95 return 1; 96 } 97 null_addr.s_addr = INADDR_ANY; 98 99 link = PacketAliasRedirectPort(local_addr, local_port, 100 null_addr, 0, 101 null_addr, alias_port, 102 proto_constant); 103 104 if (link == NULL) 105 prompt_Printf(arg->prompt, "port redirect: error returned by packed" 106 " aliasing engine (code=%d)\n", error); 107 } else 108 return -1; 109 110 return 0; 111} 112 113 114int 115alias_RedirectAddr(struct cmdargs const *arg) 116{ 117 if (!arg->bundle->AliasEnabled) { 118 prompt_Printf(arg->prompt, "alias not enabled\n"); 119 return 1; 120 } else if (arg->argc == arg->argn+2) { 121 int error; 122 struct in_addr local_addr; 123 struct in_addr alias_addr; 124 struct alias_link *link; 125 126 error = StrToAddr(arg->argv[arg->argn], &local_addr); 127 if (error) { 128 prompt_Printf(arg->prompt, "address redirect: invalid local address\n"); 129 return 1; 130 } 131 error = StrToAddr(arg->argv[arg->argn+1], &alias_addr); 132 if (error) { 133 prompt_Printf(arg->prompt, "address redirect: invalid alias address\n"); 134 prompt_Printf(arg->prompt, "Usage: alias %s %s\n", arg->cmd->name, 135 arg->cmd->syntax); 136 return 1; 137 } 138 link = PacketAliasRedirectAddr(local_addr, alias_addr); 139 if (link == NULL) { 140 prompt_Printf(arg->prompt, "address redirect: packet aliasing" 141 " engine error\n"); 142 prompt_Printf(arg->prompt, "Usage: alias %s %s\n", arg->cmd->name, 143 arg->cmd->syntax); 144 } 145 } else 146 return -1; 147 148 return 0; 149} 150 151 152static int 153StrToAddr(const char *str, struct in_addr *addr) 154{ 155 struct hostent *hp; 156 157 if (inet_aton(str, addr)) 158 return 0; 159 160 hp = gethostbyname(str); 161 if (!hp) { 162 log_Printf(LogWARN, "StrToAddr: Unknown host %s.\n", str); 163 return -1; 164 } 165 *addr = *((struct in_addr *) hp->h_addr); 166 return 0; 167} 168 169 170static int 171StrToPort(const char *str, u_short *port, const char *proto) 172{ 173 int iport; 174 struct servent *sp; 175 char *end; 176 177 iport = strtol(str, &end, 10); 178 if (end != str) { 179 *port = htons(iport); 180 return 0; 181 } 182 sp = getservbyname(str, proto); 183 if (!sp) { 184 log_Printf(LogWARN, "StrToAddr: Unknown port or service %s/%s.\n", 185 str, proto); 186 return -1; 187 } 188 *port = sp->s_port; 189 return 0; 190} 191 192 193static int 194StrToAddrAndPort(const char *str, struct in_addr *addr, u_short *port, const char *proto) 195{ 196 char *colon; 197 int res; 198 199 colon = strchr(str, ':'); 200 if (!colon) { 201 log_Printf(LogWARN, "StrToAddrAndPort: %s is missing port number.\n", str); 202 return -1; 203 } 204 205 *colon = '\0'; /* Cheat the const-ness ! */ 206 res = StrToAddr(str, addr); 207 *colon = ':'; /* Cheat the const-ness ! */ 208 if (res != 0) 209 return -1; 210 211 return StrToPort(colon+1, port, proto); 212} 213