19
19
from avatar import BumblePandoraDevice
20
20
from avatar import PandoraDevice
21
21
from avatar import PandoraDevices
22
- from avatar .common import make_bredr_connection
23
- from avatar .common import make_le_connection
22
+ from avatar import pandora_snippet
24
23
from mobly import base_test
25
24
from mobly import test_runner
26
25
from mobly .asserts import assert_equal # type: ignore
27
26
from mobly .asserts import assert_is_not_none # type: ignore
28
27
from pandora import host_pb2
29
- from pandora import l2cap_pb2
30
- from typing import Any , Awaitable , Callable , Dict , Literal , Optional , Tuple , Union
31
-
32
- CONNECTORS : Dict [
33
- str ,
34
- Callable [[avatar .PandoraDevice , avatar .PandoraDevice ], Awaitable [Tuple [host_pb2 .Connection , host_pb2 .Connection ]]],
35
- ] = {
36
- 'Classic' : make_bredr_connection ,
37
- 'LE' : make_le_connection ,
38
- }
39
-
40
- FIXED_CHANNEL_CID = 0x3E
28
+ from typing import Any , Dict , Optional
29
+
41
30
CLASSIC_PSM = 0xFEFF
42
31
LE_SPSM = 0xF0
43
32
@@ -49,6 +38,10 @@ class L2capTest(base_test.BaseTestClass): # type: ignore[misc]
49
38
dut : PandoraDevice
50
39
ref : PandoraDevice
51
40
41
+ # BR/EDR & Low-Energy connections.
42
+ dut_ref : Dict [str , host_pb2 .Connection ] = {}
43
+ ref_dut : Dict [str , host_pb2 .Connection ] = {}
44
+
52
45
def setup_class (self ) -> None :
53
46
self .devices = PandoraDevices (self )
54
47
self .dut , self .ref , * _ = self .devices
@@ -66,160 +59,122 @@ def teardown_class(self) -> None:
66
59
async def setup_test (self ) -> None : # pytype: disable=wrong-arg-types
67
60
await asyncio .gather (self .dut .reset (), self .ref .reset ())
68
61
62
+ # Connect REF to DUT in both BR/EDR and Low-Energy.
63
+ ref_dut_br , dut_ref_br = await pandora_snippet .connect (self .ref , self .dut )
64
+ ref_dut_le , dut_ref_le = await pandora_snippet .connect_le_dummy (self .ref , self .dut )
65
+
66
+ self .dut_ref = dict (basic = dut_ref_br , le_credit_based = dut_ref_le )
67
+ self .ref_dut = dict (basic = ref_dut_br , le_credit_based = ref_dut_le )
68
+
69
69
@avatar .parameterized (
70
- ('Classic' , dict (fixed = l2cap_pb2 .FixedChannelRequest (cid = FIXED_CHANNEL_CID ))),
71
- ('LE' , dict (fixed = l2cap_pb2 .FixedChannelRequest (cid = FIXED_CHANNEL_CID ))),
72
- ('Classic' , dict (basic = l2cap_pb2 .ConnectionOrientedChannelRequest (psm = CLASSIC_PSM ))),
73
- (
74
- 'LE' ,
75
- dict (
76
- le_credit_based = l2cap_pb2 .CreditBasedChannelRequest (
77
- spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256
78
- )
79
- ),
80
- ),
70
+ (dict (basic = dict (psm = CLASSIC_PSM )),),
71
+ (dict (le_credit_based = dict (spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256 )),),
81
72
) # type: ignore[misc]
82
73
@avatar .asynchronous
83
74
async def test_connect (
84
75
self ,
85
- transport : Union [Literal ['Classic' ], Literal ['LE' ]],
86
76
request : Dict [str , Any ],
87
77
) -> None :
88
- dut_ref_acl , ref_dut_acl = await CONNECTORS [transport ](self .dut , self .ref )
89
- server = self .ref .aio .l2cap .OnConnection (connection = ref_dut_acl , ** request )
90
- ref_dut_res , dut_ref_res = await asyncio .gather (
91
- anext (aiter (server )),
92
- self .dut .aio .l2cap .Connect (connection = dut_ref_acl , ** request ),
78
+ transport = next (iter (request .keys ()))
79
+ ref_dut , dut_ref = await asyncio .gather (
80
+ self .ref .aio .l2cap .WaitConnection (connection = self .ref_dut [transport ], ** request ),
81
+ self .dut .aio .l2cap .Connect (connection = self .dut_ref [transport ], ** request ),
93
82
)
94
- assert_is_not_none (ref_dut_res .channel )
95
- assert_is_not_none (dut_ref_res .channel )
83
+ assert_is_not_none (ref_dut .channel )
84
+ assert_is_not_none (dut_ref .channel )
96
85
97
86
@avatar .parameterized (
98
- ('Classic' , dict (fixed = l2cap_pb2 .FixedChannelRequest (cid = FIXED_CHANNEL_CID ))),
99
- ('LE' , dict (fixed = l2cap_pb2 .FixedChannelRequest (cid = FIXED_CHANNEL_CID ))),
100
- ('Classic' , dict (basic = l2cap_pb2 .ConnectionOrientedChannelRequest (psm = CLASSIC_PSM ))),
101
- (
102
- 'LE' ,
103
- dict (
104
- le_credit_based = l2cap_pb2 .CreditBasedChannelRequest (
105
- spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256
106
- )
107
- ),
108
- ),
87
+ (dict (basic = dict (psm = CLASSIC_PSM )),),
88
+ (dict (le_credit_based = dict (spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256 )),),
109
89
) # type: ignore[misc]
110
90
@avatar .asynchronous
111
- async def test_on_connection (
91
+ async def test_wait_connection (
112
92
self ,
113
- transport : Union [Literal ['Classic' ], Literal ['LE' ]],
114
93
request : Dict [str , Any ],
115
94
) -> None :
116
- dut_ref_acl , ref_dut_acl = await CONNECTORS [transport ](self .dut , self .ref )
117
- server = self .dut .aio .l2cap .OnConnection (connection = dut_ref_acl , ** request )
118
- ref_dut_res , dut_ref_res = await asyncio .gather (
119
- self .ref .aio .l2cap .Connect (connection = ref_dut_acl , ** request ),
120
- anext (aiter (server )),
95
+ transport = next (iter (request .keys ()))
96
+ dut_ref , ref_dut = await asyncio .gather (
97
+ self .ref .aio .l2cap .WaitConnection (connection = self .dut_ref [transport ], ** request ),
98
+ self .dut .aio .l2cap .Connect (connection = self .ref_dut [transport ], ** request ),
121
99
)
122
- assert_is_not_none (ref_dut_res .channel )
123
- assert_is_not_none (dut_ref_res .channel )
100
+ assert_is_not_none (ref_dut .channel )
101
+ assert_is_not_none (dut_ref .channel )
124
102
125
103
@avatar .parameterized (
126
- ('Classic' , dict (basic = l2cap_pb2 .ConnectionOrientedChannelRequest (psm = CLASSIC_PSM ))),
127
- (
128
- 'LE' ,
129
- dict (
130
- le_credit_based = l2cap_pb2 .CreditBasedChannelRequest (
131
- spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256
132
- )
133
- ),
134
- ),
104
+ (dict (basic = dict (psm = CLASSIC_PSM )),),
105
+ (dict (le_credit_based = dict (spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256 )),),
135
106
) # type: ignore[misc]
136
107
@avatar .asynchronous
137
108
async def test_disconnect (
138
109
self ,
139
- transport : Union [Literal ['Classic' ], Literal ['LE' ]],
140
110
request : Dict [str , Any ],
141
111
) -> None :
142
- dut_ref_acl , ref_dut_acl = await CONNECTORS [transport ](self .dut , self .ref )
143
- server = self .ref .aio .l2cap .OnConnection (connection = ref_dut_acl , ** request )
144
- ref_dut_res , dut_ref_res = await asyncio .gather (
145
- anext (aiter (server )),
146
- self .dut .aio .l2cap .Connect (connection = dut_ref_acl , ** request ),
112
+ transport = next (iter (request .keys ()))
113
+ dut_ref , ref_dut = await asyncio .gather (
114
+ self .ref .aio .l2cap .WaitConnection (connection = self .dut_ref [transport ], ** request ),
115
+ self .dut .aio .l2cap .Connect (connection = self .ref_dut [transport ], ** request ),
147
116
)
148
- assert dut_ref_res .channel and ref_dut_res .channel
117
+ assert_is_not_none (ref_dut .channel )
118
+ assert_is_not_none (dut_ref .channel )
119
+ assert ref_dut .channel and dut_ref .channel
149
120
150
- await asyncio .gather (
151
- self .dut .aio .l2cap .Disconnect (channel = dut_ref_res .channel ),
152
- self .ref .aio .l2cap .WaitDisconnection (channel = ref_dut_res .channel ),
121
+ _ , dis = await asyncio .gather (
122
+ self .ref .aio .l2cap .WaitDisconnection (channel = ref_dut .channel ),
123
+ self .dut .aio .l2cap .Disconnect (channel = dut_ref .channel ),
153
124
)
154
125
126
+ assert_equal (dis .result_variant (), 'success' )
127
+
155
128
@avatar .parameterized (
156
- ('Classic' , dict (basic = l2cap_pb2 .ConnectionOrientedChannelRequest (psm = CLASSIC_PSM ))),
157
- (
158
- 'LE' ,
159
- dict (
160
- le_credit_based = l2cap_pb2 .CreditBasedChannelRequest (
161
- spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256
162
- )
163
- ),
164
- ),
129
+ (dict (basic = dict (psm = CLASSIC_PSM )),),
130
+ (dict (le_credit_based = dict (spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256 )),),
165
131
) # type: ignore[misc]
166
132
@avatar .asynchronous
167
133
async def test_wait_disconnection (
168
134
self ,
169
- transport : Union [Literal ['Classic' ], Literal ['LE' ]],
170
135
request : Dict [str , Any ],
171
136
) -> None :
172
- dut_ref_acl , ref_dut_acl = await CONNECTORS [transport ](self .dut , self .ref )
173
- server = self .ref .aio .l2cap .OnConnection (connection = ref_dut_acl , ** request )
174
- ref_dut_res , dut_ref_res = await asyncio .gather (
175
- anext (aiter (server )),
176
- self .dut .aio .l2cap .Connect (connection = dut_ref_acl , ** request ),
137
+ transport = next (iter (request .keys ()))
138
+ dut_ref , ref_dut = await asyncio .gather (
139
+ self .ref .aio .l2cap .WaitConnection (connection = self .dut_ref [transport ], ** request ),
140
+ self .dut .aio .l2cap .Connect (connection = self .ref_dut [transport ], ** request ),
177
141
)
178
- assert dut_ref_res .channel and ref_dut_res .channel
142
+ assert_is_not_none (ref_dut .channel )
143
+ assert_is_not_none (dut_ref .channel )
144
+ assert ref_dut .channel and dut_ref .channel
179
145
180
- await asyncio .gather (
181
- self .ref .aio .l2cap .Disconnect (channel = ref_dut_res .channel ),
182
- self .dut .aio .l2cap .WaitDisconnection (channel = dut_ref_res .channel ),
146
+ dis , _ = await asyncio .gather (
147
+ self .dut .aio .l2cap .WaitDisconnection (channel = dut_ref .channel ),
148
+ self .ref .aio .l2cap .Disconnect (channel = ref_dut .channel ),
183
149
)
184
150
151
+ assert_equal (dis .result_variant (), 'success' )
152
+
185
153
@avatar .parameterized (
186
- ('Classic' , dict (fixed = l2cap_pb2 .FixedChannelRequest (cid = FIXED_CHANNEL_CID ))),
187
- ('LE' , dict (fixed = l2cap_pb2 .FixedChannelRequest (cid = FIXED_CHANNEL_CID ))),
188
- ('Classic' , dict (basic = l2cap_pb2 .ConnectionOrientedChannelRequest (psm = CLASSIC_PSM ))),
189
- (
190
- 'LE' ,
191
- dict (
192
- le_credit_based = l2cap_pb2 .CreditBasedChannelRequest (
193
- spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256
194
- )
195
- ),
196
- ),
154
+ (dict (basic = dict (psm = CLASSIC_PSM )),),
155
+ (dict (le_credit_based = dict (spsm = LE_SPSM , mtu = 2046 , mps = 2048 , initial_credit = 256 )),),
197
156
) # type: ignore[misc]
198
157
@avatar .asynchronous
199
158
async def test_send (
200
159
self ,
201
- transport : Union [Literal ['Classic' ], Literal ['LE' ]],
202
160
request : Dict [str , Any ],
203
161
) -> None :
204
- dut_ref_acl , ref_dut_acl = await CONNECTORS [transport ](self .dut , self .ref )
205
- server = self .dut .aio .l2cap .OnConnection (connection = dut_ref_acl , ** request )
206
- ref_dut_res , dut_ref_res = await asyncio .gather (
207
- self .ref .aio .l2cap .Connect (connection = ref_dut_acl , ** request ),
208
- anext (aiter (server )),
162
+ transport = next (iter (request .keys ()))
163
+ dut_ref , ref_dut = await asyncio .gather (
164
+ self .ref .aio .l2cap .WaitConnection (connection = self .dut_ref [transport ], ** request ),
165
+ self .dut .aio .l2cap .Connect (connection = self .ref_dut [transport ], ** request ),
209
166
)
210
- ref_dut_channel = ref_dut_res .channel
211
- dut_ref_channel = dut_ref_res .channel
212
- assert_is_not_none (ref_dut_res .channel )
213
- assert_is_not_none (dut_ref_res .channel )
214
- assert ref_dut_channel and dut_ref_channel
215
-
216
- dut_ref_stream = self .ref .aio .l2cap .Receive (channel = dut_ref_channel )
217
- _send_res , recv_res = await asyncio .gather (
218
- self .dut .aio .l2cap .Send (channel = ref_dut_channel , data = b"The quick brown fox jumps over the lazy dog" ),
219
- anext (aiter (dut_ref_stream )),
167
+ assert_is_not_none (ref_dut .channel )
168
+ assert_is_not_none (dut_ref .channel )
169
+ assert ref_dut .channel and dut_ref .channel
170
+
171
+ ref_source = self .ref .aio .l2cap .Receive (channel = dut_ref .channel )
172
+ _ , recv = await asyncio .gather (
173
+ self .dut .aio .l2cap .Send (channel = ref_dut .channel , data = b"The quick brown fox jumps over the lazy dog" ),
174
+ anext (aiter (ref_source )),
220
175
)
221
- assert recv_res . data
222
- assert_equal (recv_res .data , b"The quick brown fox jumps over the lazy dog" )
176
+
177
+ assert_equal (recv .data , b"The quick brown fox jumps over the lazy dog" )
223
178
224
179
225
180
if __name__ == "__main__" :
0 commit comments