Skip to content

Commit 996971d

Browse files
committed
[Darwin][Network.framework] Add src/platform/Darwin/system/SystemLayerImplDispatch.mm such that the unit tests runs using the dispatch mechanism instead of the socket based implementation
1 parent eda485e commit 996971d

16 files changed

+812
-238
lines changed

.github/workflows/lint.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -126,6 +126,7 @@ jobs:
126126
--known-failure platform/DeviceSafeQueue.h \
127127
--known-failure platform/GLibTypeDeleter.h \
128128
--known-failure platform/SingletonConfigurationManager.cpp \
129+
--known-failure system/SystemLayerImplDispatch.h \
129130
"
130131
# These ARE actually orphaned but due to dynamic-server we have code paths
131132
# for them. Keeping them as a list as they still need review ...

src/inet/tests/TestInetCommonPosix.cpp

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -358,16 +358,22 @@ void ServiceEvents(uint32_t aSleepTimeMilliseconds)
358358
}
359359
}
360360

361+
#if !CHIP_SYSTEM_CONFIG_USE_DISPATCH
361362
// Start a timer (with a no-op callback) to ensure that WaitForEvents() does not block longer than aSleepTimeMilliseconds.
362363
gSystemLayer.StartTimer(
363364
System::Clock::Milliseconds32(aSleepTimeMilliseconds), [](System::Layer *, void *) -> void {}, nullptr);
365+
#endif
364366

365-
#if CHIP_SYSTEM_CONFIG_USE_SOCKETS
367+
#if CHIP_SYSTEM_CONFIG_USE_SOCKETS && !CHIP_SYSTEM_CONFIG_USE_DISPATCH
366368
gSystemLayer.PrepareEvents();
367369
gSystemLayer.WaitForEvents();
368370
gSystemLayer.HandleEvents();
369371
#endif
370372

