wlan_bearer/wlanengine/wlan_common/wlanengine_common_3.1/src/core_sub_operation_roam_update_ts.cpp
changeset 0 c40eb8fe8501
child 12 af3fb27c7511
equal deleted inserted replaced
-1:000000000000 0:c40eb8fe8501
       
     1 /*
       
     2 * Copyright (c) 2005-2010 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 the License "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:  Statemachine for updating traffic stream statuses after roam.
       
    15 *
       
    16 */
       
    17 
       
    18 /*
       
    19 * %version: 12 %
       
    20 */
       
    21 
       
    22 #include "core_sub_operation_roam_update_ts.h"
       
    23 #include "core_sub_operation_create_ts.h"
       
    24 #include "core_frame_wmm_ie.h"
       
    25 #include "core_server.h"
       
    26 #include "core_tools.h"
       
    27 #include "am_debug.h"
       
    28 
       
    29 // ======== MEMBER FUNCTIONS ========
       
    30 
       
    31 // ---------------------------------------------------------------------------
       
    32 // ---------------------------------------------------------------------------
       
    33 //
       
    34 core_sub_operation_roam_update_ts_c::core_sub_operation_roam_update_ts_c(
       
    35     u32_t request_id,
       
    36     core_server_c* server,
       
    37     abs_core_driverif_c* drivers,
       
    38     abs_core_server_callback_c* adaptation,
       
    39     core_ap_data_c& ap_data ) :
       
    40     core_operation_base_c( core_operation_unspecified, request_id, server, drivers, adaptation,
       
    41         core_base_flag_none ),
       
    42     current_ap_m( ap_data ),
       
    43     virtual_stream_list_m(),
       
    44     virtual_stream_iter_m( virtual_stream_list_m ),
       
    45     stream_list_m(),
       
    46     stream_iter_m( stream_list_m ),
       
    47     tid_m( 0 ),
       
    48     user_priority_m( 0 )
       
    49     {
       
    50     DEBUG( "core_sub_operation_roam_update_ts_c::core_sub_operation_roam_update_ts_c()" );
       
    51     }
       
    52 
       
    53 // ---------------------------------------------------------------------------
       
    54 // ---------------------------------------------------------------------------
       
    55 //
       
    56 core_sub_operation_roam_update_ts_c::~core_sub_operation_roam_update_ts_c()
       
    57     {
       
    58     DEBUG( "core_sub_operation_roam_update_ts_c::~core_sub_operation_roam_update_ts_c()" );
       
    59     }
       
    60     
       
    61 // ---------------------------------------------------------------------------
       
    62 // ---------------------------------------------------------------------------
       
    63 //
       
    64 core_error_e core_sub_operation_roam_update_ts_c::next_state()
       
    65     {
       
    66     DEBUG( "core_sub_operation_roam_update_ts_c::next_state()" );
       
    67     
       
    68     switch( operation_state_m )
       
    69         {
       
    70         case core_state_init:
       
    71             {
       
    72             if( !server_m->get_core_settings().is_connected() )
       
    73                 {
       
    74                 DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - not connected, nothing to do" );
       
    75 
       
    76                 return core_error_general;
       
    77                 }
       
    78 
       
    79             bool_t is_ac_required[MAX_QOS_ACCESS_CLASS] =
       
    80                 { 
       
    81                 current_ap_m.is_admission_control_required(
       
    82                     core_access_class_best_effort ),
       
    83                 current_ap_m.is_admission_control_required(
       
    84                     core_access_class_background ),
       
    85                 current_ap_m.is_admission_control_required(
       
    86                     core_access_class_video ),
       
    87                 current_ap_m.is_admission_control_required(
       
    88                     core_access_class_voice )
       
    89                 };
       
    90 
       
    91             /**
       
    92              * If admission control is mandatory for an access class, send an indication
       
    93              * to notify clients that this access class is no longer admitted.
       
    94              * 
       
    95              * If admission control is not mandatory, send an indication that
       
    96              * this access class is admitted.
       
    97              */
       
    98             for( u8_t idx( 0 ); idx < MAX_QOS_ACCESS_CLASS; ++idx )
       
    99                 {
       
   100                 if( is_ac_required[idx] )
       
   101                     {
       
   102                     server_m->get_connection_data()->set_ac_traffic_status(
       
   103                         static_cast<core_access_class_e>( idx ),
       
   104                         core_access_class_traffic_status_not_admitted );
       
   105 
       
   106                     DEBUG1( "core_operation_handle_delete_ts_c::next_state() - traffic no longer admitted on AC %u, notifying clients",
       
   107                         idx );
       
   108 
       
   109                     u8_t buf[5];
       
   110                     buf[0] = idx; 
       
   111                     buf[1] = static_cast<u8_t>(
       
   112                         core_access_class_traffic_status_not_admitted );
       
   113                     adaptation_m->notify(
       
   114                         core_notification_ac_traffic_status_changed,
       
   115                         sizeof( buf ),
       
   116                         buf );                
       
   117                     }
       
   118                 else
       
   119                     {
       
   120                     server_m->get_connection_data()->set_ac_traffic_status(
       
   121                         static_cast<core_access_class_e>( idx ),
       
   122                         core_access_class_traffic_status_admitted );
       
   123 
       
   124                     DEBUG1( "core_operation_handle_delete_ts_c::next_state() - traffic admitted on AC %u, notifying clients",
       
   125                         idx );
       
   126 
       
   127                     u8_t buf[5];
       
   128                     buf[0] = idx; 
       
   129                     buf[1] = static_cast<u8_t>(
       
   130                         core_access_class_traffic_status_admitted );
       
   131                     adaptation_m->notify(
       
   132                         core_notification_ac_traffic_status_changed,
       
   133                         sizeof( buf ),
       
   134                         buf );                    
       
   135                     }
       
   136                 }
       
   137 
       
   138             core_traffic_stream_list_c& ts_list(
       
   139                 server_m->get_connection_data()->traffic_stream_list() );
       
   140             core_virtual_traffic_stream_list_c& virtual_ts_list(
       
   141                 server_m->get_connection_data()->virtual_traffic_stream_list() );
       
   142             core_traffic_stream_list_iter_c ts_iter( ts_list );
       
   143             core_virtual_traffic_stream_list_iter_c virtual_ts_iter( virtual_ts_list );
       
   144             
       
   145             DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - traffic streams before processing:" );
       
   146             virtual_ts_list.print_contents();
       
   147             ts_list.print_contents();
       
   148 
       
   149             /**
       
   150              * Create a list of virtual traffic streams that are currently
       
   151              * inactive and need to be created, i.e. admission control is
       
   152              * mandatory for the access class.
       
   153              */
       
   154             core_virtual_traffic_stream_c* virtual_iter = virtual_ts_iter.first();
       
   155             while( virtual_iter )
       
   156                 {
       
   157                 if( is_ac_required[virtual_iter->access_class()] &&
       
   158                     virtual_iter->status() != core_traffic_stream_status_active )
       
   159                     {
       
   160                     DEBUG1( "core_sub_operation_roam_update_ts_c::next_state() - virtual traffic stream with ID %u needs to created",
       
   161                         virtual_iter->id() );
       
   162 
       
   163                     virtual_stream_list_m.add_traffic_stream(
       
   164                         *virtual_iter );
       
   165                     }
       
   166 
       
   167                 virtual_iter = virtual_ts_iter.next();
       
   168                 }
       
   169 
       
   170             /**
       
   171              * Delete all traffic streams that are no longer needed or that have
       
   172              * been marked as rejected. Create a list of traffic streams that 
       
   173              * need to be re-created.
       
   174              * 
       
   175              * There is no need to reset the TX queue parameters since
       
   176              * UMAC will reset them automatically after an association.
       
   177              */
       
   178             core_traffic_stream_c* iter = ts_iter.first();
       
   179             while( iter )
       
   180                 {
       
   181                 if( !is_ac_required[iter->access_class()] )
       
   182                     {
       
   183                     DEBUG2( "core_sub_operation_roam_update_ts_c::next_state() - traffic stream (TID %u, user priority %u) is no longer needed, deleting",
       
   184                         iter->tid(), iter->user_priority() );                        
       
   185 
       
   186                     /**
       
   187                      * Send a status update to all affected virtual traffic streams. 
       
   188                      */
       
   189                     set_virtual_traffic_stream_inactive_by_tid(
       
   190                         iter->tid(),
       
   191                         core_traffic_stream_status_inactive_not_required );                    
       
   192                     
       
   193                     /**
       
   194                      * Delete the actual traffic stream.
       
   195                      */
       
   196                     server_m->get_wpx_adaptation_instance().handle_ts_delete(
       
   197                         iter->tid(), iter->user_priority() );                   
       
   198                     ts_iter.remove();
       
   199                     }
       
   200                 else if( iter->status() == core_traffic_stream_status_undefined )
       
   201                     {
       
   202                     DEBUG2( "core_sub_operation_roam_update_ts_c::next_state() - traffic stream (TID %u, user priority %u) needs to be re-created",
       
   203                         iter->tid(), iter->user_priority() );
       
   204 
       
   205                     stream_list_m.update_traffic_stream( *iter );
       
   206                     }
       
   207                 else if( iter->status() != core_traffic_stream_status_active )
       
   208                     {
       
   209                     DEBUG2( "core_sub_operation_roam_update_ts_c::next_state() - traffic stream (TID %u, user priority %u) is marked as rejected, deleting",
       
   210                         iter->tid(), iter->user_priority() );
       
   211 
       
   212                     /**
       
   213                      * Send a status update to all affected virtual traffic streams. 
       
   214                      */
       
   215                     set_virtual_traffic_stream_inactive_by_tid(
       
   216                         iter->tid(),
       
   217                         iter->status() );                        
       
   218 
       
   219                     /**
       
   220                      * Delete the actual traffic stream.
       
   221                      */
       
   222                     server_m->get_wpx_adaptation_instance().handle_ts_delete(
       
   223                         iter->tid(), iter->user_priority() );                   
       
   224                     ts_iter.remove();
       
   225                     }
       
   226 
       
   227                 iter = ts_iter.next();
       
   228                 }
       
   229 
       
   230             (void)stream_iter_m.first();
       
   231 
       
   232             return goto_state( core_state_recreate_next );
       
   233             }
       
   234         case core_state_recreate_next:
       
   235             {
       
   236             core_traffic_stream_c* iter = stream_iter_m.current();
       
   237             if( !iter )
       
   238                 {
       
   239                 /**
       
   240                  * All previously active traffic streams have now been re-created,
       
   241                  * process the virtual traffic streams that need to be created next.
       
   242                  */                
       
   243                 (void)virtual_stream_iter_m.first();
       
   244 
       
   245                 return goto_state( core_state_recreate_virtual_next );
       
   246                 }
       
   247 
       
   248             tid_m = iter->tid();
       
   249             user_priority_m = iter->user_priority();
       
   250 
       
   251             DEBUG2( "core_sub_operation_roam_update_ts_c::next_state() - trying to recreate traffic stream (TID %u, user priority %u)",
       
   252                 tid_m, user_priority_m );
       
   253 
       
   254             params_m.is_periodic_traffic = iter->is_periodic_traffic();
       
   255             params_m.direction = iter->direction();
       
   256             params_m.nominal_msdu_size = iter->nominal_msdu_size();
       
   257             params_m.maximum_msdu_size = iter->maximum_msdu_size();
       
   258             params_m.minimum_service_interval = iter->minimum_service_interval();
       
   259             params_m.maximum_service_interval = iter->maximum_service_interval();
       
   260             params_m.inactivity_interval = iter->inactivity_interval();
       
   261             params_m.suspension_interval = iter->suspension_interval();
       
   262             params_m.service_start_time = iter->service_start_time();
       
   263             params_m.minimum_data_rate = iter->minimum_data_rate();
       
   264             params_m.mean_data_rate = iter->mean_data_rate();
       
   265             params_m.peak_data_rate = iter->peak_data_rate();
       
   266             params_m.maximum_burst_size = iter->maximum_burst_size();
       
   267             params_m.delay_bound = iter->delay_bound();
       
   268             params_m.minimum_phy_rate = iter->minimum_phy_rate();
       
   269             params_m.surplus_bandwidth_allowance = iter->surplus_bandwidth_allowance();
       
   270             params_m.medium_time = iter->medium_time();
       
   271             params_m.nominal_phy_rate = iter->nominal_phy_rate();
       
   272             params_m.override_rates = iter->override_rates();
       
   273             params_m.override_max_tx_msdu_lifetime = iter->max_tx_msdu_lifetime();
       
   274 
       
   275             core_operation_base_c* operation = new core_sub_operation_create_ts_c(
       
   276                 request_id_m,
       
   277                 server_m,
       
   278                 drivers_m,
       
   279                 adaptation_m,
       
   280                 current_ap_m,
       
   281                 tid_m,
       
   282                 user_priority_m,
       
   283                 params_m,
       
   284                 stream_status_m );
       
   285 
       
   286             return run_sub_operation( operation, core_state_recreate_success );
       
   287             }
       
   288         case core_state_recreate_success:
       
   289             {
       
   290             DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - traffic stream created successfully" );
       
   291 
       
   292             /**
       
   293              * Store the new traffic stream parameters.
       
   294              */
       
   295             core_traffic_stream_c* iter = stream_iter_m.current();
       
   296             iter->set_status( core_traffic_stream_status_active );
       
   297             iter->set_traffic_values( params_m );
       
   298             server_m->get_connection_data()->traffic_stream_list().update_traffic_stream( *iter );
       
   299 
       
   300             /**
       
   301              * Move to the next entry.
       
   302              */
       
   303             stream_iter_m.remove();
       
   304             (void)stream_iter_m.first();
       
   305 
       
   306             return goto_state( core_state_recreate_next );
       
   307             }
       
   308         case core_state_recreate_fail:
       
   309             {
       
   310             DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - traffic stream creation failed" );
       
   311 
       
   312             /**
       
   313              * Send a status update to all affected virtual traffic streams. 
       
   314              */
       
   315             set_virtual_traffic_stream_inactive_by_tid(
       
   316                 tid_m,
       
   317                 core_traffic_stream_status_inactive_other );
       
   318 
       
   319             /**
       
   320              * Delete the actual traffic stream.
       
   321              */
       
   322             server_m->get_wpx_adaptation_instance().handle_ts_delete(
       
   323                 tid_m, user_priority_m );
       
   324             server_m->get_connection_data()->traffic_stream_list().remove_traffic_stream_by_tid( tid_m );
       
   325 
       
   326             /**
       
   327              * Move to the next entry.
       
   328              */
       
   329             stream_iter_m.remove();
       
   330             (void)stream_iter_m.first();
       
   331 
       
   332             return goto_state( core_state_recreate_next );
       
   333             }
       
   334         case core_state_recreate_virtual_next:
       
   335             {
       
   336             core_virtual_traffic_stream_c* virtual_iter = virtual_stream_iter_m.current();
       
   337             if( !virtual_iter )
       
   338                 {
       
   339                 DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - traffic streams after processing:" );
       
   340                 server_m->get_connection_data()->virtual_traffic_stream_list().print_contents();
       
   341                 server_m->get_connection_data()->traffic_stream_list().print_contents();
       
   342                 (void)server_m->get_connection_data()->traffic_stream_list().first();
       
   343 
       
   344                 DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - setting TX queue parameters" );
       
   345                 return goto_state( core_state_set_params_next );
       
   346                 }
       
   347 
       
   348             tid_m = virtual_iter->requested_tid();
       
   349             user_priority_m = virtual_iter->user_priority();
       
   350             params_m = virtual_iter->params();
       
   351             stream_status_m = core_traffic_stream_status_inactive_other;
       
   352             if( tid_m != TRAFFIC_STREAM_TID_NONE )
       
   353                 {
       
   354                 /**
       
   355                  * If TID has been specified for the virtual traffic stream, check
       
   356                  * whether it clashes with an existing traffic stream.
       
   357                  */
       
   358                 if( server_m->get_connection_data()->traffic_stream_list().is_traffic_stream_for_tid( tid_m ) )
       
   359                     {
       
   360                     DEBUG1( "core_operation_create_ts_c::next_state() - stream already exists for TID %u",
       
   361                         tid_m );
       
   362                     
       
   363                     return goto_state( core_state_recreate_virtual_fail );
       
   364                     }
       
   365                 }
       
   366             else
       
   367                 {
       
   368                 /**
       
   369                  * If TID has been left unspecified, select the next free
       
   370                  * TID.
       
   371                  *
       
   372                  * First try to select the next free TID from virtual traffic
       
   373                  * stream list. In the unlikely scenario where all TIDs are
       
   374                  * in use, try the traffic stream list next.
       
   375                  */
       
   376                 tid_m = server_m->get_connection_data()->virtual_traffic_stream_list().next_tid();
       
   377                 if( tid_m == MAX_TRAFFIC_STREAM_TID )
       
   378                     {
       
   379                     tid_m = server_m->get_connection_data()->traffic_stream_list().next_tid();
       
   380                     if( tid_m == MAX_TRAFFIC_STREAM_TID )
       
   381                         {                    
       
   382                         DEBUG1( "core_operation_create_ts_c::next_state() - no free TIDs for stream ID %u",
       
   383                             virtual_iter->id() );
       
   384 
       
   385                         return goto_state( core_state_recreate_virtual_fail );
       
   386                         }
       
   387                     }
       
   388                 }
       
   389 
       
   390             /**
       
   391              * Traffic stream to be created. 
       
   392              */
       
   393             core_traffic_stream_c iter(
       
   394                 tid_m,
       
   395                 user_priority_m );
       
   396             iter.set_default_traffic_values( params_m );            
       
   397             iter.reset_to_default_values();
       
   398             stream_list_m.update_traffic_stream(
       
   399                 iter );
       
   400             (void)stream_iter_m.first();
       
   401             
       
   402             DEBUG2( "core_sub_operation_roam_update_ts_c::next_state() - trying to create traffic stream (TID %u, user priority %u)",
       
   403                 tid_m, user_priority_m );
       
   404 
       
   405             core_operation_base_c* operation = new core_sub_operation_create_ts_c(
       
   406                 request_id_m,
       
   407                 server_m,
       
   408                 drivers_m,
       
   409                 adaptation_m,
       
   410                 current_ap_m,
       
   411                 tid_m,
       
   412                 user_priority_m,
       
   413                 params_m,
       
   414                 stream_status_m );
       
   415 
       
   416             return run_sub_operation( operation, core_state_recreate_virtual_success );
       
   417             }
       
   418         case core_state_recreate_virtual_success:
       
   419             {
       
   420             DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - virtual traffic stream created successfully" );
       
   421 
       
   422             /**
       
   423              * Store the new traffic stream parameters.
       
   424              */
       
   425             core_virtual_traffic_stream_c* virtual_iter = virtual_stream_iter_m.current();            
       
   426             core_traffic_stream_c* iter = stream_iter_m.current();
       
   427             iter->set_status( core_traffic_stream_status_active );
       
   428             iter->set_traffic_values( params_m );
       
   429             server_m->get_connection_data()->traffic_stream_list().update_traffic_stream( *iter );
       
   430 
       
   431             /**
       
   432              * Send a status update to all affected virtual traffic streams. 
       
   433              */
       
   434             set_virtual_traffic_stream_active_by_id(
       
   435                 virtual_iter->id(),
       
   436                 tid_m );
       
   437 
       
   438             /**
       
   439              * Move to the next entry.
       
   440              */
       
   441             stream_iter_m.remove();
       
   442             virtual_stream_iter_m.remove();
       
   443             (void)virtual_stream_iter_m.first();
       
   444 
       
   445             return goto_state( core_state_recreate_virtual_next );
       
   446             }
       
   447         case core_state_recreate_virtual_fail:
       
   448             {
       
   449             DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - virtual traffic stream creation failed" );
       
   450 
       
   451             core_virtual_traffic_stream_c* iter = virtual_stream_iter_m.current();
       
   452 
       
   453             /**
       
   454              * Send a status update to all affected virtual traffic streams. 
       
   455              */
       
   456             set_virtual_traffic_stream_inactive_by_id(
       
   457                 iter->id(),
       
   458                 stream_status_m );
       
   459 
       
   460             /**
       
   461              * Move to the next entry.
       
   462              */
       
   463             stream_iter_m.remove();
       
   464             virtual_stream_iter_m.remove();
       
   465             (void)virtual_stream_iter_m.first();
       
   466 
       
   467             return goto_state( core_state_recreate_virtual_next );
       
   468             }
       
   469         case core_state_set_params_next:
       
   470             {
       
   471             operation_state_m = core_state_set_params_success;
       
   472 
       
   473             core_traffic_stream_c* iter = server_m->get_connection_data()->traffic_stream_list().current();
       
   474             if( !iter )
       
   475                 {
       
   476                 DEBUG( "core_sub_operation_roam_update_ts_c::next_state() - all TX queue parameters set" );
       
   477 
       
   478                 return core_error_ok;
       
   479                 }
       
   480 
       
   481             ASSERT( iter->status() == core_traffic_stream_status_active );
       
   482 
       
   483             if( iter->direction() == core_traffic_stream_direction_uplink ||
       
   484                 iter->direction() == core_traffic_stream_direction_bidirectional )
       
   485                 {
       
   486                 server_m->get_connection_data()->set_ac_traffic_status(
       
   487                     iter->access_class(),
       
   488                     core_access_class_traffic_status_admitted );
       
   489 
       
   490                 /**
       
   491                  * Send an indication to notify clients that this access class
       
   492                  * is now admitted. 
       
   493                  */
       
   494                 u8_t buf[5];
       
   495                 buf[0] = static_cast<u8_t>( 
       
   496                     iter->access_class() );
       
   497                 buf[1] = static_cast<u8_t>(
       
   498                     core_access_class_traffic_status_admitted );
       
   499                 adaptation_m->notify(
       
   500                     core_notification_ac_traffic_status_changed,
       
   501                     sizeof( buf ),
       
   502                     buf );
       
   503 
       
   504                 /**
       
   505                  * Set TX queue parameters to the drivers based on the created
       
   506                  * traffic stream.
       
   507                  */
       
   508                 DEBUG3( "core_sub_operation_roam_update_ts_c::next_state() - setting queue_id %u; medium_time %u, max_tx_msdu_lifetime %u",
       
   509                     iter->access_class(),
       
   510                     iter->medium_time(),
       
   511                     iter->max_tx_msdu_lifetime() );
       
   512 
       
   513                 drivers_m->set_tx_queue_parameters(
       
   514                     request_id_m,
       
   515                     iter->access_class(),
       
   516                     iter->medium_time(),
       
   517                     iter->max_tx_msdu_lifetime() );
       
   518                 }
       
   519             else
       
   520                 {
       
   521                 /**
       
   522                  * Since TX queue parameters apply only to uplink, there is nothing
       
   523                  * more to do on downlink streams. Move to the next entry.
       
   524                  */
       
   525                 (void)server_m->get_connection_data()->traffic_stream_list().next();
       
   526 
       
   527                 return goto_state( core_state_set_params_next );                
       
   528                 }
       
   529 
       
   530             break;
       
   531             }
       
   532         case core_state_set_params_success:
       
   533             {
       
   534             /**
       
   535              * Move to the next entry.
       
   536              */
       
   537             (void)server_m->get_connection_data()->traffic_stream_list().next();
       
   538 
       
   539             return goto_state( core_state_set_params_next );
       
   540             }            
       
   541         default:
       
   542             {
       
   543             ASSERT( false_t );
       
   544             }
       
   545         }
       
   546 
       
   547     return core_error_request_pending;
       
   548     }
       
   549 
       
   550 // ---------------------------------------------------------------------------
       
   551 // ---------------------------------------------------------------------------
       
   552 //
       
   553 core_error_e core_sub_operation_roam_update_ts_c::cancel()
       
   554     {
       
   555     DEBUG( "core_sub_operation_roam_update_ts_c::cancel()" );
       
   556     
       
   557     switch ( operation_state_m )
       
   558         {
       
   559         case core_state_recreate_success:
       
   560             {
       
   561             /**
       
   562              * Unable to create a traffic stream.
       
   563              */
       
   564             return goto_state( core_state_recreate_fail );
       
   565             }
       
   566         case core_state_recreate_virtual_success:
       
   567             {
       
   568             /**
       
   569              * Unable to create a virtual traffic stream.
       
   570              */
       
   571             return goto_state( core_state_recreate_virtual_fail );
       
   572             }            
       
   573         case core_state_set_params_success:
       
   574             {
       
   575             /**
       
   576              * Ignore errors when setting TX queue parameters.
       
   577              */            
       
   578             return goto_state( core_state_set_params_success );
       
   579             }
       
   580         default:
       
   581             {
       
   582             return failure_reason_m;
       
   583             }
       
   584         }
       
   585     }
       
   586 
       
   587 // ---------------------------------------------------------------------------
       
   588 // ---------------------------------------------------------------------------
       
   589 //
       
   590 void core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_inactive_by_tid(
       
   591     u8_t tid,
       
   592     core_traffic_stream_status_e stream_status )
       
   593     {
       
   594     DEBUG( "core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_inactive_by_tid()" );
       
   595     
       
   596     core_virtual_traffic_stream_list_c& virtual_ts_list(
       
   597         server_m->get_connection_data()->virtual_traffic_stream_list() );
       
   598     core_virtual_traffic_stream_list_iter_c virtual_ts_iter( virtual_ts_list );
       
   599 
       
   600     core_virtual_traffic_stream_c* virtual_iter = virtual_ts_iter.first();
       
   601     while( virtual_iter )
       
   602         {
       
   603         if( virtual_iter->tid() == tid )
       
   604             {
       
   605             u32_t id( virtual_iter->id() );
       
   606 
       
   607             /**
       
   608              * The virtual traffic stream is no longer mapped to any actual
       
   609              * traffic stream.
       
   610              */
       
   611             virtual_iter->set_tid(
       
   612                 TRAFFIC_STREAM_TID_NONE );
       
   613             virtual_iter->set_status(
       
   614                 stream_status );
       
   615 
       
   616             DEBUG1( "core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_inactive_by_tid() - virtual traffic stream with ID %u is inactive",
       
   617                 id );
       
   618 
       
   619             u8_t buf[5];                    
       
   620             core_tools_c::copy(
       
   621                 &buf[0],
       
   622                 reinterpret_cast<u8_t*>( &id ),
       
   623                 sizeof( u32_t ) );
       
   624             buf[4] = static_cast<u8_t>( stream_status );
       
   625 
       
   626             adaptation_m->notify(
       
   627                 core_notification_ts_status_changed,
       
   628                 sizeof( buf ),
       
   629                 buf );                    
       
   630             }
       
   631 
       
   632         virtual_iter = virtual_ts_iter.next();
       
   633         }
       
   634     }
       
   635 
       
   636 // ---------------------------------------------------------------------------
       
   637 // ---------------------------------------------------------------------------
       
   638 //
       
   639 void core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_inactive_by_id(
       
   640     u32_t id,
       
   641     core_traffic_stream_status_e stream_status )
       
   642     {
       
   643     DEBUG( "core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_inactive_by_id()" );
       
   644     
       
   645     core_virtual_traffic_stream_list_c& virtual_ts_list(
       
   646         server_m->get_connection_data()->virtual_traffic_stream_list() );
       
   647     core_virtual_traffic_stream_list_iter_c virtual_ts_iter( virtual_ts_list );
       
   648 
       
   649     core_virtual_traffic_stream_c* virtual_iter = virtual_ts_iter.first();
       
   650     while( virtual_iter )
       
   651         {
       
   652         if( virtual_iter->id() == id )
       
   653             {
       
   654             u32_t id( virtual_iter->id() );
       
   655 
       
   656             /**
       
   657              * The virtual traffic stream is no longer mapped to any actual
       
   658              * traffic stream.
       
   659              */
       
   660             virtual_iter->set_tid(
       
   661                 TRAFFIC_STREAM_TID_NONE );
       
   662             virtual_iter->set_status(
       
   663                 stream_status );
       
   664 
       
   665             DEBUG1( "core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_inactive_by_tid() - virtual traffic stream with ID %u is inactive",
       
   666                 id );
       
   667 
       
   668             u8_t buf[5];                    
       
   669             core_tools_c::copy(
       
   670                 &buf[0],
       
   671                 reinterpret_cast<u8_t*>( &id ),
       
   672                 sizeof( u32_t ) );
       
   673             buf[4] = static_cast<u8_t>( stream_status );
       
   674 
       
   675             adaptation_m->notify(
       
   676                 core_notification_ts_status_changed,
       
   677                 sizeof( buf ),
       
   678                 buf );                    
       
   679 
       
   680             return;
       
   681             }
       
   682 
       
   683         virtual_iter = virtual_ts_iter.next();
       
   684         }
       
   685     }
       
   686 
       
   687 // ---------------------------------------------------------------------------
       
   688 // ---------------------------------------------------------------------------
       
   689 //
       
   690 void core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_active_by_id(
       
   691     u32_t id,
       
   692     u8_t tid )
       
   693     {
       
   694     DEBUG( "core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_active_by_id()" );
       
   695     
       
   696     core_virtual_traffic_stream_list_c& virtual_ts_list(
       
   697         server_m->get_connection_data()->virtual_traffic_stream_list() );
       
   698     core_virtual_traffic_stream_list_iter_c virtual_ts_iter( virtual_ts_list );
       
   699 
       
   700     core_virtual_traffic_stream_c* virtual_iter = virtual_ts_iter.first();
       
   701     while( virtual_iter )
       
   702         {
       
   703         if( virtual_iter->id() == id )
       
   704             {
       
   705             u32_t id( virtual_iter->id() );
       
   706 
       
   707             /**
       
   708              * The virtual traffic stream is no longer mapped to any actual
       
   709              * traffic stream.
       
   710              */
       
   711             virtual_iter->set_tid(
       
   712                 tid );
       
   713             virtual_iter->set_status(
       
   714                 core_traffic_stream_status_active );
       
   715 
       
   716             DEBUG1( "core_sub_operation_roam_update_ts_c::set_virtual_traffic_stream_active_by_id() - virtual traffic stream with ID %u is active",
       
   717                 id );
       
   718 
       
   719             u8_t buf[5];                    
       
   720             core_tools_c::copy(
       
   721                 &buf[0],
       
   722                 reinterpret_cast<u8_t*>( &id ),
       
   723                 sizeof( u32_t ) );
       
   724             buf[4] = static_cast<u8_t>( core_traffic_stream_status_active );
       
   725 
       
   726             adaptation_m->notify(
       
   727                 core_notification_ts_status_changed,
       
   728                 sizeof( buf ),
       
   729                 buf ); 
       
   730 
       
   731             return;
       
   732             }
       
   733 
       
   734         virtual_iter = virtual_ts_iter.next();
       
   735         }
       
   736     }