Esempio n. 1
0
void backend_socket_log(void *frontend, int type, SockAddr addr, int port,
                        const char *error_msg, int error_code, Conf *conf,
                        int session_started)
{
    char addrbuf[256], *msg;

    switch (type) {
      case 0:
        sk_getaddr(addr, addrbuf, lenof(addrbuf));
        if (sk_addr_needs_port(addr)) {
            msg = dupprintf("Connecting to %s port %d", addrbuf, port);
        } else {
            msg = dupprintf("Connecting to %s", addrbuf);
        }
        break;
      case 1:
        sk_getaddr(addr, addrbuf, lenof(addrbuf));
        msg = dupprintf("Failed to connect to %s: %s", addrbuf, error_msg);
        break;
      case 2:
        /* Proxy-related log messages have their own identifying
         * prefix already, put on by our caller. */
        {
            int len, log_to_term;

            /* Suffix \r\n temporarily, so we can log to the terminal. */
            msg = dupprintf("%s\r\n", error_msg);
            len = (int)strlen(msg);
            assert(len >= 2);

            log_to_term = conf_get_int(conf, CONF_proxy_log_to_term);
            if (log_to_term == AUTO)
                log_to_term = session_started ? FORCE_OFF : FORCE_ON;
            if (log_to_term == FORCE_ON)
                from_backend(frontend, TRUE, msg, len);

            msg[len-2] = '\0';         /* remove the \r\n again */
        }
        break;
      default:
        msg = NULL;  /* shouldn't happen, but placate optimiser */
        break;
    }

    if (msg) {
        logevent(frontend, msg);
        sfree(msg);
    }
}
Esempio n. 2
0
File: proxy.c Progetto: Riatre/PuTTY
int proxy_http_negotiate (ProxySocket *p, int change)
{
    if (p->state == PROXY_STATE_NEW) {
	/* we are just beginning the proxy negotiate process,
	 * so we'll send off the initial bits of the request.
	 * for this proxy method, it's just a simple HTTP
	 * request
	 */
	char *buf, dest[512];
	char *username, *password;

	sk_getaddr(p->remote_addr, dest, lenof(dest));

	buf = dupprintf("CONNECT %s:%i HTTP/1.1\r\nHost: %s:%i\r\n",
			dest, p->remote_port, dest, p->remote_port);
	sk_write(p->sub_socket, buf, strlen(buf));
	sfree(buf);

	username = conf_get_str(p->conf, CONF_proxy_username);
	password = conf_get_str(p->conf, CONF_proxy_password);
	if (username[0] || password[0]) {
	    char *buf, *buf2;
	    int i, j, len;
	    buf = dupprintf("%s:%s", username, password);
	    len = strlen(buf);
	    buf2 = snewn(len * 4 / 3 + 100, char);
	    sprintf(buf2, "Proxy-Authorization: Basic ");
	    for (i = 0, j = strlen(buf2); i < len; i += 3, j += 4)
		base64_encode_atom((unsigned char *)(buf+i),
				   (len-i > 3 ? 3 : len-i), buf2+j);
	    strcpy(buf2+j, "\r\n");
	    sk_write(p->sub_socket, buf2, strlen(buf2));
	    sfree(buf);
	    sfree(buf2);
	}
Esempio n. 3
0
static void raw_log(Plug plug, int type, SockAddr addr, int port,
		    const char *error_msg, int error_code)
{
    Raw raw = (Raw) plug;
    char addrbuf[256], *msg;

    sk_getaddr(addr, addrbuf, lenof(addrbuf));

    if (type == 0)
	msg = dupprintf("Connecting to %s port %d", addrbuf, port);
    else
	msg = dupprintf("Failed to connect to %s: %s", addrbuf, error_msg);

    logevent(raw->frontend, msg);
}
Esempio n. 4
0
File: raw.c Progetto: rdebath/sgt
/*
 * Called to set up the raw connection.
 * 
 * Returns an error message, or NULL on success.
 *
 * Also places the canonical host name into `realhost'. It must be
 * freed by the caller.
 */
static char *raw_init(char *host, int port, char **realhost, int nodelay)
{
    static struct plug_function_table fn_table = {
	raw_closing,
	raw_receive,
	raw_sent
    }, *fn_table_ptr = &fn_table;

    SockAddr addr;
    char *err;

    /*
     * Try to find host.
     */
    {
	char buf[200];
	sprintf(buf, "Looking up host \"%.170s\"", host);
	logevent(buf);
    }
    addr = sk_namelookup(host, realhost);
    if ((err = sk_addr_error(addr)))
	return err;

    if (port < 0)
	port = 23;		       /* default telnet port */

    /*
     * Open socket.
     */
    {
	char buf[200], addrbuf[100];
	sk_getaddr(addr, addrbuf, 100);
	sprintf(buf, "Connecting to %.100s port %d", addrbuf, port);
	logevent(buf);
    }
    s = new_connection(addr, *realhost, port, 0, 1, nodelay, &fn_table_ptr);
    if ((err = sk_socket_error(s)))
	return err;

    sk_addr_free(addr);

    return NULL;
}
Esempio n. 5
0
Socket new_connection(SockAddr addr,
                      const char *hostname,
                      int port,
                      int privport,
                      int oobinline,
                      int nodelay,
                      int keepalive,
                      Plug plug,
                      Conf *conf)
{
  static const struct socket_function_table socket_fn_table = {
      sk_proxy_plug,
      sk_proxy_close,
      sk_proxy_write,
      sk_proxy_write_oob,
      sk_proxy_write_eof,
      sk_proxy_flush,
      sk_proxy_set_frozen,
      sk_proxy_socket_error,
      NULL, /* peer_info */
  };

  static const struct plug_function_table plug_fn_table = {
      plug_proxy_log,
      plug_proxy_closing,
      plug_proxy_receive,
      plug_proxy_sent,
      plug_proxy_accepting};

  if (conf_get_int(conf, CONF_proxy_type) != PROXY_NONE &&
      proxy_for_destination(addr, hostname, port, conf)) {
    Proxy_Socket ret;
    Proxy_Plug pplug;
    SockAddr proxy_addr;
    char *proxy_canonical_name;
    const char *proxy_type;
    Socket sret;
    int type;

    if ((sret = platform_new_connection(addr,
                                        hostname,
                                        port,
                                        privport,
                                        oobinline,
                                        nodelay,
                                        keepalive,
                                        plug,
                                        conf)) != NULL)
      return sret;

    ret = snew(struct Socket_proxy_tag);
    ret->fn = &socket_fn_table;
    ret->conf = conf_copy(conf);
    ret->plug = plug;
    ret->remote_addr = addr; /* will need to be freed on close */
    ret->remote_port = port;

    ret->error = NULL;
    ret->pending_flush = 0;
    ret->pending_eof = 0;
    ret->freeze = 0;

    bufchain_init(&ret->pending_input_data);
    bufchain_init(&ret->pending_output_data);
    bufchain_init(&ret->pending_oob_output_data);

    ret->sub_socket = NULL;
    ret->state = PROXY_STATE_NEW;
    ret->negotiate = NULL;

    type = conf_get_int(conf, CONF_proxy_type);
    if (type == PROXY_HTTP) {
      ret->negotiate = proxy_http_negotiate;
      proxy_type = "HTTP";
    } else if (type == PROXY_SOCKS4) {
      ret->negotiate = proxy_socks4_negotiate;
      proxy_type = "SOCKS 4";
    } else if (type == PROXY_SOCKS5) {
      ret->negotiate = proxy_socks5_negotiate;
      proxy_type = "SOCKS 5";
    } else if (type == PROXY_TELNET) {
      ret->negotiate = proxy_telnet_negotiate;
      proxy_type = "Telnet";
    } else {
      ret->error = "Proxy error: Unknown proxy method";
      return (Socket)ret;
    }

    {
      char *logmsg = dupprintf("Will use %s proxy at %s:%d to connect"
                               " to %s:%d",
                               proxy_type,
                               conf_get_str(conf, CONF_proxy_host),
                               conf_get_int(conf, CONF_proxy_port),
                               hostname,
                               port);
      plug_log(plug, 2, NULL, 0, logmsg, 0);
      sfree(logmsg);
    }

    /* create the proxy plug to map calls from the actual
     * socket into our proxy socket layer */
    pplug = snew(struct Plug_proxy_tag);
    pplug->fn = &plug_fn_table;
    pplug->proxy_socket = ret;

    {
      char *logmsg = dns_log_msg(conf_get_str(conf, CONF_proxy_host),
                                 conf_get_int(conf, CONF_addressfamily),
                                 "proxy");
      plug_log(plug, 2, NULL, 0, logmsg, 0);
      sfree(logmsg);
    }

    /* look-up proxy */
    proxy_addr = sk_namelookup(conf_get_str(conf, CONF_proxy_host),
                               &proxy_canonical_name,
                               conf_get_int(conf, CONF_addressfamily));
    if (sk_addr_error(proxy_addr) != NULL) {
      ret->error = "Proxy error: Unable to resolve proxy host name";
      sfree(pplug);
      sk_addr_free(proxy_addr);
      return (Socket)ret;
    }
    sfree(proxy_canonical_name);

    {
      char addrbuf[256], *logmsg;
      sk_getaddr(proxy_addr, addrbuf, lenof(addrbuf));
      logmsg = dupprintf("Connecting to %s proxy at %s port %d",
                         proxy_type,
                         addrbuf,
                         conf_get_int(conf, CONF_proxy_port));
      plug_log(plug, 2, NULL, 0, logmsg, 0);
      sfree(logmsg);
    }

    /* create the actual socket we will be using,
     * connected to our proxy server and port.
     */
    ret->sub_socket = sk_new(proxy_addr,
                             conf_get_int(conf, CONF_proxy_port),
                             privport,
                             oobinline,
                             nodelay,
                             keepalive,
                             (Plug)pplug);
    if (sk_socket_error(ret->sub_socket) != NULL)
      return (Socket)ret;

    /* start the proxy negotiation process... */
    sk_set_frozen(ret->sub_socket, 0);
    ret->negotiate(ret, PROXY_CHANGE_NEW);

    return (Socket)ret;
  }
Esempio n. 6
0
/*
 * This function can accept a NULL pointer as `addr', in which case
 * it will only check the host name.
 */
int proxy_for_destination(SockAddr addr,
                          const char *hostname,
                          int port,
                          Conf *conf)
{
  int s = 0, e = 0;
  char hostip[64];
  int hostip_len, hostname_len;
  const char *exclude_list;

  /*
   * Special local connections such as Unix-domain sockets
   * unconditionally cannot be proxied, even in proxy-localhost
   * mode. There just isn't any way to ask any known proxy type for
   * them.
   */
  if (addr && sk_address_is_special_local(addr))
    return 0; /* do not proxy */

  /*
   * Check the host name and IP against the hard-coded
   * representations of `localhost'.
   */
  if (!conf_get_int(conf, CONF_even_proxy_localhost) &&
      (sk_hostname_is_local(hostname) || (addr && sk_address_is_local(addr))))
    return 0; /* do not proxy */

  /* we want a string representation of the IP address for comparisons */
  if (addr) {
    sk_getaddr(addr, hostip, 64);
    hostip_len = strlen(hostip);
  } else
    hostip_len = 0; /* placate gcc; shouldn't be required */

  hostname_len = strlen(hostname);

  exclude_list = conf_get_str(conf, CONF_proxy_exclude_list);

  /* now parse the exclude list, and see if either our IP
   * or hostname matches anything in it.
   */

  while (exclude_list[s]) {
    while (exclude_list[s] &&
           (isspace((unsigned char)exclude_list[s]) || exclude_list[s] == ','))
      s++;

    if (!exclude_list[s])
      break;

    e = s;

    while (exclude_list[e] &&
           (isalnum((unsigned char)exclude_list[e]) || exclude_list[e] == '-' ||
            exclude_list[e] == '.' || exclude_list[e] == '*'))
      e++;

    if (exclude_list[s] == '*') {
      /* wildcard at beginning of entry */

      if ((addr && strnicmp(hostip + hostip_len - (e - s - 1),
                            exclude_list + s + 1,
                            e - s - 1) == 0) ||
          strnicmp(hostname + hostname_len - (e - s - 1),
                   exclude_list + s + 1,
                   e - s - 1) == 0)
        return 0; /* IP/hostname range excluded. do not use proxy. */

    } else if (exclude_list[e - 1] == '*') {
      /* wildcard at end of entry */

      if ((addr && strnicmp(hostip, exclude_list + s, e - s - 1) == 0) ||
          strnicmp(hostname, exclude_list + s, e - s - 1) == 0)
        return 0; /* IP/hostname range excluded. do not use proxy. */

    } else {
      /* no wildcard at either end, so let's try an absolute
       * match (ie. a specific IP)
       */

      if (addr && strnicmp(hostip, exclude_list + s, e - s) == 0)
        return 0; /* IP/hostname excluded. do not use proxy. */
      if (strnicmp(hostname, exclude_list + s, e - s) == 0)
        return 0; /* IP/hostname excluded. do not use proxy. */
    }

    s = e;

    /* Make sure we really have reached the next comma or end-of-string */
    while (exclude_list[s] && !isspace((unsigned char)exclude_list[s]) &&
           exclude_list[s] != ',')
      s++;
  }

  /* no matches in the exclude list, so use the proxy */
  return 1;
}
Esempio n. 7
0
/*
 * Called to set up the rlogin connection.
 * 
 * Returns an error message, or NULL on success.
 *
 * Also places the canonical host name into `realhost'. It must be
 * freed by the caller.
 */
static const char *rlogin_init(void *frontend_handle, void **backend_handle,
			       Config *cfg,
			       char *host, int port, char **realhost,
			       int nodelay, int keepalive)
{
    static const struct plug_function_table fn_table = {
	rlogin_closing,
	rlogin_receive,
	rlogin_sent
    };
    SockAddr addr;
    const char *err;
    Rlogin rlogin;

    rlogin = snew(struct rlogin_tag);
    rlogin->fn = &fn_table;
    rlogin->s = NULL;
    rlogin->frontend = frontend_handle;
    rlogin->term_width = cfg->width;
    rlogin->term_height = cfg->height;
    rlogin->firstbyte = 1;
    *backend_handle = rlogin;

    /*
     * Try to find host.
     */
    {
	char *buf;
	buf = dupprintf("Looking up host \"%s\"", host);
	logevent(rlogin->frontend, buf);
	sfree(buf);
    }
    addr = name_lookup(host, port, realhost, cfg);
    if ((err = sk_addr_error(addr)) != NULL) {
	sk_addr_free(addr);
	return err;
    }

    if (port < 0)
	port = 513;		       /* default rlogin port */

    /*
     * Open socket.
     */
    {
	char *buf, addrbuf[100];
	sk_getaddr(addr, addrbuf, 100);
	buf = dupprintf("Connecting to %s port %d", addrbuf, port);
	logevent(rlogin->frontend, buf);
	sfree(buf);
    }
    rlogin->s = new_connection(addr, *realhost, port, 1, 0,
			       nodelay, keepalive, (Plug) rlogin, cfg);
    if ((err = sk_socket_error(rlogin->s)) != NULL)
	return err;

    /*
     * Send local username, remote username, terminal/speed
     */

    {
	char z = 0;
	char *p;
	sk_write(rlogin->s, &z, 1);
	sk_write(rlogin->s, cfg->localusername,
		 strlen(cfg->localusername));
	sk_write(rlogin->s, &z, 1);
	sk_write(rlogin->s, cfg->username,
		 strlen(cfg->username));
	sk_write(rlogin->s, &z, 1);
	sk_write(rlogin->s, cfg->termtype,
		 strlen(cfg->termtype));
	sk_write(rlogin->s, "/", 1);
	for (p = cfg->termspeed; isdigit((unsigned char)*p); p++) continue;
	sk_write(rlogin->s, cfg->termspeed, p - cfg->termspeed);
	rlogin->bufsize = sk_write(rlogin->s, &z, 1);
    }

    return NULL;
}
Esempio n. 8
0
Socket *new_connection(SockAddr *addr, const char *hostname,
                       int port, bool privport,
                       bool oobinline, bool nodelay, bool keepalive,
                       Plug *plug, Conf *conf)
{
    if (conf_get_int(conf, CONF_proxy_type) != PROXY_NONE &&
	proxy_for_destination(addr, hostname, port, conf))
    {
	ProxySocket *ret;
	SockAddr *proxy_addr;
	char *proxy_canonical_name;
        const char *proxy_type;
	Socket *sret;
	int type;

	if ((sret = platform_new_connection(addr, hostname, port, privport,
					    oobinline, nodelay, keepalive,
					    plug, conf)) !=
	    NULL)
	    return sret;

	ret = snew(ProxySocket);
	ret->sock.vt = &ProxySocket_sockvt;
	ret->plugimpl.vt = &ProxySocket_plugvt;
	ret->conf = conf_copy(conf);
	ret->plug = plug;
	ret->remote_addr = addr;       /* will need to be freed on close */
	ret->remote_port = port;

	ret->error = NULL;
	ret->pending_flush = false;
	ret->pending_eof = false;
	ret->freeze = false;

	bufchain_init(&ret->pending_input_data);
	bufchain_init(&ret->pending_output_data);
	bufchain_init(&ret->pending_oob_output_data);

	ret->sub_socket = NULL;
	ret->state = PROXY_STATE_NEW;
	ret->negotiate = NULL;

	type = conf_get_int(conf, CONF_proxy_type);
	if (type == PROXY_HTTP) {
	    ret->negotiate = proxy_http_negotiate;
            proxy_type = "HTTP";
	} else if (type == PROXY_SOCKS4) {
            ret->negotiate = proxy_socks4_negotiate;
            proxy_type = "SOCKS 4";
	} else if (type == PROXY_SOCKS5) {
            ret->negotiate = proxy_socks5_negotiate;
            proxy_type = "SOCKS 5";
	} else if (type == PROXY_TELNET) {
	    ret->negotiate = proxy_telnet_negotiate;
            proxy_type = "Telnet";
	} else {
	    ret->error = "Proxy error: Unknown proxy method";
	    return &ret->sock;
	}

        {
            char *logmsg = dupprintf("Will use %s proxy at %s:%d to connect"
                                      " to %s:%d", proxy_type,
                                      conf_get_str(conf, CONF_proxy_host),
                                      conf_get_int(conf, CONF_proxy_port),
                                      hostname, port);
            plug_log(plug, 2, NULL, 0, logmsg, 0);
            sfree(logmsg);
        }

        {
            char *logmsg = dns_log_msg(conf_get_str(conf, CONF_proxy_host),
                                       conf_get_int(conf, CONF_addressfamily),
                                       "proxy");
            plug_log(plug, 2, NULL, 0, logmsg, 0);
            sfree(logmsg);
        }

	/* look-up proxy */
	proxy_addr = sk_namelookup(conf_get_str(conf, CONF_proxy_host),
				   &proxy_canonical_name,
				   conf_get_int(conf, CONF_addressfamily));
	if (sk_addr_error(proxy_addr) != NULL) {
	    ret->error = "Proxy error: Unable to resolve proxy host name";
            sk_addr_free(proxy_addr);
	    return &ret->sock;
	}
	sfree(proxy_canonical_name);

        {
            char addrbuf[256], *logmsg;
            sk_getaddr(proxy_addr, addrbuf, lenof(addrbuf));
            logmsg = dupprintf("Connecting to %s proxy at %s port %d",
                               proxy_type, addrbuf,
                               conf_get_int(conf, CONF_proxy_port));
            plug_log(plug, 2, NULL, 0, logmsg, 0);
            sfree(logmsg);
        }

	/* create the actual socket we will be using,
	 * connected to our proxy server and port.
	 */
	ret->sub_socket = sk_new(proxy_addr,
				 conf_get_int(conf, CONF_proxy_port),
				 privport, oobinline,
				 nodelay, keepalive, &ret->plugimpl);
	if (sk_socket_error(ret->sub_socket) != NULL)
	    return &ret->sock;

	/* start the proxy negotiation process... */
	sk_set_frozen(ret->sub_socket, 0);
	ret->negotiate(ret, PROXY_CHANGE_NEW);

	return &ret->sock;
    }

    /* no proxy, so just return the direct socket */
    return sk_new(addr, port, privport, oobinline, nodelay, keepalive, plug);
}
Esempio n. 9
0
File: rlogin.c Progetto: rdebath/sgt
/*
 * Called to set up the rlogin connection.
 * 
 * Returns an error message, or NULL on success.
 *
 * Also places the canonical host name into `realhost'. It must be
 * freed by the caller.
 */
static char *rlogin_init(char *host, int port, char **realhost, int nodelay)
{
    static struct plug_function_table fn_table = {
	rlogin_closing,
	rlogin_receive,
	rlogin_sent
    }, *fn_table_ptr = &fn_table;

    SockAddr addr;
    char *err;

    /*
     * Try to find host.
     */
    {
	char buf[200];
	sprintf(buf, "Looking up host \"%.170s\"", host);
	logevent(buf);
    }
    addr = sk_namelookup(host, realhost);
    if ((err = sk_addr_error(addr)))
	return err;

    if (port < 0)
	port = 513;		       /* default rlogin port */

    /*
     * Open socket.
     */
    {
	char buf[200], addrbuf[100];
	sk_getaddr(addr, addrbuf, 100);
	sprintf(buf, "Connecting to %.100s port %d", addrbuf, port);
	logevent(buf);
    }
    s = sk_new(addr, port, 1, 0, nodelay, &fn_table_ptr);
    if ((err = sk_socket_error(s)))
	return err;

    sk_addr_free(addr);

    /*
     * Send local username, remote username, terminal/speed
     */

    {
	char z = 0;
	char *p;
	sk_write(s, &z, 1);
	sk_write(s, cfg.localusername, strlen(cfg.localusername));
	sk_write(s, &z, 1);
	sk_write(s, cfg.username, strlen(cfg.username));
	sk_write(s, &z, 1);
	sk_write(s, cfg.termtype, strlen(cfg.termtype));
	sk_write(s, "/", 1);
	for (p = cfg.termspeed; isdigit(*p); p++);
	sk_write(s, cfg.termspeed, p - cfg.termspeed);
	rlogin_bufsize = sk_write(s, &z, 1);
    }

    return NULL;
}