Line data Source code
1 : /*
2 : *
3 : * Copyright (c) 2020 Project CHIP Authors
4 : * All rights reserved.
5 : *
6 : * Licensed under the Apache License, Version 2.0 (the "License");
7 : * you may not use this file except in compliance with the License.
8 : * You may obtain a copy of the License at
9 : *
10 : * http://www.apache.org/licenses/LICENSE-2.0
11 : *
12 : * Unless required by applicable law or agreed to in writing, software
13 : * distributed under the License is distributed on an "AS IS" BASIS,
14 : * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 : * See the License for the specific language governing permissions and
16 : * limitations under the License.
17 : */
18 :
19 : /**
20 : * @file
21 : * This file defines the CHIP Connection object that maintains a UDP connection.
22 : * It binds to any available local addr and port and begins listening.
23 : *
24 : */
25 :
26 : #pragma once
27 :
28 : #include <utility>
29 :
30 : #include <inet/IPAddress.h>
31 : #include <inet/IPPacketInfo.h>
32 : #include <inet/InetInterface.h>
33 : #include <inet/UDPEndPoint.h>
34 : #include <lib/core/CHIPCore.h>
35 : #include <transport/raw/Base.h>
36 :
37 : #if CHIP_SYSTEM_CONFIG_USE_OPEN_THREAD_ENDPOINT
38 : struct otInstance;
39 : #endif // CHIP_SYSTEM_CONFIG_USE_OPEN_THREAD_ENDPOINT
40 :
41 : namespace chip {
42 : namespace Transport {
43 :
44 : /** Defines listening parameters for setting up a UDP transport */
45 : class UdpListenParameters
46 : {
47 : public:
48 2 : explicit UdpListenParameters(Inet::EndPointManager<Inet::UDPEndPoint> * endPointManager) : mEndPointManager(endPointManager) {}
49 : UdpListenParameters(const UdpListenParameters &) = default;
50 : UdpListenParameters(UdpListenParameters &&) = default;
51 :
52 7 : Inet::EndPointManager<Inet::UDPEndPoint> * GetEndPointManager() { return mEndPointManager; }
53 :
54 14 : Inet::IPAddressType GetAddressType() const { return mAddressType; }
55 2 : UdpListenParameters & SetAddressType(Inet::IPAddressType type)
56 : {
57 2 : mAddressType = type;
58 :
59 2 : return *this;
60 : }
61 :
62 14 : uint16_t GetListenPort() const { return mListenPort; }
63 2 : UdpListenParameters & SetListenPort(uint16_t port)
64 : {
65 2 : mListenPort = port;
66 :
67 2 : return *this;
68 : }
69 :
70 7 : Inet::InterfaceId GetInterfaceId() const { return mInterfaceId; }
71 : UdpListenParameters & SetInterfaceId(Inet::InterfaceId id)
72 : {
73 : mInterfaceId = id;
74 :
75 : return *this;
76 : }
77 :
78 : /**
79 : * Networking Stack Native parameter (optional)
80 : */
81 7 : void * GetNativeParams() const { return mNativeParams; }
82 1 : UdpListenParameters & SetNativeParams(void * params)
83 : {
84 1 : mNativeParams = params;
85 :
86 1 : return *this;
87 : }
88 :
89 : private:
90 : Inet::EndPointManager<Inet::UDPEndPoint> * mEndPointManager; ///< Associated endpoint factory
91 : Inet::IPAddressType mAddressType = Inet::IPAddressType::kIPv6; ///< type of listening socket
92 : uint16_t mListenPort = CHIP_PORT; ///< UDP listen port
93 : Inet::InterfaceId mInterfaceId = Inet::InterfaceId::Null(); ///< Interface to listen on
94 : void * mNativeParams = nullptr;
95 : };
96 :
97 : /** Implements a transport using UDP. */
98 : class DLL_EXPORT UDP : public Base
99 : {
100 : /**
101 : * The State of the UDP connection
102 : *
103 : */
104 : enum class State
105 : {
106 : kNotReady = 0, /**< State before initialization. */
107 : kInitialized = 1, /**< State after class is listening and ready. */
108 : };
109 :
110 : public:
111 : ~UDP() override;
112 :
113 : /**
114 : * Initialize a UDP transport on a given port.
115 : *
116 : * @param params UDP configuration parameters for this transport
117 : *
118 : * @details
119 : * Generally send and receive ports should be the same and equal to CHIP_PORT.
120 : * The class allows separate definitions to allow local execution of several
121 : * Nodes.
122 : */
123 : CHIP_ERROR Init(UdpListenParameters & params);
124 :
125 : uint16_t GetBoundPort();
126 :
127 : /**
128 : * Close the open endpoint without destroying the object
129 : */
130 : void Close() override;
131 :
132 : CHIP_ERROR SendMessage(const Transport::PeerAddress & address, System::PacketBufferHandle && msgBuf) override;
133 :
134 : CHIP_ERROR MulticastGroupJoinLeave(const Transport::PeerAddress & address, bool join) override;
135 :
136 0 : bool CanListenMulticast() override
137 : {
138 0 : return (mState == State::kInitialized) && (mUDPEndpointType == Inet::IPAddressType::kIPv6);
139 : }
140 :
141 2 : bool CanSendToPeer(const Transport::PeerAddress & address) override
142 : {
143 4 : return (mState == State::kInitialized) && (address.GetTransportType() == Type::kUdp) &&
144 4 : (address.GetIPAddress().Type() == mUDPEndpointType);
145 : }
146 :
147 : private:
148 : // UDP message receive handler.
149 : static void OnUdpReceive(Inet::UDPEndPoint * endPoint, System::PacketBufferHandle && buffer,
150 : const Inet::IPPacketInfo * pktInfo);
151 :
152 : static void OnUdpError(Inet::UDPEndPoint * endPoint, CHIP_ERROR err, const Inet::IPPacketInfo * pktInfo);
153 :
154 : Inet::UDPEndPoint * mUDPEndPoint = nullptr; ///< UDP socket used by the transport
155 : Inet::IPAddressType mUDPEndpointType = Inet::IPAddressType::kUnknown; ///< Socket listening type
156 : State mState = State::kNotReady; ///< State of the UDP transport
157 : };
158 :
159 : } // namespace Transport
160 : } // namespace chip
|