diff --git a/platform/linux-generic/include/odp_packet_internal.h b/platform/linux-generic/include/odp_packet_internal.h
index 9b4f59e..b23ad9c 100644
--- a/platform/linux-generic/include/odp_packet_internal.h
+++ b/platform/linux-generic/include/odp_packet_internal.h
@@ -328,9 +328,6 @@ int packet_alloc_multi(odp_pool_t pool_hdl, uint32_t len,
 /* Fill in parser metadata for L2 */
 void packet_parse_l2(packet_parser_t *prs, uint32_t frame_len);
 
-/* Perform full packet parse */
-int packet_parse_full(odp_packet_hdr_t *pkt_hdr);
-
 /* Perform packet parse up to a given protocol layer */
 int packet_parse_layer(odp_packet_hdr_t *pkt_hdr, layer_t layer);
 
diff --git a/platform/linux-generic/odp_classification.c b/platform/linux-generic/odp_classification.c
index 868058d..82760e8 100644
--- a/platform/linux-generic/odp_classification.c
+++ b/platform/linux-generic/odp_classification.c
@@ -775,7 +775,7 @@ static inline cos_t *cls_select_cos(pktio_entry_t *entry,
 
 	/* Check for lazy parse needed */
 	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+		packet_parse_layer(pkt_hdr, LAYER_ALL);
 
 	/* Return error cos for error packet */
 	if (pkt_hdr->p.error_flags.all)
diff --git a/platform/linux-generic/odp_packet.c b/platform/linux-generic/odp_packet.c
index 5f84869..df6fd1e 100644
--- a/platform/linux-generic/odp_packet.c
+++ b/platform/linux-generic/odp_packet.c
@@ -476,8 +476,8 @@ void *odp_packet_l3_ptr(odp_packet_t pkt, uint32_t *len)
 {
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L3)
+		packet_parse_layer(pkt_hdr, LAYER_L3);
 	return packet_map(pkt_hdr, pkt_hdr->p.l3_offset, len);
 }
 
@@ -485,8 +485,8 @@ uint32_t odp_packet_l3_offset(odp_packet_t pkt)
 {
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L3)
+		packet_parse_layer(pkt_hdr, LAYER_L3);
 	return pkt_hdr->p.l3_offset;
 }
 
@@ -497,8 +497,8 @@ int odp_packet_l3_offset_set(odp_packet_t pkt, uint32_t offset)
 	if (offset >= pkt_hdr->frame_len)
 		return -1;
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L3)
+		packet_parse_layer(pkt_hdr, LAYER_L3);
 	pkt_hdr->p.l3_offset = offset;
 	return 0;
 }
@@ -507,8 +507,8 @@ void *odp_packet_l4_ptr(odp_packet_t pkt, uint32_t *len)
 {
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L4)
+		packet_parse_layer(pkt_hdr, LAYER_L4);
 	return packet_map(pkt_hdr, pkt_hdr->p.l4_offset, len);
 }
 
@@ -516,8 +516,8 @@ uint32_t odp_packet_l4_offset(odp_packet_t pkt)
 {
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L4)
+		packet_parse_layer(pkt_hdr, LAYER_L4);
 	return pkt_hdr->p.l4_offset;
 }
 
@@ -528,8 +528,8 @@ int odp_packet_l4_offset_set(odp_packet_t pkt, uint32_t offset)
 	if (offset >= pkt_hdr->frame_len)
 		return -1;
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L4)
+		packet_parse_layer(pkt_hdr, LAYER_L4);
 	pkt_hdr->p.l4_offset = offset;
 	return 0;
 }
@@ -1354,18 +1354,6 @@ parse_exit:
 /**
  * Simple packet parser
  */
-int packet_parse_full(odp_packet_hdr_t *pkt_hdr)
-{
-	uint32_t seg_len;
-	void *base = packet_map(pkt_hdr, 0, &seg_len);
-
-	return packet_parse_common(&pkt_hdr->p, base, pkt_hdr->frame_len,
-				   seg_len, LAYER_ALL);
-}
-
-/**
- * Simple packet parser
- */
 int packet_parse_layer(odp_packet_hdr_t *pkt_hdr, layer_t layer)
 {
 	uint32_t seg_len;
diff --git a/platform/linux-generic/odp_packet_flags.c b/platform/linux-generic/odp_packet_flags.c
index b88324c..798fa11 100644
--- a/platform/linux-generic/odp_packet_flags.c
+++ b/platform/linux-generic/odp_packet_flags.c
@@ -7,17 +7,17 @@
 #include <odp/api/packet_flags.h>
 #include <odp_packet_internal.h>
 
-#define retflag(pkt, x) do {                             \
+#define retflag(pkt, x, layer) do {                      \
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt); \
-	if (packet_parse_not_complete(pkt_hdr))          \
-		packet_parse_full(pkt_hdr);              \
+	if (pkt_hdr->p.parsed_layers < layer)            \
+		packet_parse_layer(pkt_hdr, layer);      \
 	return pkt_hdr->p.x;                             \
 	} while (0)
 