373+
#if CHIP_SYSTEM_CONFIG_USE_DISPATCH
374+
gSystemLayer.HandleDispatchQueueEvents(System::Clock::Milliseconds32(aSleepTimeMilliseconds));
375+
#endif
376+
371377
#if CHIP_SYSTEM_CONFIG_USE_LWIP || CHIP_SYSTEM_CONFIG_USE_OPENTHREAD_ENDPOINT
372378
if (gSystemLayer.IsInitialized())
373379
{

src/platform/Darwin/BUILD.gn

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ import("//build_overrides/chip.gni")
1616
import("//build_overrides/nlassert.gni")
1717

1818
import("${chip_root}/src/platform/device.gni")
19+
import("${chip_root}/src/system/system.gni")
1920

2021
assert(chip_device_platform == "darwin")
2122

@@ -77,8 +78,14 @@ static_library("Darwin") {
7778
"SystemTimeSupport.cpp",
7879
"UserDefaults.h",
7980
"UserDefaults.mm",
81+
"system/SystemLayerImplDispatch.h",
82+
"system/SystemLayerImplDispatch.mm",
8083
]
8184

85+
if (chip_system_config_use_sockets) {
86+
sources += [ "system/SystemLayerImplDispatchSockets.mm" ]
87+
}
88+
8289
if (chip_enable_wifi) {
8390
sources += [
8491
"WiFi/ConfigurationManagerImplWiFi.cpp",

src/platform/Darwin/PlatformManagerImpl.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ CHIP_ERROR PlatformManagerImpl::_InitChipStack()
7070

7171
#if CHIP_SYSTEM_CONFIG_USE_DISPATCH
7272
// Ensure there is a dispatch queue available
73-
static_cast<System::LayerSocketsLoop &>(DeviceLayer::SystemLayer()).SetDispatchQueue(GetWorkQueue());
73+
static_cast<System::LayerDispatch &>(DeviceLayer::SystemLayer()).SetDispatchQueue(GetWorkQueue());
7474
#endif
7575

7676
// Call _InitChipStack() on the generic implementation base class
Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
/*
2+
*
3+
* Copyright (c) 2025 Project CHIP Authors
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
18+
/**
19+
* @file
20+
* This file declares an implementation of System::Layer using select().
21+
*/
22+
23+
#pragma once
24+
25+
#include "system/SystemConfig.h"
26+
27+
#include <lib/support/ObjectLifeCycle.h>
28+
#include <system/SystemLayer.h>
29+
#include <system/SystemTimer.h>
30+
31+
namespace chip {
32+
namespace System {
33+
34+
class LayerImplDispatch : public LayerDispatch
35+
{
36+
public:
37+
LayerImplDispatch() = default;
38+
~LayerImplDispatch() override { VerifyOrDie(mLayerState.Destroy()); }
39+
40+
// Layer overrides.
41+
CHIP_ERROR Init() override;
42+
void Shutdown() override;
43+
bool IsInitialized() const override { return mLayerState.IsInitialized(); }
44+
CHIP_ERROR StartTimer(Clock::Timeout delay, TimerCompleteCallback onComplete, void * appState) override;
45+
CHIP_ERROR ExtendTimerTo(Clock::Timeout delay, TimerCompleteCallback onComplete, void * appState) override;
46+
bool IsTimerActive(TimerCompleteCallback onComplete, void * appState) override;
47+
Clock::Timeout GetRemainingTime(TimerCompleteCallback onComplete, void * appState) override;
48+
void CancelTimer(TimerCompleteCallback onComplete, void * appState) override;
49+
CHIP_ERROR ScheduleWork(TimerCompleteCallback onComplete, void * appState) override;
50+
51+
// LayerDispatch overrides.
52+
void SetDispatchQueue(dispatch_queue_t dispatchQueue) override { mDispatchQueue = dispatchQueue; };
53+
dispatch_queue_t GetDispatchQueue() override { return mDispatchQueue; };
54+
void HandleDispatchQueueEvents(Clock::Timeout timeout) override;
55+
CHIP_ERROR ScheduleWorkWithBlock(dispatch_block_t block) override;
56+
57+
#if CHIP_SYSTEM_CONFIG_USE_SOCKETS
58+
// LayerSocket overrides.
59+
CHIP_ERROR StartWatchingSocket(int fd, SocketWatchToken * tokenOut) override;
60+
CHIP_ERROR SetCallback(SocketWatchToken token, SocketWatchCallback callback, intptr_t data) override;
61+
CHIP_ERROR RequestCallbackOnPendingRead(SocketWatchToken token) override;
62+
CHIP_ERROR RequestCallbackOnPendingWrite(SocketWatchToken token) override;
63+
CHIP_ERROR ClearCallbackOnPendingRead(SocketWatchToken token) override;
64+
CHIP_ERROR ClearCallbackOnPendingWrite(SocketWatchToken token) override;
65+
CHIP_ERROR StopWatchingSocket(SocketWatchToken * tokenInOut) override;
66+
SocketWatchToken InvalidSocketWatchToken() override { return reinterpret_cast<SocketWatchToken>(nullptr); }
67+
#endif
68+
69+
protected:
70+
#if CHIP_SYSTEM_CONFIG_USE_SOCKETS
71+
struct SelectSets
72+
{
73+
fd_set mReadSet;
74+
fd_set mWriteSet;
75+
fd_set mErrorSet;
76+
};
77+
78+
static constexpr int kSocketWatchMax = (INET_CONFIG_ENABLE_TCP_ENDPOINT ? INET_CONFIG_NUM_TCP_ENDPOINTS : 0) +
79+
(INET_CONFIG_ENABLE_UDP_ENDPOINT ? INET_CONFIG_NUM_UDP_ENDPOINTS : 0);
80+
81+
struct SocketWatch
82+
{
83+
int mFD;
84+
SocketEvents mPendingIO;
85+
SocketWatchCallback mCallback;
86+
intptr_t mCallbackData;
87+
88+
dispatch_source_t mRdSource = nullptr;
89+
dispatch_source_t mWrSource = nullptr;
90+
91+
bool IsActive() const { return mFD != kInvalidFd; }
92+
void PrepareEvents(SelectSets & sets, int & maxFd) const;
93+
void HandleEvents(const SelectSets & sets) const;
94+
void Clear();
95+
};
96+
SocketWatch mSocketWatchPool[kSocketWatchMax];
97+
void ClearSocketWatchPool();
98+
void HandleSocketsAndTimerEvents(Clock::Timeout timeout);
99+
CHIP_ERROR RequestCallback(SocketWatchToken token, SocketEventFlags flag);
100+
CHIP_ERROR ClearCallback(SocketWatchToken token, SocketEventFlags flag);
101+
#endif
102+
103+
TimerPool<TimerList::Node> mTimerPool;
104+
TimerList mTimerList;
105+
// List of expired timers being processed right now. Stored in a member so
106+
// we can cancel them.
107+
TimerList mExpiredTimers;
108+
void EnableTimer(const char * source, TimerList::Node *);
109+
void DisableTimer(const char * source, TimerList::Node *);
110+
CHIP_ERROR StartTimer(Clock::Timeout delay, TimerCompleteCallback onComplete, void * appState, bool shouldCancel);
111+
void HandleTimerEvents(Clock::Timeout timeout);
112+
113+
ObjectLifeCycle mLayerState;
114+
115+
dispatch_queue_t mDispatchQueue = nullptr;
116+
};
117+
118+
using LayerImpl = LayerImplDispatch;
119+
120+
} // namespace System
121+
} // namespace chip

0 commit comments

Comments
 (0)