Coverage Report

Created: 2023-01-17 06:15

/src/PcapPlusPlus/Common++/header/MacAddress.h
Line
Count
Source (jump to first uncovered line)
1
#ifndef PCAPPP_MACADDRESS
2
#define PCAPPP_MACADDRESS
3
4
#include <stdint.h>
5
#include <string.h>
6
#include <string>
7
8
#if __cplusplus > 199711L || _MSC_VER >= 1800
9
#include <initializer_list>
10
#include <algorithm>
11
#include <iterator>
12
#include <ostream>
13
#endif
14
15
/// @file
16
17
/**
18
 * \namespace pcpp
19
 * \brief The main namespace for the PcapPlusPlus lib
20
 */
21
namespace pcpp
22
{
23
24
  /**
25
   * @class MacAddress
26
   * Represents L2 MAC addresses. Can be constructed from string or a series of 6 byte octets
27
   */
28
  class MacAddress
29
  {
30
  public:
31
    /**
32
     * Default constructor for this class.
33
     * Initializes object to me MacAddress::Zero
34
     */
35
    MacAddress() : m_IsValid(true) { memset(m_Address, 0, sizeof(m_Address)); }
36
37
    /**
38
     * A constructor that creates an instance of the class out of a byte array. The byte array length must be equal or greater to 6
39
     * (as MAC address is 6-byte long)
40
     * @todo there is no verification array length >= 6. If this is not the case, address will read uninitialized memory
41
     * @param[in] addr A pointer to the byte array containing 6 bytes representing the MAC address
42
     */
43
15.1k
    MacAddress(const uint8_t* addr) : m_IsValid(true) { memcpy(m_Address, addr, sizeof(m_Address)); }
44
45
    /**
46
     *  A constructor that creates an instance of the class out of a (char*) string.
47
     *  If the string doesn't represent a valid MAC address, instance will be invalid, meaning isValid() will return false
48
     *  @param[in] addr A pointer to the (char*) string
49
     */
50
4
    MacAddress(const char* addr) { init(addr); }
51
52
    /**
53
     *  A constructor that creates an instance of the class out of a std::string.
54
     *  If the string doesn't represent a valid MAC address, instance will be invalid, meaning isValid() will return false
55
     *  @param[in] addr A pointer to the string
56
     */
57
    MacAddress(const std::string& addr) { init(addr.c_str()); }
58
59
    /**
60
     *  A constructor that creates an instance of 6 bytes representing the MAC address
61
     *  @param[in] firstOctest Represent the first octet in the address
62
     *  @param[in] secondOctet Represent the second octet in the address
63
     *  @param[in] thirdOctet Represent the third octet in the address
64
     *  @param[in] fourthOctet Represent the fourth octet in the address
65
     *  @param[in] fifthOctet Represent the fifth octet in the address
66
     *  @param[in] sixthOctet Represent the sixth octet in the address
67
     */
68
    inline MacAddress(uint8_t firstOctest, uint8_t secondOctet, uint8_t thirdOctet, uint8_t fourthOctet, uint8_t fifthOctet, uint8_t sixthOctet);
69
70
#if __cplusplus > 199711L || _MSC_VER >= 1800
71
    /**
72
     * A constructor that creates an instance out of the initializer list. The length of the list must be equal to 6 (as MAC address is 6-byte long)
73
     * @param[in] addr An initializer list containing the values of type uint8_t representing the MAC address
74
     */
75
    MacAddress(std::initializer_list<uint8_t> octets) : m_IsValid { octets.size() == sizeof(m_Address) }
76
    {
77
      if(m_IsValid)
78
      {
79
        #if _MSC_VER >= 1800
80
        std::copy(octets.begin(), octets.end(), stdext::checked_array_iterator<uint8_t*>(m_Address, 6));
81
        #else
82
        std::copy(octets.begin(), octets.end(), std::begin(m_Address));
83
        #endif
84
      }
85
      else
86
        memset(m_Address, 0, sizeof(m_Address));
87
    }
88
#endif
89
90
    /**
91
     * Overload of the comparison operator
92
     * @param[in] other The object to compare with
93
     * @return True if addresses are equal, false otherwise
94
     */
95
13.6k
    bool operator==(const MacAddress& other) const { return memcmp(m_Address, other.m_Address, sizeof(m_Address)) == 0; }
96
97
    /**
98
     * Overload of the not-equal operator
99
     * @param[in] other The object to compare with
100
     * @return True if addresses are not equal, false otherwise
101
     */
102
13.6k
    bool operator!=(const MacAddress& other) const { return !operator==(other); }
103
104
#if __cplusplus > 199711L || _MSC_VER >= 1800
105
    /**
106
     * Overload of the assignment operator
107
     */
108
    MacAddress& operator=(std::initializer_list<uint8_t> octets)
109
    {
110
      m_IsValid = (octets.size() == sizeof m_Address);
111
      if(m_IsValid)
112
      {
113
        #if _MSC_VER >= 1800
114
        std::copy(octets.begin(), octets.end(), stdext::checked_array_iterator<uint8_t*>(m_Address, sizeof(m_Address)));
115
        #else
116
        std::copy(octets.begin(), octets.end(), std::begin(m_Address));
117
        #endif
118
      }
119
      return *this;
120
    }
121
#endif
122
123
    /**
124
     * Returns the pointer to raw data
125
     * @return The pointer to raw data
126
     */
127
0
    const uint8_t* getRawData() const { return m_Address; }
128
129
    /**
130
     * Get an indication whether the MAC address is valid. An address can be invalid if it was constructed from illegal input, for example:
131
     * invalid string
132
     * @return True if the address is valid, false otherwise
133
     */
134
0
    bool isValid() const { return m_IsValid; }
135
136
    /**
137
     * Returns a std::string representation of the address
138
     * @return A string representation of the address
139
     */
140
    std::string toString() const;
141
142
    /**
143
     * Allocates a byte array of length 6 and copies address value into it. Array deallocation is user responsibility
144
     * @param[in] arr A pointer to where array will be allocated
145
     */
146
    void copyTo(uint8_t** arr) const
147
    {
148
      *arr = new uint8_t[sizeof(m_Address)];
149
      memcpy(*arr, m_Address, sizeof(m_Address));
150
    }
151
152
    /**
153
     * Gets a pointer to an already allocated byte array and copies the address value to it.
154
     * This method assumes array allocated size is at least 6 (the size of a MAC address)
155
     * @param[in] arr A pointer to the array which address will be copied to
156
     */
157
0
    void copyTo(uint8_t* arr) const { memcpy(arr, m_Address, sizeof(m_Address)); }
158
159
    /**
160
     * A static value representing a zero value of MAC address, meaning address of value "00:00:00:00:00:00"
161
     */
162
    static MacAddress Zero;
163
164
  private:
165
    uint8_t m_Address[6];
166
    bool m_IsValid;
167
    void init(const char* addr);
168
  };
169
170
  MacAddress::MacAddress(uint8_t firstOctest, uint8_t secondOctet, uint8_t thirdOctet, uint8_t fourthOctet, uint8_t fifthOctet, uint8_t sixthOctet)
171
    : m_IsValid(true)
172
2
  {
173
2
    m_Address[0] = firstOctest;
174
2
    m_Address[1] = secondOctet;
175
2
    m_Address[2] = thirdOctet;
176
2
    m_Address[3] = fourthOctet;
177
2
    m_Address[4] = fifthOctet;
178
2
    m_Address[5] = sixthOctet;
179
2
  }
180
181
} // namespace pcpp
182
183
inline std::ostream& operator<<(std::ostream& os, const pcpp::MacAddress& macAddress)
184
{
185
  os << macAddress.toString();
186
  return os;
187
}
188
189
#endif /* PCAPPP_MACADDRESS */