-#define setflag(pkt, x, v) do {                          \
+#define setflag(pkt, x, v, layer) do {                   \
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt); \
-	if (packet_parse_not_complete(pkt_hdr))          \
-		packet_parse_full(pkt_hdr);              \
+	if (pkt_hdr->p.parsed_layers < layer)            \
+		packet_parse_layer(pkt_hdr, layer);      \
 	pkt_hdr->p.x = v & 1;                            \
 	} while (0)
 
@@ -26,7 +26,7 @@ int odp_packet_has_error(odp_packet_t pkt)
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
 	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+		packet_parse_layer(pkt_hdr, LAYER_ALL);
 	return odp_packet_hdr(pkt)->p.error_flags.all != 0;
 }
 
@@ -51,30 +51,30 @@ int odp_packet_has_l2_error(odp_packet_t pkt)
 
 int odp_packet_has_l3(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.l3);
+	retflag(pkt, input_flags.l3, LAYER_L3);
 }
 
 int odp_packet_has_l3_error(odp_packet_t pkt)
 {
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L3)
+		packet_parse_layer(pkt_hdr, LAYER_L3);
 
 	return pkt_hdr->p.error_flags.ip_err;
 }
 
 int odp_packet_has_l4(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.l4);
+	retflag(pkt, input_flags.l4, LAYER_L4);
 }
 
 int odp_packet_has_l4_error(odp_packet_t pkt)
 {
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
-	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+	if (pkt_hdr->p.parsed_layers < LAYER_L4)
+		packet_parse_layer(pkt_hdr, LAYER_L4);
 
 	return pkt_hdr->p.error_flags.tcp_err | pkt_hdr->p.error_flags.udp_err;
 }
@@ -88,12 +88,12 @@ int odp_packet_has_eth(odp_packet_t pkt)
 
 int odp_packet_has_eth_bcast(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.eth_bcast);
+	retflag(pkt, input_flags.eth_bcast, LAYER_L2);
 }
 
 int odp_packet_has_eth_mcast(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.eth_mcast);
+	retflag(pkt, input_flags.eth_mcast, LAYER_L2);
 }
 
 int odp_packet_has_jumbo(odp_packet_t pkt)
@@ -105,72 +105,72 @@ int odp_packet_has_jumbo(odp_packet_t pkt)
 
 int odp_packet_has_vlan(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.vlan);
+	retflag(pkt, input_flags.vlan, LAYER_L2);
 }
 
 int odp_packet_has_vlan_qinq(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.vlan_qinq);
+	retflag(pkt, input_flags.vlan_qinq, LAYER_L2);
 }
 
 int odp_packet_has_arp(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.arp);
+	retflag(pkt, input_flags.arp, LAYER_L3);
 }
 
 int odp_packet_has_ipv4(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ipv4);
+	retflag(pkt, input_flags.ipv4, LAYER_L3);
 }
 
 int odp_packet_has_ipv6(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ipv6);
+	retflag(pkt, input_flags.ipv6, LAYER_L3);
 }
 
 int odp_packet_has_ip_bcast(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ip_bcast);
+	retflag(pkt, input_flags.ip_bcast, LAYER_L3);
 }
 
 int odp_packet_has_ip_mcast(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ip_mcast);
+	retflag(pkt, input_flags.ip_mcast, LAYER_L3);
 }
 
 int odp_packet_has_ipfrag(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ipfrag);
+	retflag(pkt, input_flags.ipfrag, LAYER_L3);
 }
 
 int odp_packet_has_ipopt(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ipopt);
+	retflag(pkt, input_flags.ipopt, LAYER_L3);
 }
 
 int odp_packet_has_ipsec(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.ipsec);
+	retflag(pkt, input_flags.ipsec, LAYER_L4);
 }
 
 int odp_packet_has_udp(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.udp);
+	retflag(pkt, input_flags.udp, LAYER_L4);
 }
 
 int odp_packet_has_tcp(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.tcp);
+	retflag(pkt, input_flags.tcp, LAYER_L4);
 }
 
 int odp_packet_has_sctp(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.sctp);
+	retflag(pkt, input_flags.sctp, LAYER_L4);
 }
 
 int odp_packet_has_icmp(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.icmp);
+	retflag(pkt, input_flags.icmp, LAYER_L4);
 }
 
 int odp_packet_has_flow_hash(odp_packet_t pkt)
@@ -189,7 +189,7 @@ int odp_packet_has_ts(odp_packet_t pkt)
 
 odp_packet_color_t odp_packet_color(odp_packet_t pkt)
 {
-	retflag(pkt, input_flags.color);
+	retflag(pkt, input_flags.color, LAYER_ALL);
 }
 
 void odp_packet_color_set(odp_packet_t pkt, odp_packet_color_t color)
@@ -197,7 +197,7 @@ void odp_packet_color_set(odp_packet_t pkt, odp_packet_color_t color)
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
 	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+		packet_parse_layer(pkt_hdr, LAYER_ALL);
 
 	pkt_hdr->p.input_flags.color = color;
 }
