Coverage Report

Created: 2025-07-11 07:47

/src/PcapPlusPlus/Packet++/header/VlanLayer.h
Line
Count
Source
1
#pragma once
2
3
#include "Layer.h"
4
#include "EthLayer.h"
5
6
/// @file
7
8
/// @namespace pcpp
9
/// @brief The main namespace for the PcapPlusPlus lib
10
namespace pcpp
11
{
12
  /// @struct vlan_header
13
  /// Represents a VLAN header
14
#pragma pack(push, 1)
15
  struct vlan_header
16
  {
17
    /// @code{.unparsed}
18
    /// 0               1               2
19
    /// 0 1 2 3 4 5 6 7 0 1 2 3 4 5 6 7 0
20
    /// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
21
    /// |Prio |C|         VLAN ID       |
22
    /// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
23
    /// @endcode
24
    uint16_t vlan;
25
    /// Ethernet type for next layer
26
    uint16_t etherType;
27
  };
28
#pragma pack(pop)
29
  static_assert(sizeof(vlan_header) == 4, "vlan_header size is not 4 bytes");
30
31
  /// @class VlanLayer
32
  /// Represents a VLAN tunnel layer
33
  class VlanLayer : public Layer
34
  {
35
  public:
36
    /// A constructor that creates the layer from an existing packet raw data
37
    /// @param[in] data A pointer to the raw data
38
    /// @param[in] dataLen Size of the data in bytes
39
    /// @param[in] prevLayer A pointer to the previous layer
40
    /// @param[in] packet A pointer to the Packet instance where layer will be stored in
41
    VlanLayer(uint8_t* data, size_t dataLen, Layer* prevLayer, Packet* packet)
42
56.0k
        : Layer(data, dataLen, prevLayer, packet, VLAN)
43
56.0k
    {}
44
45
    /// A constructor that allocates a new VLAN header
46
    /// @param[in] vlanID VLAN ID
47
    /// @param[in] cfi CFI value
48
    /// @param[in] priority Priority value
49
    /// @param[in] etherType Protocol EtherType of the next layer. It's an optional parameter, a value of 0 will be
50
    /// set if not provided
51
    VlanLayer(const uint16_t vlanID, bool cfi, uint8_t priority, uint16_t etherType = 0);
52
53
    ~VlanLayer() override = default;
54
55
    /// Get a pointer to the VLAN header. Notice this points directly to the data, so every change will change the
56
    /// actual packet data
57
    /// @return A pointer to the vlan_header
58
    vlan_header* getVlanHeader() const
59
100k
    {
60
100k
      return reinterpret_cast<vlan_header*>(m_Data);
61
100k
    }
62
63
    /// Get the VLAN ID value. This method differs from vlan_header#vlanID because vlan_header#vlanID is 12 bits
64
    /// long in a 16 bit field. This methods extracts only the 12 bit relevant for the VLAN ID
65
    /// @return VLAN ID value
66
    /// @todo Verify it works in big endian machines as well
67
    uint16_t getVlanID() const;
68
69
    /// @return The CFI bit value
70
    /// @todo Verify it works in big endian machines as well
71
    uint8_t getCFI() const;
72
73
    /// @return The priority value
74
    /// @todo Verify it works in big endian machines as well
75
    uint8_t getPriority() const;
76
77
    /// Set VLAN ID. This method differs from setting vlan_header#vlanID because vlan_header#vlanID is 12 bits long
78
    /// in a 16 bit field. This methods sets only the 12 bit relevant for the VLAN ID
79
    /// @param[in] id The VLAN ID to set
80
    /// @todo Verify it works in big endian machines as well
81
    void setVlanID(uint16_t id);
82
83
    /// Set CFI bit
84
    /// @param[in] cfi The CFI bit to set
85
    /// @todo Verify it works in big endian machines as well
86
    void setCFI(bool cfi);
87
88
    /// Set priority value
89
    /// @param[in] priority The priority value to set
90
    /// @todo Verify it works in big endian machines as well
91
    void setPriority(uint8_t priority);
92
93
    // implement abstract methods
94
95
    /// Currently identifies the following next layers: IPv4Layer, IPv6Layer, ArpLayer, VlanLayer, MplsLayer.
96
    /// Otherwise sets PayloadLayer
97
    void parseNextLayer() override;
98
99
    /// @return Size of vlan_header
100
    size_t getHeaderLen() const override
101
7.29k
    {
102
7.29k
      return sizeof(vlan_header);
103
7.29k
    }
104
105
    /// Calculate the EtherType for known protocols: IPv4, IPv6, ARP, VLAN
106
    void computeCalculateFields() override;
107
108
    std::string toString() const override;
109
110
    OsiModelLayer getOsiModelLayer() const override
111
6.52k
    {
112
6.52k
      return OsiModelDataLinkLayer;
113
6.52k
    }
114
115
    /// A static method that validates the input data
116
    /// @param[in] data The pointer to the beginning of a byte stream of an VLAN layer
117
    /// @param[in] dataLen The length of the byte stream
118
    /// @return True if the data is valid and can represent an VLAN layer
119
    static bool isDataValid(const uint8_t* data, size_t dataLen)
120
44.3k
    {
121
44.3k
      return canReinterpretAs<vlan_header>(data, dataLen);
122
44.3k
    }
123
  };
124
}  // namespace pcpp