예제 #1
0
int dhcp6_network_bind_udp_socket(int index, struct in6_addr *local_address) {
        union sockaddr_union src = {
                .in6.sin6_family = AF_INET6,
                .in6.sin6_port = htobe16(DHCP6_PORT_CLIENT),
                .in6.sin6_scope_id = index,
        };
        _cleanup_close_ int s = -1;
        int r;

        assert(index > 0);
        assert(local_address);

        src.in6.sin6_addr = *local_address;

        s = socket(AF_INET6, SOCK_DGRAM | SOCK_CLOEXEC | SOCK_NONBLOCK, IPPROTO_UDP);
        if (s < 0)
                return -errno;

        r = setsockopt_int(s, IPPROTO_IPV6, IPV6_V6ONLY, true);
        if (r < 0)
                return r;

        r = setsockopt_int(s, IPPROTO_IPV6, IPV6_MULTICAST_LOOP, false);
        if (r < 0)
                return r;

        r = setsockopt_int(s, SOL_SOCKET, SO_REUSEADDR, true);
        if (r < 0)
                return r;

        r = bind(s, &src.sa, sizeof(src.in6));
        if (r < 0)
                return -errno;

        return TAKE_FD(s);
}

int dhcp6_network_send_udp_socket(int s, struct in6_addr *server_address,
                                  const void *packet, size_t len) {
        union sockaddr_union dest = {
                .in6.sin6_family = AF_INET6,
                .in6.sin6_port = htobe16(DHCP6_PORT_SERVER),
        };
        int r;

        assert(server_address);

        memcpy(&dest.in6.sin6_addr, server_address, sizeof(dest.in6.sin6_addr));

        r = sendto(s, packet, len, 0, &dest.sa, sizeof(dest.in6));
        if (r < 0)
                return -errno;

        return 0;
}
예제 #2
0
int server_open_native_socket(Server *s) {

        static const union sockaddr_union sa = {
                .un.sun_family = AF_UNIX,
                .un.sun_path = "/run/systemd/journal/socket",
        };
        int r;

        assert(s);

        if (s->native_fd < 0) {
                s->native_fd = socket(AF_UNIX, SOCK_DGRAM|SOCK_CLOEXEC|SOCK_NONBLOCK, 0);
                if (s->native_fd < 0)
                        return log_error_errno(errno, "socket() failed: %m");

                (void) sockaddr_un_unlink(&sa.un);

                r = bind(s->native_fd, &sa.sa, SOCKADDR_UN_LEN(sa.un));
                if (r < 0)
                        return log_error_errno(errno, "bind(%s) failed: %m", sa.un.sun_path);

                (void) chmod(sa.un.sun_path, 0666);
        } else
                (void) fd_nonblock(s->native_fd, true);

        r = setsockopt_int(s->native_fd, SOL_SOCKET, SO_PASSCRED, true);
        if (r < 0)
                return log_error_errno(r, "SO_PASSCRED failed: %m");

#if HAVE_SELINUX
        if (mac_selinux_use()) {
                r = setsockopt_int(s->native_fd, SOL_SOCKET, SO_PASSSEC, true);
                if (r < 0)
                        log_warning_errno(r, "SO_PASSSEC failed: %m");
        }
#endif

        r = setsockopt_int(s->native_fd, SOL_SOCKET, SO_TIMESTAMP, true);
        if (r < 0)
                return log_error_errno(r, "SO_TIMESTAMP failed: %m");

        r = sd_event_add_io(s->event, &s->native_event_source, s->native_fd, EPOLLIN, server_process_datagram, s);
        if (r < 0)
                return log_error_errno(r, "Failed to add native server fd to event loop: %m");

        r = sd_event_source_set_priority(s->native_event_source, SD_EVENT_PRIORITY_NORMAL+5);
        if (r < 0)
                return log_error_errno(r, "Failed to adjust native event source priority: %m");

        return 0;
}
예제 #3
0
파일: tcpio.c 프로젝트: hakit-dev/hakit
static int setsockopt_keepalive(int sock)
{
	if (setsockopt_int(sock, SOL_SOCKET, SO_KEEPALIVE, 1) < 0) {
		return -1;
	}
	if (setsockopt_int(sock, IPPROTO_TCP, TCP_KEEPIDLE, KEEPALIVE_IDLE)) {
		return -1;
	}
	if (setsockopt_int(sock, IPPROTO_TCP, TCP_KEEPINTVL, KEEPALIVE_INTVL)) {
		return -1;
	}
	if (setsockopt_int(sock, IPPROTO_TCP, TCP_KEEPCNT, KEEPALIVE_CNT)) {
		return -1;
	}

	return 0;
}
예제 #4
0
/**
 * Mark address behind socket S as reusable. */