@@ -207,19 +207,19 @@ odp_bool_t odp_packet_drop_eligible(odp_packet_t pkt)
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
 	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+		packet_parse_layer(pkt_hdr, LAYER_ALL);
 
 	return !pkt_hdr->p.input_flags.nodrop;
 }
 
 void odp_packet_drop_eligible_set(odp_packet_t pkt, odp_bool_t drop)
 {
-	setflag(pkt, input_flags.nodrop, !drop);
+	setflag(pkt, input_flags.nodrop, !drop, LAYER_ALL);
 }
 
 int8_t odp_packet_shaper_len_adjust(odp_packet_t pkt)
 {
-	retflag(pkt, output_flags.shaper_len_adj);
+	retflag(pkt, output_flags.shaper_len_adj, LAYER_ALL);
 }
 
 void odp_packet_shaper_len_adjust_set(odp_packet_t pkt, int8_t adj)
@@ -227,7 +227,7 @@ void odp_packet_shaper_len_adjust_set(odp_packet_t pkt, int8_t adj)
 	odp_packet_hdr_t *pkt_hdr = odp_packet_hdr(pkt);
 
 	if (packet_parse_not_complete(pkt_hdr))
-		packet_parse_full(pkt_hdr);
+		packet_parse_layer(pkt_hdr, LAYER_ALL);
 
 	pkt_hdr->p.output_flags.shaper_len_adj = adj;
 }
@@ -236,107 +236,107 @@ void odp_packet_shaper_len_adjust_set(odp_packet_t pkt, int8_t adj)
 
 void odp_packet_has_l2_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.l2, val);
+	setflag(pkt, input_flags.l2, val, LAYER_L2);
 }
 
 void odp_packet_has_l3_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.l3, val);
+	setflag(pkt, input_flags.l3, val, LAYER_L3);
 }
 
 void odp_packet_has_l4_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.l4, val);
+	setflag(pkt, input_flags.l4, val, LAYER_L4);
 }
 
 void odp_packet_has_eth_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.eth, val);
+	setflag(pkt, input_flags.eth, val, LAYER_L2);
 }
 
 void odp_packet_has_eth_bcast_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.eth_bcast, val);
+	setflag(pkt, input_flags.eth_bcast, val, LAYER_L2);
 }
 
 void odp_packet_has_eth_mcast_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.eth_mcast, val);
+	setflag(pkt, input_flags.eth_mcast, val, LAYER_L2);
 }
 
 void odp_packet_has_jumbo_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.jumbo, val);
+	setflag(pkt, input_flags.jumbo, val, LAYER_L2);
 }
 
 void odp_packet_has_vlan_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.vlan, val);
+	setflag(pkt, input_flags.vlan, val, LAYER_L2);
 }
 
 void odp_packet_has_vlan_qinq_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.vlan_qinq, val);
+	setflag(pkt, input_flags.vlan_qinq, val, LAYER_L2);
 }
 
 void odp_packet_has_arp_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.arp, val);
+	setflag(pkt, input_flags.arp, val, LAYER_L3);
 }
 
 void odp_packet_has_ipv4_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ipv4, val);
+	setflag(pkt, input_flags.ipv4, val, LAYER_L3);
 }
 
 void odp_packet_has_ipv6_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ipv6, val);
+	setflag(pkt, input_flags.ipv6, val, LAYER_L3);
 }
 
 void odp_packet_has_ip_bcast_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ip_bcast, val);
+	setflag(pkt, input_flags.ip_bcast, val, LAYER_L3);
 }
 
 void odp_packet_has_ip_mcast_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ip_mcast, val);
+	setflag(pkt, input_flags.ip_mcast, val, LAYER_L3);
 }
 
 void odp_packet_has_ipfrag_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ipfrag, val);
+	setflag(pkt, input_flags.ipfrag, val, LAYER_L3);
 }
 
 void odp_packet_has_ipopt_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ipopt, val);
+	setflag(pkt, input_flags.ipopt, val, LAYER_L3);
 }
 
 void odp_packet_has_ipsec_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.ipsec, val);
+	setflag(pkt, input_flags.ipsec, val, LAYER_L4);
 }
 
 void odp_packet_has_udp_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.udp, val);
+	setflag(pkt, input_flags.udp, val, LAYER_L4);
 }
 
 void odp_packet_has_tcp_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.tcp, val);
+	setflag(pkt, input_flags.tcp, val, LAYER_L4);
 }
 
 void odp_packet_has_sctp_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.sctp, val);
+	setflag(pkt, input_flags.sctp, val, LAYER_L4);
 }
 
 void odp_packet_has_icmp_set(odp_packet_t pkt, int val)
 {
-	setflag(pkt, input_flags.icmp, val);
+	setflag(pkt, input_flags.icmp, val, LAYER_L4);
 }
 
 void odp_packet_has_flow_hash_clr(odp_packet_t pkt)
