int main(int argc, char *argv[])
{
	struct nl_sock *h[1025];
	int i;

	h[0] = nl_handle_alloc();
	printf("Created handle with port 0x%x\n",
			nl_socket_get_local_port(h[0]));
	nl_handle_destroy(h[0]);
	h[0] = nl_handle_alloc();
	printf("Created handle with port 0x%x\n",
			nl_socket_get_local_port(h[0]));
	nl_handle_destroy(h[0]);

	for (i = 0; i < 1025; i++) {
		h[i] = nl_handle_alloc();
		if (h[i] == NULL)
			nl_perror("Unable to allocate socket");
		else
			printf("Created handle with port 0x%x\n",
				nl_socket_get_local_port(h[i]));
	}

	return 0;
}
Пример #2
0
	NetLinkManager::NetLinkManager()
	 : _initialized(false), _sock(NULL), _refresh_cache(false)
	{
		ibrcommon::MutexLock l(_call_mutex);

		_handle = nl_handle_alloc();
		nl_connect(_handle, NETLINK_ROUTE);

		_link_cache = rtnl_link_alloc_cache(_handle);

		if (_link_cache == NULL)
		{
			nl_close(_handle);
			nl_handle_destroy(_handle);
			throw ibrcommon::vsocket_exception("netlink cache allocation failed");
		}

		_addr_cache = rtnl_addr_alloc_cache(_handle);

		if (_addr_cache == NULL)
		{
			nl_close(_handle);
			nl_handle_destroy(_handle);
			nl_cache_free(_link_cache);
			_link_cache = NULL;
			throw ibrcommon::vsocket_exception("netlink cache allocation failed");
		}

		_initialized = true;

		// create a new socket for the netlink interface
		_sock = new ibrcommon::vsocket();
	}
Пример #3
0
int
kern_bcache_init()
{
	supsocket_t *sock;

	nl_bcache = nl_handle_alloc();
	nl_disable_sequence_check(nl_bcache);
	nl_join_groups(nl_bcache, ~0);

	nl_cb_set(nl_handle_get_cb(nl_bcache), NL_CB_VALID, NL_CB_CUSTOM,
		  nl_bcache_event, NULL);

	if (nl_connect(nl_bcache, NETLINK_IP6MBLTY) < 0) {
		debug_log(1, "nl_connect(NETLINK_IP6MBLTY) failed: %s.\n",
			  strerror(errno));
		nl_close(nl_bcache);
		nl_bcache = NULL;
		return -1;
	}

	fcntl(nl_handle_get_fd(nl_bcache), F_SETFL, O_NONBLOCK);

	sock = support_register_socket(nl_handle_get_fd(nl_bcache),
				       nl_bcache_events_waiting, NULL, NULL);
	sock->mode = SUPSOCKET_READ;

	return 0;
}
Пример #4
0
	void lowpansocket::getAddress(struct ieee802154_addr *ret, const vinterface &iface)
	{
#if defined HAVE_LIBNL || HAVE_LIBNL3
#ifdef HAVE_LIBNL3
		struct nl_sock *nl = nl_socket_alloc();
#else
		struct nl_handle *nl = nl_handle_alloc();
#endif
		unsigned char *buf = NULL;
		struct sockaddr_nl nla;
		struct nlattr *attrs[IEEE802154_ATTR_MAX+1];
		struct genlmsghdr *ghdr;
		struct nlmsghdr *nlh;
		struct nl_msg *msg;
		int family;

		if (!nl)
		        return;

		genl_connect(nl);

		/* Build and send message */
		msg = nlmsg_alloc();
		family = genl_ctrl_resolve(nl, "802.15.4 MAC");
		genlmsg_put(msg, NL_AUTO_PID, NL_AUTO_SEQ, family, 0, NLM_F_ECHO, IEEE802154_LIST_IFACE, 1);
		nla_put_string(msg, IEEE802154_ATTR_DEV_NAME, iface.toString().c_str());
		nl_send_auto_complete(nl, msg);
		nlmsg_free(msg);

		/* Receive and parse answer */
		nl_recv(nl, &nla, &buf, NULL);
		nlh = (struct nlmsghdr*)buf;
		genlmsg_parse(nlh, 0, attrs, IEEE802154_ATTR_MAX, ieee802154_policy);
		ghdr = (genlmsghdr*)nlmsg_data(nlh);
		if (!attrs[IEEE802154_ATTR_SHORT_ADDR] || !attrs[IEEE802154_ATTR_SHORT_ADDR])
		        return;

		// We only handle short addresses right now
		ret->addr_type = IEEE802154_ADDR_SHORT;
		ret->pan_id = nla_get_u16(attrs[IEEE802154_ATTR_PAN_ID]);
		ret->short_addr = nla_get_u16(attrs[IEEE802154_ATTR_SHORT_ADDR]);

		free(buf);
		nl_close(nl);

#ifdef HAVE_LIBNL3
		nl_socket_free(nl);
#else
		nl_handle_destroy(nl);
#endif
#endif
	}
