summaryrefslogtreecommitdiff
path: root/SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m
diff options
context:
space:
mode:
Diffstat (limited to 'SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m')
-rw-r--r--SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m186
1 files changed, 149 insertions, 37 deletions
diff --git a/SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m b/SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m
index 137006e6b..0dee191ef 100644
--- a/SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m
+++ b/SmartDeviceLinkTests/ProtocolSpecs/MessageSpecs/SDLProtocolSpec.m
@@ -9,18 +9,22 @@
#import <Nimble/Nimble.h>
#import <OCMock/OCMock.h>
-#import "SDLTransportType.h"
#import "SDLControlFramePayloadAudioStartServiceAck.h"
#import "SDLControlFramePayloadRegisterSecondaryTransportNak.h"
#import "SDLControlFramePayloadRPCStartServiceAck.h"
#import "SDLControlFramePayloadVideoStartServiceAck.h"
+#import "SDLDeleteCommand.h"
+#import "SDLEncryptionLifecycleManager.h"
#import "SDLGlobals.h"
#import "SDLProtocolHeader.h"
#import "SDLProtocol.h"
#import "SDLProtocolMessage.h"
+#import "SDLProtocolMessageDisassembler.h"
#import "SDLProtocolReceivedMessageRouter.h"
+#import "SDLRPCFunctionNames.h"
#import "SDLRPCRequest.h"
#import "SDLRPCParameterNames.h"
+#import "SDLTransportType.h"
#import "SDLV1ProtocolMessage.h"
#import "SDLV2ProtocolMessage.h"
#import "SDLV1ProtocolHeader.h"
@@ -35,10 +39,12 @@ NSDictionary* dictionaryV1 = @{SDLRPCParameterNameRequest:
SDLRPCParameterNameCorrelationId:@0x98765,
SDLRPCParameterNameParameters:
@{SDLRPCParameterNameCommandId:@55}}};
-NSDictionary* dictionaryV2 = @{SDLRPCParameterNameCommandId:@55};
+// Send StartService Tests
describe(@"Send StartService Tests", ^{
+ // Insecure
context(@"Insecure", ^{
+ // Should send the correct data
it(@"Should send the correct data", ^{
// Reset max protocol version before test. (This test case expects V1 header. If other test ran
// prior to this one, SDLGlobals would keep the max protocol version and this test case would fail.)
@@ -110,8 +116,11 @@ describe(@"Send StartService Tests", ^{
});
});
+// Send EndSession Tests
describe(@"Send EndSession Tests", ^{
+ // During V1 session
context(@"During V1 session", ^{
+ // Should send the correct data
it(@"Should send the correct data", ^{
__block BOOL verified = NO;
id transportMock = OCMProtocolMock(@protocol(SDLTransportType));
@@ -168,7 +177,9 @@ describe(@"Send EndSession Tests", ^{
});
});
+// Send Register Secondary Transport Tests
describe(@"Send Register Secondary Transport Tests", ^{
+ // Should send the correct data
it(@"Should send the correct data", ^{
__block BOOL verified = NO;
id transportMock = OCMProtocolMock(@protocol(SDLTransportType));
@@ -201,13 +212,20 @@ describe(@"Send Register Secondary Transport Tests", ^{
});
});
-describe(@"SendRPCRequest Tests", ^{
+// SendRPC Tests
+describe(@"SendRPC Tests", ^{
__block id mockRequest;
beforeEach(^{
mockRequest = OCMPartialMock([[SDLRPCRequest alloc] init]);
});
-
+
+ afterEach(^{
+ [SDLGlobals sharedGlobals].maxHeadUnitProtocolVersion = [SDLVersion versionWithMajor:1 minor:0 patch:0];
+ });
+
+ // During V1 session
context(@"During V1 session", ^{
+ // Should send the correct data
it(@"Should send the correct data", ^{
[[[[mockRequest stub] andReturn:dictionaryV1] ignoringNonObjectArgs] serializeAsDictionary:1];
@@ -245,42 +263,28 @@ describe(@"SendRPCRequest Tests", ^{
expect(error).to(beNil());
});
});
-
+
+ // During V2 session
context(@"During V2 session", ^{
- it(@"Should send the correct data bulk data when bulk data is available", ^{
- [[[[mockRequest stub] andReturn:dictionaryV2] ignoringNonObjectArgs] serializeAsDictionary:2];
- [[[mockRequest stub] andReturn:@0x98765] correlationID];
- [[[mockRequest stub] andReturn:@"DeleteCommand"] name];
- [[[mockRequest stub] andReturn:[NSData dataWithBytes:"COMMAND" length:strlen("COMMAND")]] bulkData];
-
- __block BOOL verified = NO;
+ beforeEach(^{
+ [SDLGlobals sharedGlobals].maxHeadUnitProtocolVersion = [SDLVersion versionWithMajor:2 minor:0 patch:0];
+ });
+
+ // Should send the correct data bulk data when bulk data is available
+ it(@"should correctly send a request smaller than the MTU size", ^{
+ SDLDeleteCommand *deleteRequest = [[SDLDeleteCommand alloc] initWithId:55];
+ deleteRequest.correlationID = @12345;
+ deleteRequest.bulkData = [NSData dataWithBytes:"COMMAND" length:strlen("COMMAND")];
+
+ __block NSUInteger numTimesCalled = 0;
id transportMock = OCMProtocolMock(@protocol(SDLTransportType));
- [[[transportMock stub] andDo:^(NSInvocation* invocation) {
- verified = YES;
-
- //Without the __unsafe_unretained, a double release will occur. More information: https://github.com/erikdoe/ocmock/issues/123
- __unsafe_unretained NSData* data;
- [invocation getArgument:&data atIndex:2];
- NSData* dataSent = [data copy];
-
- NSData* jsonTestData = [NSJSONSerialization dataWithJSONObject:dictionaryV2 options:0 error:0];
- NSUInteger dataLength = jsonTestData.length;
-
- const char testPayloadHeader[12] = {0x00, 0x00, 0x00, 0x06, 0x00, 0x09, 0x87, 0x65, (dataLength >> 24) & 0xFF, (dataLength >> 16) & 0xFF, (dataLength >> 8) & 0xFF, dataLength & 0xFF};
-
- NSMutableData* payloadData = [NSMutableData dataWithBytes:testPayloadHeader length:12];
- [payloadData appendData:jsonTestData];
- [payloadData appendBytes:"COMMAND" length:strlen("COMMAND")];
-
- const char testHeader[12] = {0x20 | SDLFrameTypeSingle, SDLServiceTypeBulkData, SDLFrameInfoSingleFrame, 0x01, (payloadData.length >> 24) & 0xFF, (payloadData.length >> 16) & 0xFF,(payloadData.length >> 8) & 0xFF, payloadData.length & 0xFF, 0x00, 0x00, 0x00, 0x01};
-
- NSMutableData* testData = [NSMutableData dataWithBytes:testHeader length:12];
- [testData appendData:payloadData];
-
- expect(dataSent).to(equal([testData copy]));
+ [[[transportMock stub] andDo:^(NSInvocation *invocation) {
+ numTimesCalled++;
}] sendData:[OCMArg any]];
+
SDLProtocol *testProtocol = [[SDLProtocol alloc] initWithTransport:transportMock encryptionManager:nil];
+ // Send a start service ack to ensure that it's set up for sending the RPC
SDLV2ProtocolHeader *testHeader = [[SDLV2ProtocolHeader alloc] initWithVersion:2];
testHeader.serviceType = SDLServiceTypeRPC;
testHeader.sessionID = 0x01;
@@ -289,14 +293,109 @@ describe(@"SendRPCRequest Tests", ^{
NSError *error = nil;
BOOL sent = [testProtocol sendRPC:mockRequest error:&error];
- expect(verified).toEventually(beTrue());
+ expect(numTimesCalled).toEventually(equal(1));
expect(sent).to(beTrue());
expect(error).to(beNil());
});
+
+ it(@"should correctly send a request larger than the MTU size", ^{
+ char dummyBytes[1100];
+
+ SDLDeleteCommand *deleteRequest = [[SDLDeleteCommand alloc] initWithId:55];
+ deleteRequest.correlationID = @12345;
+ deleteRequest.bulkData = [NSData dataWithBytes:dummyBytes length:1100];
+
+ __block NSUInteger numTimesCalled = 0;
+ id transportMock = OCMProtocolMock(@protocol(SDLTransportType));
+ [[[transportMock stub] andDo:^(NSInvocation *invocation) {
+ numTimesCalled++;
+ }] sendData:[OCMArg any]];
+
+ SDLProtocol *testProtocol = [[SDLProtocol alloc] initWithTransport:transportMock encryptionManager:nil];
+
+ NSError *error = nil;
+ [SDLGlobals sharedGlobals].maxHeadUnitProtocolVersion = [SDLVersion versionWithMajor:2 minor:0 patch:0];
+ BOOL sent = [testProtocol sendRPC:deleteRequest error:&error];
+
+ expect(numTimesCalled).toEventually(equal(3));
+ expect(sent).to(beTrue());
+ expect(error).to(beNil());
+ });
+
+ describe(@"when encrypting the requests", ^{
+ context(@"when the encryption manager is not ready", ^{
+ it(@"should not send the request and return an error", ^{
+ char dummyBytes[20000];
+
+ SDLDeleteCommand *deleteRequest = [[SDLDeleteCommand alloc] initWithId:55];
+ deleteRequest.correlationID = @12345;
+ deleteRequest.bulkData = [NSData dataWithBytes:dummyBytes length:20000];
+ deleteRequest.payloadProtected = YES;
+
+ __block NSUInteger numTimesCalled = 0;
+ id transportMock = OCMProtocolMock(@protocol(SDLTransportType));
+ [[[transportMock stub] andDo:^(NSInvocation *invocation) {
+ numTimesCalled++;
+ }] sendData:[OCMArg any]];
+
+ SDLProtocol *testProtocol = [[SDLProtocol alloc] initWithTransport:transportMock encryptionManager:nil];
+
+ NSError *error = nil;
+ [SDLGlobals sharedGlobals].maxHeadUnitProtocolVersion = [SDLVersion versionWithMajor:5 minor:0 patch:0];
+ BOOL sent = [testProtocol sendRPC:deleteRequest error:&error];
+
+ expect(numTimesCalled).toEventually(equal(0));
+ expect(sent).to(beFalse());
+ expect(error).toNot(beNil());
+ });
+ });
+
+ context(@"when the encryption manager is ready", ^{
+ __block NSUInteger numTimesCalled = 0;
+ __block SDLProtocol *testProtocol = nil;
+ NSUInteger dataSize = 20000;
+ beforeEach(^{
+ id transportMock = OCMProtocolMock(@protocol(SDLTransportType));
+ [[[transportMock stub] andDo:^(NSInvocation *invocation) {
+ numTimesCalled++;
+ }] sendData:[OCMArg any]];
+
+ SDLEncryptionLifecycleManager *encryptionMock = OCMClassMock([SDLEncryptionLifecycleManager class]);
+ OCMStub(encryptionMock.isEncryptionReady).andReturn(YES);
+
+ id securityManager = OCMProtocolMock(@protocol(SDLSecurityType));
+ char dummyBytes[dataSize];
+ NSData *returnData = [NSData dataWithBytes:dummyBytes length:dataSize];
+ OCMStub([securityManager encryptData:[OCMArg any] withError:[OCMArg setTo:nil]]).andReturn(returnData);
+
+ testProtocol = [[SDLProtocol alloc] initWithTransport:transportMock encryptionManager:encryptionMock];
+ testProtocol.securityManager = securityManager;
+ });
+
+ it(@"should correctly adjust the MTU size when the packet is encrypted and the service MTU size is larger than the TLS max size", ^{
+ char dummyBytes[dataSize];
+
+ SDLDeleteCommand *deleteRequest = [[SDLDeleteCommand alloc] initWithId:55];
+ deleteRequest.correlationID = @12345;
+ deleteRequest.bulkData = [NSData dataWithBytes:dummyBytes length:dataSize];
+ deleteRequest.payloadProtected = YES;
+
+ NSError *error = nil;
+ [SDLGlobals sharedGlobals].maxHeadUnitProtocolVersion = [SDLVersion versionWithMajor:5 minor:0 patch:0];
+ BOOL sent = [testProtocol sendRPC:deleteRequest error:&error];
+
+ expect(numTimesCalled).toEventually(equal(3));
+ expect(sent).to(beTrue());
+ expect(error).to(beNil());
+ });
+ });
+ });
});
});
+// HandleBytesFromTransport Tests
describe(@"HandleBytesFromTransport Tests", ^{
+ // During V1 session
context(@"During V1 session", ^{
// it(@"Should parse the data correctly", ^{
// id routerMock = OCMClassMock(SDLProtocolReceivedMessageRouter.class);
@@ -343,7 +442,8 @@ describe(@"HandleBytesFromTransport Tests", ^{
// expect(@(verified)).toEventually(beTruthy());
// });
});
-
+
+ // During V2 session
context(@"During V2 session", ^{
// it(@"Should parse the data correctly", ^{
// id routerMock = OCMClassMock(SDLProtocolReceivedMessageRouter.class);
@@ -403,6 +503,7 @@ describe(@"HandleBytesFromTransport Tests", ^{
});
});
+// HandleProtocolSessionStarted tests
describe(@"HandleProtocolSessionStarted tests", ^{
__block id transportMock = nil;
__block SDLProtocol *testProtocol = nil;
@@ -427,7 +528,9 @@ describe(@"HandleProtocolSessionStarted tests", ^{
#pragma clang diagnostic pop
});
+ // For protocol versions 5.0.0 and greater
context(@"For protocol versions 5.0.0 and greater", ^{
+ // If the service type is RPC
context(@"If the service type is RPC", ^{
it(@"Should store the auth token, system info, and the protocol version and pass the start service along to the delegate", ^{
SDLControlFramePayloadRPCStartServiceAck *testPayload = [[SDLControlFramePayloadRPCStartServiceAck alloc] initWithHashId:hashId mtu:testMTU authToken:testAuthToken protocolVersion:@"5.2.0" secondaryTransports:nil audioServiceTransports:nil videoServiceTransports:nil make:testMake model:testModel trim:testTrim modelYear:testModelYear systemSoftwareVersion:testSystemSoftwareVersion systemHardwareVersion:testSystemHardwareVersion];
@@ -586,7 +689,9 @@ describe(@"HandleProtocolSessionStarted tests", ^{
});
});
+ // For protocol versions below 5.0.0
context(@"For protocol versions below 5.0.0", ^{
+ // If the service type is RPC
context(@"If the service type is RPC", ^{
it(@"Should store the protocol version and pass the start service along to the delegate", ^{
SDLControlFramePayloadRPCStartServiceAck *testPayload = [[SDLControlFramePayloadRPCStartServiceAck alloc] initWithHashId:hashId mtu:testMTU authToken:nil protocolVersion:@"3.1.0" secondaryTransports:nil audioServiceTransports:nil videoServiceTransports:nil make:nil model:nil trim:nil modelYear:nil systemSoftwareVersion:nil systemHardwareVersion:nil];
@@ -691,6 +796,7 @@ describe(@"HandleProtocolSessionStarted tests", ^{
});
});
+// HandleProtocolRegisterSecondaryTransport Tests
describe(@"HandleProtocolRegisterSecondaryTransport Tests", ^{
__block id transportMock = nil;
__block SDLProtocol *testProtocol = nil;
@@ -700,6 +806,7 @@ describe(@"HandleProtocolRegisterSecondaryTransport Tests", ^{
testProtocol = [[SDLProtocol alloc] initWithTransport:transportMock encryptionManager:nil];
});
+ // Should pass information along to delegate when ACKed
it(@"Should pass information along to delegate when ACKed", ^{
id delegateMock = OCMProtocolMock(@protocol(SDLProtocolDelegate));
@@ -720,6 +827,7 @@ describe(@"HandleProtocolRegisterSecondaryTransport Tests", ^{
OCMVerifyAllWithDelay(delegateMock, 0.1);
});
+ // Should pass information along to delegate when NAKed
it(@"Should pass information along to delegate when NAKed", ^{
id delegateMock = OCMProtocolMock(@protocol(SDLProtocolDelegate));
@@ -743,6 +851,7 @@ describe(@"HandleProtocolRegisterSecondaryTransport Tests", ^{
});
});
+// HandleHeartbeatForSession Tests
describe(@"HandleHeartbeatForSession Tests", ^{
__block id transportMock = nil;
__block SDLProtocol *testProtocol = nil;
@@ -764,6 +873,7 @@ describe(@"HandleHeartbeatForSession Tests", ^{
});
});
+// OnProtocolMessageReceived Tests
describe(@"OnProtocolMessageReceived Tests", ^{
__block id transportMock = nil;
__block SDLProtocol *testProtocol = nil;
@@ -790,6 +900,7 @@ describe(@"OnProtocolMessageReceived Tests", ^{
});
});
+// OnProtocolOpened Tests
describe(@"OnProtocolOpened Tests", ^{
__block id transportMock = nil;
__block SDLProtocol *testProtocol = nil;
@@ -811,6 +922,7 @@ describe(@"OnProtocolOpened Tests", ^{
});
});
+// OnProtocolClosed Tests
describe(@"OnProtocolClosed Tests", ^{
__block id transportMock = nil;
__block SDLProtocol *testProtocol = nil;