Exemplo n.º 1
0
static int
TRANS(TLIClose)(XtransConnInfo ciptr)

{
    prmsg(2, "TLIClose(%x->%d)\n", ciptr, ciptr->fd);

    t_unbind(ciptr->fd);

    return (t_close(ciptr->fd));
}
Exemplo n.º 2
0
/*
 * How to bind to reserved ports.
 * TLI handle (socket) and port version.
 */
int
bind_resv_port(int td, u_short *pp)
{
  int rc = -1, port;
  struct t_bind *treq, *tret;
  struct sockaddr_in *sin;

  treq = (struct t_bind *) t_alloc(td, T_BIND, T_ADDR);
  if (!treq) {
    plog(XLOG_ERROR, "t_alloc req");
    return -1;
  }
  tret = (struct t_bind *) t_alloc(td, T_BIND, T_ADDR);
  if (!tret) {
    t_free((char *) treq, T_BIND);
    plog(XLOG_ERROR, "t_alloc ret");
    return -1;
  }
  memset((char *) treq->addr.buf, 0, treq->addr.len);
  sin = (struct sockaddr_in *) treq->addr.buf;
  sin->sin_family = AF_INET;
  treq->qlen = 0;
  treq->addr.len = treq->addr.maxlen;
  errno = EADDRINUSE;
  port = IPPORT_RESERVED;

  do {
    --port;
    sin->sin_port = htons(port);
    rc = t_bind(td, treq, tret);
    if (rc < 0) {
      plog(XLOG_ERROR, "t_bind");
    } else {
      if (memcmp(treq->addr.buf, tret->addr.buf, tret->addr.len) == 0)
	break;
      else
	t_unbind(td);
    }
  } while ((rc < 0 || errno == EADDRINUSE) && (int) port > IPPORT_RESERVED / 2);

  if (pp) {
    if (rc == 0)
      *pp = port;
    else
      plog(XLOG_ERROR, "could not t_bind to any reserved port");
  }
  t_free((char *) tret, T_BIND);
  t_free((char *) treq, T_BIND);
  return rc;
}
Exemplo n.º 3
0
static void
get_xdmcp_sock(void)
{
#ifdef STREAMSCONN
    struct netconfig *nconf;

    if ((xdmcpSocket = t_open("/dev/udp", O_RDWR, 0)) < 0) {
        XdmcpWarning("t_open() of /dev/udp failed");
        return;
    }

    if (t_bind(xdmcpSocket, NULL, NULL) < 0) {
        XdmcpWarning("UDP socket creation failed");
        t_error("t_bind(xdmcpSocket) failed");
        t_close(xdmcpSocket);
        return;
    }

    /*
     * This part of the code looks contrived. It will actually fit in nicely
     * when the CLTS part of Xtrans is implemented.
     */

    if ((nconf = getnetconfigent("udp")) == NULL) {
        XdmcpWarning("UDP socket creation failed: getnetconfigent()");
        t_unbind(xdmcpSocket);
        t_close(xdmcpSocket);
        return;
    }

    if (netdir_options(nconf, ND_SET_BROADCAST, xdmcpSocket, NULL)) {
        XdmcpWarning("UDP set broadcast option failed: netdir_options()");
        freenetconfigent(nconf);
        t_unbind(xdmcpSocket);
        t_close(xdmcpSocket);
        return;
    }

    freenetconfigent(nconf);
#else
    int soopts = 1;

#if defined(IPv6) && defined(AF_INET6)
    if ((xdmcpSocket6 = socket(AF_INET6, SOCK_DGRAM, 0)) < 0)
        XdmcpWarning("INET6 UDP socket creation failed");
#endif
    if ((xdmcpSocket = socket(AF_INET, SOCK_DGRAM, 0)) < 0)
        XdmcpWarning("UDP socket creation failed");
#ifdef SO_BROADCAST
    else if (setsockopt(xdmcpSocket, SOL_SOCKET, SO_BROADCAST, (char *) &soopts,
                        sizeof(soopts)) < 0)
        XdmcpWarning("UDP set broadcast socket-option failed");
#endif                          /* SO_BROADCAST */
    if (xdmcpSocket >= 0 && xdm_from != NULL) {
        if (bind(xdmcpSocket, (struct sockaddr *) &FromAddress,
                 FromAddressLen) < 0) {
            FatalError("Xserver: failed to bind to -from address: %s\n",
                       xdm_from);
        }
    }
#endif                          /* STREAMSCONN */
}
Exemplo n.º 4
0
/*
 * Bind a fd to a privileged IP port.
 * This is slightly different from the code in netdir_options
 * because it has a different interface - main thing is that it
 * needs to know its own address.  We also wanted to set the qlen.
 * t_getname() can be used for those purposes and perhaps job can be done.
 */