Пример #5
0
int init_handle(struct nl_handle **handle)
{

    *handle = nl_handle_alloc();
    if (!*handle)
        return -1;

    if (nl_connect(*handle, NETLINK_ROUTE)) {
        nl_handle_destroy(*handle);
        return -1;
    }
    return 0;
}
Пример #6
0
int main(int argc, char *argv[])
{
	struct nl_handle *h;
	int i;

	for (i = 0; i < 1025; i++) {
		h = nl_handle_alloc();
		printf("Created handle with port 0x%x\n",
			nl_socket_get_local_port(h));
	}

	return 0;
}
Пример #7
0
	void NetLinkManager::run()
	{
		struct nl_handle *handle = nl_handle_alloc();
		nl_connect(handle, NETLINK_ROUTE);

		// init route messages
		nl_socket_add_membership(handle, RTNLGRP_IPV4_IFADDR);

//		IPv6 requires further support in the parsing procedures!
//		nl_socket_add_membership(handle, RTNLGRP_IPV6_IFADDR);
		nl_socket_add_membership(handle, RTNLGRP_LINK);

		// add netlink fd to vsocket
		_sock->add(nl_socket_get_fd(handle));

		try {
			while (_initialized)
			{
				std::list<int> fds;
				_sock->select(fds, NULL);
				int fd = fds.front();

				// create a new event object
				NetLinkManagerEvent lme(fd);

				// ignore if the event is unknown
				if (lme.getType() == LinkManagerEvent::EVENT_UNKOWN) continue;

				// ignore if this is an wireless extension event
				if (lme.isWirelessExtension()) continue;

				// need to refresh the cache
				{
					ibrcommon::MutexLock l(_call_mutex);
					_refresh_cache = true;
				}

				// print out some debugging
				IBRCOMMON_LOGGER_DEBUG(10) << lme.toString() << IBRCOMMON_LOGGER_ENDL;

				// notify all subscribers about this event
				raiseEvent(lme);
			}
		} catch (const vsocket_exception&) {
			// stopped / interrupted
			IBRCOMMON_LOGGER(error) << "NetLink connection stopped" << IBRCOMMON_LOGGER_ENDL;
		}

		nl_close(handle);
		nl_handle_destroy(handle);
	}
Пример #8
0
/*
 * Return a libnl handle for NETLINK_ROUTE.
 */
static struct nl_handle *_iface_get_handle(void) {
    struct nl_handle *handle = NULL;

    if ((handle = nl_handle_alloc()) == NULL) {
        return NULL;
    }

    if (nl_connect(handle, NETLINK_ROUTE)) {
        nl_handle_destroy(handle);
        return NULL;
    }

    return handle;
}
Пример #9
0
static struct nl_handle *init_netlink(void)
{
	struct nl_handle *handle;
	int ret, multicast_id;

	handle = nl_handle_alloc();
	if (!handle){
		elog("Cannot allocate netlink handle!\n");
		return NULL;
	}
	nl_disable_sequence_check(handle);
	ret = genl_connect(handle);
	if (ret < 0){
		elog("Cannot connect to netlink socket\n");
		return NULL;
	}

