Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Select maxInterval based on device sleep interval in MTRDevice. #23426

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 17 additions & 5 deletions src/darwin/Framework/CHIP/MTRDevice.mm
Original file line number Diff line number Diff line change
Expand Up @@ -174,15 +174,16 @@ + (instancetype)deviceWithNodeID:(NSNumber *)nodeID controller:(MTRDeviceControl
#pragma mark Subscription and delegate handling

// subscription intervals are in seconds
#define MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_DEFAULT (3600)
#define MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_MIN (2)
#define MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_MAX (60)

- (void)setDelegate:(id<MTRDeviceDelegate>)delegate queue:(dispatch_queue_t)queue
{
os_unfair_lock_lock(&self->_lock);

_weakDelegate = [MTRWeakReference weakReferenceWithObject:delegate];
_delegateQueue = queue;
[self subscribeWithMinInterval:0 maxInterval:MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_DEFAULT];
[self setupSubscription];

os_unfair_lock_unlock(&self->_lock);
}
Expand Down Expand Up @@ -285,7 +286,7 @@ - (void)_handleEventReport:(NSArray<NSDictionary<NSString *, id> *> *)eventRepor
os_unfair_lock_unlock(&self->_lock);
}

- (void)subscribeWithMinInterval:(uint16_t)minInterval maxInterval:(uint16_t)maxInterval
- (void)setupSubscription
{
// for now just subscribe once
if (_subscriptionActive) {
Expand All @@ -310,8 +311,19 @@ - (void)subscribeWithMinInterval:(uint16_t)minInterval maxInterval:(uint16_t)max
// We want to get event reports at the minInterval, not the maxInterval.
eventPath->mIsUrgentEvent = true;
ReadPrepareParams readParams(session.Value());
readParams.mMinIntervalFloorSeconds = minInterval;
readParams.mMaxIntervalCeilingSeconds = maxInterval;

readParams.mMinIntervalFloorSeconds = 0;
// Select a max interval based on the device's claimed idle sleep interval.
auto idleSleepInterval = std::chrono::duration_cast<System::Clock::Seconds32>(
session.Value()->GetRemoteMRPConfig().mIdleRetransTimeout);
if (idleSleepInterval.count() < MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_MIN) {
idleSleepInterval = System::Clock::Seconds32(MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_MIN);
}
if (idleSleepInterval.count() > MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_MAX) {
idleSleepInterval = System::Clock::Seconds32(MTR_DEVICE_SUBSCRIPTION_MAX_INTERVAL_MAX);
}
readParams.mMaxIntervalCeilingSeconds = static_cast<uint16_t>(idleSleepInterval.count());

readParams.mpAttributePathParamsList = attributePath.get();
readParams.mAttributePathParamsListSize = 1;
readParams.mpEventPathParamsList = eventPath.get();
Expand Down
44 changes: 44 additions & 0 deletions src/darwin/Framework/CHIPTests/MTRDeviceTests.m
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,28 @@ - (void)onAddressUpdated:(NSError *)error
}
@end

@interface MTRDeviceTestDelegate : NSObject <MTRDeviceDelegate>
@property (nonatomic) dispatch_block_t onSubscriptionEstablished;
@end

@implementation MTRDeviceTestDelegate
- (void)device:(MTRDevice *)device stateChanged:(MTRDeviceState)state
{
if (state == MTRDeviceStateReachable) {
self.onSubscriptionEstablished();
}
}

- (void)device:(MTRDevice *)device receivedAttributeReport:(NSArray<NSDictionary<NSString *, id> *> *)attributeReport
{
}

- (void)device:(MTRDevice *)device receivedEventReport:(NSArray<NSDictionary<NSString *, id> *> *)eventReport
{
}

@end

@interface MTRDeviceTests : XCTestCase
@end

Expand Down Expand Up @@ -1359,6 +1381,28 @@ - (void)test016_FailedSubscribeWithCacheReadDuringFailure
[self waitForExpectations:@[ errorExpectation ] timeout:60];
}

- (void)test017_TestMTRDeviceBasics
{
#if MANUAL_INDIVIDUAL_TEST
[self initStack];
[self waitForCommissionee];
#endif

__auto_type * device = [MTRDevice deviceWithNodeID:kDeviceId deviceController:sController];
dispatch_queue_t queue = dispatch_get_main_queue();

XCTestExpectation * subscriptionExpectation = [self expectationWithDescription:@"Subscription has been set up"];

__auto_type * delegate = [[MTRDeviceTestDelegate alloc] init];
delegate.onSubscriptionEstablished = ^() {
[subscriptionExpectation fulfill];
};

[device setDelegate:delegate queue:queue];

[self waitForExpectations:@[ subscriptionExpectation ] timeout:60];
}

- (void)test900_SubscribeAllAttributes
{
#if MANUAL_INDIVIDUAL_TEST
Expand Down