net/6lowpan/iphc.c

Source file repositories/reference/linux-study-clean/net/6lowpan/iphc.c

File Facts

System
Linux kernel
Corpus path
net/6lowpan/iphc.c
Extension
.c
Size
37568 bytes
Lines
1314
Domain
Networking Core
Bucket
Sockets, Protocols, Packet Path, And Network Policy
Inferred role
Networking Core: exported/initcall integration point
Status
integration implementation candidate

Why This File Exists

Networking stack implementation surface: socket APIs, protocol dispatch, packet flow, routing, filtering, and network namespaces.

Dependency Surface

Detected Declarations

Annotated Snippet

if (ipv6_prefix_equal(&addr_pfx, &table[i].pfx, addr_plen)) {
			/* remember first match */
			if (!ret) {
				ret = &table[i];
				continue;
			}

			/* get the context with longest prefix len */
			if (table[i].plen > ret->plen)
				ret = &table[i];
		}
	}

	return ret;
}

static struct lowpan_iphc_ctx *
lowpan_iphc_ctx_get_by_mcast_addr(const struct net_device *dev,
				  const struct in6_addr *addr)
{
	struct lowpan_iphc_ctx *table = lowpan_dev(dev)->ctx.table;
	struct lowpan_iphc_ctx *ret = NULL;
	struct in6_addr addr_mcast, network_pfx = {};
	int i;

	/* init mcast address with  */
	memcpy(&addr_mcast, addr, sizeof(*addr));

	for (i = 0; i < LOWPAN_IPHC_CTX_TABLE_SIZE; i++) {
		/* Check if context is valid. A context that is not valid
		 * MUST NOT be used for compression.
		 */
		if (!lowpan_iphc_ctx_is_active(&table[i]) ||
		    !lowpan_iphc_ctx_is_compression(&table[i]))
			continue;

		/* setting plen */
		addr_mcast.s6_addr[3] = table[i].plen;
		/* get network prefix to copy into multicast address */
		ipv6_addr_prefix(&network_pfx, &table[i].pfx,
				 table[i].plen);
		/* setting network prefix */
		memcpy(&addr_mcast.s6_addr[4], &network_pfx, 8);

		if (ipv6_addr_equal(addr, &addr_mcast)) {
			ret = &table[i];
			break;
		}
	}

	return ret;
}

static void lowpan_iphc_uncompress_lladdr(const struct net_device *dev,
					  struct in6_addr *ipaddr,
					  const void *lladdr)
{
	switch (dev->addr_len) {
	case ETH_ALEN:
		lowpan_iphc_uncompress_eui48_lladdr(ipaddr, lladdr);
		break;
	case EUI64_ADDR_LEN:
		lowpan_iphc_uncompress_eui64_lladdr(ipaddr, lladdr);
		break;
	default:
		WARN_ON_ONCE(1);
		break;
	}
}

/* Uncompress address function for source and
 * destination address(non-multicast).
 *
 * address_mode is the masked value for sam or dam value
 */
static int lowpan_iphc_uncompress_addr(struct sk_buff *skb,
				       const struct net_device *dev,
				       struct in6_addr *ipaddr,
				       u8 address_mode, const void *lladdr)
{
	bool fail;

	switch (address_mode) {
	/* SAM and DAM are the same here */
	case LOWPAN_IPHC_DAM_00:
		/* for global link addresses */
		fail = lowpan_fetch_skb(skb, ipaddr->s6_addr, 16);
		break;
	case LOWPAN_IPHC_SAM_01:
	case LOWPAN_IPHC_DAM_01:

Annotation

Implementation Notes