#define CQ_ENET_RQ_DESC_FLAGS_TRUNCATED             (0x1 << 14)
 #define CQ_ENET_RQ_DESC_FLAGS_VLAN_STRIPPED         (0x1 << 15)
 
+#define CQ_ENET_RQ_DESC_VLAN_TCI_VLAN_BITS          12
+#define CQ_ENET_RQ_DESC_VLAN_TCI_VLAN_MASK \
+       ((1 << CQ_ENET_RQ_DESC_VLAN_TCI_VLAN_BITS) - 1)
+#define CQ_ENET_RQ_DESC_VLAN_TCI_CFI_MASK           (0x1 << 12)
+#define CQ_ENET_RQ_DESC_VLAN_TCI_USER_PRIO_BITS     3
+#define CQ_ENET_RQ_DESC_VLAN_TCI_USER_PRIO_MASK \
+       ((1 << CQ_ENET_RQ_DESC_VLAN_TCI_USER_PRIO_BITS) - 1)
+#define CQ_ENET_RQ_DESC_VLAN_TCI_USER_PRIO_SHIFT    13
+
 #define CQ_ENET_RQ_DESC_FCOE_SOF_BITS               4
 #define CQ_ENET_RQ_DESC_FCOE_SOF_MASK \
        ((1 << CQ_ENET_RQ_DESC_FCOE_SOF_BITS) - 1)
        u8 *type, u8 *color, u16 *q_number, u16 *completed_index,
        u8 *ingress_port, u8 *fcoe, u8 *eop, u8 *sop, u8 *rss_type,
        u8 *csum_not_calc, u32 *rss_hash, u16 *bytes_written, u8 *packet_error,
-       u8 *vlan_stripped, u16 *vlan, u16 *checksum, u8 *fcoe_sof,
+       u8 *vlan_stripped, u16 *vlan_tci, u16 *checksum, u8 *fcoe_sof,
        u8 *fcoe_fc_crc_ok, u8 *fcoe_enc_error, u8 *fcoe_eof,
        u8 *tcp_udp_csum_ok, u8 *udp, u8 *tcp, u8 *ipv4_csum_ok,
        u8 *ipv6, u8 *ipv4, u8 *ipv4_fragment, u8 *fcs_ok)
        *vlan_stripped = (bytes_written_flags &
                CQ_ENET_RQ_DESC_FLAGS_VLAN_STRIPPED) ? 1 : 0;
 
-       *vlan = le16_to_cpu(desc->vlan);
+       /*
+        * Tag Control Information(16) = user_priority(3) + cfi(1) + vlan(12)
+        */
+       *vlan_tci = le16_to_cpu(desc->vlan);
 
        if (*fcoe) {
                *fcoe_sof = (u8)(le16_to_cpu(desc->checksum_fcoe) &
 
        u8 tcp_udp_csum_ok, udp, tcp, ipv4_csum_ok;
        u8 ipv6, ipv4, ipv4_fragment, fcs_ok, rss_type, csum_not_calc;
        u8 packet_error;
-       u16 q_number, completed_index, bytes_written, vlan, checksum;
+       u16 q_number, completed_index, bytes_written, vlan_tci, checksum;
        u32 rss_hash;
 
        if (skipped)
                &type, &color, &q_number, &completed_index,
                &ingress_port, &fcoe, &eop, &sop, &rss_type,
                &csum_not_calc, &rss_hash, &bytes_written,
-               &packet_error, &vlan_stripped, &vlan, &checksum,
+               &packet_error, &vlan_stripped, &vlan_tci, &checksum,
                &fcoe_sof, &fcoe_fc_crc_ok, &fcoe_enc_error,
                &fcoe_eof, &tcp_udp_csum_ok, &udp, &tcp,
                &ipv4_csum_ok, &ipv6, &ipv4, &ipv4_fragment,
 
                skb->dev = netdev;
 
-               if (enic->vlan_group && vlan_stripped) {
+               if (enic->vlan_group && vlan_stripped &&
+                       (vlan_tci & CQ_ENET_RQ_DESC_VLAN_TCI_VLAN_MASK)) {
 
                        if (netdev->features & NETIF_F_GRO)
                                vlan_gro_receive(&enic->napi, enic->vlan_group,
-                                       vlan, skb);
+                                       vlan_tci, skb);
                        else
                                vlan_hwaccel_receive_skb(skb,
-                                       enic->vlan_group, vlan);
+                                       enic->vlan_group, vlan_tci);
 
                } else {
 
                ig_vlan_strip_en);
 }
 