	/*
	familyid = genl_ctrl_resolve(handle, SAMPLE_NL_FAMILY_NAME);
	if (!familyid){
		elog("Cannot resolve family name(%s)\n", SAMPLE_NL_FAMILY_NAME);
		return NULL;
	}
	dlog("familyid %d\n", familyid);
	*/

	multicast_id = nl_get_multicast_id(handle, SAMPLE_NL_FAMILY_NAME, SAMPLE_NL_GRP_NAME);
	if (multicast_id < 0){
		elog("Cannot resolve grp name(%d)\n", SAMPLE_NL_GRP_NAME);
		return NULL;
	}

	ret = nl_socket_add_membership(handle, multicast_id);
	if (ret < 0){
		elog("Cannot join fs multicast group\n");
		return NULL;
	}

	ret = nl_socket_modify_cb(handle, NL_CB_VALID, NL_CB_CUSTOM,
			sample_nl_cb, NULL);
	if (ret < 0){
		elog("Cannot register callback for"
			 " netlink messages\n");
		return NULL;
	}

	return handle;
}
Пример #10
0
int main() {
	struct nl_handle *handle;
	struct nl_msg *msg;
	struct myhdr {
		char mychar[20];        
	} *hdr;
	int id;

	handle = nl_handle_alloc();
	if (handle == NULL)
	    goto open_failure;

	if (genl_connect(handle) != 0)
	    goto open_failure;

	id = genl_ctrl_resolve(handle, "CONTROL_EXMPL"); 
	if(id < 0) {
		perror("genl_ctrl_resolve\n");
		goto open_failure;
	}
	else
		printf("id %i\n", id);

	
	msg = nlmsg_alloc();
	memset(msg, 0, 16);
	int pid = getpid();
	int seq = 1;

	hdr = genlmsg_put(msg, pid, seq, id, sizeof(struct myhdr), NLM_F_REQUEST, 1, 1);

	memcpy(hdr->mychar, "hello world", strlen("hello world") + 1);

	int ret = nl_send(handle, msg);
	printf("message sent %i\n", ret);
	nlmsg_free(msg);

	return 0;

open_failure:
	if (handle) {
		nl_close(handle);
		nl_handle_destroy(handle);
	}
	printf("Erreur open_failure\n");
	return 0;

}
Пример #11
0
int usnic_rtnl_sk_alloc(struct usnic_rtnl_sk **p_sk)
{
	struct usnic_rtnl_sk *unlsk;
	struct nl_handle *nlh;
	int err;

	unlsk = calloc(1, sizeof(*unlsk));
	if (!unlsk) {
		usnic_err("Failed to allocate usnic_rtnl_sk struct\n");
		return -ENOMEM;
	}

	nlh =  nl_handle_alloc();
	if (!nlh) {
		usnic_err("Failed to allocate nl handle\n");
		err = -ENOMEM;
		goto err_free_unlsk;
	}

	err = nl_connect(nlh, NETLINK_ROUTE);
	if (err < 0) {
		usnic_err("Failed to connnect netlink route socket\n");
		goto err_free_nlh;
	}

	nl_disable_sequence_check(nlh);
	err = nl_set_recv_timeout(nlh);
	if (err < 0)
		goto err_close_nlh;

	unlsk->nlh = nlh;
	unlsk->seq = time(NULL);
	*p_sk = unlsk;
	return 0;

err_close_nlh:
	nl_close(nlh);
err_free_nlh:
	nl_handle_destroy(nlh);
err_free_unlsk:
	free(unlsk);
	return err;
}
static int netlink_init(void)
{
    info("Starting experimental netlink support");

    handle = nl_handle_alloc();
    if (!handle) {
        error("Failed to allocate netlink handle");
        return -ENOMEM;
    }

    if (genl_connect(handle) < 0) {
        error("Failed to connect to generic netlink");
        nl_handle_destroy(handle);
        return -ENOLINK;
    }

    cache = genl_ctrl_alloc_cache(handle);
    if (!cache) {
        error("Failed to allocate generic netlink cache");
        return -ENOMEM;
        nl_handle_destroy(handle);
    }

    family = genl_ctrl_search_by_name(cache, "bluetooth");
    if (!family) {
        error("Failed to find Bluetooth netlink family");
        nl_cache_free(cache);
        nl_handle_destroy(handle);
        return -ENOENT;
    }

    if (create_channel(nl_socket_get_fd(handle)) < 0)  {
        error("Failed to create netlink IO channel");
        genl_family_put(family);
        nl_cache_free(cache);
        nl_handle_destroy(handle);
        return -ENOMEM;
    }

    return 0;
}
Пример #13
0
/**
 * Connects to the NETLINK interface.  This will be called
 * for each etherinfo object being generated, and it will
 * keep a separate file descriptor open for each object
 *
 * @param data etherinfo_obj_data structure
 *
 * @return Returns 1 on success, otherwise 0.
 */