int
__rpc_bindresvport_ipv6(int fd, struct sockaddr *sin, int *portp, int qlen,
			char *fmly)
{
	int res;
	static in_port_t port, *sinport;
	struct sockaddr_in6 myaddr;
	int i;
	struct t_bind tbindstr, *tres;
	struct t_info tinfo;
	extern mutex_t portnum_lock;

	/* VARIABLES PROTECTED BY portnum_lock: port */

#define	STARTPORT 600
#define	ENDPORT (IPPORT_RESERVED - 1)
#define	NPORTS	(ENDPORT - STARTPORT + 1)

	if (sin == 0 && fmly == 0) {
		errno = EINVAL;
		return (-1);
	}
	if (geteuid()) {
		errno = EACCES;
		return (-1);
	}
	if ((i = t_getstate(fd)) != T_UNBND) {
		if (t_errno == TBADF)
			errno = EBADF;
		if (i != -1)
			errno = EISCONN;
		return (-1);
	}
	if (sin == 0) {
		sin = (struct sockaddr *)&myaddr;
		get_myaddress_ipv6(fmly, sin);
	}
	if (sin->sa_family == AF_INET) {
		/* LINTED pointer cast */
		sinport = &((struct sockaddr_in *)sin)->sin_port;
	} else if (sin->sa_family == AF_INET6) {
		/* LINTED pointer cast */
		sinport = &((struct sockaddr_in6 *)sin)->sin6_port;
	} else {
		errno = EPFNOSUPPORT;
		return (-1);
	}

	/* Transform sockaddr to netbuf */
	if (t_getinfo(fd, &tinfo) == -1) {
		return (-1);
	}
	/* LINTED pointer cast */
	tres = (struct t_bind *)t_alloc(fd, T_BIND, T_ADDR);
	if (tres == NULL)
		return (-1);

	tbindstr.qlen = qlen;
	tbindstr.addr.buf = (char *)sin;
	tbindstr.addr.len = tbindstr.addr.maxlen = __rpc_get_a_size(tinfo.addr);
	/* LINTED pointer cast */
	sin = (struct sockaddr *)tbindstr.addr.buf;

	res = -1;
	(void) mutex_lock(&portnum_lock);
	if (port == 0)
		port = (getpid() % NPORTS) + STARTPORT;
	for (i = 0; i < NPORTS; i++) {
		*sinport = htons(port++);
		if (port > ENDPORT)
			port = STARTPORT;
		res = t_bind(fd, &tbindstr, tres);
		if (res == 0) {
			if ((tbindstr.addr.len == tres->addr.len) &&
				(memcmp(tbindstr.addr.buf, tres->addr.buf,
					(int)tres->addr.len) == 0))
				break;
			(void) t_unbind(fd);
			res = -1;
		} else if (t_errno != TSYSERR || errno != EADDRINUSE)
			break;
	}
	(void) mutex_unlock(&portnum_lock);

	if ((portp != NULL) && (res == 0))
		*portp = *sinport;
	(void) t_free((char *)tres, T_BIND);
	return (res);
}
Exemplo n.º 5
0
/*
 * How to bind to reserved ports.
 * (port-only) version.
 */
int
bind_resv_port2(u_short *pp)
{
  int td, rc = -1, port;
  struct t_bind *treq, *tret;
  struct sockaddr_in *sin;
  extern char *t_errlist[];
  extern int t_errno;
  struct netconfig *nc = (struct netconfig *) NULL;
  voidp nc_handle;

  if ((nc_handle = setnetconfig()) == (voidp) NULL) {
    plog(XLOG_ERROR, "Cannot rewind netconfig: %s", nc_sperror());
    return -1;
  }
  /*
   * Search the netconfig table for INET/UDP.
   * This loop will terminate if there was an error in the /etc/netconfig
   * file or if you reached the end of the file without finding the udp
   * device.  Either way your machine has probably far more problems (for
   * example, you cannot have nfs v2 w/o UDP).
   */
  while (1) {
    if ((nc = getnetconfig(nc_handle)) == (struct netconfig *) NULL) {
      plog(XLOG_ERROR, "Error accessing getnetconfig: %s", nc_sperror());
      endnetconfig(nc_handle);
      return -1;
    }
    if (STREQ(nc->nc_protofmly, NC_INET) &&
	STREQ(nc->nc_proto, NC_UDP))
      break;
  }

  /*
   * This is the primary reason for the getnetconfig code above: to get the
   * correct device name to udp, and t_open a descriptor to be used in
   * t_bind below.
   */
  td = t_open(nc->nc_device, O_RDWR, (struct t_info *) 0);
  endnetconfig(nc_handle);

  if (td < 0) {
    plog(XLOG_ERROR, "t_open failed: %d: %s", t_errno, t_errlist[t_errno]);
    return -1;
  }
  treq = (struct t_bind *) t_alloc(td, T_BIND, T_ADDR);
  if (!treq) {
    plog(XLOG_ERROR, "t_alloc req");
    return -1;
  }
  tret = (struct t_bind *) t_alloc(td, T_BIND, T_ADDR);
  if (!tret) {
    t_free((char *) treq, T_BIND);
    plog(XLOG_ERROR, "t_alloc ret");
    return -1;
  }
  memset((char *) treq->addr.buf, 0, treq->addr.len);
  sin = (struct sockaddr_in *) treq->addr.buf;
  sin->sin_family = AF_INET;
  treq->qlen = 0;
  treq->addr.len = treq->addr.maxlen;
  errno = EADDRINUSE;
  port = IPPORT_RESERVED;

  do {
    --port;
    sin->sin_port = htons(port);
    rc = t_bind(td, treq, tret);
    if (rc < 0) {
      plog(XLOG_ERROR, "t_bind for port %d: %s", port, t_errlist[t_errno]);
    } else {
      if (memcmp(treq->addr.buf, tret->addr.buf, tret->addr.len) == 0)
	break;
      else
	t_unbind(td);
    }
  } while ((rc < 0 || errno == EADDRINUSE) && (int) port > IPPORT_RESERVED / 2);

  if (pp && rc == 0)
    *pp = port;
  t_free((char *) tret, T_BIND);
  t_free((char *) treq, T_BIND);
  return rc;
}