+int enic_dev_set_ig_vlan_rewrite_mode(struct enic *enic)
+{
+       int err;
+
+       spin_lock(&enic->devcmd_lock);
+       err = vnic_dev_set_ig_vlan_rewrite_mode(enic->vdev,
+               IG_VLAN_REWRITE_MODE_PRIORITY_TAG_DEFAULT_VLAN);
+       spin_unlock(&enic->devcmd_lock);
+
+       return err;
+}
+
 static void enic_reset(struct work_struct *work)
 {
        struct enic *enic = container_of(work, struct enic, reset);
        enic_reset_mcaddrs(enic);
        enic_init_vnic_resources(enic);
        enic_set_niccfg(enic);
+       enic_dev_set_ig_vlan_rewrite_mode(enic);
        enic_open(enic->netdev);
 
        rtnl_unlock();
                goto err_out_free_vnic_resources;
        }
 
+       err = enic_dev_set_ig_vlan_rewrite_mode(enic);
+       if (err) {
+               printk(KERN_ERR PFX
+                       "Failed to set ingress vlan rewrite mode, aborting.\n");
+               goto err_out_free_vnic_resources;
+       }
+
        switch (vnic_dev_get_intr_mode(enic->vdev)) {
        default:
                netif_napi_add(netdev, &enic->napi, enic_poll, 64);
 
        return err;
 }
 
+int vnic_dev_set_ig_vlan_rewrite_mode(struct vnic_dev *vdev,
+       u8 ig_vlan_rewrite_mode)
+{
+       u64 a0 = ig_vlan_rewrite_mode, a1 = 0;
+       int wait = 1000;
+       int err;
+
+       err = vnic_dev_cmd(vdev, CMD_IG_VLAN_REWRITE_MODE, &a0, &a1, wait);
+       if (err == ERR_ECMDUNKNOWN)
+               return 0;
+
+       return err;
+}
+
 int vnic_dev_raise_intr(struct vnic_dev *vdev, u16 intr)
 {
        u64 a0 = intr, a1 = 0;
 
        enum vnic_dev_intr_mode intr_mode);
 enum vnic_dev_intr_mode vnic_dev_get_intr_mode(struct vnic_dev *vdev);
 void vnic_dev_unregister(struct vnic_dev *vdev);
+int vnic_dev_set_ig_vlan_rewrite_mode(struct vnic_dev *vdev,
+       u8 ig_vlan_rewrite_mode);
 struct vnic_dev *vnic_dev_register(struct vnic_dev *vdev,
        void *priv, struct pci_dev *pdev, struct vnic_dev_bar *bar,
        unsigned int num_bars);
 
         * in: (u16)a0=interrupt number to assert
         */
        CMD_IAR                 = _CMDCNW(_CMD_DIR_WRITE, _CMD_VTYPE_ALL, 38),
+
+       /*
+        * Set hw ingress packet vlan rewrite mode:
+        * in:  (u32)a0=new vlan rewrite mode
+        * out: (u32)a0=old vlan rewrite mode */
+       CMD_IG_VLAN_REWRITE_MODE = _CMDC(_CMD_DIR_RW, _CMD_VTYPE_ENET, 41),
 };
 
 /* flags for CMD_OPEN */
 #define CMD_PFILTER_PROMISCUOUS                0x08
 #define CMD_PFILTER_ALL_MULTICAST      0x10
 
+/* rewrite modes for CMD_IG_VLAN_REWRITE_MODE */
+#define IG_VLAN_REWRITE_MODE_DEFAULT_TRUNK              0
+#define IG_VLAN_REWRITE_MODE_UNTAG_DEFAULT_VLAN         1
+#define IG_VLAN_REWRITE_MODE_PRIORITY_TAG_DEFAULT_VLAN  2
+#define IG_VLAN_REWRITE_MODE_PASS_THRU                  3
+
 enum vnic_devcmd_status {
        STAT_NONE = 0,
        STAT_BUSY = 1 << 0,     /* cmd in progress */