int open_netlink(struct etherinfo_obj_data *data)
{
	if( !data ) {
		return 0;
	}

	/* Reuse already established NETLINK connection, if a connection exists */
	if( *data->nlc ) {
		/* If this object has not used NETLINK earlier, tag it as a user */
		if( !data->nlc_active ) {
			pthread_mutex_lock(&nlc_counter_mtx);
			(*data->nlc_users)++;
			pthread_mutex_unlock(&nlc_counter_mtx);
		}
		data->nlc_active = 1;
		return 1;
	}

	/* No earlier connections exists, establish a new one */
	*data->nlc = nl_handle_alloc();
	nl_connect(*data->nlc, NETLINK_ROUTE);
	if( (*data->nlc != NULL) ) {
		/* Force O_CLOEXEC flag on the NETLINK socket */
		if( fcntl(nl_socket_get_fd(*data->nlc), F_SETFD, FD_CLOEXEC) == -1 ) {
			fprintf(stderr,
				"**WARNING** Failed to set O_CLOEXEC on NETLINK socket: %s\n",
				strerror(errno));
		}

		/* Tag this object as an active user */
		pthread_mutex_lock(&nlc_counter_mtx);
		(*data->nlc_users)++;
		pthread_mutex_unlock(&nlc_counter_mtx);
		data->nlc_active = 1;
		return 1;
	} else {
		return 0;
	}
}
Пример #14
0
static int
tcpTable_load_netlink(void)
{
    /*  TODO: perhaps use permanent nl handle? */
    struct nl_handle *nl = nl_handle_alloc();
    struct inet_diag_req req = {
        .idiag_family = AF_INET,
        .idiag_states = TCP_ALL,
    };

    struct nl_msg *nm;

    struct sockaddr_nl peer;
    unsigned char *buf = NULL;
    int running = 1, len;

    if (nl == NULL) {
        DEBUGMSGTL(("mibII/tcpTable", "Failed to allocate netlink handle\n"));
        snmp_log(LOG_ERR, "snmpd: Failed to allocate netlink handle\n");
        return -1;
    }

    if (nl_connect(nl, NETLINK_INET_DIAG) < 0) {
        DEBUGMSGTL(("mibII/tcpTable", "Failed to connect to netlink: %s\n", nl_geterror()));
        snmp_log(LOG_ERR, "snmpd: Couldn't connect to netlink: %s\n", nl_geterror());
        nl_handle_destroy(nl);
        return -1;
    }

    nm = nlmsg_alloc_simple(TCPDIAG_GETSOCK, NLM_F_ROOT|NLM_F_MATCH|NLM_F_REQUEST);
    nlmsg_append(nm, &req, sizeof(struct inet_diag_req), 0);

    if (nl_send_auto_complete(nl, nm) < 0) {
        DEBUGMSGTL(("mibII/tcpTable", "nl_send_autocomplete(): %s\n", nl_geterror()));
        snmp_log(LOG_ERR, "snmpd: nl_send_autocomplete(): %s\n", nl_geterror());
        nl_handle_destroy(nl);
        return -1;
    }
    nlmsg_free(nm);

    while (running) {
        struct nlmsghdr *h;
        if ((len = nl_recv(nl, &peer, &buf, NULL)) <= 0) {
            DEBUGMSGTL(("mibII/tcpTable", "nl_recv(): %s\n", nl_geterror()));
            snmp_log(LOG_ERR, "snmpd: nl_recv(): %s\n", nl_geterror());
            nl_handle_destroy(nl);
            return -1;
        }

        h = (struct nlmsghdr*)buf;

        while (nlmsg_ok(h, len)) {
            struct inet_diag_msg *r = nlmsg_data(h);
            struct inpcb    pcb, *nnew;

            if (h->nlmsg_type == NLMSG_DONE) {
                running = 0;
                break;
            }

            r = nlmsg_data(h);

            if (r->idiag_family != AF_INET) {
                h = nlmsg_next(h, &len);
                continue;
            }

            memcpy(&pcb.inp_laddr.s_addr, r->id.idiag_src, r->idiag_family == AF_INET ? 4 : 6);
            memcpy(&pcb.inp_faddr.s_addr, r->id.idiag_dst, r->idiag_family == AF_INET ? 4 : 6);

            pcb.inp_lport = r->id.idiag_sport;
            pcb.inp_fport = r->id.idiag_dport;

            pcb.inp_state = (r->idiag_state & 0xf) < 12 ? linux_states[r->idiag_state & 0xf] : 2;
            if (pcb.inp_state == 5 /* established */ ||
                    pcb.inp_state == 8 /*  closeWait  */ )
                tcp_estab++;
            pcb.uid = r->idiag_uid;

            nnew = SNMP_MALLOC_TYPEDEF(struct inpcb);
            if (nnew == NULL) {
                running = 0;
                /*  XXX report malloc error and return -1? */
                break;
            }
            memcpy(nnew, &pcb, sizeof(struct inpcb));
            nnew->inp_next = tcp_head;
            tcp_head       = nnew;

            h = nlmsg_next(h, &len);
        }
        free(buf);
    }

    nl_handle_destroy(nl);

    if (tcp_head) {
        DEBUGMSGTL(("mibII/tcpTable", "Loaded TCP Table using netlink\n"));
        return 0;
    }
    DEBUGMSGTL(("mibII/tcpTable", "Failed to load TCP Table (netlink)\n"));
    return -1;
}
Пример #15
0
/** 
 * Setups generic netlink connection with the kernel module and retrieves assocaited family id
 *
 * @return 0 on success
 */
