--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/wlan_bearer/wlanengine/wlan_common/wlanengine_common_3.1/src/core_sub_operation_create_ts.cpp Tue Feb 02 02:03:13 2010 +0200
@@ -0,0 +1,319 @@
+/*
+* Copyright (c) 2005-2009 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of the License "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: Statemachine for creating a traffic stream.
+*
+*/
+
+/*
+* %version: 12 %
+*/
+
+#include "core_sub_operation_create_ts.h"
+#include "core_server.h"
+#include "core_frame_wmm_ie.h"
+#include "core_frame_wmm_ie_tspec.h"
+#include "core_frame_action_wmm.h"
+#include "core_tools.h"
+#include "core_tools_parser.h"
+#include "am_debug.h"
+
+const u32_t CORE_AP_RESP_WAITING_TIME = 1000000;
+
+// ======== MEMBER FUNCTIONS ========
+
+// ---------------------------------------------------------------------------
+// ---------------------------------------------------------------------------
+//
+core_sub_operation_create_ts_c::core_sub_operation_create_ts_c(
+ u32_t request_id,
+ core_server_c* server,
+ abs_core_driverif_c* drivers,
+ abs_core_server_callback_c* adaptation,
+ const core_ap_data_c& ap_data,
+ u8_t tid,
+ u8_t user_priority,
+ core_traffic_stream_params_s& tspec,
+ core_traffic_stream_status_e& stream_status ) :
+ core_operation_base_c( core_operation_unspecified, request_id, server, drivers, adaptation,
+ core_base_flag_none ),
+ current_ap_m( ap_data ),
+ tid_m( tid ),
+ user_priority_m( user_priority ),
+ tspec_m( tspec ),
+ stream_status_m( stream_status )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::core_sub_operation_create_ts_c()" );
+
+ stream_status_m = core_traffic_stream_status_inactive_other;
+ }
+
+// ---------------------------------------------------------------------------
+// ---------------------------------------------------------------------------
+//
+core_sub_operation_create_ts_c::~core_sub_operation_create_ts_c()
+ {
+ DEBUG( "core_sub_operation_create_ts_c::~core_sub_operation_create_ts_c()" );
+
+ server_m->unregister_frame_handler( this );
+ }
+
+// ---------------------------------------------------------------------------
+// ---------------------------------------------------------------------------
+//
+core_error_e core_sub_operation_create_ts_c::next_state()
+ {
+ DEBUG( "core_sub_operation_create_ts_c::next_state()" );
+
+ switch ( operation_state_m )
+ {
+ case core_state_init:
+ {
+ bool_t is_uapsd( true_t );
+ if ( !current_ap_m.is_uapsd_supported() ||
+ !server_m->get_core_settings().is_uapsd_enable_for_access_class(
+ core_tools_c::convert_user_priority_to_ac( user_priority_m ) ) )
+ {
+ is_uapsd = false_t;
+ }
+ DEBUG1( "core_sub_operation_create_ts_c::next_state() - U-APSD %u", is_uapsd );
+
+ core_frame_wmm_ie_tspec_c* tspec_ie = core_frame_wmm_ie_tspec_c::instance(
+ tid_m,
+ user_priority_m,
+ is_uapsd,
+ tspec_m.is_periodic_traffic,
+ tspec_m.direction,
+ tspec_m.nominal_msdu_size,
+ tspec_m.maximum_msdu_size,
+ tspec_m.minimum_service_interval,
+ tspec_m.maximum_service_interval,
+ tspec_m.inactivity_interval,
+ tspec_m.suspension_interval,
+ tspec_m.service_start_time,
+ tspec_m.minimum_data_rate,
+ tspec_m.mean_data_rate,
+ tspec_m.peak_data_rate,
+ tspec_m.maximum_burst_size,
+ tspec_m.delay_bound,
+ tspec_m.minimum_phy_rate,
+ tspec_m.surplus_bandwidth_allowance,
+ tspec_m.medium_time );
+ if ( !tspec_ie )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - unable to allocate a WMM TSPEC IE" );
+ return core_error_no_memory;
+ }
+
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - TSPEC IE:" );
+ DEBUG_BUFFER( tspec_ie->data_length(), tspec_ie->data() );
+
+ const core_mac_address_s dest(
+ current_ap_m.bssid() );
+ const core_mac_address_s src(
+ server_m->own_mac_addr() );
+
+ core_frame_action_wmm_c* frame = core_frame_action_wmm_c::instance(
+ 0, // Duration
+ dest, // Destination
+ src, // Source
+ dest, // BSSID
+ 0, // Sequence Control
+ core_frame_action_wmm_c::core_dot11_action_wmm_type_addts_req, // Action Type
+ 255, // Dialog Token
+ core_frame_action_wmm_c::core_dot11_action_wmm_status_admission_accepted, // Status
+ tspec_ie );
+
+ delete tspec_ie;
+ tspec_ie = NULL;
+
+ if ( !frame )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - unable to allocate an action frame" );
+ return core_error_no_memory;
+ }
+
+ /**
+ * Handle the WPX-specific features in traffic stream creation.
+ */
+ server_m->get_wpx_adaptation_instance().handle_ts_create_request(
+ current_ap_m,
+ frame,
+ tid_m,
+ tspec_m );
+
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - ADDTS REQ:" );
+ DEBUG_BUFFER( frame->data_length(), frame->data() );
+
+ operation_state_m = core_state_request_sent;
+
+ server_m->register_frame_handler( this );
+
+ server_m->send_management_frame(
+ core_frame_type_dot11,
+ frame->data_length(),
+ frame->data(),
+ dest );
+
+ delete frame;
+ frame = NULL;
+
+ /**
+ * Schedule a timeout if no response is received.
+ */
+ server_m->schedule_operation_timer(
+ CORE_AP_RESP_WAITING_TIME );
+
+ break;
+ }
+ case core_state_request_sent:
+ {
+ server_m->unregister_frame_handler( this );
+
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - timer has expired, no response from AP received" );
+
+ return core_error_general;
+ }
+ case core_state_invalid_parameters:
+ {
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - AP has downgraded our parameters, retrying" );
+
+ return goto_state( core_state_init );
+ }
+ case core_state_failure:
+ {
+ server_m->unregister_frame_handler( this );
+
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - AP has rejected our traffic stream request" );
+
+ return core_error_general;
+ }
+ case core_state_success:
+ {
+ server_m->unregister_frame_handler( this );
+
+ DEBUG( "core_sub_operation_create_ts_c::next_state() - traffic stream created successfully" );
+
+ DEBUG_RATES( "core_sub_operation_create_ts_c::next_state() - nominal PHY rate: ",
+ tspec_m.nominal_phy_rate );
+ DEBUG_RATES( "core_sub_operation_create_ts_c::next_state() - override tx rates: ",
+ tspec_m.override_rates );
+
+ return core_error_ok;
+ }
+ default:
+ {
+ ASSERT( false_t );
+ }
+ }
+
+ return core_error_request_pending;
+ }
+
+// ---------------------------------------------------------------------------
+// ---------------------------------------------------------------------------
+//
+bool_t core_sub_operation_create_ts_c::receive_frame(
+ const core_frame_dot11_c* frame,
+ u8_t /* rcpi */ )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::receive_frame()" );
+
+ if ( frame->type() != core_frame_dot11_c::core_dot11_type_action )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::receive_frame() - not an action frame" );
+ return false_t;
+ }
+
+ core_frame_action_c* action = core_frame_action_c::instance(
+ *frame );
+ if ( action )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::receive_frame() - 802.11 action frame found" );
+ DEBUG1( "core_sub_operation_create_ts_c::receive_frame() - 802.11 action category: 0x%02X",
+ action->category() );
+ if ( action->category() == core_frame_action_c::core_dot11_action_category_wmm_qos )
+ {
+ core_frame_action_wmm_c* wmm_action = core_frame_action_wmm_c::instance( *action );
+ if ( wmm_action )
+ {
+ DEBUG( "core_sub_operation_create_ts_c::receive_frame() - 802.11 WMM action frame found" );
+ DEBUG1( "core_sub_operation_create_ts_c::receive_frame() - 802.11 WMM action type: 0x%02X",
+ wmm_action->action_type() );
+ DEBUG1( "core_sub_operation_create_ts_c::receive_frame() - 802.11 WMM action dialog token: 0x%02X",
+ wmm_action->dialog_token() );
+ DEBUG1( "core_sub_operation_create_ts_c::receive_frame() - 802.11 WMM action status: 0x%02X",
+ wmm_action->status() );
+
+ /**
+ * Get traffic stream parameters from the response.
+ */
+ bool_t ret = core_tools_parser_c::get_wmm_traffic_stream_params(
+ *wmm_action,
+ tid_m,
+ tspec_m );
+ if ( !ret )
+ {
+ DEBUG1( "core_sub_operation_create_ts_c::receive_frame() - TSPEC with TID %u not found, ignoring frame",
+ tid_m );
+
+ delete wmm_action;
+ wmm_action = NULL;
+
+ delete action;
+ action = NULL;
+
+ return true_t;
+ }
+
+ server_m->get_wpx_adaptation_instance().get_wpx_traffic_stream_params(
+ wmm_action,
+ tid_m,
+ tspec_m );
+
+ server_m->cancel_operation_timer();
+
+ if ( wmm_action->status() == core_frame_action_wmm_c::core_dot11_action_wmm_status_admission_accepted )
+ {
+ stream_status_m = core_traffic_stream_status_active;
+
+ server_m->get_wpx_adaptation_instance().handle_ts_create_success(
+ wmm_action,
+ tid_m,
+ user_priority_m );
+
+ asynch_goto( core_state_success, CORE_TIMER_IMMEDIATELY );
+ }
+ else if ( wmm_action->status() == core_frame_action_wmm_c::core_dot11_action_wmm_status_invalid_parameters )
+ {
+ asynch_goto( core_state_invalid_parameters, CORE_TIMER_IMMEDIATELY );
+ }
+ else
+ {
+ stream_status_m = server_m->get_wpx_adaptation_instance().get_wpx_traffic_stream_status(
+ wmm_action->status() );
+
+ asynch_goto( core_state_failure, CORE_TIMER_IMMEDIATELY );
+ }
+
+ delete wmm_action;
+ }
+ }
+
+ delete action;
+ action = NULL;
+ }
+
+ return true_t;
+ }
+