static inline int
setsock_reuseaddr(int s)
{
#if defined SO_REUSEADDR
	return setsockopt_int(s, SOL_SOCKET, SO_REUSEADDR, 1);
#else  /* !SO_REUSEADDR */
	return 0;
#endif	/* SO_REUSEADDR */
}
예제 #5
0
파일: tcpio.c 프로젝트: hakit-dev/hakit
int tcp_srv_init(tcp_srv_t *srv, int port, tcp_func_t func, void *user_data)
{
	struct sockaddr_in ilocal;

	tcp_srv_clear(srv);

	/* Create network socket */
	if ((srv->csock.chan.fd = socket(PF_INET, SOCK_STREAM, 0)) == -1) {
		log_str("ERROR: socket(PF_INET, SOCK_STREAM): %s", strerror(errno));
		return -1;
	}

	setsockopt_int(srv->csock.chan.fd, SOL_SOCKET, SO_REUSEADDR, 1);

	/* Bind network socket */
	ilocal.sin_family = AF_INET;
	ilocal.sin_addr.s_addr = htonl(INADDR_ANY);
	ilocal.sin_port = htons(port);

	if (bind(srv->csock.chan.fd, (struct sockaddr *) &ilocal, sizeof(ilocal)) == -1) { 
		log_str("ERROR: bind(%d): %s", port, strerror(errno));
		close(srv->csock.chan.fd);
		srv->csock.chan.fd = -1;
		return -1;
	}

	/* Listen to network connection (with backlog of maximum 1 pending connection) */
	if (listen(srv->csock.chan.fd, 1) == -1) {
		log_str("ERROR: listen: %s", strerror(errno));
		close(srv->csock.chan.fd);
		srv->csock.chan.fd = -1;
		return -1;
	}
	log_str("Listening to TCP connections from port %d", port);

	/* Prevent child processes from inheriting this socket */
	fcntl(srv->csock.chan.fd, F_SETFD, FD_CLOEXEC);
	srv->csock.chan.tag = sys_io_watch(srv->csock.chan.fd, (sys_io_func_t) tcp_srv_csock_event, srv);

	srv->func = func;
	srv->user_data = user_data;

	return 0;
}
예제 #6
0
static void ping6(len_and_sockaddr *lsa)
{
	struct icmp6_hdr *pkt;
	int c;
	int sockopt;

	pkt = (struct icmp6_hdr *) G.packet;
	/*memset(pkt, 0, sizeof(G.packet)); already is */
	pkt->icmp6_type = ICMP6_ECHO_REQUEST;
	pkt->icmp6_id = G.myid;

	sockopt = offsetof(struct icmp6_hdr, icmp6_cksum);
	setsockopt_int(pingsock, SOL_RAW, IPV6_CHECKSUM, sockopt);

	xsendto(pingsock, G.packet, DEFDATALEN + sizeof(struct icmp6_hdr), &lsa->u.sa, lsa->len);

	/* listen for replies */
	while (1) {
#if 0
		struct sockaddr_in6 from;
		socklen_t fromlen = sizeof(from);

		c = recvfrom(pingsock, G.packet, sizeof(G.packet), 0,
				(struct sockaddr *) &from, &fromlen);
#else
		c = recv(pingsock, G.packet, sizeof(G.packet), 0);
#endif
		if (c < 0) {
			if (errno != EINTR)
				bb_perror_msg("recvfrom");
			continue;
		}
		if (c >= ICMP_MINLEN) {	/* icmp6_hdr */
			if (pkt->icmp6_id != G.myid)
				continue; /* not our ping */
			if (pkt->icmp6_type == ICMP6_ECHO_REPLY)
				break;
		}
	}
	if (ENABLE_FEATURE_CLEAN_UP)
		close(pingsock);
}
예제 #7
0
int FAST_FUNC setsockopt_SOL_SOCKET_int(int fd, int optname, int optval)
{
	return setsockopt_int(fd, SOL_SOCKET, optname, optval);
}
예제 #8
0
int FAST_FUNC setsockopt_1(int fd, int level, int optname)
{
	return setsockopt_int(fd, level, optname, 1);
}
예제 #9
0
static void
send_probe(int seq, int ttl)
{
	int len, res;
	void *out;

	/* Payload */
#if ENABLE_TRACEROUTE6
	if (dest_lsa->u.sa.sa_family == AF_INET6) {
		struct outdata6_t *pkt = (struct outdata6_t *) outip;
		pkt->ident6 = htonl(ident);
		pkt->seq6   = htonl(seq);
		/*gettimeofday(&pkt->tv, &tz);*/
	} else
#endif
	{
		outdata->seq = seq;
		outdata->ttl = ttl;
// UNUSED: was storing gettimeofday's result there, but never ever checked it
		/*memcpy(&outdata->tv, tp, sizeof(outdata->tv));*/

		if (option_mask32 & OPT_USE_ICMP) {
			outicmp->icmp_seq = htons(seq);

			/* Always calculate checksum for icmp packets */
			outicmp->icmp_cksum = 0;
			outicmp->icmp_cksum = inet_cksum((uint16_t *)outicmp,
						packlen - (sizeof(*outip) + optlen));
			if (outicmp->icmp_cksum == 0)
				outicmp->icmp_cksum = 0xffff;
		}
	}

//BUG! verbose is (x & OPT_VERBOSE), not a counter!
#if 0 //ENABLE_FEATURE_TRACEROUTE_VERBOSE
	/* XXX undocumented debugging hack */
	if (verbose > 1) {
		const uint16_t *sp;
		int nshorts, i;

		sp = (uint16_t *)outip;
		nshorts = (unsigned)packlen / sizeof(uint16_t);
		i = 0;
		printf("[ %d bytes", packlen);
		while (--nshorts >= 0) {
			if ((i++ % 8) == 0)
				printf("\n\t");
			printf(" %04x", ntohs(*sp));
			sp++;
		}
		if (packlen & 1) {
			if ((i % 8) == 0)
				printf("\n\t");
			printf(" %02x", *(unsigned char *)sp);
		}
		printf("]\n");
	}
#endif

#if ENABLE_TRACEROUTE6
	if (dest_lsa->u.sa.sa_family == AF_INET6) {
		res = setsockopt_int(sndsock, SOL_IPV6, IPV6_UNICAST_HOPS, ttl);
		if (res != 0)
			bb_perror_msg_and_die("setsockopt(%s) %d", "UNICAST_HOPS", ttl);
		out = outip;
		len = packlen;
	} else
#endif
	{
#if defined IP_TTL
		res = setsockopt_int(sndsock, IPPROTO_IP, IP_TTL, ttl);
		if (res != 0)
			bb_perror_msg_and_die("setsockopt(%s) %d", "TTL", ttl);
#endif
		out = outicmp;
		len = packlen - sizeof(*outip);
		if (!(option_mask32 & OPT_USE_ICMP)) {
			out = outdata;
			len -= sizeof(*outudp);
			set_nport(&dest_lsa->u.sa, htons(port + seq));
		}
	}

	res = xsendto(sndsock, out, len, &dest_lsa->u.sa, dest_lsa->len);
	if (res != len)
		bb_info_msg("sent %d octets, ret=%d", len, res);
}