static int initialize_netlink_family(void) {
	struct nl_handle* hndl;
	struct nl_msg* msg = NULL;
	struct nl_msg *ans_msg = NULL;
	struct nlmsghdr *nl_hdr;
	struct genlmsghdr* genl_hdr;
	struct nlattr *nla;
	int ret_val = 0;

	hndl = nl_handle_alloc();
	nl_set_buffer_size(hndl, 15000000, 15000000);
	
	//nl_handle_set_peer_pid(hndl, 0);
	//nl_set_passcred(hndl, 1);
	nl_disable_sequence_check(hndl);

	if ( (ret_val=nl_connect(hndl, NETLINK_GENERIC)) )
		goto init_return;
	
	nl_set_buffer_size(hndl, 15000000, 15000000);
  
	if ( (ret_val=prepare_request_message(hndl, CTRL_CMD_GETFAMILY, GENL_ID_CTRL, &msg) ) != 0 ) {
		goto init_return;
  	}
  
	ret_val = nla_put_string(msg,
		   CTRL_ATTR_FAMILY_NAME,
		   "DIRECTORCHNL");

  	if (ret_val != 0)
		goto init_return;

	if ( (ret_val = send_request_message(hndl, msg, 0) ) != 0 )
		goto init_return;
	if ( (ret_val = read_message(hndl, &ans_msg) ) != 0 )
		goto init_return;

	genl_hdr = nl_msg_genlhdr(ans_msg);
 	if (genl_hdr == NULL || genl_hdr->cmd != CTRL_CMD_NEWFAMILY) {
    		ret_val = -EBADMSG;
    		goto init_return;
  	}

	nla = nlmsg_find_attr(nlmsg_hdr(ans_msg), sizeof(struct genlmsghdr), CTRL_ATTR_FAMILY_ID);
  	if (nla == NULL) {
    		ret_val = -EBADMSG;
    		goto init_return;
  	}

  	state.gnl_fid = nla_get_u16(nla);  
  	if (state.gnl_fid == 0) {
    		ret_val = -EBADMSG;
    		goto init_return;
  	}
  	  	

  	state.handle = hndl;

	return 0;

init_return:
	nlmsg_free(ans_msg);
	
	if ( state.handle == NULL ) {
		nl_close(hndl);
		nl_handle_destroy(hndl);
  	}

	return -EINVAL;
}
Пример #16
0
static inline struct nl_handle *nl_socket_alloc(void)
{
	return nl_handle_alloc();
}
Пример #17
0
void new_comunication(){
	sock = nl_handle_alloc ();
	genl_connect ( sock );
	family = genl_ctrl_resolve ( sock , " SNF_GENL " );
	msg = nlmsg_alloc();
}
Пример #18
0
int nlComm(struct nl_msg *nl_msg,
           unsigned char **respbuf, unsigned int *respbuflen,
           int nl_pid)
{
    int rc = 0;
    struct sockaddr_nl nladdr = {
            .nl_family = AF_NETLINK,
            .nl_pid    = nl_pid,
            .nl_groups = 0,
    };
    ssize_t nbytes;
    struct timeval tv = {
        .tv_sec = NETLINK_ACK_TIMEOUT_S,
    };
    fd_set readfds;
    int fd;
    int n;
    struct nlmsghdr *nlmsg = nlmsg_hdr(nl_msg);
    struct nl_handle *nlhandle = nl_handle_alloc();

    if (!nlhandle) {
        virReportSystemError(errno,
                             "%s", _("cannot allocate nlhandle for netlink"));
        return -1;
    }

    if (nl_connect(nlhandle, NETLINK_ROUTE) < 0) {
        virReportSystemError(errno,
                             "%s", _("cannot connect to netlink socket"));
        rc = -1;
        goto err_exit;
    }

    nlmsg_set_dst(nl_msg, &nladdr);

    nlmsg->nlmsg_pid = getpid();

    nbytes = nl_send_auto_complete(nlhandle, nl_msg);
    if (nbytes < 0) {
        virReportSystemError(errno,
                             "%s", _("cannot send to netlink socket"));
        rc = -1;
        goto err_exit;
    }

    fd = nl_socket_get_fd(nlhandle);

    FD_ZERO(&readfds);
    FD_SET(fd, &readfds);

    n = select(fd + 1, &readfds, NULL, NULL, &tv);
    if (n <= 0) {
        if (n < 0)
            virReportSystemError(errno, "%s",
                                 _("error in select call"));
        if (n == 0)
            virReportSystemError(ETIMEDOUT, "%s",
                                 _("no valid netlink response was received"));
        rc = -1;
        goto err_exit;
    }

    *respbuflen = nl_recv(nlhandle, &nladdr, respbuf, NULL);
    if (*respbuflen <= 0) {
        virReportSystemError(errno,
                             "%s", _("nl_recv failed"));
        rc = -1;
    }
err_exit:
    if (rc == -1) {
        VIR_FREE(*respbuf);
        *respbuf = NULL;
        *respbuflen = 0;
    }

    nl_handle_destroy(nlhandle);
    return rc;
}

