|
1 /* |
|
2 * Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 |
|
20 // INCLUDE FILES |
|
21 #include "mccresourceitem.h" |
|
22 #include "mccuids.hrh" |
|
23 #include "mcccontrollerlogs.h" |
|
24 #include "mccmultiplexer.h" |
|
25 #include "mccinternaldef.h" |
|
26 #include "mcccamerahandler.h" |
|
27 |
|
28 #include <mmf/server/mmfaudioinput.h> |
|
29 #include <mmf/server/mmfaudiooutput.h> |
|
30 |
|
31 // EXTERNAL DATA STRUCTURES |
|
32 |
|
33 // EXTERNAL FUNCTION PROTOTYPES |
|
34 |
|
35 // CONSTANTS |
|
36 const TInt KMccOneResourceUser = 1; |
|
37 |
|
38 // MACROS |
|
39 |
|
40 // LOCAL CONSTANTS AND MACROS |
|
41 |
|
42 // MODULE DATA STRUCTURES |
|
43 |
|
44 // LOCAL FUNCTION PROTOTYPES |
|
45 |
|
46 // FORWARD DECLARATIONS |
|
47 |
|
48 // ============================= LOCAL FUNCTIONS =============================== |
|
49 |
|
50 // ============================ MEMBER FUNCTIONS =============================== |
|
51 |
|
52 // ----------------------------------------------------------------------------- |
|
53 // CMccResourceItem::NewLC |
|
54 // ----------------------------------------------------------------------------- |
|
55 // |
|
56 CMccResourceItem* CMccResourceItem::NewLC( |
|
57 TUint32 aCurrentUserStreamId, |
|
58 MDataSink* aSink, |
|
59 MDataSource* aSource, |
|
60 TUint32 aEndpointId, |
|
61 TBool aIsMultiplexer ) |
|
62 { |
|
63 CMccResourceItem* self = |
|
64 new ( ELeave ) CMccResourceItem( aCurrentUserStreamId, |
|
65 aEndpointId, |
|
66 aIsMultiplexer ); |
|
67 CleanupStack::PushL( self ); |
|
68 self->ConstructL( aSink, aSource ); |
|
69 return self; |
|
70 } |
|
71 |
|
72 // ----------------------------------------------------------------------------- |
|
73 // CMccResourceItem::NewL |
|
74 // ----------------------------------------------------------------------------- |
|
75 // |
|
76 CMccResourceItem* CMccResourceItem::NewL( |
|
77 TUint32 aCurrentUserStreamId, |
|
78 MDataSink* aSink, |
|
79 MDataSource* aSource, |
|
80 TUint32 aEndpointId, |
|
81 TBool aIsMultiplexer ) |
|
82 { |
|
83 CMccResourceItem* self = |
|
84 CMccResourceItem::NewLC( aCurrentUserStreamId, |
|
85 aSink, |
|
86 aSource, |
|
87 aEndpointId, |
|
88 aIsMultiplexer ); |
|
89 CleanupStack::Pop( self ); |
|
90 return self; |
|
91 } |
|
92 |
|
93 // ----------------------------------------------------------------------------- |
|
94 // CMccResourceItem::~CMccResourceItem |
|
95 // ----------------------------------------------------------------------------- |
|
96 // |
|
97 CMccResourceItem::~CMccResourceItem() |
|
98 { |
|
99 __CONTROLLER( "CMccResourceItem::~CMccResourceItem" ) |
|
100 |
|
101 delete iMultiplexerItem; |
|
102 delete iMultiplexer; |
|
103 iUsers.Reset(); |
|
104 iUsers.Close(); |
|
105 |
|
106 iKeyFrameInfo.Close(); |
|
107 |
|
108 __CONTROLLER( "CMccResourceItem::~CMccResourceItem, exit" ) |
|
109 } |
|
110 |
|
111 // ----------------------------------------------------------------------------- |
|
112 // CMccResourceItem::IncreaseRefCount |
|
113 // ----------------------------------------------------------------------------- |
|
114 // |
|
115 TInt CMccResourceItem::IncreaseRefCount( const TMccResourceParams& aUser ) |
|
116 { |
|
117 __CONTROLLER( "CMccResourceItem::IncreaseRefCount" ) |
|
118 |
|
119 TInt err = iUsers.Append( aUser ); |
|
120 if ( !err && iMultiplexerItem ) |
|
121 { |
|
122 __CONTROLLER( "CMccResourceItem::IncreaseRefCount, call multiplexer" ) |
|
123 |
|
124 // Inform also the multiplexer |
|
125 err = iMultiplexerItem->IncreaseRefCount( aUser ); |
|
126 } |
|
127 return err; |
|
128 } |
|
129 |
|
130 // ----------------------------------------------------------------------------- |
|
131 // CMccResourceItem::DecreaseRefCount |
|
132 // ----------------------------------------------------------------------------- |
|
133 // |
|
134 TBool CMccResourceItem::DecreaseRefCount( const TMccResourceParams& aUser ) |
|
135 { |
|
136 __CONTROLLER( "CMccResourceItem::DecreaseRefCount" ) |
|
137 |
|
138 TIdentityRelation<TMccResourceParams> comparison( UserMatch ); |
|
139 TInt index = iUsers.Find( aUser, comparison ); |
|
140 if ( index != KErrNotFound ) |
|
141 { |
|
142 iUsers.Remove( index ); |
|
143 |
|
144 // Inform also the multiplexer |
|
145 if ( iMultiplexerItem ) |
|
146 { |
|
147 __CONTROLLER( "CMccResourceItem::DecreaseRefCount, call multiplexer" ) |
|
148 |
|
149 if ( iMultiplexerItem->DecreaseRefCount( aUser ) ) |
|
150 { |
|
151 __CONTROLLER( "CMccResourceItem::DecreaseRefCount, delete multiplexer" ) |
|
152 |
|
153 delete iMultiplexerItem; |
|
154 iMultiplexerItem = 0; |
|
155 } |
|
156 } |
|
157 } |
|
158 // If no more users, resource item can be deleted |
|
159 if ( iUsers.Count() == 0 ) |
|
160 { |
|
161 __CONTROLLER( "CMccResourceItem::DecreaseRefCount, can be removed" ) |
|
162 |
|
163 return ETrue; |
|
164 } |
|
165 |
|
166 __CONTROLLER( "CMccResourceItem::DecreaseRefCount, cannot be removed" ) |
|
167 |
|
168 iCurrentUserStreamId = iUsers[ 0 ].iStreamId; |
|
169 return EFalse; |
|
170 } |
|
171 |
|
172 // ----------------------------------------------------------------------------- |
|
173 // CMccResourceItem::RefCount |
|
174 // ----------------------------------------------------------------------------- |
|
175 // |
|
176 TInt CMccResourceItem::RefCount() const |
|
177 { |
|
178 return iUsers.Count(); |
|
179 } |
|
180 |
|
181 // ----------------------------------------------------------------------------- |
|
182 // CMccResourceItem::EndpointId |
|
183 // ----------------------------------------------------------------------------- |
|
184 // |
|
185 TUint32 CMccResourceItem::EndpointId() const |
|
186 { |
|
187 return iEndpointId; |
|
188 } |
|
189 |
|
190 // ----------------------------------------------------------------------------- |
|
191 // CMccResourceItem::IsNetworkResource |
|
192 // ----------------------------------------------------------------------------- |
|
193 // |
|
194 TBool CMccResourceItem::IsNetworkResource() const |
|
195 { |
|
196 TBool isNetworkResource = iSink ? |
|
197 iSink->DataSinkType().iUid == KImplUidRtpDataSink : |
|
198 iSource->DataSourceType().iUid == KImplUidRtpDataSource; |
|
199 |
|
200 return isNetworkResource; |
|
201 } |
|
202 |
|
203 // ----------------------------------------------------------------------------- |
|
204 // CMccResourceItem::IsResourceActive |
|
205 // ----------------------------------------------------------------------------- |
|
206 // |
|
207 TBool CMccResourceItem::IsResourceActive() const |
|
208 { |
|
209 return ( iState == MMccResources::EPrepared || |
|
210 iState == MMccResources::EStarted ); |
|
211 } |
|
212 |
|
213 // ----------------------------------------------------------------------------- |
|
214 // CMccResourceItem::IsSharedResource |
|
215 // ----------------------------------------------------------------------------- |
|
216 // |
|
217 TBool CMccResourceItem::IsSharedResource() const |
|
218 { |
|
219 TBool sharable = iIsMultiplexer || ( RefCount() > KMccOneResourceUser ); |
|
220 |
|
221 return sharable; |
|
222 } |
|
223 |
|
224 // ----------------------------------------------------------------------------- |
|
225 // CMccResourceItem::IsStandbyResource |
|
226 // ----------------------------------------------------------------------------- |
|
227 // |
|
228 TBool CMccResourceItem::IsStandbyResource() const |
|
229 { |
|
230 TBool standby( EFalse ); |
|
231 if ( iSink && iSink->DataSinkType() == KUidMmfAudioOutput ) |
|
232 { |
|
233 for ( TInt i = 0; i < iUsers.Count() && !standby; i++ ) |
|
234 { |
|
235 standby = iUsers[ i ].iIsStandby; |
|
236 } |
|
237 } |
|
238 return standby; |
|
239 } |
|
240 |
|
241 // ----------------------------------------------------------------------------- |
|
242 // CMccResourceItem::NeedsCamera |
|
243 // ----------------------------------------------------------------------------- |
|
244 // |
|
245 TBool CMccResourceItem::NeedsCamera( CMccCameraHandler& aCameraHandler ) |
|
246 { |
|
247 TBool needsCamera( EFalse ); |
|
248 if ( iState == MMccResources::EStarted ) |
|
249 { |
|
250 needsCamera = ETrue; |
|
251 } |
|
252 else if ( iState == MMccResources::EPrepared ) |
|
253 { |
|
254 needsCamera = aCameraHandler.IsViewFinderEnabled(); |
|
255 } |
|
256 else |
|
257 { |
|
258 // NOP |
|
259 } |
|
260 return needsCamera; |
|
261 } |
|
262 |
|
263 // ----------------------------------------------------------------------------- |
|
264 // CMccResourceItem::SetResourceStateL |
|
265 // ----------------------------------------------------------------------------- |
|
266 // |
|
267 TBool CMccResourceItem::SetResourceStateL( |
|
268 TUint32 aStreamId, |
|
269 MMccResources::TResourceState aState, |
|
270 TBool aStandbyControl, |
|
271 TBool aDtmfControl ) |
|
272 { |
|
273 __CONTROLLER_INT1( "CMccResourceItem::SetResourceStateL, old state:", iState ) |
|
274 __CONTROLLER_INT1( "CMccResourceItem::SetResourceStateL, proposed state:", aState ) |
|
275 |
|
276 TBool effectiveStateChange = EFalse; |
|
277 |
|
278 if ( iMultiplexerItem ) |
|
279 { |
|
280 __CONTROLLER( "CMccResourceItem::SetResourceStateL, multiplexer decision" ) |
|
281 |
|
282 effectiveStateChange = |
|
283 iMultiplexerItem->SetResourceStateL( |
|
284 aStreamId, aState, aStandbyControl, aDtmfControl ); |
|
285 |
|
286 // Actual resource follows multiplexer states |
|
287 iState = iMultiplexerItem->CurrentState(); |
|
288 } |
|
289 else |
|
290 { |
|
291 __CONTROLLER( "CMccResourceItem::SetResourceStateL, resource usage allowed" ) |
|
292 |
|
293 // For shared resources, all resource state change operations should |
|
294 // be passed further. |
|
295 effectiveStateChange = IsSharedResource(); |
|
296 |
|
297 TBool isStandbyResource = IsStandbyResource(); |
|
298 |
|
299 if ( isStandbyResource || aDtmfControl ) |
|
300 { |
|
301 // Special handling for standby resource and dtmf |
|
302 SpecialStateChangeL( aStreamId, |
|
303 aState, |
|
304 aStandbyControl, |
|
305 aDtmfControl, |
|
306 effectiveStateChange ); |
|
307 } |
|
308 else |
|
309 { |
|
310 TBool stateOK( EFalse ); |
|
311 |
|
312 switch ( aState ) |
|
313 { |
|
314 case MMccResources::EPrepared: |
|
315 { |
|
316 if ( MMccResources::EConstructed == iState ) |
|
317 { |
|
318 stateOK = ETrue; |
|
319 } |
|
320 else if ( iState == MMccResources::EStarted || |
|
321 iState == MMccResources::EResourcePaused ) |
|
322 { |
|
323 // Endpoint is already started by other user, |
|
324 // state is not "downgraded" |
|
325 aState = iState; |
|
326 stateOK = ETrue; |
|
327 } |
|
328 else |
|
329 { |
|
330 // NOP |
|
331 } |
|
332 break; |
|
333 } |
|
334 case MMccResources::EStarted: |
|
335 { |
|
336 if ( MMccResources::EPrepared == iState || |
|
337 MMccResources::EResourcePaused == iState ) |
|
338 { |
|
339 stateOK = ETrue; |
|
340 } |
|
341 break; |
|
342 } |
|
343 case MMccResources::EResourcePaused: |
|
344 { |
|
345 if ( MMccResources::EStarted == iState ) |
|
346 { |
|
347 stateOK = ETrue; |
|
348 } |
|
349 break; |
|
350 } |
|
351 case MMccResources::EResourceStopped: |
|
352 { |
|
353 // Endpoint cannot be stopped until all its users |
|
354 // want to stop it. |
|
355 if ( !UserStopL( aStreamId ) ) |
|
356 { |
|
357 aState = iState; |
|
358 effectiveStateChange = EFalse; |
|
359 } |
|
360 stateOK = ETrue; |
|
361 break; |
|
362 } |
|
363 default: |
|
364 { |
|
365 break; |
|
366 } |
|
367 } |
|
368 |
|
369 if ( aState != iState ) |
|
370 { |
|
371 __ASSERT_ALWAYS( stateOK || effectiveStateChange, |
|
372 User::Leave( KErrNotReady ) ); |
|
373 |
|
374 iState = aState; |
|
375 |
|
376 effectiveStateChange = ETrue; |
|
377 } |
|
378 } |
|
379 } |
|
380 |
|
381 __CONTROLLER_INT1( "CMccResourceItem::SetResourceStateL, effective change:", |
|
382 effectiveStateChange ) |
|
383 __CONTROLLER_INT1( "CMccResourceItem::SetResourceStateL, exit with state:", |
|
384 iState ) |
|
385 |
|
386 return effectiveStateChange; |
|
387 } |
|
388 |
|
389 // ----------------------------------------------------------------------------- |
|
390 // CMccResourceItem::IsSink |
|
391 // ----------------------------------------------------------------------------- |
|
392 // |
|
393 TBool CMccResourceItem::IsSink() const |
|
394 { |
|
395 return ( iSink != 0 ); |
|
396 } |
|
397 |
|
398 // ----------------------------------------------------------------------------- |
|
399 // CMccResourceItem::IsSource |
|
400 // ----------------------------------------------------------------------------- |
|
401 // |
|
402 TBool CMccResourceItem::IsSource() const |
|
403 { |
|
404 return ( iSource != 0 ); |
|
405 } |
|
406 |
|
407 // ----------------------------------------------------------------------------- |
|
408 // CMccResourceItem::IsInternal |
|
409 // ----------------------------------------------------------------------------- |
|
410 // |
|
411 TBool CMccResourceItem::IsInternal() const |
|
412 { |
|
413 TBool isInternal = iSink ? IsInternal( iSink->DataSinkType().iUid ) : |
|
414 IsInternal( iSource->DataSourceType().iUid ); |
|
415 |
|
416 return isInternal; |
|
417 } |
|
418 |
|
419 // ----------------------------------------------------------------------------- |
|
420 // CMccResourceItem::Source |
|
421 // ----------------------------------------------------------------------------- |
|
422 // |
|
423 MDataSource* CMccResourceItem::Source() |
|
424 { |
|
425 return iSource; |
|
426 } |
|
427 |
|
428 // ----------------------------------------------------------------------------- |
|
429 // CMccResourceItem::Sink |
|
430 // ----------------------------------------------------------------------------- |
|
431 // |
|
432 MDataSink* CMccResourceItem::Sink() |
|
433 { |
|
434 return iSink; |
|
435 } |
|
436 |
|
437 // ----------------------------------------------------------------------------- |
|
438 // CMccResourceItem::MultiplexerL |
|
439 // ----------------------------------------------------------------------------- |
|
440 // |
|
441 CMccMultiplexer* CMccResourceItem::MultiplexerL() |
|
442 { |
|
443 if ( !iMultiplexerItem ) |
|
444 { |
|
445 iMultiplexerItem = |
|
446 CMccResourceItem::NewL( iCurrentUserStreamId, |
|
447 iSink, |
|
448 iSource, |
|
449 iEndpointId, |
|
450 ETrue ); |
|
451 |
|
452 // Update ref count immediately |
|
453 for ( TInt i = 0; i < iUsers.Count(); i++ ) |
|
454 { |
|
455 User::LeaveIfError( |
|
456 iMultiplexerItem->IncreaseRefCount( iUsers[ i ] ) ); |
|
457 } |
|
458 } |
|
459 return iMultiplexerItem->GetMultiplexerL(); |
|
460 } |
|
461 |
|
462 // ----------------------------------------------------------------------------- |
|
463 // CMccResourceItem::GetMultiplexerL |
|
464 // ----------------------------------------------------------------------------- |
|
465 // |
|
466 CMccMultiplexer* CMccResourceItem::GetMultiplexerL() |
|
467 { |
|
468 __ASSERT_ALWAYS( iMultiplexer, User::Leave( KErrNotReady ) ); |
|
469 |
|
470 return iMultiplexer; |
|
471 } |
|
472 |
|
473 // ----------------------------------------------------------------------------- |
|
474 // CMccResourceItem::UserSessionMatch |
|
475 // ----------------------------------------------------------------------------- |
|
476 // |
|
477 TBool CMccResourceItem::UserSessionMatch( |
|
478 const TMccResourceParams& aUser1, |
|
479 const TMccResourceParams& aUser2 ) |
|
480 { |
|
481 return ( aUser1.iSessionId == aUser2.iSessionId ); |
|
482 } |
|
483 |
|
484 // ----------------------------------------------------------------------------- |
|
485 // CMccResourceItem::UserMatch |
|
486 // ----------------------------------------------------------------------------- |
|
487 // |
|
488 TBool CMccResourceItem::UserMatch( |
|
489 const TMccResourceParams& aUser1, |
|
490 const TMccResourceParams& aUser2 ) |
|
491 { |
|
492 return ( aUser1.iStreamId == aUser2.iStreamId ); |
|
493 } |
|
494 |
|
495 // ----------------------------------------------------------------------------- |
|
496 // CMccResourceItem::UserMatchNotStrict |
|
497 // ----------------------------------------------------------------------------- |
|
498 // |
|
499 TBool CMccResourceItem::UserMatchNotStrict( |
|
500 const TMccResourceParams& aUser1, |
|
501 const TMccResourceParams& aUser2 ) |
|
502 { |
|
503 if ( aUser1.iLinkId ) |
|
504 { |
|
505 return ( aUser1.iLinkId == aUser2.iLinkId ); |
|
506 } |
|
507 return UserMatch( aUser1, aUser2 ); |
|
508 } |
|
509 |
|
510 // ----------------------------------------------------------------------------- |
|
511 // CMccResourceItem::UserMatchActive |
|
512 // ----------------------------------------------------------------------------- |
|
513 // |
|
514 TBool CMccResourceItem::UserMatchActive( |
|
515 const TMccResourceParams& /*aUser1*/, |
|
516 const TMccResourceParams& aUser2 ) |
|
517 { |
|
518 // First argument is the search term, in this case it can be ignored |
|
519 return ( !aUser2.iIsStopped ); |
|
520 } |
|
521 |
|
522 // ----------------------------------------------------------------------------- |
|
523 // CMccResourceItem::UsersInfoL |
|
524 // ----------------------------------------------------------------------------- |
|
525 // |
|
526 void CMccResourceItem::UsersInfoL( RArray<TMccResourceParams>& aUsers ) |
|
527 { |
|
528 for ( TInt i = 0; i < iUsers.Count(); i++ ) |
|
529 { |
|
530 aUsers.AppendL( iUsers[ i ] ); |
|
531 } |
|
532 } |
|
533 |
|
534 // ----------------------------------------------------------------------------- |
|
535 // CMccResourceItem::CurrentState |
|
536 // ----------------------------------------------------------------------------- |
|
537 // |
|
538 MMccResources::TResourceState CMccResourceItem::CurrentState() const |
|
539 { |
|
540 return iState; |
|
541 } |
|
542 |
|
543 // ----------------------------------------------------------------------------- |
|
544 // CMccResourceItem::Match |
|
545 // ----------------------------------------------------------------------------- |
|
546 // |
|
547 TBool CMccResourceItem::Match( const TMccResourceParams& aUser ) const |
|
548 { |
|
549 TIdentityRelation<TMccResourceParams> comparison( UserMatchNotStrict ); |
|
550 TInt index = iUsers.Find( aUser, comparison ); |
|
551 return ( index != KErrNotFound ); |
|
552 } |
|
553 |
|
554 // ----------------------------------------------------------------------------- |
|
555 // CMccResourceItem::MatchSession |
|
556 // ----------------------------------------------------------------------------- |
|
557 // |
|
558 TBool CMccResourceItem::MatchSession( const TUint32 aSessionId ) const |
|
559 { |
|
560 TMccResourceParams searchTerm( aSessionId, 0, 0, 0, EFalse, 0 ); |
|
561 TIdentityRelation<TMccResourceParams> comparison( UserSessionMatch ); |
|
562 TInt index = iUsers.Find( searchTerm, comparison ); |
|
563 return ( index != KErrNotFound ); |
|
564 } |
|
565 |
|
566 // ----------------------------------------------------------------------------- |
|
567 // CMccResourceItem::StoreKeyFrameInfoL |
|
568 // ----------------------------------------------------------------------------- |
|
569 // |
|
570 void CMccResourceItem::StoreKeyFrameInfoL( CMMFBuffer& aKeyFrame ) |
|
571 { |
|
572 __CONTROLLER_INT1( "CMccResourceItem::StoreKeyFrameInfoL, timestamp:", |
|
573 aKeyFrame.TimeToPlay().Int64() ) |
|
574 |
|
575 if ( iKeyFrameInfo.Count() >= KMccMaxNumKeyFrames ) |
|
576 { |
|
577 iKeyFrameInfo.Remove( 0 ); |
|
578 iKeyFrameInfo.Compress(); |
|
579 } |
|
580 TMccKeyFrameInfo info; |
|
581 info.iSeqNum = aKeyFrame.FrameNumber(); |
|
582 info.iTimestamp = aKeyFrame.TimeToPlay().Int64(); |
|
583 iKeyFrameInfo.AppendL( info ); |
|
584 } |
|
585 |
|
586 // ----------------------------------------------------------------------------- |
|
587 // CMccResourceItem::IsKeyFrame |
|
588 // ----------------------------------------------------------------------------- |
|
589 // |
|
590 TBool CMccResourceItem::IsKeyFrame( CMMFBuffer& aBuffer ) |
|
591 { |
|
592 TBool isKeyFrame( EFalse ); |
|
593 for ( TInt i = 0; i < iKeyFrameInfo.Count() && !isKeyFrame; i++ ) |
|
594 { |
|
595 TMccKeyFrameInfo& info = iKeyFrameInfo[ i ]; |
|
596 isKeyFrame = ( info.iSeqNum == aBuffer.FrameNumber() && |
|
597 info.iTimestamp == aBuffer.TimeToPlay().Int64() ); |
|
598 } |
|
599 return isKeyFrame; |
|
600 } |
|
601 |
|
602 // ----------------------------------------------------------------------------- |
|
603 // CMccResourceItem::IsCurrentUser |
|
604 // ----------------------------------------------------------------------------- |
|
605 // |
|
606 TBool CMccResourceItem::IsCurrentUser( TUint32 aStreamId ) const |
|
607 { |
|
608 return ( iCurrentUserStreamId == aStreamId ); |
|
609 } |
|
610 |
|
611 // ----------------------------------------------------------------------------- |
|
612 // CMccResourceItem::NonSharableResource |
|
613 // ----------------------------------------------------------------------------- |
|
614 // |
|
615 TBool CMccResourceItem::NonSharableResource( TUid aUid ) const |
|
616 { |
|
617 // TBD! sharing audiooutput should be possible with multiplexer |
|
618 return ( aUid == KUidMmfAudioInput || |
|
619 aUid == KUidMmfAudioOutput ); |
|
620 } |
|
621 |
|
622 // ----------------------------------------------------------------------------- |
|
623 // CMccResourceItem::IsInternal |
|
624 // ----------------------------------------------------------------------------- |
|
625 // |
|
626 TBool CMccResourceItem::IsInternal( TUint32 aUid ) const |
|
627 { |
|
628 return MCC_INTERNAL_ENDPOINT( aUid ); |
|
629 } |
|
630 |
|
631 // ----------------------------------------------------------------------------- |
|
632 // CMccResourceItem::CMccResourceItem |
|
633 // ----------------------------------------------------------------------------- |
|
634 // |
|
635 CMccResourceItem::CMccResourceItem( |
|
636 TUint32 aCurrentUserStreamId, |
|
637 TUint32 aEndpointId, |
|
638 TBool aIsMultiplexer ) : |
|
639 iCurrentUserStreamId( aCurrentUserStreamId ), |
|
640 iEndpointId( aEndpointId ), |
|
641 iIsMultiplexer( aIsMultiplexer ) |
|
642 { |
|
643 } |
|
644 |
|
645 // ----------------------------------------------------------------------------- |
|
646 // CMccResourceItem::ConstructL |
|
647 // ----------------------------------------------------------------------------- |
|
648 // |
|
649 void CMccResourceItem::ConstructL( |
|
650 MDataSink* aSink, |
|
651 MDataSource* aSource ) |
|
652 { |
|
653 __CONTROLLER( "CMccResourceItem::ConstructL" ) |
|
654 |
|
655 // Resource item can contain sink OR source |
|
656 |
|
657 if ( aSink ) |
|
658 { |
|
659 __ASSERT_ALWAYS( !aSource, User::Leave( KErrArgument ) ); |
|
660 iSink = aSink; |
|
661 } |
|
662 else if ( aSource ) |
|
663 { |
|
664 __ASSERT_ALWAYS( !aSink, User::Leave( KErrArgument ) ); |
|
665 iSource = aSource; |
|
666 } |
|
667 else |
|
668 { |
|
669 User::Leave( KErrArgument ); |
|
670 } |
|
671 |
|
672 if ( iIsMultiplexer ) |
|
673 { |
|
674 __CONTROLLER( "CMccResourceItem::ConstructL, create real multiplexer" ) |
|
675 |
|
676 __ASSERT_ALWAYS( iSource, User::Leave( KErrNotReady ) ); |
|
677 iMultiplexer = CMccMultiplexer::NewL( iSource ); |
|
678 } |
|
679 |
|
680 __CONTROLLER( "CMccResourceItem::ConstructL, exit" ) |
|
681 } |
|
682 |
|
683 // ----------------------------------------------------------------------------- |
|
684 // CMccResourceItem::SpecialStateChangeL |
|
685 // ----------------------------------------------------------------------------- |
|
686 // |
|
687 void CMccResourceItem::SpecialStateChangeL( |
|
688 TUint32 aStreamId, |
|
689 MMccResources::TResourceState aState, |
|
690 TBool aStandbyControl, |
|
691 TBool aDtmfControl, |
|
692 TBool& aEffectiveStateChange ) |
|
693 { |
|
694 __CONTROLLER( "CMccResourceItem::StandbyStateChangeL" ) |
|
695 __CONTROLLER_INT1( "CMccResourceItem::StandbyStateChangeL, paused by user:", |
|
696 iPausedByUser ) |
|
697 __CONTROLLER_INT1( "CMccResourceItem::StandbyStateChangeL, standby control:", |
|
698 aStandbyControl ) |
|
699 |
|
700 // For standby resource, pausing prepared resource is ok but it's not |
|
701 // an effective state change as pause is not really needed. If standby |
|
702 // resource has been paused by user, standby control will not have |
|
703 // any effect. Additionally, user paused stream is not resumed if user |
|
704 // tries to do it. Dtmf stream cannot pause its endpoints if others are |
|
705 // using them. |
|
706 |
|
707 TBool stateOK( EFalse ); |
|
708 |
|
709 TBool nonEffective = |
|
710 ( iPausedByUser && aStandbyControl ) || |
|
711 ( !aStandbyControl && !aDtmfControl && aState == MMccResources::EStarted ) || |
|
712 ( aDtmfControl && aStandbyControl && aState == MMccResources::EResourcePaused && |
|
713 ( RefCount() > KMccOneResourceUser ) ); |
|
714 |
|
715 switch ( aState ) |
|
716 { |
|
717 case MMccResources::EPrepared: |
|
718 { |
|
719 if ( MMccResources::EConstructed == iState ) |
|
720 { |
|
721 stateOK = ETrue; |
|
722 } |
|
723 else if ( iState == MMccResources::EStarted || |
|
724 iState == MMccResources::EResourcePaused ) |
|
725 { |
|
726 // Endpoint is already started by other user, |
|
727 // state is not "downgraded" |
|
728 aState = iState; |
|
729 stateOK = ETrue; |
|
730 } |
|
731 else |
|
732 { |
|
733 // NOP |
|
734 } |
|
735 break; |
|
736 } |
|
737 case MMccResources::EStarted: |
|
738 { |
|
739 if ( MMccResources::EPrepared == iState || |
|
740 MMccResources::EResourcePaused == iState ) |
|
741 { |
|
742 stateOK = ETrue; |
|
743 } |
|
744 break; |
|
745 } |
|
746 case MMccResources::EResourcePaused: |
|
747 { |
|
748 if ( MMccResources::EStarted == iState ) |
|
749 { |
|
750 stateOK = ETrue; |
|
751 } |
|
752 else if ( MMccResources::EPrepared == iState ) |
|
753 { |
|
754 stateOK = ETrue; |
|
755 nonEffective = ETrue; |
|
756 } |
|
757 else |
|
758 { |
|
759 } |
|
760 |
|
761 break; |
|
762 } |
|
763 case MMccResources::EResourceStopped: |
|
764 { |
|
765 nonEffective = !UserStopL( aStreamId ); |
|
766 stateOK = ETrue; |
|
767 break; |
|
768 } |
|
769 default: |
|
770 { |
|
771 break; |
|
772 } |
|
773 } |
|
774 |
|
775 if ( aState != iState ) |
|
776 { |
|
777 if ( !nonEffective ) |
|
778 { |
|
779 __ASSERT_ALWAYS( stateOK, User::Leave( KErrNotReady ) ); |
|
780 |
|
781 iState = aState; |
|
782 } |
|
783 |
|
784 aEffectiveStateChange = !nonEffective; |
|
785 } |
|
786 |
|
787 if ( !aStandbyControl ) |
|
788 { |
|
789 // Update paused by user info |
|
790 iPausedByUser = ( MMccResources::EResourcePaused == aState || |
|
791 MMccResources::EPrepared == aState ); |
|
792 } |
|
793 |
|
794 __CONTROLLER( "CMccResourceItem::StandbyStateChangeL, exit" ) |
|
795 } |
|
796 |
|
797 // ----------------------------------------------------------------------------- |
|
798 // CMccResourceItem::UserStopL |
|
799 // ----------------------------------------------------------------------------- |
|
800 // |
|
801 TBool CMccResourceItem::UserStopL( TUint32 aStreamId ) |
|
802 { |
|
803 TMccResourceParams searchTerm( 0, 0, aStreamId, 0, EFalse, 0 ); |
|
804 TIdentityRelation<TMccResourceParams> comparison( UserMatch ); |
|
805 TInt index = iUsers.Find( searchTerm, comparison ); |
|
806 __ASSERT_ALWAYS( index != KErrNotFound, User::Leave( KErrNotFound ) ); |
|
807 iUsers[ index ].iIsStopped = ETrue; |
|
808 |
|
809 TIdentityRelation<TMccResourceParams> comparison2( UserMatchActive ); |
|
810 index = iUsers.Find( searchTerm, comparison2 ); |
|
811 |
|
812 // If didn't found any active ones, the resource can be stopped |
|
813 return ( index == KErrNotFound ); |
|
814 } |
|
815 |
|
816 // End of file |
|
817 |