upnpmediaserver/contentdirectoryservice/src/upnpstatehandler.cpp
changeset 0 7f85d04be362
child 30 5ec426854821
equal deleted inserted replaced
-1:000000000000 0:7f85d04be362
       
     1 /** @file
       
     2 * Copyright (c) 2005-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:  State handler
       
    15 *
       
    16 */
       
    17 
       
    18 
       
    19 //  INCLUDES
       
    20 #include "upnpstatehandler.h"
       
    21 #include "upnpstring.h"
       
    22 #include "upnpcontainerupdateid.h"
       
    23 #include "upnpcontentdirectory.h"
       
    24 #include "upnpcontentdirectoryglobals.h"
       
    25 #include "upnpcommonupnplits.h"
       
    26 
       
    27 
       
    28 // -----------------------------------------------------------------------------
       
    29 // CUpnpStateHandler::CUpnpStateHandler
       
    30 // C++ default constructor can NOT contain any code, that
       
    31 // might leave.
       
    32 // -----------------------------------------------------------------------------
       
    33 //
       
    34 CUpnpStateHandler::CUpnpStateHandler(  )
       
    35 {
       
    36     iContainerUpdateIdsEvented = EFalse;          
       
    37 }
       
    38 
       
    39 
       
    40 // -----------------------------------------------------------------------------
       
    41 // CUpnpStateHandler::ConstructL
       
    42 // Symbian 2nd phase constructor can leave.
       
    43 // -----------------------------------------------------------------------------
       
    44 //
       
    45 void CUpnpStateHandler::ConstructL( CUpnpContentDirectory* aCd )
       
    46 {    
       
    47     iContainerUpdateIds.Reset();
       
    48     iCurrentContainerUpdateIds.Reset();
       
    49     iCd=aCd;
       
    50 }
       
    51 
       
    52 // -----------------------------------------------------------------------------
       
    53 // CUpnpStateHandler::NewL
       
    54 // Two-phased constructor.
       
    55 // -----------------------------------------------------------------------------
       
    56 //
       
    57 CUpnpStateHandler* CUpnpStateHandler::NewL( CUpnpContentDirectory* aCd )
       
    58 {
       
    59     CUpnpStateHandler* self = new (ELeave) CUpnpStateHandler(  );
       
    60 
       
    61     CleanupStack::PushL( self );
       
    62     self->ConstructL( aCd );
       
    63     CleanupStack::Pop( self );
       
    64     return self;
       
    65 }
       
    66 
       
    67 // -----------------------------------------------------------------------------
       
    68 // CUpnpStateHandler::~CUpnpStateHandler
       
    69 // Destructor
       
    70 // -----------------------------------------------------------------------------
       
    71 //
       
    72 CUpnpStateHandler::~CUpnpStateHandler()
       
    73 {   
       
    74     // clear tables related to ContainerUpdateIds state variable
       
    75     for( TInt i( 0 ); i < iContainerUpdateIds.Count(); i++ )
       
    76     {
       
    77         delete iContainerUpdateIds[i].iContainerId;
       
    78     }
       
    79     iContainerUpdateIds.Close(); 
       
    80     //--------------------------
       
    81     for( TInt i( 0 ); i < iCurrentContainerUpdateIds.Count(); i++ )
       
    82     {
       
    83         delete iCurrentContainerUpdateIds[i].iContainerId;
       
    84     }
       
    85     iCurrentContainerUpdateIds.Close();
       
    86     //-------------------------- 
       
    87 }
       
    88 
       
    89 // -----------------------------------------------------------------------------
       
    90 // CUpnpStateHandler::ContainerUpdateIds
       
    91 // Symbian 2nd phase constructor can leave.
       
    92 // -----------------------------------------------------------------------------
       
    93 //
       
    94 TInt CUpnpStateHandler::ContainerUpdateId( const TDesC8& aContainerID ) 
       
    95 {
       
    96     if( aContainerID.Compare( KZero ) == 0 )
       
    97     {
       
    98         return iSystemUpdateId;
       
    99     }
       
   100 
       
   101     for(TInt i( 0 ); i < iContainerUpdateIds.Count(); i++ )
       
   102     {
       
   103         if( aContainerID.Compare(*(iContainerUpdateIds[i].iContainerId))==0)
       
   104         {
       
   105             return iContainerUpdateIds[i].iUpdateId;
       
   106         }
       
   107     }
       
   108     return 0; //container not found so it is unmodified and updateId is zero.
       
   109 }
       
   110 
       
   111 // -----------------------------------------------------------------------------
       
   112 // CUpnpStateHandler::ContainerUpdateIds
       
   113 // Symbian 2nd phase constructor can leave.
       
   114 // -----------------------------------------------------------------------------
       
   115 //
       
   116 RArray<TUpnpContainerUpdateId>& CUpnpStateHandler::ContainerUpdateIds( )
       
   117 {    
       
   118     return iContainerUpdateIds;
       
   119 }
       
   120 // -----------------------------------------------------------------------------
       
   121 // CUpnpStateHandler::IsEnableL
       
   122 // (other items were commented in a header).
       
   123 // -----------------------------------------------------------------------------
       
   124 //
       
   125 TBool CUpnpStateHandler::IsEnable()
       
   126 {
       
   127     if (iCd->SubcribersAmount() > 0) return ETrue;       
       
   128     else return EFalse;
       
   129 }
       
   130 
       
   131 // -----------------------------------------------------------------------------
       
   132 // CUpnpStateHandler::IncreaseSystemUpdateIdL
       
   133 // (other items were commented in a header).
       
   134 // -----------------------------------------------------------------------------
       
   135 //
       
   136 TInt CUpnpStateHandler::IncreaseSystemUpdateIdL()
       
   137 {
       
   138     if( iSystemUpdateId < KMaxTUint )
       
   139     {
       
   140         iSystemUpdateId++;
       
   141     }
       
   142     else
       
   143     {
       
   144         iSystemUpdateId = 1;
       
   145     }
       
   146     TBuf8<UpnpString::KMaxIntLength> suid;
       
   147     suid.Num( iSystemUpdateId );
       
   148     iCd->SetStateVariableL( KSystemUpdateID, suid );
       
   149     return iSystemUpdateId;
       
   150 }
       
   151 // -----------------------------------------------------------------------------
       
   152 // CUpnpStateHandler::IncreaseContainerUpdateIdL
       
   153 // (other items were commented in a header).
       
   154 // -----------------------------------------------------------------------------
       
   155 //
       
   156 void CUpnpStateHandler::IncreaseContainerUpdateIdL( const TDesC8& aContainerID )
       
   157 {
       
   158     // DLNA.ORG_AnyContainer support - 'any container' 
       
   159     //mapped into container with id=1 
       
   160     HBufC8* properContainerID;
       
   161     
       
   162     if( !aContainerID.Compare(KAnyContainerIndicator8) )    
       
   163         properContainerID = KOne().AllocLC();    
       
   164     else    
       
   165         properContainerID = aContainerID.AllocLC();
       
   166     
       
   167     // iContainerUpdateIds table serving ---------------           
       
   168     TInt updateId( KErrNotFound );
       
   169     TInt i( 0 );
       
   170     for( ; i < iContainerUpdateIds.Count(); i++ )
       
   171     {
       
   172         if( properContainerID->Des().Compare(
       
   173                          *(iContainerUpdateIds[i].iContainerId) ) == 0 )
       
   174         {
       
   175             updateId = iContainerUpdateIds[i].iUpdateId;
       
   176             break;
       
   177         }
       
   178     }
       
   179 
       
   180     if( KErrNotFound == updateId ) //first touch to this conītainer
       
   181     {
       
   182         TUpnpContainerUpdateId cui;
       
   183         
       
   184         cui.iContainerId = properContainerID->AllocL();                                                                           
       
   185         //First time of modification, thus ID is 1.
       
   186         // No magic (white nor black) used here.
       
   187         cui.iUpdateId = 1;
       
   188         iContainerUpdateIds.Append( cui );
       
   189         updateId = cui.iUpdateId;
       
   190     }
       
   191     else
       
   192     {
       
   193         if( iContainerUpdateIds[i].iUpdateId == KMaxTInt )
       
   194         {
       
   195             iContainerUpdateIds[i].iUpdateId = 1;
       
   196         }
       
   197         else
       
   198         {
       
   199             iContainerUpdateIds[i].iUpdateId++;
       
   200         }
       
   201         updateId = iContainerUpdateIds[i].iUpdateId;
       
   202     }
       
   203     
       
   204     // iCurrentContainerUpdateIds table serving ---------------           
       
   205     if (IsEnable())     //if any CP subscribed   
       
   206     {
       
   207     if(iContainerUpdateIdsEvented)
       
   208     {
       
   209         // clearing iCurrentContainerUpdateIds table after:
       
   210         // 1. sending NOTIFY events, and
       
   211         // 2. 'ContainerUpdateIds' state variable change
       
   212         for( TInt i(0); i < iCurrentContainerUpdateIds.Count(); i++ )
       
   213         {
       
   214             delete iCurrentContainerUpdateIds[i].iContainerId;
       
   215         }
       
   216         iCurrentContainerUpdateIds.Reset();
       
   217          
       
   218        iContainerUpdateIdsEvented = EFalse; 
       
   219     }
       
   220     
       
   221     // finding out whether element should be updated or added                                       
       
   222     TBool isEelementFound = EFalse;
       
   223     TInt j( 0 );
       
   224     
       
   225     for( ; j < iCurrentContainerUpdateIds.Count(); j++ )
       
   226     {
       
   227         if( properContainerID->Des().Compare(
       
   228                          *(iCurrentContainerUpdateIds[j].iContainerId) ) == 0 )
       
   229         {            
       
   230             isEelementFound = ETrue;
       
   231             break;
       
   232         }
       
   233     }
       
   234     
       
   235     if(isEelementFound)
       
   236     {
       
   237         iCurrentContainerUpdateIds[j].iUpdateId = updateId;                              
       
   238     }
       
   239     else
       
   240     {
       
   241         TUpnpContainerUpdateId newEl;
       
   242         
       
   243         newEl.iContainerId = properContainerID->AllocL();                                                                                   
       
   244         newEl.iUpdateId = updateId;
       
   245         
       
   246         iCurrentContainerUpdateIds.Append(newEl);
       
   247     }
       
   248                             
       
   249     // preparing new value of 'ContainerUpdateIds' state variable ----   
       
   250                                 
       
   251     TInt elCount = iCurrentContainerUpdateIds.Count();
       
   252     TInt totalDescLength = 0;
       
   253         
       
   254     for( TInt k = 0; k < elCount; k++ )
       
   255     {
       
   256         totalDescLength = totalDescLength + 
       
   257                 (iCurrentContainerUpdateIds[k].iContainerId)->Des().Length();
       
   258     }    
       
   259     
       
   260     totalDescLength = totalDescLength + elCount*(UpnpString::KMaxIntLength)
       
   261             + elCount - 1;// 'elCount-1'-> quantity of commas in the descriptor
       
   262     
       
   263     HBufC8* variableValue  = HBufC8::NewLC(totalDescLength);                        
       
   264     TPtr8 pVar = variableValue->Des();
       
   265     pVar.Zero();
       
   266         
       
   267     for( TInt k = 0; k < elCount; k++ )
       
   268     {
       
   269         pVar.Append( *(iCurrentContainerUpdateIds[k].iContainerId) );
       
   270         pVar.Append(',');
       
   271         if ((iCurrentContainerUpdateIds[k].iContainerId)->Compare(KZero) == 0)
       
   272             pVar.AppendNum( iSystemUpdateId );
       
   273         else        
       
   274             pVar.AppendNum( iCurrentContainerUpdateIds[k].iUpdateId );    
       
   275         
       
   276         if( k != elCount - 1 ) // last comma not appended
       
   277             pVar.Append(',');
       
   278     }
       
   279                     
       
   280     //Set new value to be evented
       
   281     iCd->SetStateVariableL( KContainerUpdateIDs, *variableValue );
       
   282                             
       
   283     CleanupStack::PopAndDestroy( variableValue );
       
   284     }
       
   285     CleanupStack::PopAndDestroy( properContainerID );   
       
   286          
       
   287  }
       
   288 
       
   289 // -----------------------------------------------------------------------------
       
   290 // CUpnpStateHandler::StateVariableEvented
       
   291 // (other items were commented in a header).
       
   292 // -----------------------------------------------------------------------------
       
   293 //
       
   294 void CUpnpStateHandler::StateVariableEvented(const TDesC8& aVariableName)
       
   295 {
       
   296    /* if( aVariableName.Compare(KContainerUpdateIDs) == 0 
       
   297                         && (iCd->SubcribersAmount() > 0 )) */
       
   298     if( aVariableName.Compare(KContainerUpdateIDs) == 0)                         
       
   299     {        
       
   300         iContainerUpdateIdsEvented = ETrue;                                                
       
   301         return;
       
   302     }
       
   303 }
       
   304 
       
   305 //end of file