#else

int nlComm(struct nl_msg *nl_msg ATTRIBUTE_UNUSED,
           unsigned char **respbuf ATTRIBUTE_UNUSED,
           unsigned int *respbuflen ATTRIBUTE_UNUSED,
           int nl_pid ATTRIBUTE_UNUSED)
{
    netlinkError(VIR_ERR_INTERNAL_ERROR, "%s",
# if defined(__linux__) && !defined(HAVE_LIBNL)
                 _("nlComm is not supported since libnl was not available"));
# else
                 _("nlComm is not supported on non-linux platforms"));
# endif
    return -1;
}
struct nl_handle *nltool_alloc_handle(void)
{
	return nl_handle_alloc();
}
Пример #20
0
int netlink_wrapper::open_channel()
{
	auto_unlocker lock(m_cache_lock);
	nl_logdbg("opening netlink channel");

	/*
	 // build to subscriptions groups mask for indicating what type of events the kernel will send on channel
	 unsigned subscriptions = ~RTMGRP_TC;
	 if (netlink_route_group_mask & nlgrpLINK) {
	 subscriptions |= (1 << (RTNLGRP_LINK - 1));
	 }
	 if (netlink_route_group_mask & nlgrpADDRESS) {
	 if (!m_preferred_family || m_preferred_family == AF_INET)
	 subscriptions |= (1 << (RTNLGRP_IPV4_IFADDR - 1));
	 if (!m_preferred_family || m_preferred_family == AF_INET6)
	 subscriptions |= (1 << (RTNLGRP_IPV6_IFADDR - 1));
	 }
	 if (netlink_route_group_mask & nlgrpROUTE) {
	 if (!m_preferred_family || m_preferred_family == AF_INET)
	 subscriptions |= (1 << (RTNLGRP_IPV4_ROUTE - 1));
	 if (!m_preferred_family || m_preferred_family == AF_INET6)
	 subscriptions |= (1 << (RTNLGRP_IPV4_ROUTE - 1));
	 }
	 if (netlink_route_group_mask & nlgrpPREFIX) {
	 if (!m_preferred_family || m_preferred_family == AF_INET6)
	 subscriptions |= (1 << (RTNLGRP_IPV6_PREFIX - 1));
	 }
	 if (netlink_route_group_mask & nlgrpNEIGH) {
	 subscriptions |= (1 << (RTNLGRP_NEIGH - 1));
	 }
	 */

	// Allocate a new netlink handle
	m_handle = nl_handle_alloc();

	BULLSEYE_EXCLUDE_BLOCK_START
	if (m_handle == NULL) {
		nl_logerr("failed to allocate netlink handle, nl_errno=%d", nl_get_errno());
		return -1;
	}
	BULLSEYE_EXCLUDE_BLOCK_END

	// set internal structure to pass the handle with callbacks from netlink
	g_nl_rcv_arg.handle = m_handle;

	// if multiple handles being allocated then a unique netlink PID need to be provided
	// If port is 0, a unique port identifier will be generated automatically as a unique PID
	nl_socket_set_local_port(m_handle, 0);


	//Disables checking of sequence numbers on the netlink handle.
	//This is required to allow messages to be processed which were not requested by a preceding request message, e.g. netlink events.
	nl_disable_sequence_check(m_handle);

	//joining group
	//nl_join_groups(m_handle, 0);

	// Allocate a new cache manager for RTNETLINK
	// NL_AUTO_PROVIDE = automatically provide the caches added to the manager.
	m_mngr = nl_cache_mngr_alloc(m_handle, NETLINK_ROUTE, NL_AUTO_PROVIDE);

	BULLSEYE_EXCLUDE_BLOCK_START
	if (!m_mngr) {
		nl_logerr("Fail to allocate cac he manager");
		return -1;
	}
	BULLSEYE_EXCLUDE_BLOCK_END

	nl_logdbg("netlink socket is open");

	m_cache_neigh = nl_cache_mngr_add(m_mngr, "route/neigh", neigh_cache_callback);
	m_cache_link = nl_cache_mngr_add(m_mngr, "route/link", link_cache_callback);
	m_cache_route = nl_cache_mngr_add(m_mngr, "route/route", route_cache_callback);

	// set custom callback for every message to update message
	nl_socket_modify_cb(m_handle, NL_CB_MSG_IN, NL_CB_CUSTOM, nl_msg_rcv_cb ,NULL);

	// set the socket non-blocking
	BULLSEYE_EXCLUDE_BLOCK_START
	if (nl_socket_set_nonblocking(m_handle)) {
		nl_logerr("Failed to set the socket non-blocking");
		return -1;
	}
	BULLSEYE_EXCLUDE_BLOCK_END

	return 0;

}