# HG changeset patch # User Pat Downey # Date 1283339708 -3600 # Node ID 1aa8c82cb4cbf257fdd60d4dbfe9a5991049eaca # Parent 88ee4cf65e199e8183220b34977d7875fdafd7cf Revert incorrect RCL_3 drop: Revision: 201021 Kit: 201035 diff -r 88ee4cf65e19 -r 1aa8c82cb4cb group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,24 @@ +/* +* Copyright (c) 2008-2008 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: This file provides the information required for building the whole project +* +*/ + + + +#include "../rsfw_plat/rsfw_access_protocol_plugin_api/group/bld.inf" +#include "../remotestoragefw/group/bld.inf" + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb layers.sysdef.xml --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/layers.sysdef.xml Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,14 @@ + + +]> + + + + + + + + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/MDebug/inc/mdebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/MDebug/inc/mdebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,93 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug printing to a log file + * +*/ + + +#ifndef MDEBUG_H +#define MDEBUG_H + +// INCLUDES +#include + +#include "mydebug.h" + +// Take care that the correct mydebug.h will be included +// In mydebug.h in your module inc directory, +// define your application-specific configuration like this: +// ---------------------------------------------------------- +// Debug file - debug output is disabled if the parent dir does not exist +// _LIT(KDebugFileName, "C:\\logs\\remotefileengine\\remotefileengine.txt"); + +// Replace the current debug file - if not defined appends to the file +#ifndef APPEND_TO_DEBUG_FILE +#define REPLACE_DEBUG_FILE +#endif + +// Maximum formatted size resulting from a single DEBUG* call +#ifndef MAX_DEBUG_STRING_LENGTH +#define MAX_DEBUG_STRING_LENGTH 4096 +#endif +// ---------------------------------------------------------- + +// FUNCTION PROTOTYPES +void DebugInit(TBool aDebugSuspended = EFalse); +void SetDebugEnabled(TBool aValue); +void SetDebugSuspended(TBool aValue); +void DebugStringNarrowL(const char* aFmt, ...); +void DebugStringWideL(const char* aFmt, ...); +void DebugBufferL(const TDesC8& aBuf); +void DebugBufferL(const TDesC& aBuf); +void DebugTimeL(const TTime& aTime); + +// MACROS +// If you output one or more narrow descriptors by using '%S', +// use DEBUGSTRING8 +// else if you output one or more unicode descriptors by using '%S', +// use DEBUGSTRING16 +// else +// use DEBUGSTRING +// +// Narrow and unicode cannot be mixed in a single DEBUGSTRINGx call. + +#ifdef _DEBUG +#define DEBUGINIT() DebugInit() +#define DEBUGINITSUSPENDED() DebugInit(ETrue) +#define DEBUGENABLE() SetDebugEnabled(ETrue) +#define DEBUGDISABLE() SetDebugEnabled(EFalse) +#define DEBUGSUSPEND() SetDebugSuspended(ETrue) +#define DEBUGCONTINUE() SetDebugSuspended(EFalse) +#define DEBUGSTRING(x) DebugStringNarrowL x +#define DEBUGSTRING8(x) DebugStringNarrowL x +#define DEBUGSTRING16(x) DebugStringWideL x +#define DEBUGBUFFER(x) DebugBufferL x +#define DEBUGTIME(x) DebugTimeL x +#else +#define DEBUGINIT() +#define DEBUGINITSUSPENDED() +#define DEBUGENABLE() +#define DEBUGDISABLE() +#define DEBUGSUSPEND() +#define DEBUGCONTINUE() +#define DEBUGSTRING(x) +#define DEBUGSTRING8(x) +#define DEBUGSTRING16(x) +#define DEBUGBUFFER(x) +#define DEBUGTIME(x) +#endif + +#endif // MDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/MDebug/src/mdebug.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/MDebug/src/mdebug.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,90 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug printing to a log file + * +*/ + + +// INCLUDES +#include + +#include "mdebug.h" + +// FORWARD DECLARATIONS +void DoOutput(TDesC8& aData); + +void DebugStringNarrowL(const char* aFmt, ...) + { + VA_LIST args; + VA_START(args, aFmt); + + TPtrC8 fmt(reinterpret_cast(aFmt)); + HBufC8* buf = HBufC8::NewLC(MAX_DEBUG_STRING_LENGTH); + buf->Des().FormatList(fmt, args); + buf->Des().Append('\n'); + DoOutput(*buf); + CleanupStack::PopAndDestroy(); // buf + + VA_END(args); + } + +void DebugStringWideL(const char* aFmt, ...) + { + VA_LIST args; + VA_START(args, aFmt); + + TPtrC8 fmt(reinterpret_cast(aFmt)); + HBufC* fmt16 = HBufC::NewLC(fmt.Length()); + fmt16->Des().Copy(fmt); + HBufC* buf = HBufC::NewLC(MAX_DEBUG_STRING_LENGTH); + buf->Des().FormatList(*fmt16, args); + buf->Des().Append('\n'); + HBufC8* buf8 = HBufC8::NewLC(buf->Length()); + buf8->Des().Copy(*buf); + DoOutput(*buf8); + CleanupStack::PopAndDestroy(3); // fmt16, buf, buf8 + + VA_END(args); + } + +void DebugBufferL(const TDesC8& aBuf) + { + DebugStringNarrowL("\"%S\"", &aBuf); + } + +void DebugBufferL(const TDesC& aBuf) + { + DebugStringWideL("\"%S\"", &aBuf); + } + +void DebugTimeL(const TTime& aTime) + { + TBuf<64> dateTimeString; + _LIT(KDateString, "%E%D%X%N%Y %1 %2 %3"); + aTime.FormatL(dateTimeString, KDateString); + DebugBufferL(dateTimeString); + _LIT(KTimeString, "%-B%:0%J%:1%T%:2%S%.%*C4%:3%+B"); + aTime.FormatL(dateTimeString, KTimeString); + DebugBufferL(dateTimeString); + } + +void DoOutput(TDesC8& aData) + { + RFileLogger::Write(KDebugDirName, + KDebugFileName, + EFileLoggingModeAppend, + aData); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/cenrep/backup_registration.xml --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/cenrep/backup_registration.xml Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,5 @@ + + + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/cenrep/keys_remote_storage_fw.xls Binary file remotestoragefw/cenrep/keys_remote_storage_fw.xls has changed diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/conf/remote_storage_fw.confml Binary file remotestoragefw/conf/remote_storage_fw.confml has changed diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/conf/remote_storage_fw_101F9775.crml Binary file remotestoragefw/conf/remote_storage_fw_101F9775.crml has changed diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,45 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build info for RSFW +* +*/ + + +#include + +PRJ_PLATFORMS +DEFAULT + +PRJ_MMPFILES +#include "../mountstore/group/bld.inf" +#include "../rsfwnotifierplugins/group/bld.inf" +#include "../remotefileengine/group/bld.inf" // rsfwcontrol.dll comes from here, and should be always included +#include "../mountmanager/group/bld.inf" +#include "../webdavaccessplugin/group/bld.inf" +#include "../remotefilesystemplugin/group/bld.inf" +#ifdef __REMOTE_STORAGE_FW +#include "../gsplugin/group/bld.inf" +#include "../remotedriveconfigurationbiocontrol/group/bld.inf" +#endif + +PRJ_EXPORTS +// .iby files (only for 5.0) +../rom/rsfw.iby CORE_MW_LAYER_IBY_EXPORT_PATH(rsfw.iby) +../rom/rsfw_resources.iby LANGUAGE_MW_LAYER_IBY_EXPORT_PATH(rsfw_resources.iby) + +// conf files +../conf/remote_storage_fw.confml APP_LAYER_CONFML(remote_storage_fw.confml) +../conf/remote_storage_fw_101F9775.crml APP_LAYER_CRML(remote_storage_fw_101F9775.crml) + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/data/101f9777.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/data/101f9777.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,45 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: +* ECOM plugin resource file for RSFW GS plugin. +* +* +*/ + +#include + + +RESOURCE REGISTRY_INFO theInfo + { + dll_uid = 0x101F9777; + interfaces = + { + INTERFACE_INFO + { + interface_uid = 0x10207236; // UID for CGSPluginInterface - do not change. + implementations = + { + IMPLEMENTATION_INFO + { + implementation_uid = 0x101F9778; + version_no = 1; + display_name = "RSFW GS plugin"; + default_data = "0x10207250"; // Parent UID connection settings + opaque_data = "90"; // Order number + } + }; + } + }; + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/data/rsfwgspluginrsc.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/data/rsfwgspluginrsc.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,580 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Resource file for RSFW GS plugin +* +*/ + + +// RESOURCE IDENTIFIER +NAME RSFW // 4 letter ID + +// INCLUDES +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "rsfwgsplugin.hrh" +#include +#include +#include + +// RESOURCE DEFINITIONS + +RESOURCE RSS_SIGNATURE + { + } + +//------------------------------------------------------------------------------ +// +// EIK_APP_INFO +// It contains application information. +// +//------------------------------------------------------------------------------ +// +RESOURCE EIK_APP_INFO + { + } + + +// **COMMON RESOURCES + +//------------------------------------------------------------------------------ +// +// r_gs_menubar_open_exit +// Options menu with 'Open' and 'Exit' items. +// +//------------------------------------------------------------------------------ +// +RESOURCE MENU_BAR r_gs_menubar_open_exit + { + titles = + { + MENU_TITLE + { + menu_pane = r_gs_menu_item_exit; + }, + MENU_TITLE + { + menu_pane = r_gs_menu_item_open; + } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_menubar_change_exit +// Options menu with 'Change' and 'Exit' items. +// +//------------------------------------------------------------------------------ +// +RESOURCE MENU_BAR r_gs_menubar_change_exit + { + titles = + { + MENU_TITLE + { + menu_pane = r_gs_menu_item_exit; + }, + MENU_TITLE + { + menu_pane = r_gs_menu_item_change; + } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_menu_item_open +// Options menu item 'Open'. +// +//------------------------------------------------------------------------------ +// +RESOURCE MENU_PANE r_gs_menu_item_open + { + items = + { + MENU_ITEM + { + command = EGSCmdAppOpen; + txt = qtn_set_options_open; + } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_menu_item_change +// Options menu item 'Change'. +// +//------------------------------------------------------------------------------ +// +RESOURCE MENU_PANE r_gs_menu_item_change + { + items = + { + MENU_ITEM + { + command = EGSCmdAppChange; + txt = qtn_set_options_change; + } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_menu_item_exit +// Options menu items 'Help' and 'Exit'. +// Used instead of plain 'Exit' when help is wanted +// to be shown in UI. +// +//------------------------------------------------------------------------------ +// +RESOURCE MENU_PANE r_gs_menu_item_exit + { + items = + { + MENU_ITEM + { + command = EAknCmdHelp; + txt = qtn_options_help; + }, + MENU_ITEM + { + command = EAknCmdExit; + txt = qtn_options_exit; + } + }; + } + + +// RSFW SETTINGS + +//---------------------------------------------------- +// r_gs_remote_drives_view_caption +// +// remote drives view caption +//---------------------------------------------------- +// +RESOURCE TBUF r_gs_remote_drives_view_caption + { + buf = qtn_set_folder_conn_remote_drives; + } + + +//------------------------------------------------------------------------------ +// +// r_gs_menubar_remote_drives_view +// Menubar for Remote drive list view. +//------------------------------------------------------------------------------ +// +RESOURCE MENU_BAR r_gs_menubar_remote_drives_view + { + titles = + { + MENU_TITLE + { + menu_pane = r_gs_menu_item_exit; + }, + MENU_TITLE + { + menu_pane = r_gs_remote_drives_menu; + } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_remote_drives_menu +// Menu items in Profiles menu. +//------------------------------------------------------------------------------ +// +RESOURCE MENU_PANE r_gs_remote_drives_menu + { + items= + { + MENU_ITEM + { + command = EGSCmdAppChange; + txt = qtn_options_change; + flags = EEikMenuItemAction; + }, + MENU_ITEM + { + command = EGSCmdAppEdit; + txt = qtn_rd_opt_edit; + flags = EEikMenuItemSpecific; + }, + MENU_ITEM + { + command = EGSCmdAppNew; + txt = qtn_rd_opt_new_drive; + }, + MENU_ITEM + { + command = EGSCmdAppConnect; + txt = qtn_rd_opt_connect; + flags = EEikMenuItemSpecific; + }, + MENU_ITEM + { + command = EGSCmdAppDisconnect; + txt = qtn_rd_opt_disconnect; + flags = EEikMenuItemSpecific; + }, + MENU_ITEM + { + command = EGSCmdAppSendLink; + txt = qtn_rd_opt_send_link; + flags = EEikMenuItemSpecific; + }, + MENU_ITEM + { + command = EGSCmdAppDelete; + txt = qtn_rd_opt_delete; + flags = EEikMenuItemSpecific; + } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_rsfw_main_view +// RSFW plugin main view. +// +//------------------------------------------------------------------------------ +// +RESOURCE AVKON_VIEW r_gs_rsfw_main_view + { + menubar = r_gs_menubar_remote_drives_view; + cba = r_rsfw_softkeys_options_back_edit; + } + + +//------------------------------------------------------------------------------ +// +// r_gs_rsfw_no_remote_drives +// Remote Drives view's listbox empty text. +// +//------------------------------------------------------------------------------ +// +RESOURCE TBUF r_gs_rsfw_no_remote_drives + { + buf = qtn_rd_empty_list_primary; + } + + +//------------------------------------------------------------------------------ +// +// r_gs_rsfw_no_remote_drives +// Remote Drives view's listbox empty text. +// +//------------------------------------------------------------------------------ +// +RESOURCE TBUF r_gs_rsfw_no_remote_drives_explanatory + { + buf = qtn_rd_empty_list_secondary; + } + + +//------------------------------------------------------------------------------ +// +// r_gs_rsfw_remote_drive_settings_view +// Remote drive settings view. +// +//------------------------------------------------------------------------------ +// +RESOURCE AVKON_VIEW r_gs_rsfw_remote_drive_settings_view + { + menubar = r_gs_menubar_change_exit; + cba = r_rsfw_softkeys_options_back_change; + } + + +RESOURCE CBA r_rsfw_softkeys_options_back_edit + { + buttons = + { + CBA_BUTTON { id = EAknSoftkeyOptions; txt = text_softkey_option; }, + CBA_BUTTON { id = EAknSoftkeyBack; txt = text_softkey_back; }, + CBA_BUTTON { id = EGSCmdAppEdit; txt = qtn_msk_edit; } + }; + } + +RESOURCE CBA r_rsfw_softkeys_options_back_change + { + buttons = + { + CBA_BUTTON { id = EAknSoftkeyOptions; txt = text_softkey_option; }, + CBA_BUTTON { id = EAknSoftkeyBack; txt = text_softkey_back; }, + CBA_BUTTON { id = EGSCmdAppChange; txt = qtn_msk_change; } + }; + } + +RESOURCE CBA r_rsfw_softkeys_options_back_empty + { + buttons = + { + CBA_BUTTON { id = EAknSoftkeyOptions; txt = text_softkey_option; }, + CBA_BUTTON { id = EAknSoftkeyBack; txt = text_softkey_back; }, + CBA_BUTTON { id = EAknSoftkeyEmpty; txt = text_softkey_empty; } + }; + } + +//------------------------------------------------------------------------------ +// +// r_gs_rsfw_remote_drive_settings_view_title +// Remote drives setting view's default title. +// +//------------------------------------------------------------------------------ +// +RESOURCE TITLE_PANE r_gs_rsfw_remote_drive_settings_view_title + { + txt = qtn_rd_title_drives; + } + +// --------------------------------------------------------- +// +// r_settings +// +// settings list - collection of all setting types +// +// --------------------------------------------------------- +RESOURCE AVKON_SETTING_ITEM_LIST r_settings + { + flags = EAknSettingItemIncludeHiddenInOrdinal; + title = qtn_rd_title_new_drive; + items = + { + AVKON_SETTING_ITEM + { + identifier = ESettingItemDriveName; + setting_page_resource = r_server_name_editor_page; + name = qtn_rd_setting_drive_name; + empty_item_text = qtn_rd_default_drive_name; + compulsory_ind_string = "*"; + }, + AVKON_SETTING_ITEM + { + identifier = ESettingItemURL; + setting_page_resource = r_url_editor_page; + name = qtn_rd_setting_url; + compulsory_ind_string = "*"; + }, + AVKON_SETTING_ITEM + { + identifier = ESettingItemAccessPoint; + setting_page_resource = r_accesspoint_editor_page; + name = qtn_rd_setting_ap; + empty_item_text = qtn_netw_conset_sett_always_ask; + }, + AVKON_SETTING_ITEM + { + identifier = ESettingItemUserID; + setting_page_resource = r_user_id_editor_page; + name = qtn_rd_setting_user; + }, + AVKON_SETTING_ITEM + { + identifier = ESettingItemPassword; + setting_page_resource = r_password_editor_page; + name = qtn_rd_setting_pw; + } + }; + } + +// --------------------------------------------------------- +// +// Settings Pages +// +// defines the AVKON_SETTING_PAGE structures referred to in +// setting_page_resource fields above. +// +// These structures define the way in which the editors used +// to change the setting data are presented. +// +// --------------------------------------------------------- +// +RESOURCE AVKON_SETTING_PAGE r_server_name_editor_page + { + label= qtn_rd_setting_drive_name; + type = EEikCtEdwin; + softkey_resource = R_AVKON_SOFTKEYS_OK_CANCEL__OK; + editor_resource_id = r_server_name_editor; + } + +RESOURCE AVKON_SETTING_PAGE r_url_editor_page + { + label= qtn_rd_setting_url; + type = EEikCtEdwin; + softkey_resource = R_AVKON_SOFTKEYS_OK_CANCEL__OK; + editor_resource_id = r_url_editor; + } + +RESOURCE AVKON_SETTING_PAGE r_accesspoint_editor_page + { + label= qtn_rd_setting_ap; + type = EEikCtEdwin; + softkey_resource = R_AVKON_SOFTKEYS_OK_CANCEL__OK; + editor_resource_id = r_accesspoint_editor; + } + +RESOURCE AVKON_SETTING_PAGE r_user_id_editor_page + { + label= qtn_rd_setting_user; + type = EEikCtEdwin; + softkey_resource = R_AVKON_SOFTKEYS_OK_CANCEL__OK; + editor_resource_id = r_user_id_editor; + } + +RESOURCE AVKON_SETTING_PAGE r_password_editor_page + { + label= qtn_rd_setting_pw; + type = EEikCtSecretEd; + softkey_resource = R_AVKON_SOFTKEYS_OK_CANCEL__OK; + editor_resource_id = r_password_editor; + } + +RESOURCE EDWIN r_user_id_editor + { + flags = EEikEdwinAutoSelection | EAknEditorLowerCase | EEikEdwinNoLineOrParaBreaks; + allowed_case_modes = EAknEditorLowerCase | EAknEditorUpperCase; + numeric_keymap=EAknEditorCalculatorNumberModeKeymap; + allowed_input_modes = EAknEditorTextInputMode | EAknEditorNumericInputMode; + default_input_mode = EAknEditorTextInputMode; + special_character_table = R_AVKON_URL_SPECIAL_CHARACTER_TABLE_DIALOG; + default_case = EAknEditorLowerCase; + avkon_flags = EAknEditorFlagLatinInputModesOnly; + width = 0; + lines = 0; + maxlength = KMaxUserIDLength; + } + +RESOURCE SECRETED r_password_editor + { + num_letters = KMaxPasswordLength; + } + +RESOURCE EDWIN r_server_address_editor + { + maxlength = KMaxServerAddressLength; + } + +RESOURCE EDWIN r_accesspoint_editor + { + maxlength = KMaxAccessPointNameLength; + } + +RESOURCE EDWIN r_server_name_editor + { + width = 0; + lines = 0; + flags = EEikEdwinNoLineOrParaBreaks; + maxlength = KMaxFriendlyNameLength; + } + +RESOURCE EDWIN r_url_editor + { + maxlength = KMaxURLLength; + numeric_keymap = EAknEditorCalculatorNumberModeKeymap; + allowed_input_modes = EAknEditorTextInputMode | EAknEditorNumericInputMode; + default_input_mode = EAknEditorTextInputMode; + special_character_table = R_AVKON_URL_SPECIAL_CHARACTER_TABLE_DIALOG; + allowed_case_modes = EAknEditorLowerCase | EAknEditorUpperCase; + default_case = EAknEditorLowerCase; + flags = EEikEdwinAutoSelection | EAknEditorLowerCase | EEikEdwinNoLineOrParaBreaks; + avkon_flags = EAknEditorFlagLatinInputModesOnly; + width = 0; + lines = 0; + } + +RESOURCE DIALOG r_confirmation_query + { + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_YES_NO; + items= + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout =EConfirmationQueryLayout; + }; + } + }; + } +RESOURCE DIALOG r_rsfw_information_note + { + flags = EAknInformationNoteFlags; + buttons = R_AVKON_SOFTKEYS_OK_EMPTY; + items = + { + DLG_LINE + { + type = EAknCtNote; + id = EGeneralNote; + control = AVKON_NOTE + { + // localised string for default text, see Notes UI spec. + layout = EGeneralLayout; + animation = R_QGN_NOTE_INFO_ANIM; + }; + } + }; + } + + +RESOURCE DIALOG r_drive_unavailable_query + { + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_OK_CANCEL; + items= + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout =EConfirmationQueryLayout; + }; + } + }; + } + +//---------------------------------------------------- +// +// string resouces +// the strings can be localized in loc file +// +//---------------------------------------------------- +// +RESOURCE TBUF r_str_remote_drive_new_name { buf = qtn_rd_title_new_drive; } +RESOURCE TBUF r_str_rsfw_conf_delete { buf = qtn_rd_query_delete_drive; } +RESOURCE TBUF r_str_remote_drive_conf_compulsory { buf = qtn_rd_query_incomplete; } +RESOURCE TBUF r_str_remote_drives_view_title { buf = qtn_rd_title_drives; } +RESOURCE TBUF r_str_remote_drive_name_already_exist { buf = qtn_rd_error_existing_name; } +RESOURCE TBUF r_str_rsfw_error_max_drives { buf = qtn_rd_error_max_drives; } +RESOURCE TBUF r_str_rsfw_error_edit_connected { buf = qtn_rd_error_edit_connected; } +RESOURCE TBUF r_str_rsfw_error_illegal_characters { buf = qtn_fldr_illegal_characters; } +RESOURCE TBUF r_str_rsfw_error_illegal_address { buf = qtn_rd_infonote_missing_http_prefix; } +RESOURCE TBUF r_str_rsfw_send_credentials_query { buf = qtn_rd_conf_query_send_auth_info; } + +//End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,35 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build information file for project GS Plugin +* +*/ + +#include + +PRJ_EXPORTS +../inc/rsfwgsplugin.hrh |../../inc/rsfwgsplugin.hrh +// export localised loc file +../loc/rsfwgsplugin.loc MW_LAYER_LOC_EXPORT_PATH(rsfwgsplugin.loc) + +PRJ_MMPFILES + +rsfwgsplugin.mmp + +PRJ_EXTENSIONS +START EXTENSION s60/mifconv + OPTION TARGETFILE rsfwgsplugin.mif + OPTION HEADERFILE rsfwgsplugin.mbg + OPTION SOURCES -c8,8 qgn_prop_set_conn_remotedrive \ + -c8,8 qgn_indi_connection_on_add +END \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/group/rsfwgsplugin.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/group/rsfwgsplugin.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,96 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project GS plugin +* +*/ + +#include +#include //this is needed for RESOURCE_FILES_DIR + +CAPABILITY CAP_ECOM_PLUGIN +TARGET rsfwgsplugin.dll +TARGETTYPE PLUGIN +UID 0x10009D8D 0x101F9777 +VENDORID VID_DEFAULT + +SOURCEPATH ../src +SOURCE rsfwgsplugin.cpp +SOURCE rsfwgsplugindrivelistcontainer.cpp +SOURCE rsfwgsremotedrivesettingscontainer.cpp +SOURCE rsfwgspluginsettinglist.cpp +SOURCE rsfwgssettingsdata.cpp +SOURCE rsfwgspluginimplementationtable.cpp +SOURCE rsfwgspropertywatch.cpp +SOURCE rsfwgsremotedrivesend.cpp +SOURCEPATH ../../MDebug/src +SOURCE mdebug.cpp + +APP_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +SYSTEMINCLUDE /epoc32/include/ecom +USERINCLUDE ../inc + +SOURCEPATH ../data + +//ECOM resource definition +START RESOURCE 101f9777.rss +TARGET rsfwgsplugin.rsc +END // ECOM resource definition + +//Resource file +START RESOURCE rsfwgspluginrsc.rss +HEADER +TARGETPATH RESOURCE_FILES_DIR +LANGUAGE_IDS +END // resource + +LIBRARY euser.lib +//LIBRARY ecom.lib +LIBRARY gsecomplugin.lib +LIBRARY efsrv.lib +LIBRARY avkon.lib +LIBRARY bafl.lib +LIBRARY cone.lib +LIBRARY eikcoctl.lib // For CEikMenuPane +LIBRARY eikcore.lib // For MEikMenuObserver +LIBRARY eikctl.lib // Column Listbox +LIBRARY commonengine.lib //For RConeResourceLoader +//LIBRARY egul.lib // CGulIcon +LIBRARY apsettingshandlerui.lib // access point UI +LIBRARY apengine.lib //AP engine +LIBRARY commdb.lib // AP handling +//LIBRARY fbscli.lib // For CFbsBitmap +LIBRARY aknicon.lib // For AknIconUtils +LIBRARY agentdialog.lib // To show access points only in emulator +LIBRARY rsfwmountman.lib // For remote mount handling +LIBRARY rsfwmountstore.lib // for CMountEntry +LIBRARY rsfwmountutils.lib +LIBRARY hlplch.lib // HlpLauncher +LIBRARY connectionuiutilities.lib +LIBRARY sendui.lib +LIBRARY etext.lib +LIBRARY charconv.lib // for CnvUtfConverter +LIBRARY aknskins.lib // AknsUtils.h +LIBRARY featmgr.lib +LIBRARY ecom.lib +LIBRARY sysutil.lib // DiskSpaceBelowCriticalLevel +LIBRARY flogger.lib +LIBRARY inetprotutil.lib + + +// This is optional - used only by Codewarrior for convenience. +//DOCUMENT 101F9777.rss + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/group/rsfwgspluginicons.mk --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/group/rsfwgspluginicons.mk Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,51 @@ +# +# Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +# All rights reserved. +# This component and the accompanying materials are made available +# under the terms of "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: icons makefile for project RsfwGsPlugin +# + +ifeq (WINS,$(findstring WINS,$(PLATFORM))) +ZDIR=$(EPOCROOT)epoc32\release\$(PLATFORM)\$(CFG)\z +else +ZDIR=$(EPOCROOT)epoc32\data\z +endif + +TARGETDIR=$(ZDIR)\resource\apps +HEADERDIR=$(EPOCROOT)epoc32\include +ICONTARGETFILENAME=$(TARGETDIR)\rsfwgsplugin.mif +HEADERFILENAME=$(HEADERDIR)\rsfwgsplugin.mbg + +MAKMAKE : ; + +BLD : ; + +CLEAN : ; + +LIB : ; + +CLEANLIB : ; + +RESOURCE : + mifconv $(ICONTARGETFILENAME) /h$(HEADERFILENAME) \ + /c8,8 qgn_prop_set_conn_remotedrive.svg \ + /c8,8 qgn_indi_connection_on_add.svg + +FREEZE : ; + +SAVESPACE : ; + +RELEASABLES : + @echo $(HEADERFILENAME)&& \ + @echo $(ICONTARGETFILENAME) + +FINAL : ; diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/mydebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/mydebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,31 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug printing to a log file + * +*/ + + +#ifndef MYDEBUG_H +#define MYDEBUG_H + +// Debug defines for MountMan: + +#define APPEND_TO_DEBUG_FILE + +_LIT(KDebugDirName, "gsplugin"); +_LIT(KDebugFileName, "gsplugin.txt"); + +#endif // MYDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgslocalviewids.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgslocalviewids.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,33 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: View ID's for all RsfwGsPlugin views. +* +*/ + + +#ifndef GS_RSFW_LOCAL_VIEW_IDS_H +#define GS_RSFW_LOCAL_VIEW_IDS_H + +// CONSTANTS +const TUid KRemoteDriveSettingsViewId = {11}; + +/** +* This UID is used for both the view UID and the ECOM plugin implementation +* UID. +*/ +const TUid KGSRsfwPluginUID = { 0x101F9778 }; + +#endif // GS_RSFW_LOCAL_VIEW_IDS_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgsplugin.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgsplugin.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,235 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin, UI(CAknView) interface header +* +*/ + + + +#ifndef CRSFWGSPLUGIN_H +#define CRSFWGSPLUGIN_H + +// INCLUDES +#include +#include +#include +#include "rsfwgsplugin.hrh" +#include "rsfwgsremotedrivesend.h" + +// CONSTANTS + +// the drive letter is required in these +// resource file +_LIT( KRsfwGsPluginResourceFileName, "Z:\\resource\\rsfwgspluginrsc.rsc" ); +// icons +_LIT(KGSPluginBitmapFile, "Z:\\resource\\apps\\rsfwgsplugin.mif"); + +// FORWARD DECLARATIONS +class CRsfwGsPluginDriveListContainer; +class CRsfwGsPluginDriveSettingsContainer; +class CRsfwMountMan; + +/** +* CRsfwGsPlugin view class (CAknView). +* +* This is RSFW GS plugin. +*/ +class CRsfwGsPlugin : public CGSPluginInterface + { + + public: // Constructors and destructor + + /** + * Symbian OS two-phased constructor + * @return + */ + static CRsfwGsPlugin* NewL( TAny* aInitParams ); + + /** + * Destructor. + */ + ~CRsfwGsPlugin(); + + /** + * Load the SettingsView with specified mount entry and type of loading + * The types are EEditExisting, ENewDefault, ENewFromExisting + */ + void LoadSettingsViewL(TRsfwSettingsViewType aType, TDesC& aMountName, TBool aAddToViewStack); + + /** + * Loads the Main View where list of remote drives is visible + */ + void LoadMainViewL(); + + /** + * Help launcher method. + * @param aContext The help context + */ + void LaunchHelpL( const TDesC& aContext ); + + public: // From CAknView + + /** + * This function is used for identifying the plugin + */ + TUid Id() const; + + /** + * See CAknView + */ + void HandleViewRectChange(); + + /** + * See CAknView + */ + void DoActivateL( const TVwsViewId& aPrevViewId, + TUid aCustomMessageId, + const TDesC8& aCustomMessage ); + /** + * See CAknView + */ + void DoDeactivate(); + + /** + * See CAknView + */ + void HandleCommandL( TInt aCommand ); + + public: + + /** + * Is the current remote drive connected? + * Fetches the information from RFE + */ + TBool IsDriveConnectedL(); + + /** + * Update softkeys + */ + void UpdateCbaL(); + + /** + * This function deletes the current remote drive. + */ + void DeleteRemoteDriveL(); + + /** + * Return the currently active container + */ + CCoeControl* CurrentContainer(); + + /** + * Process the existed deleting dialog + */ + void ProcessDeletingDialog(); + + protected: + + /** + * C++ default constructor. + */ + CRsfwGsPlugin( ); + + /** + * Symbian OS default constructor. + */ + void ConstructL(); + + private: + + /** + * See base classes + */ + void DynInitMenuPaneL(TInt aResourceId,CEikMenuPane* aMenuPane); + + + /** + * Connect he current remote drive + */ + void ConnectRemoteDriveL(); + + /** + * Disconnect he current remote drive + */ + void DisconnectRemoteDriveL(); + + + /** + * Sends a link to the current remote drive as a smart message + */ + void SendLinkL(); + + + /** + * Process "Send As" + */ + void DoSendAsL(); + + + public: // From CGSPluginInterface + + /** + * See CGSPluginInterface + */ + void GetCaptionL( TDes& aCaption ) const; + + /** + * See CGSPluginInterface + */ + CGulIcon* CreateIconL( const TUid aIconType ); + + public: + + void HandleResourceChangeManual(TInt aType); + + protected: //Data + + // Reference to application UI - not owned. + CAknViewAppUi* iAppUi; + + // RConeResourceLoader + RConeResourceLoader iResources; + + // Previous View ID + TVwsViewId iPrevViewId; // Previous view. + + private: + + // Pointer to the main list container - owned + CRsfwGsPluginDriveListContainer* iMainListContainer; + + // Pointer to the setting list container - owned. + CRsfwGsPluginDriveSettingsContainer* iSettingListContainer; + + // Pointer to the model - owned + CRsfwMountMan* iMountMan; + + // Pointer to the current container - not owned. + CCoeControl* iCurrentContainer; + + // for sending remote drive links - owned + CRsfwGsRemoteDriveSend* iSender; + + // Pointer to the possible deleting dialog + CAknQueryDialog* iDialog; + + // The deleting id of remote drive + TChar iDeletingId; + }; + + + +#endif // CRSFWGSPLUGIN_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgsplugin.hrh --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgsplugin.hrh Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,108 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: contains comman definitions for menu id:s +* +*/ + + +#ifndef GS_RSFW_PLUGIN_HRH +#define GS_RSFW_PLUGIN_HRH + + +/** + * TSettingItems - identifiers for individual setting items + */ +enum TSettingItems + { + ESettingItemDriveName = 1, + ESettingItemURL, + ESettingItemAccessPoint, + ESettingItemServerAddress, + ESettingItemUserID, + ESettingItemPassword + }; + + +// DATA TYPES +// CONSTANTS +#define MAXCONFITEMLENGTH 128 + +// Menu commands +enum TGSRsfwPluginMenuCommands + { + EGSCmdAppConnect = 400, + EGSCmdAppOpen, + EGSCmdAppDisconnect, + EGSCmdAppEdit, + EGSCmdAppChange, + EGSCmdAppNew, + EGSCmdAppDelete, + EGSCmdAppSendLink, + EGSCmdUpdateList + }; + +/** + * Constants used in application + */ +enum TRsfwSettingsIndex + { + ESettingNameIndex = 0, + EServerAddressIndex, + EAccessPointIndex, + EUserIDIndex, + EPasswordIndex + }; + +/** + * TRsfwSettingsViewType - Used inside UI to differentiate + * different kinds of editing + */ +enum TRsfwSettingsViewType + { + EEditExisting, + ENewDefault, + ENewFromExisting + }; + +/** + * Constants used in resources and in application + */ +// maximum length for the drive name +#define KMaxFriendlyNameLength 20 // from UI spec +#define KMaxSettingSetNameArrayGran 10 +#define KMaxUserIDLength 50 +#define KMaxServerAddressLength 200 +#define KMaxPasswordLength 50 +#define KMaxURLLength 200 // from UI spec +#define KMaxServerNameLength 20 +#define KMaxAccessPointNameLength 100 // from ApSettingsHandlerUI +#define KMaxAccessPointDesLength 10 +#define KMaxCompulsoryTextLength 25 +#define KMaxInactivityTimeoutString 10 +// maximum length for menu pane title +#define KMaxMenuPaneTitleLength 25 + +// List items of remote drive settings view +enum { + KGSRsfwSettingsName, + KGSRsfwSettingsAddress, + KGSRsfwSettingsAccessPoint, + KGSRsfwSettingsUserName, + KGSRsfwSettingsPassword + }; + +#endif // GS_RSFW_PLUGIN_HRH + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgsplugindrivelistcontainer.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgsplugindrivelistcontainer.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,280 @@ +/* +* Copyright (c) 2003 - 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: The control container (view) of the remote drives list view +* +*/ + + +#ifndef CRSFWGSPLUGINDRIVELISTCONTAINER_H +#define CRSFWGSPLUGINDRIVELISTCONTAINER_H + +// INCLUDES +// System includes +#include +#include + +#include "rsfwgsplugin.hrh" +#include "rsfwgspropertywatch.h" + +// FORWARD DECLARATIONS + +class CRsfwGsPlugin; +class CRsfwMountMan; +class CEikButtonGroupContainer; +class CAknColumnListBox; + +// CLASS DECLARATION + +/** +* CRsfwGsPluginDriveListContainer container class +* @since 3.1 +* container class for Remote Drives view +*/ +class CRsfwGsPluginDriveListContainer : public CCoeControl, + MEikListBoxObserver, + MCoeForegroundObserver + { + public: // Constructors and destructor + + /** + * Constructor + */ + CRsfwGsPluginDriveListContainer(CRsfwGsPlugin* aView); + + + /** + * Symbian OS default constructor. + * + * @param aRect gives the correct TRect for construction. + */ + void ConstructL( const TRect& aRect, CRsfwMountMan* aMountMan ); + + /** + * Destructor. + */ + ~CRsfwGsPluginDriveListContainer(); + + public: // From CCoeControl + + /** + * See CCoeControl + */ + TInt CountComponentControls() const; + + /** + * See CCoeControl + */ + CCoeControl* ComponentControl( TInt aIndex ) const; + + /** + * See CCoeControl + */ + TKeyResponse OfferKeyEventL( + const TKeyEvent& aKeyEvent, TEventCode aType ); + + /** + * See CCoeControl + */ + void SizeChanged(); + + /** + * See CCoeControl + */ + void HandleResourceChange( TInt aType ); + + /** + * Gets help context + */ + void GetHelpContext( TCoeHelpContext& aContext ) const; + + /** + * See CCoeControl + */ + void FocusChanged(TDrawNow aDrawNow); + + public: // MCoeForegroundObserver + + /** Handles the drive list view coming to the foreground. */ + void HandleGainingForeground(); + /** Handles the drive list view going into the background. */ + void HandleLosingForeground(); + + + public: // own methods + + /** + * Invokes editing on current item, in response to UI Edit command + */ + void EditCurrentItemL(); + + /** + * See MEikListBoxObserver + */ + void HandleListBoxEventL(CEikListBox* aListBox, TListBoxEvent aEventType); + + /** + * Finds whether main list is empty + * @return ETrue if main list is empty. + */ + TBool IsListEmpty(); + + /** + * Finds whether the current item is the last item in main list + * @return ETrue if current item is last in main list. + */ + TBool IsLastItem(); + + /** + * Delete the currently focused drive. Also deletes it from CentRep + */ + void DeleteCurrentRemoteDriveL(); + + /** + * Is drive connected? + * Fetches the information from RFE + * @param the Friendly name of the drive + */ + TBool IsDriveConnectedL(const TDesC& aName); + + /** + * Sets drive in the list to 'connected' or 'disconnected' + * (modifies the icon) + * @param the Friendly name of the drive + */ + void SetDriveConnectedStateL(const TDesC& aName, TBool aConnected); + + /** + * Connects the currently chose remote drive + */ + void ConnectCurrentRemoteDriveL(); + + /** + * Disconnects the remote drive + */ + void DisconnectCurrentRemoteDriveL(); + + /** + * Loads remote drives from Central Repository + * @return TInt the number of remote drives + */ + TInt LoadRemoteDriveListArrayL(); + + /** + * Suggests next new remote drive name, this usually called by UI when + * user create a new remote drive. + * @return TDesC& new remote drive name + */ + TDesC& GetNextRemoteDriveNameL(); + + /** + * Get the name of currently focused drive. Usually called by UI. + * The pointer to buffer remains on heap, which is deleted by caller. + * @return HBufC* pointer to currently focused remote drive name + */ + HBufC* GetCurrentRemoteDriveNameLC(); + + /** + * Get the name of remote drive at index aIndex. Usually called by UI + * @return TPtrC16 Pointer to a buffer owned by the list array + */ + TPtrC GetRemoteDriveNameL(TInt aIndex); + + /** + * Sets the model + */ + void SetModel(CRsfwMountMan* iMountMan); + + /** + * Returns the number of remote drives in the list + */ + TInt RemoteDriveCount(); + + /** + * Sets the focus + */ + void SetFocus(); + + /** + * Sets the focus to given drive + */ + void SetFocusL(const TDes& aDriveName); + + /** + * Get the ID of the current remote drive. + * ID is the drive letter under which the drive is mounted + * @return TInt ID of the current remote drive + */ + TChar GetCurrentRemoteDriveIdL(); + + + void HandleResourceChangeManual(TInt aType); + + private: // own methods + + /** + * Perform the initial setup of the main list. Called by Constructor + */ + void SetupListL(); + + + /** + * Get Remote drive names + * @return CDesCArray remote drives + */ + CDesCArray* GetRemoteDriveNamesL(); + + /** + * Handles the drive list view coming to the foreground. + * Leaving variant + */ + void HandleGainingForegroundL(); + + public: // data + + // model, not owned + CRsfwMountMan* iMountMan; + + // for setting focus + TInt iCurrentItemIndex; + + private: // data + + // Pointer to the main list, owned + CAknColumnListBox* iMainList; + + // Pointer to the application view, not owned + CRsfwGsPlugin* iView; // not owned + + // The remote drive names list array, not owned + CDesCArray* iRemoteDriveListArray; + + // Buffer for holding remote drive setting name + TBuf iSettingNewName; + + // Title for menu pane + TBuf iTitle; + + // Pointer to title pane, not owned + CAknTitlePane* iTitlePane; + + // P&S notifier about changes in drive connection state + CRsfwGsPropertyWatch* iDriveConnectObserver; + + + + }; + +#endif //CRSFWGSPLUGINDRIVELISTCONTAINER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgspluginsettinglist.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgspluginsettinglist.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,130 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin, Setting List class +* +*/ + + +#ifndef CRSFWGSPLUGINSETTINGSLIST_H +#define CRSFWGSPLUGINSETTINGSLIST_H + +// INCLUDE FILES +//#include +#include +#include +#include "rsfwgsplugin.hrh" + +// FORWARD DECLARATIONS +class CRsfwGsSettingsData; + +/** +* CRsfwGsPluginSettingsList derived from CAknSettingItemList +*/ +class CRsfwGsPluginSettingsList : public CAknSettingItemList + { + + public: + + /** + * Symbian OS two-phased constructor + * @param reference to CRsfwGsSettingsData from which data to be displayed + */ + static CRsfwGsPluginSettingsList* NewL(CRsfwGsSettingsData &aData); + + /** + * Symbian OS two-phased constructor, leave pointer to stack + * @param reference to CRsfwGsSettingsData from which data to be displayed + */ + static CRsfwGsPluginSettingsList* NewLC(CRsfwGsSettingsData &aData); + + /** + * Destructor. + */ + virtual ~CRsfwGsPluginSettingsList(); + + /** + * Inherited from base classes. See CCoeControl + */ + void SizeChanged(); + + /** + * Edit the indexed item. This probably came as a result of UI command + * @param aIndex index to the item + * aCalledFromMenu ETrue of this call resulted from UI command + */ + void EditItemL (TInt aIndex, TBool aCalledFromMenu); + + /** + * Actual editing of item done here, from whereever the call is made from + */ + void EditCurrentItemL(); + + /** + * Gets the Access point name + * @param aAP Access point number as integer + * aAccessPoint reference to TDes, doesnt change if AP not found + * otherwise access point name returns here + */ + void GetAccessPointNameL(TInt32 aAP, TDes& aAccessPoint); + + /** + * Sets the focus to the first item of the settings list + */ + void ResetItemIndex(); + + private: + + /** + * C++ constructor + * @param reference to CRsfwGsSettingsData + */ + CRsfwGsPluginSettingsList(CRsfwGsSettingsData &aData); + + /** + * See CAknSettingItemList + */ + CAknSettingItem* CreateSettingItemL (TInt aSettingId); + + /** + * Edit the AccessPoint, We edit the access point differently than other + * settings. We bypass the list's text editor and open the S60 standard + * access point editor + */ + void EditAccessPointL(); + + /** + * Saves the changed settings to the list's data + * @param aIndex index of the setting to be saved + */ + void SaveSettingL(TInt aIndex); + + /** + * Sets the title pane text with given discriptor + * @param aTitleText text to be shown on title pane + */ + void SetTitlePaneTextL( const TDesC& aTitleText ) const; + + private: + + // Reference to the data owned by container + CRsfwGsSettingsData& iSettingsData; + + // Dialog server for access point selection + RGenConAgentDialogServer iDlgSrv; + + // Request status for requests made to RGenConAgentDialogServer + TRequestStatus iStatus; + }; + +#endif // CRSFWGSPLUGINSETTINGSLIST_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgspropertywatch.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgspropertywatch.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,49 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: P&S observer +* +*/ + + +#ifndef CRSFWGSPROPERTYWATCH_H +#define CRSFWGSPROPERTYWATCH_H + +#include +#include +#include + +// FORWARD DECLARATIONS +class CRsfwGsPluginDriveListContainer; + +class CRsfwGsPropertyWatch : public CActive +{ + enum { EPriority=0 }; + +public: + static CRsfwGsPropertyWatch* NewL(CRsfwGsPluginDriveListContainer* aContainer); + ~CRsfwGsPropertyWatch(); +private: + CRsfwGsPropertyWatch(); + void ConstructL(CRsfwGsPluginDriveListContainer* aContainer); + void RunL(); + void DoCancel(); +private: + RProperty iProperty; + CRsfwGsPluginDriveListContainer* iContainer; + TDriveList iDriveList; +}; + +#endif // CRSFWGSPROPERTYWATCH_H + +// End of File \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgsremotedrivesend.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgsremotedrivesend.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,69 @@ +/* +* Copyright (c) 2002 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin, for sending drive + * +*/ + + +#ifndef CRSFWGSREMOTEDRIVESEND_H +#define CRSFWGSREMOTEDRIVESEND_H + +// INCLUDES +#include + +// FORWARD DECLARATIONS; +class CRsfwMountEntry; +class CEikMenuPane; +class CSendUi; +class TParse; +class RFile; + +// path and filename for vCalendar attachment +_LIT( KRemoteDriveAttachmentFilename, "c:\\system\\data\\rsfw_cache\\rdrive.cfg" ); + +NONSHARABLE_CLASS( CRsfwGsRemoteDriveSend ) : public CBase + { +public: // Factory method and destructor + static CRsfwGsRemoteDriveSend* NewL(TInt aMenuCommandId); + virtual ~CRsfwGsRemoteDriveSend(); + +public: // API + TBool CanSend(); + void DisplaySendMenuItemL(CEikMenuPane& aMenuPane, TInt aIndex); + void DisplaySendCascadeMenuL(); + void SendL(const CRsfwMountEntry& aEntry); + +private: // utility functions + void DoSendAsAttachmentFileL(TInt aCommand, TParse& aFilename); + + void DoSendAsAttachmentHandleL(const RFile& aHandle); + + HBufC8* ConvertToUtf7LC(const TDesC16& aText); + +private: // constrution + CRsfwGsRemoteDriveSend(); + void ConstructL(TInt aMenuCommandId); +private: // data + CSendUi* iSendUi; + TInt iSendAsCmdId; + TUid iSelectedMtmUid; + CArrayFixFlat* iSendMtmsToDim; + + + }; + +#endif // CRSFWGSREMOTEDRIVESEND_H + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgsremotedrivesettingscontainer.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgsremotedrivesettingscontainer.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,249 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: The control container (view) of the settings list view +* +*/ + + +#ifndef CRSFWGSPLUGINDRIVESETTINGSCONTAINER_H +#define CRSFWGSPLUGINDRIVESETTINGSCONTAINER_H + +// INCLUDES +#include +//#include "rsfwgsplugin.h" + + +// FORWARD DECLARATIONS +//class CGSListBoxItemTextArray; +class CRsfwGsPluginSettingsList; +class CRsfwGsSettingsData; +class CRsfwMountMan; +class CAknView; +class CRsfwMountEntry; + + +// CLASS DECLARATION + +/** +* CRsfwGsPluginDriveSettingsContainer container class +* container class for Remote drive settings view +* +* @lib rsfwgsplugin.dll +* @since Series 60 3.1 +*/ +class CRsfwGsPluginDriveSettingsContainer : public CCoeControl, + MEikListBoxObserver, + MCoeForegroundObserver + + { + public: // Constructors and destructor + + /** + * Constructor. + */ + CRsfwGsPluginDriveSettingsContainer(CAknView* aView); + + + /** + * By default Symbian 2nd phase constructor is private. + * @param aRect gives the correct TRect for construction + * @param aModel for the model + */ + void ConstructL( const TRect& aRect, + CRsfwMountMan* aMountMan ); + + + /** + * Destructor. + */ + ~CRsfwGsPluginDriveSettingsContainer(); + + public: // From CCoeControl + + /** + * See CCoeControl. + */ + TInt CountComponentControls() const; + + /** + * See CCoeControl. + */ + CCoeControl* ComponentControl( TInt aIndex ) const; + + /** + * See CCoeControl. + */ + TKeyResponse OfferKeyEventL( + const TKeyEvent& aKeyEvent, TEventCode aType ); + + /** + * See CCoeControl. + */ + void SizeChanged(); + + /** + * See CCoeControl. + */ + void Draw(const TRect& aRect) const; + + /** + * See CCoeControl + */ + void HandleResourceChange( TInt aType ); + + /** + * Gets help context + */ + void GetHelpContext( TCoeHelpContext& aContext ) const; + + /** + * See CCoeControl + */ + void FocusChanged(TDrawNow aDrawNow); + + public: // MCoeForegroundObserver + + /** Handles the drive list view coming to the foreground. */ + void HandleGainingForeground(); + /** Handles the drive list view going into the background. */ + void HandleLosingForeground(); + + + public: + + /** + * Edit currently focused item on settings list. called from UI + */ + void EditCurrentItemL(); + + /** + * See MEikListBoxObserver + */ + void HandleListBoxEventL(CEikListBox* aListBox, TListBoxEvent aEventType); + + /** + * Prepare a Remote drive with given name for editing + * @param aRemoteDriveName reference to the remote drive to be edited + */ + void PrepareRemoteDriveForEditingL(const TDesC& aRemoteDriveName); + + /** + * Prepare the a new remote drive with default values with given name + * @param aRemoteDrive name reference to the new remote drive name + */ + void PrepareRemoteDriveNewDefaultL(TDesC& aRemoteDriveName); + + + /** + * Called by the UI when back button is pressed, to perform needed steps + * @return ETrue if settings list is allowed to close + */ + TBool IsExitProcessingOKL(); + + /** + * Save current drive settings + */ + void SaveSettingsL(); + + /* + * Return the name of current set in iData + * @return TDes reference to current set + */ + TDes& GetCurrentRemoteDriveName(); + + + void HandleResourceChangeManual(TInt aType); + + private: // Most of these methods perform operations using iData + + /** + * Sets the title pane text with given discriptor + * @param aTitleText text to be shown on title pane + */ + void SetTitlePaneTextL( const TDesC& aTitleText ) const; + + /** + * Finds out whether compulsory items are filled + * @return ETrue if compulsory items are filled + */ + TBool AreCompulsoryItemsFilled(); + + /** + * Display a query dialog to user that compulsory settings are not + * filled, and if user wants to delete the settings + * @return ETrue if user wants to delete the settings + */ + TBool DisplayDeleteOrDontSaveDialogL(); + + /** + * Update a remote drive if it already exist or create it if it doesnt exist + * @param aShowDialog if false then possible error notes won't be shown + * @return ETrue if save procedure goes ok + */ + TBool SaveOrCreateAndSaveRemoteDriveL(TBool aShowDialog); + + /** + * Deletes the remote drive if it exist in the Central Repository + */ + void DeleteRemoteDriveIfExistL(); + + /** + * Load Remote drive names with trap, useful when list doesnt have anything + * @param Reference to setting ids + * @return CDesCArray remote drives + */ + CDesCArray* LoadRemoteDriveNamesL(); + + /** + * See if the remote drive setting under edit was changed + * @param Reference to the current mount conf + * @return ETrue if something has been changed + */ + TBool DataChanged(const CRsfwMountEntry* aCurrentData); + + /** + * Check whether some other drive (some other drive letter) already uses this name + * @param aRemoteDriveNamereference the remote drive name + * @param aDriveLetter the drive letter + * @return ETrue if remote drive exist with given name + */ + TBool IsRemoteDriveNameConflictL(TDesC& aRemoteDriveName, const TDesC& aDriveLetter); + + /** + * Returns ETrue if the address (URL) for a remote drive is valid + * Calls RsfwMountUtils API + * @since S60 3.2 + * @param aFriendlyName remote drive friendly name + */ + TBool IsDriveAddressValidL(const TDesC& aDriveAddress); + + private: // data + + // CRsfwGsPluginSettingsList owned + CRsfwGsPluginSettingsList* iSettingList; + + // Pointer to settings data owned + CRsfwGsSettingsData* iData; + + // Pointer to the application view, not owned + CAknView* iView; // not owned + + // model, not owned + CRsfwMountMan* iMountMan; + }; + + +#endif // CRSFWGSPLUGINDRIVESETTINGSCONTAINER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/inc/rsfwgssettingsdata.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/inc/rsfwgssettingsdata.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,102 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin data holding class for Rsfw setting list +* +*/ + + +#ifndef CRSFWGSSETTINGSDATA_H +#define CRSFWGSSETTINGSDATA_H + +// INCLUDE FILES +#include + +#include "rsfwgsplugin.hrh" + + +// CONSTANTS +const TInt KDefaultInactivityTimeout = 600; // 5min + +/** +* CRsfwGsSettingsData holds single remote drive configuration +*/ +class CRsfwGsSettingsData : public CBase + { + public: + + /** + * Default 1st phase factory method. + * Creates an instance of CRsfwGsSettingsData + */ + static CRsfwGsSettingsData* NewL(); + + /** + * Default 1st phase factory method. + * Creates an instance of CRsfwGsSettingsData, leaves it on stack + */ + static CRsfwGsSettingsData* NewLC(); + + /** + * Destructor + */ + virtual ~CRsfwGsSettingsData(); + + /** + * Resets all data to initial values + */ + void Reset(); + + private: + + /** + * 2nd Phase constructor + */ + void ConstructL(); + + /** + * C++ Constructor + */ + CRsfwGsSettingsData(); + + public: + + // Buffer holding the remote drive friendly name + TBuf iSettingName; + + // Access point number + TInt32 iAccessPoint; + + // Buffer holding the access point number as a descriptor + TBuf iAccessPointDes; + + // Buffer holding the URL + TBuf iURL; + + // Buffer holding the User ID + TBuf iUserID; + + // Buffer holding the password + TBuf iPassword; + + // Buffer holding the access point name + TBuf iAccessPointName; + + // Inactivity timeout + TBuf iInActivityTimeout; + + // drive letter + TChar iDriveLetter; + }; + +#endif // CRSFWGSSETTINGSDATA_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/loc/rsfwgsplugin.loc --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/loc/rsfwgsplugin.loc Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,192 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Localization strings for RsfwGSPlugin +* +*/ + + +// LOCALISATION STRINGS + +//d:error note; not able to add a new drive +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_error_max_drives "Maximum number of remote drives configured. Remove old configurations to create new." + +//d:error note; not able to edit settings for a connected drive +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_error_edit_connected "%U connected. Drive configuration cannot be changed during active connection." + +//d:error note; new configuration is incomplete +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_query_incomplete "Remote drive configuration incomplete. Delete configuration?" + +//d:error note; drive name already exists +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_error_existing_name "Drive name %U already exists. Please enter unique drive name." + +//d:Default name for a new remote drive +//l:list_set_graphic_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_default_drive_name "New drive" + +//d:Password setting for a remote drive +//l:list_setting_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_setting_pw "Password" + +//d:User name setting for a remote drive +//l:list_setting_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_setting_user "User name" + +//d:Access point setting for a remote drive +//l:list_setting_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_setting_ap "Access point" + +//d:Address setting for a remote drive +//l:list_setting_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_setting_url "Address" + +//d:Drive name setting for a remote drive +//l:list_setting_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_setting_drive_name "Drive name" + +//d:Default title for settings for a new remote drive +//l:title_pane_t2/opt9 +//w: +//r:3.1 +// +#define qtn_rd_title_new_drive "New drive" + +//d:Text in confirmation query when deleting a drive +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_query_delete_drive "Delete configuration for %U?" + +//d:Options list text for deleting a remote drive +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_opt_delete "Delete" + +//d:Options list text for new remote drive +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_opt_new_drive "New remote drive" + +//d:Options list text for editing a remote drive +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_opt_edit "Edit" + +//d:Options list text for connecting a remote drive +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_opt_connect "Connect" + +//d:Options list text for disconnecting a remote drive +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_opt_disconnect "Disconnect" + +//d:Options list text for sending a remote drive configuration +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_opt_send_link "Send link" + +//d:Text for empty listbox item +//l:main_pane_empty_t1/opt2 +//w: +//r:3.1 +// +#define qtn_rd_empty_list_primary "(no remote drives)" + +//d:Secondary text for empty listbox item +//l:main_list_empty_pane/opt2 +//w: +//r:3.1 +// +#define qtn_rd_empty_list_secondary "Select New remote drive from options menu" + +//d:Text in title pane +//l:title_pane_t2/opt9 +//w: +//r:3.1 +// +#define qtn_rd_title_drives "Remote drives" + +//d:Title showed by Control Panel application for this plugin +//l:list_double_large_graphic_pane_t1 +//w: +//r:5.0 +// +#define qtn_set_folder_conn_remote_drives "Remote drives" + +//d:Default value for access point name +//l:list_set_graphic_pane_t1 +//w: +//r:3.1 +// +#define qtn_rd_default_access_point "Always ask" + +//d:Information note +//l:popup_note_window +//d:There has to be '\' character before '"' character. +//d: This combination is shown as '"' character +//w: +//r:3.2 +#define qtn_rd_infonote_missing_http_prefix "Add a supported prefix to drive address. For example \"https://\" or \"http://\"." + +// End of File + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgsplugin.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgsplugin.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,699 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RsfwPlugin Implementation +* +*/ + + +// Includes +#include +#include +#include // for KUidGS +#include +#include +#include +#include +#include +#include +#include +#include + +#include "rsfwgsplugin.h" +#include "rsfwinterface.h" +#include "rsfwgsplugindrivelistcontainer.h" +#include "rsfwgsremotedrivesettingscontainer.h" +#include "rsfwgslocalviewids.h" + + +#define KUidGeneralSettings 0x100058EC + +// ========================= MEMBER FUNCTIONS ================================ + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::CRsfwGsPlugin() +// Constructor +// +// --------------------------------------------------------------------------- +// +CRsfwGsPlugin::CRsfwGsPlugin( ) + : iAppUi( CAknView::AppUi() ), iResources( *CCoeEnv::Static() ) + { + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::~CRsfwGsPlugin() +// Destructor +// +// --------------------------------------------------------------------------- +// +CRsfwGsPlugin::~CRsfwGsPlugin() + { + FeatureManager::UnInitializeLib(); + + if (iCurrentContainer && iAppUi) + { + iAppUi->RemoveFromViewStack( *this, iCurrentContainer ); + } + delete iMainListContainer; + delete iSettingListContainer; + delete iMountMan; + delete iSender; + iResources.Close(); + /** Nice to know when the plugin is cleaned up */ + #ifdef _DEBUG + RDebug::Print( _L( "[CRsfwGsPlugin] ~CRsfwGsPlugin()" ) ); + #endif + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::ConstructL() +// Symbian OS two-phased constructor +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::ConstructL() + { + // To know if the plugin is loaded (for debugging) + #ifdef _DEBUG + RDebug::Print(_L("[CRsfwGsPlugin] ConstructL()" )); + RDebug::Print( _L( "[CRsfwGsPlugin] Loading resource from :" ) ); + RDebug::Print( KRsfwGsPluginResourceFileName ); + #endif + + iMountMan = CRsfwMountMan::NewL(0, NULL); + + iSender = CRsfwGsRemoteDriveSend::NewL(EGSCmdAppSendLink); + + TFileName fileName( KRsfwGsPluginResourceFileName ); + iResources.OpenL( fileName ); + BaseConstructL( R_GS_RSFW_MAIN_VIEW ); + + FeatureManager::InitializeLibL(); + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::NewL() +// Static constructor +// --------------------------------------------------------------------------- +// +CRsfwGsPlugin* CRsfwGsPlugin::NewL( TAny* /*aInitParams*/ ) + { + CRsfwGsPlugin* self = new(ELeave) CRsfwGsPlugin( ); + CleanupStack::PushL(self); + self->ConstructL(); + CleanupStack::Pop(self); + return self; + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::Id() const +// --------------------------------------------------------------------------- +// +TUid CRsfwGsPlugin::Id() const + { + return KGSRsfwPluginUID; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::HandleClientRectChange() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::HandleViewRectChange() + { + if ( iMainListContainer->IsVisible() ) + { + iMainListContainer->SetRect( ClientRect() ); + } + + if ( iSettingListContainer->IsVisible() ) + { + iSettingListContainer->SetRect( ClientRect() ); + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::DoActivateL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::DoActivateL( const TVwsViewId& aPrevViewId, + TUid aCustomMessageId, + const TDesC8& aCustomMessage ) + { + iPrevViewId = aPrevViewId; + if (iCurrentContainer) + { + iAppUi->RemoveFromViewStack( *this, iCurrentContainer ); + iCurrentContainer = NULL; + } + + + if( iMainListContainer ) + { + delete iMainListContainer; + iMainListContainer=NULL; + } + + if( iSettingListContainer ) + { + delete iSettingListContainer; + iSettingListContainer = NULL; + } + + iMainListContainer = new( ELeave ) CRsfwGsPluginDriveListContainer(this); + iMainListContainer->SetMopParent(this); + TRAPD( error, iMainListContainer->ConstructL( ClientRect(), iMountMan ) ); + if (error) + { + delete iMainListContainer; + iMainListContainer = NULL; + User::Leave( error ); + } + + iSettingListContainer = new( ELeave ) CRsfwGsPluginDriveSettingsContainer(this); + iSettingListContainer->SetMopParent(this); + TRAPD( error1, iSettingListContainer->ConstructL( ClientRect(), iMountMan)); + if (error1) + { + delete iSettingListContainer; + iSettingListContainer = NULL; + User::Leave( error1 ); + } + + if (aCustomMessageId == KRemoteDriveSettingsViewId) + { + TBuf remoteDrive; + CnvUtfConverter::ConvertToUnicodeFromUtf8(remoteDrive, aCustomMessage); + iSettingListContainer->MakeVisible(ETrue); + if (remoteDrive.Length() > 0) + { + LoadSettingsViewL(EEditExisting, remoteDrive, EFalse); + } + else + { + LoadSettingsViewL(ENewDefault, + iMainListContainer->GetNextRemoteDriveNameL(), EFalse); + } + iCurrentContainer = iSettingListContainer; + } + else + { + iSettingListContainer->MakeVisible(EFalse); + iCurrentContainer = iMainListContainer; + } + + UpdateCbaL(); + iAppUi->AddToViewStackL( *this, iCurrentContainer ); + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::DoDeactivate() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::DoDeactivate() + { + // try to save settings if in settings list container + if ( iCurrentContainer && iSettingListContainer + && iCurrentContainer == iSettingListContainer ) + { + TRAP_IGNORE(iSettingListContainer->SaveSettingsL()); + } + + if ( iCurrentContainer ) + { + iAppUi->RemoveFromViewStack( *this, iCurrentContainer ); + } + iCurrentContainer = NULL; + + if( iMainListContainer ) + { + delete iMainListContainer; + iMainListContainer = NULL; + } + + if( iSettingListContainer ) + { + delete iSettingListContainer; + iSettingListContainer = NULL; + } + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::HandleCommandL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::HandleCommandL( TInt aCommand ) + { + switch ( aCommand ) + { + case EAknSoftkeyBack: + if (iCurrentContainer == iSettingListContainer) + { + if (iSettingListContainer->IsExitProcessingOKL()) + { + // if we are called from GS, go back to the main view + // otherwise we are called e.g. from FileManager => + // go back to the previous view + if (iPrevViewId.iAppUid == KUidGS) + { + LoadMainViewL(); + // set focus on the newly created/modified drive + // we have to pass the name cause in case a drive has just been created + // we don't know its position on the list + iMainListContainer->SetFocusL(iSettingListContainer->GetCurrentRemoteDriveName()); + } + else + { + iAppUi->ActivateLocalViewL( iPrevViewId.iViewUid ); + } + + } + } + else + { + iAppUi->ActivateLocalViewL( iPrevViewId.iViewUid ); + } + + break; + case EGSCmdAppEdit: + if (!(iMainListContainer->IsListEmpty())) + { + iMainListContainer->EditCurrentItemL(); + } + break; + case EGSCmdAppChange: + iSettingListContainer->EditCurrentItemL(); + break; + case EGSCmdAppNew: + // Number of remote drives is limited to 9, so that drive + // letters are also available for other technologies. + if (iMainListContainer->RemoteDriveCount() < KMaxRemoteDrives) + { + LoadSettingsViewL(ENewDefault, + iMainListContainer->GetNextRemoteDriveNameL(), ETrue); + } + else + { + HBufC* myDisplayMessage = NULL; + myDisplayMessage = StringLoader::LoadLC(R_STR_RSFW_ERROR_MAX_DRIVES); + CAknErrorNote* errorNote = new CAknErrorNote(EFalse); + errorNote->ExecuteLD(*myDisplayMessage); + CleanupStack::PopAndDestroy(myDisplayMessage); + } + break; + case EGSCmdAppDelete: + DeleteRemoteDriveL(); + break; + case EGSCmdAppConnect: + ConnectRemoteDriveL(); + break; + case EGSCmdAppDisconnect: + DisconnectRemoteDriveL(); + break; + case EAknCmdHelp: + { + if (iCurrentContainer == iSettingListContainer) + { + LaunchHelpL(KRD_HLP_REMOTE_DRIVE_CONFIG); + } + + else + { + LaunchHelpL(KRD_HLP_REMOTE_DRIVES); + } + + } + break; + case EGSCmdAppSendLink: + { + SendLinkL(); + } + break; + default: + iAppUi->HandleCommandL( aCommand ); + break; + } + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::GetCaptionL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::GetCaptionL( TDes& aCaption ) const + { + StringLoader::Load( aCaption, R_GS_REMOTE_DRIVES_VIEW_CAPTION ); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::CreateIconL() +// --------------------------------------------------------------------------- +// + CGulIcon* CRsfwGsPlugin::CreateIconL( const TUid aIconType ) + { + CGulIcon* icon; + + if( aIconType == KGSIconTypeLbxItem ) + { + icon = AknsUtils::CreateGulIconL( + AknsUtils::SkinInstance(), + KAknsIIDQgnPropSetConnRemotedrive, + KGSPluginBitmapFile, + EMbmRsfwgspluginQgn_prop_set_conn_remotedrive, + EMbmRsfwgspluginQgn_prop_set_conn_remotedrive_mask); + } + else + { + icon = CGSPluginInterface::CreateIconL( aIconType ); + } + return icon; + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::LoadSettingsViewL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::LoadSettingsViewL(TRsfwSettingsViewType aType, TDesC& aRemoteDrive, TBool aAddToViewStack) + { + switch(aType) + { + case EEditExisting: + iSettingListContainer->PrepareRemoteDriveForEditingL(aRemoteDrive); + break; + case ENewDefault: + iSettingListContainer->PrepareRemoteDriveNewDefaultL(aRemoteDrive); + break; + default: + break; + } + if (iCurrentContainer) + iAppUi->RemoveFromViewStack( *this, iCurrentContainer ); + iCurrentContainer = iSettingListContainer; + if (aAddToViewStack) + { + iAppUi->AddToViewStackL( *this, iCurrentContainer ); + } + iMainListContainer->MakeVisible(EFalse); + iSettingListContainer->MakeVisible(ETrue); + UpdateCbaL(); + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::LoadMainViewL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::LoadMainViewL() + { + iMainListContainer->LoadRemoteDriveListArrayL(); + if (iCurrentContainer) + iAppUi->RemoveFromViewStack( *this, iCurrentContainer ); + iCurrentContainer = iMainListContainer; + iAppUi->AddToViewStackL( *this, iCurrentContainer ); + + iMainListContainer->SetFocus(); + + iSettingListContainer->MakeVisible(EFalse); + UpdateCbaL(); + iMainListContainer->MakeVisible(ETrue); + Cba()->DrawDeferred(); + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::DynInitMenuPaneL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::DynInitMenuPaneL( TInt aResourceId, + CEikMenuPane* aMenuPane ) + { + if ( aResourceId == R_GS_REMOTE_DRIVES_MENU ) + { + if (iCurrentContainer == iMainListContainer) + { + aMenuPane->SetItemDimmed(EGSCmdAppChange, ETrue); + if (iMainListContainer->IsListEmpty()) + { + aMenuPane->SetItemDimmed( EGSCmdAppEdit, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppDelete, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppConnect, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppDisconnect, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppSendLink, ETrue ); + } + else + { + TBool isDriveConnected = IsDriveConnectedL(); + aMenuPane->SetItemDimmed( EGSCmdAppDelete, isDriveConnected ); + aMenuPane->SetItemDimmed( EGSCmdAppConnect, isDriveConnected ); + aMenuPane->SetItemDimmed( EGSCmdAppEdit, isDriveConnected ); + aMenuPane->SetItemDimmed( EGSCmdAppDisconnect, !isDriveConnected ); + } + } + else + { + aMenuPane->SetItemDimmed( EGSCmdAppNew, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppEdit, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppDelete, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppConnect, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppDisconnect, ETrue ); + aMenuPane->SetItemDimmed( EGSCmdAppSendLink, ETrue ); + } + + } + + if (aResourceId == R_GS_MENU_ITEM_EXIT) + { + if (!FeatureManager::FeatureSupported( KFeatureIdHelp )) + { + aMenuPane->SetItemDimmed( EAknCmdHelp , ETrue ); + } + } + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::DeleteRemoteDriveL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::DeleteRemoteDriveL() + { + + HBufC* myFormatMessage = NULL; + HBufC* here = iMainListContainer->GetCurrentRemoteDriveNameLC(); + TChar driveId = iMainListContainer->GetCurrentRemoteDriveIdL(); + + if (!iMainListContainer->IsDriveConnectedL(*here)) + { + if ( here->Length() ) + { + myFormatMessage = StringLoader::LoadLC( R_STR_RSFW_CONF_DELETE, *here ); + } + else + { + myFormatMessage = StringLoader::LoadLC( R_STR_RSFW_CONF_DELETE ); + } + + CAknQueryDialog* query = CAknQueryDialog::NewL(CAknQueryDialog::EConfirmationTone); + + iDialog = query; + iDeletingId = iMainListContainer->GetCurrentRemoteDriveIdL(); + + if ( query->ExecuteLD( R_CONFIRMATION_QUERY, *myFormatMessage ) ) + { + if (iMainListContainer->RemoteDriveCount() > 0) + { + TChar currentdriveId = iMainListContainer->GetCurrentRemoteDriveIdL(); + if (driveId == currentdriveId) + { + iMainListContainer->DeleteCurrentRemoteDriveL(); + } + } + } + iDialog = NULL; + + CleanupStack::PopAndDestroy(myFormatMessage); + + UpdateCbaL(); + + } + CleanupStack::PopAndDestroy(here); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::ProcessDeletingDialog() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::ProcessDeletingDialog() + { + if ( (iMainListContainer->RemoteDriveCount() == 0) || + (iDeletingId != iMainListContainer->GetCurrentRemoteDriveIdL()) ) + { + if (iDialog) + { + delete iDialog; + iDialog = NULL; + } + } + } + +// --------------------------------------------------------- +// CRsfwGsPlugin::LaunchHelpL() +// --------------------------------------------------------- +// +void CRsfwGsPlugin::LaunchHelpL( const TDesC& aContext ) + { + //make context array + //granurality 1 is ok cos there is added just one item + CArrayFix< TCoeHelpContext >* cntx = new( ELeave ) CArrayFixFlat< TCoeHelpContext >( 1 ); + CleanupStack::PushL( cntx ); + + cntx->AppendL( TCoeHelpContext( TUid::Uid(KUidGeneralSettings), aContext ) ); + CleanupStack::Pop( cntx ); + + //and launch help - takes ownership of context array + HlpLauncher::LaunchHelpApplicationL( iEikonEnv->WsSession(), cntx); + } + +// --------------------------------------------------------- +// CRsfwGsPlugin::HandleResourceChangeManual +// --------------------------------------------------------- +// +void CRsfwGsPlugin::HandleResourceChangeManual(TInt aType) + { + if (iCurrentContainer==iSettingListContainer) + iMainListContainer->HandleResourceChangeManual(aType); + else if (iCurrentContainer==iMainListContainer) + iSettingListContainer->HandleResourceChangeManual(aType); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::IsDriveConnected() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPlugin::IsDriveConnectedL() + { + TBool connected; + HBufC* currentDriveName = iMainListContainer->GetCurrentRemoteDriveNameLC(); + if (!currentDriveName) + { + User::Leave(KErrNotFound); + } + TPtrC drivePtr = currentDriveName->Ptr(); + connected = iMainListContainer->IsDriveConnectedL(drivePtr.Left(currentDriveName->Length())); + CleanupStack::PopAndDestroy(currentDriveName); + return connected; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::ConnectRemoteDrive() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::ConnectRemoteDriveL() + { + iMainListContainer->ConnectCurrentRemoteDriveL(); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPlugin::DisconnectRemoteDrive() +// --------------------------------------------------------------------------- +// +void CRsfwGsPlugin::DisconnectRemoteDriveL() + { + iMainListContainer->DisconnectCurrentRemoteDriveL(); + } + + + +// ---------------------------------------------------- +// CRsfwGsPlugin::DoSendAsL +// ---------------------------------------------------- +// +void CRsfwGsPlugin::DoSendAsL() + { + // read the source setting + const CRsfwMountEntry* mountEntry = NULL; + HBufC* currentDriveName = iMainListContainer->GetCurrentRemoteDriveNameLC(); + TPtrC drivePtr = currentDriveName->Ptr(); + mountEntry = iMountMan->MountEntryL( + drivePtr.Left(currentDriveName->Length())); + CleanupStack::PopAndDestroy(currentDriveName); + iSender->SendL( *mountEntry ); + } + + +void CRsfwGsPlugin::SendLinkL( ) + { + HBufC* driveBuf = iMainListContainer->GetCurrentRemoteDriveNameLC(); + iSender->DisplaySendCascadeMenuL(); + + // make sure that the mountentry was not deleted + if (driveBuf) + { + const CRsfwMountEntry* mountentry = iMountMan->MountEntryL(*driveBuf); + CleanupStack::PopAndDestroy(driveBuf); + if (mountentry) + { + if (iSender->CanSend()) + { + DoSendAsL(); + } + } + } + + } + +void CRsfwGsPlugin::UpdateCbaL() + { + CEikButtonGroupContainer* cbaGroup = Cba(); + + if (iCurrentContainer == iMainListContainer) + { + cbaGroup->SetCommandSetL(R_RSFW_SOFTKEYS_OPTIONS_BACK_EDIT); + if (iMainListContainer->IsListEmpty()) + { + cbaGroup->MakeCommandVisible(EGSCmdAppEdit, EFalse); + } + else if (IsDriveConnectedL()) + { + cbaGroup->MakeCommandVisible(EGSCmdAppEdit, EFalse); + } + else + { + cbaGroup->MakeCommandVisible(EGSCmdAppEdit, ETrue); + } + } + else if (iCurrentContainer == iSettingListContainer) + { + cbaGroup->SetCommandSetL(R_RSFW_SOFTKEYS_OPTIONS_BACK_CHANGE); + // it is possible that the MSK command was dimmed + cbaGroup->MakeCommandVisible(EGSCmdAppChange, ETrue); + } + + Cba()->DrawDeferred(); + } + +CCoeControl* CRsfwGsPlugin::CurrentContainer() + { + return iCurrentContainer; + } + +// End of file + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgsplugindrivelistcontainer.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgsplugindrivelistcontainer.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,735 @@ +/* +* Copyright (c) 2003 - 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: The control container (view) of the remote drives list view +* +*/ + + +// INCLUDE FILES +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "rsfwgslocalviewids.h" +#include "rsfwgsplugindrivelistcontainer.h" +#include "rsfwgsplugin.h" +#include "rsfwmountman.h" +#include "rsfwcontrol.h" +#include "rsfwmountentry.h" + + _LIT(KTabulator, "\t"); + _LIT(KConnectedIcon, "\t0"); + +// ============================ MEMBER FUNCTIONS =============================== + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::CRsfwGsPluginDriveListContainer() +// --------------------------------------------------------------------------- +// +CRsfwGsPluginDriveListContainer::CRsfwGsPluginDriveListContainer(CRsfwGsPlugin* aView) : iView(aView) + { + + } + + +// ----------------------------------------------------------------------------- +// GSSettListRemoteDrivesListContainer::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::ConstructL( + const TRect& aRect, + CRsfwMountMan* aMountMan) + { + iMountMan = aMountMan; + + CEikStatusPane* sp = static_cast + ( iEikonEnv->EikAppUi() )->StatusPane(); + iTitlePane = static_cast + ( sp->ControlL( TUid::Uid( EEikStatusPaneUidTitle ) ) ); + + // Set title + StringLoader::Load ( iTitle, R_STR_REMOTE_DRIVES_VIEW_TITLE ); + iTitlePane->SetTextL(iTitle);// FromResourceL( rReader ); + CreateWindowL(); // Makes the control a window-owning control + + // Main List creation and initialization + iMainList = new(ELeave) CAknSingleStyleListBox(); + iMainList->SetContainerWindowL(*this); + iMainList->ConstructL(this, EAknListBoxLoopScrolling); + + // Main list scroll bar issues + iMainList->CreateScrollBarFrameL(EFalse); + iMainList->ScrollBarFrame()->SetScrollBarVisibilityL( + CEikScrollBarFrame::EOff, CEikScrollBarFrame::EAuto); + + // Empty text processing + _LIT (KStringHeader, "%S\n%S"); + HBufC* emptyText = iEikonEnv->AllocReadResourceLC(R_GS_RSFW_NO_REMOTE_DRIVES); + HBufC* emptyText2 = iEikonEnv->AllocReadResourceLC(R_GS_RSFW_NO_REMOTE_DRIVES_EXPLANATORY); + HBufC* myString = HBufC::NewLC(emptyText->Length() + emptyText2->Length() + 5); + TPtr emptyStringPtr = myString->Des(); + emptyStringPtr.Format(KStringHeader, emptyText, emptyText2); + + iMainList->SetListBoxObserver(this); + iMainList->View()->SetListEmptyTextL(*myString); + CleanupStack::PopAndDestroy( 3 ); //emptyText, emptyText2, myString + + CArrayPtrFlat* iconArray = new(ELeave) CAknIconArray(4); + + CGulIcon* icon2; + icon2 = AknsUtils::CreateGulIconL( + AknsUtils::SkinInstance(), + KAknsIIDQgnIndiConnectionOnAdd, + KGSPluginBitmapFile, + EMbmRsfwgspluginQgn_indi_connection_on_add, + EMbmRsfwgspluginQgn_indi_connection_on_add_mask); + + CleanupStack::PushL(icon2); + iconArray->AppendL(icon2); + CleanupStack::Pop(icon2); + + CGulIcon* icon3; + icon3 = AknsUtils::CreateGulIconL( + AknsUtils::SkinInstance(), + KAknsIIDQgnIndiMarkedAdd, + AknIconUtils::AvkonIconFileName(), + EMbmAvkonQgn_indi_marked_add, + EMbmAvkonQgn_indi_marked_add_mask); + + CleanupStack::PushL(icon3); + iconArray->AppendL(icon3); + CleanupStack::Pop(icon3); + + (static_cast(iMainList))-> + ItemDrawer()->ColumnData()->SetIconArray(iconArray); + + SetupListL(); + + // Start receiving P&S notifier about the changes in drive connection states + // if the key is not found, will leave with an error code + // just ignore for now... + TRAP_IGNORE(iDriveConnectObserver = CRsfwGsPropertyWatch::NewL(this)); + + SetRect( aRect ); + ActivateL(); + + iCoeEnv->AddForegroundObserverL( *this ); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::~CRsfwGsPluginDriveListContainer() +// Destructor +// +// --------------------------------------------------------------------------- +// +CRsfwGsPluginDriveListContainer::~CRsfwGsPluginDriveListContainer() + { + if (iMainList) + { + delete iMainList; + } + + if (iDriveConnectObserver) + { + delete iDriveConnectObserver; + } + iCoeEnv->RemoveForegroundObserver( *this ); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::SizeChanged() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::SizeChanged() + { + iMainList->SetRect(Rect()); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::CountComponentControls() const +// --------------------------------------------------------------------------- +// +TInt CRsfwGsPluginDriveListContainer::CountComponentControls() const + { + return 1; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::ComponentControl() const +// --------------------------------------------------------------------------- +// +CCoeControl* CRsfwGsPluginDriveListContainer::ComponentControl( TInt aIndex ) const + { + switch ( aIndex ) + { + case 0: + return iMainList; + default: + return NULL; + } + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::EditCurrentItemL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::EditCurrentItemL() + { + HBufC* currentDriveName = GetCurrentRemoteDriveNameLC(); + if (!(iView->IsDriveConnectedL())) + { + TPtrC drivePtr = currentDriveName->Ptr(); + iCurrentItemIndex=iMainList->CurrentItemIndex(); + TPtrC namePtr = drivePtr.Left(currentDriveName->Length()); + iView->LoadSettingsViewL(EEditExisting, namePtr, ETrue); + + } + else + { + HBufC* myDisplayMessage = NULL; + if ( currentDriveName->Length() ) + { + myDisplayMessage = StringLoader::LoadLC( R_STR_RSFW_ERROR_EDIT_CONNECTED, *currentDriveName ); + } + else + { + myDisplayMessage = StringLoader::LoadLC( R_STR_RSFW_ERROR_EDIT_CONNECTED ); + } + CAknErrorNote* errorNote = new CAknErrorNote(EFalse); + errorNote->ExecuteLD(*myDisplayMessage); + CleanupStack::PopAndDestroy(myDisplayMessage); + } + CleanupStack::PopAndDestroy(currentDriveName); + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::GetCurrentRemoteDriveNameLC() +// --------------------------------------------------------------------------- +// +HBufC* CRsfwGsPluginDriveListContainer::GetCurrentRemoteDriveNameLC() + { + TPtrC16 remoteDriveName, remoteDriveNameClipped, remoteDriveNamePtr; + TInt currentItemIndex = iMainList->CurrentItemIndex(); + if (currentItemIndex == KErrNotFound) + { + User::Leave(KErrNotFound); + } + remoteDriveName.Set(iRemoteDriveListArray->MdcaPoint(currentItemIndex)); + // remove '\t' from the beginning + remoteDriveNameClipped.Set(remoteDriveName.Mid(1)); + // remove the trailing '\tn'if exists + TInt posit = remoteDriveNameClipped.Find(KTabulator); + if (posit != KErrNotFound) + { + remoteDriveNamePtr.Set(remoteDriveNameClipped.Left(posit)); + } + else + { + remoteDriveNamePtr.Set(remoteDriveNameClipped); + } + + return remoteDriveNamePtr.AllocLC(); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::GetRemoteDriveNameLC(TInt aIndex) +// --------------------------------------------------------------------------- +// +TPtrC CRsfwGsPluginDriveListContainer::GetRemoteDriveNameL(TInt aIndex) + { + TPtrC16 remoteDriveName, remoteDriveNameClipped, remoteDriveNamePtr; + remoteDriveName.Set(iRemoteDriveListArray->MdcaPoint(aIndex)); + // remove '\t' from the beginning + remoteDriveNameClipped.Set(remoteDriveName.Mid(1)); + // remove the trailing '\tn' + TInt posit = remoteDriveNameClipped.Find(KTabulator); + if (posit != KErrNotFound) + { + remoteDriveNamePtr.Set(remoteDriveNameClipped.Left(posit)); + } + else + { + remoteDriveNamePtr.Set(remoteDriveNameClipped); + } + + return remoteDriveNamePtr; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::OfferKeyEventL() +// --------------------------------------------------------------------------- +// +TKeyResponse CRsfwGsPluginDriveListContainer::OfferKeyEventL( const TKeyEvent& aKeyEvent, + TEventCode aType ) + { + if (iMainList) + { + // if cancel key is pressed and list is not empty, invoke deletion + if ((aKeyEvent.iCode == EKeyBackspace ) && (aType == EEventKey) ) + { + if(!IsListEmpty()) + { + CRsfwGsPlugin* iTempView = static_cast (iView); + iTempView->DeleteRemoteDriveL(); + } + return EKeyWasConsumed; + } + else + { + TKeyResponse returnValue = iMainList->OfferKeyEventL (aKeyEvent, aType); + if ((aKeyEvent.iCode == EKeyUpArrow || aKeyEvent.iCode == EKeyDownArrow ) + && (aType == EEventKey)) + { + // Cba needs to be updated any time the user goes through the drive list + // as MSK "Edit" is dependent on connection state + // Note that we had to call iMainList->OfferKeyEventL() first + // to make sure that the correct drive is highlighted + iCurrentItemIndex = iMainList->CurrentItemIndex(); + iView->UpdateCbaL(); + } + return returnValue; + } + } + return EKeyWasNotConsumed; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::HandleListBoxEventL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::HandleListBoxEventL(CEikListBox* /*aListBox*/, TListBoxEvent aListBoxEvent) + { + // if the Select Key has been pressed + if ((aListBoxEvent == MEikListBoxObserver::EEventEnterKeyPressed) || + (aListBoxEvent == MEikListBoxObserver::EEventItemSingleClicked)) + { + EditCurrentItemL(); + } + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::SetupListL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::SetupListL() + { + CTextListBoxModel* model = iMainList->Model(); + model->SetOwnershipType(ELbmOwnsItemArray); + + iRemoteDriveListArray = static_cast(model->ItemTextArray()); + LoadRemoteDriveListArrayL(); + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::LoadSettingsListArrayL() +// --------------------------------------------------------------------------- +// +TInt CRsfwGsPluginDriveListContainer::LoadRemoteDriveListArrayL() + { + iTitlePane->SetTextL(iTitle); + + CDesCArray* remoteDriveList = NULL; + remoteDriveList = GetRemoteDriveNamesL(); + CleanupStack::PushL(remoteDriveList); + TInt remoteDriveListCount = remoteDriveList->Count(); + iRemoteDriveListArray->Reset(); + for (TInt i = 0; i< remoteDriveListCount; i++) + { + TBuf string; // maximum name + \t + \tn + string.Append(KTabulator); + string.Append(remoteDriveList->MdcaPoint(i)); + if ( IsDriveConnectedL(remoteDriveList->MdcaPoint(i))) + { + string.Append(KConnectedIcon); + } + iRemoteDriveListArray->AppendL(string); + + } + CleanupStack::PopAndDestroy(remoteDriveList); + iMainList->HandleItemRemovalL(); + iMainList->HandleItemAdditionL(); + return remoteDriveListCount; + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::IsListEmpty() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveListContainer::IsListEmpty() + { + if (iRemoteDriveListArray->Count()) + return EFalse; + return ETrue; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::IsLastItem() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveListContainer::IsLastItem() + { + if (iRemoteDriveListArray->Count() == 1) + return ETrue; + return EFalse; + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::DeleteCurrentRemoteDriveL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::DeleteCurrentRemoteDriveL() + { + TBool deletingLast = EFalse; + if (iMainList->CurrentItemIndex() == iMainList->BottomItemIndex()) + { + deletingLast = ETrue; + } + + HBufC* currentDriveName = GetCurrentRemoteDriveNameLC(); + TPtrC drivePtr = currentDriveName->Ptr(); + iMountMan->DeleteMountEntryL(drivePtr.Left(currentDriveName->Length())); + iRemoteDriveListArray->Delete(iMainList->CurrentItemIndex()); + iMainList->HandleItemRemovalL(); + iMainList->DrawDeferred(); + CleanupStack::PopAndDestroy(currentDriveName); + + if (deletingLast) + { + if (iRemoteDriveListArray->Count() > 0) + { + iMainList->SetCurrentItemIndex(iMainList->BottomItemIndex()); + } + + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::IsDriveConnectedL() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveListContainer::IsDriveConnectedL(const TDesC& aName) + { + + TInt err; + const CRsfwMountEntry* mountEntry; + TRsfwMountInfo mountInfo; + TChar driveL; + mountEntry = mountEntry = iMountMan->MountEntryL(aName); + if (!mountEntry) + { + User::Leave(KErrNotFound); + } + const HBufC* drive = (mountEntry->Item(EMountEntryItemDrive)); + if (drive && drive->Length()) + { + driveL =(*drive)[0]; + } + else + { + // getting drive letter failed + return EFalse; + } + err = iMountMan->GetMountInfo(driveL, mountInfo); + if ((err == KErrNone) && (mountInfo.iMountStatus.iConnectionState == KMountStronglyConnected)) + { + return ETrue; + } + return EFalse; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::SetDriveConnectedStateL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::SetDriveConnectedStateL(const TDesC& aName, TBool aConnected) + { + TInt i; + for (i=0; i < iRemoteDriveListArray->Count(); i++) + { + TPtrC driveString = GetRemoteDriveNameL(i); + if (driveString.Compare(aName) == 0) + { + // newString has space for the friendly name, tabulator and connected icon + TBuf newString; + newString.Append(KTabulator); + newString.Append(driveString); + if (aConnected) + { + newString.Append(KConnectedIcon); + } + iRemoteDriveListArray->Delete(i); + iRemoteDriveListArray->InsertL(i, newString); + iMainList->DrawDeferred(); + // Cba needs to be updated as MSK "Edit" is dependent on connection state + iView->UpdateCbaL(); + break; + } + + } + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::ConnectCurrentRemoteDriveL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::ConnectCurrentRemoteDriveL() +{ + User::LeaveIfError(iMountMan->SetMountConnectionStateBlind(GetCurrentRemoteDriveIdL(), + KMountStronglyConnected)); +} + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::DisconnectCurrentRemoteDriveL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::DisconnectCurrentRemoteDriveL() +{ + User::LeaveIfError(iMountMan->SetMountConnectionState(GetCurrentRemoteDriveIdL(), + KMountNotConnected)); + +} + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::GetNextRemoteDriveNameL +// --------------------------------------------------------------------------- +// +TDesC& CRsfwGsPluginDriveListContainer::GetNextRemoteDriveNameL() + { + // Always return "New drive" as the default starting name + // in case there is already a drive with the name "new name" + // user is not allowed to save the new drive before changing the name. + StringLoader::Load(iSettingNewName, R_STR_REMOTE_DRIVE_NEW_NAME); + return iSettingNewName; + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::GetCurrentRemoteDriveIdL +// --------------------------------------------------------------------------- +// +TChar CRsfwGsPluginDriveListContainer::GetCurrentRemoteDriveIdL() + { + const CRsfwMountEntry* mountEntry; + HBufC* currentDriveName = GetCurrentRemoteDriveNameLC(); + TPtrC drivePtr = currentDriveName->Ptr(); + mountEntry = iMountMan->MountEntryL(drivePtr.Left(currentDriveName->Length())); + if (!mountEntry) + { + User::Leave(KErrNotFound); + } + CleanupStack::PopAndDestroy(currentDriveName); + const HBufC* drive = (mountEntry->Item(EMountEntryItemDrive)); + if (drive && drive->Length()) + { + return (*drive)[0]; + } + + // should not come here.... + // return the drive letter of the default drive + RFs fs; + User::LeaveIfError(fs.Connect()); + TChar defaultd; + fs.DriveToChar(EDriveC, defaultd); + fs.Close(); + return defaultd; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::GetRemoteDriveNamesL +// --------------------------------------------------------------------------- +// +CDesCArray* CRsfwGsPluginDriveListContainer::GetRemoteDriveNamesL() + { + CDesCArray* myArray = new (ELeave) CDesC16ArraySeg(4); + iMountMan->GetMountNamesL(myArray); + return myArray; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::RemoteDriveCount +// --------------------------------------------------------------------------- +// +TInt CRsfwGsPluginDriveListContainer::RemoteDriveCount() + { + return iRemoteDriveListArray->Count(); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::HandleResourceChange() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::HandleResourceChange( TInt aType ) + { + if ( aType == KAknsMessageSkinChange || + aType == KEikDynamicLayoutVariantSwitch ) + { + if (aType != KAknsMessageSkinChange) + { + TRect mainPaneRect; + AknLayoutUtils::LayoutMetricsRect( AknLayoutUtils::EMainPane, + mainPaneRect); + SetRect( mainPaneRect ); + } + DrawDeferred(); + CRsfwGsPlugin* iTempView = static_cast (iView); + + iTempView->HandleResourceChangeManual(aType); + } + CCoeControl::HandleResourceChange( aType ); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::HandleResourceChangeManual() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::HandleResourceChangeManual(TInt aType) + { + if (aType != KAknsMessageSkinChange) + { + TRect mainPaneRect; + AknLayoutUtils::LayoutMetricsRect( AknLayoutUtils::EMainPane, + mainPaneRect); + SetRect( mainPaneRect ); + } + DrawDeferred(); + iMainList->HandleResourceChange(aType); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::FocusChanged +// Set focus on the selected listbox. For animated skins feature. +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::FocusChanged(TDrawNow /*aDrawNow*/) + { + if(iMainList) + { + iMainList->SetFocus( IsFocused() ); + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::GetHelpContext +// This function is called when Help application is launched. +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::GetHelpContext( TCoeHelpContext& aContext ) const + { + aContext.iMajor = KGSRsfwPluginUID; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::HandleGainingForeground +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::HandleGainingForeground() + { + TRAP_IGNORE(HandleGainingForegroundL()); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::HandleGainingForegroundL +// Called from HandleGainingForeground in order to trap potential leaves. +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::HandleGainingForegroundL() + { + if (iView->CurrentContainer() == this) + { + // update the drive list + LoadRemoteDriveListArrayL(); + SetFocus(); + iView->ProcessDeletingDialog(); + iView->UpdateCbaL(); + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::HandleLosingForeground +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::HandleLosingForeground() + { + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::SetFocus +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::SetFocus() + { + TInt remoteDriveCount = iRemoteDriveListArray->Count(); + + if (remoteDriveCount > 0) + { + if (iCurrentItemIndex >= remoteDriveCount) + { + // set to the beginning of the list + iCurrentItemIndex = 0; + } + + iMainList->SetCurrentItemIndex(iCurrentItemIndex); + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveListContainer::SetFocusL +// finds the given name on the drive list and sets focus accordingly +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveListContainer::SetFocusL(const TDes& aDriveName) + { + CDesCArray* remoteDriveList = NULL; + remoteDriveList = GetRemoteDriveNamesL(); + CleanupStack::PushL(remoteDriveList); + + for ( TInt i = 0; i < remoteDriveList->Count(); i++ ) + { + if (aDriveName.Compare(remoteDriveList->MdcaPoint(i)) == 0) + { + iMainList->SetCurrentItemIndex(i); + CleanupStack::PopAndDestroy(remoteDriveList); + return; + } + } + CleanupStack::PopAndDestroy(remoteDriveList); + + // if drive name not found on the list, use default behaviour + SetFocus(); + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgspluginimplementationtable.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgspluginimplementationtable.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: +* ECOM proxy table for this plugin +* +*/ + + +// System includes +#include + +// User includes +#include "rsfwgsplugin.h" + +// Constants +const TImplementationProxy KGSRsfwPluginImplementationTable[] = + { + IMPLEMENTATION_PROXY_ENTRY( 0x101F9778, CRsfwGsPlugin::NewL ) + }; + + +// --------------------------------------------------------------------------- +// ImplementationGroupProxy +// +// Gate/factory function +// --------------------------------------------------------------------------- +// +EXPORT_C const TImplementationProxy* ImplementationGroupProxy( + TInt& aTableCount ) + { + aTableCount = sizeof( KGSRsfwPluginImplementationTable ) + / sizeof( TImplementationProxy ); + return KGSRsfwPluginImplementationTable; + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgspluginsettinglist.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgspluginsettinglist.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,347 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin, Setting List class implementation +* +*/ + + +// INCLUDE FILES +#include +#include +#include +#include +#include +#include +#include + +#include "rsfwgspluginsettinglist.h" +#include "rsfwgssettingsdata.h" +#include "mdebug.h" + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::NewL(CRsfwGsSettingsData &aData) +// ----------------------------------------------------------------------------- +// +CRsfwGsPluginSettingsList *CRsfwGsPluginSettingsList::NewL(CRsfwGsSettingsData &aData) + { + CRsfwGsPluginSettingsList* self = CRsfwGsPluginSettingsList::NewLC(aData); + CleanupStack::Pop(self); + return self; + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::NewLC(CRsfwGsSettingsData &aData) +// ----------------------------------------------------------------------------- +// +CRsfwGsPluginSettingsList *CRsfwGsPluginSettingsList::NewLC(CRsfwGsSettingsData &aData) + { + CRsfwGsPluginSettingsList* self = new (ELeave) CRsfwGsPluginSettingsList(aData); + CleanupStack::PushL(self); + return self; + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::CRsfwGsPluginSettingsList(CRsfwGsSettingsData &aData) +// ----------------------------------------------------------------------------- +// +CRsfwGsPluginSettingsList::CRsfwGsPluginSettingsList(CRsfwGsSettingsData &aData) : + CAknSettingItemList(), + iSettingsData(aData) + { + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::~CRsfwGsPluginSettingsList() +// ----------------------------------------------------------------------------- +// +CRsfwGsPluginSettingsList::~CRsfwGsPluginSettingsList() + { +#if defined __WINS__ + iDlgSrv.Close(); +#endif + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::SizeChanged() +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::SizeChanged() + { + // if size changes, make sure component takes whole available space + if (ListBox()) + { + ListBox()->SetRect(Rect()); + } + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::EditCurrentItemL() +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::EditCurrentItemL() + { + // invoke EditItemL on the current item + + TInt index = ListBox()->CurrentItemIndex(); + EditItemL(index,ETrue); // invoked from menu + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::EditItemL (TInt aIndex, TBool aCalledFromMenu) +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::EditItemL (TInt aIndex, TBool aCalledFromMenu) + { + if (aIndex == EAccessPointIndex) + { + EditAccessPointL(); + } + else + { + TInt cflags = (*SettingItemArray())[aIndex]->SettingPageFlags(); + // allow user to exit address field without typing anything, + // if he e.g. realizes that he does not remember the address + if ((aIndex == EUserIDIndex) || (aIndex == EServerAddressIndex)) + { + cflags |= CAknTextSettingPage::EZeroLengthAllowed; + } + else + { + //coverity[logical_vs_bitwise] + cflags &= (!CAknTextSettingPage::EZeroLengthAllowed); + } + (*SettingItemArray())[aIndex]->SetSettingPageFlags(cflags); + CAknSettingItemList::EditItemL(aIndex, aCalledFromMenu); + (*SettingItemArray())[aIndex]->StoreL(); + } + SaveSettingL(aIndex); + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::SaveSettingL(TInt aIndex) +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::SaveSettingL(TInt aIndex) + { + + switch (aIndex) + { + case ESettingNameIndex: + SetTitlePaneTextL(iSettingsData.iSettingName); + break; + case EServerAddressIndex: + break; + + case EAccessPointIndex: + if (iSettingsData.iAccessPoint > -1) // if Valid AP number + { + (iSettingsData.iAccessPointDes).Num(iSettingsData.iAccessPoint); + GetAccessPointNameL(iSettingsData.iAccessPoint, + iSettingsData.iAccessPointName); + } + break; + case EUserIDIndex: + break; + + case EPasswordIndex: + break; + + default: + break; + } + LoadSettingsL(); + DrawNow(); + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::CreateSettingItemL (TInt aIdentifier) +// ----------------------------------------------------------------------------- +// +CAknSettingItem * CRsfwGsPluginSettingsList::CreateSettingItemL (TInt aIdentifier) + { + // method is used to create specific setting item as required at run-time. + // aIdentifier is used to determine what kind of setting item should be + // created + + CAknSettingItem* settingItem = NULL; + + switch (aIdentifier) + { + case ESettingItemDriveName: + settingItem = new (ELeave) CAknTextSettingItem ( aIdentifier, + iSettingsData.iSettingName); + break; + case ESettingItemURL: + settingItem = new (ELeave) CAknTextSettingItem ( + aIdentifier, + iSettingsData.iURL); + break; + + case ESettingItemAccessPoint: + GetAccessPointNameL(iSettingsData.iAccessPoint, iSettingsData.iAccessPointName); + settingItem = new (ELeave) CAknTextSettingItem ( + aIdentifier, iSettingsData.iAccessPointName); + break; + + + + case ESettingItemUserID: + settingItem = new (ELeave) CAknTextSettingItem ( + aIdentifier, + iSettingsData.iUserID); + settingItem->SetEmptyItemTextL(KNullDesC); + settingItem->LoadL(); + break; + case ESettingItemPassword: + settingItem = new (ELeave) CAknPasswordSettingItem ( + aIdentifier, + CAknPasswordSettingItem::EAlpha, + iSettingsData.iPassword); + break; + default: + break; + } + return settingItem; + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::EditAccessPoint() +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::EditAccessPointL() + { + + CCommsDatabase* commsDb = CCommsDatabase::NewL( EDatabaseTypeIAP ); + CleanupStack::PushL(commsDb); + CApUtils* aPUtils = CApUtils::NewLC( *commsDb ); + + TUint32 id = 0; + TRAP_IGNORE(id = aPUtils->WapIdFromIapIdL(iSettingsData.iAccessPoint)); + + CConnectionUiUtilities* connUiUtils = + CConnectionUiUtilities::NewL(); + CleanupStack::PushL( connUiUtils ); + + TCuuAlwaysAskResults result; + // determine how radio button will be initially displayed to the user + // (depending on what is the current IAP choice) + iSettingsData.iAccessPoint < 0 ? result = ECuuAlwaysAsk : result = ECuuUserDefined; + + if (connUiUtils->AlwaysAskPageL(result)) + { + if (result == ECuuUserDefined) + { + +#if defined __WINS__ + // In wins emulator mode we need to show emulator-lan access point so we + // different technique + TConnectionPrefs prefs; + + User::LeaveIfError(iDlgSrv.Connect()); + + prefs.iRank = 1; + prefs.iDirection = ECommDbConnectionDirectionOutgoing; + prefs.iBearerSet = ECommDbBearerCSD | ECommDbBearerWcdma | ECommDbBearerVirtual; + + TUint32 id = iSettingsData.iAccessPoint; + + TRAPD( err, iDlgSrv.IapConnection( id, prefs, iStatus ) ); + User::LeaveIfError( err ); + + User::WaitForRequest( iStatus ); + iSettingsData.iAccessPoint = id; + iDlgSrv.Close(); + +#else + CApSettingsHandler *ApUi = CApSettingsHandler::NewLC( + ETrue, + EApSettingsSelListIsPopUp, + EApSettingsSelMenuSelectNormal, + KEApIspTypeAll, + EApBearerTypeAllBearers, + KEApSortNameAscending, + EIPv4 | EIPv6 + ); + ApUi->RunSettingsL( id, id ); + CleanupStack::PopAndDestroy(ApUi); + iSettingsData.iAccessPoint = aPUtils->IapIdFromWapIdL(id); +#endif + } + else if (result == ECuuAlwaysAsk) + { + iSettingsData.iAccessPoint = -1; + iSettingsData.iAccessPointDes = KNullDesC; + iSettingsData.iAccessPointName = KNullDesC; + } + } + + + CleanupStack::PopAndDestroy(3); //commsDb, aPUtils, CConnectionUtilities + + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::GetAccessPointNameL(TInt32 aAP, TDes& aAccessPoint) +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::GetAccessPointNameL(TInt32 aAP, TDes& aAccessPoint) + { + // Fetch CommDB data for a matching IAP Id or IAP Name + CCommsDatabase* commsDb = CCommsDatabase::NewL(); + CleanupStack::PushL(commsDb); + CCommsDbTableView* table; + table = commsDb->OpenViewMatchingUintLC(TPtrC(IAP), + TPtrC(COMMDB_ID), + aAP); + + TInt err = table->GotoFirstRecord(); + if (err != KErrNone) + { + CleanupStack::PopAndDestroy(2, commsDb); // table, commsDb + return; + } + + // Read name for IAP information + table->ReadTextL(TPtrC(COMMDB_NAME), aAccessPoint); + CleanupStack::PopAndDestroy(2, commsDb); // table, commsDb + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::SetTitlePaneTextL( const TDesC& aTitleText ) const +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::SetTitlePaneTextL( const TDesC& aTitleText ) const + { + DEBUGSTRING(("CRsfwGsPluginSettingsList::SetTitlePaneTextL")); + CAknTitlePane* title = static_cast< CAknTitlePane* > + ( iEikonEnv->AppUiFactory()->StatusPane()->ControlL( + TUid::Uid( EEikStatusPaneUidTitle ) ) ); + if ( !title ) + { + User::Leave( KErrNotSupported ); + } + + title->SetTextL( aTitleText ); + } + +// ----------------------------------------------------------------------------- +// CRsfwGsPluginSettingsList::ResetItemIndex() +// ----------------------------------------------------------------------------- +// +void CRsfwGsPluginSettingsList::ResetItemIndex() + { + ListBox()->SetCurrentItemIndex(NULL); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgspropertywatch.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgspropertywatch.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,108 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RsfwPlugin Implementation +* +*/ + + +#include +#include + +#include "rsfwgspropertywatch.h" +//#include "rsfwgsplugin.hrh" +#include "rsfwgsplugindrivelistcontainer.h" +#include "rsfwcommon.h" + + +CRsfwGsPropertyWatch* CRsfwGsPropertyWatch::NewL(CRsfwGsPluginDriveListContainer* aContainer) + { + CRsfwGsPropertyWatch* me=new(ELeave) CRsfwGsPropertyWatch; + CleanupStack::PushL(me); + me->ConstructL(aContainer); + CleanupStack::Pop(me); + return me; + } + +CRsfwGsPropertyWatch::CRsfwGsPropertyWatch() + :CActive(EPriority) + {} + +void CRsfwGsPropertyWatch::ConstructL(CRsfwGsPluginDriveListContainer* aContainer) + { + iContainer = aContainer; + User::LeaveIfError(iProperty.Attach(KRfeServerSecureUid, ERsfwPSKeyConnect)); + CActiveScheduler::Add(this); + iProperty.Subscribe(iStatus); + SetActive(); + } + +CRsfwGsPropertyWatch::~CRsfwGsPropertyWatch() + { + Cancel(); + iProperty.Close(); + } + +void CRsfwGsPropertyWatch::DoCancel() +{ + iProperty.Cancel(); +} + +void CRsfwGsPropertyWatch::RunL() +{ + // resubscribe before processing new value to prevent missing updates + iProperty.Subscribe(iStatus); + SetActive(); + if ((iProperty.Get(KRfeServerSecureUid, ERsfwPSKeyConnect, iDriveList) == KErrNone) && + // if the key is defined but not written to, the length of the list is zero + (iDriveList.Length() == KMaxDrives)) + { + TDriveList fsDriveList; + RFs fs; + User::LeaveIfError(fs.Connect()); + CleanupClosePushL(fs); + fs.DriveList(fsDriveList, KDriveAttRemote); + TInt drive = EDriveY; + while (drive >=0) { + if (fsDriveList[drive] && (fsDriveList[drive] & KDriveAttRemote)) { + // get the friendly name for this drive + TChar driveChar; + fs.DriveToChar(drive, driveChar); + const CRsfwMountEntry* mountEntry; + mountEntry = iContainer->iMountMan->MountEntryL(driveChar); + if (!mountEntry) + { + User::Leave(KErrNotFound); + } + const HBufC* mountName; + mountName= mountEntry->Item(EMountEntryItemName); + if (!mountName) + { + User::Leave(KErrNotFound); + } + if (iDriveList[drive] == 0) + { + iContainer->SetDriveConnectedStateL(*mountName, EFalse); + } + else if (iDriveList[drive] == 1) + { + iContainer->SetDriveConnectedStateL(*mountName, ETrue); + } + } + drive--; + } + CleanupStack::PopAndDestroy(); // fs + } +} + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgsremotedrivesend.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgsremotedrivesend.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,298 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Sending remote drive configuration entries +* +*/ + + +#include +#include +#include +#include +#include +#include // for CnvUtfConverter +#include +#include +#include +#include +#include + +#include "rsfwgsremotedrivesend.h" +#include "rsfwmountutils.h" +#include "rsfwgsplugin.hrh" + + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::NewL +// Static constructor +// (other items were commented in a header). +// --------------------------------------------------------- +// +CRsfwGsRemoteDriveSend* CRsfwGsRemoteDriveSend::NewL(TInt aMenuCommandId) + { + CRsfwGsRemoteDriveSend* self = new (ELeave) CRsfwGsRemoteDriveSend(); + CleanupStack::PushL(self); + self->ConstructL(aMenuCommandId); + CleanupStack::Pop(self); + return self; + } + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::CRsfwGsRemoteDriveSend +// C++ constructor +// (other items were commented in a header). +// --------------------------------------------------------- +// +CRsfwGsRemoteDriveSend::CRsfwGsRemoteDriveSend() + { + } + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::ConstructL +// 2nd phase constructor +// (other items were commented in a header). +// --------------------------------------------------------- +// +void CRsfwGsRemoteDriveSend::ConstructL(TInt aMenuCommandId) + { + iSendUi = CSendUi::NewL(); + iSendAsCmdId=aMenuCommandId; + iSendMtmsToDim = new (ELeave) CArrayFixFlat(4); + + // for the time being, dim everything else but SMS + // for some reason technology-group UIDs do not seem to work + // e-mail Mtmss + iSendMtmsToDim->AppendL(KSenduiMtmSmtpUid); + iSendMtmsToDim->AppendL(KSenduiMtmImap4Uid); + iSendMtmsToDim->AppendL(KSenduiMtmPop3Uid); + + // MMS, BT, Irda, Postcard + iSendMtmsToDim->AppendL(KSenduiMtmMmsUid); + iSendMtmsToDim->AppendL(KSenduiMtmPostcardUid); + iSendMtmsToDim->AppendL(KSenduiMtmBtUid); + iSendMtmsToDim->AppendL(KSenduiMtmIrUid); + + // Audio Message + iSendMtmsToDim->AppendL(KSenduiMtmAudioMessageUid); + + iSendMtmsToDim->AppendL(KSenduiMtmSyncMLEmailUid ); + + // filters out EMail Via Exchange, as we only support SMS + // for some reason this cannot be found from headers currently + const TUid KEmailViaExchange = { 0x102826F8 }; + iSendMtmsToDim->AppendL(KEmailViaExchange ); + + } + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::~CRsfwGsRemoteDriveSend +// Destructor +// (other items were commented in a header). +// --------------------------------------------------------- +// +CRsfwGsRemoteDriveSend::~CRsfwGsRemoteDriveSend() + { + delete iSendUi; + delete iSendMtmsToDim; + } + + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::CanSendL +// Check wheter sending is possible +// (other items were commented in a header). +// --------------------------------------------------------- +// +TBool CRsfwGsRemoteDriveSend::CanSend() + { + if( iSelectedMtmUid != KNullUid ) + { + return ETrue; + } + else + { + return EFalse; + } + } + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::DisplaySendMenuItemL +// Show sendui menu +// (other items were commented in a header). +// --------------------------------------------------------- +// +void CRsfwGsRemoteDriveSend::DisplaySendMenuItemL(CEikMenuPane& aMenuPane, + TInt aIndex) + { + iSendUi->AddSendMenuItemL( aMenuPane, aIndex, iSendAsCmdId, TSendingCapabilities() ); + } + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::DisplaySendCascadeMenuL +// Show send quesry / cascaded menu +// (other items were commented in a header). +// --------------------------------------------------------- +// +void CRsfwGsRemoteDriveSend::DisplaySendCascadeMenuL() + { + iSelectedMtmUid = iSendUi->ShowSendQueryL( NULL, KCapabilitiesForAllServices, iSendMtmsToDim, KNullDesC ); + } + + + +// --------------------------------------------------------- +// CRsfwGsRemoteDriveSend::SendL +// Send a remote drive entry via SendUi +// (other items were commented in a header). +// --------------------------------------------------------- +// +void CRsfwGsRemoteDriveSend::SendL(const CRsfwMountEntry& anEntry) + { + + // the old entry can be deleted in the middle of the operation + // e.g. from the File Manager + CRsfwMountEntry* entryToBeSent = anEntry.CloneL(); + CleanupStack::PushL(entryToBeSent); + + CEikonEnv* eikonEnv = CEikonEnv::Static(); + CRichText* text = CRichText::NewL( + eikonEnv->SystemParaFormatLayerL(), + eikonEnv->SystemCharFormatLayerL()); + CleanupStack::PushL(text); + + + // if user name has been set + // ask user whether he would like to send the login credentials + TBool sendCredentials = EFalse; + if ((entryToBeSent->Item(EMountEntryItemUserName))->Length() > 0) + { + HBufC* myDisplayMessage = NULL; + myDisplayMessage = StringLoader::LoadLC(R_STR_RSFW_SEND_CREDENTIALS_QUERY); + CAknQueryDialog* query = CAknQueryDialog::NewL + (CAknQueryDialog::EConfirmationTone); + sendCredentials = + query->ExecuteLD( R_CONFIRMATION_QUERY, *myDisplayMessage); + CleanupStack::PopAndDestroy(myDisplayMessage); + } + + + // Encode configuration entry + HBufC* vcal = HBufC::NewLC(KMaxMountConfLength); + TPtr p = vcal->Des(); + RsfwMountUtils::ExportMountEntryL(*entryToBeSent, sendCredentials, p); + + // convert to 8-bit + // note that safe conversion is needed both when sending + // as an attachement and when sending as message text + HBufC8* temp = ConvertToUtf7LC(p); + + TUid mtmUid = iSelectedMtmUid; + TSendingCapabilities capabilities; + iSendUi->ServiceCapabilitiesL( mtmUid, capabilities ); + if (capabilities.iFlags & TSendingCapabilities::ESupportsAttachments) + { + // send as Attachment + RFs fs; + User::LeaveIfError( fs.Connect() ); + CleanupClosePushL( fs ); + // must share the handle between processes + User::LeaveIfError( fs.ShareProtected() ); + TInt err = fs.MkDirAll(KRemoteDriveAttachmentFilename); + RFile file; + err = file.Replace(fs,KRemoteDriveAttachmentFilename,EFileWrite | EFileShareAny ); + CleanupClosePushL(file); + TInt spaceNeeded = vcal->Size(); + if ( SysUtil::FFSSpaceBelowCriticalLevelL( &fs, spaceNeeded ) ) + { + // don't show any own notes here + User::Leave( KErrDiskFull ); + } + + User::LeaveIfError(file.Write(*temp)); + + TParse parse; + User::LeaveIfError(parse.SetNoWild(KRemoteDriveAttachmentFilename, + NULL, NULL)); + + CMessageData* messageData = CMessageData::NewL(); + CleanupStack::PushL( messageData ); + messageData->AppendAttachmentHandleL(file); + iSendUi->CreateAndSendMessageL( iSelectedMtmUid, messageData, KUidBIOMountConfMsg, ETrue ); + + CleanupStack::PopAndDestroy( 2 ); // messageData, file + fs.Delete(parse.FullName()); + CleanupStack::PopAndDestroy( &fs );; + } + else + { + // send as message body + // message data interface is 16-bit + // however, along the way 8-bit interface is used + // to pass the data without safe conversion + // so the unicode conversion above is still needed + HBufC* bufCnv = HBufC::NewLC(temp->Length()); + TPtr16 des(bufCnv->Des()); + des.Copy(p); + text->InsertL(0, des); + + CMessageData* messageData = CMessageData::NewL(); + CleanupStack::PushL( messageData ); + messageData->SetBodyTextL( text ); + iSendUi->CreateAndSendMessageL( iSelectedMtmUid, messageData, KUidBIOMountConfMsg, ETrue ); + CleanupStack::PopAndDestroy(2); // messageData, bufCnv + } + + CleanupStack::PopAndDestroy(4); // entryToBeSent, text, vcal, temp + + } + +// ------------------------------------------------------------------------------------------------ +// HBufC* CRsfwGsRemoteDriveSend::ConvertToUtf7LC +// Encodes from Unicode UCS-2 to UTF-8 +// ------------------------------------------------------------------------------------------------ +HBufC8* CRsfwGsRemoteDriveSend::ConvertToUtf7LC(const TDesC16& aText) + { + TPtrC16 remainder( aText ); + TBuf8<20> utfBuffer; + HBufC8 *ret = 0; + CBufFlat *buffer = CBufFlat::NewL( 128 ); + CleanupStack::PushL( buffer ); + + TBool finish = EFalse; + while( !finish ) + { + utfBuffer.Zero(); + TInt unconverted = CnvUtfConverter::ConvertFromUnicodeToUtf7(utfBuffer, remainder, EFalse ); + if( unconverted >= 0 ) + { + remainder.Set( remainder.Right( unconverted ) ); + buffer->InsertL( buffer->Size(), utfBuffer ); + finish = (unconverted == 0); + } + else + { + User::Leave( unconverted ); + } + } + + buffer->Compress(); + ret = buffer->Ptr( 0 ).Alloc(); + CleanupStack::PopAndDestroy( buffer ); + CleanupStack::PushL( ret ); + return ret; + } + + + +// end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgsremotedrivesettingscontainer.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgsremotedrivesettingscontainer.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,757 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin Settins list container +* +*/ + + +// INCLUDE FILES +#include +#include +#include +#include +#include +#include +#include + +#include "rsfwgslocalviewids.h" +#include "rsfwgsplugin.h" +#include "rsfwgsremotedrivesettingscontainer.h" +#include "rsfwgspluginsettinglist.h" +#include "rsfwgssettingsdata.h" +#include "rsfwmountman.h" +#include "rsfwmountentry.h" +#include "rsfwmountutils.h" +#include "rsfwcommon.h" +#include "mdebug.h" + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::CRsfwGsPluginDriveSettingsContainer() +// --------------------------------------------------------------------------- +// +CRsfwGsPluginDriveSettingsContainer::CRsfwGsPluginDriveSettingsContainer(CAknView* aView) : iView(aView) + { + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::ConstructL(const TRect& aRect) +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::ConstructL( const TRect& aRect, + CRsfwMountMan* aMountMan) + { + #ifdef _DEBUG + RDebug::Print( _L( "[CRsfwGsPluginDriveSettingsContainer] ConstructL()" ) ); + #endif + + iMountMan = aMountMan; + + CEikStatusPane* sp = static_cast + ( iEikonEnv->EikAppUi() )->StatusPane(); + CAknTitlePane* title = static_cast + ( sp->ControlL( TUid::Uid( EEikStatusPaneUidTitle ) ) ); + + // Set the proper title of this list + TResourceReader rReader; + iCoeEnv->CreateResourceReaderLC( rReader, R_GS_RSFW_REMOTE_DRIVE_SETTINGS_VIEW_TITLE ); + title->SetFromResourceL( rReader ); + CleanupStack::PopAndDestroy(); //rReader + + CreateWindowL(); // Makes the control a window-owning control + + // construct the data object the settings list will use + iData = CRsfwGsSettingsData::NewL(); + // construct control and set parent + iSettingList = CRsfwGsPluginSettingsList::NewL(*iData); + iSettingList->SetContainerWindowL(*this); + + // CreateResourceReaderLC will allocate a buffer to be used by + // the TResourceReader. This buffer is pushed onto the cleanup + // stack - not the TResourceReader itself + iEikonEnv->CreateResourceReaderLC(rReader, R_SETTINGS); + iSettingList->ConstructFromResourceL(rReader); + + // Clean up the buffer allocated above, NOT the reader itself. + // Cannot use expected item overload of PopAndDestroy() as buffer + // is inaccessible. + CleanupStack::PopAndDestroy(); + iSettingList->ActivateL(); + + iCoeEnv->AddForegroundObserverL( *this ); + + SetRect( aRect ); + ActivateL(); + + + #ifdef _DEBUG + RDebug::Print( _L( "[CRsfwGsPluginDriveSettingsContainer] Construct done" ) ); + #endif + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::~CRsfwGsPluginDriveSettingsContainer() +// --------------------------------------------------------------------------- +// +CRsfwGsPluginDriveSettingsContainer::~CRsfwGsPluginDriveSettingsContainer() + { + iCoeEnv->RemoveForegroundObserver( *this ); + if (iData) + delete iData; + if(iSettingList) // if setting list has been created + { + delete iSettingList; + iSettingList = NULL; + } + + // Ecom session is used to make sure that user gives address + // that corresponds to some installed access plugin + // (currently via mountils::isaddressvalid) + // this closes the session (if not in use anymore) + REComSession::FinalClose(); + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::SizeChanged() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::SizeChanged() + { + iSettingList->SetRect(Rect()); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::CountComponentControls() const +// --------------------------------------------------------------------------- +// +TInt CRsfwGsPluginDriveSettingsContainer::CountComponentControls() const + { + return 1; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::ComponentControl( TInt aIndex ) const +// --------------------------------------------------------------------------- +// +CCoeControl* CRsfwGsPluginDriveSettingsContainer::ComponentControl( TInt aIndex ) const + { + switch ( aIndex ) + { + case 0: + return iSettingList; + default: + return NULL; + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::EditCurrentItemL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::EditCurrentItemL() + { + iSettingList->EditCurrentItemL(); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::OfferKeyEventL() +// --------------------------------------------------------------------------- +// +TKeyResponse CRsfwGsPluginDriveSettingsContainer::OfferKeyEventL( + const TKeyEvent& aKeyEvent, + TEventCode aType ) + { + if (iSettingList) + return iSettingList->OfferKeyEventL(aKeyEvent, aType); + else + return EKeyWasNotConsumed; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::Draw(const TRect& aRect) const +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::Draw(const TRect& aRect) const + { + CWindowGc& gc = SystemGc(); + gc.Clear(aRect); + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::HandleListBoxEventL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::HandleListBoxEventL(CEikListBox* /*aListBox*/, TListBoxEvent aListBoxEvent) + { + // if the Select Key has been pressed + if ((aListBoxEvent == MEikListBoxObserver::EEventEnterKeyPressed) || + (aListBoxEvent == MEikListBoxObserver::EEventItemSingleClicked)) + { + iSettingList->EditCurrentItemL(); + } + } + + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::PrepareRemoteDriveForEditingL(TDesC& aRemoteDriveName) +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::PrepareRemoteDriveForEditingL(const TDesC& aRemoteDriveName) + { + DEBUGSTRING(("CRsfwGsPluginDriveSettingsContainer::PrepareRemoteDriveForEditingL enter")); + const CRsfwMountEntry* mountEntry = NULL; + + // read the source setting + DEBUGSTRING(("read the source setting")); + mountEntry = iMountMan->MountEntryL(aRemoteDriveName); + User::LeaveIfNull((TAny *)mountEntry); + + // compulsory fields + DEBUGSTRING(("compulsory fields")); + iData->Reset(); + iData->iSettingName = *(mountEntry->Item(EMountEntryItemName)); + iData->iURL =*(mountEntry->Item(EMountEntryItemUri)); + const HBufC* drive = (mountEntry->Item(EMountEntryItemDrive)); + if (drive && drive->Length()) + { + iData->iDriveLetter =(*drive)[0]; + } + // optional fields + DEBUGSTRING(("optional fields")); + if (mountEntry->Item(EMountEntryItemUserName)) + { + DEBUGSTRING(("setting user id")); + iData->iUserID = *(mountEntry->Item(EMountEntryItemUserName)); + } + + if (mountEntry->Item(EMountEntryItemPassword)) + { + DEBUGSTRING(("setting passwd")); + iData->iPassword = *(mountEntry->Item(EMountEntryItemPassword)); + } + + if (mountEntry->Item(EMountEntryItemIap)) + { + DEBUGSTRING16(("setting access pointDes to %S", (mountEntry->Item(EMountEntryItemIap)))); + iData->iAccessPointDes = *(mountEntry->Item(EMountEntryItemIap)); + // if the access point name returned from CenRep was '?', set it to "None" in UI + if (iData->iAccessPointDes == KIapAskUser) + { + iData->iAccessPointName = KNullDesC; + } + else + { + // try to resolve access point id into name + TLex lex(iData->iAccessPointDes); + TInt ap, err; + err = lex.Val(ap); + if (!err) + { + iSettingList->GetAccessPointNameL(ap, iData->iAccessPointName); + DEBUGSTRING(("setting access point")); + iData->iAccessPoint = ap; + } + else + { + DEBUGSTRING(("setting access point name")); + iData->iAccessPointName = KNullDesC; + } + } + } + + DEBUGSTRING(("iData constructed")); + iSettingList->LoadSettingsL(); + SetTitlePaneTextL(iData->iSettingName); + iSettingList->ResetItemIndex(); + DEBUGSTRING(("CRsfwGsPluginDriveSettingsContainer::PrepareRemoteDriveForEditingL exit")); + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::PrepareRemoteDriveNewDefaultL(TDesC& aRemoteDriveName); +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::PrepareRemoteDriveNewDefaultL(TDesC& aRemoteDriveName) + { + iData->Reset(); + iData->iSettingName = aRemoteDriveName; + iSettingList->LoadSettingsL(); + iSettingList->ResetItemIndex(); + iSettingList->DrawDeferred(); + SetTitlePaneTextL(iData->iSettingName); + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::SetTitlePaneTextL( const TDesC& aTitleText ) const +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::SetTitlePaneTextL( const TDesC& aTitleText ) const + { + CAknTitlePane* title = static_cast< CAknTitlePane* > + ( iEikonEnv->AppUiFactory()->StatusPane()->ControlL( + TUid::Uid( EEikStatusPaneUidTitle ) ) ); + if ( !title ) + { + User::Leave( KErrNotSupported ); + } + title->SetTextL( aTitleText ); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::AreCompulsoryItemsFilled() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::AreCompulsoryItemsFilled() + { + TUriParser uriParser; + uriParser.Parse(iData->iURL); + HBufC* host = HBufC::NewL(KMaxURLLength); + TPtr hostPtr = host->Des(); + hostPtr = uriParser.Extract(EUriHost); + + if ( ((iData->iSettingName)!=KNullDesC) && (hostPtr!=KNullDesC)) + { + delete host; + return ETrue; + } + delete host; + return EFalse; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::DisplayDeleteOrDontSaveDialog() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::DisplayDeleteOrDontSaveDialogL() + { + + HBufC* myDisplayMessage = NULL; + myDisplayMessage = StringLoader::LoadLC(R_STR_REMOTE_DRIVE_CONF_COMPULSORY); + CAknQueryDialog* query = CAknQueryDialog::NewL + (CAknQueryDialog::EConfirmationTone); + TBool answer = query->ExecuteLD( R_CONFIRMATION_QUERY, *myDisplayMessage ); + CleanupStack::PopAndDestroy(myDisplayMessage); + return answer; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::DeleteremoteDriveIfExistL() +// --------------------------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::DeleteRemoteDriveIfExistL() + { + iMountMan->DeleteMountEntryL(iData->iDriveLetter); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::IsExitProcessingOKL() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::IsExitProcessingOKL() + { + if (AreCompulsoryItemsFilled()) + { + if (!(RsfwMountUtils::IsFriendlyNameValid(iData->iSettingName))) + { + HBufC* myDisplayMessage = NULL; + myDisplayMessage = StringLoader::LoadLC(R_STR_RSFW_ERROR_ILLEGAL_CHARACTERS); + CAknErrorNote* errorNote = new CAknErrorNote(EFalse); + errorNote->ExecuteLD(*myDisplayMessage); + CleanupStack::PopAndDestroy(myDisplayMessage); + iSettingList->ListBox()->SetCurrentItemIndex(ESettingItemDriveName-1); + return EFalse; + } + + // Uri must contain some scheme, like http:// or upnp:// + if (!IsDriveAddressValidL(iData->iURL)) + { + HBufC* myDisplayMessage = NULL; + myDisplayMessage = StringLoader::LoadLC(R_STR_RSFW_ERROR_ILLEGAL_ADDRESS); + CAknNoteDialog* noteDlg = new ( ELeave ) CAknNoteDialog( ); + noteDlg->SetTextL( *myDisplayMessage ); + noteDlg->ExecuteLD( R_RSFW_INFORMATION_NOTE ); + CleanupStack::PopAndDestroy(myDisplayMessage); + iSettingList->ListBox()->SetCurrentItemIndex(ESettingItemURL-1); + return EFalse; + } + + // settings seem to be ok + return SaveOrCreateAndSaveRemoteDriveL(ETrue); + } + else + { + if (DisplayDeleteOrDontSaveDialogL()) + { + DeleteRemoteDriveIfExistL(); + } + else + { + // set focus on the address field as that is the first (and only) + // unfilled compulsary setting field + iSettingList->ListBox()->SetCurrentItemIndex(ESettingItemURL-1); + return EFalse; + } + } + + return ETrue; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::SaveSettingsL +// Attempts to save settings +// --------------------------------------------------------------------------- +void CRsfwGsPluginDriveSettingsContainer::SaveSettingsL() + { + if (AreCompulsoryItemsFilled()) + { + if (!(RsfwMountUtils::IsFriendlyNameValid(iData->iSettingName))) + { + return; + } + // Uri must contain some scheme, like http:// or upnp:// + if (!IsDriveAddressValidL(iData->iURL)) + { + return; + } + // settings seem to be ok + SaveOrCreateAndSaveRemoteDriveL(EFalse); + } + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::SaveOrCreateAndSaveremoteDriveL() +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::SaveOrCreateAndSaveRemoteDriveL(TBool aShowDialog) + { + // try to get mountentry with this drive letter + const CRsfwMountEntry* existingMountEntry = iMountMan->MountEntryL(iData->iDriveLetter); + + // to keep names unique check if the setting with this name is already exist + // ask user to change name + TBool isConflict; + if (existingMountEntry) + { + isConflict = IsRemoteDriveNameConflictL(iData->iSettingName, *(existingMountEntry->Item(EMountEntryItemDrive))); + } + else + { + TBuf<5> bogusDrive; + bogusDrive.Append(_L("C:\\")); + isConflict = IsRemoteDriveNameConflictL(iData->iSettingName, bogusDrive); + } + + if (isConflict) + { + if (aShowDialog) + { + HBufC* myFormatMessage = NULL; + if ( iData->iSettingName.Length() ) + { + myFormatMessage = StringLoader::LoadLC( R_STR_REMOTE_DRIVE_NAME_ALREADY_EXIST, iData->iSettingName); + } + else + { + myFormatMessage = StringLoader::LoadLC( R_STR_REMOTE_DRIVE_NAME_ALREADY_EXIST ); + } + + CAknErrorNote* note = new CAknErrorNote(EFalse); + note->SetTimeout( CAknNoteDialog::ELongTimeout ); + note->ExecuteLD( *myFormatMessage ); + CleanupStack::PopAndDestroy(myFormatMessage); + // set focus to drive + iSettingList->ListBox()->SetCurrentItemIndex(ESettingItemDriveName-1); + } + return EFalse; + } + else if (!existingMountEntry || DataChanged(existingMountEntry)) + { + + CRsfwMountEntry* newMountEntry = CRsfwMountEntry::NewLC(); + if (existingMountEntry) + { + // the same drive letter must be set as it is the key + newMountEntry->SetItemL(EMountEntryItemDrive, *(existingMountEntry->Item(EMountEntryItemDrive))); + } + + newMountEntry->SetItemL(EMountEntryItemName, iData->iSettingName); + newMountEntry->SetItemL(EMountEntryItemUri, iData->iURL); + if ((iData->iUserID)!=KNullDesC) + { + newMountEntry->SetItemL(EMountEntryItemUserName, iData->iUserID); + } + + if ((iData->iPassword)!=KNullDesC) + { + newMountEntry->SetItemL(EMountEntryItemPassword, iData->iPassword); + } + if ((iData->iAccessPointDes)!=KNullDesC) + { + newMountEntry->SetItemL(EMountEntryItemIap, iData->iAccessPointDes); + } + else + { + newMountEntry->SetItemL(EMountEntryItemIap, KIapAskUser); + } + + newMountEntry->SetItemL(EMountEntryItemInactivityTimeout, iData->iInActivityTimeout); + + // depending on whether this is new mount created or existing mount edited + // choose proper method from MountMan API + // pop here from the stack since ownership is passed to the mountman + CleanupStack::Pop(newMountEntry); + + if (!existingMountEntry) + { + iMountMan->AddMountEntryL(newMountEntry); + } + else + { + iMountMan->EditMountEntryL(newMountEntry); + } + } + return ETrue; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::DataChanged +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::DataChanged(const CRsfwMountEntry* aCurrentData) +{ + if (!aCurrentData) + { + return ETrue; + } + + // compulsary settings + if (iData->iSettingName != *(aCurrentData->Item(EMountEntryItemName))) + { + return ETrue; + } + if (iData->iURL != *(aCurrentData->Item(EMountEntryItemUri))) + { + return ETrue; + } + + // optional settings + if (!aCurrentData->Item(EMountEntryItemUserName)) + { + if (iData->iUserID != KNullDesC) + { + return ETrue; + } + } + else + { + if (iData->iUserID != *(aCurrentData->Item(EMountEntryItemUserName))) + { + return ETrue; + } + } + + if (!aCurrentData->Item(EMountEntryItemPassword)) + { + if (iData->iPassword != KNullDesC) + { + return ETrue; + } + } + else + { + if (iData->iPassword != *(aCurrentData->Item(EMountEntryItemPassword))) + { + return ETrue; + } + } + + if (!aCurrentData->Item(EMountEntryItemIap)) + { + if (iData->iAccessPointDes != KNullDesC) + { + return ETrue; + } + } + else + { + if (iData->iAccessPointDes != *(aCurrentData->Item(EMountEntryItemIap))) + { + return ETrue; + } + } + + + return EFalse; +} + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::IsRemoteDriveNameExistL(TDesC& aremoteDriveName) +// +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::IsRemoteDriveNameConflictL( + TDesC& aRemoteDriveName, + const TDesC& aDriveLetter) + { + TBool ret(EFalse); + CDesCArray* remoteDriveList = NULL; + + TRAPD(err, remoteDriveList = LoadRemoteDriveNamesL()); + if(err!=KErrNone) + { + return EFalse; + } + CleanupStack::PushL(remoteDriveList); + + TInt remoteDriveListCount = remoteDriveList->Count(); + for (TInt i = 0; i< remoteDriveListCount; i++) + { + if (!((remoteDriveList->MdcaPoint(i)).CompareF(aRemoteDriveName))) // if equal + { + // check whether the drive letter is the same or not + const CRsfwMountEntry* existingDrive = + iMountMan->MountEntryL(aRemoteDriveName); + if ((existingDrive->Item(EMountEntryItemDrive))->Compare(aDriveLetter) == 0 ) + { + ret = EFalse; + } + else + { + ret = ETrue; + } + break; + } + } + CleanupStack::PopAndDestroy(remoteDriveList); + return ret; + + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::IsDriveAddressValidL +// --------------------------------------------------------------------------- +// +TBool CRsfwGsPluginDriveSettingsContainer::IsDriveAddressValidL(const TDesC& aDriveAddress) + { + HBufC8* urlBuffer = HBufC8::NewL(KMaxURLLength); + TPtr8 bufPtr = urlBuffer->Des(); + bufPtr.Append(aDriveAddress); + TBool isAddressValid = RsfwMountUtils::IsDriveAddressValid(*urlBuffer); + delete urlBuffer; + return isAddressValid; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::LoadRemoteDriveNamesL +// --------------------------------------------------------------------------- +// +CDesCArray* CRsfwGsPluginDriveSettingsContainer::LoadRemoteDriveNamesL() + { + CDesCArray* myArray = new (ELeave) CDesC16ArraySeg(4); + iMountMan->GetMountNamesL(myArray); + return myArray; + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::HandleResourceChange() +// --------------------------------------------------------------------------- +void CRsfwGsPluginDriveSettingsContainer::HandleResourceChange( TInt aType ) + { + if ( aType == KAknsMessageSkinChange || + aType == KEikDynamicLayoutVariantSwitch ) + { + if (aType != KAknsMessageSkinChange) + { + TRect mainPaneRect; + AknLayoutUtils::LayoutMetricsRect( AknLayoutUtils::EMainPane, + mainPaneRect); + SetRect( mainPaneRect ); + } + + DrawDeferred(); + CRsfwGsPlugin* tempView = static_cast (iView); + tempView->HandleResourceChangeManual(aType); + } + CCoeControl::HandleResourceChange( aType ); + } + + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::HandleResourceChangeManual() +// --------------------------------------------------------------------------- +void CRsfwGsPluginDriveSettingsContainer::HandleResourceChangeManual(TInt aType) + { + if (aType != KAknsMessageSkinChange) + { + TRect mainPaneRect; + AknLayoutUtils::LayoutMetricsRect( AknLayoutUtils::EMainPane, + mainPaneRect); + SetRect( mainPaneRect ); + } + + DrawDeferred(); + iSettingList->HandleResourceChange(aType); + } + +// --------------------------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::FocusChanged +// Set focus on the selected listbox. For animated skins feature. +// --------------------------------------------------------------------------- +void CRsfwGsPluginDriveSettingsContainer::FocusChanged(TDrawNow /*aDrawNow*/) + { + if(iSettingList) + { + iSettingList->SetFocus( IsFocused() ); + } + } + +// --------------------------------------------------------- +// CRsfwGsPluginDriveSettingsContainer::GetHelpContext +// This function is called when Help application is launched +// --------------------------------------------------------- +// +void CRsfwGsPluginDriveSettingsContainer::GetHelpContext( TCoeHelpContext& aContext ) const + { + aContext.iMajor = KGSRsfwPluginUID; + // aContext.iContext = KRSFW_HLP_EDIT_SET; + } + + + TDes& CRsfwGsPluginDriveSettingsContainer::GetCurrentRemoteDriveName() + { + return iData->iSettingName; + } + + +// from MCoeForegroundObserver + +void CRsfwGsPluginDriveSettingsContainer::HandleGainingForeground() + { + + } + + +void CRsfwGsPluginDriveSettingsContainer::HandleLosingForeground() + { + + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/gsplugin/src/rsfwgssettingsdata.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/gsplugin/src/rsfwgssettingsdata.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,96 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw GS plugin data holding class for Rsfw setting list +* +*/ + + +// INCLUDE FILES +#include "rsfwgssettingsdata.h" + +_LIT(KDefaultAddress, "https://"); + +// ----------------------------------------------------------------------------- +// CRsfwGsSettingsData::NewL +// ----------------------------------------------------------------------------- +// +CRsfwGsSettingsData *CRsfwGsSettingsData::NewL() + { + CRsfwGsSettingsData *self = CRsfwGsSettingsData::NewLC(); + CleanupStack::Pop(self); + return self; + } + +// ----------------------------------------------------------------------------- +// CRsfwGsSettingsData::NewLC() +// ----------------------------------------------------------------------------- +// +CRsfwGsSettingsData *CRsfwGsSettingsData::NewLC() + { + CRsfwGsSettingsData *self = new (ELeave) CRsfwGsSettingsData(); + CleanupStack::PushL(self); + + self->ConstructL(); + + return self; + } + +// ----------------------------------------------------------------------------- +// CRsfwGsSettingsData::~CRsfwGsSettingsData() +// ----------------------------------------------------------------------------- +// +CRsfwGsSettingsData::~CRsfwGsSettingsData() + { + } + +// ----------------------------------------------------------------------------- +// CRsfwGsSettingsData::CRsfwGsSettingsData() +// ----------------------------------------------------------------------------- +// +CRsfwGsSettingsData::CRsfwGsSettingsData() + { + // initialise local data + Reset(); + } + +// ----------------------------------------------------------------------------- +// CRsfwGsSettingsData::ConstructL() +// ----------------------------------------------------------------------------- +// +void CRsfwGsSettingsData::ConstructL() + { + iURL = KNullDesC; + iURL.Copy(KDefaultAddress); + } + +// ----------------------------------------------------------------------------- +// CRsfwGsSettingsData::Reset() +// ----------------------------------------------------------------------------- +// +void CRsfwGsSettingsData::Reset() + { + iSettingName = KNullDesC; + iAccessPoint = KErrNotFound; + iAccessPointDes = KNullDesC; + iURL = KNullDesC; + iURL.Copy(KDefaultAddress); + iUserID= KNullDesC; + iPassword = KNullDesC; + iAccessPointName = KNullDesC; + iInActivityTimeout.Num(KDefaultInactivityTimeout); + iDriveLetter = 0; + } + +// End of File + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/bwins/rsfwmountmanu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/bwins/rsfwmountmanu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,30 @@ +EXPORTS + ??1CRsfwMountMan@@UAE@XZ @ 1 NONAME ; CRsfwMountMan::~CRsfwMountMan(void) + ?AddMountEntryL@CRsfwMountMan@@QAEXPAVCRsfwMountEntry@@@Z @ 2 NONAME ; void CRsfwMountMan::AddMountEntryL(class CRsfwMountEntry *) + ?DeleteMountEntryL@CRsfwMountMan@@QAEXABVTDesC16@@@Z @ 3 NONAME ; void CRsfwMountMan::DeleteMountEntryL(class TDesC16 const &) + ?DeleteMountEntryL@CRsfwMountMan@@QAEXVTChar@@@Z @ 4 NONAME ; void CRsfwMountMan::DeleteMountEntryL(class TChar) + ?EditMountEntryL@CRsfwMountMan@@QAEXPAVCRsfwMountEntry@@@Z @ 5 NONAME ; void CRsfwMountMan::EditMountEntryL(class CRsfwMountEntry *) + ?GetAllDrivesL@CRsfwMountMan@@QBEHAAV?$TBuf8@$0BK@@@@Z @ 6 NONAME ; int CRsfwMountMan::GetAllDrivesL(class TBuf8<26> &) const + ?GetMountInfo@CRsfwMountMan@@QBEHVTChar@@AAVTRsfwMountInfo@@@Z @ 7 NONAME ; int CRsfwMountMan::GetMountInfo(class TChar, class TRsfwMountInfo &) const + ?GetMountNamesL@CRsfwMountMan@@QBEXPAVCDesC16Array@@@Z @ 8 NONAME ; void CRsfwMountMan::GetMountNamesL(class CDesC16Array *) const + ?GetRemoteMountListL@CRsfwMountMan@@QBEHAAV?$TBuf8@$0BK@@@@Z @ 9 NONAME ; int CRsfwMountMan::GetRemoteMountListL(class TBuf8<26> &) const + ?IsAppOnBlackList@CRsfwMountMan@@QBEHVTUid@@@Z @ 10 NONAME ; int CRsfwMountMan::IsAppOnBlackList(class TUid) const + ?MountEntryL@CRsfwMountMan@@QBEPBVCRsfwMountEntry@@ABVTDesC16@@@Z @ 11 NONAME ; class CRsfwMountEntry const * CRsfwMountMan::MountEntryL(class TDesC16 const &) const + ?MountEntryL@CRsfwMountMan@@QBEPBVCRsfwMountEntry@@VTChar@@@Z @ 12 NONAME ; class CRsfwMountEntry const * CRsfwMountMan::MountEntryL(class TChar) const + ?NewL@CRsfwMountMan@@SAPAV1@IPAVMRsfwMountManObserver@@@Z @ 13 NONAME ; class CRsfwMountMan * CRsfwMountMan::NewL(unsigned int, class MRsfwMountManObserver *) + ?RefreshDirectory@CRsfwMountMan@@QAEHABVTDesC16@@@Z @ 14 NONAME ; int CRsfwMountMan::RefreshDirectory(class TDesC16 const &) + ?SetMountConnectionState@CRsfwMountMan@@QAEHVTChar@@I@Z @ 15 NONAME ; int CRsfwMountMan::SetMountConnectionState(class TChar, unsigned int) + ?CancelRemoteTransfer@CRsfwMountMan@@QAEHABVTDesC16@@@Z @ 16 NONAME ; int CRsfwMountMan::CancelRemoteTransfer(class TDesC16 const &) + ?ExternalizeL@TRsfwMountConfig@@QBEXAAVRWriteStream@@@Z @ 17 NONAME ; void TRsfwMountConfig::ExternalizeL(class RWriteStream &) const + ?InternalizeL@TRsfwMountConfig@@QAEXAAVRReadStream@@@Z @ 18 NONAME ; void TRsfwMountConfig::InternalizeL(class RReadStream &) + ??1CRsfwMountEntry@@UAE@XZ @ 19 NONAME ; CRsfwMountEntry::~CRsfwMountEntry(void) + ?Clear@CRsfwMountEntry@@QAEXXZ @ 20 NONAME ; void CRsfwMountEntry::Clear(void) + ?CloneL@CRsfwMountEntry@@QBEPAV1@XZ @ 21 NONAME ; class CRsfwMountEntry * CRsfwMountEntry::CloneL(void) const + ?Item@CRsfwMountEntry@@QBEPBVHBufC16@@H@Z @ 22 NONAME ; class HBufC16 const * CRsfwMountEntry::Item(int) const + ?NewL@CRsfwMountEntry@@SAPAV1@XZ @ 23 NONAME ; class CRsfwMountEntry * CRsfwMountEntry::NewL(void) + ?NewLC@CRsfwMountEntry@@SAPAV1@XZ @ 24 NONAME ; class CRsfwMountEntry * CRsfwMountEntry::NewLC(void) + ?SetEntryL@CRsfwMountEntry@@QAEXHABVTDesC16@@VTChar@@0000@Z @ 25 NONAME ; void CRsfwMountEntry::SetEntryL(int, class TDesC16 const &, class TChar, class TDesC16 const &, class TDesC16 const &, class TDesC16 const &, class TDesC16 const &) + ?SetItemL@CRsfwMountEntry@@QAEXHABVTDesC16@@@Z @ 26 NONAME ; void CRsfwMountEntry::SetItemL(int, class TDesC16 const &) + ?SetItemL@CRsfwMountEntry@@QAEXHABVTDesC8@@@Z @ 27 NONAME ; void CRsfwMountEntry::SetItemL(int, class TDesC8 const &) + ?SetMountConnectionStateBlind@CRsfwMountMan@@QAEHVTChar@@I@Z @ 28 NONAME ; int CRsfwMountMan::SetMountConnectionStateBlind(class TChar, unsigned int) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/bwins/rsfwmountutilsu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/bwins/rsfwmountutilsu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,7 @@ +EXPORTS + ?ExportMountEntryL@RsfwMountUtils@@SAXABVCRsfwMountEntry@@HAAVTDes16@@@Z @ 1 NONAME ; void RsfwMountUtils::ExportMountEntryL(class CRsfwMountEntry const &, int, class TDes16 &) + ?ImportMountEntryFromStreamL@RsfwMountUtils@@SAXAAVRReadStream@@HPAPAVCRsfwMountEntry@@@Z @ 2 NONAME ; void RsfwMountUtils::ImportMountEntryFromStreamL(class RReadStream &, int, class CRsfwMountEntry * *) + ?ImportMountEntryL@RsfwMountUtils@@SAXABVTDesC16@@PAPAVCRsfwMountEntry@@@Z @ 3 NONAME ; void RsfwMountUtils::ImportMountEntryL(class TDesC16 const &, class CRsfwMountEntry * *) + ?IsDriveAddressValid@RsfwMountUtils@@SAHABVTDesC8@@@Z @ 4 NONAME ; int RsfwMountUtils::IsDriveAddressValid(class TDesC8 const &) + ?IsFriendlyNameValid@RsfwMountUtils@@SAHABVTDesC16@@@Z @ 5 NONAME ; int RsfwMountUtils::IsFriendlyNameValid(class TDesC16 const &) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/eabi/rsfwmountmanu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/eabi/rsfwmountmanu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,40 @@ +EXPORTS + _ZN13CRsfwMountMan14AddMountEntryLEP15CRsfwMountEntry @ 1 NONAME + _ZN13CRsfwMountMan15EditMountEntryLEP15CRsfwMountEntry @ 2 NONAME + _ZN13CRsfwMountMan16RefreshDirectoryERK7TDesC16 @ 3 NONAME + _ZN13CRsfwMountMan17DeleteMountEntryLE5TChar @ 4 NONAME + _ZN13CRsfwMountMan17DeleteMountEntryLERK7TDesC16 @ 5 NONAME + _ZN13CRsfwMountMan23SetMountConnectionStateE5TCharj @ 6 NONAME + _ZN13CRsfwMountMan4NewLEjP21MRsfwMountManObserver @ 7 NONAME + _ZN13CRsfwMountManD0Ev @ 8 NONAME + _ZN13CRsfwMountManD1Ev @ 9 NONAME + _ZN13CRsfwMountManD2Ev @ 10 NONAME + _ZNK13CRsfwMountMan11MountEntryLE5TChar @ 11 NONAME + _ZNK13CRsfwMountMan11MountEntryLERK7TDesC16 @ 12 NONAME + _ZNK13CRsfwMountMan12GetMountInfoE5TCharR14TRsfwMountInfo @ 13 NONAME + _ZNK13CRsfwMountMan13GetAllDrivesLER5TBuf8ILi26EE @ 14 NONAME + _ZNK13CRsfwMountMan14GetMountNamesLEP12CDesC16Array @ 15 NONAME + _ZNK13CRsfwMountMan16IsAppOnBlackListE4TUid @ 16 NONAME + _ZNK13CRsfwMountMan19GetRemoteMountListLER5TBuf8ILi26EE @ 17 NONAME + _ZTI13CRsfwMountMan @ 18 NONAME ; ## + _ZTI17CRsfwMountManImpl @ 19 NONAME ; ## + _ZTV13CRsfwMountMan @ 20 NONAME ; ## + _ZTV17CRsfwMountManImpl @ 21 NONAME ; ## + _ZN13CRsfwMountMan20CancelRemoteTransferERK7TDesC16 @ 22 NONAME + _ZN16TRsfwMountConfig12InternalizeLER11RReadStream @ 23 NONAME + _ZNK16TRsfwMountConfig12ExternalizeLER12RWriteStream @ 24 NONAME + _ZN15CRsfwMountEntry4NewLEv @ 25 NONAME + _ZN15CRsfwMountEntry5ClearEv @ 26 NONAME + _ZN15CRsfwMountEntry5NewLCEv @ 27 NONAME + _ZN15CRsfwMountEntry8SetItemLEiRK6TDesC8 @ 28 NONAME + _ZN15CRsfwMountEntry8SetItemLEiRK7TDesC16 @ 29 NONAME + _ZN15CRsfwMountEntry9SetEntryLEiRK7TDesC165TCharS2_S2_S2_S2_ @ 30 NONAME + _ZN15CRsfwMountEntryD0Ev @ 31 NONAME + _ZN15CRsfwMountEntryD1Ev @ 32 NONAME + _ZN15CRsfwMountEntryD2Ev @ 33 NONAME + _ZNK15CRsfwMountEntry4ItemEi @ 34 NONAME + _ZNK15CRsfwMountEntry6CloneLEv @ 35 NONAME + _ZTI15CRsfwMountEntry @ 36 NONAME ; ## + _ZTV15CRsfwMountEntry @ 37 NONAME ; ## + _ZN13CRsfwMountMan28SetMountConnectionStateBlindE5TCharj @ 38 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/eabi/rsfwmountutilsu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/eabi/rsfwmountutilsu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,7 @@ +EXPORTS + _ZN14RsfwMountUtils17ExportMountEntryLERK15CRsfwMountEntryiR6TDes16 @ 1 NONAME + _ZN14RsfwMountUtils17ImportMountEntryLERK7TDesC16PP15CRsfwMountEntry @ 2 NONAME + _ZN14RsfwMountUtils19IsDriveAddressValidERK6TDesC8 @ 3 NONAME + _ZN14RsfwMountUtils19IsFriendlyNameValidERK7TDesC16 @ 4 NONAME + _ZN14RsfwMountUtils27ImportMountEntryFromStreamLER11RReadStreamiPP15CRsfwMountEntry @ 5 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,28 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build information file for project MountMan API +* +*/ + +#include + +PRJ_EXPORTS +../inc/rsfwmountutils.h |../../inc/rsfwmountutils.h + +PRJ_MMPFILES +rsfwmountutils.mmp +rsfwbootmounter.mmp +rsfwmountman.mmp + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/group/rsfwbootmounter.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/group/rsfwbootmounter.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,38 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project bootmounter +* +*/ + + +#include + +TARGET rsfwbootmounter.exe +TARGETTYPE exe +UID 0x101F970F +SECUREID 0x101F970F + +CAPABILITY DISKADMIN ReadDeviceData + +SOURCEPATH ../src +SOURCE rsfwbootmounter.cpp + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY euser.lib +LIBRARY efsrv.lib +LIBRARY centralrepository.lib \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/group/rsfwmountman.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/group/rsfwmountman.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,50 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project MountMan API +* +*/ + +#include +TARGET rsfwmountman.dll + +TARGETTYPE dll + +UID 0x1000008d 0x101F976F + +CAPABILITY CAP_GENERAL_DLL + +SOURCEPATH ../src + +SOURCE rsfwmountman.cpp +SOURCE rsfwmountmanimpl.cpp +SOURCE rsfwmountentry.cpp + +LANG SC + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY efsrv.lib +LIBRARY euser.lib +LIBRARY bafl.lib +LIBRARY estor.lib +LIBRARY rsfwmountstore.lib +LIBRARY rsfwmountutils.lib +LIBRARY rsfwcontrol.lib + +DEFFILE rsfwmountman.def + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/group/rsfwmountutils.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/group/rsfwmountutils.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,52 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project specification for MountUtils +* +*/ + + +#include + +TARGET rsfwmountutils.dll + +TARGETTYPE dll + +UID 0x1000008d 0x101F9774 + +CAPABILITY CAP_GENERAL_DLL + + +SOURCEPATH ../src + +SOURCE rsfwmountutils.cpp + +LANG SC + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY efsrv.lib +LIBRARY estor.lib +LIBRARY euser.lib +LIBRARY ecom.lib +LIBRARY inetprotutil.lib +LIBRARY rsfwmountman.lib +LIBRARY charconv.lib // for CnvUtfConverter + + +DEFFILE rsfwmountutils.def + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/inc/mydebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/inc/mydebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,31 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug printing to a log file + * +*/ + + +#ifndef MYDEBUG_H +#define MYDEBUG_H + +// Debug defines for MountMan: + +#define APPEND_TO_DEBUG_FILE + +_LIT(KDebugDirName, "mountman"); +_LIT(KDebugFileName, "mountman.txt"); + +#endif // MYDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/inc/rsfwmountmanimpl.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/inc/rsfwmountmanimpl.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,144 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mount manager + * +*/ + + +#ifndef CRSFWMOUNTMANIMPL_H +#define CRSFWMOUNTMANIMPL_H + + +// INCLUDES +#include "rsfwmountstore.h" +#include "rsfwcontrol.h" + +// FORWARD DECLARATIONS +class MRsfwMountManObserver; + +// CLASS DECLARATION +/** + * Class for implementing mount management of remote file repositories + * + * @lib mountman.dll + * @since Series 60 3.1 + */ + +class CRsfwMountManImpl : public CBase, public MRsfwMountStoreObserver + { +public: // Constructors and destructor + /** + * Two-phased constructor. + * + * @param aDefaultFlags must be set to KMountFlagInteractive + * if the user is to be prompted during the mount procedure. + * Otherwise the parameter can be omitted (defaults to zero) + * @param mount event observer + * @return pointer to the created CRsfwMountManImpl object instance + */ + static CRsfwMountManImpl* NewL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver); + + /** + * Destructor. + */ + virtual ~CRsfwMountManImpl(); + +public: // New functions + // Methods that implement the mount management functions + // See MountMan.h for documentation + void GetMountNamesL(CDesC16Array* aNames); + + const CRsfwMountEntry* MountEntryL(const TDesC& aName); + + const CRsfwMountEntry* MountEntryL(TChar aDriveLetter); + + void AddMountEntryL(CRsfwMountEntry* aMountEntry); + + void DeleteMountEntryL(const TDesC& aName); + + void DeleteMountEntryL(TChar aDriveLetter); + + void EditMountEntryL(CRsfwMountEntry* aMountEntry); + + void MountL(TChar& aDriveLetter); + void MountBlindL(TChar& aDriveLetter); + + TInt GetAllDrivesL(TDriveList& aDriveList); + + TInt GetRemoteMountListL(TDriveList& aDriveList); + + TInt GetMountInfo(TChar aDriveLetter, TRsfwMountInfo& aMountInfo); + + TInt SetMountConnectionState(TChar aDriveLetter, + TUint aConnectionState); + + TInt RefreshDirectory(const TDesC& aPath); + + TBool IsAppOnBlackList(TUid aUid); + + TInt CancelRemoteTransfer(const TDesC& aFile); + + + // Methods from MMountStoreObserver + void HandleMountStoreEvent(TMountStoreEvent aEvent, + TInt aStatus, + TAny* aArg); + +private: + enum TRsfwMountState + { + EMountStateIdle = 0, + EMountStateWait, + EMountStateCanceled + }; + +private: + // Default constructor + CRsfwMountManImpl(); + + void ConstructL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver); + TInt GetRsfwControlConnection(); + TInt MountFileSystem(const TDesC& aDriveName, TChar aDriveLetter); + TInt RemoteMountCountL(); + + + void DoUnmountL(TChar aDriveLetter, TUint aFlags); + TInt ExecuteUnmount(TChar aDriveLetter); + TChar FreeDriveLetterL(TChar aDriveLetter); + TChar DriveLetterFromMountEntry(const CRsfwMountEntry& aMountEntry); + void AddEntryL(CRsfwMountEntry* aMountEntry); + TInt SyncWithMounterExe(TBool aSetDrive, TChar aDrive = EDriveQ); + void GetFsDriveListL(TDriveList& aDriveList, TBool aRemoteOnly); + TInt GetRemoteDriveListL(TDriveList& aDriveList); + TInt SetDriveNameToFileSystem(TChar aDriveLetter, + const TDesC& aDriveName); + void LoadBlackListL(); + +private: // Data + RFs iFs; + RRsfwControl iRsfwControl; + TBool iRsfwControlConnected; + TUint iDefaultFlags; // default mount options + TRsfwMountInfo iMountInfo; // current mount info + TRsfwMountState iMountState; + MRsfwMountManObserver* iMountManObserver; + CRsfwMountStore* iMountStore; + RArray iBlackList; + }; + +#endif // CRSFWMOUNTMANIMPL_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/inc/rsfwmountutils.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/inc/rsfwmountutils.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,106 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mounting utilities + * +*/ + + +#ifndef RSFWMOUNTUTILS_H +#define RSFWMOUNTUTILS_H + +#include + +// CONSTANTS + +/// BIO message UID +const TUid KUidBIOMountConfMsg = {0x1bdeff02}; +const TInt KMountMessagePrefixLength = 29; // length of "//vnd.nokia.s60.mount.config\n" + +// FORWARD DECLARATIONS +class CRsfwMountEntry; + +// CLASS DECLARATION +/** ImportMountEntry is used from smart messaging bio control. +ExportMountEntryL is used from general settings plugin. +Both functions call GetKeyWord(), so only common thing +are actually the keywords used +Note that because this is only used for smart messaging, +currently exports and imports only mount name and address +*/ + + +class RsfwMountUtils + { +public: // New functions + /** + * Imports a mount configuration from a descriptor + * + * @param aMsg descriptor to be imported + * memory is reserved by this function, but ownership transferred to the caller + * @param aEntry returned mount entry + * @return nothing + */ + IMPORT_C static void ImportMountEntryL(const TDesC& aMsg, + CRsfwMountEntry** aEntry); + /** + * Imports a mount configuration from a stream + * + * @param aReadStream stream data to be imported + * function assumes that the stream contains 8-bit data + * @param aSize data size + * @param aEntry returned mount entry + * memory is reserved by this function, but ownership transferred to the caller + * @return nothing + */ + IMPORT_C static void ImportMountEntryFromStreamL(RReadStream& aReadStream, + TInt aSize, + CRsfwMountEntry** aEntry); + /** + * Exports a mount configuration to a descriptor. + * + * @param aEntry mount entry to be exported + * @param aSendCredentials controls whether username/passwd is exported + * @param aBuf returned descriptor + * @return nothing + */ + IMPORT_C static void ExportMountEntryL(const CRsfwMountEntry& aEntry, + TBool aSendCredentials, + TDes& aBuf); + /** + * Returns ETrue if the friendly name for a remote drive is valid + * Used from MountEntry and the General Settings plugin + * Currently just calls RFs::IsDriveNameValid() as + * the friendly name is stored to RFs::DriveName() + * @since S60 3.2 + * @param aFriendlyName remote drive friendly name + */ + IMPORT_C static TBool IsFriendlyNameValid(const TDesC& aFriendlyName); + + /** + * Returns ETrue if the address (URL) for a remote drive is valid + * Used from MountEntry and the General Settings plugin + * @since S60 3.2 + * @param aFriendlyName remote drive friendly name + */ + IMPORT_C static TBool IsDriveAddressValid(const TDesC8& aDriveAddress); + + +private: + static void ParseLineL(const TDesC& aLine, CRsfwMountEntry& aEntry); + static const TDesC& GetKeyWord(TInt aIndex); + }; + +#endif // RSFWMOUNTUTILS_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/src/rsfwbootmounter.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/src/rsfwbootmounter.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,307 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mounts during boot remote drives configured in CenRep + * +*/ + + +#include // link against efsrv.lib +#include // link against centralrepository.lib +#include + +// for the file server client side API +_LIT(KRemoteFSName, "RemoteFS"); +_LIT(KRemoteFs, "eremotefs"); + + +// for the central repository API +enum TMountEntryItemIndex + { + EMountEntryItemIndex, + EMountEntryItemName, + EMountEntryItemDrive, + EMountEntryItemUri, + EMountEntryItemUserName, + EMountEntryItemPassword, + EMountEntryItemIap, + EMountEntryItemInactivityTimeout, + EMountEntryItemReserved, + EMountEntryItemCount + }; +const TUid KCRUidRsfwCtrl = { 0x101F9775 }; // RSFW cenrep table id +const TUint KColumnName = EMountEntryItemName; +const TUint KColumnMask = 0x000000ff; +const TUint KRowMask = 0xffffff00; +const TInt KMaxFileSystemName = 256; +const TInt KMaxDriveLetterLength = 5; +const TInt KMaxFriendlyNameLength = 20; + + +// isRsfwFileSystem +// +// Checks whether certain drive has rsfw file system mounted on it +// +// +LOCAL_C TBool isRsfwFileSystemL(TInt aDrive, + TDriveList aDriveList, + RFs aFsSession) + { + TBool rsfwFileSystem = EFalse; + // check first KDriveAttRemote bit as if that is missing it is a quick way + // to conclude that this is not a rsfw mount + if (aDriveList[aDrive] & KDriveAttRemote) + { + TInt err; + HBufC* filesystemName = HBufC::NewL(KMaxFileSystemName); + TPtr itemPtr = filesystemName->Des(); + err = aFsSession.FileSystemName(itemPtr, aDrive); + if (!err && (itemPtr.Compare(KRemoteFSName) == 0)) + { + rsfwFileSystem = ETrue; + } + delete filesystemName; + } + return rsfwFileSystem; + } + + + +// DoMountL +// +// Do either simple mount or replace (our) existing mount +// by doing dismount and mount +// +// +LOCAL_C TInt DoMount(TInt aDrive, RFs aFsSession, TBool aReplaceExisting) + + { + TInt err; + if (aReplaceExisting) + { + // ignore dismount error code + aFsSession.DismountFileSystem(KRemoteFSName, aDrive); + err = aFsSession.MountFileSystem(KRemoteFSName, aDrive); + } + else + { + err = aFsSession.MountFileSystem(KRemoteFSName, aDrive); + } + return err; + } + + +// ExecuteFileServerMountL +// +// Attempts to mount our file system to the file server +// +// +LOCAL_C TInt ExecuteFileServerMountL(TInt aDrive, + TDriveList aDriveList, + RFs aFsSession) + { + TInt err; + if (aDriveList[aDrive]) + { + if (isRsfwFileSystemL(aDrive, aDriveList, aFsSession)) + { + err = DoMount(aDrive, aFsSession, ETrue); + } + else + { + // the drive we attempt to mount contains some other file system + return KErrInUse; + } + } + else + { + // the drive we attempt to mount does not contain an existing mount + err = DoMount(aDrive, aFsSession, EFalse); + } + return err; + } + + +// SetFriendlyNameL +// +// Sets the friendly name of the remote drive to +// mounted fs drivename and volumename fields +// (to the volume name field first 11 chars) +// +// This function assumes that we are allowed to manipulate +// drive aDrive, in practise that ExecuteFileServerMount() +// has been called succesfully +// +LOCAL_C TInt SetFriendlyName(TInt aDrive, + TDesC& aFriendlyName, + RFs aFsSession) + { + TInt err; + err = aFsSession.SetDriveName(aDrive, aFriendlyName); + if (!err) + { + TPtrC volumeNamePtr = aFriendlyName.Left(KMaxVolumeNameLength); + err = aFsSession.SetVolumeLabel(volumeNamePtr, aDrive); + } + return err; + } + +// ---------------------------------------------------------------------------- +// SyncConfiguredRemoteDrivesL +// adds RSFW File Server plug-in +// and synchronizes Central Repository's view of configured remote drives +// with File Server's view (mounts the remote drives configured in CR and +// unmounts those remote drives that are not anymore configured) +// ---------------------------------------------------------------------------- +// +LOCAL_C void SyncConfiguredRemoteDrivesL() + { + TInt err = 0; + TInt row = 0; + TInt driveNumber = 0; + RFs fs; + TChar paramLetter(90); + TBool paramSet = EFalse; + + User::LeaveIfError(fs.Connect()); + CleanupClosePushL(fs); + + // it is possible to manipulate only one drive letter, and give that as an argument + TInt clinelength = User::CommandLineLength(); + if (clinelength > 0) + { + HBufC* cl = HBufC::NewL(clinelength); + TPtr linePtr = cl->Des(); + User::CommandLine(linePtr); + TLex lex(linePtr); + paramLetter = lex.Get(); + paramSet = ETrue; + delete cl; + } + + // add our file system plugin to the file server + err = fs.AddFileSystem(KRemoteFs); + if ((err != KErrNone) && (err != KErrAlreadyExists)) + { + User::Leave(err); + } + + // Get a list of drives in the File Server + TDriveList drives; + User::LeaveIfError(fs.DriveList(drives, KDriveAttAll)); + // (drives[i] & KDriveAttRemote) now tells whether i:th drive is remote + + // Get a list of remote drives in the central repository table + + // connect + CRepository* cenrep; + cenrep = CRepository::NewL(KCRUidRsfwCtrl); + CleanupStack::PushL(cenrep); + + // find all entries by name + RArray nameIds; + CleanupClosePushL(nameIds); + err = cenrep->FindL(KColumnName, KColumnMask, nameIds); + if (!err) + { + // for each remote drive entry, represented by a record in central repository, do the following: + // 1) get drive letter from central repository + // 2) based on drive letter acquire corresponding drive number from the File Server + // 3) check whether in the File Server there is already mounted a drive with given number + // 3.1) if there is NOT, then mount the drive + // 3.2) if there is and it appears to be remote, then do re-mounting + // 3.3) if there is and it appears NOT to be remote, then this means error + // 4) still for the same record from central repository, get the name of the drive + // 5) use this name as the volume label in the File Server + for (row = 0; row < nameIds.Count(); row++) + { + TUint rowId = (nameIds[row] & KRowMask); + // don't touch zero row as it DOES NOT contain info about mounted drives + if (rowId > 0) + { + TInt i; + // mount it to the file server + + // get drive number + TBuf driveLetter; + i = EMountEntryItemDrive; + User::LeaveIfError(cenrep->Get(rowId | i, driveLetter)); + + // driveNumber needed in any case, so that we can mark this as existing drive + if (driveLetter.Length() > 0) + { + User::LeaveIfError(fs.CharToDrive((driveLetter)[0], driveNumber)); + } + else + { + User::Leave(KErrBadName); + } + + // proceed this drive if we didn't get any drive + // letter as a parameter or we got this one + if ((!paramSet) || (paramLetter == driveLetter[0])) + { + // get friendly name + TBuf friendlyName; + i = EMountEntryItemName; + User::LeaveIfError(cenrep->Get(rowId | i, friendlyName)); + + if (friendlyName.Length() > 0) + { + User::LeaveIfError(ExecuteFileServerMountL(driveNumber, drives, fs)); + User::LeaveIfError(SetFriendlyName(driveNumber, friendlyName,fs)); + } + + else + { + User::Leave(KErrBadName); + } + } + + // do not unmount this drive as it is still in the CenRep table + // after this loop non-zero drives are used to see + // which remote drives should be unmounted + drives[driveNumber] = 0; + } + } // loop + } + + // If drives now contain some remote drives, this means that they are not + // anymore configured in CenRep and should be unmounted. + for (int i = 0; i < EDriveZ; i++) + { + if (isRsfwFileSystemL(i, drives, fs)) + { + fs.DismountFileSystem(KRemoteFSName, i); + } + } + + CleanupStack::PopAndDestroy(3, &fs); // fs, cenrep, nameIds + + } + +// ---------------------------------------------------------------------------- +// E32Main +// +// ---------------------------------------------------------------------------- +// +GLDEF_C TInt E32Main() + { + CTrapCleanup* cleanupStack = CTrapCleanup::New(); + TRAPD(err, SyncConfiguredRemoteDrivesL()); + delete cleanupStack; + return err; + } + + +// End of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/src/rsfwmountentry.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/src/rsfwmountentry.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,239 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mount configuration entry + * +*/ + + +// INCLUDE FILES +#include +#include +#include "rsfwmountutils.h" + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::NewLC +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountEntry* CRsfwMountEntry::NewLC() + { + CRsfwMountEntry* self = new (ELeave) CRsfwMountEntry(); + CleanupStack::PushL(self); + self->ConstructL(); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountEntry* CRsfwMountEntry::NewL() + { + CRsfwMountEntry* self = NewLC(); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::CRsfwMountEntry +// ---------------------------------------------------------------------------- +// +CRsfwMountEntry::CRsfwMountEntry() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::~CRsfwMountEntry +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountEntry::~CRsfwMountEntry() + { + Clear(); + iFs.Close(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::SetItemL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountEntry::SetItemL(TInt aIndex, const TDesC& aValue) + { + TChar driveChar; + + if ((aIndex < EMountEntryItemIndex) || (aIndex >= EMountEntryItemCount)) + { + User::Leave(KErrArgument); + } + + switch (aIndex) + { + case EMountEntryItemName: + if (aValue.Length() > KMaxMountNameLength) + { + User::Leave(KErrArgument); + } + // name must not contain chars not allowed in Symbian file names + // as the name will be stored as drive friendly name + // (rules for allowed chars are the same) + if (!(RsfwMountUtils::IsFriendlyNameValid(aValue))) + { + User::Leave(KErrArgument); + } + break; + case EMountEntryItemUri: + if (aValue.Length() > KMaxMountUriLength) + { + User::Leave(KErrArgument); + } + break; + case EMountEntryItemUserName: + if (aValue.Length() > KMaxMountUserNameLength) + { + User::Leave(KErrArgument); + } + break; + case EMountEntryItemPassword: + if (aValue.Length() > KMaxMountPasswordLength) + { + User::Leave(KErrArgument); + } + break; + case EMountEntryItemDrive: + // remote drives can take drive letters from J through Y + // (see documentation for RFs::DriveList()) + driveChar = aValue[0]; + TInt driveNumber; + User::LeaveIfError(iFs.CharToDrive(driveChar, driveNumber)); + if (!((driveNumber >= EDriveJ) && (driveNumber < EDriveZ))) + { + User::Leave(KErrArgument); + } + break; + default: + // check that the value is not too long + if (aValue.Length() > KMaxMountConfItemLength) + { + User::Leave(KErrArgument); + } + break; + } + + HBufC*& p = iMountEntryItems[aIndex]; + if (p) + { + delete p; + p = NULL; + } + p = aValue.AllocL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::SetItemL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountEntry::SetItemL(TInt aIndex, const TDesC8& aValue) + { + HBufC* p = HBufC::NewLC(aValue.Length()); + TPtr pPtr = p->Des(); + pPtr.Copy(aValue); + SetItemL(aIndex, pPtr); + CleanupStack::PopAndDestroy(p); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::SetEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountEntry::SetEntryL(TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap) + { + TBuf index; + index.Num(aIndex); + SetItemL(EMountEntryItemIndex, index); + SetItemL(EMountEntryItemName, aName); + TBuf drive; + drive.Append(aDriveLetter); + SetItemL(EMountEntryItemDrive, drive); + SetItemL(EMountEntryItemUri, aUri); + SetItemL(EMountEntryItemUserName, aUserName); + SetItemL(EMountEntryItemPassword, aPassword); + SetItemL(EMountEntryItemIap, aIap); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::Item +// ---------------------------------------------------------------------------- +// +EXPORT_C const HBufC* CRsfwMountEntry::Item(TInt aIndex) const + { + if ((aIndex >= EMountEntryItemIndex) && (aIndex < EMountEntryItemCount)) + { + return iMountEntryItems[aIndex]; + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::Clear +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountEntry::Clear() + { + TInt i; + for (i = EMountEntryItemIndex; i < EMountEntryItemCount; i++) + { + if (iMountEntryItems[i]) + { + delete iMountEntryItems[i]; + iMountEntryItems[i] = NULL; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::CloneL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountEntry* CRsfwMountEntry::CloneL() const + { + CRsfwMountEntry* entry = CRsfwMountEntry::NewLC(); + TInt i; + for (i = EMountEntryItemIndex; i < EMountEntryItemCount; i++) + { + HBufC* item = iMountEntryItems[i]; + if (item) + { + entry->iMountEntryItems[i] = (*item).AllocL(); + } + } + CleanupStack::Pop(entry); + return entry; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountEntry::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwMountEntry::ConstructL() + { + User::LeaveIfError(iFs.Connect()); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/src/rsfwmountman.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/src/rsfwmountman.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,295 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RSFW Mount Manager API +* +*/ + + +// INCLUDE FILES +#include +#include "rsfwmountmanimpl.h" + +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// TRsfwMountConfig::ExternalizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void TRsfwMountConfig::ExternalizeL(RWriteStream& aStream) const + { + aStream.WriteUint32L(iDriveLetter); + aStream << iName; + aStream << iUri; + aStream << iUserName; + // Don't externalize a password that is not part of the mount configuration + // (this is for security) + if (iFlags & KMountFlagAskPassword) + { + TPtrC emptyPassword; + aStream << emptyPassword; + } + else + { + aStream << iPassword; + } + aStream << iAuxData; + aStream.WriteUint32L(iFlags); + aStream.WriteInt32L(iInactivityTimeout); + } + + +// ---------------------------------------------------------------------------- +// TRsfwMountConfig::InternalizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void TRsfwMountConfig::InternalizeL(RReadStream& aStream) + { + iDriveLetter = aStream.ReadUint32L(); + aStream >> iName; + aStream >> iUri; + aStream >> iUserName; + aStream >> iPassword; + aStream >> iAuxData; + iFlags = aStream.ReadUint32L(); + iInactivityTimeout = aStream.ReadInt32L(); + } + + +// ---------------------------------------------------------------------------- +// TRsfwMountInfo::ExternalizeL +// ---------------------------------------------------------------------------- +// +void TRsfwMountInfo::ExternalizeL(RWriteStream& aStream) const + { + iMountConfig.ExternalizeL(aStream); + } + + +// ---------------------------------------------------------------------------- +// TRsfwMountInfo::InternalizeL +// ---------------------------------------------------------------------------- +// +void TRsfwMountInfo::InternalizeL(RReadStream& aStream) + { + Mem::FillZ(this, sizeof(*this)); + iMountConfig.InternalizeL(aStream); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::CRsfwMountMan +// Constructor +// ---------------------------------------------------------------------------- +// +CRsfwMountMan::CRsfwMountMan() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwMountMan::ConstructL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver) + { + iMountManImpl = CRsfwMountManImpl::NewL(aDefaultFlags, aMountManObserver); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountMan* CRsfwMountMan::NewL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver) + { + CRsfwMountMan* self = new (ELeave) CRsfwMountMan(); + CleanupStack::PushL(self); + self->ConstructL(aDefaultFlags, aMountManObserver); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::~CRsfwMountMan +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountMan::~CRsfwMountMan() + { + delete iMountManImpl; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::GetMountNamesL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountMan::GetMountNamesL(CDesC16Array* aNames) const + { + iMountManImpl->GetMountNamesL(aNames); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::MountEntry +// ---------------------------------------------------------------------------- +// +EXPORT_C const CRsfwMountEntry* CRsfwMountMan::MountEntryL(const TDesC& aName) const + { + return iMountManImpl->MountEntryL(aName); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::MountEntry +// ---------------------------------------------------------------------------- +// +EXPORT_C const CRsfwMountEntry* CRsfwMountMan::MountEntryL(TChar aDriveLetter) const + { + return iMountManImpl->MountEntryL(aDriveLetter); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::AddMountEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountMan::AddMountEntryL(CRsfwMountEntry* aMountEntry) + { + iMountManImpl->AddMountEntryL(aMountEntry); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::DeleteMountEntry +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountMan::DeleteMountEntryL(const TDesC& aName) + { + iMountManImpl->DeleteMountEntryL(aName); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::DeleteMountEntry +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountMan::DeleteMountEntryL(TChar aDriveLetter) + { + iMountManImpl->DeleteMountEntryL(aDriveLetter); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::GetAllDrivesL +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::GetAllDrivesL(TDriveList& aDriveList) const + { + return iMountManImpl->GetAllDrivesL(aDriveList); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::GetRemoteMountList +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::GetRemoteMountListL(TDriveList& aDriveList) const + { + return iMountManImpl->GetRemoteMountListL(aDriveList); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::GetMountInfo +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::GetMountInfo(TChar aDriveLetter, + TRsfwMountInfo& aMountInfo) const + { + return iMountManImpl->GetMountInfo(aDriveLetter, aMountInfo); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::SetMountConnectionState +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::SetMountConnectionState(TChar aDriveLetter, + TUint aConnectionState) + { + if (aConnectionState == KMountStronglyConnected) + { + TRsfwMountConfig mountConfig; + mountConfig.iDriveLetter = aDriveLetter; + mountConfig.iFlags = KMountFlagMountAtRfeOnly; + TRAPD(err, iMountManImpl->MountL(aDriveLetter)); + return err; + } + else + { + return iMountManImpl->SetMountConnectionState(aDriveLetter, + aConnectionState); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::SetMountConnectionStateBlind +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::SetMountConnectionStateBlind(TChar aDriveLetter, + TUint aConnectionState) + { + if (aConnectionState == KMountStronglyConnected) + { + TRsfwMountConfig mountConfig; + mountConfig.iDriveLetter = aDriveLetter; + mountConfig.iFlags = KMountFlagMountAtRfeOnly; + TRAPD(err, iMountManImpl->MountBlindL(aDriveLetter)); + return err; + } + else + { + return iMountManImpl->SetMountConnectionState(aDriveLetter, + aConnectionState); + } + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::EditMountEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountMan::EditMountEntryL(CRsfwMountEntry* aMountEntry) + { + iMountManImpl->EditMountEntryL(aMountEntry); + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::RefreshDirectoryL +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::RefreshDirectory(const TDesC& aPath) + { + return iMountManImpl->RefreshDirectory(aPath); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::IsAppOnBlackList +// ---------------------------------------------------------------------------- +// +EXPORT_C TBool CRsfwMountMan::IsAppOnBlackList(TUid aUid) const + { + return iMountManImpl->IsAppOnBlackList(aUid); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountMan::CancelAllRemoteTransfers +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwMountMan::CancelRemoteTransfer(const TDesC& aFile) + { + return iMountManImpl->CancelRemoteTransfer(aFile); + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/src/rsfwmountmanimpl.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/src/rsfwmountmanimpl.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,755 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mount manager + * +*/ + + +// INCLUDE FILES +#include +#include // KMaxVolumeNameLength +#include +#include + +#include "rsfwinterface.h" +#include "rsfwmountmanimpl.h" + + +// CONSTANTS +const TUint8 KDefaultDriveLetter = 'J'; + // system default if no other specified; + // remote drives should use letters from J: to Y: + + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::CRsfwMountManImpl +// Constructor +// ---------------------------------------------------------------------------- +// +CRsfwMountManImpl::CRsfwMountManImpl() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::NewL +// ---------------------------------------------------------------------------- +// +CRsfwMountManImpl* CRsfwMountManImpl::NewL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver) + { + CRsfwMountManImpl* self = new (ELeave) CRsfwMountManImpl(); + CleanupStack::PushL(self); + self->ConstructL(aDefaultFlags, aMountManObserver); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::~CRsfwMountManImpl +// ---------------------------------------------------------------------------- +// +CRsfwMountManImpl::~CRsfwMountManImpl() + { + iFs.Close(); + if (iRsfwControlConnected) + { + iRsfwControl.Close(); + } + delete iMountStore; + + iBlackList.Close(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetMountNamesL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::GetMountNamesL(CDesC16Array* aNames) + { + iMountStore->GetNamesL(aNames); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::MountEntry +// ---------------------------------------------------------------------------- +// +const CRsfwMountEntry* CRsfwMountManImpl::MountEntryL(const TDesC& aName) + { + return iMountStore->LookupEntryByNameL(aName); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::MountEntry +// ---------------------------------------------------------------------------- +// +const CRsfwMountEntry* CRsfwMountManImpl::MountEntryL(TChar aDriveLetter) + { + return iMountStore->LookupEntryByDriveL(aDriveLetter); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::AddMountEntryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::AddMountEntryL(CRsfwMountEntry* aMountEntry) + { + // Take ownership + CleanupStack::PushL(aMountEntry); + + // Look for existing configuration with the same friendly name + // overwriting not allowed + const HBufC* driveName = aMountEntry->Item(EMountEntryItemName); + const CRsfwMountEntry* entry = MountEntryL(*driveName); + if (entry) + { + User::Leave(KErrInUse); + } + // Also look for existing configuration with the same drive letter + // overwriting not allowed + TChar driveLetter = DriveLetterFromMountEntry(*aMountEntry); + if (driveLetter != '?') + { + entry = MountEntryL(driveLetter); + if (entry) + { + User::Leave(KErrInUse); + } + } + else + { + driveLetter = FreeDriveLetterL(driveLetter); + TBuf<1> driveLetterBuf; + driveLetterBuf.Append(driveLetter); + // Replace '?' with the allocated drive letter + aMountEntry->SetItemL(EMountEntryItemDrive, driveLetterBuf); + } + + // find the number of remote drives in use + // if 9 already new ones are not allowed + TDriveList fsDriveList; + User::LeaveIfError(iFs.DriveList(fsDriveList, KDriveAttRemote)); + TInt i; + TInt remoteDrives = 0; + for (i = EDriveA; i <= EDriveZ; i++) + { + if (fsDriveList[i] & KDriveAttRemote) + { + remoteDrives++; + } + } + + if (remoteDrives == KMaxRemoteDrives) + { + User::Leave(KErrInUse); + } + + // Save the friendly name (not guaranteed to survive CMountStore::AddEntryL + HBufC* name = NULL; + if (aMountEntry->Item(EMountEntryItemName)) + { + name = aMountEntry->Item(EMountEntryItemName)->AllocL(); + } + + // Release ownership + CleanupStack::Pop(aMountEntry); + // Add mount configuration repository entry + TRAPD(err, AddEntryL(aMountEntry)); + CleanupStack::PushL(name); + User::LeaveIfError(err); + + // Add mount in File Server + if (name) + { + User::LeaveIfError(MountFileSystem(*name, driveLetter)); + } + else + { + _LIT(KRsfwNoName, "remotedrive"); + User::LeaveIfError(MountFileSystem(KRsfwNoName, driveLetter)); + } + + // finally set mountconnection state to disconnected + // this will make in Remote File Engine what is called "disconnected dormant mount" + SetMountConnectionState(driveLetter, KMountNotConnected); + + CleanupStack::PopAndDestroy(name); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::DeleteMountEntryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::DeleteMountEntryL(const TDesC& aName) + { + const CRsfwMountEntry* mountEntry = iMountStore->LookupEntryByNameL(aName); + if (mountEntry) + { + TChar driveLetter = DriveLetterFromMountEntry(*mountEntry); + if (driveLetter != '?') + { + DeleteMountEntryL(driveLetter); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::DeleteMountEntryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::DeleteMountEntryL(TChar aDriveLetter) + { + const CRsfwMountEntry* mountEntry = + iMountStore->LookupEntryByDriveL(aDriveLetter); + if (mountEntry) + { + // Remove entry from configuration repository + iMountStore->RemoveEntryL(aDriveLetter); + // Dismount from file server and Remote File Engine + ExecuteUnmount(aDriveLetter); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::EditMountEntryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::EditMountEntryL(CRsfwMountEntry* aMountEntry) + { + // take ownership + CleanupStack::PushL(aMountEntry); + + // look for the drive based on the letter + TChar driveLetter = DriveLetterFromMountEntry(*aMountEntry); + const CRsfwMountEntry* entryByDrive = MountEntryL(driveLetter); + if ( !entryByDrive ) + { + User::Leave(KErrNotFound); + } + + // check whether the name has changed + TBool nameChanged = EFalse; + const HBufC* newName = aMountEntry->Item(EMountEntryItemName); + const HBufC* oldName = entryByDrive->Item(EMountEntryItemName); + if ( newName->Compare(*oldName) != KErrNone ) + { + nameChanged = ETrue; + } + + // check whether URI has changed + TBool uriChanged = EFalse; + const HBufC* newUri = aMountEntry->Item(EMountEntryItemUri); + const HBufC* oldUri = entryByDrive->Item(EMountEntryItemUri); + if ( newUri->Compare(*oldUri) != KErrNone ) + { + uriChanged = ETrue; + } + + // if the name has changed -> check whether it is not used by the other mount entry + if ( nameChanged ) + { + const CRsfwMountEntry* entryByName = MountEntryL(*newName); + if ( entryByName && entryByDrive != entryByName ) + { + User::Leave(KErrInUse); + } + } + + // release ownership and call MountStore API + CleanupStack::Pop(aMountEntry); + AddEntryL(aMountEntry); + + // if URI has changed we have to unmount the drive from RFE in order + // to clear the cache and mount it again + // note there is no need to make unmounting from File System + if ( uriChanged ) + { + TInt err; + User::LeaveIfError(GetRsfwControlConnection()); + err = iRsfwControl.DismountByDriveLetter(driveLetter); + if ((err != KErrNone) && (err != KErrNotFound)) + { + User::Leave(err); + } + User::LeaveIfError(iRsfwControl.SetMountConnectionState(driveLetter, KMountNotConnected)); + } + + // if the name has changed -> change label in File System + if ( nameChanged ) + { + User::LeaveIfError(SetDriveNameToFileSystem(driveLetter, *newName)); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::MountL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::MountL(TChar& aDriveLetter) + { + TInt driveNumber; + User::LeaveIfError(iFs.CharToDrive(aDriveLetter, driveNumber)); + User::LeaveIfError(GetRsfwControlConnection()); + User::LeaveIfError(iRsfwControl.Mount(driveNumber)); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::MountL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::MountBlindL(TChar& aDriveLetter) + { + TInt driveNumber; + User::LeaveIfError(iFs.CharToDrive(aDriveLetter, driveNumber)); + User::LeaveIfError(GetRsfwControlConnection()); + User::LeaveIfError(iRsfwControl.MountBlind(driveNumber)); + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::SetMountConnectionState +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::SetMountConnectionState(TChar aDriveLetter, + TUint aConnectionState) + { + TInt err = GetRsfwControlConnection(); + if (err != KErrNone) + { + return err; + } + + err = iRsfwControl.SetMountConnectionState(aDriveLetter, aConnectionState); + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::IsAppOnBlackList +// ---------------------------------------------------------------------------- +// +TBool CRsfwMountManImpl::IsAppOnBlackList(TUid aUid) + { + TInt i; + for ( i = 0; i < iBlackList.Count(); i++ ) + { + if ( aUid == iBlackList[i] ) + { + return ETrue; + } + } + return EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetAllDrivesL +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::GetAllDrivesL(TDriveList& aDriveList) + { + GetFsDriveListL(aDriveList, EFalse); + return aDriveList.Length(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetRemoteMountList +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::GetRemoteMountListL(TDriveList& aDriveList) + { + GetFsDriveListL(aDriveList, ETrue); + return aDriveList.Length(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetMountInfo +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::GetMountInfo(TChar aDriveLetter, + TRsfwMountInfo& aMountInfo) + { + TInt err = GetRsfwControlConnection(); + if (err == KErrNone) + { + err = iRsfwControl.GetMountInfo(aDriveLetter, aMountInfo); + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetRsfwControlConnection +// Set a Remote File Engine control connection unless +// we already have a connection +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::GetRsfwControlConnection() + { + TInt err = KErrNone; + if (!iRsfwControlConnected) + { + err = iRsfwControl.Connect(); + if (!err) + { + iRsfwControlConnected = ETrue; + } + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::MountFileSystem +// Install ERemoteFS file system plugin (if not already done) and +// mount a filesystem designated with the given drive letter +// on that file system +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::MountFileSystem(const TDesC& /*aDriveName*/, + TChar aDriveLetter) + { + return SyncWithMounterExe(ETrue, aDriveLetter); + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::RemoteDriveCount +// Get the number of remote mounts as seen by the File Server +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::RemoteMountCountL() + { + // Check if how many mounts there are (also dormant mounts are counted) + TDriveList driveList; + return GetRemoteMountListL(driveList); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::DoUnmountL +// Do conditional unmounting by consulting the user +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::DoUnmountL(TChar aDriveLetter, TUint /* aFlags */) + { + TInt err = ExecuteUnmount(aDriveLetter); + User::LeaveIfError(err); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::ExecuteUnmount +// Do unconditional unmounting +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::ExecuteUnmount(TChar aDriveLetter) + { + TInt err = GetRsfwControlConnection(); + if (err != KErrNone) + { + return err; + } + + // Drop the mount both from the File Server and from Remote File Engine + TInt errFs = KErrNone; + TInt driveNumber; + err = iFs.CharToDrive(aDriveLetter, driveNumber); + if (err != KErrNone) + { + return err; + } + TDriveInfo driveInfo; + err = iFs.Drive(driveInfo, driveNumber); + if (err != KErrNone) + { + return err; + } + if (driveInfo.iDriveAtt & KDriveAttRemote) + { + // The mount is known by the File Server + errFs = iFs.DismountFileSystem(KRemoteFSName, driveNumber); + if (errFs == KErrPermissionDenied) + { + // Client does not have sufficient capabilities to do the operation + // execute mount with the boot mounter application + SyncWithMounterExe(ETrue, aDriveLetter); + } + } + + // We also request dismount from the RFE because + // The File Server (eremotefs) does not pass the + // dismount request to the RFE. + err = iRsfwControl.DismountByDriveLetter(aDriveLetter); + if (errFs != KErrNone) + { + // give priority to the File Server error + err = errFs; + } + return err; + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::ConstructL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver) + { + iDefaultFlags = aDefaultFlags; + + User::LeaveIfError(iFs.Connect()); + iRsfwControlConnected = EFalse; + iMountManObserver = aMountManObserver; + iMountStore = CRsfwMountStore::NewL(this); + LoadBlackListL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::FreeDriveLetterL +// Find a drive letter that has not yet been allocated by the File Server or +// defined in the mount configuration data base +// If the suggested drive letter (given as an input parameter) +// is already occupied, an adjacent letter in the alphabet is returned. +// Letter '?' as an input parameter is equal to KDefaultDriveLetter. +// Leave with KErrInUse if there are no free drive slots +// ---------------------------------------------------------------------------- +// +TChar CRsfwMountManImpl::FreeDriveLetterL(TChar aDriveLetter) + { + if (aDriveLetter == '?') + { + // Use the system default drive letter if none is specified + aDriveLetter = KDefaultDriveLetter; + } + else if ((aDriveLetter < 'A') || (aDriveLetter > 'Z')) + { + aDriveLetter.UpperCase(); + } + + TInt driveNumber; + User::LeaveIfError(iFs.CharToDrive(aDriveLetter, driveNumber)); + + // Try to find a free drive around the given drive + + // Get drives that are already mounted in the File Server + TDriveList fsDriveList; + User::LeaveIfError(iFs.DriveList(fsDriveList, KDriveAttAll)); + // scan first upwards, then downwards from the requested drive + // (or default drive letter) until a free and legal drive letter is found + // remote drives should use letters from J: to Y: + TInt i; + for (i = driveNumber; i <= EDriveY; i++) + { + if (fsDriveList[i] == 0) + { + User::LeaveIfError(iFs.DriveToChar(i, aDriveLetter)); + return aDriveLetter; + } + } + for (i = driveNumber - 1; i >= EDriveJ; i--) + { + if (fsDriveList[i] == 0) + { + User::LeaveIfError(iFs.DriveToChar(i, aDriveLetter)); + return aDriveLetter; + } + } + + // no free drive letters for remote drives + User::Leave(KErrInUse); + return 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::DriveLetterFromMountEntry +// Build a TRsfwMountConfig +// ---------------------------------------------------------------------------- +// +TChar CRsfwMountManImpl::DriveLetterFromMountEntry(const CRsfwMountEntry& aMountEntry) + { + const HBufC* drive = aMountEntry.Item(EMountEntryItemDrive); + if (drive && drive->Length()) + { + return (*drive)[0]; + } + else + { + return '?'; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::AddEntryL +// Add an entry in the mount configurarion store +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::AddEntryL(CRsfwMountEntry* aMountEntry) + { + iMountStore->AddEntryL(aMountEntry); + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::HandleMountStoreEvent +// Handle a mount store change notification +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::HandleMountStoreEvent(TMountStoreEvent aEvent, + TInt aStatus, + TAny* aArg) + { + if (iMountManObserver) + { + if (aEvent == EMountStoreEventMountConfigurationChanged) + { + TRAP_IGNORE(iMountManObserver->HandleMountManEventL( + EMountManEventMountConfigurationChanged, + aStatus, + aArg)); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::SyncWithMounterExe +// Uses boot mounter exe to mount or unmount remote drives in File Server +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::SyncWithMounterExe(TBool aSetDrive, TChar aDrive) + { + TInt err; + RProcess mounter; + TRequestStatus status; + TBuf<5> parameter; + if (!aSetDrive) + { + err = mounter.Create(KRsfwMounterExe, _L("")); + } + else + { + parameter.Append(aDrive); + err = mounter.Create(KRsfwMounterExe, parameter); + } + + if (err == KErrNone) + { + mounter.Resume(); + mounter.Logon(status); + User::WaitForRequest(status); + mounter.Close(); + err = status.Int(); + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetFsDriveList +// +// Returns drive letters. Letters for remote drives in order defined in CenRep +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::GetFsDriveListL(TDriveList& aDriveList, TBool aRemoteOnly) + { + TDriveList driveList; + // get local drives + User::LeaveIfError(iFs.DriveList(driveList)); + + // local drives are assumed to be from C:\ to R:\ + // these will go to the front of the list + if (!aRemoteOnly) + { + for (int i = EDriveC; i <= EDriveZ; i++) + { + if ( (driveList[i]) && (!(driveList[i] & KDriveAttRemote)) ) + { + TChar driveLetter; + User::LeaveIfError(iFs.DriveToChar(i, driveLetter)); + aDriveList.Append(driveLetter); + } + } + } + + GetRemoteDriveListL(driveList); + + for (int i = 0; i < driveList.Length(); i++) + { + aDriveList.Append(driveList[i]); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::GetRemoteDriveList +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::GetRemoteDriveListL(TDriveList& aDriveList) + { + iMountStore->GetDriveLettersL(aDriveList); + return aDriveList.Length(); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::SetDriveNameToFileSystem +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::SetDriveNameToFileSystem(TChar aDriveLetter, + const TDesC& /*aDriveName*/) + { + return SyncWithMounterExe(ETrue, aDriveLetter); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::RefreshDirectoryL +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::RefreshDirectory(const TDesC& aPath) + { + TInt err; + err = GetRsfwControlConnection(); + if (err != KErrNone) + { + return err; + } + return iRsfwControl.RefreshDirectory(aPath); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::LoadBlackListL +// ---------------------------------------------------------------------------- +// +void CRsfwMountManImpl::LoadBlackListL() + { + +// const TUid app1 = TUid::Uid(0x00000000); +// const TUid app2 = TUid::Uid(0x00000001); +// const TUid app3 = TUid::Uid(0x00000002); + + iBlackList.Reset(); +// iBlackList.AppendL(app1); +// iBlackList.AppendL(app2); +// iBlackList.AppendL(app3); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountManImpl::LoadBlackListL +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountManImpl::CancelRemoteTransfer(const TDesC& aFile) + { + TInt err; + err = GetRsfwControlConnection(); + if (err != KErrNone) + { + return err; + } + return iRsfwControl.CancelRemoteTransfer(aFile); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/src/rsfwmountutils.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/src/rsfwmountutils.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,381 @@ +/* +* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Utility functions for managing mount configurations +* +*/ + +// INCLUDES + +#include +#include +#include +#include +#include +#include + +#include "rsfwmountutils.h" +#include "rsfwremoteaccess.h" + + +// CONSTANTS +// These keywords must match with the entry items +_LIT(KKId, "Fname"); +_LIT(KKDrive, "Fdrv"); +_LIT(KKUri, "Furi"); +_LIT(KKUserName, "Fuid"); +_LIT(KKPassword, "Fpsw"); + +_LIT(KMountMessagePrefix, "//vnd.nokia.s60.mount.config\n"); + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::ImportMountEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void RsfwMountUtils::ImportMountEntryL(const TDesC& aMsg, + CRsfwMountEntry** aEntry) + { + // Expected to start with + // //vnd.nokia.s60.mount.config\n + + TPtrC prefix = aMsg.Left(KMountMessagePrefixLength); + if (prefix.Compare(KMountMessagePrefix) != 0) + { + User::Leave(KErrNotFound); + } + + // It is a mount configuration message + CRsfwMountEntry* entry = CRsfwMountEntry::NewLC(); + + TInt lineNumber = 0; + + // SMS rich text messages may be have trailing characters - + // that looks like ')' characters + TInt i = aMsg.Length() - 1; + while (i > 0) + { + TUint8 c = static_cast(aMsg[i]); + if (c != ')') + { + break; + } + i--; + } + TPtrC msg = aMsg.Left(i + 1); + + TLex lex(msg); + while (!lex.Eos()) + { + lineNumber++; + lex.SkipSpaceAndMark(); + while (lex.Peek() != '\n' && !lex.Eos()) + { + lex.Inc(); + } + // The marked token is now the whole line + TPtrC line = lex.MarkedToken(); + ParseLineL(line, *entry); + if (!lex.Eos()) + { + // Skip the '\n' + lex.Inc(); + } + } + + CleanupStack::Pop(entry); + *aEntry = entry; + } + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::ImportMountEntryFromStreamL +// ---------------------------------------------------------------------------- +// +EXPORT_C void RsfwMountUtils::ImportMountEntryFromStreamL(RReadStream& aReadStream, + TInt aSize, + CRsfwMountEntry** aEntry) + { + // the string is assumed to be 8-bit in stream, + // and should be converted to Unicode + *aEntry = NULL; + HBufC8* tempbuf = HBufC8::NewLC(aSize); + TPtr8 tbufPtr = tempbuf->Des(); + tbufPtr.Zero(); + TRAPD(err, aReadStream.ReadL(tbufPtr)); + + HBufC* buf = HBufC::NewLC(aSize); + TPtr bufPtr = buf->Des(); + CnvUtfConverter::ConvertToUnicodeFromUtf8(bufPtr, tbufPtr); + if ((err == KErrNone) || (err == KErrEof)) + { + ImportMountEntryL(bufPtr, aEntry); + } + CleanupStack::PopAndDestroy(2, tempbuf); // buf, tempbuf + } + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::ExportMountEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void RsfwMountUtils::ExportMountEntryL(const CRsfwMountEntry& aEntry, + TBool aSendCredentials, + TDes& aBuf) + { + aBuf.Copy(KMountMessagePrefix); + TInt i; + // smart messaging sends: + // EMountEntryItemName + // EMountEntryItemUri + // if aSendCredentials sends also: + // EMountEntryItemUserName + // EMountEntryItemPassword + TInt lastToExport; + if (aSendCredentials) + { + lastToExport = EMountEntryItemPassword; + } + else + { + lastToExport = EMountEntryItemUri; + } + + for (i = EMountEntryItemName; i < lastToExport + 1; i++) + { + if (i != EMountEntryItemDrive) + { + const HBufC* item = aEntry.Item(i); + if (item && item->Length()) + { + aBuf.Append(GetKeyWord(i)); + aBuf.Append(':'); + const TPtrC ip(*item); + aBuf.Append(ip); + aBuf.Append('\n'); + } + } + } + } + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::IsFriendlyNameValid +// ---------------------------------------------------------------------------- +// +EXPORT_C TBool RsfwMountUtils::IsFriendlyNameValid(const TDesC& aFriendlyName) + { + TInt err; + TBool retValue = ETrue; + RFs fsSession; + err = fsSession.Connect(); + if (err) + { + return retValue; + } + retValue = fsSession.IsValidName(aFriendlyName); + fsSession.Close(); + + // Some names are acceptable by RFs.IsValidName(), + // but not acceptable by RFs.SetDriveName() + // Those are checked below: + + // solely period characters ( e.g. "...") + if (retValue) + { + retValue = EFalse; + TChar period(46); // period (".") character + TInt i; + for (i = 0; i < aFriendlyName.Length(); i++) + { + if (aFriendlyName[i] != period) + { + retValue = ETrue; + break; + } + } + } + + // period as the last character ( e.g. "myDrive.") + if (retValue) + { + TChar period(46); // period (".") character + TInt nameLength = aFriendlyName.Length(); + if (nameLength > 0 && aFriendlyName[nameLength-1] == period) + { + retValue = EFalse; + } + } + + return retValue; + } + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::IsDriveAddressValid +// ---------------------------------------------------------------------------- +// +EXPORT_C TBool RsfwMountUtils::IsDriveAddressValid(const TDesC8& aDriveAddress) + { + // extract the protocol + TInt err; + TUriParser8 parser; + err = parser.Parse(aDriveAddress); + if (err) + { + return EFalse; + } + TPtrC8 protocol = parser.Extract(EUriScheme); + + + TBuf8 matchString; + _LIT8(KRemoteMatchPrefix, "remoteaccess/"); + matchString.Copy(KRemoteMatchPrefix); + + // Both "http" and "https" are handled by davaccess module + _LIT8(KHttps, "https"); + if (protocol.Compare(KHttps) == 0) + { + _LIT8(KHttp, "http"); + matchString.Append(KHttp); + } + else + { + matchString.Append(protocol); + } + TEComResolverParams resolverParams; + resolverParams.SetDataType(matchString); + // Disable wildcard matching + resolverParams.SetWildcardMatch(EFalse); + + + // check whether there is a remote access plugin implementation for that protocol + RImplInfoPtrArray implinfo; + TRAP(err, REComSession::ListImplementationsL( + KCRemoteAccessUid, + resolverParams, + implinfo)); + + if (err != KErrNone) + { + // if fetching the list of implemenations fail,' + // (for example a temporary out of memory situation) + // just accept the string + implinfo.ResetAndDestroy(); + return ETrue; + } + + // we assume that protocol used for remote access + // represents hierarchical relationships within the namespace. This + // "generic URI" syntax consists of a sequence of four main components: + // ://? + // check that scheme is followed by "://" + _LIT8(KDelimiter, "://"); + if (aDriveAddress.Length() < protocol.Length()+3) + { + implinfo.ResetAndDestroy(); + return EFalse; + } + + TPtrC8 test = aDriveAddress.Mid(protocol.Length(), 3); + if (!(test.Compare(KDelimiter) == 0)) + { + implinfo.ResetAndDestroy(); + return EFalse; + } + + TInt count = implinfo.Count(); + implinfo.ResetAndDestroy(); + if (count > 0) + { + return ETrue; + } + else + { + return EFalse; + } + } + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::ParseLineL +// ---------------------------------------------------------------------------- +// +void RsfwMountUtils::ParseLineL(const TDesC& aLine, + CRsfwMountEntry& aEntry) + { + TLex lex(aLine); + // Extract Line i.e "leftToken:RightToken", then asign to TLex object + while (lex.Peek() != ':' && lex.Peek() != '\n' && !lex.Eos()) + { + lex.Inc(); + } + + // We are only interested in lines containing a colon delimeter ':' + // other text lines are ignored i.e "Welcome !" + if(lex.Peek() != ':') + { + // It was not a name value pair + return; + } + if (lex.TokenLength() == 0) + { + User::Leave(KErrNotFound); + } + // Get the keyword + HBufC* keyWord = lex.MarkedToken().AllocLC(); + // Go past the ':' + lex.Inc(); + lex.SkipSpaceAndMark(); + while (lex.Peek() != '\n' && lex.Peek() != '\r' && !lex.Eos()) + { + lex.Inc(); + } + + TInt i; + // Keyword matching + // password is the last possible entry that is transferred + for (i = EMountEntryItemName; i < EMountEntryItemPassword + 1; i++) + { + if (GetKeyWord(i).Compare(*keyWord) == 0) + { + aEntry.SetItemL(i, lex.MarkedToken()); + } + } + CleanupStack::PopAndDestroy(keyWord); + } + +// ---------------------------------------------------------------------------- +// RsfwMountUtils::GetKeyWord +// ---------------------------------------------------------------------------- +// +const TDesC& RsfwMountUtils::GetKeyWord(TInt iItem) + { + switch (iItem) + { + case EMountEntryItemName: + return KKId; + + case EMountEntryItemDrive: + return KKDrive; + + case EMountEntryItemUri: + return KKUri; + + case EMountEntryItemUserName: + return KKUserName; + + case EMountEntryItemPassword: + return KKPassword; + + default: + return KKId; + } + } +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/bwins/T_RSFW_TA_Basicu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/bwins/T_RSFW_TA_Basicu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,3 @@ +EXPORTS + ?CreateTestSuiteL@@YAPAVMEUnitTest@@XZ @ 1 NONAME ; class MEUnitTest * CreateTestSuiteL(void) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/eabi/T_RSFW_TA_Basicu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/eabi/T_RSFW_TA_Basicu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,3 @@ +EXPORTS + _Z16CreateTestSuiteLv @ 1 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/group/T_RSFW_TA_Basic.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/group/T_RSFW_TA_Basic.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for EUnit test app for MountMan API +* +*/ + +#include + +TARGET T_RSFW_TA_Basic.dll +TARGETTYPE dll +TARGETPATH /DigiaEUnit/Tests +UID 0x1000af5a 0x01700000 + +CAPABILITY ALL -TCB + +SOURCEPATH ../src +SOURCE T_RSFW_TA_BasicDllMain.cpp +SOURCE T_RSFW_TA_Basic.cpp + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE /epoc32/include/Digia/EUnit +SYSTEMINCLUDE /epoc32/include/ecom + +USERINCLUDE ../inc +USERINCLUDE ../../../../../remotefileengine/inc + +LIBRARY EUnit.lib +LIBRARY euser.lib +LIBRARY efsrv.lib +LIBRARY bafl.lib +LIBRARY ecom.lib +LIBRARY rsfwmountman.lib // mountman +LIBRARY estor.lib + +// End of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,20 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build info for module tests for RemoteStorage FW +* +*/ + +PRJ_MMPFILES +T_RSFW_TA_Basic.mmp +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/inc/T_RSFW_TA_Basic.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/inc/T_RSFW_TA_Basic.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,173 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Header file for EUnit test app for MountMan API +* +*/ + + +#ifndef __T_MOUNTMAN_H__ +#define __T_MOUNTMAN_H__ + +// EXTERNAL INCLUDES +#include +#include + +// INTERNAL INCLUDES + + +// FORWARD DECLARATIONS +class CDesC16Array; + +#include +#ifndef NONSHARABLE_CLASS + #define NONSHARABLE_CLASS(x) class x +#endif + +// CLASS DEFINITION +/** + * + * EUnitWizard generated test class. + * + */ +NONSHARABLE_CLASS( T_MountMan ) + : public CEUnitTestSuiteClass + { + public: // Constructors and destructors + + /** + * Two phase construction + */ + static T_MountMan* NewL(); + static T_MountMan* NewLC(); + /** + * Destructor + */ + ~T_MountMan(); + + private: // Constructors and destructors + + T_MountMan(); + void ConstructL(); + + public: // From observer interface + + + + private: // New methods + + void SetupL(); + + void Teardown(); + + // CRsfwMountEntry API + + void TestSetMountEntryL(); + + void TestSetItemL(); + + void TestSetItem2L(); + + void TestClearL(); + + void TestCloneL(); + + // CRsfwMountMan API + + void TestAddMountEntryL(); + + void TestAddMountEntry2L(); + + void TestAddMountEntry3L(); + + void TestEditMountEntryL(); + + void TestEditMountEntry2L(); + + void TestEditMountEntry3L(); + + void TestDeleteMountEntryL(); + + void TestDeleteMountEntry2L(); + + void TestDeleteMountEntry3L(); + + void TestMountEntryL(); + + void TestMountEntry2L(); + + void TestGetAllDrivesL(); + + void TestGetRemoteMountListL(); + + void TestGetMountNamesL(); + + void TestGetMountInfoL(); + + void TestIsAppOnBlackListL(); + + void TestSetMountConnectionStateL(); + + void TestRefreshDirectoryL(); + + void TestCancelRemoteTransferL(); + + void TestSetMountConnectionStateBlindL(); + + // TRsfwMountConfig API + + void TestExternalizeAndInternalizeL(); + + // utility functions + + TInt AddMountEntryL(TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap); + + TInt EditMountEntryL(TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap); + + void ClearAllMountsL(); + + TChar DriveToChar(TInt aDrive); + + TInt CompareArrays(CDesC16Array* aArray1, CDesC16Array* aArray2); + + TInt CheckEntryL(const CRsfwMountEntry* aEntry, + TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap); + + private: // Data + CRsfwMountMan* iMountMan; + RFs iFs; + EUNIT_DECLARE_TEST_TABLE; + + }; + +#endif // __T_MOUNTMAN_H__ + +// End of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/rom/T_RSFW_TA_Basic.pkg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/rom/T_RSFW_TA_Basic.pkg Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,32 @@ +; +; Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). +; All rights reserved. +; This component and the accompanying materials are made available +; under the terms of "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: package file +; +;Languages +&EN + +;Header +#{"RemoteStorageFW cases"}, (0x0B1ABCED),0,2,0 + +;Dependency for S60 3.0 +[0x101F7961], 0, 0, 0, {"Series60ProductID"} + +;Localised Vendor name +%{"Nokia/TP/ASP"} + +;Unique Vendor name +:"Nokia/TP/ASP" + +;Files to install +"\epoc32\release\armv5\urel\T_RSFW_TA_Basic.dll"-"!:\sys\bin\T_RSFW_TA_Basic.dll" diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/rom/t_rsfw_ta_basic.iby --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/rom/t_rsfw_ta_basic.iby Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,25 @@ +/* +* Copyright (c) 2007 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Image description file for avobjects +* +*/ + + + +#ifndef __T_RSFW_TA_BASIC_IBY__ +#define __T_RSFW_TA_BASIC_IBY__ + +file=ABI_DIR\BUILD_DIR\T_RSFW_TA_Basic.dll \sys\bin\T_RSFW_TA_Basic.dll + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/src/T_RSFW_TA_Basic.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/src/T_RSFW_TA_Basic.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1520 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Source file for EUnit test app for MountMan API +* +*/ + + +// CLASS HEADER +#include "T_RSFW_TA_Basic.h" + +// INCLUDES +#include +#include +#include +#include +#include +#include +#include "rsfwcontrol.h" +#include + +// CONSTRUCTION +T_MountMan* T_MountMan::NewL() + { + T_MountMan* self = T_MountMan::NewLC(); + CleanupStack::Pop(); + + return self; + } + +T_MountMan* T_MountMan::NewLC() + { + T_MountMan* self = new( ELeave ) T_MountMan(); + CleanupStack::PushL( self ); + + self->ConstructL(); + + return self; + } + +// Destructor (virtual by CBase) +T_MountMan::~T_MountMan() + { + iFs.Close(); + REComSession::FinalClose(); + } + +// Default constructor +T_MountMan::T_MountMan() + { + } + +// Second phase construct +void T_MountMan::ConstructL() + { + // The ConstructL from the base class CEUnitTestSuiteClass must be called. + // It generates the test case table. + CEUnitTestSuiteClass::ConstructL(); + + iFs.Connect(); + } + +// METHODS + +// ---------------------------------------------------------------------------- +// T_MountMan::SetupL +// ---------------------------------------------------------------------------- +// +void T_MountMan::SetupL( ) + { + iMountMan = CRsfwMountMan::NewL(0,NULL); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::Teardown +// ---------------------------------------------------------------------------- +// +void T_MountMan::Teardown( ) + { + delete iMountMan; + iMountMan = NULL; + } + +/////////////////////////////////////////////////////////////////////////////// +////// CRsfwMountEntry /////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////// + + +// ---------------------------------------------------------------------------- +// T_MountMan::TestSetMountEntryL +// Tests that it is not possible to create an entry with too long attributes +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestSetMountEntryL( ) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewLC(); + + // too long friendly name + TBuf longName; + longName.FillZ(longName.MaxLength()); + TRAP(err, mountEntry->SetItemL(EMountEntryItemName, longName)); + EUNIT_ASSERT(err == KErrArgument); + + // too long URI + TBuf longUri; + longUri.FillZ(longUri.MaxLength()); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUri, longUri)); + EUNIT_ASSERT(err == KErrArgument); + + // too long username + TBuf longUserName; + longUserName.FillZ(longUserName.MaxLength()); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUserName, longUserName)); + EUNIT_ASSERT(err == KErrArgument); + + // too long password + TBuf longPassword; + longPassword.FillZ(longPassword.MaxLength()); + TRAP(err, mountEntry->SetItemL(EMountEntryItemPassword, longPassword)); + EUNIT_ASSERT(err == KErrArgument); + + // too long IAP + TBuf longIap; + longIap.FillZ(longIap.MaxLength()); + TRAP(err, mountEntry->SetItemL(EMountEntryItemIap, longIap)); + EUNIT_ASSERT(err == KErrArgument); + + CleanupStack::PopAndDestroy(mountEntry); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestSetItemL +// Tests CRsfwMountEntry::SetItemL(TInt aIndex, const TDesC8& aValue); +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestSetItemL( ) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewLC(); + + // set entry items one by one + TRAP(err, mountEntry->SetItemL(EMountEntryItemName, _L8("name"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUri, _L8("http://url"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUserName, _L8("username"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemPassword, _L8("password"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemIap, _L8("iap"))); + EUNIT_ASSERT(err == KErrNone); + + // check the values + const HBufC* item = mountEntry->Item(EMountEntryItemName); + EUNIT_ASSERT((*item).Compare(_L("name")) == KErrNone); + item = mountEntry->Item(EMountEntryItemUri); + EUNIT_ASSERT((*item).Compare(_L("http://url")) == KErrNone); + item = mountEntry->Item(EMountEntryItemUserName); + EUNIT_ASSERT((*item).Compare(_L("username")) == KErrNone); + item = mountEntry->Item(EMountEntryItemPassword); + EUNIT_ASSERT((*item).Compare(_L("password")) == KErrNone); + item = mountEntry->Item(EMountEntryItemIap); + EUNIT_ASSERT((*item).Compare(_L("iap")) == KErrNone); + + CleanupStack::PopAndDestroy(mountEntry); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestSetItemL +// Tests CRsfwMountEntry::SetItemL(TInt aIndex, const TDesC& aValue); +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestSetItem2L( ) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewLC(); + + // set entry items one by one + TRAP(err, mountEntry->SetItemL(EMountEntryItemName, _L("name"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUri, _L("http://url"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUserName, _L("username"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemPassword, _L("password"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemIap, _L("iap"))); + EUNIT_ASSERT(err == KErrNone); + + // check the values + const HBufC* item = mountEntry->Item(EMountEntryItemName); + EUNIT_ASSERT((*item).Compare(_L("name")) == KErrNone); + item = mountEntry->Item(EMountEntryItemUri); + EUNIT_ASSERT((*item).Compare(_L("http://url")) == KErrNone); + item = mountEntry->Item(EMountEntryItemUserName); + EUNIT_ASSERT((*item).Compare(_L("username")) == KErrNone); + item = mountEntry->Item(EMountEntryItemPassword); + EUNIT_ASSERT((*item).Compare(_L("password")) == KErrNone); + item = mountEntry->Item(EMountEntryItemIap); + EUNIT_ASSERT((*item).Compare(_L("iap")) == KErrNone); + + CleanupStack::PopAndDestroy(mountEntry); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestClearL +// Tests CRsfwMountEntry::Clear +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestClearL( ) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewL(); + CleanupStack::PushL(mountEntry); + + // set entry items one by one + TRAP(err, mountEntry->SetItemL(EMountEntryItemName, _L("name"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUri, _L("http://url"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUserName, _L("username"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemPassword, _L("password"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemIap, _L("iap"))); + EUNIT_ASSERT(err == KErrNone); + + // clear the values + mountEntry->Clear(); + + // check whether the values are NULL + const HBufC* item = mountEntry->Item(EMountEntryItemName); + EUNIT_ASSERT(item == NULL); + item = mountEntry->Item(EMountEntryItemUri); + EUNIT_ASSERT(item == NULL); + item = mountEntry->Item(EMountEntryItemUserName); + EUNIT_ASSERT(item == NULL); + item = mountEntry->Item(EMountEntryItemPassword); + EUNIT_ASSERT(item == NULL); + item = mountEntry->Item(EMountEntryItemIap); + EUNIT_ASSERT(item == NULL); + + CleanupStack::PopAndDestroy(mountEntry); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestCloneL +// Tests CRsfwMountEntry::Clone +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestCloneL( ) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewL(); + CleanupStack::PushL(mountEntry); + + // set entry items one by one + TRAP(err, mountEntry->SetItemL(EMountEntryItemName, _L("name"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUri, _L("http://url"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemUserName, _L("username"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemPassword, _L("password"))); + EUNIT_ASSERT(err == KErrNone); + TRAP(err, mountEntry->SetItemL(EMountEntryItemIap, _L("iap"))); + EUNIT_ASSERT(err == KErrNone); + + // clone the entry + CRsfwMountEntry* clonedEntry = mountEntry->CloneL(); + CleanupStack::PushL(clonedEntry); + + // check the values in cloned entry + const HBufC* item = clonedEntry->Item(EMountEntryItemName); + EUNIT_ASSERT((*item).Compare(_L("name")) == KErrNone); + item = clonedEntry->Item(EMountEntryItemUri); + EUNIT_ASSERT((*item).Compare(_L("http://url")) == KErrNone); + item = clonedEntry->Item(EMountEntryItemUserName); + EUNIT_ASSERT((*item).Compare(_L("username")) == KErrNone); + item = clonedEntry->Item(EMountEntryItemPassword); + EUNIT_ASSERT((*item).Compare(_L("password")) == KErrNone); + item = clonedEntry->Item(EMountEntryItemIap); + EUNIT_ASSERT((*item).Compare(_L("iap")) == KErrNone); + + CleanupStack::PopAndDestroy(clonedEntry); + CleanupStack::PopAndDestroy(mountEntry); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestAddMountEntryL +// Tests that it is possible to add 9 mount entries, but not more +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestAddMountEntryL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(2, + _L("drivename2"), + DriveToChar(EDriveM), + _L("http://url2.com"), + _L("userName2"), + _L("password2"), + _L("iap2")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(3, + _L("drivename3"), + DriveToChar(EDriveN), + _L("http://url3.com"), + _L("userName3"), + _L("password3"), + _L("iap3")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(4, + _L("drivename4"), + DriveToChar(EDriveO), + _L("http://url4.com"), + _L("userName4"), + _L("password4"), + _L("iap4")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(5, + _L("drivename5"), + DriveToChar(EDriveP), + _L("http://url5.com"), + _L("userName5"), + _L("password5"), + _L("iap5")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(6, + _L("drivename6"), + DriveToChar(EDriveQ), + _L("http://url6.com"), + _L("userName6"), + _L("password6"), + _L("iap6")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(7, + _L("drivename7"), + DriveToChar(EDriveR), + _L("http://url7.com"), + _L("userName7"), + _L("password7"), + _L("iap7")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(8, + _L("drivename8"), + DriveToChar(EDriveS), + _L("http://url8.com"), + _L("userName8"), + _L("password8"), + _L("iap8")); + EUNIT_ASSERT(err == KErrNone); + // 10th drive should not pass! + err = AddMountEntryL(9, + _L("drivename9"), + DriveToChar(EDriveT), + _L("http://url9.com"), + _L("userName9"), + _L("password9"), + _L("iap9")); + EUNIT_ASSERT(err == KErrInUse); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestAddMountEntry2L +// Tests that it is not possible to add two entries with the same name +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestAddMountEntry2L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("thesamename"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(1, + _L("thesamename"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrInUse); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestAddMountEntry3L +// Tests that it is not possible to add two entries with the same drive letter +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestAddMountEntry3L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveK), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrInUse); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestEditMountEntryL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestEditMountEntryL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + err = EditMountEntryL(0, + _L("differentName"), + DriveToChar(EDriveK), + _L("http://different.com"), + _L("differentUserName"), + _L("differentPassword"), + _L("differentIap")); + EUNIT_ASSERT(err == KErrNone); + + const CRsfwMountEntry* entry = NULL; + TRAP (err, entry = iMountMan->MountEntryL(DriveToChar(EDriveK))); + EUNIT_ASSERT(err == KErrNone); + + err = CheckEntryL(entry, + 0, + _L("differentName"), + DriveToChar(EDriveK), + _L("http://different.com"), + _L("differentUserName"), + _L("differentPassword"), + _L("differentIap")); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestEditMountEntry2L +// tests that nonexising mount cannot be edited +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestEditMountEntry2L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + // try to edit nonexisting mount + err = EditMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url1.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNotFound); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestEditMountEntry3L +// tests that it is not allowed to change the name into the one +// that is already in use +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestEditMountEntry3L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + + // change the name of the 1st mount into the one used by the 2nd one + err = EditMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrInUse); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestDeleteMountEntryL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestDeleteMountEntryL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + + TRAP (err, iMountMan->DeleteMountEntryL(_L("drivename0"))); + EUNIT_ASSERT(err == KErrNone); + + TDriveList expectedList; + expectedList.Append(DriveToChar(EDriveL)); + + TDriveList returnedList; + TRAP(err,iMountMan->GetRemoteMountListL(returnedList)); + EUNIT_ASSERT(err == KErrNone); + + err = expectedList.Compare(returnedList); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestDeleteMountEntry2L +// Tests that deleting nonexisting mount entry does not hurt +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestDeleteMountEntry2L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + TRAP (err, iMountMan->DeleteMountEntryL(_L("drivename0"))); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestDeleteMountEntry3L +// tests DeleteMountEntryL(const TDesC& aName); +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestDeleteMountEntry3L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + + TRAP (err, iMountMan->DeleteMountEntryL(DriveToChar(EDriveK))); + EUNIT_ASSERT(err == KErrNone); + + TDriveList expectedList; + expectedList.Append(DriveToChar(EDriveL)); + + TDriveList returnedList; + TRAP(err,iMountMan->GetRemoteMountListL(returnedList)); + EUNIT_ASSERT(err == KErrNone); + + err = expectedList.Compare(returnedList); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestMountEntryL +// tests MountEntryL(TChar aDriveLetter) +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestMountEntryL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + + const CRsfwMountEntry* entry = NULL; + TRAP (err, entry = iMountMan->MountEntryL(DriveToChar(EDriveK))); + EUNIT_ASSERT(err == KErrNone); + + err = CheckEntryL(entry, + 0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + TRAP (err, entry = iMountMan->MountEntryL(DriveToChar(EDriveL))); + EUNIT_ASSERT(err == KErrNone); + + err = CheckEntryL(entry, + 1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestMountEntryL +// tests MountEntryL(const TDesC& aName) +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestMountEntry2L( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + + const CRsfwMountEntry* entry = NULL; + TRAP (err, entry = iMountMan->MountEntryL(_L("drivename0"))); + EUNIT_ASSERT(err == KErrNone); + + err = CheckEntryL(entry, + 0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + + TRAP (err, entry = iMountMan->MountEntryL(_L("drivename1"))); + EUNIT_ASSERT(err == KErrNone); + + err = CheckEntryL(entry, + 1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestGetAllDrivesL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestGetAllDrivesL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + // add some remote drives + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(2, + _L("drivename2"), + DriveToChar(EDriveM), + _L("http://url2.com"), + _L("userName2"), + _L("password2"), + _L("iap2")); + EUNIT_ASSERT(err == KErrNone); + + // prepare expected list + TDriveList expectedList; + + // first populate the list with local drives + TDriveList driveList; + err = iFs.DriveList(driveList); + EUNIT_ASSERT(err == KErrNone); + TInt i; + for ( i = EDriveC; i <= EDriveZ; i++) + { + if ( (driveList[i]) && (!(driveList[i] & KDriveAttRemote)) ) + { + TChar driveLetter; + err = iFs.DriveToChar(i, driveLetter); + EUNIT_ASSERT(err == KErrNone); + expectedList.Append(driveLetter); + } + } + // append remote drive that just has been added + expectedList.Append(DriveToChar(EDriveK)); + expectedList.Append(DriveToChar(EDriveL)); + expectedList.Append(DriveToChar(EDriveM)); + + TDriveList returnedList; + iMountMan->GetAllDrivesL(returnedList); + + err = expectedList.Compare(returnedList); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestGetRemoteMountListL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestGetRemoteMountListL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TDriveList expectedList; + TDriveList returnedList; + + TInt err; + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + expectedList.Append(DriveToChar(EDriveK)); + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + expectedList.Append(DriveToChar(EDriveL)); + err = AddMountEntryL(2, + _L("drivename2"), + DriveToChar(EDriveM), + _L("http://url2.com"), + _L("userName2"), + _L("password2"), + _L("iap2")); + EUNIT_ASSERT(err == KErrNone); + expectedList.Append(DriveToChar(EDriveM)); + + TRAP(err,iMountMan->GetRemoteMountListL(returnedList)); + EUNIT_ASSERT(err == KErrNone); + + err = expectedList.Compare(returnedList); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestGetMountNamesL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestGetMountNamesL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + // add some remote drives + err = AddMountEntryL(0, + _L("drivename0"), + DriveToChar(EDriveK), + _L("http://url0.com"), + _L("userName0"), + _L("password0"), + _L("iap0")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(1, + _L("drivename1"), + DriveToChar(EDriveL), + _L("http://url1.com"), + _L("userName1"), + _L("password1"), + _L("iap1")); + EUNIT_ASSERT(err == KErrNone); + err = AddMountEntryL(2, + _L("drivename2"), + DriveToChar(EDriveM), + _L("http://url2.com"), + _L("userName2"), + _L("password2"), + _L("iap2")); + EUNIT_ASSERT(err == KErrNone); + + // prepare expected list of names + CDesC16Array* expectedNames = new (ELeave) CDesC16ArraySeg(4); + CleanupStack::PushL(expectedNames); + expectedNames->AppendL(_L("drivename0")); + expectedNames->AppendL(_L("drivename1")); + expectedNames->AppendL(_L("drivename2")); + + CDesC16Array* names = new (ELeave) CDesC16ArraySeg(4); + CleanupStack::PushL(names); + TRAP (err, iMountMan->GetMountNamesL(names)); + + if (err == KErrNone) + { + err = CompareArrays(names, expectedNames); + } + CleanupStack::PopAndDestroy(names); + CleanupStack::PopAndDestroy(expectedNames); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestIsAppOnBlackListL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestIsAppOnBlackListL( ) + { + const TUid app1 = TUid::Uid(0x00000000); + const TUid app2 = TUid::Uid(0x11111111); + + TBool isOnList; + + isOnList = iMountMan->IsAppOnBlackList(app1); + EUNIT_ASSERT(isOnList == EFalse); + + isOnList = iMountMan->IsAppOnBlackList(app2); + EUNIT_ASSERT(isOnList == EFalse); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestGetMountInfoL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestGetMountInfoL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + // add remote drive + err = AddMountEntryL(0, + _L("drivename"), + DriveToChar(EDriveK), + _L("http://testurl"), + _L("username"), + _L("password"), + _L("")); + EUNIT_ASSERT(err == KErrNone); + + TRsfwMountInfo mountInfo; + TRAP (err, iMountMan->GetMountInfo(DriveToChar(EDriveK), mountInfo)); + EUNIT_ASSERT(err == KErrNone); + + // check as much mount info as possible at this point + EUNIT_ASSERT(mountInfo.iMountConfig.iDriveLetter == DriveToChar(EDriveK)); + EUNIT_ASSERT(mountInfo.iMountConfig.iName.Compare(_L("drivename")) == KErrNone); + EUNIT_ASSERT(mountInfo.iMountConfig.iUri.Compare(_L("http://testurl")) == KErrNone); + EUNIT_ASSERT(mountInfo.iMountConfig.iUserName.Compare(_L("username")) == KErrNone); + EUNIT_ASSERT(mountInfo.iMountConfig.iPassword.Compare(_L("password")) == KErrNone); + EUNIT_ASSERT(mountInfo.iMountStatus.iVolumeId == EDriveK); + EUNIT_ASSERT(mountInfo.iMountStatus.iMountState == KMountStateDormant); + EUNIT_ASSERT(mountInfo.iMountStatus.iConnectionState == KMountNotConnected); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestSetMountConnectionStateL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestSetMountConnectionStateL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + // add remote drive + err = AddMountEntryL(0, + _L("drivename"), + DriveToChar(EDriveK), + _L("http://url"), + _L("username"), + _L("password"), + _L("")); + EUNIT_ASSERT(err == KErrNone); + + // set to not connected + TRAP (err, iMountMan->SetMountConnectionState(DriveToChar(EDriveK), KMountNotConnected)); + EUNIT_ASSERT(err == KErrNone); + + // get mount info + TRsfwMountInfo mountInfo; + TRAP (err, iMountMan->GetMountInfo(DriveToChar(EDriveK), mountInfo)); + EUNIT_ASSERT(err == KErrNone); + + // check mount status + EUNIT_ASSERT(mountInfo.iMountStatus.iVolumeId == EDriveK); + EUNIT_ASSERT(mountInfo.iMountStatus.iMountState == KMountStateDormant); + EUNIT_ASSERT(mountInfo.iMountStatus.iConnectionState == KMountNotConnected); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestRefreshDirectoryL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestRefreshDirectoryL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err = iMountMan->RefreshDirectory(_L("K:\\nonexisting\\")); + EUNIT_ASSERT(err == KErrNotFound); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestCancelRemoteTransferL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestCancelRemoteTransferL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err = iMountMan->CancelRemoteTransfer(_L("K:\\nonexisting\\")); + EUNIT_ASSERT(err == KErrNotFound); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::TestSetMountConnectionStateBlindL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestSetMountConnectionStateBlindL( ) + { + // be sure no mount entries are in CenRep + ClearAllMountsL(); + + TInt err; + // add remote drive + err = AddMountEntryL(0, + _L("drivename"), + DriveToChar(EDriveK), + _L("http://url"), + _L("username"), + _L("password"), + _L("")); + EUNIT_ASSERT(err == KErrNone); + + // set to not connected + TRAP (err, iMountMan->SetMountConnectionStateBlind(DriveToChar(EDriveK), KMountNotConnected)); + EUNIT_ASSERT(err == KErrNone); + } + + +/////////////////////////////////////////////////////////////////////////////// +////// CRsfwMountEntry /////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////// + +// ---------------------------------------------------------------------------- +// T_MountMan::TestExternalizeAndInternalizeL +// Tests TRsfwMountConfig::ExternalizeL & TRsfwMountConfig::InternalizeL +// ---------------------------------------------------------------------------- +// +void T_MountMan::TestExternalizeAndInternalizeL( ) + { + TInt err; + TRsfwMountConfig mountConfig; + + mountConfig.iDriveLetter = DriveToChar(EDriveK); + mountConfig.iName.Copy(_L("name")); + mountConfig.iUri.Copy(_L("uri")); + mountConfig.iUserName.Copy(_L("username")); + mountConfig.iPassword.Copy(_L("password")); + mountConfig.iAuxData.Copy(_L("auxdata")); + mountConfig.iFlags = KMountFlagNull; + mountConfig.iInactivityTimeout = 10; + + RFile f; + CleanupClosePushL(f); + err = f.Replace(iFs, _L("C:\\mountmantest.txt"), EFileShareAny | EFileWrite); + EUNIT_ASSERT(err == KErrNone); + RFileWriteStream wStream(f); + CleanupClosePushL(wStream); + mountConfig.ExternalizeL(wStream); + CleanupStack::PopAndDestroy(&wStream); + CleanupStack::PopAndDestroy(&f); + + f.Open(iFs, _L("C:\\mountmantest.txt"), EFileShareAny | EFileRead); + CleanupClosePushL(f); + RFileReadStream rStream(f); + CleanupClosePushL(rStream); + TRsfwMountConfig anotherMountConfig; + anotherMountConfig.InternalizeL(rStream); + CleanupStack::PopAndDestroy(&rStream); + CleanupStack::PopAndDestroy(&f); + + EUNIT_ASSERT(anotherMountConfig.iDriveLetter == DriveToChar(EDriveK)); + EUNIT_ASSERT(anotherMountConfig.iName.Compare(_L("name")) == KErrNone); + EUNIT_ASSERT(anotherMountConfig.iUri.Compare(_L("uri")) == KErrNone); + EUNIT_ASSERT(anotherMountConfig.iUserName.Compare(_L("username")) == KErrNone); + EUNIT_ASSERT(anotherMountConfig.iPassword.Compare(_L("password")) == KErrNone); + EUNIT_ASSERT(anotherMountConfig.iAuxData.Compare(_L("auxdata")) == KErrNone); + EUNIT_ASSERT(anotherMountConfig.iFlags == KMountFlagNull); + EUNIT_ASSERT(anotherMountConfig.iInactivityTimeout == 10); + } + +/////////////////////////////////////////////////////////////////////////////// +////// Utility functions ////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////// + +// ---------------------------------------------------------------------------- +// T_MountMan::AddMountEntryL +// Helping function: based on given parameters creates CRsfwMountEntry object +// and attempts to add it using AddMountEntry() +// ---------------------------------------------------------------------------- +// +TInt T_MountMan::AddMountEntryL(TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewLC(); + TRAP (err, mountEntry->SetEntryL(aIndex, + aName, + aDriveLetter, + aUri, + aUserName, + aPassword, + aIap)); + + if (err != KErrNone) + { + CleanupStack::PopAndDestroy(mountEntry); + return err; + } + + // release ownership and add entry + CleanupStack::Pop(mountEntry); + TRAP (err, iMountMan->AddMountEntryL(mountEntry)); + return err; + } + +// ---------------------------------------------------------------------------- +// T_MountMan::EditMountEntryL +// Helping function: based on given parameters creates CRsfwMountEntry object +// and attempts to edit it using EditMountEntry() +// ---------------------------------------------------------------------------- +// +TInt T_MountMan::EditMountEntryL(TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap) + { + TInt err; + CRsfwMountEntry* mountEntry; + mountEntry = CRsfwMountEntry::NewLC(); + TRAP (err, mountEntry->SetEntryL(aIndex, + aName, + aDriveLetter, + aUri, + aUserName, + aPassword, + aIap)); + + if (err != KErrNone) + { + CleanupStack::PopAndDestroy(mountEntry); + return err; + } + + // release ownership and edit entry + CleanupStack::Pop(mountEntry); + TRAP (err, iMountMan->EditMountEntryL(mountEntry)); + return err; + } + +// ---------------------------------------------------------------------------- +// T_MountMan::ClearAllMountsL +// Deletes all mount entries +// ---------------------------------------------------------------------------- +// +void T_MountMan::ClearAllMountsL( ) + { + TInt err; + CDesC16Array* names = new (ELeave) CDesC16ArraySeg(4); + CleanupStack::PushL(names); + TRAP (err, iMountMan->GetMountNamesL(names)); + if (err == KErrNone) + { + TInt i; + for ( i = 0; i < names->Count(); i++) + { + TRAP (err, iMountMan->DeleteMountEntryL((*names)[i])); + if (err != KErrNone) + { + break; + } + } + } + names->Reset(); + CleanupStack::PopAndDestroy(names); + EUNIT_ASSERT(err == KErrNone); + } + +// ---------------------------------------------------------------------------- +// T_MountMan::DriveToChar +// ---------------------------------------------------------------------------- +// +TChar T_MountMan::DriveToChar(TInt aDrive) + { + TChar c; + TInt err = iFs.DriveToChar(aDrive, c); + EUNIT_ASSERT(err == KErrNone); + return c; + } + +// ---------------------------------------------------------------------------- +// T_MountMan::CompareArrays +// Compares two arrays e.g. with mount names +// Note that order DOES matter! +// ---------------------------------------------------------------------------- +// +TInt T_MountMan::CompareArrays(CDesC16Array* aArray1, CDesC16Array* aArray2) + { + if (aArray1->Count() != aArray2->Count()) + { + return KErrNotFound; + } + TInt i; + for ( i = 0; i < aArray1->Count(); i++ ) + { + if ((*aArray1)[i].Compare((*aArray2)[i]) != KErrNone) + { + return KErrNotFound; + } + } + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// T_MountMan::CheckEntryL +// Checks whether all fields in given entry matches +// ---------------------------------------------------------------------------- +// +TInt T_MountMan::CheckEntryL(const CRsfwMountEntry* aEntry, + TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUri, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap) + { + TInt err; + CRsfwMountEntry* entry; + entry = CRsfwMountEntry::NewLC(); + TRAP (err, entry->SetEntryL(aIndex, + aName, + aDriveLetter, + aUri, + aUserName, + aPassword, + aIap)); + if (err != KErrNone) + { + CleanupStack::PopAndDestroy(entry); + return err; + } + + TInt i; + for ( i = EMountEntryItemIndex; i < EMountEntryItemCount; i++ ) + { + const HBufC* item1 = aEntry->Item(i); + const HBufC* item2 = entry->Item(i); + if ( (item1 && !item2) || + (item2 && !item1) || + (item1 && item2 && (*item1).Compare(*item2)!=KErrNone) ) + { + CleanupStack::PopAndDestroy(entry); + return KErrNotFound; + } + } + + CleanupStack::PopAndDestroy(entry); + return KErrNone; + } + + +// TEST TABLE + +EUNIT_BEGIN_TEST_TABLE( + T_MountMan, + "Add test suite description here.", + "MODULE" ) + +EUNIT_TEST( + "SetMountEntryL - set mount entry with too long attributes", + "RsfwMountMan", + "SetMountEntryL", + "FUNCTIONALITY", + SetupL, TestSetMountEntryL, Teardown) + +EUNIT_TEST( + "TestSetItemL - set mount items - SetItemL(TInt aIndex, const TDesC8& aValue)", + "RsfwMountMan", + "SetItemL", + "FUNCTIONALITY", + SetupL, TestSetItemL, Teardown) + +EUNIT_TEST( + "TestSetItemL - set mount items - SetItemL(TInt aIndex, const TDesC& aValue)", + "RsfwMountMan", + "SetItemL", + "FUNCTIONALITY", + SetupL, TestSetItem2L, Teardown) + +EUNIT_TEST( + "TestClearL - clear mount entry", + "RsfwMountMan", + "Clear", + "FUNCTIONALITY", + SetupL, TestClearL, Teardown) + +EUNIT_TEST( + "TestCloneL - clone mount entry", + "RsfwMountMan", + "CloneL", + "FUNCTIONALITY", + SetupL, TestCloneL, Teardown) + +EUNIT_TEST( + "AddMountEntryL - add max number of mounts", + "RsfwMountMan", + "AddMountEntryL", + "FUNCTIONALITY", + SetupL, TestAddMountEntryL, Teardown) + +EUNIT_TEST( + "AddMountEntryL - add two mounts with the same name", + "RsfwMountMan", + "AddMountEntryL", + "FUNCTIONALITY", + SetupL, TestAddMountEntry2L, Teardown) + +EUNIT_TEST( + "AddMountEntryL - add two mounts with the same drive letter", + "RsfwMountMan", + "AddMountEntryL", + "FUNCTIONALITY", + SetupL, TestAddMountEntry3L, Teardown) + +EUNIT_TEST( + "EditMountEntryL - basic test", + "RsfwMountMan", + "EditMountEntryL", + "FUNCTIONALITY", + SetupL, TestEditMountEntryL, Teardown) + +EUNIT_TEST( + "EditMountEntryL - test nonexisting mount", + "RsfwMountMan", + "EditMountEntryL", + "FUNCTIONALITY", + SetupL, TestEditMountEntry2L, Teardown) + +EUNIT_TEST( + "EditMountEntryL - test the name that is in use", + "RsfwMountMan", + "EditMountEntryL", + "FUNCTIONALITY", + SetupL, TestEditMountEntry3L, Teardown) + +EUNIT_TEST( + "DeleteMountEntryL - basic test", + "RsfwMountMan", + "DeleteMountEntryL", + "FUNCTIONALITY", + SetupL, TestDeleteMountEntryL, Teardown) + +EUNIT_TEST( + "DeleteMountEntryL - test nonexisting mount", + "RsfwMountMan", + "DeleteMountEntryL", + "FUNCTIONALITY", + SetupL, TestDeleteMountEntry2L, Teardown) + +EUNIT_TEST( + "DeleteMountEntryL - by drive letter", + "RsfwMountMan", + "DeleteMountEntryL", + "FUNCTIONALITY", + SetupL, TestDeleteMountEntry3L, Teardown) + +EUNIT_TEST( + "TestMountEntryL - basic test", + "RsfwMountMan", + "MountEntryL", + "FUNCTIONALITY", + SetupL, TestMountEntryL, Teardown) + +EUNIT_TEST( + "TestMountEntryL - test nonexisting mount", + "RsfwMountMan", + "MountEntryL", + "FUNCTIONALITY", + SetupL, TestMountEntry2L, Teardown) + +EUNIT_TEST( + "GetAllDrivesL - basic test", + "RsfwMountMan", + "GetAllDrivesL", + "FUNCTIONALITY", + SetupL, TestGetAllDrivesL, Teardown) + +EUNIT_TEST( + "GetMountNamesL - basic test", + "RsfwMountMan", + "GetMountNamesL", + "FUNCTIONALITY", + SetupL, TestGetMountNamesL, Teardown) + +EUNIT_TEST( + "GetRemoteMountListL - basic test", + "RsfwMountMan", + "GetRemoteMountListL", + "FUNCTIONALITY", + SetupL, TestGetRemoteMountListL, Teardown) + +EUNIT_TEST( + "IsAppOnBlackList - basic test", + "RsfwMountMan", + "IsAppOnBlackList", + "FUNCTIONALITY", + SetupL, TestIsAppOnBlackListL, Teardown) + +EUNIT_TEST( + "GetMountInfoL - basic test", + "RsfwMountMan", + "GetMountInfoL", + "FUNCTIONALITY", + SetupL, TestGetMountInfoL, Teardown) + +EUNIT_TEST( + "SetMountConnectionStateL - basic test", + "RsfwMountMan", + "SetMountConnectionStateL", + "FUNCTIONALITY", + SetupL, TestSetMountConnectionStateL, Teardown) + +EUNIT_TEST( + "RefreshDirectory - basic test", + "RsfwMountMan", + "RefreshDirectory", + "FUNCTIONALITY", + SetupL, TestRefreshDirectoryL, Teardown) + +EUNIT_TEST( + "CancelRemoteTransfer - basic test", + "RsfwMountMan", + "CancelRemoteTransfer", + "FUNCTIONALITY", + SetupL, TestCancelRemoteTransferL, Teardown) + +EUNIT_TEST( + "SetMountConnectionStateBlindL - basic test", + "RsfwMountMan", + "SetMountConnectionStateBlindL", + "FUNCTIONALITY", + SetupL, TestSetMountConnectionStateBlindL, Teardown) + +EUNIT_TEST( + "Externalize and internalize - basic test", + "RsfwMountMan", + "InternalizeL, ExternalizeL", + "FUNCTIONALITY", + SetupL, TestExternalizeAndInternalizeL, Teardown) + +EUNIT_END_TEST_TABLE + +// END OF FILE diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountmanager/tsrc/public/basic/src/T_RSFW_TA_BasicDllMain.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountmanager/tsrc/public/basic/src/T_RSFW_TA_BasicDllMain.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,41 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Source file for EUnit test app for MountMan API +* +*/ + + +// CLASS HEADER +#include "T_RSFW_TA_Basic.h" + +// EXTERNAL INCLUDES +#include + +/** + * Test suite factory function. + */ +EXPORT_C MEUnitTest* CreateTestSuiteL() + { + return T_MountMan::NewL(); + } + + + +// END OF FILE + + + + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/bwins/rsfwconfigu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/bwins/rsfwconfigu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,9 @@ +EXPORTS + ?Get@CRsfwConfig@@QAEHIAAH@Z @ 1 NONAME ; int CRsfwConfig::Get(unsigned int, int &) + ?Get@CRsfwConfig@@QAEHIAAVTDes16@@@Z @ 2 NONAME ; int CRsfwConfig::Get(unsigned int, class TDes16 &) + ?IsFalse@CRsfwConfig@@QAEHI@Z @ 3 NONAME ; int CRsfwConfig::IsFalse(unsigned int) + ?IsTrue@CRsfwConfig@@QAEHI@Z @ 4 NONAME ; int CRsfwConfig::IsTrue(unsigned int) + ?NewL@CRsfwConfig@@SAPAV1@VTUid@@@Z @ 5 NONAME ; class CRsfwConfig * CRsfwConfig::NewL(class TUid) + ?Set@CRsfwConfig@@QAEHIAAH@Z @ 6 NONAME ; int CRsfwConfig::Set(unsigned int, int &) + ?Set@CRsfwConfig@@QAEHIAAVTDes16@@@Z @ 7 NONAME ; int CRsfwConfig::Set(unsigned int, class TDes16 &) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/bwins/rsfwmountstoreu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/bwins/rsfwmountstoreu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,13 @@ +EXPORTS + ??1CRsfwMountStore@@UAE@XZ @ 1 NONAME ; CRsfwMountStore::~CRsfwMountStore(void) + ?AddEntryL@CRsfwMountStore@@QAEXPAVCRsfwMountEntry@@@Z @ 2 NONAME ; void CRsfwMountStore::AddEntryL(class CRsfwMountEntry *) + ?CommitL@CRsfwMountStore@@QAEXXZ @ 3 NONAME ; void CRsfwMountStore::CommitL(void) + ?GetDriveLettersL@CRsfwMountStore@@QAEXAAV?$TBuf8@$0BK@@@@Z @ 4 NONAME ; void CRsfwMountStore::GetDriveLettersL(class TBuf8<26> &) + ?GetNamesL@CRsfwMountStore@@QAEXPAVCDesC16Array@@@Z @ 5 NONAME ; void CRsfwMountStore::GetNamesL(class CDesC16Array *) + ?LoadEntriesL@CRsfwMountStore@@QAEXXZ @ 6 NONAME ; void CRsfwMountStore::LoadEntriesL(void) + ?LookupEntryByDriveL@CRsfwMountStore@@QAEPBVCRsfwMountEntry@@VTChar@@@Z @ 7 NONAME ; class CRsfwMountEntry const * CRsfwMountStore::LookupEntryByDriveL(class TChar) + ?LookupEntryByNameL@CRsfwMountStore@@QAEPBVCRsfwMountEntry@@ABVTDesC16@@@Z @ 8 NONAME ; class CRsfwMountEntry const * CRsfwMountStore::LookupEntryByNameL(class TDesC16 const &) + ?NewL@CRsfwMountStore@@SAPAV1@PAVMRsfwMountStoreObserver@@@Z @ 9 NONAME ; class CRsfwMountStore * CRsfwMountStore::NewL(class MRsfwMountStoreObserver *) + ?RemoveEntryL@CRsfwMountStore@@QAEXABVTDesC16@@@Z @ 10 NONAME ; void CRsfwMountStore::RemoveEntryL(class TDesC16 const &) + ?RemoveEntryL@CRsfwMountStore@@QAEXVTChar@@@Z @ 11 NONAME ; void CRsfwMountStore::RemoveEntryL(class TChar) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/eabi/rsfwconfigu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/eabi/rsfwconfigu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,11 @@ +EXPORTS + _ZN11CRsfwConfig3GetEjR6TDes16 @ 1 NONAME + _ZN11CRsfwConfig3GetEjRi @ 2 NONAME + _ZN11CRsfwConfig3SetEjR6TDes16 @ 3 NONAME + _ZN11CRsfwConfig3SetEjRi @ 4 NONAME + _ZN11CRsfwConfig4NewLE4TUid @ 5 NONAME + _ZN11CRsfwConfig6IsTrueEj @ 6 NONAME + _ZN11CRsfwConfig7IsFalseEj @ 7 NONAME + _ZTI11CRsfwConfig @ 8 NONAME ; ## + _ZTV11CRsfwConfig @ 9 NONAME ; ## + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/eabi/rsfwmountstoreu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/eabi/rsfwmountstoreu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,17 @@ +EXPORTS + _ZN15CRsfwMountStore12LoadEntriesLEv @ 1 NONAME + _ZN15CRsfwMountStore12RemoveEntryLE5TChar @ 2 NONAME + _ZN15CRsfwMountStore12RemoveEntryLERK7TDesC16 @ 3 NONAME + _ZN15CRsfwMountStore16GetDriveLettersLER5TBuf8ILi26EE @ 4 NONAME + _ZN15CRsfwMountStore18LookupEntryByNameLERK7TDesC16 @ 5 NONAME + _ZN15CRsfwMountStore19LookupEntryByDriveLE5TChar @ 6 NONAME + _ZN15CRsfwMountStore4NewLEP23MRsfwMountStoreObserver @ 7 NONAME + _ZN15CRsfwMountStore7CommitLEv @ 8 NONAME + _ZN15CRsfwMountStore9AddEntryLEP15CRsfwMountEntry @ 9 NONAME + _ZN15CRsfwMountStore9GetNamesLEP12CDesC16Array @ 10 NONAME + _ZN15CRsfwMountStoreD0Ev @ 11 NONAME + _ZN15CRsfwMountStoreD1Ev @ 12 NONAME + _ZN15CRsfwMountStoreD2Ev @ 13 NONAME + _ZTI15CRsfwMountStore @ 14 NONAME ; ## + _ZTV15CRsfwMountStore @ 15 NONAME ; ## + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,29 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build info for Central Repository related subcomponents +* +*/ + +#include + +PRJ_EXPORTS +../inc/rsfwmountstore.h |../../inc/rsfwmountstore.h +../inc/mdebug.h |../../inc/mdebug.h +../inc/rsfwconfig.h |../../inc/rsfwconfig.h + +PRJ_MMPFILES +rsfwmountstore.mmp +rsfwconfig.mmp + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/group/rsfwconfig.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/group/rsfwconfig.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,41 @@ +/* +* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project RSFW Config +* +*/ + +#include +TARGET rsfwconfig.dll + +TARGETTYPE dll + +CAPABILITY ALL -TCB + +UID 0x1000008d 0x101F976D + +SOURCEPATH ../src + +SOURCE rsfwconfig.cpp + +LANG SC + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY centralrepository.lib +LIBRARY euser.lib + +DEFFILE rsfwconfig.def diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/group/rsfwmountstore.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/group/rsfwmountstore.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,48 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project mount store API +* +*/ + +#include +TARGET rsfwmountstore.dll + +TARGETTYPE dll + +UID 0x1000008d 0x101F9773 + + +CAPABILITY CAP_GENERAL_DLL + + +SOURCEPATH ../src +SOURCE rsfwmountstore.cpp + +LANG SC + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY bafl.lib +LIBRARY centralrepository.lib +LIBRARY cenrepnotifhandler.lib +LIBRARY efsrv.lib +LIBRARY euser.lib +LIBRARY avkon.lib +LIBRARY rsfwmountman.lib + +DEFFILE rsfwmountstore.def +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/inc/mdebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/inc/mdebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,93 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug printing to a log file + * +*/ + + +#ifndef MDEBUG_H +#define MDEBUG_H + +// INCLUDES +#include + +#include "mydebug.h" + +// Take care that the correct mydebug.h will be included +// In mydebug.h in your module inc directory, +// define your application-specific configuration like this: +// ---------------------------------------------------------- +// Debug file - debug output is disabled if the parent dir does not exist +// _LIT(KDebugFileName, "C:\\logs\\remotefileengine\\remotefileengine.txt"); + +// Replace the current debug file - if not defined appends to the file +#ifndef APPEND_TO_DEBUG_FILE +#define REPLACE_DEBUG_FILE +#endif + +// Maximum formatted size resulting from a single DEBUG* call +#ifndef MAX_DEBUG_STRING_LENGTH +#define MAX_DEBUG_STRING_LENGTH 4096 +#endif +// ---------------------------------------------------------- + +// FUNCTION PROTOTYPES +void DebugInit(TBool aDebugSuspended = EFalse); +void SetDebugEnabled(TBool aValue); +void SetDebugSuspended(TBool aValue); +void DebugStringNarrowL(const char* aFmt, ...); +void DebugStringWideL(const char* aFmt, ...); +void DebugBufferL(const TDesC8& aBuf); +void DebugBufferL(const TDesC& aBuf); +void DebugTimeL(const TTime& aTime); + +// MACROS +// If you output one or more narrow descriptors by using '%S', +// use DEBUGSTRING8 +// else if you output one or more unicode descriptors by using '%S', +// use DEBUGSTRING16 +// else +// use DEBUGSTRING +// +// Narrow and unicode cannot be mixed in a single DEBUGSTRINGx call. + +#ifdef _DEBUG +#define DEBUGINIT() DebugInit() +#define DEBUGINITSUSPENDED() DebugInit(ETrue) +#define DEBUGENABLE() SetDebugEnabled(ETrue) +#define DEBUGDISABLE() SetDebugEnabled(EFalse) +#define DEBUGSUSPEND() SetDebugSuspended(ETrue) +#define DEBUGCONTINUE() SetDebugSuspended(EFalse) +#define DEBUGSTRING(x) DebugStringNarrowL x +#define DEBUGSTRING8(x) DebugStringNarrowL x +#define DEBUGSTRING16(x) DebugStringWideL x +#define DEBUGBUFFER(x) DebugBufferL x +#define DEBUGTIME(x) DebugTimeL x +#else +#define DEBUGINIT() +#define DEBUGINITSUSPENDED() +#define DEBUGENABLE() +#define DEBUGDISABLE() +#define DEBUGSUSPEND() +#define DEBUGCONTINUE() +#define DEBUGSTRING(x) +#define DEBUGSTRING8(x) +#define DEBUGSTRING16(x) +#define DEBUGBUFFER(x) +#define DEBUGTIME(x) +#endif + +#endif // MDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/inc/rsfwconfig.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/inc/rsfwconfig.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,131 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw operational parameter config + * (not for mount configurations) + * +*/ + + +#ifndef CRSFWCONFIG_H +#define CRSFWCONFIG_H + +// INCLUDES +#include + +// CONSTANTS +const TUid KCRUidRsfwCtrl = { 0x101F9775 }; +const TInt KMaxRsfwConfItemLength = 128; + +namespace RsfwConfigKeys + { + const TUint KRsfwDefaultDrive = 1; + const TUint KCacheDirectoryPath = 2; + const TUint KMaxEntryCount = 3; + const TUint KMaxCacheSize = 4; + const TUint KFileCacheValidity = 5; + const TUint KDirCacheValidity = 6; + const TUint KCachingMode = 7; + const TUint KRecognizerLimit = 8; + const TUint KAudMpegLimit = 9; + const TUint KImgJpegLimit = 10; + const TUint KRsfwReserved1 = 11; + const TUint KLockTimeout = 12; + const TUint KInactivityTimeout = 13; + } + +// FORWARD DECLARATIONS +class CRepository; + +// CLASS DECLARATION + +/** + * Configuration API for Rsfw operation + * + * @lib rsfwconfig.lib + * @since Series 60 3.1 + */ + +class CRsfwConfig: public CBase + { +public: +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + IMPORT_C static CRsfwConfig* NewL(TUid aRepositoryUid); + + /** + * Destructor. + */ + virtual ~CRsfwConfig(); + +public: // New functions + /** + Sets numeric value. + @param aId parameter id + @return error code + */ + IMPORT_C TInt Set(TUint aId, TInt& aValue); + + /** + Sets string value. + @param aId parameter id + @return error code + */ + IMPORT_C TInt Set(TUint aId, TDes& aValue); + + /** + Gets numeric value. + @param aId parameter id + @return error code + */ + IMPORT_C TInt Get(TUint aId, TInt& aValue); + + /** + Gets string value. + @param aId parameter id + @return error code + */ + IMPORT_C TInt Get(TUint aId, TDes& aValue); + + /** + Checks whether a string value is True. + Gets boolean value: return true iff string starts with '1' | 'Y' | 'T' + (case-insensitive). + If the repository value is missing returns False. + @param aId parameter id + @return boolean + */ + IMPORT_C TBool IsTrue(TUint aId); + + /** + Checks whether a string value is False. + Gets boolean value: returns true iff string starts with '0' | 'N' | 'F' + (case-insensitive) + If the repository or value is missing returns False. + @param aId parameter id + @return boolean + */ + IMPORT_C TBool IsFalse(TUint aId); + +private: + void ConstructL(TUid aRepositoryId); + +private: // Data + CRepository* iRepository; + }; + +#endif // CRSFWCONFIG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/inc/rsfwmountstore.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/inc/rsfwmountstore.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,193 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mount configuration repository management + * +*/ + + +#ifndef CRSFWMOUNTSTORE_H +#define CRSFWMOUNTSTORE_H + +// INCLUDES +#include + +// DATA TYPES +// Event types for MMountStoreObserver +enum TMountStoreEvent + { + EMountStoreEventMountConfigurationChanged = 1 + }; + +// FORWARD DECLARATIONS +class CRepository; +class CDesC16Array; +class CRsfwMountEntry; + +// CLASS DECLARATION +/** + * Interface for receiving mounting events + * + * @lib mountman.dll + * @since Series 60 3.1 + */ + +class MRsfwMountStoreObserver + { +public: + /** + * Handles an event emanating from a CRsfwMountStore class. + * Used for notifying about changes in the configurations + * + * @param aEventType type of the event + * @param aStatus status code + * @param aArg miscellaneous arguments + */ + virtual void HandleMountStoreEvent(TMountStoreEvent aEvent, + TInt aStatus, + TAny* aArg) = 0; + }; + +// CLASS DECLARATION +/** + * Maintain permanent storage of mount configuration entries + * + * @lib mountstore.lib + * @since Series 60 3.1 + */ +class CRsfwMountStore: public CBase, public MCenRepNotifyHandlerCallback + { +public: // Constructors and destructor + /** + * Two-phased constructor. + * At the construction phase, all mount configurations are loaded + * into memory (that is, LoadEntries() is called). + * @param aMountStoreObserver store change notification handler + */ + IMPORT_C static CRsfwMountStore* NewL( + MRsfwMountStoreObserver* aMountStoreObserver); + + CRsfwMountStore(); + + /** + * Destructor. + */ + IMPORT_C virtual ~CRsfwMountStore(); + +public: // New functions + /** + * (Re)loads the mount configurations into memory from the repository. + * + */ + IMPORT_C void LoadEntriesL(); + + /** + * Gets a list of friendly names of all mount configurations stored + * in Central Repository + * + * @param aNames returned information + * @return nothing + * this array must be created by the caller + */ + IMPORT_C void GetNamesL(CDesC16Array* aNames); + + /** + * Gets remote drive letters of all mount configurations stored + * in Central Repository (in correct order) + * + * @param aDriveList returned information + * @return nothing + * this array must be created by the caller + */ + IMPORT_C void GetDriveLettersL(TDriveList& aDriveList); + + + /** + * Finds the configuration configuration entry by drive letter. + * @param aDrive drive letter + * @return a pointer to the configuration entry or NULL if not found + */ + IMPORT_C const CRsfwMountEntry* LookupEntryByDriveL(TChar aDriveLetter); + + /** + * Finds the mount configuration entry by friendly name. + * The ownership of the entry is not moved + * @param aName friendly name + * @return a pointer to the configuration entry or NULL if not found + * the ownership of the pointer is NOT transferred + */ + IMPORT_C const CRsfwMountEntry* LookupEntryByNameL(const TDesC& aName); + + /** + * Adds a new mount configuration entry in the list of entries. + * If an entry with the same name already exists, + * that entry is replaced with the new entry. + * The entry is positioned among the existing entries + * according to the EMountEntryItemIndex value + * The drive letter in aMountEntry must be set before calling. + * @param aMountEntry mount configuration entry - + * the ownership of the pointer is transferred to CMountStore + * @leave KErrArgument drive letter not set + * @leave KErrInUse all nine allowed remote drives are in use + * + */ + IMPORT_C void AddEntryL(CRsfwMountEntry* aMountEntry); + + /** + * Removes a mount configuration entry from the list of entries. + * Nothing is done if no entry with the name is found + * @param aDriveLetter name of the entry to be removed + */ + IMPORT_C void RemoveEntryL(const TDesC& aName); + + /** + * Removes a mount configuration entry from the list of entries. + * Nothing is done if no entry with the drive letter is found. + * @param aDriveLetter name of the entry to be removed + */ + IMPORT_C void RemoveEntryL(const TChar aDriveLetter); + + /** + * Saves the mount configuration entries permanently. + * This function must be called after changes have been made in the + * mount configuration entries in order to store the cahnges permanently. + */ + IMPORT_C void CommitL(); + +private: + void ConstructL(MRsfwMountStoreObserver* aMountStoreObserver); + void ReloadEntriesL(); + void AddToRepositoryL(const CRsfwMountEntry* aMountEntry); + void RemoveFromRepositoryL(const CRsfwMountEntry* aMountEntry); + void ClearRepositoryL(); + void SynchronizeIndexesL(); + // From MCenRepNotifyHandlerCallback + void HandleNotifyError(TUint32 aId, + TInt aError, + CCenRepNotifyHandler* aHandler); + void HandleNotifyGeneric(TUint32 aId); + TInt MapDriveLetterToRecordIdL(const HBufC* drive); + + +private: // Data + RPointerArray iMountEntries; + CRepository* iRepository; + CCenRepNotifyHandler* iCenRepNotifyHandler; + TBool iReceivingCenRepNotifications; + TBool iCenRepChanged; + MRsfwMountStoreObserver* iMountStoreObserver; + }; + +#endif // CRSFWMOUNTSTORE_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/src/rsfwconfig.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/src/rsfwconfig.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,176 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Rsfw operational parameter config using central repository + * +*/ + + +// INCLUDE FILES +#include + +#include "rsfwconfig.h" + + +// =========================== MEMBER FUNCTIONS =============================== +// ---------------------------------------------------------------------------- +// CRsfwConfig::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwConfig::ConstructL(TUid aRepositoryUid) + { + TRAPD(err, iRepository = CRepository::NewL(aRepositoryUid)); + if (err) + { + iRepository = NULL; + } + } + +// ---------------------------------------------------------------------------- +// RsfwConfig::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwConfig* CRsfwConfig::NewL(TUid aRepositoryUid) + { + CRsfwConfig* self = new (ELeave) CRsfwConfig(); + CleanupStack::PushL(self); + self->ConstructL(aRepositoryUid); + CleanupStack::Pop(self); + return self; + } + +// Destructor +CRsfwConfig::~CRsfwConfig() + { + delete iRepository; + } + +// ---------------------------------------------------------------------------- +// CRsfwConfig::Set +// See RsfwConfig.h +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwConfig::Set(TUint aId, TInt& aValue) + { + if (iRepository) + { + return iRepository->Set(aId, aValue); + } + else + { + return KErrNotFound; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConfig::Set +// See RsfwConfig.h +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwConfig::Set(TUint aId, TDes& aValue) + { + if (iRepository) + { + return iRepository->Set(aId, aValue); + } + else + { + return KErrNotFound; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConfig::Get +// See RsfwConfig.h +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwConfig::Get(TUint aId, TInt& aValue) + { + if (iRepository) + { + return iRepository->Get(aId, aValue); + } + else + { + return KErrNotFound; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConfig::Get +// See RsfwConfig.h +// --------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwConfig::Get(TUint aId, TDes& aValue) + { + if (iRepository) + { + return iRepository->Get(aId, aValue); + } + else + { + return KErrNotFound; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConfig::IsTrue +// See RsfwConfig.h +// ---------------------------------------------------------------------------- +// +EXPORT_C TBool CRsfwConfig::IsTrue(TUint aId) + { + if (iRepository) + { + TBuf value; + TInt err = iRepository->Get(aId, value); + if (err == KErrNone) + { + TChar c = value[0]; + c.UpperCase(); + if ((c == '1') || (c == 'Y') || (c == 'T')) + { + return ETrue; + } + } + } + return EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwConfig::IsFalse +// See RsfwConfig.h +// ---------------------------------------------------------------------------- +// +EXPORT_C TBool CRsfwConfig::IsFalse(TUint aId) + { + if (iRepository) + { + TBuf value; + TInt err = iRepository->Get(aId, value); + if (err == KErrNone) + { + TChar c = value[0]; + c.UpperCase(); + if ((c == '0') || (c == 'N') || (c == 'F')) + { + return ETrue; + } + } + } + return EFalse; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/mountstore/src/rsfwmountstore.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/mountstore/src/rsfwmountstore.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,556 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Access mount configuration storage + * +*/ + + +// In order to use the central repository, +// The repository initialization file must be put in +// [epoc32/release/winscw/udeb/]z/private/10202be9/101F9775.txt + +// The mount configurations form a table where +// individual configuration entries form the rows and +// the entry items form the columns. +// - rows are indexed with the upper 24 bits of the Id, starting from 1. +// - columns are indexed by the lower 8 bits of the Id, starting from 1. +// +// Row number 0 is reserved for system config name/value pairs (see RsfwConfig) + +// INCLUDES +#include +#include +#include +#include +#include +#include + +#include "rsfwmountstore.h" + + +// CONSTANTS +const TUid KCRUidRsfwCtrl = { 0x101F9775 }; + +// Current mount configuration repository version +const TInt KCurrentVersion = 1000; +const TUint KCurrentVersionId = 0xff; + +const TInt KColumnMaskSize = 8; +const TUint KRowMask = 0xffffff00; +const TUint KColumnMask = 0x000000ff; + +const TUint KColumnName = EMountEntryItemName; + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountStore* CRsfwMountStore::NewL( + MRsfwMountStoreObserver* aMountStoreObserver) + { + CRsfwMountStore* self = new (ELeave) CRsfwMountStore(); + CleanupStack::PushL(self); + self->ConstructL(aMountStoreObserver); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::CRsfwMountStore +// ---------------------------------------------------------------------------- +// +CRsfwMountStore::CRsfwMountStore() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::ConstructL(MRsfwMountStoreObserver* aMountStoreObserver) + { + iMountStoreObserver = aMountStoreObserver; + // if CenRep not found, just leave + iRepository = CRepository::NewL(KCRUidRsfwCtrl); + + // Check version + TInt version; + // allow versionless repositories until the version id is + // included in the backup/restore scheme. + if (iRepository->Get(KCurrentVersionId, version) == KErrNone) + { + if (version != KCurrentVersion) + { + // This causes the repository to be cleared and + // stamped with the current version + CommitL(); + } + } + LoadEntriesL(); + + // Start listening to changes in the repository + iCenRepNotifyHandler = CCenRepNotifyHandler::NewL(*this, *iRepository); + iCenRepNotifyHandler->StartListeningL(); + iReceivingCenRepNotifications = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::~CRsfwMountStore +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwMountStore::~CRsfwMountStore() + { + iMountEntries.ResetAndDestroy(); + if (iCenRepNotifyHandler) + { + iCenRepNotifyHandler->StopListening(); + delete iCenRepNotifyHandler; + } + delete iRepository; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::LoadEntriesL +// CenRep keeps data in alphabetical order, and we want also iMountEntries to +// to be filled in the same order +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::LoadEntriesL() + { + iMountEntries.ResetAndDestroy(); + + // go through the records in CenRep and populate the array + RArray nameIds; + CleanupClosePushL(nameIds); + User::LeaveIfError(iRepository->FindL(KColumnName, KColumnMask, nameIds)); + HBufC* item = HBufC::NewLC(KMaxMountConfItemLength); + TPtr itemPtr = item->Des(); + TInt row; + for (row = 0; row < nameIds.Count(); row++) + { + TUint rowId = (nameIds[row] & KRowMask); + // don't touch record number 0, as it stores RSFW general data + if (rowId > 0) + { + CRsfwMountEntry* entry = CRsfwMountEntry::NewLC(); + TUint i; + for (i = EMountEntryItemIndex; i < EMountEntryItemCount; i++) + { + TInt err = iRepository->Get(rowId | i, itemPtr); + if ( err != KErrNone && err != KErrNotFound ) + { + User::Leave(err); + } + entry->SetItemL(i, itemPtr); + } + User::LeaveIfError(iMountEntries.Append(entry)); + // ownership's been taken by the array + CleanupStack::Pop(entry); + } + } + CleanupStack::PopAndDestroy(item); + CleanupStack::PopAndDestroy(&nameIds); + + // now mount entries array is up-to-date + iCenRepChanged = EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::GetNamesL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::GetNamesL(CDesC16Array* aNames) + { + ReloadEntriesL(); + aNames->Reset(); + HBufC* name = HBufC::NewLC(KMaxMountConfItemLength); + TPtr namePtr = name->Des(); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + namePtr.Copy(*iMountEntries[i]->Item(EMountEntryItemName)); + aNames->AppendL(namePtr); + } + CleanupStack::PopAndDestroy(name); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::GetDriveLettersL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::GetDriveLettersL(TDriveList& aDriveList) + { + ReloadEntriesL(); + aDriveList.Zero(); + HBufC* name = HBufC::NewLC(KMaxMountConfItemLength); + TPtr namePtr = name->Des(); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + namePtr.Copy(*iMountEntries[i]->Item(EMountEntryItemDrive)); + aDriveList.Append(namePtr); + } + CleanupStack::PopAndDestroy(name); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::LookupEntryByName +// ---------------------------------------------------------------------------- +// +EXPORT_C const CRsfwMountEntry* CRsfwMountStore::LookupEntryByNameL(const TDesC& aName) + { + ReloadEntriesL(); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + CRsfwMountEntry* entry = iMountEntries[i]; + const HBufC* name = entry->Item(EMountEntryItemName); + if (name && name->CompareF(aName) == 0) + { + return entry; + } + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::LookupEntryByDrive +// ---------------------------------------------------------------------------- +// +EXPORT_C const CRsfwMountEntry* CRsfwMountStore::LookupEntryByDriveL(TChar aDriveLetter) + { + ReloadEntriesL(); + TBuf<1> driveBuf; + driveBuf.Append(aDriveLetter); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + CRsfwMountEntry* entry = iMountEntries[i]; + const HBufC* drive = entry->Item(EMountEntryItemDrive); + if (drive && drive->CompareF(driveBuf) == 0) + { + return entry; + } + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::AddEntryL +// Adds entry to CenRep, replaces existing item, so it can be used +// for edit operation as well +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::AddEntryL(CRsfwMountEntry* aMountEntry) + { + // Take ownership + CleanupStack::PushL(aMountEntry); + + if ((!aMountEntry) || + (!aMountEntry->Item(EMountEntryItemDrive))) + { + User::Leave(KErrArgument); + } + + ReloadEntriesL(); + + TPtrC drive(*aMountEntry->Item(EMountEntryItemDrive)); + + // Check whether an entry with given drive letter exists. + // If so, delete it and remember index of deleted item. + // Otherwise find the index at which a new item should be added. + // Keep in mind the order is aphabetical. + TInt i; + TInt index = -1; + for (i = 0; i < iMountEntries.Count(); i++) + { + CRsfwMountEntry* entry = iMountEntries[i]; + TInt cmp = entry->Item(EMountEntryItemDrive)->CompareF(drive); + if (cmp == 0) + { + // Replace an existing entry + RemoveFromRepositoryL(entry); + delete entry; + entry = NULL; + iMountEntries.Remove(i); + // save the position, new item will be added here + index = i; + break; + } + else if (cmp > 0) + { + // we've found the entry whose drive letter is larger, which + // means we've found the place where a new entry should be added + index = i; + break; + } + } + + // before we add a new entry, make sure that we don't exceed max drives allowed + if (iMountEntries.Count() >= KMaxRemoteDrives) + { + User::Leave(KErrInUse); + } + + // add entry to the array + if (index < 0) + { + // this means the drive letter of newly added entry is the latest + // in the alphabet. hence just append the entry + User::LeaveIfError(iMountEntries.Append(aMountEntry)); + } + else + { + User::LeaveIfError(iMountEntries.Insert(aMountEntry, index)); + } + + + // add to repository + AddToRepositoryL(aMountEntry); + + // cleanup + CleanupStack::Pop(aMountEntry); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::RemoveEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::RemoveEntryL(const TDesC& aName) + { + ReloadEntriesL(); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + CRsfwMountEntry* entry = iMountEntries[i]; + const HBufC* name = entry->Item(EMountEntryItemName); + if (name && name->CompareF(aName) == 0) + { + RemoveFromRepositoryL(entry); + iMountEntries.Remove(i); + delete entry; + break; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::RemoveEntryL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::RemoveEntryL(TChar aDrive) + { + ReloadEntriesL(); + TBuf<1> driveBuf; + driveBuf.Append(aDrive); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + CRsfwMountEntry* entry = iMountEntries[i]; + const HBufC* drive = entry->Item(EMountEntryItemDrive); + if (drive && drive->CompareF(driveBuf) == 0) + { + RemoveFromRepositoryL(entry); + iMountEntries.Remove(i); + delete entry; + break; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::CommitL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwMountStore::CommitL() + { + if (iRepository) + { + // We don't want to get reports of our own changes + iCenRepNotifyHandler->StopListening(); + ClearRepositoryL(); + TInt i; + for (i = 0; i < iMountEntries.Count(); i++) + { + CRsfwMountEntry* entry = iMountEntries[i]; + AddToRepositoryL(entry); + } + // Set correct version id + User::LeaveIfError(iRepository->Set(KCurrentVersionId, KCurrentVersion)); + // Restart listening + iCenRepNotifyHandler->StartListeningL(); + } + else + { + _LIT(KWarningText, "Cannot store entries permanently!"); + TRAP_IGNORE(CAknWarningNote* note = new (ELeave) CAknWarningNote; + note->ExecuteLD(KWarningText); + ); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::AddToRepositoryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::AddToRepositoryL(const CRsfwMountEntry* aMountEntry) + { + // retrieve drive letter + const HBufC* drive = aMountEntry->Item(EMountEntryItemDrive); + + // calculate record ID for the drive letter + TInt recordId = MapDriveLetterToRecordIdL(drive); + + // write down the entry settings to given record ID + TInt i = 0; + for (i = EMountEntryItemIndex; i < EMountEntryItemCount; i++) + { + TInt fieldId = (recordId << KColumnMaskSize) | i; + const HBufC* item = aMountEntry->Item(i); + if (item) + { + User::LeaveIfError(iRepository->Create(fieldId, *item)); + } + else + { + TPtrC null; + User::LeaveIfError(iRepository->Create(fieldId, null)); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::RemoveFromRepositoryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::RemoveFromRepositoryL(const CRsfwMountEntry* aMountEntry) + { + // retrieve drive letter + const HBufC* drive = aMountEntry->Item(EMountEntryItemDrive); + + // calculate record ID for the drive letter + TInt recordId = MapDriveLetterToRecordIdL(drive); + + // delete settings from given record ID + TInt i = 0; + for (i = EMountEntryItemIndex; i < EMountEntryItemCount; i++) + { + TInt fieldId = (recordId << KColumnMaskSize) | i; + User::LeaveIfError(iRepository->Delete(fieldId)); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::ClearRepositoryL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::ClearRepositoryL() + { + // find all non-empty records + RArray nameIds; + CleanupClosePushL(nameIds); + User::LeaveIfError(iRepository->FindL(KColumnName, KColumnMask, nameIds)); + + TInt record; + for (record = 0; record < nameIds.Count(); record++) + { + TUint recordId = (nameIds[record] & KRowMask); + // don't touch record number 0, as it stores RSFW general data + if (recordId > 0) + { + TInt i; + for (i = EMountEntryItemIndex; i < EMountEntryItemCount; i++) + { + TUint fieldId = (recordId | i); + User::LeaveIfError(iRepository->Delete(fieldId)); + } + } + } + CleanupStack::PopAndDestroy(&nameIds); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::ReloadEntriesL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::ReloadEntriesL() + { + if (!iReceivingCenRepNotifications || iCenRepChanged) + { + // We only need reload if it is not done automatically + // through notifications + LoadEntriesL(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::HandleNotifyGeneric +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::HandleNotifyGeneric(TUint32 /* aId */) + { + iCenRepChanged = ETrue; + if (iMountStoreObserver) + { + iMountStoreObserver->HandleMountStoreEvent( + EMountStoreEventMountConfigurationChanged, + 0, + NULL); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::HandleNotifyError +// ---------------------------------------------------------------------------- +// +void CRsfwMountStore::HandleNotifyError(TUint32 /* aId */, + TInt /* aError */, + CCenRepNotifyHandler* /* aHandler */) + { + iReceivingCenRepNotifications = EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStore::MapDriveLetterToRecordIdL +// drive with letter 'J' will take record number 1 +// drive with letter 'K' will take record number 2 +// etc. +// (remember that record number 0 stores RSFW general data, so don't touch it) +// ---------------------------------------------------------------------------- +// +TInt CRsfwMountStore::MapDriveLetterToRecordIdL(const HBufC* drive) + { + if (!drive || !drive->Length()) + { + User::Leave(KErrArgument); + } + + // we have to convert HBufC to TChar and then TChar to TInt + TChar driveChar = (*drive)[0]; + TInt driveNumber; + RFs fs; + User::LeaveIfError(fs.Connect()); + TInt err = fs.CharToDrive(driveChar, driveNumber); + fs.Close(); + User::LeaveIfError(err); + + // count record ID based on drive number + // +1 is to omit record number 0! + return driveNumber - EDriveJ + 1; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/bif/rsfwmountconfbcbif.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/bif/rsfwmountconfbcbif.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,67 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: BIF definition for the remote drive BIO control +* +*/ + + +// RESOURCE IDENTIFIER + +NAME MCFB + +// INCLUDES + +#include + +#include + +// RESOURCE DEFINITIONS + + RESOURCE BIO_INFO_FILE + { + message_type_uid = 0x1bdeff02; // KUidBIOMountConfMsg +// Messaging API v. 2 assumed + message_parser_name = "gfp.dll"; + message_appctrl_name = "rsfwmountconfbc.dll"; + message_app_uid = KUidUseDefaultApp; + file_extension = ".mpmc"; + description = qtn_rd_msg_sm_type; + icons_filename = "none"; + icon_zoom_levels = {1}; + + ids= + { + ID + { + type = EWap; + confidence = ECertain; + port = 7777; //SCKL1E61 is a NBS Port + text = "//vnd.nokia.s60.mount.config"; + }, + ID + { + type = ENbs; + confidence = ECertain; + // port = 7777; + text = "//vnd.nokia.s60.mount.config"; + }, + ID + { + type = EIana; + confidence = ECertain; + text = "//vnd.nokia.s60.mount.config"; + } + }; + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/bwins/rsfwmountconfbcu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/bwins/rsfwmountconfbcu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,3 @@ +EXPORTS + ?NewL@CRsfwMountConfBioControl@@SAPAVCMsgBioControl@@AAVMMsgBioControlObserver@@PAVCMsvSession@@JW4TMsgBioMode@@PBVRFile@@@Z @ 1 NONAME ; class CMsgBioControl * CRsfwMountConfBioControl::NewL(class MMsgBioControlObserver &, class CMsvSession *, long, enum TMsgBioMode, class RFile const *) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/eabi/rsfwmountconfbcu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/eabi/rsfwmountconfbcu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,3 @@ +EXPORTS + _ZN24CRsfwMountConfBioControl4NewLER22MMsgBioControlObserverP11CMsvSessionl11TMsgBioModePK5RFile @ 1 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,24 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build information file for project remote drive BIO control +* +*/ + + +PRJ_EXPORTS +// export localised loc file +../loc/rsfwmountconfbc.loc MW_LAYER_LOC_EXPORT_PATH(rsfwmountconfbc.loc) + +PRJ_MMPFILES +../group/rsfwmountconfbc.mmp diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/group/rsfwmountconfbc.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/group/rsfwmountconfbc.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,72 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project remote drive BIO control +* +*/ + + +#include +#include + +TARGET rsfwmountconfbc.dll + +TARGETTYPE dll + +UID 0x10005f5f 0x101F976E +CAPABILITY CAP_GENERAL_DLL +TARGETPATH /system/libs + +// APP HEADER DIRS NEEDED FOR PLUG-IN BIO CONTROL API: +APP_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc + +USERINCLUDE ../inc + +SOURCEPATH ../src + +SOURCE rsfwmountconfbc.cpp +SOURCEPATH ../../MDebug/src +SOURCE mdebug.cpp + +SOURCEPATH ../src +START RESOURCE ../inc/rsfwmountconfbc.rss +HEADER +TARGETPATH RESOURCE_FILES_DIR +LANGUAGE_IDS +END + +START RESOURCE ../bif/rsfwmountconfbcbif.rss +TARGETPATH BIOFILE_DIR +LANGUAGE_IDS +END + +LIBRARY cone.lib +LIBRARY efsrv.lib +LIBRARY eikcoctl.lib // Menus API +LIBRARY euser.lib +LIBRARY rsfwmountstore.lib +LIBRARY rsfwmountutils.lib +LIBRARY rsfwmountman.lib +LIBRARY rsfwnotplugin.lib // dialog for renaming drives +LIBRARY msgeditorutils.lib //CMsgBioControl +LIBRARY msgs.lib +LIBRARY richbio.lib +LIBRARY estor.lib //for RFileReadStream +LIBRARY commonengine.lib // StringLoader +LIBRARY bafl.lib +LIBRARY avkon.lib +LIBRARY flogger.lib +LIBRARY charconv.lib // for CnvUtfConverter + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/inc/mydebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/inc/mydebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,33 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug definitions for Remote File Engine + * +*/ + + +#ifndef MYDEBUG_H +#define MYDEBUG_H + +// Debug defines for Remote File Engine + +// MACROS +#define APPEND_TO_DEBUG_FILE + +// CONSTANTS +_LIT(KDebugDirName, "rsfwbiocontrol"); +_LIT(KDebugFileName, "rsfwbiocontrol.txt"); + +#endif // MYDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/inc/rsfwmountconfbc.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/inc/rsfwmountconfbc.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,191 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote drive configuration BIO control +* +*/ + + +#ifndef CRSFWMOUNTCONFBIOCONTROL_H +#define CRSFWMOUNTCONFBIOCONTROL_H + +// INCLUDES +#include // CMsgBioControl + + +// FORWARD DECLARATIONS +class CRichBio; +class CRsfwMountMan; +class CRsfwMountEntry; + +// CLASS DECLARATION + +/** + * Bio control for Remote drive settings + */ +NONSHARABLE_CLASS(CRsfwMountConfBioControl) : + public CMsgBioControl + { + public: + /** + * Two-phased constructor + * @param aObserver Reference to the Bio control observer. + * @param aSession Reference to Message Server session. + * @param aId Id of the message. + * @param aEditorOrViewerMode Flags the new Bio control as editor or viewer. + * @param aFile filehandle. + * @return The newly created object. + */ + IMPORT_C static CMsgBioControl* NewL(MMsgBioControlObserver& aObserver, + CMsvSession* aSession, + TMsvId aId, + TMsgBioMode aEditorOrViewerMode, + const RFile* aFile); + // Destructor + ~CRsfwMountConfBioControl(); + +public: //from MMsgBioControl + + /** + * Calculates and sets size for a Bio control according to aSize. + * @param aSize A reference to the suggested size and new size. + */ + void SetAndGetSizeL(TSize& aSize); + + /** + * Adds a menu command. + * @param aMenuPane Reference to the CEikMenuPane of the application. + */ + void SetMenuCommandSetL(CEikMenuPane& aMenuPane); + + /* + * The command handler of the bio control. + * The commands usually originate from a bio specific menu item being + * selected by the user. + * @param aCommand Id of command to be handled. + */ + TBool HandleBioCommandL(TInt aCommand); + + /** + * Returns a rectangle slice of the bio controls viewing area. + * It is used by the CMsgEditorView class for scrolling the screen. + * @return TRect + */ + TRect CurrentLineRect() const; + + /** + * This is used by the body container for managing focus and + * scrolling. + * @param aDirection The direction to be checked. + */ + TBool IsFocusChangePossible(TMsgFocusDirection aDirection) const; + + + /** + * Returns the header text. + * @return The header text. + */ + HBufC* HeaderTextL(void) const; + + /** + * Gives the height of the text in pixels. + * It is used by the scrolling framework of Editor Base. + * @return Height of the text in pixels. + */ + TInt VirtualHeight(); + + /** + * Gives the cursor position in pixels. + * It is used by the scrolling framework of Editor Base. + * @return Cursor position in pixels. + */ + TInt VirtualVisibleTop(); + + /* Tells whether the cursor is in the topmost or bottom position. + * It is used by the scrolling framework. + * @param aLocation Specifies either top or bottom. + * @return ETrue if the cursor is in the part specified by aLocation. + */ + TBool IsCursorLocation(TMsgCursorLocation aLocation) const; + + + // Functions from CCoeControl + TKeyResponse OfferKeyEventL( + const TKeyEvent& aKeyEvent, + TEventCode aType); + +protected: + // Functions from CCoeControl + TInt CountComponentControls() const; + CCoeControl* ComponentControl(TInt aIndex) const; + void SizeChanged(); + void FocusChanged(TDrawNow aDrawNow); + void SetContainerWindowL(const CCoeControl& aContainer); + +private: + CRsfwMountConfBioControl( + MMsgBioControlObserver& aObserver, + CMsvSession* aSession, + TMsvId aId, + TMsgBioMode aEditorOrViewerMode, + const RFile* aFile); + void ConstructL(); + + void DoMountL(CRsfwMountEntry*); + void EncodeMounterEntry(CRsfwMountEntry&, TDes&); + TBool isNameUniqueL(const TDesC& aFriendlyName); + + /* returns true when user has selected an unique name for the new drive + * + */ + TBool GetNameForNewMountL(TDes& aName); + + /** + * Fills the viewer with data from the mount entry + */ + void FillViewerWithDataL(); + + /** + * Helper for adding to viewer. + * @param aLabelRes Resource id for label + * @param aValue Value text + */ + void AddItemL(TInt aLabelRes, const TDesC& aValue); + + /** + * Resolve the file handle of the data file that is used as input. + * @param aFile A reference that gets the file handle. + */ + void ResolveFileL( RFile& aFile ); + + /** + * This is needed because the menuPane adding is done in a different + * way in BVA than in SMS Editor/Viewer. + * @param aMenuPane Reference to the menu pane. + * @param aStringRes String resource ID of the command text. + * @param aCommandOffset Offset in the Options list. + */ + void FileBasedAddMenuItemL(CEikMenuPane& aMenuPane, + TInt aStringRes, TInt aCommandOffset); + +private: + CRichBio* iViewer; // The viewer control + + TBool iIsFileBased; // ETrue if BIO Control is lauched through BVA + + CRsfwMountEntry* iMountEntry; // Contains the imported mount entry + // only one because the list in GS is not markable + CRsfwMountMan* iMountMan; // mount manager + }; + +#endif // CRSFWMOUNTCONFBIOCONTROL_H diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/inc/rsfwmountconfbc.hrh --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/inc/rsfwmountconfbc.hrh Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,31 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Resource headers for project remote drive BIO control +* +*/ + + +#ifndef RSFWMOUNTCONFBC_HRH +#define RSFWMOUNTCONFBC_HRH + +#define MAXCONFITEMLENGTH 128 + +enum + { + EMountConfBcCmdSave = 0, + EMountConfBcCmdMount + }; + +#endif // RSFWMOUNTCONFBC_HRH + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/inc/rsfwmountconfbc.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/inc/rsfwmountconfbc.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,148 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Resource definitions for project ?myapp +* +*/ + + +NAME MCBC + +#include +#include + +#include +#include +#include +#include + +#include "rsfwmountconfbc.hrh" +#include // Localisable text +#include + + +RESOURCE RSS_SIGNATURE { } + +RESOURCE TBUF { buf = ""; } + +RESOURCE EIK_APP_INFO + { + status_pane = R_AVKON_STATUS_PANE_LAYOUT_USUAL; + cba = R_AVKON_SOFTKEYS_OPTIONS_EXIT; + } + +RESOURCE TBUF r_sm_save + { + buf = qtn_rd_msg_option_save_drive; + } + + +RESOURCE TBUF r_sm_success_mount + { + buf = qtn_rd_msg_note_drive_saved; + } + +RESOURCE TBUF r_sm_default_drive_name + { + buf = qtn_rd_msg_query_default_name; + } +RESOURCE TBUF r_sm_too_many_remote_drives + { + buf = qtn_rd_error_max_drives; + } + +RESOURCE DIALOG r_name_query + { + flags = EEikDialogFlagWait | EEikDialogFlagNoDrag | EEikDialogFlagNoTitleBar | EEikDialogFlagCbaButtons | EEikDialogFlagNoShadow; + buttons = R_AVKON_SOFTKEYS_OK_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_DATA_QUERY + { + layout = EDataLayout; + label = "Enter name"; + control = EDWIN + { + flags = EEikEdwinNoHorizScrolling; + avkon_flags = EAknEditorFlagNoT9; + maxlength = MAXCONFITEMLENGTH; + width = 16; + lines = 3; + }; + }; + } + }; + } + +RESOURCE DIALOG r_confirmation_query + { + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_OK_CANCEL; + items= + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout =EConfirmationQueryLayout; + }; + } + }; + } +RESOURCE DIALOG r_file_name_query + { + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_OK_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_DATA_QUERY + { + layout = EDataLayout; + label = qtn_fldr_item_name_prmpt; + control = EDWIN + { + flags = EEikEdwinNoHorizScrolling | EEikEdwinResizable; + lines = 1; + maxlength = 256; + }; + }; + } + }; + } + + +RESOURCE TBUF r_sm_title_mount_conf + { + buf = qtn_rd_msg_title_remote_drive; + } +//---------------------------------------------------- +// +// string resouces +// the strings can be localized in loc file +// +//---------------------------------------------------- +// +RESOURCE TBUF r_str_setting_item_drive_name { buf = qtn_rd_msg_label_drive_name; } +RESOURCE TBUF r_str_name_rename_query { buf = qtn_fldr_rename_query; } +RESOURCE TBUF r_str_new_name_prompt { buf = qtn_fldr_item_name_prmpt; } +RESOURCE TBUF r_str_saving_wait_note { buf = qtn_rd_msg_note_saving_drive; } diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/loc/rsfwmountconfbc.loc --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/loc/rsfwmountconfbc.loc Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,75 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Localization strings for project MountConfiguration BioControl +* +*/ + + +//d:Success note saving a remote drive configuration +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_msg_note_drive_saved "Remote drive saved" + +//d:Saving received remote drive configuration in progress +//l:popup_note_wait_window +//w: +//r:3.1 +// +#define qtn_rd_msg_note_saving_drive "Saving remote drive" + +//d:Default new name if user must be queried for a new name +//l: popup_query_data_window +//w: +//r:3.1 +// +#define qtn_rd_msg_query_default_name "New drive" + +//d:Options list text for saving the remote drive configuration entry. +//l:list_single_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_msg_option_save_drive "Save drive settings" + +//d:Remote drive name header in smart messaging "send message" view +//l:list_double_heading_pane_t1_cp2 +//w: +//r:3.1 +// +#define qtn_rd_msg_label_drive_name "Drive name:" + +//d:Remote drive configuration message type in "Message details" +//l:list_double_graphic_pane_t2 +//w: +//r:3.1 +// +#define qtn_rd_msg_sm_type "Remote drive settings" + +//d:Title pane when sending a remote drive setting +//l:title_pane_t2/opt9 +//w: +//r:3.1 +// +#define qtn_rd_msg_title_remote_drive "Remote drive settings" + +//d:Message id in Send message view +//l:navi_text_pane_t1 +//w: +//r:3.1 +// +#define qtn_stat_msg_number "%0N/%1N" + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotedriveconfigurationbiocontrol/src/rsfwmountconfbc.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotedriveconfigurationbiocontrol/src/rsfwmountconfbc.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,530 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: BIO control for handling remote drive configurations as +* smart messages +* +*/ + + +// INCLUDE FILES + +#include // for CBIOClientMtm +#include // for MMsgBioControlObserver +#include // for StringLoader +#include // CRichBio +#include // for CAknInformationNote +#include +#include // for CnvUtfConverter +#include +#include + +#include // for resouce identifiers + +#include "rsfwmountconfbc.h" +#include "rsfwmountconfbc.hrh" +#include "rsfwmountutils.h" +#include "rsfwgsplugin.hrh" +#include "rsfwnotpluginnamedialog.h" +#include "mdebug.h" + +#define KUidGeneralSettings 0x100058EC + +enum TOptionListLocation + { + EFirstMenuItem = 0, + ESecondMenuItem, + EThirdMenuItem, + EFourthMenuItem + }; + +const TInt KMConfBcHeightReductionBva = 9; +_LIT(KMountConfBcResourceFile, "rsfwmountconfbc.rsc"); +_LIT(KAvkonResourceFile, "avkon.rsc"); + + +// ======== MEMBER FUNCTIONS ======== + +// --------------------------------------------------------------------------- +// constructor +// --------------------------------------------------------------------------- +// +EXPORT_C CMsgBioControl* CRsfwMountConfBioControl::NewL( + MMsgBioControlObserver& aObserver, + CMsvSession* aSession, + TMsvId aId, + TMsgBioMode aEditorOrViewerMode, + const RFile* aFile) + { + CRsfwMountConfBioControl* self = + new(ELeave) CRsfwMountConfBioControl(aObserver, + aSession, + aId, + aEditorOrViewerMode, + aFile); + CleanupStack::PushL(self); + self->ConstructL(); + CleanupStack::Pop(self); + + return self; + } + +// --------------------------------------------------------------------------- +// destructor +// --------------------------------------------------------------------------- +// +CRsfwMountConfBioControl::~CRsfwMountConfBioControl() + { + delete iViewer; + + if (iMountEntry) + { + delete iMountEntry; + } + delete iMountMan; + } + +// --------------------------------------------------------------------------- +// constructor +// --------------------------------------------------------------------------- +// +CRsfwMountConfBioControl::CRsfwMountConfBioControl( + MMsgBioControlObserver& aObserver, + CMsvSession* aSession, + TMsvId aId, + TMsgBioMode aEditorOrViewerMode, + const RFile* aFile): + CMsgBioControl(aObserver, + aSession, + aId, + aEditorOrViewerMode, + aFile) + { + } + +// --------------------------------------------------------------------------- +// second phase constructor +// --------------------------------------------------------------------------- +// +void CRsfwMountConfBioControl::ConstructL() + { + DEBUGSTRING16(("CRsfwMountConfBioControl::ConstructL")); + iMountMan = CRsfwMountMan::NewL(0, NULL); + + iIsFileBased = IsFileBased(); + LoadResourceL(KMountConfBcResourceFile); + LoadResourceL(KAvkonResourceFile); + LoadResourceL(KNotPluginResourcePath); + LoadStandardBioResourceL(); + // file handle to the remote drive configuration attachment in msv store + RFile fileHandle; + ResolveFileL( fileHandle ); + CleanupClosePushL( fileHandle ); + + // read stream + RFileReadStream stream( fileHandle,0 ); + CleanupClosePushL( stream ); + + MStreamBuf* buf = stream.Source(); + buf->PushL(); + User::LeaveIfNull(buf); + TInt bufferSize = buf->SizeL(); + if (bufferSize == 0 || (bufferSize < KMountMessagePrefixLength)) + { + User::Leave(KErrMsgBioMessageNotValid); + } + TRequestStatus status; + HBufC8* utf8configuration = HBufC8::NewMaxLC(bufferSize); + TPtr8 utfPtr = utf8configuration->Des(); + buf->ReadL(utfPtr, status); + User::WaitForRequest(status); + + HBufC* unistring(NULL); + unistring = CnvUtfConverter::ConvertToUnicodeFromUtf7L(*utf8configuration); + CleanupStack::PushL(unistring); + + RsfwMountUtils::ImportMountEntryL(*unistring,&iMountEntry); + + iViewer = new (ELeave) CRichBio(ERichBioModeEditorBase); + + FillViewerWithDataL(); + + CleanupStack::PopAndDestroy(5,&fileHandle); + } + +// --------------------------------------------------------------------------- +// Formats displaying a remote drive (only the drive name is shown) +// --------------------------------------------------------------------------- +// +void CRsfwMountConfBioControl::FillViewerWithDataL() + { + DEBUGSTRING16(("CRsfwMountConfBioControl::FillViewerWithDataL")); + AddItemL(R_STR_SETTING_ITEM_DRIVE_NAME, *(*iMountEntry).Item(EMountEntryItemName)); + } + + +// --------------------------------------------------------------------------- +// Display a single item +// --------------------------------------------------------------------------- +// +void CRsfwMountConfBioControl::AddItemL(TInt aLabelRes, const TDesC& aValue) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::AddItemL")); + // Empty fields are not shown. + if (&aValue) + { + if (aValue.Length()) + { + HBufC* labelTxt = StringLoader::LoadLC(aLabelRes, iCoeEnv); + iViewer->AddItemL(*labelTxt, aValue); + CleanupStack::PopAndDestroy(labelTxt); + } + } + } + + +void CRsfwMountConfBioControl::SetAndGetSizeL(TSize& aSize) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::SetAndGetSizeL")); + if(iIsFileBased) + { + SetPosition(TPoint(0,KMConfBcHeightReductionBva)); + aSize.iHeight -= KMConfBcHeightReductionBva; + iViewer->SetAndGetSizeL(aSize); + } + else + { + iViewer->SetAndGetSizeL(aSize); + } + SetSizeWithoutNotification(aSize); + } + +// --------------------------------------------------------------------------- +// Adds Save command to "Options" set +// --------------------------------------------------------------------------- +// +void CRsfwMountConfBioControl::SetMenuCommandSetL(CEikMenuPane& aMenuPane) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::SetMenuCommandSetL")); + if (!IsEditor()) + { + if( iIsFileBased ) + { + FileBasedAddMenuItemL(aMenuPane, R_SM_SAVE, + EMountConfBcCmdSave); + } + else + { + AddMenuItemL(aMenuPane, R_SM_SAVE, + EMountConfBcCmdSave, EFirstMenuItem); + + } + } + } + + +void CRsfwMountConfBioControl::FileBasedAddMenuItemL(CEikMenuPane& aMenuPane, + TInt aStringRes, TInt aCommandOffset) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::FileBasedAddMenuItemL")); + CEikMenuPaneItem::SData menuItem; + menuItem.iCascadeId = NULL; + menuItem.iFlags = NULL; + HBufC* string = StringLoader::LoadL(aStringRes, iCoeEnv); + menuItem.iText.Format(*string); + delete string; + menuItem.iCommandId = iBioControlObserver.FirstFreeCommand() + + aCommandOffset; + aMenuPane.InsertMenuItemL(menuItem, 0); + } + +TRect CRsfwMountConfBioControl::CurrentLineRect() const + { + DEBUGSTRING16(("CRsfwMountConfBioControl::CurrentLineRect")); + return iViewer->CurrentLineRect(); + } + +TBool CRsfwMountConfBioControl::IsFocusChangePossible( + TMsgFocusDirection aDirection) const + { + DEBUGSTRING16(("CRsfwMountConfBioControl::IsFocusChangePossible")); + if (aDirection == EMsgFocusUp) + { + return iViewer->IsCursorLocation(EMsgTop); + } + return EFalse; + } + +// --------------------------------------------------------------------------- +// Sets the header or the remote drive view +// --------------------------------------------------------------------------- +// +HBufC* CRsfwMountConfBioControl::HeaderTextL() const + { + DEBUGSTRING16(("CRsfwMountConfBioControl::HeaderTextL")); + return StringLoader::LoadL(R_SM_TITLE_MOUNT_CONF, iCoeEnv); + } + + +// --------------------------------------------------------------------------- +// Handles the command selected by the user +// --------------------------------------------------------------------------- +// +TBool CRsfwMountConfBioControl::HandleBioCommandL(TInt aCommand) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::HandleBioCommandL %d", aCommand)); + + aCommand -= iBioControlObserver.FirstFreeCommand(); + switch (aCommand) + { + case EMountConfBcCmdSave: + TRAPD(err, DoMountL(iMountEntry)); + if (!err) + { + HBufC* buf = StringLoader::LoadLC(R_SM_SUCCESS_MOUNT); + CAknConfirmationNote* note = new (ELeave) CAknConfirmationNote; + note->ExecuteLD(*buf); + CleanupStack::PopAndDestroy(buf); + } + else if (KErrInUse == err) + { + HBufC* buf = StringLoader::LoadLC(R_SM_TOO_MANY_REMOTE_DRIVES); + CAknErrorNote* note = new (ELeave) CAknErrorNote; + note->ExecuteLD(*buf); + CleanupStack::PopAndDestroy(buf); + } + else if (!(KErrCancel == err)) + { + // cancel means that user does not want to rename + User::Leave(err); + } + + return ETrue; + default: + return EFalse; + } + } + +TKeyResponse CRsfwMountConfBioControl::OfferKeyEventL( + const TKeyEvent& aKeyEvent, + TEventCode aType) + { +DEBUGSTRING16(("CRsfwMountConfBioControl::OfferKeyEventL")); + return iViewer->OfferKeyEventL(aKeyEvent, aType); + } + +TInt CRsfwMountConfBioControl::CountComponentControls() const + { +DEBUGSTRING16(("CRsfwMountConfBioControl::CountComponentControls")); + return 1; // the viewer component + } + +CCoeControl* CRsfwMountConfBioControl::ComponentControl(TInt aIndex) const + { + DEBUGSTRING16(("CRsfwMountConfBioControl::ComponentControl")); + if (aIndex == 0) + { + return iViewer; + } + return NULL; + + } + +void CRsfwMountConfBioControl::SizeChanged() + { + DEBUGSTRING16(("CRsfwMountConfBioControl::SizeChanged")); + iViewer->SetExtent(Position(), iViewer->Size()); + } + +void CRsfwMountConfBioControl::FocusChanged(TDrawNow /* aDrawNow */) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::FocusChanged")); + iViewer->SetFocus(IsFocused()); + } + +void CRsfwMountConfBioControl::SetContainerWindowL(const CCoeControl& aContainer) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::SetContainerWindowL")); + CCoeControl::SetContainerWindowL(aContainer); + + // The reason for creating the viewer control here is that the + // construction of the viewer requires a parent with a window. So it + // cannot be done in ConstructL(). + // + iViewer->ConstructL(this); + + } + +TInt CRsfwMountConfBioControl::VirtualHeight() + { + DEBUGSTRING16(("CRsfwMountConfBioControl::VirtualHeight")); + return iViewer->VirtualHeight(); + } + +TInt CRsfwMountConfBioControl::VirtualVisibleTop() + { + DEBUGSTRING16(("CRsfwMountConfBioControl::VirtualVisibleTop")); + return iViewer->VirtualVisibleTop(); + } + +TBool CRsfwMountConfBioControl::IsCursorLocation(TMsgCursorLocation aLocation) const + { + DEBUGSTRING16(("CRsfwMountConfBioControl::IsCursorLocation")); + return iViewer->IsCursorLocation(aLocation); + } + + +void CRsfwMountConfBioControl::ResolveFileL( RFile& aFile ) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::ResolveFileL")); + if ( iIsFileBased ) + { + aFile.Duplicate(FileHandle()); + } + else + { + CMsvEntry* entry = MsvSession().GetEntryL( iId ); + + CleanupStack::PushL( entry ); + CMsvStore* store = entry->ReadStoreL(); + CleanupStack::PushL(store); + MMsvAttachmentManager& attachMan = store->AttachmentManagerL(); + aFile = attachMan.GetAttachmentFileL( 0 ); //entry is the first attachment + CleanupStack::PopAndDestroy( 2, entry ); // store, entry + } + } + +// --------------------------------------------------------------------------- +// Saves the selected remote drive to the Central Repository table +// --------------------------------------------------------------------------- +// +void CRsfwMountConfBioControl::DoMountL(CRsfwMountEntry* aMounterEntry) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::DoMountL")); + // CRsfwMountEntry API ensures that EMountEntryItemName + // length does not exceed KMaxFriendlyNameLength characters + TBuf newFriendlyName; + newFriendlyName.Copy(*aMounterEntry->Item(EMountEntryItemName)); + + TBool nameUnique = EFalse; + TBool operationCancelled = EFalse; + + nameUnique = isNameUniqueL(newFriendlyName); + + while ((!nameUnique) && (!operationCancelled)) + { + operationCancelled = GetNameForNewMountL(newFriendlyName); + nameUnique = isNameUniqueL(newFriendlyName); + } + + if (!operationCancelled) + { + // clone the entry and add it to the cenrep + // we clone it so that the original smart message content does not change + CRsfwMountEntry* entrytoBeSaved = aMounterEntry->CloneL(); + + // copy newFriendlyName to name + entrytoBeSaved->SetItemL(EMountEntryItemName, newFriendlyName); + + // set mountentryindex to -1 so that this will go the end of the list + TBuf<5> index; + index.Num(-1); + entrytoBeSaved->SetItemL(EMountEntryItemIndex, index); + + // ownership is transferred to MountMan + iMountMan->AddMountEntryL(entrytoBeSaved); + } + else + { + User::Leave(KErrCancel); + } + + } + +// --------------------------------------------------------------------------- +// Tests whether the chosen remote drive name is unique +// --------------------------------------------------------------------------- +// +TBool CRsfwMountConfBioControl::isNameUniqueL(const TDesC& aName) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::isNameUniqueL")); + // figure out whether a drive with the same name already exists + CDesCArray* driveArray = new (ELeave) CDesC16ArraySeg(4); + CleanupStack::PushL(driveArray); + iMountMan->GetMountNamesL(driveArray); + // report error if there are already 9 remote drives + if (driveArray->Count() == KMaxRemoteDrives) + { + CleanupStack::PopAndDestroy(driveArray); + User::Leave(KErrInUse); + } + + for (int i = 0; i < driveArray->Count(); i++) + { + if (aName == driveArray->MdcaPoint(i)) + { + // there was a match and the name is not unique + CleanupStack::PopAndDestroy(driveArray); + return EFalse; + } + } + CleanupStack::PopAndDestroy(driveArray); + return ETrue; + } + +// --------------------------------------------------------------------------- +// Queries new remote drive name from the user +// --------------------------------------------------------------------------- +// +TBool CRsfwMountConfBioControl::GetNameForNewMountL(TDes& aName) + { + DEBUGSTRING16(("CRsfwMountConfBioControl::GetNameForNewMountL")); + TBool operationCancelled = EFalse; + // ask user to change the name and try again + HBufC* confmess = StringLoader::LoadLC(R_STR_NAME_RENAME_QUERY, aName); + CAknQueryDialog* query = CAknQueryDialog::NewL + (CAknQueryDialog::EConfirmationTone); + + if (query->ExecuteLD( R_CONFIRMATION_QUERY, *confmess)) + { + TBuf newName; + TBool retval; + + // for getting the new name, use name dialog from the "global save as dialog" + HBufC* defaultname = StringLoader::LoadLC(R_SM_DEFAULT_DRIVE_NAME); + + CRsfwNotPluginNameDialog* dlg = + CRsfwNotPluginNameDialog::NewL( + *defaultname, newName, iEikonEnv->FsSession()); + dlg->SetMaxLength(KMaxFriendlyNameLength); + dlg->PrepareLC( R_FILE_NAME_QUERY ); + retval = dlg->RunLD(); + CleanupStack::PopAndDestroy(defaultname); + if (!retval) + { + // user cancelled renaming + operationCancelled = ETrue; + } + else + { + aName = newName; + } + } + else + { + // user does not want to rename + operationCancelled = ETrue; + } + CleanupStack::PopAndDestroy(confmess); + return operationCancelled; + } diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/bwins/rsfwcommonu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/bwins/rsfwcommonu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,41 @@ +EXPORTS + ??1CRsfwConnectionManager@@UAE@XZ @ 1 NONAME ; CRsfwConnectionManager::~CRsfwConnectionManager(void) + ??1CRsfwDirEnt@@UAE@XZ @ 2 NONAME ; CRsfwDirEnt::~CRsfwDirEnt(void) + ??1CRsfwDirEntAttr@@UAE@XZ @ 3 NONAME ; CRsfwDirEntAttr::~CRsfwDirEntAttr(void) + ??1CRsfwRemoteAccess@@UAE@XZ @ 4 NONAME ; CRsfwRemoteAccess::~CRsfwRemoteAccess(void) + ?Att@CRsfwDirEntAttr@@QBEIXZ @ 5 NONAME ; unsigned int CRsfwDirEntAttr::Att(void) const + ?Attr@CRsfwDirEnt@@QBEPAVCRsfwDirEntAttr@@XZ @ 6 NONAME ; class CRsfwDirEntAttr * CRsfwDirEnt::Attr(void) const + ?ETag@CRsfwDirEntAttr@@QBEPBVTDesC8@@XZ @ 7 NONAME ; class TDesC8 const * CRsfwDirEntAttr::ETag(void) const + ?ExtractAttr@CRsfwDirEnt@@QAEPAVCRsfwDirEntAttr@@XZ @ 8 NONAME ; class CRsfwDirEntAttr * CRsfwDirEnt::ExtractAttr(void) + ?GetConnection@CRsfwConnectionManager@@QAEHAAPAVRSocketServ@@AAPAVRConnection@@@Z @ 9 NONAME ; int CRsfwConnectionManager::GetConnection(class RSocketServ * &, class RConnection * &) + ?GetName@CRsfwDirEnt@@QBEXAAVTDes16@@@Z @ 10 NONAME ; void CRsfwDirEnt::GetName(class TDes16 &) const + ?GetName@CRsfwDirEnt@@QBEXAAVTDes8@@@Z @ 11 NONAME ; void CRsfwDirEnt::GetName(class TDes8 &) const + ?GetQuotaAndSizeL@CRsfwRemoteAccess@@UAEHAAH0@Z @ 12 NONAME ; int CRsfwRemoteAccess::GetQuotaAndSizeL(int &, int &) + ?MimeType@CRsfwDirEntAttr@@QBEPBVTDesC8@@XZ @ 13 NONAME ; class TDesC8 const * CRsfwDirEntAttr::MimeType(void) const + ?Modified@CRsfwDirEntAttr@@QBE?AVTTime@@XZ @ 14 NONAME ; class TTime CRsfwDirEntAttr::Modified(void) const + ?Name@CRsfwDirEnt@@QBEPBVHBufC16@@XZ @ 15 NONAME ; class HBufC16 const * CRsfwDirEnt::Name(void) const + ?NewL@CRsfwConnectionManager@@SAPAV1@PAVMRsfwConnectionObserver@@@Z @ 16 NONAME ; class CRsfwConnectionManager * CRsfwConnectionManager::NewL(class MRsfwConnectionObserver *) + ?NewL@CRsfwDirEnt@@SAPAV1@ABVTDesC16@@PAVCRsfwDirEntAttr@@@Z @ 17 NONAME ; class CRsfwDirEnt * CRsfwDirEnt::NewL(class TDesC16 const &, class CRsfwDirEntAttr *) + ?NewL@CRsfwDirEnt@@SAPAV1@ABVTDesC8@@PAVCRsfwDirEntAttr@@@Z @ 18 NONAME ; class CRsfwDirEnt * CRsfwDirEnt::NewL(class TDesC8 const &, class CRsfwDirEntAttr *) + ?NewL@CRsfwDirEntAttr@@SAPAV1@XZ @ 19 NONAME ; class CRsfwDirEntAttr * CRsfwDirEntAttr::NewL(void) + ?NewL@CRsfwRemoteAccess@@SAPAV1@ABVTDesC8@@@Z @ 20 NONAME ; class CRsfwRemoteAccess * CRsfwRemoteAccess::NewL(class TDesC8 const &) + ?NewLC@CRsfwDirEnt@@SAPAV1@ABVTDesC16@@PAVCRsfwDirEntAttr@@@Z @ 21 NONAME ; class CRsfwDirEnt * CRsfwDirEnt::NewLC(class TDesC16 const &, class CRsfwDirEntAttr *) + ?NewLC@CRsfwDirEnt@@SAPAV1@ABVTDesC8@@PAVCRsfwDirEntAttr@@@Z @ 22 NONAME ; class CRsfwDirEnt * CRsfwDirEnt::NewLC(class TDesC8 const &, class CRsfwDirEntAttr *) + ?NewLC@CRsfwDirEntAttr@@SAPAV1@XZ @ 23 NONAME ; class CRsfwDirEntAttr * CRsfwDirEntAttr::NewLC(void) + ?ResetAttFlags@CRsfwDirEntAttr@@QAEXI@Z @ 24 NONAME ; void CRsfwDirEntAttr::ResetAttFlags(unsigned int) + ?SetAtt@CRsfwDirEntAttr@@QAEXI@Z @ 25 NONAME ; void CRsfwDirEntAttr::SetAtt(unsigned int) + ?SetAttFlags@CRsfwDirEntAttr@@QAEXI@Z @ 26 NONAME ; void CRsfwDirEntAttr::SetAttFlags(unsigned int) + ?SetAttrL@CRsfwDirEnt@@QAEXPAVCRsfwDirEntAttr@@@Z @ 27 NONAME ; void CRsfwDirEnt::SetAttrL(class CRsfwDirEntAttr *) + ?SetETagL@CRsfwDirEntAttr@@QAEXABVTDesC8@@@Z @ 28 NONAME ; void CRsfwDirEntAttr::SetETagL(class TDesC8 const &) + ?SetMimeTypeL@CRsfwDirEntAttr@@QAEXABVTDesC8@@@Z @ 29 NONAME ; void CRsfwDirEntAttr::SetMimeTypeL(class TDesC8 const &) + ?SetModified@CRsfwDirEntAttr@@QAEXABVTTime@@@Z @ 30 NONAME ; void CRsfwDirEntAttr::SetModified(class TTime const &) + ?SetNameL@CRsfwDirEnt@@QAEXABVTDesC16@@@Z @ 31 NONAME ; void CRsfwDirEnt::SetNameL(class TDesC16 const &) + ?SetNameL@CRsfwDirEnt@@QAEXABVTDesC8@@@Z @ 32 NONAME ; void CRsfwDirEnt::SetNameL(class TDesC8 const &) + ?SetSize@CRsfwDirEntAttr@@QAEXH@Z @ 33 NONAME ; void CRsfwDirEntAttr::SetSize(int) + ?SetStringValueL@CRsfwDirEntAttr@@QAEXHABVTDesC8@@@Z @ 34 NONAME ; void CRsfwDirEntAttr::SetStringValueL(int, class TDesC8 const &) + ?SetUid@CRsfwDirEntAttr@@QAEXVTUid@@@Z @ 35 NONAME ; void CRsfwDirEntAttr::SetUid(class TUid) + ?Size@CRsfwDirEntAttr@@QBEHXZ @ 36 NONAME ; int CRsfwDirEntAttr::Size(void) const + ?StringValue@CRsfwDirEntAttr@@QBEPBVTDesC8@@H@Z @ 37 NONAME ; class TDesC8 const * CRsfwDirEntAttr::StringValue(int) const + ?Uid@CRsfwDirEntAttr@@QAEABVTUid@@XZ @ 38 NONAME ; class TUid const & CRsfwDirEntAttr::Uid(void) + ?UseIapL@CRsfwConnectionManager@@QAEXABVTDesC16@@@Z @ 39 NONAME ; void CRsfwConnectionManager::UseIapL(class TDesC16 const &) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/bwins/rsfwcontrolu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/bwins/rsfwcontrolu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,15 @@ +EXPORTS + ??0RRsfwControl@@QAE@XZ @ 1 NONAME ; RRsfwControl::RRsfwControl(void) + ?CancelRemoteTransfer@RRsfwControl@@QAEHABVTDesC16@@@Z @ 2 NONAME ; int RRsfwControl::CancelRemoteTransfer(class TDesC16 const &) + ?Connect@RRsfwControl@@QAEHXZ @ 3 NONAME ; int RRsfwControl::Connect(void) + ?DismountByDriveLetter@RRsfwControl@@QAEHVTChar@@@Z @ 4 NONAME ; int RRsfwControl::DismountByDriveLetter(class TChar) + ?DismountByVolumeId@RRsfwControl@@QAEHH@Z @ 5 NONAME ; int RRsfwControl::DismountByVolumeId(int) + ?GetMountInfo@RRsfwControl@@QAEHABVTChar@@AAVTRsfwMountInfo@@@Z @ 6 NONAME ; int RRsfwControl::GetMountInfo(class TChar const &, class TRsfwMountInfo &) + ?Mount@RRsfwControl@@QAEHH@Z @ 7 NONAME ; int RRsfwControl::Mount(int) + ?Mount@RRsfwControl@@QAEXABVTRsfwMountConfig@@AAVTRequestStatus@@@Z @ 8 NONAME ; void RRsfwControl::Mount(class TRsfwMountConfig const &, class TRequestStatus &) + ?RefreshDirectory@RRsfwControl@@QAEHABVTDesC16@@@Z @ 9 NONAME ; int RRsfwControl::RefreshDirectory(class TDesC16 const &) + ?SetMountConnectionState@RRsfwControl@@QAEHABVTChar@@I@Z @ 10 NONAME ; int RRsfwControl::SetMountConnectionState(class TChar const &, unsigned int) + ?Version@RRsfwControl@@QAE?AVTVersion@@XZ @ 11 NONAME ; class TVersion RRsfwControl::Version(void) + ?MountBlind@RRsfwControl@@QAEHH@Z @ 12 NONAME ; int RRsfwControl::MountBlind(int) + ?Mount@RRsfwControl@@QAEHABVTRsfwMountConfig@@@Z @ 13 NONAME ; int RRsfwControl::Mount(class TRsfwMountConfig const &) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/bwins/rsfwsessionu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/bwins/rsfwsessionu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,29 @@ +EXPORTS + ??0RRsfwSession@@QAE@XZ @ 1 NONAME ; RRsfwSession::RRsfwSession(void) + ?Clear@TDirEnt@@QAEXXZ @ 2 NONAME ; void TDirEnt::Clear(void) + ?Clear@TDirEntAttr@@QAEXXZ @ 3 NONAME ; void TDirEntAttr::Clear(void) + ?Close@RRsfwSession@@QAEXXZ @ 4 NONAME ; void RRsfwSession::Close(void) + ?CloseFile@RRsfwSession@@QAEXVTFid@@I@Z @ 5 NONAME ; void RRsfwSession::CloseFile(class TFid, unsigned int) + ?Connect@RRsfwSession@@QAEHXZ @ 6 NONAME ; int RRsfwSession::Connect(void) + ?CreateFile@RRsfwSession@@QAEHVTFid@@ABVTDesC16@@IIAAV2@@Z @ 7 NONAME ; int RRsfwSession::CreateFile(class TFid, class TDesC16 const &, unsigned int, unsigned int, class TFid &) + ?ExternalizeL@TDirEnt@@QBEXAAVRWriteStream@@@Z @ 8 NONAME ; void TDirEnt::ExternalizeL(class RWriteStream &) const + ?ExternalizeL@TDirEntAttr@@QBEXAAVRWriteStream@@@Z @ 9 NONAME ; void TDirEntAttr::ExternalizeL(class RWriteStream &) const + ?Fetch@RRsfwSession@@QAEHVTFid@@HHAAH@Z @ 10 NONAME ; int RRsfwSession::Fetch(class TFid, int, int, int &) + ?FetchData@RRsfwSession@@QAEHVTFid@@HHAAVTDes16@@AAH@Z @ 11 NONAME ; int RRsfwSession::FetchData(class TFid, int, int, class TDes16 &, int &) + ?Flush@RRsfwSession@@QAEHVTFid@@HHH@Z @ 12 NONAME ; int RRsfwSession::Flush(class TFid, int, int, int) + ?FlushCache@RRsfwSession@@QAEHAAVTFid@@@Z @ 13 NONAME ; int RRsfwSession::FlushCache(class TFid &) + ?GetAttributes@RRsfwSession@@QAEHVTFid@@AAVTEntry@@@Z @ 14 NONAME ; int RRsfwSession::GetAttributes(class TFid, class TEntry &) + ?InternalizeL@TDirEnt@@QAEXAAVRReadStream@@@Z @ 15 NONAME ; void TDirEnt::InternalizeL(class RReadStream &) + ?InternalizeL@TDirEntAttr@@QAEXAAVRReadStream@@@Z @ 16 NONAME ; void TDirEntAttr::InternalizeL(class RReadStream &) + ?Lookup@RRsfwSession@@QAEHVTFid@@ABVTDesC16@@IAAV2@@Z @ 17 NONAME ; int RRsfwSession::Lookup(class TFid, class TDesC16 const &, unsigned int, class TFid &) + ?MakeDirectory@RRsfwSession@@QAEHVTFid@@ABVTDesC16@@@Z @ 18 NONAME ; int RRsfwSession::MakeDirectory(class TFid, class TDesC16 const &) + ?MoveFids@RRsfwSession@@QAEHVTFid@@ABVTDesC16@@01H@Z @ 19 NONAME ; int RRsfwSession::MoveFids(class TFid, class TDesC16 const &, class TFid, class TDesC16 const &, int) + ?OkToWrite@RRsfwSession@@QAEHVTFid@@IAAH@Z @ 20 NONAME ; int RRsfwSession::OkToWrite(class TFid, unsigned int, int &) + ?OpenByPath@RRsfwSession@@QAEHVTFid@@AAVTDes16@@PAVTDirEntAttr@@H@Z @ 21 NONAME ; int RRsfwSession::OpenByPath(class TFid, class TDes16 &, class TDirEntAttr *, int) + ?RemoveDirectory@RRsfwSession@@QAEHVTFid@@ABVTDesC16@@@Z @ 22 NONAME ; int RRsfwSession::RemoveDirectory(class TFid, class TDesC16 const &) + ?RemoveFile@RRsfwSession@@QAEHVTFid@@ABVTDesC16@@@Z @ 23 NONAME ; int RRsfwSession::RemoveFile(class TFid, class TDesC16 const &) + ?RfeInit@RRsfwSession@@QAEHAAVTFid@@@Z @ 24 NONAME ; int RRsfwSession::RfeInit(class TFid &) + ?SetEntry@RRsfwSession@@QAEHVTFid@@ABVTTime@@II@Z @ 25 NONAME ; int RRsfwSession::SetEntry(class TFid, class TTime const &, unsigned int, unsigned int) + ?SetHighCachePriority@RRsfwSession@@QAEHAAVTFid@@@Z @ 26 NONAME ; int RRsfwSession::SetHighCachePriority(class TFid &) + ?Version@RRsfwSession@@QBE?AVTVersion@@XZ @ 27 NONAME ; class TVersion RRsfwSession::Version(void) const + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/data/RemoteFileEngine.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/data/RemoteFileEngine.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,81 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Resource file Remote File Engine +* +*/ + + +// RESOURCE IDENTIFIER +NAME RSFE // 4 letter ID + +// INCLUDES +#include +#include +#include +#include +#include +#include +#include +#include + +// RESOURCE DEFINITIONS + +RESOURCE RSS_SIGNATURE + { + } + +// --------------------------------------------------------- +// +// Default Document Name +// +// --------------------------------------------------------- +// +RESOURCE TBUF + { + buf=""; + } + + +//------------------------------------------------------------------------------ +// +// r_remotefe_memory_selection_dialog +// Defines a memory selection dialog +// +//------------------------------------------------------------------------------ +RESOURCE MEMORYSELECTIONDIALOG r_remotefe_memory_selection_dialog + { + softkey_1 = text_softkey_select; + softkey_2 = text_softkey_cancel; + } + +//---------------------------------------------------- +// +// string resouces +// the strings can be localized in loc file +// +//---------------------------------------------------- +// +RESOURCE LBUF r_wait_note_connecting { txt = qtn_rd_wait_connecting; } +RESOURCE LBUF r_wait_note_transferring { txt = qtn_rd_wait_transferring; } +RESOURCE LBUF r_save_query_confirm { txt = qtn_rd_query_file_save_fail; } +RESOURCE LBUF r_wait_note_retrieving { txt = qtn_gen_note_fetching; } +RESOURCE LBUF r_note_address_not_available { txt = qtn_rd_error_faulty_address; } +RESOURCE LBUF r_confirm_drive_unavailable { txt = qtn_rd_conf_drive_unavailable; } +RESOURCE LBUF r_confirm_file_saved_to { txt = qtn_fldr_file_saved_to; } +RESOURCE LBUF r_saving_failed { txt = qtn_rd_all_serv_failed; } +RESOURCE LBUF r_wait_note_disc_warning { txt = qtn_rd_conf_query_open_files_disconnect; } +RESOURCE LBUF r_no_network_coverage { txt = qtn_rd_err_no_network_cover; } +RESOURCE LBUF r_offline_not_possible { txt = qtn_offline_not_possible; } +RESOURCE LBUF r_ram_out_of_memory { txt = qtn_memlo_ram_out_of_mem; } +//End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/data/rsfw.cfg --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/data/rsfw.cfg Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,4 @@ +SIP=no +SipId=sip:mypocket1@hera.wipsl.com +permanent_meta_data=yes +conflict_resolution_policy=client_dominates diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/eabi/rsfwcommonu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/eabi/rsfwcommonu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,57 @@ +EXPORTS + _ZN11CRsfwDirEnt11ExtractAttrEv @ 1 NONAME + _ZN11CRsfwDirEnt4NewLERK6TDesC8P15CRsfwDirEntAttr @ 2 NONAME + _ZN11CRsfwDirEnt4NewLERK7TDesC16P15CRsfwDirEntAttr @ 3 NONAME + _ZN11CRsfwDirEnt5NewLCERK6TDesC8P15CRsfwDirEntAttr @ 4 NONAME + _ZN11CRsfwDirEnt5NewLCERK7TDesC16P15CRsfwDirEntAttr @ 5 NONAME + _ZN11CRsfwDirEnt8SetAttrLEP15CRsfwDirEntAttr @ 6 NONAME + _ZN11CRsfwDirEnt8SetNameLERK6TDesC8 @ 7 NONAME + _ZN11CRsfwDirEnt8SetNameLERK7TDesC16 @ 8 NONAME + _ZN11CRsfwDirEntD0Ev @ 9 NONAME + _ZN11CRsfwDirEntD1Ev @ 10 NONAME + _ZN11CRsfwDirEntD2Ev @ 11 NONAME + _ZN15CRsfwDirEntAttr11SetAttFlagsEj @ 12 NONAME + _ZN15CRsfwDirEntAttr11SetModifiedERK5TTime @ 13 NONAME + _ZN15CRsfwDirEntAttr12SetMimeTypeLERK6TDesC8 @ 14 NONAME + _ZN15CRsfwDirEntAttr13ResetAttFlagsEj @ 15 NONAME + _ZN15CRsfwDirEntAttr15SetStringValueLEiRK6TDesC8 @ 16 NONAME + _ZN15CRsfwDirEntAttr3UidEv @ 17 NONAME + _ZN15CRsfwDirEntAttr4NewLEv @ 18 NONAME + _ZN15CRsfwDirEntAttr5NewLCEv @ 19 NONAME + _ZN15CRsfwDirEntAttr6SetAttEj @ 20 NONAME + _ZN15CRsfwDirEntAttr6SetUidE4TUid @ 21 NONAME + _ZN15CRsfwDirEntAttr7SetSizeEi @ 22 NONAME + _ZN15CRsfwDirEntAttr8SetETagLERK6TDesC8 @ 23 NONAME + _ZN15CRsfwDirEntAttrD0Ev @ 24 NONAME + _ZN15CRsfwDirEntAttrD1Ev @ 25 NONAME + _ZN15CRsfwDirEntAttrD2Ev @ 26 NONAME + _ZN17CRsfwRemoteAccess16GetQuotaAndSizeLERiS0_ @ 27 NONAME + _ZN17CRsfwRemoteAccess4NewLERK6TDesC8 @ 28 NONAME + _ZN17CRsfwRemoteAccessD0Ev @ 29 NONAME + _ZN17CRsfwRemoteAccessD1Ev @ 30 NONAME + _ZN17CRsfwRemoteAccessD2Ev @ 31 NONAME + _ZN22CRsfwConnectionManager13GetConnectionERP11RSocketServRP11RConnection @ 32 NONAME + _ZN22CRsfwConnectionManager4NewLEP23MRsfwConnectionObserver @ 33 NONAME + _ZN22CRsfwConnectionManager7UseIapLERK7TDesC16 @ 34 NONAME + _ZN22CRsfwConnectionManagerD0Ev @ 35 NONAME + _ZN22CRsfwConnectionManagerD1Ev @ 36 NONAME + _ZN22CRsfwConnectionManagerD2Ev @ 37 NONAME + _ZNK11CRsfwDirEnt4AttrEv @ 38 NONAME + _ZNK11CRsfwDirEnt4NameEv @ 39 NONAME + _ZNK11CRsfwDirEnt7GetNameER5TDes8 @ 40 NONAME + _ZNK11CRsfwDirEnt7GetNameER6TDes16 @ 41 NONAME + _ZNK15CRsfwDirEntAttr11StringValueEi @ 42 NONAME + _ZNK15CRsfwDirEntAttr3AttEv @ 43 NONAME + _ZNK15CRsfwDirEntAttr4ETagEv @ 44 NONAME + _ZNK15CRsfwDirEntAttr4SizeEv @ 45 NONAME + _ZNK15CRsfwDirEntAttr8MimeTypeEv @ 46 NONAME + _ZNK15CRsfwDirEntAttr8ModifiedEv @ 47 NONAME + _ZTI11CRsfwDirEnt @ 48 NONAME ; ## + _ZTI15CRsfwDirEntAttr @ 49 NONAME ; ## + _ZTI17CRsfwRemoteAccess @ 50 NONAME ; ## + _ZTI22CRsfwConnectionManager @ 51 NONAME ; ## + _ZTV11CRsfwDirEnt @ 52 NONAME ; ## + _ZTV15CRsfwDirEntAttr @ 53 NONAME ; ## + _ZTV17CRsfwRemoteAccess @ 54 NONAME ; ## + _ZTV22CRsfwConnectionManager @ 55 NONAME ; ## + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/eabi/rsfwcontrolu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/eabi/rsfwcontrolu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,16 @@ +EXPORTS + _ZN12RRsfwControl12GetMountInfoERK5TCharR14TRsfwMountInfo @ 1 NONAME + _ZN12RRsfwControl16RefreshDirectoryERK7TDesC16 @ 2 NONAME + _ZN12RRsfwControl18DismountByVolumeIdEi @ 3 NONAME + _ZN12RRsfwControl20CancelRemoteTransferERK7TDesC16 @ 4 NONAME + _ZN12RRsfwControl21DismountByDriveLetterE5TChar @ 5 NONAME + _ZN12RRsfwControl23SetMountConnectionStateERK5TCharj @ 6 NONAME + _ZN12RRsfwControl5MountERK16TRsfwMountConfigR14TRequestStatus @ 7 NONAME + _ZN12RRsfwControl5MountEi @ 8 NONAME + _ZN12RRsfwControl7ConnectEv @ 9 NONAME + _ZN12RRsfwControl7VersionEv @ 10 NONAME + _ZN12RRsfwControlC1Ev @ 11 NONAME + _ZN12RRsfwControlC2Ev @ 12 NONAME + _ZN12RRsfwControl10MountBlindEi @ 13 NONAME + _ZN12RRsfwControl5MountERK16TRsfwMountConfig @ 14 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/eabi/rsfwsessionu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/eabi/rsfwsessionu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,30 @@ +EXPORTS + _ZN11TDirEntAttr12InternalizeLER11RReadStream @ 1 NONAME + _ZN11TDirEntAttr5ClearEv @ 2 NONAME + _ZN12RRsfwSession10CreateFileE4TFidRK7TDesC16jjRS0_ @ 3 NONAME + _ZN12RRsfwSession10FlushCacheER4TFid @ 4 NONAME + _ZN12RRsfwSession10OpenByPathE4TFidR6TDes16P11TDirEntAttri @ 5 NONAME + _ZN12RRsfwSession10RemoveFileE4TFidRK7TDesC16 @ 6 NONAME + _ZN12RRsfwSession13GetAttributesE4TFidR6TEntry @ 7 NONAME + _ZN12RRsfwSession13MakeDirectoryE4TFidRK7TDesC16 @ 8 NONAME + _ZN12RRsfwSession15RemoveDirectoryE4TFidRK7TDesC16 @ 9 NONAME + _ZN12RRsfwSession20SetHighCachePriorityER4TFid @ 10 NONAME + _ZN12RRsfwSession5CloseEv @ 11 NONAME + _ZN12RRsfwSession5FetchE4TFidiiRi @ 12 NONAME + _ZN12RRsfwSession5FlushE4TFidiii @ 13 NONAME + _ZN12RRsfwSession6LookupE4TFidRK7TDesC16jRS0_ @ 14 NONAME + _ZN12RRsfwSession7ConnectEv @ 15 NONAME + _ZN12RRsfwSession7RfeInitER4TFid @ 16 NONAME + _ZN12RRsfwSession8MoveFidsE4TFidRK7TDesC16S0_S3_i @ 17 NONAME + _ZN12RRsfwSession8SetEntryE4TFidRK5TTimejj @ 18 NONAME + _ZN12RRsfwSession9CloseFileE4TFidj @ 19 NONAME + _ZN12RRsfwSession9FetchDataE4TFidiiR6TDes16Ri @ 20 NONAME + _ZN12RRsfwSession9OkToWriteE4TFidjRi @ 21 NONAME + _ZN12RRsfwSessionC1Ev @ 22 NONAME + _ZN12RRsfwSessionC2Ev @ 23 NONAME + _ZN7TDirEnt12InternalizeLER11RReadStream @ 24 NONAME + _ZN7TDirEnt5ClearEv @ 25 NONAME + _ZNK11TDirEntAttr12ExternalizeLER12RWriteStream @ 26 NONAME + _ZNK12RRsfwSession7VersionEv @ 27 NONAME + _ZNK7TDirEnt12ExternalizeLER12RWriteStream @ 28 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,39 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build information file for project Remote File Engine +* +*/ + +#include + +PRJ_EXPORTS +../inc/rsfwdirent.h |../../../inc/rsfwdirent.h +../inc/rsfwdirentattr.h |../../../inc/rsfwdirentattr.h +../inc/rsfwremoteaccess.h |../../../inc/rsfwremoteaccess.h +../inc/rsfwcontrol.h |../../inc/rsfwcontrol.h +../inc/rsfwcommon.h |../../inc/rsfwcommon.h +../inc/rsfwconnectionmanager.h |../../inc/rsfwconnectionmanager.h +../inc/rsfwfile.h |../../inc/rsfwfile.h +../inc/rsfwinterface.h |../../inc/rsfwinterface.h +../inc/rsfwinterface.inl |../../inc/rsfwinterface.inl +../inc/rsfwsession.h |../../inc/rsfwsession.h +// export localised loc file +../loc/RemoteFileEngine.loc MW_LAYER_LOC_EXPORT_PATH(RemoteFileEngine.loc) + +PRJ_MMPFILES +rsfwsession.mmp +rsfwcontrol.mmp +rsfwcommon.mmp +remotefe.mmp +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/group/remotefe.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/group/remotefe.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,108 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project remote file engine +* +*/ + + +#include +#include + +TARGET remotefe.exe +TARGETTYPE exe +UID 0x100039ce 0x101F970D + +CAPABILITY NetworkServices ReadDeviceData WriteDeviceData ReadUserData +VENDORID VID_DEFAULT + +SOURCEPATH ../src +SOURCE rsfwrfestatemachine.cpp +SOURCE rsfwwaitnotestatemachine.cpp +SOURCE rsfwattributerefreshingstatemachine.cpp +SOURCE rsfwclosestatemachine.cpp +SOURCE rsfwflushstatemachine.cpp +SOURCE rsfwcreatefilestatemachine.cpp +SOURCE rsfwdeletestatemachine.cpp +SOURCE rsfwfetchandcachestatemachine.cpp +SOURCE rsfwfetchdatastatemachine.cpp +SOURCE rsfwgetattributesstatemachine.cpp +SOURCE rsfwlookupstatemachine.cpp +SOURCE rsfwmkdirstatemachine.cpp +SOURCE rsfwmountconnectionstatemachine.cpp +SOURCE rsfwmountstatemachine.cpp +SOURCE rsfwopenbypathstatemachine.cpp +SOURCE rsfwrenamefilestatemachine.cpp +SOURCE rsfwsyncoperations.cpp +SOURCE rsfwrequestallocator.cpp +SOURCE rsfwrferequest.cpp +SOURCE rsfwrfemessagerequest.cpp +SOURCE rsfwrfeoperation.cpp +SOURCE rsfwrfesyncoperation.cpp +SOURCE rsfwrfeasyncoperation.cpp +SOURCE rsfwfiletable.cpp +SOURCE rsfwfileentry.cpp +SOURCE rsfwvolumetable.cpp +SOURCE rsfwvolume.cpp +SOURCE rsfwlruprioritylist.cpp +SOURCE rsfwlrulistnode.cpp +SOURCE rsfwfileengine.cpp +SOURCE rsfwrfeserver.cpp +SOURCE rsfwrfesession.cpp +SOURCE rsfwlockmanager.cpp +SOURCE rsfwpermanentstore.cpp +SOURCE rsfwmetadatastore.cpp +SOURCE rsfwwaitnotemanager.cpp +SOURCE rsfwdormantmountloader.cpp +SOURCEPATH ../../MDebug/src +SOURCE mdebug.cpp + +SOURCEPATH ../data +START RESOURCE RemoteFileEngine.rss +HEADER +TARGETPATH RESOURCE_FILES_DIR +LANGUAGE_IDS +END // RESOURCE + + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +SYSTEMINCLUDE /epoc32/include/libc +SYSTEMINCLUDE /epoc32/include/libc/sys +SYSTEMINCLUDE /epoc32/include/ecom +USERINCLUDE ../inc + + +LIBRARY euser.lib +LIBRARY efsrv.lib +LIBRARY estor.lib +LIBRARY apgrfx.lib // for RApaLsSession +LIBRARY apmime.lib // for TDataType +LIBRARY inetprotutil.lib // uri parsers +LIBRARY sysutil.lib // DiskSpaceBelowCriticalLevel +LIBRARY ecom.lib +LIBRARY bafl.lib // for RResourceFile +LIBRARY aknnotify.lib // for the global notes +LIBRARY commonengine.lib // for S60 .loc formatting in stringloader +LIBRARY directorylocalizer.lib +LIBRARY rsfwmountstore.lib +LIBRARY rsfwmountman.lib +LIBRARY rsfwcommon.lib +LIBRARY rsfwconfig.lib +LIBRARY rsfwsession.lib +LIBRARY flogger.lib + + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/group/rsfwcommon.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/group/rsfwcommon.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,51 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project RSFW common definitions +* +*/ + +#include + +CAPABILITY ALL -TCB + +TARGET rsfwcommon.dll +TARGETTYPE dll +UID 0x1000008d 0x101F9776 + +SOURCEPATH ../src +SOURCE rsfwremoteaccess.cpp +SOURCE rsfwdirent.cpp +SOURCE rsfwdirentattr.cpp +SOURCE rsfwconnectionmanager.cpp +SOURCEPATH ../../MDebug/src +SOURCE mdebug.cpp + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +SYSTEMINCLUDE /epoc32/include/ecom +USERINCLUDE ../inc + +LIBRARY commdb.lib +LIBRARY connmon.lib +LIBRARY ecom.lib +LIBRARY esock.lib +LIBRARY euser.lib +LIBRARY flogger.lib + +DEFFILE rsfwcommon.def + +LANG SC + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/group/rsfwcontrol.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/group/rsfwcontrol.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,43 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project Remote File Engine Control API +* +*/ + +#include + +CAPABILITY ALL -TCB + +TARGET rsfwcontrol.dll +TARGETTYPE dll +UID 0x1000008d 0x101F976C + +SOURCEPATH ../src +SOURCE rsfwcontrol.cpp + + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY euser.lib + +DEFFILE rsfwcontrol.def + +LANG SC + + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/group/rsfwsession.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/group/rsfwsession.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,48 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project Remote File Engine Access API +* +*/ + + +#include +// Must have TCB as is used by the File Server process +CAPABILITY ALL + +TARGET rsfwsession.dll +TARGETTYPE dll +UID 0x1000008d 0x101F976B + +SOURCEPATH ../src +SOURCE rsfwsession.cpp +SOURCE rsfwinterface.cpp + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +USERINCLUDE ../inc + +LIBRARY euser.lib +LIBRARY estor.lib + +DEFFILE rsfwsession.def + +LANG SC + +// End of File + + + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/mydebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/mydebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,33 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug definitions for Remote File Engine + * +*/ + + +#ifndef MYDEBUG_H +#define MYDEBUG_H + +// Debug defines for Remote File Engine + +// MACROS +#define APPEND_TO_DEBUG_FILE + +// CONSTANTS +_LIT(KDebugDirName, "rfe"); +_LIT(KDebugFileName, "rfe.txt"); + +#endif // MYDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwattributerefreshingstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwattributerefreshingstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,45 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: States that need to refresh file or directory attributes +* +*/ + +#ifndef C_RSFW_ATTRIBUTEREFRESHINGSTATEMACHINE_H +#define C_RSFW_ATTRIBUTEREFRESHINGSTATEMACHINE_H + +#include "rsfwrfestatemachine.h" + +// FORWARD DECLARATIONS +class CRsfwDirEntAttr; + +/** + * Parent class for operations that need to refresh file or + * directory attributes. + * + */ + class CRsfwAttributeRefreshingStateMachine : public CRsfwRfeStateMachine + { + public: + ~CRsfwAttributeRefreshingStateMachine(); + public: + // file or directory attributes + CRsfwDirEntAttr* iDirEntAttr; + // The old attributes for a cached file or directory. + // Comparing the tells whether the actual data must + // be fetched from the server. + CRsfwDirEntAttr* iDirEntAttrOld; + }; + + +#endif // C_RSFW_ATTRIBUTEREFRESHINGSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwclosestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwclosestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,79 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for closing a file +* +*/ + + +#ifndef C_RSFW_CLOSESTATEMACHINE_H +#define C_RSFW_CLOSESTATEMACHINE_H + + +#include "rsfwwaitnotestatemachine.h" +#include "rsfwsavetodlgrequest.h" + +/** + * State machine for closing a file + * + * Consists of following states: + * - File is written to the server + * - Possible lock is released + * - If writing fails, file becomes "dirty" and + * is saved locally. + * + */ + +class CRsfwCloseStateMachine : public CRsfwWaitNoteStateMachine + { +public: + CRsfwCloseStateMachine(); + ~CRsfwCloseStateMachine(); + +public: + // STATES + class TReleaseLockState : public CRsfwCloseStateMachine::TState + { + public: + TReleaseLockState(CRsfwCloseStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwCloseStateMachine* iOperation; + }; + + class TSaveLocallyState : public CRsfwCloseStateMachine::TState + { + public: + TSaveLocallyState(CRsfwCloseStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwCloseStateMachine* iOperation; + TRsfwSaveToDlgRequest iSaveToRequest; + TBuf iFileSizeString; + }; + +public: + TState* CompleteRequestL(TInt aError); + TState* ErrorOnStateEntry(TInt aError); + +public: + TInt iFlags; + }; + + + +#endif // C_RSFW_CLOSESTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwcommon.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwcommon.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,76 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Definitions that are common to the Access API and Control API + * +*/ + +#ifndef RSFWCOMMON_H +#define RSFWCOMMON_H + +// INCLUDES +#include + +// names needed when starting the server. +_LIT(KRfeSemaphoreName, "RfeSemaphore"); +// the name of the server, used in Connect() +_LIT(KRfeServerName, "remotefe"); + +// special values for IAP selection +_LIT(KIapDefaultPreferences, "*"); +_LIT(KIapAskUser, "?"); + +// the server version +// A version must be specified when creating a session with the server +const TUint KRfeMajorVersionNumber = 0; +const TUint KRfeMinorVersionNumber = 1; +const TUint KRfeBuildVersionNumber = 1; + +// DATA TYPES +// opcodes used in message passing between client and server +// opcodes used in message passing between client and server +enum TRfeRqst + { + ERfeRequest, + EAsynchRequest, + EMount, + EMountByDriveLetter, + EDismountByVolumeId, + EDismountByDriveLetter, + EGetMountList, + EGetMountInfo, + ESetMountConnectionState, + EDirRefresh, + ECancelAll, + ERenameReplace, + ESetAttr, + EFsIoctl, + EGetAttr, + EOpenByPath, + EFsRoot, + EMkDir, + ERemoveDir, + ECreateFile, + ERemove, + ELookUp, + EClose, + EFlush, + EFetch, + EFetchData, + EOkToWrite, + EMaxRfeOperations + }; + +#endif // RSFWCOMMON_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwconnectionmanager.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwconnectionmanager.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,123 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Connection manager + * +*/ + + +#ifndef CRSFWCONNECTIONMANAGER_H +#define CRSFWCONNECTIONMANAGER_H + +// INCLUDES +#include +#include +#include + +// FORWARD DECLARATIONS + +// DATA TYPES +// Connection event types for MRsfwConnectionObserver +enum TRsfwConnectionObserverEventConnection + { + ERsfwConnectionObserverEventConnectionDisconnected = 0, + ERsfwConnectionObserverEventConnectionWeaklyConnected, + ERsfwConnectionObserverEventConnectionStronglyConnected + }; + +enum TRsfwConnectionManagerConnectionQuality + { + ERsfwConnectionQualityNull = 0, + ERsfwConnectionQualityStrong + }; + +// IAP selection algorithms +enum TRsfwConnectionManagerIapSelection + { + ERsfwIapSelectionAskUser = 0, // show the IAP selection menu + ERsfwIapSelectionUseDefaultPreferences, // use CommDB preferences + ERsfwIapSelectionExplicit // use explicit list + }; + +// CLASS DECLARATION +class TIapInfo + { +public: + TBuf iName; + TUint32 iId; + TBuf iNetworkName; + TBuf iServiceName; + TBuf iSsId; + TBuf iBearerType; + TInt iBearerQuality; // weak/strong + }; + +// CLASS DECLARATION +class MRsfwConnectionObserver + { +public: + virtual void HandleConnectionEventL(TInt aConnectionEventType, + TAny* aArg) = 0; + }; + +// CLASS DECLARATION +// This class manages the link layer for the Rsfw remote access modules. +// +// The primary input is a list of access point names that are assumed +// to be in preference order. However, +// 1) if the list only contains a "*" string, +// static commdb preference order will be used, or else +// 2) if the list is empty, +// the user will be prompted for an access point +// +class CRsfwConnectionManager: public CActive + { +public: + // Ownership of aIapNames moves to RsfwConnectionManager + IMPORT_C static CRsfwConnectionManager* NewL( + MRsfwConnectionObserver* aConnectionObserver); + IMPORT_C virtual ~CRsfwConnectionManager(); + IMPORT_C void UseIapL(const TDesC& aIap); + IMPORT_C TInt GetConnection(RSocketServ*& aSocketServ, RConnection*& aConnection); + +private: + CRsfwConnectionManager(); + void ConstructL(MRsfwConnectionObserver* aConnectionObserver); + TInt LoadIapInfoL(TIapInfo& aIapInfo); + TInt StartConnection(TUint32 aIapId, TCommDbDialogPref aDialogPreference); + void HandleDisconnectionEventL(); + + // functions related to timer for GPRS 'suspend' event + static TInt SuspensionTimerExpiredL(TAny* aArg); + void StartSuspensionTimer(); + void StopSuspensionTimer(); + + + // from CActive + void RunL(); + TInt RunError(TInt aError); + void DoCancel(); + +private: // Data + RSocketServ iSocketServ; + RConnection iConnection; + MRsfwConnectionObserver* iConnectionObserver; + TInt iIapSelection; // IAP selection policy + RArray iIaps; // allowed IAPs, if any + TPckgBuf iProgress; + CPeriodic* iSuspensionTimer; // for GPRS 'suspend' events + }; + +#endif // CRSFWCONNECTIONMANAGER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwcontrol.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwcontrol.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,207 @@ +/* +* Copyright (c) 2005-2007 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File Engine Control API +* +*/ + + + +#ifndef RRSFWCONTROL_H +#define RRSFWCONTROL_H + +// INCLUDES +#include +#include +#include +#include + +// CONSTANTS + +// Number of message slots to reserve for this client server session. +const TUint KDefaultMessageSlots = 4; + +// Mounting options +const TUint KMountFlagNull = 0x00; // nothing +const TUint KMountFlagInteractive = 0x01; // do user prompting +const TUint KMountFlagAskPassword = 0x02; // ask the user for password +const TUint KMountFlagOffLine = 0x04; // mount in disconnected mode +const TUint KMountFlagAsync = 0x10; // mount asynchronously +const TUint KMountFlagAllocDriveLetter = 0x20; // find a free drive letter +const TUint KMountFlagMountAtRfeOnly = 0x40; // mount only at the RFE + +// Mount states +const TUint KMountStateDormant = 0x01; // only persistent metada on disk +const TUint KMountStateMounted = 0x02; + +// Data types + +enum TMountControl + { + EMountControlPermanence + }; + +enum TRfeError + { + EServerNotAvailable = 3 + }; + + +// CLASS DECLARATIONS + +class RRsfwControl : public RSessionBase + { +public: // Constructors and destructor + /** + * Constructor. + */ + IMPORT_C RRsfwControl(); + +public: // New functions + /** + * Connect to the server and create a session. + * @since Series 60 3.1 + * @param aServerName Server name. + * @return Standard error code. + */ + IMPORT_C TInt Connect(); + + /** + * Get the server version number. + * @since Series 60 3.1 + * @return The version number of the server. + */ + IMPORT_C TVersion Version(); + + /** + * Mount a remote drive - synchronous version + * @since Series 60 3.1 + * @param aDriveLetter - letter of the drive to be mounted + * @return error code. + */ + IMPORT_C TInt Mount(TInt aDriveLetter); + + + /** + * Mount a remote drive - synchronous version + * @since Series 60 3.1 + * @param aMountConfig mount configuration information + * The following TRsfwMountConfig::iFlags are used in this function: + * KMountFlagOffLine mount in disconnected mode + * @param aStatus returned status code. + * @return error code. + */ + IMPORT_C TInt Mount(const TRsfwMountConfig& aMountConfig); + + /** + * Mount a remote drive - asynchronous version + * @since Series 60 3.1 + * @param aMountConfig mount configuration information + * The following TRsfwMountConfig::iFlags are used in this function: + * KMountFlagOffLine mount in disconnected mode + * @param aStatus returned status code. + * @return error code. + */ + IMPORT_C void Mount(const TRsfwMountConfig& aMountConfig, + TRequestStatus& aStatus); + + /** + * Dismount a remote drive by referring to the id of the volume in RFE + * @since Series 60 3.1 + * @param aVolumeId volume identifier (can be found in TRsfwMountInfo) + * @return error code. + */ + IMPORT_C TInt DismountByVolumeId(TInt aVolumeId); + + /** + * Dismount a remote drive by referring to the drive letter + * @since Series 60 3.1 + * @param aDriveLetter drive letter (can be found in TRsfwMountInfo) + * @return error code. + */ + IMPORT_C TInt DismountByDriveLetter(TChar aDriveLetter); + + /** + * Get information about the specified drive + * @since Series 60 3.1 + * @param aDriveLetter drive letter. + * @param aMountInfo to be filled. + * @return error code. + */ + IMPORT_C TInt GetMountInfo(const TChar& aDriveLetter, + TRsfwMountInfo& aMountInfo); + + /** + * Set mount connection state + * @since Series 60 3.1 + * @param aDriveLetter drive letter. + * @param aState connection state: + * KMountStronglyConnected or KMountNotConnected. + * @return error code. + */ + IMPORT_C TInt SetMountConnectionState(const TChar& aDriveLetter, + TUint aState); + + + /** + * Refresh a remote directory + * + * Ensures that contents of a remote directory are up to date. + * Synchronous variant deletes the currently cached version. + * Note that this function intentionally does not return directory + * contents. All data should be read through the File Server instead. + * + * @param aPath the remote path + * @return KErrArgument Path refers to a file + * KErrNotFound path is not found from cache + */ + IMPORT_C TInt RefreshDirectory(const TDesC& aPath); + + /** + * Cancels an active remote file upload or download + * + * @param aFile file name + * @return The number of remote operations cancelled + * or one of the system wide error codes. + */ + IMPORT_C TInt CancelRemoteTransfer(const TDesC& aFile); + + + /** + * Mount a remote drive - "blind request" version + * @since Series 60 3.1 + * @param aDriveLetter - letter of the drive to be mounted + * @return error code. + */ + IMPORT_C TInt MountBlind(TInt aDriveLetter); + + + +private: + static TInt StartServer(const TDesC& aServerName); + static TInt CreateServerProcess(const TDesC& aServerName); + TInt SendRequest(TInt aOpCode, + TIpcArgs aArgs); + void SendRequest(TInt aOpCode, + TIpcArgs aArgs, + TRequestStatus& aStatus); + +private: + TIpcArgs iArgs; + TPckgBuf iPckgBufMountConfig; // for asynchronous ipc + }; + + +#endif // RRSFWCONTROL_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwcreatefilestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwcreatefilestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,89 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for creating files +* +*/ + + +#ifndef C_RSFW_CREATEFILESTATEMACHINE_H +#define C_RSFW_CREATEFILESTATEMACHINE_H + +#include "rsfwrfestatemachine.h" + +/** + * Creates a file + * + * State machine for creating a file. Possibly could be combined with + * CRsfwMkDirStateMachine, the differences are not that big... + * + */ +class CRsfwCreateFileStateMachine : public CRsfwRfeStateMachine + { +public: + CRsfwCreateFileStateMachine(); + ~CRsfwCreateFileStateMachine(); + +public: + + class TCheckIfExistsState : public CRsfwCreateFileStateMachine::TState + { + public: + TCheckIfExistsState(CRsfwCreateFileStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwCreateFileStateMachine* iOperation; + TInt iExclp; + }; + + class TCreateNodeState : public CRsfwCreateFileStateMachine::TState + { + public: + TCreateNodeState(CRsfwCreateFileStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwCreateFileStateMachine* iOperation; + }; + + class TAcquireLockState : public CRsfwCreateFileStateMachine::TState + { + public: + TAcquireLockState(CRsfwCreateFileStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwCreateFileStateMachine* iOperation; + private: + TBool iRequestedLock; + }; + +public: + TState* CompleteRequestL(TInt aError); + + CRsfwFileEntry* iKidFep; + TBool iKidCreated; + // file open mode + TUint iFlags; + + // used in TCheckIfExistsState + CRsfwDirEntAttr* iDirEntAttr; + TDesC8* iLockToken; + }; + + +#endif // C_RSFW_CREATEFILESTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwdeletestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwdeletestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,77 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Delete a file or directory +* +*/ + + +#ifndef C_RSFW_DELETESTATEMACHINE_H +#define C_RSFW_DELETESTATEMACHINE_H + +#include "rsfwrfestatemachine.h" + +/** + * Deletes a file or directory + * + * State machine for deleting a file or directory. + * + */ + class CRsfwDeleteStateMachine : public CRsfwRfeStateMachine + { +public: + CRsfwDeleteStateMachine(TUint iNodeType); + ~CRsfwDeleteStateMachine(); + +public: + // STATES + // TCheckIfCanBeDeleted: + // If a directory is not empty, it must not be deleted + class TCheckIfCanBeDeleted : public CRsfwDeleteStateMachine::TState + { + public: + TCheckIfCanBeDeleted(CRsfwDeleteStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwDeleteStateMachine* iOperation; + }; + + class TDeleteNodeState : public CRsfwDeleteStateMachine::TState + { + public: + TDeleteNodeState(CRsfwDeleteStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwDeleteStateMachine* iOperation; + }; + +public: + TState* CompleteRequestL(TInt aError); + + TBool iKidCreated; + HBufC* iKidPath; + CRsfwFileEntry* iKidFep; + + TUint iNodeType; // are we removing file or directory... + + // directory entries + // used to fetch directory contents in TCheckIfCanBeDeleted + RPointerArray iDirEnts; + }; + + +#endif // C_RSFW_DELETESTATEMACHINE_H diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwdirent.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwdirent.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,148 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Directory entry container + * +*/ + + +#ifndef CRSFWDIRENT_H +#define CRSFWDIRENT_H + +// INCLUDES +#include + +// CONSTANTS + +// DATA TYPES + +// FORWARD DECLARATIONS +class CRsfwDirEntAttr; + +// CLASS DECLARATION +/** + * Directory entry container + * + * @lib rsfwcommon.lib + * @since Series 60 3.1 + */ +class CRsfwDirEnt: public CBase + { +public: + + /** + * Two-phased constructor + * @param aName name of the entry + * @param aAttr attributes - if this parameter is NULL, + * an attribute object with attribute values set to zero will be created. + * The entry takes ownership of the attribute object. + */ + IMPORT_C static CRsfwDirEnt* NewLC(const TDesC& aName, CRsfwDirEntAttr* aAttr); + + /** + * Two-phased constructor + * @param aName name of the entry + * @param aAttr attributes - if this parameter is NULL, + * an attribute object with attribute values set to zero will be created. + * The entry takes ownership of the attribute object. + */ + IMPORT_C static CRsfwDirEnt* NewLC(const TDesC8& aName, CRsfwDirEntAttr* aAttr); + + /** + * Two-phased constructor. + * @param aName name of the entry + * @param aAttr attributes - if this parameter is NULL, + * an attribute object with attribute values set to zero will be created. + * The entry takes ownership of the attribute object. + */ + IMPORT_C static CRsfwDirEnt* NewL(const TDesC& aName, CRsfwDirEntAttr* aAttr); + + /** + * Two-phased constructor. + * @param aName name of the entry + * @param aAttr attributes - if this parameter is NULL, + * an attribute object with attribute values set to zero will be created. + * The entry takes ownership of the attribute object. + */ + IMPORT_C static CRsfwDirEnt* NewL(const TDesC8& aName, CRsfwDirEntAttr* aAttr); + + CRsfwDirEnt(); + + IMPORT_C ~CRsfwDirEnt(); + + /** + * Gets the name of the filesystem object + * @return pointer to the name + */ + IMPORT_C const HBufC* Name() const; + + /** + * Gets the name of the filesystem object + * @param aName name + */ + IMPORT_C void GetName(TDes& aName) const; + + /** + * Gets the name of the filesystem object + * @param aName name + */ + IMPORT_C void GetName(TDes8& aName) const; + + /** + * Sets the name of the filesystem object + * @param aName name + */ + IMPORT_C void SetNameL(const TDesC& aName); + + /** + * Sets the name of the filesystem object + * @param aName name + */ + IMPORT_C void SetNameL(const TDesC8& aName); + + /** + * Returns a pointer to the filesystem object's attributes + * @return pointer to the attributes + */ + IMPORT_C CRsfwDirEntAttr* Attr() const; + + /** + * Returns a pointer to the filesystem object's attributes + * The ownership to the attribute object is transferred to the caller + * @return pointer to the attributes + */ + IMPORT_C CRsfwDirEntAttr* ExtractAttr(); + + /** + * Sets the attribute object for the directory entry. + * The pre-existing attribute object is deleted (if owned by the entry). + * The directory entry gets ownership of the new attribute object. + * If the aAttr parameter is NULL, + * an attribute object with default values is created. + * @param pointer to the attribute object + */ + IMPORT_C void SetAttrL(CRsfwDirEntAttr* aAttr); + +private: + void ConstructL(const TDesC& aName, CRsfwDirEntAttr* aAttr); + void Construct8L(const TDesC8& aName, CRsfwDirEntAttr* aAttr); + +private: + HBufC* iName; // name + CRsfwDirEntAttr* iAttr; // attributes + TBool iNotOwnAttr; // we do not own the attributes (extracted) + }; + +#endif // CRSFWDIRENT_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwdirentattr.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwdirentattr.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,187 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Directory entry container + * +*/ + + +#ifndef CRSFWDIRENTATTR_H +#define CRSFWDIRENTATTR_H + +// INCLUDES +#include + +// CONSTANTS + +// DATA TYPES + +// FORWARD DECLARATIONS + +// CLASS DECLARATION +/** + * Filesystem object attribute container + * The attribute setting operations on this class + * do not affect any external objects - + * only the internal state of the object will be changed. + * Similarily, attribute getting operations only reflect the + * state of the object. + * + * @lib rsfwcommon.lib + * @since Series 60 3.1 + */ +class CRsfwDirEntAttr: public CBase + { +public: + enum TDirEntAttrString + { + EDirEntAttrStringMimeType = 0, + EDirEntAttrStringETag, + EDirEntAttrStringReserved, + EDirEntAttrStringCount + }; + +public: + /** + * Two-phased constructor + */ + IMPORT_C static CRsfwDirEntAttr* NewLC(); + + /** + * Two-phased constructor. + * The attribute values are zeroed + */ + IMPORT_C static CRsfwDirEntAttr* NewL(); + + CRsfwDirEntAttr(); + + IMPORT_C ~CRsfwDirEntAttr(); + + /** + * Gets file or directory attribute bits + * (for SymbianOS standard bit definitions, see f32file.h) + * @return attribute bits + */ + IMPORT_C TUint Att() const; + + /** + * Sets file or directory attribute bits + * (for SymbianOS standard bit definitions, see f32file.h) + * @param aAtt attribute bits + */ + IMPORT_C void SetAtt(TUint aAtt); + + /** + * Sets the given file or directory attribute bits to 1 + * (for SymbianOS standard bit definitions, see f32file.h) + * @param aFlags attribute bits + */ + IMPORT_C void SetAttFlags(TUint aFlags); + + /** + * Resets the given file or directory attribute bits to 0 + * (for SymbianOS standard bit definitions, see f32file.h) + * @param aFlags attribute bits + * (those bits are cleared that are set in aFlags) + */ + IMPORT_C void ResetAttFlags(TUint aFlags); + + /** + * Returns the size of the filesystem object + * @return size in bytes + */ + IMPORT_C TInt Size() const; + + /** + * Sets the size of the filesystem object + * @param aSize size in bytes + */ + IMPORT_C void SetSize(TInt aSize); + + /** + * Returns the last modified time of the filesystem object + * @return last modified time + */ + IMPORT_C TTime Modified() const; + + /** + * Sets the last modified time of the filesystem object + * @param aModified last modified time + */ + IMPORT_C void SetModified(const TTime& aModified); + + /** + * Returns the UID3 of the filesystem object + * @return UID value + */ + IMPORT_C const TUid& Uid(); + + /** + * Sets the UID3 time of the filesystem object + * @param aUid UID value + */ + IMPORT_C void SetUid(TUid aUid); + + /** + * Returns a string value at the given index + * @param aIndex index + * @return string value + */ + IMPORT_C const TDesC8* StringValue(TInt aIndex) const; + + /** + * Sets a string value at the given index + * @param aIndex index + * @param string value + */ + IMPORT_C void SetStringValueL(TInt aIndex, const TDesC8& aString); + + /** + * Gets the MIME type + * @return MIME type string + */ + IMPORT_C const TDesC8* MimeType() const; + + /** + * Sets the MIME type + * @param aMimeType MIME type string + */ + IMPORT_C void SetMimeTypeL(const TDesC8& aMimeType); + + /** + * Gets the ETag + * @return ETag string + */ + IMPORT_C const TDesC8* ETag() const; + + /** + * Sets the ETag type + * @param aETag ETag type string + */ + IMPORT_C void SetETagL(const TDesC8& aETag); + +private: + void ConstructL(); + +private: + TUint iAtt; // attribute bits + TInt iSize; // file size in bytes + TTime iModified; // last modified + TUid iUid; // Symbian data-type (UID3) + HBufC8* iStringValues[EDirEntAttrStringCount]; // string values + }; + + +#endif // CRSFWDIRENTATTR_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwdormantmountloader.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwdormantmountloader.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,101 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: class for restoring dormant mounts asynchronously when server starts +* +*/ + + +#ifndef C_RSFWDORMANTMOUNTLOADER_H +#define C_RSFWDORMANTMOUNTLOADER_H + +// INCLUDES +#include +#include "rsfwvolumetable.h" + + +// how many microseconds after server startup +// we start to restore the dormant mounts. +#define KDormantLoaderDelay 1000000 // 1s + +// CLASS DECLARATION + +/** +* Crsfwdormantmountloader class +* +* This class is for doing stuff asynchronously when loading dormant +* mounts at server startup. When server is started, dormant mounts +* are loaded. However, if there is something that takes more time +* it can be done synchronously while client is waiting for server to start. +* +* Currently only such operation is saving "dirty" files to the local cache +*/ +class CRsfwDormantMountLoader : public CActive + { + public: // Constructors and destructor + + /** + * Symbian OS two-phased constructor + * @return Pointer to this component. + */ + IMPORT_C static CRsfwDormantMountLoader* NewL(CRsfwVolumeTable *aTheTable); + + /** + * C++ default destructor. + */ + virtual ~CRsfwDormantMountLoader(); + + private: + + /** + * C++ default constructor. + */ + CRsfwDormantMountLoader(); + + /** + * Symbian OS default constructor. + */ + void ConstructL(CRsfwVolumeTable *aTheTable); + + + private: // New functions + + void ResolveDirtyFilesL(); + + +private: // Functions from base classes + + /** + * Handles an active object’s request completion event. + */ + void RunL(); + + /** + *Implements cancellation of an outstanding request. + */ + void DoCancel(); + + /** + * Called in case RunL() leaves + */ + TInt RunError(TInt aError); + +private: // Data + RTimer iTimer; + CRsfwVolumeTable* iVolumeTable; + + }; + +#endif // REMOTEWAITNOTEMANAGER_H + +// End of File \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfetchandcachestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfetchandcachestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,72 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for fetching and caching files and directories +* +*/ + + +#ifndef C_RSFW_FETCHANDCACHESTATEMACHINE_H +#define C_RSFW_FETCHANDCACHESTATEMACHINE_H + +#include "rsfwwaitnotestatemachine.h" + +/** + * State machine for fetching and caching files and directories + * + */ +class CRsfwFetchAndCacheStateMachine : public CRsfwWaitNoteStateMachine + { +public: + CRsfwFetchAndCacheStateMachine(); + TState* ErrorOnStateExit(TInt aError); + +public: + // STATES + // Before DoFetch we call UpdateAttributesL, + // where it is decided whether cached data is used... + // so this operation has only one state that fetches the data - + // possibly from the server or then from the local cache + class TFetchDataState : public CRsfwFetchAndCacheStateMachine::TState + { + public: + TFetchDataState(CRsfwFetchAndCacheStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwFetchAndCacheStateMachine* iOperation; + }; + +public: + TState* CompleteRequestL(TInt aError); + +public: + // input params + // the first byte requested + // = the current cached size + TInt iFirstByte; + + // output params: + // last byte of the container file after fetch + TInt iLastByte; + + // directory entries, when used to fetch directory contents... + RPointerArray iDirEnts; + + // length of the data fetched + TInt iLength; + + }; + +#endif // C_RSFW_FETCHANDCACHESTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfetchdatastatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfetchdatastatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,58 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for fetching data without caching it permanently +* +*/ + +#ifndef C_RSFW_FETCHDATASTATEMACHINE_H +#define C_RSFW_FETCHDATASTATEMACHINE_H + +#include "rsfwwaitnotestatemachine.h" + +/** + * State machine for fetching data without caching it permanently. + * + * Fetches data to a temporary cache file, i.e. the data + * does not become part of the permanent cache. + * + */ +class CRsfwFetchDataStateMachine : public CRsfwWaitNoteStateMachine + { +public: + CRsfwFetchDataStateMachine(); + +public: + // STATES + class TFetchDataState : public CRsfwFetchDataStateMachine::TState + { + public: + TFetchDataState(CRsfwFetchDataStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwFetchDataStateMachine* iOperation; + }; +public: + TState* CompleteRequestL(TInt aError); + +public: + // directory entries, when used to fetch directory contents... + RPointerArray iDirEnts; + // output params + TDesC* iCacheName; + TInt iLength; + }; + +#endif // C_RSFW_FETCHDATASTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfile.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfile.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,35 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: New file attributes defined in the subsystem + * +*/ + + +#ifndef RSFW_FILE_H +#define RSFW_FILE_H + +// CONSTANTS +// Other file attributes are defined in \epoc32\include\f32file.h and +// f32\inc\common.h +// KEntryAttCachePriorityHigh is reserved for possible "briefcase" use cases +const TUint KEntryAttCachePriorityHigh=0x10000; // bit 16 + + +// A file attribute that marks the file as having been modified. +// from common.h +const TUint KEntryAttModified=0x20000000; + +#endif // RSFW_FILE_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfileengine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfileengine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,160 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Operation independent remote file handling functions +* +*/ + +#ifndef C_RSFWFILEENGINE_H +#define C_RSFWFILEENGINE_H + +#include "rsfwinterface.h" +#include "rsfwremoteaccess.h" + +class CRsfwLockManager; +class TDirEnt; +class CRsfwFileTable; +class CRsfwRfeStateMachine; +class CRsfwVolume; +class CRsfwFileEntry; + +// Default values for various operation parameters +const TInt KDefaultMaxCacheSize = (16 * 1024 * 1024); // 16 MB +const TInt KDefaultMaxEntryCount = 1024; +const TInt KDefaultCacheValidity = 30; // in seconds +const TInt KDefaultDirCacheValidity = 30; +const TInt KDefaultRecognizerLimit = 256; +const TInt KDefaultJpegLimit = 0; +const TInt KDefaultMpegLimit = 10000; + + +class CRsfwFileEngine: public CBase, public MRsfwRemoteAccessObserver + { +public: + static CRsfwFileEngine* NewL(CRsfwVolume* aVolume); + static CRsfwFileEngine* NewLC(CRsfwVolume* aVolume); + ~CRsfwFileEngine(); + + void DispatchL(TRfeInArgs& aIn, TRfeOutArgs& aOut); + HBufC* FullNameLC(CRsfwFileEntry& aFe); + HBufC* FullNameL(CRsfwFileEntry& aFe); + void SetupAttributes(CRsfwFileEntry& aFe); + void MakeDirectoryEntry(CRsfwFileEntry& aFe, TDirEnt& aDirEnt); + void UpdateDirectoryContainerL(CRsfwFileEntry& aFe); + TBool DataChanged(const CRsfwDirEntAttr& oldAttr, const CRsfwDirEntAttr& newAttr); + TBool UseCachedData(CRsfwFileEntry& aFe); + TBool UseCachedAttributes(CRsfwFileEntry& aFe); + void GetAttributesL(CRsfwFileEntry& aFe, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + CRsfwRfeStateMachine* aCaller = NULL); + void UpdateAttributesL(TDesC& aPath, + TDesC& aName, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + MRsfwRemoteAccessResponseHandler* aCaller = NULL); + void UpdateAttributesL(CRsfwFileEntry& aFe, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + MRsfwRemoteAccessResponseHandler* aCaller = NULL); + void UpdateAttributesL(TDesC& aFullPath, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + MRsfwRemoteAccessResponseHandler* aCaller = NULL); + void CreateContainerFileL(CRsfwFileEntry& aFe); + TUint FetchAndCacheL(CRsfwFileEntry& aFe, + TInt aFirstByte, + TInt* aLength, + RPointerArray* aDirEntsp, + CRsfwRfeStateMachine* aCaller = NULL); + TUint RequestConnectionStateL(TUint aConnectionState, + CRsfwRfeStateMachine* aCaller = NULL); + void EnteredConnectionStateL(TUint aConnectionState, TBool aRequested); + TUint ConnectionState(); + CRsfwLockManager* LockManager(); + void SetPermanenceL(TBool aPermanence); + TBool Disconnected(); + TBool WriteDisconnected(); + TInt AddToCacheL(CRsfwFileEntry& aFe, + RPointerArray* aDirEnts, + CRsfwFileEngine *aFileEngine, + TUint cachedSize); + CRsfwRemoteAccess* RemoteAccessL(); + void OperationCompleted(); + void CancelTransactionL(TDesC& aPathName); + void CancelTransaction(TUint aTransactionId); + void SetFailedLookup(TDesC& aPath, TDesC& aKidName); + void ResetFailedLookup(); + CRsfwVolume* Volume(); + TInt PurgeFromCache(const TDesC& aPath); + HBufC8* GetContentType(TDesC& aName); + CRsfwFileEntry* FetchFep(const TDesC& aPath); + +private: + void ConstructL(CRsfwVolume* aVolume); + void PrepareCacheL(); + TInt UpdateDirectoryL(CRsfwFileEntry& aFe, TDesC* aFullName); + TInt UpdateDirectoryL(CRsfwFileEntry& aFe); + TUint GetDirectoryL(CRsfwFileEntry& aFe, + TDesC& aFullName, + RFile& aF, + RPointerArray* aDirEntsp, + MRsfwRemoteAccessResponseHandler* aCaller = NULL); + void BuildContainerPathL(CRsfwFileEntry& aFe, TDes& aPath); + void ApplyMultiDirCacheL(TDes& aPath); + void CreateContainerFileL(CRsfwFileEntry& aFe, TDes& aPath, RFile& aF); + void DoCreateL(TRfeCreateInArgs& aIn, TRfeCreateOutArgs& aOut); + void DoIoctlL(TRfeIoctlInArgs& aIn,TRfeOutArgs& aOut); + void DoRootL(TRfeRootInArgs& aIn, TRfeRootOutArgs& aOut); + void DoSetAttrL(TRfeSetAttrInArgs& aIn, TRfeOutArgs& aOut); + void SetupRootL(TBool aPermanence); + void CleanupCorruptedCacheL(); + TUint ConnectL(TBool aRestart, CRsfwRfeStateMachine* aCaller = NULL); + void DisconnectL(); + void StartInactivityTimer(); + void StopInactivityTimer(); + static TInt InactivityTimerExpired(TAny* aArg); + + + // the purpose of these functions is to give capability info + // for the access protocol plugin used + + // whether getting the directory listing also gives reliable file metadata + TBool DirectoryListingContainsFileMetadata(); + + // from MRsfwRemoteAccessObserver + void HandleRemoteAccessEventL(TInt aEventType, TInt aEvent, TAny* aArg); + +public: + CRsfwFileTable* iFileTable; // table of known vnodes, by fid + TUint iConnectionState; // connection state + CRsfwRemoteAccess* iRemoteAccess; // remote file transport module + CRsfwLockManager* iLockManager; // implement locking for files + +private: + + // Data + CRsfwFileEntry* iRootFep; // root file entry + CRsfwVolume* iVolume; // volume info + const TFid* iRootFid; // root file id + TFileName iCacheRoot; // location of local cache files + RFs iFs; // fileserver handle + TInt iInactivityTimeout; // inactivity timeout + CPeriodic* iInactivityTimer; // remote access inactivity watch dog + TBool iConnectionStateChanged; + TFileName iLastFailedLookup; // path of the last failed lookup, cached + TTime iLookupTime; // then this failed lookup happened + }; + + +#endif diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfileentry.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfileentry.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,181 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: data struct for a remote file metadata +* +*/ + + +#ifndef C_RSFWFILEENTRY_H +#define C_RSFWFILEENTRY_H + +#include "rsfwinterface.h" +#include "rsfwlrulistnode.h" + +class TDirEntAttr; +class CRsfwLockManager; +class CRsfwDirEntAttr; +class CRsfwFileTable; + + +class CRsfwFileEntry: public CBase + { + friend class CRsfwFileTable; + friend class CRsfwVolumeTable; + friend class CRsfwLockManager; + +public: + ~CRsfwFileEntry(); + static CRsfwFileEntry* NewLC(const TDesC& aName, CRsfwFileEntry* aParent); + static CRsfwFileEntry* NewL(const TDesC& aName, CRsfwFileEntry* aParent); + static CRsfwFileEntry* NewL(RReadStream& aStream); + + CRsfwFileEntry* FindKidByName(const TDesC& aName); + void RenameL(const TDesC& aName); + void AddKid(CRsfwFileEntry& aFe); + TInt RemoveKidL(CRsfwFileEntry* aFep); + TInt KidsCount(); + void UnmarkKids(); + void DropUnmarkedKidsL(); + void DropLD(); + void GetAttributes(TDirEntAttr& aAttr) const; + void GetAttributesL(CRsfwDirEntAttr& aAttr) const; + void SetAttributesL(CRsfwDirEntAttr& aAttr, TBool aAllMetaData); + TDesC* CacheFileName(); + void SetCacheFileName(TDesC* aFn); + TBool IsCached() const; + TBool IsFullyCached() const; + void SetCached(TBool aCached); + void SetCachedSize(TInt aFetchedSize); + void RemoveCacheFile(); + void ValidateCacheFile(); + void PrintL(TInt aLevel, TBool aKids, TBool aall) const; + HBufC* FullNameLC() const; + TInt TotalCachedSize(); + TInt TotalEntryCount(); + CRsfwFileEntry* Lookup(const TFid& aFid); + void SetLockedL(CRsfwLockManager* aLockManager, TDesC8* aLockToken); + void RemoveLocked(); + static int LockTimerExpiredL(TAny* aParam); + TBool UseCachedData(); + void SetAttribValidationTime(); + void ExternalizeL(RWriteStream& aStream) const; + void InternalizeL(RReadStream& aStream); + void SetType(TUint8 aType); + void SetSize(TInt aSize); + void SetModified(const TTime& aModified); + void SetAtt(TUint aAtt); + void SetMimeTypeL(const TDesC8& aMimeType); + void SetOpaqueFileIdL(const TDesC8& aOpaqueFileId); + TBool IsLocallyDirty() const; + TBool IsCancelled() const; + void SetLocallyDirty(); + void ResetLocallyDirty(); + TBool RemotelyDirty() const; + void SetRemotelyDirty(); + void ResetRemotelyDirty(); + void SetNewlyCreated(); + void ResetNewlyCreated(); + TBool IsNewlyCreated() const; + TBool IsMarked() const; + void Mark(); + void Unmark(); + void SetFlags(TUint aFlags); + void ResetFlags(TUint aFlags); + void SetOpenedForWriting(TBool aOpenedForWriting); + TBool IsOpenedForWriting() const; + // for a remote file which has been locally modified, but not yet written back to the + // server the cache file is set as read only until the file has been resolved + TBool IsLocked() const; + void ReportEvent(TInt aEvent); + inline const TFid& Fid() const; + inline void SetFid(const TFid& aFid); + inline const TDesC* Name() const; + inline TUint8 Type() const; + inline TInt Size() const; + inline TTime Modified() const; + inline TUint Att() const; + inline const TDesC8* MimeType() const; + inline const TDesC8* OpaqueFileId() const; + inline void SetUid(TUid anUid); + inline CRsfwFileEntry* Parent(); + inline void SetParent(CRsfwFileEntry* aFep); + inline TInt CachePriority() const; + inline TBool IsFlagged(TUint aFlag) const; + inline RPointerArray* Kids(); + inline const TDesC8* LockToken(); + inline const TDesC* ProtectionDomainName() const; + inline void SetCachePriority(TCachePriority); + inline TInt ProtectionDomainId() const; + void ResolveDirtyFilesL(); + +private: + void ConstructL(const TDesC& aName, CRsfwFileEntry* aParent); + void ConstructL(RReadStream& aStream); + + void SetLockTimeout(); + +public: + + // how much has been cached + TInt iCachedSize; + + // when the file attributes have been fetched from the server + TTime iAttribValidation; + + // uid of the symbian app which handles this datatype + TUid iUid; + + // Timer associated with a possible file locked + CPeriodic* iLockTimer; + + +protected: + RPointerArray iKids; // contained files and dirs + +private: + TFid iFid; // id + HBufC* iName; // name + TInt iSize; // file size in bytes + TUint iAtt; // attribute bits + TUint iFlags; // local state + TTime iModified; // last modified + TUint8 iType; // type (unknown, file, dir) + HBufC8* iMimeType; // MIME type + HBufC8* iOpaqueFileId; // e.g. ETag in WebDAV + CRsfwFileEntry* iParent; // parent dir + TBuf iCacheName; // local cache filename + TDesC8* iLockToken; // lock token + // cache priority is currently always KCachePriorityNormal + TInt iCachePriority; + + // Lock timeout for this locked file + // In practise we need to store this per-file + // as server may always ignore our request + // and e.g. mod_dav allows setting different min timeout + // for different directories. + TUint iLockTimeout; + +public: + // pointer to lock manager that can be called to refresh the lock + CRsfwLockManager* iLockManager; + TBool iUseCachedData; + // only used at recovery when iParent is not set (yet) + TInt iParentNodeId; + // the table in which the entry belongs + CRsfwFileTable* iFileTable; + }; + +#include "rsfwfileentry.inl" + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfileentry.inl --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfileentry.inl Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,165 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: inlines for file entry data structure +* +*/ + + + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Fid +// ---------------------------------------------------------------------------- +// +inline const TFid& CRsfwFileEntry::Fid() const + { + return iFid; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetFid +// ---------------------------------------------------------------------------- +// +inline void CRsfwFileEntry::SetFid(const TFid& aFid) + { + iFid = aFid; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Name +// ---------------------------------------------------------------------------- +// +inline const TDesC* CRsfwFileEntry::Name() const + { + return iName; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Type +// ---------------------------------------------------------------------------- +// +inline TUint8 CRsfwFileEntry::Type() const + { + return iType; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Size +// ---------------------------------------------------------------------------- +// +inline TInt CRsfwFileEntry::Size() const + { + return iSize; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Modified +// ---------------------------------------------------------------------------- +// +inline TTime CRsfwFileEntry::Modified() const + { + return iModified; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Att +// ---------------------------------------------------------------------------- +// +inline TUint CRsfwFileEntry::Att() const + { + return iAtt; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::MimeType +// ---------------------------------------------------------------------------- +// +inline const TDesC8* CRsfwFileEntry::MimeType() const + { + return iMimeType; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::OpaqueFileId +// ---------------------------------------------------------------------------- +// +inline const TDesC8* CRsfwFileEntry::OpaqueFileId() const + { + return iOpaqueFileId; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetUid +// ---------------------------------------------------------------------------- +// +inline void CRsfwFileEntry::SetUid(TUid anUid) + { + iUid = anUid; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Parent +// ---------------------------------------------------------------------------- +// +inline CRsfwFileEntry* CRsfwFileEntry::Parent() + { + return iParent; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetParent +// ---------------------------------------------------------------------------- +// +inline void CRsfwFileEntry::SetParent(CRsfwFileEntry* aParent) + { + // This meta data event is handle in kid Add/Remove functions + iParent = aParent; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::CachePriority +// ---------------------------------------------------------------------------- +// +inline TInt CRsfwFileEntry::CachePriority() const + { + return iCachePriority; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsFlagged +// ---------------------------------------------------------------------------- +// +inline TBool CRsfwFileEntry::IsFlagged(TUint aFlag) const + { + return (iFlags & aFlag) != 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Kids +// ---------------------------------------------------------------------------- +// +inline RPointerArray* CRsfwFileEntry::Kids() + { + return &iKids; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::LockToken +// ---------------------------------------------------------------------------- +// +inline const TDesC8* CRsfwFileEntry::LockToken() + { + return iLockToken; + } + + \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfiletable.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfiletable.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,158 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: data struct for remote files metadata +* +*/ + + +#ifndef C_RSFWFILETABLE_H +#define C_RSFWFILETABLE_H + +#include +#include +#include "rsfwmetadatastore.h" + +class CRsfwVolume; +class CRsfwFileEntry; +class TFid; +class TMetaDataEvent; + +/** file where permanent metadata is stored */ +_LIT(KMetaDataFileName, "M.dat"); + +/** an entry has been added */ +const TInt KNotifyNodeAdded = 1; + +/** an entry has been modified */ +const TInt KNotifyNodeModified = 2; + +/** an entry has been deleted */ +const TInt KNotifyNodeRemoved = 3; + +/** size of the buffer used when writing file entry to permanent metadata */ +const TInt KMaxExternalizedFileEntrySize = 1024; + +/** internal state bits */ + +/** local changes (eg caching bits) */ +const TUint KNodeLocallyDirty = 0x0001; +/** remote changes */ +const TUint KNodeRemotelyDirty = 0x0002; +/** temp mark for various purposes */ +const TUint KNodeMarked = 0x0004; + +const TUint KNodeHasValidLock = 0x0008; +const TUint KNodeOpenedForWriting = 0x0010; + +const TUint KNodeWritingCancelled = 0x0020; + +const TUint KNodePartlyCached = 0x0100; + +/** indicates that a file that has been +opened has been created (instead of opening +an already existing file). This affects +logic when closing the file (PUT + RENAME +trick to protect the existing file in case of +cancelled PUT is not used) + **/ +const TUint KNodeNewlyCreated = 0x0200; + + +class TMetaDataEvent + { +public: + TInt iEvent; // notified event + TInt iNodeId; // node id + CRsfwFileEntry* iEntry; // file entry + }; + + +class CRsfwFileTable: public CBase + { +private: + enum TMetaDataState + { + EMetaDataSaveNone = 0, // meta data saving has not started yet + EMetaDataSaveStarted, // meta data saving has been started + EMetaDataSaveFailed // meta data saving has failed + }; + + class TMetaDataSlot + { + public: + TInt iNodeId; // node id + TInt iSlotId; // slot index + }; + +public: + static CRsfwFileTable* NewL(CRsfwVolume* aVolume, TFileName& aCachePath); + + inline CRsfwVolume* Volume(); + inline CRsfwFileEntry* Root(); + + ~CRsfwFileTable(); + + // add node to three + void AddL(CRsfwFileEntry* aFep); + + // remove node from thee + void RemoveL(CRsfwFileEntry* aFep); + + // lookup three + CRsfwFileEntry *Lookup(const TFid& aFid); + void DumpL(TBool aAll); + inline const TBool Permanence() const; + void SetPermanenceL(TBool aPermanence); + void HandleMetaDataEvent(TInt aEvent, CRsfwFileEntry* aFep); + CRsfwFileEntry* LoadMetaDataL(); + TInt SaveMetaDataDelta(); + void SetupCacheL(); + TInt TotalCachedSize(); + TInt TotalEntryCount(); + inline TInt OpenFileCount(); + inline void UpdateOpenFileCount(TInt aDelta); + void ResolveDirtyFilesL(); + void ResolveDirtyFileL(CRsfwFileEntry* aFep); + + +private: + void ConstructL(CRsfwVolume* aVolume, TFileName& aCachePath); + void ClearCacheL(); + void ConstructL(RReadStream& aStream); + TMetaDataEvent* NodeEvent(TInt aNodeId); + void AddEvent(TInt aEvent, CRsfwFileEntry* aFep); + void RemoveEvent(TInt aNodeId); + void LoadNodeL(CRsfwFileEntry*& aFep, TInt &aSlot); + void SaveNodeL(CRsfwFileEntry* aFep, TInt &aSlot); + void SaveMetaDataDeltaL(); + +private: + RFs iFs; // inherited from RFE environment + TInt iNodeId; // next node id to assign + CRsfwVolume* iVolume; // volume info + CRsfwFileEntry* iRootFep; // root file entry + TFileName iCachePath; // cache directory path + TBool iPermanence; // permanent meta data + RArray iMetaDataEvents; // dirty entries since last flush + CRsfwMetaDataStore* iMetaDataStore; // permanent store for metadata + RArray iMetaDataSlots; // maps file slot to node ids + TFileName iMetaDataFilePath; // meta data file path + TInt iMetaDataSaveState; // the state of meta data saving + CRsfwFileEntry* iCurrentParent; // parent of last looked up entry + TInt iOpenFileCount; // count of open files + }; + +#include "rsfwfiletable.inl" + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwfiletable.inl --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwfiletable.inl Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,66 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: inlines for file table data structure +* +*/ + + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::Volume +// ---------------------------------------------------------------------------- +// +inline CRsfwVolume* CRsfwFileTable::Volume() + { + return iVolume; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::Root +// ---------------------------------------------------------------------------- +// +inline CRsfwFileEntry* CRsfwFileTable::Root() + { + return iRootFep; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::Permanence +// ---------------------------------------------------------------------------- +// +inline const TBool CRsfwFileTable::Permanence() const + { + return iPermanence; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::OpenFileCount +// ---------------------------------------------------------------------------- +// +inline TInt CRsfwFileTable::OpenFileCount() + { + return iOpenFileCount; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::UpdateOpenFileCount +// ---------------------------------------------------------------------------- +// +inline void CRsfwFileTable::UpdateOpenFileCount(TInt aDelta) + { + iOpenFileCount += aDelta; + if (iOpenFileCount < 0) + { + iOpenFileCount = 0; + } + } \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwflushstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwflushstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,56 @@ +/* +* Copyright (c) 2007 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for flushing file contexts +* +*/ + + +#ifndef C_RSFW_FLUSHSTATEMACHINE_H +#define C_RSFW_FLUSHSTATEMACHINE_H + +#include "rsfwwaitnotestatemachine.h" +#include "rsfwsavetodlgrequest.h" + +/** + * State machine for flushing a file + * + */ + +class CRsfwFlushStateMachine : public CRsfwWaitNoteStateMachine + { +public: + CRsfwFlushStateMachine(); + +public: + // STATES + class TFlushDataToServerState : public CRsfwFlushStateMachine::TState + { + public: + TFlushDataToServerState(CRsfwFlushStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwFlushStateMachine* iOperation; + }; + +public: + TState* CompleteL(TInt aError); + TState* CompleteRequestL(TInt aError); + + }; + + + +#endif // C_RSFW_FLUSHSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwgetattributesstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwgetattributesstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,52 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for getting attributes of a file +* +*/ + +#ifndef C_RSFW_GETATTRIBUTESSTATEMACHINE_H +#define C_RSFW_GETATTRIBUTESSTATEMACHINE_H + + +#include "rsfwgetattributesstatemachine.h" +#include "rsfwattributerefreshingstatemachine.h" + +class CRsfwGetAttributesStateMachine : public CRsfwAttributeRefreshingStateMachine + { +public: + CRsfwGetAttributesStateMachine(); + +public: + // STATES + // get remote attributes + class TRefreshAttributesState : + public CRsfwGetAttributesStateMachine::TState + { + public: + TRefreshAttributesState(CRsfwAttributeRefreshingStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + TState* CompleteOurRequestL(TInt aErr); + private: + // iOperation = CRsfwGetAttributesStateMachine or COpenByPath + CRsfwAttributeRefreshingStateMachine* iOperation; + }; + +public: + TState* CompleteRequestL(TInt aError); + }; + +#endif // C_RSFW_GETATTRIBUTESSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwinterface.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwinterface.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,367 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: The definitions of file operation codes and their parameters + * +*/ + + +#ifndef RSFWINTERFACE_H +#define RSFWINTERFACE_H + +// INCLUDES +#include +#include + +#include "rsfwcommon.h" +#include "rsfwfile.h" + +// CONSTANTS +_LIT(KRSFWDefaultDrive, "C:"); +_LIT(KCacheRootDefault, "\\system\\data\\rsfw_cache\\"); +_LIT(KTempFileName, "temp"); +_LIT(KRsfwConfigPath, "\\data\\rscfw.cfg"); +_LIT(KResolutionLogPath, "\\logs\\rsfw\\rsfw.log"); +_LIT(KConfigNameCacheRoot, "cache_root"); +_LIT(KDirReadAllMask, "*"); +_LIT(KRemoteFs, "eremotefs"); +_LIT(KRemoteFSName, "RemoteFS"); +_LIT(KPanicSource, "RemoteFS"); +_LIT(KRemoteVolumeName, "RemoteFS"); +_LIT(KRemoteFEName, "RemoteFE"); +_LIT(KCachePanicSource, "cache manager"); +_LIT(KRfeInputData, "RemoteFeInputArgsChunk"); +_LIT(KRfeOutputData, "RemoteFeOutputArgsChunk"); +_LIT(KRfeDataSemaphoreName, "RemoteFeDataSemaphore"); +_LIT(KRfeMain, "RemoteFeMain"); +_LIT(KRsfwMounterExe, "rsfwbootmounter"); + +const TInt KMaxMimeTypeLength = 64; +// Node Types +const TUint KNodeTypeUnknown = 0x00; +const TUint KNodeTypeFile = 0x01; +const TUint KNodeTypeDir = 0x02; + + +// DATA TYPES +// Remote File System plug-in <--> Remote File Engine communications +enum TRfeIoctl + { + ERemoteFsIoctlRefresh = 1, + ERemoteFsProtect, + ERemoteFsHighCachePriority + }; + +enum TRfeClose + { + ECloseNotModified, + ECloseModified, + ECloseLastFlushFailed + }; + +// CLASS DECLARATIONS + +/** + * Node identifier in the framework + * + * @lib Rsfwsession.dll + * @since Series 60 3.1 + */ +class TFid + { +public: // New functions + inline TBool operator==( const TFid& aFid ) const; +public: // Data + // Identifiers the volume. Each mount is an own volume. + TInt iVolumeId; + // Identifies the node (i.e. file or directory) inside the volume. + TInt iNodeId; + }; + +/** + * Directory attributes for a file or directory. + * + * @lib rsfwsession.dll + * @since Series 60 3.1 + */ +class TDirEntAttr + { +public: // New functions + IMPORT_C void ExternalizeL( RWriteStream& aStream ) const; + IMPORT_C void InternalizeL( RReadStream& aStream ); + IMPORT_C void Clear(); + +public: // Data + // attribute bits + TUint iAtt; + // file size in bytes + TInt iSize; + // last modified + TTime iModified; + // Symbian data-type (UID) + TUid iUid3; + }; + +/** + * Encapsulates a file or directory entry. + * + * @lib rsfwsession.dll + * @since Series 60 3.1 + */ +class TDirEnt + { +public: // New functions + IMPORT_C void ExternalizeL( RWriteStream& aStream ) const; + IMPORT_C void InternalizeL( RReadStream& aStream ); + IMPORT_C void Clear(); + +public: // Data + // attributes + TDirEntAttr iAttr; + // filename + TFileName iName; + }; + +/** + * Remote File Engine input parameters header + * + * @lib rsfwsession.dll + * @since Series 60 3.1 + */ +class TRfeInArgs + { +public: + // operation code, used to cast this instance into the right impl. class + TInt iOpCode; + // The fid of the target file (not used in root operation). + TFid iFid; + }; + +/** + * Remote File Engine output parameters header + * + * @lib rsfwsession.dll + * @since Series 60 3.1 + */ +class TRfeOutArgs + { +public: // Data + TUint iUnique; // The request ID + }; + +/** + * Remote File Engine operation input and output parameter structures + * + * @lib rsfwsession.dll + * @since Series 60 3.1 + */ +// Close +class TRfeCloseInArgs : public TRfeInArgs + { +public: + TInt iFlags; + }; + +// Create +class TRfeCreateInArgs : public TRfeInArgs + { +public: + TDirEnt iEntry; + TInt iExcl; + }; + +class TRfeCreateOutArgs : public TRfeOutArgs + { +public: + TFid iFid; + TDirEntAttr iAttr; + }; + +// Fetch and cache +class TRfeFetchInArgs : public TRfeInArgs + { +public: + TInt iFirstByte; + TInt iLastByte; + }; + +class TRfeFetchOutArgs : public TRfeOutArgs + { +public: + // last byte that was actually fetched, might be more than was requested + TInt iLastByte; + }; + +// Fetch without caching +class TRfeFetchDataInArgs : public TRfeInArgs + { +public: + TInt iFirstByte; + TInt iLastByte; + }; + +class TRfeFetchDataOutArgs : public TRfeOutArgs + { +public: + TFileName iTempPath; + TBool iUseTempPath; + }; + +// flush +class TRfeFlushInArgs : public TRfeInArgs + { +public: + TInt iFirstByte; + TInt iDataLength; + TInt iTotalSize; + }; + + +// Fsync +class TRfeFsyncInArgs : public TRfeInArgs + { +public: + }; + +// GetAttr +class TRfeGetAttrInArgs : public TRfeInArgs + { +public: + }; + +class TRfeGetAttrOutArgs : public TRfeOutArgs + { +public: + TDirEntAttr iAttr; + }; + +// Ioctl +class TRfeIoctlInArgs : public TRfeInArgs + { +public: + TInt iCmd; + TInt iLen; + union + { + TUint8 iData8[1]; + TUint32 iData32[1]; + }; + }; + +// Lookup +class TRfeLookupInArgs : public TRfeInArgs + { +public: + TFileName iName; + TUint iNodeType; + }; + +class TRfeLookupOutArgs : public TRfeOutArgs + { +public: + TFid iFid; + }; + +// Mkdir +class TRfeMkdirInArgs : public TRfeInArgs + { +public: + TDirEnt iEntry; + }; + +class TRfeMkdirOutArgs : public TRfeOutArgs + { +public: + TFid iFid; + TDirEntAttr iAttr; + }; + +// OpenByPath +class TRfeOpenByPathInArgs : public TRfeInArgs + { +public: + TUint iFlags; + TBool iTrueOpen; + }; + + +class TRfeOpenByPathOutArgs : public TRfeOutArgs + { +public: + TFileName iPath; + TDirEntAttr iAttr; + }; + +// Remove +class TRfeRemoveInArgs : public TRfeInArgs + { +public: + TFileName iName; + }; + +// Rename +class TRfeRenameInArgs : public TRfeInArgs + { +public: + TFileName iSrcName; + TFid iDstFid; + TFileName iDstName; + TBool iOverWrite; + }; + +// Rmdir +class TRfeRmdirInArgs : public TRfeInArgs + { +public: + TFileName iName; + }; + +// Root operation returns the fid of the volume root +class TRfeRootInArgs : public TRfeInArgs + { + }; + +class TRfeRootOutArgs : public TRfeOutArgs + { +public: + TFid iFid; + }; + +// SetAttr +class TRfeSetAttrInArgs : public TRfeInArgs + { +public: + TDirEntAttr iMask; + TDirEntAttr iAttr; + }; + +// Requests whether it is ok to write n bytes to the local cache +class TRfeWriteDataInArgs : public TRfeInArgs + { +public: + // Number of bytes to be written. + TUint iBytes; + }; + +class TRfeWriteDataOutArgs : public TRfeOutArgs + { +public: + // Permission to write. + TBool iOkToWrite; + }; + +#include "rsfwinterface.inl" + +#endif // RSFWINTERFACE_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwinterface.inl --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwinterface.inl Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,25 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: inlines for rsfw interface + * +*/ + + + +inline TBool TFid::operator==(const TFid& aFid) const + { + return ((iNodeId == aFid.iNodeId) && (iVolumeId == aFid.iVolumeId)); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwlockmanager.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwlockmanager.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,91 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Lock manager for locked remote files +* +*/ + + +#ifndef C_RSFWLOCKMANAGER_H +#define C_RSFWLOCKMANAGER_H + +#include + +#include "rsfwrfesession.h" +#include "rsfwremoteaccess.h" + +class CRsfwFileEntry; +class CRsfwRfeStateMachine; + +/** lock timeout in seconds */ +const TInt KDefaultLockTimeout = 900; + +/** KDefaultLockTimeout is the lock timeout requested from the server + Our lock timer is set to value KDefaultLockTimeout / KLockRefreshAdjustment. + It must be smaller, as it is started only when we receive the reply + from the server, and when it expires we still must have time to sent the + refresh request */ +const TInt KLockRefreshAdjustment = 3; + +/** If lock refresh attempt results in an error from the protocol stack + we use timeout mechanism to try again, but with a small timeout + as we are not even sending packets to the server. */ +const TInt KMinLockRefreshAttempt = 5; + +/** + * Pending lock renewal requests + * + * @lib remotefe.exe + * @since Series 60 3.1 + */ +class TPendingLockRefreshContext + { +public: + // Lock refresh request transaction Id + TUint iId; + // Pointer to the file entry waiting for this refresh + CRsfwFileEntry* iFileEntry; + }; + +class CRsfwLockManager: public CBase, public MRsfwRemoteAccessResponseHandler + { +public: + static CRsfwLockManager* NewL(CRsfwRemoteAccess* aRemoteAccess); + static CRsfwLockManager* NewLC(CRsfwRemoteAccess* aRemoteAccess); + ~CRsfwLockManager(); + + void HandleRemoteAccessResponse(TUint aId, TInt aStatus); + void ObtainLockL(CRsfwFileEntry* + aFileEntry, + TUint aLockFlags, + TDesC8*& aLockToken, + CRsfwRfeStateMachine* aOperation); + void ReleaseLockL(CRsfwFileEntry* aFileEntry, CRsfwRfeStateMachine* aOperation); + void RefreshLockL(CRsfwFileEntry* aFileEntry); + TInt LockedCount(); + void AddLockedEntryL(CRsfwFileEntry* aEntry); + void RemoveLockedEntry(CRsfwFileEntry* aEntry); + void PopulateExternalLockTokenCacheL(CRsfwFileEntry* aRoot); + +private: + void ConstructL(CRsfwRemoteAccess*) ; + +private: + CRsfwRemoteAccess* iRemoteAccess; // remote file transport module + RArray iLockRefreshContexts; + RPointerArray iLockedEntries; + }; + +#endif // LOCKMANAGER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwlookupstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwlookupstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,80 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for file lookup +* +*/ + + +#ifndef C_RSFW_LOOKUPSTATEMACHINE_H +#define C_RSFW_LOOKUPSTATEMACHINE_H + +#include "rsfwrfestatemachine.h" + +/** + * state machine for file lookup + * + * + */ +class CRsfwLookupStateMachine : public CRsfwRfeStateMachine + { +public: + CRsfwLookupStateMachine(); + ~CRsfwLookupStateMachine(); +public: + // STATES + // updating attributes + // if the file type is unknow we first try file then directory + class TUpdateKidAttributesTryFirstTypeState : public CRsfwLookupStateMachine::TState + { + public: + TUpdateKidAttributesTryFirstTypeState(CRsfwLookupStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwLookupStateMachine *iOperation; + }; + + class TUpdateKidAttributesTrySecondTypeState : public CRsfwLookupStateMachine::TState + { + public: + TUpdateKidAttributesTrySecondTypeState(CRsfwLookupStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwLookupStateMachine *iOperation; + }; + +public: + TState* CompleteL(); + TState* CompleteRequestL(TInt aError); + +public: + // input parameters + TUint iNodeType; // are we looking up file, directory or unknown... + + // output parameters: + CRsfwFileEntry *iKidFep; + + TPtrC iKidName; + TFid* iParentFidp; + + CRsfwDirEntAttr* iDirEntAttr; + TBool iKidCreated; + HBufC* iPath; + }; + + +#endif // C_RSFW_LOOKUPSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwlrulistnode.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwlrulistnode.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,48 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: A node in the LRU list +* +*/ + +#ifndef C_RSFWLRULISTNODE_H +#define C_RSFWLRULISTNODE_H + +#include + +class CRsfwFileEntry; + +/** Priority of the cached entry */ +enum TCachePriority + { + ECachePriorityNormal + }; + +class CRsfwLruListNode : public CBase + { +public: + static CRsfwLruListNode* NewLC(CRsfwFileEntry* aFe, TInt aPriority); + static CRsfwLruListNode* NewL(CRsfwFileEntry* aFe, TInt aPriority); + virtual ~CRsfwLruListNode(); +public: + static const TInt iOffset; +private: + void ConstructL(CRsfwFileEntry* aFe, TInt aPriority); + +private: + TPriQueLink iLink; + CRsfwFileEntry* iEntryPtr; + friend class CRsfwLruPriorityList; + }; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwlruprioritylist.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwlruprioritylist.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: LRU priority list for cache entries +* +*/ + +#ifndef C_RSFWLRUPRIORITYLIST_H +#define C_RSFWLRUPRIORITYLIST_H + +#include +#include + +class CRsfwLruListNode; +class CRsfwFileEntry; +class CRsfwVolumeTable; + +class CRsfwLruPriorityList : public CBase + { +public: + CRsfwLruPriorityList(); + virtual ~CRsfwLruPriorityList(); + + void AddNodeL(CRsfwFileEntry *aFe, TInt aPriority); + TInt RemoveNode(CRsfwFileEntry *aFe); + CRsfwFileEntry* GetAndRemoveFirstEntry(); + void ExternalizeL(RWriteStream& aStream); + void InternalizeL(RReadStream& aStream, CRsfwVolumeTable* aVolumeTable); + +private: + TPriQue iHdr; + TDblQueIter iIter; + }; + + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwmetadatastore.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwmetadatastore.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,42 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Keeps metadata persistent +* +*/ + + +#ifndef C_RSFWMETADATASTORE_H +#define C_RSFWMETADATASTORE_H + +// INCLUDES +#include "rsfwcontrol.h" +#include "rsfwpermanentstore.h" + +// CLASS DECLARATION +class CRsfwMetaDataStore: public CRsfwPermanentStore + { + +public: + static CRsfwMetaDataStore* NewL(const TDesC& aPath); + static CRsfwMetaDataStore* NewLC(const TDesC& aPath); + void GetMountConfigL(TRsfwMountConfig& aMountConfig); + void SetMountConfigL(const TRsfwMountConfig& aMountConfig); + +private: + void ConstructL(const TDesC& aPath); + }; + +#endif // METADATASTORE_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwmkdirstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwmkdirstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,69 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for creating directories +* +*/ + +#ifndef C_RSFW_MKDIRSTATEMACHINE_H +#define C_RSFW_MKDIRSTATEMACHINE_H + +#include "rsfwrfestatemachine.h" + +/** + * Creates a directory + * + * State machine for creating directories. + * + */ +class CRsfwMkDirStateMachine : public CRsfwRfeStateMachine + { +public: + CRsfwMkDirStateMachine(); + ~CRsfwMkDirStateMachine(); + +public: + // STATES + class TCheckIfExistsState : public CRsfwMkDirStateMachine::TState + { + public: + TCheckIfExistsState(CRsfwMkDirStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwMkDirStateMachine* iOperation; + }; + + class TMakeDirectoryState : public CRsfwMkDirStateMachine::TState + { + public: + TMakeDirectoryState(CRsfwMkDirStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwMkDirStateMachine* iOperation; + }; + +public: + TState* CompleteRequestL(TInt aError); + + CRsfwFileEntry* iKidFep; + TBool iKidCreated; + CRsfwDirEntAttr* iDirEntAttr; + }; + + + +#endif // C_RSFW_MKDIRSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwmountconnectionstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwmountconnectionstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,60 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for changing mount state, e.g. online->offline +* +*/ + +#ifndef C_RSFW_MOUNTCONNECTIONSTATEMACHINE_H +#define C_RSFW_MOUNTCONNECTIONSTATEMACHINE_H + +#include "rsfwwaitnotestatemachine.h" +#include "rsfwvolume.h" + +/** + * State machine for changing mount state, e.g. online->offline + * This state machine is currently only used for disconnecting + * For connecting CRsfWMountStateMachine is used + * Disconnecting does not currently send packets to network, + * but it is possible that this happens in the future. + * + */ +class CRsfwMountConnectionStateMachine : public CRsfwWaitNoteStateMachine + { +public: + CRsfwMountConnectionStateMachine(TChar aDriveLetter, TUint aState); + +public: + // STATES + class TChangeConnectionState : public CRsfwMountConnectionStateMachine::TState + { + public: + TChangeConnectionState(CRsfwMountConnectionStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + // backpointer to the operation + CRsfwMountConnectionStateMachine* iOperation; + // + CRsfwVolume *iVolume; + }; + +public: + // parameters of the operation + TChar iDriveLetter; + TUint iState; + + }; + +#endif // C_RSFW_MOUNTCONNECTIONSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwmountstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwmountstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,128 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for mounting +* +*/ + +#ifndef C_RSFW_MOUNTSTATEMACHINE_H +#define C_RSFW_MOUNTSTATEMACHINE_H + +#include // KMaxMountNameLength + +#include "rsfwwaitnotestatemachine.h" +#include "rsfwcontrol.h" +#include "rsfwauthenticationdlgrequest.h" + +class CRsfwVolume; +class CRsfwVolumeTable; + +/** + * State machine for mounting. + * + * This state machine assumes that connection awareness is off. + * In "connection awareness" error state for mounting is quite different, + * as failure to connect to the server is not considered to be fatal, + * but instead puts the engine to disconnected mode. + * Feasible strategy is probably to create an alternative initial state + * with a different ErrorL, set if connection awareness is on. + * + */ +class CRsfwMountStateMachine : public CRsfwWaitNoteStateMachine + { +public: + static CRsfwMountStateMachine* NewL(TRsfwMountConfig aMountConfig, + TInt aMountState, + CRsfwVolumeTable* aVolumeTable); +private: + void ConstructL(TRsfwMountConfig aMountConfig, + TInt aMountState, + CRsfwVolumeTable* aVolumeTable); +public: + // STATES + // requesting connection state e.g. sending OPTIONS to WebDAV server + class TRequestConnectionState : public CRsfwMountStateMachine::TState + { + public: + TRequestConnectionState(CRsfwMountStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + // backpointer to the operation + CRsfwMountStateMachine* iOperation; + }; + + // dismiss the wait note + class TDismissConnectionWaitNoteState : public CRsfwMountStateMachine::TState + { + public: + TDismissConnectionWaitNoteState(CRsfwMountStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + // backpointer to the operation + CRsfwMountStateMachine* iOperation; + }; + + // asynchronously waits for user to type in authentication infomation + class TGetAuthCredentials : public CRsfwMountStateMachine::TState + { + public: + TGetAuthCredentials(CRsfwMountStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + // backpointer to the operation + CRsfwMountStateMachine* iOperation; + TRsfwAuthenticationDlgRequest iAuthRequest; + + }; + + // asynchronously waits for "drive unavailabe, retry? query" + class TUnavailableRetry : public CRsfwMountStateMachine::TState + { + public: + TUnavailableRetry(CRsfwMountStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + // backpointer to the operation + CRsfwMountStateMachine* iOperation; + TRsfwNotPluginRequest iRetryRequest; + }; + + +public: + CRsfwRfeStateMachine::TState* CompleteRequestL(TInt aError); + TState* ErrorOnStateEntry(TInt aError); +public: + CRsfwVolume* iVolume; // volume to be mounter or recovered + + // parameters of the operation + // we read from mountconfig a drive letter to be mounted or recovered + // currently volumeId is always set by us + TRsfwMountConfig iMountConfig; + TInt iVolumeId; + TInt iMountState; +private: + TBuf iFriendlyName; + TBool iRequestingConnection; // flag indicating 'opening connection' event + TInt iConnectingError; // remember why the connection attempt failed + }; + + +#endif // C_RSFW_MOUNTSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwopenbypathstatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwopenbypathstatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,73 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for opening a file or directory +* +*/ + + +#ifndef C_RSFW_OPENBYPATHSTATEMACHINE_H +#define C_RSFW_OPENBYPATHSTATEMACHINE_H + +#include "rsfwattributerefreshingstatemachine.h" + +class TDirEntAttr; + +/** + * State machine for OpenByPath operation. + * + * Assumes FID is not yet cached. Note that here we know FID <-> pathname + * association and in principle the file with that pathname should exist + * as this call has been preceded by a call to Entry() + * - of course, there is a possibility that the file has been deleted from + * the server + * + */ +class CRsfwOpenByPathStateMachine : public CRsfwAttributeRefreshingStateMachine + { +public: + CRsfwOpenByPathStateMachine(); + ~CRsfwOpenByPathStateMachine(); + +public: + //STATES + // requiring opening in the relevant mode - e.g. obtain a write lock + class TRequestOpenModeState : public CRsfwOpenByPathStateMachine::TState + { + public: + TRequestOpenModeState(CRsfwOpenByPathStateMachine* aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwOpenByPathStateMachine* iOperation; + TBool iRequestedLock; + }; + +public: + TState* CompleteRequestL(TInt aError); + +public: + // input parameters; + TBool iRealOpen; + // file open mode + TUint iFlags; + + //output params: + TDesC* iCacheName; + TDirEntAttr* iAttrp; + TDesC8* iLockToken; + }; + + +#endif // C_RSFW_OPENBYPATHSTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwpermanentstore.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwpermanentstore.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,121 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Provides persistent storage for memory blocks +* +*/ + + +#ifndef C_RSFWPERMANENTSTORE_H +#define C_RSFWPERMANENTSTORE_H + +// INCLUDES +#include +#include +#include + +// CLASS DECLARATION +class TFileHeader + { +public: + TUint iHeaderStart; // magic number + TInt iHeaderSize; // (max) header size + TInt iBlockSize; // block size + HBufC8* iHeader; // header + +public: + void ExternalizeL(RWriteStream& aStream) const; + void InternalizeL(RReadStream& aStream); + }; + +class TSlot + { + public: + TInt iIndex; // data index (used as key for RArray) + TInt iBlockNumber; // starting block number + TInt iBlockCount; // number of blocks + }; + +class CRsfwPermanentStore: public CBase + { + +class TFreeBlockList + { + public: + RArray iFreeBlockList; // list of continuous free block sequences + }; + + enum TFileStateInPermanentStore + { + EFileStateClosed = 0, + EFileStateReading, + EFileStateWriting + }; +public: + static CRsfwPermanentStore* NewL(const TDesC& aPath, + TInt aHeaderSize = 0, + TInt aBlockSize = 0); + ~CRsfwPermanentStore(); + void ResetL(TBool aWriting); + TInt Commit(); + TInt Purge(); + void CompactL(); + void SetHeaderL(TDesC8& aHeader); + const HBufC8* Header(); + void GetNextDataL(TUint8* aData, TInt& aDataLength, TInt& aIndex); + void PutDataL(const TUint8* aData, TInt aDataLength, TInt& aIndex); + +protected: + void ConstructL(const TDesC& aPath, + TInt aHeaderSize, + TInt aBlockSize); + +private: + TInt BlockCount(TInt aDataLength); + TInt StreamPosition(TInt aBlockNumber); + TSlot* Slot(TInt aIndex); + void FixSlot(TInt aOldBlockNumber, TInt aNewBlockNumber); + void SetFileStateL(TInt aFileState); + void LoadHeaderL(); + void SaveHeaderL(); + void ClearFreeBlockLists(); + void ClearSlotL(TInt aIndex); + void WriteBlocksL(const TUint8* aData, + TInt aDataLength, + TInt aBlockNumber); + void ReserveSlot(TInt aIndex, TInt aBlockNumber, TInt aBlockCount); + void PutToFreeBlockList(TInt aBlockPos, TInt aBlockCount); + TInt GetFromFreeBlockList(TInt aBlockCount); + +private: + RFs iFs; // file server session + RFile iFile; // the file + RFileReadStream iFileReadStream; // iFile mapped to read stream + RFileWriteStream iFileWriteStream; // iFile mapped to write stream + TBuf iPath; // path name of the store file + TInt iHeaderSize; // size of header payload + TInt iFileHeaderSize; // total size of header + TInt iBlockSize; // size of elementary block + TInt iFileState; // file opening state + RArray iFreeBlockLists; // lists of free blocks + TFileHeader iFileHeader; // file information in the header + RArray iSlots; // maps index/block number + TInt iIndex; // next slot position + TInt iReadBlockNumber; // next block to read + TInt iWriteBlockNumber; // next block to write + HBufC8* iZeroBlock; // a filler block + }; + +#endif // PERMANENTSTORE_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwremoteaccess.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwremoteaccess.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,492 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Defines a class for accessing files via a file transport protocol +* +*/ + + +#ifndef CRSFWREMOTEACCESS_H +#define CRSFWREMOTEACCESS_H + +// INCLUDES +#include +#include + +//FORWARD DECLARATIONS +class CRsfwDirEntAttr; +class CRsfwDirEnt; + +// CONSTANTS +// +// UID of this interface +const TUid KCRemoteAccessUid = {0x101F96E3}; +// Default quota and free space sizes +const TInt KMountReportedSize = 10000000; +const TInt KMountReportedFreeSize = 5000000; + +// Operation option flags +const TUint KRemoteAccessOptionGetToStartOfFile = 0x01; + +// DATA TYPES +// Event types for MRsfwRemoteAccessObserver +enum TRsfwRemoteAccessObserverEvent + { + ERsfwRemoteAccessObserverEventConnection = 1 + }; + +// Connection events for MRsfwRemoteAccessObserver +enum TRsfwRemoteAccessObserverEventConnection + { + ERsfwRemoteAccessObserverEventConnectionDisconnected = 0, + ERsfwRemoteAccessObserverEventConnectionWeaklyConnected, + ERsfwRemoteAccessObserverEventConnectionStronglyConnected + }; + +// CONSTANTS +const TInt KMaxMatchStringSize = 64; + +// CLASS DECLARATION +/** + * Class for handling remote access events + * + * @lib rsfwcommon.lib + * @since Series 60 3.1 + */ +class MRsfwRemoteAccessObserver + { +public: + /** + * Handles an event emanating from a remote access module. + * + * @param aEventType type of the event + * @param aEvent event code + * @param aArg miscellaneous arguments + */ + virtual void HandleRemoteAccessEventL(TInt aEventType, + TInt aEvent, + TAny* aArg) = 0; + }; + +// CLASS DECLARATION +/** + * Class for handling remote access operation responses. + * + * @lib rsfwcommon.lib + * @since Series 60 3.1 + */ +class MRsfwRemoteAccessResponseHandler + { +public: + /** + * Handles responses for requests to a remote access module. + * + * @param aId transaction id + * @param aStatus return status + */ + virtual void HandleRemoteAccessResponse(TUint aId, TInt aStatus) = 0; + }; + + +// CLASS DECLARATION +/** + * Class for accessing files via a file transport protocol, like WebDAV. + * + * @lib rsfwcommon.lib + * @since Series 60 3.1 + * + * The derived classes are supposed to be registered and instantiated + * by using the the ECOM architecture. + */ +class CRsfwRemoteAccess : public CBase + { +public: + /** + * Two-phased constructor. + * + * @param aProtocol protocol name, like "http", "https", or "ftp" + * @return a pointer to an object instance that implements + * this interface by using the given protocol. + */ + IMPORT_C static CRsfwRemoteAccess* NewL(const TDesC8& aProtocol); + + IMPORT_C virtual ~CRsfwRemoteAccess(); + + /** + * Set up parameters for operation. + * @param aRsfwRemoteAccessObserver MRsfwRemoteAccessObserver for receiving + * asynchronous events from the accessor plugin, + * e.g. changes in connectivity. + * This parameter may be NULL + */ + virtual void SetupL( + MRsfwRemoteAccessObserver* aRsfwRemoteAccessObserver) = 0; + + /** + * Opens a connection to the server given by aServerName parameter. + * + * @param aUri URI of the remote repository. + * The URI must not contain authority part (user name/password) + * @param aFriendlyName friendly name for the server + * (for possible access control dialog) (can be empty) + * @param aUserName user name for access control (can be empty) + * @param aPassword password for access control (can be empty) + * @param aAuxData auxiliary parameters for connection setup (eg IAP info) + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint OpenL(const TUriC& aUri, + const TDesC& aFriendlyName, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aAuxData, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Gets contents of the directory given by aPathName parameter. + * + * @param aPathName path name of the directory + * @param aDirentsp an array of directory entries to be filled. + * Any pre-existing CRsfwDirEnt items in the array are destroyed + * and the array is reset before filling it with pointers to + * new entries. Within the created CRsfwDirEntAttr objects, pointers + * to descriptors for meta-data items that are not available or + * that are irrelevant are set to NULL value. + * The caller owns the array and thus also the entries. + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint GetDirectoryL(const TDesC& aPathName, + RPointerArray& aDirEntsp, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Gets attributes of the directory given by aPathName parameter. + * This function may also be called if the type of the object is + * not yet known (e.g., the object could be a file). + * + * @param aPathName path name of the directory + * @param aAttr A pointer to the attribute object to be filled. This + * attribute is set to point to a newly created CRsfwDirEntAttr + * object that will contain the directory attributes. + * In the created attribute object, pointers to descriptors for + * meta-data items that are not available or that are irrelevant + * are set to NULL value. The ownership of the object is + * transferred to the caller. If the attributes cannot be defined, + * the pointer will be set to NULL. + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint GetDirectoryAttributesL(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Gets attributes of the file given by aPathName parameter. + * + * @param aPathName path name of the file + * @param aAttr A pointer to the attribute object to be filled. This + * attribute is set to point to a newly created CRsfwDirEntAttr + * object that will contain the file attributes. + * In the created attribute object, pointers to descriptors for + * meta-data items that are not available or that are irrelevant + * are set to NULL value. The ownership of the object is + * transferred to the caller. If the attributes cannot be defined, + * the pointer will be set to NULL. + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint GetFileAttributesL(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Sets attributes of the file or directory given by aPathName parameter. + * This function is typically only used for files and even then + * the implementation may do nothing since standard file attributes + * are implied by the contents of the file or set in conjunction with + * other operations on the file system object. + * + * @param aPathName path name of the file or directory + * @param aAttr attribute structure + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint SetAttributesL(const TDesC& aPathName, + CRsfwDirEntAttr& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Gets a remote file and copies it to a local file. + * Note that byte ranges are not be implemented by all + * file access protocols. + * A non-zero aLength means partial get. + * Caller can assume that either aLength remains intact + * in which case byte range offset + aLength was fetched, + * or aLength is reset to the full length of the file, in which + * case aOffset is meaningless. + * + * @param aRemotePathName path name of the remote file + * @param aLocalPathName path name of the local file + * @param aOffset offset of the first byte to be accessed + * @param aLength length of data to be accessed/was accessed + * (on entry NULL or zero value means fetching the whole file - + * on exit contains the length of fetched data, unless the pointer is NULL) + * @param aFlags operation qualifier. + * The following flags have been defined: + * KRemoteAccessOptionGetToStartOfFile: even if an offset is specified + * the fetched data is still put at the beginning of the local file. + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint GetFileL(const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Puts a range of a file to the server. + * A non-zero aLength means partial file putting. + * The access protocol/server doesn't have to support partial file putting. + * In this case, it should return KErrNotSupported (if aLength is not zero) + * + * @param aLocalPathName path name of the local file + * @param aRemotePathName path name of the remote file + * @param MIME-type of the file + * (will be put to Content-Type, e.g. text/plain or + * application/octet-stream) + * @param aOffset offset of the first byte to be accessed + * @param aLength length of data to be accessed/was accessed (NULL/0=all) + * @param aTotalLength total length of the file, set to 0 if not known + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint PutFileL(const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Puts a file to the server. + * + * @param aLocalPathName path name of the local file + * @param aRemotePathName path name of the remote file + * @param MIME-type of the file (will be put to Content-Type, + * e.g. text/plain or application/octet-stream) + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint PutFileL(const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Creates an empty file on the remote server + * + * @param aPathName path name of the new file + * @param aResponseHandler response handler + * @param aOverWriting whether we are overwriting an existing file + * Note that the semantics of this operation is such that it must + * always overwrite an existing file. This boolean is for information. + * If the protocol requires additional parameter to allow overwriting, + * the parameter should be set if aOverWriting is TRUE. + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint CreateFileL(const TDesC& aPathName, + TBool aOverWriting, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Makes a directory. + * + * @param aPathName path name of the new directory + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint MakeDirectoryL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + + /** + * Deletes a directory. + * + * @param aPathName path name of the directory to be deleted + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + + virtual TUint DeleteDirectoryL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Deletes a file. + * + * @param aPathName path name of the file to be deleted + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint DeleteFileL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + + /** + * Renames a file or a directory. + * (may involve movement to another directory). + * + * @param aSrcPathName path name of the object to be renamed + * @param aDstPathName new path name of the object + * @param aOverwrite allow overwriting an existing object + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint RenameL(const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Obtains a lock for the given file system object + * Note that this function is not be implemented by all + * file access protocols (e.g. FTP), some protocols only + * implement write locking (e.g. WebDAV). + * + * @param aPathName path name of the object to be locked + * @param aLockFlags indicates whether a write or read lock is requested + * @param aTimeout the timeout that is requested and granted (in seconds) + * @param aLockToken acquired lock token - the caller gets ownership + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint ObtainLockL(const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8*& aLockToken, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Releases the lock of the given file system object + * Note that this function is not be implemented by all + * file access protocols (e.g. FTP). + * + * @param aPathName path name of the object to be locked + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint ReleaseLockL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Refreshes the lock of the given file system object + * Note that this function is not be implemented by all + * file access protocols (e.g. FTP). + * + * @param aPathName path name of the object to be locked + * @param aTimeout the timeout that is requested and granted (in seconds) + * @param aResponseHandler response handler + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + virtual TUint RefreshLockL(const TDesC& aPathName, + TUint& aTimeout, + MRsfwRemoteAccessResponseHandler* aResponseHandler) = 0; + + /** + * Cancels a transaction + * Eventually the HandleRemoteAccessResponseL will be called + * with status KErrCancel + + * @param aId the identifier of the transaction to be canceled. + * If aId is zero, all pending requests are cancelled. + */ + virtual void Cancel(TUint aId) = 0; + + /** + * Cancels a transaction + * Eventually the HandleRemoteAccessResponseL will be called + * with status KErrCancel + + * @param aTargetPath the path of the target file or directory for the + * operation that shall be cancelled + * + */ + virtual void Cancel(TDesC& aTargetPath) = 0; + + + /** + * Sets lock token for the a given resource + * This lock token value replaces any previously cached token value + * + * @param aPathName path name + * @param aLockToken lock token + * @return error code + */ + virtual TInt SetLockToken(const TDesC& aPathName, + const TDesC8& aLockToken) = 0; + + /** + * Gets quota and size. + * + * @param aQuota The maximum size of the drive for this user in bytes, + * @param aSize The amount of free space for this user on the disk in bytes. + * @return identifier of the created transaction + * (> 0 for async. operations, 0 if the operation is synchronous + * (has been completed when the call returns) + */ + IMPORT_C virtual TInt GetQuotaAndSizeL(TInt& aQuota, TInt& aSize); + + +private: + // Unique instance identifier key + TUid iDtor_ID_Key; + }; + +#endif // CRSFWREMOTEACCESS_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwremoteaccesssync.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwremoteaccesssync.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,259 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Synchronous layer on top of the Access Protocol plug-in API + * +*/ + + +#ifndef CRSFWREMOTEACCESSSYNC_H +#define CRSFWREMOTEACCESSSYNC_H + +// INCLUDES +#include + +#include "rsfwremoteaccess.h" + +// FORWARD DECLARATIONS +class CRsfwRemoteAccess; + +// CLASS DECLARATION +/** + * Class for accessing files via a file transport protocol + * by using synchronous calls. + * + * The derived classes are supposed to be registered and instantiated + * by using the the ECOM architecture. + */ + +class CRsfwRemoteAccessSync: public CBase, public MRsfwRemoteAccessResponseHandler + { +public: + /** + * Two-phased constructor. + * + * @param aProtocol protocol name, like "http", "https", or "ftp" + * @return a pointer to an object instance that implements + * this interface by using the given protocol. + */ + static CRsfwRemoteAccessSync* NewL(const TDesC8& aProtocol, + CRsfwRemoteAccess* aRemoteAccess = NULL); + + ~CRsfwRemoteAccessSync(); + + /** + * Configures the remote access module. + * Sets the connection state observer if available + * In davaccess creates the WebDAV session class + * + * @param aRemoteAccess asynchronous accessor (may be NULL) + * @param aRsfwRemoteAccessObserver connection event observer + * @return error code + */ + TInt Setup(MRsfwRemoteAccessObserver* aRsfwRemoteAccessObserver); + + /** + * Opens a connection to the server given by aServerName parameter. + * + * @param aUserName user name for access control (can be empty) + * @param aPassword password for access control (can be empty) + * @param aServerName the server's DNS name or IP address + * @param aPortNumber port number (like 80 for HTTP) + * @param aRootDirectory sub directory to be accessed (can be empty) + * @param aAuxData auxiliary parameters for connection setup (IAP info) + */ + TInt Open(const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aServerName, + TInt aPortNumber, + const TDesC& aRootDirectory, + const TDesC& aAuxData); + + /** + * Gets contents of the directory given by aPathName parameter. + * + * @param aPathName path name of the directory + * @param aDirEnts an array of directory entries to be filled. + */ + TInt GetDirectory(const TDesC& aPathName, + RPointerArray& aDirEntsp); + + /** + * Gets attributes of the directory given by aPathName parameter. + * This function may also be called if the type of the object is + * not yet known (e.g., the object could be a file). + * + * @param aPathName path name of the directory + * @param aAttr attribute structure to be filled + */ + TInt GetDirectoryAttributes(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr); + + /** + * Gets attributes of the file given by aPathName parameter. + * + * @param aPathName path name of the file + * @param aAttr attribute structure to be filled + */ + TInt GetFileAttributes(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr); + + /** + * Sets attributes of the file or directory given by aPathName parameter. + * This function is typically only used for files and even then + * the implementation may do nothing since standard file attributes + * are implied by the contents of the file or set in conjunction with + * other operations on the file system object. + * + * @param aPathName path name of the file or directory + * @param aAttr attribute structure + */ + TInt SetAttributes(const TDesC& aPathName, + CRsfwDirEntAttr& aAttr); + + /** + * Gets a remote file and copies it to a local file. + * Note that byte ranges are not be implemented by all + * file access protocols. + * + * @param aRemotePathName path name of the remote file + * @param aLocalPathName path name of the local file + * @param aOffset offset of the first byte to be accessed + * @param aLength length of data to be accessed/was accessed (0=all) + * @param aFlags operation flags (see RemoteAccess.h) + */ + TInt GetFile(const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags); + + /** + * Makes a directory. + * + * @param aPathName path name of the new directory + */ + TInt MakeDirectory(const TDesC& aPathName); + + + /** + * Creates an empty file on the remote server + * + * @param aPathName path name of the new file + */ + TInt CreateFile(const TDesC& aPathName); + + /** + * Puts a file to the server. + * + * @param aLocalPathName path name of the local file + * @param aRemotePathName path name of the remote file + */ + TInt PutFile(const TDesC& aLocalPathName, + const TDesC& aRemotePathName); + + /** + * Deletes a directory. + * + * @param aPathName path name of the directory to be deleted + */ + + TInt DeleteDirectory(const TDesC& aPathName); + + /** + * Deletes a file. + * + * @param aPathName path name of the file to be deleted + */ + TInt DeleteFile(const TDesC& aPathName); + + + /** + * Renames a file or a directory. + * (may involve movement to another directory). + * + * @param aSrcPathName path name of the object to be renamed + * @param aDstPathName new path name of the object + * @param aOverwrite allow overwriting an existing object + */ + TInt Rename(const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite); + + /** + * Obtains a lock for the given file system object + * Note that this function is not be implemented by all + * file access protocols (e.g., FTP), some protocols only + * implement write locking (e.g., WebDAV). + * + * @param aPathName path name of the object to be locked + * @param aLockFlags indicates whether a write or read lock is requested + * @param aTimeout the timeout that is requested and granted + * @param aLockToken acquired lock token - the caller gets ownership + */ + TInt ObtainLock(const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8*& aLockToken + ); + + /** + * Releases the lock of the given file system object + * Note that this function is not be implemented by all + * file access protocols (e.g., FTP). + * + * @param aPathName path name of the object to be locked + */ + TInt ReleaseLock(const TDesC& aPathName); + + /** + * Refreshes the lock of the given file system object + * Note that this function is not be implemented by all + * file access protocols (e.g., FTP). + * + * @param aPathName path name of the object to be locked + * @param aTimeout the timeout that is requested and granted + * @param aResponseHandler response handler + */ + TInt RefreshLock(const TDesC& aPathName, TUint& aTimeout); + + // from MRemoteAccessResponseHandler + virtual void HandleRemoteAccessResponse(TUint aId, TInt aStatus); + + /** + * Sets lock token for the a given resource + * This lock token value replaces any previously cached token value + * + * @param aPathName path name + * @param aLockToken lock token + * @return error code + */ + TInt SetLockToken(const TDesC& aPathName, const TDesC8& aLockToken); + +private: + void ConstructL(const TDesC8& aProtocol, + CRsfwRemoteAccess* aRemoteAccess = NULL); + TInt Epilog(); + + +private: + CRsfwRemoteAccess* iRemoteAccess; + TBool iOwnRemoteAccess; // whether we own iRemoteAccess + CActiveSchedulerWait* iSchedulerWait; + TInt iStatus; // operation return status + TBool iPending; // is there a pending request + }; + +#endif // CRSFWREMOTEACCESSSYNC_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrenamefilestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrenamefilestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,82 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for renaming files +* +*/ + + +#ifndef C_RSFW_RENAMEFILESTATEMACHINE_H +#define C_RSFW_RENAMEFILESTATEMACHINE_H + +#include "rsfwrfestatemachine.h" + +/** + * Renames a file + * + * State machine for renaming a file. Re-acquires possible lock. + * + */ + class CRsfwRenameFileStateMachine : public CRsfwRfeStateMachine + { +public: + CRsfwRenameFileStateMachine(); + ~CRsfwRenameFileStateMachine(); + +public: + class TRenameFileState : public CRsfwRenameFileStateMachine::TState + { + public: + TRenameFileState(CRsfwRenameFileStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwRenameFileStateMachine* iOperation; + }; + + class TAcquireLockState : public CRsfwRenameFileStateMachine::TState + { + public: + TAcquireLockState(CRsfwRenameFileStateMachine *aOperation); + void EnterL(); + TState* CompleteL(); + TState* ErrorL(TInt aCode); + private: + CRsfwRenameFileStateMachine* iOperation; + private: + TBool iRequestedLock; + }; + +public: + TState* CompleteRequestL(TInt aError); + +public: + // rename or replace + TBool iOverWrite; + + TPtrC iDstKidName; + + CRsfwFileEntry* iDstParentFep; + CRsfwFileEntry* iSrcKidFep; + CRsfwFileEntry* iDstKidFep; + + TBool iSrcKidCreated; + TBool iDstKidCreated; + + CRsfwDirEntAttr* iDirEntAttr; + TDesC8* iLockToken; + }; + + +#endif // C_RSFW_RENAMEFILESTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrequestallocator.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrequestallocator.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Operation and request allocation and deletion +* +*/ + +#ifndef RSFWTRequestType_H +#define RSFWTRequestType_H + +#include + +class CRsfwRfeSyncOperation; +class CRsfwRfeAsyncOperation; +class CRsfwRfeMessageRequest; +class CRsfwRfeRequest; +class RMessage2; +class CRsfwRfeSession; + +/** + * Operation and request allocation and deletion + */ +class RsfwRequestAllocator + { +public: + static CRsfwRfeSyncOperation* GetSyncOperation(CRsfwRfeRequest* aRequest, + TInt aCaller); + static CRsfwRfeAsyncOperation* GetAsyncOperation(CRsfwRfeRequest* aRequest, + TInt aCaller); + static CRsfwRfeMessageRequest* GetMessageRequest(const RMessage2& aMessage, + CRsfwRfeSession* aSession); + // request gets ownership of its operation, and deletes it + static void FreeRequest(CRsfwRfeRequest* aRequest); + }; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfeasyncoperation.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfeasyncoperation.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,47 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Encapsulates an asynchronous operation +* +*/ + +#ifndef C_RSFWRFEASYNCOPERATION_H +#define C_RSFWRFEASYNCOPERATION_H + +#include "rsfwrfeoperation.h" + +class CRsfwRfeStateMachine; +class CRsfwRfeRequest; +class TRsfwMountConfig; + +/** + * Encapsulates an asynchronous operation. + * + * Async. operations are implemented as state machines. + * + */ +class CRsfwRfeAsyncOperation : public CRsfwRfeOperation + { +public: + ~CRsfwRfeAsyncOperation(); +public: + CRsfwRfeStateMachine* Implementation(); + void SetImplementation(CRsfwRfeStateMachine*); + void SetL(CRsfwRfeRequest* aRequest, TInt aOpCode); +private: + void VerifyMountConfigL(TRsfwMountConfig& aMountConfig); +private: + CRsfwRfeStateMachine* iImplementation; + }; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfemessagerequest.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfemessagerequest.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,53 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: A request sent by a client (i.e. non-internal request) +* +*/ + +#ifndef C_RSFWRFEMESSAGEREQUEST_H +#define C_RSFWRFEMESSAGEREQUEST_H + +#include "rsfwrferequest.h" + +class CRsfwRfeSession; + + +/** + * A request sent by a client (i.e. non-internal request) + * + * In practise from Remote file-system plugin + * + */ +class CRsfwRfeMessageRequest : public CRsfwRfeRequest + { +public: + CRsfwRfeMessageRequest(); + void SetL(const RMessage2& aMessage,CRsfwRfeSession* aSession); + const RMessage2& Message(); + CRsfwRfeSession* Session(); + void SetSession(CRsfwRfeSession* aSession); + // + void Complete(TInt aError); + void CompleteAndDestroy(TInt aError); +private: + void Destroy(); +public: + TBool iMessageCompleted; + +protected: + RMessage2 iMessage; + CRsfwRfeSession* iSession; + }; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfeoperation.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfeoperation.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,49 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Base class for operation encapsulation +* +*/ + +#ifndef C_RSFWRFEOPERATION_H +#define C_RSFWRFEOPERATION_H + +#include + +#include "rsfwrferequest.h" + +/************************ + * Operation Encapsulation + ************************/ +typedef void (*TRFeRequestFunc)(CRsfwRfeRequest*); + + +/** + * Base class for operation encapsulation + * + * + */ +class CRsfwRfeOperation : public CBase + { +public: + TBool IsSync() const; + TInt Function(); + void Set(TInt aOpCode); +public: + TInt iFunction; + TBool iIsSync; + }; + + + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrferequest.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrferequest.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,78 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Base class for request encapsulation. +* +*/ + +#ifndef C_RSFWRFEREQUEST_H +#define C_RSFWRFEREQUEST_H + +class TParse; +class TRfeInArgs; +class TRfeOutArgs; +class CRsfwVolumeTable; +class CRsfwVolume; +class CRsfwRfeOperation; + + +#include + +// type of the request +// in the future we could have e.g. internal requests +enum TRequestType + { + EMessageRequest + }; + + +/** + * Base class for request encapsulation. + * + * + */ +class CRsfwRfeRequest : public CBase + { +public: + ~CRsfwRfeRequest(); + // + virtual void CompleteAndDestroy(TInt aError) = 0; // pure virtual + + void Destroy(); + virtual void Dispatch(); + virtual TParse& Src(); + virtual TParse& Dest(); + // + CRsfwRfeOperation* Operation(); + void SetOperation(CRsfwRfeOperation* aCaller); + TRequestType RequestType(); + void SetRequestType(TRequestType aRequestType); + +// Request parameters +public: + TRfeInArgs* iInArgs; + TRfeOutArgs* iOutArgs; + + CRsfwVolumeTable* iVolumeTable; + // volume can be null in mount operation, but not after that + CRsfwVolume* iVolume; +public: + TDblQueLink iLink; +protected: + CRsfwRfeOperation* iOperation; +private: + TRequestType iRequestType; + }; + +#endif + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfeserver.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfeserver.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,129 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File Engine server +* +*/ + + +#ifndef C_RSFWRFESERVER_H +#define C_RSFWRFESERVER_H + +// INCLUDES +#include +#include + +class CRsfwVolumeTable; + +// CONSTANTS +/** Panic Category */ +_LIT(KRfeServer, "RemoteFileEngine"); + +// for security check, same as File Server UID +const TUint KFileServerSecureUid = 0x100039e3; + +/** server inactivity timeout, in seconds */ +const TInt KRfeServerShutdownInterval = 5; + + +// DATA TYPES +/** Remote File Engine panic codes */ +enum TRfePanic + { + EBadRequest, + EBadDescriptor, + ESrvCreateServer, + ECreateTrapCleanup, + ENullRequestHandler, + EUndefinedRequest, + ECacheInconsistency, + EConstructingServerStructs + }; + +// MACROS + +// FORWARD DECLARATIONS +class CRsfwConfig; +class CRsfwRfeServer; + + +// CLASS DECLARATION +class TRfeEnv + { +public: + RFs iFs; + TInt iCacheDrive; + TFileName iCacheRoot; + CRsfwConfig* iRsfwConfig; + }; + + +// CLASS DECLARATION + +class CRsfwRfeServer: public CPolicyServer + { + friend class CRsfwRfeSession; + +public: + static CRsfwRfeServer* NewL(); + static CRsfwRfeServer* NewLC(); + static TInt ThreadFunction(TAny* aNone); + + void IncrementSessions(); + void DecrementSessions(); + + void AllEnginesIdling(TInt aTimeout); + void ServiceRequested(); + + static TRfeEnv* Env() + { + return iEnvp; + } + +protected: + TInt RunError(TInt aError); + + // custom action when capability checked failed - basically this allows File Server to always + // pass based on its SID (File Server does not have NetworkServices or ReadDeviceData capabilities) + TCustomResult CustomFailureActionL(const RMessage2& aMsg, + TInt aAction, + const TSecurityInfo& aMissing); + +private: + CRsfwRfeServer(TInt aPriority, TServerType aType) ; + void ConstructL() ; + static void PanicClient(const RMessage2& aMessage, TRfePanic aReason); + static void PanicServer(TRfePanic aReason); + static void ThreadFunctionL(); + CSession2* NewSessionL(const TVersion &aVersion, + const RMessage2& aMessage) const; + void PrepareCacheRootL(); + void ShutDown(); + void StartDelayedShutdownTimer(TInt aTimeout); + void StopDelayedShutdownTimer(); + static TInt DelayedShutdownTimerExpired(TAny* aArg); + +protected: + CRsfwVolumeTable* iVolumes; + +private: + TInt iSessionCount; + TRfeEnv iEnv; + static TRfeEnv* iEnvp; + TBool iShuttingDown; + CPeriodic* iDelayedShutdownTimer; + }; + +#endif // RFESERVER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfesession.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfesession.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,66 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File Engine session manager +* +*/ + + +#ifndef C_RSFWRFESESSION_H +#define C_RSFWRFESESSION_H + +#include +#include "rsfwrfemessagerequest.h" +#include "rsfwcontrol.h" // KDefaultMessageSlots = 4 + +class CRsfwRfeServer; +class CRsfwRfeOperation; +class CRsfwVolumeTable; +class CRsfwRfeRequest; + +// CLASS DECLARATION +// class CRsfwRfeSession: public CSharableSession + +class CRsfwRfeSession: public CSession2 +{ +public: + static CRsfwRfeSession* NewL(CRsfwRfeServer& aServer); + static CRsfwRfeSession* NewLC(CRsfwRfeServer& aServer); + ~CRsfwRfeSession(); + void ServiceL(const RMessage2& aMessage); + CRsfwVolumeTable* Volume(); + CRsfwRfeServer* Server(); + + void RemoveFromMessageRequestArray(CRsfwRfeMessageRequest* aMessageRequest); + private: + CRsfwRfeSession(CRsfwRfeServer& aServer); + CRsfwRfeOperation* GetOperation(CRsfwRfeRequest* pR, TInt aOperation); + void ConstructL(); +#ifndef SHARABLE_SESSION + void PanicClient(TInt aPanic) const; +#endif + void SetToMessageRequestArray(CRsfwRfeMessageRequest* aMessageRequest); + +protected: + void Disconnect(const RMessage2& aMessage); + + +private: + CRsfwRfeServer& iRfeServer; + CRsfwVolumeTable* iVolumes; + CRsfwRfeMessageRequest* iMessageRequests[KDefaultMessageSlots]; + }; + +#endif RFESESSION_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,109 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Base class for all operation state machines +* +*/ + +#ifndef C_RSFW_RFESTATEMACHINE_H +#define C_RSFW_RFESTATEMACHINE_H + +#include +#include "rsfwremoteaccess.h" + +class CRsfwRfeRequest; +class CRsfwVolumeTable; +class CRsfwFileEngine; +class TRfeInArgs; +class TRfeOutArgs; +class CRsfwFileEntry; +class TFid; + +const TInt KUpdateNotRequired = 5; + +/** + * Base class for all operation state machines + * + */ +class CRsfwRfeStateMachine : public CBase, public MRsfwRemoteAccessResponseHandler + { +public: + + class TState + { + public: + virtual void EnterL()=0;// pure virtual + virtual TState* CompleteL(); + virtual TState* ErrorL(TInt aCode); + virtual void Cancel(); + }; + + class TCompleteAndDestroyState : public CRsfwRfeStateMachine::TState + { + public: + TCompleteAndDestroyState(CRsfwRfeStateMachine* aOperation, + TInt aErrCode = 0); + void EnterL(); + void SetErrorCode(TInt aErrorCode); + private: + CRsfwRfeStateMachine* iOperation; + TInt iErrCode; + }; + +public: + void BaseConstructL(); + ~CRsfwRfeStateMachine(); + + virtual TState* ErrorOnStateEntry(TInt aError); + + void ChangeState(TState* aNextState); + void EnterState(TState* aNextState); + void SetNextState(TState* aNextState); + void ReEnterCurrentState(); + void SetRequest(CRsfwRfeRequest* aRequest); + CRsfwRfeRequest* Request(); + inline TState* CurrentState(){return iState;}; + inline TCompleteAndDestroyState* CompleteAndDestroyState() + {return iCompleteAndDestroyState;}; + + // completes client's request + virtual TState* CompleteRequestL(TInt aError)=0; + + void SetVolumes(CRsfwVolumeTable* aImplementor); + void SetFileEngine(CRsfwFileEngine* aFileEngine); + void SetArguments(TRfeInArgs* aInArgs, TRfeOutArgs* aOutArgs); + CRsfwVolumeTable* Volumes(); + CRsfwFileEngine* FileEngine(); + CRsfwFileEntry* Node(); + virtual TState* ErrorOnStateExit(TInt aError); + + // from MRsfwRemoteAccessResponseHandler + void HandleRemoteAccessResponse(TUint aId, TInt aStatus); + void DoCancel(); + +public: + TRfeInArgs* iInArgs; + TRfeOutArgs* iOutArgs; + +private: + CRsfwFileEntry* iFep; // target file/directory parameter used by almost all state machines: + TCompleteAndDestroyState* iCompleteAndDestroyState; // pre-created so that the request can always be completed (OOM situations etc.) + TState* iState; // our current state + CRsfwRfeRequest *iRFeRequest; // back pointer to the request we are running + CRsfwVolumeTable* iImplementor; // class that implements the operations + CRsfwFileEngine* iFileEngine; // the file engine + }; + + + +#endif // C_RSFW_RFESTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwrfesyncoperation.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwrfesyncoperation.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,41 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Encapsulates synchronous operation +* +*/ + +#ifndef C_RSFWRFESYNCOPERATION_H +#define C_RSFWRFESYNCOPERATION_H + +#include "rsfwrfeoperation.h" + + + +/** + * Encapsulates a synchronous operation + * + * Synchronous operation can be implemented as a simple function pointer. + * + */ + class CRsfwRfeSyncOperation : public CRsfwRfeOperation + { +public: + void DoRequestL(CRsfwRfeRequest* aRequest); + void Set(CRsfwRfeRequest* aRequest, TInt aCaller); +private: + TRFeRequestFunc iDoRequestL; + }; + +#endif + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwsession.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwsession.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,319 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Defines the standard Symbian IPC for using Access API + * +*/ + + +#ifndef RRSFWSESSION_H +#define RRSFWSESSION_H + +// INCLUDES +#include +//#include +//#include + +// INTERNAL INCLUDES +//#include "rsfwcontrol.h" +#include "rsfwcommon.h" +//#include "rsfwinterface.h" +class TFid; +class TEntry; +class TDirEntAttr; + +enum TRequestCodes + { + ERequestPending + }; + + +// CLASS DECLARATION +/** + * This class provides the client-side interface to the server session. + * + * @lib rsfwsession.dll + * @since Series 60 3.1 + */ +class RRsfwSession : public RSessionBase + { +public: // Constructors and destructor + /** + * Constructor. + */ + IMPORT_C RRsfwSession(); + +public: // New functions + /** + * Connect to the server and create a session. + * @since Series 60 3.1 + * @param aServerName Server name. + * @return Standard error code. + */ + IMPORT_C TInt Connect(); + + /** + * Close the session + * @since Series 60 3.1 + */ + IMPORT_C void Close(); + + /** + * Get the server version number. + * @since Series 60 3.1 + * @return The version number of the server. + */ + IMPORT_C TVersion Version() const; + + /** + * Issue request to rename or replace a file or a directory + * @since Series 60 3.1 + * @param aSourceFid Fid of the source file's parent directory + * @param aSourceName The name of the object to be renamed + * (for dirs must have a trailing backslash) + * @param aDestFid Fid of the destination directory + * @param aDestName The name of the target object + * (for dirs must have a trailing backslash) + * @return + */ + IMPORT_C TInt MoveFids( TFid aSourceFid, + const TDesC& aSourceName, + TFid aDestFid, + const TDesC& aDestName, + TBool aOverWrite ); + + /** + * Issue request to set entry details for a specified file or directory. + * @since Series60 3.1 + * @param aFid Fid of the target file or directory + * @param aTime A reference to the time object holding the new universal + * modified time for aName. + * @param aSetAttMask Attribute mask for setting the entry's attributes. + * @param aClearAttMask Attribute mask for clearing the entry's attributes. + * @return + */ + IMPORT_C TInt SetEntry( TFid aFid, + const TTime& aTime, + TUint aSetAttMask, + TUint aClearAttMask); + + /** + * Issue request to flush an entry from the cache. + * @since Series 60 3.1 + * @param aFid The fid of the file or directory to be flushed. + * @return + */ + IMPORT_C TInt FlushCache( TFid& aFid ); + + /** + * Issue request to raise the cache priority of an already + * cached file. + * @since Series 60 3.1 + * @param aFid The fid of the file. + * @return + */ + IMPORT_C TInt SetHighCachePriority( TFid& aFid ); + + /** + * Issue request to fetch file or directory attributes. + * @since Series 60 3.1 + * @param aFileFid Fid of the file. + * @param aAttributes On success, contains the file attributes + * (TEntry::iName is not filled) + * @return + */ + IMPORT_C TInt GetAttributes( TFid aFileFid, + TEntry& aAttributes ); + + /** + * Issue request to open this fid and return the path of the container file + * Note that this is "OPEN" operation, e.g. if the mode is relevant a lock + * will be acquired and will be refreshed until the file is closed. + * @since Series 60 3.1 + * @param aFid Fid of the file or directory. + * @param aContainer Pointer to descriptor which will, on success, contain + * the full path of the container file. + * @param aAttr aAttr.iAtt: Open mode, controls acquiring locks etc. + * on return, contains size etc. + * @param aTrueOpen Whether File Server opens the file, or ReadSection was called in + * which case we also mimic the sequence of opening a file + * (file is not candidate for removing from cache if it has been + * opened by the File Server). + * @return + */ + IMPORT_C TInt OpenByPath( TFid aFid, + TDes& aContainerPath, + TDirEntAttr* aAttr, + TBool aTrueOpen); + + /** + * Issue request to initialize the remote mount. + * @since Series 60 3.1 + * @param Upon successfull return, will contain the Fid of the root directory + * @return + */ + IMPORT_C TInt RfeInit(TFid& aRootFid); + + + /** + * Issue request to make a directory. + * @since Series 60 3.1 + * @param aParentFid Fid of the parent directory. + * @param aDirName The name of the new directory. + * @return + */ + IMPORT_C TInt MakeDirectory( TFid aParentFid, + const TDesC& aDirName ); + + /** + * Issue request to remove a directory. + * @since Series 60 3.1 + * @param aParentFid Fid of the parent directory. + * @param aDirName The name of the directory to be removed. + * @return + */ + IMPORT_C TInt RemoveDirectory( TFid aParentFid, + const TDesC& aDirName ); + + + /** + * Issue request to create and open a file. + * Note that this is "OPEN" operation, e.g. if the mode is relevant a lock + * will be acquired and will be refreshed until the file is closed. + * @since Series 60 3.1 + * @param aParentFid Fid of the parent directory. + * @param aFileName The name of the new file. + * @param aMode The mode in which the file will be opened. + * @param aExcl Boolean indicating whether it is ok to overwrite an existing file. + * (ETrue = exclusive = no overwriting) + * @param aNewFid Upon successful return, contains the fid of the new file + * @return + */ + IMPORT_C TInt CreateFile( TFid aParentFid, + const TDesC& aFileName, + TUint aMode, + TUint aExcl, + TFid& aNewFid); + + /** + * Issue request to remove a file. + * @since Series 60 3.1 + * @param aParentFid Fid of the parent directory. + * @param aFileName The name of the file to be removed. + * @return + */ + IMPORT_C TInt RemoveFile( TFid aParentFid, + const TDesC& aFileName ); + + + /** + * finds the fid of a file system object + * @since Series 60 3.1 + * @param aParentFid fid of the parent directory + * @param aName name of the child to be looked up + * @param aNodeType is the type of the child, + * KNodeTypeUnknown,KNodeTypeFile or KNodeTypeDir + * (also a trailing backslash in the name indicates KNodeTypeDir) + * @param aFid upon successful return contains the fid + * of the object to be looked up + * @return + */ + IMPORT_C TInt Lookup( TFid aParentFid, + const TDesC& aName, + TUint aNodeType, + TFid& aFid ); + + /** + * Tells Remote File Engine that a file has been closed + * @since Series 60 3.1 + * @param aFid Fid of the file that was closed + * @param aFlags whether the file has been changed + * @return + */ + IMPORT_C void CloseFile( const TFid aFid, + TUint aFlags); + + + /** + * Tells Remote File Engine to write a file that has been + * modified back to the server. However, File Server does + * not close the file. + * @since Series 60 3.1 + * @param aFid Fid of the file to be flushed + * @param aFirstByte the first byte to be flushed + * @param aLastByte the first byte to be flushed + * @param aTotalSize the full size of the file + * @return + */ + IMPORT_C TInt Flush( const TFid aFid, + TInt aFirstByte, + TInt aDataLength, + TInt aTotalSize ); + + /** + * Issue requet to fetch and cache a file or a directory + * @since Series 60 3.1 + * @param aFileFid the fid of the file to be cached + * @param aFirstByte the first byte to be cached (0 for dirs) + * @param aLastByte the last byte to be cached (0 for dirs) + * @param aCachedBytes upon succesful return, + * the number of bytes cached after this fetch + * @return + */ + IMPORT_C TInt Fetch( TFid aFileFid, + TInt aFirstByte, + TInt aLastByte, + TInt& aCachedBytes ); + + + /** + * Issue request to fetch data without permanent caching. + * @since Series 60 3.1 + * @param aFileFid the fid of the file to be fetched + * @param aFirstByte the first byte to be fetched + * @param aLastByte the last byte to be fetched + * @param aTempFileName the path of the temp file + * where the data will be stored + * @param aUseTempPath FALSE if the caching mode was such + * that the data was anyway stored into + * the normal cache file. + * + * @return + */ + IMPORT_C TInt FetchData( TFid aFileFid, + TInt aFirstByte, + TInt aLastByte, + TDes& aTempFileName, + TBool& aUseTempPath); + + /** + * Queries from Remote File Engine whether there is enough local cache + * space to write aBytes of data + * @since Series 60 3,1 + * @param aFid fid of the file whose data will be written + * @param aBytes the number of bytes to be written + * @return a boolean value indicating whether the data can be written + */ + IMPORT_C TInt OkToWrite( TFid aFid, + TUint aBytes, + TBool& aOkToWrite ); + +private: + static TInt StartServer( const TDesC& aServerName ); + static TInt CreateServerProcess( const TDesC& aServerName ); + TInt SendRequest(TInt aOpCode, TInt aDrive, TIpcArgs aArgs); + }; + +#endif // RRSFWSESSION_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwsyncoperations.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwsyncoperations.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,108 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: functions for synchronous operations +* +*/ + + +#ifndef RSFW_SYNCOPERATIONS_H +#define RSFW_SYNCOPERATIONS_H + +class CRsfwRfeRequest; + + +/** + * wrapper for all sync requests + * + */ +class TRFeSynCRsfwRfeRequest + { +public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + +/** + * dismount a previously mounted volume + * + * by volume ID + * + */ +class TRFeDismountVolumeId + { +public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + +/** + * dismount a previously mounted volume + * + * by drive letter + * + */ +class TRFeDismountByDriveLetter + { +public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + + /** + * get a list of currently active mounts + * + */ +class TRFeGetMountList + { +public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + +/** + * get information about a specific mount + * + */ +class TRFeGetMountInfo + { +public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + +/** + * get permission to write certain amount of data + * + */ +class TRFeWriteData + { +public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + +/** + * refresh a directory + * + */ +class TRFeDirectoryRefresh + { + public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; + +/** + * cancel all active upload/dowload operations + * + */ +class TRFeCancelAll + { + public: + static void DoRequestL(CRsfwRfeRequest* aRequest); + }; +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwvolume.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwvolume.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: data struct for a volume +* +*/ + +#ifndef C_RSFWVOLUME_H +#define C_RSFWVOLUME_H + +#include "rsfwcontrol.h" + + +class CRsfwFileEngine; +class CRsfwVolumeTable; + +/** default volume inactivity timeout, in seconds */ +const TInt KDefaultInactivityTimeout = 600; + +class CRsfwVolume: public CBase + { +public: + ~CRsfwVolume(); + TRsfwMountInfo* MountInfo(); + void GetMountInfo(TRsfwMountInfo& aMountInfo); + void OperationCompleted(); + void ConnectionStateChanged(TInt aConnectionState); + +public: + TRsfwMountInfo iMountInfo; // mount configuration information + CRsfwFileEngine* iFileEngine; // remote file engine + CRsfwVolumeTable* iVolumeTable; // backpointer to volume table + }; + + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwvolumetable.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwvolumetable.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,158 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: data struct for all volumes +* +*/ + +#ifndef C_RSFWVOLUMETABLE_H +#define C_RSFWVOLUMETABLE_H + +#include +#include + +#include "rsfwlruprioritylist.h" + +class CRsfwRfeServer; +class CRsfwConfig; +class TRsfwMountInfo; +class TRsfwMountConfig; +class TRsfwMountStatus; +class CRsfwVolume; +class TTime; +class CRsfwMountStateMachine; +class CRsfwWaitNoteManager; +class CRsfwMountStore; +class CRsfwDormantMountLoader; + +/** caching mode */ +enum TCachingMode + { + EWholeFileCaching, + EMetadataIfa, + EFullIfa + }; + +/** theoretical maximum number of volumes - A to Z */ +const TInt KMaxVolumes = 26; + + +/** Shutdown after all mounts have become dormant/disconnected */ +const TInt KRsfwDormantShutdownTimeout = 120; + +class CRsfwVolumeTable: public CBase + { +public: + static CRsfwVolumeTable* NewL(CRsfwRfeServer* aRfeServer, + CRsfwConfig* aRsfwConfig); + ~CRsfwVolumeTable(); + + void DispatchL(TAny* aIp, TAny* aOp); + TInt VolumeIdByDriveLetter(TChar aDriveLetter); + CRsfwVolume* VolumeByVolumeId(TInt aVolumeId); + CRsfwVolume* VolumeByDriveLetter(TChar aDriveLetter); + void RestoreDormantMountsL(); + TUint RecoverVolumeL(const TRsfwMountConfig& aMountConfig, + CRsfwMountStateMachine* aCaller); + TInt MountState(TChar aDriveLetter); + TInt GetMountConfigL(TRsfwMountConfig& aMountConfig); + void RestoreVolumesL(); + void DismountByVolumeIdL(TInt aVolumeId, TBool aDiscardPermanentData); + void DismountByDriveLetterL(TChar aDriveLetter, + TBool aDiscardPermanentData); + void GetMountList(TDriveList& aMountList); + TInt GetMountInfo(TRsfwMountInfo& aMountInfo); + void GetMimeTypeSpecificLimits(); + + // Cache management functions + TBool EnsureCacheCanBeAddedL(TInt aBytes); + TBool EnsureMetadataCanBeAddedL(CRsfwFileEntry* aParent); + TBool IsRoot(const CRsfwFileEntry* aEntry); + TInt TotalCachedSize(); + TInt TotalEntryCount(); + void AddToLRUPriorityListL(CRsfwFileEntry *aFe, TInt aPriority); + void RemoveFromLRUPriorityList(CRsfwFileEntry *aFe); + void AddToMetadataLRUPriorityListL(CRsfwFileEntry *aFe, TInt aPriority); + void RemoveFromMetadataLRUPriorityList(CRsfwFileEntry *aFe); + void MoveToTheBackOfMetadataLRUPriorityListL(CRsfwFileEntry *aFe); + void WillLRUPriorityListBeInternalized(); + TBool CheckAndAddProcessStartMarker(); + void DeleteTheMarker(); + void CleanupCorruptedCacheL(); + void OperationCompleted(CRsfwVolume* aVolume); + void VolumeStateChanged(CRsfwVolume* aVolume); + CRsfwWaitNoteManager* WaitNoteManager(); + TBool IsCachedDataStillValid(TTime aCachedTime); + TBool IsCachedAttrStillValid(TTime aCachedTime); + + // removes from cache all the data for certain path + // this is "refresh", i.e to ensure that next readdir fetches the data + // form server + TInt PurgeFromCache(TDesC& aCachePath); + + TInt CancelTransferL(TDesC& aFilePath); + + void MountDormantL(const TRsfwMountConfig& aMountConfig, TInt aVolumeId); + + void PublishConnectionStatus(CRsfwVolume* aVolume); + +private: + void ConstructL(CRsfwRfeServer* aRfeServer, CRsfwConfig* aRsfwConfig); + TBool IsCacheStillValid(TTime aCachedTime, TTimeIntervalSeconds aValidity); + void ExternalizeLRUPriorityList(); + void ExternalizeLRUPriorityListL(); + void InternalizeLRUPriorityListL(); + TBool IsMountIdle(TRsfwMountStatus& aMountStatus); + +public: + // configuration parameters read from the configuration file + TInt iMaxCacheSize; // maximum allowed cache size (global) + TInt iMaxEntryCount; // maximum number of cached entries (global) + + TCachingMode iCachingMode; + TInt iRecognizerLimit; + TInt iImageJpegLimit; + TInt iAudioMpegLimit; + TInt iInactivityTimeout; + +public: + CRsfwVolume* iVolumes[KMaxVolumes]; // alphabet + TInt iLastVolumeId; + CRsfwConfig* iRsfwConfig; // RSC configuration + + TBool iPermanence; // use permanent meta data + CRsfwMountStore* iMountStore; // mount configuration repository + CRsfwLruPriorityList iLRUPriorityList; + CRsfwLruPriorityList iMetadataLRUPriorityList; + CRsfwRfeServer* iRfeServer; + TBool iUseExternalizedLRUList; // whether to use externalized LRU list data or not + TBool iDormantMountRestorePending; // true when, after server startup, we start to restore mounts + +private: + CRsfwDormantMountLoader* iDormantMountLoader; // loads dormant mounts asynchronously shortly after server start + CRsfwWaitNoteManager* iWaitNoteManager; // Implements handling of global wait notes + // associated with this class because when we come to Connect(), not much else is available + + TBool iAllEnginesIdle; // are all the engines idle + RProperty iMountStateProperty; // property for connection state signaling + TInt iFileCacheTimeout; // how long cached files are assumed to be valid + TInt iDirCacheTimeout; // how long cached dirs are assumed to be valid + + // these are also available from TRfeEnv, but they are used so many times + // by this class that an own pointer is justified + RFs iFs; // handle to RFs session, owned by RfeServer + TFileName* iCacheRoot; // pointer to cacheroot, owned by RfeServer + }; + + +#endif diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwwaitnotemanager.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwwaitnotemanager.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,187 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Global wait notes used in Remote File Engine +* +*/ + + +#ifndef C_RSFWWAITNOTEMANAGER_H +#define C_RSFWWAITNOTEMANAGER_H + +// INCLUDES +#include +#include +#include +#include "rsfwwaitnotestatemachine.h" +#include "rsfwauthenticationdlgrequest.h" +#include "rsfwsavetodlgrequest.h" + +// CONSTANTS +_LIT(KResourceFile, "Z:\\resource\\remotefileengine.rsc"); + +// FORWARD DECLARATIONS +class TRsfwAuthenticationDlgRequest; +class TRsfwAuthenticationDlgResponse; +class CAknGlobalConfirmationQuery; + +// CLASS DECLARATION + +/** +* CRsfwWaitNoteManager class +* +* Wait Note Manager class for Remote File Engine +*/ +class CRsfwWaitNoteManager : public CActive + { + public: // Constructors and destructor + + /** + * Symbian OS two-phased constructor + * @return Pointer to this component. + */ + IMPORT_C static CRsfwWaitNoteManager* NewL(); + + /** + * C++ default destructor. + */ + virtual ~CRsfwWaitNoteManager(); + + private: + + /** + * C++ default constructor. + */ + CRsfwWaitNoteManager(); + + /** + * Symbian OS default constructor. + */ + void ConstructL(); + + void ShowGlobalInformationNoteL(TInt aResourceId); + + public: // New functions + + /** + * Start to display wait note. + * Note: A new wait note can only be activated when the previous one is + * dismissed. + * @since 3.1 + * @param aOpType Wait Note operation type. + */ + TInt StartWaitNoteL( TRemoteOperationType aOpType, + CRsfwWaitNoteStateMachine* aOperation ); + + + /** + * Server or path not found, when connecting + */ + void ShowAddressNotFoundErrorL(const TDesC& aFriendlyName); + + void SetAuthenticationDialogL(TRsfwAuthenticationDlgRequest& aAuthRequest); + + void SetGlobalNoteRequestL(TRsfwNotPluginRequest& aRequestStruct); + + void SetSaveToDialogRequestL(TRsfwSaveToDlgRequest& aSaveRequest); + + void ShowFileSavedToDialogL(const TDesC& aValue); + + void ShowFailedSaveNoteL(); + + void ShowNoNetworkCoverageNoteL(); + + void ShowOfflineNotPossibleNoteL(); + + void ShowOutOfMemoryNoteL(); + + // inform the wait note manager that no operation is waiting for + // it to trigger its state anymore + void ResetOperation(); + + /** + * Cancel wait note. + * Note: Please make sure the system is still able to handle key press + * events during an operation. + * @since 3.1 + */ + void CancelWaitNoteL(TInt aNoteId); + + +private: // Functions from base classes + + /** + * Handles an active object’s request completion event. + */ + void RunL(); + + /** + *Implements cancellation of an outstanding request. + */ + void DoCancel(); + + /** + * Called in case RunL() leaves + */ + TInt RunError(TInt aError); + +private: // Data + + // Current operation type + TRemoteOperationType iOpType; + + // Operation state + TRemoteWaitNoteStates iOpState; + + // sequental id for the curren note + // this is unique unlike CAknGlobalNote's id + TInt iNoteId; + + // standard global confirmation query + CAknGlobalConfirmationQuery* iQuery; + + // note Id of the active CAknGlobalNote + TInt iAvkonNoteId; + + // custom global notes server + RNotifier iNotifier; + + // IPC parameters struct for authentication dialog + TRsfwAuthParamsPckg* iAuthRequest; + + // pointer to the mount state machines auth info + // so that new username and/or passwd can be written + TRsfwAuthenticationDlgRequest* iAuthCredentials; + + // IPC parameters struct for wait notes and the retry note + TRsfwRetryParamsPckg *iGlobalNoteRequest; + + // IPC parameters struct for saveto dialog + TRsfwSaveToParamsPckg* iSaveToRequest; + + // pointer to state machine's save to params + TRsfwSaveToDlgRequest* iSaveParams; + + // buffer for the disconnect warning note txt + HBufC* iNoteTxt; + + // resource file reading + RResourceFile iResourceFile; + TResourceReader iResourceReader; + + CRsfwWaitNoteStateMachine* iOperation; + }; + +#endif // REMOTEWAITNOTEMANAGER_H + +// End of File \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/inc/rsfwwaitnotestatemachine.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/inc/rsfwwaitnotestatemachine.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,62 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: States that use a global wait dialog +* +*/ + +#ifndef C_RSFW_WAITNOTESTATEMACHINE_H +#define C_RSFW_WAITNOTESTATEMACHINE_H + +#include "rsfwrfestatemachine.h" +#include "rsfwnotpluginrequest.h" + +// Wait Note States +enum TRemoteWaitNoteStates + { + ERemoteWaitNoteStateOk = 0, + ERemoteWaitNoteStateInProgress + }; + +// Operation type supported for wait note +enum TRemoteOperationType + { + ERemoteOpIdle = 0, + ERemoteOpConnecting, + ERemoteOpDirDownloading, + ERemoteOpAuthDialog, + ERemoteUnavailableRetry, + ERemoteSaveToLocal, + ERemoteWarnDisconnect, + }; + +/** + * Parent class for states that use global wait dialogs + * + */ + class CRsfwWaitNoteStateMachine : public CRsfwRfeStateMachine + { + public: + void CancelTransaction(); + void ShowWaitNoteL(TRemoteOperationType aResourceId); + void DeleteWaitNoteL(TBool aCancelOpWait); + TState* ErrorOnStateEntry(TInt aError); + TState* ErrorOnStateExit(TInt aError); + TState* CompleteRequestL(TInt aError); + public: + TRsfwNotPluginRequest iGlobalWaitNoteRequest; + TUint iTransactionId; // for cancelling requests + TUint iNoteId; // id of the global note + }; + +#endif // C_RSFW_WAITNOTESTATEMACHINE_H \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/loc/RemoteFileEngine.loc --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/loc/RemoteFileEngine.loc Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,102 @@ +/* +* Copyright (c) 2002-2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Localization strings for global notes in Remote File Engine +* +*/ + + +// LOCALISATION STRINGS + +//d:Save file option +//l:control_pane_t1/opt7 +//w: +//r: 3.1 +// +#define qtn_rd_softkey_save "Save" + +//d:Failed remote save error note +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_query_file_save_fail "File %0U cannot be saved to %1U. File needs to be saved manually." + +//d:Wait note for file transfer +//l:popup_note_wait_window +//w: +//r:3.1 +// +#define qtn_rd_wait_transferring "Transferring..." + +//d:Wait note for connecting to a remote drive +//l:popup_note_wait_window +//w: +//r:3.1 +// +#define qtn_rd_wait_connecting "Connecting..." + +//d:Retry option when connecting failed +//l:control_pane_t1/opt7 +//w: +//r:3.1 +// +#define qtn_rd_softkey_retry "Retry" + +//d:Remote drive unavailable error note +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_conf_drive_unavailable "%U unavailable" + +//d:Remote drive address not found error note +//l:popup_note_window +//w: +//r:3.1 +// +#define qtn_rd_error_faulty_address "%U address not found. Check settings." + +//d:Warning dialog about open files when disconnecting +//l:popup_note_window +//w: +//r:3.2 +// +#define qtn_rd_conf_query_open_files_disconnect "Files have been opened from this location. Changes made to the files are discarded if disconnecting before closing them. Continue?" + +//d:Information note +//l:popup_note_window +//d:There has to be '\' character before '"' character. +//d: This combination is shown as '"' character +//w: +//r:3.2 +#define qtn_rd_infonote_missing_prefix "Add prefix to drive address. For example \"https://\",\"http://\" or \"upnp://\"." + +//d:query +//l:popup_note_window +//w: +//r:3.2 +#define qtn_rd_conf_query_send_auth_info "Send remote drive user name and password?" + +//d:Information note +//l:popup_note_window +//w: +//r:3.2 +#define qtn_rd_err_no_network_cover "Unable to connect. No network coverage." + +//dError note +//l:popup_note_window +//w: +//r:3.2 +#define qtn_rd_all_serv_failed "Saving failed." + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwattributerefreshingstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwattributerefreshingstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,32 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: States that need to refresh file or directory attributes +* +*/ + + +#include "rsfwattributerefreshingstatemachine.h" +#include "rsfwdirentattr.h" + +// ---------------------------------------------------------------------------- +// CRsfwAttributeRefreshingStateMachine::~CRsfwAttributeRefreshingStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwAttributeRefreshingStateMachine::~CRsfwAttributeRefreshingStateMachine() + { + delete iDirEntAttr; + delete iDirEntAttrOld; + } + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwclosestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwclosestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,317 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for closing a file +* +*/ + +#include + +#include "rsfwclosestatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwfileengine.h" +#include "rsfwrfeserver.h" +#include "rsfwwaitnotemanager.h" +#include "rsfwlockmanager.h" +#include "mdebug.h" + + +// CRsfwCloseStateMachine + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::CRsfwCloseStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::CRsfwCloseStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::~CRsfwCloseStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::~CRsfwCloseStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::TState* CRsfwCloseStateMachine::CompleteRequestL(TInt aError) + { + DEBUGSTRING(("CRsfwCloseStateMachine::CompleteRequestL::ErrorL %d", aError)); + + // decrease count of files opened for writing + Node()->iFileTable->UpdateOpenFileCount(-1); + + if (iFlags != ECloseLastFlushFailed) + { + // file was closed successfully (not saved locally and deleted from filetable) + DEBUGSTRING(("file was closed successfully (not saved locally and deleted from filetable)")); + + // If we just wrote the file to the server set attributes from the cache + // file's attributes. + if (Node()->CacheFileName() && Node()->IsOpenedForWriting()) + { + Node()->SetCached(ETrue); + FileEngine()->SetupAttributes(*Node()); + } + + // Add new cached and closed file to LRU cache managemet list. + if ((Node()->Type() == KNodeTypeFile) && + (Node()->iCachedSize >0)) + { + Volumes()->AddToLRUPriorityListL(Node(), Node()->CachePriority()); + } + + // If no content is in the cache then add closed file to the metadata LRU list. + if ((Node()->Type() == KNodeTypeFile) && + (Node()->iCachedSize == 0)) + { + Volumes()->AddToMetadataLRUPriorityListL(Node(), Node()->CachePriority()); + } + + // uncommitted modifications have been resolved + Node()->SetOpenedForWriting(EFalse); + } + else + { + // remove the file from filetable as it was saved locally as a result of error + // (either ECloseLastFlushFailed was set or we attempted to write the data and + // there was error) + Node()->iFileTable->RemoveL(Node()); + delete Node(); + } + + CompleteAndDestroyState()->SetErrorCode(aError); + // remove the wait note + DeleteWaitNoteL(ETrue); + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::ErrorOnStateEntry +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::TState* CRsfwCloseStateMachine::ErrorOnStateEntry(TInt aError) + { + DEBUGSTRING16(("CRsfwCloseStateMachine::ErrorOnStateEntry %d", aError)); + + if (aError == KErrNotFound) + { + // the node was not found, do not try to clos it + return CRsfwRfeStateMachine::ErrorOnStateEntry(aError); + } + else + { + // don't show 'save as' note if transfer was cancelled explicitily by the user + if (iFlags == ECloseLastFlushFailed && !Node()->IsCancelled()) + { + // modified file, last flush failed so let user to save the file locally + return new CRsfwCloseStateMachine::TSaveLocallyState(this); + } + else + { + // in any case, we mark this file as closed + CRsfwCloseStateMachine::TState* nextstate = NULL; + TRAP_IGNORE(nextstate = CompleteRequestL(KErrNone)); + return nextstate; + } + } + + } + +// Release lock + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TReleaseLockState::TReleaseLockState +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine:: +TReleaseLockState::TReleaseLockState(CRsfwCloseStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TReleaseLockState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwCloseStateMachine::TReleaseLockState::EnterL() + { + DEBUGSTRING(("CRsfwCloseStateMachine::TReleaseLockState::EnterL")); + + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + DEBUGSTRING16(("closing fid %d (%S)", + iOperation->Node()->Fid().iNodeId, + iOperation->Node()->Name())); + + + if (iOperation->Node()->Type() != KNodeTypeFile) + { + // Sanity + DEBUGSTRING(("closing something else than a file!!!")); + User::Leave(KErrArgument); + } + + TRfeCloseInArgs* inArgs = + static_cast(iOperation->iInArgs); + + DEBUGSTRING(("flags %d", inArgs->iFlags)); + + iOperation->iFlags = inArgs->iFlags; + + if (iOperation->Node()->IsLocked()) + { + // always attempt to unlock the file if it was locked + iOperation->FileEngine()->LockManager()->ReleaseLockL(iOperation->Node(), + iOperation); + } + else + { + // no need to release the lock + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TReleaseLockState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::TState* CRsfwCloseStateMachine::TReleaseLockState::CompleteL() + { + DEBUGSTRING(("CRsfwCloseStateMachine::TReleaseLockState::CompleteL")); + iOperation->Node()->RemoveLocked(); + + // don't show 'save as' note if transfer was cancelled explicitily by the user + if (iOperation->iFlags == ECloseLastFlushFailed && !iOperation->Node()->IsCancelled()) + { + // modified file, last flush failed so let user to save the file locally + return new CRsfwCloseStateMachine::TSaveLocallyState(iOperation); + } + else + { + return iOperation->CompleteRequestL(KErrNone); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TReleaseLockState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::TState* +CRsfwCloseStateMachine::TReleaseLockState::ErrorL(TInt /* aCode */) + { + DEBUGSTRING(("CRsfwCloseStateMachine::TReleaseLockState::ErrorL")); + // Probably not really an error as according to the RFC locks + // can disappear anytime anyway, lets just run the logic in CompleteL + return CompleteL(); + } + + +// save as + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TSaveLocallyState::TSaveLocallyState +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine:: +TSaveLocallyState::TSaveLocallyState(CRsfwCloseStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TSaveLocallyState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwCloseStateMachine::TSaveLocallyState::EnterL() + { + DEBUGSTRING(("CRsfwCloseStateMachine::TSaveLocallyState::EnterL")); + TEntry fEntry; + CRsfwRfeServer::Env()->iFs.Entry((*(iOperation->Node()->CacheFileName())), fEntry); + iFileSizeString.Num(fEntry.iSize); + TPtrC cacheDriveLetter = iOperation->Node()->CacheFileName()->Left(1); + + iSaveToRequest.iMethod = TRsfwNotPluginRequest::ESaveToDlg; + iSaveToRequest.iDriveName = iOperation->Node()->iFileTable->Volume()->MountInfo() + ->iMountConfig.iName; + + iSaveToRequest.iFileName = *(iOperation->Node()->Name()); + iSaveToRequest.iCacheDrive = cacheDriveLetter; + iSaveToRequest.iFileSize = iFileSizeString; + + + iOperation->Volumes()->WaitNoteManager()->SetSaveToDialogRequestL(iSaveToRequest); + + iOperation->Volumes()->WaitNoteManager() + ->StartWaitNoteL(ERemoteSaveToLocal, iOperation); + } + + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TSaveLocallyState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::TState* CRsfwCloseStateMachine::TSaveLocallyState::CompleteL() + { + DEBUGSTRING(("CRsfwCloseStateMachine::TSaveLocallyState::CompleteL")); + TInt err; + + // move the file from cache to the new location + HBufC* newName = HBufC::NewMaxLC(KMaxPath); + TPtr pathPtr = newName->Des(); + pathPtr = iSaveToRequest.iFileName; + CFileMan* fman = CFileMan::NewL(CRsfwRfeServer::Env()->iFs); + // we assume that this is local-to-local move, and can be synch. call + err = fman->Move((*(iOperation->Node()->CacheFileName())), + pathPtr, CFileMan::EOverWrite); + delete fman; + if (err == KErrNone) + { + iOperation->Volumes()->WaitNoteManager()->ShowFileSavedToDialogL(pathPtr); + } + else + { + iOperation->Volumes()->WaitNoteManager()->ShowFailedSaveNoteL(); + } + + CleanupStack::PopAndDestroy(newName); + + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwCloseStateMachine::TSaveLocallyState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwCloseStateMachine::TState* +CRsfwCloseStateMachine::TSaveLocallyState::ErrorL(TInt aCode) + { + DEBUGSTRING(("CRsfwCloseStateMachine::TSaveLocallyState::ErrorL %d", aCode)); + return iOperation->CompleteRequestL(KErrNone); + } + + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwconnectionmanager.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwconnectionmanager.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,424 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Connection manager + * +*/ + + +// Copyright (C) 2002-2004 Nokia + +// INCLUDE FILES +#include +#include +#include "rsfwconnectionmanager.h" +#include "rsfwcommon.h" +#include "mdebug.h" + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwConnectionManager* CRsfwConnectionManager::NewL( + MRsfwConnectionObserver* aConnectionObserver) + { + DEBUGSTRING(("CRsfwConnectionManager::NewL")); + CRsfwConnectionManager* self = new (ELeave) CRsfwConnectionManager(); + CleanupStack::PushL(self); + self->ConstructL(aConnectionObserver); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::CRsfwConnectionManager +// ---------------------------------------------------------------------------- +// +CRsfwConnectionManager::CRsfwConnectionManager() +: CActive( EPriorityStandard ) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwConnectionManager::ConstructL( + MRsfwConnectionObserver* aConnectionObserver) + { + DEBUGSTRING(("CRsfwConnectionManager::ConstructL")); + iConnectionObserver = aConnectionObserver; + // Connect to the socket server + User::LeaveIfError(iSocketServ.Connect()); + // Add this to active scheduler + CActiveScheduler::Add( this ); + + iSuspensionTimer = CPeriodic::NewL(CActive::EPriorityLow); + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::~CRsfwConnectionManager +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwConnectionManager::~CRsfwConnectionManager() + { + DEBUGSTRING(("CRsfwConnectionManager::~CRsfwConnectionManager")); + Cancel(); + iConnection.Close(); + iSocketServ.Close(); + iIaps.Close(); + + StopSuspensionTimer(); + delete iSuspensionTimer; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::UseIapL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwConnectionManager::UseIapL(const TDesC& aIap) + { + // aIap may contain an IAP name or an IAP Id (or '?'/'*') + DEBUGSTRING(("IAP: %S", &aIap)); + + // Determine IAP selection policy + // By default, ask the user + iIapSelection = ERsfwIapSelectionAskUser; + if (aIap.CompareF(KIapDefaultPreferences) == 0) + { + // Use static CommDB preferences + iIapSelection = ERsfwIapSelectionUseDefaultPreferences; + } + else if (aIap.CompareF(KIapAskUser) == 0) + { + // Ask the user + } + else + { + // Build a table of acceptable IAPs. + // Now the table only contains one entry + TIapInfo iapInfo; + iapInfo.iId = 0; + iapInfo.iName.SetLength(0); + // try to retrieve ID or name based on aIap + TLex iapLex(aIap); + TInt err = iapLex.Val(iapInfo.iId, EDecimal); + if (err != KErrNone) + { + // The IAP name was given + iapInfo.iName.Copy(aIap); + } + if (LoadIapInfoL(iapInfo) == KErrNone) + { + iIaps.Append(iapInfo); + iIapSelection = ERsfwIapSelectionExplicit; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::GetConnection +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwConnectionManager::GetConnection(RSocketServ*& aSocketServ, + RConnection*& aConnection) + { + DEBUGSTRING(("Get connection")); + TInt err = iConnection.Open(iSocketServ); + if (err == KErrNone) + { + TUint32 iapId = 0; + TCommDbDialogPref dialogPreference = ECommDbDialogPrefDoNotPrompt; + switch (iIapSelection) + { + case ERsfwIapSelectionAskUser: + iapId = 0; + dialogPreference = ECommDbDialogPrefPrompt; + break; + + case ERsfwIapSelectionUseDefaultPreferences: + break; + + case ERsfwIapSelectionExplicit: + iapId = iIaps[0].iId; + dialogPreference = ECommDbDialogPrefDoNotPrompt; + break; + + default: + break; + } + + err = StartConnection(iapId, dialogPreference); + if (err == KErrNone) + { + aSocketServ = &iSocketServ; + aConnection = &iConnection; + } + } + DEBUGSTRING(("Get connection returning %d", err)); + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::LoadIapInfoL +// ---------------------------------------------------------------------------- +// +TInt CRsfwConnectionManager::LoadIapInfoL(TIapInfo& aIapInfo) + { + DEBUGSTRING(("CRsfwConnectionManager::LoadIapInfoL")); + // Fetch CommDB data for a matching IAP Id or IAP Name + CCommsDatabase* commsDb = CCommsDatabase::NewL(); + CleanupStack::PushL(commsDb); + CCommsDbTableView* table; + if (aIapInfo.iId) + { + table = commsDb->OpenViewMatchingUintLC(TPtrC(IAP), + TPtrC(COMMDB_ID), + aIapInfo.iId); + } + else + { + table = commsDb->OpenViewMatchingTextLC(TPtrC(IAP), + TPtrC(COMMDB_NAME), + aIapInfo.iName); + } + TInt err = table->GotoFirstRecord(); + if (err != KErrNone) + { + DEBUGSTRING16(("Could not find IAP '%S' (id=%d)!", + &aIapInfo.iName, + aIapInfo.iId)); + CleanupStack::PopAndDestroy(2, commsDb); // table, commsDb + return KErrNotFound; + } + + // Read IAP information + table->ReadUintL(TPtrC(COMMDB_ID), aIapInfo.iId); + table->ReadTextL(TPtrC(COMMDB_NAME), aIapInfo.iName); + table->ReadTextL(TPtrC(IAP_BEARER_TYPE), aIapInfo.iBearerType); + TBuf serviceType; + table->ReadTextL(TPtrC(IAP_SERVICE_TYPE), serviceType); + TUint32 service; + table->ReadUintL(TPtrC(IAP_SERVICE), service); + // Find out the network + TUint32 networkId; + table->ReadUintL(TPtrC(IAP_NETWORK), networkId); + CleanupStack::PopAndDestroy(table); // table + + table = commsDb->OpenViewMatchingUintLC(TPtrC(NETWORK), + TPtrC(COMMDB_ID), + networkId); + err = table->GotoFirstRecord(); + if (err == KErrNone) + { + table->ReadTextL(TPtrC(COMMDB_NAME), aIapInfo.iNetworkName); + } + else + { + DEBUGSTRING(("Could not find network for the IAP!")); + } + CleanupStack::PopAndDestroy(table); // table + + aIapInfo.iServiceName.Zero(); + aIapInfo.iSsId.Zero(); + + CleanupStack::PopAndDestroy(commsDb); // commsDb + + + aIapInfo.iBearerQuality = ERsfwConnectionQualityStrong; + + DEBUGSTRING16(("found IAP %S: id=%d, servicetype=%S, service=%d, network=%S, servicename=%S, ssid=%S, bearer=%S, quality=%d", + &aIapInfo.iName, + aIapInfo.iId, + &serviceType, + service, + &aIapInfo.iNetworkName, + &aIapInfo.iServiceName, + &aIapInfo.iSsId, + &aIapInfo.iBearerType, + aIapInfo.iBearerQuality)); + + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::StartConnection +// ---------------------------------------------------------------------------- +// +TInt CRsfwConnectionManager::StartConnection(TUint32 aIapId, + TCommDbDialogPref aDialogPreference) + { + DEBUGSTRING(("CRsfwConnectionManager::StartConnection with id %d", &aIapId)); + TCommDbConnPref connectionPref; + connectionPref.SetIapId(aIapId); + connectionPref.SetDialogPreference(aDialogPreference); + connectionPref.SetDirection(ECommDbConnectionDirectionOutgoing); + DEBUGSTRING(("Starting connection to IAP %d with pref %d", + aIapId, + aDialogPreference)); + TInt err = iConnection.Start(connectionPref); + DEBUGSTRING(("Connection starting returned %d", err)); + // start observing the connection, any events will occur in RunL() function + if ( !IsActive() ) + { + iConnection.ProgressNotification(iProgress, iStatus); + SetActive(); + } + else + { + DEBUGSTRING(("StartConnection called twice!")); + Cancel(); + + DEBUGSTRING(("StartConnection Cancel!")); + + iConnection.ProgressNotification(iProgress, iStatus); + DEBUGSTRING(("CRsfwConnectionManager iConnection.ProgressNotification!")); + + SetActive(); + + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::HandleDisconnectionEventL +// ---------------------------------------------------------------------------- +// +void CRsfwConnectionManager::HandleDisconnectionEventL() + { + DEBUGSTRING(("CRsfwConnectionManager::HandleDisconnectionEventL")); + if (iConnectionObserver) + { + iConnectionObserver->HandleConnectionEventL( + ERsfwConnectionObserverEventConnectionDisconnected, + NULL); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::StartSuspensionTimer +// ---------------------------------------------------------------------------- +// +void CRsfwConnectionManager::StartSuspensionTimer() + { + DEBUGSTRING(("CRsfwConnectionManager::StartSuspensionTimer")); + if (iSuspensionTimer) + { + const TInt KRsfwGPRSSuspensionTimeout = 60 * 1000000; // 60 sec + + DEBUGSTRING(("GPRS suspension timer started (%d us)", + KRsfwGPRSSuspensionTimeout)); + iSuspensionTimer->Cancel(); + TCallBack callBack(CRsfwConnectionManager::SuspensionTimerExpiredL, this); + iSuspensionTimer->Start(KRsfwGPRSSuspensionTimeout, + KRsfwGPRSSuspensionTimeout, + callBack); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::StopSuspensionTimer +// ---------------------------------------------------------------------------- +// +void CRsfwConnectionManager::StopSuspensionTimer() + { + DEBUGSTRING(("CRsfwConnectionManager::StopSuspensionTimer")); + if (iSuspensionTimer) + { + DEBUGSTRING(("GPRS suspension timer stopped")); + iSuspensionTimer->Cancel(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::SuspensionTimerExpired +// ---------------------------------------------------------------------------- +// +TInt CRsfwConnectionManager::SuspensionTimerExpiredL(TAny* aArg) + { + DEBUGSTRING(("GPRS suspension timer expired")); + CRsfwConnectionManager* connMan = static_cast(aArg); + connMan->StopSuspensionTimer(); + connMan->HandleDisconnectionEventL(); + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::RunL +// ---------------------------------------------------------------------------- +// +void CRsfwConnectionManager::RunL() + { + TInt status = iStatus.Int(); + DEBUGSTRING(("CRsfwConnectionManager::RunL %d", &status)); + TInt stage = iProgress().iStage; + TInt error = iProgress().iError; + DEBUGSTRING(("ConnectionManager::RunL - status: %d, stage: %d, error: %d", status, stage, error)); + + if ( error == KErrConnectionTerminated || error == KErrDisconnected + || stage == KLinkLayerClosed || stage == KConnectionClosed ) + { + // KErrDisconnected occurs if WLAN goes out of range + // KErrConnectionTerminated occurs if user cancels connection from "Active connections" menu + // stage values KLinkLayerClosed & KConnectionClosed should be generated by GPRS + // (however GPRS usually generates KDataTransferTemporarilyBlocked event) + HandleDisconnectionEventL(); + } + else if ( stage == KDataTransferTemporarilyBlocked ) + { + // KDataTransferTemporarilyBlocked means GPRS 'suspend' event + // start timer, when it expires we will disconnect + StartSuspensionTimer(); + } + else if ( stage == KLinkLayerOpen ) + { + // KLinkLayerOpen may mean GPRS 'resume' event + StopSuspensionTimer(); + } + else + { + // ignore the event + } + + // request new events if necessary + iConnection.ProgressNotification(iProgress, iStatus, KConnProgressDefault); + SetActive(); + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::RunError +// ---------------------------------------------------------------------------- +// +#ifdef _DEBUG +TInt CRsfwConnectionManager::RunError(TInt aError) +#else +TInt CRsfwConnectionManager::RunError(TInt /*aError*/) +#endif + { + DEBUGSTRING(("ConnectionManager::RunErrorL - error: %d", aError)); + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwConnectionManager::DoCancel +// ---------------------------------------------------------------------------- +// +void CRsfwConnectionManager::DoCancel() + { + DEBUGSTRING(("CRsfwConnectionManager::::DoCancel()")); + //cancel request issued by ProgressNotification() + iConnection.CancelProgressNotification(); + } +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwcontrol.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwcontrol.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,305 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Client side implementation of Remote Storage FW API + * : for control functions such as mounting and unmounting. + * +*/ + + +// INCLUDE FILES +#include "rsfwcommon.h" +#include "rsfwcontrol.h" + + +// CONSTANTS + +#ifdef __WINS__ +const TUint KServerMinHeapSize = 0x1000; // 4K +const TUint KServerMaxHeapSize = 0x100000; // 64K +#endif + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// RRsfwControl::RRsfwControl +// C++ default constructor can NOT contain any code, that +// might leave. +// ---------------------------------------------------------------------------- +// +EXPORT_C RRsfwControl::RRsfwControl() : RSessionBase() + { + } + +// ---------------------------------------------------------------------------- +// RRRsfwControl::Connect +// Connects to the framework by starting the server if neccessary and creating +// a session. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::Connect() + { + const TInt KTryCount = 3; + + TInt err; + TBool retry; + TInt i = KTryCount; + do + { + err = StartServer(KRfeServerName); + if (err == KErrNone) + { + err = CreateSession(KRfeServerName, + Version(), + KDefaultMessageSlots); + } + retry = ((err == KErrNotFound) || (err == KErrServerTerminated)); + } while (retry && (++i <= KTryCount)); + + return err; + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::Version +// Returns the version of Remote File Engine +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TVersion RRsfwControl::Version() + { + return(TVersion(KRfeMajorVersionNumber, + KRfeMinorVersionNumber, + KRfeBuildVersionNumber)); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::Mount +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::Mount(TInt aDriveLetter) + { + TIpcArgs args; + args.Set(0, aDriveLetter); + return SendRequest(EMountByDriveLetter, args); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::Mount +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::Mount(const TRsfwMountConfig& aMountConfig) + { + TPckg pckgMountConfig(aMountConfig); + return SendRequest(EMount, TIpcArgs(&pckgMountConfig)); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::Mount +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::MountBlind(TInt aDriveLetter) + { + iArgs.Set(0, aDriveLetter); + return Send(EMountByDriveLetter, iArgs); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::Mount +// ---------------------------------------------------------------------------- +// +EXPORT_C void RRsfwControl::Mount(const TRsfwMountConfig& aMountConfig, + TRequestStatus& aStatus) + { + aStatus = KRequestPending; + iPckgBufMountConfig = aMountConfig; + SendRequest(EMount, TIpcArgs(&iPckgBufMountConfig), aStatus); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::DismountByVolumeId +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::DismountByVolumeId(TInt aVolumeId) + { + return SendRequest(EDismountByVolumeId, TIpcArgs(aVolumeId)); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::DismountByDriveLetter +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::DismountByDriveLetter(TChar aDriveLetter) + { + aDriveLetter.UpperCase(); + return SendRequest(EDismountByDriveLetter, TIpcArgs(aDriveLetter)); + } + + +// ---------------------------------------------------------------------------- +// RRsfwControl::GetMountInfo +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::GetMountInfo(const TChar& aDriveLetter, + TRsfwMountInfo& aMountInfo) + { + TPckg pckgMountInfo(aMountInfo); + SendRequest(EGetMountInfo, TIpcArgs(aDriveLetter, &pckgMountInfo)); + TInt err; + if (aMountInfo.iMountConfig.iUri.Length()) + { + err = KErrNone; + } + else + { + err = KErrNotFound; + } + return err; + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::SetMountConnectionState +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::SetMountConnectionState(const TChar& aDriveLetter, + TUint aState) + { + // send a blind request + return Send(ESetMountConnectionState, + TIpcArgs(aDriveLetter, + aState)); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::RefreshDirectoryL +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::RefreshDirectory(const TDesC& aPath) + { + return(SendRequest(EDirRefresh, TIpcArgs(&aPath))); + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::CancelAllRemoteTransfers +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwControl::CancelRemoteTransfer(const TDesC& aFile) + { + // server must be running in order to successfully cancel anything + return(SendReceive(ECancelAll, TIpcArgs(&aFile))); + } + + +// ---------------------------------------------------------------------------- +// RRsfwControl::StartServer +// Starts the Remote File Engine if it is not running, uses semaphore to +// synchronize startup. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +TInt RRsfwControl::StartServer(const TDesC& aServerName) + { + TInt err; + + TFindServer findRfe(aServerName); + TFullName name; + + err = findRfe.Next(name); + if (err == KErrNone) + { + // Server already running + return KErrNone; + } + + RSemaphore semaphore; + err = semaphore.CreateGlobal(KRfeSemaphoreName, 0); + if (err != KErrNone) + { + return err; + } + + err = CreateServerProcess(aServerName); + if (err != KErrNone) + { + semaphore.Close(); + return err; + } + semaphore.Wait(); + semaphore.Close(); + + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// RRRsfwControl::CreateServerProcess +// Starts the Remote File Engine using name to find the binary +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +TInt RRsfwControl::CreateServerProcess(const TDesC& aServerName) + { + TInt err; + + // just load anything that matches with the name + const TUidType serverUid(KNullUid, KNullUid, KNullUid); + + RProcess server; + + _LIT(KStartCommand, ""); + err = server.Create(aServerName, KStartCommand, serverUid); + if (err != KErrNone) + { + return err; + } + server.Resume(); + server.Close(); + + return KErrNone; + } + + + +// ---------------------------------------------------------------------------- +// RRsfwControl::SendRequest +// ---------------------------------------------------------------------------- +// +TInt RRsfwControl::SendRequest(TInt aOpCode, TIpcArgs aArgs) + { + TInt err = SendReceive(aOpCode, aArgs); + if (err == KErrServerTerminated) + { + // Close handle before opening new, otherwise client leaks old handle and panics CONE 36 + Close(); + + // try to restart the server + err = Connect(); + if (err == KErrNone) + { + err = SendReceive(aOpCode, aArgs); + } + } + return err; + } + +// ---------------------------------------------------------------------------- +// RRsfwControl::SendRequest +// ---------------------------------------------------------------------------- +// +void RRsfwControl::SendRequest(TInt aOpCode, + TIpcArgs aArgs, + TRequestStatus& aStatus) + { + SendReceive(aOpCode, aArgs, aStatus); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwcreatefilestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwcreatefilestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,358 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for creating files +* +*/ + + +#include "rsfwcreatefilestatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwinterface.h" +#include "rsfwfileengine.h" +#include "rsfwlockmanager.h" +#include "mdebug.h" +#include "rsfwdirentattr.h" +#include "rsfwvolumetable.h" + + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::CRsfwCreateFileStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::CRsfwCreateFileStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::~CRsfwCreateFileStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::~CRsfwCreateFileStateMachine() + { + delete iDirEntAttr; + delete iLockToken; + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwCreateFileStateMachine::CompleteRequestL(TInt aError) + { + TRfeCreateOutArgs* outArgs = + static_cast(iOutArgs); + if (!aError) + { + // Set the return values for the create call + TFid* kidFidp = &(outArgs->iFid); + TDirEntAttr* oAttrp = &(outArgs->iAttr); + *kidFidp = iKidFep->Fid(); + iKidFep->GetAttributes(*oAttrp); + } + + if (iKidCreated && aError) + { + delete iKidFep; + iKidFep = NULL; + } + + // it may happen by chance that the new name is equal to iLastFailedLookup value + FileEngine()->ResetFailedLookup(); + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// Check if exists + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCheckIfExistsState::TCheckIfExistsState +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine:: +TCheckIfExistsState::TCheckIfExistsState(CRsfwCreateFileStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCheckIfExistsState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwCreateFileStateMachine::TCheckIfExistsState::EnterL() + { + DEBUGSTRING(("CRsfwCreateFileStateMachine::TCheckIfExistsState::EnterL()")); + TRfeCreateInArgs* inArgs = + static_cast(iOperation->iInArgs); + TPtrC kidName(inArgs->iEntry.iName); + iExclp = inArgs->iExcl; + + // used to pass the file open mode + // could be something simpler, e.g. only one int + iOperation->iFlags = inArgs->iEntry.iAttr.iAtt; + + // Get the parent to which we are creating this + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + + DEBUGSTRING16(("creating file '%S' in fid %d", + &kidName, + iOperation->Node()->Fid().iNodeId)); + + // Do we know about the kid yet? + iOperation->iKidFep = iOperation->Node()->FindKidByName(kidName); + if (!iOperation->iKidFep) + { + // This is either a completely new file, or a file that we + // have not yet created a file entry for. + + if (! iOperation->Volumes()->EnsureMetadataCanBeAddedL(iOperation->Node())) + { + User::Leave(KErrNoMemory); + } + iOperation->iKidFep = CRsfwFileEntry::NewL(kidName, iOperation->Node()); + iOperation->iKidCreated = ETrue; + iOperation->iKidFep->SetNewlyCreated(); + } + + if (iOperation->FileEngine()->Disconnected()) + { + if (iOperation->iKidFep->Type() != KNodeTypeUnknown) + { + // "file exists" + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + else + { + iOperation->HandleRemoteAccessResponse(0, KErrNotFound); + } + } + else + { + iOperation->FileEngine()->GetAttributesL(*iOperation->iKidFep, + iOperation->iDirEntAttr, + KNodeTypeFile, + iOperation); + } + } + + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCheckIfExistsState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::TState* +CRsfwCreateFileStateMachine::TCheckIfExistsState::CompleteL() + { + DEBUGSTRING(("CRsfwCreateFileStateMachine::TCheckIfExistsState::CompleteL()")); + if (iExclp) + { + DEBUGSTRING(("kid exists!")); + return iOperation->CompleteRequestL(KErrAlreadyExists); + } + else + { // file with the same name exists, but exclusive is false + return new CRsfwCreateFileStateMachine::TCreateNodeState(iOperation); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCheckIfExistsState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::TState* +CRsfwCreateFileStateMachine::TCheckIfExistsState::ErrorL(TInt aCode) + { + DEBUGSTRING16(("CRsfwCreateFileStateMachine::TCheckIfExistsState::ErrorL error=%d", aCode)); + return new CRsfwCreateFileStateMachine::TCreateNodeState(iOperation); + } + +// create node + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCreateNodeState::TCreateNodeState +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine:: +TCreateNodeState::TCreateNodeState(CRsfwCreateFileStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCreateNodeState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwCreateFileStateMachine::TCreateNodeState::EnterL() + { + DEBUGSTRING(("CRsfwCreateFileStateMachine::TCreateNodeState::EnterL()")); + if (iOperation->iKidCreated) + { + iOperation->iKidFep->SetType(KNodeTypeFile); + } + + if (!iOperation->FileEngine()->WriteDisconnected()) + { + // Create the file + HBufC16* kidPath = + iOperation->FileEngine()->FullNameLC(*iOperation->iKidFep); + // iDirEntAttr exists, we know we are overwriting + // pass this info to the access module (needed e.g. by UPnP) + iOperation-> + FileEngine()-> + RemoteAccessL()->CreateFileL(*kidPath, + (iOperation->iDirEntAttr != NULL), + iOperation); + CleanupStack::PopAndDestroy(kidPath); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCreateNodeState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::TState* +CRsfwCreateFileStateMachine::TCreateNodeState::CompleteL() + { + DEBUGSTRING(("CRsfwCreateFileStateMachine::TCreateNodeState::CompleteL()")); + return new CRsfwCreateFileStateMachine::TAcquireLockState(iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TCreateNodeState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::TState* +CRsfwCreateFileStateMachine::TCreateNodeState::ErrorL(TInt aCode) + { + DEBUGSTRING16(("CRsfwCreateFileStateMachine::TCreateNodeState::ErrorL error=%d", aCode)); + DEBUGSTRING(("remote create failed!")); + return iOperation->CompleteRequestL(aCode); + } + +// Acquire lock + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TAcquireLockState::TAcquireLockState +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine:: +TAcquireLockState::TAcquireLockState(CRsfwCreateFileStateMachine* aParent) + { + iOperation = aParent; + iRequestedLock = EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TAcquireLockState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwCreateFileStateMachine::TAcquireLockState::EnterL() + { + DEBUGSTRING(("CRsfwCreateFileStateMachine::TAcquireLockState::EnterL()")); + if (!iOperation->FileEngine()->WriteDisconnected()) + { + // There are two state machines currently, + // which may take a lock for a file based on the mode, + // OpenByPath and this. + // Currently the mode check is different which is not a good + // thing, there is a clear risk of an error where they + // acquire a lock in different situations. + if (!iOperation->iKidFep->IsLocked() + && iOperation->iFlags != KEntryAttReadOnly) + { + iOperation->FileEngine()->LockManager()-> + ObtainLockL(iOperation->iKidFep, + EFileWrite, + iOperation->iLockToken, + iOperation); + iRequestedLock = ETrue; + } + else + { + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + else + { + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TAcquireLockState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::TState* +CRsfwCreateFileStateMachine::TAcquireLockState::CompleteL() + { + DEBUGSTRING(("CRsfwCreateFileStateMachine::TAcquireLockState::CompleteL()")); + if (iRequestedLock) + { + iOperation->iKidFep-> + SetLockedL(iOperation->FileEngine()->LockManager(), + iOperation->iLockToken); + iOperation->iLockToken = NULL; + } + + // Note that the kid has to be attached to the file table + // to get a NodeId before the cache file is created. + if (iOperation->iKidCreated) + { + // Attach a new kid to its parent + iOperation->FileEngine()->iFileTable->AddL(iOperation->iKidFep); + iOperation->Node()->AddKid(*iOperation->iKidFep); + } + + // Create an empty container file locally + iOperation->FileEngine()->CreateContainerFileL(*iOperation->iKidFep); + + iOperation->iKidFep->SetSize(0); + iOperation->iKidFep->SetCachedSize(0); + iOperation->iKidFep->SetCached(ETrue); + iOperation->iKidFep->SetAttribValidationTime(); + + iOperation->FileEngine()->SetupAttributes(*iOperation->iKidFep); + + iOperation->Node()->SetLocallyDirty(); + + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwCreateFileStateMachine::TAcquireLockState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwCreateFileStateMachine::TState* +CRsfwCreateFileStateMachine::TAcquireLockState::ErrorL(TInt aCode) + { + DEBUGSTRING16(("CRsfwCreateFileStateMachine::TAcquireLockState::ErrorL error=%d", aCode)); + if (aCode == KErrNotSupported) + { + iRequestedLock = EFalse; + return this->CompleteL(); + } + else + { + return iOperation->CompleteRequestL(aCode); + } + } + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwdeletestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwdeletestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,268 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Delete a file or directory +* +*/ + + +#include "rsfwdeletestatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwinterface.h" +#include "rsfwfileengine.h" +#include "mdebug.h" +#include "rsfwdirent.h" + + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::CRsfwDeleteStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine::CRsfwDeleteStateMachine(TUint aNodeType) + : iNodeType(aNodeType) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::~CRsfwDeleteStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine::~CRsfwDeleteStateMachine() + { + iDirEnts.ResetAndDestroy(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwDeleteStateMachine::CompleteRequestL(TInt aError) + { + if (iKidPath) + { + delete iKidPath; + iKidPath = NULL; + } + + // If the return code was KErrInUse, the directory we were about to delete + // was not empty, and we couldn't delete it. In this case it has anyway + //been added to the cache (as a side effect), + // so we don't want to delete the fep. + if (aError != KErrInUse && iKidCreated) + { + delete iKidFep; + iKidFep = NULL; + } + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// Check if exists + + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::TCheckIfCanBeDeleted +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine:: +TCheckIfCanBeDeleted::TCheckIfCanBeDeleted(CRsfwDeleteStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::EnterL() + { + // Kidname is in the same place in remove and rmdir structures,,, + TRfeRemoveInArgs* inArgs = + static_cast(iOperation->iInArgs); + TPtrC kidName(inArgs->iName); + + // the parent from which we are removing + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + DEBUGSTRING16(("removing entry '%S' from fid %d", + &kidName, + iOperation->Node()->Fid().iNodeId)); + + // Do we know about the kid yet? + iOperation->iKidFep = iOperation->Node()->FindKidByName(kidName); + if (!iOperation->iKidFep) + { + // Create a temporary file entry for the target + iOperation->iKidFep = CRsfwFileEntry::NewL(kidName, iOperation->Node()); + iOperation->iKidCreated = ETrue; + } + + // Ensure the type matches with the operation (RmDir() or Delete()) + if ((iOperation->iKidFep->Type() != KNodeTypeUnknown) && + (iOperation->iKidFep->Type() != iOperation->iNodeType)) + { + DEBUGSTRING(("object type does not match the parameter type!")); + User::Leave(KErrArgument); + } + + // if the type is unknown, set it from the operation parameter + if (iOperation->iKidFep->Type() == KNodeTypeUnknown) + { + iOperation->iKidFep->SetType(iOperation->iNodeType); + } + + // If it is a directory, check that it is empty + if (!iOperation->FileEngine()->Disconnected() && + iOperation->iNodeType == KNodeTypeDir) + { + TInt zero = 0; + iOperation->FileEngine()-> + FetchAndCacheL(*iOperation->iKidFep, + 0, + &zero, + &iOperation->iDirEnts, + iOperation); + } + else + { + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine::TState* +CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::CompleteL() + { + if ((iOperation->iNodeType == KNodeTypeDir) && + ((iOperation->iDirEnts).Count() > 0)) + { + // Attach the directory itself if it was unknown + if (iOperation->iKidCreated) + { + iOperation->FileEngine()->iFileTable->AddL(iOperation->iKidFep); + iOperation->Node()->AddKid(*iOperation->iKidFep); + } + + // if the directory is not empty we cannot delete it + // however, let's add its entries to the cache + iOperation->FileEngine()->AddToCacheL( + *iOperation->iKidFep, + &iOperation->iDirEnts, + iOperation->FileEngine(), + 0); + + return iOperation->CompleteRequestL(KErrInUse); + } + else + { + return new CRsfwDeleteStateMachine::TDeleteNodeState(iOperation); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine::TState* +CRsfwDeleteStateMachine::TCheckIfCanBeDeleted::ErrorL(TInt aCode) + { + DEBUGSTRING(("kid didn't exist!")); + return iOperation->CompleteRequestL(aCode); + } + +// Remove directory + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TDeleteNodeState::TDeleteNodeState +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine:: +TDeleteNodeState::TDeleteNodeState(CRsfwDeleteStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TDeleteNodeState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwDeleteStateMachine::TDeleteNodeState::EnterL() + { + // Get the path for the actual remove + iOperation->iKidPath = + iOperation->FileEngine()->FullNameL(*iOperation->iKidFep); + if (!iOperation->FileEngine()->Disconnected()) + { + if (iOperation->iNodeType == KNodeTypeDir) + { + iOperation-> + FileEngine()-> + RemoteAccessL()->DeleteDirectoryL(*iOperation->iKidPath, + iOperation); + } + else // KNodeTypFile + { + iOperation-> + FileEngine()-> + RemoteAccessL()->DeleteFileL(*iOperation->iKidPath, + iOperation); + } + } + else + { + // Disconnected + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TDeleteNodeState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine::TState* CRsfwDeleteStateMachine::TDeleteNodeState::CompleteL() + { + if (!iOperation->FileEngine()->Disconnected()) + { + // If the target was already known, remove and destroy it + if (!iOperation->iKidCreated) + { + iOperation->FileEngine()->iFileTable->RemoveL(iOperation->iKidFep); + delete iOperation->iKidFep; + iOperation->iKidFep = NULL; + } + } + + iOperation->Node()->SetLocallyDirty(); + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwDeleteStateMachine::TDeleteNodeState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwDeleteStateMachine::TState* +CRsfwDeleteStateMachine::TDeleteNodeState::ErrorL(TInt aCode) + { + return iOperation->CompleteRequestL(aCode); + } + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwdirent.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwdirent.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,201 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Directory entry container + * +*/ + + +// INCLUDE FILES +#include "rsfwdirent.h" +#include "rsfwdirentattr.h" + +// ======================== CRsfwDirEnt MEMBER FUNCTIONS ========================== + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::NewLC +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEnt* CRsfwDirEnt::NewLC(const TDesC& aName, CRsfwDirEntAttr* aAttr) + { + CRsfwDirEnt* self = new (ELeave) CRsfwDirEnt(); + CleanupStack::PushL(self); + self->ConstructL(aName, aAttr); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::NewLC +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEnt* CRsfwDirEnt::NewLC(const TDesC8& aName, CRsfwDirEntAttr* aAttr) + { + CRsfwDirEnt* self = new (ELeave) CRsfwDirEnt(); + CleanupStack::PushL(self); + self->Construct8L(aName, aAttr); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEnt* CRsfwDirEnt::NewL(const TDesC& aName, CRsfwDirEntAttr* aAttr) + { + CRsfwDirEnt* self = NewLC(aName, aAttr); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEnt* CRsfwDirEnt::NewL(const TDesC8& aName, CRsfwDirEntAttr* aAttr) + { + CRsfwDirEnt* self = NewLC(aName, aAttr); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::CRsfwDirEnt +// ---------------------------------------------------------------------------- +// +CRsfwDirEnt::CRsfwDirEnt() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::~CRsfwDirEnt +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEnt::~CRsfwDirEnt() + { + delete iName; + if (!iNotOwnAttr) + { + delete iAttr; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::Name +// ---------------------------------------------------------------------------- +// +EXPORT_C const HBufC* CRsfwDirEnt::Name() const + { + return iName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::GetName +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEnt::GetName(TDes& aName) const + { + aName.Copy(*iName); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::GetName +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEnt::GetName(TDes8& aName) const + { + aName.Copy(*iName); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::SetNameL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEnt::SetNameL(const TDesC& aName) + { + if (iName) + { + delete iName; + iName = NULL; + } + iName = aName.AllocL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::SetNameL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEnt::SetNameL(const TDesC8& aName) + { + if (iName) + { + delete iName; + iName = NULL; + } + iName = HBufC::NewL(aName.Length()); + TPtr namePtr = iName->Des(); + namePtr.Copy(aName); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::Attr +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEntAttr* CRsfwDirEnt::Attr() const + { + return iAttr; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::ExtractAttr +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEntAttr* CRsfwDirEnt::ExtractAttr() + { + iNotOwnAttr = ETrue; + return iAttr; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEnt::SetAttrL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEnt::SetAttrL(CRsfwDirEntAttr* aAttr) + { + if (iAttr && !iNotOwnAttr) + { + delete iAttr; + } + if (aAttr) + { + iAttr = aAttr; + } + else + { + iAttr = CRsfwDirEntAttr::NewL(); + } + iNotOwnAttr = EFalse; + } + +void CRsfwDirEnt::ConstructL(const TDesC& aName, CRsfwDirEntAttr* aAttr) + { + SetNameL(aName); + SetAttrL(aAttr); + } + +void CRsfwDirEnt::Construct8L(const TDesC8& aName, CRsfwDirEntAttr* aAttr) + { + SetNameL(aName); + SetAttrL(aAttr); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwdirentattr.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwdirentattr.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,238 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Directory entry container + * +*/ + + +// INCLUDE FILES +#include "rsfwdirentattr.h" + +// ====================== CRsfwDirEntAttr MEMBER FUNCTIONS ======================== + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::NewLC +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEntAttr* CRsfwDirEntAttr::NewLC() + { + CRsfwDirEntAttr* self = new (ELeave) CRsfwDirEntAttr(); + CleanupStack::PushL(self); + self->ConstructL(); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEntAttr* CRsfwDirEntAttr::NewL() + { + CRsfwDirEntAttr* self = NewLC(); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::CRsfwDirEntAttr +// ---------------------------------------------------------------------------- +// +CRsfwDirEntAttr::CRsfwDirEntAttr() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwDirEntAttr::ConstructL() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::~CRsfwDirEntAttr +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwDirEntAttr::~CRsfwDirEntAttr() + { + TInt i; + for (i = 0; i < EDirEntAttrStringCount; i ++) + { + delete iStringValues[i]; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::Att +// ---------------------------------------------------------------------------- +// +EXPORT_C TUint CRsfwDirEntAttr::Att() const + { + return iAtt; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetAtt +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetAtt(TUint aAtt) + { + iAtt = aAtt; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetAttFlags +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetAttFlags(TUint aFlags) + { + iAtt |= aFlags; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::ResetAttFlags +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::ResetAttFlags(TUint aFlags) + { + iAtt &= ~aFlags; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::Size +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwDirEntAttr::Size() const + { + return iSize; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetSize +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetSize(TInt aSize) + { + iSize = aSize; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::Modified +// ---------------------------------------------------------------------------- +// +EXPORT_C TTime CRsfwDirEntAttr::Modified() const + { + return iModified; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetModified +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetModified(const TTime& aModified) + { + iModified = aModified; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::Uid +// ---------------------------------------------------------------------------- +// +EXPORT_C const TUid& CRsfwDirEntAttr::Uid() + { + return iUid; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetUid +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetUid(TUid aUid) + { + iUid = aUid; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::StringValue +// ---------------------------------------------------------------------------- +// +EXPORT_C const TDesC8* CRsfwDirEntAttr::StringValue(TInt aIndex) const + { + if ((aIndex < 0) || (aIndex >= EDirEntAttrStringCount)) + { + return NULL; + } + return iStringValues[aIndex]; + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetStringValueL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetStringValueL(TInt aIndex, const TDesC8& aString) + { + if ((aIndex < 0) || (aIndex >= EDirEntAttrStringCount)) + { + User::Leave(KErrArgument); + } + HBufC8** s = &iStringValues[aIndex]; + if (*s) + { + delete *s; + *s = NULL; + } + if (aString.Length()) + { + *s = aString.AllocL(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::MimeType +// ---------------------------------------------------------------------------- +// +EXPORT_C const TDesC8* CRsfwDirEntAttr::MimeType() const + { + return StringValue(EDirEntAttrStringMimeType); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetMimeTypeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetMimeTypeL(const TDesC8& aMimeType) + { + SetStringValueL(EDirEntAttrStringMimeType, aMimeType); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::ETag +// ---------------------------------------------------------------------------- +// +EXPORT_C const TDesC8* CRsfwDirEntAttr::ETag() const + { + return StringValue(EDirEntAttrStringETag); + } + +// ---------------------------------------------------------------------------- +// CRsfwDirEntAttr::SetETagL +// ---------------------------------------------------------------------------- +// +EXPORT_C void CRsfwDirEntAttr::SetETagL(const TDesC8& aETag) + { + SetStringValueL(EDirEntAttrStringETag, aETag); + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwdormantmountloader.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwdormantmountloader.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,145 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: class for restoring dormant mounts asynchronously when server starts +* +*/ + + +// INCLUDE FILES +#include "rsfwdormantmountloader.h" +#include "rsfwvolume.h" +#include "rsfwfileengine.h" +#include "rsfwfiletable.h" +#include "mdebug.h" + + +// ============================ MEMBER FUNCTIONS =============================== + +// ----------------------------------------------------------------------------- +// CRsfwDormantMountLoader::CRsfwDormantMountLoader +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwDormantMountLoader::CRsfwDormantMountLoader() : + CActive( CActive::EPriorityUserInput ) + { + + } + +// ----------------------------------------------------------------------------- +// CRsfwDormantMountLoader::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +void CRsfwDormantMountLoader::ConstructL(CRsfwVolumeTable *aTheTable) + { + DEBUGSTRING(("CRsfwDormantMountLoader::ConstructL")); + iVolumeTable = aTheTable; + CActiveScheduler::Add( this ); + iTimer.CreateLocal(); + iTimer.After(iStatus, KDormantLoaderDelay); + SetActive(); + } + +// ----------------------------------------------------------------------------- +// CRsfwDormantMountLoader::NewL() +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +EXPORT_C CRsfwDormantMountLoader* CRsfwDormantMountLoader::NewL(CRsfwVolumeTable *aTheTable) + { + DEBUGSTRING(("CRsfwDormantMountLoader::NewL")); + CRsfwDormantMountLoader* self = new ( ELeave ) CRsfwDormantMountLoader(); + + CleanupStack::PushL( self ); + self->ConstructL(aTheTable); + CleanupStack::Pop(); + + return self; + } + +// ----------------------------------------------------------------------------- +// Destructor +// ----------------------------------------------------------------------------- +// +EXPORT_C CRsfwDormantMountLoader::~CRsfwDormantMountLoader() + { + DEBUGSTRING16(("CRsfwDormantMountLoader::~CRsfwDormantMountLoader")); + Deque(); + iTimer.Close(); + } + + +// ----------------------------------------------------------------------------- +// CRsfwDormantMountLoader::SaveDirtyFiles +// ----------------------------------------------------------------------------- +// + void CRsfwDormantMountLoader::ResolveDirtyFilesL() + { + DEBUGSTRING16(("CRsfwDormantMountLoader::ResolveDirtyFilesL")); + for (int i = 0; i < KMaxVolumes; i++) + { + if (iVolumeTable) + { + DEBUGSTRING16(("CRsfwDormantMountLoader::ResolveDirtyFilesL drive %d", i)); + CRsfwVolume* volume = iVolumeTable->iVolumes[i]; + if (volume && volume->iFileEngine && volume->iFileEngine->iFileTable) + { + DEBUGSTRING16(("drive contains active remote mount")); + volume->iFileEngine->iFileTable->ResolveDirtyFilesL(); + } + } + } + } + +// ----------------------------------------------------------------------------- +// CRsfwDormantMountLoader::RunL +// Handles an active object’s request completion event. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwDormantMountLoader::RunL() + { + DEBUGSTRING(("CRsfwDormantMountLoader::RunL")); + ResolveDirtyFilesL(); + iVolumeTable->DeleteTheMarker(); + iVolumeTable->iDormantMountRestorePending = EFalse; + // "Simulate" operation completion (which may result in RFE shutdown) + iVolumeTable->OperationCompleted(NULL); + } + +// ---------------------------------------------------------------------------- +// CRsfwDormantMountLoader::RunError +// ---------------------------------------------------------------------------- +// +TInt CRsfwDormantMountLoader::RunError(TInt /*aError*/) + { + DEBUGSTRING16(("CRsfwDormantMountLoader::RunError")); + return KErrNone; + } + +// ----------------------------------------------------------------------------- +// CRsfwDormantMountLoader::DoCancel +// ----------------------------------------------------------------------------- +// +void CRsfwDormantMountLoader::DoCancel() + { + DEBUGSTRING(("CRsfwDormantMountLoader::RunL")); + } + + +// ----------------------------------------------------------------------------- + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwfetchandcachestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwfetchandcachestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,373 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for fetching and caching files and directories +* +*/ + + +#include "rsfwfetchandcachestatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwinterface.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwrfeserver.h" +#include "mdebug.h" +#include "rsfwfileengine.h" +#include "rsfwdirent.h" + +_LIT8(KMimeTypeJpeg, "image/jpeg"); +_LIT8(KMimeTypeMpeg, "audio/mpeg"); + + +// ---------------------------------------------------------------------------- +// CRsfwFetchAndCacheStateMachine::CRsfwFetchAndCacheStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwFetchAndCacheStateMachine::CRsfwFetchAndCacheStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchAndCacheStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwFetchAndCacheStateMachine::CompleteRequestL(TInt aError) + { + if (aError == KUpdateNotRequired) + { // discard + aError = KErrNone; + } + + iDirEnts.ResetAndDestroy(); + // last byte that was actually fetched, may be more than was requested + TRfeFetchOutArgs* outArgs = static_cast(iOutArgs); + outArgs->iLastByte = iLastByte; + CompleteAndDestroyState()->SetErrorCode(aError); + + // remove the fetching directory wait note + if (Node()->Type() == KNodeTypeDir) + { + DeleteWaitNoteL(ETrue); + } + + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchAndCacheStateMachine::TFetchDataState::TFetchDataState +// ---------------------------------------------------------------------------- +// +CRsfwFetchAndCacheStateMachine::TFetchDataState::TFetchDataState( + CRsfwFetchAndCacheStateMachine* aParent) + : iOperation(aParent) + { + + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchAndCacheStateMachine::TFetchDataState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwFetchAndCacheStateMachine::TFetchDataState::EnterL() + { + TRfeFetchInArgs* inArgs = + static_cast(iOperation->iInArgs); + iOperation->iFirstByte = inArgs->iFirstByte; + iOperation->iLastByte = inArgs->iLastByte; + + TInt recognizerLimit; + TInt metadataLimit = 0; + TCachingMode cachingMode; + + if (!(iOperation->Node())) + { + User::Leave(KErrNotFound); + } + + // the cache file should be continuos + // i.e. we always add to the end of the cache + __ASSERT_DEBUG(iOperation->iFirstByte <= iOperation->Node()->iCachedSize, + User::Panic(KRfeServer, ECacheInconsistency)); + + cachingMode = + iOperation->Node()->iFileTable->Volume()->iVolumeTable->iCachingMode; + recognizerLimit = + iOperation-> + Node()->iFileTable->Volume()->iVolumeTable->iRecognizerLimit; + + + // for files, adjust lastByte based on the caching mode... + if (iOperation->Node()->Type() == KNodeTypeFile) + { + switch (cachingMode) + { + case EWholeFileCaching: + if (iOperation->iLastByte < recognizerLimit) + { + // iLastByte = 127 + iOperation->iLastByte = recognizerLimit-1; + } + else + { + // fetch the whole file + iOperation->iLastByte = iOperation->Node()->Size() -1; + } + + break; + case EFullIfa: + if (iOperation->iLastByte < recognizerLimit) + { + // iLastByte = 127 + iOperation->iLastByte = recognizerLimit-1; + } + // othewise no change + break; + case EMetadataIfa: + // set metadataLimit based on the MIME-type + if (iOperation->Node()->MimeType()) + { + if ((*iOperation->Node()->MimeType()).Compare( + KMimeTypeJpeg) == 0) + { + metadataLimit = + iOperation->Node()->iFileTable-> + Volume()->iVolumeTable->iImageJpegLimit; + } + + if ((*iOperation->Node()->MimeType()).Compare( + KMimeTypeMpeg) == 0) + { + metadataLimit = + iOperation->Node()->iFileTable-> + Volume()->iVolumeTable->iAudioMpegLimit; + } + + // set the lastbyte + if (iOperation->iLastByte < recognizerLimit) + { + // iLastByte = 127 + iOperation->iLastByte = recognizerLimit-1; + } + + else if (iOperation->iLastByte < metadataLimit) + { + // Fetch "enough" metadata to avoid + // unnecessary many round-trips... + iOperation->iLastByte = metadataLimit - 1; + } + else if (iOperation->iLastByte >= metadataLimit) + { + iOperation->iLastByte = iOperation->Node()->Size() - 1; + } + } + else + { + // MIME-type not recognized + if (iOperation->iLastByte < recognizerLimit) + { + // iLastByte = 127 + iOperation->iLastByte = recognizerLimit-1; + } + else + { + // fetch the whole file + iOperation->iLastByte = iOperation->Node()->Size() -1; + } + } + } + } + + // Now we know what actually will be fetched, write to debug... + // and put up wait notes. + if (iOperation->Node()->Type() == KNodeTypeFile) + { + + DEBUGSTRING(("FETCH for a file with fid %d, bytes %d - %d", + iOperation->Node()->Fid().iNodeId, + iOperation->iFirstByte, + iOperation->iLastByte)); + + DEBUGSTRING16(("name is '%S", + iOperation->Node()->Name())); + + DEBUGSTRING(("full size is %d, cached size is %d", + iOperation->Node()->Size(), + iOperation->Node()->iCachedSize)); + + + } + else if (iOperation->Node()->Type() == KNodeTypeDir) + { + + DEBUGSTRING(("FETCH for a directory with fid %d, bytes %d - %d", + iOperation->Node()->Fid().iNodeId, + iOperation->iFirstByte, + iOperation->iLastByte)); + + DEBUGSTRING16(("name is '%S", + iOperation->Node()->Name())); + DEBUGSTRING(("full size is %d, cached size is %d", + iOperation->Node()->Size(), + iOperation->Node()->iCachedSize)); + + } + + // whether cached data is used... + // for files: + if (((iOperation->Node()->Type() == KNodeTypeFile) && + (iOperation->FileEngine()->UseCachedData(*iOperation->Node())) && + ((iOperation->iLastByte <= iOperation->Node()->iCachedSize) || + iOperation->Node()->IsFullyCached())) || + + // for directories: + ((iOperation->Node()->Type() == KNodeTypeDir) && + (iOperation->FileEngine()->UseCachedAttributes(*iOperation->Node())) && + (iOperation->FileEngine()->UseCachedData(*iOperation->Node())))) + { + DEBUGSTRING(("using cached data")); + + if (iOperation->Node()->IsLocallyDirty()) + { + DEBUGSTRING16(("directory is locally dirty")); + + // This is a directory which has at least one kid + // that has been cached or flushed since the last opening + // of the directory. + iOperation->FileEngine()->UpdateDirectoryContainerL( + *iOperation->Node()); + } + // if the directory appeared to be childless add it to metadata LRU list + if ( iOperation->Node()->Type() == KNodeTypeDir && + iOperation->Node()->Kids()->Count() == 0 ) + { + iOperation->Volumes()->AddToMetadataLRUPriorityListL(iOperation->Node(), ECachePriorityNormal); + } + + iOperation->iLastByte = iOperation->Node()->Size(); + iOperation->HandleRemoteAccessResponse(0, KUpdateNotRequired); + } + else + { + DEBUGSTRING(("fetching data from server")); + // put up a wait note if getting a directory + // (for files no global wait notes, as that would take a too long time) + if (iOperation->Node()->Type() == KNodeTypeDir) + { + // directory - pu up a 'Retrieving...' global wait note + iOperation->ShowWaitNoteL( ERemoteOpDirDownloading ); + } + + + if (iOperation->iLastByte > iOperation->Node()->Size()) + { // Don't try to read beyond the end of the file... + // Don't try to read beyond the end of the file... + iOperation->iLastByte = iOperation->Node()->Size(); + } + + if (iOperation->iLastByte == 0) + { + iOperation->iLength = 0; + // aLastByte == 0 indicates "no partial caching..." + // i.e. range 0 - 0 + TUint transactionId = + iOperation->FileEngine()-> + FetchAndCacheL(*iOperation->Node(), + 0 , + &(iOperation->iLength), + &(iOperation->iDirEnts), + iOperation); + // transactionId = 0 means syncronous non-cancellable operation + if (transactionId > 0) + { + iOperation->iTransactionId = transactionId; + } + } + else + { + iOperation->iLength = + iOperation->iLastByte - iOperation->Node()->iCachedSize + 1; + // Continue filling the cache-file sequentially + TUint transactionId = + iOperation->FileEngine()-> + FetchAndCacheL(*iOperation->Node(), + iOperation->Node()->iCachedSize, + &(iOperation->iLength), + &(iOperation->iDirEnts), + iOperation); + // transactionId = 0 means syncronous non-cancellable operation + if (transactionId > 0) + { + iOperation->iTransactionId = transactionId; + } + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchAndCacheStateMachine::TFetchDataState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwFetchAndCacheStateMachine::TState* +CRsfwFetchAndCacheStateMachine::TFetchDataState::CompleteL() + { + iOperation->iLastByte = iOperation->FileEngine()->AddToCacheL( + *iOperation->Node(), + &iOperation->iDirEnts, + iOperation->FileEngine(), + iOperation->Node()->iCachedSize + + iOperation->iLength); + + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchAndCacheStateMachine::TFetchDataState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwFetchAndCacheStateMachine::TState* +CRsfwFetchAndCacheStateMachine::TFetchDataState::ErrorL(TInt aCode) + { + // *********** from CRsfwFileEngine::GetDirectoryL() + if (iOperation->Node()->Type() == KNodeTypeDir) + { + TInt err = aCode; + if (aCode == KUpdateNotRequired) + { + err = KErrNone; + } + return iOperation->CompleteRequestL(err); + } + + // file + return iOperation->CompleteRequestL(aCode); + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::ErrorOnStateExit +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwFetchAndCacheStateMachine::ErrorOnStateExit(TInt aError) + { + iDirEnts.ResetAndDestroy(); + // remove the fetching directory wait note + if (Node()->Type() == KNodeTypeDir) + { + TRAP_IGNORE(DeleteWaitNoteL(ETrue)); + } + + + return CRsfwRfeStateMachine::ErrorOnStateExit(aError); + } diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwfetchdatastatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwfetchdatastatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,180 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for fetching data without caching it permanently +* +*/ + + +#include "rsfwfetchdatastatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwinterface.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwrfeserver.h" +#include "mdebug.h" +#include "rsfwfileengine.h" + + +// ---------------------------------------------------------------------------- +// CRsfwFetchDataStateMachine::CRsfwFetchDataStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwFetchDataStateMachine::CRsfwFetchDataStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchDataStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwFetchDataStateMachine::CompleteRequestL(TInt aError) + { + TRfeFetchDataOutArgs* outArgs = + static_cast(iOutArgs); + if(!aError) + { + outArgs->iTempPath.Copy(*iCacheName); + } + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchDataStateMachine::TFetchDataState::TFetchDataState +// ---------------------------------------------------------------------------- +// +CRsfwFetchDataStateMachine::TFetchDataState::TFetchDataState( + CRsfwFetchDataStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchDataStateMachine::TFetchDataState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwFetchDataStateMachine::TFetchDataState::EnterL() + { + TInt err = KErrNone; + TRfeFetchDataInArgs* inArgs = + static_cast(iOperation->iInArgs); + TRfeFetchDataOutArgs* outArgs = + static_cast(iOperation->iOutArgs); + TInt firstByte = inArgs->iFirstByte; + TInt lastByte = inArgs->iLastByte; + + + TCachingMode cachingMode = + iOperation->Node()->iFileTable->Volume()->iVolumeTable->iCachingMode; + + if (iOperation->Node()) + { + DEBUGSTRING(("Fetch without caching fid %d, bytes %d - %d", + iOperation->Node()->Fid().iNodeId, + firstByte, + lastByte)); + + if (cachingMode == EWholeFileCaching) + { + outArgs->iUseTempPath = EFalse; + // in this mode we always fetch the whole file to the normal cache + iOperation->iCacheName = iOperation->Node()->CacheFileName(); + iOperation->iLength = iOperation->Node()->Size() - + iOperation->Node()->iCachedSize + + 1; + TUint transactionId = iOperation-> + FileEngine()->FetchAndCacheL(*iOperation->Node(), + iOperation->Node()->iCachedSize, + &iOperation->iLength, + &(iOperation->iDirEnts), + iOperation); + // transactionId = 0 means syncronous non-cancellable operation + if (transactionId > 0) + { + iOperation->iTransactionId = transactionId; + } + } + else + { + // reset and use the temporary cache file... + outArgs->iUseTempPath = ETrue; + TParse parser; + parser.Set(*iOperation->Node()->CacheFileName(), NULL, NULL); + HBufC* tempPath = HBufC::NewLC(KMaxPath); + TPtr tempfile = tempPath->Des(); + tempfile.Append(parser.DriveAndPath()); + tempfile.Append(KTempFileName); + iOperation->iCacheName = iOperation->Node()->CacheFileName(); + // This much will be added to the cache by this fetch + iOperation->iLength =lastByte - firstByte + 1; + if (!iOperation-> + Node()-> + iFileTable-> + Volume()-> + iVolumeTable->EnsureCacheCanBeAddedL(iOperation->iLength)) + { + User::Leave(KErrDiskFull); + } + RFile f; + err = f.Replace(CRsfwRfeServer::Env()->iFs, + *tempPath, + EFileShareAny | EFileWrite); + if (err == KErrNone) + { + f.Close(); + HBufC* fullName = + iOperation->FileEngine()->FullNameLC(*iOperation->Node()); + TUint transactionId = iOperation->FileEngine()->RemoteAccessL()-> + GetFileL(*fullName, + *tempPath, + firstByte, + &iOperation->iLength, + KRemoteAccessOptionGetToStartOfFile, + iOperation); + // transactionId = 0 means syncronous non-cancellable operation + if (transactionId > 0) + { + iOperation->iTransactionId = transactionId; + } + CleanupStack::PopAndDestroy(fullName); + } + CleanupStack::PopAndDestroy(tempPath); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchDataStateMachine::TFetchDataState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwFetchDataStateMachine::TState* +CRsfwFetchDataStateMachine::TFetchDataState::CompleteL() + { + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwFetchDataStateMachine::TFetchDataState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwFetchDataStateMachine::TState* +CRsfwFetchDataStateMachine::TFetchDataState::ErrorL(TInt aCode) + { + return iOperation->CompleteRequestL(aCode); + } + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwfileengine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwfileengine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1763 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Operation independent remote file handling functions +* +*/ + + +#include +#include + +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwrfestatemachine.h" +#include "rsfwinterface.h" +#include "rsfwcontrol.h" +#include "rsfwremoteaccess.h" +#include "rsfwfileengine.h" +#include "rsfwrfeserver.h" +#include "rsfwlockmanager.h" +#include "mdebug.h" +#include "rsfwdirent.h" +#include "rsfwdirentattr.h" +#include "rsfwinterface.h" + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::NewL +// ---------------------------------------------------------------------------- +// +CRsfwFileEngine* CRsfwFileEngine::NewL(CRsfwVolume* aVolume) + { + CRsfwFileEngine* self = CRsfwFileEngine::NewLC(aVolume); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::NewLC +// ---------------------------------------------------------------------------- +// +CRsfwFileEngine* CRsfwFileEngine::NewLC(CRsfwVolume* aVolume) + { + DEBUGSTRING(("CRsfwFileEngine::NewLC")); + CRsfwFileEngine* self = new (ELeave) CRsfwFileEngine(); + DEBUGSTRING(("CRsfwFileEngine: in NewLC 0x%x", self)); + CleanupStack::PushL(self); + self->ConstructL(aVolume); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::ConstructL(CRsfwVolume* aVolume) + { + iRemoteAccess = NULL; + iRootFid = NULL; + iRootFep = NULL; + iVolume = aVolume; + iFs = CRsfwRfeServer::Env()->iFs; + iConnectionState = KMountNotConnected; + __ASSERT_ALWAYS(iVolume != NULL, User::Panic(KRfeServer, EConstructingServerStructs)); + iInactivityTimeout = + iVolume->iMountInfo.iMountConfig.iInactivityTimeout * 1000000; + PrepareCacheL(); + // Create file table + iFileTable = CRsfwFileTable::NewL(aVolume, iCacheRoot); + __ASSERT_ALWAYS(iVolume->iVolumeTable != NULL, User::Panic(KRfeServer, + EConstructingServerStructs)); + SetupRootL(iVolume->iVolumeTable->iPermanence); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::~CRsfwFileEngine +// ---------------------------------------------------------------------------- +// +CRsfwFileEngine::~CRsfwFileEngine() + { + DEBUGSTRING(("CRsfwFileEngine destructor")); + delete iFileTable; + delete iRemoteAccess; + delete iLockManager; + StopInactivityTimer(); + delete iInactivityTimer; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::DispatchL +// we should only come here with some synchronous requests +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::DispatchL(TRfeInArgs& aIn, TRfeOutArgs& aOut) + { + + switch(aIn.iOpCode) + { + case EFsIoctl: + DEBUGSTRING(("IOCTL")); + DoIoctlL(static_cast(aIn), + aOut); + break; + + case EFsRoot: + DEBUGSTRING(("ROOT")); + DoRootL(static_cast(aIn), + static_cast(aOut)); + break; + + case ESetAttr: + DEBUGSTRING(("SETATTR")); + DoSetAttrL(static_cast(aIn), + aOut); + break; + + default: + DEBUGSTRING(("WHAT??? - %d", aIn.iOpCode)); + User::Leave(KErrArgument); + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::FullNameLC +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwFileEngine::FullNameLC(CRsfwFileEntry& aFe) + { + HBufC* fn = aFe.FullNameLC(); + return fn; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::FullNameL +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwFileEngine::FullNameL(CRsfwFileEntry& aFe) + { + HBufC* fn = FullNameLC(aFe); + CleanupStack::Pop(fn); + return fn; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::SetupAttributes +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::SetupAttributes(CRsfwFileEntry& aFe) + { + DEBUGSTRING(("CRsfwFileEngine::SetupAttributes")); + // Construct the attributes for a newly created file or directory, + // or a file that that was locally modified and just written to the server, + // based on local knowledge of time and file size. + // We assume that either the file is cached or it is an empty file. + // We do not touch the local or protection attributes. + + TUint att; + + // Assume that the file type has already been setup + if (aFe.Type() == KNodeTypeDir) + { + att = KEntryAttDir; + } + else + { + att = 0; + } + + TTime time; + if (aFe.IsCached()) + { + TDesC* cacheNamep = aFe.CacheFileName(); + RFile f; + if (f.Open(iFs, *cacheNamep, EFileShareAny) == KErrNone) + { + // attribute bits + TUint a; + f.Att(a); + + att |= a & KEntryAttReadOnly; + + if (aFe.Type() == KNodeTypeDir) + { + aFe.SetSize(0); + } + else + { + if (aFe.IsFullyCached()) + { + // size + TInt siz; + f.Size(siz); + DEBUGSTRING(("File is fully cached, setting size to %d", siz)); + aFe.SetSize(siz); + aFe.SetCachedSize(siz); + } + else + { + DEBUGSTRING(("File is not fully cached, not touching the size")); + // file is not fully cached + // the size cannot be set from the local cache container + } + } + // modification time + f.Modified(time); + + f.Close(); + aFe.iUseCachedData = ETrue; + } + else + { + // No cache + aFe.SetSize(0); + time.HomeTime(); + } + + } + else + { + // No cache + aFe.SetSize(0); + time.HomeTime(); + } + + aFe.SetAtt(att); + + aFe.SetModified(time); + aFe.SetAttribValidationTime(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::MakeDirectoryEntry +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::MakeDirectoryEntry(CRsfwFileEntry& aFe, TDirEnt& aDirEnt) + { + DEBUGSTRING(("CRsfwFileEngine::MakeDirectoryEntry")); + DEBUGSTRING16(("name %S, att %d, size %d", aFe.Name(), aFe.Att(), aFe.Size()));; + aDirEnt.Clear(); + aDirEnt.iName.Copy(*aFe.Name()); + aDirEnt.iAttr.iAtt = aFe.Att(); + aDirEnt.iAttr.iSize = aFe.Size(); + aDirEnt.iAttr.iModified = aFe.Modified(); + aDirEnt.iAttr.iUid3 = aFe.iUid; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::UpdateDirectoryContainerL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::UpdateDirectoryContainerL(CRsfwFileEntry& aFe) + { + // Construct the directory container based on + // file table information + DEBUGSTRING16(("Update directory container of %d (%S)", aFe.Fid().iNodeId, aFe.Name())); + + TDesC* cacheNamep = aFe.CacheFileName(); + if (!cacheNamep) + { + // There was no prior cache. + DEBUGSTRING(("Cache missing!")); + User::Leave(KErrGeneral); + } + + RFile f; + CleanupClosePushL(f); + User::LeaveIfError(f.Replace(iFs, + *cacheNamep, + EFileShareAny | EFileWrite)); + RFileWriteStream fStream(f); + CleanupClosePushL(fStream); + + RPointerArray* kidsp = aFe.Kids(); + TInt i; + if (!(iVolume->iVolumeTable->EnsureCacheCanBeAddedL( + sizeof(TEntry) * kidsp->Count()))) + { // pessimistic estimate + User::Leave(KErrDiskFull); + } + for (i = 0; i < kidsp->Count(); i++) + { + CRsfwFileEntry* kidFep = (*kidsp)[i]; + TDirEnt dirEnt; + MakeDirectoryEntry(*kidFep, dirEnt); + dirEnt.ExternalizeL(fStream); + } + CleanupStack::PopAndDestroy(2, &f); // f + + aFe.ResetLocallyDirty(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::DataChanged +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEngine::DataChanged(const CRsfwDirEntAttr& aOldAttr, + const CRsfwDirEntAttr& aNewAttr) + { + // Based on attributes or metadata in general, + // tell whether the actual data, if cached, + // should be updated + if (aOldAttr.Att() == KEntryAttDir) + { + // use Last Modified (a weak entity tag) + if (aOldAttr.Modified() == aNewAttr.Modified()) + { + return EFalse; + } + else + { + return ETrue; + } + } + else + { + // use ETags if available + // a strong entity tag + if (aOldAttr.ETag() && aNewAttr.ETag()) + { + if (*aOldAttr.ETag() == *aNewAttr.ETag()) + { + return EFalse; + } + else + { + return ETrue; + } + } + + // use Last Modified (a weak entity tag) + // we assume it's file and compare also iSize... + if ((aOldAttr.Modified() == aNewAttr.Modified()) && + (aOldAttr.Size() == aNewAttr.Size())) + { + return EFalse; + } + else + { + return ETrue; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::UseCachedData +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEngine::UseCachedData(CRsfwFileEntry& aFe) + { + if (!Disconnected()) + { + return aFe.UseCachedData(); + } + else + { + return ETrue; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::UseCachedAttributes +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEngine::UseCachedAttributes(CRsfwFileEntry& aFe) + { + if (!Disconnected()) + { + if (aFe.Type() == KNodeTypeDir) + { + return iFileTable->Volume()->iVolumeTable-> + IsCachedAttrStillValid(aFe.iAttribValidation); + } + else + { // file + return iFileTable->Volume()->iVolumeTable-> + IsCachedDataStillValid(aFe.iAttribValidation); + + } + } + else + { + return ETrue; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::GetAttributesL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::GetAttributesL(CRsfwFileEntry& aFe, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + CRsfwRfeStateMachine* aCaller) + { + // Gets attributes for File Entry aFe. + // Uses either cached attributes (if they are still deemed to be valid), or + // fetches the attributes from the server*/ + DEBUGSTRING(("GetAttributesL")); + if ((aFe.Type() == aNodeType) && UseCachedAttributes(aFe)) + { + // Nothing to do + + if (aFe.IsOpenedForWriting()) + { + // update attributes when we are writing to the file + DEBUGSTRING(("volatile attributes")); + SetupAttributes(aFe); + } + else + { + DEBUGSTRING(("using cached attributes")); + } + aCaller->HandleRemoteAccessResponse(0, KErrNone); // "file exists" + } + else + { + // Refresh attributes + UpdateAttributesL(aFe, aAttr, aNodeType, aCaller); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::UpdateAttributesL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::UpdateAttributesL(CRsfwFileEntry& aFe, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + MRsfwRemoteAccessResponseHandler* aCaller) + { + // UpdateAttributes doesn't attempt to use cached attributes + HBufC* path = FullNameLC(aFe); + TPtr p = path->Des(); + DEBUGSTRING16(("UpdateAttributesL of '%S'", &p)); + + + UpdateAttributesL(*path, aAttr, aNodeType, aCaller); + + CleanupStack::PopAndDestroy(path); // path + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::UpdateAttributesL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::UpdateAttributesL(TDesC& aPath, + TDesC& aName, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + MRsfwRemoteAccessResponseHandler* aCaller) + { + HBufC* pn = HBufC::NewLC(KMaxPath); + TPtr pnPtr = pn->Des(); + + if (aPath.Length()) + { + pnPtr.Copy(aPath); + pnPtr.Append('/'); + } + pnPtr.Append(aName); + + DEBUGSTRING16(("UpdateKidAttributes of '%S'", &pnPtr)); + + UpdateAttributesL(pnPtr, aAttr, aNodeType, aCaller); + + CleanupStack::PopAndDestroy(pn); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::UpdateAttributesL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::UpdateAttributesL(TDesC& aFullPath, + CRsfwDirEntAttr*& aAttr, + TUint aNodeType, + MRsfwRemoteAccessResponseHandler* aCaller) + { + + // If we have "recently" found out that this file/dir does NOT exist + // we cache even this negative result. Time limit is cache expiry for + // directory attributes + if ((aFullPath.Length() > 0) && // do not compare root folder (always exists) + (iLastFailedLookup == aFullPath) && + (iFileTable->Volume()->iVolumeTable-> + IsCachedAttrStillValid(iLookupTime))) + { + if (aNodeType == KNodeTypeDir) + { + aCaller->HandleRemoteAccessResponse(0, KErrPathNotFound); + } + else if (aNodeType == KNodeTypeFile) + { + aCaller->HandleRemoteAccessResponse(0, KErrNotFound); + } + return; + + } + + if (!Disconnected()) + { + if (aNodeType == KNodeTypeDir) + { + RemoteAccessL()->GetDirectoryAttributesL(aFullPath, aAttr, aCaller); + } + else if (aNodeType == KNodeTypeFile) + { + RemoteAccessL()->GetFileAttributesL(aFullPath, aAttr, aCaller); + } + } + else + { + User::Leave(KErrNotFound); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::CreateContainerFileL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::CreateContainerFileL(CRsfwFileEntry& aFe) + { + // Create a container file for the Fid. + // If the cache file already exists, it will be deleted + + RFile f; + HBufC* cachePath = HBufC::NewMaxLC(KMaxPath); + TPtr pathPtr = cachePath->Des(); + BuildContainerPathL(aFe, pathPtr); + + TInt err = f.Replace(iFs, *cachePath, EFileShareAny | EFileWrite); + f.Close(); + if (err != KErrNone) + { + DEBUGSTRING(("Error when creating container file! err=%d", err)); + User::Leave(KErrGeneral); + } + aFe.SetCacheFileName(cachePath); + CleanupStack::PopAndDestroy(cachePath); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::FetchAndCacheL +// ---------------------------------------------------------------------------- +// +TUint CRsfwFileEngine::FetchAndCacheL(CRsfwFileEntry& aFe, + TInt aFirstByte, + TInt* aLength, + RPointerArray* aDirEntsp, + CRsfwRfeStateMachine* aCaller) + { + // Fetch a file from the remote store and decrypt it if necessary. + // The assumption is that the file has not yet been fetched + // or has been cached up to the byte indicated by (aFe.iCachedSize - 1) + // and filling the cache will continue linearly + // i.e. aFirstByte = 0 || aFirstByte = aFe.iCachedSize + // Access modules can fetch more than requested, so aLastByte might change. + + DEBUGSTRING(("Fetch fid %d, bytes %d - %d", + aFe.Fid().iNodeId, + aFirstByte, + aFirstByte + *aLength)); + + TUint transactionId = 0; + RFile f; + HBufC* fullName = NULL; + HBufC* cacheName = HBufC::NewMaxLC(KMaxPath); + TPtr cachePtr = cacheName->Des(); + TInt err; + + TInt usedCache = iVolume->iVolumeTable->TotalCachedSize(); + + // This much will be added to the cache by this fetch + if (!iVolume->iVolumeTable->EnsureCacheCanBeAddedL(*aLength)) + { + User::Leave(KErrDiskFull); + } + + if (!Disconnected()) + { + if (aFe.CacheFileName()) + { + // modify an existing cachefile ... + cachePtr = *(aFe.CacheFileName()); + + if (aFe.Type() == KNodeTypeFile) + { + // If the cache file exists, + // we will just continue filling it... + err = f.Open(iFs, *cacheName, EFileShareAny | EFileWrite); + if (err) + { + User::LeaveIfError(f.Replace(iFs, + *cacheName, + EFileShareAny | EFileWrite)); + } + } + else + { + User::LeaveIfError(f.Replace(iFs, + *cacheName, + EFileShareAny | EFileWrite)); + } + } + else + { + // create a new cache file + CreateContainerFileL(aFe, cachePtr, f); + } + + CleanupClosePushL(f); + fullName = FullNameLC(aFe); + if (aFe.Type() == KNodeTypeDir) + { + transactionId = GetDirectoryL(aFe, + *fullName, + f, + aDirEntsp, + aCaller); + } + else if (aFe.Type() == KNodeTypeFile) + { + f.Close(); + transactionId = RemoteAccessL()->GetFileL(*fullName, + *cacheName, + aFirstByte, + aLength, + 0, + aCaller); + } + + // fullName, f (duplicate close in the case of files) + CleanupStack::PopAndDestroy(2, &f); + } + CleanupStack::PopAndDestroy(cacheName); + return transactionId; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::RequestConnectionStateL +// ---------------------------------------------------------------------------- +// +TUint CRsfwFileEngine::RequestConnectionStateL(TUint aConnectionState, + CRsfwRfeStateMachine* aCaller) + { + DEBUGSTRING16(("CRsfwFileEngine::RequestConnectionStateL %d", aConnectionState)); + DEBUGSTRING16(("current connection state is %d", iConnectionState)); + TUint transactionId = 0; + if (aConnectionState != iConnectionState) + { + switch (aConnectionState) + { + case KMountNotConnected: + DisconnectL(); + break; + case KMountStronglyConnected: + transactionId = ConnectL(ETrue, aCaller); + break; + + default: + break; + } + } + // else does not do anything (if iConnectionState == aConnectionState) + return transactionId; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::EnteredConnectionStateL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::EnteredConnectionStateL(TUint aConnectionState, + TBool aRequested) + { + DEBUGSTRING16(("CRsfwFileEngine::EnteredConnectionStateL %d", aConnectionState)); + DEBUGSTRING16(("current connection state is %d", iConnectionState)); + if (aConnectionState != iConnectionState) + { + iConnectionState = aConnectionState; + iVolume->ConnectionStateChanged(iConnectionState); + + switch (aConnectionState) + { + case KMountNotConnected: + if (!aRequested) + { + iRemoteAccess->Cancel(0); + } + break; + + case KMountStronglyConnected: + if (aRequested) + { + if (iLockManager) + { + iLockManager->PopulateExternalLockTokenCacheL(iRootFep); + } + } + break; + + default: + break; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::ConnectionState +// ---------------------------------------------------------------------------- +// +TUint CRsfwFileEngine::ConnectionState() + { + return iConnectionState; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::LockManager +// ---------------------------------------------------------------------------- +// +CRsfwLockManager* CRsfwFileEngine::LockManager() + { + return iLockManager; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::SetPermanenceL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::SetPermanenceL(TBool aPermanence) + { + iFileTable->SetPermanenceL(aPermanence); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::Disconnected +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEngine::Disconnected() + { + return (iConnectionState == KMountNotConnected); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::WriteDisconnected +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEngine::WriteDisconnected() + { + // This also encompasses disconnected mode + return (iConnectionState != KMountStronglyConnected); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::AddToCacheL +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEngine::AddToCacheL(CRsfwFileEntry& aFe, + RPointerArray* aDirEnts, + CRsfwFileEngine *aFileEngine, + TUint cachedSize) + { + // returns the size of the cached data + RFs fs = CRsfwRfeServer::Env()->iFs; + TInt err; + TInt kidsCount = 0; + TInt containerSize = cachedSize; + // holds true for files, will be overwritten for directories + + if (aFe.Type() == KNodeTypeDir) + { + // *********** originally from CRsfwFileEngine::GetDirectoryL() + // ********************************************************** + // Unmark and mark kids only when getdirectory returns KErrNone + // otherwise (i.e. KErrUpdateNotRequired) let's just keep + // the cached kids... + aFe.UnmarkKids(); + + RApaLsSession lsSession; + User::LeaveIfError(lsSession.Connect()); + CleanupClosePushL(lsSession); + + RFileWriteStream fStream; + // Dump to the local cache + User::LeaveIfError( + fStream.Open(fs, + *(aFe.CacheFileName()), + EFileWrite | EFileShareAny)); + CleanupClosePushL(fStream); + + containerSize = fStream.Sink()->SizeL(); + TInt i; + TLex lex; + for (i = 0; i < aDirEnts->Count(); i++) + { + CRsfwDirEnt* d = (*aDirEnts)[i]; + TUid appUid; + // For each TDirEnt we just read... + // ... if the server returned content-type + if (d->Attr()->MimeType() && d->Attr()->MimeType()->Length()) + { + err = lsSession.AppForDataType(*(d->Attr()->MimeType()), + appUid); + if (err == KErrNone) + { + d->Attr()->SetUid(appUid); + } + } + + d->Attr()->SetAttFlags(KEntryAttRemote); + CRsfwFileEntry* kidFep = aFe.FindKidByName(*d->Name()); + if (kidFep) + { + // We already know this kid + // However we must check whether the kid has been modified + CRsfwDirEntAttr* oldAttr = CRsfwDirEntAttr::NewLC(); + kidFep->GetAttributesL(*oldAttr); + if (DataChanged(*oldAttr, *d->Attr())) + { + kidFep->RemoveCacheFile(); + } + CleanupStack::PopAndDestroy(oldAttr); + if (kidFep->IsFullyCached()) + { + // Mark the kid as cached + d->Attr()->ResetAttFlags(KEntryAttRemote); + } + // as this entry is "used", move it to the back of metadata LRU list + iVolume->iVolumeTable->MoveToTheBackOfMetadataLRUPriorityListL(kidFep); + } + + // As a side effect, + // insert this kid into the file table and + // set its attributes + if (!kidFep) + { + if (!iVolume->iVolumeTable->EnsureMetadataCanBeAddedL(&aFe)) + { + User::Leave(KErrNoMemory); + } + kidFep = CRsfwFileEntry::NewL(*d->Name(), &aFe); + // Attach the new kid + aFileEngine->iFileTable->AddL(kidFep); + aFe.AddKid(*kidFep); + } + + kidFep->Mark(); + + // set attributes if getting directory listing also supports getting file attributes + if (DirectoryListingContainsFileMetadata()) + { + kidFep->SetAttributesL(*d->Attr(), ETrue); + } + else + { + kidFep->SetAttributesL(*d->Attr(), EFalse); + } + + TDirEnt dirEnt; + MakeDirectoryEntry(*kidFep, dirEnt); + dirEnt.ExternalizeL(fStream); + kidsCount++; + } + + aFe.DropUnmarkedKidsL(); + + containerSize = fStream.Sink()->SizeL(); + // assumes that this fetch will write the whole directory, + + // i.e. there is no partial fetching for the directories + if(!iFileTable->Volume()->iVolumeTable-> + EnsureCacheCanBeAddedL(containerSize)) + { + User::Leave(KErrDiskFull); + } + fStream.CommitL(); + + CleanupStack::PopAndDestroy(2, &lsSession); // fStream, lsSession + + // if the directory appeared to be childless add it to metadata LRU list + if ( aDirEnts->Count() == 0 ) + { + iVolume->iVolumeTable->AddToMetadataLRUPriorityListL(&aFe, ECachePriorityNormal); + } + + }// if directory + + // assumes the files are cached in continuos chunks, + // i.e. always cached up to the last byte fetched + aFe.SetCachedSize(containerSize); + + aFe.SetCached(ETrue); + + // We have to update locally dirty bit for the parent container + if (aFe.Parent()) + { + aFe.Parent()->SetLocallyDirty(); + } + // But the object itself cannot be remotely dirty any more + aFe.ResetRemotelyDirty(); + + // *** from CRsfwFileEngine::DoFetch *** + if (aFe.Type() == KNodeTypeDir) + { + // the reason why kidsCount may be different than aFe.Kids.Count is that for big directories + // some kids could have been removed when adding the others to memory. this is due to memory management cap. + // however this should not happen so often + aFe.KidsCount() == kidsCount ? aFe.iUseCachedData = ETrue : aFe.iUseCachedData = EFalse; + } + else + { + aFe.iUseCachedData = ETrue; + } + + return containerSize; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::RemoteAccessL +// ---------------------------------------------------------------------------- +// +CRsfwRemoteAccess* CRsfwFileEngine::RemoteAccessL() + { + DEBUGSTRING(("CRsfwFileEngine::RemoteAccessL")); + if (!iRemoteAccess) + { + User::Leave(KErrNotReady); + } + + // Prevent the inactivity timer from triggering + // in the middle of a remote access operation + StopInactivityTimer(); + + return iRemoteAccess; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::OperationCompleted +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::OperationCompleted() + { + DEBUGSTRING(("File engine operation completed")); + if (iVolume->iVolumeTable->iPermanence) + { + iFileTable->SaveMetaDataDelta(); + } + + if (iLockManager && (iLockManager->LockedCount() == 0)) + { + // Start timer only if we don't have files open for writing + StartInactivityTimer(); + } + + iVolume->OperationCompleted(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::CancelTransaction +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::CancelTransaction(TUint iTransactionId) + { + DEBUGSTRING(("CRsfwFileEngine::CancelTransactionL")); + if (iRemoteAccess) + { + iRemoteAccess->Cancel(iTransactionId); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::CancelTransaction +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::CancelTransactionL(TDesC& aPathName) + { + DEBUGSTRING(("CRsfwFileEngine::CancelTransactionL")); + TPtrC testPtr; + testPtr.Set(aPathName.Right(aPathName.Length() - 3)); + HBufC* cancelPath = HBufC::NewLC(KMaxPath); + TPtr cancelPathPtr = cancelPath->Des(); + // change '\\' to '/' so the path matches + TLex parser(testPtr); + TChar theChar; + + for (int i = 0; i < testPtr.Length(); i++) + { + theChar = parser.Get(); + if (theChar == 0) + { + break; + } + // assumes that the input string always has "\\" and not just "\" + // this is true as the input is a file path + if (theChar != '\\') + { + cancelPathPtr.Append(theChar); + } + else + { + cancelPathPtr.Append('/'); + } + } + + if (iRemoteAccess) + { + iRemoteAccess->Cancel(*cancelPath); + } + + CleanupStack::PopAndDestroy(cancelPath); + + } + + + + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::SetFailedLookup +// Caches the last failed lookup result +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::SetFailedLookup(TDesC& aPath, TDesC& aKidName) + { + iLastFailedLookup = aPath; + iLastFailedLookup.Append('/'); + iLastFailedLookup.Append(aKidName); + iLookupTime.HomeTime(); + DEBUGSTRING16(("SetFailedLookup: %S", &iLastFailedLookup)); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::ResetFailedLookup +// Clears the last failed lookup result +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::ResetFailedLookup() + { + DEBUGSTRING16(("ResetFailedLookup: %S", &iLastFailedLookup)); + iLastFailedLookup.Zero(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::Volume +// ---------------------------------------------------------------------------- +// +CRsfwVolume* CRsfwFileEngine::Volume() + { + return iVolume; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::PrepareCacheL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::PrepareCacheL() + { + // make sure the file cache (of this volume) exists + iCacheRoot.Copy(CRsfwRfeServer::Env()->iCacheRoot); + iCacheRoot.Append('C'); + iCacheRoot.AppendNum(iVolume->iMountInfo.iMountStatus.iVolumeId); + iCacheRoot.Append('\\'); + + if (! BaflUtils::FileExists(iFs, iCacheRoot)) + { + // There was no prior cache directory + TInt err = iFs.MkDirAll(iCacheRoot); + DEBUGSTRING(("Cache directory created with err=%d", err)); + User::LeaveIfError(err); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::GetDirectoryL +// ---------------------------------------------------------------------------- +// +TUint CRsfwFileEngine::GetDirectoryL(CRsfwFileEntry& /*aFe*/, + TDesC& aFullName, + RFile& /*aF*/, + RPointerArray* aDirEntsp, + MRsfwRemoteAccessResponseHandler* aCaller) + { + return RemoteAccessL()->GetDirectoryL(aFullName, *aDirEntsp, aCaller); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::BuildContainerPathL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::BuildContainerPathL(CRsfwFileEntry& aFe, TDes& aPath) + { + if (aPath.MaxLength() < (aPath.Length() + iCacheRoot.Length())) + { + aPath.Copy(iCacheRoot); + } + else + { + User::Leave(KErrOverflow); + } + + ApplyMultiDirCacheL(aPath); + // This filename tagging based on container type is just for convenience + if (aFe.Type() == KNodeTypeFile) + { + aPath.Append('F'); + } + else + { + aPath.Append('D'); + } + aPath.AppendNum((TInt)aFe.Fid().iNodeId); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::ApplyMultiDirCachePathL +// Due to Symbian performance problems with huge directories, items will not +// be stored in one directory in the cache. +// Now instead one dir like: +// C:\system\data\rsfw_cache\C16 +// there will be dirs like: +// C:\system\data\rsfw_cache\C16\M0 +// C:\system\data\rsfw_cache\C16\M1 +// ... and so on +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::ApplyMultiDirCacheL(TDes& aPath) + { + // maximum number of items in a single dir in the cache + const TInt KRsfwMaxItemsInDir = 100; + TInt i; + // this loop will surely break (or leave) at some point + for ( i = 0; ; i++ ) + { + // create path like "C:\system\data\rsfw_cache\C16\M0" + HBufC* trypath = HBufC::NewMaxL(KMaxPath); + TPtr pathPtr = trypath->Des(); + pathPtr.Copy(aPath); + pathPtr.Append('M'); + pathPtr.AppendNum(i); + pathPtr.Append('\\'); + + // check whether dir exists and if so, how many items it contains + CDir* dir = NULL; + // note that KEntryAttDir att means files & directories + TInt err = iFs.GetDir(*trypath, KEntryAttDir, ESortNone, dir); + if ( err == KErrNone ) + { + // count the items + TInt count = dir->Count(); + delete dir; + dir = NULL; + + //limit is not exceeded -> return the path + if ( count < KRsfwMaxItemsInDir ) + { + aPath.Copy(pathPtr); + delete trypath; + break; + } + // limit exceeded -> let's try the next dir + else + { + delete trypath; + continue; + } + } + else if ( err == KErrPathNotFound ) + { + // create dir and return the path to empty dir + err = iFs.MkDir(*trypath); + if (!err) + { + aPath.Copy(pathPtr); + delete trypath; + } + else + { + delete trypath; + DEBUGSTRING(("Error when creating cache dir! err=%d", err)); + User::Leave(KErrGeneral); + } + + break; + } + else + { + delete trypath; + DEBUGSTRING(("Cache directory cannot be created! err=%d", err)); + User::Leave(KErrGeneral); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::CreateContainerFileL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::CreateContainerFileL(CRsfwFileEntry& aFe, + TDes& aPath, + RFile& aF) + { + // Create a container file for the Fid. + // If the cache file already exists, it will be deleted + + BuildContainerPathL(aFe, aPath); + + TInt err = aF.Replace(iFs, aPath, EFileShareAny | EFileWrite); + if (err != KErrNone) + { + User::Leave(KErrGeneral); + } + aF.Close(); + + aFe.SetCacheFileName(&aPath); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::DoIoctlL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::DoIoctlL(TRfeIoctlInArgs& aIn, TRfeOutArgs& /* aOut */) + { + TFid fidp = aIn.iFid; + TInt cmd = aIn.iCmd; + + TInt err = KErrNone; + + DEBUGSTRING(("ioctl fid %d - command=%d, data=%d", + fidp.iNodeId, + cmd, + aIn.iData32[0])); + + CRsfwFileEntry* fep = iFileTable->Lookup(fidp); + if (fep) + { + switch (cmd) + { + case ERemoteFsIoctlRefresh: + + + if (fep->Type() == KNodeTypeFile) + { + + fep->SetCacheFileName(NULL); + fep->SetCached(EFalse); + + // There is a change in the parent's container + fep->Parent()->SetLocallyDirty(); + } + break; + + case ERemoteFsHighCachePriority: + default: + err = KErrArgument; + break; + } + } + else + { + err = KErrNotFound; + } + + if (err != KErrNone) + { + User::Leave(err); + } + + return; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::DoRootL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::DoRootL(TRfeRootInArgs& /* aIn */, TRfeRootOutArgs& aOut) + { + SetupRootL(iVolume->iVolumeTable->iPermanence); + aOut.iFid.iVolumeId = iRootFid->iVolumeId; + aOut.iFid.iNodeId = iRootFid->iNodeId; + return; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::DoSetAttrL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::DoSetAttrL(TRfeSetAttrInArgs& aIn, TRfeOutArgs& /* aOut */) + // We cannot really set anything but this is the way to implement this + // note that if this is implemented, it should really be a state machine + { + TInt err = KErrNone; + TFid fidp = aIn.iFid; +#ifdef _DEBUG + TDirEntAttr* attrp = &(aIn.iAttr); +#endif + + DEBUGSTRING(("setting attributes of fid %d, attr=0x%x, size=%d, time=", + fidp.iNodeId, + attrp->iAtt, + attrp->iSize)); + DEBUGTIME((attrp->iModified)); + + // Get the file or directory to setattr + CRsfwFileEntry* fep = iFileTable->Lookup(fidp); + if (fep) + { + err = KErrNotSupported; + } + else + { + err = KErrNotFound; + } + + User::Leave(err); + return; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::SetupRootL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::SetupRootL(TBool aPermanence) + { + _LIT(KRootPath, "."); // dummy + + if (!iRootFid) + { + CRsfwFileEntry* root = NULL; + TInt err; + if (aPermanence) + { + TRAP(err, root = iFileTable->LoadMetaDataL()); + } + if (err == KErrCorrupt) + { + DEBUGSTRING(("Metadata corrupted! Recreating cache file...")); + // corrupted cache file, recreate filetable and cache file + delete iFileTable; + iFileTable = NULL; + CleanupCorruptedCacheL(); + PrepareCacheL(); + iFileTable = CRsfwFileTable::NewL(iVolume, iCacheRoot); + } + if (!aPermanence || (err != KErrNone)) + { + root = CRsfwFileEntry::NewL(KRootPath, NULL); + // Insert root into the file table + iFileTable->AddL(root); + root->SetType(KNodeTypeDir); + } + if (aPermanence) + { + iFileTable->SaveMetaDataDelta(); + } + iRootFep = root; + iRootFid = &(root->Fid()); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::CleanupCorruptedCacheL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::CleanupCorruptedCacheL() + { + // delete everything from the cache + TFileName cachepath; + cachepath.Copy(iCacheRoot); + CFileMan* fileMan = CFileMan::NewL(iFs); + fileMan->Delete(cachepath, CFileMan::ERecurse); + delete fileMan; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::ConnectL +// ---------------------------------------------------------------------------- +// +TUint CRsfwFileEngine::ConnectL(TBool aRestart, CRsfwRfeStateMachine* aCaller) + { + // Assume parameter format: + // protocol://username:password@server:port/rootdir or + // The ":password", ":port", and "[/]rootdir" can be omitted. + // If the length of password parameter is bigger than 1, + // it overrides the one in uri, if any. + // Characters can be quoted with % format + TUint transactionId = 0; + + if (iRemoteAccess) + { + // We already have a remote accessor + if (aRestart) + { + // Restarting + delete iLockManager; + iLockManager = NULL; + delete iRemoteAccess; + iRemoteAccess = NULL; + } + else + { + User::Leave(KErrAlreadyExists); + } + } + + DEBUGSTRING16(("ConnectL(): '%S'", + &iVolume->iMountInfo.iMountConfig.iUri)); + + TUriParser uriParser; + User::LeaveIfError(uriParser.Parse(iVolume->iMountInfo.iMountConfig.iUri)); + + TPtrC userName; + TPtrC password; + TPtrC friendlyName; + + if (uriParser.IsPresent(EUriUserinfo)) + { + TPtrC userInfo(uriParser.Extract(EUriUserinfo)); + // Split the user info into user name and password (seprated by ':') + TInt pos = userInfo.Locate(':'); + if (pos != KErrNotFound) + { + password.Set(userInfo.Mid(pos + 1)); + userName.Set(userInfo.Left(pos)); + } + else + { + userName.Set(userInfo); + } + } + + HBufC* userNameBuf = NULL; + if (!userName.Length() && + iVolume->iMountInfo.iMountConfig.iUserName.Length()) + { + // separate user name overwrites the username embedded in the URI + userName.Set(iVolume->iMountInfo.iMountConfig.iUserName); + } + + HBufC* passwordBuf = NULL; + if (!password.Length() && + (iVolume->iMountInfo.iMountConfig.iPassword.Length() > 1)) + { + // separate password overwrites the password embedded in the URI + password.Set(iVolume->iMountInfo.iMountConfig.iPassword); + } + + friendlyName.Set(iVolume->iMountInfo.iMountConfig.iName); + + TPtrC scheme(uriParser.Extract(EUriScheme)); + HBufC8* protocol = HBufC8::NewLC(scheme.Length()); + TPtr8 protocolPtr = protocol->Des(); + protocolPtr.Copy(scheme); + iRemoteAccess = CRsfwRemoteAccess::NewL(protocolPtr); + CleanupStack::PopAndDestroy(protocol); + + // user name and password are conveyed separately from the URI + CUri* uri = CUri::NewLC(uriParser); + uri->RemoveComponentL(EUriUserinfo); + + // leaves if error + iRemoteAccess->SetupL(this); + transactionId = iRemoteAccess-> + OpenL(uri->Uri(), + friendlyName, + userName, + password, + iVolume->iMountInfo.iMountConfig.iAuxData, + aCaller); + + CleanupStack::PopAndDestroy(uri); + if (passwordBuf) + { + CleanupStack::PopAndDestroy(passwordBuf); + } + if (userNameBuf) + { + CleanupStack::PopAndDestroy(userNameBuf); + } + + // lock manager can be created before we know whether connecting was + // succesful - however it must be deleted upon unsuccesful connect + if (!iLockManager) + { + iLockManager = CRsfwLockManager::NewL(iRemoteAccess); + } + + if ((iInactivityTimeout > 0) && !iInactivityTimer) + { + iInactivityTimer = CPeriodic::NewL(CActive::EPriorityLow); + } + return transactionId; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::DisconnectL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::DisconnectL() + { + DEBUGSTRING(("CRsfwFileEngine::DisconnectL")); + if (iRemoteAccess) + { + iRemoteAccess->Cancel(0); + delete iRemoteAccess; + iRemoteAccess = NULL; + } + + if (iLockManager) + { + delete iLockManager; + iLockManager = NULL; + } + + + // Set open file count to zero + // If there are open files, after disconnecting we do not necessarily + // get close events. + // Note that this variable is not "dirty bit" (file has currently + // uncommitted modifications), so it is safe to set it to zero + TInt openfiles = iFileTable->OpenFileCount(); + iFileTable->UpdateOpenFileCount(-openfiles); + + EnteredConnectionStateL(KMountNotConnected, ETrue); + + // publish connection status when disconnecting + iVolume->iVolumeTable->PublishConnectionStatus(iVolume); + + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::StartInactivityTimer +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::StartInactivityTimer() + { + if (iInactivityTimer) + { + DEBUGSTRING(("inactivity timer started (%d us)", + iInactivityTimeout)); + iInactivityTimer->Cancel(); + TCallBack callBack(CRsfwFileEngine::InactivityTimerExpired, this); + iInactivityTimer->Start(iInactivityTimeout, + iInactivityTimeout, + callBack); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::StopInactivityTimer +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::StopInactivityTimer() + { + DEBUGSTRING(("CRsfwFileEngine::StopInactivityTimer")); + if (iInactivityTimer) + { + DEBUGSTRING(("inactivity timer stopped")); + iInactivityTimer->Cancel(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::InactivityTimerExpired +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEngine::InactivityTimerExpired(TAny* aArg) + { + DEBUGSTRING(("CRsfwFileEngine::InactivityTimerExpired")); + CRsfwFileEngine* fileEngine = static_cast(aArg); + if (fileEngine->iFileTable->OpenFileCount() == 0) + { + fileEngine->StopInactivityTimer(); + TRAP_IGNORE(fileEngine->DisconnectL()); + // "Simulate" operation completion (which may result in RFE shutdown) + fileEngine->OperationCompleted(); + } + else + { + // if there are open files on this volume, just restart the inactivity timer + fileEngine->StartInactivityTimer(); + } + + return 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::HandleRemoteAccessEventL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEngine::HandleRemoteAccessEventL(TInt aEventType, + TInt aEvent, + TAny* /* aArg */) + { + DEBUGSTRING(("Handle remote access event: %d/%d in connection state %d", + aEventType, + aEvent, + iConnectionState)); + switch (aEventType) + { + case ERsfwRemoteAccessObserverEventConnection: + switch (aEvent) + { + case ERsfwRemoteAccessObserverEventConnectionDisconnected: + EnteredConnectionStateL(KMountNotConnected, EFalse); + break; + + case ERsfwRemoteAccessObserverEventConnectionWeaklyConnected: +#if 0 + // This event does not appear + EnteredConnectionStateL(KMountWeaklyConnected, EFalse); +#endif + break; + + case ERsfwRemoteAccessObserverEventConnectionStronglyConnected: +#if 0 + // This event does not appear + EnteredConnectionStateL(KMountStronglyConnected, EFalse); +#endif + break; + + default: + break; + } + break; + + default: + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEngine::PurgeFromCacheL +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEngine::PurgeFromCache(const TDesC& aPath) + { + // get the fid of the entry for which the cached data is removed + CRsfwFileEntry* targetFid = FetchFep(aPath); + if (!targetFid) + { + return KErrPathNotFound; + } + // only directories can be refreshed currently + if (targetFid->Type() != KNodeTypeDir) + { + return KErrArgument; + } + targetFid->SetCached(EFalse); + return KErrNone; + } + +CRsfwFileEntry* CRsfwFileEngine::FetchFep(const TDesC& aPath) + { + DEBUGSTRING16(("CRsfwFileEngine::FetchFep for file %S", &aPath)); + if (aPath.Length() <= 1) + { + DEBUGSTRING(("returning rootFep")); + return iRootFep; + } + else + { + TInt delimiterPos = aPath.LocateReverse(KPathDelimiter); + if (delimiterPos == (aPath.Length() - 1)) + { + // The path ends with a slash, + //i.e. this is a directory - continue parsing + TPtrC nextdelimiter; + nextdelimiter.Set(aPath.Left(delimiterPos)); + delimiterPos = nextdelimiter.LocateReverse(KPathDelimiter); + } + TPtrC entry(aPath.Right(aPath.Length() - (delimiterPos + 1))); + TPtrC path(aPath.Left(delimiterPos + 1)); + + // strip a trailing backslash if found + delimiterPos = entry.LocateReverse(KPathDelimiter); + if (delimiterPos == (entry.Length() - 1)) + { + TPtrC stripped(entry.Left(entry.Length() - 1)); + return (FetchFep(path)->FindKidByName(stripped)); + } + else + { + return (FetchFep(path)->FindKidByName(entry)); + } + + } + + } + +HBufC8* CRsfwFileEngine::GetContentType(TDesC& aName) + { + TInt err; + RApaLsSession lsSession; + err = lsSession.Connect(); + if (err) + { + return NULL; + } + + RFs fsSession; + err = fsSession.Connect(); + if (err) + { + lsSession.Close(); + return NULL; + } + fsSession.ShareProtected(); + TDataRecognitionResult dataType; + RFile theFile; + // the mode must mach the mode that is used in the file system plugin + // (EFileWrite|EFileShareAny) + err = theFile.Open(fsSession, aName, EFileWrite|EFileShareAny); + if (err) + { + lsSession.Close(); + fsSession.Close(); + return NULL; + } + err = lsSession.RecognizeData(theFile, dataType); + lsSession.Close(); + theFile.Close(); + fsSession.Close(); + if (err) + { + return NULL; + } + + return dataType.iDataType.Des8().Alloc(); + } + + // The purpose of these functions is to give capability info + // for the access protocol plugin used. + + // Currently this information is hard coded and takes into account webdav and upnp + // access modules. New function should be added to the access plugin api to get + // this information from the protocol module + + // whether getting the directory listing also gives reliable file metadata +TBool CRsfwFileEngine::DirectoryListingContainsFileMetadata() + { + _LIT(KUPnP, "upnp"); + if (iVolume->MountInfo()->iMountConfig.iUri.Left(4) == KUPnP) + { + return EFalse; + } + else + { + return ETrue; + } + + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwfileentry.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwfileentry.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1356 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: metadata struct for a remote file entry +* +*/ + + +#include + +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwconfig.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwrfeserver.h" +#include "rsfwlockmanager.h" +#include "mdebug.h" +#include "rsfwdirentattr.h" + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::NewLC +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileEntry::NewLC(const TDesC& aName, CRsfwFileEntry* aParent) + { + CRsfwFileEntry* self = new (ELeave) CRsfwFileEntry(); + CleanupStack::PushL(self); + self->ConstructL(aName, aParent); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::NewL +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileEntry::NewL(const TDesC& aName, CRsfwFileEntry* aParent) + { + CRsfwFileEntry* self = NewLC(aName, aParent); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::NewL +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileEntry::NewL(RReadStream& aStream) + { + CRsfwFileEntry* self = new (ELeave) CRsfwFileEntry(); + CleanupStack::PushL(self); + self->ConstructL(aStream); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ConstructL(const TDesC& aName, CRsfwFileEntry* aParent) + { + iType = KNodeTypeUnknown; + iParent = aParent; + iName = aName.AllocL(); + iAtt = KEntryAttRemote; + iCachePriority = ECachePriorityNormal; + + SetLockTimeout(); + // Note that we don't yet attach the kid to its parent + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ConstructL(RReadStream& aStream) + { + // aStream >> *this; + this->InternalizeL(aStream); + SetLockTimeout(); + // Note that we don't yet attach the kid to its parent + } + +void CRsfwFileEntry::SetLockTimeout() + { + // When creating a file entry, the lock timeout is set to default + // even when internalizing from stream. + // We do not assume any locks that would survive server restarts + TInt timeout; + TInt err = CRsfwRfeServer::Env()->iRsfwConfig->Get(RsfwConfigKeys::KLockTimeout, + timeout); + if (!err) + { + iLockTimeout = (TUint)timeout; + } + else + { + iLockTimeout = KDefaultLockTimeout; + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::~CRsfwFileEntry +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry::~CRsfwFileEntry() + { + if (iFlags & KNodeHasValidLock) + { + if (iLockManager) + { + iLockManager->RemoveLockedEntry(this); + } + } + delete iName; + delete iMimeType; + delete iOpaqueFileId; + delete iLockToken; + + if (!iFileTable || !iFileTable->Permanence()) + { + RemoveCacheFile(); + } + + if ( iFileTable ) + { + iFileTable->Volume()->iVolumeTable->RemoveFromMetadataLRUPriorityList(this); + } + + delete iLockTimer; + + // delete kids + TInt i; + for(i = 0; i < iKids.Count(); i++) + { + delete iKids[i]; + } + iKids.Close(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::FindKidByName +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileEntry::FindKidByName(const TDesC& aName) + { + DEBUGSTRING(("CRsfwFileEntry::FindKidByName")); + // finds a kid from a parent directory + TInt i; + for (i = 0; i < iKids.Count(); i++) + { + CRsfwFileEntry* kid = iKids[i]; + if (kid->iName->Compare(aName) == 0) + { + return iKids[i]; + } + } + DEBUGSTRING(("...kid not found!")); + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::RenameL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::RenameL(const TDesC& aName) + { + delete iName; + iName = NULL; + iName = aName.AllocL(); + ReportEvent(KNotifyNodeModified); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::AddKid +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::AddKid(CRsfwFileEntry& aFe) + { + // if this is the first kid to be added then probably + // we have to remove the entry from metadata LRU list + if ( iKids.Count() == 0 ) + { + iFileTable->Volume()->iVolumeTable->RemoveFromMetadataLRUPriorityList(this); + } + iKids.Append(&aFe); + // (This assignment is sometimes redundant) + aFe.SetParent(this); + ReportEvent(KNotifyNodeModified); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::RemoveKidL +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEntry::RemoveKidL(CRsfwFileEntry* aFep) + { + TInt i; + for (i = 0; i < iKids.Count(); i++) + { + if (iKids[i] == aFep) + { + ReportEvent(KNotifyNodeModified); + iKids.Remove(i); + // if we've just removed the last kid of the entry + // we can add the entry to metadata LRU list + if ( iKids.Count() == 0 ) + { + iFileTable->Volume()->iVolumeTable->AddToMetadataLRUPriorityListL(this, ECachePriorityNormal); + } + return KErrNone; + } + } + DEBUGSTRING(("remove kid %d not found in %d", + aFep->Fid().iNodeId, + Fid().iNodeId)); + return KErrNotFound; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::KidsCount +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEntry::KidsCount() + { + return iKids.Count(); + } + + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::UnmarkKids +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::UnmarkKids() + { + TInt i; + for (i = 0; i < iKids.Count(); i++) + { + iKids[i]->Unmark(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::DropUnmarkedKidsL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::DropUnmarkedKidsL() + { + TInt i = 0; + while (i < iKids.Count()) + { + if (!iKids[i]->IsMarked()) + { + iKids[i]->DropLD(); + } + else + { + i++; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::DropLD +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::DropLD() + { + DEBUGSTRING(("CRsfwFileEntry::DropLD")); + TInt i = 0; + while (i < iKids.Count()) + { + iKids[i]->DropLD(); + } + + iFileTable->RemoveL(this); + delete this; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::GetAttributes +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::GetAttributes(TDirEntAttr& aAttr) const + { + aAttr.iAtt = Att(); + aAttr.iSize = Size(); + aAttr.iModified = Modified(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::GetAttributesL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::GetAttributesL(CRsfwDirEntAttr& aAttr) const + { + aAttr.SetAtt(Att()); + aAttr.SetSize(Size()); + aAttr.SetModified(Modified()); + if (iOpaqueFileId) + { + aAttr.SetETagL(*OpaqueFileId()); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetAttributesL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetAttributesL(CRsfwDirEntAttr& aAttr, + TBool aAllMetaData) + { + SetAtt(aAttr.Att()); + if (aAllMetaData) + { + SetSize(aAttr.Size()); + SetModified(aAttr.Modified()); + if (aAttr.MimeType()) + { + SetMimeTypeL(*aAttr.MimeType()); + } + if (aAttr.ETag()) + { + SetOpaqueFileIdL(*aAttr.ETag()); + } + SetUid(aAttr.Uid()); + SetAttribValidationTime(); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::CacheFileName +// ---------------------------------------------------------------------------- +// +TDesC* CRsfwFileEntry::CacheFileName() + { + DEBUGSTRING(("CRsfwFileEntry::CacheFileName")); + if (iCacheName.Length()) + { + return &iCacheName; + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetCacheFileName +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetCacheFileName(TDesC* aFn) + { + DEBUGSTRING16(("SetCacheFileName for file %S", Name())); + if (aFn) + { + iCacheName = *aFn; + ReportEvent(KNotifyNodeModified); + } + else + { + if (iCacheName.Length()) + { + if (IsCached()) + { + // Remove the cache list entry... + iFileTable-> + Volume()-> + iVolumeTable->RemoveFromLRUPriorityList(this); + } + // This is a request to discard the container + RFs fs = CRsfwRfeServer::Env()->iFs; + TInt err = fs.Delete(iCacheName); + if (err != KErrNone) + { + DEBUGSTRING(("Cannot purge cache file (err=%d)", err)); + } + iCacheName.Zero(); + // Reset locally dirty in case this is a directory. + // "locally dirty" means that the container + // doesn't have the "cached"/"protected" indicator bits up to date + // (these indicators refer to files contained in the directory). + iFlags &= ~KNodeLocallyDirty; + ReportEvent(KNotifyNodeModified); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsCached +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsCached() const + { + DEBUGSTRING(("CRsfwFileEntry::IsCached, iAtt = %d, iFlags = %d", iAtt, iFlags)); + if (((iAtt & KEntryAttRemote) == 0) || + (iFlags & KNodePartlyCached)) + { + DEBUGSTRING(("returning ETrue")); + // File is either fully or partly cached + return ETrue; + } + + DEBUGSTRING(("returning EFalse")); + return EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsFullyCached +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsFullyCached() const + { + DEBUGSTRING(("CRsfwFileEntry::IsFullyCached")); + DEBUGSTRING(("iCachedSize = %d, iSize = %d", iCachedSize, iSize)); + if (Type() == KNodeTypeDir) + { + return IsCached(); + } + else + { + if (iCachedSize == iSize) + { + return IsCached(); + } + else + { + return EFalse; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetCached +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetCached(TBool aCached) + { + DEBUGSTRING(("CRsfwFileEntry::SetCached")); + TUint oldAtt = iAtt; + if (aCached) + { + if (Type() == KNodeTypeDir) + { + // set to fully cached + DEBUGSTRING(("set directory to fully cached")); + iAtt &= ~KEntryAttRemote; + iFlags &= ~KNodePartlyCached; + } + else + { + if (iCachedSize == iSize) + { + // set file to fully cached + DEBUGSTRING(("set file to fully cached")); + iAtt &= ~KEntryAttRemote; + iFlags &= ~KNodePartlyCached; + } + else + { + // Set file to partly cached + DEBUGSTRING(("set file to partly cached")); + iAtt |= KEntryAttRemote; + iFlags |= KNodePartlyCached; + } + } + } + else + { + // set to "fully" remote + DEBUGSTRING(("set to fully remote")); + iFlags &= ~KNodePartlyCached; + iAtt |= KEntryAttRemote; + iUseCachedData = EFalse; + iCachedSize = 0; + } + if (iAtt != oldAtt) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetCachedSize +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetCachedSize(TInt aFetchedSize) + { + TInt oldCachedSize = iCachedSize; + iCachedSize = aFetchedSize; + if (iCachedSize != oldCachedSize) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::RemoveCacheFile +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::RemoveCacheFile() + { + DEBUGSTRING(("CRsfwFileEntry::RemoveCacheFile")); + if (IsCached() && iFileTable) + { + // Remove the cache list entry... + iFileTable->Volume()->iVolumeTable->RemoveFromLRUPriorityList(this); + } + + if (iCacheName.Length()) + { + RFs fs = CRsfwRfeServer::Env()->iFs; + TInt err = fs.Delete(iCacheName); + if ((err != KErrNone) && (err != KErrNotFound)) + { + DEBUGSTRING(("Cannot delete cache file (err=%d)", err)); + } + iCacheName.Zero(); + } + SetCached(EFalse); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ValidateCacheFile +// Function checks whether cache file has not been accidentally or intentionally +// removed from the cache (which would mean the cache has been corrupted) +// In case the corruption has happened, the function sets entry as non-cached +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ValidateCacheFile() + { + if (iCacheName.Length() > 0) + { + RFs fs = CRsfwRfeServer::Env()->iFs; + if (! BaflUtils::FileExists(fs, iCacheName)) + { + SetCached(EFalse); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::PrintL +// ---------------------------------------------------------------------------- +// +#ifdef _DEBUG +void CRsfwFileEntry::PrintL(TInt aLevel, TBool aKids, TBool aAll) const + { + if (!IsCached() && !aAll) + { + // Print only information about cached files + return; + } + + HBufC* sBuf = HBufC::NewLC(KMaxPath); + TPtr s = sBuf->Des(); + + s.Fill(' ', 4 * aLevel); + s.AppendNum(iFid.iNodeId); + s.Append('|'); + s.Append(*iName); + switch (iType) + { + case KNodeTypeDir: + s.Append('/'); + break; + + case KNodeTypeFile: + break; + + default: + s.Append('?'); + break; + } + + if (IsCached()) + { + s.Append('|'); + s.Append(iCacheName); + } + + DEBUGBUFFER((s)); + + CleanupStack::PopAndDestroy(sBuf); // sBuf + + if (aKids) + { + TInt i; + for (i = 0; i < iKids.Count(); i++) + { + iKids[i]->PrintL(aLevel + 1, aKids, aAll); + } + } + } +#else +void CRsfwFileEntry::PrintL(TInt, TBool, TBool) const + { + } +#endif //DEBUG + + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::FullNameLC +// Construct full name relative to the root. +// The caller is responsible for deallocating the return value. +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwFileEntry::FullNameLC() const + { + // We know that we can't have more than KMaxPath entries, + // because each entry is minimally "/" + CRsfwFileEntry* entList[KMaxPath / 2]; + + HBufC* fn = HBufC::NewLC(KMaxPath); + TPtr fnp = fn->Des(); + CRsfwFileEntry* fep = const_cast(this); + TInt depth = 0; + do + { + if (depth >= (KMaxPath / 2)) + { + // Too deep hierarchy + DEBUGSTRING(("CRsfwFileEntry::FullNameLC - Too deep hierarchy! %d", depth)); + User::Leave(KErrGeneral); + } + entList[depth++] = fep; + fep = fep->iParent; + } + while (fep); + + // We want to avoid going right to the root to avoid dots + depth--; + + TInt i; + for (i = depth - 1; i >= 0; i--) + { + TPtr name = entList[i]->iName->Des(); + if (i != (depth - 1)) + { + // Skip "this" directories (should not happen) + if ((name[0] == '.') && (name.Length() == 1)) + { + continue; + } + } + if ((fnp.Length() + name.Length()) >= (KMaxPath - 1)) + { + // Too long name + DEBUGSTRING(("CRsfwFileEntry::FullNameLC - Too long name!")); + User::Leave(KErrGeneral); + } + fnp.Append(name); + if (i != 0) + { + fnp.Append('/'); + } + } + + return fn; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::TotalCachedSize +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEntry::TotalCachedSize() + { + TInt cachedSize = 0; + TInt i; + + for (i = 0; i < iKids.Count(); i++) + { + TInt newSize = iKids[i]->TotalCachedSize(); + cachedSize = cachedSize + newSize; + } + cachedSize = cachedSize + iCachedSize; + return cachedSize; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::TotalEntryCount +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEntry::TotalEntryCount() + { + TInt entryCount = 0; + TInt i; + for (i = 0; i < iKids.Count(); i++) + { + TInt kidCount = iKids[i]->TotalEntryCount(); + entryCount += kidCount; + } + entryCount += 1; // itself + return entryCount; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Lookup +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileEntry::Lookup(const TFid& aFid) + { + // linear search - immediate kids first + TInt i; + for (i = 0; i < iKids.Count(); i++) + { + CRsfwFileEntry* fep = iKids[i]; + if (fep->Fid().iNodeId == aFid.iNodeId) + { + return iKids[i]; + } + } + // Not found - lookup the kids' kids + for (i = 0; i < iKids.Count(); i++) + { + CRsfwFileEntry* fep; + fep = iKids[i]->Lookup(aFid); + if (fep) + { + return fep; + } + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetLockedL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetLockedL(CRsfwLockManager* lockManager, TDesC8* aLockToken) + { + DEBUGSTRING16(("Set locked: marking file '%S' locked", Name())); + if (iLockTimeout > 0) + { + if (!iLockTimer) + { + iLockTimer = CPeriodic::NewL(CActive::EPriorityHigh); + } + + // attempt to refresh when one third of the timeout has expired + TCallBack callBack(CRsfwFileEntry::LockTimerExpiredL, this); + iLockTimer->Start(1000000*(iLockTimeout/KLockRefreshAdjustment), + 1000000*(iLockTimeout/KLockRefreshAdjustment), + callBack); + } + iFlags |= KNodeHasValidLock; + iLockManager = lockManager; + iLockManager->AddLockedEntryL(this); + if (aLockToken) + { + // We were not just refreshing the lock + delete iLockToken; + iLockToken = aLockToken; + } + ReportEvent(KNotifyNodeModified); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::RemoveLocked +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::RemoveLocked() + { + DEBUGSTRING16(("Remove locked: marking file '%S' unlocked", Name())); + if (iFlags & KNodeHasValidLock) + { + iLockManager->RemoveLockedEntry(this); + iLockManager = NULL; // will be set in SetLockedL, if needed once again + iFlags &= ~KNodeHasValidLock; + ReportEvent(KNotifyNodeModified); + } + + if (iLockToken) + { + delete iLockToken; + iLockToken = NULL; + } + if (iLockTimer) + { + delete iLockTimer; + iLockTimer = NULL; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::LockTimerExpiredL +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileEntry::LockTimerExpiredL(TAny* aParam) + { + CRsfwFileEntry* fe = static_cast(aParam); + DEBUGSTRING16(("Lock timer expired for '%S'", fe->Name())); + fe->iLockManager->RefreshLockL(fe); + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::UseCachedData +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::UseCachedData() + { + // now meta data should tell us whether to use cached data or not + return iUseCachedData && !RemotelyDirty(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetAttribValidationTime +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetAttribValidationTime() + { + iAttribValidation.UniversalTime(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ExternalizeL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ExternalizeL(RWriteStream& aStream) const + { + DEBUGSTRING16(("CRsfwFileEntry::ExternalizeL for node %d", iFid.iNodeId)); + DEBUGSTRING16(("iFlags: %d", &iFlags)); + // The node Id must be the first entry + + // iNodeId, iParentNodeId, iType, iSize, iAtt, iModified, iFlags, + // iCachedSize, iCachePriority + // iCacheName, iName, iMimeType, + // iOpaqueFileId, iLockToken + + aStream.WriteInt32L(iFid.iNodeId); + if (iParent) + { + aStream.WriteUint32L(iParent->Fid().iNodeId); + } + else + { + // Root + aStream.WriteUint32L(0); + } + aStream.WriteUint8L(iType); + aStream.WriteInt32L(iSize); + aStream.WriteUint32L(iAtt); + aStream.WriteUint32L(I64HIGH(iModified.Int64())); + aStream.WriteUint32L(I64LOW(iModified.Int64())); + aStream.WriteUint32L(iFlags); + aStream.WriteInt32L(iCachedSize); + aStream.WriteInt32L(iCachePriority); + aStream.WriteInt32L(iUseCachedData); + aStream << iCacheName; + + HBufC* null = HBufC::NewLC(0); + if (iName) + { + aStream << *iName; + } + else + { + aStream << *null; + } + + if (iMimeType) + { + aStream << *iMimeType; + } + else + { + aStream << *null; + } + + if (iOpaqueFileId) + { + aStream << *iOpaqueFileId; + } + else + { + aStream << *null; + } + + if (iLockToken) + { + aStream << *iLockToken; + } + else + { + aStream << *null; + } + + CleanupStack::PopAndDestroy(null); // null + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::InternalizeL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::InternalizeL(RReadStream& aStream) + { + DEBUGSTRING16(("CRsfwFileEntry::InternalizeL for node %d", iFid.iNodeId)); + // iNodeId, iParentNodeId, iType, iSize, iAtt, iModified, iFlags, + // iCachedSize, iCachePriority + // iCacheName, iName, iMimeType, + // iOpaqueFileId, iLockToken + + // make some basic checking whether data being internalized is correct + iFid.iNodeId = aStream.ReadInt32L(); + if (iFid.iNodeId < 0) + { + User::Leave(KErrCorrupt); + } + iParentNodeId = aStream.ReadInt32L(); + if (iParentNodeId < 0) + { + User::Leave(KErrCorrupt); + } + iType = aStream.ReadUint8L(); + iSize = aStream.ReadInt32L(); + if (iSize < 0) + { + User::Leave(KErrCorrupt); + } + iAtt = aStream.ReadUint32L(); + TInt highTime = aStream.ReadUint32L(); + TInt lowTime = aStream.ReadUint32L(); + iModified = MAKE_TINT64(highTime, lowTime); + iFlags = aStream.ReadUint32L(); + DEBUGSTRING16(("iFlags: %d", &iFlags)); + iCachedSize = aStream.ReadInt32L(); + if (iCachedSize < 0) + { + User::Leave(KErrCorrupt); + } + iCachePriority = aStream.ReadInt32L(); + iUseCachedData = aStream.ReadInt32L(); + aStream >> iCacheName; + + HBufC* buf = HBufC::NewL(aStream, KMaxPath); + if (buf->Length()) + { + iName = buf; + } + else + { + delete buf; + buf = NULL; + } + + // MimeType + HBufC8* buf8 = HBufC8::NewL(aStream, KMaxPath); + if (buf8->Length()) + { + iMimeType = buf8; + } + else + { + delete buf8; + } + + // OpaqueFileId + buf8 = HBufC8::NewL(aStream, KMaxPath); + if (buf8->Length()) + { + iOpaqueFileId = buf8; + } + else + { + delete buf8; + } + + // LockToken + buf8 = HBufC8::NewL(aStream, KMaxPath); + if (buf8->Length()) + { + iLockToken = buf8; + } + else + { + delete buf8; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetType +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetType(TUint8 aType) + { + TUint8 oldType = iType; + iType = aType; + if (aType == KNodeTypeDir) + { + iAtt |= KEntryAttDir; + } + else + { + iAtt &= ~KEntryAttDir; + } + if (iType != oldType) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetSize +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetSize(TInt aSize) + { + TInt oldSize = iSize; + iSize = aSize; + if (iSize != oldSize) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetModified +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetModified(const TTime& aModified) + { + TTime oldModified = iModified; + iModified = aModified; + if (iModified != oldModified) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetAtt +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetAtt(TUint aAtt) + { + // Don't change caching and protected state + TUint oldAtt = iAtt; + if (IsFullyCached()) + { + aAtt &= ~KEntryAttRemote; + } + else + { + aAtt |= KEntryAttRemote; + } + iAtt = aAtt; + + // Set node type + if (iAtt & KEntryAttDir) + { + iType = KNodeTypeDir; + } + else + { + iType = KNodeTypeFile; + } + + if (iAtt != oldAtt) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetMimeTypeL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetMimeTypeL(const TDesC8& aMimeType) + { + if (iMimeType) + { + delete iMimeType; + iMimeType = NULL; + } + if (aMimeType.Length()) + { + iMimeType = aMimeType.AllocL(); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetOpaqueFileIdL +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetOpaqueFileIdL(const TDesC8& aOpaqueFileId) + { + if (iOpaqueFileId) + { + delete iOpaqueFileId; + iOpaqueFileId = NULL; + } + if (aOpaqueFileId.Length()) + { + iOpaqueFileId = aOpaqueFileId.AllocL(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsLocallyDirty +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsLocallyDirty() const + { + DEBUGSTRING16(("IsLocallyDirty for file %S", Name())); + return (iFlags & KNodeLocallyDirty) != 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsCancelled +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsCancelled() const + { + DEBUGSTRING16(("CRsfwFileEntry::IsCancelled()")); + return (iFlags & KNodeWritingCancelled) != 0; + } + + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetLocallyDirty +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetLocallyDirty() + { + DEBUGSTRING16(("SetLocallyDirty for file %S", Name())); + TUint oldFlags = iFlags; + iFlags |= KNodeLocallyDirty; + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ResetLocallyDirty +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ResetLocallyDirty() + { + DEBUGSTRING16(("ResetLocallyDirty for file %S", Name())); + TUint oldFlags = iFlags; + iFlags &= ~KNodeLocallyDirty; + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::RemotelyDirty +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::RemotelyDirty() const + { + return (iFlags & KNodeRemotelyDirty) != 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetRemotelyDirty +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetRemotelyDirty() + { + TUint oldFlags = iFlags; + iFlags |= KNodeRemotelyDirty; + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ResetRemotelyDirty +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ResetRemotelyDirty() + { + TUint oldFlags = iFlags; + iFlags &= ~KNodeRemotelyDirty; + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsMarked +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsMarked() const + { + return (iFlags & KNodeMarked) != 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Mark +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::Mark() + { + // This is transient state (so, it need not be saved persistently) + iFlags |= KNodeMarked; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::Unmark +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::Unmark() + { + iFlags &= ~KNodeMarked; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetFlags +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetFlags(TUint aFlags) + { + TUint oldFlags = iFlags; + iFlags |= aFlags; + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ResetFlags +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ResetFlags(TUint aFlags) + { + TUint oldFlags = iFlags; + iFlags &= ~aFlags; + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetOpenedForWriting +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetOpenedForWriting(TBool aOpenedForWriting) + { + TUint oldFlags = iFlags; + if (aOpenedForWriting) + { + DEBUGSTRING(("CRsfwFileEntry::SetOpenedForWriting TRUE")); + iFlags |= KNodeOpenedForWriting; + } + else + { + DEBUGSTRING(("CRsfwFileEntry::SetOpenedForWriting FALSE")); + iFlags &= ~KNodeOpenedForWriting; + } + if (iFlags != oldFlags) + { + ReportEvent(KNotifyNodeModified); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsOpenedForWriting +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsOpenedForWriting() const + { + DEBUGSTRING(("CRsfwFileEntry::IsOpenedForWriting")); + return (iFlags & KNodeOpenedForWriting) != 0; + } + + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::SetNewlyCreated +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::SetNewlyCreated() + { + iFlags |= KNodeNewlyCreated; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ResetNewlyCreated +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ResetNewlyCreated() + { + iFlags &= ~KNodeNewlyCreated; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsNewlyCreated +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsNewlyCreated() const + { + return (iFlags & KNodeNewlyCreated) != 0; + } + + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::IsLocked +// ---------------------------------------------------------------------------- +// +TBool CRsfwFileEntry::IsLocked() const + { + return (iFlags & KNodeHasValidLock) != 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ReportEvent +// ---------------------------------------------------------------------------- +// +void CRsfwFileEntry::ReportEvent(TInt aEvent) + { + // If there is no file table, + // this is a transient entry + if (iFileTable && iFileTable->Permanence()) + { + iFileTable->HandleMetaDataEvent(aEvent, this); + } + } + + +void CRsfwFileEntry::ResolveDirtyFilesL() + { + DEBUGSTRING(("CRsfwFileEntry::ResolveDirtyFilesL")); + if (this->Type() == KNodeTypeDir) + { + for (int i = 0; i < iKids.Count(); i++) + { + iKids[i]->ResolveDirtyFilesL(); + } + } + else if (this->Type() == KNodeTypeFile) + { + // this is a leaf + iFileTable->ResolveDirtyFileL(this); + } + + } diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwfiletable.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwfiletable.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,816 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: metadata struct for remote files +* +*/ + + +#include + +#include "rsfwfiletable.h" +#include "rsfwfileentry.h" +#include "rsfwfileengine.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwrfeserver.h" +#include "rsfwwaitnotemanager.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::NewL +// ---------------------------------------------------------------------------- +// +CRsfwFileTable* CRsfwFileTable::NewL(CRsfwVolume* aVolume, TFileName& aCachePath) + { + CRsfwFileTable* self = new (ELeave) CRsfwFileTable(); + DEBUGSTRING(("CRsfwFileTable: in NewL 0x%x", self)); + CleanupStack::PushL(self); + self->ConstructL(aVolume, aCachePath); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::ConstructL(CRsfwVolume* aVolume, TFileName& aCachePath) + { + iFs = CRsfwRfeServer::Env()->iFs; + // The root will be number 1 + iNodeId = 1; + iVolume = aVolume; + iRootFep = NULL; + iCachePath.Copy(aCachePath); + iPermanence = iVolume->iMountInfo.iMountStatus.iPermanence; + iMetaDataFilePath.Copy(aCachePath); + iMetaDataFilePath.Append(KMetaDataFileName); + iMetaDataEvents.Reset(); + SetupCacheL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::~CRsfwFileTable +// ---------------------------------------------------------------------------- +// +CRsfwFileTable::~CRsfwFileTable() + { + if (iRootFep) + { + // Delete the whole tree recursively + delete iRootFep; + iRootFep = NULL; + } + // Discard events + iMetaDataEvents.Close(); + iMetaDataSlots.Close(); + if (iMetaDataStore) + { + delete iMetaDataStore; + } + } + + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::AddL +// this function associates aFep with this file table but does no +// yet set to any other node's child (or root node), that must be done sepately +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::AddL(CRsfwFileEntry* aFep) + { + // Just assign a unique id + TFid newFid; + newFid.iVolumeId = iVolume->iMountInfo.iMountStatus.iVolumeId; + newFid.iNodeId = iNodeId; + aFep->SetFid(newFid); + aFep->iFileTable = this; + iNodeId++; + if (!iRootFep) + { + iRootFep = aFep; + } + // add item to metadata LRU list, + // only add childless directories and non-cached files + if ( (aFep->Type() == KNodeTypeFile && aFep->iCachedSize == 0) + || (aFep->Type() == KNodeTypeDir && aFep->Kids()->Count() == 0) + || (aFep->Type() == KNodeTypeUnknown) ) + { + iVolume->iVolumeTable->AddToMetadataLRUPriorityListL(aFep, ECachePriorityNormal); + } + // Note that the first added entry will always be the root + HandleMetaDataEvent(KNotifyNodeAdded, aFep); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::Remove +// removed this fileentry and disconnects from the parent +// does not delete the kid file/directory entries +// in practise this means that if deleting a directory, all its entries must be deleted +// recursively first +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::RemoveL(CRsfwFileEntry* aFep) + { + DEBUGSTRING(("CRsfwFileTable::RemoveL")); + // remove item from metadata LRU list + iVolume->iVolumeTable->RemoveFromMetadataLRUPriorityList(aFep); + + if (aFep == iCurrentParent) + { + iCurrentParent = NULL; + } + if (iPermanence) + { + aFep->RemoveCacheFile(); + HandleMetaDataEvent(KNotifyNodeRemoved, aFep); + } + + // remove this file entry from its parent node + if (aFep->iParent) + { + aFep->iParent->RemoveKidL(aFep); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::Lookup +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileTable::Lookup(const TFid& aFid) + { + if (!iRootFep) + { + return NULL; + } + if (iRootFep->Fid().iNodeId == aFid.iNodeId) + { + return iRootFep; + } + // Try to optimize by starting from the latest parent + CRsfwFileEntry* fep = NULL; + if (iCurrentParent) + { + fep = iCurrentParent->Lookup(aFid); + } + if (!fep) + { + fep = iRootFep->Lookup(aFid); + } + if (fep) + { + iCurrentParent = fep->Parent(); + } + return fep; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::DumpL +// ---------------------------------------------------------------------------- +// +#ifdef _DEBUG +void CRsfwFileTable::DumpL(TBool aAll) + { + if (iRootFep) + { + iRootFep->PrintL(0, ETrue, aAll); + } + } +#else +void CRsfwFileTable::DumpL(TBool /* aAll */) + { + } +#endif //DEBUG + + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::SetPermanenceL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::SetPermanenceL(TBool aPermanence) + { + if (iPermanence != aPermanence) + { + iPermanence = aPermanence; + if (!iPermanence) + { + delete iMetaDataStore; + iMetaDataStore = NULL; + } + SetupCacheL(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::HandleMetaDataEvent +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::HandleMetaDataEvent(TInt aEvent, CRsfwFileEntry* aFep) + { + if (iMetaDataSaveState == EMetaDataSaveFailed) + { + // No use + return; + } + + switch (aEvent) + { + + case KNotifyNodeAdded: + { + // There should not be any previous additions + AddEvent(aEvent, aFep); + } + break; + + case KNotifyNodeModified: + { + // There may appear spurious modifications + // to removed entries (like cache state set to false). + // We filter them out. + if (!NodeEvent(aFep->Fid().iNodeId)) + { + AddEvent(aEvent, aFep); + } + } + break; + + case KNotifyNodeRemoved: + { + TMetaDataEvent* oldEvent = NodeEvent(aFep->Fid().iNodeId); + if (oldEvent) + { + if (oldEvent->iEvent == KNotifyNodeAdded) + { + // just remove a previous "added" + RemoveEvent(oldEvent->iNodeId); + AddEvent(aEvent, aFep); + } + else + { + // Just replace "modified" (or duplicate "deleted") + // with "deleted" + oldEvent->iEvent = KNotifyNodeRemoved; + } + } + else + { + AddEvent(aEvent, aFep); + } + } + break; + + default: + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::LoadMetaDataL +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwFileTable::LoadMetaDataL() + { + // When this function is called the root node + // must already be created in the file table + iMetaDataStore->CompactL(); + iMetaDataStore->ResetL(EFalse); + + RPointerArray feps; + CleanupClosePushL(feps); + + TBool done = EFalse; + while (!done) + { + CRsfwFileEntry* fep; + TMetaDataSlot slot; + TRAPD(err, LoadNodeL(fep, slot.iSlotId)); + if (err == KErrNone) + { + if (fep != NULL) + { + feps.Append(fep); + slot.iNodeId = fep->Fid().iNodeId; + iMetaDataSlots.Append(slot); + if (!fep->iParentNodeId) + { + // This must be the root + DEBUGSTRING(("Root found at slot %d", + iMetaDataSlots.Count() - 1)); + iRootFep = fep; + } + } + } + else + { + // All or nothing ... + DEBUGSTRING(("LoadNode returned with err = %d", err)); + if (err != KErrEof) + { + User::Leave(err); + } + done = ETrue; + } + } + + // Now we have the restored the file entries + TInt i; + for (i = 0; i < feps.Count(); i++) + { + CRsfwFileEntry* fep = feps[i]; + // Determine the next free node id + if (fep->Fid().iNodeId >= iNodeId) + { + iNodeId = fep->Fid().iNodeId + 1; + } + + if (fep->iParentNodeId == 0) + { + // This is the root node + fep->SetParent(NULL); + } + else if (fep->iParentNodeId == 1) + { + // The parent is the root node + fep->SetParent(iRootFep); + iRootFep->iKids.Append(fep); + } + else + { + TInt j; + // This is O(n**2) + for (j = 0; j < feps.Count(); j++) + { + if (j != i) + { + // Find the parent for the node + CRsfwFileEntry* parent = feps[j]; + if (fep->iParentNodeId == parent->Fid().iNodeId) + { + // Set up the two-way linkage + fep->SetParent(parent); + parent->iKids.Append(fep); + break; + } + } + } + } + } + + // Final fixes + for (i = 0; i < feps.Count(); i++) + { + CRsfwFileEntry* fep = feps[i]; + // Fix volume ids and such ... + TFid fid; + fid = fep->Fid(); + fid.iVolumeId = iVolume->iMountInfo.iMountStatus.iVolumeId; + fep->SetFid(fid); + fep->iFileTable = this; + // Add to LRU list (only cached files) + if ( fep->Type() == KNodeTypeFile && fep->IsCached() + && (!iVolume->iVolumeTable->iUseExternalizedLRUList)) + { + iVolume->iVolumeTable->AddToLRUPriorityListL(fep, ECachePriorityNormal); + } + // add item to metadata LRU list, + // only add childless directories and non-cached files + if ( (fep->Type() == KNodeTypeFile && fep->iCachedSize == 0) + || (fep->Type() == KNodeTypeDir && fep->Kids()->Count() == 0) ) + { + iVolume->iVolumeTable->AddToMetadataLRUPriorityListL(fep, ECachePriorityNormal); + } + + // Check consistency + if ((fep != iRootFep) && (!fep->Parent())) + { + // Should never happen + DEBUGSTRING16(("LodaMetaDataL() - parent missing for '%S'", + fep->Name())); + } + } + + // Now we don't need the file entry pointer array any more + CleanupStack::PopAndDestroy(&feps); // feps + return iRootFep; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::SaveMetaDataDelta +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileTable::SaveMetaDataDelta() + { + DEBUGSTRING16(("CRsfwFileTable::SaveMetaDataDelta")); + TRAPD(err, SaveMetaDataDeltaL()); + if (err != KErrNone) + { + DEBUGSTRING(("SaveMetaDataDeltaL() returns %d", err)); + // Stop recording meta data + iMetaDataEvents.Reset(); + iMetaDataSaveState = EMetaDataSaveFailed; + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::SetupCacheL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::SetupCacheL() + { + if (iPermanence) + { + iMetaDataStore = CRsfwMetaDataStore::NewL(iMetaDataFilePath); + DEBUGSTRING(("SetupCacheL()")); + // The format of label is :. + TRsfwMountConfig mountConfig; + TRAPD(err, iMetaDataStore->GetMountConfigL(mountConfig)); + if ((err != KErrNone) || + mountConfig.iUri.Compare(iVolume->iMountInfo.iMountConfig.iUri) != + 0) + { + // The saved metadata is not current - delete all + DEBUGSTRING(("Clearing Metadata ...")); + delete iMetaDataStore; + iMetaDataStore = NULL; + ClearCacheL(); + // Start from scratch + iMetaDataStore = CRsfwMetaDataStore::NewL(iMetaDataFilePath); + iMetaDataStore->SetMountConfigL(iVolume->iMountInfo.iMountConfig); + } + } + else + { + ClearCacheL(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::TotalCachedSize +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileTable::TotalCachedSize() + { + if (!iRootFep) + { + return 0; + } + return iRootFep->TotalCachedSize(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::TotalEntryCount +// ---------------------------------------------------------------------------- +// +TInt CRsfwFileTable::TotalEntryCount() + { + if (!iRootFep) + { + return 0; + } + return iRootFep->TotalEntryCount(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::ClearCacheL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::ClearCacheL() + { + DEBUGSTRING(("Clearing cache ...")); + TFileName cachePath = iCachePath; + _LIT(KWild, "*"); + cachePath.Append(KWild); + + CFileMan* fM = CFileMan::NewL(iFs); + CleanupStack::PushL(fM); + TInt err = fM->Delete(cachePath, CFileMan::ERecurse); + CleanupStack::PopAndDestroy(fM); // fM + if (err != KErrNone) + { + DEBUGSTRING16(("Cache cleaning of '%S' failed with err=%d", + &cachePath, + err)); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::NodeEvent +// ---------------------------------------------------------------------------- +// +TMetaDataEvent* CRsfwFileTable::NodeEvent(TInt aNodeId) + { + // Search downwards (for efficiency) + TInt count = iMetaDataEvents.Count(); + if (count) + { + TInt i; + for (i = count - 1; i >= 0; i--) + { + if (iMetaDataEvents[i].iNodeId == aNodeId) + { + return &iMetaDataEvents[i]; + } + } + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::AddEvent +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::AddEvent(TInt aEvent, CRsfwFileEntry* aFep) + { + TMetaDataEvent event; + event.iEvent = aEvent; + event.iEntry = aFep; + event.iNodeId= aFep->Fid().iNodeId; + // For searching efficiency insert at the head + if (iMetaDataEvents.Append(event) != KErrNone) + { + iMetaDataEvents.Close(); + iMetaDataSaveState = EMetaDataSaveFailed; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::RemoveEvent +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::RemoveEvent(TInt aNodeId) + { + TInt i; + for (i = 0; i < iMetaDataEvents.Count(); i++) + { + if (iMetaDataEvents[i].iNodeId == aNodeId) + { + iMetaDataEvents.Remove(i); + return; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::LoadNodeL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::LoadNodeL(CRsfwFileEntry*& aFep, TInt &aSlot) + { + // Internalize a file entry + // Read data from the file at the specified slot + HBufC8* buf = HBufC8::NewLC(KMaxExternalizedFileEntrySize); + TPtr8 ptr = buf->Des(); + TUint8* data = const_cast(ptr.Ptr()); + TInt dataLength; + iMetaDataStore->GetNextDataL(data, dataLength, aSlot); + RMemReadStream stream(data, dataLength); + CleanupClosePushL(stream); + CRsfwFileEntry* fep = CRsfwFileEntry::NewL(stream); + DEBUGSTRING16(("CRsfwFileTable::LoadNodeL: Loaded node '%S'(id=%d, pid=%d, cn='%S')", + fep->Name(), + fep->Fid().iNodeId, + fep->iParentNodeId, + &fep->iCacheName)); + CleanupStack::PopAndDestroy(2); // stream, buf + + aFep = fep; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::SaveNodeL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::SaveNodeL(CRsfwFileEntry* aFep, TInt& aSlot) + { + // Externalize the file entry + HBufC8* buf = HBufC8::NewLC(KMaxExternalizedFileEntrySize); + TPtr8 ptr = buf->Des(); + TUint8* data = const_cast(ptr.Ptr()); + TInt dataLen; + + RMemWriteStream stream(data, KMaxExternalizedFileEntrySize); + CleanupClosePushL(stream); + + if (aFep) + { + // dump the externalized data in the memory buffer + // stream << *aFep; + aFep->ExternalizeL(stream); + MStreamBuf* streamBuf = stream.Sink(); + dataLen = streamBuf->TellL(MStreamBuf::EWrite).Offset(); + stream.CommitL(); + } + else + { + + DEBUGSTRING(("Removing slot %d", aSlot)); + // This will clear the slot + data = NULL; + dataLen = 0; + } + + // Write data to the file at the specified slot + iMetaDataStore->PutDataL(data, dataLen, aSlot); + + CleanupStack::PopAndDestroy(2, buf); // stream, buf + } + +// ---------------------------------------------------------------------------- +// CRsfwFileTable::SaveMetaDataDeltaL +// ---------------------------------------------------------------------------- +// +void CRsfwFileTable::SaveMetaDataDeltaL() + { + DEBUGSTRING(("CRsfwFileTable::SaveMetaDataDeltaL")); + if (!iPermanence) + { + return; + } + + if (iMetaDataEvents.Count() == 0) + + { + // Nothing to do + return; + } + + switch (iMetaDataSaveState) + { + case EMetaDataSaveNone: + iMetaDataStore->ResetL(ETrue); + iMetaDataSaveState = EMetaDataSaveStarted; + break; + + case EMetaDataSaveStarted: + break; + + case EMetaDataSaveFailed: + DEBUGSTRING(("EMetaDataSaveFailed!")); + User::Leave(KErrGeneral); + break; + + default: + break; + } + + TInt i; + for (i = 0; i < iMetaDataEvents.Count(); i++) + { + TInt slotPos; + TMetaDataEvent *event = &iMetaDataEvents[i]; + + DEBUGSTRING(("SaveMetaDataDeltaL: id=%d, event=%d", + event->iNodeId, + event->iEvent)); + + switch (event->iEvent) + { + case KNotifyNodeModified: + case KNotifyNodeAdded: + { + TMetaDataSlot s; // dummy for finding + s.iNodeId = event->iNodeId; + slotPos = iMetaDataSlots.Find(s); + TInt slotId; + if (slotPos != KErrNotFound) + { + slotId = iMetaDataSlots[slotPos].iSlotId; + } + else + { + // We don't have a slot yet + slotId = -1; + } + SaveNodeL(event->iEntry, slotId); + if (slotPos == KErrNotFound) + { + TMetaDataSlot slot; + slot.iNodeId = event->iEntry->Fid().iNodeId; + slot.iSlotId = slotId; + iMetaDataSlots.Append(slot); + } + else + { + // The index may have changed + iMetaDataSlots[slotPos].iSlotId = slotId; + } + } + break; + + case KNotifyNodeRemoved: + { + TMetaDataSlot s; // dummy for finding + s.iNodeId = event->iNodeId; + slotPos = iMetaDataSlots.Find(s); + if (slotPos != KErrNotFound) + { + TInt slotId = iMetaDataSlots[slotPos].iSlotId; + iMetaDataSlots.Remove(slotPos); + // Saving null is the same as removing + SaveNodeL(NULL, slotId); + } + } + break; + + default: + break; + } + } + iMetaDataEvents.Reset(); + + User::LeaveIfError(iMetaDataStore->Commit()); +#if 0 + iMetaDataStore->CompactL(); +#endif + } + + +void CRsfwFileTable::ResolveDirtyFilesL() + { + DEBUGSTRING(("CRsfwFileTable::ResolveDirtyFilesL")); + if (iRootFep) + { + iRootFep->ResolveDirtyFilesL(); + } + SaveMetaDataDeltaL(); + } + +void CRsfwFileTable::ResolveDirtyFileL(CRsfwFileEntry *aFileEntry) + { + DEBUGSTRING(("CRsfwFileTable::ResolveDirtyFileL")); + if ((aFileEntry->IsOpenedForWriting() && (aFileEntry->CacheFileName()))) + { + + DEBUGSTRING16(("file %S has uncommitted modifications, must be saved locally", aFileEntry->Name())); + // file with uncommitted modifications + // (i.e. saving changes to a remote server failed + // show "save as" dialog for this file + TRequestStatus status; + TInt err; + TPckgBuf savetoRequest; + TBuf fileSizeString; + TEntry fEntry; + CRsfwRfeServer::Env()->iFs.Entry((*(aFileEntry->CacheFileName())), fEntry); + fileSizeString.Num(fEntry.iSize); + TPtrC cacheDriveLetter = aFileEntry->CacheFileName()->Left(1); + + savetoRequest().iMethod = TRsfwNotPluginRequest::ESaveToDlg; + savetoRequest().iDriveName = Volume()->MountInfo()->iMountConfig.iName; + savetoRequest().iFileName = *(aFileEntry->Name()); + savetoRequest().iCacheDrive = cacheDriveLetter; + savetoRequest().iFileSize = fileSizeString; + + + RNotifier notifier; + User::LeaveIfError(notifier.Connect()); + notifier.StartNotifierAndGetResponse(status, KRsfwNotifierPluginUID, + savetoRequest, savetoRequest); + User::WaitForRequest(status); + notifier.NotifyCancel(); + notifier.Close(); + + if (status.Int() != KErrCancel) + { + // move the file from cache to the new location + HBufC* newName = HBufC::NewMaxLC(KMaxPath); + TPtr pathPtr = newName->Des(); + pathPtr = savetoRequest().iFileName; + CFileMan* fman = CFileMan::NewL(CRsfwRfeServer::Env()->iFs); + // we assume that this is local-to-local move, and can be synch. call + err = fman->Move(*(aFileEntry->CacheFileName()), pathPtr, CFileMan::EOverWrite); + delete fman; + if (err == KErrNone) + { + Volume()->iVolumeTable->WaitNoteManager()->ShowFileSavedToDialogL(pathPtr); + } + else + { + Volume()->iVolumeTable->WaitNoteManager()->ShowFailedSaveNoteL(); + } + + CleanupStack::PopAndDestroy(newName); + } + + // in any case, remove the file entry from the file table and cache + // (has been moved or deleted) + RemoveL(aFileEntry); + delete aFileEntry; + aFileEntry = NULL; + DEBUGSTRING(("possible uncommitted modifications resolved")); + } + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwflushstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwflushstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,171 @@ +/* +* Copyright (c) 2007 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for fetching data without caching it permanently +* +*/ + + +#include "rsfwflushstatemachine.h" +#include "rsfwinterface.h" +#include "rsfwfileentry.h" +#include "rsfwfileengine.h" +#include "rsfwrfeserver.h" +#include "rsfwvolumetable.h" +#include "rsfwfiletable.h" +#include "rsfwwaitnotemanager.h" +#include "rsfwvolume.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// CRsfwFlushStateMachine::CRsfwFlushStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwFlushStateMachine::CRsfwFlushStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwFlushStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwFlushStateMachine::CompleteRequestL(TInt aError) + { + DEBUGSTRING(("CRsfwFlushStateMachine::CompleteRequestL()")); + // If we just wrote the file to the server set attributes from the cache + // file's attributes.Even if writing the file failed, attributes should + // reflect the local modifications + if (Node()->CacheFileName()) + { + FileEngine()->SetupAttributes(*Node()); + } + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwFlushStateMachine::TFlushDataToServerState::TFlushDataToServerState +// ---------------------------------------------------------------------------- +// +CRsfwFlushStateMachine::TFlushDataToServerState::TFlushDataToServerState( + CRsfwFlushStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwFlushStateMachine::TFlushDataToServerState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwFlushStateMachine::TFlushDataToServerState::EnterL() + { + DEBUGSTRING(("CRsfwFlushStateMachine::TFlushDataToServerState::EnterL()")); + + TDesC* cacheNamep; + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + TRfeFlushInArgs* inArgs = + static_cast(iOperation->iInArgs); + + + if (iOperation->Node()->IsCancelled()) + { + // user has cancelled writing this file to server even before we got to flush + // (when the file was being written to the local cache) + iOperation->HandleRemoteAccessResponse(0, KErrCancel); + } + else + { + TInt firstByte = inArgs->iFirstByte; + TInt dataLength = inArgs->iDataLength; + TInt totalSize = inArgs->iTotalSize; + + cacheNamep = iOperation->Node()->CacheFileName(); + + _LIT8(KTextPlain, "text/plain"); + HBufC* fullName = + iOperation->FileEngine()->FullNameLC(*(iOperation->Node())); + + + // get the MIME-type of the file + HBufC8* contentType = iOperation->FileEngine()->GetContentType(*cacheNamep); + + if (contentType) + { + CleanupStack::PushL(contentType); + } + else + { + contentType = KTextPlain().AllocLC(); + } + + if ((firstByte == 0) && + (dataLength == totalSize)) + { + // non-partial put + TUint transactionId + = iOperation->FileEngine()->RemoteAccessL()->PutFileL(*cacheNamep, + *fullName, + *contentType, + iOperation); + + } + else + { + // partial put + TUint transactionId + = iOperation->FileEngine()->RemoteAccessL()->PutFileL(*cacheNamep, + *fullName, + *contentType, + firstByte, + dataLength-firstByte, + totalSize, + iOperation); + } + + CleanupStack::PopAndDestroy(2); // fullName, contentType + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwFlushStateMachine::TFlushDataToServerState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwFlushStateMachine::TFlushDataToServerState::CompleteL() + { + DEBUGSTRING(("CRsfwFlushStateMachine::TFlushDataToServerState::CompleteL()")); + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwFlushStateMachine::TFlushDataToServerState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwFlushStateMachine::TFlushDataToServerState::ErrorL(TInt aCode) + { + DEBUGSTRING(("CRsfwFlushStateMachine::TFlushDataToServerState::ErrorL() %d", aCode)); + return iOperation->CompleteRequestL(aCode); + } + + +// End of file + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwgetattributesstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwgetattributesstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,226 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for getting attributes of a file +* +*/ + + +#include "rsfwgetattributesstatemachine.h" +#include "rsfwopenbypathstatemachine.h" +#include "rsfwinterface.h" +#include "rsfwrferequest.h" +#include "rsfwrfeoperation.h" +#include "rsfwfileentry.h" +#include "rsfwfileengine.h" +#include "mdebug.h" +#include "rsfwdirentattr.h" +#include "rsfwvolumetable.h" + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::CRsfwGetAttributesStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwGetAttributesStateMachine::CRsfwGetAttributesStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwGetAttributesStateMachine::CompleteRequestL(TInt aError) + { + TRfeGetAttrOutArgs* outArgs = static_cast(iOutArgs); + + if (!aError) + { + outArgs->iAttr.iAtt = Node()->Att(); + outArgs->iAttr.iSize = Node()->Size(); + outArgs->iAttr.iModified = Node()->Modified(); + } + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::TRefreshAttributesState::TRefreshAttributesState +// ---------------------------------------------------------------------------- +// +CRsfwGetAttributesStateMachine:: +TRefreshAttributesState:: +TRefreshAttributesState(CRsfwAttributeRefreshingStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::TRefreshAttributesState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwGetAttributesStateMachine::TRefreshAttributesState::EnterL() + { + DEBUGSTRING(("CRsfwGetAttributesStateMachine::TRefreshAttributesState::EnterL")); + TInt err = KErrNone; + + if (iOperation->Node()) + { + DEBUGSTRING(("getting attributes of fid %d", + iOperation->Node()->Fid().iNodeId)); + + // as the entry is "needed" move it to the back of metadata LRU list + iOperation->Volumes()->MoveToTheBackOfMetadataLRUPriorityListL(iOperation->Node()); + + if (!(iOperation->FileEngine()->UseCachedAttributes(*iOperation->Node()))) + { + // If we find the file entry and + // the time window to use cached attributes has passed. + // Store the old attributes + delete iOperation->iDirEntAttrOld; + iOperation->iDirEntAttrOld = NULL; + iOperation->iDirEntAttrOld = CRsfwDirEntAttr::NewL(); + iOperation->Node()->GetAttributesL(*iOperation->iDirEntAttrOld); + if (!iOperation->FileEngine()->WriteDisconnected()) + { + iOperation->FileEngine()->GetAttributesL( + *(iOperation->Node()), + iOperation->iDirEntAttr, + iOperation->Node()->Type(), + iOperation); + } + else + { + iOperation->HandleRemoteAccessResponse(0, KUpdateNotRequired); + } + if (err) + { + User::Leave(err); + } + } + else + { + // use cached attributes + iOperation->HandleRemoteAccessResponse(0, KUpdateNotRequired); + } + } + else + { + User::Leave(KErrPathNotFound); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::TRefreshAttributesState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwGetAttributesStateMachine::TState* +CRsfwGetAttributesStateMachine::TRefreshAttributesState::CompleteL() + { + + DEBUGSTRING(("TRefreshAttributesState::CompleteL for fid %d", + iOperation->Node()->Fid().iNodeId)); + + // from CRsfwFileEngine::UpdateAttributes() + iOperation->Node()->SetAttributesL(*iOperation->iDirEntAttr, ETrue); + + if (iOperation->Node()->IsOpenedForWriting()) + { + iOperation->Node()->iUseCachedData = ETrue; + } + else if (iOperation->FileEngine()->DataChanged(*iOperation->iDirEntAttrOld, + *iOperation->iDirEntAttr)) + { + // discard the old cache file + // this will also call SetCached(EFalse) etc... + iOperation->Node()->RemoveCacheFile(); + } + + DEBUGSTRING(("Attributes: attr=0x%x, size=%d, time=", + iOperation->Node()->Att(), + iOperation->Node()->Size())); + DEBUGTIME((iOperation->Node()->Modified())); + + // from CRsfwFileEngine::UpdateFileAttributes/UpdateDirAttributes + return CompleteOurRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::TRefreshAttributesState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwGetAttributesStateMachine::TState* +CRsfwGetAttributesStateMachine::TRefreshAttributesState::ErrorL(TInt aCode) + { + DEBUGSTRING(("CRsfwGetAttributesStateMachine::TRefreshAttributesState::ErrorL %d", aCode)); + if (aCode == KUpdateNotRequired) + { + // note that we should NOT set iUseCachedData to ETrue here + // (if it is false, only after fetch it should be set to true + // , or openbypath if we are writing to the file) + aCode = KErrNone; + + DEBUGSTRING(("update was not required")); + + DEBUGSTRING(("Attributes: attr=0x%x, size=%d, time=", + iOperation->Node()->Att(), + iOperation->Node()->Size())); + DEBUGTIME((iOperation->Node()->Modified())); + + } + else + { + // from CRsfwFileEngine::UpdateAttributes() + if (!(iOperation->Node()->IsOpenedForWriting())) + { + // "iOperation->Node()" has been removed from the server?? + // : remove FEP here + iOperation->Node()->RemoveCacheFile(); + } + } + return CompleteOurRequestL(aCode); + } + +// ---------------------------------------------------------------------------- +// CRsfwGetAttributesStateMachine::TRefreshAttributesState::CompleteOurRequestL +// ---------------------------------------------------------------------------- +// +CRsfwGetAttributesStateMachine::TState* +CRsfwGetAttributesStateMachine::TRefreshAttributesState::CompleteOurRequestL(TInt aCode) + { + if (iOperation->Request()->Operation()->Function() == EGetAttr) + { + // we are running in GetAttr() + return iOperation->CompleteRequestL(aCode); + } + else if (iOperation->Request()->Operation()->Function() == EOpenByPath) + { + // we are running in OpenByPath() + if (aCode == KErrNone) + { + return new (ELeave) CRsfwOpenByPathStateMachine::TRequestOpenModeState( + (CRsfwOpenByPathStateMachine *)iOperation); + } + else + { + // attributes expired, refrshing them failed, do not open the file + return iOperation->CompleteRequestL(aCode); + } + } + else + { + return NULL; + } + } + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwinterface.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwinterface.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,93 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RSFW interface + * +*/ + + +#include "rsfwinterface.h" +#include + + +// ---------------------------------------------------------------------------- +// TDirEntAttr::ExternalizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void TDirEntAttr::ExternalizeL(RWriteStream& aStream) const + { + aStream.WriteUint32L(iAtt); + aStream.WriteInt32L(iSize); + aStream.WriteUint32L(iUid3.iUid); + aStream.WriteUint32L(I64HIGH(iModified.Int64())); + aStream.WriteUint32L(I64LOW(iModified.Int64())); + } + +// ---------------------------------------------------------------------------- +// TDirEntAttr::InternalizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void TDirEntAttr::InternalizeL(RReadStream& aStream) + { + iAtt = aStream.ReadUint32L(); + iSize = aStream.ReadInt32L(); + iUid3.iUid = aStream.ReadUint32L(); + TInt highTime = aStream.ReadUint32L(); + TInt lowTime = aStream.ReadUint32L(); + iModified = MAKE_TINT64(highTime, lowTime); + } + +// ---------------------------------------------------------------------------- +// TDirEntAttr::Clear +// ---------------------------------------------------------------------------- +// +EXPORT_C void TDirEntAttr::Clear() + { + iAtt = 0; + iSize = 0; + iModified = 0; + iUid3.iUid = 0; + } + +// ---------------------------------------------------------------------------- +// TDirEnt::ExternalizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void TDirEnt::ExternalizeL(RWriteStream& aStream) const + { + iAttr.ExternalizeL(aStream); + aStream << iName; + } + +// ---------------------------------------------------------------------------- +// TDirEnt::InternalizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C void TDirEnt::InternalizeL(RReadStream& aStream) + { + iAttr.InternalizeL(aStream); + aStream >> iName; + } + +// ---------------------------------------------------------------------------- +// TDirEnt::Clear +// ---------------------------------------------------------------------------- +// +EXPORT_C void TDirEnt::Clear() + { + iAttr.Clear(); + iName.SetLength(0); + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwlockmanager.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwlockmanager.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,318 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Lock manager for locked remote files +* +*/ + + +#include "rsfwfileentry.h" +#include "rsfwrfestatemachine.h" +#include "rsfwlockmanager.h" +#include "rsfwfileentry.h" +#include "rsfwconfig.h" +#include "mdebug.h" + +// ---------------------------------------------------------------------------- + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::NewL +// ---------------------------------------------------------------------------- +// +CRsfwLockManager* CRsfwLockManager::NewL(CRsfwRemoteAccess* aRemoteAccess) + { + CRsfwLockManager* self = CRsfwLockManager::NewLC(aRemoteAccess); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::NewLC +// ---------------------------------------------------------------------------- +// +CRsfwLockManager* CRsfwLockManager::NewLC(CRsfwRemoteAccess* aRemoteAccess) + { + DEBUGSTRING(("CRsfwLockManager::NewLC")); + CRsfwLockManager* self = new (ELeave) CRsfwLockManager(); + CleanupStack::PushL(self); + self->ConstructL(aRemoteAccess); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::ConstructL(CRsfwRemoteAccess* aRemoteAccess) + { + iRemoteAccess = aRemoteAccess; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::~CRsfwLockManager +// ---------------------------------------------------------------------------- +// +CRsfwLockManager::~CRsfwLockManager() + { + iLockRefreshContexts.Close(); + + // set unlock flag for all the entries locked + while (iLockedEntries.Count() > 0) + { + CRsfwFileEntry* entry = iLockedEntries[0]; + iLockedEntries.Remove(0); + // note that RemoveLocked will call CRsfwLockManager::RemoveLockedEntry + entry->RemoveLocked(); + } + iLockedEntries.Close(); + } + + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::HandleRemoteAccessResponse +// For handling the response from RefreshLockL(). +// If the lock refresh is successful we restart the timer +// as the server may have changed the timeout. +// If the refresh request returns an error we remove the lock +// We assume that server does not hold the lock anymore, +// so we cannot re-acquire it simply by trying to refresh it again. +// Instead, we should do a fresh lock operation +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::HandleRemoteAccessResponse(TUint aId, + TInt aStatus) + { + DEBUGSTRING(("CRsfwLockManager::HandleRemoteAccessResponse id: %d, status: %d", aId, aStatus)); + TPendingLockRefreshContext lockRefresh; + lockRefresh.iId = aId; + TInt index = iLockRefreshContexts.Find(lockRefresh); + if (index != KErrNotFound) + { + lockRefresh = iLockRefreshContexts[index]; + if (aStatus == KErrNone) + { + // Note that this can leave only when creating the timer + // so it shouldn't really leave anymore at this point. + // Also resetting the timer and calling Start() do not even + // return an error, so there is no need to examine err or ret value + TRAP_IGNORE(lockRefresh.iFileEntry->SetLockedL(this, NULL)); + } + else + { + lockRefresh.iFileEntry->RemoveLocked(); + } + iLockRefreshContexts.Remove(index); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::ObtainLockL +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::ObtainLockL(CRsfwFileEntry *aFileEntry, + TUint aLockFlags, + TDesC8*& aLockToken, + CRsfwRfeStateMachine* aOperation) + { + DEBUGSTRING(("CRsfwLockManager::ObtainLockL")); + if (aFileEntry->iLockTimeout == 0) + { + // No locking wanted, + // we use notsupported as a return code in this case too.... + DEBUGSTRING(("lock timeout in CFileEntry is 0, no locking")); + aOperation->HandleRemoteAccessResponse(0, KErrNotSupported); + } + else + { + HBufC* fullName = aFileEntry->FullNameLC(); + if (!iRemoteAccess) + { + DEBUGSTRING(("iRemoteAccess NULL")); + User::Leave(KErrNotReady); + } + else + { + DEBUGSTRING(("calling iRemoteAccess::ObtainLockL()")); + iRemoteAccess->ObtainLockL(*fullName, + aLockFlags, + aFileEntry->iLockTimeout, + aLockToken, + aOperation); + } + + CleanupStack::PopAndDestroy(fullName); // fullname + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::ReleaseLockL +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::ReleaseLockL(CRsfwFileEntry* aFileEntry, + CRsfwRfeStateMachine* aOperation) + { + DEBUGSTRING(("CRsfwLockManager::ReleaseLockL")); + if (aFileEntry->iLockTimeout == 0) + { + // No locking + User::Leave(KErrNotFound); + } + + + if (!iRemoteAccess) + { + User::Leave(KErrNotReady); + } + else + { + HBufC* fullName = aFileEntry->FullNameLC(); +#ifdef _DEBUG + TInt err; + err = iRemoteAccess->ReleaseLockL(*fullName, aOperation); + TPtrC p = fullName->Des(); + DEBUGSTRING16(("ReleaseLockL(): returned %d for file '%S'", err, &p)); + + + +#else + iRemoteAccess->ReleaseLockL(*fullName, aOperation); +#endif + CleanupStack::PopAndDestroy(fullName); // fullname + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::RefreshLockL +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::RefreshLockL(CRsfwFileEntry* aFileEntry) + { + DEBUGSTRING(("CRsfwLockManager::RefreshLockL")); + TInt id = 0; + if (aFileEntry->iLockTimeout > 0) // timeout = 0 indicates no locking + { + aFileEntry->iLockTimer->Cancel(); // cancel the old timer + HBufC* fullName = aFileEntry->FullNameLC(); + TRAPD(err, id = iRemoteAccess->RefreshLockL(*fullName, + aFileEntry->iLockTimeout, + this)); + if (err == KErrNone) + { + TPendingLockRefreshContext lockRefresh; + lockRefresh.iId = id; + lockRefresh.iFileEntry = aFileEntry; + iLockRefreshContexts.AppendL(lockRefresh); + } + else + { + // This error would come from the lower layers of the communication + // stack, not from the server. + // We use the timer mechanism to try again + // but set the timeout to smaller. + // Note that we don't touch aFileEntry->iLockTimer, + // which will be used to set the timeout requested from the server + TInt lockTimeout = + Min((aFileEntry->iLockTimeout / KLockRefreshAdjustment) / 2, + KMinLockRefreshAttempt); + TCallBack callBack(CRsfwFileEntry::LockTimerExpiredL, this); + aFileEntry->iLockTimer->Start(1000000 * lockTimeout, + 1000000 * lockTimeout, + callBack); + } + CleanupStack::PopAndDestroy(fullName); // fullname + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::LockedCount +// ---------------------------------------------------------------------------- +// +TInt CRsfwLockManager::LockedCount() + { + return iLockedEntries.Count(); + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::AddLockedEntryL +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::AddLockedEntryL(CRsfwFileEntry* aEntry) + { + // prevent from adding the same item twice + if (iLockedEntries.Find(aEntry) != KErrNotFound) + { + return; + } + + iLockedEntries.AppendL(aEntry); + DEBUGSTRING(("Update locked count %d -> %d", + iLockedEntries.Count() - 1, + iLockedEntries.Count())); + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::RemoveLockedEntry +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::RemoveLockedEntry(CRsfwFileEntry* aEntry) + { + TInt index = iLockedEntries.Find(aEntry); + if (index != KErrNotFound) + { + iLockedEntries.Remove(index); + DEBUGSTRING(("Update locked count %d -> %d", + iLockedEntries.Count() + 1, + iLockedEntries.Count())); + + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockManager::PopulateExternalLockTokenCacheL +// ---------------------------------------------------------------------------- +// +void CRsfwLockManager::PopulateExternalLockTokenCacheL(CRsfwFileEntry* aRoot) + { + if (aRoot) + { + const TDesC8* lockToken = aRoot->LockToken(); + if (lockToken) + { + HBufC* path = aRoot->FullNameLC(); + TPtr pathPtr = path->Des(); + if (aRoot->Type() == KNodeTypeDir) + { + // the MaxLength() of path is KMaxPath, so we can append + if (pathPtr.Length() && (pathPtr[pathPtr.Length() - 1] != '/')) + { + pathPtr.Append('/'); + } + } + iRemoteAccess->SetLockToken(pathPtr, *lockToken); + CleanupStack::PopAndDestroy(path); + } + + RPointerArray* kids = aRoot->Kids(); + TInt i; + for (i = 0; i < kids->Count(); i++) + { + PopulateExternalLockTokenCacheL((*kids)[i]); + } + } + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwlookupstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwlookupstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,330 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for file lookup +* +*/ + + +#include "rsfwlookupstatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwinterface.h" +#include "rsfwfileengine.h" +#include "mdebug.h" +#include "rsfwdirentattr.h" +#include "rsfwvolumetable.h" + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::CRsfwLookupStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::CRsfwLookupStateMachine() + { + iKidCreated = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::~CRsfwLookupStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::~CRsfwLookupStateMachine() + { + delete iDirEntAttr; + if (iPath) + { + delete iPath; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwLookupStateMachine::CompleteRequestL(TInt aError) + { + TRfeLookupOutArgs* outArgs = static_cast(iOutArgs); + if (aError == KUpdateNotRequired) + { // discard + aError = KErrNone; + } + + if (!aError) + { + outArgs->iFid = iKidFep->Fid(); + } + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::TState* CRsfwLookupStateMachine::CompleteL() + { + // from CRsfwFileEngine::UpdateFileAttributes/UpdateDirAttributes +#ifdef _DEBUG + if (iDirEntAttr) + { + DEBUGSTRING(("Kid attributes: attr=0x%x, size=%d, time=", + iDirEntAttr->Att(), + iDirEntAttr->Size())); + DEBUGTIME((iDirEntAttr->Modified())); + } +#endif + + if (iKidCreated) + { + /* from CRsfwFileEngine::DoLookupL */ + // Create a file entry for this kid + if (!Volumes()->EnsureMetadataCanBeAddedL(Node())) + { + User::Leave(KErrNoMemory); + } + iKidFep = CRsfwFileEntry::NewL(iKidName, Node()); + if (iDirEntAttr->Att() & KEntryAttDir) + { + iKidFep->SetType(KNodeTypeDir); + } + else + { + iKidFep->SetType(KNodeTypeFile); + } + + iKidFep->SetAttributesL(*iDirEntAttr, ETrue); + + // Remember that we have this kid + FileEngine()->iFileTable->AddL(iKidFep); + Node()->AddKid(*iKidFep); + // If we really find a new kid that we were not aware of + // we must set the parent as locally dirty + // (this should not happen too often) + Node()->SetLocallyDirty(); + } + + // We now have a valid kid entry + return CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::TUpdateKidAttributesTryFirstTypeState +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine:: +TUpdateKidAttributesTryFirstTypeState:: +TUpdateKidAttributesTryFirstTypeState(CRsfwLookupStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::EnterL() + { + DEBUGSTRING(("CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::EnterL")); + TRfeLookupInArgs* inArgs = + static_cast(iOperation->iInArgs); + TRfeLookupOutArgs* outArgs = + static_cast(iOperation->iOutArgs); + iOperation->iNodeType = inArgs->iNodeType; + iOperation->iKidName.Set(inArgs->iName); + + TInt err = KErrNone; + iOperation->iKidFep = NULL; + + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + DEBUGSTRING16(("looking up '%S' in fid=%d", + &(iOperation->iKidName), + iOperation->Node()->Fid().iNodeId)); + + // We'd better be looking up in a directory + if (iOperation->Node()->Type() != KNodeTypeDir) + { + User::Leave(KErrNotFound); + } + + // Try to get the entry from the parent directory + iOperation->iKidFep = + iOperation->Node()->FindKidByName(iOperation->iKidName); + if (!iOperation->iKidFep) + { + DEBUGSTRING(("no such kid!")); + // Didn't find it + // if the parent directory's cache entry is still valid + // we return "not found" + if ((iOperation->FileEngine()->UseCachedAttributes(*iOperation->Node())) && + (iOperation->FileEngine()->UseCachedData(*iOperation->Node()))) + { + User::Leave(KErrNotFound); + } + + iOperation->iPath = + iOperation->FileEngine()->FullNameL(*iOperation->Node()); + if (iOperation->iNodeType == KNodeTypeUnknown) + { + iOperation->FileEngine()-> + UpdateAttributesL(*iOperation->iPath, + iOperation->iKidName, + iOperation->iDirEntAttr, + KNodeTypeFile, + iOperation); + } + else + { + iOperation->FileEngine()-> + UpdateAttributesL(*iOperation->iPath, + iOperation->iKidName, + iOperation->iDirEntAttr, + iOperation->iNodeType, + iOperation); + } + + if (err) + { + // communication to the server failed, + //e.g. we are in disconnected mode + User::Leave(err); + } + } + else + { + // We now have a valid kid entry + outArgs->iFid = iOperation->iKidFep->Fid(); + iOperation->HandleRemoteAccessResponse(0, KUpdateNotRequired); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::TState* +CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::CompleteL() + { + DEBUGSTRING(("CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::CompleteL")); + return iOperation->CompleteL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::ErrorL +// If we were looking for a file return KErrNotFound +// if for directory KErrPathNotFound. +// File Server seems to always call Entry() (-->lookup()) before other file +// operations so as long as we return the right variant of "not found" +// error here other places do not matter. +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::TState* +CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::ErrorL(TInt aCode) + { + DEBUGSTRING(("CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState::ErrorL %d", aCode)); + if (aCode == KUpdateNotRequired) + { + iOperation->iKidCreated = EFalse; + return iOperation->CompleteL(); + } + else if (iOperation->iNodeType == KNodeTypeUnknown) + { + return new CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState( + iOperation); + } + else if ((aCode != KErrNotFound) && (aCode != KErrPathNotFound)) + { + return iOperation->CompleteRequestL(aCode); + } + else if (iOperation->iNodeType == KNodeTypeDir) + { + return iOperation->CompleteRequestL(KErrPathNotFound); + } + else + { + return iOperation->CompleteRequestL(KErrNotFound); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::TUpdateKidAttributesTrySecondTypeState +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine:: +TUpdateKidAttributesTrySecondTypeState:: +TUpdateKidAttributesTrySecondTypeState(CRsfwLookupStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::EnterL() + { + DEBUGSTRING(("CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::EnterL")); + // We only come here if nodetype is unknown and + // we already tried to lookup as a file + iOperation->FileEngine()->UpdateAttributesL(*iOperation->iPath, + iOperation->iKidName, + iOperation->iDirEntAttr, + KNodeTypeDir, iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::TState* +CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::CompleteL() + { + DEBUGSTRING(("CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::CompleteL")); + // from CRsfwFileEngine::UpdateFileAttributes/UpdateDirAttributes + return iOperation->CompleteL(); + } + + +// ---------------------------------------------------------------------------- +// CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::ErrorL +// If we were looking for a file return KErrNotFound, +// if for directory KErrPathNotFound. +// File Server seems to always call Entry() (-->lookup()) before other file +// operations so as long as we return the right variant of "not found" +// error here other places do not matter. +// ---------------------------------------------------------------------------- +// +CRsfwLookupStateMachine::TState* +CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::ErrorL(TInt aCode) + { + DEBUGSTRING(("CRsfwLookupStateMachine::TUpdateKidAttributesTrySecondTypeState::ErrorL %d", aCode)); + // from CRsfwFileEngine::Lookup() + // No such kid + + // cache the last failed lookup results + iOperation->FileEngine()->SetFailedLookup(*iOperation->iPath, + iOperation->iKidName); + + if (iOperation->iNodeType == KNodeTypeDir) + { + return iOperation->CompleteRequestL(KErrPathNotFound); + } + else + { + return iOperation->CompleteRequestL(KErrNotFound); + } + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwlrulistnode.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwlrulistnode.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,68 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: A node in the LRU list +* +*/ + + +#include "rsfwlrulistnode.h" + +const TInt CRsfwLruListNode::iOffset = _FOFF(CRsfwLruListNode,iLink); + + +// ---------------------------------------------------------------------------- +// CRsfwLruListNode::NewLC +// +// ---------------------------------------------------------------------------- +// +CRsfwLruListNode* CRsfwLruListNode::NewLC(CRsfwFileEntry *aFe, TInt aPriority) + { + CRsfwLruListNode* self = new (ELeave) CRsfwLruListNode; + CleanupStack::PushL(self); + self->ConstructL(aFe, aPriority); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwLruListNode::NewL +// +// ---------------------------------------------------------------------------- +// +CRsfwLruListNode* CRsfwLruListNode::NewL(CRsfwFileEntry *aFe, TInt aPriority) + { + CRsfwLruListNode* self = CRsfwLruListNode::NewLC(aFe, aPriority); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwLruListNode::ConstructL +// +// ---------------------------------------------------------------------------- +// +void CRsfwLruListNode::ConstructL(CRsfwFileEntry *aFe, TInt aPriority) + { + iEntryPtr = aFe; + iLink.iPriority = aPriority; + } + +// ---------------------------------------------------------------------------- +// CRsfwLruListNode::~CRsfwLruListNode +// +// ---------------------------------------------------------------------------- +// +CRsfwLruListNode::~CRsfwLruListNode() + { + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwlruprioritylist.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwlruprioritylist.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,219 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: LRU priority list for the file cache +* +*/ + + +#include "rsfwlruprioritylist.h" +#include "rsfwlrulistnode.h" +#include "rsfwfileentry.h" +#include "mdebug.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwfileengine.h" +#include "rsfwfiletable.h" + +// ---------------------------------------------------------------------------- +// CRsfwLruPriorityList::CRsfwLruPriorityList +// +// ---------------------------------------------------------------------------- +// +CRsfwLruPriorityList::CRsfwLruPriorityList() + : iHdr(CRsfwLruListNode::iOffset),iIter(iHdr) //construct header & iterator + {} + +// ---------------------------------------------------------------------------- +// CRsfwLruPriorityList::~CRsfwLruPriorityList +// +// ---------------------------------------------------------------------------- +// +CRsfwLruPriorityList::~CRsfwLruPriorityList() + { + CRsfwLruListNode* node; + + iIter.SetToFirst(); + node = iIter++; + while (node) + { + node->iLink.Deque(); + delete node; + node = iIter++; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLruPriorityList::AddNodeL +// +// ---------------------------------------------------------------------------- +// +void CRsfwLruPriorityList::AddNodeL(CRsfwFileEntry *aFe, TInt aPriority) + { + CRsfwLruListNode* currentNode; + + iIter.SetToFirst(); + + currentNode = iIter++; + while (currentNode) + { + if (currentNode->iEntryPtr->Fid() == aFe->Fid()) + { + DEBUGSTRING(("LRU list: '%d' already exists on the list", + aFe->Fid().iNodeId)); + return; + } + currentNode = iIter++; + } + + // Inserts the specified list element in descending priority order. + // If there is an existing list element with the same priority, + // then the new element is added after the existing element. + CRsfwLruListNode* newNode = CRsfwLruListNode::NewL(aFe, aPriority); + iHdr.Add(*newNode); + DEBUGSTRING(("LRU list: added fid '%d' to the list", + aFe->Fid().iNodeId)); + } + + +// ---------------------------------------------------------------------------- +// CRsfwLruPriorityList::RemoveNode +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwLruPriorityList::RemoveNode(CRsfwFileEntry *aFe) + { + DEBUGSTRING(("CRsfwLruPriorityList::RemoveNode")); + // When file is opened, it must be removed from LRU list + // as it is not candidate for removal from cache. + // Returns KErrNotFound if the file is not found at all + + TInt err = KErrNotFound; + CRsfwLruListNode* currentNode; + + iIter.SetToFirst(); + + currentNode = iIter++; + while (currentNode) + { + if (currentNode->iEntryPtr->Fid() == aFe->Fid()) + { + currentNode->iLink.Deque(); + delete currentNode; + err = KErrNone; + DEBUGSTRING(("LRU list: removed fid '%d' from the list", + aFe->Fid().iNodeId)); + break; + } + currentNode = iIter++; + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwLruPriorityList::GetAndRemoveFirstEntry +// +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwLruPriorityList::GetAndRemoveFirstEntry() + { + + CRsfwLruListNode* firstNode = iHdr.First(); + CRsfwFileEntry* firstEntry = NULL; + + if (iHdr.IsHead(firstNode)) + { + return NULL; // the head has been reached, and must not be removed + } + + if (firstNode) + { + firstEntry = firstNode->iEntryPtr; + firstNode->iLink.Deque(); + delete firstNode; + } + + DEBUGSTRING(("LRU list: first fid on the list removed, '%d'", + firstEntry->Fid().iNodeId)); + return firstEntry; + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::ExternalizeL +// ---------------------------------------------------------------------------- +// +void CRsfwLruPriorityList::ExternalizeL(RWriteStream& aStream) + { + // start from the end! + iIter.SetToLast(); + CRsfwLruListNode* currentNode = iIter--; + while (currentNode) + { + CRsfwFileEntry* currentEntry = currentNode->iEntryPtr; + if (currentEntry) + { + TFid fid = currentEntry->Fid(); + aStream.WriteInt32L(fid.iNodeId); + aStream.WriteInt32L(fid.iVolumeId); + } + currentNode = iIter--; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwFileEntry::InternalizeL +// ---------------------------------------------------------------------------- +// +void CRsfwLruPriorityList::InternalizeL(RReadStream& aStream, CRsfwVolumeTable* aVolumeTable) + { + if ( !aVolumeTable ) + { + User::Leave(KErrArgument); + } + + // reset existing list + iHdr.Reset(); + + // get stream size + MStreamBuf* streamBuf = aStream.Source(); + TInt streamSize = streamBuf->SizeL(); + + TInt i; + // note i+8 as one entry takes two TInt32 (2 times 4 bytes) + for ( i = 0; i < streamSize; i = i+8 ) + { + TFid fid; + fid.iNodeId = aStream.ReadInt32L(); + fid.iVolumeId = aStream.ReadInt32L(); + + // check whether there is no trash in the data being internalized + if (fid.iVolumeId >= 0 && fid.iVolumeId < KMaxVolumes && fid.iNodeId > 0) + { + // find existing CRsfwFileEntry object based on TFid + CRsfwVolume* volume = aVolumeTable->iVolumes[fid.iVolumeId]; + if ( volume ) + { + CRsfwFileEntry* entry = volume->iFileEngine->iFileTable->Root()->Lookup(fid); + if ( entry ) + { + AddNodeL(entry, ECachePriorityNormal); + } + } + } + else + { + DEBUGSTRING(("LRU List: wrong item on the list being internalized!")); + } + } + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwmetadatastore.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwmetadatastore.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,125 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Keeps metadata persistent +* +*/ + + +// INCLUDE FILES +#include + +#include "rsfwmetadatastore.h" +#include "mdebug.h" + +// CONSTANTS +const TUint32 KMetaDataStoreVersion = 0x010101; // current version +const TInt KMaxExternalizedMountConfigSize = 512; +const TInt KDefaultMetaDataBlockSize = 128; + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwMetaDataStore::NewL +// ---------------------------------------------------------------------------- +// +CRsfwMetaDataStore* CRsfwMetaDataStore::NewL(const TDesC& aPath) + { + DEBUGSTRING(("CRsfwMetaDataStore::NewL")); + CRsfwMetaDataStore* self = CRsfwMetaDataStore::NewLC(aPath); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMetaDataStore::NewLC +// ---------------------------------------------------------------------------- +// +CRsfwMetaDataStore* CRsfwMetaDataStore::NewLC(const TDesC& aPath) + { + DEBUGSTRING(("CRsfwMetaDataStore::NewLC")); + CRsfwMetaDataStore* self = new (ELeave) CRsfwMetaDataStore(); + CleanupStack::PushL(self); + self->ConstructL(aPath); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMetaDataStore::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwMetaDataStore::ConstructL(const TDesC& aPath) + { + DEBUGSTRING(("CRsfwMetaDataStore::ConstructL")); + CRsfwPermanentStore::ConstructL(aPath, + KMaxExternalizedMountConfigSize, + KDefaultMetaDataBlockSize); + } + +// ---------------------------------------------------------------------------- +// CRsfwMetaDataStore::GetMountConfigL +// ---------------------------------------------------------------------------- +// +void CRsfwMetaDataStore::GetMountConfigL(TRsfwMountConfig& aMountConfig) + { + // Load the configuration information + DEBUGSTRING(("CRsfwMetaDataStore::GetMountConfigL")); + const HBufC8* header = Header(); + if (header) + { + RMemReadStream stream(header->Ptr(), header->Length()); + CleanupClosePushL(stream); + TUint32 version = stream.ReadUint32L(); + if (version != KMetaDataStoreVersion) + { + DEBUGSTRING(("metadata store version 0x%x differs from 0x%x", + version, + KMetaDataStoreVersion)); + User::Leave(KErrCorrupt); + } + aMountConfig.InternalizeL(stream); + CleanupStack::PopAndDestroy(&stream); // stream + } + else + { + User::Leave(KErrNotFound); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMetaDataStore::SetMountConfigL +// ---------------------------------------------------------------------------- +// +void CRsfwMetaDataStore::SetMountConfigL(const TRsfwMountConfig& aMountConfig) + { + // Store the configuration information + HBufC8* buf = HBufC8::NewLC(KMaxExternalizedMountConfigSize); + TPtr8 ptr = buf->Des(); + TUint8* data = const_cast(ptr.Ptr()); + RMemWriteStream stream(data, KMaxExternalizedMountConfigSize); + CleanupClosePushL(stream); + + // Dump the externalized data in the memory buffer + stream.WriteUint32L(KMetaDataStoreVersion); + aMountConfig.ExternalizeL(stream); + MStreamBuf* streamBuf = stream.Sink(); + TInt dataLen = streamBuf->TellL(MStreamBuf::EWrite).Offset(); + DEBUGSTRING(("mount config data len = %d,", dataLen)); + stream.CommitL(); + TPtrC8 header(data, dataLen); + SetHeaderL(header); + + CleanupStack::PopAndDestroy(2, buf); // stream, buf + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwmkdirstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwmkdirstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,223 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for creating directories +* +*/ + + +#include "rsfwmkdirstatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwinterface.h" +#include "rsfwfileengine.h" +#include "mdebug.h" +#include "rsfwdirentattr.h" +#include "rsfwvolumetable.h" + +// Make dir + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::CRsfwMkDirStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine::CRsfwMkDirStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::~CRsfwMkDirStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine::~CRsfwMkDirStateMachine() + { + delete iDirEntAttr; + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwMkDirStateMachine::CompleteRequestL(TInt aError) + { + if (iKidCreated && aError) + { + if ( aError == KErrNotFound ) + { + User::Leave( KErrNotFound ); + } + delete iKidFep; + iKidFep = NULL; + } + + // it may happen by chance that the new name is equal to iLastFailedLookup value + FileEngine()->ResetFailedLookup(); + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + + + +// Check if exists + + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TCheckIfExistsState::TCheckIfExistsState +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine:: +TCheckIfExistsState::TCheckIfExistsState(CRsfwMkDirStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TCheckIfExistsState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMkDirStateMachine::TCheckIfExistsState::EnterL() + { + TRfeMkdirInArgs* inArgs = + static_cast(iOperation->iInArgs); + TPtrC kidName(inArgs->iEntry.iName); + + iOperation->iKidFep = NULL; + iOperation->iKidCreated = EFalse; + + // the parent to which we are making + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + DEBUGSTRING16(("making directory '%S' in fid %d", + &kidName, + iOperation->Node()->Fid().iNodeId)); + + // Do we know about the kid yet? + iOperation->iKidFep = iOperation->Node()->FindKidByName(kidName); + if (!iOperation->iKidFep) + { + // This is either a completely new directory, + // or a directory that we have not yet created a file entry for. + // (should always happen) + if (!iOperation->Volumes()->EnsureMetadataCanBeAddedL(iOperation->Node())) + { + User::Leave(KErrNoMemory); + } + iOperation->iKidFep = CRsfwFileEntry::NewL(kidName, iOperation->Node()); + iOperation->iKidCreated = ETrue; + } + + iOperation->FileEngine()->GetAttributesL(*iOperation->iKidFep, + iOperation->iDirEntAttr, + KNodeTypeDir, + iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TCheckIfExistsState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine::TState* +CRsfwMkDirStateMachine::TCheckIfExistsState::CompleteL() + { + // GetAttributes returned KErrNone + // directory exist and we return KErrAlreadyExitsts + return iOperation->CompleteRequestL(KErrAlreadyExists); + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TCheckIfExistsState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine::TState* +CRsfwMkDirStateMachine::TCheckIfExistsState::ErrorL(TInt /*aCode*/) + { + // GetAttributes returned error - + // directory does not exists, let's create it + + return new CRsfwMkDirStateMachine::TMakeDirectoryState(iOperation); + } + + + +// Make directory + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TMakeDirectoryState::TMakeDirectoryState +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine:: +TMakeDirectoryState::TMakeDirectoryState(CRsfwMkDirStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TMakeDirectoryState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMkDirStateMachine::TMakeDirectoryState::EnterL() + { + // Make the directory + if (!iOperation->FileEngine()->Disconnected()) + { + HBufC* kidPath = + iOperation->FileEngine()->FullNameLC(*iOperation->iKidFep); + iOperation->FileEngine()->RemoteAccessL()->MakeDirectoryL(*kidPath, + iOperation); + CleanupStack::PopAndDestroy(kidPath); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TMakeDirectoryState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine::TState* +CRsfwMkDirStateMachine::TMakeDirectoryState::CompleteL() + { + iOperation->iKidFep->SetType(KNodeTypeDir); + iOperation->FileEngine()->SetupAttributes(*iOperation->iKidFep); + + // Attach the kid + if (iOperation->iKidCreated) + { + iOperation->FileEngine()->iFileTable->AddL(iOperation->iKidFep); + iOperation->Node()->AddKid(*iOperation->iKidFep); + } + + // Create an empty container file locally + iOperation->FileEngine()->CreateContainerFileL(*iOperation->iKidFep); + iOperation->iKidFep->SetCached(ETrue); + iOperation->iKidFep->SetAttribValidationTime(); + + // Refresh parent directory next time it is accessed + iOperation->Node()->SetLocallyDirty(); + + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwMkDirStateMachine::TMakeDirectoryState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwMkDirStateMachine::TState* +CRsfwMkDirStateMachine::TMakeDirectoryState::ErrorL(TInt aCode) + { + DEBUGSTRING(("remote mkdir failed!")); + return iOperation->CompleteRequestL(aCode); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwmountconnectionstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwmountconnectionstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,174 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for changing mount state, e.g. online->offline +* +*/ + + +#include "rsfwmountconnectionstatemachine.h" +#include "rsfwvolumetable.h" +#include "rsfwfileengine.h" +#include "rsfwfiletable.h" +#include "rsfwlockmanager.h" +#include "rsfwwaitnotemanager.h" +#include "mdebug.h" +#include "rsfwrfeserver.h" + +/********************************************************** + * CRsfwMountConnectionStateMachine + * + * If connect to server fails, deletes the remote accessor + * (this comes from the way synch version fo CRsfwFileEngine::ConnectL() used to + * to work, but I'm not quite sure how correct behaviour this is). + * Note that EnteredConnectionState() in CompleteL + * may start reintegration. + * However instead of writing special reintegration states here + * it is better to later implement a reintegration thred. + *********************************************************/ + + +// ---------------------------------------------------------------------------- +// CRsfwMountConnectionStateMachine::CRsfwMountConnectionStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwMountConnectionStateMachine::CRsfwMountConnectionStateMachine(TChar aDriveLetter, + TUint aState) + { + iDriveLetter = aDriveLetter; + iState = aState; + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountConnectionStateMachine::TChangeConnectionState::TChangeConnectionState +// ---------------------------------------------------------------------------- +// +CRsfwMountConnectionStateMachine::TChangeConnectionState::TChangeConnectionState( + CRsfwMountConnectionStateMachine* aParent) + : iOperation(aParent) + {} + +// ---------------------------------------------------------------------------- +// CRsfwMountConnectionStateMachine::TChangeConnectionState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMountConnectionStateMachine::TChangeConnectionState::EnterL() + { + // The user has forced us to go offline/online + iVolume = + iOperation->Volumes()->VolumeByDriveLetter(iOperation->iDriveLetter); + if (iVolume) + { + DEBUGSTRING(("Set state of volume %d to %d", + iVolume->iMountInfo.iMountStatus.iVolumeId, + iOperation->iState)); + + // Note that eventually the volume state may differ + // from the engine state + if ((iVolume->iFileEngine->ConnectionState() == KMountStronglyConnected) + && (iOperation->iState == KMountNotConnected)) + { + // request to move from connected to disconnected state + // warn user if this volume contains open files + if (iVolume->iFileEngine->iFileTable->OpenFileCount() > 0) + { + iOperation->Volumes()->WaitNoteManager() + ->StartWaitNoteL(ERemoteWarnDisconnect, iOperation); + } + else + { + // actual move happens in CRsfwMountConnectionStateMachine::TChangeConnectionState::CompleteL + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + + } + else + { + // currently setting mount state to Connected state not supported + // but user is assumed to use Mount() instead + // this used to work, but authentication options and retry dialogs + // are now missing + User::Leave(KErrNotSupported); + } + } + else + { + if (iOperation->iState == KMountNotConnected) + { + // when volume is not yet found, we execute dormant mount + TInt err; + TInt drivenumber; + TRsfwMountConfig mountConfig; + CRsfwRfeServer::Env()->iFs.CharToDrive(iOperation->iDriveLetter, drivenumber); + mountConfig.iDriveLetter = iOperation->iDriveLetter; + err = iOperation->Volumes()->GetMountConfigL(mountConfig); + if (!err) + { + iOperation->Volumes()->MountDormantL(mountConfig, drivenumber); + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + else + { + iOperation->HandleRemoteAccessResponse(0, err); + } + } + else + { + User::Leave(KErrNotSupported); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountConnectionStateMachine::TChangeConnectionState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwMountConnectionStateMachine::TState* +CRsfwMountConnectionStateMachine::TChangeConnectionState::CompleteL() + { + // from CRsfwFileEngine::RequestConnectionStateL + if (iVolume && iVolume->iFileEngine) + { + + // we successfully disconnected + iVolume->iFileEngine->RequestConnectionStateL( + KMountNotConnected, + NULL); + + if (iVolume->iFileEngine->ConnectionState() != iOperation->iState) + { + iVolume->iFileEngine->EnteredConnectionStateL(iOperation->iState, EFalse); + } + } + + if (iVolume) + { + // from CRsfwVolumeTable::SetMountConnectionStateL + iVolume->iMountInfo.iMountStatus.iConnectionState = + iVolume->iFileEngine->ConnectionState(); + } + + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountConnectionStateMachine::TChangeConnectionState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwMountConnectionStateMachine::TState* +CRsfwMountConnectionStateMachine::TChangeConnectionState::ErrorL(TInt aCode) + { + return iOperation->CompleteRequestL(aCode); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwmountstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwmountstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,517 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for mounting +* +*/ + + +#include +#include "rsfwmountstatemachine.h" +#include "rsfwwaitnotemanager.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwfileengine.h" +#include "rsfwrferequest.h" +#include "rsfwnotpluginrequest.h" +#include "mdebug.h" +#include + +// CONSTANTS +// errors returned by connection layer +const TInt KRsfwErrNoNetworkCoverage = -4159; // device out of range +const TInt KRsfwErrOfflineNotPossible = -4180; // device in off-line mode + +/************************************* + * CRsfwMountStateMachine + * + * Note that EnteredConnectionState() in CompleteL + * may start reintegration. + * However instead of writing special reintegration states here + * it is better to later implement a reintegration thread. + * + ***************************************/ + + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::NewL +// ---------------------------------------------------------------------------- +// +CRsfwMountStateMachine* +CRsfwMountStateMachine::NewL(TRsfwMountConfig aMountConfig, + TInt aMountState, + CRsfwVolumeTable* aVolumeTable) + { + CRsfwMountStateMachine* self = new (ELeave) CRsfwMountStateMachine(); + CleanupStack::PushL(self); + self->ConstructL(aMountConfig, aMountState, aVolumeTable); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStateMachine::ConstructL(TRsfwMountConfig aMountConfig, + TInt aMountState, + CRsfwVolumeTable* aVolumeTable) + { + DEBUGSTRING16(("Mounting drive '%c' with uri '%S', flags=0x%x, to=%d", + TUint(aMountConfig.iDriveLetter), + &(aMountConfig).iUri, + aMountConfig.iFlags, + aMountConfig.iInactivityTimeout)); + + iMountConfig = aMountConfig; + iMountState = aMountState; + iFriendlyName = iMountConfig.iName; + SetVolumes(aVolumeTable); + + iVolumeId = Volumes()->VolumeIdByDriveLetter(iMountConfig.iDriveLetter); + if (iVolumeId == KErrNotFound) + { + User::Leave(KErrArgument); + } + + // set volume and file engine + if (iMountState == KMountStateDormant) + { + // volume and file engine must exist + CRsfwVolume* volume = Volumes()->VolumeByVolumeId(iVolumeId); + if (volume) + { + iVolume = volume; + } + else + { + User::Leave(KErrNotFound); + } + } + else + { + // create volume + iVolume = new (ELeave) CRsfwVolume(); + iVolume->iVolumeTable = Volumes(); + + // set mountinfo for the volume + TRsfwMountInfo& mountInfo = iVolume->iMountInfo; + mountInfo.iMountConfig = iMountConfig; + mountInfo.iMountStatus.iVolumeId = iVolumeId; + iVolume->iVolumeTable = Volumes(); + + if (mountInfo.iMountConfig.iInactivityTimeout < 0) + { + // Negative value means that we don't want to time out + mountInfo.iMountConfig.iInactivityTimeout = 0; + } + else if (mountInfo.iMountConfig.iInactivityTimeout > 0) + { + // Positive means using system default + mountInfo.iMountConfig.iInactivityTimeout = + Volumes()->iInactivityTimeout; + } + // Just copy the adapted parameter + mountInfo.iMountStatus.iInactivityTimeout = + mountInfo.iMountConfig.iInactivityTimeout; + + mountInfo.iMountStatus.iPermanence = Volumes()->iPermanence; + if (iMountConfig.iFlags & KMountFlagOffLine) + { + // We are working offline + mountInfo.iMountStatus.iConnectionState = KMountNotConnected; + } + else + { + mountInfo.iMountStatus.iConnectionState = KMountStronglyConnected; + } + + // create fileengine and attack to volume + iVolume->iFileEngine = CRsfwFileEngine::NewL(iVolume); + } + + // set also fileengine pointer in the operation state machine, + // so that the operation can be cancelled + SetFileEngine(iVolume->iFileEngine); + + + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwMountStateMachine::CompleteRequestL(TInt aError) + { + DEBUGSTRING16(("CRsfwMountStateMachine:::CompleteRequestL error %d", aError)); + // Attach volume to the table + // Note that this is always done, even if "request_connection_state" + // returned an error. + // This is because sending packets to remote server required construction + // of CRsfwFileEngine etc. anyway, and they will be deleted from elsewhere + // (deleting the mount configuration or the inactivity timeout) + if (!(iMountState == KMountStateDormant)) + { + Volumes()->iVolumes[iVolumeId] = iVolume; + } + + // make sure engine disconnects if there was an error + if (aError != KErrNone) + { + iVolume->iFileEngine->RequestConnectionStateL( + KMountNotConnected, + NULL); + } + + return CRsfwWaitNoteStateMachine::CompleteRequestL(aError); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::ErrorOnStateEntry +// ---------------------------------------------------------------------------- +// +CRsfwWaitNoteStateMachine::TState* CRsfwMountStateMachine::ErrorOnStateEntry(TInt aError) + { + DEBUGSTRING16(("CRsfwMountStateMachine::ErrorOnStateEntry %d", aError)); + + if (aError == KEComErrNoInterfaceIdentified) + { + aError = KErrNotFound; + } + + // If error when connecting: + // For most errors we have to show "drive not available, retry?" + // or some other connection error dialog + // for this we must first dismiss the current wait note and then show + // a new note. + // Hower, if user presses Cancel or the red button we return immediately + if ((iRequestingConnection) && (aError != KErrCancel)) + { + iRequestingConnection = EFalse; + iConnectingError = aError; + return new CRsfwMountStateMachine::TDismissConnectionWaitNoteState(this); + } + else + { + return CRsfwWaitNoteStateMachine::ErrorOnStateEntry(aError); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TRequestConnectionState::TRequestConnectionState +// ---------------------------------------------------------------------------- +// +CRsfwMountStateMachine:: +TRequestConnectionState::TRequestConnectionState(CRsfwMountStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TRequestConnectionState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStateMachine::TRequestConnectionState::EnterL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TRequestConnectionState::EnterL")); + + // set volume mountconfig + iOperation->iVolume->iMountInfo.iMountConfig = iOperation->iMountConfig; + + // put up a 'Connecting...' global wait note + + iOperation->ShowWaitNoteL( ERemoteOpConnecting ); + + // mark mount connection state as KMountConnecting + // this is done, because will prevent engine from shutdown + iOperation->FileEngine()->EnteredConnectionStateL(KMountConnecting, EFalse); + + // request KMountStronglyConnected state + // this will open connection to the server + iOperation->iRequestingConnection = ETrue; + TUint transactionId = iOperation->FileEngine() + ->RequestConnectionStateL(KMountStronglyConnected, + iOperation); + + // transactionId = 0 means syncronous non-cancellable operation + if (transactionId > 0) + { + iOperation->iRequestingConnection = EFalse; + iOperation->iTransactionId = transactionId; + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TRequestConnectionState::CompleteL +// This function should be able to do what CRsfwVolumeTable::MountL normally does +// after fileEngine->RequestConnectionStateL() has returned +// (with non-error return code) +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TRequestConnectionState::CompleteL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TRequestConnectionState::CompleteL")); + + if (iOperation->iRequestingConnection) + { + iOperation->iRequestingConnection = EFalse; + } + + if (!(iOperation->iMountState == KMountStateDormant)) + { + // Attach volume to the table + iOperation->Volumes()->iVolumes[iOperation->iVolumeId] = + iOperation->iVolume; + } + + // Attach volume to the request + // (such that the request can notify File Engine of operation completion) + iOperation->Request()->iVolume = iOperation->iVolume; + + iOperation->FileEngine()->EnteredConnectionStateL(KMountStronglyConnected, EFalse); + + // publish the new connection state (P&S notification) + iOperation->Volumes()->PublishConnectionStatus(iOperation->iVolume); + + // Remember the volume id for the next root setup + iOperation->Volumes()->iLastVolumeId = iOperation->iVolumeId; + + // remember why the connection attempt failed + iOperation->iConnectingError = KErrNone; + + // dismiss the connecting dialog + return new CRsfwMountStateMachine::TDismissConnectionWaitNoteState( + iOperation); + + } + + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TRequestConnectionState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TRequestConnectionState::ErrorL(TInt aCode) + { + DEBUGSTRING16(("CRsfwMountStateMachine::TRequestConnectionState error=%d", aCode)); + + if (iOperation->iRequestingConnection) + { + iOperation->iRequestingConnection = EFalse; + } + + // remember why the connection attempt failed + iOperation->iConnectingError = aCode; + + if ((aCode == KErrNone) || (aCode == KErrCancel)) + { + // immediately return + return iOperation->CompleteRequestL(aCode); + } + + // else remove wait note dialog first + return new CRsfwMountStateMachine::TDismissConnectionWaitNoteState( + iOperation); + } + + +// ************* + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine:: +// TDismissConnectionWaitNoteState::TDismissConnectionWaitNoteState +// ---------------------------------------------------------------------------- +// +CRsfwMountStateMachine:: +TDismissConnectionWaitNoteState::TDismissConnectionWaitNoteState(CRsfwMountStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TDismissConnectionWaitNoteState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStateMachine::TDismissConnectionWaitNoteState::EnterL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TDismissConnectionWaitNoteState::EnterL")); + iOperation->DeleteWaitNoteL(EFalse); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TDismissConnectionWaitNoteState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TDismissConnectionWaitNoteState::CompleteL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TDismissConnectionWaitNoteState::CompleteL")); + switch (iOperation->iConnectingError) + { + case KErrNone: + return iOperation->CompleteRequestL(KErrNone); + case KErrCancel: + return iOperation->CompleteRequestL(KErrCancel); + case KErrAccessDenied: + return new CRsfwMountStateMachine::TGetAuthCredentials(iOperation); + case KErrNoMemory: + iOperation->Volumes()->WaitNoteManager() + ->ShowOutOfMemoryNoteL(); + return iOperation->CompleteRequestL(KErrNoMemory); + case KErrNotFound: + case KErrPathNotFound: + iOperation->Volumes()->WaitNoteManager() + ->ShowAddressNotFoundErrorL(iOperation->iFriendlyName); + return iOperation->CompleteRequestL(iOperation->iConnectingError); + case KRsfwErrNoNetworkCoverage: + iOperation->Volumes()->WaitNoteManager() + ->ShowNoNetworkCoverageNoteL(); + return iOperation->CompleteRequestL(KRsfwErrNoNetworkCoverage); + case KRsfwErrOfflineNotPossible: + iOperation->Volumes()->WaitNoteManager() + ->ShowOfflineNotPossibleNoteL(); + return iOperation->CompleteRequestL(KRsfwErrOfflineNotPossible); + default: + // ask user whether to retry + return new CRsfwMountStateMachine::TUnavailableRetry(iOperation); + } + } + +//----------------------------------------------------------------------------- +// CRsfwMountStateMachine::TDismissConnectionWaitNoteState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TDismissConnectionWaitNoteState::ErrorL(TInt /*aCode*/) + { + DEBUGSTRING16(("CRsfwMountStateMachine::TDismissConnectionWaitNoteState::ErrorL")); + // dismissing the dialog failed + // no code for this case + return CompleteL(); + } + +// ************* + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TGetAuthCredentials::TGetAuthCredentials +// ---------------------------------------------------------------------------- +// +CRsfwMountStateMachine:: +TGetAuthCredentials::TGetAuthCredentials(CRsfwMountStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TGetAuthCredentials::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStateMachine::TGetAuthCredentials::EnterL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TGetAuthCredentials::EnterL")); + iAuthRequest.iMethod = TRsfwNotPluginRequest::EAuthenticationDlg; + iAuthRequest.iDriveName = iOperation->iFriendlyName; + iAuthRequest.iUserName = iOperation->iMountConfig.iUserName; + iAuthRequest.iPassword = iOperation->iMountConfig.iPassword; + + iOperation->Volumes()->WaitNoteManager()->SetAuthenticationDialogL(iAuthRequest); + iOperation->Volumes()->WaitNoteManager() + ->StartWaitNoteL(ERemoteOpAuthDialog, iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TGetAuthCredentials::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TGetAuthCredentials::CompleteL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TGetAuthCredentials::CompleteL")); + // re-set username and password and try connecting again + iOperation->iMountConfig.iUserName = iAuthRequest.iUserName; + iOperation->iMountConfig.iPassword = iAuthRequest.iPassword; + + return new CRsfwMountStateMachine::TRequestConnectionState(iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TGetAuthCredentials::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TGetAuthCredentials::ErrorL(TInt /*aCode*/) + { + DEBUGSTRING16(("CRsfwMountStateMachine::TGetAuthCredentials::ErrorL")); + return iOperation->CompleteRequestL(KErrAccessDenied); + } + +// ************** + + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TUnavailableRetry::TGetAuthCredentials +// ---------------------------------------------------------------------------- +// +CRsfwMountStateMachine:: +TUnavailableRetry::TUnavailableRetry(CRsfwMountStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TUnavailableRetry::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwMountStateMachine::TUnavailableRetry::EnterL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TUnavailableRetry::EnterL")); + iRetryRequest.iMethod = TRsfwNotPluginRequest::EUnavailableRetryDlg; + iRetryRequest.iDriveName = iOperation->iFriendlyName; + + iOperation->Volumes()->WaitNoteManager()->SetGlobalNoteRequestL(iRetryRequest); + iOperation->Volumes()->WaitNoteManager() + ->StartWaitNoteL(ERemoteUnavailableRetry, iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TUnavailableRetry::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TUnavailableRetry::CompleteL() + { + DEBUGSTRING16(("CRsfwMountStateMachine::TUnavailableRetry::CompleteL")); + // retry + return new CRsfwMountStateMachine::TRequestConnectionState(iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwMountStateMachine::TUnavailableRetry::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwMountStateMachine::TUnavailableRetry::ErrorL(TInt aCode) + { + DEBUGSTRING16(("CRsfwMountStateMachine::TUnavailableRetry::ErrorL")); + if (aCode == KErrCancel) + { + // user cancelled the a dialog + return iOperation->CompleteRequestL(KErrCancel); + } + else + { + return iOperation->CompleteRequestL(aCode); + } + } diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwopenbypathstatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwopenbypathstatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,254 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for opening a file or directory +* +*/ + + +#include "rsfwopenbypathstatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwinterface.h" +#include "rsfwfileengine.h" +#include "rsfwlockmanager.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::CRsfwOpenByPathStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwOpenByPathStateMachine::CRsfwOpenByPathStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::~CRsfwOpenByPathStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwOpenByPathStateMachine::~CRsfwOpenByPathStateMachine() + { + delete iLockToken; + } + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwOpenByPathStateMachine::CompleteRequestL(TInt aError) + { + DEBUGSTRING(("CRsfwOpenByPathStateMachine::CompleteRequestL %d", aError)); + TRfeOpenByPathOutArgs* outArgs = + static_cast(iOutArgs); + if(!aError) + { + if ((Node()->Type() == KNodeTypeFile) && + iRealOpen) + { + // file opened successfully and was not already opened in create + Node()->iFileTable->UpdateOpenFileCount(1); + } + + outArgs->iPath.Copy(*iCacheName); + iAttrp->iAtt = Node()->Att(); + iAttrp->iSize = Node()->Size(); + iAttrp->iModified = Node()->Modified(); + } + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::TRequestOpenModeState::TRequestOpenModeState +// ---------------------------------------------------------------------------- +// +CRsfwOpenByPathStateMachine::TRequestOpenModeState::TRequestOpenModeState( + CRsfwOpenByPathStateMachine* aParent) + : iOperation(aParent) + { + iRequestedLock = EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::TRequestOpenModeState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwOpenByPathStateMachine::TRequestOpenModeState::EnterL() + { + + DEBUGSTRING(("CRsfwOpenByPathStateMachine::TRequestOpenModeState::EnterL")); + + TRfeOpenByPathInArgs* inArgs = + static_cast(iOperation->iInArgs); + TRfeOpenByPathOutArgs* outArgs = + static_cast(iOperation->iOutArgs); + iOperation->iRealOpen = inArgs->iTrueOpen; + // Use inArgs->iFlags to pass desired locking information + iOperation->iFlags = inArgs->iFlags; + iOperation->iAttrp = &(outArgs->iAttr); + + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + if (iOperation->Node()->Size() > iOperation->Volumes()->iMaxCacheSize) + { + DEBUGSTRING(("OPENBYPATH failed: file too large: file size %d, max cache size %d", + iOperation->Node()->Size(), + iOperation->Volumes()->iMaxCacheSize)); + User::Leave(KErrTooBig); + } + + DEBUGSTRING(("opening fid %d with flags 0x%x", + iOperation->Node()->Fid().iNodeId, + iOperation->iFlags)); + + if (!iOperation->FileEngine()->WriteDisconnected()) + { + if (!(iOperation->Node()->IsLocked()) && + (iOperation->Node()->Type() != KNodeTypeDir) && + (iOperation->iFlags & EFileWrite)) + { + DEBUGSTRING(("requesting lock")); + // For the time being + // if flag is 0 we are not interested in getting a lock + iOperation->FileEngine()->LockManager()->ObtainLockL( + iOperation->Node(), + iOperation->iFlags, + iOperation->iLockToken, + iOperation); + iRequestedLock = ETrue; + } + else + { + // IsLocked() || !(iOperation->iFlags & EFileWrite) + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + else + { + // if WriteDisconnected() + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::TRequestOpenModeState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwOpenByPathStateMachine::TState* +CRsfwOpenByPathStateMachine::TRequestOpenModeState::CompleteL() + { + DEBUGSTRING(("CRsfwOpenByPathStateMachine::TRequestOpenModeState::CompleteL")); + if (iRequestedLock) + { + //from CRsfwLockManager::ObtainLock() +#ifdef _DEBUG + TPtrC p = iOperation->Node()->FullNameLC()->Des(); + DEBUGSTRING16(("ObtainLockL(): flags %d returned %d for file '%S'", + iOperation->iFlags, + KErrNone, + &p)); + CleanupStack::PopAndDestroy(); +#endif // DEBUG + iOperation->Node()->SetLockedL( + iOperation->FileEngine()->LockManager(), + iOperation->iLockToken); + iOperation->iLockToken = NULL; + } + + iOperation->iCacheName = iOperation->Node()->CacheFileName(); + + // make sure that the relevant cache file is on place + // (i.e. it has not been removed e.g. by other apps) + iOperation->Node()->ValidateCacheFile(); + + if (!iOperation->Node()->IsCached()) + { + if (iOperation->FileEngine()->Disconnected()) + { + if ((iOperation->Node()->Type() != KNodeTypeDir) && + !(iOperation->iFlags & EFileWrite)) + { + // While disconnected, + // write access of files returns "not found" + return iOperation->CompleteRequestL(KErrNotFound); + } + } + iOperation->FileEngine()->CreateContainerFileL(*(iOperation->Node())); + iOperation->iCacheName = iOperation->Node()->CacheFileName(); + } + else // is cached + { + if (iOperation->Node()->IsLocallyDirty()) + { + // This is a directory which has at least one kid + // that has been cached or flushed since the last opening + // of the directory + iOperation->FileEngine()->UpdateDirectoryContainerL( + *(iOperation->Node())); + } + + // If this is a cached file, + // we must remove it from LRUlist as it is now open + if (iOperation->iRealOpen) + { + iOperation->Node()->iFileTable->Volume()->iVolumeTable-> + RemoveFromLRUPriorityList(iOperation->Node()); + } + } + + // if file or dir has just been opened, remove it from metadata LRU list + iOperation->Node()->iFileTable->Volume()->iVolumeTable-> + RemoveFromMetadataLRUPriorityList(iOperation->Node()); + + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwOpenByPathStateMachine::TRequestOpenModeState::ErrorL +// fileEngine->RequestConnectionStateL() has returned with error +// ---------------------------------------------------------------------------- +// +CRsfwOpenByPathStateMachine::TState* +CRsfwOpenByPathStateMachine::TRequestOpenModeState::ErrorL(TInt aCode) + { + DEBUGSTRING(("CRsfwOpenByPathStateMachine::TRequestOpenModeState::ErrorL %d", aCode)); + // from CRsfwFileEngine::DoOpenByPath() + if (aCode == KErrNotSupported) + { + iRequestedLock = EFalse; + // locks not supported is not an error state + // instead we run the success state... + return CompleteL(); + } + + //from CRsfwLockManager::ObtainLock() +#ifdef _DEBUG + TPtrC p = iOperation->Node()->FullNameLC()->Des(); + DEBUGSTRING16(("ObtainLockL(): flags %d returned %d for file '%S'", + iOperation->iFlags, + aCode, + &p)); + CleanupStack::PopAndDestroy(); +#endif + + return iOperation->CompleteRequestL(aCode); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwpermanentstore.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwpermanentstore.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,885 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Provides persistent storage for memory blocks +* +*/ + + +// This is a simple block based permanent storage, in which transient +// indices are computed on the fly when all data is sequentially read +// from the storage. +// +// The data is put into "slots" that consist of one or more "blocks". +// Subsequent updates to the data slots only use the current slot +// if the required slot size (block count) has not changed. +// +// The storage contains a header that may contain any data. +// In addition, Each slot contains a header (of type TInt) that +// describes the size of the data in the slot. +// +// The file can be compressed for space efficiency. +// +// The assumption is that the store is first opened for reading for loading +// the data, and then it is only opened for writing until the file is closed. +// +// (We don't use CRsfwPermanentStore because besides data, we should +// also maintain the indices in a stream of its own) + +// INCLUDE FILES +#include +#include + +#include "rsfwpermanentstore.h" +#include "mdebug.h" + + +// CONSTANTS +const TUint KHeaderStart = 0xbabefade; +const TInt KSlotHeaderSize = 4; // sizeof(TInt) +const TInt KDefaultBlockSize = 128; // default block size in bytes +// max value for integer read from the stream, subsequently used to create descriptor +const TInt KMaxDescriptorSize = 16384; + + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// TFileHeader::ExternalizeL +// ---------------------------------------------------------------------------- +// +void TFileHeader::ExternalizeL(RWriteStream& aStream) const + { + aStream.WriteInt32L(iHeaderStart); + aStream.WriteInt32L(iBlockSize); + aStream.WriteInt32L(iHeaderSize); + aStream << *iHeader; + } + +// ---------------------------------------------------------------------------- +// TFileHeader::InternalizeL +// ---------------------------------------------------------------------------- +// +void TFileHeader::InternalizeL(RReadStream& aStream) + { + iHeaderStart = aStream.ReadInt32L(); + iBlockSize = aStream.ReadInt32L(); + if (iBlockSize < 0 || iBlockSize > KMaxDescriptorSize) + { + User::Leave(KErrCorrupt); + } + iHeaderSize = aStream.ReadInt32L(); + if (iHeaderSize < 0 || iHeaderSize > KMaxDescriptorSize) + { + User::Leave(KErrCorrupt); + } + iHeader = HBufC8::NewL(aStream, iHeaderSize); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::NewL +// ---------------------------------------------------------------------------- +// +CRsfwPermanentStore* CRsfwPermanentStore::NewL(const TDesC& aPath, + TInt aHeaderSize, + TInt aBlockSize) + { + CRsfwPermanentStore* self = new (ELeave) CRsfwPermanentStore(); + CleanupStack::PushL(self); + self->ConstructL(aPath, aHeaderSize, aBlockSize); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::~CRsfwPermanentStore +// ---------------------------------------------------------------------------- +// +CRsfwPermanentStore::~CRsfwPermanentStore() + { + ClearFreeBlockLists(); + iSlots.Close(); + iFileReadStream.Close(); + iFileWriteStream.Close(); + iFile.Close(); + iFs.Close(); + delete iFileHeader.iHeader; + delete iZeroBlock; + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::ConstructL(const TDesC& aPath, + TInt aHeaderSize, + TInt aBlockSize) + { + DEBUGSTRING(("CRsfwPermanentStore::ConstructL()")); + User::LeaveIfError(iFs.Connect()); + iPath.Copy(aPath); + + iHeaderSize = aHeaderSize; + // Offset to the block data + iFileHeaderSize = iHeaderSize + sizeof(TFileHeader); + TRAPD(err, LoadHeaderL()); + if (err == KErrNone) + { + // Read parameters from the existing file, if any + iHeaderSize = iFileHeader.iHeaderSize; + iBlockSize = iFileHeader.iBlockSize; + } + else + { + // There was no existing file + DEBUGSTRING(("LoadHeaderL returns %d", err)); + if (aBlockSize) + { + iBlockSize = aBlockSize; + } + else + { + iBlockSize = KDefaultBlockSize; + } + iFileHeader.iHeaderStart = KHeaderStart; + iFileHeader.iHeaderSize = iHeaderSize; + iFileHeader.iBlockSize = iBlockSize; + } + // Compute the offset to data blocks + // (this is 4 bytes too many but that is OK ...) + iFileHeaderSize = iHeaderSize + sizeof(TFileHeader); + // Make a block of zeroes + iZeroBlock = HBufC8::NewL(iBlockSize); + iZeroBlock->Des().FillZ(); + DEBUGSTRING(("ConstructL() done, blocksize=%d", iBlockSize)); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::ResetL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::ResetL(TBool aWriting) + { + // This function is called by the client + // before starting to read or write data slots + if (aWriting) + { + SetFileStateL(EFileStateWriting); + // Set write pointer to the end of the file + MStreamBuf* streamBuf = iFileWriteStream.Sink(); + TInt size = streamBuf->SizeL(); + iWriteBlockNumber = (size - iFileHeaderSize) / iBlockSize; + if ((iWriteBlockNumber * iBlockSize) != (size - iFileHeaderSize)) + { + DEBUGSTRING(("ResetL(): file size incorrect (%d)", + size)); + } + } + else + { + // reading + SetFileStateL(EFileStateReading); + // Skip file header + MStreamBuf* streamBuf = iFileReadStream.Source(); + streamBuf->SeekL(MStreamBuf::ERead, + EStreamBeginning, + iFileHeaderSize); + iReadBlockNumber = 0; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::Commit +// ---------------------------------------------------------------------------- +// +TInt CRsfwPermanentStore::Commit() + { + TInt err = KErrNone; + // Commit writing + if (iFileState == EFileStateWriting) + { + MStreamBuf* streamBuf = iFileWriteStream.Sink(); + err = streamBuf->Synch(); + } + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::Purge +// ---------------------------------------------------------------------------- +// +TInt CRsfwPermanentStore::Purge() + { + iFileReadStream.Close(); + iFileWriteStream.Close(); + iFile.Close(); + return iFs.Delete(iPath); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::CompactL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::CompactL() + { + // Compact the file by dropping empty slots. + // The slot table is also fixed and the free block lists are cleared + // to reflect the new file layout. + + // This function must not be called while the file is opened for reading. + // It is most efficient to call this function before any data is read + // (then there is no slot table to fix) + + // This function must be called before doing GetNextDataL() + // (must be followed by ResetL()). + // However, this function can be called while doing PutDataL(). + + DEBUGSTRING(("CompactL()")); + SetFileStateL(EFileStateClosed); + SetFileStateL(EFileStateReading); + + TBuf dstPath; + dstPath.Copy(iPath); + dstPath.Append('a'); + RFile dstFile; + User::LeaveIfError(dstFile.Replace(iFs, + dstPath, + EFileShareAny | EFileWrite)); + CleanupClosePushL(dstFile); + RFileWriteStream dstFileWriteStream(dstFile); + CleanupClosePushL(dstFileWriteStream); + MStreamBuf* streamBuf = iFileReadStream.Source(); + + // Copy header + dstFileWriteStream.WriteL(iFileReadStream, iFileHeaderSize); + + RArray gaps; + CleanupClosePushL(gaps); + + TInt blockNumber = 0; + TInt lastReadBlockNumber = 0; + TInt nextWriteBlockNumber = 0; + TInt err = KErrNone; + while (err == KErrNone) + { + TSlot gap; + TInt dataLength = 0; + TRAP(err, dataLength = iFileReadStream.ReadInt32L()); + if (err == KErrNone) + { + TInt blockCount; + if (dataLength >= 0) + { + // real data + blockCount = BlockCount(dataLength); +#if 0 + DEBUGSTRING(("Copying at block %d, count %d", + blockNumber, + blockCount)); +#endif + // Back off four bytes + streamBuf->SeekL(MStreamBuf::ERead, + EStreamMark, + -KSlotHeaderSize); + dstFileWriteStream.WriteL(iFileReadStream, + blockCount * iBlockSize); + lastReadBlockNumber = blockNumber; + nextWriteBlockNumber += blockCount; + } + else + { + // empty slot + DEBUGSTRING(("Compacting at block %d", blockNumber)); + blockCount = -dataLength; + streamBuf->SeekL(MStreamBuf::ERead, + EStreamMark, + blockCount * iBlockSize - KSlotHeaderSize); + // Mark block position + gap.iIndex = 0; // not needed here + gap.iBlockNumber = blockNumber; + gap.iBlockCount = blockCount; + gaps.Append(gap); + } + blockNumber += blockCount; + } + } + if (err == KErrEof) + { + err = KErrNone; + } + // Replace old file with the compressed file + SetFileStateL(EFileStateClosed); + dstFileWriteStream.Close(); + dstFile.Close(); + if ((err == KErrNone) && gaps.Count()) + { + // No errors and some compaction was achieved + err = iFs.Delete(iPath); + if (err == KErrNone) + { + err = iFs.Rename(dstPath, iPath); + if (err == KErrNone) + { + DEBUGSTRING(("CompactL(): gaps %d slots %d", + gaps.Count(), + iSlots.Count())); + if (gaps.Count() && iSlots.Count()) + { + // Fix slot table (0(n**2)) + TInt oldBlockNumber = 0; + TInt newBlockNumber = 0; + while (oldBlockNumber <= lastReadBlockNumber) + { + if (gaps.Count()) + { + // still more gaps ... + if (oldBlockNumber == gaps[0].iBlockNumber) + { + oldBlockNumber += gaps[0].iBlockCount; + gaps.Remove(0); + } + } + if (oldBlockNumber != newBlockNumber) + { + FixSlot(oldBlockNumber, newBlockNumber); + } + oldBlockNumber++; + newBlockNumber++; + } + } + } + } + // Clear free block lists + ClearFreeBlockLists(); + // Setup next block to write + iWriteBlockNumber = nextWriteBlockNumber; + } + else + { + // Some error occured or no compaction was achieved + TInt r = iFs.Delete(dstPath); +#ifdef _DEBUG + DEBUGSTRING(("CompactL(): destination file deletion returns %d ", r)); +#endif + } + + CleanupStack::PopAndDestroy(3, &dstFile); // gaps, dstFileWriteStream, dstFile + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::SetHeaderL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::SetHeaderL(TDesC8& aHeader) + { + delete iFileHeader.iHeader; + iFileHeader.iHeader = NULL; + iFileHeader.iHeader = aHeader.AllocL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::Header +// ---------------------------------------------------------------------------- +// +const HBufC8* CRsfwPermanentStore::Header() + { + if (iFileHeader.iHeader) + { + return iFileHeader.iHeader; + } + else + { + return NULL; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::GetNextDataL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::GetNextDataL(TUint8* aData, + TInt& aDataLength, + TInt& aIndex) + { + // Return the next slotful of data. + // This function must only be used for sequential access + SetFileStateL(EFileStateReading); + + MStreamBuf* streamBuf = iFileReadStream.Source(); + + TBool done = EFalse; + while (!done) + { + TInt dataLength = 0; + // Eventually leaves with KErrEof + dataLength = iFileReadStream.ReadInt32L(); + TInt blockCount; + if (dataLength >= 0) + { + // Fill data + iFileReadStream.ReadL(aData, dataLength); + aDataLength = dataLength; + aIndex = iIndex; + + // Update block map + blockCount = BlockCount(dataLength); +#if 0 + DEBUGSTRING(( + "GetNextDataL(): index=%d, block=%d, count=%d, len=%d", + iIndex, + iReadBlockNumber, + blockCount, + dataLength)); +#endif + + ReserveSlot(iIndex, iReadBlockNumber, blockCount); + iIndex++; + iReadBlockNumber += blockCount; + + // Update read position to the start of next block + TInt offset = iBlockSize - + (KSlotHeaderSize + dataLength) % iBlockSize; + if (offset != iBlockSize) + { + streamBuf->SeekL(MStreamBuf::ERead, EStreamMark, offset); + } + + done = ETrue; + } + else + { + // Negative length indicates a number of free blocks. + // Put such empty blocks into the free block list + blockCount = -dataLength; + PutToFreeBlockList(iReadBlockNumber, blockCount); + + // Seek to the next slot + streamBuf->SeekL(MStreamBuf::ERead, + EStreamMark, + blockCount * iBlockSize - KSlotHeaderSize); + iReadBlockNumber += blockCount; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::PutDataL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::PutDataL(const TUint8* aData, + TInt aDataLength, + TInt& aIndex) + { + // Write data with the given index + // If the index < 0, this a new data + SetFileStateL(EFileStateWriting); + + if (aDataLength == 0) + { + // We just want to dispose of the slot + ClearSlotL(aIndex); + return; + } + + TBool done = EFalse; + TInt blockCount = BlockCount(aDataLength); + if (aIndex >= 0) + { + // Check if we have space in the existing slot + TSlot* slot = Slot(aIndex); + // We should always find the slot + if (slot) + { + if (slot->iBlockCount == blockCount) + { + // We can use the current slot + WriteBlocksL(aData, aDataLength, slot->iBlockNumber); + done = ETrue; + } + else + { + // Clear the slot + ClearSlotL(aIndex); + } + } + else + { + DEBUGSTRING(("Slot %d not found!", aIndex)); + } + } + else + { + // Allocate new index + aIndex = iIndex++; + } + + if (!done) + { + // Try to get a free slot + TInt blockNumber = GetFromFreeBlockList(blockCount); + if (blockNumber == KErrNotFound) + { + // We have to append to the file + blockNumber = iWriteBlockNumber; + iWriteBlockNumber += blockCount; + } + + ReserveSlot(aIndex, blockNumber, blockCount); + WriteBlocksL(aData, aDataLength, blockNumber); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::BlockCount +// ---------------------------------------------------------------------------- +// +TInt CRsfwPermanentStore::BlockCount(TInt aDataLength) + { + // Get the block count for a given data size + return (KSlotHeaderSize + aDataLength - 1) / iBlockSize + 1; + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::StreamPosition +// ---------------------------------------------------------------------------- +// +TInt CRsfwPermanentStore::StreamPosition(TInt aBlockNumber) + { + // Get the stream position from block position + return (iFileHeaderSize + aBlockNumber * iBlockSize); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::Slot +// ---------------------------------------------------------------------------- +// +TSlot* CRsfwPermanentStore::Slot(TInt aIndex) + { + // Find the slot with the given index + TSlot slot; // dummy slot for Find() + slot.iIndex = aIndex; + TInt i = iSlots.Find(slot); + if (i != KErrNotFound) + { + return &iSlots[i]; + } + else + { + return NULL; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::FixSlot +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::FixSlot(TInt aOldBlockNumber, TInt aNewBlockNumber) + { + // Assign a new starting block to the slot that used to + // start at aOldBlockNumber. + // The block numbers are changed due to compaction - + // thus the block numbers can only become smaller. + TInt i; + for (i = 0; i < iSlots.Count(); i++) + { + TSlot& slot = iSlots[i]; + // Note that this function can also be called with block numbers + // that do not start a slot - then there will be no match + if (slot.iBlockNumber == aOldBlockNumber) + { + DEBUGSTRING(("Fixing slot %d = %d", + aOldBlockNumber, + aNewBlockNumber)); + slot.iBlockNumber = aNewBlockNumber; + return; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::SetFileStateL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::SetFileStateL(TInt aFileState) + { + DEBUGSTRING(("CRsfwPermanentStore::SetFileStateL")); + DEBUGSTRING(("iFileState = %d, aFileState = %d", iFileState, aFileState)); + if (iFileState != aFileState) + { + switch (iFileState) + { + case EFileStateClosed: + { + if (aFileState == EFileStateReading) + { + DEBUGSTRING(("opening a closed file for reading")); + DEBUGSTRING16(("path is %S", &iPath)); + User::LeaveIfError(iFile.Open(iFs, + iPath, + EFileShareAny | EFileRead)); + TInt size; + iFile.Size(size); + DEBUGSTRING(("opening successfull, file size is %d", size)); + DEBUGSTRING(("header size %d", iFileHeaderSize)); + // sanity + if (size < iFileHeaderSize) + { + // Close the file and leave the file state as "closed" + iFile.Close(); + User::Leave(KErrNotFound); + } + else + { + iFileReadStream.Attach(iFile); + } + } + else + { + // EFileStateWriting + TInt err = iFile.Open(iFs, iPath, EFileShareAny | EFileWrite); + if (err != KErrNone) + { + // The file did not exist + User::LeaveIfError( + iFile.Create(iFs, + iPath, + EFileShareAny | EFileWrite)); + } + TInt size; + User::LeaveIfError(iFile.Size(size)); + iFileWriteStream.Attach(iFile); + if (size < iFileHeaderSize) + { + // Store header if this was a new file + SaveHeaderL(); + } + } + } + break; + + case EFileStateReading: + case EFileStateWriting: + { + // close and redo + if (iFileState == EFileStateReading) + { + iFileReadStream.Close(); + } + else + { + iFileWriteStream.Close(); + } + iFile.Close(); + iFileState = EFileStateClosed; + SetFileStateL(aFileState); + } + break; + + default: + break; + } + + iFileState = aFileState; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::LoadHeaderL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::LoadHeaderL() + { + DEBUGSTRING(("CRsfwPermanentStore::LoadHeaderL")); + SetFileStateL(EFileStateReading); + iFileHeader.InternalizeL(iFileReadStream); + ResetL(EFalse); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::SaveHeaderL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::SaveHeaderL() + { + // Write header with filler + iFileHeader.ExternalizeL(iFileWriteStream); + MStreamBuf* streamBuf = iFileWriteStream.Sink(); + TInt fileHeaderSize = streamBuf->TellL(MStreamBuf::EWrite).Offset(); + TInt residue = iFileHeaderSize - fileHeaderSize; + HBufC8* fill = HBufC8::NewLC(residue); + TPtr8 fillZ = fill->Des(); + fillZ.SetLength(residue); + fillZ.FillZ(); + DEBUGSTRING(("SaveHeader(): header=%d, filler=%d", + iFileHeaderSize, + fillZ.Length())); + iFileWriteStream.WriteL(fillZ); + Commit(); + CleanupStack::PopAndDestroy(fill); // fill + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::ClearFreeBlockLists +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::ClearFreeBlockLists() + { + TInt i; + for (i = 0; i < iFreeBlockLists.Count(); i++) + { + iFreeBlockLists[i].iFreeBlockList.Close(); + } + iFreeBlockLists.Close(); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::ClearSlotL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::ClearSlotL(TInt aIndex) + { + // Mark a slot as unused in the file and + // add the slot in the free block list + + TSlot s; // dummy slot for iSlots.Find() + s.iIndex = aIndex; + TInt i = iSlots.Find(s); + if (i != KErrNotFound) + { + TSlot& slot = iSlots[i]; + // Mark the slot in the file as empty + TInt pos = iFileHeaderSize + slot.iBlockNumber * iBlockSize; + + DEBUGSTRING(("ClearSlotL(): index=%d, block=%d, count=%d, pos=%d", + aIndex, + slot.iBlockNumber, + slot.iBlockCount, + pos)); + + MStreamBuf* streamBuf = iFileWriteStream.Sink(); + streamBuf->SeekL(MStreamBuf::EWrite, EStreamBeginning, pos); + iFileWriteStream.WriteInt32L(-slot.iBlockCount); + + // Add the slot in the free block list + PutToFreeBlockList(slot.iBlockNumber, slot.iBlockCount); + + // Delete the slot from the slot table + iSlots.Remove(i); + } + else + { + DEBUGSTRING(("ClearSlotL(): index=%d not found!", aIndex)); + User::Leave(KErrNotFound); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::WriteBlocksL +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::WriteBlocksL(const TUint8* aData, + TInt aDataLength, + TInt aBlockNumber) + { + // Put the given data in the slot specified by the index + TInt pos = iFileHeaderSize + aBlockNumber * iBlockSize; + +#if 0 + DEBUGSTRING(("WriteBlocksL(): block=%d, len=%d, pos=%d", + aBlockNumber, + aDataLength, + pos)); +#endif +#if 0 + TInt size; + iFile.Size(size); + + DEBUGSTRING(("size=%d", size)); +#endif + + MStreamBuf* streamBuf = iFileWriteStream.Sink(); + streamBuf->SeekL(MStreamBuf::EWrite, EStreamBeginning, pos); + + // Write the data in the file (preceded by the length) + iFileWriteStream.WriteInt32L(aDataLength); + iFileWriteStream.WriteL(aData, aDataLength); + + // We have to fill the whole slot if this is the last slot + // in the file. Well, we will will the last bock of all slots + TInt residue = iBlockSize - (KSlotHeaderSize + aDataLength) % iBlockSize; + if (residue != iBlockSize) + { + iFileWriteStream.WriteL(iZeroBlock->Des().Ptr(), residue); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::ReserveSlot +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::ReserveSlot(TInt aIndex, + TInt aBlockNumber, + TInt aBlockCount) + { + TSlot slot; + + slot.iIndex = aIndex; + slot.iBlockNumber = aBlockNumber; + slot.iBlockCount = aBlockCount; + iSlots.Append(slot); + } + + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::PutToFreeBlockList +// ---------------------------------------------------------------------------- +// +void CRsfwPermanentStore::PutToFreeBlockList(TInt aBlockPos, TInt aBlockCount) + { + while (iFreeBlockLists.Count() < aBlockCount) + { + // Construct list until blockCount size + TFreeBlockList freeBlockList; + iFreeBlockLists.Append(freeBlockList); + } + iFreeBlockLists[aBlockCount - 1].iFreeBlockList.Append(aBlockPos); + } + +// ---------------------------------------------------------------------------- +// CRsfwPermanentStore::GetFromFreeBlockList +// ---------------------------------------------------------------------------- +// +TInt CRsfwPermanentStore::GetFromFreeBlockList(TInt aBlockCount) + { + // Only support exact matches. + // That is, bigger slots are not broken into smaller slots + if (iFreeBlockLists.Count() < aBlockCount) + { + // no list + return KErrNotFound; + } + + TFreeBlockList& freeBlockList = iFreeBlockLists[aBlockCount - 1]; + if (freeBlockList.iFreeBlockList.Count() == 0) + { + // no entries in the list + return KErrNotFound; + } + + // Get the first entry in the list + TInt blockPos = freeBlockList.iFreeBlockList[0]; + freeBlockList.iFreeBlockList.Remove(0); + return blockPos; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwremoteaccess.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwremoteaccess.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,80 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Access Protocol plug-in loader + * +*/ + + +// INCLUDES +#include "rsfwremoteaccess.h" +#include + + +// ---------------------------------------------------------------------------- +// CRsfwRemoteAccess* CRsfwRemoteAccess::NewL +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwRemoteAccess* CRsfwRemoteAccess::NewL(const TDesC8& aProtocol) + { + // Set up the interface find for the default resolver + TBuf8 matchString; + _LIT8(KRemoteMatchPrefix, "remoteaccess/"); + matchString.Copy(KRemoteMatchPrefix); + + // Both "http" and "https" are handled by davaccess module + _LIT8(KHttps, "https"); + if (aProtocol.Compare(KHttps) == 0) + { + _LIT8(KHttp, "http"); + matchString.Append(KHttp); + } + else + { + matchString.Append(aProtocol); + } + TEComResolverParams resolverParams; + resolverParams.SetDataType(matchString); + // Disable wildcard matching + resolverParams.SetWildcardMatch(EFalse); + + return REINTERPRET_CAST(CRsfwRemoteAccess*, + REComSession::CreateImplementationL( + KCRemoteAccessUid, + _FOFF(CRsfwRemoteAccess, iDtor_ID_Key), + resolverParams)); + } + +// ---------------------------------------------------------------------------- +// CRsfwRemoteAccess::~CRsfwRemoteAccess +// ---------------------------------------------------------------------------- +// +EXPORT_C CRsfwRemoteAccess::~CRsfwRemoteAccess() + { + // Inform the framework that this specific + // instance of the interface has been destroyed. + REComSession::DestroyedImplementation(iDtor_ID_Key); + } + +// ---------------------------------------------------------------------------- +// CRsfwRemoteAccess:: GetQuotaAndSizeL +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt CRsfwRemoteAccess:: GetQuotaAndSizeL(TInt& aQuota, TInt& aSize) + { + aQuota = KMountReportedSize; + aSize = KMountReportedFreeSize; + return 0; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwremoteaccesssync.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwremoteaccesssync.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,324 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Synchronous layer on top of the Access Protocol plug-in API + * +*/ + + +// INCLUDE FILES +#include "rsfwremoteaccesssync.h" + + +// ============================ MEMBER FUNCTIONS ============================== + +CRsfwRemoteAccessSync* CRsfwRemoteAccessSync::NewL(const TDesC8& aService, + CRsfwRemoteAccess* aRemoteAccess) + { + CRsfwRemoteAccessSync* self = new (ELeave) CRsfwRemoteAccessSync; + CleanupStack::PushL(self); + self->ConstructL(aService, aRemoteAccess); + CleanupStack::Pop(self); + return self; + } + +void CRsfwRemoteAccessSync::ConstructL(const TDesC8& aService, + CRsfwRemoteAccess* aRemoteAccess) + { + if (aRemoteAccess) + { + iRemoteAccess = aRemoteAccess; + } + else + { + iRemoteAccess = CRsfwRemoteAccess::NewL(aService); + iOwnRemoteAccess = ETrue; + } + iSchedulerWait = new CActiveSchedulerWait(); + } + +CRsfwRemoteAccessSync::~CRsfwRemoteAccessSync() + { + if (iOwnRemoteAccess) + { + delete iRemoteAccess; + } + delete iSchedulerWait; + } + +TInt CRsfwRemoteAccessSync::Setup( + MRsfwRemoteAccessObserver* aRsfwRemoteAccessObserver) + { + TRAPD(err, iRemoteAccess->SetupL(aRsfwRemoteAccessObserver)); + return err; + } + +TInt CRsfwRemoteAccessSync::Open(const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aServerName, + TInt aPortNumber, + const TDesC& aRootDirectory, + const TDesC& aAuxData) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TBuf url; + url.Append(_L("http://")); + url.Append(aServerName); + url.Append(_L(":")); + url.AppendNum(aPortNumber); + url.Append(_L("/")); + url.Append(aRootDirectory); + + + TUriParser uriParser; + uriParser.Parse(url); + + TRAP(iStatus, iRemoteAccess->OpenL(uriParser, + aServerName, + aUserName, + aPassword, + aAuxData, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::GetDirectory(const TDesC& aPathName, + RPointerArray& aDirEnts) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->GetDirectoryL(aPathName, + aDirEnts, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::GetFile(const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->GetFileL(aRemotePathName, + aLocalPathName, + aOffset, + aLength, + aFlags, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::MakeDirectory(const TDesC& aPathName) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->MakeDirectoryL(aPathName, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::CreateFile(const TDesC& aPathName) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->CreateFileL(aPathName, 0, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::PutFile(const TDesC& aLocalPathName, + const TDesC& aRemotePathName) + { + _LIT8(KTextPlain, "text/plain"); + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->PutFileL(aLocalPathName, + aRemotePathName, + KTextPlain, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::DeleteDirectory(const TDesC& aPathName) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->DeleteDirectoryL(aPathName, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::DeleteFile(const TDesC& aPathName) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->DeleteFileL(aPathName, this)); + return Epilog(); + } + + +TInt CRsfwRemoteAccessSync::Rename(const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->RenameL(aSrcPathName, + aDstPathName, + aOverwrite, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::GetDirectoryAttributes(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, + iRemoteAccess->GetDirectoryAttributesL(aPathName, aAttr, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::GetFileAttributes(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->GetFileAttributesL(aPathName, + aAttr, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::SetAttributes(const TDesC& aPathName, + CRsfwDirEntAttr& aAttr) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->SetAttributesL(aPathName, aAttr, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::ObtainLock(const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8*& aLockToken) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, + iRemoteAccess->ObtainLockL(aPathName, + aLockFlags, + aTimeout, + aLockToken, + this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::ReleaseLock(const TDesC& aPathName) + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->ReleaseLockL(aPathName, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::RefreshLock(const TDesC& aPathName, + TUint& aTimeout) + + { + if (iPending) + { + return KErrServerBusy; + } + iPending = ETrue; + TRAP(iStatus, iRemoteAccess->RefreshLockL(aPathName, aTimeout, this)); + return Epilog(); + } + +TInt CRsfwRemoteAccessSync::SetLockToken(const TDesC& aPathName, + const TDesC8& aLockToken) + { + return iRemoteAccess->SetLockToken(aPathName, aLockToken); + } + +// ----------------------------------------------------------------- +// from MRemoteAccessResponseHandler +// ----------------------------------------------------------------- + +void CRsfwRemoteAccessSync::HandleRemoteAccessResponse(TUint /* aId */, + TInt aStatus) + { + iStatus = aStatus; + if (iSchedulerWait->IsStarted()) + { + iSchedulerWait->AsyncStop(); + } + iPending = EFalse; + } + +// ----------------------------------------------------------------- + +TInt CRsfwRemoteAccessSync::Epilog() + { + if (iPending && (iStatus == KErrNone)) + { + iSchedulerWait->Start(); + } + return iStatus; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrenamefilestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrenamefilestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,296 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: State machine for renaming files +* +*/ + + +#include "rsfwrenamefilestatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwfileengine.h" +#include "rsfwlockmanager.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::CRsfwRenameFileStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine::CRsfwRenameFileStateMachine() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::~CRsfwRenameFileStateMachine +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine::~CRsfwRenameFileStateMachine() + { + delete iLockToken; + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* +CRsfwRenameFileStateMachine::CompleteRequestL(TInt aError) + { + if (iSrcKidCreated) + { + if (aError) + { + delete iSrcKidFep; + iSrcKidFep = NULL; + } + } + if (iDstKidCreated) + { + delete iDstKidFep; + iDstKidFep = NULL; + } + + // it may happen that the new name is equal to iLastFailedLookup value + FileEngine()->ResetFailedLookup(); + + CompleteAndDestroyState()->SetErrorCode(aError); + return CompleteAndDestroyState(); + } + + + +// Rename the file + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TRenameFileState::TRenameFileState +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine:: +TRenameFileState::TRenameFileState(CRsfwRenameFileStateMachine* aParent) + : iOperation(aParent) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TRenameFileState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwRenameFileStateMachine::TRenameFileState::EnterL() + { + // rename or replace + TRfeRenameInArgs* inArgs = + static_cast(iOperation->iInArgs); + iOperation->iOverWrite = inArgs->iOverWrite; + + TFid* dstParentFidp = &(inArgs->iDstFid); + TPtrC16 srcKidName(inArgs->iSrcName); + iOperation->iDstKidName.Set(inArgs->iDstName); + + // Get the parent from which we are removing + if (!iOperation->Node()) + { + User::Leave(KErrNotFound); + } + + // Get the parent to which we are removing + iOperation->iDstParentFep = + iOperation->FileEngine()->iFileTable->Lookup(*dstParentFidp); + if (!iOperation->iDstParentFep) + { + User::Leave(KErrNotFound); + } + + // Do we know the target kid yet? + iOperation->iDstKidFep = + iOperation->iDstParentFep->FindKidByName(iOperation->iDstKidName); + if (!iOperation->iDstKidFep) + { + // Create a temporary file entry for building the full path + iOperation->iDstKidFep = + CRsfwFileEntry::NewL(iOperation->iDstKidName, + iOperation->iDstParentFep); + iOperation->iDstKidCreated = ETrue; + } + + // Do we know the source kid yet? + iOperation->iSrcKidFep = iOperation->Node()->FindKidByName(srcKidName); + if (!iOperation->iSrcKidFep) + { + iOperation->iSrcKidFep = CRsfwFileEntry::NewL(srcKidName, + iOperation->Node()); + iOperation->iSrcKidCreated = ETrue; + } + + if (!iOperation->FileEngine()->Disconnected()) + { + // Do the rename + HBufC* srcKidPath = + iOperation->FileEngine()->FullNameLC(*iOperation->iSrcKidFep); + if ((*iOperation->iSrcKidFep).Type() == KNodeTypeDir) + { // if source is a directory, make sure the name ends with a slash + if ((*srcKidPath)[(srcKidPath->Length() - 1)] != '/') + { + TPtr srcKidAppend = srcKidPath->Des(); + srcKidAppend.Append('/'); + } + } + + HBufC* dstKidPath = + iOperation->FileEngine()->FullNameLC(*iOperation->iDstKidFep); + if ((*iOperation->iDstKidFep).Type() == KNodeTypeDir) + { // if source is a directory, make sure the name ends with a slash + if ((*dstKidPath)[(dstKidPath->Length() -1)] != '/') + { + TPtr dstKidAppend = dstKidPath->Des(); + dstKidAppend.Append('/'); + } + } + iOperation-> + FileEngine()-> + RemoteAccessL()->RenameL(*srcKidPath, + *dstKidPath, + iOperation->iOverWrite, + iOperation); + CleanupStack::PopAndDestroy(2, srcKidPath); // dstKidPath, srcKidPath + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TRenameFileState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine::TState* +CRsfwRenameFileStateMachine::TRenameFileState::CompleteL() + { + if (!iOperation->iSrcKidCreated) + { + // If we didn't create the srcKidFep, + // we must remove it from parent's list + iOperation->Node()->RemoveKidL(iOperation->iSrcKidFep); + } + else + { + // Enter source into the file table + iOperation->Node()->iFileTable->AddL(iOperation->iSrcKidFep); + } + + if (!iOperation->iDstKidCreated) + { + // If we didn't create the dstKidFep, we must remove and destroy it + // unless the node has a removed marking set + // (should not happen, except for removed nodes) + iOperation->FileEngine()->iFileTable->RemoveL(iOperation->iDstKidFep); + delete iOperation->iDstKidFep; + iOperation->iDstKidFep = NULL; + } + + // Change srcKidFep's name, + // and insert the fep into the dstParentFep directory + iOperation->iSrcKidFep->RenameL(iOperation->iDstKidName); + iOperation->iDstParentFep->AddKid(*iOperation->iSrcKidFep); + + // Refresh both parent directories + iOperation->Node()->SetLocallyDirty(); + if (iOperation->Node() != iOperation->iDstParentFep) + { + iOperation->Node()->SetLocallyDirty(); + } + + return new CRsfwRenameFileStateMachine::TAcquireLockState(iOperation); + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TRenameFileState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine::TState* +CRsfwRenameFileStateMachine::TRenameFileState::ErrorL(TInt aCode) + { + DEBUGSTRING(("remote rename failed")); + return iOperation->CompleteRequestL(aCode); + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TAcquireLockState::TAcquireLockState +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine:: +TAcquireLockState::TAcquireLockState(CRsfwRenameFileStateMachine* aParent) + { + iOperation = aParent; + iRequestedLock = EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TAcquireLockState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwRenameFileStateMachine::TAcquireLockState::EnterL() + { + if (!iOperation->FileEngine()->WriteDisconnected()) + { + // Now we have updated everything necessary in iSrcKidFep + // possibly lock timer is ticking with etc. + // However, at least WebDAV does not lock the new file in move, + // so if the old file was locked we need to tell + // the access protocol plug-in that it must lock the new file. + if (iOperation->iSrcKidFep->IsLocked()) + { + iOperation->iSrcKidFep->iLockTimer->Cancel(); + iOperation->FileEngine()->LockManager()-> + ObtainLockL(iOperation->iSrcKidFep, + EFileWrite, + iOperation->iLockToken, + iOperation); + iRequestedLock = ETrue; + } + else + { + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + else + { + iOperation->HandleRemoteAccessResponse(0, KErrNone); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TAcquireLockState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine::TState* +CRsfwRenameFileStateMachine::TAcquireLockState::CompleteL() + { + if (iRequestedLock) + { + iOperation-> + iSrcKidFep->SetLockedL(iOperation->FileEngine()->LockManager(), + iOperation->iLockToken); + iOperation->iLockToken = NULL; + } + return iOperation->CompleteRequestL(KErrNone); + } + +// ---------------------------------------------------------------------------- +// CRsfwRenameFileStateMachine::TAcquireLockState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRenameFileStateMachine::TState* +CRsfwRenameFileStateMachine::TAcquireLockState::ErrorL(TInt aCode) + { + return iOperation->CompleteRequestL(aCode); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrequestallocator.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrequestallocator.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,103 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Operation and request allocation and deletion +* +*/ + + +#include "rsfwrequestallocator.h" +#include "rsfwrfesyncoperation.h" +#include "rsfwrfeasyncoperation.h" +#include "rsfwrfemessagerequest.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// RsfwRequestAllocator::GetSyncOperation +// ---------------------------------------------------------------------------- +// +CRsfwRfeSyncOperation* RsfwRequestAllocator::GetSyncOperation(CRsfwRfeRequest* aRequest, + TInt aCaller) + { + CRsfwRfeSyncOperation* pO = NULL; + pO = new CRsfwRfeSyncOperation(); + if (pO) + { + pO->Set(aRequest, aCaller); + } + return pO; + } + +// ---------------------------------------------------------------------------- +// RsfwRequestAllocator::GetAsyncOperation +// ---------------------------------------------------------------------------- +// +CRsfwRfeAsyncOperation* RsfwRequestAllocator::GetAsyncOperation(CRsfwRfeRequest* aRequest, + TInt aCaller) + { + CRsfwRfeAsyncOperation* pO = NULL; + pO = new CRsfwRfeAsyncOperation(); + if (pO) + { + TRAPD(err, pO->SetL(aRequest, aCaller)); + if (err) + { + DEBUGSTRING(("Setting the operation failed with error %d!!!",err)); + delete pO; + pO = NULL; + } + } + return pO; + } + +// ---------------------------------------------------------------------------- +// RsfwRequestAllocator::GetMessageRequest +// allocate requests +// Return a pointer to a message request of type specificied by aCaller and initialised +// ---------------------------------------------------------------------------- +// +CRsfwRfeMessageRequest* RsfwRequestAllocator::GetMessageRequest( + const RMessage2& aMessage, + CRsfwRfeSession* aSession) + { + CRsfwRfeMessageRequest* pM = NULL; + + pM = new CRsfwRfeMessageRequest(); + + if (pM) + { + TRAPD(err, pM->SetL(aMessage,aSession)); + if (err) + { + delete pM; + pM = NULL; + } + return pM; + } + else + { + return NULL; + } + } + +// ---------------------------------------------------------------------------- +// RsfwRequestAllocator::FreeRequest +// ---------------------------------------------------------------------------- +// +void RsfwRequestAllocator::FreeRequest(CRsfwRfeRequest* aRequest) + { + delete aRequest; + } + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfeasyncoperation.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfeasyncoperation.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,378 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Encapsulates an asynchronous operation +* +*/ + + +#include "rsfwrfeasyncoperation.h" +#include "rsfwrfemessagerequest.h" +#include "rsfwrfestatemachine.h" +#include "rsfwmountstatemachine.h" +#include "rsfwmountconnectionstatemachine.h" +#include "rsfwopenbypathstatemachine.h" +#include "rsfwgetattributesstatemachine.h" +#include "rsfwattributerefreshingstatemachine.h" +#include "rsfwfetchandcachestatemachine.h" +#include "rsfwfetchdatastatemachine.h" +#include "rsfwlookupstatemachine.h" +#include "rsfwclosestatemachine.h" +#include "rsfwflushstatemachine.h" +#include "rsfwmkdirstatemachine.h" +#include "rsfwdeletestatemachine.h" +#include "rsfwcreatefilestatemachine.h" +#include "rsfwrenamefilestatemachine.h" +#include "rsfwvolumetable.h" +#include "mdebug.h" +#include "rsfwcommon.h" +#include "rsfwrfeserver.h" +#include "rsfwinterface.h" + + +// ---------------------------------------------------------------------------- +// CRsfwRfeAsyncOperation::~CRsfwRfeAsyncOperation +// ---------------------------------------------------------------------------- +// +CRsfwRfeAsyncOperation::~CRsfwRfeAsyncOperation() + { + delete iImplementation; + iImplementation = NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeAsyncOperation::Implementation +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine* CRsfwRfeAsyncOperation::Implementation() + { + return iImplementation; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeAsyncOperation::SetImplementation +// ---------------------------------------------------------------------------- +// +void CRsfwRfeAsyncOperation::SetImplementation(CRsfwRfeStateMachine* aImpl) + { + iImplementation = aImpl; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeAsyncOperation::SetL +// Set asynchronous operation and its parameters +// Leave if OOM etc. +// ---------------------------------------------------------------------------- +// +void CRsfwRfeAsyncOperation::SetL(CRsfwRfeRequest* aRequest, TInt aOpCode) + { + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*)aRequest; + CRsfwRfeStateMachine::TState* initialState = NULL; + CRsfwRfeStateMachine* operation = NULL; + + if (aRequest->iVolume) + { + DEBUGSTRING(("<<< Dispatch enter (operation=%d, volume=%d)", + aOpCode, + aRequest->iVolume->iMountInfo.iMountStatus.iVolumeId)); + } + else + { + DEBUGSTRING(("<<< Dispatch enter (operation=%d)", aOpCode)); + } + + switch (aOpCode) + { + case EMount: + case EMountByDriveLetter: + { + DEBUGSTRING(("EMount / EMountByDriveLetter")); + TRsfwMountConfig* mountConfig = new (ELeave) TRsfwMountConfig; + CleanupStack::PushL(mountConfig); + TPckg mountConfigPackage(*mountConfig); + if (aOpCode == EMount) + { + request->Message().ReadL(0, mountConfigPackage); + // this is to satisfy IPC fuzz testing + VerifyMountConfigL(*mountConfig); + } + else + { + // EMountByDriveLetter - create a stub TRsfwMountConfig + TInt driveNumber = request->Message().Int0(); + RFs fs = CRsfwRfeServer::Env()->iFs; + fs.DriveToChar(driveNumber, mountConfig->iDriveLetter); + mountConfig->iUri.SetLength(0); + } + + // fetch mountconfig from mountStore + if (!mountConfig->iUri.Length() || aOpCode == EMountByDriveLetter) + { + // the drive letter must be set + User::LeaveIfError(aRequest->iVolumeTable->GetMountConfigL( + *mountConfig)); + } + + // If there is an existing mount, the configurations must match. + // Otherwise we unmount the already existing mount. + CRsfwVolume* volume = + aRequest-> + iVolumeTable-> + VolumeByDriveLetter(mountConfig->iDriveLetter); + if (volume) + { + if (volume->iMountInfo.iMountConfig.iUri.CompareF( + mountConfig->iUri) != 0) + { + // We have a mismatch + DEBUGSTRING16(("Dismounting an obsolete mount %S", + &volume->iMountInfo.iMountConfig.iUri)); + aRequest-> + iVolumeTable-> + DismountByDriveLetterL(mountConfig->iDriveLetter, + ETrue); + } + } + TInt mountState = + aRequest->iVolumeTable->MountState(mountConfig->iDriveLetter); + operation = CRsfwMountStateMachine::NewL(*mountConfig, + mountState, + aRequest->iVolumeTable); + CleanupStack::PushL(operation); + ((CRsfwWaitNoteStateMachine *) operation)->BaseConstructL(); + initialState = + new (ELeave) CRsfwMountStateMachine::TRequestConnectionState( + (CRsfwMountStateMachine *)operation); + + CleanupStack::Pop(operation); + DEBUGSTRING16(("EMount: name '%S' with URI='%S' as '%c' (state=%d)", + &mountConfig->iName, + &mountConfig->iUri, + TUint(mountConfig->iDriveLetter), + mountState)); + CleanupStack::PopAndDestroy(mountConfig); + } + break; + + case ESetMountConnectionState: + { + DEBUGSTRING(("ESetMountConnectionState")); + // Set the connection state of the mount + TChar driveLetter = reinterpret_cast(request->Message().Ptr0()); + TUint state = reinterpret_cast(request->Message().Ptr1()); + DEBUGSTRING(("EMountConnectionState: drive '%c', state=%d", + TUint(driveLetter), + state)); + + operation = new(ELeave) CRsfwMountConnectionStateMachine(driveLetter, + state); + CleanupStack::PushL(operation); + ((CRsfwWaitNoteStateMachine *) operation)->BaseConstructL(); + initialState = + new (ELeave) CRsfwMountConnectionStateMachine::TChangeConnectionState( + (CRsfwMountConnectionStateMachine *)operation); + CleanupStack::Pop(operation); + } + + break; + + case EOpenByPath: + { + DEBUGSTRING(("OPENBYPATH")); + operation = new (ELeave) CRsfwOpenByPathStateMachine(); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + // we need to refresh attributes first + initialState = + new (ELeave) CRsfwGetAttributesStateMachine::TRefreshAttributesState( + (CRsfwAttributeRefreshingStateMachine *)operation); + CleanupStack::Pop(operation); + break; + } + + case EFetch: + { + DEBUGSTRING(("FETCH")); + operation = new (ELeave) CRsfwFetchAndCacheStateMachine(); + CleanupStack::PushL(operation); + ((CRsfwWaitNoteStateMachine *) operation)->BaseConstructL(); + initialState = + new (ELeave) CRsfwFetchAndCacheStateMachine::TFetchDataState( + (CRsfwFetchAndCacheStateMachine *)operation); + CleanupStack::Pop(operation); + break; + } + + case EFetchData: + { + DEBUGSTRING(("FETCHDATA")); + operation = new (ELeave) CRsfwFetchDataStateMachine(); + CleanupStack::PushL(operation); + ((CRsfwWaitNoteStateMachine *) operation)->BaseConstructL(); + initialState = new (ELeave) CRsfwFetchDataStateMachine::TFetchDataState( + (CRsfwFetchDataStateMachine *)operation); + CleanupStack::Pop(operation); + break; + } + + case ELookUp: + { + DEBUGSTRING(("LOOKUP")); + operation = new (ELeave) CRsfwLookupStateMachine(); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = new (ELeave) + CRsfwLookupStateMachine::TUpdateKidAttributesTryFirstTypeState( + (CRsfwLookupStateMachine *)operation); + CleanupStack::Pop(operation); + break; + } + + case EGetAttr: + { + DEBUGSTRING(("GETATTR")); + operation = new (ELeave) CRsfwGetAttributesStateMachine(); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = + new (ELeave) CRsfwGetAttributesStateMachine::TRefreshAttributesState( + (CRsfwGetAttributesStateMachine *)operation); + CleanupStack::Pop(operation); + break; + } + + case EClose: + { + DEBUGSTRING(("CLOSE")); + operation = new (ELeave) CRsfwCloseStateMachine(); + CleanupStack::PushL(operation); + ((CRsfwWaitNoteStateMachine *) operation)->BaseConstructL(); + initialState = + new (ELeave) CRsfwCloseStateMachine::TReleaseLockState( + (CRsfwCloseStateMachine *) operation); + CleanupStack::Pop(operation); + break; + } + case EFlush: + { + DEBUGSTRING(("FLUSH")); + operation = new (ELeave) CRsfwFlushStateMachine(); + CleanupStack::PushL(operation); + ((CRsfwFlushStateMachine *) operation)->BaseConstructL(); + initialState = + new (ELeave) CRsfwFlushStateMachine::TFlushDataToServerState( + (CRsfwFlushStateMachine *) operation); + CleanupStack::Pop(operation); + break; + } + + case EMkDir: + { + DEBUGSTRING(("MKDIR")); + operation = new (ELeave) CRsfwMkDirStateMachine(); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = new (ELeave) CRsfwMkDirStateMachine::TCheckIfExistsState( + (CRsfwMkDirStateMachine *) operation); + CleanupStack::Pop(operation); + break; + } + + case ERemoveDir: + { + DEBUGSTRING(("RMDIR")); + operation = new (ELeave) CRsfwDeleteStateMachine(KNodeTypeDir); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = new (ELeave) CRsfwDeleteStateMachine::TCheckIfCanBeDeleted( + (CRsfwDeleteStateMachine *) operation); + CleanupStack::Pop(operation); + break; + } + + case ERemove: + DEBUGSTRING(("REMOVE")); + operation = new (ELeave) CRsfwDeleteStateMachine(KNodeTypeFile); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = new (ELeave) CRsfwDeleteStateMachine::TCheckIfCanBeDeleted( + (CRsfwDeleteStateMachine *) operation); + CleanupStack::Pop(operation); + break; + + case ECreateFile: + DEBUGSTRING(("CREATE")); + operation = new (ELeave) CRsfwCreateFileStateMachine(); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = + new (ELeave) CRsfwCreateFileStateMachine::TCheckIfExistsState( + (CRsfwCreateFileStateMachine *) operation); + CleanupStack::Pop(operation); + break; + + case ERenameReplace: + DEBUGSTRING(("RENAME")); + operation = new (ELeave) CRsfwRenameFileStateMachine(); + CleanupStack::PushL(operation); + operation->BaseConstructL(); + initialState = new (ELeave) CRsfwRenameFileStateMachine::TRenameFileState( + (CRsfwRenameFileStateMachine *) operation); + CleanupStack::Pop(operation); + break; + + default: + // request handler function not set, + // would lead to accessing a NULL pointer + User::Panic(KRfeServer, ENullRequestHandler); + } + + SetImplementation(operation); + Implementation()->SetNextState(initialState); + + // Set parameters + iImplementation->SetVolumes(aRequest->iVolumeTable); + + if (aRequest->iVolume) + { + iImplementation->SetFileEngine(aRequest->iVolume->iFileEngine); + } + + iImplementation->SetArguments(aRequest->iInArgs, aRequest->iOutArgs); + + // Set backpointer to the request we are running, + // so that the state machine can easily complete it + iImplementation->SetRequest(aRequest); + + iIsSync = EFalse; + CRsfwRfeOperation::Set(aOpCode); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeAsyncOperation::VerifyMountConfigL +// Checks whether mount config data is correct +// ---------------------------------------------------------------------------- +// +void CRsfwRfeAsyncOperation::VerifyMountConfigL(TRsfwMountConfig& aMountConfig) + { + if (aMountConfig.iName.Length() > KMaxMountNameLength || + aMountConfig.iUri.Length() > KMaxMountUriLength || + aMountConfig.iUserName.Length() > KMaxMountUserNameLength || + aMountConfig.iPassword.Length() > KMaxMountPasswordLength || + aMountConfig.iAuxData.Length() > KMaxMountAuxDataLength) + { + DEBUGSTRING16(("CRsfwRfeAsyncOperation::VerifyMountConfigL bad aMountConfig argument")); + User::Leave(KErrArgument); + } + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfemessagerequest.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfemessagerequest.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,461 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: A request sent by a client (i.e. non-internal request) +* +*/ + + +#include "rsfwrfemessagerequest.h" +#include "rsfwrfeoperation.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwcommon.h" +#include "rsfwinterface.h" +#include "mdebug.h" +#include "rsfwrfesession.h" + + + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::CRsfwRfeMessageRequest +// ---------------------------------------------------------------------------- +// +CRsfwRfeMessageRequest::CRsfwRfeMessageRequest() + { + SetRequestType(EMessageRequest); + iMessageCompleted = EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::SetL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeMessageRequest::SetL(const RMessage2& aMessage, + CRsfwRfeSession* aSession) + { + DEBUGSTRING(("CRsfwRfeMessageRequest::Set")); + + // common for all operations + iMessage = aMessage; + iSession = aSession; + iVolumeTable = aSession->Volume(); + + // if a file system access operation + if (aMessage.Function() >= ERenameReplace) + { + switch (aMessage.Function()) + { + // read input parameters + case ERenameReplace: + { + TRfeRenameInArgs* inArgs = new (ELeave) TRfeRenameInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + case ESetAttr: + { + TRfeSetAttrInArgs* inArgs = new (ELeave) TRfeSetAttrInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + case EFsIoctl: + { + TRfeIoctlInArgs* inArgs = new (ELeave) TRfeIoctlInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + + case EGetAttr: + { + TRfeGetAttrInArgs* inArgs = new (ELeave) TRfeGetAttrInArgs(); + CleanupStack::PushL(inArgs); + TRfeGetAttrOutArgs* outArgs = new (ELeave )TRfeGetAttrOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); // inArgs, outArgs + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case EOpenByPath: + { + TRfeOpenByPathInArgs* inArgs = new (ELeave) TRfeOpenByPathInArgs(); + CleanupStack::PushL(inArgs); + TRfeOpenByPathOutArgs* outArgs = new (ELeave) TRfeOpenByPathOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); // inArgs, outArgs + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case EFsRoot: + { + TRfeRootInArgs* inArgs = new (ELeave) TRfeRootInArgs(); + CleanupStack::PushL(inArgs); + TRfeRootOutArgs* outArgs = new (ELeave) TRfeRootOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); // inArgs, outArgs + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case EMkDir: + { + TRfeMkdirInArgs* inArgs = new (ELeave) TRfeMkdirInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + + case ERemoveDir: + { + TRfeRmdirInArgs* inArgs = new (ELeave) TRfeRmdirInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + + case ECreateFile: + { + TRfeCreateInArgs* inArgs = new (ELeave) TRfeCreateInArgs(); + CleanupStack::PushL(inArgs); + TRfeCreateOutArgs* outArgs = new (ELeave) TRfeCreateOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); // inArgs, outArgs + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case ERemove: + { + TRfeRemoveInArgs* inArgs = new (ELeave) TRfeRemoveInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + + case ELookUp: + { + TRfeLookupInArgs* inArgs = new (ELeave) TRfeLookupInArgs(); + CleanupStack::PushL(inArgs); + TRfeLookupOutArgs* outArgs = new (ELeave) TRfeLookupOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case EClose: + { + TRfeCloseInArgs* inArgs = new (ELeave) TRfeCloseInArgs(); + inArgs->iFid.iVolumeId = aMessage.Int0(); + inArgs->iFid.iNodeId = aMessage.Int1(); + inArgs->iOpCode = EClose; + inArgs->iFlags = aMessage.Int2(); + iInArgs = inArgs; + iOutArgs = NULL; + break; + } + + case EFlush: + { + TRfeFlushInArgs* inArgs = new (ELeave) TRfeFlushInArgs(); + CleanupStack::PushL(inArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(inArgs); + iInArgs = inArgs; + break; + } + + case EFetch: + { + TRfeFetchInArgs* inArgs = new (ELeave) TRfeFetchInArgs(); + CleanupStack::PushL(inArgs); + TRfeFetchOutArgs* outArgs = new (ELeave) TRfeFetchOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case EFetchData: + { + TRfeFetchDataInArgs* inArgs = new (ELeave) TRfeFetchDataInArgs(); + CleanupStack::PushL(inArgs); + TRfeFetchDataOutArgs* outArgs = new (ELeave) TRfeFetchDataOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + + case EOkToWrite: + { + TRfeWriteDataInArgs* inArgs = new (ELeave) TRfeWriteDataInArgs(); + CleanupStack::PushL(inArgs); + TRfeWriteDataOutArgs* outArgs = new (ELeave) TRfeWriteDataOutArgs(); + CleanupStack::PushL(outArgs); + TPckg pkgInArgs(*inArgs); + aMessage.ReadL(0, pkgInArgs); + CleanupStack::Pop(2, inArgs); + iInArgs = inArgs; + iOutArgs = outArgs; + break; + } + } + + DEBUGSTRING(("volume id %d", iInArgs->iFid.iVolumeId)); + // Here volumeId may be 0 to denote "no volume id" + // This is OK - we assume that drive letter A is never allocated + iVolume = iVolumeTable->VolumeByVolumeId(iInArgs->iFid.iVolumeId); + + // As this is a file system access operation - not mount operation, + // if volume is null we are not ready for file operations + // - indicate this to the client who needs to call mount + TBool ready = + iVolume && + (iVolume->iMountInfo.iMountStatus.iMountState != + KMountStateDormant); + if (!ready && aMessage.Function() != EFsRoot && aMessage.Function() != EClose) + { + aMessage.Complete(KErrNotReady); + iMessageCompleted = ETrue; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::Message +// ---------------------------------------------------------------------------- +// +const RMessage2& CRsfwRfeMessageRequest::Message() + { + return iMessage; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::Session +// ---------------------------------------------------------------------------- +// +CRsfwRfeSession* CRsfwRfeMessageRequest::Session() + { + return iSession; + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::Session +// ---------------------------------------------------------------------------- +// +void CRsfwRfeMessageRequest::SetSession(CRsfwRfeSession* aSession) + { + iSession = aSession; + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::Complete +// ---------------------------------------------------------------------------- +// +void CRsfwRfeMessageRequest::Complete(TInt aError) + { + DEBUGSTRING(("CRsfwRfeMessageRequest::Complete")); + if (iSession) + { + DEBUGSTRING((">>> Dispatch exit (operation %d, error %d, return %d)", + Operation()->iFunction, + aError, + aError)); + DEBUGSTRING(("completing request")); + if (!Message().IsNull()) + { + Message().Complete(aError); + } + DEBUGSTRING(("request completed")); + iMessageCompleted = ETrue; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeMessageRequest::CompleteAndDestroy +// ---------------------------------------------------------------------------- +// +void CRsfwRfeMessageRequest::CompleteAndDestroy(TInt aError) + { + DEBUGSTRING(("CRsfwRfeMessageRequest::CompleteAndDestroy")); + + TInt err; + err = KErrNone; + if (iSession) + { + DEBUGSTRING((">>> Dispatch exit (operation %d, error %d, return %d)", + Operation()->iFunction, aError, aError)); + switch (Operation()->iFunction) + { + // write output parameters + case EFetch: + { + DEBUGSTRING(("writing parameters: EFetch")); + TRfeFetchOutArgs* outArgs = (TRfeFetchOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case EFetchData: + { + DEBUGSTRING(("writing parameters: EFetchData")); + TRfeFetchDataOutArgs* outArgs = (TRfeFetchDataOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case EOkToWrite: + { + DEBUGSTRING(("writing parameters: EOkToWrite")); + TRfeWriteDataOutArgs* outArgs = (TRfeWriteDataOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case ELookUp: + { + DEBUGSTRING(("writing parameters: ELookup")); + TRfeLookupOutArgs* outArgs = (TRfeLookupOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case ECreateFile: + { + DEBUGSTRING(("writing parameters: ECreateFile")); + TRfeCreateOutArgs* outArgs = (TRfeCreateOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case EOpenByPath: + { + DEBUGSTRING(("writing parameters: EOpenByPath")); + TRfeOpenByPathOutArgs* outArgs = + (TRfeOpenByPathOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case EGetAttr: + { + DEBUGSTRING(("writing parameters: EGetAttr")); + TRfeGetAttrOutArgs* outArgs = (TRfeGetAttrOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + + case EFsRoot: + { + DEBUGSTRING(("writing parameters: EFsRoot")); + TRfeRootOutArgs* outArgs = (TRfeRootOutArgs *)(iOutArgs); + TPckg pkgOutArgs(*outArgs); + err = Message().Write(1, pkgOutArgs); + break; + } + } + + if (err) + { + aError = err; + } + + DEBUGSTRING(("completing request")); + if (!Message().IsNull()) + { + Message().Complete(aError); + } + DEBUGSTRING(("request completed")); + iMessageCompleted = ETrue; + } + + Destroy(); + } + + + // ---------------------------------------------------------------------------- +// CRsfwRfeRequest::Destroy +// ---------------------------------------------------------------------------- +// +void CRsfwRfeMessageRequest::Destroy() + { + if (iSession) + { + iSession->RemoveFromMessageRequestArray(this); + } + + CRsfwRfeRequest::Destroy(); + } + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfeoperation.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfeoperation.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,50 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Base class for operation encapsulation +* +*/ + + +#include + +#include "rsfwrfeoperation.h" + + +// ---------------------------------------------------------------------------- +// CRsfwRfeOperation::IsSync +// ---------------------------------------------------------------------------- +// +TBool CRsfwRfeOperation::IsSync() const + { + return iIsSync; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeOperation::Function +// ---------------------------------------------------------------------------- +// +TInt CRsfwRfeOperation::Function() + { + return iFunction; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeOperation::Set +// ---------------------------------------------------------------------------- +// +void CRsfwRfeOperation::Set(TInt aOpCode) + { + iFunction = aOpCode; + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrferequest.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrferequest.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,153 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Base class for request encapsulation. +* +*/ + + +#include +#include "rsfwrferequest.h" +#include "rsfwinterface.h" +#include "rsfwrfeoperation.h" +#include "rsfwrfesyncoperation.h" +#include "rsfwrfeasyncoperation.h" +#include "rsfwrfestatemachine.h" +#include "rsfwrequestallocator.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwfileengine.h" + +TParse dummyP; +RMessage2 dummyM; + + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::~CRsfwRfeRequest +// ---------------------------------------------------------------------------- +// +CRsfwRfeRequest::~CRsfwRfeRequest() + { + delete iInArgs; + delete iOutArgs; + if (iOperation) + { + if (Operation()->IsSync()) + { + delete (CRsfwRfeSyncOperation *)iOperation; + iOperation = NULL; + } + else + { + delete (CRsfwRfeAsyncOperation *)iOperation; + iOperation = NULL; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::Destroy +// ---------------------------------------------------------------------------- +// +void CRsfwRfeRequest::Destroy() + { + CRsfwVolume* volume = iVolume; + CRsfwVolumeTable* volumeTable = iVolumeTable; + + RsfwRequestAllocator::FreeRequest(this); + + if (volume && volume->iFileEngine) + { + // Signal the engine of operation completion + volume->iFileEngine->OperationCompleted(); + } + else + { + volumeTable->OperationCompleted(NULL); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::Dispatch +// ---------------------------------------------------------------------------- +// +void CRsfwRfeRequest::Dispatch() + { + if (Operation()->IsSync()) + { + TRAPD(leaveValue, + ((CRsfwRfeSyncOperation * )Operation())->DoRequestL(this)); + CompleteAndDestroy(leaveValue); + } + else + { + // run the operation state machine + // start from the initial state + ((CRsfwRfeAsyncOperation *)Operation())->Implementation()-> + ReEnterCurrentState(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::Src +// ---------------------------------------------------------------------------- +// +TParse& CRsfwRfeRequest::Src() + { + return(dummyP); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::Dest +// ---------------------------------------------------------------------------- +// +TParse& CRsfwRfeRequest::Dest() + { + return(dummyP); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::Operation +// ---------------------------------------------------------------------------- +// +CRsfwRfeOperation* CRsfwRfeRequest::Operation() + {return(iOperation);} + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::SetOperation +// ---------------------------------------------------------------------------- +// +void CRsfwRfeRequest::SetOperation(CRsfwRfeOperation* aCaller) + { + iOperation = aCaller; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::RequestType +// ---------------------------------------------------------------------------- +// +TRequestType CRsfwRfeRequest::RequestType() + { + return iRequestType; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeRequest::SetRequestType +// ---------------------------------------------------------------------------- +// +void CRsfwRfeRequest::SetRequestType(TRequestType aRequestType) + { + iRequestType = aRequestType; + } + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfeserver.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfeserver.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,498 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File Engine server +* +*/ + + + +// INCLUDE FILES +#include +#include +#include + +#include + +#include "rsfwvolumetable.h" +#include "rsfwcommon.h" +#include "rsfwinterface.h" +#include "rsfwrfesession.h" +#include "rsfwrfeserver.h" +#include "mdebug.h" +#include "ecom.h" +#include "rsfwmountstore.h" + +#include "rsfwconfig.h" + + +// ---------------------------------------------------------------------------------------- +// Server's policy here +// ---------------------------------------------------------------------------------------- + +//Total number of ranges +const TUint remoteFileEngineRangeCount = 3; + +//Definition of the ranges of IPC numbers +const TInt remoteFileEngineRanges[remoteFileEngineRangeCount] = + { + 0, // 0 & 1 ; ERfeRequest, EAsynchRequest + 2, // 2 ; The Control API starts from EMount + 12 // 12 ; The Access API starts from ERenameReplace + }; + +//Policy to implement for each of the above ranges +const TUint8 remoteFileEngineElementsIndex[remoteFileEngineRangeCount] = + { + CPolicyServer::EAlwaysPass, //applies to 0th range + 0, //applies to 1st range + 1 //applies to 2nd range + }; + +//Specific capability checks +const static CPolicyServer::TPolicyElement remoteFileEngineElements[] = + { + // action = -1 ===> failing calls happens via CustomFailureActionL + // File Server is always allowed based on its SID from that function + //policy "0" for the Control API; fail call if NetworkServices and ReadDeviceData not present + {_INIT_SECURITY_POLICY_C2(ECapabilityNetworkServices, ECapabilityReadDeviceData), -1}, + //policy "1"; for the Access API, fail call if Network Services and AllFiles not prosent + {_INIT_SECURITY_POLICY_C2(ECapabilityNetworkServices, ECapabilityAllFiles), -1} + }; + +//Package all the above together into a policy +const CPolicyServer::TPolicy remoteFileEnginePolicy = + { + CPolicyServer::EAlwaysPass, //specifies all connect attempts should pass + remoteFileEngineRangeCount, //number of ranges + remoteFileEngineRanges, //ranges array + remoteFileEngineElementsIndex, //elements<->ranges index + remoteFileEngineElements, //array of elements + }; + + +// DATA STRUCTURES +TRfeEnv* CRsfwRfeServer::iEnvp; + +// ============================ MEMBER FUNCTIONS ============================== + + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::CRsfwRfeServer +// ---------------------------------------------------------------------------- +// +inline CRsfwRfeServer::CRsfwRfeServer(TInt aPriority, TServerType aType) + :CPolicyServer(aPriority, remoteFileEnginePolicy, aType) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::NewL +// ---------------------------------------------------------------------------- +// + +CRsfwRfeServer* CRsfwRfeServer::NewL() + { + CRsfwRfeServer* self = CRsfwRfeServer::NewLC(); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::NewLC +// ---------------------------------------------------------------------------- +// + +CRsfwRfeServer* CRsfwRfeServer::NewLC() + { + CRsfwRfeServer* self = new (ELeave) CRsfwRfeServer(EPriorityNormal, + ESharableSessions); + CleanupStack::PushL(self); + self->ConstructL(); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::ConstructL +// ---------------------------------------------------------------------------- +// + +void CRsfwRfeServer::ConstructL() + { + StartL(KRemoteFEName); + DEBUGSTRING(("registered RFE name 0x%x", this)); + + // Prepare the environment + iEnvp = &iEnv; + iDelayedShutdownTimer = CPeriodic::NewL(CActive::EPriorityLow); + User::LeaveIfError(iEnvp->iFs.Connect()); + iEnvp->iRsfwConfig = CRsfwConfig::NewL(KCRUidRsfwCtrl); + + // Make cache root directory + PrepareCacheRootL(); + // Load configuration + // Create volume table + iVolumes = CRsfwVolumeTable::NewL(this, iEnvp->iRsfwConfig); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::ThreadFunction +// ---------------------------------------------------------------------------- +// +TInt CRsfwRfeServer::ThreadFunction(TAny* /*aNone*/) + { + CTrapCleanup* cleanupStack = CTrapCleanup::New(); + if (!cleanupStack) + { + PanicServer(ECreateTrapCleanup); + } + +// __UHEAP_MARK; + TRAPD(err, ThreadFunctionL()); +// __UHEAP_MARKENDC(0); + if (err != KErrNone) + { + PanicServer(ESrvCreateServer); + } + + delete cleanupStack; + cleanupStack = NULL; + + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::IncrementSessions +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::IncrementSessions() + { + StopDelayedShutdownTimer(); + iSessionCount++; + DEBUGSTRING(("+session count = %d", iSessionCount)); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::DecrementSessions +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::DecrementSessions() + { + iSessionCount--; + // this debug output crashes the server for some reason +// DEBUGSTRING(("-session count = %d", iSessionCount)); + // Note that the event causing server to shut down + // is not session count going to zero, as + // there are "permanent" session(s) from the File Server plugin. + // (they would be closed when remote drives are unmounted, which never happens) + // Instead, server shutdown is triggered by last connected volume + // going to disconnect state, or inactivity timeout expires and + // there are no open files. + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::AllEnginesIdling +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::AllEnginesIdling(TInt aTimeout) + { + if (!iShuttingDown) + { + DEBUGSTRING(("starting to shut down after %d seconds", aTimeout)); + if (aTimeout) + { + StartDelayedShutdownTimer(aTimeout); + } + else + { + ShutDown(); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::ServiceRequested +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::ServiceRequested() + { + StopDelayedShutdownTimer(); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::RunError +// ---------------------------------------------------------------------------- +// +TInt CRsfwRfeServer::RunError(TInt aError) + { + if (aError == KErrBadDescriptor) + { + // A bad descriptor error implies a badly programmed client, + // so panic it; + // otherwise report the error to the client + PanicClient(Message(), EBadDescriptor); + } + else + { + Message().Complete(aError); + } + + // The leave will result in an early return from CServer::RunL(), skipping + // the call to request another message. So do that now in order to keep the + // server running. + ReStart(); + + return KErrNone; // handled the error fully + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::CustomFailureActionL +// ---------------------------------------------------------------------------- +// +CPolicyServer::TCustomResult CRsfwRfeServer::CustomFailureActionL(const RMessage2& aMsg, + TInt /* aAction */, + const TSecurityInfo& /*aMissing */) + { + TCustomResult result = EFail; + TSecureId secId = aMsg.SecureId(); + if (secId = KFileServerSecureUid) + { + result = EPass; + } + return result; + } + + + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::PanicClient +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::PanicClient(const RMessage2& aMessage, TRfePanic aPanic) + { + aMessage.Panic(KRfeServer, aPanic); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::PanicServer +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::PanicServer(TRfePanic aPanic) + { + User::Panic(KRfeServer, aPanic); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::ThreadFunctionL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::ThreadFunctionL() + { + + // Construct active scheduler + CActiveScheduler* activeScheduler = new (ELeave) CActiveScheduler; + CleanupStack::PushL(activeScheduler); + + // Install active scheduler. + // We don't need to check whether an active scheduler is already installed + // as this is a new thread, so there won't be one + CActiveScheduler::Install(activeScheduler); + + // Change the name of the thread, so it is easier to recognize + User::RenameThread(KRfeMain); + // Construct our server + CRsfwRfeServer::NewLC(); // anonymous + + RSemaphore semaphore; + TInt err; + err = semaphore.OpenGlobal(KRfeSemaphoreName); + if (err == KErrNotFound) + { + err = semaphore.CreateGlobal(KRfeSemaphoreName, 0); + } + User::LeaveIfError(err); + + // Semaphore opened ok + semaphore.Signal(); + semaphore.Close(); + +#ifdef _DEBUG + { + TInt8* p = (TInt8*)User::Alloc(1); + DEBUGSTRING(("Test alloc addr=0x%x", p)); + delete p; + DEBUGSTRING(("Enter alloc count=%d", User::CountAllocCells())); + TInt b; + TInt a = User::Available(b); + DEBUGSTRING(("Enter alloc avail=%d, biggest=%d", a, b)); + } +#endif + + // Start handling requests + CActiveScheduler::Start(); +#ifdef _DEBUG + { + DEBUGSTRING(("Exit alloc count=%d", User::CountAllocCells())); + TInt b; + TInt a = User::Available(b); + DEBUGSTRING(("Exit alloc avail=%d, biggest=%d", a, b)); + } +#endif + CleanupStack::PopAndDestroy(2, activeScheduler); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::NewSessionL +// ---------------------------------------------------------------------------- +// +CSession2* CRsfwRfeServer::NewSessionL(const TVersion &aVersion, + const RMessage2&) const + { + // Check we're the right version + if (!User::QueryVersionSupported(TVersion(KRfeMajorVersionNumber, + KRfeMinorVersionNumber, + KRfeBuildVersionNumber), + aVersion)) + { + User::Leave(KErrNotSupported); + } + // Make new session + return CRsfwRfeSession::NewL(*const_cast (this)); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::PrepareCacheRootL +// Get the cache path and create the directory if it does not exist +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::PrepareCacheRootL() + { + TInt err; + err = iEnvp->iRsfwConfig->Get(RsfwConfigKeys::KCacheDirectoryPath, + iEnvp->iCacheRoot); + if (err == KErrNone) + { + TBuf driveString; + if ((iEnvp->iCacheRoot.Length() < 2) || (iEnvp->iCacheRoot[1] != ':')) + { + err = iEnvp->iRsfwConfig->Get(RsfwConfigKeys::KRsfwDefaultDrive, + driveString); + if (err != KErrNone) + { + driveString.Copy(KRSFWDefaultDrive); + } + } + if (driveString.Length() < 2) + { + driveString.Append(':'); + } + iEnvp->iCacheRoot.Insert(0, driveString); + } + else + { + HBufC* defaultcacheRoot = HBufC::NewL(KMaxPath); + TPtr defaultCache(defaultcacheRoot->Des()); + defaultCache.Append(KRSFWDefaultDrive); + defaultCache.Append(KCacheRootDefault); + iEnvp->iCacheRoot.Copy(defaultCache); + delete defaultcacheRoot; + } + RFs& fs = iEnvp->iFs; + TUint att; + TChar cacheDriveChar = iEnvp->iCacheRoot[0]; + User::LeaveIfError(fs.CharToDrive(cacheDriveChar, iEnvp->iCacheDrive)); + err = fs.Att(iEnvp->iCacheRoot, att); + if (err != KErrNone) + { + // There was no prior cache root + err = fs.MkDirAll(iEnvp->iCacheRoot); + DEBUGSTRING(("Cache root creation failed with err=%d", err)); + User::LeaveIfError(err); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::ShutDown +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::ShutDown() + { + DEBUGSTRING(("shutting down")); + iShuttingDown = ETrue; + CActiveScheduler::Stop(); + delete iVolumes; + iVolumes = NULL; + delete iEnvp->iRsfwConfig; + iEnvp->iRsfwConfig = NULL; + iEnvp->iFs.Close(); + delete iDelayedShutdownTimer; + iDelayedShutdownTimer = NULL; + // REComSession::FinalClose must be called when everything else + // related to ECom use has been deleted + REComSession::FinalClose(); + DEBUGSTRING(("shut down")); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::StartDelayedShutdownTimer +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::StartDelayedShutdownTimer(TInt aTimeout) + { + if (!iShuttingDown) + { + iDelayedShutdownTimer->Cancel(); + DEBUGSTRING(("shutting down in %d seconds", + aTimeout)); + TCallBack callBack(CRsfwRfeServer::DelayedShutdownTimerExpired, this); + iDelayedShutdownTimer->Start(aTimeout * 1000000, + aTimeout * 1000000, + callBack); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::StopDelayedShutdownTimer +// ---------------------------------------------------------------------------- +// +void CRsfwRfeServer::StopDelayedShutdownTimer() + { + if (iDelayedShutdownTimer) + { + iDelayedShutdownTimer->Cancel(); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeServer::DelayedShutdownTimerExpired +// ---------------------------------------------------------------------------- +// +TInt CRsfwRfeServer::DelayedShutdownTimerExpired(TAny* aArg) + { + CRsfwRfeServer* rfeServer = static_cast(aArg); + rfeServer->ShutDown(); + return 0; + } + +// ---------------------------------------------------------------------------- +// E32Main +// ---------------------------------------------------------------------------- +// +TInt E32Main() + { + return CRsfwRfeServer::ThreadFunction(NULL); + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfesession.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfesession.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,297 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File Engine session manager +* +*/ + + + +// INCLUDE FILES +#include +#include +#include +#include +#include + +#include "rsfwcommon.h" +#include "rsfwinterface.h" +#include "rsfwrfesession.h" +#include "rsfwremoteaccess.h" +#include "mdebug.h" +#include "rsfwrfeserver.h" +#include "rsfwrfemessagerequest.h" +#include "rsfwrequestallocator.h" +#include "rsfwrfeoperation.h" +#include "rsfwrfesyncoperation.h" +#include "rsfwrfeasyncoperation.h" + + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::NewL +// ---------------------------------------------------------------------------- +// +CRsfwRfeSession* CRsfwRfeSession::NewL(CRsfwRfeServer& aServer) + { + CRsfwRfeSession* self = CRsfwRfeSession::NewLC(aServer); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::NewLC +// ---------------------------------------------------------------------------- +// +CRsfwRfeSession* CRsfwRfeSession::NewLC(CRsfwRfeServer& aServer) + { + // the following debug print crashes easily with USER 24: + // DEBUGSTRING(("CRsfwRfeSession::NewLC")); + CRsfwRfeSession* self; + self = new (ELeave) CRsfwRfeSession(aServer); + CleanupStack::PushL(self); + self->ConstructL(); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::CRsfwRfeSession +// ---------------------------------------------------------------------------- +// +CRsfwRfeSession::CRsfwRfeSession(CRsfwRfeServer& aServer) : + CSession2(), + iRfeServer(aServer) + { + // Implementation not required + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::ConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSession::ConstructL() + { + iVolumes = iRfeServer.iVolumes; + iRfeServer.IncrementSessions(); + + for (int i = 0; i < KDefaultMessageSlots; i++ ) + { + iMessageRequests[i] = NULL; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::~CRsfwRfeSession +// ---------------------------------------------------------------------------- +// +CRsfwRfeSession::~CRsfwRfeSession() + { + // When the sessions are shared we don't know which + // volumes can be freed at session shutdown + iRfeServer.DecrementSessions(); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::DisconnectL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSession::Disconnect(const RMessage2& aMessage) + { + // in all messages pending completion for this session + // mark the session as NULL so that we do not try to complete them later + for (int i = 0 ; i SetSession(NULL); + } + + } + CSession2::Disconnect(aMessage); + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::ServiceL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSession::ServiceL(const RMessage2& aMessage) + { + DEBUGSTRING16(("CRsfwRfeSession::ServiceL(), function %d", aMessage.Function())); + + iRfeServer.ServiceRequested(); + + if(aMessage.Function() >= EMaxRfeOperations) + { + aMessage.Complete(KErrNotSupported); + return; + } + + CRsfwRfeMessageRequest* pR = NULL; + pR=RsfwRequestAllocator::GetMessageRequest(aMessage, this); + if (!pR) + { + aMessage.Complete(KErrNoMemory); + return; + } + + SetToMessageRequestArray(pR); + + // if volume was not found and this was a file system request + // (not a mounting request), we have completed now with + // KErrNotReady + if (pR->iMessageCompleted) + { + delete pR; + return; + } + + CRsfwRfeOperation* pO = NULL; + pO = GetOperation(pR, aMessage.Function()); + if(!pO) + { + delete pR; + aMessage.Complete(KErrNoMemory); + return; + } + + // Request will take ownership of the operation + pR->SetOperation(pO); + + pR->Dispatch(); + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::SetToMessageRequestArray +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSession::SetToMessageRequestArray(CRsfwRfeMessageRequest* aMessageRequest) + { + // set message request to the message request array + for (int i = 0; i < KDefaultMessageSlots; i++) + { + if (iMessageRequests[i] == NULL) + { + // completely unused slot + iMessageRequests[i] = aMessageRequest; + break; + } + } + + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::RemoveFromMessageRequestArray +// call by request prior to self-destruction +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSession::RemoveFromMessageRequestArray(CRsfwRfeMessageRequest* aMessageRequest) + { + // set message request to the message request array + for (int i = 0; i < KDefaultMessageSlots; i++) + { + if (iMessageRequests[i] == aMessageRequest) + { + iMessageRequests[i] = NULL; + } + } + + } + + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::Volume +// ---------------------------------------------------------------------------- +// +CRsfwVolumeTable* CRsfwRfeSession::Volume() + { + return iVolumes; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::Server +// ---------------------------------------------------------------------------- +// +CRsfwRfeServer* CRsfwRfeSession::Server() + { + return &iRfeServer; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::GetOperation +// Sets operations to be synchronous or asynhronous +// ---------------------------------------------------------------------------- +// +CRsfwRfeOperation* CRsfwRfeSession::GetOperation(CRsfwRfeRequest* aRequest, TInt aOpCode) + { + CRsfwRfeOperation* pO = NULL; + switch (aOpCode) + { + case EDismountByVolumeId: + case EDismountByDriveLetter: + case EGetMountList: + case EGetMountInfo: + case EFsRoot: + case EOkToWrite: + case ESetAttr: + case EFsIoctl: + case EDirRefresh: + case ECancelAll: + pO = RsfwRequestAllocator::GetSyncOperation(aRequest, aOpCode); + break; + + case EMount: + case EMountByDriveLetter: + case ESetMountConnectionState: + case ERenameReplace: + case EOpenByPath: + case EFetch: + case EFetchData: + case ELookUp: + case EGetAttr: + case EMkDir: + case ERemoveDir: + case ERemove: + case ECreateFile: + case EClose: + case EFlush: + pO = RsfwRequestAllocator::GetAsyncOperation(aRequest, aOpCode); + break; + + default: + __ASSERT_DEBUG(FALSE, User::Panic(KRfeServer, EUndefinedRequest)); + // if this happens even in release build + // pO will stay NULL and the request is completed with KErrNoMemory... + } + + return pO; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSession::PanicClient +// ---------------------------------------------------------------------------- +// +#ifdef NONSHARABLE_SESSION +void CRsfwRfeSession::PanicClient(TInt aPanic) const + { + // Note: this panics the client thread, not server + Panic(KRfeServer, aPanic); + } +#endif + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,329 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Base class for all operation state machines +* +*/ + + +#include "mdebug.h" +#include "rsfwrfestatemachine.h" +#include "rsfwinterface.h" +#include "rsfwfiletable.h" +#include "rsfwrferequest.h" +#include "rsfwfileengine.h" + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::BaseConstructL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::BaseConstructL() + { + DEBUGSTRING(("CRsfwRfeStateMachine::BaseConstructL")); + iCompleteAndDestroyState = + new (ELeave) CRsfwRfeStateMachine::TCompleteAndDestroyState(this); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::~CRsfwRfeStateMachine +// Note that normally when we come here iState = iCompleteAndDestroyState, +// only delete once +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::~CRsfwRfeStateMachine() + { + DEBUGSTRING(("CRsfwRfeStateMachine::~CRsfwRfeStateMachine")); + if (CurrentState() == CompleteAndDestroyState()) + { + delete iState; + } + else + { + delete iState; + delete iCompleteAndDestroyState; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::ErrorOnStateEntry +// Entering the current state failed, so loop in EnterState() will replace +// it by CompleteAndDestroy state as we return that state. +// Deleting the current state happens in EnterState() +// The state machine logic does not do that, as it allows us to eg resolve +// the problem by fixing the current state. +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwRfeStateMachine::ErrorOnStateEntry(TInt aError) + { + DEBUGSTRING(("CRsfwRfeStateMachine::ErrorOnStateEntry")); + iCompleteAndDestroyState->SetErrorCode(aError); + return iCompleteAndDestroyState; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::ChangeState +// Enters aNextState, and makes it our current state. +// Deletes the previous state +// (assumes we never go backwards in the state machine) +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::ChangeState(CRsfwRfeStateMachine::TState* aNextState) + { + DEBUGSTRING(("CRsfwRfeStateMachine::ChangeState")); + if (iState && (iState != aNextState) ) + { + delete iState; + iState = NULL; + } + EnterState(aNextState); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::EnterState +// Enters aNextState, and makes it our current state. +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::EnterState(CRsfwRfeStateMachine::TState* aNextState) + { + DEBUGSTRING(("CRsfwRfeStateMachine::EnterState")); + TInt err; + while (aNextState) + {// State change required. + iState = aNextState; + TRAP(err, iState->EnterL()); + if (err) + { + aNextState = ErrorOnStateEntry(err); + delete iState; + iState = NULL; + } + else + { + aNextState = NULL; + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::SetNextState +// Sets the current state, but doesn't actually enter it. +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::SetNextState(TState* aNextState) + { + DEBUGSTRING(("CRsfwRfeStateMachine::SetNextState")); + iState = aNextState; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::ReEnterCurrentState +// Re-enters the state we're currently in. +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::ReEnterCurrentState() + { + DEBUGSTRING(("CRsfwRfeStateMachine::ReEnterCurrentState")); + EnterState(iState); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::SetRequest +// Sets the backpointer to our request +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::SetRequest(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("CRsfwRfeStateMachine::SetRequest")); + iRFeRequest = aRequest; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::Request +// ---------------------------------------------------------------------------- +// +CRsfwRfeRequest* CRsfwRfeStateMachine::Request() + { + DEBUGSTRING(("CRsfwRfeStateMachine::Request")); + return iRFeRequest; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::SetVolumes +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::SetVolumes(CRsfwVolumeTable* aImplementor) + { + DEBUGSTRING(("CRsfwRfeStateMachine::SetVolumes")); + iImplementor = aImplementor; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::SetFileEngine +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::SetFileEngine(CRsfwFileEngine* aFileEngine) + { + DEBUGSTRING(("CRsfwRfeStateMachine::SetFileEngine")); + iFileEngine = aFileEngine; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::SetArguments +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::SetArguments(TRfeInArgs* aInArgs, TRfeOutArgs* aOutArgs) + { + DEBUGSTRING(("CRsfwRfeStateMachine::SetArguments")); + iInArgs = aInArgs; + iOutArgs = aOutArgs; + + // Set the target node for this operation. + if (iInArgs && iFileEngine) + { + TFid* fidp = &(iInArgs->iFid); + iFep = iFileEngine->iFileTable->Lookup(*fidp); + } + else + { + iFep = NULL; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::Volumes +// ---------------------------------------------------------------------------- +// +CRsfwVolumeTable* CRsfwRfeStateMachine::Volumes() + { + DEBUGSTRING(("CRsfwRfeStateMachine::Volumes")); + return iImplementor; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::FileEngine +// ---------------------------------------------------------------------------- +// +CRsfwFileEngine* CRsfwRfeStateMachine::FileEngine() + { + return iFileEngine; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::Node +// ---------------------------------------------------------------------------- +// +CRsfwFileEntry* CRsfwRfeStateMachine::Node() + { + return iFep; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::ErrorOnStateExit +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwRfeStateMachine::ErrorOnStateExit(TInt aError) + { + DEBUGSTRING(("CRsfwRfeStateMachine::ErrorOnStateExit %d", aError)); + iCompleteAndDestroyState->SetErrorCode(aError); + return iCompleteAndDestroyState; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::HandleRemoteAccessResponse +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::HandleRemoteAccessResponse(TUint /*aId*/, TInt aStatus) + { + DEBUGSTRING(("CRsfwRfeStateMachine::HandleRemoteAccessResponse")); + TState* nextState = NULL; + TRAPD(err, nextState = aStatus ? iState->ErrorL(aStatus) + : iState->CompleteL()); + if (err) + { + nextState = ErrorOnStateExit(err); + } + ChangeState(nextState); + } + +// empty defaults for CRsfwRfeStateMachine::TState functions CompleteL(), ErrorL() and Cancel() + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::TState::CompleteL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwRfeStateMachine::TState::CompleteL() + { + DEBUGSTRING(("CRsfwRfeStateMachine::TState::CompleteL")); + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::TState::ErrorL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwRfeStateMachine::TState::ErrorL(TInt /*aCode*/) + { + DEBUGSTRING(("CRsfwRfeStateMachine::TState::ErrorL")); + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::TState::Cancel +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::TState::Cancel() + { + DEBUGSTRING(("CRsfwRfeStateMachine::TState::Cancel")); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::TCompleteAndDestroyState::TCompleteAndDestroyState +// Completes the remote request with error code aErrCode and +// destroys it (CRsfwRfeRequest) +// as well as the classes pointed to by it, that it the instances of +// CRsfwRfeAsyncOperation, CRsfwRfeStateMachine and CRsfwRfeStateMachine::TState classes. +// +// In RemoteFS requests error code is 0, +// as the error is returned in iOutArgs->iResult +// For RemoteEngine API requests aErrCode should have the error code +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine:: +TCompleteAndDestroyState::TCompleteAndDestroyState(CRsfwRfeStateMachine* aParent, + TInt aErrCode) + : iOperation(aParent), iErrCode(aErrCode) + { + DEBUGSTRING(("TCompleteAndDestroyState::TCompleteAndDestroyState")); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::TCompleteAndDestroyState::EnterL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::TCompleteAndDestroyState::EnterL() + { + DEBUGSTRING(("CRsfwRfeStateMachine::TCompleteAndDestroyState::EnterL")); + iOperation->Request()->CompleteAndDestroy(iErrCode); + // nothing can be called here as we have been deallocated!!! + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeStateMachine::TCompleteAndDestroyState::SetErrorCode +// ---------------------------------------------------------------------------- +// +void CRsfwRfeStateMachine::TCompleteAndDestroyState::SetErrorCode(TInt aErrorCode) + { + DEBUGSTRING(("CRsfwRfeStateMachine::TCompleteAndDestroyState::SetErrorCode")); + iErrCode = aErrorCode; + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwrfesyncoperation.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwrfesyncoperation.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,99 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Encapsulates synchronous operation +* +*/ + + +#include "rsfwrfesyncoperation.h" +#include "rsfwsyncoperations.h" +#include "rsfwvolume.h" +#include "rsfwcommon.h" +#include "rsfwrfeserver.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// CRsfwRfeSyncOperation::DoRequestL +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSyncOperation::DoRequestL(CRsfwRfeRequest* aRequest) + { + __ASSERT_ALWAYS(iDoRequestL, User::Panic(KRfeServer, ENullRequestHandler)); + (*iDoRequestL)(aRequest); + } + +// ---------------------------------------------------------------------------- +// CRsfwRfeSyncOperation::Set +// ---------------------------------------------------------------------------- +// +void CRsfwRfeSyncOperation::Set(CRsfwRfeRequest* aRequest, TInt aOpCode) + { + if (aRequest->iVolume) + { + DEBUGSTRING(("<<< Dispatch enter (volume=%d)", + aRequest->iVolume->iMountInfo.iMountStatus.iVolumeId)); + } + else + { + DEBUGSTRING(("<<< Dispatch enter")); + } + + switch (aOpCode) + { + case EDismountByVolumeId: + DEBUGSTRING(("DISMOUNTBYVOLUMEID (operation %d)", aOpCode)); + iDoRequestL = &TRFeDismountVolumeId::DoRequestL; + break; + + case EDismountByDriveLetter: + DEBUGSTRING(("DISMOUNTBYDRIVELETTER (operation %d)", aOpCode)); + iDoRequestL = &TRFeDismountByDriveLetter::DoRequestL; + break; + + case EGetMountList: + DEBUGSTRING(("GETMOUNTLIST (operation %d)", aOpCode)); + iDoRequestL = &TRFeGetMountList::DoRequestL; + break; + + case EGetMountInfo: + DEBUGSTRING(("GETMOUNTINFO (operation %d)", aOpCode)); + iDoRequestL = &TRFeGetMountInfo::DoRequestL; + break; + + case EFsRoot: + case ESetAttr: + case EFsIoctl: + DEBUGSTRING(("ROOT (operation %d)", aOpCode)); + iDoRequestL = &TRFeSynCRsfwRfeRequest::DoRequestL; + break; + + case EOkToWrite: + DEBUGSTRING(("WRITEDATA (operation %d)", aOpCode)); + iDoRequestL = &TRFeWriteData::DoRequestL; + break; + case EDirRefresh: + DEBUGSTRING(("REFRESHDIR (operation %d)", aOpCode)); + iDoRequestL = &TRFeDirectoryRefresh::DoRequestL; + break; + case ECancelAll: + DEBUGSTRING(("CANCEL TRANSFER (operation %d)", aOpCode)); + iDoRequestL = &TRFeCancelAll::DoRequestL; + break; + } + + iIsSync = ETrue; + CRsfwRfeOperation::Set(aOpCode); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwsession.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwsession.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,946 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Client side of Remote Storage FW API access functions. + * +*/ + + +// INCLUDE FILES +#include "rsfwsession.h" +#include "rsfwinterface.h" + +#ifdef __WINS__ +#include +#endif + +// CONSTANTS + +// Number of message slots to reserve for this client server session. +// Since we only communicate synchronously here, we never have any +// outstanding asynchronous requests. +const TUint KDefaultMessageSlots = 4; + +#ifdef __WINS__ +const TUint KServerMinHeapSize = 0x1000; // 4K +const TUint KServerMaxHeapSize = 0x100000; // 64K +#endif + +// ============================ MEMBER FUNCTIONS ============================== + +// ---------------------------------------------------------------------------- +// RRsfwSession::RRsfwSession +// C++ default constructor can NOT contain any code, that +// might leave. +// ---------------------------------------------------------------------------- +// +EXPORT_C RRsfwSession::RRsfwSession() : RSessionBase() + { + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::Connect +// Connects to the framework by starting the server if neccessary and creating +// a session. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::Connect() + { + const TInt KTryCount = 3; + + TInt err; + TBool retry; + TInt i = KTryCount; + do + { + err = StartServer(KRfeServerName); + if (err == KErrNone) + { + err = CreateSession(KRfeServerName, + Version(), + KDefaultMessageSlots); + } + retry = ((err == KErrNotFound) || (err == KErrServerTerminated)); + } while (retry && (++i <= KTryCount)); + + return err; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::Close +// ---------------------------------------------------------------------------- +// +EXPORT_C void RRsfwSession::Close() + { + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::Version +// Returns the version of Remote File Engine +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TVersion RRsfwSession::Version() const + { + return(TVersion(KRfeMajorVersionNumber, + KRfeMinorVersionNumber, + KRfeBuildVersionNumber)); + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::MoveFids +// Sends the rename operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::MoveFids( + TFid aSourceFid, + const TDesC& aSourceName, + TFid aDestFid, + const TDesC& aDestName, + TBool aOverWrite) + { + + TRfeRenameInArgs* renameArgs = new TRfeRenameInArgs(); + if (!renameArgs) + { + return KErrNoMemory; + } + + // TRfeRenameInArgs* writePtr = static_cast(iWritePtr); + renameArgs->iOpCode = ERenameReplace; + + renameArgs->iFid = aSourceFid; + renameArgs->iSrcName.Copy(aSourceName); + renameArgs->iDstFid = aDestFid; + renameArgs->iDstName.Copy(aDestName); + renameArgs->iOverWrite = aOverWrite; + + TPckg pckgInArgs(*renameArgs); + + TInt result = SendRequest(ERenameReplace, aSourceFid.iVolumeId, + TIpcArgs(&pckgInArgs)); + delete renameArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::SetEntry +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::SetEntry( + const TFid aFid, + const TTime& aTime, + TUint aSetAttMask, + TUint aClearAttMask) + { + TRfeSetAttrInArgs* setEntryArgs = new TRfeSetAttrInArgs(); + if (!setEntryArgs) + { + return KErrNoMemory; + } + + setEntryArgs->iOpCode = ESetAttr; + setEntryArgs->iFid = aFid; + + // default: no change + setEntryArgs->iAttr.iAtt = 0; + setEntryArgs->iMask.iAtt = 0; + + if (aSetAttMask & KEntryAttReadOnly) + { + // Set read-only + setEntryArgs->iAttr.iAtt |= KEntryAttReadOnly; + setEntryArgs->iMask.iAtt |= KEntryAttReadOnly; + } + if (aClearAttMask & KEntryAttReadOnly) + { + // Reset read-only + setEntryArgs->iMask.iAtt |= KEntryAttReadOnly; + } + + // Setting time + setEntryArgs->iAttr.iModified = aTime; + + // Let's see - we will not want to do anything unless + // the attributes convey something significant. + TInt result = KErrNone; + if (setEntryArgs->iMask.iAtt) + { + TPckg pckgInArgs(*setEntryArgs); + result = SendRequest(ESetAttr, aFid.iVolumeId, TIpcArgs(&pckgInArgs)); + } + delete setEntryArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::FlushCache +// Flushes the directory cache of a file or directory by putting the parameters +// into the shared memory chunk and sending the request. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::FlushCache( + TFid& aFid) + { + TRfeIoctlInArgs* ioctlArgs = new TRfeIoctlInArgs(); + if (!ioctlArgs) + { + return KErrNoMemory; + } + + ioctlArgs->iOpCode = EFsIoctl; + ioctlArgs->iFid = aFid; + ioctlArgs->iCmd = ERemoteFsIoctlRefresh; + ioctlArgs->iLen = 0; + + TPckg pckgInArgs(*ioctlArgs); + TInt result = SendRequest(EFsIoctl, aFid.iVolumeId, TIpcArgs(&pckgInArgs)); + delete ioctlArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::SetHighCachePriority +// Sets higher cache priority for a file by putting the parameters +// into the shared memory chunk and sending the request. +// This feature is not supported currently. +// Perhaps will be implemented in near future. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::SetHighCachePriority(TFid& /* aFid */) + { + return KErrNotSupported; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::GetAttributes +// Sends GetAttr operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::GetAttributes( + TFid aFileFid, + TEntry& aAttributes) + { + TRfeGetAttrInArgs* getattrArgs = new TRfeGetAttrInArgs(); + if (!getattrArgs) + { + return KErrNoMemory; + } + TRfeGetAttrOutArgs* getattrOutArgs = new TRfeGetAttrOutArgs(); + if (!getattrOutArgs) + { + return KErrNoMemory; + } + + getattrArgs->iOpCode = EGetAttr; + getattrArgs->iFid = aFileFid; + + TPckg pckgInArgs(*getattrArgs); + TPckg pckgOutArgs(*getattrOutArgs); + + TInt result = SendRequest(EGetAttr, aFileFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + // Note that aAttributes.iType (the entry UID) + // should only be set for a file whose + // size is greater than or equal to sizeof(TCheckedUid). + aAttributes.iAtt = getattrOutArgs->iAttr.iAtt; + aAttributes.iSize = getattrOutArgs->iAttr.iSize; + aAttributes.iModified = getattrOutArgs->iAttr.iModified; + aAttributes.iType = KNullUid; + } + + delete getattrArgs; + delete getattrOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::OpenByPathL +// Sends OpenByPath operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// Remote File Engine returns the path of the cache container file for this fid +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::OpenByPath( + TFid aFid, + TDes& aContainerPath, + TDirEntAttr* aAttributes, + TBool aTrueOpen) + { + TRfeOpenByPathInArgs* openbypathArgs = new TRfeOpenByPathInArgs(); + if (!openbypathArgs) + { + return KErrNoMemory; + } + TRfeOpenByPathOutArgs* openbypathOutArgs = new TRfeOpenByPathOutArgs(); + if (!openbypathOutArgs) + { + return KErrNoMemory; + } + + openbypathArgs->iOpCode = EOpenByPath; + openbypathArgs->iFid = aFid; + + // Flag field is used to pass attributes, + // which indicate which lock should be obtained for the file + if (aAttributes) + { + openbypathArgs->iFlags = aAttributes->iAtt; + } + else + { + openbypathArgs->iFlags = 0; + } + + // tells whether the file is really opened or do we need it because + // ReadSection() was called... (in the latter case Symbian File Server + // does not open the file...) */ + openbypathArgs->iTrueOpen = aTrueOpen; + + TPckg pckgInArgs(*openbypathArgs); + TPckg pckgOutArgs(*openbypathOutArgs); + + TInt result = SendRequest(EOpenByPath, aFid.iVolumeId, TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + if (aAttributes) + { + *aAttributes = openbypathOutArgs->iAttr; + } + // Processing the response + _LIT(KPathRedundancy, "\\.\\"); + TInt j = openbypathOutArgs->iPath.Find(KPathRedundancy); + if (j != KErrNotFound) + { + TInt i = openbypathOutArgs->iPath.Length(); + TInt k; + for (k = j; k + 2 < i; k++) + { + openbypathOutArgs->iPath[k] = + openbypathOutArgs->iPath[k + 2]; + } + openbypathOutArgs->iPath.SetLength(i - 2); + } + + const TInt maximumLength = aContainerPath.MaxLength(); + if (maximumLength >= openbypathOutArgs->iPath.Length()) + { + aContainerPath.Copy(openbypathOutArgs->iPath); + } + else + { + aContainerPath.Copy( + openbypathOutArgs->iPath.Left(maximumLength)); + } + } + delete openbypathArgs; + delete openbypathOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::RfeInit +// Gets the fid of the root of the mount for Remote File Engine by putting the +// parameters into the shared memory chunk, sending the request and reading +// the result. +// This allows us to get other fids by lookup(). +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::RfeInit(TFid& aRootFid) + { + TRfeRootInArgs* rootArgs = new TRfeRootInArgs(); + if (!rootArgs) + { + return KErrNoMemory; + } + + TRfeRootOutArgs* rootOutArgs = new TRfeRootOutArgs(); + if (!rootOutArgs) + { + return KErrNoMemory; + } + + rootArgs->iOpCode = EFsRoot; + rootArgs->iFid.iVolumeId = 0; + rootArgs->iFid.iNodeId = 0; + + TPckg pckgInArgs(*rootArgs); + TPckg pckgOutArgs(*rootOutArgs); + + TInt result = SendRequest(EFsRoot, aRootFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + aRootFid = rootOutArgs->iFid; + } + + delete rootArgs; + delete rootOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::MakeDirectoryL +// Sends MkDir operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::MakeDirectory( + TFid aParentFid, + const TDesC& aDirName) + { + TRfeMkdirInArgs* mkdirArgs = new TRfeMkdirInArgs(); + if (!mkdirArgs) + { + return KErrNoMemory; + } + + mkdirArgs->iOpCode = EMkDir; + mkdirArgs->iFid = aParentFid; + + mkdirArgs->iEntry.iName.Copy(aDirName); + mkdirArgs->iEntry.iAttr.iAtt = 0; // not read only + + TPckg pckgInArgs(*mkdirArgs); + TInt result = SendRequest(EMkDir, + aParentFid.iVolumeId, + TIpcArgs(&pckgInArgs)); + delete mkdirArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::RemoveDirectoryL +// Sends Remove Directory operation to Remote File Engine by putting the +// parameters into the shared memory chunk, sending the request and reading +// the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::RemoveDirectory( + TFid aParentFid, + const TDesC& aDirName) + { + TRfeRmdirInArgs* rmdirArgs = new TRfeRmdirInArgs(); + if (!rmdirArgs) + { + return KErrNoMemory; + } + + rmdirArgs->iOpCode = ERemoveDir; + rmdirArgs->iFid = aParentFid; + + rmdirArgs->iName.Copy(aDirName); + + TPckg pckgInArgs(*rmdirArgs); + TInt result = SendRequest(ERemoveDir, + aParentFid.iVolumeId, + TIpcArgs(&pckgInArgs)); + + delete rmdirArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::CreateFileL +// Sends Create File operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::CreateFile( + TFid aParentFid, + const TDesC& aFileName, + TUint aMode, + TUint aExcl, + TFid& aNewFid) + { + TRfeCreateInArgs* createArgs = new TRfeCreateInArgs(); + if (!createArgs) + { + return KErrNoMemory; + } + + TRfeCreateOutArgs* createOutArgs = new TRfeCreateOutArgs(); + if (!createOutArgs) + { + return KErrNoMemory; + } + + createArgs->iOpCode = ECreateFile; + createArgs->iFid = aParentFid; + + createArgs->iEntry.iName.Copy(aFileName); + + if (aMode & EFileWrite) + { + createArgs->iEntry.iAttr.iAtt = 0; + } + else + { + createArgs->iEntry.iAttr.iAtt = KEntryAttReadOnly; + } + createArgs->iEntry.iAttr.iSize = 0; + createArgs->iEntry.iAttr.iModified = 0; + + createArgs->iExcl = aExcl; + + TPckg pckgInArgs(*createArgs); + TPckg pckgOutArgs(*createOutArgs); + TInt result = SendRequest(ECreateFile, + aParentFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + aNewFid = createOutArgs->iFid; + } + + delete createArgs; + delete createOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::RemoveFileL +// Sends Remove File operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::RemoveFile( + TFid aParentFid, + const TDesC& aFileName) + { + TRfeRemoveInArgs* removeArgs = new TRfeRemoveInArgs(); + if (!removeArgs) + { + return KErrNoMemory; + } + + removeArgs->iOpCode = ERemove; + removeArgs->iFid = aParentFid; + + removeArgs->iName.Copy(aFileName); + + TPckg pckgInArgs(*removeArgs); + TInt result = SendRequest(ERemove, + aParentFid.iVolumeId, + TIpcArgs(&pckgInArgs)); + + delete removeArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::LookupL +// Sends Lookup operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::Lookup( + TFid aParentFid, + const TDesC& aName, + TUint aNodeType, + TFid& aFid) + { + TBool directory = EFalse; + + TPtrC peek; + peek.Set(aName.Right(1)); // the last char + if ((peek.Length() > 0) && (peek[0] == '\\')) + { + directory = ETrue; + } + + TRfeLookupInArgs* lookupArgs = new TRfeLookupInArgs(); + if (!lookupArgs) + { + return KErrNoMemory; + } + + TRfeLookupOutArgs* lookupOutArgs = new TRfeLookupOutArgs(); + if (!lookupOutArgs) + { + return KErrNoMemory; + } + + lookupArgs->iOpCode = ELookUp; + lookupArgs->iFid = aParentFid; + lookupArgs->iNodeType = aNodeType; + + lookupArgs->iName.Copy(aName); + + if (directory) + { + // We don't want to copy the trailing backslash + TInt len = lookupArgs->iName.Length(); + lookupArgs->iName.SetLength(len - 1); + } + + TPckg pckgInArgs(*lookupArgs); + TPckg pckgOutArgs(*lookupOutArgs); + TInt result = SendRequest(ELookUp, + aParentFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + aFid = lookupOutArgs->iFid; + } + + if (result == KErrNotFound) + { + if (directory) + { + return KErrPathNotFound; + } + else + { + return KErrNotFound; + } + } + + delete lookupArgs; + delete lookupOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::CloseFile +// Sends Close operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C void RRsfwSession::CloseFile( + const TFid aFid, + const TUint aFlags) + { + // close cannot be called asynchronously in the file server API + // and cannot return an error code + // so we make a blind request to the server + SendReceive(EClose, TIpcArgs(aFid.iVolumeId, aFid.iNodeId, aFlags)); + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::FlushL +// This "abuses" close operation code. +// The file is not really closed by the File Server, +// and Remote File Engine only writes the (changed) file back to the +// remote server, but does not release a possible write lock. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::Flush( + const TFid aFid, + TInt aFirstByte, + TInt aDataLength, + TInt aTotalSize) + { + TRfeFlushInArgs* flushArgs = new TRfeFlushInArgs(); + if (!flushArgs) + { + return KErrNoMemory; + } + + flushArgs->iOpCode = EFlush; + flushArgs->iFid = aFid; + flushArgs->iFirstByte = aFirstByte; + flushArgs->iDataLength = aDataLength; + flushArgs->iTotalSize = aTotalSize; + + TPckg pckgInArgs(*flushArgs); + + TInt result = SendRequest(EFlush, aFid.iVolumeId, + TIpcArgs(&pckgInArgs)); + + delete flushArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::Fetch +// Sends Fetch operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// Remote File Engine will write data into cache file, which path it knows by +// the fid. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::Fetch( + TFid aFileFid, + TInt aFirstByte, + TInt aLastByte, + TInt& aCachedBytes) + { + TRfeFetchInArgs* fetchArgs = new TRfeFetchInArgs(); + if (!fetchArgs) + { + return KErrNoMemory; + } + TRfeFetchOutArgs* fetchOutArgs = new TRfeFetchOutArgs(); + if (!fetchOutArgs) + { + return KErrNoMemory; + } + + fetchArgs->iOpCode = EFetch; + fetchArgs->iFid = aFileFid; + fetchArgs->iFirstByte = aFirstByte; + fetchArgs->iLastByte = aLastByte; + + TPckg pckgInArgs(*fetchArgs); + TPckg pckgOutArgs(*fetchOutArgs); + TInt result = SendRequest(EFetch, aFileFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + aCachedBytes = fetchOutArgs->iLastByte; + } + + delete fetchArgs; + delete fetchOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::FetchData +// Sends Fetch operation to Remote File Engine by putting the parameters +// into the shared memory chunk, sending the request and reading the result. +// Remote File Engine will write data into a temporary cache file, +// valid only for the duration of this request. +// Note that in this case Remote File Engine will read exactly the requested +// amount, so aLastByte is not reset. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::FetchData( + TFid aFileFid, + TInt aFirstByte, + TInt aLastByte, + TDes& aTempFileName, + TBool& aUseTempPath) + { + TRfeFetchDataInArgs* fetchDataArgs = new TRfeFetchDataInArgs(); + if (!fetchDataArgs) + { + return KErrNoMemory; + } + + TRfeFetchDataOutArgs* fetchDataOutArgs = new TRfeFetchDataOutArgs(); + if (!fetchDataOutArgs) + { + return KErrNoMemory; + } + + fetchDataArgs->iOpCode = EFetchData; + fetchDataArgs->iFid = aFileFid; + fetchDataArgs->iFirstByte = aFirstByte; + fetchDataArgs->iLastByte = aLastByte; + + TPckg pckgInArgs(*fetchDataArgs); + TPckg pckgOutArgs(*fetchDataOutArgs); + TInt result = SendRequest(EFetchData, aFileFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + // Processing the response + _LIT(KPathRedundancy, "\\.\\"); + TInt j = fetchDataOutArgs->iTempPath.Find(KPathRedundancy); + if (j != KErrNotFound) + { + TInt i = fetchDataOutArgs->iTempPath.Length(); + TInt k; + for (k = j; k + 2 < i; k++) + { + fetchDataOutArgs->iTempPath[k] = + fetchDataOutArgs->iTempPath[k + 2]; + } + fetchDataOutArgs->iTempPath.SetLength(i - 2); + } + + const TInt maximumLength = aTempFileName.MaxLength(); + if (maximumLength >= fetchDataOutArgs->iTempPath.Length()) + { + aTempFileName.Copy(fetchDataOutArgs->iTempPath); + } + else + { + aTempFileName.Copy( + fetchDataOutArgs->iTempPath.Left(maximumLength)); + } + aUseTempPath = fetchDataOutArgs->iUseTempPath; + } + delete fetchDataArgs; + delete fetchDataOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::OkToWriteL +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +EXPORT_C TInt RRsfwSession::OkToWrite( + TFid aFid, + TUint aBytes, + TBool& aOkToWrite) + { + TRfeWriteDataInArgs* writedataArgs = new TRfeWriteDataInArgs(); + if (!writedataArgs) + { + return KErrNoMemory; + } + + TRfeWriteDataOutArgs* writedataOutArgs = new TRfeWriteDataOutArgs(); + if (!writedataOutArgs) + { + return KErrNoMemory; + } + + writedataArgs->iOpCode = EOkToWrite; + writedataArgs->iFid = aFid; + writedataArgs->iBytes = aBytes; + + TPckg pckgInArgs(*writedataArgs); + TPckg pckgOutArgs(*writedataOutArgs); + TInt result = SendRequest(EOkToWrite, aFid.iVolumeId, + TIpcArgs(&pckgInArgs, &pckgOutArgs)); + + if (result == KErrNone) + { + aOkToWrite = writedataOutArgs->iOkToWrite; + } + + delete writedataArgs; + delete writedataOutArgs; + return result; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::StartServer +// Starts the Remote File Engine if it is not running, uses semaphore to +// synchronize startup. +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +TInt RRsfwSession::StartServer(const TDesC& aServerName) + { + TFindServer findRfe(aServerName); + TFullName name; + + TInt result = findRfe.Next(name); + if (result == KErrNone) + { + // Server already running + return KErrNone; + } + + RSemaphore semaphore; + result = semaphore.CreateGlobal(KRfeSemaphoreName, 0); + if (result != KErrNone) + { + return result; + } + + result = CreateServerProcess(aServerName); + if (result != KErrNone) + { + semaphore.Close(); + return result; + } + semaphore.Wait(); + semaphore.Close(); + + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::CreateServerProcess +// Starts the Remote File Engine using name to find the binary +// (other items were commented in a header). +// ---------------------------------------------------------------------------- +// +TInt RRsfwSession::CreateServerProcess(const TDesC& aServerName) + { + // Just load anything that matches with the name + const TUidType serverUid(KNullUid, KNullUid, KNullUid); + + RProcess server; + + _LIT(KStartCommand, ""); + TInt result = server.Create(aServerName, KStartCommand, serverUid); + if (result != KErrNone) + { + return result; + } + server.Resume(); + server.Close(); + + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// RRsfwSession::SendRequest +// ---------------------------------------------------------------------------- +// +TInt RRsfwSession::SendRequest(TInt aOpCode, TInt aDrive, TIpcArgs aArgs) + { + TInt result = SendReceive(aOpCode, aArgs); + if (result == KErrServerTerminated) + { + // try to restart the server + result = Connect(); + if (result == KErrNone) + { + result = SendReceive(aOpCode, aArgs); + } + } + + // Disable following codes will fix auto connection of rsfw + /* + if (result == KErrNotReady) + { + // try to restore the mount + result = SendReceive(EMountByDriveLetter, TIpcArgs(aDrive)); + if (result == KErrNone) + { + result = SendReceive(aOpCode, aArgs); + } + } + */ + + return result; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwsyncoperations.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwsyncoperations.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,180 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Encapsulated all sync operations +* +*/ + + +#include "rsfwsyncoperations.h" +#include "rsfwrfemessagerequest.h" +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwfileengine.h" +#include "rsfwfiletable.h" +#include "rsfwfileentry.h" +#include "rsfwrfesession.h" +#include "rsfwinterface.h" +#include "rsfwcontrol.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// TRFeSynCRsfwRfeRequest::DoRequestL +// wrapper for all sync requests +// ---------------------------------------------------------------------------- +// +void TRFeSynCRsfwRfeRequest::DoRequestL(CRsfwRfeRequest* aRequest) + { + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + request->Session()->Volume()->DispatchL(request->iInArgs, + request->iOutArgs); + } + +// ---------------------------------------------------------------------------- +// TRFeDismountVolumeId::DoRequestL +// dismount a previously mounted volume by volume ID +// ---------------------------------------------------------------------------- +// +void TRFeDismountVolumeId::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeDismountVolumeId::DoRequestL")); + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + TInt volumeId = reinterpret_cast(request->Message().Ptr0()); + DEBUGSTRING(("EDismount: volume %d", volumeId)); + request->Session()->Volume()->DismountByVolumeIdL(volumeId, ETrue); + // This is called from the fileserver main thread. + // Therefore, we should return quickly. + } + +// ---------------------------------------------------------------------------- +// TRFeDismountByDriveLetter::DoRequestL +// dismount a previously mounted volume by drive letter +// ---------------------------------------------------------------------------- +// +void TRFeDismountByDriveLetter::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeDismountByDriveLetter::DoRequestL")); + // Dismount a volume by drive letter + // synchronous request + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + TChar driveLetter = reinterpret_cast(request->Message().Ptr0()); + DEBUGSTRING(("EDismountByDriveLetter: '%c'", TUint(driveLetter))); + request->Session()->Volume()->DismountByDriveLetterL(driveLetter, ETrue); + } + + +// ---------------------------------------------------------------------------- +// TRFeGetMountList::DoRequestL +// get a list of currently active mounts +// ---------------------------------------------------------------------------- +// +void TRFeGetMountList::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeGetMountList::DoRequestL")); + // synchronous request + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + TDriveList mountList; + request->Session()->Volume()->GetMountList(mountList); + TPckg p(mountList); + request->Message().WriteL(0, p); + DEBUGSTRING8(("EGetMountList: '%S'", &mountList)); + } + + +// ---------------------------------------------------------------------------- +// TRFeGetMountInfo::DoRequestL +// get information about a specific mount +// ---------------------------------------------------------------------------- +// +void TRFeGetMountInfo::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeGetMountInfo::DoRequestL")); + // synchronous request + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + TRsfwMountInfo* mountInfo = new (ELeave) TRsfwMountInfo; + CleanupStack::PushL(mountInfo); + mountInfo->iMountConfig.iDriveLetter = + reinterpret_cast(request->Message().Ptr0()); + TInt err = request->Session()->Volume()->GetMountInfo(*mountInfo); + DEBUGSTRING(("EGetMountInfo for '%c' (err=%d)", + TUint(mountInfo->iMountConfig.iDriveLetter), + err)); + if (err != KErrNone) + { + mountInfo->iMountConfig.iUri.Zero(); + } + TPckg mountInfoPackage(*mountInfo); + request->Message().WriteL(1, mountInfoPackage); + CleanupStack::PopAndDestroy(mountInfo); + } + + +// ---------------------------------------------------------------------------- +// TRFeWriteData::DoRequestL +// get permission to write certain amount of data +// ---------------------------------------------------------------------------- +// +void TRFeWriteData::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeWriteData::DoRequestL")); + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + TRfeWriteDataInArgs* inArgs = + static_cast(request->iInArgs); + TRfeWriteDataOutArgs* outArgs = + static_cast(request->iOutArgs); + outArgs->iOkToWrite = + request->iVolumeTable->EnsureCacheCanBeAddedL(inArgs->iBytes); + + if (outArgs->iOkToWrite) + { + // make sure "dirty bit" is on (file has uncommited modifications) + CRsfwFileEntry* entry= + request->iVolume->iFileEngine->iFileTable->Lookup(inArgs->iFid); + if (entry) + { + entry->SetOpenedForWriting(ETrue); + request->iVolume->iFileEngine->iFileTable->SaveMetaDataDelta(); + } + // if writing has been cancelled, we have to inform the file server plugin + if (entry->IsCancelled()) + { + User::Leave(KErrCancel); + } + + } + } + +void TRFeDirectoryRefresh::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeDirectoryRefresh::DoRequestL")); + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + HBufC* refreshBuf = HBufC::NewLC(KMaxPath); + TPtr refPtr = refreshBuf->Des(); + request->Message().ReadL(0, refPtr); + User::LeaveIfError(request->Session()->Volume()->PurgeFromCache(refPtr)); + CleanupStack::PopAndDestroy(refreshBuf); + } + + +void TRFeCancelAll::DoRequestL(CRsfwRfeRequest* aRequest) + { + DEBUGSTRING(("TRFeCancelAll::DoRequestL")); + CRsfwRfeMessageRequest* request = (CRsfwRfeMessageRequest*) aRequest; + HBufC* fileBuf = HBufC::NewLC(KMaxPath); + TPtr filePtr = fileBuf->Des(); + request->Message().ReadL(0, filePtr); + User::LeaveIfError(request->Session()->Volume()->CancelTransferL(filePtr)); + CleanupStack::PopAndDestroy(fileBuf); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwvolume.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwvolume.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,93 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: data structure for a volume +* +*/ + + +#include "rsfwvolume.h" +#include "rsfwvolumetable.h" +#include "rsfwfiletable.h" +#include "rsfwfileengine.h" + +// ---------------------------------------------------------------------------- +// CRsfwVolume::~CRsfwVolume +// +// ---------------------------------------------------------------------------- +// +CRsfwVolume::~CRsfwVolume() + { + delete iFileEngine; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolume::MountInfo +// +// ---------------------------------------------------------------------------- +// +TRsfwMountInfo* CRsfwVolume::MountInfo() + { + return &iMountInfo; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolume::GetMountInfo +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolume::GetMountInfo(TRsfwMountInfo& aMountInfo) + { + aMountInfo = iMountInfo; + aMountInfo.iMountStatus.iConnectionState = iFileEngine->ConnectionState(); + aMountInfo.iMountStatus.iCachedSize = + iFileEngine->iFileTable->TotalCachedSize(); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolume::OperationCompleted() +// ---------------------------------------------------------------------------- +// +void CRsfwVolume::OperationCompleted() + { + iVolumeTable->OperationCompleted(this); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolume::ConnectionStateChanged +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolume::ConnectionStateChanged(TInt aConnectionState) + { + // The mount state and connection state are tightly bound together + switch (aConnectionState) + { + case KMountNotConnected: + iMountInfo.iMountStatus.iMountState = KMountStateDormant; + iMountInfo.iMountStatus.iConnectionState = KMountNotConnected; + break; + case KMountStronglyConnected: + iMountInfo.iMountStatus.iMountState = KMountStateMounted; + iMountInfo.iMountStatus.iConnectionState = KMountStronglyConnected; + break; + case KMountConnecting: + iMountInfo.iMountStatus.iMountState = KMountStateDormant; + iMountInfo.iMountStatus.iConnectionState = KMountConnecting; + break; + default: + break; + } + iVolumeTable->VolumeStateChanged(this); + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwvolumetable.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwvolumetable.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1471 @@ +/* +* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: data struct for all volumes +* +*/ + + +#include +#include +#include +#include + +#include "rsfwvolumetable.h" +#include "rsfwvolume.h" +#include "rsfwinterface.h" +#include "rsfwmountstatemachine.h" +#include "rsfwfileentry.h" +#include "rsfwfiletable.h" +#include "rsfwconfig.h" +#include "rsfwfileengine.h" +#include "rsfwrfeserver.h" + +#include "rsfwmountstore.h" +#include "rsfwwaitnotemanager.h" +#include "rsfwdormantmountloader.h" +#include "mdebug.h" + +//CONSTANTS +_LIT(KRsfwLruFileName, "lru.dat"); +_LIT(KRsfwRestorePendingMark, "rsfwmetadatarestorepending.dat"); + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::NewL +// +// ---------------------------------------------------------------------------- +// +CRsfwVolumeTable* CRsfwVolumeTable::NewL(CRsfwRfeServer* aRfeServer, + CRsfwConfig* aRsfwConfig) + { + CRsfwVolumeTable* self = new (ELeave) CRsfwVolumeTable; + DEBUGSTRING(("CRsfwVolumeTable: in NewL 0x%x", self)); + CleanupStack::PushL(self); + self->ConstructL(aRfeServer, aRsfwConfig); + CleanupStack::Pop(self); + return self; + } + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::RestoreDormantMountsL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::RestoreDormantMountsL() + { + DEBUGSTRING(("CRsfwVolumeTable::RestoreDormantMountsL enter")); + // Currently, we always enable persistence (used to be configurrable) + iPermanence = ETrue; + if (iPermanence) + { + // if restoring permanent state causes RFE panic, we must delete + // the old permanent metadata and skip restoring it + // otherwise RFE will just crash every time + // Strategy is to add a file that tells that the process is ongoing. + // If it is not able to finish successfully, we can conclude that there was a crash + // marker is deleted from CRsfwDormantMountLoader, when we have succesfully also checked for dirty files + TBool internalize = CheckAndAddProcessStartMarker(); + if (internalize) + { + WillLRUPriorityListBeInternalized(); + RestoreVolumesL(); + InternalizeLRUPriorityListL(); + } + else + { + CleanupCorruptedCacheL(); + } + } + iDormantMountRestorePending = EFalse; + DEBUGSTRING(("CRsfwVolumeTable::RestoreDormantMountsL exit")); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::ConstructL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::ConstructL(CRsfwRfeServer* aRfeServer, CRsfwConfig* aRsfwConfig) + { + iRfeServer = aRfeServer; + iRsfwConfig = aRsfwConfig; + + iAllEnginesIdle = ETrue; + + // set some local pointers for commonly used variable from CRsfwRfeServer::Env() + iFs = CRsfwRfeServer::Env()->iFs; + iCacheRoot = &(CRsfwRfeServer::Env()->iCacheRoot); + + TInt err = iRsfwConfig->Get(RsfwConfigKeys::KMaxCacheSize, + iMaxCacheSize); + if (err != KErrNone) + { + iMaxCacheSize = KDefaultMaxCacheSize; + } + + err = iRsfwConfig->Get(RsfwConfigKeys::KMaxEntryCount, + iMaxEntryCount); + if (err != KErrNone) + { + iMaxEntryCount = KDefaultMaxEntryCount; + } + + HBufC* confItem = HBufC::NewLC(KMaxRsfwConfItemLength); + TPtr confItemPtr = confItem->Des(); + + // global wait notes manager class + // must be created before restoring the volumes + iWaitNoteManager = CRsfwWaitNoteManager::NewL(); + + RestoreDormantMountsL(); + + err = iRsfwConfig->Get(RsfwConfigKeys::KFileCacheValidity, + iFileCacheTimeout); + if (err) + { + iFileCacheTimeout = KDefaultCacheValidity; + } + err = iRsfwConfig->Get(RsfwConfigKeys::KDirCacheValidity, + iDirCacheTimeout); + if (err) + { + iDirCacheTimeout = KDefaultDirCacheValidity; + } + + err = iRsfwConfig->Get(RsfwConfigKeys::KRecognizerLimit, + iRecognizerLimit); + if (err) + { + iRecognizerLimit = KDefaultRecognizerLimit; + } + + err = iRsfwConfig->Get(RsfwConfigKeys::KCachingMode, confItemPtr); + if (err == KErrNone) + { + TLex lex(confItemPtr); + TChar firstChar = lex.Get(); + firstChar.UpperCase(); + switch (firstChar) + { + case 'W': + iCachingMode = EWholeFileCaching; + break; + + case 'F': + iCachingMode = EFullIfa; + break; + + case 'M': + default: + iCachingMode = EMetadataIfa; + break; + } + } + else + { + // caching mode configuration entry not found + iCachingMode = EMetadataIfa; + } + if (iCachingMode != EWholeFileCaching) + { + GetMimeTypeSpecificLimits(); + } + + err = iRsfwConfig->Get(RsfwConfigKeys::KInactivityTimeout, + iInactivityTimeout); + if (err) + { + iInactivityTimeout = KDefaultInactivityTimeout; + } + + CleanupStack::PopAndDestroy(confItem); + + iMountStore = CRsfwMountStore::NewL(NULL); + + RProperty::Define(KRfeServerSecureUid, + ERsfwPSKeyConnect, + RProperty::EByteArray, + KMaxDrives); + + iMountStateProperty.Attach(KRfeServerSecureUid, + ERsfwPSKeyConnect); + + + // this restores the dormant mounts asynchrously shortly after the server has started + iDormantMountLoader = CRsfwDormantMountLoader::NewL(this); + iDormantMountRestorePending = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::~CRsfwVolumeTable +// +// ---------------------------------------------------------------------------- +// +CRsfwVolumeTable::~CRsfwVolumeTable() + { + // save LRU list to the file + ExternalizeLRUPriorityList(); + + TInt i; + DEBUGSTRING(("Deleting all volumes")); + for (i = 0; i < KMaxVolumes; i++) + { + if (iVolumes[i]) + { + delete iVolumes[i]; + } + } + delete iMountStore; + iMountStateProperty.Close(); + if (iWaitNoteManager) + { + delete iWaitNoteManager; + } + if (iDormantMountLoader) + { + delete iDormantMountLoader; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::DispatchL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::DispatchL(TAny* aIp, TAny* aOp) + { + TRfeInArgs* ip = reinterpret_cast(aIp); + TRfeOutArgs* op = reinterpret_cast(aOp); + CRsfwFileEngine* fileEngine = NULL; + TInt volumeId; + + if(ip->iOpCode == EFsRoot) + { + volumeId = iLastVolumeId; + // boot - assume that ROOT + // immediately follows after MountL() + if (volumeId) + { + DEBUGSTRING(("Volume: acquired engine %d", volumeId)); + CRsfwVolume* volume = iVolumes[volumeId]; + if (volume) + { + fileEngine = volume->iFileEngine; + } + } + } + else + { + // iFid is always in the same position in the messages + volumeId = static_cast(ip)->iFid.iVolumeId; + CRsfwVolume* volume = VolumeByVolumeId(volumeId); + if (volume) + { + fileEngine = volume->iFileEngine; + } + } + if (fileEngine) + { + fileEngine->DispatchL(*ip, *op); + } + else + { + DEBUGSTRING(("Volume: no engine for %d", volumeId)); + User::Leave(KErrNotReady); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::VolumeIdByDriveLetter +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::VolumeIdByDriveLetter(TChar aDriveLetter) + { + TInt driveNumber; + iFs.CharToDrive(aDriveLetter, driveNumber); + if (driveNumber < 0) // note that 0 = EDriveA is allowed + { + driveNumber = KErrNotFound; + } + return driveNumber; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::VolumeByVolumeId +// +// ---------------------------------------------------------------------------- +// +CRsfwVolume* CRsfwVolumeTable::VolumeByVolumeId(TInt aVolumeId) + { + if ((aVolumeId >= 0) && (aVolumeId < KMaxVolumes)) + { + return iVolumes[aVolumeId]; + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::VolumeByDriveLetter +// +// ---------------------------------------------------------------------------- +// +CRsfwVolume* CRsfwVolumeTable::VolumeByDriveLetter(TChar aDriveLetter) + { + return VolumeByVolumeId(VolumeIdByDriveLetter(aDriveLetter)); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::RecoverVolumeL +// +// ---------------------------------------------------------------------------- +// +TUint CRsfwVolumeTable::RecoverVolumeL(const TRsfwMountConfig& aMountConfig, + CRsfwMountStateMachine* aCaller) + { + DEBUGSTRING(("Recovering volume")); + TUint transactionId = 0; + CRsfwVolume* volume = VolumeByVolumeId(aCaller->iVolumeId); + if (volume) + { + aCaller->iVolume = volume; + // set also fileengine pointer in the state machine, + // so that the operation can be cancelled + aCaller->SetFileEngine(volume->iFileEngine); + if (User::UpperCase( + aCaller->iVolume->iMountInfo.iMountConfig.iDriveLetter) == + User::UpperCase(aMountConfig.iDriveLetter)) + { + if (aCaller->iVolume->iMountInfo.iMountConfig.iFlags & + KMountFlagOffLine) + { + // We are working offline + aCaller->iVolume->iMountInfo.iMountStatus.iConnectionState = + KMountNotConnected; + } + else + { + aCaller->iVolume->iMountInfo.iMountStatus.iConnectionState = + KMountStronglyConnected; + } + + transactionId = + aCaller->iVolume->iFileEngine->RequestConnectionStateL( + aCaller->iVolume->iMountInfo.iMountStatus.iConnectionState, + aCaller); + } + else + { + User::Leave(KErrArgument); + } + } + else + { + User::Leave(KErrNotFound); + } + + return transactionId; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::MountState +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::MountState(TChar aDriveLetter) + { + DEBUGSTRING(("Getting mount state")); + TInt state; + // Find the volume + CRsfwVolume* volume = VolumeByDriveLetter(aDriveLetter); + if (volume) + { + TRsfwMountInfo& mountInfo = volume->iMountInfo; + DEBUGSTRING16(("mount '%S'in state %d", + &mountInfo.iMountConfig.iName, + mountInfo.iMountStatus.iMountState)); + state = mountInfo.iMountStatus.iMountState; + } + else + { + DEBUGSTRING(("mount not found")); + state = 0; // define KMountStateNone=0 in RsfwControl.h + } + return state; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::GetMountConfigL +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::GetMountConfigL(TRsfwMountConfig& aMountConfig) + { + DEBUGSTRING16(("Getting mount config for name '%S', drive %c", + &aMountConfig.iName, + TUint(aMountConfig.iDriveLetter))); + TInt err = KErrNone; + const CRsfwMountEntry* entry = + iMountStore->LookupEntryByDriveL(aMountConfig.iDriveLetter); + if (!entry) + { + // Could not find by drive letter - retry with name + entry = iMountStore->LookupEntryByNameL(aMountConfig.iName); + } + if (entry && + entry->Item(EMountEntryItemDrive) && + entry->Item(EMountEntryItemUri)) + { + if (entry->Item(EMountEntryItemDrive)->Length()) + { + TLex parse(*entry->Item(EMountEntryItemDrive)); + aMountConfig.iDriveLetter = parse.Get(); + if (entry->Item(EMountEntryItemName)) + { + aMountConfig.iName.Copy(*entry->Item(EMountEntryItemName)); + } + else + { + aMountConfig.iName.SetLength(0); + } + aMountConfig.iUri.Copy(*entry->Item(EMountEntryItemUri)); + if (entry->Item(EMountEntryItemUserName)) + { + aMountConfig.iUserName.Copy( + *entry->Item(EMountEntryItemUserName)); + } + else + { + aMountConfig.iUserName.SetLength(0); + } + + if (entry->Item(EMountEntryItemPassword)) + { + aMountConfig.iPassword.Copy( + *entry->Item(EMountEntryItemPassword)); + } + else + { + aMountConfig.iPassword.SetLength(0); + } + + if (entry->Item(EMountEntryItemIap)) + { + aMountConfig.iAuxData.Copy( + *entry->Item(EMountEntryItemIap)); + } + else + { + aMountConfig.iAuxData.SetLength(0); + } + + TInt inactivityTimeout = iInactivityTimeout; + if (entry->Item(EMountEntryItemInactivityTimeout)) + { + TLex timeout(*entry->Item(EMountEntryItemInactivityTimeout)); + timeout.Val(inactivityTimeout); + DEBUGSTRING(("Set inactivity timeout = %d", + inactivityTimeout)); + } + aMountConfig.iInactivityTimeout = inactivityTimeout; + + aMountConfig.iFlags = 0; + } + else + { + err = KErrArgument; + } + } + else + { + DEBUGSTRING(("mount configuration not found")); + err = KErrNotFound; + } + + return err; + } + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::RestoreVolumesL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::RestoreVolumesL() + { + DEBUGSTRING(("CRsfwVolumeTable::RestoreVolumesL")); + // Load persistently stored volumes + CDir* dirList; + TInt err = iFs.GetDir(*iCacheRoot, + KEntryAttMaskSupported, + ESortByName, + dirList); + CleanupStack::PushL(dirList); + DEBUGSTRING(("GetDir for cacheRoot returned %d", err)); + if (err == KErrNone) + { + TInt i; + for (i = 0; i < dirList->Count(); i++) + { + const TEntry& entry = (*dirList)[i]; + if (entry.iAtt & KEntryAttDir) + { + // The name of cache directories are C + _LIT(KCacheMatch, "C*"); + if (entry.iName.Match(KCacheMatch) == 0) + { + TLex volumeAlpha(entry.iName.Mid(1)); + TInt volumeId; + err = volumeAlpha.Val(volumeId); + if ((err == KErrNone) && + (volumeId >= 0) && + (volumeId < KMaxVolumes)) + { + TRsfwMountConfig* mountConfig = new (ELeave) TRsfwMountConfig; + CleanupStack::PushL(mountConfig); + HBufC* metaDataPath = HBufC::NewLC(KMaxPath); + TPtr metaDataPathPtr = metaDataPath->Des(); + metaDataPathPtr.Copy(*iCacheRoot); + metaDataPathPtr.Append(entry.iName); + metaDataPathPtr.Append('\\'); + metaDataPathPtr.Append(KMetaDataFileName); + CRsfwMetaDataStore* metaDataStore = + CRsfwMetaDataStore::NewLC(metaDataPathPtr); + // Get the mount configuration info from the + // persistent store + TRAP(err, + metaDataStore->GetMountConfigL(*mountConfig)); + // metaDataStore, metaDataPath + CleanupStack::PopAndDestroy(2); + if (err == KErrNone) + { + DEBUGSTRING16(("Restoring '%S' as volume %d'", + &mountConfig->iUri, + volumeId)); + TRAP_IGNORE(MountDormantL(*mountConfig, + volumeId)); + // In case of error, we should clear the cache + } + CleanupStack::PopAndDestroy(mountConfig); + } + } + } + } + } + CleanupStack::PopAndDestroy(dirList); // dirList + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::DismountByVolumeId +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::DismountByVolumeIdL(TInt aVolumeId, + TBool aDiscardPermanentData) + { + DEBUGSTRING(("Dismounting volume %d", aVolumeId)); + CRsfwVolume* volume = VolumeByVolumeId(aVolumeId); + if (volume) + { + if (aDiscardPermanentData) + { + // Delete also the meta data + CRsfwFileEngine* fileEngine = volume->iFileEngine; + if (fileEngine) + { + // Clear cache of files and meta data + fileEngine->SetPermanenceL(EFalse); + if (!volume->iMountInfo.iMountStatus.iPermanence) + { + // There was no change in the above - + // so, we have to clear the cache explicitly + fileEngine->iFileTable->SetupCacheL(); + } + } + } + delete volume; + iVolumes[aVolumeId] = NULL; + } + else + { + User::Leave(KErrNotFound); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::DismountByDriveLetter +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::DismountByDriveLetterL(TChar aDriveLetter, + TBool aDiscardPermanentData) + { + DEBUGSTRING(("Dismounting drive %c", TUint(aDriveLetter))); + CRsfwVolume* volume = VolumeByDriveLetter(aDriveLetter); + if (volume) + { + DismountByVolumeIdL(volume->iMountInfo.iMountStatus.iVolumeId, + aDiscardPermanentData); + } + else + { + User::Leave(KErrNotFound); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::GetMountList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::GetMountList(TDriveList& aMountList) + { + aMountList.Zero(); + TInt i; + for (i = 0; i < KMaxVolumes; i++) + { + if (iVolumes[i]) + { + aMountList.Append(iVolumes[i]-> + iMountInfo.iMountConfig.iDriveLetter); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::GetMountInfo +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::GetMountInfo(TRsfwMountInfo& aMountInfo) + { + CRsfwVolume* volume = + VolumeByDriveLetter(aMountInfo.iMountConfig.iDriveLetter); + if (volume) + { + volume->GetMountInfo(aMountInfo); + return KErrNone; + } + return KErrNotFound; + } + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::GetMimeTypeSpecificLimits +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::GetMimeTypeSpecificLimits() + { + TInt err; + err = iRsfwConfig->Get(RsfwConfigKeys::KImgJpegLimit, iImageJpegLimit); + if (err != KErrNone) + { + iImageJpegLimit = KDefaultJpegLimit; + } + + err = iRsfwConfig->Get(RsfwConfigKeys::KAudMpegLimit, iAudioMpegLimit); + if (err) + { + iAudioMpegLimit = KDefaultMpegLimit; + } + } + + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::EnsureCacheCanBeAddedL +// +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::EnsureCacheCanBeAddedL(TInt aBytes) + { + DEBUGSTRING(("CACHE MANAGER: ensure that %d bytes can be added to cache", + aBytes)); + DEBUGSTRING(("CACHE MANAGER: total cached size is currently %d", + TotalCachedSize())); + DEBUGSTRING(("CACHE MANAGER: max cache size is %d", iMaxCacheSize)); + + + // FIRST: Is there enough space on the cache drive to store the new data + TInt cacheDrive = CRsfwRfeServer::Env()->iCacheDrive; + TBool isDiskFull = SysUtil::DiskSpaceBelowCriticalLevelL(&iFs, + aBytes, + cacheDrive); + if ( isDiskFull ) + { + // check whether clearing cache may help at all + if ( aBytes > TotalCachedSize() ) + { + isDiskFull = SysUtil::DiskSpaceBelowCriticalLevelL(&iFs, + aBytes - TotalCachedSize(), + cacheDrive); + if ( isDiskFull ) + { + DEBUGSTRING(("CACHE MANAGER: no space on disk")); + return EFalse; + } + } + // seems that clearing cache may help + else + { + DEBUGSTRING(("CACHE MANAGER: running out of disk space, attempting to purge some bytes from cache")); + do + { + CRsfwFileEntry* victim = iLRUPriorityList.GetAndRemoveFirstEntry(); + + if (!victim) + { + DEBUGSTRING(("CACHE MANAGER: nothing to delete!!!")); + return EFalse; // cannot clear enough cache space + } + + DEBUGSTRING(("CACHE MANAGER: removing fid %d from the cache ", + victim->Fid().iNodeId)); + + TDesC* cacheNamep = victim->CacheFileName(); + User::LeaveIfError(iFs.Delete(*cacheNamep)); + + victim->SetCached(EFalse); + victim->iCachedSize = 0; + victim->Parent()->SetLocallyDirty(); + + + isDiskFull = SysUtil::DiskSpaceBelowCriticalLevelL(&iFs, + aBytes, + cacheDrive); + } + while ( isDiskFull ); + } + } + + // SECOND: is there enough space in the cache + if (TotalCachedSize() + aBytes > iMaxCacheSize) + { + TInt bytesDeleted = 0; + TInt bytesToBeDeleted = TotalCachedSize() + aBytes - iMaxCacheSize; + DEBUGSTRING(("CACHE MANAGER: attempting to purge %d bytes from cache", + bytesToBeDeleted)); + + while (bytesDeleted < bytesToBeDeleted) + { + CRsfwFileEntry* victim = iLRUPriorityList.GetAndRemoveFirstEntry(); + + if (!victim) + { + DEBUGSTRING(("CACHE MANAGER: XXXX: nothing to delete!!!")); + return EFalse; // cannot clear enough cache space + } + + DEBUGSTRING(("CACHE MANAGER: removing fid %d from the cache ", + victim->Fid().iNodeId)); + + TDesC* cacheNamep = victim->CacheFileName(); + TInt victimSize = victim->iCachedSize; + User::LeaveIfError(iFs.Delete(*cacheNamep)); + + victim->SetCached(EFalse); + victim->iCachedSize = 0; + victim->Parent()->SetLocallyDirty(); + + bytesDeleted = bytesDeleted + victimSize; + } + } + + return ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::EnsureMetadataCanBeAddedL +// This function is called at any time a new CRsfwFileEntry object is about to +// be created in memory. +// However we want to prevent the scenario in which parent entry is deleted +// just before its kid creation. +// That's why function takes as a parameter a parent entry for the entry +// that is about to be created. +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::EnsureMetadataCanBeAddedL(CRsfwFileEntry* aParent) + { + DEBUGSTRING(("memory cap: number of entries %d, entry limit: %d", + TotalEntryCount(), iMaxEntryCount)); + + TBool parentFound = EFalse; + + while ( TotalEntryCount() >= iMaxEntryCount ) + { + CRsfwFileEntry* victim = iMetadataLRUPriorityList.GetAndRemoveFirstEntry(); + + // if no entries to delete on metadata LRU list try to remove item from file cache LRU list + if (!victim) + { + victim = iLRUPriorityList.GetAndRemoveFirstEntry(); + + if (!victim) + { + DEBUGSTRING(("memory cap: nothing to delete!!!")); + return EFalse; // no posibility to add new entry + } + } + + // don't touch the root items + if ( IsRoot(victim) ) + { + continue; + } + + // if we've found the parent don't touch it, just find the other victim ... + if (victim && aParent && victim == aParent) + { + DEBUGSTRING(("<<<<< SAVED THE PARENT!!!! >>>>")); + parentFound = ETrue; + continue; + } + + + // destroy the item + DEBUGSTRING(("memory cap: removing fid %d from memory", + victim->Fid().iNodeId)); + // victim's parent metadata will become out-of-date if we remove victim from memory + if ( victim->Parent() ) + { + victim->Parent()->iUseCachedData = EFalse; + } + + victim->DropLD(); + } + + // put the parent back to the list if it was removed from the list. + // the reason is that at this point we are not sure whether child will be in fact created. + // for now we were only interested in preventing the parent from being deleted, nothing more + // as soon as the child is created, the parent will be removed from the list anyway + if (parentFound) + { + iMetadataLRUPriorityList.AddNodeL(aParent, ECachePriorityNormal); + } + + return ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::IsRoot +// Checks whether given entry is a root of some file table +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::IsRoot(const CRsfwFileEntry* aEntry) + { + if (!aEntry) + { + return EFalse; + } + + TInt i; + for ( i = 0; i < KMaxVolumes; i++ ) + { + CRsfwVolume* volume; + volume = iVolumes[i]; + if ( volume && aEntry == volume->iFileEngine->iFileTable->Root()) + { + return ETrue; + } + } + return EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::TotalCachedSize +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::TotalCachedSize() + { + TInt totalSize = 0; + CRsfwVolume* volume; + TInt i = 0; + while (i < KMaxVolumes) + { + volume = iVolumes[i]; + if (volume) + { + TInt newSize = volume->iFileEngine->iFileTable->TotalCachedSize(); + totalSize += newSize; + } + i++; + } + return totalSize; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::TotalEntryCount +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::TotalEntryCount() + { + TInt totalCount = 0; + CRsfwVolume* volume; + for ( TInt i = 0; i < KMaxVolumes; i++ ) + { + volume = iVolumes[i]; + if (volume) + { + TInt volumeCount = volume->iFileEngine->iFileTable->TotalEntryCount(); + totalCount += volumeCount; + } + } + return totalCount; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::AddToLRUPriorityListL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::AddToLRUPriorityListL(CRsfwFileEntry *aFe, TInt aPriority) + { + DEBUGSTRING(("CACHE MANAGER: adding fid '%d' to the LRU cache", + aFe->Fid().iNodeId)); + iLRUPriorityList.AddNodeL(aFe, aPriority); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::RemoveFromLRUPriorityList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::RemoveFromLRUPriorityList(CRsfwFileEntry *aFe) + { + DEBUGSTRING(("CACHE MANAGER: removing fid '%d' from the LRU cache", + aFe->Fid().iNodeId)); + iLRUPriorityList.RemoveNode(aFe); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::AddToMetadataLRUPriorityListL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::AddToMetadataLRUPriorityListL(CRsfwFileEntry *aFe, TInt aPriority) + { + DEBUGSTRING(("memory cap: adding fid '%d' to the metadata LRU list", + aFe->Fid().iNodeId)); + iMetadataLRUPriorityList.AddNodeL(aFe, aPriority); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::RemoveFromMetadataLRUPriorityList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::RemoveFromMetadataLRUPriorityList(CRsfwFileEntry *aFe) + { + DEBUGSTRING(("CRsfwVolumeTable::RemoveFromMetadataLRUPriorityList")); + iMetadataLRUPriorityList.RemoveNode(aFe); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::MoveToTheBackOfMetadataLRUPriorityList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::MoveToTheBackOfMetadataLRUPriorityListL(CRsfwFileEntry *aFe) + { + // just try to remove the entry from the list and if it was on the list then append it again + if ( iMetadataLRUPriorityList.RemoveNode(aFe) == KErrNone ) + { + DEBUGSTRING(("memory cap: moving fid '%d' to the back of metadata LRU list", + aFe->Fid().iNodeId)); + iMetadataLRUPriorityList.AddNodeL(aFe, ECachePriorityNormal); + } + } + + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::CheckAndAddProcessStartMarker +// +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::CheckAndAddProcessStartMarker() + { + DEBUGSTRING(("CRsfwVolumeTable::CheckAndAddProcessStartMarker")); + TFileName path; + path.Copy(*iCacheRoot); + path.Append(KRsfwRestorePendingMark); + + if (BaflUtils::FileExists(iFs, path)) + { + // file already exists, the previous attempt to restore metadata must have failed + DEBUGSTRING(("returning EFalse; file already exists")); + return EFalse; + } + else + { + // create an empty file + TInt err; + RFile markerFile; + err = markerFile.Create(iFs, path, EFileWrite); + if (err) + { + return EFalse; + } + else + { + DEBUGSTRING(("returning ETrue; file created")); + markerFile.Close(); + return ETrue; + } + + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::DeleteTheMarker +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::DeleteTheMarker() + { + TFileName path; + path.Copy(*iCacheRoot); + path.Append(KRsfwRestorePendingMark); + + // ignore the error + // if this fails for some reason, lets allow the file to be there + // as "something" must be wrong + iFs.Delete(path); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::CleanupCorrutedCacheL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::CleanupCorruptedCacheL() + { + // delete everything from the cache + TFileName cachepath; + cachepath.Copy(*iCacheRoot); + CFileMan* fileMan = CFileMan::NewL(iFs); + fileMan->Delete(cachepath, CFileMan::ERecurse); + delete fileMan; + } + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::WillExternalizedLRUPriorityListBeUsed +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::WillLRUPriorityListBeInternalized() + { + DEBUGSTRING(("CRsfwVolumeTable::WillLRUPriorityListBeInternalized")); + iUseExternalizedLRUList = EFalse; + // check whether the file with externalized data exists + TFileName path; + path.Copy(*iCacheRoot); + path.Append(KRsfwLruFileName); + + if (BaflUtils::FileExists(iFs, path)) + { + iUseExternalizedLRUList = ETrue; + } + DEBUGSTRING(("...set to %d", iUseExternalizedLRUList)); + } + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::ExternalizeLRUPriorityList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::ExternalizeLRUPriorityList() + { + TRAPD(err, ExternalizeLRUPriorityListL()); + if (err) + { + DEBUGSTRING(("Externalizing LRU priority list failed!")); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::ExternalizeLRUPriorityList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::ExternalizeLRUPriorityListL() + { + // prepare temp path + _LIT(KRsfwLruTempFileName, "lru.temp"); + TFileName tempPath; + tempPath.Copy(*iCacheRoot); + tempPath.Append(KRsfwLruTempFileName); + + // create temp file + RFile file; + CleanupClosePushL(file); + User::LeaveIfError(file.Replace(iFs, tempPath, EFileShareAny | EFileWrite)); + + // associate stream + RFileWriteStream stream(file); + CleanupClosePushL(stream); + + // externalize + iLRUPriorityList.ExternalizeL(stream); + stream.CommitL(); + + // cleanup + CleanupStack::PopAndDestroy(2); // stream, file + + // everything went ok -> rename lru.temp into lru.dat + TFileName path; + path.Copy(*iCacheRoot); + path.Append(KRsfwLruFileName); + CFileMan* fm = CFileMan::NewL(iFs); + CleanupStack::PushL(fm); + TInt err = fm->Rename(tempPath, path, CFileMan::EOverWrite); + if (err) + { + fm->Delete(tempPath); + fm->Delete(path); + User::Leave(err); + } + CleanupStack::PopAndDestroy(fm); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::InternalizeLRUPriorityList +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::InternalizeLRUPriorityListL() + { + if (!iUseExternalizedLRUList) + { + // it means LRU has been already populated when loading metadata + // so nothing to do here + return; + } + // prepare path + TFileName path; + path.Copy(*iCacheRoot); + path.Append(KRsfwLruFileName); + + // open file + RFile file; + TInt err = file.Open(iFs, path, EFileShareAny | EFileRead); + if ( err == KErrNone ) + { + CleanupClosePushL(file); + + // associate stream + RFileReadStream stream(file); + CleanupClosePushL(stream); + + // internalize + TRAP(err, iLRUPriorityList.InternalizeL(stream, this)); + + // cleanup + CleanupStack::PopAndDestroy(2); // stream, file + } + + DEBUGSTRING(("InternalizeLRUPriorityListL: status %d", err)); + + // once internalizing is done, the file is not needed anymore + // ignore the result + iFs.Delete(path); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::OperationCompleted() +// This function may shut down RFE. +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::OperationCompleted(CRsfwVolume* /* aVolume */) + { + DEBUGSTRING(("Volume operation completed")); + // Shut down the whole server if all remaining mounts are dormant + // and we are not still restoring dormant mounts + if ((iAllEnginesIdle) && (!iDormantMountRestorePending)) + { + iRfeServer->AllEnginesIdling(KRsfwDormantShutdownTimeout); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::VolumeStateChanged() +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::VolumeStateChanged(CRsfwVolume* aVolume) + { + DEBUGSTRING(("Volume state changed")); + + TBool allEnginesIdle = ETrue; + TInt i = 0; + do + { + if (iVolumes[i]) + { + if (!IsMountIdle(iVolumes[i]->iMountInfo.iMountStatus)) + { + // Do not shut down if there are connected mounts + allEnginesIdle = EFalse; + } + } + } while ((++i < KMaxVolumes) && allEnginesIdle); + + // one more thing is to check the current volume since + // if the drive was newly mounted, it will not be found from the volume table + if (allEnginesIdle) + { + TInt driveNumber = VolumeIdByDriveLetter(aVolume->MountInfo()->iMountConfig.iDriveLetter); + if ((driveNumber != KErrNotFound) && + (!IsMountIdle(aVolume->MountInfo()->iMountStatus))) + { + allEnginesIdle = EFalse; + } + } + + DEBUGSTRING(("All engines idle = %d", allEnginesIdle)); + iAllEnginesIdle = allEnginesIdle; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::PublishConnectionStatus() +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::PublishConnectionStatus(CRsfwVolume* aVolume) + { + DEBUGSTRING(("Publishing connection status:")); + TDriveList driveList; + driveList.FillZ(driveList.MaxLength()); + TInt i; + // (at least) record the state of the volume received as a parameter + // (if the drive was newly mounted, it will not be found from the volume table + TInt driveNumber = VolumeIdByDriveLetter(aVolume->MountInfo()->iMountConfig.iDriveLetter); + if ((driveNumber != KErrNotFound) && + (aVolume->MountInfo()->iMountStatus.iMountState != KMountStateDormant)) + { + DEBUGSTRING(("- connected: %c", TUint(aVolume->MountInfo()->iMountConfig.iDriveLetter))); + driveList[driveNumber] = 1; + } + + // for convenience, record the states of other volumes too from the volume table + for (i = 0; i < KMaxVolumes; i++) + { + if (iVolumes[i]) + { + TRsfwMountInfo& mountInfo = iVolumes[i]->iMountInfo; + if (mountInfo.iMountStatus.iMountState != KMountStateDormant) + { + driveNumber = + VolumeIdByDriveLetter(mountInfo.iMountConfig.iDriveLetter); + if (driveNumber != KErrNotFound) + { + DEBUGSTRING(("- connected: %c", + TUint(mountInfo.iMountConfig.iDriveLetter))); + driveList[driveNumber] = 1; + } + } + } + } + + iMountStateProperty.Set(driveList); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::WaitNoteManager() +// +// ---------------------------------------------------------------------------- +// +CRsfwWaitNoteManager* CRsfwVolumeTable::WaitNoteManager() + { + return iWaitNoteManager; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::IsCachedDataStillValid() +// +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::IsCachedDataStillValid(TTime aCachedTime) + { + return IsCacheStillValid(aCachedTime, + TTimeIntervalSeconds(iFileCacheTimeout)); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::IsCachedAttrStillValid() +// +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::IsCachedAttrStillValid(TTime aCachedTime) + { + return IsCacheStillValid(aCachedTime, + TTimeIntervalSeconds(iDirCacheTimeout)); + } + + + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::MountDormantL +// +// ---------------------------------------------------------------------------- +// +void CRsfwVolumeTable::MountDormantL(const TRsfwMountConfig& aMountConfig, + TInt aVolumeId) + { + // Bind a volume id to a file engine + DEBUGSTRING16(("Restoring drive '%c' with uri '%S' and flags 0x%x", + TUint(aMountConfig.iDriveLetter), + &aMountConfig.iUri, + aMountConfig.iFlags)); + + // Create a file engine for the volume + CRsfwVolume* volume = new (ELeave) CRsfwVolume(); + CleanupStack::PushL(volume); + volume->iMountInfo.iMountConfig = aMountConfig; + volume->iMountInfo.iMountStatus.iVolumeId = aVolumeId; + volume->iVolumeTable = this; + volume->iMountInfo.iMountStatus.iPermanence = iPermanence; + // We are working offline + volume->iMountInfo.iMountStatus.iMountState = KMountStateDormant; + volume->iMountInfo.iMountStatus.iConnectionState = KMountNotConnected; + CRsfwFileEngine* fileEngine = CRsfwFileEngine::NewL(volume); + volume->iFileEngine = fileEngine; + delete iVolumes[aVolumeId]; + iVolumes[aVolumeId] = volume; + CleanupStack::Pop(volume); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::IsCachedAttrStillValid() +// +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::IsCacheStillValid(TTime aCachedTime, + TTimeIntervalSeconds aValidity) + { + TTime now; + TTime comp; + + now.UniversalTime(); + comp = now - aValidity; + + if (comp >= aCachedTime) + { + return EFalse; + } + else + { + return ETrue; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::PurgeFromCache() +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::PurgeFromCache(TDesC& aCachePath) + { + // get the volume id for this path + TParse parser; + parser.Set(aCachePath, NULL, NULL); + if (!(parser.DrivePresent())) + { + return KErrArgument; + } + TPtrC drive = parser.Drive(); + CRsfwVolume* volume = VolumeByDriveLetter(drive[0]); + if (!volume) + { + return KErrNotFound; + } + + if (!(parser.PathPresent())) + { + return KErrArgument; + } + + if (parser.NamePresent()) + { + // this is a file + return KErrArgument; + } + return volume->iFileEngine->PurgeFromCache(parser.Path()); + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::CancelTransfer() +// +// ---------------------------------------------------------------------------- +// +TInt CRsfwVolumeTable::CancelTransferL(TDesC& aFilePath) + { + DEBUGSTRING16(("CRsfwVolumeTable::CancelTransferL for %S", &aFilePath)); + // get the volume id for this path + TParse parser; + parser.Set(aFilePath, NULL, NULL); + if (!(parser.DrivePresent())) + { + return KErrArgument; + } + TPtrC drive = parser.Drive(); + CRsfwVolume* volume = VolumeByDriveLetter(drive[0]); + if (!volume) + { + return KErrNotFound; + } + + if (!(parser.NamePresent())) + { + // this is not a file + return KErrArgument; + } + + + // mark the file entry as "cancelled" + TPtrC pathPtr = aFilePath.Right(aFilePath.Length() - 2); //drop the drive letter + CRsfwFileEntry* targetFid = volume->iFileEngine->FetchFep(pathPtr); + if (targetFid) + { + DEBUGSTRING(("setting KNodeWritingCancelled for fid %d", targetFid->Fid().iNodeId)); + targetFid->SetFlags(KNodeWritingCancelled); + } + + volume->iFileEngine->CancelTransactionL(aFilePath); + + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwVolumeTable::IsMountIdle() +// +// ---------------------------------------------------------------------------- +// +TBool CRsfwVolumeTable::IsMountIdle(TRsfwMountStatus& aMountStatus) + { + if (aMountStatus.iMountState != KMountStateDormant + || aMountStatus.iConnectionState == KMountConnecting) + { + return EFalse; + } + else + { + return ETrue; + } + } diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwwaitnotemanager.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwwaitnotemanager.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,564 @@ +/* +* Copyright (c) 2005 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Global wait notes used in Remote File Engine +* +*/ + + +// INCLUDE FILES +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "rsfwwaitnotemanager.h" +#include "rsfwrfeserver.h" +#include "sysutil.h" +#include "mdebug.h" + + +// ============================ MEMBER FUNCTIONS =============================== + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::CRsfwWaitNoteManager +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwWaitNoteManager::CRsfwWaitNoteManager() : + CActive( CActive::EPriorityUserInput ) + { + + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ConstructL +// Symbian 2nd phase constructor can leave. +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ConstructL() + { + DEBUGSTRING(("CRsfwWaitNoteManager::ConstructL")); + CActiveScheduler::Add( this ); + iOpState = ERemoteWaitNoteStateOk; + + // read wait note txt:s from the localization file + TFileName resourceFile; + resourceFile.Copy(KResourceFile); + BaflUtils::NearestLanguageFile(CRsfwRfeServer::Env()->iFs,resourceFile); + + DEBUGSTRING16(("opening resource file '%S'", &resourceFile)); + iResourceFile.OpenL(CRsfwRfeServer::Env()->iFs, resourceFile); + iResourceFile.ConfirmSignatureL(); + DEBUGSTRING(("resource file ok")); + + // pre-read the most common strings + HBufC8* warningNoteLabel = iResourceFile.AllocReadL(R_WAIT_NOTE_DISC_WARNING); + CleanupStack::PushL(warningNoteLabel); + iResourceReader.SetBuffer(warningNoteLabel); + iNoteTxt = iResourceReader.ReadHBufCL(); + CleanupStack::PopAndDestroy(warningNoteLabel); + + iAvkonNoteId = 0; + + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::NewL() +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +EXPORT_C CRsfwWaitNoteManager* CRsfwWaitNoteManager::NewL() + { + CRsfwWaitNoteManager* self = new ( ELeave ) CRsfwWaitNoteManager(); + + CleanupStack::PushL( self ); + self->ConstructL(); + CleanupStack::Pop(); + + return self; + } + +// ----------------------------------------------------------------------------- +// Destructor +// ----------------------------------------------------------------------------- +// +EXPORT_C CRsfwWaitNoteManager::~CRsfwWaitNoteManager() + { + Deque(); + iResourceFile.Close(); + + + if (iNoteTxt) + { + delete iNoteTxt; + } + if (iAuthRequest) + { + delete iAuthRequest; + } + + if (iGlobalNoteRequest) + { + delete iGlobalNoteRequest; + } + + if (iSaveToRequest) + { + delete iSaveToRequest; + iSaveToRequest = NULL; + } + + iNotifier.Close(); + + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::StartWaitNoteL +// Start to display a wait note. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CRsfwWaitNoteManager::StartWaitNoteL( + TRemoteOperationType aOpType, + CRsfwWaitNoteStateMachine* aOperation) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::StartWaitNoteL")); + + // It is possible that when this function is called there already is + // a wait note. In this case we allow the new operation and its wait note + // to override the ongoing concurrent operation's wait note. + // However, we want to protect some dialogs. + // These are + // 1) Wait note when uploading a file + // The reason for this is that the wait note is in fact the only indication + // the user gets about the status of writing a file to the server. + // 2) User query when uploading failed and we need to give time to read + // the dialogs about selecting a new location from a local media + if (!((iOpState == ERemoteWaitNoteStateInProgress) && (iOpType == ERemoteSaveToLocal))) + { + iOperation = aOperation; + + // cancel whatever is there currently + CancelWaitNoteL(iNoteId); + + DEBUGSTRING16(("CRsfwWaitNoteManager::CancelWaitNoteL returned")); + + // don't make asynchronous request when there has been already any! + if(!IsActive()) + { + if (aOpType <= ERemoteSaveToLocal) + { + DEBUGSTRING16(("calling iNotifier.Connect()")); + User::LeaveIfError(iNotifier.Connect()); + DEBUGSTRING16(("called iNotifier.Connect()")); + } + + switch( aOpType ) + { + // these "basic request" pass the method and drive friendly name + // drive friendly name is not needed for wait notes, only for retryrequest + // so there could be even more simple IPC struct without it + // (on the other hand, current param struct would easily allow showing the friendly name + // with the wait notes) + case ERemoteOpConnecting: + case ERemoteOpDirDownloading: + case ERemoteUnavailableRetry: + { + iNotifier.StartNotifierAndGetResponse(iStatus, KRsfwNotifierPluginUID, + *iGlobalNoteRequest, *iGlobalNoteRequest); + } + break; + case ERemoteWarnDisconnect: + { + CAknGlobalConfirmationQuery* iQuery = CAknGlobalConfirmationQuery::NewL(); + iQuery->ShowConfirmationQueryL(iStatus, *iNoteTxt); + break; + } + case ERemoteOpAuthDialog: + { + DEBUGSTRING16(("calling ERemoteOpAuthDialog/ERemoteUnavailableRetry")); + // same struct used for input and output params. + iNotifier.StartNotifierAndGetResponse(iStatus, KRsfwNotifierPluginUID, + *iAuthRequest, *iAuthRequest); + break; + } + + case ERemoteSaveToLocal: + DEBUGSTRING16(("calling ERemoteOpAuthDialog/ERemoteSaveToLocal")); + iNotifier.StartNotifierAndGetResponse(iStatus, KRsfwNotifierPluginUID, + *iSaveToRequest, *iSaveToRequest); + break; + } + + DEBUGSTRING16(("CRsfwWaitNoteManager calling SetActive()")); + SetActive(); + + + DEBUGSTRING16(("CRsfwWaitNoteManager::StartWaitNoteL function returns")); + iOpType = aOpType; + iOpState = ERemoteWaitNoteStateInProgress; + return ++iNoteId; + } + else + { + DEBUGSTRING16(("CRsfwWaitNoteManager::StartWaitNoteL attempt to make request when object is active")); + DEBUGSTRING16(("CRsfwWaitNoteManager::StartWaitNoteL function returns 0")); + return 0; // caller didn't "get" the note + } + } + else + { + DEBUGSTRING16(("CRsfwWaitNoteManager::StartWaitNoteL function returns 0")); + return 0; // caller didn't "get" the note + } + } + + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::CancelWaitNote +// Cancel a wait note. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::CancelWaitNoteL(TInt aNoteId) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::CancelWaitNoteL, iOpState = %d, iOpType = %d", iOpState, iOpType)); + // Cancel a wait note if there is one and it is the same one that + // the caller thinks it is removing... + if ( (iOpState == ERemoteWaitNoteStateInProgress ) && (aNoteId == iNoteId)) + { + + if (iOpType <= ERemoteSaveToLocal) + { + // notifier plugin dialogs + User::LeaveIfError(iNotifier.CancelNotifier(KRsfwNotifierPluginUID)); + iNotifier.Close(); + } + + + // Dismiss qlobal query + if ( iQuery ) + { + iQuery->CancelConfirmationQuery(); + delete iQuery; + iQuery = NULL; + } + + + + iOpState = ERemoteWaitNoteStateOk; + } + + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::RunL +// Handles an active object’s request completion event. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::RunL() + { + DEBUGSTRING16(("CRsfwWaitNoteManager::RunL, status=%d, optype=%d", iStatus.Int(), iOpType)); + CancelWaitNoteL(iNoteId); + + TInt errorCode = iStatus.Int(); + + switch (iOpType) + { + case ERemoteWarnDisconnect: + if (iStatus == EAknSoftkeyYes) + { + errorCode = KErrNone; + } + else + { + errorCode = KErrCancel; + } + break; + case ERemoteOpAuthDialog: + iAuthCredentials->iUserName = (*iAuthRequest)().iUserName; + iAuthCredentials->iPassword = (*iAuthRequest)().iPassword; + delete iAuthRequest; + iAuthRequest = NULL; + break; + case ERemoteUnavailableRetry: + case ERemoteOpConnecting: + case ERemoteOpDirDownloading: + delete iGlobalNoteRequest; + iGlobalNoteRequest = NULL; + break; + case ERemoteSaveToLocal: + iSaveParams->iFileName = (*iSaveToRequest)().iFileName; + delete iSaveToRequest; + iSaveToRequest = NULL; + break; + } + + if (iOperation) // is some operation waiting for info about this wait note? + { + if (((iOpType == ERemoteOpDirDownloading) || (iOpType == ERemoteOpConnecting)) + && (errorCode == KErrCancel)) + { + DEBUGSTRING16(("calling iOperation->CancelTransaction()")); + // we received from the dialog information that user wants to cancel + // call CancelTransaction on the access protocol module + // this then must cancel our pending transaction + // so we finally get to the ErrorL() state of the state machine + iOperation->CancelTransaction(); + } + + else + { + DEBUGSTRING16(("calling iOperation->HandleRemoteAccessResponse()")); + iOperation->HandleRemoteAccessResponse(0, errorCode); + } + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteManager::RunError +// ---------------------------------------------------------------------------- +// +TInt CRsfwWaitNoteManager::RunError(TInt /*aError*/) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::RunError")); + return KErrNone; + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::DoCancel +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::DoCancel() + { + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowAddressNotFoundErrorL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowAddressNotFoundErrorL( + const TDesC& aFriendlyName) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ShowAddressNotFoundErrorL (drive '%S')", &aFriendlyName)); + RResourceFile resourceFile; + TResourceReader resourceReader; + + // get the name of the localized resource file + TFileName resourceFileName; + resourceFileName.Copy(KResourceFile); + BaflUtils::NearestLanguageFile(CRsfwRfeServer::Env()->iFs,resourceFileName); + + DEBUGSTRING16(("opening resource file '%S'", &resourceFileName)); + // read localized string from resource file + resourceFile.OpenL(CRsfwRfeServer::Env()->iFs, resourceFileName); + CleanupClosePushL(resourceFile); + resourceFile.ConfirmSignatureL(); + DEBUGSTRING(("resource file ok")); + HBufC8* noteBuffer = resourceFile.AllocReadLC(R_NOTE_ADDRESS_NOT_AVAILABLE); + resourceReader.SetBuffer(noteBuffer); + HBufC* noteText = resourceReader.ReadHBufCL(); + CleanupStack::PushL(noteText); + + // S60 .loc formatting + HBufC* formattedText = HBufC::NewLC(noteText->Length() + aFriendlyName.Length()); + TPtr fprt = formattedText->Des(); + StringLoader::Format(fprt, *noteText , -1, aFriendlyName); + + // error dialog + CAknGlobalNote* errorDialog = CAknGlobalNote::NewLC(); + errorDialog->ShowNoteL(EAknGlobalErrorNote, *formattedText); + CleanupStack::PopAndDestroy(5); // resourceFile, noteBuffer, noteText, formattedText, errordialog + } + + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::SetAuthenticationDialogL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::SetAuthenticationDialogL(TRsfwAuthenticationDlgRequest& aAuthRequest) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::SetAuthenticationDialogL")); + if (iAuthRequest) + { + delete iAuthRequest; + iAuthRequest = NULL; + } + iAuthRequest = new (ELeave) TRsfwAuthParamsPckg(); + + (*iAuthRequest)() = aAuthRequest; + iAuthCredentials = &aAuthRequest; + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::SetGlobalNoteRequestL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::SetGlobalNoteRequestL(TRsfwNotPluginRequest& aRequestStruct) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::SetGlobalNoteRequestL")); + if (iGlobalNoteRequest) + { + delete iGlobalNoteRequest; + iGlobalNoteRequest = NULL; + } + + iGlobalNoteRequest = new (ELeave) TRsfwRetryParamsPckg(); + (*iGlobalNoteRequest)() = aRequestStruct; + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::SetSaveToDialogRequestL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::SetSaveToDialogRequestL(TRsfwSaveToDlgRequest& aSaveToRequest) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::SetSaveToDialogRequestL")); + if (iSaveToRequest) + { + delete iSaveToRequest; + iSaveToRequest = NULL; + } + + iSaveToRequest = new (ELeave) TRsfwSaveToParamsPckg(); + + (*iSaveToRequest)() = aSaveToRequest; + iSaveParams = &aSaveToRequest; + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowFileSavedToDialogL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowFileSavedToDialogL(const TDesC& aPath ) + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ShowFileSavedToDialogL")); + HBufC8* textbuffer = iResourceFile.AllocReadL(R_CONFIRM_FILE_SAVED_TO); + CleanupStack::PushL(textbuffer); + iResourceReader.SetBuffer(textbuffer); + HBufC* text = iResourceReader.ReadHBufCL(); + CleanupStack::PushL(text); + HBufC* formattedText = NULL; + + // extract the path + TParse parser; + parser.Set(aPath, NULL, NULL); + // try to get localized path + CDirectoryLocalizer* localizer = CDirectoryLocalizer::NewL(); + CleanupStack::PushL(localizer); + // S60 localizer requires also drive letter, + // i.e. matches are like C:\\Data\\Images + localizer->SetFullPath(parser.DriveAndPath()); + TPtrC localizedName = localizer->LocalizedName(); + + if (localizedName != KNullDesC) + { + formattedText = HBufC::NewMaxLC(text->Length() + + localizedName.Length()); + + TPtr formatPtr(formattedText->Des()); + StringLoader::Format(formatPtr, *text, -1, localizedName); + } + else + { + formattedText = HBufC::NewMaxLC(text->Length() + + aPath.Length()); + + TPtr formatPtr(formattedText->Des()); + StringLoader::Format(formatPtr, *text, -1, parser.Path()); + } + + + CAknGlobalNote* dlg = CAknGlobalNote::NewLC(); + dlg->ShowNoteL(EAknGlobalInformationNote, *formattedText ); + CleanupStack::PopAndDestroy(5); // textbuffer, text, localizer, formattedtext, dlg + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowFailedSaveNoteL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowFailedSaveNoteL() + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ShowFailedSaveNoteL")); + ShowGlobalInformationNoteL(R_SAVING_FAILED); + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowFailedSaveNoteL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowNoNetworkCoverageNoteL() + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ShowNoNetworkCoverageNoteL")); + ShowGlobalInformationNoteL(R_NO_NETWORK_COVERAGE); + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowOfflineNotPossibleNoteL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowOfflineNotPossibleNoteL() + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ShowOfflineNotPossibleNoteL")); + ShowGlobalInformationNoteL(R_OFFLINE_NOT_POSSIBLE); + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowOutOfMemoryNoteL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowOutOfMemoryNoteL() + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ShowOutOfMemoryNoteL")); + ShowGlobalInformationNoteL(R_RAM_OUT_OF_MEMORY); + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ShowGlobalInformationNoteL +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ShowGlobalInformationNoteL(TInt aResourceId) + { + HBufC8* textbuffer = iResourceFile.AllocReadL(aResourceId); + CleanupStack::PushL(textbuffer); + iResourceReader.SetBuffer(textbuffer); + HBufC* text = iResourceReader.ReadHBufCL(); + CleanupStack::PushL(text); + CAknGlobalNote* dlg = CAknGlobalNote::NewLC(); + dlg->ShowNoteL(EAknGlobalInformationNote, *text ); + CleanupStack::PopAndDestroy(3); // textBuffer, text, dlg + } + +// ----------------------------------------------------------------------------- +// CRsfwWaitNoteManager::ResetOperation +// ----------------------------------------------------------------------------- +// +void CRsfwWaitNoteManager::ResetOperation() + { + DEBUGSTRING16(("CRsfwWaitNoteManager::ResetOperation")); + iOperation = NULL; + } + +// ----------------------------------------------------------------------------- + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefileengine/src/rsfwwaitnotestatemachine.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefileengine/src/rsfwwaitnotestatemachine.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,133 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: States that use a global wait dialog +* +*/ + + +#include "rsfwwaitnotestatemachine.h" +#include "rsfwvolumetable.h" +#include "rsfwwaitnotemanager.h" +#include "rsfwfileengine.h" +#include "rsfwvolume.h" +#include "mdebug.h" + + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::CancelTransaction +// ---------------------------------------------------------------------------- +// +void CRsfwWaitNoteStateMachine::CancelTransaction() + { + //if ((iTransactionId > 0) && FileEngine()) + if (FileEngine()) + { + if ((iTransactionId > 0)) + { + // with cancelled global wait notes the operation is + // completed via access protocol Cancel + // that is transaction is cancelled and the operation state machine + // receives KErrCancel callback + FileEngine()->CancelTransaction(iTransactionId); + } + else + { + HandleRemoteAccessResponse(0, KErrCancel); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::ShowWaitNoteL +// ---------------------------------------------------------------------------- +// +void CRsfwWaitNoteStateMachine::ShowWaitNoteL(TRemoteOperationType aOperationType) + { + if (FileEngine() && FileEngine()->Volume()) + { + switch (aOperationType) + { + case ERemoteOpConnecting: + iGlobalWaitNoteRequest.iMethod = TRsfwNotPluginRequest::EConnectingDlg; + break; + case ERemoteOpDirDownloading: + iGlobalWaitNoteRequest.iMethod = TRsfwNotPluginRequest::EFetchingDlg; + break; + case ERemoteUnavailableRetry: + iGlobalWaitNoteRequest.iMethod = TRsfwNotPluginRequest::EUnavailableRetryDlg; + break; + } + Volumes()->WaitNoteManager()->SetGlobalNoteRequestL(iGlobalWaitNoteRequest); + iNoteId = Volumes()->WaitNoteManager() + ->StartWaitNoteL(aOperationType, this); + } + else + {// show note if Uri info not available + iNoteId = Volumes()->WaitNoteManager()->StartWaitNoteL(aOperationType, this); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::DeleteWaitNoteL +// ---------------------------------------------------------------------------- +// +void CRsfwWaitNoteStateMachine::DeleteWaitNoteL(TBool aCancelOpWait) + { + DEBUGSTRING16(("CRsfwWaitNoteStateMachine::DeleteWaitNoteL")); + if (aCancelOpWait) + { + // let the wait note manager know that we are not expecting any event anymore + Volumes()->WaitNoteManager()->ResetOperation(); + } + if (iNoteId > 0) + { + Volumes()->WaitNoteManager()->CancelWaitNoteL(iNoteId); + iNoteId = 0; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::ErrorOnStateEntry +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwWaitNoteStateMachine::ErrorOnStateEntry(TInt aError) + { + TRAP_IGNORE(DeleteWaitNoteL(ETrue)); + return CRsfwRfeStateMachine::ErrorOnStateEntry(aError); + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::ErrorOnStateExit +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwWaitNoteStateMachine::ErrorOnStateExit(TInt aError) + { + TRAP_IGNORE(DeleteWaitNoteL(ETrue)); + return CRsfwRfeStateMachine::ErrorOnStateExit(aError); + } + +// ---------------------------------------------------------------------------- +// CRsfwWaitNoteStateMachine::CompleteRequestL +// ---------------------------------------------------------------------------- +// +CRsfwRfeStateMachine::TState* CRsfwWaitNoteStateMachine::CompleteRequestL( + TInt aError) + { + CompleteAndDestroyState()->SetErrorCode(aError); + DeleteWaitNoteL(ETrue); + return CompleteAndDestroyState(); + } + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/bwins/eremotefsu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/bwins/eremotefsu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,3 @@ +EXPORTS + CreateFileSystem @ 1 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/eabi/eremotefsu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/eabi/eremotefsu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,13 @@ +EXPORTS + CreateFileSystem @ 1 NONAME + _ZTI12CRsfwFsDirCB @ 2 NONAME DATA 12 ; ## + _ZTI13CRsfwFsFileCB @ 3 NONAME DATA 12 ; ## + _ZTI14CRsfwFsMountCB @ 4 NONAME DATA 12 ; ## + _ZTI15CRsfwFileSystem @ 5 NONAME DATA 12 ; ## + _ZTI15CRsfwFsFormatCB @ 6 NONAME DATA 12 ; ## + _ZTV12CRsfwFsDirCB @ 7 NONAME DATA 44 ; ## + _ZTV13CRsfwFsFileCB @ 8 NONAME DATA 68 ; ## + _ZTV14CRsfwFsMountCB @ 9 NONAME DATA 152 ; ## + _ZTV15CRsfwFileSystem @ 10 NONAME DATA 76 ; ## + _ZTV15CRsfwFsFormatCB @ 11 NONAME DATA 40 ; ## + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,21 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Controls building of Remote file System plug-in. +* +*/ + +PRJ_MMPFILES +eremotefs.mmp + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/group/eremotefs.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/group/eremotefs.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,57 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project Remote File System plug-in +* +*/ + + +#include +// Capabilities of File Server process +CAPABILITY TCB ProtServ DiskAdmin AllFiles PowerMgmt CommDD + +TARGET eremotefs.fsy +TARGETTYPE fsy +UID 0x100039df 0x101F9768 +TARGETPATH /system/libs + +SOURCEPATH ../src +SOURCE rsfwfs.cpp +SOURCE rsfwfsdircb.cpp +SOURCE rsfwfsfilecb.cpp +SOURCE rsfwfilesystem.cpp +SOURCE rsfwfsformatcb.cpp +SOURCE rsfwfsmountcb.cpp + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +SYSTEMINCLUDE /epoc32/include/libc +USERINCLUDE ../inc + +LIBRARY euser.lib +LIBRARY efile.lib +LIBRARY efsrv.lib +LIBRARY estor.lib +LIBRARY rsfwsession.lib + +START WINS +BASEADDRESS 0x63000000 +END + +unpagedcode + +DEFFILE eremotefs.def + +// End of File + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/inc/rsfwfilesystem.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/inc/rsfwfilesystem.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,131 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File System Plug-in implementation +* +*/ + + +#ifndef CRSFWFILESYSTEM_H +#define CRSFWFILESYSTEM_H + +#include + + +/** + * Classes that a plug-in file system must implement. + * + * A plug-in filesystem must implement CFileSystem, which is a factory + * class for a file system. That class must create objects derived from + * CMountCB, CFileCB, CDirCB and CFormatCB. These are defined in f32fsys.h + * + * @lib eremotefs.fsy + * @since Series 60 3.2 + */ +class CRsfwFileSystem : public CFileSystem + { +public: // Constructors and destructor + /** + * Static constructor. + */ + static CRsfwFileSystem* New(); + + /** + * Constructor. + */ + CRsfwFileSystem(); + + /** + * Destructor. + */ + ~CRsfwFileSystem(); + +public: // Functions from base class + /** + * From CFileSystem Installs the file system. + * @since Series 60 3.2 + * @return + */ + TInt Install(); + + /** + * From CFileSystem Creates a new mount control block. + * @since Series 60 3.2 + * @return A pointer to the new mount object. + */ + CMountCB* NewMountL() const; + + /** + * From CFileSystem Creates a new file control block. + * @since Series 60 3.2 + * @return A pointer to the new file object. + */ + CFileCB* NewFileL() const; + + /** + * From CFileSystem Creates a new directory control block. + * @since Series 60 3.2 + * @return A pointer to the new directory object. + */ + CDirCB* NewDirL() const; + + /** + * From CFileSystem Creates a new volume format control block. + * @since Series 60 3.2 + * @return A pointer to the new volume format object. + */ + CFormatCB* NewFormatL() const; + + /** + * From CFileSystem Retrieves drive information. + * @since Series 60 3.2 + * @param anInfo On return, contains the drive information. + * @param aDriveNumber The drive number. + * @return + */ + void DriveInfo(TDriveInfo& anInfo,TInt aDriveNumber) const; + + /** + * From CFileSystem Returns the default path for the file system. + * @since Series 60 3.2 + * @param aPath On return, contains the default path. + * @return KErrNone or an appropriate error code when the default path + * cannot be supplied. + */ + TInt DefaultPath(TDes& aPath) const; + + + /** + * From CFileSystem Does clean up before the filesystem is destroyed. + * @since Series 60 3.2 + * @return An error code. + */ + TInt Remove(); + +private: + /** + * Creates a new mount control block. + * @since Series 60 3.2 + * @return A pointer to the new mount object. + */ + CMountCB* NewRemoteFsMountL(); + +public: // Data + // unique id of the file system + TUint iUniqueID; + + }; + +#endif // CRSFWFILESYSTEM_H + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/inc/rsfwfsdircb.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/inc/rsfwfsdircb.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,119 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File System Plug-in implementation +* +*/ + + +#ifndef CRSFWFSDIRCB_H +#define CRSFWFSDIRCB_H + +// INCLUDES +#include +#include +//#include "rsfwsession.h" +#include "rsfwinterface.h" + +// CONSTANTS + +// DATA TYPES + +// FORWARD DECLARATIONS + +// CLASS DECLARATIONS + +/** + * Classes that a plug-in file system must implement. A plug-in + * filesystem must implement CFileSystem, which is a factory class for + * a file system. That class must create objects derived from CMountCB, + * CFileCB, CDirCB and CFormatCB. These are defined in f32fsys.h + * + * @lib eremotefs.fsy + * @since Series 60 3.2 + */ +class CRsfwFsDirCB : public CDirCB + { +public: // Constructors and destructor + + /** + * Static constructor. + */ + static CRsfwFsDirCB* NewL(); + + /** + * Destructor. + */ + ~CRsfwFsDirCB(); + +public: // New functions + + /** + * Prepares the class to read directory entries from a local cache container file + * @since Series 60 3.2 + * @param aPath path of the directory container in the local cache + * @param aName the entries to be read from the directory, for example, "*" + * @return + */ + void SetDirL( const TDesC& aPath, + const TDesC& aName ); + +public: // Functions from base classes + + /** + * From CDirCB Gets information from the first suitable entry in the directory, + * starting from the current read position. + * @since Series 60 3.2 + * @param anEntry Entry information object. + * @return + */ + void ReadL( TEntry& anEntry ); + +private: + + /** + * C++ default constructor. + */ + CRsfwFsDirCB(); + +public: // Data + + // the Fid of this dir + TFid iThisFid; + +private: // Data + + // stream attached to the local cache container file + RFileReadStream iDirContReadStream; + + // the entries to be read from the directory, for example, "*" + HBufC* iMatch; + + // whether the cache container includes the contents the directory + TBool iHasBeenFetched; + + // which entry position to read next + TInt iEntryPos; + + // at which stream position to read next + TStreamPos iStreamPos; + + // where to read if we must re-read the last entry to be read + TStreamPos iPendingPos; + + }; + +#endif // CRSFWFSDIRCB_H + +// End of File + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/inc/rsfwfsfilecb.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/inc/rsfwfsfilecb.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,190 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File System Plug-in implementation +* +*/ + + +#ifndef CRSFWFSFILECB_H +#define CRSFWFSFILECB_H + +// INCLUDES +#include +#include "rsfwinterface.h" + +/** + * Classes that a plug-in file system must implement. A plug-in + * filesystem must implement CFileSystem, which is a factory class for + * a file system. That class must create objects derived from CMountCB, + * CFileCB, CDirCB and CFormatCB. These are defined in f32fsys.h + * + * @lib eremotefs.fsy + * @since Series 60 3.2 + */ +class CRsfwFsFileCB : public CFileCB + { +public: // Constructors and destructor + + /** + * Constructor. + */ + CRsfwFsFileCB(); + + /** + * Destructor. + */ + ~CRsfwFsFileCB(); + +public: // New functions + + /** + * Prepares the class to read file from a local cache file + * @since Series 60 3.2 + * @param aPath path of the cache file + * @return + */ + void SetContainerFileL( const TDesC& aPath); + +public: // Functions from base class + + /** + * From CFileCB Renames the file with the full file name provided. + * @since Series 60 3.2 + * @param aNewName The new full name of the file. + * @return + */ + void RenameL( const TDesC& aNewName ); + + /** + * From CFileCB Reads from an open file + * @since Series 60 3.2 + * @param aPos Represents a position relative to the start of the file + * where ReadL() starts to read. + * @param aLength On entry, specifies the number of bytes to be read + * from the file. On return, contains the number of bytes + * read, but this is not valid if the function leaves. + * @param aDes Pointer to a descriptor into which the data is written. + * @param aMessage The client request. + * @return + */ + void ReadL( TInt aPos, + TInt& aLength, + const TAny* aDes, + const RMessagePtr2& aMessage ); + + /** + * From CFileCB Writes to an open file + * @since Series 60 3.2 + * @param aPos Represents a position relative to the start of the file + * where WriteL() starts to write. + * @param aLength Specifies the number of bytes to be written to the file. + * On return, the number of bytes written, but this is not + * valid if the function leaves. + * @param aDes Pointer to a descriptor containing the data to be written + * to the file. + * @param aMessage The client request. + * @return + */ + void WriteL( TInt aPos, + TInt& aLength, + const TAny* aDes, + const RMessagePtr2& aMessage ); + + /** + * From CFileCB Extends or truncates the file by re-setting the file size. + * @since Series 60 3.2 + * @param aSize The new file size in number of bytes. + * @return + */ + void SetSizeL( TInt aSize ); + + /** + * From CFileCB Sets the attribute mask and the modified time of the file. + * @since Series 60 3.2 + * @param aTime The new modified time, if the modified flag is set in aMask. + * @param aMask Bit mask containing bits set (to 1) that are to be set (to 1) + * in iAtt. + * @param aVal Bitmask containing bits set (to 1) that are to be unset (to 0) + * in iAtt. + * @return + */ + void SetEntryL(const TTime& aTime,TUint aMask,TUint aVal); + + + /** + * From CFileCB Flushes, to disk, the cached information necessary for + * the integrity of recently written data, such as the file size. + * @since Series 60 3.2 + * @return + */ + void FlushDataL(); + + /** + * From CFileCB Flushes, to disk, all cached file data (e.g. attributes, + * modification time, file size). + * @since Series 60 3.2 + * @return + */ + void FlushAllL(); + + +public: // Data + // the fid of this file + TFid iThisFid; + + // the fid of the parent, needed for rename + TFid iParentFid; + + // If flush returned an error, we do not attempt to write the file to server in close() + // either, unless new data is written to the cache file. We assume that the application + // has handled the flush error, also this is required for example to make File Manager UI + // to work correctly (if user presses cancel when flushing), writing should be cancelled. + TBool iLastFlushFailed; + + +private: // Data + // open file handle on the cache file + RFile iContFile; + + // the path of the local cache + TBuf iCachePath; + + // cached size bookkeeping + TInt iCachedSize; + + // indicates whether a file was fetched to the local cache before writing + TBool iFetchedBeforeWriting; + + // some varibles needed when flushing a big file + // in continuous parts (currently used in File + // Manager copy). + + // how much already has been flushed + TInt iFlushedSize; + + // how much has been written to since the file was opened + TInt iWrittenSize; + + // the total size of the file, reported by client + // via RFile::SetSize() + TInt iReportedSize; + + // does the server support writing the file partially + // assumed to be true unless we get KErrNotSupported + TBool iPartialWriteSupported; + }; + +#endif // CRSFWFSFILECB_H + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/inc/rsfwfsformatcb.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/inc/rsfwfsformatcb.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,63 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File System Plug-in implementation +* +*/ + + +#ifndef CRSFWFSFORMATCB_H +#define CRSFWFSFORMATCB_H + +// INCLUDES +#include + +/** + * Classes that a plug-in file system must implement. A plug-in + * filesystem must implement CFileSystem, which is a factory class for + * a file system. That class must create objects derived from CMountCB, + * CFileCB, CDirCB and CFormatCB. These are defined in f32fsys.h + * + * @lib eremotefs.fsy + * @since Series 60 3.2 + */ + +// --------------------------------------------------------------------- +// CRsfwFsFormatCB +// --------------------------------------------------------------------- +class CRsfwFsFormatCB : public CFormatCB + { +public: // Constructors and destructor + + /** + * Constructor. + */ + CRsfwFsFormatCB(); + + /** + * Destructor. + */ + ~CRsfwFsFormatCB(); + +public: // Functions from base classes¨ + /** + * From CFormatCB Performs a formatting step on the drive. + * @since Series 60 3.2 + * @return + */ + void DoFormatStepL(); + }; + +#endif // CRSFWFSFORMATCB_H + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/inc/rsfwfsmountcb.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/inc/rsfwfsmountcb.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,386 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Remote File System Plug-in implementation +* +*/ + + +#ifndef CRSFWFSMOUNTCB_H +#define CRSFWFSMOUNTCB_H + +// INCLUDES +#include +#include "rsfwsession.h" +#include "rsfwinterface.h" + +class CRsfwFileSystem; + +// CLASS DECLARATIONS + +/** + * Classes that a plug-in file system must implement. A plug-in + * filesystem must implement CFileSystem, which is a factory class for + * a file system. That class must create objects derived from CMountCB, + * CFileCB, CDirCB and CFormatCB. These are defined in f32fsys.h + * + * @lib eremotefs.fsy + * @since Series 60 3.2 + */ +class CRsfwFsMountCB : public CMountCB + { +public: // Constructors and destructor + + /** + * Static constructor. + */ + static CRsfwFsMountCB* NewL(); + + /** + * Destructor. + */ + ~CRsfwFsMountCB(); + +public: // New functions + + + /** + * Renames a file. + * @since Series 60 3.2 + * @param aDirFid fid of the parent directory of the file to be renamed + * @param aSourceName A reference to a descriptor containing the name + * of the file to be renamed. + * @param aNewName A reference to a descriptor containing the new full entry + * name for the entry to be renamed. + * @return + */ + void RenameFidL( TFid aDirFid, + const TDesC& aSourceName, + const TDesC& aNewName ); + + + /** + * Returnes a handle to the Remote File Engine session + * @since Series 60 3.1 + * @return a session handle. + */ + RRsfwSession* RSessionL(); + + +public: // Functions from base classes + + /** + * From CMountCB Sets the mount control block properties. + * @since Series 60 3.2 + * @param aForceMount Indicates whether the properties of a corrupt + * volume should be stored. + * @return + */ + void MountL( TBool aForceMount ); + + /** + * From CMountCB Checks whether the mount control block represents the current mount on + * the associated drive. + * @since Series 60 3.2 + * @return KErrNone if the mount represented by this object is found to be + the current mount; + KErrGeneral if this object is found not to represent + the current mount; + otherwise one of the other sytem wide error codes. + */ + TInt ReMount( ); + + /** + * From CMountCB Carries out any clean-up necessary for a volume dismount. + * @since Series 60 3.2 + * @return + */ + void Dismounted( ); + + /** + * From CMountCB Gets volume information. + * @since Series 60 3.2 + * @param aVolume On return, a reference to the filled volume + * information object. + * @return + */ + void VolumeL( TVolumeInfo& aVolume ) const; + + + /** + * From CMountCB Sets the volume name for the mount. + * @since Series 60 3.2 + * @param aName A reference to a descriptor containing the new volume name. + * @return + */ + void SetVolumeL( TDes& aName ); + + /** + * From CMountCB Creates a new directory on the mount. + * @since Series60 3.2 + * @param aName A reference to a descriptor containing the full name of + the directory to be created. + * @return + */ + void MkDirL( const TDesC& aName ); + + /** + * From CMountCB Removes the directory specified by aName from the volume. + * @since Series60 3.2 + * @param aName A reference to a descriptor containing the full name of + the directory to be removed. + * @return + */ + void RmDirL( const TDesC& aName ); + + /** + * From CMountCB Deletes the specified file from the mount. + * @since Series60 3.2 + * @param aName A reference to a descriptor containing the full path name + of the file that will be removed. + * @return + */ + void DeleteL( const TDesC& aName ); + + /** + * From CMountCB Renames or moves a single file or directory on the mount. + * @since Series60 3.2 + * @param anOldName A reference to a descriptor containing the full entry + * name of the entry to be renamed. + * @param anNewName A reference to a descriptor containing the new full entry + * name for the entry to be renamed. + * @return + */ + void RenameL( const TDesC& anOldName, + const TDesC& aNewName ); + + /** + * From CMountCB Replaces one file on the mount with another. + * @since Series60 3.2 + * @param anOldName A reference to a descriptor containing the full file name + * of the file to replace the file specified by anNewName + * @param anNewName A reference to a descriptor containing the new full file + * name for the entry to be replaced. + * @return + */ + void ReplaceL( const TDesC& anOldName, + const TDesC& aNewName ); + + + /** + * From CMountCB Gets the entry details for the specified file or directory. + * @since Series60 3.2 + * @param aName A reference to a descriptor containing the full name of + * the entry whose details are required. + * @param anEntry On return, a reference to the filled entry object. + * @return + */ + void EntryL( const TDesC& aName, + TEntry& anEntry ) const; + + /** + * From CMountCB Sets entry details for a specified file or directory. + * @since Series60 3.2 + * @param aName A reference to a descriptor containing the full name of + * the entry to be updated. + * @param aTime A reference to the time object holding the new universal + * modified time for aName. + * @param aSetAttMask Attribute mask for setting the entry's attributes. + * @param aClearAttMask Attribute mask for clearing the entry's attributes. + * @return + */ + void SetEntryL( const TDesC& aName, + const TTime& aTime, + TUint aMask, + TUint aVal ); + + /** + * From CMountCB Opens a new or existing file on the mount. + * @since Series 60 3.2 + * @param aName The full name of the file that will be opened. + * @param aMode The file share mode. The following share modes are available: + * EFileShareExclusive; + * EFileShareReadersOnly; + * EFileShareAny; + * EFileStream; + * EFileStreamText; + * EFileRead; + * EFileWrite. + * @param anOpen Indicates how the file will be opened. It can be one of + * the following: + * EFileOpen; + * EFileCreate; + * EFileReplace. + * @param aFile Pointer to the file control block which will, on success, + * represent the open file. + * @return + */ + void FileOpenL( const TDesC& aName, + TUint aMode, + TFileOpen anOpen, + CFileCB* aFile ); + + /** + * From CMountCB Opens a directory on the mount. + * @since Series 60 3.2 + * @param aName A reference to a descriptor containing the full name of + the directory that will be opened. + * @param aDir Points to a directory control block which will, on success, + represent the open directory. + * @return + */ + void DirOpenL( const TDesC& aName, + CDirCB* aDir ); + + /** + * From CMountCB Gets the short name of the file or directory with + * the given full name. + * @since Series 60 3.2 + * @param aLongName A reference to a descriptor containing the full name + * of the entry. + * @param aShortName On return, a reference to a descriptor containing + * the short name of the entry. + * @return + */ + void GetShortNameL( const TDesC& aLongName, + TDes& aShortName ); + + /** + * From CMountCB Gets the long name of the file or directory associated with + * the given short name. + * @since Series 60 3.2 + * @param aShorName A reference to a descriptor containing the short name + * of the entry. + * @param aLongName On return, a reference to a descriptor containing + * the long name of the entry. + * @return + */ + void GetLongNameL( const TDesC& aShortName, + TDes& aLongName ); + + /** + * From CMountCB Reads a specified section of the file, regardless of the file's lock state. + * @since Series 60 3.2 + * @param aName A reference to a descriptor containing the full name of + * the file to be read from + * @param aPos The byte position to start reading from. + * @param aTrg A pointer to the buffer into which data is to be read. + * @param aLength The length of data to be read, in bytes. + * @param aMessage Client message. + * @return + */ + void ReadSectionL( const TDesC& aName, + TInt aPos,TAny* aTrg, + TInt aLength, + const RMessagePtr2& aMessage ); + + /** + * From CMountCB Reads the specified length of data from the specified position on + * the volume directly into the client thread. + * @since Series 60 3.2 + * @param aPos Start position in the volume for the read operation, + * in bytes. + * @param aLength The number of bytes to be read. + * @param aTrg A pointer to the buffer into which data is to be read. + * @param anOffset The offset at which to start adding data to the read buffer. + * @param aMessage Client message. + * @return + */ + void RawReadL( TInt64 aPos, + TInt aLength, + const TAny* aTrg, + TInt anOffset, + const RMessagePtr2& aMessage ) const; + + /** + * From CMountCB Writes a specified length of data from the client thread to the volume + * at the specified position. + * @since Series 60 3.2 + * @param aPos Start position in the volume for the write operation, + * in bytes. + * @param aLength The number of bytes to be written. + * @param aSrc Pointer to the buffer from which data will be written. + * @param anOffset The offset in the buffer at which to start writing data. + * @param aMessage Client message. + * @return + */ + void RawWriteL( TInt64 aPos, + TInt aLength, + const TAny* aSrc, + TInt anOffset, + const RMessagePtr2& aMessage ); + + /** + Checks the integrity of the file system on the volume and returns an + appropriate error value. + + @return KErrNone if the file system is stable; otherwise one of + the other system wide error codes. + */ + TInt CheckDisk(); + +private: + + /** + * C++ default constructor. + */ + CRsfwFsMountCB(); + + + /** + * Gets entry details for a file or directory + * @since Series 60 3.2 + * @param aName Name of the file or directory. + * @param anEntry On success, contains the entry details. + * @return + */ + void RemoteFsEntryL( const TDesC& aName, + TEntry& anEntry ); + + /** + * Fetches fid for a file or directory. + * @since Series 60 3.2 + * @param aPath The full path of the file or directory. + * @param aNodeType Type of the node (i.e. file or directory). + * @return + */ + TFid FetchFidL( const TDesC& aPath, + TUint aNodeType ); + + + + +public: // Data + // Server to which this mount is connected. + // The pointer is stored as volumename to CMountCB, + // which takes of the desc. ownership and deletes it. + HBufC* iServerName; + + // File Server session used to access the local cache. + RFs iFsSession; + +private: // Data + // Pointer to filesystem object. + CRsfwFileSystem* iRemoteFs; + + // Session to Remote File Engine + RRsfwSession* iSession; + + // Root Fid, can be different for different mounts + TFid iRootFid; + }; + +#endif // CRSFWFSMOUNTCB_H + +// End of File + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/src/rsfwfilesystem.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/src/rsfwfilesystem.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,223 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Factory class for a file system. Allows creating +* objects derived from CMountCB, CFileCB, CDirCB and CFormatCB. +* +*/ + + +#include "rsfwfilesystem.h" +#include +#include "rsfwfsfilecb.h" +#include "rsfwfsdircb.h" +#include "rsfwfsmountcb.h" +#include "rsfwfsformatcb.h" +#include "rsfwinterface.h" + +// ============================ MEMBER FUNCTIONS =============================== + +// static constructor +CRsfwFileSystem* CRsfwFileSystem::New() + { + // non-leaving new, NULL returned for failed creation + CRsfwFileSystem *self = new CRsfwFileSystem; + return self; + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::CRsfwFileSystem +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwFileSystem::CRsfwFileSystem() + { + } + +// Destructor +CRsfwFileSystem::~CRsfwFileSystem() + { + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::Install +// Installs the file system. + +// The function sets the name of the file system object through a call +// to CObject::SetName(), thus making it accessible, internally, +// using FileSystems->FindByFullName(). This enables the file server +// to find and handle installed file systems. The function also sets +// unique identifier for the file system and the file system version. +// The version is determined by the file system implementation. +// It is used in calls to CFileSystem::QueryVersionSupported(). +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CRsfwFileSystem::Install() + { + + iVersion = TVersion(KF32MajorVersionNumber, + KF32MinorVersionNumber, + KF32BuildVersionNumber); + + TTime timeID; + timeID.HomeTime(); + iUniqueID = I64LOW(timeID.Int64()); + + return (SetName(&KRemoteFSName)); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::Remove +// This is called just before the file system object is destroyed, and allows +// any clean up to be carried out. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CRsfwFileSystem::Remove() + { + + return KErrNone; + + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::NewMountL +// Creates a new remote mount control block, a CMountCB derived object. +// On success, a pointer to the new mount object is returned, +// otherwise the function leaves. +// +// This function is defined as a const function in the base class CFileSystem. +// However, we need to pass to the mount class modifiable pointers to +// the shared memory chunks used in the parameter passing. That's why we need +// to cast away const. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +CMountCB* CRsfwFileSystem::NewMountL() const + { + + return const_cast(this)->NewRemoteFsMountL(); + + } + + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::NewFileL +// Creates a new remote file control block, i.e. a CFileCB derived object. +// On success, a pointer to the new file object is returned, +// otherwise the function leaves. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +CFileCB* CRsfwFileSystem::NewFileL() const + { + return new(ELeave) CRsfwFsFileCB(); + } + + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::NewDirL +// Creates a new remote directory control block, i.e. a CDirCB derived object. +// On success, a pointer to the new directory control block is returned, +// otherwise the function leaves. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +CDirCB* CRsfwFileSystem::NewDirL() const + { + return(CRsfwFsDirCB::NewL()); + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::NewFormatL +// Creates a new remote volume format control block, i.e. a CFormatCB derived object. +// On success, a pointer to the new volume format control block is returned, +// otherwise the function leaves. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +CFormatCB* CRsfwFileSystem::NewFormatL() const + { + return new(ELeave) CRsfwFsFormatCB(); + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::DriveInfo +// Retrieves drive information. +// The function assumes that we are not handling different local drives, and +// sets anInfo.iMediaAtt, anInfo.iDriveAtt and anInfo.iType to values "sensible" +// for remote drives discarding the specified drive number. For local drives +// the function would obtain the necessary information by calling the appropriate +// TBusLocalDrive::Caps() function using the argument aDriveNumber. + +// Note that and anInfo.iBatteryState will already have been +// set by the calling function. + +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFileSystem::DriveInfo( + TDriveInfo& anInfo, + TInt /* aDriveNumber */) const + { + + anInfo.iType = EMediaRemote; + anInfo.iMediaAtt = KMediaAttVariableSize; + anInfo.iDriveAtt = KDriveAttRemote; + + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::NewRemoteFsMountL +// Creates a new remote mount control block, a CMountCB derived object. +// On success, a pointer to the new mount object is returned, +// otherwise the function leaves. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +CMountCB* CRsfwFileSystem::NewRemoteFsMountL() + { + + return CRsfwFsMountCB::NewL(); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFileSystem::DefaultPath +// Returns the default path for the file system. +// Always returns "C:\\". +// +// Each session with the file server has a current session path. +// When a new session is opened, its session path is set to the default path +// of the file server. At file server start-up, this default path is set to the +// default path returned by the local file system. +// The default implementation in the base class raises an "Fserv fault" 31 panic. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CRsfwFileSystem::DefaultPath( + TDes& aPath) const + { + + _LIT(KDefaultPath, "C:\\"); + aPath = KDefaultPath; + return (KErrNone); + + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/src/rsfwfs.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/src/rsfwfs.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,44 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Allows creating a Remote Storage FW file system plug-in from +* : a factory function. +* +*/ + + + +// INCLUDE FILES +#include "rsfwfilesystem.h" +#include "rsfwsession.h" +#include "rsfwinterface.h" + + +// ----------------------------------------------------------------------------- +// CreateFileSystem +// Implements factory function for creating new file systems. +// Allows creating a Remote Storage FW file system plug-in from this DLL. +// Returns: CRemoteFsFileSystem*: pointer to the Remote Storage FW file system +// plug-in main class +// ----------------------------------------------------------------------------- +// +extern "C" + { + EXPORT_C CFileSystem* CreateFileSystem() + { + + return(CRsfwFileSystem::New()); + + } + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/src/rsfwfsdircb.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/src/rsfwfsdircb.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,216 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File server interface class representing an open directory. +* The code in this class allows to access a specific +* remote directory. +* +*/ + + +// INCLUDE FILES +#include "rsfwfsdircb.h" +#include "rsfwfsmountcb.h" + +// ============================ MEMBER FUNCTIONS =============================== + +// static constructor +CRsfwFsDirCB* CRsfwFsDirCB::NewL() + { + CRsfwFsDirCB* remoteFsDirCB = new (ELeave) CRsfwFsDirCB; + return remoteFsDirCB; + } + +// ----------------------------------------------------------------------------- +// CRsfwFsDirCB::CRsfwFsDirCB +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwFsDirCB::CRsfwFsDirCB() + { + iHasBeenFetched = EFalse; + iEntryPos = 0; + iStreamPos = 0; + } + +// destructor +CRsfwFsDirCB::~CRsfwFsDirCB() + { + delete iMatch; + iDirContReadStream.Close(); + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsDirCB::ReadL +// File Server calls this function to retrieve one entry from open directory +// (next unread). When the last entry has been read, the function leaves with +// User::Leave(KErrEof). All of the properties of a TEntry, other than the UID +// types, are always read. The time stored in the iModified member of anEntry +// should be converted from UTC time to local time. When storing the iName +// member of anEntry, the current (.), or parent marker (..) in the directory +// should not be returned. +// +// If the KEntryAttAllowUid flag is set in the iAtt member of anEntry, then +// the entry UID type of an entry will be read. If, on reading the UID from +// a file, KErrCorrupt is generated, because the file is corrupt, +// ReadL() should not leave with this error message, but should return +// as normal. +// +// FILTERING: +// The function should read successive entries until a suitable entry is found. +// An entry is suitable if the entry attributes match the criteria set by this +// object's attributes, which are set on initialisation. The File Server has +// set CDirCB::iAtt (which we inherit) with the bitmask. +// +// The File Server opened the directory with a name mask (e.g. "*"). +// This mask has been to stored to iMask of this class. We must only return entries, +// whose name match this mask. +// +// If, on return, the entry's full file name, TEntry::iName, is longer than +// the maximum buffer size, then the entry cannot be returned to the client. +// In this case the file server will set iPending to true and will call +// StoreLongEntryName() before calling this function again. +// In this case (when iPending is true), the function should re-read +// the last entry to be read; it should also set iPending to false and +// should not advance the current read position. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsDirCB::ReadL +(TEntry& anEntry) + { + + if (!iHasBeenFetched) + { + // First read, the directory hasn't been fetched from the server + // yet (can't be done from open as that is always synchronous + // operation from UI's point of view) + TInt totalBytes; + User::LeaveIfError(static_cast + (Mount()).RSessionL()->Fetch(iThisFid, 0, 0, totalBytes)); + iHasBeenFetched = ETrue; + } + + TEntry entry; + + if (iPending) + { + iStreamPos = iPendingPos; + iPending = EFalse; + } + + MStreamBuf* contFileStreamBuf = iDirContReadStream.Source(); + // Skip over entries already read + contFileStreamBuf->SeekL(MStreamBuf::ERead, iStreamPos); + + TDirEnt d; + + do + { + TInt strippedBits = 0; + TBool matchName = EFalse; + TBool matchAttr = EFalse; + + iPendingPos = iStreamPos; + // Each round must fill one TEntry (or leave with KErrEof) + d.InternalizeL(iDirContReadStream); // leaves with KErrEof + iEntryPos++; + + entry.iName.Des().Copy(d.iName); + entry.iAtt = d.iAttr.iAtt; + entry.iSize = d.iAttr.iSize; + entry.iModified = d.iAttr.iModified; + entry.iType = (KNullUid, KNullUid, d.iAttr.iUid3); + // do not set KEntryAttRemote for directories + // it is defined by Symbian to be a file attribute only + // remote file engine uses it internally for dirs also + if (entry.iAtt & KEntryAttDir) + { + entry.iAtt &= ~KEntryAttRemote; + } + + // Filtering: + + // compare name against the match pattern + matchName = (entry.iName.Match(*iMatch) != KErrNotFound); + + // compare against iAtt attribute mask + // The mask works as follows: + // To match files only, specify KEntryAttNormal. + // To match both files and directories, specify KEntryAttDir. + // To match directories only, specify KEntryAttDir|KEntryAttMatchExclusive. + // To match files with a specific attribute, then OR the attribute involved with KEntryAttMatchExclusive. + // For example, to match read-only files, specify KEntryAttReadOnly|KEntryAttMatchExclusive. + if (iAtt & KEntryAttMatchExclusive) + { // files with a specific attribute only + matchAttr = iAtt & entry.iAtt; + } + else + { + if (iAtt & KEntryAttDir) + { + // both files and directories + matchAttr = ETrue; + } + else + { + // files only + if (!(entry.iAtt & KEntryAttDir)) + { + matchAttr = ETrue; + } + } + } + if (matchName && matchAttr) + { + // "reverse" bits modified to make comparison easier + entry.iAtt |= strippedBits; + entry.iAtt &= ~KEntryAttMatchExclusive; + anEntry = entry; + break; + } + } + while (1); + + iStreamPos = contFileStreamBuf->TellL(MStreamBuf::ERead); + + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsDirCB::SetDirL +// Opens read stream in the container file. Called in CRsfwFsMountCB when the +// directory is opened. +// Implementation notice: As this class only reads the container file, it would +// seem sensible to open EFileRead|EFileShareAny here, but when Remote +// File Engine then tries to open EFileWrite|EFileShareAny it fails unless +// EFileWrite is specified here also... +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsDirCB::SetDirL( + const TDesC& aPath, + const TDesC& aName) + { + + User::LeaveIfError(iDirContReadStream.Open(*(RFs* )Dll::Tls(), + aPath, EFileWrite | EFileShareAny)); + iMatch = aName.AllocL(); + + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/src/rsfwfsfilecb.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/src/rsfwfsfilecb.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,473 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File server interface class representing an open file. +* Allows to access a specific remote file. +* +*/ + + +// INCLUDE FILES +#include "rsfwfsfilecb.h" +#include "rsfwfsmountcb.h" + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::CRsfwFsFileCB +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwFsFileCB::CRsfwFsFileCB() + { + iLastFlushFailed = ETrue; + iPartialWriteSupported = ETrue; + } + +// Destructor +CRsfwFsFileCB::~CRsfwFsFileCB() + { + // close the cache file first so that RFE can move/delete it if upload fails + iContFile.Close(); + TUint flags = 0; + if (iFileName) + { + if (!iLastFlushFailed) + { + // Now the container file has been changed, + // tell Remote File Engine to update it on the servers + // RSessionL() should not leave here as the remote session surely is created by now... + if (iAtt & KEntryAttModified) + { + flags |= ECloseModified; + + // File was modified use, flush to write data to the server + // We write the whole file always, if flush was never called we cannot + // know whether partial write is supported. + TRAP_IGNORE(static_cast + (Mount()).RSessionL()->Flush(iThisFid, 0, iCachedSize, iCachedSize)); + } + else + { + flags |= ECloseNotModified; + } + + } + else + { + // flush was called and failed + // do not try to flush again if the application closes the file + // instead indicate this to the close state machine + flags |= ECloseLastFlushFailed; + } + } + + // close will release the write lock if possible + // and also allows user to save the file locally if flush failed + TRAP_IGNORE(static_cast + (Mount()).RSessionL()->CloseFile(iThisFid, flags)); + + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::RenameL +// Renames the file with the full file name provided. Because the full name of +// the file includes the path, the function can also be used to move the file. +// +// It can be assumed that no other sub-session has access to the file: +// i.e. the file has not been opened in EFileShareAny share mode. +// It can also be assumed that the file has been opened for writing. +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::RenameL( + const TDesC& aNewName) + { + static_cast(Mount()).RenameFidL(iParentFid, *iFileName, aNewName); + delete iFileName; + iFileName = NULL; + iFileName = aNewName.AllocL(); + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::ReadL +// Reads a specified number of bytes from the open file starting at +// the specified position, and writes the result into a descriptor. +// +// It can be assumed that aPos is inside the file and aLength > 0. +// The file should only be read up to its end regardless of +// the value of aPos + aLength. The number of bytes read should be stored +// in aLength on return. +// +// Implemented by sending FETCH request to Remote File Engine for the +// specified data and subsequently reading the data from the local cache file. +// Reading the local cache file sets aLength. +// Note that we want to keept the cache file continuos. If the requested data +// starts behind the end of the current cache file, the function sends FETCHDATA +// and Remote File Engine puts this data into a temp cache file valid only +// for the duration of this operation if the caching mode is something else than +// Whole File Caching +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::ReadL( + TInt aPos, + TInt& aLength, + const TAny* /*aDes*/, + const RMessagePtr2& aMessage) + + { + + if (iCachedSize == 0) + { + // iCachedSize possibly not up-to-date... + iContFile.Size(iCachedSize); + } + + HBufC8* data = HBufC8::NewMaxLC(aLength); + TPtr8 buf(data->Des()); + + if (aPos > iCachedSize) + { + // Depending on the caching mode this type of request may bypass the + // normal cache file. + TBool useTempCache = EFalse; + HBufC* tmpCacheFile = HBufC::NewLC(KMaxPath); + TPtr tmpCache(tmpCacheFile->Des()); + User::LeaveIfError(static_cast + (Mount()).RSessionL()->FetchData(iThisFid, + aPos, + aPos + aLength - 1, + tmpCache, + useTempCache)); + if (useTempCache) + { + // use "temp" in the same directory instead of the cache file + RFile tempFile; + TParse parser; + parser.Set(tmpCache, NULL, NULL); + HBufC* tempPath = HBufC::NewLC(KMaxPath); + TPtr tempptr = tempPath->Des(); + tempptr.Append(parser.DriveAndPath()); + tempptr.Append(KTempFileName); + User::LeaveIfError(tempFile.Open(*(RFs* )Dll::Tls(), + tempptr, EFileRead)); + CleanupStack::PopAndDestroy(tempPath); + CleanupClosePushL(tempFile); + User::LeaveIfError(tempFile.Read(buf, aLength)); + CleanupStack::PopAndDestroy(&tempFile); + } + else + { + // read from the normal container file (Whole File Caching mode). + iContFile.Size(iCachedSize); + User::LeaveIfError(iContFile.Read(aPos, buf, aLength)); + } + CleanupStack::PopAndDestroy(tmpCacheFile); // tempcacheFile + } + else if ((aPos + aLength) > iCachedSize) + { + User::LeaveIfError(static_cast + (Mount()).RSessionL()->Fetch(iThisFid, + aPos, + aPos + aLength - 1, + iCachedSize)); + + User::LeaveIfError(iContFile.Read(aPos, buf, aLength)); + } + else + { + User::LeaveIfError(iContFile.Read(aPos, buf, aLength)); + } + + aMessage.WriteL(0, buf, 0); + CleanupStack::PopAndDestroy(data); + if (iCachedSize == iSize) + { + // clear the remote attribute if the whole file has now been fetched + iAtt &= ~KEntryAttRemote; + } + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::WriteL +// Writes data to the open file. iModified and iSize are set by the file server +// after this function has completed successfully. +// +// It can be assumed that aPos is within the file range and aLength > 0. +// When aPos + aLength is greater than the file size then the file should +// be enlarged using SetSizeL(). The number of bytes written should be +// returned through the argument aLength. +// +// Implemented by writing to the local cache file. First requests Remote File +// Engine whether there is enough space in the cache to write the file (this +// also calls SysUtil::DiskSpaceBelowCritical()). FE attempts to free space +// from the cache if necessary Implementation notice: writes a large file in +// chunks of 64K. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::WriteL( + TInt aPos, + TInt& aLength, + const TAny* /*aDes*/, + const RMessagePtr2& aMessage) + { + + if (iCachedSize == 0) + { + // iCachedSize possibly not up-to-date... + iContFile.Size(iCachedSize); + } + + // if flush was cancelled, but we come again to write, again set iLastFlushFailed to EFalse + iLastFlushFailed = EFalse; + + // We must first fetch the file to the local cache + // unless aPos = 0 and aLength => iSize + // Note that if files are written to they cannot be partially cached + // as the whole file will be sent to the server and overwrites the old file. + // That is why we must ensure that the whole file is cached as soon as we + // get the first write. + // in subsequent writes iCachedSize will equal iSize + // This may eventually change if we start to use some kind of "delta-PUT". + if (!((aPos == 0) && (aLength >= iSize)) && iCachedSize < iSize && !iFetchedBeforeWriting) + { + User::LeaveIfError(static_cast + (Mount()).RSessionL()->Fetch(iThisFid, iCachedSize, iSize-1, iCachedSize)); + iFetchedBeforeWriting = ETrue; + } + + // make sure that a potential cache addition still fits into the cache + TInt sizeToBeWritten = 0; + + if (iSize > iCachedSize) + { + // when current Write is executed as a part of Copy operation + // then iSize has been set to final size, even before any writing started + sizeToBeWritten = iSize - iCachedSize; + } + else if (aPos + aLength > iCachedSize) + { + sizeToBeWritten = aPos + aLength - iCachedSize + iWrittenSize; + } + + TBool okToWrite; + User::LeaveIfError(static_cast + (Mount()).RSessionL()->OkToWrite(iThisFid, + sizeToBeWritten, + okToWrite)); + + if (!okToWrite) + { + User::Leave(KErrDiskFull); + } + + TInt anOffset = 0; + HBufC8* data = HBufC8::NewMaxLC(aLength); + TPtr8 buf(data->Des()); + + aMessage.ReadL(0, buf, anOffset); + + User::LeaveIfError(iContFile.Write(aPos, *data, aLength)); + User::LeaveIfError(iContFile.Flush()); + CleanupStack::PopAndDestroy(data); + + // update iCachedSize and iWrittenSize if the container file size has grown + if (aPos + aLength > iCachedSize) + { + iCachedSize = aPos + aLength; + iWrittenSize = sizeToBeWritten; + } + + // for flush() calls after this call: + // set iFlushedSize to aPos, so that changes will be flushed + if (iFlushedSize > aPos) + { + iFlushedSize = aPos; + } + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::SetSizeL +// Emply implementation, upper class already set iSize +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::SetSizeL( + TInt aSize) + { + iReportedSize = aSize; + // we cannot set the actual size of the remote file, but also we do not + // return KErrNotSupported as that would cause problems with CFileMan + // and File Manager, which use SetSize() as an optimization to set the + // target file size in copy. + // Propably calling setsize() on remote files when for example just writing + // to an existing file would cause weird results. + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::SetEntryL +// Sets the attribute mask, iAtt, and the modified time of the file, iModified. +// If aMask|aVal does not equal zero, then aMask should be OR'ed with iAtt, +// whilst the inverse of aVal should be AND'ed with iAtt. +// If the modified flag is set in aMask then iModified should be set to aTime. +// +// Implemented by calling CRsfwFsMountCB::SetEntryL(). +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::SetEntryL( + const TTime& aTime, + TUint aMask, + TUint aVal) + { + static_cast(Mount()).SetEntryL(*iFileName, + aTime, + aMask, + aVal); + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::FlushAllL +// Flushes, to disk, all cached file data (e.g. attributes, modification time, +// file size). The modified bit in the file attributes mask should be cleared if +// the flush was successful. +// +// File Server calls this before reading directory entries, getting an entry +// details for a directory entry etc. The idea is to make sure that all the +// information to be retrieved is up to date. We don't need to implement this, +// as our framework does not have buffers that could cause this problem. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::FlushAllL() + { + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::FlushDataL +// Flushes, to disk, the cached information necessary for the integrity +// of recently written data, such as the file size. +// +// Called by File Server as a result of RFile::Flush() (if the file has been +// modified). In our framework the file should be written to the server. +// We should also clear KEntryAttModified here. +// +// (other items were commented in a header). +// +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::FlushDataL() + { + TInt err = KErrNone; + + // close the container file to make sure all the local changes are cached + iContFile.Close(); + + // if flush was cancelled, but we come again to write, + // again set lastflushfailed to EFale + iLastFlushFailed = EFalse; + + // may attempt to write part of the file or whole file + // also we may or may not know for sure whether the + // server supports partial write +starttoflush: + if (!iPartialWriteSupported) + { + // If we know that partial write is not supported + // AND the client has reported the full size of + // the file, do not really flush until all the data + // has been written to the cache file. + // * + // If we do not know the total size flush whatever is cached + if ((iCachedSize == iReportedSize) || iReportedSize == 0) + { + err = static_cast + (Mount()).RSessionL()->Flush(iThisFid, + 0, + iCachedSize, + iCachedSize); + } + // else do not do anything yet, only when the whole file is in cache + } + else + { + // we "still" assume that partial write is supported + err = static_cast + (Mount()).RSessionL()->Flush(iThisFid, + iFlushedSize, + iCachedSize, + iReportedSize); + if (err == KErrNotSupported) + { + err = KErrNone; // reset the error + // flushing the file not supported + // probably because the access protol plugin does not support partial write + iPartialWriteSupported = EFalse; + // apply the flush logic again + // this time with the knowledge that the server does not support partial + // write + goto starttoflush; + } + else + { + iAtt &= ~KEntryAttModified; // clear KEntryAttModified if flush worked + } + + } + + // re-open the container file + User::LeaveIfError(iContFile.Open(*(RFs* )Dll::Tls(), + iCachePath, + EFileWrite | EFileShareAny)); + + + // handling the results + if (err == KErrNone) + { + // the operation was successful + iFlushedSize = iCachedSize; + } + else if (err != KErrNone) + { + iLastFlushFailed = ETrue; + User::Leave(err); + } + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFileCB::SetContainerFileL +// Opens the container file. +// Called in CRsfwFsMountCB when the file is opened. +// Implementation notice: If this file is only opened for reading, it would +// seem sensible to open EFileRead|EFileShareAny here, but when Remote +// File Engine then tries to open EFileWrite|EFileShareAny it fails unless +// EFileWrite is specified here also... +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFileCB::SetContainerFileL( + const TDesC& aPath) + { + iCachePath = aPath; + User::LeaveIfError(iContFile.Open(*(RFs* )Dll::Tls(), + aPath, + EFileWrite | EFileShareAny)); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/src/rsfwfsformatcb.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/src/rsfwfsformatcb.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,66 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File server interface class representing a format +* operation on a disk. Not supported for remote drives. +* +*/ + + +// INCLUDE FILES +#include "rsfwfsformatcb.h" + +// ============================ MEMBER FUNCTIONS =============================== + +// ----------------------------------------------------------------------------- +// CRsfwFsFormatCB::CRsfwFsFormatCB +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwFsFormatCB::CRsfwFsFormatCB() + { + } + +// Destructor +CRsfwFsFormatCB::~CRsfwFsFormatCB() + { + } + +// ----------------------------------------------------------------------------- +// CRsfwFsFormatCB::DoFormatStepL +// Performs a formatting step on the drive. The step performed should depend on +// the values of iMode and iCurrentStep. It can be assumed that there are no +// resources open on the mount, that the media is formattable, and that the media +// is not write protected. +// +// If iMode == EQuickFormat, then only meta data is to be written. +// This should be carried out in a single step, with iCurrentStep set +// to zero on completion. +// +// If iMode != EQuickFormat, then the format step performed by +// this function should depend on iCurrentStep. When the function +// returns with iCurrentStep set to zero, the formatting of the drive is complete. +// +// implementation: not supported for remote drives +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsFormatCB::DoFormatStepL() + { + iCurrentStep = 0; + User::Leave(KErrNotSupported); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/remotefilesystemplugin/src/rsfwfsmountcb.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/remotefilesystemplugin/src/rsfwfsmountcb.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,857 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File server interface class representing a mount. +* An instance of this object is referred to as +* a mount control block. +* +*/ + + + + +#include "rsfwfsmountcb.h" +#include "rsfwfsfilecb.h" +#include "rsfwfsdircb.h" + + +// there is no good way to give remote storage size so just put some big numbers here +const TInt KMountReportedSize = 999999999; +const TInt KMountReportedFreeSize = 999999999; + +// ============================ MEMBER FUNCTIONS =============================== + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::NewL +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwFsMountCB* CRsfwFsMountCB::NewL() + { + CRsfwFsMountCB* remoteFsMntCB = new(ELeave) CRsfwFsMountCB(); + return remoteFsMntCB; + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::CRsfwFsMountCB +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwFsMountCB::CRsfwFsMountCB() + { + + } + +// Destructor +CRsfwFsMountCB::~CRsfwFsMountCB() + { + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::MountL +// The function should set the volume name (iVolumeName), the unique ID +// (iUniqueID) and the volume size (iSize) by reading and processing the current +// mount. The function should leave, on error detection, with an appropriate error +// code. When aForceMount is set to ETrue, the properties of a corrupt volume +// should be forcibly stored. The classic case of when this is desirable is when a +// corrupt volume needs to be formatted. +// +// We set the values (iSize to a fixed size). We also create a +// File Server session (needed to access the local cache) and put the handle into +// the TLS for future access. aForceMount is ignored. +// Note that this operation does not attempt to connect to remote server. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::MountL( + TBool /* aForceMount */) + { + + iServerName = HBufC::NewL( KMaxVolumeNameLength); + TPtr serverName (iServerName->Des()); + serverName.Append(KRemoteVolumeName); + SetVolumeName(iServerName); + + TTime timeID; + timeID.HomeTime(); + iUniqueID = I64LOW(timeID.Int64()); + iSize = KMountReportedSize; + + User::LeaveIfError(iFsSession.Connect()); + User::LeaveIfError(Dll::SetTls(&iFsSession)); + + iRootFid.iVolumeId = Drive().DriveNumber(); + iRootFid.iNodeId = 1; + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::ReMount +// The function should check whether the mount control block represents the +// current mount on the associated drive. The function should read mount +// information from the current volume, and check it against the mount +// information from this mount - typically iVolumeName and iUniqueID. If the mount +// information matches, the function should return KErrNone, otherwise it should +// return KErrGeneral. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +int CRsfwFsMountCB::ReMount() + { + // we assume that this operation - if called on remote drive + // - can be succesfull + return KErrNone; + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::Dismounted +// Carries out clean-up necessary for a volume dismount: +// Closing the session to the File Server used for local cache. +// Closing the session to Remote File Engine. +// Dismounting a volume will always succeed, so the function does not need to +// return an error value. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::Dismounted() + { + + iSession->Close(); + iFsSession.Close(); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::VolumeL +// Gets volume information. The only information that the function has to supply +// is the free space, TVolumeInfo::iFree, since the remaining members have already +// been set by the calling function. The function should leave, on error detection, +// with an appropriate error code. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::VolumeL( + TVolumeInfo& aVolume) const + { + + // : we should return info about free storage + // at the remote server, if possible... + aVolume.iFree = KMountReportedFreeSize; + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::SetVolumeL +// Sets the volume name for the mount, thus writing the new volume name to the +// corresponding volume. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::SetVolumeL( + TDes& aName) + { + + if (aName.Length() > KMaxVolumeNameLength) + { + User::Leave(KErrBadName); + } + if (iServerName) + { + delete iServerName; + iServerName = NULL; + } + iServerName = HBufC::NewL( KMaxVolumeNameLength); + TPtr serverName (iServerName->Des()); + serverName.Append(aName); + SetVolumeName(iServerName); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::MkDirL +// Creates a new directory on the mount by figuring out the FID of the parent +// directory and the name of the child to be created. +// +// The full name in aName is in the form: +// \\dirA\\dirB\\dirC\\dirD +// where dirD is the new directory to be created in \\dirA\\dirB\\dirC\\. +// This means that dirC is the leaf directory in which dirD will be created. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::MkDirL( + const TDesC& aName) + { + + TInt delimiterPos; + TPtrC directory, path; + TFid theFid; + + delimiterPos = aName.LocateReverse(KPathDelimiter); + directory.Set(aName.Right(aName.Length() - (delimiterPos + 1))); + path.Set(aName.Left(delimiterPos + 1)); + theFid = FetchFidL(path, KNodeTypeDir); + User::LeaveIfError(RSessionL()->MakeDirectory(theFid, directory)); + + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RmDirL +// Removes the directory specified by aName by figuring out the FID of the parent +// directory and the name of the child to be created. The function can assume +// that the directory exists and is not read-only. +// +// The directory specified by aName is in the form: +// \\dirA\\dirB\\dirC\\dirD +// where dirD is the directory to be removed from \\dirA\\dirB\\dirC\\. +// This means that dirC is the leaf directory from which dirD should be removed. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::RmDirL( + const TDesC& aName) + { + + TInt delimiterPos; + TPtrC directory, path; + TFid parentFid; + + delimiterPos = aName.LocateReverse(KPathDelimiter); + directory.Set(aName.Right(aName.Length() - (delimiterPos + 1))); + path.Set(aName.Left(delimiterPos + 1)); + parentFid = FetchFidL(path, KNodeTypeDir); + User::LeaveIfError(RSessionL()->RemoveDirectory(parentFid, directory)); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::DeleteL +// Deletes the specified file from the mount by figuring out the FID of the parent +// directory and the name of the child to be created. The function can assume that +// the file is closed. +// +// The file name specified by aName is of the form: +// \\dirA\\dirB\\dirC\\file.ext +// The extension is optional. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// + +void CRsfwFsMountCB::DeleteL( + const TDesC& aName) + { + + TInt delimiterPos; + TPtrC file, path; + TFid parentFid; + + delimiterPos = aName.LocateReverse(KPathDelimiter); + file.Set(aName.Right(aName.Length() - (delimiterPos + 1))); + path.Set(aName.Left(delimiterPos + 1)); + parentFid = FetchFidL(path, KNodeTypeDir); + User::LeaveIfError(RSessionL()->RemoveFile(parentFid, file)); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RenameL +// Renames or moves a single file or directory on the mount by figuring out +// the FIDs of the parent directories and child names for both anOldName and +// anNewName. If oldEntryName is a file, it can be assumed that it is closed. +// If oldEntryName is a directory, it can be assumed that there are no +// open files in this directory. Furthermore, if newEntryName specifies +// a directory, it can be assumed that it is not a subdirectory of oldEntryName. +// +// anOldName and anNewName specify the respective entries with full names; +// for example, +// \\dirA\\dirB\\dirC\\oldEntryName +// and +// \\dirE\\dirF\\dirG\\newEntryName +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::RenameL( + const TDesC& anOldName, + const TDesC& aNewName) + { + + TInt delimiterPos; + TPtrC sourcepath, destpath; + TPtrC srcname, destname; + TFid sourceFid, destFid; + + delimiterPos = anOldName.LocateReverse(KPathDelimiter); + srcname.Set(anOldName.Right(anOldName.Length() - (delimiterPos + 1))); + sourcepath.Set(anOldName.Left(delimiterPos + 1)); + sourceFid = FetchFidL(sourcepath, KNodeTypeDir); + + delimiterPos = aNewName.LocateReverse(KPathDelimiter); + destname.Set(aNewName.Right(aNewName.Length() - (delimiterPos + 1))); + destpath.Set(aNewName.Left(delimiterPos + 1)); + destFid = FetchFidL(destpath, KNodeTypeDir); + + User::LeaveIfError(RSessionL()->MoveFids(sourceFid, + srcname, + destFid, + destname, + EFalse)); + + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::ReplaceL +// Replaces one file on the mount with another. The file anOldName should have +// its contents, attributes, and the universal date and time of its last +// modification, copied to the file aNewName, overwriting any existing contents +// and attribute details. If the file aNewName does not exist it should be created. +// The function can assume that both anOldName and, if it exists, anNewName +// contain the full file names of files, and that these files are not open. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::ReplaceL( + const TDesC& anOldName, + const TDesC& aNewName ) + { + + TInt delimiterPos; + TPtrC sourcepath, destpath; + TPtrC srcname, destname; + TFid sourceFid, destFid; + + delimiterPos = anOldName.LocateReverse(KPathDelimiter); + srcname.Set(anOldName.Right(anOldName.Length() - (delimiterPos + 1))); + sourcepath.Set(anOldName.Left(delimiterPos + 1)); + sourceFid = FetchFidL(sourcepath, KNodeTypeDir); + + delimiterPos = aNewName.LocateReverse(KPathDelimiter); + destname.Set(aNewName.Right(aNewName.Length() - (delimiterPos + 1))); + destpath.Set(aNewName.Left(delimiterPos + 1)); + destFid = FetchFidL(destpath, KNodeTypeDir); + + User::LeaveIfError(RSessionL()->MoveFids(sourceFid, + srcname, + destFid, + destname, + ETrue)); + + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::EntryL +// Gets the entry details for the specified file or directory. +// This function is defined as a const function in the base class CMountCB. +// However, we need to modify the shared memory chunks used in the parameter +// passing. That's why we need to cast away const. +// +// Always returns KErrPathNotFoud for certain Symbian system directories. The +// reason for this is that scanning all drives for some system directory does +// not always skip remote drives, but it is not feasible to start to look +// for some library, recognizer etc. from a remote drive. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::EntryL( + const TDesC& aName, + TEntry& anEntry) const + { + + if (aName.Length() > KMaxPath) + { + User::Leave(KErrBadName); + } + + CONST_CAST(CRsfwFsMountCB*, this)->RemoteFsEntryL(aName, anEntry); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RemoteFsEntryL +// Gets the entry details for the specified file or directory by figuring out +// the fid of the entry. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::RemoteFsEntryL(const TDesC& aName, TEntry& anEntry) + { + + anEntry.iName = aName; + TFid fileFid = FetchFidL(aName, KNodeTypeUnknown); + User::LeaveIfError(RSessionL()->GetAttributes(fileFid, anEntry)); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::SetEntryL +// Sets entry details for a specified file or directory. +// The entry identified by the full name descriptor aName should have +// its modification time and its attributes mask updated as required. +// We also use this function to control (using new attributes bits) the file +// caching state (KEntryAttCachePriorityHigh) +// +// The entry receives a new universal modified time from aTime. +// The entry attributes are set with aSetAttMask and cleared with aClearAttMask: +// the bits that are set in aSetAttMask should be set in the entry attribute mask; +// the bits that are set in aClearAttMask should be cleared from the entry +// attribute mask. +// +// The function can assume that aSetAttMask and aClearAttMask do not change +// the type of attribute (i.e. volume or directory). Furthermore, if aName +// specifies a file, it can be assumed that this file is closed. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::SetEntryL( + const TDesC& aName, + const TTime& aTime, + TUint aSetAttMask, + TUint aClearAttMask) + { + + TFid thisFid; + thisFid = FetchFidL(aName, KNodeTypeUnknown); + + TInt result = RSessionL()->SetEntry(thisFid, aTime, aSetAttMask, aClearAttMask); + + // KErrNotSupported is dismissed currently + // The reason for this is CFileMan::Copy + // CFileMan::Copy is a composite operation which as a last step + // calls RFs::SetAtt() for the target file. + // If we honestly return KErrNotSupported CFileMan::Copy will now + // return KErrNotSupported also, although it already copied the file on the server. + // We rather have a working copy and return false information about the success of + // SetAtt(). + if ((result != KErrNone) && (result != KErrNotSupported)) + { + User::Leave(result); + } + + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::FileOpenL +// If needed creates a new file by figuring out the FID of the parent directory +// and the name of the new file. After that opens the file. After successful +// completion of the function, the file control block pointer will be added to the +// file server's global files container. Adds information to the file control +// block (e.g. path of the local cache file and pointer to this mount control block) +// +// If anOpen specifies EFileReplace (rather than EFileCreate or EFileOpen) then +// the data contained in the file should be discarded, the archive attribute +// should be set, and the size of the file should be set to zero. Note that it can +// be assumed that if anOpen specifies EFileReplace then the file already exists. +// +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::FileOpenL( + const TDesC& aName, + TUint aMode, + TFileOpen anOpen, + CFileCB* aFile) + { + + TFid parentFid; + TFid thisFid; + TInt delimiterPos; + TPtrC filename, path; + delimiterPos = aName.LocateReverse(KPathDelimiter); + filename.Set(aName.Right(aName.Length() - (delimiterPos + 1))); + path.Set(aName.Left(delimiterPos + 1)); + parentFid = FetchFidL(path, KNodeTypeDir); + + switch (anOpen) + { + case EFileCreate: + // exclusive = 1 + User::LeaveIfError(RSessionL()-> + CreateFile(parentFid, filename, aMode, TRUE, thisFid)); + break; + case EFileReplace: + // exclusive = 0 + User::LeaveIfError(RSessionL()-> + CreateFile(parentFid, filename, aMode, FALSE, thisFid)); + break; + case EFileOpen: // the file must exist + default: + User::LeaveIfError(RSessionL()-> + Lookup(parentFid, filename, KNodeTypeFile, thisFid)); + break; + } + + TDirEntAttr attributes; + HBufC* unicodepath = HBufC::NewMaxLC(KMaxPath); + TPtr unicodepathptr(unicodepath->Des()); + attributes.iAtt = aMode; + User::LeaveIfError(RSessionL()-> + OpenByPath(thisFid, unicodepathptr, &attributes, ETrue)); + unicodepathptr.SetLength(unicodepath->Length()); + + ((CRsfwFsFileCB*)aFile)->iLastFlushFailed = EFalse; + ((CRsfwFsFileCB*)aFile)->iThisFid = thisFid; + ((CRsfwFsFileCB*)aFile)->iParentFid = parentFid; + ((CRsfwFsFileCB*)aFile)->SetContainerFileL(unicodepathptr); + // set size, att, modified for the file + ((CRsfwFsFileCB*)aFile)->SetSize(attributes.iSize); + ((CRsfwFsFileCB*)aFile)->SetAtt(attributes.iAtt); + ((CRsfwFsFileCB*)aFile)->SetModified(attributes.iModified); + aFile->SetMount(this); + CleanupStack::PopAndDestroy(unicodepath); // unicodepath + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::DirOpenL +// Opens a directory on the mount by figuring out the FID of the parent +// directory and the name of the directory. +// Note that aName is of the form +// \\dirA\\dirB\\dirC\\file.ext +// where \\dirA\\dirB\\dirC\\ is the directory to be opened and file.ext is +// an optional entry name and extension. The name and extension (e.g. "*" or +// "*.txt") limit entries that reading the directory should return. +// +// Always returns KErrPathNotFoud for certain Symbian system directories. The +// reason for this is that scanning all drives for some system directory does +// not always skip remote drives, but it is not feasible to start to look +// for some library, recognizer etc. from a remote drive. +// +// After successful completion of the function, the directory control block +// pointer will be added to the file server global directories container. Adds +// information to the directory control block (e.g. path of the local cache file +// and possible name and extension) +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::DirOpenL( + const TDesC& aName, + CDirCB* aDir) + { + + TFid fileFid; + TInt namePos; + namePos = aName.LocateReverse(KPathDelimiter); + TPtrC directoryPathName(aName.Left(namePos + 1)); + TPtrC matchName(aName.Mid(namePos + 1)); + if (matchName.Length() == 0) + { + matchName.Set(KDirReadAllMask); + } + if (directoryPathName.Length() == 0) + { + fileFid = iRootFid; + } + else + { + fileFid = FetchFidL(directoryPathName, KNodeTypeDir); + } + + HBufC* unicodepath = HBufC::NewMaxLC(KMaxPath); + TPtr unicodepathptr(unicodepath->Des()); + User::LeaveIfError(RSessionL()-> + OpenByPath(fileFid, unicodepathptr, NULL, EFalse)); + ((CRsfwFsDirCB*)aDir)->SetDirL(unicodepathptr, matchName); + ((CRsfwFsDirCB*)aDir)->iThisFid = fileFid; + ((CRsfwFsDirCB*)aDir)->SetMount(this); + CleanupStack::PopAndDestroy(unicodepath); // unicopath + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RawReadL +// Should read the specified length of data from the specified position on +// the volume directly into the client thread. It can be assumed that if this +// function is called, then there has been a successful mount. +// Not supported, as "position in a volume" without files is meaningless to +// us. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::RawReadL( + TInt64 /* aPos */, + TInt /* aLength */ , + const TAny* /* aTrg */, + TInt /* anOffset */ , + const RMessagePtr2& /* aMessage */) const + { + + User::Leave(KErrNotSupported); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RawWriteL +// Should write a specified length of data from the client thread to the volume +// at the specified position. It can be assumed that if this +// function is called, then there has been a successful mount. +// Not supported, as "position in a volume" without files is meaningless to +// us. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::RawWriteL( + TInt64 /* aPos */, + TInt /* aLength */, + const TAny* /* aSrc */, + TInt /* anOffset */, + const RMessagePtr2& /* aMessage */) + { + + User::Leave(KErrNotSupported); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::GetShortNameL +// Should get the short name of the file or directory with the given full name. +// This function is used in circumstances where a file system mangles +// Symbian OS natural names, in order to be able to store them on +// a file system that is not entirely compatible. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::GetShortNameL( + const TDesC& /* aLongName */, + TDes& /* aShortName */) + { + + User::Leave(KErrNotSupported); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::GetLongNameL +// Should get the long name of the file or directory associated with the given +// short name. This function is used in circumstances where a file system mangles +// Symbian OS natural names in order to be able to store them on +// a file system that is not entirely compatible. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::GetLongNameL( + const TDesC& /* aShortName */, + TDes& /* aLongName */) + { + + User::Leave(KErrNotSupported); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::ReadSectionL +// Reads a specified section of the file, regardless of the file's lock state. +// This function basically does what the chain of opening a file, creating +// the file control block, and reading file data using CRsfwFsFile::Read() +// does, but without creating the file control block. For us file's lock state +// does not have meaning. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::ReadSectionL( + const TDesC& aName, + TInt aPos, + TAny* /*aTrg */, + TInt aLength, + const RMessagePtr2& aMessage) + + { + + HBufC8* data = HBufC8::NewMaxLC(aLength); + TPtr8 buf(data->Des()); + + TFid parentFid; + TFid newFid; + TInt delimiterPos; + TPtrC filename, path; + HBufC* unicodepath = HBufC::NewMaxLC(KMaxPath); + TPtr unicodepathptr(unicodepath->Des()); + + delimiterPos = aName.LocateReverse(KPathDelimiter); + filename.Set(aName.Right(aName.Length() - (delimiterPos + 1))); + path.Set(aName.Left(delimiterPos + 1)); + parentFid = FetchFidL(path, KNodeTypeDir); + User::LeaveIfError(RSessionL()-> + Lookup(parentFid, filename, KNodeTypeFile, newFid)); + User::LeaveIfError(RSessionL()-> + OpenByPath(newFid, unicodepathptr, NULL, EFalse)); + + // get the size of the container file + TEntry tentry; + User::LeaveIfError((*(RFs* )Dll::Tls()).Entry(unicodepathptr, tentry)); + if (aPos > tentry.iSize) + { + // non-sequential read + // i.e. if 128 bytes have been cached + // starting read from pos 128 continues to fill the cache file + // but starting read from pos 129- is "random access" + // that by-passes the cache */ + RFile tempFile; + TBool usetempCache = EFalse; + HBufC* tmpcacheFile = HBufC::NewLC(KMaxPath); + TPtr tmpCache(tmpcacheFile->Des()); + User::LeaveIfError(RSessionL()->FetchData(newFid, + aPos, + aPos + aLength - 1, + tmpCache, + usetempCache)); + // if caching mode is "Whole File Caching" this operation may fetch + // the whole file into normal cache anyway. "tmpCache" contains + // the right path in this case too, so in this function (where the file + // is not open), we don't have to check "usetempCache" boolean. + User::LeaveIfError(tempFile.Open(*(RFs* )Dll::Tls(), tmpCache, EFileRead)); + CleanupClosePushL(tempFile); + User::LeaveIfError(tempFile.Read(buf, aLength)); + CleanupStack::PopAndDestroy(2, tmpcacheFile); // tempfile, tempcacheFile + } + else + { + TInt lastByte; + User::LeaveIfError(RSessionL()->Fetch(newFid, aPos, aPos + aLength-1, lastByte)); + User::LeaveIfError((*(RFs* )Dll::Tls()).ReadFileSection(*unicodepath, + aPos, + buf, + aLength)); + } + CleanupStack::PopAndDestroy(unicodepath); // unicodepath + + // we have read the data into buf + aMessage.WriteL(0, buf, 0); + CleanupStack::PopAndDestroy(data); // data + + } + + + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::FetchFidL +// Fetches fid for an entry. +// aPath is of the form \\dirA\\dirB\\dirC\\entry +// Goes through the path recursively. I.e. first gets the fid of dirA by +// fid_dirA = lookup(iRootFid, dirA), then does lookup(fid_dirA, dirB) etc. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TFid CRsfwFsMountCB::FetchFidL( + const TDesC& aPath, + TUint aNodeType) + { + TFid newFid; + TInt pathlength = aPath.Length(); + + if (pathlength <= 1) + { + // '\' + // In some rare cases called with zero length aPath, + // it seems to be ok to return rootFid + return iRootFid; + } + else + { + TInt delimiterPos = aPath.LocateReverse(KPathDelimiter); + if (delimiterPos == (pathlength - 1)) + { + // The path ends with a slash, + //i.e. this is a directory - continue parsing + TPtrC nextdelimiter; + nextdelimiter.Set(aPath.Left(delimiterPos)); + delimiterPos = nextdelimiter.LocateReverse(KPathDelimiter); + } + TPtrC entry(aPath.Right(aPath.Length() - (delimiterPos + 1))); + TPtrC path(aPath.Left(delimiterPos + 1)); + // fetch recursively TFid of path + User::LeaveIfError(RSessionL()-> + Lookup(FetchFidL(path, KNodeTypeDir), entry, aNodeType, newFid)); + return newFid; + } + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RenameFidL +// Renames a file +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +void CRsfwFsMountCB::RenameFidL( + TFid aDirFid, + const TDesC& aSourceName, + const TDesC& aNewName ) + { + + TInt delimiterPos; + TPtrC destpath, srcname, destname; + TFid destFid; + + delimiterPos = aSourceName.LocateReverse(KPathDelimiter); + srcname.Set(aSourceName.Right(aSourceName.Length() - (delimiterPos + 1))); + + delimiterPos = aNewName.LocateReverse(KPathDelimiter); + destname.Set(aNewName.Right(aNewName.Length() - (delimiterPos + 1))); + destpath.Set(aNewName.Left(delimiterPos + 1)); + destFid = FetchFidL(destpath, KNodeTypeDir); + + User::LeaveIfError(RSessionL()->MoveFids(aDirFid, + srcname, + destFid, + destname, + EFalse)); + + } + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::CheckDisk +// Checks the integrity of the disk on the specified drive +// temporarily return KErrNone as a workaround for CommonDialogs +// should return KErrNotSupported for remote drives +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +TInt CRsfwFsMountCB::CheckDisk() + { + return KErrNone; + } + + +// ----------------------------------------------------------------------------- +// CRsfwFsMountCB::RSessionL +// Singleton-function that creates a session to Remote File Engine once. +// (other items were commented in a header). +// ----------------------------------------------------------------------------- +// +RRsfwSession* CRsfwFsMountCB::RSessionL() + { + + if (!iSession) + { + iSession = new (ELeave) RRsfwSession(); + User::LeaveIfError(iSession->Connect()); + } + return iSession; + + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rom/rsfw.iby --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rom/rsfw.iby Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,68 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: IBY file for Remote Storage FW +* +*/ + + +#ifndef RSFW_IBY +#define RSFW_IBY + +// DLLs used by RSFW MountMan API, always included +file=ABI_DIR\BUILD_DIR\rsfwcontrol.dll SHARED_LIB_DIR\rsfwcontrol.dll +file=ABI_DIR\BUILD_DIR\rsfwmountman.dll SHARED_LIB_DIR\rsfwmountman.dll +file=ABI_DIR\BUILD_DIR\rsfwmountstore.dll SHARED_LIB_DIR\rsfwmountstore.dll +file=ABI_DIR\BUILD_DIR\rsfwmountutils.dll SHARED_LIB_DIR\rsfwmountutils.dll + +#ifdef __REMOTE_STORAGE_FW + +// Common objects +file=ABI_DIR\BUILD_DIR\rsfwcommon.dll SHARED_LIB_DIR\rsfwcommon.dll + +// Remote File System plug-in +file=ABI_DIR\BUILD_DIR\eremotefs.fsy SHARED_LIB_DIR\eremotefs.fsy + +// Remote File Engine +file=ABI_DIR\BUILD_DIR\remotefe.exe PROGRAMS_DIR\remotefe.exe + +// RSFW Boot Mounter +file=ABI_DIR\BUILD_DIR\rsfwbootmounter.exe PROGRAMS_DIR\rsfwbootmounter.exe + +// Access Modules (ECom plug-ins) +ECOM_PLUGIN(rsfwdavaccess.dll, 101F9769.rsc) + +// Remote File Engine client-side DLLs +file=ABI_DIR\BUILD_DIR\rsfwsession.dll SHARED_LIB_DIR\rsfwsession.dll + +// RSFW config +file=ABI_DIR\BUILD_DIR\rsfwconfig.dll SHARED_LIB_DIR\rsfwconfig.dll + +// RSFW General Settings Plugin UI +ECOM_PLUGIN(rsfwgsplugin.dll,101f9777.rsc) // this publishes the DLL and the + // resource file to the correct location +data=DATAZ_\BITMAP_DIR\rsfwgsplugin.mif BITMAP_DIR\rsfwgsplugin.mif + +// extended notifier server plugin (global dialogs) +//NotifierPlugin +ECOM_PLUGIN(rsfwnotplugin.dll, 101F9770.rss) + +// Bio Control +// dll location +file=ABI_DIR\BUILD_DIR\rsfwmountconfbc.dll SHARED_LIB_DIR\rsfwmountconfbc.dll + +#endif // __REMOTE_STORAGE_FW + +#endif // RSFW_IBY + +// End of File \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rom/rsfw_resources.iby --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rom/rsfw_resources.iby Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,36 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: The resource iby file contains resource that needs to be localized for +* Remotes Storage Framework +* +*/ + +#ifndef RSFWRESOURCES_IBY +#define RSFWRESOURCES_IBY + +#ifdef __REMOTE_STORAGE_FW + +data=DATAZ_\RESOURCE_FILES_DIR\rsfwgspluginrsc.RSC RESOURCE_FILES_DIR\rsfwgspluginrsc.RSC +data=DATAZ_\RESOURCE_FILES_DIR\RemoteFileEngine.RSC RESOURCE_FILES_DIR\RemoteFileEngine.RSC +data=DATAZ_\RESOURCE_FILES_DIR\rsfwmountconfbc.rsc RESOURCE_FILES_DIR\rsfwmountconfbc.rsc +// smart messaging BIO control +data=DATAZ_\BIOFILE_DIR\rsfwmountconfbcbif.rsc BIOFILE_DIR\rsfwmountconfbcbif.rsc +// global dialogs +data=DATAZ_\RESOURCE_FILES_DIR\rsfwnotplugindlg.rsc RESOURCE_FILES_DIR\rsfwnotplugindlg.rsc + +#endif // __REMOTE_STORAGE_FW + +#endif // RSFWRESOURCES_IBY + +// End of File \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/bwins/rsfwnotpluginu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/bwins/rsfwnotpluginu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,5 @@ +EXPORTS + ?ImplementationGroupProxy@@YAPBUTImplementationProxy@@AAH@Z @ 1 NONAME ; struct TImplementationProxy const * ImplementationGroupProxy(int &) + ?NotifierArray@@YAPAV?$CArrayPtr@VMEikSrvNotifierBase2@@@@XZ @ 2 NONAME ; class CArrayPtr * NotifierArray(void) + ?NewL@CRsfwNotPluginNameDialog@@SAPAV1@ABVTDesC16@@AAVTDes16@@AAVRFs@@@Z @ 3 NONAME ; class CRsfwNotPluginNameDialog * CRsfwNotPluginNameDialog::NewL(class TDesC16 const &, class TDes16 &, class RFs &) + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/data/101f9770.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/data/101f9770.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Resource definitions for project notifier plugins +* +*/ + +// INCLUDES + +#include "registryinfo.rh" +#include "uikon.hrh" + +// RESOURCE DEFINITIONS + +RESOURCE REGISTRY_INFO theInfo +{ + dll_uid = 0x101F9770; + interfaces = + { + INTERFACE_INFO + { + interface_uid = KUikonUidPluginInterfaceNotifiers; + implementations = + { + IMPLEMENTATION_INFO + { + implementation_uid = 0x101F9772; + version_no = 1; + display_name = "Rsfw Notifier Plugin"; + default_data = "RsfwNotifierPlugin"; + opaque_data = "0"; + } + }; + } + }; +} diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/data/rsfwnotplugindialog.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/data/rsfwnotplugindialog.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,370 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Resource definitions for project notifier plugins +* +*/ + + +// RESOURCE IDENTIFIER +NAME RSFN + +// INCLUDES +#include +#include +#include +#include +#include +#include +#include +#include + +#include "avkon.loc" +#include +// some strings moved from rfe to here +#include + +// RESOURCE DEFINITIONS +// --------------------------------------------------------- +// +// Define the resource file signature +// This resource should be empty. +// +// --------------------------------------------------------- +// +RESOURCE RSS_SIGNATURE + { + } + +// --------------------------------------------------------- +// +// Default Document Name +// +// --------------------------------------------------------- +// +RESOURCE TBUF + { + buf=""; + } + +RESOURCE CBA r_custom_softkeys_retry_cancel + { + flags = EAknCBAFlagRespondWhenInvisible; + + buttons = + { + CBA_BUTTON + { + id = EAknSoftkeyOk; + txt = qtn_rd_softkey_retry; + }, + CBA_BUTTON + { + id = EAknSoftkeyCancel; + txt = text_softkey_cancel; + }, + CBA_BUTTON + { + id = EAknSoftkeyOk; + txt = qgn_prop_msk_select; + } + }; + } + +RESOURCE CBA r_custom_softkeys_save_no + { + flags = EAknCBAFlagRespondWhenInvisible; + + buttons = + { + CBA_BUTTON + { + id = EAknSoftkeySave; + txt = qtn_rd_softkey_save; + }, + CBA_BUTTON + { + id = EAknSoftkeyNo; + txt = text_softkey_no; + }, + CBA_BUTTON + { + id = EAknSoftkeySave; + txt = qgn_prop_msk_select; + } + }; + } + + +//---------------------------------------------------- +// r_custom_retry_query +// +//---------------------------------------------------- +// +RESOURCE DIALOG r_custom_retry_query +{ + flags = EGeneralQueryFlags; + buttons = r_custom_softkeys_retry_cancel; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout = EConfirmationQueryLayout; + bmpfile = AVKON_BITMAP_FILE; + bmpid = EMbmAvkonQgn_note_warning; + bmpmask = EMbmAvkonQgn_note_warning_mask; + }; + } + }; +} + +RESOURCE DIALOG r_transfer_wait_note + { + flags = EAknWaitNoteFlags; + buttons = R_AVKON_SOFTKEYS_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtNote; + id = EGeneralNote; + control= AVKON_NOTE + { + layout = EWaitLayout; + singular_label = qtn_rd_wait_transferring; + animation =R_QGN_GRAF_WAIT_BAR_ANIM; + }; + } + }; + } + + +RESOURCE DIALOG r_connecting_wait_note + { + flags = EAknWaitNoteFlags; + buttons = R_AVKON_SOFTKEYS_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtNote; + id = EGeneralNote; + control= AVKON_NOTE + { + layout = EWaitLayout; + singular_label = qtn_rd_wait_connecting; + animation =R_QGN_GRAF_WAIT_BAR_ANIM; + }; + } + }; + } + + +RESOURCE DIALOG r_fetching_wait_note + { + flags = EAknWaitNoteFlags; + buttons = R_AVKON_SOFTKEYS_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtNote; + id = EGeneralNote; + control= AVKON_NOTE + { + layout = EWaitLayout; + singular_label = qtn_gen_note_fetching; + animation =R_QGN_GRAF_WAIT_BAR_ANIM; + }; + } + }; + } + +RESOURCE DIALOG r_rsfw_not_plugin_file_name_query + { + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_OK_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_DATA_QUERY + { + layout = EDataLayout; + label = qtn_fldr_item_name_prmpt; + control = EDWIN + { + flags = EEikEdwinNoHorizScrolling | EEikEdwinResizable; + lines = 1; + maxlength = 256; + }; + }; + } + }; + } + +//---------------------------------------------------- +// r_custom_save_query +// +//---------------------------------------------------- +// +RESOURCE DIALOG r_custom_save_query +{ + flags = EGeneralQueryFlags; + buttons = r_custom_softkeys_save_no; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout = EConfirmationQueryLayout; + bmpfile = AVKON_BITMAP_FILE; + bmpid = EMbmAvkonQgn_note_warning; + bmpmask = EMbmAvkonQgn_note_warning_mask; + }; + } + }; +} + +//---------------------------------------------------- +// r_rsfw_plugin_rename_query +// +//---------------------------------------------------- +// +RESOURCE DIALOG r_rsfw_plugin_rename_query +{ + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_OK_CANCEL; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout = EConfirmationQueryLayout; + }; + } + }; +} + +RESOURCE DIALOG r_rsfw_plugin_overwrite_query + { + flags = EGeneralQueryFlags; + buttons = R_AVKON_SOFTKEYS_YES_NO; + items = + { + DLG_LINE + { + type = EAknCtQuery; + id = EGeneralQuery; + control = AVKON_CONFIRMATION_QUERY + { + layout = EConfirmationQueryLayout; + label = qtn_fldr_overwrite_query; + }; + } + }; + } + + +//---------------------------------------------------- +// r_custom_usernamepasswd_dialog +// +// This is used to show user custom authentication +// dialog. +// +//---------------------------------------------------- +// +RESOURCE DIALOG r_custom_usernamepasswd_dialog +{ + flags = EGeneralQueryFlags; + buttons=R_AVKON_SOFTKEYS_OK_CANCEL; + items = { + DLG_LINE { + type = EAknCtMultilineQuery; + id = EMultilineFirstLine; + control = AVERELL_DATA_QUERY { + layout = EMultiDataFirstEdwin; + control = EDWIN { + default_case = EAknEditorLowerCase; + flags = EEikEdwinNoHorizScrolling | EEikEdwinResizable | EAknEditorLowerCase; + width = 25; + maxlength = 50;//KRsfwMaxUsernameLength + avkon_flags = EAknEditorFlagLatinInputModesOnly; + allowed_input_modes = EAknEditorTextInputMode | EAknEditorNumericInputMode; + default_input_mode = EAknEditorTextInputMode; + }; + }; + }, + DLG_LINE { + type = EAknCtMultilineQuery; + id = EMultilineSecondLine; + control = AVERELL_DATA_QUERY { + layout = EMultiDataSecondSecEd; + control = SECRETED { + num_letters = 50;//KRsfwMaxUsernameLength + }; + }; + } + }; +} + +// --------------------------------------------------- +// +// r_rswfplugin_not_enough_memory +// +// --------------------------------------------------- +// +RESOURCE TBUF r_rsfwplugin_not_enough_memory + { + buf = qtn_memlo_not_enough_memory; + } + + +// --------------------------------------------------- +// +// r_rswfplugin_mmc_not_enough_memory +// +// --------------------------------------------------- +// +RESOURCE TBUF r_rsfwplugin_mmc_not_enough_memory + { + buf = qtn_memlo_mmc_not_enough_memory; + } + +RESOURCE TBUF r_rd_query_username { buf = qtn_rd_query_username; } +RESOURCE TBUF r_rd_query_password { buf = qtn_rd_query_password; } +RESOURCE TBUF r_rd_drive_unavailable { buf = qtn_rd_conf_drive_unavailable; } +RESOURCE TBUF r_rd_file_save_fail { buf = qtn_rd_query_file_save_fail; } +RESOURCE TBUF r_rd_select_dir_back { buf = text_softkey_back; } +RESOURCE TBUF r_rd_item_rename_query { buf = qtn_fldr_rename_query; } +RESOURCE TBUF r_rd_name_in_use_rename { buf = qtn_fldr_item_name_prmp; } +RESOURCE TBUF r_rd_fldr_illegal_characters { buf = qtn_fldr_illegal_characters; } +RESOURCE TBUF r_rd_fldr_bad_file_name { buf = qtn_fldr_bad_file_name; } +RESOURCE TBUF r_rd_fldr_name_already_used { buf = qtn_fldr_name_already_used; } +RESOURCE TBUF r_rd_item_overwrite_query { buf = qtn_fldr_overwrite_query; } + +// End of File + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/eabi/rsfwnotpluginu.def --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/eabi/rsfwnotpluginu.def Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,9 @@ +EXPORTS + _Z24ImplementationGroupProxyRi @ 1 NONAME + _Z13NotifierArrayv @ 2 NONAME + _ZTI17CRsfwNotPluginDlg @ 3 NONAME ; ## + _ZTI24CRsfwNotPluginNameDialog @ 4 NONAME ; ## + _ZTV17CRsfwNotPluginDlg @ 5 NONAME ; ## + _ZTV24CRsfwNotPluginNameDialog @ 6 NONAME ; ## + _ZN24CRsfwNotPluginNameDialog4NewLERK7TDesC16R6TDes16R3RFs @ 7 NONAME + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,28 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build information file for project notifier plugins +* +*/ + + +PRJ_EXPORTS +../inc/rsfwauthenticationdlgrequest.h |../../inc/rsfwauthenticationdlgrequest.h +../inc/rsfwsavetodlgrequest.h |../../inc/rsfwsavetodlgrequest.h +../inc/rsfwnotpluginrequest.h |../../inc/rsfwnotpluginrequest.h +../inc/rsfwnotpluginnamedialog.h |../../inc/rsfwnotpluginnamedialog.h +// export localised loc file +../loc/rsfwnotplugindialog.loc MW_LAYER_LOC_EXPORT_PATH(rsfwnotplugindialog.loc) + +PRJ_MMPFILES +rsfwnotplugin.mmp diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/group/rsfwnotplugin.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/group/rsfwnotplugin.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,72 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project rsfw notifier plugins +* +*/ + + +#include +#include + +TARGET rsfwnotplugin.dll +TARGETTYPE PLUGIN +UID 0x10009D8D 0x101F9770 + +CAPABILITY CAP_ECOM_PLUGIN +VENDORID VID_DEFAULT + +SOURCEPATH ../src +SOURCE rsfwnotplugindlg.cpp +SOURCE rsfwnotpluginnamedialog.cpp +SOURCEPATH ../../MDebug/src +SOURCE mdebug.cpp + +// ECom resource file +SOURCEPATH ../data +START RESOURCE 101f9770.rss + TARGET rsfwnotplugin.rsc +END // ECom resource file + +// Notifier resource file +START RESOURCE rsfwnotplugindialog.rss +HEADER +TARGET rsfwnotplugindlg.rsc +TARGETPATH RESOURCE_FILES_DIR +LANGUAGE_IDS +END // RESOURCE + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +SYSTEMINCLUDE /epoc32/include/ecom +USERINCLUDE ../inc + +LIBRARY avkon.lib +LIBRARY commonengine.lib +LIBRARY commondialogs.lib +LIBRARY cone.lib +LIBRARY eikcoctl.lib +LIBRARY eikcore.lib +LIBRARY eikdlg.lib +LIBRARY eiksrv.lib +LIBRARY euser.lib +LIBRARY efsrv.lib +LIBRARY bafl.lib +LIBRARY sysutil.lib +LIBRARY aknnotify.lib +LIBRARY flogger.lib +LIBRARY eiksrvui.lib // CEikServAppUi + +DEFFILE rsfwnotplugin.def + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/inc/mydebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/inc/mydebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,32 @@ +/* +* Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug printing to a log file +* +*/ + +#ifndef MYDEBUG_H +#define MYDEBUG_H + +// Debug defines for Remote File Engine + +// MACROS +#define APPEND_TO_DEBUG_FILE + +// CONSTANTS +_LIT(KDebugDirName, "rsfwnotifier"); +_LIT(KDebugFileName, "rsfwnotifier.txt"); + +#endif // MYDEBUG_H + +// End of File \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/inc/rsfwauthenticationdlgrequest.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/inc/rsfwauthenticationdlgrequest.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,44 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Authentication dialog request to the notifier plugin +* +*/ + + +#ifndef T_RSFWAUTHENTICATIONDLGREQUEST_H +#define T_RSFWAUTHENTICATIONDLGREQUEST_H + +#include "e32cmn.h" + +#include "rsfwnotpluginrequest.h" + +/** +* Parameters for authentication dialog request +* +*/ +class TRsfwAuthenticationDlgRequest : public TRsfwNotPluginRequest + { +public: + // current username + TBuf iUserName; + + // current password + TBuf iPassword; + + }; + +// Package buffer to hold auht request parameter information +typedef TPckgBuf TRsfwAuthParamsPckg; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/inc/rsfwnotplugindlg.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/inc/rsfwnotplugindlg.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,263 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RSFW notifier server plugin +* +*/ + +#ifndef C_RSFWNOTPLUGIN_H +#define C_RSFWNOTPLUGIN_H + +#include +#include +#include // MEikSrvNotifierBase +#include +#include "rsfwauthenticationdlgrequest.h" +#include "rsfwsavetodlgrequest.h" +#include "rsfwnotpluginrequest.h" + +class CAknDialog; + + +IMPORT_C CArrayPtr* NotifierArray(); + +/** + * Remote Storage FW plugin to the notifier server. + * + * This plugin implements the custom global dialogs needed by + * Remote Storage Framework. + * + * @lib rsfwnotplugin.dll + * @since S60 v3.2 + */ +class CRsfwNotPluginDlg : public CActive, + public MEikSrvNotifierBase2, + public MAknMemorySelectionObserver, + public MProgressDialogCallback + { +public: + + static CRsfwNotPluginDlg* NewL(); + + ~CRsfwNotPluginDlg(); + + // for base class CActive + + /** + * From CActive + * Handles an active object's request completion event. + * + * @since S60 v3.2 + */ + void RunL(); + + /** + * From CActive + * Handles a leave occurring in the request completion event handler RunL(). + * + * @since S60 v3.2 + */ + TInt RunError(TInt aError); + + /** + * From CActive + * Implements cancellation of an outstanding request. + * + * @since S60 v3.2 + */ + void DoCancel(); + + // from base class MEikSrvNotifierBase2 + + /** + * From .MEikSrvNotifierBase2 + * Called when all resources allocated by notifiers should be freed. + * + * @since S60 v3.2 + * + */ + virtual void Release(); + + + /** + * From MEikSrvNotifierBase2 + * Called when a notifier is first loaded to allow any initial construction that is required. + * + * @since S60 v3.2 + * + */ + virtual MEikSrvNotifierBase2::TNotifierInfo RegisterL(); + + + /** + * From MEikSrvNotifierBase2 + * Return the priority a notifier takes and the channels it acts on. The return value may be varied + * at run-time. + * + * @since S60 v3.2 + */ + virtual MEikSrvNotifierBase2::TNotifierInfo Info() const; + + + /** + * From MEikSrvNotifierBase2 + * Start the notifier with data aBuffer and return an initial response. + * + * @since S60 v3.2 + * @param aBuffer Data that can be passed from the client-side. The format and + * meaning of any data is implementation dependent. + */ + virtual TPtrC8 StartL(const TDesC8& aBuffer); + + + /** + * From MEikSrvNotifierBase2 + * Start the notifier with data aBuffer. aMessage should be completed when the notifier is deactivated. + * May be called multiple times if more than one client starts the notifier. The notifier is immediately + * responsible for completing aMessage. + * + * @since S60 v3.2 + * @param aBuffer Data that can be passed from the client-side. The format and + * meaning of any data is implementation dependent. + * @param aReplySlot Identifies which message argument to use for the reply. + * This message argument will refer to a modifiable descriptor, a TDes8 type, + * into which data can be returned. The format and meaning of any returned data + * is implementation dependent. + @param aMessage Encapsulates a client request + */ + virtual void StartL(const TDesC8& aBuffer, TInt aReplySlot, const RMessagePtr2& aMessage); + + + /** + * From MEikSrvNotifierBase2 + * The notifier has been deactivated so resources can be freed and outstanding messages completed. + * + * @since S60 v3.2 + */ + virtual void Cancel(); + + + /** + * From MEikSrvNotifierBase2 + * Update a currently active notifier with data aBuffer. + * + * @since S60 v3.2 + * @param aBuffer Data that can be passed from the client-side. The format and + * meaning of any data is implementation dependent. + * @return A pointer descriptor representing data that may be returned. The format + * and meaning of any data is implementation dependent. + */ + virtual TPtrC8 UpdateL(const TDesC8& aBuffer); + + // from base class MAknMemorySelectionObserver + + /** + * From MAknMemorySelectionObserver + * Logic to decide whether the inputs given in the dialog are ok + * + * @since S60 v3.2 + * @param aMemory the selected memory + */ + TBool OkToExitL( CAknMemorySelectionDialog::TMemory aMemory ); + + // from base class MProgressDialogCallback + + /** + * From MProgressDialogCallback + * Callback we receive when a non-modal wait dialog is dismissed + * + * @since S60 v3.2 + * @param aButtonId the button user pressed + */ + void DialogDismissedL( TInt aButtonId ); + + private: + + /** + * C++ default constructor. + */ + CRsfwNotPluginDlg(); + + /** + * By default Symbian 2nd phase constructor is private. + */ + void ConstructL(); + + // New functions + + // Helpers + void HandleAsyncRequestL(); + + // show dialogs + TInt ShowAuthenticationDialogL(); + TBool ShowUnavailableRetryNoteL(); + TBool ShowSaveToDlgL(); + void ShowWaitNoteL(); + + /** + * Returns the type of given item index in CFileManagerItemProperties bitmask + * @param aFullPath Full path to item which type is needed.. + * @return CFileManagerItemProperties bitmask + */ + TUint32 FileTypeL( const TDesC& aFullPath ) const; + + void Cleanup(); + + TBool GetValidNameL(TDesC& aPath, TDes& aName); + + void ShowDiskFullNoteL( TBool aInternal ); + + void CancelL(); + + /** + * Temporarily disables 'app key', so that user cannot switch or close + * the app when global dialog is being displayed + */ + void BlockAppSwitching(); + void UnblockAppSwitching(); + + private: // Data + TInt iMethod; // See TRsfwNotPluginRequest::TRsfwNotPluginMethod + RMessagePtr2 iMessage; + TInt iReplySlot; + MEikSrvNotifierBase2::TNotifierInfo iInfo; + + // for all dialogs + TBuf iDriveName; + // for authentication dialog + HBufC* iUserName; + HBufC* iPassword; + + // param structs + TRsfwAuthParamsPckg* iAuthRequest; + TRsfwSaveToParamsPckg* iSaveToRequest; + + // Valid during showing a dialog + CAknDialog* iDialog; + CAknWaitDialog* iWaitDialog; + TBool iCancelled; + + // for save as dialog + HBufC* iFileName; + TInt iFileSize; + TBuf iCacheDrive; + CAknMemorySelectionDialog* iMemDialog; + HBufC* iCurrentRootPath; + RFs iFs; + + // + TBool iDialogDismissedCalled; + TBool iAppSwitchingBlocked; // is 'app key' disabled + }; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/inc/rsfwnotpluginnamedialog.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/inc/rsfwnotpluginnamedialog.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,91 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File name query dialog for "save as" dialog +* +*/ + + +#ifndef C_RSFWNOTPLUGINNAMEDIALOG_H +#define C_RSFWNOTPLUGINNAMEDIALOG_H + +#include + +// CONSTANTS +_LIT(KDot, "."); +_LIT(KNotPluginResourcePath, "rsfwnotplugindlg.rsc"); + +// CLASS DECLARATION + +/** + * Dialog for "rename file" query in the Notifier plugin + * This dialog is used to get a new name for a file from the user. + * It only returns when user has entered a name that is legal in + * Symbian file system + */ +class CRsfwNotPluginNameDialog : public CAknTextQueryDialog + { + public: // Constructors and destructor + + /** + * Two-phased constructor. + * @param aOldName Old name of the file, this will be the default name + * This contains the path, but the path is not shown to the user + * @param aNewName On return, the user entered new name of the file. + * Does not contain the path, as it is assumed to remain the same + * @return Newly created query dialog. + */ + IMPORT_C static CRsfwNotPluginNameDialog* NewL( const TDesC& aOldName, + TDes& aNewName, + RFs& aFs); + + /** + * Destructor. + */ + ~CRsfwNotPluginNameDialog(); + + protected: // from CAknTextQueryDialog + /** + * @see CAknTextQueryDialog + */ + TBool OkToExitL( TInt aButtonId ); + + private: + /** + * C++ default constructor. + */ + CRsfwNotPluginNameDialog( TDes& aNewName, RFs& aFs ); + + /** + * Symbian OS 2nd phase constructor. + * @param aOldName Old name of the file, this will be the default name + */ + void ConstructL( const TDesC& aOldName ); + + + /** + * Show simple error note if something is wrong with the name the user chose + * @param aTextId localized string + */ + void ShowSimpleInfoNoteL( + const TInt aTextId); + + + + private: // Data + /// Own: Old file name + HBufC* iOldName; + RFs& iFs; + }; + +#endif diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/inc/rsfwnotpluginrequest.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/inc/rsfwnotpluginrequest.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,68 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: notifier plugin request encapsulation +* +*/ + +#ifndef T_RSFWNOTPLUGINGREQUEST_H +#define T_RSFWNOTPLUGINGREQUEST_H + +const TUid KRsfwNotifierPluginUID = { 0x101F9770 }; + +// CONSTANTS +const TInt KRsfwMaxDrivenameLength = 20; +const TInt KRsfwMaxDriveletterLength = 2; +const TInt KRsfwMaxFileSizeString = 20; +const TInt KRsfwMaxUsernameLength = 50; +const TInt KRsfwMaxPasswordLength = 50; +const TInt KRsfwNotifierMsgDataMaxSize = 1024; + +/** +* Class TRsfwNotPluginRequest +* Base class for fixed sized requests transferred between client and plug-in +* notifier implementation. +* This is used internally. This should not be instantiated by the clients. +*/ +class TRsfwNotPluginRequest + { + public: + + /** + * List of supported functionalities in plug-in implementation + */ + enum TRsfwNotPluginMethod + { + ENoMethod, + EAuthenticationDlg, + ESaveToDlg, + EUnavailableRetryDlg, + // wait dialogs, note that these could come after EUnavailableRetryDlg + EConnectingDlg, + EFetchingDlg + }; + + + // method + TRsfwNotPluginMethod iMethod; + + // Drive Friendly name + TBuf iDriveName; + + + }; + +// Package buffer to hold parameter information +typedef TPckgBuf TRsfwRetryParamsPckg; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/inc/rsfwsavetodlgrequest.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/inc/rsfwsavetodlgrequest.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,48 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File selection dialog request to the notifier plugin +* +*/ + + +#ifndef T_RSFWSAVETODLGREQUEST_H +#define T_RSFWSAVETODLGREQUEST_H + +#include "e32cmn.h" + +#include "rsfwnotpluginrequest.h" + + +/** +* Class TRsfwSaveToDlgRequest +*/ +class TRsfwSaveToDlgRequest : public TRsfwNotPluginRequest + { + public: // New functions + + // File name + TBuf iFileName; + + // Drive letter + TBuf iCacheDrive; + + // File size as a string (in bytes) + TBuf iFileSize; + + }; + +// Package buffer to hold update parameter information +typedef TPckgBuf TRsfwSaveToParamsPckg; + +#endif \ No newline at end of file diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/loc/rsfwnotplugindialog.loc --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/loc/rsfwnotplugindialog.loc Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,32 @@ +/* +* Copyright (c) 2005-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Localization strings for notifier server plugin +* +*/ + +//d:Prompt text for username in username/password dialog +//l:popup_query_data_window +//w: +//r:3.2 +// +#define qtn_rd_query_username "%U username:" + +//d:Prompt text for passwordin username/password dialog +//l:popup_query_data_window +//w: +//r:3.2 +// +#define qtn_rd_query_password "Password:" + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/src/rsfwnotplugindlg.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/src/rsfwnotplugindlg.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,868 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RSFW notifier server plugin +* +*/ + + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include // CEikServAppUi + +#include "rsfwnotplugindlg.h" +#include "rsfwnotpluginnamedialog.h" +#include "mdebug.h" + +#include + +_LIT(KResourceFile, "z:\\resource\\RsfwNotPluginDlg.RSC"); // emulator + + +void CreateNotifierL(CArrayPtr* aNotifiers) + { + MEikSrvNotifierBase2* notifier; + notifier = CRsfwNotPluginDlg::NewL(); + CleanupStack::PushL(notifier); + aNotifiers->AppendL(notifier); + CleanupStack::Pop(notifier); + } + +EXPORT_C CArrayPtr* NotifierArray() + { + CArrayPtrFlat* notifiers + = new CArrayPtrFlat(1); + if (notifiers) + { + TRAPD(err, CreateNotifierL(notifiers)); + if(err) + { + notifiers->ResetAndDestroy(); + delete notifiers; + notifiers = NULL; + } + } + return(notifiers); + } + + + +CRsfwNotPluginDlg* CRsfwNotPluginDlg::NewL() + { + CRsfwNotPluginDlg* dlg = new(ELeave)CRsfwNotPluginDlg(); + CleanupStack::PushL(dlg); + dlg->ConstructL(); + CleanupStack::Pop(dlg); + return dlg; + } + +CRsfwNotPluginDlg::~CRsfwNotPluginDlg() + { + Cleanup(); + iFs.Close(); + if (iWaitDialog) + { + delete iWaitDialog; + } + // just in case make sure the app key is unblocked + UnblockAppSwitching(); + } + +void CRsfwNotPluginDlg::Cleanup() + { + + iMethod = TRsfwNotPluginRequest::ENoMethod; + iCancelled = EFalse; + iReplySlot = NULL; + + + if (iUserName) + { + delete iUserName; + iUserName = NULL; + } + + if (iPassword) + { + delete iPassword; + iPassword = NULL; + } + + if (iCurrentRootPath) + { + delete iCurrentRootPath; + iCurrentRootPath = NULL; + } + + + if (iMemDialog) + { + delete iMemDialog; + iMemDialog = NULL; + } + + if (iFileName) + { + delete iFileName; + iFileName = NULL; + } + + if (iAuthRequest) + { + delete iAuthRequest; + iAuthRequest = NULL; + } + + if (iSaveToRequest) + { + delete iSaveToRequest; + iSaveToRequest = NULL; + } + + if (iWaitDialog) + { + delete iWaitDialog; + iWaitDialog = NULL; + } + + } + +CRsfwNotPluginDlg::CRsfwNotPluginDlg() : CActive(EPriorityStandard), + iMethod(TRsfwNotPluginRequest::ENoMethod) + { + CActiveScheduler::Add(this); + } + +void CRsfwNotPluginDlg::ConstructL() + { + User::LeaveIfError(iFs.Connect()); + iAppSwitchingBlocked = EFalse; + } + +void CRsfwNotPluginDlg::RunL() + { + if(iMethod == TRsfwNotPluginRequest::ENoMethod) + return; // Notifier canceled or request signaled by other means + + HandleAsyncRequestL(); // show dialog + } + +TInt CRsfwNotPluginDlg::RunError(TInt aError) + { + DEBUGSTRING16(("CRsfwNotPluginDlg::RunError, error=%d",aError)); + UnblockAppSwitching(); + iMessage.Complete(aError); + Cleanup(); + return KErrNone; + } + +void CRsfwNotPluginDlg::DoCancel() + { + } + +/** + * Called when all resources allocated by notifiers shoudl be freed. + */ +void CRsfwNotPluginDlg::Release() + { + delete this; + } + +/** + * Called when a notifier is first loaded to allow any initial construction that is required. + */ +MEikSrvNotifierBase2::TNotifierInfo CRsfwNotPluginDlg::RegisterL() + { + iInfo.iUid = KRsfwNotifierPluginUID; + // Because there are some longer wait notes here, we use low priority + // (lower than ENotifierPriorityVLow). This allows e.g. VPN credentials dialog on + // top of the "Connecting..." wait note. + iInfo.iChannel = EAknNotifierChannelProgressDialog; + iInfo.iPriority = ENotifierPriorityVLow; + return iInfo; + } + +/** + * Return the priority a notifier takes and the channels it acts on. The return value may be varied + * at run-time. + */ +MEikSrvNotifierBase2::TNotifierInfo CRsfwNotPluginDlg::Info() const + { + return iInfo; + } + +/** + * Start the notifier with data aBuffer and return an initial response. + */ +TPtrC8 CRsfwNotPluginDlg::StartL(const TDesC8& /*aBuffer*/) + { + //Create and launch confirmation dialog using static function. + //The function returns True when the OK button is pressed. + return TPtrC8(NULL, 0); + } + +void CRsfwNotPluginDlg::HandleAsyncRequestL() + { + // Load resource file + CEikonEnv* eikEnv = CEikonEnv::Static(); + TFileName filename(KResourceFile); + RConeResourceLoader resLoader(*eikEnv); + User::LeaveIfError(resLoader.Open(filename)); + CleanupClosePushL(resLoader); + TInt result; + TBool okpressed = EFalse; + switch(iMethod) + { + + case TRsfwNotPluginRequest::EAuthenticationDlg: + DEBUGSTRING16(("CRsfwNotPluginDlg::HandleAsyncRequestL EAuthenticationDlg")); + okpressed = ShowAuthenticationDialogL(); + DEBUGSTRING16(("CRsfwNotPluginDlg::::ShowAuthenticationDialogL returned %d", okpressed)); + break; + case TRsfwNotPluginRequest::EUnavailableRetryDlg: + DEBUGSTRING16(("CRsfwNotPluginDlg::HandleAsyncRequestL EUnavailableRetryDlg")); + okpressed = ShowUnavailableRetryNoteL(); + break; + case TRsfwNotPluginRequest::ESaveToDlg: + DEBUGSTRING16(("CRsfwNotPluginDlg::HandleAsyncRequestL ESaveToDlg")); + okpressed = ShowSaveToDlgL(); + break; + case TRsfwNotPluginRequest::EConnectingDlg: + case TRsfwNotPluginRequest::EFetchingDlg: + ShowWaitNoteL(); + break; + default: + break; + + } + +// some message dialogs will be completed here, +// others from the DialogDismissedL callback +if (iMethod <= TRsfwNotPluginRequest::EUnavailableRetryDlg) + { + if(iCancelled) + { + iMessage.Complete(KErrCancel); + } + else + { + if(okpressed) + { + if (iMethod == TRsfwNotPluginRequest::EAuthenticationDlg) + { + iMessage.WriteL(iReplySlot, *iAuthRequest); + } + else if (iMethod == TRsfwNotPluginRequest::ESaveToDlg) + { + iMessage.WriteL(iReplySlot, *iSaveToRequest); + } + + result = KErrNone; + } + else + { + result = KErrCancel; + } + iMessage.Complete(result); + } + } + + CleanupStack::PopAndDestroy(&resLoader); + + } + +/** + * Start the notifier with data aBuffer. aMessage should be completed when the notifier is deactivated. + * May be called multiple times if more than one client starts the notifier. The notifier is immediately + * responsible for completing aMessage. + */ + +void CRsfwNotPluginDlg::StartL(const TDesC8& aBuffer, TInt aReplySlot, const RMessagePtr2& aMessage) + { + if(iMethod != TRsfwNotPluginRequest::ENoMethod) + { + aMessage.Complete(KErrInUse); + return; + } + + Cleanup(); + + // Read incoming parameters + TRsfwNotPluginRequest params; + TPckgC pckg( params ); + pckg.Set( aBuffer ); + iMethod = pckg().iMethod; + iDriveName = pckg().iDriveName; + + + if (iMethod == TRsfwNotPluginRequest::EAuthenticationDlg) + { + TRsfwAuthenticationDlgRequest authparams; + TPckgC authpckg( authparams ); + authpckg.Set( aBuffer ); + + // read parameters + iUserName = HBufC::NewL(KRsfwMaxUsernameLength); + TPtr username = iUserName->Des(); + username.Append(authpckg().iUserName); + iPassword = HBufC::NewL(KRsfwMaxPasswordLength); + TPtr psswd= iPassword->Des(); + psswd.Append(authpckg().iPassword); + } + else if (iMethod == TRsfwNotPluginRequest::ESaveToDlg) + { + TRsfwSaveToDlgRequest saveToparams; + TPckgC savepckg( saveToparams ); + savepckg.Set( aBuffer ); + + // read parameters + iFileName = HBufC::NewL(KMaxFileName); + TPtr filename = iFileName->Des(); + filename.Append(savepckg().iFileName); + iCacheDrive = savepckg().iCacheDrive; + TLex lex(savepckg().iFileSize); + lex.Val(iFileSize); + } + + + iMessage = aMessage; + iReplySlot = aReplySlot; + iStatus = KRequestPending; + TRequestStatus* status = &iStatus; + SetActive(); + User::RequestComplete(status, KErrNone); + + } + + +TBool CRsfwNotPluginDlg::ShowAuthenticationDialogL() + { + DEBUGSTRING16(("CRsfwNotPluginDlg::::ShowAuthenticationDialogL")); + + TBool returnValue = EFalse; + HBufC* firstprompt = NULL; + HBufC* secondprompt = NULL; + firstprompt = StringLoader::LoadLC( R_RD_QUERY_USERNAME, iDriveName ); + DEBUGSTRING16(("loaded firstprompt")); + secondprompt = StringLoader::LoadLC( R_RD_QUERY_PASSWORD); + + DEBUGSTRING16(("loaded secondprompt")); + iAuthRequest = new (ELeave) TRsfwAuthParamsPckg(); + TPtr username = iUserName->Des(); + TPtr password = iPassword->Des(); + CAknMultiLineDataQueryDialog* dlg = CAknMultiLineDataQueryDialog::NewL(username,password); + CleanupStack::PushL(dlg); + DEBUGSTRING16(("created dialog")); + dlg->SetPromptL(*firstprompt, *secondprompt); + DEBUGSTRING16(("set prompts")); + CleanupStack::Pop(dlg); + dlg->SetMaxLengthOfFirstEditor(KRsfwMaxUsernameLength); + dlg->SetMaxLengthOfFirstEditor(KRsfwMaxPasswordLength); + iDialog = dlg; + + BlockAppSwitching(); + TBool okButtonSelected = dlg->ExecuteLD(R_CUSTOM_USERNAMEPASSWD_DIALOG); + UnblockAppSwitching(); + + + if (okButtonSelected) + { + returnValue = ETrue; + (*iAuthRequest)().iUserName = username; + (*iAuthRequest)().iPassword = password; + } + + CleanupStack::PopAndDestroy(2, firstprompt); // secondprompt, firstprompt + return returnValue; + + } + +TBool CRsfwNotPluginDlg::ShowSaveToDlgL() + { + + TPtr filename = iFileName->Des(); + + CDesCArrayFlat* strings = new (ELeave) CDesCArrayFlat( 2 ); + CleanupStack::PushL( strings ); + strings->AppendL( filename ); + strings->AppendL( iDriveName ); + + TBool dialogCancelled = EFalse; + TBool fileSelected = EFalse; + iCurrentRootPath = HBufC::NewL(KMaxPath); + TPtr rootptr = iCurrentRootPath->Des(); + TPtr folderptr(NULL, 0); + + TInt saveSelection; + iSaveToRequest = new (ELeave) TRsfwSaveToParamsPckg(); + CAknQueryDialog* note = CAknQueryDialog::NewL(); + CleanupStack::PushL(note); + HBufC* saveprompt = StringLoader::LoadLC( R_RD_FILE_SAVE_FAIL, *strings); + note->SetPromptL(*saveprompt); + CleanupStack::PopAndDestroy(saveprompt); + CleanupStack::Pop(note); + + BlockAppSwitching(); + saveSelection = note->ExecuteLD(R_CUSTOM_SAVE_QUERY); + UnblockAppSwitching(); + + CleanupStack::PopAndDestroy(strings); // strings + + if (saveSelection == EAknSoftkeySave) + { + while (!fileSelected && !dialogCancelled) + { + CAknMemorySelectionDialog::TMemory selectedMem = + CAknMemorySelectionDialog::EPhoneMemory; + if (iMemDialog) + { + delete iMemDialog; + iMemDialog = NULL; + } + + iMemDialog = CAknMemorySelectionDialog::NewL(ECFDDialogTypeSave, EFalse); + CAknCommonDialogsBase::TReturnKey retvalue; + + iMemDialog->SetObserver(this); + retvalue = iMemDialog->ExecuteL(selectedMem, &rootptr, &folderptr); + if (retvalue) + { + CAknFileSelectionDialog* filedialog = CAknFileSelectionDialog::NewL(ECFDDialogTypeSave); + CleanupStack::PushL(filedialog); + HBufC* dialogtxt = NULL; + dialogtxt = StringLoader::LoadLC( R_RD_SELECT_DIR_BACK ); + filedialog->SetRightSoftkeyRootFolderL(*dialogtxt); + fileSelected = filedialog->ExecuteL(rootptr); + CleanupStack::PopAndDestroy(2, filedialog); // dialogtxt, filedialog + } + else + { + dialogCancelled = ETrue; + } + } + + } + else + { + dialogCancelled = ETrue; + } + + if (!dialogCancelled) + { + dialogCancelled = !GetValidNameL(rootptr, filename); + + } + + rootptr.Append(filename); + + if (!dialogCancelled) + { + (*iSaveToRequest)().iFileName= rootptr; + } + + + return !dialogCancelled; + + } + +void CRsfwNotPluginDlg::ShowWaitNoteL() + { + if (iWaitDialog) + { + delete iWaitDialog; + iWaitDialog = NULL; + } + + // We set visibilityDelayOff + // As we show wait dialog only for remote operations + // we can assumet that the length of the operation is always + // over 1.5 seconds.. + iWaitDialog = new( ELeave ) CAknWaitDialog( + reinterpret_cast< CEikDialog** >( &iWaitDialog ), + ETrue ); + + + // if user cancels the wait note, this is received via the callbakc. + iWaitDialog->SetCallback(this); + + switch (iMethod) + { + case TRsfwNotPluginRequest::EConnectingDlg: + // 'app key' will be unblocked in DialogDismissedL() + BlockAppSwitching(); + iWaitDialog->ExecuteLD(R_CONNECTING_WAIT_NOTE); + break; + case TRsfwNotPluginRequest::EFetchingDlg: + // 'app key' will be unblocked in DialogDismissedL() + BlockAppSwitching(); + iWaitDialog->ExecuteLD(R_FETCHING_WAIT_NOTE); + break; + } + } + + +TBool CRsfwNotPluginDlg::ShowUnavailableRetryNoteL() + { + HBufC* retryprompt = NULL; + retryprompt = StringLoader::LoadLC( R_RD_DRIVE_UNAVAILABLE, iDriveName ); + + CAknQueryDialog* note = CAknQueryDialog::NewL(); + CleanupStack::PushL(note); + note->SetPromptL(*retryprompt); + CleanupStack::Pop(note); + + BlockAppSwitching(); + TBool retryButtonSelected = note->ExecuteLD(R_CUSTOM_RETRY_QUERY); + UnblockAppSwitching(); + + CleanupStack::PopAndDestroy(retryprompt); + if (retryButtonSelected) + { + return ETrue; + } + else + { + return EFalse; + } + } + + + +TBool CRsfwNotPluginDlg::OkToExitL( CAknMemorySelectionDialog::TMemory aMemory ) + { + TBool returnValue = EFalse; + TPtr rootptr = iCurrentRootPath->Des(); + TPtr folderptr(NULL, 0); + iMemDialog->GetMemories( aMemory, &rootptr, &folderptr); + + TDriveUnit selectedDrive(iCurrentRootPath[0]); + TDriveUnit cacheDrive(iCacheDrive); + if (selectedDrive == cacheDrive) + { + // just move between one drive + returnValue = ETrue; + } + else if (aMemory == CAknMemorySelectionDialog::EMemoryCard) + { + if (SysUtil::MMCSpaceBelowCriticalLevelL(&iFs, iFileSize)) + { + ShowDiskFullNoteL(EFalse); + } + else + { + returnValue = ETrue; + } + } + else if (aMemory == CAknMemorySelectionDialog::EPhoneMemory) + { + if (SysUtil::FFSSpaceBelowCriticalLevelL(&iFs, iFileSize)) + { + ShowDiskFullNoteL(ETrue); + } + else + { + returnValue = ETrue; + } + } + else + { + // only allow memorycard or phone memory + returnValue = EFalse; + } + return returnValue; + } + +TBool CRsfwNotPluginDlg::GetValidNameL(TDesC& aPath, TDes& aName) + { + HBufC* fullPath = HBufC::NewLC(KMaxFileName); + TPtr pathPtr= fullPath->Des(); + pathPtr.Append(aPath); + pathPtr.Append(aName); + TBool renameFile = EFalse; + TBool userCancelled = EFalse; + TBool overwriteSelection = EFalse; + + + while (BaflUtils::FileExists(iFs, pathPtr) && !userCancelled && !overwriteSelection) + { + TUint32 fileType( 0 ); + fileType = FileTypeL( pathPtr ); + // returns KEntryAttReadOnly if file is read only or open + CAknQueryDialog* note = CAknQueryDialog::NewL(); + CleanupStack::PushL(note); + HBufC* queryprompt; + if (fileType & KEntryAttReadOnly) + { + TBool retValue; + queryprompt = StringLoader::LoadLC( R_RD_ITEM_RENAME_QUERY, aName); + note->SetPromptL(*queryprompt); + CleanupStack::PopAndDestroy(queryprompt); + CleanupStack::Pop(note); + retValue = note->ExecuteLD(R_RSFW_PLUGIN_RENAME_QUERY); + if (retValue) + { + renameFile = ETrue; + } + else + { + userCancelled = ETrue; + } + } + else + { + TBool retValue; + queryprompt = StringLoader::LoadLC( R_RD_ITEM_OVERWRITE_QUERY, aName); + note->SetPromptL(*queryprompt); + CleanupStack::PopAndDestroy(queryprompt); + CleanupStack::Pop(note); + retValue = note->ExecuteLD(R_RSFW_PLUGIN_OVERWRITE_QUERY); + if (!retValue) + { + renameFile = ETrue; + } + else + { + overwriteSelection = ETrue; + } + } + + + if (renameFile) + { + TBool retval; + CRsfwNotPluginNameDialog* dlg = + CRsfwNotPluginNameDialog::NewL( + pathPtr, aName, iFs); + dlg->SetMaxLength(KMaxFileName - aPath.Length()); + dlg->PrepareLC( R_RSFW_NOT_PLUGIN_FILE_NAME_QUERY ); + retval = dlg->RunLD(); + if (!retval) + { + userCancelled = ETrue; + } + else + { + // reset the path after user renamed the file + CleanupStack::PopAndDestroy(fullPath); + fullPath = HBufC::NewLC(KMaxFileName); + pathPtr= fullPath->Des(); + pathPtr.Append(aPath); + pathPtr.Append(aName); + } + } + + } + + CleanupStack::PopAndDestroy(fullPath); + + if (!userCancelled) + { + return ETrue; + } + else + { + return EFalse; + } + + + } + + + + +// --------------------------------------------------------- +// CRsfwNotPluginDlg::ShowDiskFullNoteL +// Show an out of disk note. +// --------------------------------------------------------- +// +void CRsfwNotPluginDlg::ShowDiskFullNoteL( TBool aInternal ) + { + + HBufC* message = NULL; + + if ( aInternal ) + { + message = StringLoader::LoadLC( R_RSFWPLUGIN_NOT_ENOUGH_MEMORY ); + } + else + { + message = StringLoader::LoadLC( R_RSFWPLUGIN_MMC_NOT_ENOUGH_MEMORY ); + } + + TRequestStatus status = KErrNone; + CAknGlobalNote* note = CAknGlobalNote::NewL(); + CleanupStack::PushL( note ); + note->SetSoftkeys( R_AVKON_SOFTKEYS_OK_EMPTY ); + note->ShowNoteL( status, EAknGlobalErrorNote, *message ); + User::WaitForRequest( status ); + + CleanupStack::PopAndDestroy( 2, message ); // note, message + } + + +// --------------------------------------------------------------------------- +// The notifier has been deactivated so resources can be freed and outstanding messages completed. +// --------------------------------------------------------------------------- +// +void CRsfwNotPluginDlg::Cancel() + { + DEBUGSTRING(("CRsfwNotPluginDlg::Cancel")); + TRAP_IGNORE(CancelL()); + DEBUGSTRING(("exiting CRsfwNotPluginDlg::Cancel")); + } + +// --------------------------------------------------------------------------- +// Called by Cancel() in order to catch the possible leaves. +// --------------------------------------------------------------------------- +// +void CRsfwNotPluginDlg::CancelL() + { + if ((iMethod >= TRsfwNotPluginRequest::EConnectingDlg) && + iWaitDialog) + { + DEBUGSTRING(("calling ProcessFinishedL()")); + iDialogDismissedCalled = EFalse; + iWaitDialog->ProcessFinishedL(); + // iWaitDialog->ProcessFinishedL() should call + // dialogdismissed, but for some reason this does not always + // happen (really looks and feels like a ) + // this extra help should save the day + if (!iDialogDismissedCalled) + { + DEBUGSTRING(("extra call to ProcessFinishedL()")); + DialogDismissedL(EAknSoftkeyDone); + } + } + Cleanup(); + } + +// --------------------------------------------------------------------------- +// Sets KEntryAttReadOnly if the file is read only, system or open +// --------------------------------------------------------------------------- +// +TUint32 CRsfwNotPluginDlg::FileTypeL( const TDesC& aFullPath ) const + { + TUint32 fileType(0); + // Full check for local and removable drives + TEntry entry; + TInt err( iFs.Entry( aFullPath, entry ) ); + + // Check if item was deleted outside this component + if ( err == KErrNotFound || err == KErrPathNotFound ) + { + User::Leave( err ); + } + + TBool fileOpen( EFalse ); + iFs.IsFileOpen( aFullPath, fileOpen ); + if ( fileOpen || entry.IsReadOnly() || entry.IsSystem() ) + { + fileType |= KEntryAttReadOnly; + } + + return fileType; + + } + +// --------------------------------------------------------------------------- +// Update a currently active notifier with data aBuffer. +// --------------------------------------------------------------------------- +// +TPtrC8 CRsfwNotPluginDlg::UpdateL(const TDesC8& /*aBuffer*/) + { + return TPtrC8(NULL, 0); + } + + +void CRsfwNotPluginDlg::DialogDismissedL( TInt aButtonId ) + { + DEBUGSTRING(("CRsfwNotPluginDlg::DialogDismissedL")); + iDialogDismissedCalled = ETrue; + + UnblockAppSwitching(); + + if (aButtonId == EAknSoftkeyCancel) + { + DEBUGSTRING(("Completing dialogrequest with KErrCancel")); + iMessage.Complete(KErrCancel); + } + else if (aButtonId == EAknSoftkeyDone) + { + DEBUGSTRING(("Completing dialogrequest with KErrNone")); + iMessage.Complete(KErrNone); + } + else + { + DEBUGSTRING16(("Completing dialogrequest with %d", aButtonId)); + iMessage.Complete(aButtonId); + } + } + +// --------------------------------------------------------------------------- +// CRsfwNotPluginDlg::BlockAppSwitching +// Temporarily disables 'app key', so that user cannot switch or close +// the app when global dialog is being displayed +// --------------------------------------------------------------------------- +// +void CRsfwNotPluginDlg::BlockAppSwitching( ) + { + if ( !iAppSwitchingBlocked ) + { + ((CEikServAppUi*)(CEikonEnv::Static())->EikAppUi()) + ->SuppressAppSwitching(ETrue); + iAppSwitchingBlocked = ETrue; + } + } + +// --------------------------------------------------------------------------- +// CRsfwNotPluginDlg::UnblockAppSwitching +// Enables 'app key' back +// --------------------------------------------------------------------------- +// +void CRsfwNotPluginDlg::UnblockAppSwitching( ) + { + if ( iAppSwitchingBlocked ) + { + ((CEikServAppUi*)(CEikonEnv::Static())->EikAppUi()) + ->SuppressAppSwitching(EFalse); + iAppSwitchingBlocked = EFalse; + } + } + +// --------------------------------------------------------------------------- +// ECOM interface +// --------------------------------------------------------------------------- +// +const TImplementationProxy ImplementationTable[] = + { + + IMPLEMENTATION_PROXY_ENTRY(0x101F9772,NotifierArray) + + }; + +EXPORT_C const TImplementationProxy* ImplementationGroupProxy(TInt& aTableCount) + { + aTableCount = sizeof(ImplementationTable) / sizeof(TImplementationProxy) ; + return ImplementationTable; + } + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/rsfwnotifierplugins/src/rsfwnotpluginnamedialog.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/rsfwnotifierplugins/src/rsfwnotpluginnamedialog.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,164 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File name query dialog for "save as" dialog +* +*/ + +// ============================ MEMBER FUNCTIONS =============================== + +#include +#include +#include +#include +#include "rsfwnotpluginnamedialog.h" + +// Left to right and right to left markers +_LIT( KDirectionalChars, "\x202A\x202B\x202C\x202D\x200E\x200F" ); + + + + +// ----------------------------------------------------------------------------- +// CRsfwNotPluginNameDialog::NewL +// +// ----------------------------------------------------------------------------- +// +EXPORT_C CRsfwNotPluginNameDialog* CRsfwNotPluginNameDialog::NewL( + const TDesC& aOldName, + TDes& aNewName, + RFs& aFs) + { + CRsfwNotPluginNameDialog* self = + new( ELeave ) CRsfwNotPluginNameDialog( + aNewName, aFs); + + CleanupStack::PushL( self ); + self->ConstructL( aOldName ); + CleanupStack::Pop( self ); + + return self; + } + +// ----------------------------------------------------------------------------- +// CRsfwNotPluginNameDialog::CRsfwNotPluginNameDialog +// C++ default constructor can NOT contain any code, that +// might leave. +// ----------------------------------------------------------------------------- +// +CRsfwNotPluginNameDialog::CRsfwNotPluginNameDialog( + TDes& aNewName, RFs& aFs ) : + CAknTextQueryDialog( aNewName ), iFs(aFs) + { + } + +// ----------------------------------------------------------------------------- +// CRsfwNotPluginNameDialog::ConstructL +// +// ----------------------------------------------------------------------------- +// +void CRsfwNotPluginNameDialog::ConstructL( const TDesC& aOldName ) + { + TParsePtrC name( aOldName ); + Text().Copy( name.NameAndExt() ); + iOldName = aOldName.AllocL(); + + // Strip any directionality markers to get pure name + TPtr ptr( iOldName->Des() ); + AknTextUtils::StripCharacters( ptr, KDirectionalChars ); + } + +// ----------------------------------------------------------------------------- +// CRsfwNotPluginNameDialog::~CRsfwNotPluginNameDialog +// Destructor +// ----------------------------------------------------------------------------- +// +CRsfwNotPluginNameDialog::~CRsfwNotPluginNameDialog() + { + delete iOldName; + } + +// ----------------------------------------------------------------------------- +// CRsfwNotPluginNameDialog::OkToExitL +// +// ----------------------------------------------------------------------------- +// +TBool CRsfwNotPluginNameDialog::OkToExitL( TInt aButtonId ) + { + TBool result( CAknTextQueryDialog::OkToExitL( aButtonId ) ); + + HBufC* userText = Text().AllocLC(); + TPtr ptrUserText( userText->Des() ); + + // Strip any directionality markers to get pure name + AknTextUtils::StripCharacters( ptrUserText, KDirectionalChars ); + + // Check file name + TBool isValidName( EFalse ); + TText badChar(NULL); + isValidName = iFs.IsValidName(*userText, badChar); + + + if( !isValidName ) + { + TBuf<5> dotbuf; + dotbuf.Append(KDot); + TChar dot(dotbuf[0]); + if (badChar == dot) + { + // dot is a special case, as "." or ".." are illegal file names + // but for example "file.name" is not, and thus dot is not mentioned + // in R_RD_FLDR_ILLEGAL_CHARACTERS + ShowSimpleInfoNoteL(R_RD_FLDR_BAD_FILE_NAME ); + } + else + { + ShowSimpleInfoNoteL(R_RD_FLDR_ILLEGAL_CHARACTERS ); + } + + CAknQueryControl* queryControl = QueryControl(); + if (queryControl) + { + CEikEdwin* edwin = static_cast< CEikEdwin* >( + queryControl->ControlByLayoutOrNull( EDataLayout ) ); + if (edwin) + { + edwin->SetSelectionL( edwin->TextLength(), 0 ); + } + } + CleanupStack::PopAndDestroy( userText ); + return EFalse; + } + CleanupStack::PopAndDestroy( userText ); + return result; + + } + + +// ------------------------------------------------------------------------------ +// CRsfwNotPluginNameDialog::ShowSimpleInfoNoteL +// +// ------------------------------------------------------------------------------ +// +void CRsfwNotPluginNameDialog::ShowSimpleInfoNoteL( + const TInt aTextId) + { + HBufC* text = NULL; + text = StringLoader::LoadLC( aTextId ); + CAknInformationNote* dlg = new(ELeave) CAknInformationNote( ETrue ); + dlg->ExecuteLD( *text ); + CleanupStack::PopAndDestroy( text ); + } + + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/data/101f9769.rss --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/data/101f9769.rss Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,57 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: ECOM registration for DavAccess +* +*/ + + +// INCLUDES +#include "registryinfo.rh" + +// RESOURCE DEFINITIONS +// ----------------------------------------------------------------------------- +// +// REGISTRY_INFO theInfo +// Declares info for the "remoteaccess/http" implementation +// +// ----------------------------------------------------------------------------- +// +RESOURCE REGISTRY_INFO theInfo + { + // UID for the DLL + dll_uid = 0x101F9769; + // Declare array of interface info + interfaces = + { + INTERFACE_INFO + { + // UID of interface that is implemented + interface_uid = 0x101F96E3; + implementations = + { + // Info for CDavAccess + IMPLEMENTATION_INFO + { + implementation_uid = 0x101F9769; + version_no = 1; + display_name = "http"; + default_data = "remoteaccess/http||WebDAV"; + opaque_data = "params"; + } + }; + } + }; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,22 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Build info for DavAccess +* +*/ + + +PRJ_MMPFILES +rsfwdavaccess.mmp + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/group/rsfwdavaccess.mmp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/group/rsfwdavaccess.mmp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,68 @@ +/* +* Copyright (c) 2003-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Project definition file for project WebDAV Access plug-in +* +*/ + +#include + +TARGET rsfwdavaccess.dll +TARGETTYPE PLUGIN + + +UID 0x10009D8D 0x101F9769 +CAPABILITY ALL -TCB + +// Classes in webdavsession.cpp call many times +// classes in propfindparser.cpp and lockqueryparser.cpp, +// so in ideal case these should be linked next to each other +// in the binary - don't know if the order here helps anything though.... +SOURCEPATH ../src +SOURCE rsfwdavproxy.cpp +SOURCE rsfwdavaccess.cpp +SOURCE rsfwdavaccesscontext.cpp +SOURCE rsfwdavfileinfo.cpp +SOURCE rsfwdavtransaction.cpp +SOURCE rsfwdavsession.cpp +SOURCE rsfwpropfindparser.cpp +SOURCE rsfwlockqueryparser.cpp +SOURCEPATH ../../MDebug/src +SOURCE mdebug.cpp + +MW_LAYER_SYSTEMINCLUDE +SYSTEMINCLUDE ../../../inc +SYSTEMINCLUDE ../../inc +SYSTEMINCLUDE /epoc32/include/libc +SYSTEMINCLUDE /epoc32/include/ecom +SYSTEMINCLUDE /epoc32/include/networking // dns error codes +USERINCLUDE ../inc + +SOURCEPATH ../data +START RESOURCE 101f9769.rss +HEADER +TARGET rsfwdavaccess.rsc +TARGETPATH resource/plugins +END + +// RESOURCE davaccess.rss + +LIBRARY bafl.lib +LIBRARY ecom.lib +LIBRARY efsrv.lib +LIBRARY euser.lib +LIBRARY http.lib +LIBRARY inetprotutil.lib +LIBRARY rsfwcommon.lib +LIBRARY xmlframework.lib +LIBRARY flogger.lib diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/mydebug.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/mydebug.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,31 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Debug definitions for DavAccess +* +*/ + + +#ifndef MYDEBUG_H +#define MYDEBUG_H + +// MACROS +#define APPEND_TO_DEBUG_FILE + +// CONSTANTS +_LIT(KDebugDirName, "davaccess"); +_LIT(KDebugFileName, "davaccess.txt"); + +#endif // MYDEBUG_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwdavaccess.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwdavaccess.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,235 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: WebDAV plugin interface for RSFW + * +*/ + + +#ifndef CRSFWDAVACCESS_H +#define CRSFWDAVACCESS_H + +// INCLUDES +//#include + +#include "rsfwremoteaccess.h" +#include "rsfwdavsession.h" +//#include "rsfwdavfileinfo.h" +#include "rsfwconnectionmanager.h" + +// CONSTANTS +const TInt KCommRetries = 3; + +// DATA TYPES +enum TRemoteAccessOp + { + ERemoteAccessOpNone = 0, + ERemoteAccessOpOpen, + ERemoteAccessOpGetDirectory, + ERemoteAccessOpGetDirectoryAttributes, + ERemoteAccessOpGetFileAttributes, + ERemoteAccessOpSetAttributes, + ERemoteAccessOpGetFile, + ERemoteAccessOpMakeDirectory, + ERemoteAccessOpCreateFile, + ERemoteAccessOpPutFile, + ERemoteAccessOpDeleteDirectory, + ERemoteAccessOpDeleteFile, + ERemoteAccessOpRename, + ERemoteAccessOpObtainLock, + ERemoteAccessOpReleaseLock, + ERemoteAccessOpRefreshLock + }; + +// FORWARD DECLARATIONS +class CRsfwDavAccessContext; +//class CRsfwDirEnt; +//class CRsfwDirEntAttr; + +// CLASS DECLARATION + +/** + * WebDAV protocol plugin for Rsfw + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ + +class CRsfwDavAccess: public CRsfwRemoteAccess, + public MRsfwDavResponseObserver, + public MRsfwConnectionObserver + { +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + static CRsfwDavAccess* NewL(); + + /** + * Destructor. + */ + virtual ~CRsfwDavAccess(); + +public: // New functions + + /** + Return information about the given object + @param aPath path of the object + @return file information + */ + CRsfwDavFileInfo* DavFileInfoL(const TDesC& aPath); + + /** + Add information about the given object + @param aDavFileInfo information about the object + */ + void AddDavFileInfo(CRsfwDavFileInfo* aDavFileInfo); + + /** + Remove all information about the given object + @param aPath path of the object + @return file information + */ + void RemoveDavFileInfoL(const TDesC& aPath); + + /** + Return the WebDAV session object + @return WebDAV session + */ + inline CRsfwDavSession* WebDavSession() { return iWebDavSession; }; + + /** + Return next access context id + @return id + */ + inline TUint GetNextAccessContextId() { return ++iCurrentDavContextId; }; + +public: // Functions from base classes + // From CRsfwRemoteAccess + void SetupL(MRsfwRemoteAccessObserver* aRsfwRemoteAccessObserver); + + /* In this plug-in aAuxData is the access point + special values for IAP selection + DefaultPreferences = * + AskUser = ? + */ + TUint OpenL(const TUriC& aUri, + const TDesC& aFriendlyName, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aAuxData, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint GetDirectoryL(const TDesC& aPathName, + RPointerArray& aDirEnts, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint GetDirectoryAttributesL( + const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint GetFileAttributesL(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint SetAttributesL(const TDesC& aPathName, + CRsfwDirEntAttr& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint GetFileL(const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint PutFileL(const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint PutFileL(const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint CreateFileL(const TDesC& aPathName, + TBool aIsOverwriting, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint MakeDirectoryL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint DeleteDirectoryL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint DeleteFileL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint RenameL(const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint ObtainLockL(const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8*& aLockToken, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint ReleaseLockL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + TUint RefreshLockL(const TDesC& aPathName, + TUint& aTimeout, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + + void Cancel(TUint aId); + + void Cancel(TDesC& aTargetPath); + + TInt SetLockToken(const TDesC& aPathName, const TDesC8& aLockToken); + + // From MRsfwDavResponseObserver + void RequestCompleteL(TUint aWebDavTransactionId); + void RequestError(TUint aWebDavTransactionId, TInt aStatus); + + // From MRsfwConnectionObserver + void HandleConnectionEventL(TInt aConnectionEvent, TAny* aArg); + +private: + void ConstructL(); + TUint AddAccessContext(CRsfwDavAccessContext* aDavAccessContext); + TInt LookupAccessContextByTransactionId(TUint aWebDavTransactionId); + TInt LookupAccessContextByContextId(TUint aId); + TInt LookupAccessContextByPath(TDesC& aTargetPath); + TInt DavFileInfoIndexL(const TDesC& aPath); + TUint OptionsL(MRsfwRemoteAccessResponseHandler* aResponseHandler); + void SetLockTokenL(const TDesC& aPathName, const TDesC8& aLockToken); + +private: // Data + TBuf iRootDirectory; + CRsfwDavSession* iWebDavSession; + RPointerArray iDavFileInfos; + RPointerArray iDavAccessContexts; + TUint iCurrentDavContextId; + MRsfwRemoteAccessObserver* iRsfwRemoteAccessObserver; + }; + +#endif // CRSFWDAVACCESS_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwdavaccesscontext.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwdavaccesscontext.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,589 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Contexts for keeping transaction state + * +*/ + + +#ifndef CRSFWDAVACCESSCONTEXT_H +#define CRSFWDAVACCESSCONTEXT_H + +// INCLUDES +#include +//#include + +#include "rsfwremoteaccess.h" +//#include "rsfwdavsession.h" +#include "rsfwdavtransaction.h" +//#include "rsfwdavfileinfo.h" + +// FORWARD DECLARATIONS +class CRsfwDavAccess; +//class CRsfwDirEntAttr; + +// CONSTANTS +const TInt KMaxMimeTypeLength = 64; + +// CLASS DECLARATIONS + +/** + * WebDAV access contexts (state machines) + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ + +class CRsfwDavAccessContext : public CBase + { +public: // Constructors and destructor + /** + * Destructor. + */ + virtual ~CRsfwDavAccessContext(); + +public: // New functions + /** + * This is used for GET and PUT operations, to allow cancelling + * the operations by target path name (local dialog from File Manager will + * call CancelByPath) + * @return TDesC, the target path for the operation + */ + virtual const TDesC& TargetPath(); + + /** + * Start transaction + */ + virtual void StartL() = 0; + + /** + * Receive a notification of a complete transaction + */ + virtual void TransactionCompleteL() = 0; + + /** + * Receive a notification of a failed transaction + * @param aError error code + */ + virtual void TransactionError(TInt aError) = 0; + + + /** + * Return the underlying WebDAV transaction + * @return WebDAV transaction + */ + inline CRsfwDavTransaction* WebDavTransaction() + { return iWebDavTransaction; }; + + /** + * Set context id + * @param aId id + */ + inline void SetId(TUint aId) { iId = aId; }; + + /** + * Get id of the current WebDAV transaction + * @return id + */ + inline TUint WebDavTransactionId() { return iWebDavTransactionId; }; + + /** + * Get context id + * @return id + */ + inline TUint Id() { return iId; }; + + /** + * Get context status + * @return status + */ + inline TUint Status() { return iStatus; }; + + /** + * Get response handler + * @return response handler + */ + inline MRsfwRemoteAccessResponseHandler* ResponseHandler() + { return iResponseHandler; }; + + /** + * Tell wether the context is in finished state + * @return ETrue, if the context has finished + */ + inline TBool Done() { return iDone; }; + + +protected: // New functions + /** + * Submit transaction + * @return none + */ + void SubmitL(); + + /** + * Retry transaction + * @return none + */ + void Retry(); + + /** + * Map HTTP error code to SymbianOS error code + * @param aError, input and output error code + */ + void MapError(TInt& aError); + + +protected: // Data + TUint iId; + CRsfwDavAccess* iDavAccess; + TUint iStatus; + MRsfwRemoteAccessResponseHandler* iResponseHandler; + CRsfwDavTransaction* iWebDavTransaction; + TUint iWebDavTransactionId; + TBool iDone; + TInt iTryCount; + // allows to cancel the operation by path + TBufC iRemotePathName; + + }; + +// --------------------------------------------------------------------- +// Options +// --------------------------------------------------------------------- + +class CRsfwDavAccessContextOptions: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + */ + static CRsfwDavAccessContextOptions* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler); + }; + +// ----------------------------------------------------------------- +// PropFindDir +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextPropFindDir: public CRsfwDavAccessContext + { +public: // Constructors and destructor + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextPropFindDir* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TInt aDepth, + CRsfwDirEntAttr** aDirEntAttr, + RPointerArray* aDirEnts); + + /** + * Destructor. + */ + virtual ~CRsfwDavAccessContextPropFindDir(); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TInt aDepth, + CRsfwDirEntAttr** aDirEntAttr, + RPointerArray* aDirEnts); +private: // Data + TInt iDepth; + CRsfwDirEntAttr** iDirEntAttr; + RPointerArray* iDirEnts; + RPointerArray iOwnDirEnts; + }; + +// ----------------------------------------------------------------- +// PropFindFile +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextPropFindFile: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextPropFindFile* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + CRsfwDirEntAttr** aDirEntAttr); + + /** + * Destructor. + */ + virtual ~CRsfwDavAccessContextPropFindFile(); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + CRsfwDirEntAttr** aDirEntAttr); + +private: // Data + CRsfwDirEntAttr** iDirEntAttr; + RPointerArray iOwnDirEnts; + }; + +// ----------------------------------------------------------------- +// Get +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextGet: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextGet* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags); + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags); + +private: // Data + TBufC iLocalPathName; + TInt iOffset; + TInt* iLength; + TUint iFlags; + }; + +// ----------------------------------------------------------------- +// Put +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextPut: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextPut* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + const TDesC8* aLockToken); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + const TDesC8* aLockToken); + +private: // Data + TBufC iLocalPathName; + TBufC8 iMimeType; + TInt iOffset; + TInt iLength; + TInt iTotalLength; + const TDesC8* iLockToken; + + // The recipient of the entity MUST NOT ignore any Content-* + // (e.g. Content-Range) headers that it does not understand or implement + // and MUST return a 501 (Not Implemented) response in such cases. + TBool iContentRangeSupported; + }; + +// ----------------------------------------------------------------- +// MkDir +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextMkDir: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextMkDir* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName); + }; + +// ----------------------------------------------------------------- +// Delete +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextDelete: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextDelete* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TBool aIsDir, + const TDesC8* aLockToken); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TBool aIsdir, + const TDesC8* aLockToken); + +private: // Data + TBool iIsDir; + const TDesC8* iLockToken; + }; + +// ----------------------------------------------------------------- +// Move +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextMove: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextMove* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + const TDesC8* aSrcLockToken, + const TDesC8* aDstLockToken); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + const TDesC8* aSrcLockToken, + const TDesC8* aDstLockToken); + +private: // Data + TBufC iSrcPathName; + const TDesC8* iSrcLockToken; + const TDesC8* iDstLockToken; + TBool iOverwrite; + }; + +// ----------------------------------------------------------------- +// Lock +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextLock: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextLock* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8** aLockToken); + + /** + * Destructor. + */ + virtual ~CRsfwDavAccessContextLock(); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8** aLockToken); + +private: // Data + TUint iLockFlags; + TUint* iTimeout; + TDesC8** iLockToken; + CRsfwDavFileInfo* iDavFileInfo; + }; + +// ----------------------------------------------------------------- +// RefreshLock +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextRefreshLock: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextRefreshLock* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken, + TUint& aTimeout); + + /** + * Destructor. + */ + virtual ~CRsfwDavAccessContextRefreshLock(); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken, + TUint& aTimeout); + +private: // Data + TBufC iPathName; + const TDesC8* iLockToken; + TUint* iTimeout; + CRsfwDavFileInfo* iDavFileInfo; + }; + +// ----------------------------------------------------------------- +// Unlock +// ----------------------------------------------------------------- + +class CRsfwDavAccessContextUnlock: public CRsfwDavAccessContext + { +public: + /** + * Two-phased constructor. + * + */ + static CRsfwDavAccessContextUnlock* NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken); + +public: // Functions from base classes + // From CRsfwDavAccessContext + void StartL(); + void TransactionCompleteL(); + void TransactionError(TInt aError); + +private: + void ConstructL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken); + +private: // Data + const TDesC8* iLockToken; + }; + +#endif // CRSFWDAVACCESSCONTEXT_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwdavdefs.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwdavdefs.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,148 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: WebDAV specific constant definitions +* +*/ + + +#ifndef RSFWDAVDEFS_H +#define RSFWDAVDEFS_H + +// CONSTANTS +// max name for the server +const TInt KMaxServerNameLen = 210; + +// max length for each connection parameter +// (username, password etc.) +const TInt KMaxConnParameter = 64; + +// Size of buffer used when submitting request bodies (PUT, PROPFIND...) +const TInt KDefaultSubmitSize = 14000; + +// Size of buffer used when reading a reply to file (like GET) +const TInt KDefaultFileBufferSize = 81800; + +// maximum length for range, content-range +// or timeout header values +const TInt KMaxFieldValueLength = 64; + +// length for the DAV version, which should be simply DAV: 1 or DAV: 1,2 +const TInt KMaxDavVersionValue = 15; + +const TInt KDavResourceTypeCollection = 1; +const TInt KDavResourceTypeOther = 0; +const TInt KDavVersionTwo = 2; + +// expat XML-parser wants the data in the chunks of 2k +// actually crashes otherwise... +const TInt KSymbianXmlParserMaxData = 2048; + +// overhead of UTF-8 encoding +const TInt KEncodingOverhead = 2; + +// length of "http://" +const TInt KProtocolPrefix = 7; + +// when building " ()" +const TInt KTaggedLockTokenOverhead = 7; + +// when building "" +const TInt KLockTokenOverhead = 2; + +_LIT8(KUserAgent,"S60 Remote Storage WebDav client"); +_LIT8(KAccept, "*/*"); +_LIT8(KTextXml, "text/xml"); +_LIT8(KTextPlain, "text/plain"); +_LIT8(KSecondDash, "Second-"); + +_LIT8(KParenthAngleFormat, "(<%S>)"); +_LIT8(KTaggedParenthAngleFormat, "<%S> (<%S>)"); +_LIT(KDateFormat,"%D%M%Y%/0%1%/1%2%/2%3%/3 %:0%H%:1%T%:2%S.%C%:3"); + +_LIT(KWebDavClientPanic, "WEBDAV-EC"); + +_LIT8(KWebDavPropFind, "PROPFIND"); +_LIT8(KWebDavMkCol, "MKCOL"); +_LIT8(KWebDavDelete, "DELETE"); +_LIT8(KWebDavCopy, "COPY"); +_LIT8(KWebDavPut, "PUT"); +_LIT8(KWebDavOptions, "OPTIONS"); +_LIT8(KWebDavMove, "MOVE"); +_LIT8(KWebDavLock, "LOCK"); +_LIT8(KWebDavUnlock, "UNLOCK"); + +_LIT8(KWebDavDepth, "Depth"); +_LIT8(KWebDavIf, "If"); +_LIT8(KWebDavDest, "Destination"); +_LIT8(KWedDavLockToken, "Lock-Token"); +_LIT8(KWebDavTimeout, "Timeout"); +_LIT8(KWebDavOverwrite, "Overwrite"); +_LIT8(KWebDavOverwriteY,"T"); +_LIT8(KWebDavOverwriteN,"F"); +_LIT8(KWebDavNoProxy, "no-cache"); +_LIT8(KKeepAlive, "keep-alive"); + + +class RsfwDavStatus +/** +Status code extensions to HTTP/1.1 +Defined in RFC 2518 (WebDAV) +*/ + { +public: + enum TRsfwDavStatus + { + /** 'Informational' range of codes 1xx */ + EProcessing = 102, + /** 'Successful' range of codes 2xx */ + EMultiStatus = 207, + /** 'Client Error' range of codes 4xx */ + EUnprocessableEntity = 422, + ELocked = 423, + EFailedDependency = 424, + /** 'Server Error' range of codes 5xx */ + EInsufficientStorage = 507 + }; + }; + + +// DATA TYPES +enum TWebDavClientPanics + { + EReqBodySumitBufferNotAllocated, + KBodyWithInvalidSize, + KCouldntNotifyBodyDataPart, + KOutOfMemory + }; + +enum TWebDavOp + { + EWebDavOpNone, + EWebDavOpOptions, + EWebDavOpGet, + EWebDavOpPut, + EWebDavOpDelete, + EWebDavOpPropFindSingle, + EWebDavOpPropFindMulti, + EWebDavOpMkCol, + EWebDavOpMove, + EWebDavOpLock, + EWebDavOpUnlock, + EWebDavOpRefreshLock + }; + + +#endif // RSFWDAVDEFS_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwdavfileinfo.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwdavfileinfo.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,141 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Cache for file metadata + * +*/ + + +#ifndef CRSFWDAVFILEINFO_H +#define CRSFWDAVFILEINFO_H + +// INCLUDES +#include + +// CLASS DECLARATION + +class TRsfwDavFileInfoFlags + { +public: + enum TDavFileInfoFlag + { + EUnlockPending = 0x01 + }; + }; + +// CLASS DECLARATION + +/** + * WebDAV file information object + * Used by DAV access module to handle file locking + * This information is thus internal to WebDAV access module + * and separated from metadata that is passed to Remote File Engine + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ + +class CRsfwDavFileInfo : public CBase + { +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + static CRsfwDavFileInfo* NewL(); + + /** + * Destructor. + */ + ~CRsfwDavFileInfo(); + +public: // New functions + + /** + * Get name + * @return name + */ + HBufC* Name(); + + /** + * Set name + * @param aName name + */ + void SetNameL(const TDesC& aName); + + /** + * Get lock token + * @return lock token + */ + HBufC8* LockToken(); + + /** + * Set lock token + * @param aLockToken lock token + */ + void SetLockTokenL(const TDesC8& aLockToken); + + /** + * Clear lock token + */ + void ResetLockToken(); + + /** + * Get lock timeout + * @return lock timeout + */ + TUint Timeout(); + + /** + * Set timeout + * @param aTimeout timeout + */ + void SetTimeout(TUint aTimeout); + + /** + * Check if a flag is set + * @param aFlag flag mask (only supports a single bit) + * @return ETrue if the flag is set + */ + TBool IsFlag(TUint aFlag); + + /** + * Set a flag bit + * @param aFlag flag bit to be set + */ + void SetFlag(TUint aFlag); + + /** + * Clear a flag bit + * @param flag bit to be cleared + */ + void ResetFlag(TUint aFlag); + +private: + void SetL(HBufC*& aDst, const TDesC& aSrc); + void SetL(HBufC8*& aDst, const TDesC8& aSrc); + +private: // Data + // These are used when constructing messages, thus 8 bit + HBufC* iName; + HBufC8* iLockToken; + + // Active lock info: + // lock timeout + TUint iTimeout; + // lock flags (currently always write lock) + TUint iFlags; + }; + +#endif // CRSFWDAVFILEINFO_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwdavsession.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwdavsession.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,357 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: WebDAV session + * +*/ + + +#ifndef CRSFWDAVSESSION_H +#define CRSFWDAVSESSION_H + +// INCLUDES +#include +#include +#include "rsfwdavdefs.h" + + +// FORWARD DECLARATIONS +class CRsfwDavTransaction; +class CRsfwDavFileInfo; +class CRsfwPropFindParser; +class CRsfwConnectionManager; +class MRsfwDavResponseObserver; +class MRsfwConnectionObserver; +class CRsfwLockQueryParser; +class CRsfwDirEnt; + +// CLASS DECLARATION +/** + * Response handler for WebDAV requests + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ +class MRsfwDavResponseObserver + { +public: + /** + * Receive a notification of a completed request. + * @param aWebDavTransactionId id of the request. + */ + virtual void RequestCompleteL(TUint aWebDavTransactionId) = 0; + + /** + * Receive a notification of a failed request. + * @param aWebDavTransactionId id of the request. + */ + virtual void RequestError(TUint aWebDavTransactionId, TInt aStatus) = 0; + }; + + +// CLASS DECLARATION +/** + * WebDAV session + * + * Class created for the interface to webdav client library + * Designed to encapsulate http,xml stuff + * Intended for communicating with one server at a time ! + * + * Uses http transport framework: can do SSL, Basic + Digest Auth + * Uses symbian xmllib library for parsing + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ +class CRsfwDavSession: public CBase, + public MHTTPAuthenticationCallback + { +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + static CRsfwDavSession* + CRsfwDavSession::NewL(MRsfwDavResponseObserver* aWebDavResponseObserver, + MRsfwConnectionObserver* aRsfwConnectionObserver); + /** + * Destructor. + */ + virtual ~CRsfwDavSession(); + +public: // New functions + /** + @function OpenL + @discussion Opens the HTTP session and + sets up parameters for the session + @param aHost The full URI of the server + including the path to the root directory + @param aPort The port to connect to there + @param aUserName UserName to be used in Http basic or digest auth there + @param aPassword Password to be used in Http basic or digest auth there + @param aAuxData Auxiliary information used for IAP selection + */ + void OpenL(const TDesC& aHost, + TInt aPort, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aAuxData); + + /** + @function OptionsL + @discussion Runs an OPTIONS command to the passed uri to see if its + available and force the authentication to run + @return nothing + */ + CRsfwDavTransaction* OptionsL(); + + /** + @function PropFindL + @discussion Runs a PROPFIND command against the current server. + Tells the server to only look for name, size related properties + @param aPath The path relative to the root which should be used + @param aIsDir Indicates whether the path points to a directory or a file + @param aDirEnts Directory entry array to be filled + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* PropFindL(const TDesC& aPath, + TInt aDepth, + TBool aIsDir, + RPointerArray& aDirEnts); + + /** + @function GetL + @discussion Runs GET command against the server + @param aSrcPath The name of the resource to be fetched: + expects this to be the path relative to the root directory + @param aDstPath The path of the local file where the data is fetched + @param aOffset offset from the start of the file + @param aLength data length (can be NULL) + @param aFlags operation options (see RemoteAccess.h) + @return pointer to the submitted WebDAV transaction + */ + // == GET + CRsfwDavTransaction* GetL(const TDesC& aSrcPath, + const TDesC& aDstPath, + TInt aOffset, + TInt* aLength, + TUint aFlags); + + /** + @function PutL + @discussion Runs PUT command against the server + @param aSrcPath The name of the resource to be copied: + expects this to be an absolute path + @param aDstPath The name of the resource to be created on the server: + expected to be the path relative to the root directory + @param aMimeType The MIME-type of the file + @param aOffset offset from the start of the file + @param aLength data length (can be NULL) + @param aTotalLength The total length, can be 0 if aLength is NULL or 0 + @param aUseContentRange Whether the server is assumed to support + Content-Range- header + @param aLocktoken Possible lock token + @return pointer to the submitted WebDAV transaction + */ + // == PUT + CRsfwDavTransaction* PutL(const TDesC& aSrcPath, + const TDesC& aDstPath, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + TBool aUseContentRange, + const TDesC8* aLockToken = NULL); + + /** + @function DeleteL + @discussion Runs DELETE command against the server + @param aResource The name of the resource to be deleted: + expects this to be the path relative to the root directory + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* DeleteL(const TDesC& aPath, + TBool aDir, + const TDesC8* aLockToken = NULL); + + /** + @function MkDirL + @discussion Runs MKCOL webdav command against the server + @param aPath The name of the directory to be made: + expects this to be the path relative to the root directory + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* MkDirL(const TDesC& aPath); + + /** + @function MoveL + @discussion Runs MOVE command against the server + @param aOldPath The name of the resource to be renamed: + expects this to be the path relative to the root directory + @param aNewPath The new name of the resource + to be created on the server: + expected to be the path relative to the root directory + @param aOverwrite Specifies + whether the server should overwrite a non-null destination resource + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* MoveL(const TDesC& aOldPath, + const TDesC& aNewPath, + TBool aOverwrite, + const TDesC8* aSrcLockToken, + const TDesC8* aDstLockToken); + + /** + @function LockL + @discussion Runs LOCK command against the server + @param aPath the resource to be locked: + expects this to be the path relative to the root directory + @param aFlags flags + @param aTimeout lock timeout in seconds + @param aDavFileInfo the location where collected file info should be set + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* LockL(const TDesC& aPath, + TUint aFlags, + TUint aTimeOut, + CRsfwDavFileInfo** aDavFileInfo); + + /** + @function UnlockL + @discussion Runs UNLOCK command against the server + @param aPath the resource to be locked: + expects this to be the path relative to the root directory + @param aLockToken lock token + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* UnlockL(const TDesC& aPath, + const TDesC8* aLockToken); + + /** + @function RefreshLockL + @discussion Refreshes a locked resource by using LOCK method + @param aPath the resource to be locked: + expects this to be the path relative to the root directory + @param aTimeout lock timeout in seconds + @param aLockToken lock token + @param aDavFileInfo the location where collected file info should be set + @return pointer to the submitted WebDAV transaction + */ + CRsfwDavTransaction* RefreshLockL(const TDesC& aPath, + TUint aTimeOut, + const TDesC8* aLockToken, + CRsfwDavFileInfo** aDavFileInfo); + + /** + @function Error + @return Most recently recieved error code + */ + TInt Error(); + + /** + @function ErrorMsg + @return Most recently received error message from server + */ + const TDesC& ErrorMsg(); + + RHTTPSession& HttpSession(); + void SetConnected(TBool aConnected); + void SetWebDavSupportClass(TInt aWebDavSupportClass); + TInt WebDavSupportClass(); + + inline RFs& FileServerSession() {return iFs;}; + inline const TDesC& RootDirectory() {return iDavRoot;}; + void WebDavTransactionCompleteL(CRsfwDavTransaction* aWebDavTransaction); + void WebDavTransactionError(CRsfwDavTransaction* aWebDavTransaction); + void SetPropFindParametersL(RPointerArray* aDirEntArray, + const TDesC& aPropFindPath, + TInt aDepth); + void SetLockQueryParameters(CRsfwDavFileInfo* aDavFileInfo); + void ParsePropFindResponseL(const TDesC8& aResponse); + void ParseLockResponseL(const TDesC8& aResponse); + void PropFindResponseEndL(); + void LockResponseEndL(); + void CancelParsing(TWebDavOp aOp); + +public: // Functions from base classes + // From MHTTPAuthenticationCallback + TBool GetCredentialsL(const TUriC8& aURI, + RString aRealm, + RStringF aAuthenticationType, + RString& aUserName, + RString& aPassword); + +private: + void ConstructL(MRsfwDavResponseObserver* aWebDavResponseObserver, + MRsfwConnectionObserver* aRsfwConnectionObserver); + RStringPool StringPool(); + void Slashify(TDes& aStr); + HBufC* BuildPathLC(const TDesC& aRoot, + const TDesC& aPath, + TBool aEndSlash); + HBufC* BuildFullPathLC(const TDesC& aPath, TBool aEndSlash); + HBufC8* BuildUriLC(const TDesC& aPath, + TBool aEndSlash, + TUriParser8* aUriParser); + void SetHeaderL(RHTTPHeaders aHeaders, + TInt aHdrField, + const TDesC8& aHdrValue); + void SetHeaderL(RHTTPHeaders aHeaders, + const TDesC8& aHdrName, + const TDesC8& aHdrValue); + void SetBasicHeadersL(RHTTPHeaders aHeaders, + const TUriC8& aUri, + TBool aNoProxy); + void SetDepthHeaderL(RHTTPHeaders aHeaders, TInt aDepth); + void SetLockTokenHeaderL(RHTTPHeaders aHeaders, + const TDesC8* aUri, + const TDesC8* aLockToken, + TBool aUseTaggedLockToken); + TBool IsConnected(); + TUint NextWebDavTransactionId(); + HBufC8* EncodeL(const TDesC& aData); + void SetupConnectionL(); + +private: // Data + // information about the connection + HBufC8* iUserName; + HBufC8* iPassword; + TBuf iHost; + TBuf iDavRoot; + TBuf iHostRoot; + TBuf iAuxData; + HBufC8* iEncodedHost; // UTF8-encoded host name part + + MRsfwDavResponseObserver* iWebDavResponseObserver; + MRsfwConnectionObserver* iRsfwConnectionObserver; + + CRsfwPropFindParser* iPropFindParserImpl; + CRsfwLockQueryParser* iLockQueryParserImpl; + Xml::CParser* iPropFindParser; + Xml::CParser* iLockQueryParser; + + // whether XML parser should be cancelled if the transaction is cancelled + TBool iPropfindParsingActive; + + + TBool iConnected; // whether we have a successful TCP session + RFs iFs; + TInt iWebDavSupportClass; + TInt iCredentialRequestCount; + TUint iCurrentWebDavTransactionId; + RHTTPSession iHttpSession; + CRsfwConnectionManager* iRsfwConnectionManager; + }; + +#endif // CRSFWDAVSESSION_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwdavtransaction.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwdavtransaction.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,164 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: WebDAV transaction + * +*/ + + +#ifndef CRSFWDAVTRANSACTION_H +#define CRSFWDAVTRANSACTION_H + +// INCLUDES +#include +#include +//#include +//#include +//#include +#include +//#include +#include + +//#include + +#include "rsfwdavdefs.h" +//#include "rsfwremoteaccess.h" +//#include "rsfwdavsession.h" + +// FORWARD DECLARATIONS +class CRsfwDavSession; +class CRsfwDirEnt; +class CRsfwDavFileInfo; + +// CONSTANTS +const TInt KHttpPortNumber = 80; +const TInt KHttpsPortNumber = 443; +_LIT(KHttpScheme, "http"); +_LIT(KHttpsScheme, "https"); +_LIT8(KHttpsScheme8, "https"); + +/** + * WebDAV transaction + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ +class CRsfwDavTransaction: public CBase, + public MHTTPTransactionCallback, + public MHTTPDataSupplier + + { +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + static CRsfwDavTransaction* NewL(CRsfwDavSession* aWebDavSession, + TWebDavOp aWebDavOp, + const TUriC8& aUri, + RStringF aMethod, + TUint aTransactionId); + /** + * Destructor. + */ + virtual ~CRsfwDavTransaction(); + +public: // New functions + void SetBodyData(HBufC8* aRequestBodyBuffer); + void SetBodyFileL(const TDesC& aPath, + TInt aOffset, + TInt* aLength, + TUint aFlags); + void SetPropFindPath(HBufC* aPropFindPath); + void SetPropFindDirEntryArray(RPointerArray& aDirEnts); + void SubmitL(); + void Cancel(); + void SetDavFileInfoL(CRsfwDavFileInfo** aDavFileInfo, const TDesC& aPath); + inline RHTTPTransaction HttpTransaction() {return iHttpTransaction;}; + inline TUint Id() {return iTransactionId;}; + inline TInt Status() {return iStatus;}; + +public: // Functions from base classes + // From MHTTPTransactionCallback + void MHFRunL(RHTTPTransaction aTransaction, + const THTTPEvent& aEvent); + TInt MHFRunError(TInt aError, + RHTTPTransaction aTransaction, + const THTTPEvent& aEvent); + + // From MHTTPDataSupplier + TBool GetNextDataPart(TPtrC8& aDataPart); + void ReleaseData(); + TInt OverallDataSize(); + TInt Reset(); + +private: + void ConstructL(CRsfwDavSession* aWebDavSession, + TWebDavOp aWebDavOp, + const TUriC8& aUri, + RStringF aMethod, + TInt aTransactionId); + void TransactionCompleteL(); + void TransactionError(); + void Cleanup(); + void PropFindResponseBeginL(TInt aDepth); + void LockQueryResponseBegin(); + void ParsePropFindResponseL(const TDesC8& aFragment); + void ParseLockResponseL(const TDesC8& aFragment); + void PropFindResponseEndL(); + void LockResponseEndL(); + +public: // data + TWebDavOp iWebDavOp; + +private: // Data + TUint iTransactionId; + CRsfwDavSession* iWebDavSession; + RHTTPTransaction iHttpTransaction; + TBool iMoreToCome; + RFs iFs; + + // files used with PUT and GET + RFile iBodyFile; + TFileName iBodyFilePath; + TInt iBodyFileOffset; + TUint iBodyFileFlags; + TParse iParsedBodyFilePath; + + // pointer to client's "length" variable + // GET operation will set this based on "content-length" from the server + TInt* iClientsLength; + + HBufC8* iRequestBodyBuffer; + + // PROPFIND parser needs to now where it is prop finding.... + HBufC* iPropFindPath; + // PROPFIND etc: response body is copied to a memory buffer + HBufC8* iResponseBuffer; + // how much body data has been sent to the HTTP stack + TInt iSendDataCount; + // total size of body the data + TInt iOverallDataSize; + TInt iStatus; + TBool iNoContentLength; + TBool iDiscardBody; // there may be body that we discard + + // Used with LOCKs to store files lock token + CRsfwDavFileInfo* iDavFileInfo; + + // Used with PROPFIND to store metadata of all entries in a directory + RPointerArray* iDirEnts; + }; + +#endif // CRSFWDAVTRANSACTION_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwlockqueryparser.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwlockqueryparser.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,118 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: WebDAV Lock method response body parser + * +*/ + + +#ifndef CRSFWLOCKQUERYPARSER_H +#define CRSFWLOCKQUERYPARSER_H + +// INCLUDES +#include +#include // needed for RAttributeArray + +// FORWARD DECLARATIONS +class CRsfwDavFileInfo; + +// CLASS DECLARATION + +/** + * WebDAV Lock operation response body parser + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ + +class CRsfwLockQueryParser: public CBase, public Xml::MContentHandler + { + // DATA TYPES + enum TLockType + { + EWriteLock + }; + + enum TLockScope + { + ESharedLock, + EExclLock + }; + + enum TState + { + ELooking, + ELockToken, + ELockScope, + EDepth, + ETimeout, + ELockType, + EHrefToken + }; + +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + static CRsfwLockQueryParser* NewL(); + static CRsfwLockQueryParser* NewLC(); + + /** + * Destructor. + */ + virtual ~CRsfwLockQueryParser(); + +public: // Functions from base classes + // From Xml::MContentHandler + void OnStartDocumentL(const Xml::RDocumentParameters& aDocParam, + TInt aErrorCode); + void OnEndDocumentL(TInt aErrorCode); + void OnStartElementL(const Xml::RTagInfo& aElement, + const Xml::RAttributeArray& aAttributes, + TInt aErrorCode); + void OnEndElementL(const Xml::RTagInfo& aElement, TInt aErrorCode); + void OnContentL(const TDesC8& aBytes, TInt aErrorCode); + void OnStartPrefixMappingL(const RString& aPrefix, + const RString& aUri, + TInt aErrorCode); + void OnEndPrefixMappingL(const RString& aPrefix, TInt aErrorCode); + void OnIgnorableWhiteSpaceL(const TDesC8& aBytes, TInt aErrorCode); + void OnSkippedEntityL(const RString& aName, TInt aErrorCode); + void OnProcessingInstructionL(const TDesC8& aTarget, + const TDesC8& aData, + TInt aErrorCode); + void OnError(TInt aErrorCode); + TAny* GetExtendedInterface(const TInt32 aUid); + +public: // New functions + /** + Set file information container to be filled + @param aFileInfo file info + */ + void SetDavFileInfo(CRsfwDavFileInfo* aDavFileInfo); + + TInt GetLastError(); + +private: + void ConstructL(); + +private: // Data + TState iParseState; + CRsfwDavFileInfo* iDavFileInfo; + HBufC8* iContentString; + TInt iError; + }; + +#endif // CRSFWLOCKQUERYPARSER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/inc/rsfwpropfindparser.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/inc/rsfwpropfindparser.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,151 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: WebDAV PropFind method response body parser + * +*/ + + +#ifndef CRSFWPROPFINDPARSER_H +#define CRSFWPROPFINDPARSER_H + +// INCLUDES +#include +#include // needed for RAttributeArray + +#include "rsfwdavfileinfo.h" +#include "rsfwdirent.h" + +// CONSTANTS +const TInt KMaxNameSpaces = 10; + +// FORWARD DECLARATIONS +class CRsfwDirEnt; + +// CLASS DECLARATION +/** + * WebDAV Lock operation response body parser. + * Parses directory listing from WebDAV-server, which we got + * as XML-body response to PROPFIND-query. + * + * FOR METADATA: + * This comes from upper lever and are used to store relevant metadata + * from directory listing. + * Currently we want to extract the following to the entry + * displayname + * 2002-12-19T13:51:16Z + * Thu, 19 Dec 2002 13:51:16 GMT + * 2324; + * + * FOR CACHE CONCISTENCY: + * We need to remember the ETag of searched directory + * + * @lib davaccess.lib + * @since Series 60 3.1 + */ + +class CRsfwPropFindParser : public CBase, public Xml::MContentHandler + { +// EName = parsing is inside etc., +// ELooking = parsing is outside all tags of interest + enum TState + { + EName, + EResponse, + ENameInDisplayName, + EDate, + EModified, + ELength, + EResourceType, + EContentType, + EETag, + ELooking + }; + +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + static CRsfwPropFindParser* NewL(); + static CRsfwPropFindParser* NewLC(); + + /** + * Destructor. + */ + virtual ~CRsfwPropFindParser(); + +public: // Functions from base classes +// Symbian parser + // From XML::MContentHandler + void OnStartDocumentL(const Xml::RDocumentParameters& aDocParam, + TInt aErrorCode); + void OnEndDocumentL(TInt aErrorCode); + void OnStartElementL(const Xml::RTagInfo& aElement, + const Xml::RAttributeArray& aAttributes, + TInt aErrorCode); + void OnEndElementL(const Xml::RTagInfo& aElement, TInt aErrorCode); + void OnContentL(const TDesC8& aBytes, TInt aErrorCode); + void OnStartPrefixMappingL(const RString& aPrefix, + const RString& aUri, + TInt aErrorCode); + void OnEndPrefixMappingL(const RString& aPrefix, TInt aErrorCode); + void OnIgnorableWhiteSpaceL(const TDesC8& aBytes, TInt aErrorCode); + void OnSkippedEntityL(const RString& aName, TInt aErrorCode); + void OnProcessingInstructionL(const TDesC8& aTarget, + const TDesC8& aData, + TInt aErrorCode); + void OnError(TInt aErrorCode); + TAny* GetExtendedInterface(const TInt32 aUid); + +public: // New functions + // setters for the parser + /** + Set directory entry to be filled + @param aDirEntArray directory entry array + */ + void SetDirEntArray(RPointerArray* aDirEntArray); + + /** + Set target directory + @param aPropFindPath Propfind resource path + @param aDepth Propfind depth + */ + void SetTargetDirectory(const TDesC& aPropFindPath, TInt aDepth); + + /** + Returns the error code if there was an error during parsing of + the response. + */ + TInt GetLastError(); + + +private: + void ConstructL(); + void ClearDirEntryL(); + HBufC* DecodeL(const TDesC8& aData); + +private: // Data + // Internal variables + RPointerArray* iDirEntArray; // not owned by us + const TDesC* iPropFindPath; // path + HBufC8* iContentString; + TInt iDepth; + CRsfwDirEnt* iDirEntry; // metadata entry currently read + TState iParseState; // internal state + TBool iCurrentIsParent; + TInt iError; // indicates a processing error + }; + +#endif // CRSFWPROPFINDPARSER_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwdavaccess.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavaccess.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1179 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Implements remote access plugin API using WebDAV protocol + * +*/ + + +// INCLUDE FILES +#include "rsfwdavaccess.h" +#include "rsfwdavfileinfo.h" +#include "rsfwdavaccesscontext.h" +#include "rsfwdavtransaction.h" +#include "mdebug.h" + + +// ============================ MEMBER FUNCTIONS ============================== + +void CRsfwDavAccess::ConstructL() + { + } + +CRsfwDavAccess* CRsfwDavAccess::NewL() + { + CRsfwDavAccess* self = new (ELeave) CRsfwDavAccess; + CleanupStack::PushL(self); + self->ConstructL(); + CleanupStack::Pop(self); + return self; + } + +CRsfwDavAccess::~CRsfwDavAccess() + { + delete iWebDavSession; + iDavFileInfos.ResetAndDestroy(); + iDavAccessContexts.ResetAndDestroy(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::DavFileInfoL +// Find the file info for the given file name. +// ---------------------------------------------------------------------------- +// +CRsfwDavFileInfo* CRsfwDavAccess::DavFileInfoL(const TDesC& aName) + { + TInt index = DavFileInfoIndexL(aName); + if (index != KErrNotFound) + { + return iDavFileInfos[index]; + } + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::AddDavFileInfo +// Add a new file info entry. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::AddDavFileInfo(CRsfwDavFileInfo* aDavFileInfo) + { +#ifdef _DEBUG + TPtrC namePtr; + if (aDavFileInfo->Name()) + { + namePtr.Set(*aDavFileInfo->Name()); + } + TPtrC8 lockPtr; + if (aDavFileInfo->LockToken()) + { + lockPtr.Set(*aDavFileInfo->LockToken()); + } + DEBUGSTRING16(("Add file info: name='%S'", &namePtr)); + DEBUGSTRING8((" lock='%S', time=%d", + &lockPtr, + aDavFileInfo->Timeout())); + +#endif // DEBUG + iDavFileInfos.Append(aDavFileInfo); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::RemoveDavFileInfoL +// Remove a file info entry. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::RemoveDavFileInfoL(const TDesC& aPath) + { + TInt index = DavFileInfoIndexL(aPath); + if (index != KErrNotFound) + { + CRsfwDavFileInfo* davFileInfo = iDavFileInfos[index]; +#ifdef _DEBUG + TPtrC namePtr; + if (davFileInfo->Name()) + { + namePtr.Set(*davFileInfo->Name()); + } + DEBUGSTRING16(("Remove file info: name='%S'", &namePtr)); +#endif // DEBUG + iDavFileInfos.Remove(index); + delete davFileInfo; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::SetupL +// Setup - should be immediately followed by NewL() call. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::SetupL(MRsfwRemoteAccessObserver* aRsfwRemoteAccessObserver) + { + DEBUGSTRING(("DAV: SetupL")); + MRsfwConnectionObserver* rsfwConnectionObserver = NULL; + if (aRsfwRemoteAccessObserver) + { + // Cascade remote access observers + iRsfwRemoteAccessObserver = aRsfwRemoteAccessObserver; + rsfwConnectionObserver = this; + } + iWebDavSession = CRsfwDavSession::NewL(this, rsfwConnectionObserver); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::OpenL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::OpenL(const TUriC& aUri, + const TDesC& /*aFriendlyName*/, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aAuxData, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + HBufC* url = HBufC::NewLC(KHttpsScheme().Length() + + KMaxServerNameLen + + 1 + + KMaxPath); + TPtr urlPtr = url->Des(); + + TInt portNumber = 0; + if (aUri.IsPresent(EUriPort)) + { + TLex portx(aUri.Extract(EUriPort)); + if (portx.Val(portNumber) != KErrNone) + { + portNumber = 0; + } + } + + // Check scheme and map it to port number or vice versa + TPtrC scheme; + if (aUri.IsPresent(EUriScheme)) + { + scheme.Set(aUri.Extract(EUriScheme)); + } + if (scheme.Length()) + { + if (portNumber == 0) + { + if (scheme.CompareF(KHttpsScheme) == 0) + { + portNumber = KHttpsPortNumber; + } + else + { + portNumber = KHttpPortNumber; + } + } + } + else + { + if (portNumber == 0) + { + portNumber = KHttpPortNumber; + } + if (portNumber == KHttpPortNumber) + { + scheme.Set(KHttpScheme); + } + else if (portNumber == KHttpsPortNumber) + { + scheme.Set(KHttpsScheme); + } + else + { + User::Leave(KErrBadName); + } + } + + TPtrC rootDirectory; + if (aUri.IsPresent(EUriPath)) + { + rootDirectory.Set(aUri.Extract(EUriPath)); + } + iRootDirectory.Copy(rootDirectory); + if (!iRootDirectory.Length() || + iRootDirectory[iRootDirectory.Length() - 1] != '/') + { + // Append trailing '/' + iRootDirectory.Append('/'); + } + + urlPtr.Copy(scheme); + urlPtr.Append(':'); + urlPtr.Append('/'); + urlPtr.Append('/'); + urlPtr.Append(aUri.Extract(EUriHost)); + // There needs to be a slash between server name and the root dir + // (we assume that there cannot be an excess of slash characters) + if (urlPtr[urlPtr.Length() - 1] != '/') + { + if (!iRootDirectory.Length() || (iRootDirectory[0] != '/')) + { + urlPtr.Append('/'); + } + } + urlPtr.Append(iRootDirectory); + + DEBUGSTRING16(("DAV: OpenL to URL '%S'", &urlPtr)); + + iWebDavSession->OpenL(urlPtr, + portNumber, + aUserName, + aPassword, + aAuxData); + CleanupStack::PopAndDestroy(url); + return OptionsL(aResponseHandler); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::GetDirectoryL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::GetDirectoryL(const TDesC& aPathName, + RPointerArray& aDirEnts, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + // Get the contents of the directory + DEBUGSTRING16(("DAV: GetDirectory '%S'", &aPathName)); + + // check that arguments are sensible + // aPathName might here be null (mounted root directory) + if (aPathName.Length() > KMaxPath) + { + User::Leave(KErrBadName); + } + + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + CRsfwDavAccessContextPropFindDir* davAccessContextPropFindDir = + CRsfwDavAccessContextPropFindDir::NewL(this, + aResponseHandler, + aPathName, + 1, + NULL, + &aDirEnts); + TUint id = AddAccessContext(davAccessContextPropFindDir); + davAccessContextPropFindDir->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::GetFileL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::GetFileL(const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + +#ifdef _DEBUG + { + TInt length; + if (aLength) + { + length = *aLength; + } + else + { + length = 0; + } + DEBUGSTRING16(("DAV: GetFile rn='%S', ln='%S' (off=%d, len=%d)", + &aRemotePathName, + &aLocalPathName, + aOffset, + length)); + } +#endif // DEBUG + + // check that arguments are sensible + if (aOffset < 0 || + (aLength && *aLength < 0) || + (!aResponseHandler)) + { + User::Leave(KErrArgument); + } + + if ((aLocalPathName.Length() == 0) || + (aLocalPathName.Length() > KMaxPath) || + (aRemotePathName.Length() == 0) || + (aRemotePathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + CRsfwDavAccessContextGet* davAccessContextGet = + CRsfwDavAccessContextGet::NewL(this, + aResponseHandler, + aRemotePathName, + aLocalPathName, + aOffset, + aLength, + aFlags); + TUint id = AddAccessContext(davAccessContextGet); + davAccessContextGet->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::PutFileL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::PutFileL(const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + // Copy file to server using PUT, + // might require lock token, if the destination file is locked... +#ifdef _DEBUG + { + TInt length; + if (aLength) + { + length = aLength; + } + else + { + length = 0; + } + DEBUGSTRING16(("DAV: PutFile ln='%S', rn='%S' (off=%d, len=%d)", + &aLocalPathName, + &aRemotePathName, + aOffset, + length)); + } +#endif // DEBUG + + // check that arguments are sensible + if (aOffset < 0 || + (aLength < 0) || + (((aOffset + aLength) > aTotalLength) && aTotalLength > 0) || + (!aResponseHandler)) + { + User::Leave(KErrArgument); + } + + // note that aLocalPathName can be undefined + // (CreateFile calls with null-ptr) + if ((aLocalPathName.Length() > KMaxPath) || + (aRemotePathName.Length() == 0) || + (aRemotePathName.Length() > KMaxPath) || + (aMimeType.Length() > KMaxMimeTypeLength)) + { + User::Leave(KErrBadName); + } + + + const HBufC8* lockToken = NULL; + CRsfwDavFileInfo *davFileInfo = DavFileInfoL(aRemotePathName); + if (davFileInfo) + { + lockToken = davFileInfo->LockToken(); + } + CRsfwDavAccessContextPut* davAccessContextPut = + CRsfwDavAccessContextPut::NewL(this, + aResponseHandler, + aLocalPathName, + aRemotePathName, + aMimeType, + aOffset, + aLength, + aTotalLength, + lockToken); + TUint id = AddAccessContext(davAccessContextPut); + davAccessContextPut->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::PutFileL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::PutFileL(const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + return PutFileL(aLocalPathName, + aRemotePathName, + aMimeType, + 0, + NULL, + 0, + aResponseHandler); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::CreateFileL +// overwriting info not needed in HTTP PUT +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::CreateFileL(const TDesC& aPathName, + TBool /*aOverWriting*/, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: CreateFile '%S'", &aPathName)); + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + // Could create the file only from LOCK, + // but that seems to cause 500 Internal Error with several + // Apache servers... + TPtrC null; + return PutFileL(null, aPathName, KTextPlain, 0, NULL, 0, aResponseHandler); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::MakeDirectoryL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::MakeDirectoryL( + const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: MakeDirectory", &aPathName)); + + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + CRsfwDavAccessContextMkDir* davAccessContextMkDir = + CRsfwDavAccessContextMkDir::NewL(this, + aResponseHandler, + aPathName); + TUint id = AddAccessContext(davAccessContextMkDir); + davAccessContextMkDir->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::DeleteDirectoryL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::DeleteDirectoryL( + const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: DeleteDirectory '%S'", &aPathName)); + + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + CRsfwDavAccessContextDelete* davAccessContextDelete = + CRsfwDavAccessContextDelete::NewL(this, + aResponseHandler, + aPathName, + ETrue, + NULL); + TUint id = AddAccessContext(davAccessContextDelete); + davAccessContextDelete->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::DeleteFileL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::DeleteFileL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: DeleteFile '%S'", &aPathName)); + + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + const HBufC8* lockToken = NULL; + CRsfwDavFileInfo *davFileInfo = DavFileInfoL(aPathName); + if (davFileInfo) + { + lockToken = davFileInfo->LockToken(); + } + CRsfwDavAccessContextDelete* davAccessContextDelete = + CRsfwDavAccessContextDelete::NewL(this, + aResponseHandler, + aPathName, + EFalse, + lockToken); + TUint id = AddAccessContext(davAccessContextDelete); + davAccessContextDelete->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::RenameL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::RenameL(const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: Rename '%S' to '%S'", &aSrcPathName, &aDstPathName)); + + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aSrcPathName.Length() == 0) || + (aSrcPathName.Length() > KMaxPath) || + (aDstPathName.Length() == 0) || + (aDstPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + // lock token for the source file, if the source is locked... + const HBufC8* lockToken = NULL; + CRsfwDavFileInfo* davFileInfo = DavFileInfoL(aSrcPathName); + if (davFileInfo) + { + lockToken = davFileInfo->LockToken(); + } + + + // lock token for the destination file, if the destination is locked + const HBufC8* destLockToken = NULL; + CRsfwDavFileInfo* destDavFileInfo = DavFileInfoL(aDstPathName); + if (destDavFileInfo) + { + destLockToken = destDavFileInfo->LockToken(); + } + + + CRsfwDavAccessContextMove* davAccessContextMove = + CRsfwDavAccessContextMove::NewL(this, + aResponseHandler, + aSrcPathName, + aDstPathName, + aOverwrite, + lockToken, + destLockToken); + TUint id = AddAccessContext(davAccessContextMove); + davAccessContextMove->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::GetDirectoryAttributesL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::GetDirectoryAttributesL( + const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: GetDirectoryAttributes of '%S'", + &aPathName)); + + // check that arguments are sensible + // aPathName might here be null (mounted root directory) + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if (aPathName.Length() > KMaxPath) + { + User::Leave(KErrBadName); + } + + CRsfwDavAccessContextPropFindDir* davAccessContextPropFindDir = + CRsfwDavAccessContextPropFindDir::NewL(this, + aResponseHandler, + aPathName, + 0, + &aAttr, + NULL); + TUint id = AddAccessContext(davAccessContextPropFindDir); + davAccessContextPropFindDir->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::GetFileAttributesL +// ---------------------------------------------------------------------------- +// +TUint +CRsfwDavAccess::GetFileAttributesL(const TDesC& aPathName, + CRsfwDirEntAttr*& aAttr, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING16(("DAV: GetFileAttributes of '%S'", + &aPathName)); + + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + CRsfwDavAccessContextPropFindFile* davAccessContextPropFindFile = + CRsfwDavAccessContextPropFindFile::NewL(this, + aResponseHandler, + aPathName, + &aAttr); + TUint id = AddAccessContext(davAccessContextPropFindFile); + davAccessContextPropFindFile->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::SetAttributesL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::SetAttributesL( + const TDesC& /* aPathName */, + CRsfwDirEntAttr& /* aAttr */, + MRsfwRemoteAccessResponseHandler* /* aResponseHandler */) + { + DEBUGSTRING(("DAV: SetAttributes")); + User::Leave(KErrNotSupported); + // Not reached + return 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::ObtainLockL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::ObtainLockL(const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8*& aLockToken, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + // check that arguments are sensible + if ((!aResponseHandler) || + (aTimeout == 0)) + { + User::Leave(KErrArgument); + } + + // CRsfwDavAccess is the place to know about webdab locks + // We only try to obtain a lock if the file was opened for writing + if ((!(aLockFlags & EFileWrite)) || + (iWebDavSession->WebDavSupportClass() < KDavVersionTwo)) + { + // WebDAV doesn't have read locks + aResponseHandler->HandleRemoteAccessResponse(0, KErrNotSupported); + return 0; + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + CRsfwDavAccessContextLock* davAccessContextLock = + CRsfwDavAccessContextLock::NewL(this, + aResponseHandler, + aPathName, + aLockFlags, + aTimeout, + &aLockToken); + TUint id = AddAccessContext(davAccessContextLock); + davAccessContextLock->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::ReleaseLockL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::ReleaseLockL(const TDesC& aPathName, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + /* + Precondition: + - File has been at least locked so there must be fileInfo and + locktoken for it + */ + // check that arguments are sensible + if (!aResponseHandler) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + // Must send the Lock Token + CRsfwDavFileInfo* davFileInfo = DavFileInfoL(aPathName); + if (!davFileInfo) + { + User::Leave(KErrNotFound); + } + + const HBufC8* lockToken = davFileInfo->LockToken(); + if (!lockToken) + { + User::Leave(KErrNotFound); + } + // Prevent further access to lock token + davFileInfo->SetFlag(TRsfwDavFileInfoFlags::EUnlockPending); + + CRsfwDavAccessContextUnlock* davAccessContextUnlock = + CRsfwDavAccessContextUnlock::NewL(this, + aResponseHandler, + aPathName, + lockToken); + TUint id = AddAccessContext(davAccessContextUnlock); + davAccessContextUnlock->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::RefreshLockL +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::RefreshLockL(const TDesC& aPathName, + TUint& aTimeout, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + + { + /* + Precondition: + - File has been at least locked + so there must be fileInfo and locktoken for it + */ + // check that arguments are sensible + if ((!aResponseHandler) || + (aTimeout == 0)) + { + User::Leave(KErrArgument); + } + + if ((aPathName.Length() == 0) || + (aPathName.Length() > KMaxPath)) + { + User::Leave(KErrBadName); + } + + + // Must send the Lock Token + CRsfwDavFileInfo* davFileInfo = DavFileInfoL(aPathName); + if (!davFileInfo) + { + User::Leave(KErrNotFound); + } + const HBufC8* lockToken = davFileInfo->LockToken(); + if (!lockToken) + { + User::Leave(KErrNotFound); + } + + CRsfwDavAccessContextRefreshLock* davAccessContextRefreshLock = + CRsfwDavAccessContextRefreshLock::NewL(this, + aResponseHandler, + aPathName, + lockToken, + aTimeout); + TUint id = AddAccessContext(davAccessContextRefreshLock); + davAccessContextRefreshLock->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::CancelL by ID +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::Cancel(TUint aId) + { + TInt i; + if (aId) + { + i = LookupAccessContextByContextId(aId); + if (i != KErrNotFound) + { + CRsfwDavAccessContext* context = iDavAccessContexts[i]; + // sometimes it may happen that transaction has not been created for + // some context (e.g. if a leave has occured) + if (context->WebDavTransaction()) + { + context->WebDavTransaction()->Cancel(); + } + else + { + iDavAccessContexts.Remove(i); + delete context; + } + } + } + else + { + // Cancel all pending transactions. + // Note that cancelling one transaction may result in creating the other + // e.g. if you cancel PUT, then RELEASE LOCK is generated. + // Anyway the purpose here is to 'kill' all of them, even those generated later + DEBUGSTRING(("Cancelling all pending transactions...")); + while (iDavAccessContexts.Count() > 0) + { + CRsfwDavAccessContext* context = iDavAccessContexts[0]; + TUint id = context->Id(); + Cancel(id); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::CancelL by path +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::Cancel(TDesC& aTargetPath) + { + DEBUGSTRING16(("CRsfwDavAccess::Cancel '%S'", &aTargetPath)); + TInt i; + i = LookupAccessContextByPath(aTargetPath); + if (i != KErrNotFound) + { + DEBUGSTRING16(("found transaction....cancelling webdavop %d", + iDavAccessContexts[i]->WebDavTransaction()->iWebDavOp)); + iDavAccessContexts[i]->WebDavTransaction()->Cancel(); + } + } + + + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::SetLockToken +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavAccess::SetLockToken(const TDesC& aPathName, + const TDesC8& aLockToken) + { + TRAPD(err, SetLockTokenL(aPathName, aLockToken)); + return err; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::SetLockTokenL +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::SetLockTokenL(const TDesC& aPathName, + const TDesC8& aLockToken) + { + HBufC* path = HBufC::NewLC(iRootDirectory.Length() + KMaxPath + 1); + TPtr pathPtr = path->Des(); + pathPtr.Copy(iRootDirectory); + pathPtr.Append(aPathName); + + DEBUGSTRING16(("DAV: setting lock token: path = '%S'", &pathPtr)); + DEBUGSTRING8((" token = '%S'", &aLockToken)); + + if (aLockToken.Length()) + { + CRsfwDavFileInfo* fileInfo = DavFileInfoL(pathPtr); + if (fileInfo) + { + fileInfo->SetLockTokenL(aLockToken); + } + else + { + // new file + fileInfo = CRsfwDavFileInfo::NewL(); + CleanupStack::PushL(fileInfo); + fileInfo->SetNameL(pathPtr); + fileInfo->SetLockTokenL(aLockToken); + CleanupStack::Pop(fileInfo); + // Ownership transferred to file info array + AddDavFileInfo(fileInfo); + } + } + else + { + // Remove lock token + RemoveDavFileInfoL(pathPtr); + } + + CleanupStack::PopAndDestroy(path); + } + +// ---------------------------------------------------------------------------- +// From MRsfwDavResponseObserver +// ---------------------------------------------------------------------------- + +void CRsfwDavAccess::RequestCompleteL(TUint aWebDavTransactionId) + { + TInt i = LookupAccessContextByTransactionId(aWebDavTransactionId); + if (i != KErrNotFound) + { + CRsfwDavAccessContext* context = iDavAccessContexts[i]; + DEBUGSTRING(("DAV: Request %d complete", aWebDavTransactionId)); + context->TransactionCompleteL(); + if (context->Done()) + { + MRsfwRemoteAccessResponseHandler* responseHandler = + context->ResponseHandler(); + TUint id = context->Id(); + TInt status = context->Status(); + iDavAccessContexts.Remove(i); + delete context; + responseHandler->HandleRemoteAccessResponse(id, status); + } + } + else + { + DEBUGSTRING(("DAV: Stray request (id=%d) complete", + aWebDavTransactionId)); + } + } + +void CRsfwDavAccess::RequestError(TUint aWebDavTransactionId, TInt aStatus) + { + TInt i = LookupAccessContextByTransactionId(aWebDavTransactionId); + if (i != KErrNotFound) + { + CRsfwDavAccessContext* context = iDavAccessContexts[i]; + DEBUGSTRING(("DAV: Request %d error %d", + aWebDavTransactionId, + aStatus)); + context->TransactionError(aStatus); + if (context->Done()) + { + MRsfwRemoteAccessResponseHandler* responseHandler = + context->ResponseHandler(); + TUint id = context->Id(); + TInt status = context->Status(); + iDavAccessContexts.Remove(i); + delete context; + responseHandler->HandleRemoteAccessResponse(id, status); + } + } + else + { + DEBUGSTRING(("DAV: Stray request (id=%d) error", + aWebDavTransactionId)); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::AddAccessContext +// Add a context entry in the table of currently active contexts. +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::AddAccessContext(CRsfwDavAccessContext* aDavAccessContext) + { + TUint id = GetNextAccessContextId(); + DEBUGSTRING(("DAV: Added transaction %d", id)); + aDavAccessContext->SetId(id); + iDavAccessContexts.Append(aDavAccessContext); + return id; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::LookupAccessContextByTransactionId +// Find an access context for the given WebDAV transaction id. +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavAccess::LookupAccessContextByTransactionId(TUint aWebDavTransactionId) + { + TInt i; + for (i = 0; i < iDavAccessContexts.Count(); i++) + { + if (iDavAccessContexts[i]->WebDavTransactionId() == + aWebDavTransactionId) + { + return i; + } + } + DEBUGSTRING(("Access context for id %d is missing !!!", + aWebDavTransactionId)); + return KErrNotFound; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::LookupAccessContext +// Find an access context having the given id. +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavAccess::LookupAccessContextByContextId(TUint aId) + { + TInt i; + for (i = 0; i < iDavAccessContexts.Count(); i++) + { + if (iDavAccessContexts[i]->Id() == aId) + { + return i; + } + } + DEBUGSTRING(("Access context for id %d is missing !!!", aId)); + return KErrNotFound; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::LookupAccessContextByPath +// Find an access context based on the path of the targer file/directory. +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavAccess::LookupAccessContextByPath(TDesC& aTargetPath) + { + TInt i; + for (i = 0; i < iDavAccessContexts.Count(); i++) + { + if (iDavAccessContexts[i]->TargetPath() == aTargetPath) + { + return i; + } + } + return KErrNotFound; + } + + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::DavFileInfoIndexL +// Find the index to file info array for the given file name. +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavAccess::DavFileInfoIndexL(const TDesC& aName) + { + HBufC* path = HBufC::NewLC(iRootDirectory.Length() + KMaxPath + 1); + TPtr pathPtr = path->Des(); + pathPtr.Copy(iRootDirectory); + pathPtr.Append(aName); + + DEBUGSTRING16(("Finding file info for '%S'", &pathPtr)); + TInt index; + for (index = 0; index < iDavFileInfos.Count(); index++) + { + const HBufC* name = iDavFileInfos[index]->Name(); + if (name) + { + if (pathPtr.Compare(*name) == 0) + { + DEBUGSTRING(("info found")); + CleanupStack::PopAndDestroy(path); + return index; + } + } + } + CleanupStack::PopAndDestroy(path); + return KErrNotFound; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::OptionsL +// Perform an Options query +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavAccess::OptionsL(MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + CRsfwDavAccessContextOptions* davAccessContextOptions = + CRsfwDavAccessContextOptions::NewL(this, aResponseHandler); + TUint id = AddAccessContext(davAccessContextOptions); + davAccessContextOptions->StartL(); + return id; + } + +// ---------------------------------------------------------------------------- +// From MRsfwConnectionObserver +// ---------------------------------------------------------------------------- + +// ---------------------------------------------------------------------------- +// CRsfwDavAccess::HandleConnectionEventL +// Perform an Options query +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccess::HandleConnectionEventL(TInt aConnectionEvent, + TAny* /*aArg*/) + + { + switch (aConnectionEvent) + { + case ERsfwConnectionObserverEventConnectionDisconnected: + if (iRsfwRemoteAccessObserver) + { + iRsfwRemoteAccessObserver-> + HandleRemoteAccessEventL( + ERsfwRemoteAccessObserverEventConnection, + ERsfwRemoteAccessObserverEventConnectionDisconnected, + NULL); + } + break; + + case ERsfwConnectionObserverEventConnectionWeaklyConnected: + // If we were reacting to link up events, we would do OptionsL(this); + break; + + case ERsfwConnectionObserverEventConnectionStronglyConnected: + // If we were reacting to link up events, we would do OptionsL(this); + break; + + default: + break; + } + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwdavaccesscontext.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavaccesscontext.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1773 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Maintain contexts for WebDAV transactions + * +*/ + + +// INCLUDE FILES +#include +#include +//#include "rsfwdavtransaction.h" +#include "rsfwdavaccesscontext.h" +#include "rsfwdavaccess.h" +#include "rsfwdavfileinfo.h" +#include "mdebug.h" +#include "xml/xmlparsererrors.h" +#include "rsfwdirentattr.h" +#include "rsfwdirent.h" + + +// CRsfwDavAccessContext +// ============================ MEMBER FUNCTIONS ============================== +// Destructor +CRsfwDavAccessContext::~CRsfwDavAccessContext() + { + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContext::SubmitL +// Submit the operation. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContext::SubmitL() + { + iWebDavTransactionId = iWebDavTransaction->Id(); + iWebDavTransaction->SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContext::Retry +// Retry the operation. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContext::Retry() + { + TRAPD(err, StartL()); + if (err != KErrNone) + { + iStatus = err; + iDone = ETrue; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContext::MapError +// Map an HTTP error code to SymbianOS error code. +// Whenever possible, these default mappings should be overriden +// in the derived classes. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContext::MapError(TInt& aError) + { + switch (aError) + { + case HTTPStatus::EBadRequest: + aError = KErrBadName; + break; + + case HTTPStatus::EMovedPermanently: + case HTTPStatus::ETemporaryRedirect: + aError = KErrNotFound; + break; + + default: + if (HTTPStatus::IsServerError(aError)) + { + aError = KErrNotSupported; + } + else if (HTTPStatus::IsClientError(aError)) + { + aError = KErrAccessDenied; + } + else if (HTTPStatus::IsRedirection(aError)) + { + aError = KErrNotFound; + } + else + { + if (aError > 0) + { + // An arbitrary choice for error codes that should not occur + aError = KErrAccessDenied; + } + } + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContext::TargetPath +// return target path, to support cancel by path from +// FM local dialogs +// This can be NULL for some non-cancellable operations like OPTIONS +// but note that for example when reading files the active operation may be +// PROPFIND when user presses cancel. +// ---------------------------------------------------------------------------- +// +const TDesC& CRsfwDavAccessContext::TargetPath() + { + return iRemotePathName; + } + + +// ---------------------------------------------------------------------------- +// Derived access contexts +// ---------------------------------------------------------------------------- + +// CRsfwDavAccessContextOptions +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextOptions::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextOptions* +CRsfwDavAccessContextOptions::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + CRsfwDavAccessContextOptions* self = new (ELeave) CRsfwDavAccessContextOptions; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, aResponseHandler); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextOptions::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextOptions::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler) + { + DEBUGSTRING(("======= START =======")); + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iTryCount = KCommRetries; + iRemotePathName = KNullDesC; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextOptions::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextOptions::StartL() + { + DEBUGSTRING(("DAV: Options StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->OptionsL(); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextOptions::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextOptions::TransactionCompleteL() + { + DEBUGSTRING(("DAV: OptionsL done")); + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextOptions::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextOptions::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: OptionsL raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) ) +// (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map protocol specific error codes into symbian error codes + switch (aError) + { + case HTTPStatus::EMethodNotAllowed: + // Server doesn't support DAV + aError = KErrNotSupported; + break; + + case HTTPStatus::EBadRequest: + aError = KErrPathNotFound; + break; + + case HTTPStatus::EBadGateway: // Proxy didn't find the server + case HTTPStatus::ENotFound: + case KErrDndNameNotFound: // name resolver didn't find the server + case KErrDndAddrNotFound: + case KErrHttpCannotEstablishTunnel: // ssl error when server not found + aError = KErrNotFound; + break; + + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: OptionsL err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextPropFindDir +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindDir::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextPropFindDir* CRsfwDavAccessContextPropFindDir::NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TInt aDepth, + CRsfwDirEntAttr** aDirEntAttr, + RPointerArray* aDirEnts) + { + CRsfwDavAccessContextPropFindDir* self = + new (ELeave) CRsfwDavAccessContextPropFindDir; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aPathName, + aDepth, + aDirEntAttr, + aDirEnts); + CleanupStack::Pop(self); + return self; + } + +CRsfwDavAccessContextPropFindDir::~CRsfwDavAccessContextPropFindDir() + { + iOwnDirEnts.ResetAndDestroy(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindDir::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindDir::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TInt aDepth, + CRsfwDirEntAttr** aDirEntAttr, + RPointerArray* aDirEnts) + { + DEBUGSTRING(("CRsfwDavAccessContextPropFindDir::ConstructL")); + DEBUGSTRING16(("aPathName ='%S'", &aPathName)); + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iDepth = aDepth; + iDirEntAttr = aDirEntAttr; + iDirEnts = aDirEnts; + if (aDirEnts) + { + iDirEnts = aDirEnts; + } + else + { + iDirEnts = &iOwnDirEnts; + } + iTryCount = KCommRetries; + iRemotePathName = aPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropfindDir::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindDir::StartL() + { + /* + Preconditions: + - we haven't seen the directory at all (there is no CRsfwDavFileInfo for it) + - we have seen the directory and now the e-tag, + but haven't fetched the contents + - we have cached the contents also + */ + DEBUGSTRING(("DAV: PropFindDir StartL")); + iDirEnts->ResetAndDestroy(); + iWebDavTransaction = iDavAccess->WebDavSession()->PropFindL(iRemotePathName, + iDepth, + ETrue, + *iDirEnts); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindDir::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindDir::TransactionCompleteL() + { + TInt err = KErrNone; + DEBUGSTRING(("DAV: PropFindDir complete")); + + if (iDirEntAttr) + { + if (iDirEnts->Count()) + { + *iDirEntAttr = (*iDirEnts)[0]->ExtractAttr(); + } + } + +#ifdef _DEBUG + DEBUGSTRING(("DAV: DoPropFindDir: returning %d", err)); + TInt i; + for (i = 0; i < iDirEnts->Count(); i++) + { + CRsfwDirEnt* d = (*iDirEnts)[i]; + TPtrC name(*d->Name()); + DEBUGSTRING16(("'%S' - (size=%d, attr=0x%x)", + &name, + d->Attr()->Size(), + d->Attr()->Att())); + } +#endif // DEBUG + + iStatus = err; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindDir::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindDir::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: PropFindDir raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map XML parser errors to KErrCorrupt + if ((aError <= EXmlFeatureLockedWhileParsing) && + (aError >= EXmlParserError)) + { + aError = EXmlParserError; + } + + // Map protocol specific error codes into symbian error codes + switch (aError) + { + case EXmlParserError: + aError = KErrCorrupt; + break; + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case HTTPStatus::EForbidden: + case HTTPStatus::EUnauthorized: + aError = KErrAccessDenied; + break; + case HTTPStatus::EMovedPermanently: + case HTTPStatus::ETemporaryRedirect: + // The object we are looking for exists, but has a different + // type (e.g. we were looking for a file but it is a directory). + // PROPFIND should return not found... + aError = KErrNotFound; + break; + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: PropFindDir err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextPropFindFile +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindFile::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextPropFindFile* CRsfwDavAccessContextPropFindFile::NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + CRsfwDirEntAttr** aDirEntAttr) + { + CRsfwDavAccessContextPropFindFile* self = + new (ELeave) CRsfwDavAccessContextPropFindFile; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, aResponseHandler, aPathName, aDirEntAttr); + CleanupStack::Pop(self); + return self; + } + +CRsfwDavAccessContextPropFindFile::~CRsfwDavAccessContextPropFindFile() + { + iOwnDirEnts.ResetAndDestroy(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropfindFile::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindFile::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + CRsfwDirEntAttr** aDirEntAttr) + { + DEBUGSTRING(("CRsfwDavAccessContextPropFindFile::ConstructL")); + DEBUGSTRING16(("aPathName ='%S'", &aPathName)); + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iDirEntAttr = aDirEntAttr; + iTryCount = KCommRetries; + iRemotePathName = aPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindFile::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindFile::StartL() + { + DEBUGSTRING(("DAV: PropFindFile StartL")); + iOwnDirEnts.ResetAndDestroy(); + iWebDavTransaction = iDavAccess->WebDavSession()->PropFindL(iRemotePathName, + 0, + EFalse, + iOwnDirEnts); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindFile::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindFile::TransactionCompleteL() + { + DEBUGSTRING(("DAV: PropFindFile complete")); + + if (iOwnDirEnts.Count() > 0) + { + *iDirEntAttr = iOwnDirEnts[0]->ExtractAttr(); + } + + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPropFindFile::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPropFindFile::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: PropFindFile raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map XML parser errors to KErrCorrupt + if ((aError <= EXmlFeatureLockedWhileParsing) && + (aError >= EXmlParserError)) + { + aError = EXmlParserError; + } + // Map protocol specific error codes into symbian error codes + switch (aError) + { + case EXmlParserError: + aError = KErrCorrupt; + break; + + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case HTTPStatus::EForbidden: + case HTTPStatus::EUnauthorized: + aError = KErrAccessDenied; + break; + case HTTPStatus::EMovedPermanently: + case HTTPStatus::ETemporaryRedirect: + // The object we are looking for exists, but has a different + // type (e.g. we were looking for a file but it is a directory). + // PROPFIND should return not found... + aError = KErrNotFound; + break; + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: PropFindFile err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextGet +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextGet::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextGet* +CRsfwDavAccessContextGet::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags) + { + CRsfwDavAccessContextGet* self = new (ELeave) CRsfwDavAccessContextGet; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aRemotePathName, + aLocalPathName, + aOffset, + aLength, + aFlags); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextGet::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextGet::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aRemotePathName, + const TDesC& aLocalPathName, + TInt aOffset, + TInt* aLength, + TUint aFlags) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iRemotePathName = aRemotePathName; + iLocalPathName = aLocalPathName; + iOffset = aOffset; + iLength = aLength; + iFlags = aFlags; + iTryCount = KCommRetries; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextGet::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextGet::StartL() + { + DEBUGSTRING(("DAV: Get StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->GetL(iRemotePathName, + iLocalPathName, + iOffset, + iLength, + iFlags); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextGet::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextGet::TransactionCompleteL() + { + DEBUGSTRING(("DAV: Get done")); + + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextGet::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextGet::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: Get raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map protocol specific error codes into symbian error codes + switch (aError) + { + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case HTTPStatus::ENotModified: + aError = KErrNone; + break; + + case HTTPStatus::EForbidden: + aError = KErrAccessDenied; + break; + + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: Get err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + + + +// CRsfwDavAccessContextPut +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPut::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextPut* +CRsfwDavAccessContextPut::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + const TDesC8* aLockToken) + { + CRsfwDavAccessContextPut* self = new (ELeave) CRsfwDavAccessContextPut; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aLocalPathName, + aRemotePathName, + aMimeType, + aOffset, + aLength, + aTotalLength, + aLockToken); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPut::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPut::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aLocalPathName, + const TDesC& aRemotePathName, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + const TDesC8* aLockToken) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iLocalPathName = aLocalPathName; + iRemotePathName = aRemotePathName; + iMimeType = aMimeType; + iOffset = aOffset; + iLength = aLength; + iTotalLength = aTotalLength; + iLockToken = aLockToken; + iTryCount = KCommRetries; + iContentRangeSupported = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPut::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPut::StartL() + { + DEBUGSTRING(("DAV: Put StartL")); + iWebDavTransaction = + iDavAccess-> + WebDavSession()-> + PutL(iLocalPathName, + iRemotePathName, + iMimeType, + iOffset, + iLength, + iTotalLength, + iContentRangeSupported, + iLockToken); + + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPut::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPut::TransactionCompleteL() + { + DEBUGSTRING(("DAV: Put done")); + iStatus = KErrNone; + iDone = ETrue; + } + + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextPut::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextPut::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: Put raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected) || + (aError == HTTPStatus::ENotImplemented)) + { + iTryCount--; + } + else + { + // Map protocol specific error codes into Symbian error codes + switch (aError) + { + case HTTPStatus::EForbidden: + aError = KErrAccessDenied; + break; + + case HTTPStatus::EMethodNotAllowed: + case HTTPStatus::EConflict: + // EConflict can mean either resource already exists or + // the parent does not exist. + // However, in our code we make sure that the parent exists. + aError = KErrAlreadyExists; + break; + + case HTTPStatus::EUnsupportedMediaType: + aError = KErrNotSupported; + break; + case HTTPStatus::EInternalServerError: + case RsfwDavStatus::EInsufficientStorage: + aError = KErrDiskFull; + break; + case HTTPStatus::EMovedPermanently: + case HTTPStatus::ETemporaryRedirect: + // It is not allowed to write a file with the same name + // as an existing directory. + aError = KErrAccessDenied; + break; + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: Put err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (aError == HTTPStatus::ENotImplemented) + { + // we assume that the server does not support Content-Range: with PUT + iContentRangeSupported = EFalse; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextMkDir +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMkDir::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextMkDir* +CRsfwDavAccessContextMkDir::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName) + { + CRsfwDavAccessContextMkDir* self = new (ELeave) CRsfwDavAccessContextMkDir; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, aResponseHandler, aPathName); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMkDir::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMkDir::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iTryCount = KCommRetries; + iRemotePathName = aPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMkDir::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMkDir::StartL() + { + DEBUGSTRING(("DAV: MkDir StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->MkDirL(iRemotePathName); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMkDir::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMkDir::TransactionCompleteL() + { + DEBUGSTRING(("DAV: MkDir done")); + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMkDir::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMkDir::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: MkDir raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + /* + Map protocol specific error codes into Symbian error codes + KErrAlreadyExists dirD already exists in /dirA/dirB/dirC/ + KErrAccessDenied dirD already exists but is not a directory. + KErrDirFull There is no room in /dirA/dirB/dirC/ for the new entry, + which is especially applicable to the root directory. + */ + switch (aError) + { + case HTTPStatus::EForbidden: + case HTTPStatus::EConflict: + /* + EConflict can mean either resource already exists + but is not a collection or the parent does not exist. + However, in our code we make sure that the parent exists. + */ + aError = KErrAccessDenied; + break; + + case HTTPStatus::EMethodNotAllowed: + case HTTPStatus::EMovedPermanently: + aError = KErrAlreadyExists; + break; + + case HTTPStatus::EUnsupportedMediaType: + aError = KErrNotSupported; + break; + + case HTTPStatus::EInternalServerError: + case RsfwDavStatus::EInsufficientStorage: + aError = KErrDirFull; + break; + + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: MkDir err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextDelete +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextDelete::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextDelete* +CRsfwDavAccessContextDelete::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TBool aIsDir, + const TDesC8* aLockToken) + { + CRsfwDavAccessContextDelete* self = new (ELeave) CRsfwDavAccessContextDelete; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, aResponseHandler, aPathName, aIsDir, aLockToken); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextDelete::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextDelete::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TBool aIsDir, + const TDesC8* aLockToken) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iIsDir = aIsDir; + iLockToken = aLockToken; + iTryCount = KCommRetries; + iRemotePathName = aPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextDelete::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextDelete::StartL() + { + DEBUGSTRING(("DAV: Delete StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->DeleteL(iRemotePathName, + iIsDir, + iLockToken); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextDelete::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextDelete::TransactionCompleteL() + { + DEBUGSTRING(("DAV: Delete done")); + iDavAccess->RemoveDavFileInfoL(iRemotePathName); + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextDelete::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextDelete::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: Delete raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + switch (aError) + { + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case HTTPStatus::EForbidden: + case RsfwDavStatus::ELocked: + aError = KErrAccessDenied; + break; + case HTTPStatus::EMovedPermanently: + case HTTPStatus::ETemporaryRedirect: + // We are attempting to delete a file + // with the same name as an existing directory + aError = KErrBadName; + break; + + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: Delete err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextMove +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMove::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextMove* +CRsfwDavAccessContextMove::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + const TDesC8* aSrcLockToken, + const TDesC8* aDstLockToken) + { + CRsfwDavAccessContextMove* self = new (ELeave) CRsfwDavAccessContextMove; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aSrcPathName, + aDstPathName, + aOverwrite, + aSrcLockToken, + aDstLockToken); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMove::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMove::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aSrcPathName, + const TDesC& aDstPathName, + TBool aOverwrite, + const TDesC8* aSrcLockToken, + const TDesC8* aDstLockToken) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iSrcPathName = aSrcPathName; + iOverwrite = aOverwrite; + iSrcLockToken = aSrcLockToken; + iDstLockToken = aDstLockToken; + iTryCount = KCommRetries; + iRemotePathName = aDstPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMove::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMove::StartL() + { + DEBUGSTRING(("DAV: Move StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->MoveL(iSrcPathName, + iRemotePathName, + iOverwrite, + iSrcLockToken, + iDstLockToken); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMove::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMove::TransactionCompleteL() + { + DEBUGSTRING(("DAV: Move done")); + // move will delete the old file and does not lock the new one + // so we just remove the token lock info + iDavAccess->RemoveDavFileInfoL(iSrcPathName); + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextMove::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextMove::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: Move raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map protocol specific error codes into Symbian error codes + switch (aError) + { + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case HTTPStatus::EConflict: // source file not found + aError = KErrNotFound; + break; + + case HTTPStatus::EBadGateway: + case HTTPStatus::EForbidden: + aError = KErrBadName; + break; + + case HTTPStatus::EPreconditionFailed: + // Not performed due to the value of the Overwrite header + aError = KErrAlreadyExists; + break; + + case RsfwDavStatus::ELocked: + aError = KErrAccessDenied; + break; + + case HTTPStatus::EMovedPermanently: + case HTTPStatus::ETemporaryRedirect: + // The operation failed as object exists, although its type + // didn't match the type of our parameter (file vs. dir) + aError = KErrAlreadyExists; + break; + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: Move err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextLock +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextLock::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextLock* +CRsfwDavAccessContextLock::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8** aLockToken) + { + CRsfwDavAccessContextLock* self = new (ELeave) CRsfwDavAccessContextLock; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aPathName, + aLockFlags, + aTimeout, + aLockToken); + CleanupStack::Pop(self); + return self; + } + +CRsfwDavAccessContextLock::~CRsfwDavAccessContextLock() + { + delete iDavFileInfo; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextLock::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextLock::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + TUint aLockFlags, + TUint& aTimeout, + TDesC8** aLockToken) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iLockFlags = aLockFlags; + iTimeout = &aTimeout; + iLockToken = aLockToken; + iTryCount = KCommRetries; + iRemotePathName = aPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextLock::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextLock::StartL() + { + DEBUGSTRING(("DAV: Lock StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->LockL(iRemotePathName, + iLockFlags, + *iTimeout, + &iDavFileInfo); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextLock::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextLock::TransactionCompleteL() + { + DEBUGSTRING(("DAV: Lock done")); + + /* + Preconditions: + - we haven't seen the file at all (there is no fileInfo for it) + or + - we have cached it and there is fileinfo with a + lock token (lock token is never assumed to be valid, + if FileEngine decides to call this function) + */ + *iTimeout = iDavFileInfo->Timeout(); + + CRsfwDavFileInfo* storedFileInfo = iDavAccess->DavFileInfoL(iRemotePathName); + HBufC8* lockToken; + if (storedFileInfo) + { + // Lock operation succesful, set lock timeout + if (iDavFileInfo->Name()) + { + storedFileInfo->SetNameL(*(iDavFileInfo->Name())); + } + if (iDavFileInfo->LockToken()) + { + storedFileInfo->SetLockTokenL(*(iDavFileInfo->LockToken())); + } + storedFileInfo->SetTimeout(iDavFileInfo->Timeout()); + lockToken = storedFileInfo->LockToken(); + } + else + { + // new file + iDavAccess->AddDavFileInfo(iDavFileInfo); + lockToken = iDavFileInfo->LockToken(); + // Ownership transferred to CRsfwDavAccess + iDavFileInfo = NULL; + } + + if (iLockToken) + { + // Allocate and return the lock token to the caller + *iLockToken = lockToken->Des().AllocL(); + } + + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextLock::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextLock::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: Lock raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map XML parser errors to KErrCorrupt + if ((aError <= EXmlFeatureLockedWhileParsing) && + (aError >= EXmlParserError)) + { + aError = EXmlParserError; + } + + // Map protocol specific error codes into Symbian error codes + switch (aError) + { + case EXmlParserError: + aError = KErrCorrupt; + break; + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case RsfwDavStatus::ELocked: + aError = KErrAccessDenied; + break; + + default: + MapError(aError); + break; + } + + // Lock operation not successful. + // If we have file info for this let's "reset" relevant parts + // DavFileInfoL may leave if the path is over 255 chars + // that shouldn't happen anymore here as we have already used the path + CRsfwDavFileInfo* davFileInfo = NULL; + TRAPD(err, davFileInfo = iDavAccess->DavFileInfoL(iRemotePathName)); + if (!err && davFileInfo) + { + davFileInfo->ResetLockToken(); + davFileInfo->SetTimeout(0); + } + + DEBUGSTRING(("DAV: Lock err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextRefreshLock +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextRefreshLock::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextRefreshLock* CRsfwDavAccessContextRefreshLock::NewL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken, + TUint& aTimeout) + { + CRsfwDavAccessContextRefreshLock* self = + new (ELeave) CRsfwDavAccessContextRefreshLock; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aPathName, + aLockToken, + aTimeout); + CleanupStack::Pop(self); + return self; + } + +CRsfwDavAccessContextRefreshLock::~CRsfwDavAccessContextRefreshLock() + { + delete iDavFileInfo; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextRefreshLock::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextRefreshLock::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken, + TUint& aTimeout) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iPathName = aPathName; + iLockToken = aLockToken; + iTimeout = &aTimeout; + iTryCount = KCommRetries; + + // set remotepathname to null, so that this request cannot be cancelled + // cancellations come from the UI and this is internal to RFE + iRemotePathName = KNullDesC; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextRefreshLock::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextRefreshLock::StartL() + { + DEBUGSTRING(("DAV: RefreshLock StartL")); + iWebDavTransaction = + iDavAccess-> + WebDavSession()-> + RefreshLockL(iPathName, + *iTimeout, + iLockToken, + &iDavFileInfo); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextRefreshLock::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextRefreshLock::TransactionCompleteL() + { + DEBUGSTRING(("DAV: RefreshLock done")); + + // The server may have changed the timeout, + *iTimeout = iDavFileInfo->Timeout(); + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextRefreshLock::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextRefreshLock::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: RefreshLock raw err=%d", aError)); + if ((aError == KErrCommsLineFail) || +// ? (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map XML parser errors to KErrCorrupt + if ((aError <= EXmlFeatureLockedWhileParsing) && + (aError >= EXmlParserError)) + { + aError = EXmlParserError; + } + + // Map protocol specific error codes into Symbian error codes + switch (aError) + { + case EXmlParserError: + aError = KErrCorrupt; + break; + case HTTPStatus::ENotFound: + aError = KErrNotFound; + break; + + case HTTPStatus::EPreconditionFailed: + aError = KErrArgument; + break; + + case RsfwDavStatus::ELocked: + aError = KErrLocked; + break; + + default: + MapError(aError); + break; + } + + DEBUGSTRING(("DAV: RefreshLock err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// CRsfwDavAccessContextUnlock +// ============================ MEMBER FUNCTIONS ============================== +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextUnlock::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavAccessContextUnlock* +CRsfwDavAccessContextUnlock::NewL(CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken) + { + CRsfwDavAccessContextUnlock* self = new (ELeave) CRsfwDavAccessContextUnlock; + CleanupStack::PushL(self); + self->ConstructL(aDavAccess, + aResponseHandler, + aPathName, + aLockToken); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextUnlock::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextUnlock::ConstructL( + CRsfwDavAccess* aDavAccess, + MRsfwRemoteAccessResponseHandler* aResponseHandler, + const TDesC& aPathName, + const TDesC8* aLockToken) + { + iDavAccess = aDavAccess; + iResponseHandler = aResponseHandler; + iLockToken = aLockToken; + iTryCount = KCommRetries; + iRemotePathName = aPathName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextUnlock::StartL +// Submit the WebDAV transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextUnlock::StartL() + { + DEBUGSTRING(("DAV: Unlock StartL")); + iWebDavTransaction = iDavAccess->WebDavSession()->UnlockL(iRemotePathName, + iLockToken); + SubmitL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextUnlock::TransactionCompleteL +// Handle a successfully completed transaction +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextUnlock::TransactionCompleteL() + { + DEBUGSTRING(("DAV: Unlock done")); + + // Remove the lock + CRsfwDavFileInfo* davFileInfo = iDavAccess->DavFileInfoL(iRemotePathName); + if (davFileInfo) + { + davFileInfo->ResetFlag(TRsfwDavFileInfoFlags::EUnlockPending); + davFileInfo->ResetLockToken(); + iDavAccess->RemoveDavFileInfoL(iRemotePathName); + } + + iStatus = KErrNone; + iDone = ETrue; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavAccessContextUnlock::TransactionError +// Handle a transaction fault +// ---------------------------------------------------------------------------- +// +void CRsfwDavAccessContextUnlock::TransactionError(TInt aError) + { + DEBUGSTRING(("DAV: Unlock raw err=%d", aError)); + + // Currently we don't remove the lock token (CRsfwDavFileInfo struct) + // if UNLOCK returns an error for some reason. + // If lock timeouts are smallish, deleting would make sense + // as the lock may have timed out in which case server returns an + // error for UNLOCK and our client might not even care about + // the result of UNLOCK. + // In this case we have a risk of unwanted never-to-be-deleted + // CRsfwDavFileInfos. + // On the other hand, + // if infinite timeout is used, the current behaviour is better + // (if UNLOCK fails for some reason the client must re-try). + + // at least remove 'unlock pending' flag + CRsfwDavFileInfo* davFileInfo = NULL; + TRAP_IGNORE(davFileInfo = iDavAccess->DavFileInfoL(iRemotePathName)); + + if (davFileInfo) + { + davFileInfo->ResetFlag(TRsfwDavFileInfoFlags::EUnlockPending); + } + + if ((aError == KErrCommsLineFail) || + (aError == KErrNotReady) || + (aError == KErrDisconnected)) + { + iTryCount--; + } + else + { + // Map protocol specific error codes into Symbian error codes + MapError(aError); + DEBUGSTRING(("DAV: Unlock err=%d", aError)); + iStatus = aError; + iTryCount = 0; + } + + if (iTryCount) + { + DEBUGSTRING(("DAV: Retry %d", iTryCount)); + Retry(); + } + else + { + iStatus = aError; + iDone = ETrue; + } + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwdavfileinfo.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavfileinfo.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,184 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Maintain WebDAV info about resources + * +*/ + + +// INCLUDE FILES +#include "rsfwdavfileinfo.h" + +// ============================ MEMBER FUNCTIONS ============================== + +CRsfwDavFileInfo* CRsfwDavFileInfo::NewL() + { + return new (ELeave) CRsfwDavFileInfo(); + } + + +CRsfwDavFileInfo::~CRsfwDavFileInfo() + { + delete iName; + delete iLockToken; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::Name +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwDavFileInfo::Name() + { + return iName; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::SetNameL +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::SetNameL(const TDesC& aName) + { + SetL(iName, aName); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::LockToken +// ---------------------------------------------------------------------------- +// +HBufC8* CRsfwDavFileInfo::LockToken() + { + if (iFlags & TRsfwDavFileInfoFlags::EUnlockPending) + { + return NULL; + } + return iLockToken; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::SetLockTokenL +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::SetLockTokenL(const TDesC8& aLockToken) + { + SetL(iLockToken, aLockToken); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::ResetLockToken +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::ResetLockToken() + { + delete iLockToken; + iLockToken = NULL; + iFlags &= ~TRsfwDavFileInfoFlags::EUnlockPending; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::Timeout +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavFileInfo::Timeout() + { + return iTimeout; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::SetTimeout +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::SetTimeout(TUint aTimeout) + { + iTimeout = aTimeout; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::IsFlag +// ---------------------------------------------------------------------------- +// +TBool CRsfwDavFileInfo::IsFlag(TUint aFlag) + { + return iFlags & aFlag != 0; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::SetFlag +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::SetFlag(TUint aFlag) + { + iFlags |= aFlag; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::ResetFlag +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::ResetFlag(TUint aFlag) + { + iFlags &= ~aFlag; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::SetL +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::SetL(HBufC8*& aDst, const TDesC8& aSrc) + { + if (!aDst) + { + aDst = HBufC8::NewMaxL(aSrc.Length()); + *aDst = aSrc; + } + else if (aSrc.Length() > aDst->Length()) + { + aDst = aDst->ReAllocL(aSrc.Length()); // expand + *aDst = aSrc; + } + else + { + *aDst = aSrc; + if (aSrc.Length() < aDst->Length()) + { + aDst = aDst->ReAllocL(aSrc.Length()); // reclaim space + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavFileInfo::SetL +// ---------------------------------------------------------------------------- +// +void CRsfwDavFileInfo::SetL(HBufC*& aDst, const TDesC& aSrc) + { + if (!aDst) + { + aDst = HBufC::NewMaxL(aSrc.Length()); + *aDst = aSrc; + } + else if (aSrc.Length() > aDst->Length()) + { + aDst = aDst->ReAllocL(aSrc.Length()); // expand + *aDst = aSrc; + } + else + { + *aDst = aSrc; + if (aSrc.Length() < aDst->Length()) + { + aDst = aDst->ReAllocL(aSrc.Length()); // reclaim space + } + } + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwdavproxy.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavproxy.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,46 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: ECOM proxy for DavAccess + * +*/ + + +// INCLUDE FILES +//#include +#include +#include "rsfwdavaccess.h" + +// CONSTANTS +// Map the interface UIDs to implementation factory functions +const TImplementationProxy ImplementationTable[] = + { + {{0x101F9769}, (TProxyNewLPtr)CRsfwDavAccess::NewL} + }; + +// ========================== OTHER EXPORTED FUNCTIONS ======================== + +// ---------------------------------------------------------------------------- +// ImplementationGroupProxy +// Exported proxy for instantiation method resolution +// ---------------------------------------------------------------------------- +// +EXPORT_C const TImplementationProxy* +ImplementationGroupProxy(TInt& aTableCount) + { + aTableCount = sizeof(ImplementationTable) / sizeof(TImplementationProxy); + + return ImplementationTable; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwdavsession.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavsession.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1322 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: API for WebDAV operations + * +*/ + + +// INCLUDE FILES +#include +#include +#include +#include + +#include "rsfwdavsession.h" +#include "rsfwdavtransaction.h" +#include "rsfwconnectionmanager.h" +#include "rsfwpropfindparser.h" +#include "rsfwlockqueryparser.h" +#include "mdebug.h" + +// CONSTANTS +// characters that will be encoded in the url +_LIT8(KSpecials8, " \"<>#%{}|\\^~[]`"); + +// ============================ MEMBER FUNCTIONS ============================== +CRsfwDavSession* CRsfwDavSession::NewL( + MRsfwDavResponseObserver* aWebDavResponseObserver, + MRsfwConnectionObserver* aRsfwConnectionObserver) + { + CRsfwDavSession* self = new (ELeave) CRsfwDavSession; + CleanupStack::PushL(self); + self->ConstructL(aWebDavResponseObserver, aRsfwConnectionObserver); + CleanupStack::Pop(self); + return self; + } + +void CRsfwDavSession::ConstructL( + MRsfwDavResponseObserver* aWebDavResponseObserver, + MRsfwConnectionObserver* aRsfwConnectionObserver) + { + DEBUGSTRING(("DavSess: ConstructL: enter")); + User::LeaveIfError(iFs.Connect()); + iWebDavResponseObserver = aWebDavResponseObserver; + iRsfwConnectionObserver = aRsfwConnectionObserver; + + // Create classes needed for parsing PropFind and Lock request replies + // Creating these later seems to cause emulator hang-ups. + // If the problem does not exist in the real device we may want to + // delay especially Lock parser creation as locking may not be used at all. + Xml::CMatchData* matchData = Xml::CMatchData::NewLC(); + matchData->SetMimeTypeL(KTextXml); + // Select libxml2 parsesr + matchData->SetVariantL(_L8("libxml2")); + // Select Symbian XML Parser (=Expat) +// matchData->SetVariantL(_L8("Symbian")); + iPropFindParserImpl = CRsfwPropFindParser::NewL(); + iPropFindParser = Xml::CParser::NewL(*matchData, *iPropFindParserImpl); + iLockQueryParserImpl = CRsfwLockQueryParser::NewL(); + iLockQueryParser = Xml::CParser::NewL(*matchData, *iLockQueryParserImpl); + CleanupStack::PopAndDestroy(matchData); + + // Open the RHTTPSession + iHttpSession.OpenL(); + iHttpSession.FilterCollection().RemoveFilter( + iHttpSession.StringPool().StringF( HTTP::EAuthentication, RHTTPSession::GetTable() )); + // Install this class as the callback for authentication requests: + // it will take care of basic/digest auth, SSL + InstallAuthenticationL(iHttpSession); + DEBUGSTRING(("auth filter installed")); + } + +CRsfwDavSession::~CRsfwDavSession() + { + DEBUGSTRING(("CRsfwDavSession::~CRsfwDavSession")); + delete iPropFindParser; + delete iPropFindParserImpl; + delete iLockQueryParser; + delete iLockQueryParserImpl; + delete iEncodedHost; + if (iUserName) + { + delete iUserName; + } + if (iPassword) + { + delete iPassword; + } + iHttpSession.Close(); + delete iRsfwConnectionManager; + iFs.Close(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetConnected +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetConnected(TBool aConnected) + { + iConnected = aConnected; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetWebDavSupportClass +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetWebDavSupportClass(TInt aWebDavSupportClass) + { + iWebDavSupportClass = aWebDavSupportClass; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::WebDavSupportClass +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavSession::WebDavSupportClass() + { + return iWebDavSupportClass; + } + + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::OpenL +// After calling this function, use options query +// to trigger TCP level connection. +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::OpenL(const TDesC& aUri, + TInt aPort, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aAuxData) + { + // Store connection parameters + iHost.Zero(); + iDavRoot.Zero(); + + // Here we add the port using a simple approach: + // it needs to go after http://name/ + TInt slashCnt = 0; + TInt cnt = 0; + while (cnt < aUri.Length()) + { + TChar ch = aUri[cnt++]; + if (ch == '/') + { + slashCnt++; + if (slashCnt == 3) + { + iHost.Append(':'); + iHost.AppendNum(aPort); + // At this point we know that + // the remainder of the uri is the root directory + } + } + + if (slashCnt > 2) + { + iDavRoot.Append(ch); + } + else + { + iHost.Append(ch); + } + } + // We elso need an encoded form of the host part + iEncodedHost = EncodeL(iHost.Right(iHost.Length() - KProtocolPrefix)); + + // iDavRoot must be a directory, and thus should end with a slash + Slashify(iDavRoot); + + // Make the pair + iHostRoot.Copy(iHost); + iHostRoot.Append(iDavRoot); + + // Assume that the parameters are constant and stable across the session + iUserName = EncodeL(aUserName); + iPassword = EncodeL(aPassword); + iAuxData.Copy(aAuxData); + + DEBUGSTRING16(("connecting to host='%S', port=%d, root='%S', data=%S", + &iHost, + aPort, + &iDavRoot, + &iAuxData)); + + if (iAuxData.Length() == 0) + { + // in case of empty access point info, set it to '?' (ask user) + _LIT(KAskUser, "?"); + iAuxData.Copy(KAskUser); + } + + if (!iRsfwConnectionManager) + { + iRsfwConnectionManager = + CRsfwConnectionManager::NewL(iRsfwConnectionObserver); + iRsfwConnectionManager->UseIapL(aAuxData); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::OptionsL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::OptionsL() + { + TPtrC null; + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(null, EFalse, &uriParser); + + DEBUGSTRING8(("OPTIONS '%S'", &uriParser.UriDes())); + + // Establish a link-layer connection + if (iRsfwConnectionManager) + { + SetupConnectionL(); + } + + RStringPool stringPool = StringPool(); + + // Introducing the webdav headers for the propfind + RStringF mOptions = stringPool.OpenFStringL(KWebDavOptions); + CleanupClosePushL(mOptions); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpOptions, + uriParser, + mOptions, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(); // mOptions + CleanupStack::PushL(webDavTransaction); + + RHTTPHeaders hdr = webDavTransaction-> + HttpTransaction().Request().GetHeaderCollection(); + + SetBasicHeadersL(hdr, uriParser, ETrue); + + CleanupStack::Pop(2); //webDavTransaction, uri + delete uri; + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::PropFindL +// Implements WebDAV PROPFIND method. +// Parameters: Name of the directory or file +// CRsfwDirEnt pointer array to be filled with directory metadata +// PROPFIND depth +// aIsDir, is this directory or file, +// some extra checks are made based on this... +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::PropFindL(const TDesC &aPath, + TInt aDepth, + TBool aIsDir, + RPointerArray& aDirEnts) + { + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aPath, aIsDir, &uriParser); + + DEBUGSTRING8(("PROPFIND '%S'", &uriParser.UriDes())); + + // This function is used from several places + TWebDavOp op; + if (aDepth == 1) + { + op = EWebDavOpPropFindMulti; + } + else // (aDepth == 0) + { + op = EWebDavOpPropFindSingle; + } + + RStringPool stringPool = StringPool(); + RStringF mPropFind = stringPool.OpenFStringL(KWebDavPropFind); + CleanupClosePushL(mPropFind); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + op, + uriParser, + mPropFind, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(); // mPropFind + CleanupStack::PushL(webDavTransaction); + + RHTTPHeaders hdr = webDavTransaction-> + HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + SetHeaderL(hdr, HTTP::EContentType, KTextXml); + + // Assumes that the target uri has been cached in an earlier connect + SetDepthHeaderL(hdr, aDepth); + + // XML body + HBufC8* requestBodyBuffer = HBufC8::NewL(KDefaultSubmitSize); + TPtr8 requestBodyBufferPtr = requestBodyBuffer->Des(); + + // To make things at least little bit faster, + // let's try to get "minimal" set + // Maybe useful one day: + // - + // - + // Apache mod_dav 1.0.3 doesn't support: + // - + _LIT8(KPropFindRequestBody, "\ +\ +\ +\ +\ +\ +\ +\ +\ +\ +\ +"); + requestBodyBufferPtr.Append(KPropFindRequestBody); + webDavTransaction->SetBodyData(requestBodyBuffer); + + webDavTransaction->SetPropFindDirEntryArray(aDirEnts); + // We must remember the work directory, + // as we don't want to list that when building directory listing. + HBufC* propFindPath = HBufC::NewL(iHostRoot.Length() + + KMaxPath + + 1); + TPtr propFindPathPtr = propFindPath->Des(); + propFindPathPtr.Copy(iDavRoot); + propFindPathPtr.Append(aPath); + // The whole path must end with a slash + Slashify(propFindPathPtr); + // Before comparing the path from the server is decoded, + // so we can compare against the original 16-bit string. + webDavTransaction->SetPropFindPath(propFindPath); + CleanupStack::Pop(2); // webdavtransaction, uri + delete uri; + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::GetL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::GetL(const TDesC& aSrcPath, + const TDesC& aDstPath, + TInt aOffset, + TInt* aLength, + TUint aFlags) + { + // Basically just a HTTP get with some local processing + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aSrcPath, EFalse, &uriParser); + +#ifdef _DEBUG + { + TInt length; + if (aLength) + { + length = *aLength; + } + else + { + length = 0; + } + DEBUGSTRING8(("GET '%S' (off=%d, len=%d)", + &uriParser.UriDes(), + aOffset, + length)); + } +#endif // DEBUG + + // Introducing the webdav headers for GET + RStringPool stringPool = StringPool(); + RStringF mGet = stringPool.StringF(HTTP::EGET, + RHTTPSession::GetTable()); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpGet, + uriParser, + mGet, + NextWebDavTransactionId()); + CleanupStack::PushL(webDavTransaction); + + // Not sure if this is needed: we are setting conditions + // which mod_dav never gets, cos this is a GET.. + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + if (aLength && (*aLength > 0)) // partial get + { + TBuf8 rangeHeader; + _LIT8(KBytesEquals, "bytes="); + rangeHeader.Append(KBytesEquals); + rangeHeader.AppendNum(aOffset); + rangeHeader.Append('-'); + rangeHeader.AppendNum(aOffset + *aLength - 1); + SetHeaderL(hdr, HTTP::ERange, rangeHeader); + } + + webDavTransaction->SetBodyFileL(aDstPath, aOffset, aLength, aFlags); + CleanupStack::Pop(webDavTransaction); + CleanupStack::PopAndDestroy(uri); + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::PutL +// This amounts to a PUT sending the src data to the destination. +// Expects that the aSrcPath param is relative to iDavRoot. +// If aSrcPath is empty, an empty file will be created. +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::PutL(const TDesC& aSrcPath, + const TDesC& aDstPath, + const TDesC8& aMimeType, + TInt aOffset, + TInt aLength, + TInt aTotalLength, + TBool aUseContentRange, + const TDesC8* aLockToken) + { + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aDstPath, EFalse, &uriParser); + + DEBUGSTRING8(("PUT '%S'", &uriParser.UriDes())); + + RStringPool stringPool = StringPool(); + RStringF mPut = stringPool.OpenFStringL(KWebDavPut); + CleanupClosePushL(mPut); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpPut, + uriParser, + mPut, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(); // mPut + CleanupStack::PushL(webDavTransaction); + + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + SetHeaderL(hdr, HTTP::EContentType, aMimeType); + + if (aLength > 0) // partial put + { + if (aUseContentRange) + { + TBuf8 rangeHeader; + _LIT8(KBytes, "bytes "); + rangeHeader.Append(KBytes); + rangeHeader.AppendNum(aOffset); + rangeHeader.Append('-'); + rangeHeader.AppendNum(aOffset + aLength - 1); + rangeHeader.Append('/'); + if (aTotalLength == 0) + { + // The asterisk "*" character means that + // the instance-length is unknown at the time when + // the message was generated. + rangeHeader.Append('*'); + } + else + { + rangeHeader.AppendNum(aTotalLength); + } + SetHeaderL(hdr, HTTP::EContentRange, rangeHeader); + } + else + { + // server doesn't support Content-Range + // Leave with KrrNotSupported + // *aLength = aTotalLength; + } + } + + if (aLockToken) + { + SetLockTokenHeaderL(hdr, uri, aLockToken, ETrue); + } + + webDavTransaction->SetBodyFileL(aSrcPath, aOffset, &aLength, 0); + CleanupStack::Pop(webDavTransaction); + CleanupStack::PopAndDestroy(uri); + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::DeleteL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::DeleteL(const TDesC& aPath, + TBool aIsDir, + const TDesC8* aLockToken) + { + // Needs to take locking into account + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aPath, aIsDir, &uriParser); + + DEBUGSTRING8(("DELETE '%S'", &uriParser.UriDes())); + + RStringPool stringPool = StringPool(); + RStringF mDelete = stringPool.OpenFStringL(KWebDavDelete); + CleanupClosePushL(mDelete); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpDelete, + uriParser, + mDelete, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(); // mDelete + CleanupStack::PushL(webDavTransaction); + + // need to add a special dir on the i + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + if (aLockToken) + { + SetLockTokenHeaderL(hdr, uri, aLockToken, ETrue); + } + + CleanupStack::Pop(webDavTransaction); + CleanupStack::PopAndDestroy(uri); + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::MkDirL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::MkDirL(const TDesC& aPath) + { + // Executes a MKCOL with the specified name + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aPath, ETrue, &uriParser); + + DEBUGSTRING8(("MKCOL '%S'", &uriParser.UriDes())); + + RStringPool stringPool = StringPool(); + RStringF mMkCol = stringPool.OpenFStringL(KWebDavMkCol); + CleanupClosePushL(mMkCol); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpMkCol, + uriParser, + mMkCol, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(1); // mMkCol + CleanupStack::PushL(webDavTransaction); + + // Neeed to add a special dir on the i + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + CleanupStack::Pop(2); // webDavTransaction, uri + delete uri; + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::MoveL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::MoveL(const TDesC& aOldPath, + const TDesC& aNewPath, + TBool aOverwrite, + const TDesC8* aSrcLockToken, + const TDesC8* aDstLockToken) + { + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParserNew; + HBufC8* uriNew = BuildUriLC(aNewPath, EFalse, &uriParserNew); + TUriParser8 uriParserOld; + HBufC8* uriOld = BuildUriLC(aOldPath, EFalse, &uriParserOld); + + DEBUGSTRING8(("MOVE '%S' to '%S'", + &uriParserOld.UriDes(), + &uriParserNew.UriDes())); + + RStringPool stringPool = StringPool(); + RStringF mMove = stringPool.OpenFStringL(KWebDavMove); + CleanupClosePushL(mMove); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpMove, + uriParserOld, + mMove, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(); // mMove + CleanupStack::PushL(webDavTransaction); + + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParserOld, ETrue); + + if (aSrcLockToken) + { + SetLockTokenHeaderL(hdr, uriOld, aSrcLockToken, ETrue); + } + + + if (aDstLockToken) + { + SetLockTokenHeaderL(hdr, uriNew, aDstLockToken, ETrue); + } + + SetHeaderL(hdr, KWebDavDest, *uriNew); + if (aOverwrite) + { + SetHeaderL(hdr, KWebDavOverwrite, KWebDavOverwriteY); + } + else + { + SetHeaderL(hdr, KWebDavOverwrite, KWebDavOverwriteN); + } + + CleanupStack::Pop(webDavTransaction); + CleanupStack::PopAndDestroy(2, uriNew); // uriOld, uriNew + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::LockL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::LockL(const TDesC& aPath, + TUint aFlags, + TUint aTimeout, + CRsfwDavFileInfo** aDavFileInfo) + { + // Opens LOCK transaction + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aPath, EFalse, &uriParser); + + DEBUGSTRING8(("LOCK '%S' (%d seconds)", &uriParser.UriDes(), aTimeout)); + + RStringPool stringPool = StringPool(); + RStringF mLock = stringPool.OpenFStringL(KWebDavLock); + CleanupClosePushL(mLock); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpLock, + uriParser, + mLock, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(&mLock); + CleanupStack::PushL(webDavTransaction); + + // headers + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + SetHeaderL(hdr, HTTP::EContentType, KTextXml); + + HBufC8* timeoutBuffer = HBufC8::NewLC(KMaxFieldValueLength); + TPtr8 timeoutBufferPtr = timeoutBuffer->Des(); + timeoutBufferPtr.Append(KSecondDash); + if (aTimeout != 0) + { + timeoutBufferPtr.AppendNum(aTimeout); + } + SetHeaderL(hdr, KWebDavTimeout, timeoutBufferPtr); + CleanupStack::PopAndDestroy(timeoutBuffer); + + // XML body + HBufC8* requestBodyBuffer = HBufC8::NewL(KDefaultSubmitSize); + TPtr8 requestBodyBufferPtr = requestBodyBuffer->Des(); + + // Note: locktype "write" is currently the only legal value + _LIT8(KLockHeaderFormat, "\ +\ +\ +\ +\ +\ +%S\ +%S\ +\ +"); + + _LIT8(KLockScopeShared, "shared"); + _LIT8(KLockScopeExclusive, "exclusive"); + TPtrC8 lockScope; + if (aFlags & EFileShareAny) + { + lockScope.Set(KLockScopeShared); + } + else + { + lockScope.Set(KLockScopeExclusive); + } + + requestBodyBufferPtr.Format(KLockHeaderFormat, &lockScope, iUserName, iUserName); + webDavTransaction->SetBodyData(requestBodyBuffer); + + HBufC* fileInfoPath = BuildFullPathLC(aPath, EFalse); + webDavTransaction->SetDavFileInfoL(aDavFileInfo, *fileInfoPath); + CleanupStack::PopAndDestroy(fileInfoPath); + CleanupStack::Pop(webDavTransaction); + CleanupStack::PopAndDestroy(uri); + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::UnlockL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::UnlockL(const TDesC& aPath, + const TDesC8* aLockToken) + { + // Opens LOCK transaction + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + if (iWebDavSupportClass < KDavVersionTwo) + { + User::Leave(KErrNotSupported); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aPath, EFalse, &uriParser); + + DEBUGSTRING8(("UNLOCK '%S'", &uriParser.UriDes())); + + RStringPool stringPool = StringPool(); + RStringF mUnlock = stringPool.OpenFStringL(KWebDavUnlock); + CleanupClosePushL(mUnlock); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpUnlock, + uriParser, + mUnlock, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(); // mUnlock + CleanupStack::PushL(webDavTransaction); + + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + HBufC8* lockToken = HBufC8::NewLC(aLockToken->Length() + + KLockTokenOverhead); + TPtr8 lockTokenPtr = lockToken->Des(); + lockTokenPtr.Append('<'); + lockTokenPtr.Append(*aLockToken); + lockTokenPtr.Append('>'); + SetHeaderL(hdr, KWedDavLockToken, lockTokenPtr); + CleanupStack::PopAndDestroy(lockToken); + + CleanupStack::Pop(2); // webdavtransaction , uri + delete uri; + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::RefreshLockL +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavSession::RefreshLockL(const TDesC& aPath, + TUint aTimeout, + const TDesC8* aLockToken, + CRsfwDavFileInfo** aDavFileInfo) + { + // Opens LOCK transaction + if (!IsConnected()) + { + User::Leave(KErrNotReady); + } + + if (iWebDavSupportClass < KDavVersionTwo) + { + User::Leave(KErrNotSupported); + } + + TUriParser8 uriParser; + HBufC8* uri = BuildUriLC(aPath, EFalse, &uriParser); + + DEBUGSTRING8(("LOCK (refresh) '%S' (%d seconds)", + &uriParser.UriDes(), + aTimeout)); + + RStringPool stringPool = StringPool(); + RStringF mLock = stringPool.OpenFStringL(KWebDavLock); + CleanupClosePushL(mLock); + CRsfwDavTransaction* webDavTransaction = + CRsfwDavTransaction::NewL(this, + EWebDavOpRefreshLock, + uriParser, + mLock, + NextWebDavTransactionId()); + CleanupStack::PopAndDestroy(&mLock); + CleanupStack::PushL(webDavTransaction); + + RHTTPHeaders hdr = + webDavTransaction->HttpTransaction().Request().GetHeaderCollection(); + + // Add headers appropriate to all methods + SetBasicHeadersL(hdr, uriParser, ETrue); + + // do not use tagged lock token, as refresh 'If' header + // should always contain only a single lock token + // (only one lock may be refreshed at a time). + SetLockTokenHeaderL(hdr, uri, aLockToken, EFalse); + + HBufC8* timeoutBuffer = HBufC8::NewLC(KMaxFieldValueLength); + TPtr8 timeoutBufferPtr = timeoutBuffer->Des(); + timeoutBufferPtr.Append(KSecondDash); + if (aTimeout != 0) + { + timeoutBufferPtr.AppendNum(aTimeout); + } + SetHeaderL(hdr, KWebDavTimeout, timeoutBufferPtr); + CleanupStack::PopAndDestroy(timeoutBuffer); + + HBufC* fileInfoPath = BuildFullPathLC(aPath, EFalse); + webDavTransaction->SetDavFileInfoL(aDavFileInfo, *fileInfoPath); + CleanupStack::PopAndDestroy(fileInfoPath); + CleanupStack::Pop(webDavTransaction); + CleanupStack::PopAndDestroy(uri); + return webDavTransaction; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::GetCredentialsL +// From MHTTPAuthenticationCallback +// ---------------------------------------------------------------------------- +// +TBool CRsfwDavSession::GetCredentialsL(const TUriC8& /* aURI */, + RString aRealm, + RStringF /*aAuthenticationType*/, + RString& aUserName, + RString& aPassword) + { + // if we have not tried to send the current credentials once, + // and we have at least username proceed, othwise return KErrAccessDenied + if (iCredentialRequestCount || (!iUserName)) + { + iCredentialRequestCount = 0; + User::Leave(KErrAccessDenied); + } + iCredentialRequestCount++; + + TRAPD(err, aUserName = aRealm.Pool().OpenStringL(*iUserName)); + if (!err) + { + TRAP(err, aPassword = aRealm.Pool().OpenStringL(*iPassword)); + if (!err) + { + return ETrue; + } + } + return EFalse; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetHeaderL +// Convenience method for setting up the header. +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetHeaderL(RHTTPHeaders aHeaders, + TInt aHdrField, + const TDesC8& aHdrValue) + { + RStringF valStr = StringPool().OpenFStringL(aHdrValue); + CleanupClosePushL(valStr); + THTTPHdrVal val(valStr); + aHeaders.SetFieldL( + StringPool().StringF(aHdrField, RHTTPSession::GetTable()), val); + CleanupStack::PopAndDestroy(&valStr); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetHeaderL +// Convenience method for setting up the header. +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetHeaderL(RHTTPHeaders aHeaders, + const TDesC8& aHdrName, + const TDesC8& aHdrValue) + { + RStringF nameStr = StringPool().OpenFStringL(aHdrName); + CleanupClosePushL(nameStr); + RStringF valueStr = StringPool().OpenFStringL(aHdrValue); + CleanupClosePushL(valueStr); + THTTPHdrVal value(valueStr); + aHeaders.SetFieldL(nameStr, value); + CleanupStack::PopAndDestroy(2); // valueStr, nameStr + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetBasicHeadersL +// Convenience method for setting up the header. +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetBasicHeadersL(RHTTPHeaders aHeaders, + const TUriC8& aUri, + TBool aNoProxy) + { + // Add headers appropriate to all methods + SetHeaderL(aHeaders, HTTP::EUserAgent, KUserAgent); + SetHeaderL(aHeaders, HTTP::EAccept, KAccept); + // do not send host header if using SSL (not supported currently) + TPtrC8 scheme; + if (aUri.IsPresent(EUriScheme)) + { + scheme.Set(aUri.Extract(EUriScheme)); + } + if (scheme.CompareF(KHttpsScheme8) != 0) + { + SetHeaderL(aHeaders, HTTP::EHost, *iEncodedHost); + } + SetHeaderL(aHeaders, HTTP::EConnection, KKeepAlive); + if (aNoProxy) + { + // see RFC 2518 10.4.5 If Header and Non-DAV Aware Proxies + // "As in general clients may not be able to reliably detect + // non-DAV aware intermediates, they are advised to always + // prevent caching using the request directives mentioned above." + SetHeaderL(aHeaders, HTTP::EPragma, KWebDavNoProxy); + SetHeaderL(aHeaders, HTTP::ECacheControl, KWebDavNoProxy); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetDepthHeaderL +// Some DAV requests require this for specifying depth of copies etc. +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetDepthHeaderL(RHTTPHeaders aHeaders, TInt aDepth) + { + RStringF depthStr = StringPool().OpenFStringL(KWebDavDepth); + CleanupClosePushL(depthStr); + THTTPHdrVal depth(aDepth); + aHeaders.SetFieldL(depthStr, depth); + CleanupStack::PopAndDestroy(&depthStr); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetLockTokenHeaderL +// The lock token header can be tagged with the resource (file) URI +// This is especially important for DELETE and MOVE of a file, +// as they will also affect the container (directory), which is not locked +// (in which case supplying a lock token is an error). +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetLockTokenHeaderL(RHTTPHeaders aHeaders, + const TDesC8* aUri, + const TDesC8* aLockToken, + TBool aUseTaggedLockToken) + { + DEBUGSTRING(("using a tagged lock token")); + // KLockTokenOverhead for 'tagged' lock token is 2 chars around the uri, + // one space, and 4 chars around the locktoken + // i.e. () + TInt tagoverhead; + if (aUseTaggedLockToken) + { + tagoverhead = KTaggedLockTokenOverhead; + } + else + { + tagoverhead = KLockTokenOverhead; + } + HBufC8* lockToken = HBufC8::NewLC(aUri->Length()+ aLockToken->Length() + + tagoverhead); + TPtr8 lockTokenPtr = lockToken->Des(); + if (aUseTaggedLockToken) + { + lockTokenPtr.Format(KTaggedParenthAngleFormat, aUri, aLockToken); + } + else + { + lockTokenPtr.Format(KParenthAngleFormat, aLockToken); + } + + DEBUGSTRING8(("lt='%S'", &lockTokenPtr)); + SetHeaderL(aHeaders, KWebDavIf, lockTokenPtr); + CleanupStack::PopAndDestroy(lockToken); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::WebDavTransactionCompleteL +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::WebDavTransactionCompleteL( + CRsfwDavTransaction* aWebDavTransaction) + { + TUint webDavTransactionId = aWebDavTransaction->Id(); + delete aWebDavTransaction; + iWebDavResponseObserver->RequestCompleteL(webDavTransactionId); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::WebDavTransactionError +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::WebDavTransactionError( + CRsfwDavTransaction* aWebDavTransaction) + { + TUint webDavTransactionId = aWebDavTransaction->Id(); + TInt status = aWebDavTransaction->Status(); + delete aWebDavTransaction; + iWebDavResponseObserver->RequestError(webDavTransactionId, status); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetPropFindParameters +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetPropFindParametersL( + RPointerArray* aDirEntArray, + const TDesC& aPropFindPath, + TInt aDepth) + { + iPropFindParserImpl->SetDirEntArray(aDirEntArray); + iPropFindParserImpl->SetTargetDirectory(aPropFindPath, aDepth); + iPropFindParser->ParseBeginL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetLockQueryParameters +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetLockQueryParameters(CRsfwDavFileInfo* aDavFileInfo) + { + iLockQueryParserImpl->SetDavFileInfo(aDavFileInfo); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::ParsePropFindResponseL +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::ParsePropFindResponseL(const TDesC8& aResponse) + { + // only first call to this function really initiates data structures in the XML parser + iPropfindParsingActive = ETrue; + iPropFindParser->ParseL(aResponse); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::ParseLockResponseL +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::ParseLockResponseL(const TDesC8& aResponse) + { + iLockQueryParser->ParseL(aResponse); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::PropFindResponseEndL +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::PropFindResponseEndL() + { + iPropFindParser->ParseEndL(); + iPropfindParsingActive = EFalse; + TInt err = iPropFindParserImpl->GetLastError(); + if (err) + { + User::Leave(err); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::LockResponseEndL +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::LockResponseEndL() + { + iLockQueryParser->ParseEndL(); + TInt err = iPropFindParserImpl->GetLastError(); + if (err) + { + User::Leave(err); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::CancelParsing +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::CancelParsing(TWebDavOp aOp) + { + // Only will do something if this operation is PROPFIND, + // and we have started to parse the response. + // UI does not allow to cancel LOCK requests. + // If this would be possible this mechanism should be expanded + // to also cover LOCK parsing. + if ((aOp == EWebDavOpPropFindSingle) || + (aOp == EWebDavOpPropFindMulti)) + { + if (iPropfindParsingActive) + { + // When XML parsing is cancelled when the request is cancelled, + // there is some XML error (invalid token etc.), ignore the error + TRAP_IGNORE(iPropFindParser->ParseEndL()); + iPropfindParsingActive = EFalse; + } + } + } + + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::HttpSession +// ---------------------------------------------------------------------------- +// +RHTTPSession& CRsfwDavSession::HttpSession() + { + return iHttpSession; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::StringPool +// ---------------------------------------------------------------------------- +// +RStringPool CRsfwDavSession::StringPool() + { + return iHttpSession.StringPool(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::Slashify +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::Slashify(TDes& aStr) + { + if (aStr.Length() && + (aStr[aStr.Length() - 1] != '/') && + aStr.Length() < aStr.MaxLength()) + { + aStr.Append('/'); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::BuildPathLC +// This function constructs a file path from davroot + path +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwDavSession::BuildPathLC(const TDesC& aRoot, + const TDesC& aPath, + TBool aEndSlash) + { + // 1 is for a possible slash added to the end of the uri... + HBufC* path = HBufC::NewLC(aRoot.Length() + + aPath.Length() + + 1); + TPtr pathPtr = path->Des(); + pathPtr.Append(aRoot); + pathPtr.Append(aPath); + if (aEndSlash) + { + Slashify(pathPtr); + } + return path; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::BuildFullPathLC +// This function constructs a file path from davroot + path +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwDavSession::BuildFullPathLC(const TDesC& aPath, + TBool aEndSlash) + { + return BuildPathLC(iDavRoot, aPath, aEndSlash); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::BuildUriLC +// This function constructs an URI from hostname + davroot + path +// The URI is first escape encoded and then UTF-8 encoded. +// Note that in addition to returning the uri string, this function +// will also "populate" aUriParser with the full URI +// ---------------------------------------------------------------------------- +// +HBufC8* CRsfwDavSession::BuildUriLC(const TDesC& aPath, + TBool aEndSlash, + TUriParser8* aUriParser) + { + // 1 is for a possible slash added to the end of the uri... + HBufC* uri = BuildPathLC(iHostRoot, aPath, aEndSlash); + HBufC8* utf8Path = EncodeL(*uri); + CleanupStack::PopAndDestroy(uri); + CleanupStack::PushL(utf8Path); + TPtr8 utf8PathPtr = utf8Path->Des(); + if (aUriParser) + { + if (aUriParser->Parse(utf8PathPtr) != KErrNone) + { + User::Leave(KErrBadName); + } + } + return utf8Path; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::EncodeL +// First escape encode and then UTF-8 encode data. +// ---------------------------------------------------------------------------- +// +HBufC8* CRsfwDavSession::EncodeL(const TDesC& aData) + { + HBufC8* utf8Data = EscapeUtils::ConvertFromUnicodeToUtf8L(aData); + CleanupStack::PushL(utf8Data); + HBufC8* escapedData = EscapeUtils::EscapeEncodeL(*utf8Data, KSpecials8); + CleanupStack::PopAndDestroy(utf8Data); + return escapedData; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::IsConnected +// ---------------------------------------------------------------------------- +// +TBool CRsfwDavSession::IsConnected() + { + return iConnected; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::NextWebDavTransactionId +// ---------------------------------------------------------------------------- +// +TUint CRsfwDavSession::NextWebDavTransactionId() + { + return ++iCurrentWebDavTransactionId; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavSession::SetupConnectionL +// ---------------------------------------------------------------------------- +// +void CRsfwDavSession::SetupConnectionL() + { + RSocketServ* socketServ; + RConnection* connection; + + DEBUGSTRING(("SetupConnection - start")); + User::LeaveIfError(iRsfwConnectionManager->GetConnection(socketServ, + connection)); + DEBUGSTRING(("iRsfwConnectionManager->GetConnection called")); + // Now bind the HTTP session with the socket server connection + RStringPool stringPool = iHttpSession.StringPool(); + RHTTPConnectionInfo connInfo = iHttpSession.ConnectionInfo(); + connInfo.SetPropertyL( + stringPool.StringF(HTTP::EHttpSocketServ, RHTTPSession::GetTable()), + THTTPHdrVal(socketServ->Handle())); + connInfo.SetPropertyL( + stringPool.StringF(HTTP::EHttpSocketConnection, + RHTTPSession::GetTable()), + THTTPHdrVal(reinterpret_cast(connection))); + DEBUGSTRING(("SetupConnection - done")); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwdavtransaction.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwdavtransaction.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,1013 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Handle WebDAV transactions + * +*/ + + +// INCLUDE FILES +//#include +#include +#include +#include + +#include "rsfwremoteaccess.h" +#include "rsfwdavtransaction.h" +#include "rsfwdavsession.h" +#include "rsfwdavfileinfo.h" +#include "mdebug.h" + +// ============================ MEMBER FUNCTIONS ============================== +// Destructor +CRsfwDavTransaction::~CRsfwDavTransaction() + { + DEBUGSTRING(("WebDAV transaction %d in destructor ...", Id())); + iHttpTransaction.Close(); + iBodyFile.Close(); + delete iRequestBodyBuffer; + delete iPropFindPath; + delete iResponseBuffer; + DEBUGSTRING(("... done")); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction:::NewL +// Two-phased constructor. +// ---------------------------------------------------------------------------- +// +CRsfwDavTransaction* CRsfwDavTransaction::NewL(CRsfwDavSession* aWebDavSession, + TWebDavOp aWebDavOp, + const TUriC8& aUri, + RStringF aMethod, + TUint aTransactionId) + { + CRsfwDavTransaction* self = new (ELeave) CRsfwDavTransaction; + CleanupStack::PushL(self); + self->ConstructL(aWebDavSession, + aWebDavOp, + aUri, + aMethod, + aTransactionId); + CleanupStack::Pop(self); + return self; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::ConstructL +// Symbian 2nd phase constructor can leave. +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::ConstructL(CRsfwDavSession* aWebDavSession, + TWebDavOp aWebDavOp, + const TUriC8& aUri, + RStringF aMethod, + TInt aTransactionId) + { + iWebDavSession = aWebDavSession; + iTransactionId = aTransactionId; + // Borrow the file server from the parent + iFs = iWebDavSession->FileServerSession(); + iWebDavOp = aWebDavOp; + // User may cancel the IAP selection + iStatus = KErrCancel; + iHttpTransaction = iWebDavSession->HttpSession().OpenTransactionL(aUri, + *this, + aMethod); + // Set body supplier as me + switch (aWebDavOp) + { + case EWebDavOpPut: + case EWebDavOpPropFindSingle: + case EWebDavOpPropFindMulti: + case EWebDavOpLock: + iHttpTransaction.Request().SetBody(*this); + break; + + default: + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::SetBodyDataL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::SetBodyData(HBufC8* aRequestBodyBuffer) + { + iRequestBodyBuffer = aRequestBodyBuffer; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::SetBodyFileL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::SetBodyFileL(const TDesC& aPath, + TInt aOffset, + TInt* aLength, + TUint aFlags) + { + iBodyFilePath = aPath; + iBodyFileOffset = aOffset; + iBodyFileFlags = aFlags; + + iParsedBodyFilePath.Set(iBodyFilePath, NULL, NULL); + DEBUGBUFFER((iParsedBodyFilePath.FullName())); + if (iWebDavOp == EWebDavOpPut) + { + if (iBodyFilePath.Length()) + { + + // Check it exists and open a file handle + if (!iFs.IsValidName(iBodyFilePath)) + { + User::Leave(KErrPathNotFound); + } + TInt err = iBodyFile.Open(iFs, + iParsedBodyFilePath.FullName(), + EFileRead | EFileShareAny); + if (err != KErrNone) + { + DEBUGSTRING(("Cannot set body file (err=%d)", err)); + User::Leave(err); + } + if ((*aLength) > 0) // partial PUT + { + iOverallDataSize = *aLength; + } + else + { + User::LeaveIfError(iBodyFile.Size(iOverallDataSize)); + iOverallDataSize -= iBodyFileOffset; + } + iRequestBodyBuffer = HBufC8::NewL(KDefaultSubmitSize); + } + } + else + { + // EWebDavOpGet + iClientsLength = aLength; + if (iClientsLength) + { + *iClientsLength = 0; + } + // store pointer to client's length variable and set it to zero + // we will later reset it based on the content-length header + + if (!iFs.IsValidName(iBodyFilePath)) + { + User::Leave(KErrPathNotFound); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::SetDavFileInfoL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::SetDavFileInfoL(CRsfwDavFileInfo** aDavFileInfo, + const TDesC& aPath) + { + if (aDavFileInfo) + { + iDavFileInfo = CRsfwDavFileInfo::NewL(); + iDavFileInfo->SetNameL(aPath); + *aDavFileInfo = iDavFileInfo; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::SetPropFindDirEntryArray +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::SetPropFindDirEntryArray( + RPointerArray& aDirEnts) + { + // We do not get the ownership + iDirEnts = &aDirEnts; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::SetPropfindPath +// ---------------------------------------------------------------------------- +void CRsfwDavTransaction::SetPropFindPath(HBufC* aPropFindPath) + { + // We get the ownership + iPropFindPath = aPropFindPath; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::Submit +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::SubmitL() + { + DEBUGSTRING(("submitting WebDav operation %d, id=%d ...", + iWebDavOp, + Id())); + TRAPD(err, iHttpTransaction.SubmitL()); + if (err != KErrNone) + { + DEBUGSTRING(("WebDav transaction %d left with err %d!", + Id(), + err)); + // Release resources + Cleanup(); + User::Leave(err); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::Cancel +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::Cancel() + { + DEBUGSTRING(("Canceling WebDav transaction %d ...", Id())); + iHttpTransaction.Cancel(); + // Cancel XML parsing, if ongoing + iWebDavSession->CancelParsing(iWebDavOp); + + // We don't receive any callback from the HTTP stack, + // as we have not registered a filter to get ECancel event, + // so we have to initiate the cleanup process ourselves... + iStatus = KErrCancel; + TransactionError(); + } + +// ------------------------------------------------------------------ +// From MHTTPTransactionCallback +// ------------------------------------------------------------------ + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::MHFRunL +// Called when an action takes place on the transaction. +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::MHFRunL(RHTTPTransaction aTransaction, + const THTTPEvent& aEvent) + { + DEBUGSTRING(("MHFRunL() transaction %d (http id = %d) status: %d", + iTransactionId, + aTransaction.Id(), + aEvent.iStatus)); + + TBool done = EFalse; + TBool ok = EFalse; + switch (aEvent.iStatus) + { + case THTTPEvent::EGotResponseHeaders: // process the headers + { + // HTTP response headers have been received. + // We can determine now if there is + // going to be a response body to save. + RHTTPResponse response = aTransaction.Response(); + iStatus = response.StatusCode(); + DEBUGSTRING(("MHFRunL() THTTPEvent::EGotResponseHeaders, status %d", + iStatus)); + + if (iWebDavOp == EWebDavOpOptions) + { + // Get a pointer to the session owned by WebDavSession + RHTTPSession session = aTransaction.Session(); + RHTTPHeaders hdr = response.GetHeaderCollection(); + + // Get DAV:- header, + // which should be DAV: 1 if WebDAV v. 1 supported + // or DAV: 1, 2 if also WebDAV v. 2 is supported + TBuf8 davBuffer; + _LIT8(KDav, "DAV"); + davBuffer.Append(KDav); + RStringF davString = + session.StringPool().OpenFStringL(davBuffer); + THTTPHdrVal val; + TInt r = hdr.GetField(davString, 0, val); + davString.Close(); + + if (r == KErrNone) + { + RStringF valStr; + valStr = val.StrF(); + TPtrC8 davTag = valStr.DesC(); + DEBUGSTRING8(("DAV: DAV=%S", &davTag)); + TLex8 lex(davTag); + // Skip over non-numeric chars as long as the list continues... + TChar theChar; + TInt supportedLevel = -1; + while (lex.Peek()) + { + theChar = lex.Get(); + if (theChar.IsDigit()) + { + supportedLevel = theChar.GetNumericValue(); + } + } + if (supportedLevel == -1) + { + // DAV not supported... + User::Leave(KErrNotSupported); + } + iWebDavSession->SetWebDavSupportClass(supportedLevel); + } + else + { + DEBUGSTRING(("DAV=")); + if (iStatus == HTTPStatus::EUnauthorized) + { + User::Leave(KErrAccessDenied); + } + else + { + if (iStatus == HTTPStatus::EOk) + { + // everything seemed to be ok, + // but no DAV: header + User::Leave(KErrNotSupported); + } + else + { + User::Leave(iStatus); + } + } + } + } + // Get the content length and create iResponseBuffer, + // where the body will be stored. + // However, if we are copying file from the server, + // the body (file) will just be stored into + // the container file, no memory buffer is needed + if (response.HasBody() && + // iStatus must be in 'Successful' range of HTTP codes 2xx + (iStatus >= 200) && + (iStatus < 300) && + (iStatus != HTTPStatus::ENoContent)) + { + DEBUGSTRING(("MHFRunL() response has a body...")); + MHTTPDataSupplier* responseBody = response.Body(); + switch (iWebDavOp) + { + case EWebDavOpGet: + { + // Prepare to dump the body to container file + TInt err; + if (iStatus == HTTPStatus::EPartialContent) + { + err = iBodyFile.Open(iFs, + iParsedBodyFilePath.FullName(), + EFileWrite | EFileShareAny); + if (err == KErrNone) + { + if (!(iBodyFileFlags & + KRemoteAccessOptionGetToStartOfFile)) + { + TInt pos = iBodyFileOffset; + DEBUGSTRING(("Get: partial content received, seek to %d", pos)); + iBodyFile.Seek(ESeekStart, pos); + if (pos != iBodyFileOffset) + { + // Should never happen + DEBUGSTRING(("Get: seek to %d failed (pos=%d)", + iBodyFileOffset, + pos)); + User::Leave(KErrArgument); + } + } + } + else + { + DEBUGSTRING(("Get: partial content received, will overwrite the cache file, err=%d", err)); + User::LeaveIfError( + iBodyFile.Replace( + iFs, + iParsedBodyFilePath.FullName(), + EFileWrite | EFileShareAny)); + } + } + else // overwrite... + { + DEBUGSTRING(("Get: full content received")); + User::LeaveIfError( + iBodyFile.Replace( + iFs, + iParsedBodyFilePath.FullName(), + EFileStream | EFileWrite | EFileShareAny)); + } + + // larger memory buffer + TInt dataSize = responseBody->OverallDataSize(); + DEBUGSTRING(("MHFRunL() creating a response buffer, size=%d", + dataSize)); + if (dataSize <= KDefaultFileBufferSize) // 40k + { + iResponseBuffer = HBufC8::NewL(dataSize); + } + else + { + iResponseBuffer = HBufC8::NewL(KDefaultFileBufferSize); + } + + } + break; + + case EWebDavOpPropFindSingle: + case EWebDavOpPropFindMulti: + case EWebDavOpLock: + case EWebDavOpRefreshLock: + { + if (iWebDavOp == EWebDavOpPropFindMulti) + { + PropFindResponseBeginL(KDavResourceTypeCollection); + } + else if (iWebDavOp == EWebDavOpPropFindSingle) + { + PropFindResponseBeginL(KDavResourceTypeOther); + } + else + { + LockQueryResponseBegin(); + } + } + break; + + default: + { + // We are not interested in any body + iDiscardBody = ETrue; + } + break; + } + } + else + { + DEBUGSTRING(("MHFRunL() response does not have a body...")); + iDiscardBody = ETrue; + } + } + break; + + case THTTPEvent::EGotResponseBodyData: + { + DEBUGSTRING(("MHFRunL() THTTPEvent::EGotResponseBodyData")); + // Get the body data supplier + TBool allDone; + + MHTTPDataSupplier* responseBody = aTransaction.Response().Body(); + ASSERT(responseBody); + + // Some (more) body data has been received (in the HTTP response) + TPtrC8 bodyData; + allDone = responseBody->GetNextDataPart(bodyData); + DEBUGSTRING(("MHFRunL() body size = %d (all=%d)", + bodyData.Length(), + allDone)); + + if (!iDiscardBody) + { + switch (iWebDavOp) + { + case EWebDavOpPropFindSingle: + case EWebDavOpPropFindMulti: + { + ParsePropFindResponseL(bodyData); + if (allDone) + { + PropFindResponseEndL(); + } + } + break; + case EWebDavOpLock: + case EWebDavOpRefreshLock: + { + ParseLockResponseL(bodyData); + if (allDone) + { + LockResponseEndL(); + } + } + break; + case EWebDavOpGet: + { + // set client's length variable + // based on the amount of data fetched + if (iClientsLength) + { + *iClientsLength += bodyData.Length(); + } + + TPtr8 responseBodyPtr = iResponseBuffer->Des(); + if ((responseBodyPtr.Length() + bodyData.Length()) <= + KDefaultFileBufferSize) + { + responseBodyPtr.Append(bodyData); + } + else + { + DEBUGSTRING(("Get: writing to cache file: %d bytes", + responseBodyPtr.Length())); + User::LeaveIfError(iBodyFile.Write(responseBodyPtr)); + // Reset buffer with new data + responseBodyPtr.Copy(bodyData); + } + + if (allDone) // this was the last chunk + { + DEBUGSTRING(("Get: writing to cache file %d bytes and closing", + responseBodyPtr.Length())); + User::LeaveIfError(iBodyFile.Write(responseBodyPtr)); + iBodyFile.Close(); + } + } + break; + + default: + break; + } + } + + // Done with that bit of body data + responseBody->ReleaseData(); + } + break; + + case THTTPEvent::EResponseComplete: + { + // The transaction's response is complete + DEBUGSTRING(("Transaction Complete")); + } + break; + + case THTTPEvent::ESucceeded: + { + DEBUGSTRING(("Transaction Successful")); + // We need to process the iStatus for the different cases + switch (iWebDavOp) + { + case EWebDavOpPropFindMulti: + case EWebDavOpPropFindSingle: + if (iStatus == RsfwDavStatus::EMultiStatus) + { + iStatus = KErrNone; + ok = ETrue; + } + break; + // Other states which need processing of reponses + case EWebDavOpDelete: + { + // DELETE contains the status of the response in a XML document + // STATUS tag which should be parsed to produce an error + // condition for this working is that we get back a + // status from the server of 204: No Content + if ((iStatus == HTTPStatus::ENoContent || + iStatus == HTTPStatus::EOk)) + { + ok = ETrue; + } + + // Note that if the server reported an error they usually + // return 207 multistatus with an xml body + // containing the status of the DELETE + // should parse the body here + } + break; + + case EWebDavOpMove: + case EWebDavOpMkCol: + case EWebDavOpPut: + if ((iStatus == HTTPStatus::EOk) || + (iStatus == HTTPStatus::ECreated) || + (iStatus == HTTPStatus::ENoContent)) + { + // 200, 201 or 204 would be the expected response + // that everything went well + DEBUGSTRING(("Move/MkCol/Put: status ok")); + ok = ETrue; + } + else + { + // 207 responses contains a status tag in xml data + // 409 would indicate there was a conflict + DEBUGSTRING(("Move/MkCol/Put: bad status!")); + } + break; + + case EWebDavOpGet: + if ((iStatus == HTTPStatus::EOk) || + (iStatus == HTTPStatus::EPartialContent)) + { + ok = ETrue; + } + break; + + case EWebDavOpOptions: + if (iStatus == 200) + { + ok = ETrue; + } + break; + + case EWebDavOpLock: + case EWebDavOpRefreshLock: + { + if ((iStatus == HTTPStatus::ECreated) || + (iStatus == HTTPStatus::EOk)) + { + ok = ETrue; + } + } + break; + + case EWebDavOpUnlock: + ok = ETrue; + break; + + default: + break; + } + + done = ETrue; + } + break; + + case THTTPEvent::EFailed: + { + switch (iWebDavOp) + { + case EWebDavOpOptions: + iStatus = KErrAccessDenied; + break; + + default: + break; + } + + DEBUGSTRING(("Transaction failed")); + done = ETrue; + } + break; + + case THTTPEvent::ERedirectedPermanently: + case KErrHttpRedirectNoLocationField: + { + DEBUGSTRING(("Permanent Redirection")); + iStatus = HTTPStatus::EMovedPermanently; + done = ETrue; + } + break; + + case THTTPEvent::ERedirectedTemporarily: + { + DEBUGSTRING(("Temporary Redirection")); + iStatus = HTTPStatus::ETemporaryRedirect; + done = ETrue; + } + break; + + case THTTPEvent::ERedirectRequiresConfirmation: + iStatus = HTTPStatus::EMovedPermanently; + DEBUGSTRING(("Requires Confirmation")); + // we don't want to resend the request with the new url + // let's just close the request + iHttpTransaction.Close(); + done = ETrue; + break; + + case THTTPEvent::EUnrecoverableError: + DEBUGSTRING(("Unrecoverable error")); + // Go on - we will end up to EFailed later + break; + + case THTTPEvent::ETooMuchRequestData: + DEBUGSTRING(("Too much request data")); + break; + // ESock errors: + case KErrConnectionTerminated: + DEBUGSTRING(("Connection Terminated")); + iStatus = KErrCommsLineFail; + break; + default: + { + // Check the httperr.h header for the meaning of the different fields + DEBUGSTRING(("unrecognized event: %d", aEvent.iStatus)); + iStatus = aEvent.iStatus; + // Close off the transaction if it's an error + if (iStatus < 0) + { + done = ETrue; + } + } + break; + } + + if (done) + { + if (ok) + { + TransactionCompleteL(); + } + else + { + TransactionError(); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::MHFRunError +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavTransaction::MHFRunError(TInt aError, + RHTTPTransaction /* aTransaction*/ , + const THTTPEvent& /* aEvent */) + { + DEBUGSTRING(("MHFRunError() http transaction fired with error %d", + aError)); + + iStatus = aError; + TransactionError(); + return KErrNone; + } + +// ------------------------------------------------------------------ +// From MHTTPDataSupplier +// ------------------------------------------------------------------ + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::GetNextDataPart +// return ETrue if all data has been sent, EFalse otherwise +// ---------------------------------------------------------------------------- +// +TBool CRsfwDavTransaction::GetNextDataPart(TPtrC8& aDataPart) + { + DEBUGSTRING(("GetNextDataPart() (iMoreToCome = EFalse)")); + // Read from the request body file + iMoreToCome = EFalse; + + // we cannot supply more data if the condition is true + if ((!iRequestBodyBuffer) || + (iOverallDataSize == 0 && iWebDavOp == EWebDavOpPut)) + { + DEBUGSTRING(("All data supplied")); + return !iMoreToCome; + } + + switch (iWebDavOp) + { + case EWebDavOpOptions: + case EWebDavOpPropFindSingle: + case EWebDavOpPropFindMulti: + case EWebDavOpLock: + { + // Called when the request body is being filled + aDataPart.Set(*iRequestBodyBuffer); + } + break; + + case EWebDavOpPut: + { + DEBUGSTRING(("Put: GetNextDataPart()")); + if (iSendDataCount == 0) + { + // first run + DEBUGSTRING(("first run")); + TInt pos = iBodyFileOffset; + iBodyFile.Seek(ESeekStart, pos); + } + else + { + DEBUGSTRING(("%d bytes of data have been sent", iSendDataCount)); + } + + // We read data that will be given to the stack next time, + // or we will find out that there is no more data... + TInt readLength; + if ((iOverallDataSize - iSendDataCount) >= KDefaultSubmitSize) + { + readLength = KDefaultSubmitSize; + } + else + { + readLength = iOverallDataSize - iSendDataCount; + } + + + TPtr8 requestBodyBufferPtr = iRequestBodyBuffer->Des(); + TInt err = iBodyFile.Read(requestBodyBufferPtr, readLength); + iSendDataCount = iSendDataCount + iRequestBodyBuffer->Length(); + if (err == KErrNone) + { + DEBUGSTRING(("passing %d bytes of data to the HTTP stack", iRequestBodyBuffer->Length())); + if ((iSendDataCount < iOverallDataSize) && iRequestBodyBuffer->Length() > 0) + { + DEBUGSTRING(("Put: More data to come (iMoreToCome = ETrue)")); + iMoreToCome = ETrue; + } + else + { + DEBUGSTRING(("Put: all data has been exhausted")); + iMoreToCome = EFalse; + } + } + else + { + DEBUGSTRING(("Put: failed to read the local file (err=%d)", + err)); + iMoreToCome = EFalse; + } + aDataPart.Set(*iRequestBodyBuffer); + + break; + } + + default: + break; + } + + return !iMoreToCome; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::ReleaseData +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::ReleaseData() + { + if (iMoreToCome) + { + TRAP_IGNORE(iHttpTransaction.NotifyNewRequestBodyPartL()); + } + else + { + DEBUGSTRING(("Releasing request body buffer")); + delete iRequestBodyBuffer; + iRequestBodyBuffer = NULL; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::OverallDataSize +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavTransaction::OverallDataSize() + { + TInt ods; + switch (iWebDavOp) + { + case EWebDavOpPut: + DEBUGSTRING(("Put: OverallDataSize returned %d", + iOverallDataSize)); + // the size of the file to be copied + ods = iOverallDataSize; + break; + + default: + if (!iRequestBodyBuffer) + { + ods = 0; + } + else + { + ods = iRequestBodyBuffer->Length(); + } + + break; + } + return ods; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::Reset +// ---------------------------------------------------------------------------- +// +TInt CRsfwDavTransaction::Reset() + { + DEBUGSTRING(("Reset data suplier")); + switch (iWebDavOp) + { + case EWebDavOpPut: + iSendDataCount = 0; + break; + + default: + break; + } + return KErrNone; + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::TransactionComplete +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::TransactionCompleteL() + { + iStatus = KErrNone; + if (iWebDavOp == EWebDavOpOptions) + { + iWebDavSession->SetConnected(ETrue); + } + iWebDavOp = EWebDavOpNone; + iWebDavSession->WebDavTransactionCompleteL(this); + // Must not do anything with this transaction object + // after calling the completion callback because this will be destroyed + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::TransactionError +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::TransactionError() + { + Cleanup(); + iWebDavOp = EWebDavOpNone; + iWebDavSession->WebDavTransactionError(this); + // Must not do anything with this transaction object + // after calling the error callback because this will be destroyed + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::Cleanup +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::Cleanup() + { + // Cleanup (e.g., after a failed transaction). + // Only release resources that may block further transactions + // before this transaction has been destroyed. + switch (iWebDavOp) + { + case EWebDavOpGet: + case EWebDavOpPut: + iBodyFile.Close(); + break; + + default: + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::PropFindResponseBeginL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::PropFindResponseBeginL(TInt aDepth) + { + iWebDavSession->SetPropFindParametersL(iDirEnts, + *iPropFindPath, + aDepth); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::LockQueryResponseBeginL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::LockQueryResponseBegin() + { + iWebDavSession->SetLockQueryParameters(iDavFileInfo); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::PropFindResponseEndL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::PropFindResponseEndL() + { + iWebDavSession->PropFindResponseEndL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::LockResponseEndL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::LockResponseEndL() + { + iWebDavSession->LockResponseEndL(); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::ParsePropFindResponseL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::ParsePropFindResponseL(const TDesC8& aResponse) + { + iWebDavSession->ParsePropFindResponseL(aResponse); + } + +// ---------------------------------------------------------------------------- +// CRsfwDavTransaction::ParseLockResponseL +// ---------------------------------------------------------------------------- +// +void CRsfwDavTransaction::ParseLockResponseL(const TDesC8& aResponse) + { + iWebDavSession->ParseLockResponseL(aResponse); + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwlockqueryparser.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwlockqueryparser.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,436 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Parse WebDAV LOCK method response body + * +*/ + + +// INCLUDE FILES +#include "rsfwlockqueryparser.h" +#include "rsfwdavfileinfo.h" +#include "mdebug.h" + +// CONSTANTS +_LIT(KTimeOutTag,"Second-"); + +// ============================ MEMBER FUNCTIONS ============================== + +CRsfwLockQueryParser* CRsfwLockQueryParser::NewLC() + { + CRsfwLockQueryParser* self = new(ELeave) CRsfwLockQueryParser; + CleanupStack::PushL(self); + self->ConstructL(); + return self; + } + +CRsfwLockQueryParser* CRsfwLockQueryParser::NewL() + { + CRsfwLockQueryParser* self = NewLC(); + CleanupStack::Pop(self); + return self; + } + +void CRsfwLockQueryParser::ConstructL() + { + /* + iParseState = ELooking; + */ + } + +CRsfwLockQueryParser::~CRsfwLockQueryParser() + { + delete iContentString; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnStartDocumentL +// This method is a callback to indicate the start of the document. +// @param aDocParam Specifies the various parameters of the document. +// @arg aDocParam.iCharacterSetName The character encoding of the document. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnStartDocumentL( + const Xml::RDocumentParameters& /* aDocParam */, + TInt /* aErrCode */) + { + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnStartDocumentL +// This method is a callback to indicate the end of the document. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnEndDocumentL(TInt aErrCode) + { + if (aErrCode) + { + User::Leave(aErrCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnStartElementL +// This method is a callback to indicate an element has been parsed. +// @param aElement is a handle to the element's details. +// @param aAttributes contains the attributes for the element. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnStartElementL( + const Xml::RTagInfo& aElement, + const Xml::RAttributeArray& /* aAttributes */, + TInt aErrorCode) + { + _LIT8(KLockType, "locktype"); + _LIT8(KLockScope, "lockscope"); + _LIT8(KDepth, "depth"); + _LIT8(KTimeout, "timeout"); + _LIT8(KLockToken, "locktoken"); + + if (aErrorCode) + { + User::Leave(aErrorCode); + } + + switch (iParseState) + { + case ELockType: + // Currently, write is the only acquired type, might change later + break; + + case ELockScope: + // Currently, exclusive is the only acquired type, might change later + break; + + case EDepth: + break; + + case ETimeout: + break; + + case ELockToken: + { + _LIT8(KHref, "href"); + if (((aElement.LocalName()).DesC()).Compare(KHref) == 0) + { + iParseState = EHrefToken; + } + } + break; + + case EHrefToken: + break; + + case ELooking: // we are trying to find the next interesting tag + if (((aElement.LocalName()).DesC()).Compare(KLockType) == 0) + { + iParseState = ELockType; + } + else if (((aElement.LocalName()).DesC()).Compare(KLockScope) == 0) + { + iParseState = ELockScope; + } + else if (((aElement.LocalName()).DesC()).Compare(KDepth) == 0) + { + iParseState = EDepth; + } + else if (((aElement.LocalName()).DesC()).Compare(KTimeout) == 0) + { + iParseState = ETimeout; + } + else if (((aElement.LocalName()).DesC()).Compare(KLockToken) == 0) + { + iParseState = ELockToken; + } + else + { + // lint + } + break; + + default: + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnEndElementL +// This method is a callback to indicate that end of element has been reached. +// @param aElement is a handle to the element's details. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnEndElementL(const Xml::RTagInfo& /* aElement */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + + // otherwise we will continue reading + // if we have some interesting content + if ((iParseState != ELooking) && !iContentString) + { + iParseState = ELooking; + return; + } + + switch (iParseState) + { + case ELockType: + break; + + case ELockScope: + break; + + case EDepth: + { + /* + TPtrC aux; + aux.Set(aBuf); + TLex lex(aux); + lex.Val(iDepth); + */ + } + break; + + case ETimeout: + { + if (iDavFileInfo) + { + _LIT8(KInfinite, "Infinite"); + if (iContentString->Compare(KInfinite) == 0) + { + iDavFileInfo->SetTimeout(KMaxTUint); + } + else + { + // We expect 'Second-x" where x a positive integer + TInt timeout = 0; + if (iContentString->Length() > KTimeOutTag().Length()) + { + TPtrC8 aux; + aux.Set(*iContentString); + TLex8 lex(aux); + lex.SkipAndMark(KTimeOutTag().Length()); + lex.Val(timeout); + } + iDavFileInfo->SetTimeout(timeout); + } + } + } + break; + + case ELockToken: + break; + + case EHrefToken: + if (iDavFileInfo) + { + iDavFileInfo->SetLockTokenL(*iContentString); + } + break; + + case ELooking: + break; + + default: + break; + } + + delete iContentString; + iContentString = NULL; + iParseState = ELooking; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnContentL +// This method is a callback that sends the content of the element. +// Not all the content may be returned in one go. +// The data may be sent in chunks. +// When an OnEndElementL is received there is no more content to be sent. +// @param aBytes is the raw content data for the element. +// The client is responsible for converting the data to the +// required character set if necessary. +// In some instances the content may be binary and must not be converted. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// +void CRsfwLockQueryParser::OnContentL(const TDesC8& aBytes, TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + + // We want to add to contentstring only if we are in a state + // where the content is interesting to us + if ((iParseState == ETimeout) || (iParseState == EHrefToken)) + { + if (!iContentString) + { + iContentString = HBufC8::NewL(aBytes.Length()); + TPtr8 string = iContentString->Des(); + string.Append(aBytes); + } + else + { + iContentString = + iContentString->ReAllocL(iContentString->Length() + + aBytes.Length()); + TPtr8 string = iContentString->Des(); + string.Append(aBytes); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnStartPrefixMappingL +// This method is a notification of the beginning of the scope of a prefix-URI +// Namespace mapping. +// This method is always called before corresponding OnStartElementL method. +// @param aPrefix is the Namespace prefix being declared. +// @param aUri is the Namespace URI the prefix is mapped to. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnStartPrefixMappingL(const RString& /* aPrefix */, + const RString& /* aUri */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnEndPrefixMappingL +// This method is a notification of end of the scope of a prefix-URI mapping. +// This method is called after the corresponding DoEndElementL method. +// @param aPrefix is the Namespace prefix that was mapped. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnEndPrefixMappingL(const RString& /* aPrefix */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnIgnorableWhiteSpaceL +// This method is a notification of ignorable whitespace in element content. +// @param aBytes are the ignored bytes from the document being parsed. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnIgnorableWhiteSpaceL(const TDesC8& /* aBytes */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnSkippedEntityL +// This method is a notification of a skipped entity. +// If the parser encounters an external entity it does not need to expand it - +// it can return the entity as aName for the client to deal with. +// @param aName is the name of the skipped entity. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnSkippedEntityL(const RString& /* aName */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnProcessingInstructionL +// This method is a receive notification of a processing instruction. +// @param aTarget is the processing instruction target. +// @param aData is the processing instruction data. If empty none was supplied. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::OnProcessingInstructionL(const TDesC8& /* aTarget */, + const TDesC8& /* aData */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::OnError +// This method indicates an error has occurred. +// @param aErrorCode is the error code +// ---------------------------------------------------------------------------- +// + +void CRsfwLockQueryParser::OnError(TInt aErrorCode) + { + DEBUGSTRING(("CRsfwLockQueryParser::OnError(%d)", aErrorCode)); + iError = aErrorCode; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::GetExtendedInterface +// This method obtains the interface matching the specified uid. +// @return 0 if no interface matching the uid is found. +// Otherwise, the this pointer cast to that interface. +// @param aUid the uid identifying the required interface. +// ---------------------------------------------------------------------------- +// +TAny* CRsfwLockQueryParser::GetExtendedInterface(const TInt32 /* aUid */) + { + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwLockQueryParser::SetFileDavInfo +// Set a pointer to the directory information structure to be filled. +// ---------------------------------------------------------------------------- +// +void CRsfwLockQueryParser::SetDavFileInfo(CRsfwDavFileInfo* aDavFileInfo) + { + iDavFileInfo = aDavFileInfo; + } + +TInt CRsfwLockQueryParser::GetLastError() + { + return iError; + } + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb remotestoragefw/webdavaccessplugin/src/rsfwpropfindparser.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/remotestoragefw/webdavaccessplugin/src/rsfwpropfindparser.cpp Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,590 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Parse WebDAV PROPFIND method response body + * +*/ + + +// INCLUDE FILES +#include +#include +#include + +#include "rsfwpropfindparser.h" +//#include "rsfwdirent.h" +#include "rsfwdirentattr.h" +#include "mdebug.h" +#include "uri8.h" + +// ============================ MEMBER FUNCTIONS ============================== +CRsfwPropFindParser* CRsfwPropFindParser::NewLC() + { + CRsfwPropFindParser* self = new (ELeave) CRsfwPropFindParser; + CleanupStack::PushL(self); + self->ConstructL(); + return self; + } + +CRsfwPropFindParser* CRsfwPropFindParser::NewL() + { + CRsfwPropFindParser* self = NewLC(); + CleanupStack::Pop(self); + return self; + } + +void CRsfwPropFindParser::ConstructL() + { + ClearDirEntryL(); + iCurrentIsParent = EFalse; + } + +CRsfwPropFindParser::~CRsfwPropFindParser() + { + delete iDirEntry; + delete iContentString; + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnStartDocumentL +// This method is a callback to indicate the start of the document. +// @param aDocParam Specifies the various parameters of the document. +// @arg aDocParam.iCharacterSetName The character encoding of the document. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnStartDocumentL( + const Xml::RDocumentParameters& /* aDocParam */, + TInt aErrCode) + { + iError = KErrNone; // discard the old error + if (!aErrCode) + { + iParseState = ELooking; + } + else + { + User::Leave(aErrCode); + } + + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnStartDocumentL +// This method is a callback to indicate the end of the document. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnEndDocumentL(TInt aErrCode) + { + if (aErrCode) + { + User::Leave(aErrCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnStartElementL +// This method is a callback to indicate an element has been parsed. +// @param aElement is a handle to the element's details. +// @param aAttributes contains the attributes for the element. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnStartElementL( + const Xml::RTagInfo& aElement, + const Xml::RAttributeArray& /* aAttributes */, + TInt aErrorCode) + { + _LIT8(KResponseHeader, "response"); + _LIT8(KContentType, "getcontenttype"); + _LIT8(KDate, "creationdate"); + _LIT8(KModified, "getlastmodified"); + _LIT8(KLength, "getcontentlength"); + _LIT8(KResourceType, "resourcetype"); + _LIT8(KEtag, "getetag"); + + if (aErrorCode) + { + User::Leave(aErrorCode); + } + + switch (iParseState) + { + case EName: + break; + + case EResponse: + { + _LIT8(KHRef, "href"); + if (((aElement.LocalName()).DesC()).Compare(KHRef) == 0) + { + // href that follows response tag is the name of the file + iParseState = EName; + } + } + break; + + case EModified: + break; + + case ELength: + break; + + case EDate: + break; + + case EResourceType: + { + _LIT8(KCollection, "collection"); + if (((aElement.LocalName()).DesC()).Compare(KCollection) == 0) + { + iDirEntry->Attr()->SetAtt(KEntryAttDir); + } + } + break; + + case EContentType: + break; + + case EETag: + break; + + case ELooking: // we are trying to find the next interesting tag + if (((aElement.LocalName()).DesC()).Compare(KModified) == 0) + { + iParseState = EModified; + } + else if (((aElement.LocalName()).DesC()).Compare(KLength) == 0) + { + iParseState = ELength; + } + else if (((aElement.LocalName()).DesC()).Compare(KDate) == 0) + { + iParseState = EDate; + } + else if (((aElement.LocalName()).DesC()).Compare(KResourceType) == 0) + { + iParseState = EResourceType; + } + else if (((aElement.LocalName()).DesC()).Compare(KContentType) == 0) + { + iParseState = EContentType; + } + else if (((aElement.LocalName()).DesC()).Compare(KResponseHeader) == 0) + { + iParseState = EResponse; + } + else if (((aElement.LocalName()).DesC()).Compare(KEtag) == 0) + { + iParseState = EETag; + } + else + { + // lint + } + break; + + default: + break; + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnEndElementL +// This method is a callback to indicate that end of element has been reached. +// @param aElement is a handle to the element's details. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnEndElementL(const Xml::RTagInfo& aElement, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + + // If we reached we can fill next entry in iDirEntArray + _LIT8(KResponse, "*response"); + if (((aElement.LocalName()).DesC()).Match(KResponse) != KErrNotFound) + { + // Save the entry if depth = 0 or depth = 1 and + // this is not the parent directory + switch (iDepth) + { + case 0: + iDirEntArray->Append(iDirEntry); + // ownership transferred + iDirEntry = NULL; + break; + + case 1: + if (!iCurrentIsParent) + { + iDirEntArray->Append(iDirEntry); + // ownership transferred + iDirEntry = NULL; + } + break; + + default: + break; + } + + if (iCurrentIsParent) + { + // We have 'seen' the end tag of parent directory + iCurrentIsParent = EFalse; + } + + // In any case going through an entry is complete, + // reset iDirEntry + ClearDirEntryL(); + delete iContentString; + iContentString = NULL; + iParseState = ELooking; + } + + // otherwise we will continue reading + // if we have some interesting content + if ((iParseState != ELooking) && !iContentString) + { + iParseState = ELooking; + return; + } + + switch (iParseState) + { + case EName: + { + // Figure out whether the entry we are currently reading + // is the directory itself. + // The directory itself is the first one in the reply that + // comes from server, + // and the last one that our XML-parser passes to us + + // if the name is fully qualified URI, only take the path + TPtrC8 uriPtr = iContentString->Des(); + TPtrC8 pathPtr = uriPtr; + TUriParser8 uriParser; + if (uriParser.Parse(uriPtr) == KErrNone) + { + pathPtr.Set(uriParser.Extract(EUriPath)); + } + + + HBufC* name = DecodeL(pathPtr); + CleanupStack::PushL(name); + + if (name->Compare(*iPropFindPath) == 0) + { + iCurrentIsParent = ETrue; + } + else + { + TPtrC namePtr = name->Des(); + if ((namePtr.Length() > 1) && + (namePtr[namePtr.Length() - 1] == '/')) + { + // strip off trailing '/' + namePtr.Set(namePtr.Left(namePtr.Length() - 1)); + } + + TInt pos = namePtr.LocateReverse('/'); + // Shouldn't be negative as + // the path should always start with '/' + if ((pos >= 0) && (namePtr.Length() > 1)) + { + namePtr.Set((namePtr.Right(namePtr.Length() - (pos + 1)))); + } + iDirEntry->SetNameL(namePtr); + } + CleanupStack::PopAndDestroy(name); + } + break; + + case EModified: + { + // Webdav sends dates in RFC 822 format + // (e.g., "Thu, 19 Dec 2002 13:51:16 GMT"). + // We parse them as 8 bit data. + TInternetDate inetDate; + inetDate.SetDateL(*iContentString); + iDirEntry->Attr()->SetModified(inetDate.DateTime()); + } + break; + + case ELength: + { + // Convert to int + TLex8 lex(*iContentString); + TInt len; + User::LeaveIfError(lex.Val(len)); + iDirEntry->Attr()->SetSize(len); + } + break; + + case EETag: + // etag is stored for files + if (!(iDirEntry->Attr()->Att() & KEntryAttDir)) + { + iDirEntry->Attr()->SetETagL(*iContentString); + } + + break; + + case EContentType: + { + iDirEntry->Attr()->SetMimeTypeL(*iContentString); + } + break; + + default: + break; + } + + delete iContentString; + iContentString = NULL; + iParseState = ELooking; + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnContentL +// This method is a callback that sends the content of the element. +// Not all the content may be returned in one go. +// The data may be sent in chunks. +// When an OnEndElementL is received there is no more content to be sent. +// @param aBytes is the raw content data for the element. +// The client is responsible for converting the data to the +// required character set if necessary. +// In some instances the content may be binary and must not be converted. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// +void CRsfwPropFindParser::OnContentL(const TDesC8& aBytes, TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + + // We want to add to contentstring only if we are in a state + // where the content is interesting to us + if ((iParseState == EName) || (iParseState == EModified) || + (iParseState == ELength) || (iParseState ==EETag) || + (iParseState == EContentType)) + { + if (!iContentString) + { + iContentString = HBufC8::NewL(aBytes.Length()); + TPtr8 string = iContentString->Des(); + string.Append(aBytes); + } + else + { + iContentString = + iContentString->ReAllocL(iContentString->Length() + + aBytes.Length()); + TPtr8 string = iContentString->Des(); + string.Append(aBytes); + } + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnStartPrefixMappingL +// This method is a notification of the beginning of the scope of a prefix-URI +// Namespace mapping. +// This method is always called before corresponding OnStartElementL method. +// @param aPrefix is the Namespace prefix being declared. +// @param aUri is the Namespace URI the prefix is mapped to. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnStartPrefixMappingL(const RString& /* aPrefix */, + const RString& /* aUri */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnEndPrefixMappingL +// This method is a notification of end of the scope of a prefix-URI mapping. +// This method is called after the corresponding DoEndElementL method. +// @param aPrefix is the Namespace prefix that was mapped. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnEndPrefixMappingL(const RString& /* aPrefix */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnIgnorableWhiteSpaceL +// This method is a notification of ignorable whitespace in element content. +// @param aBytes are the ignored bytes from the document being parsed. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnIgnorableWhiteSpaceL(const TDesC8& /* aBytes */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnSkippedEntityL +// This method is a notification of a skipped entity. +// If the parser encounters an external entity it does not need to expand it - +// it can return the entity as aName for the client to deal with. +// @param aName is the name of the skipped entity. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnSkippedEntityL(const RString& /* aName */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnProcessingInstructionL +// This method is a receive notification of a processing instruction. +// @param aTarget is the processing instruction target. +// @param aData is the processing instruction data. If empty none was supplied. +// @param aErrorCode is the error code. +// If this is not KErrNone then special action may be required. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnProcessingInstructionL(const TDesC8& /* aTarget */, + const TDesC8& /* aData */, + TInt aErrorCode) + { + if (aErrorCode) + { + User::Leave(aErrorCode); + } + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::OnError +// This method indicates an error has occurred. +// @param aErrorCode is the error code +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::OnError(TInt aErrorCode) + { + DEBUGSTRING(("CRsfwPropFindParser::OnError(%d)", aErrorCode)); + iError = aErrorCode; + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::GetExtendedInterface +// This method obtains the interface matching the specified uid. +// @return 0 if no interface matching the uid is found. +// Otherwise, the this pointer cast to that interface. +// @param aUid the uid identifying the required interface. +// ---------------------------------------------------------------------------- +// +TAny* CRsfwPropFindParser::GetExtendedInterface(const TInt32 /* aUid */) + { + return NULL; + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::SetDirEntArray +// Set a pointer to the directory entry array to be filled. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::SetDirEntArray(RPointerArray* aDirEntArray) + { + iDirEntArray = aDirEntArray; + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::SetTargetDirectory +// Set the directory for which PROPFIND was targeted. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::SetTargetDirectory(const TDesC& aPropFindPath, + TInt aDepth) + { + iPropFindPath = &aPropFindPath; + iDepth = aDepth; + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::ClearDirEntryL() +// Clear directory entry for later use. +// ---------------------------------------------------------------------------- +// +void CRsfwPropFindParser::ClearDirEntryL() + { + delete iDirEntry; + iDirEntry = NULL; + TPtrC noName; + iDirEntry = CRsfwDirEnt::NewL(noName, NULL); + // Will be changed to directory, if we ran into ´ tag + iDirEntry->Attr()->SetAtt(KEntryAttNormal); + } + +// ---------------------------------------------------------------------------- +// CRsfwPropFindParser::DecodeL() +// First UTF-8 decode and then escape decode data. +// ---------------------------------------------------------------------------- +// +HBufC* CRsfwPropFindParser::DecodeL(const TDesC8& aData) + { + HBufC8* utf8Data = EscapeUtils::EscapeDecodeL(aData); + CleanupStack::PushL(utf8Data); + HBufC* data = NULL; + // if converting to unicode fails, just return the escapedecoded string. + TRAPD(err, data = EscapeUtils::ConvertToUnicodeFromUtf8L(*utf8Data)); + if (err) + { + data = HBufC::NewMaxL(utf8Data->Length()); + TPtr dataPtr = data->Des(); + dataPtr.Copy(*utf8Data); + } + CleanupStack::PopAndDestroy(utf8Data); + return data; + + } + +TInt CRsfwPropFindParser::GetLastError() + { + return iError; + } + + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb rsfw_plat/rsfw_access_protocol_plugin_api/group/bld.inf --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/rsfw_plat/rsfw_access_protocol_plugin_api/group/bld.inf Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,29 @@ +/* +* Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: File that exports the files belonging to +: Remote Storage FW MountMan API +* +*/ + + +#include + +PRJ_PLATFORMS +DEFAULT + +PRJ_EXPORTS + +../inc/rsfwmountentryitem.h MW_LAYER_PUBLIC_EXPORT_PATH(rsfwmountentryitem.h) +../inc/rsfwmountman.h MW_LAYER_PUBLIC_EXPORT_PATH(rsfwmountman.h) +../inc/rsfwmountentry.h MW_LAYER_PUBLIC_EXPORT_PATH(rsfwmountentry.h) diff -r 88ee4cf65e19 -r 1aa8c82cb4cb rsfw_plat/rsfw_access_protocol_plugin_api/inc/rsfwmountentry.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/rsfw_plat/rsfw_access_protocol_plugin_api/inc/rsfwmountentry.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,150 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mount configuration entry +* +*/ + + +#ifndef CRSFWMOUNTENTRY_H +#define CRSFWMOUNTENTRY_H + +// INCLUDES +#include +#include +#include + + +// Drive entry constants +// these come from UI specification +const TInt KMaxMountNameLength = 20; +const TInt KMaxMountUriLength = 200; +const TInt KMaxMountUserNameLength = 50; +const TInt KMaxMountPasswordLength = 50; +const TInt KMaxMountAuxDataLength = 64; +const TInt KMaxMountConfItemLength = 200; // Longest possible conf item value. +const TInt KMaxMountConfLength = 512; // Buffer for sending all drive + // configuration values +const TInt KIndexAsStringLength = 4; // how wide string for index + + +// CLASS DECLARATION +/** +* Remote drive (configuration) entry +* +* Drive configuration entry consists of the following values: +* - Index of the entry. Optional. +* - Friendly name. Mandatory. +* - Drive letter. Optional. +* - Drive URL. Mandatory. +* - User name. Optional. +* - Password. Optional +* - Internet Access point. Optional. +* +* Maximum lengths for the strings: +* - Friendly name 20 characters +* - Drive URL 200 characters +* - User name 50 characters +* - Password 50 characters +* Setter functions leave with KErrArgument, if longer values are attempted +* +* Drive Letter must be between J: and Y: +* (see also RFs::DriveList() documentation)¨ +* +* Drive Url must begin with a valid scheme (e.g. https:// or upnp://) +* +* @lib mountstore.dll +* @since Series 60 3.1 +*/ +class CRsfwMountEntry: public CBase + { +public: // Constructors and destructor + /** + * Two-phased constructor. + */ + IMPORT_C static CRsfwMountEntry* NewL(); + + /** + * Two-phased constructor + */ + IMPORT_C static CRsfwMountEntry* NewLC(); + + /** + * Destructor. + */ + IMPORT_C virtual ~CRsfwMountEntry(); + + /** + * Sets an item value + * @param aIndex item index + * @param aValue string value + * @leave KErrArgument, incorrect index or value + */ + IMPORT_C void SetItemL(TInt aIndex, const TDesC8& aValue); + + /** + * Sets an item value + * @param aIndex item index + * @param aValue string value + * @leave KErrArgument, incorrect index or value + */ + IMPORT_C void SetItemL(TInt aIndex, const TDesC& aValue); + + /** + * Sets all item values + * @param aIndex index (only used for positioning the entry - not stored) + * @param aName name + * @param aDriveLetter drive letter + * @param aUri URI + * @param aUserName user name + * @param aPassword password + * @param aIap IAP name + * @leave KErrArgument, one or more parameters incorrect + */ + IMPORT_C void SetEntryL(TInt aIndex, + const TDesC& aName, + TChar aDriveLetter, + const TDesC& aUrl, + const TDesC& aUserName, + const TDesC& aPassword, + const TDesC& aIap); + + /** + * Returns an item value + * An empty value may be an empty string or NULL + */ + IMPORT_C const HBufC* Item(TInt aIndex) const; + + /** + * Clear the entry - the items are set to NULL + */ + IMPORT_C void Clear(); + + /** + * Clone the entry - the items are are copied to the newly created entry + * @return cloned entry + */ + IMPORT_C CRsfwMountEntry* CloneL() const; + +private: + CRsfwMountEntry(); + void ConstructL(); + +private: // Data + RFs iFs; + HBufC* iMountEntryItems[EMountEntryItemCount]; + }; + +#endif // CRSFWMOUNTENTRY_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb rsfw_plat/rsfw_access_protocol_plugin_api/inc/rsfwmountentryitem.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/rsfw_plat/rsfw_access_protocol_plugin_api/inc/rsfwmountentryitem.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,39 @@ +/* +* Copyright (c) 2002-2004 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: Mount entry item definitions +* +*/ + + +#ifndef RSFWMOUNTENTRYITEM_H +#define RSFWMOUNTENTRYITEM_H + +// DATA TYPES +enum TMountEntryItemIndex + { + EMountEntryItemIndex, // used for positioning the entry + EMountEntryItemName, + EMountEntryItemDrive, + EMountEntryItemUri, + EMountEntryItemUserName, + EMountEntryItemPassword, + EMountEntryItemIap, + EMountEntryItemInactivityTimeout, + EMountEntryItemReserved, + EMountEntryItemCount + }; + +#endif // RSFWMOUNTENTRYITEM_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb rsfw_plat/rsfw_access_protocol_plugin_api/inc/rsfwmountman.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/rsfw_plat/rsfw_access_protocol_plugin_api/inc/rsfwmountman.h Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,391 @@ +/* +* Copyright (c) 2004-2006 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "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: RSFW Mount Manager API +* +*/ + + +#ifndef CRSFWMOUNTMAN_H +#define CRSFWMOUNTMAN_H + +#include +#include +#include +#include + +#include // mount entry constants + +class TRsfwMountInfo; + +// FORWARD DECLARATIONS +class CRsfwMountEntry; +class CRsfwMountManImpl; +class CDesC16Array; + +// CONSTANTS +// the secure UID of the server, used as a P&S key category +const TUid KRfeServerSecureUid = { 0x101F970D }; +//the maximum number of remote drives +const TInt KMaxRemoteDrives = 9; + +// DATA TYPES +// Event types for MRsfwMountManObserver +enum TMountManEvent + { + EMountManEventMountConfigurationChanged = 1, + EMountManEventMounted + }; + +// P&S keys +// for notifying UI that a remote drive has been connected or disconnected +enum TRfePSKeys + { + ERsfwPSKeyConnect + }; + +// Connection states +const TUint KMountStronglyConnected = 0x01; +const TUint KMountConnecting = 0x02; // temporary state during establishing a connection + // to the drive, not to be used via MountMan API +const TUint KMountNotConnected = 0x03; + +// CLASS DECLARATION +/** + * Interface for receiving mounting events + * + * @lib mountman.dll + * @since Series 60 3.1 + */ + +class MRsfwMountManObserver + { +public: + /** + * Handles an event emanating from a CRsfwMountMan class + * + * @param aEventType type of the event + * @param aStatus status code + * @param aArg miscellaneous arguments + */ + virtual void HandleMountManEventL(TMountManEvent aEvent, + TInt aStatus, + TAny* aArg) = 0; + }; + +/** + * Encapsulates remote mount configuration. + * + * @lib rsfwmountman.dll + * @since Series 60 3.1 + */ +class TRsfwMountConfig + { +public: // New functions + IMPORT_C void ExternalizeL(RWriteStream& aStream) const; + IMPORT_C void InternalizeL(RReadStream& aStream); + +public: // Data + TChar iDriveLetter; + TBuf iName; + TBuf iUri; + TBuf iUserName; + TBuf iPassword; + TBuf iAuxData; + TUint iFlags; + TInt iInactivityTimeout; + }; + + +/** + * Encapsulates remote mount status information. + * + * @lib rsfwmountman.dll + * @since Series 60 3.1 + */ +class TRsfwMountStatus + { +public: // Data + TInt iVolumeId; + /** iMountState is not used and will be removed */ + TUint iMountState; + /** see KMountStronglyConnected and other connection states */ + TUint iConnectionState; + TInt iCachedSize; + TInt iInactivityTime; + TInt iInactivityTimeout; + TBool iPermanence; + }; + + +/** + * Encapsulates all information about a mount. + * + * @lib rsfwmountman.dll + * @since Series 60 3.1 + */ +class TRsfwMountInfo + { +public: // New functions + void ExternalizeL(RWriteStream& aStream) const; + void InternalizeL(RReadStream& aStream); + +public: // Data + TRsfwMountConfig iMountConfig; + TRsfwMountStatus iMountStatus; + }; + + + + +// CLASS DECLARATION + +/** + * Class for managing mounts to remote file repositories + * + * @lib mountman.dll + * @since Series 60 3.1 + */ + +class CRsfwMountMan : public CBase + { +public: // Constructors and destructor + /** + * Two-phased constructor. + * + * @param aDefaultFlags must be set to KMountFlagInteractive + * if the user is to be prompted during the mount procedure. + * Otherwise the parameter can be set to zero. + * @param mount event observer + * @return pointer to the created CRsfwMountMan object instance + */ + IMPORT_C static CRsfwMountMan* NewL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver); + + /** + * Destructor. + */ + IMPORT_C virtual ~CRsfwMountMan(); + +public: // New functions + /** + * Returns a list of friendly names of all mount configurations + * in the mount configuration repository. + * The entries are returned in the order that they appear in the + * repository. + * @param aNames friendly names + * @return nothing + */ + IMPORT_C void GetMountNamesL(CDesC16Array* aNames) const; + + /** + * Gets the mount configuration entry having the given friendly name. + * The caller must make sure that the name is unique. + * @param aId friendly name + * @return a pointer to the configuration entry or NULL if not found + */ + IMPORT_C const CRsfwMountEntry* MountEntryL(const TDesC& aName) const; + + /** + * Gets the mount configuration entry for the given drive letter. + * @param aDriveLetter drive letter + * @return a pointer to the configuration entry or NULL if not found + */ + IMPORT_C const CRsfwMountEntry* MountEntryL(TChar aDriveLetter) const; + + /** + * Adds a mount configuration entry in the configurations and + * mounts the drive in the File Server. + * If the drive letter item is not set in the configuration, + * a free letter will be allocated. + * Then the EMountEntryItemDrive value in aMountEntry will be changed. + * The EMountEntryItemIndex item of aMountEntry is used for + * positioning the entry in a specific order in the configuration database + * (the index itself is not stored) + * + * @param aMountEntry mount configuration entry + * the ownership of the pointer is transferred to CRsfwMountMan + * @return nothing + * @leave KErrInUse selected drive letter already in used + * @leave KErrInUse selected name is in use + * @leave KErrInUse 9 remote drives already define + * (Number of remote drives is limited by default to 9 so that drive + * letters are also available for other technologies) + * @leave KErrAccessDenied program does not have sufficient capabilities + * required capabilities are DiskAdmin (to mount new remote drive in + * File Server) and WriteDeviceData (to add new remote drive to + * Central Repository) + * @leave KErrNotFound + * File System plug-in, Central Repository table etc. not found + */ + IMPORT_C void AddMountEntryL(CRsfwMountEntry* aMountEntry); + + /** + * Deletes a mount entry from the configurations and unmounts the drive. + * Nothing is done if the entry does not exist. + * + * @param aName name + * @return nothing + */ + IMPORT_C void DeleteMountEntryL(const TDesC& aName); + + /** + * Deletes a mount entry from the configurations and unmounts the drive. + * Nothing is done if the entry does not exist. + * + * @param aDriveLetter drive letter + * @return nothing + */ + IMPORT_C void DeleteMountEntryL(TChar aDriveLetter); + + + /** + * Gets a list of all drives as seen by the File Server + * + * Returns drive letters. + * Letters for local drives are in the front of the list + * Letters for remote drives in order defined in CenRep + * The number of the drives is the same as the length of the list + * + * @param aDriveList returned drive list + * @return number of remote drives + */ + IMPORT_C TInt GetAllDrivesL(TDriveList& aDriveList) const; + + /** + * Gets a list of all remote drives as seen by the File Server + * + * The list contains the letters of the remote drives. + * Letters for remote drives in order defined in CenRep + * The number of the drives is the same as the length of the list + * + * @param aDriveList returned drive list + * @return number of remote drives + */ + IMPORT_C TInt GetRemoteMountListL(TDriveList& aDriveList) const; + + /** + * Gets mount information for an active remote drive. + * + * The information consists of static configuration information and + * status information (such as strongly or weakly connected). + * Note that if the drive is not atctive this function will + * return -1, you need to use MountEntryL to get just the static + * configuration information + * + * @param aDriveLetter drive letter of the mount + * @param aMountInfo returned information + * @return error code + */ + IMPORT_C TInt GetMountInfo(TChar aDriveLetter, TRsfwMountInfo& aMountInfo) const; + + /** + * Sets the connection state of a mount for an active remote drive + * + * @param aDriveLetter drive letter of the mount + * @param aConnectionState + * The following connection states have been defined: + * KMountStronglyConnected = strongly connected state + * KMountWeaklyConnected = weakly connected state + * KMountNotConnected = disconnected state + * + * @return error code + */ + IMPORT_C TInt SetMountConnectionState(TChar aDriveLetter, + TUint aConnectionState); + + /** + * Changes a mount configuration entry in the configurations + * + * @param aMountEntry mount configuration entry + * the ownership of the pointer is transferred to CRsfwMountMan + * @return nothing + * @leave KErrInUse if the name of the mount is used by other mount + * @leave KErrAccessDenied program does not have sufficient capabilities + * required capabilities are DiskAdmin (to mount new remote drive in + * File Server) and WriteDeviceData (to add new remote drive to + * Central Repository) + * @leave KErrNotFound if mount with given letter not found or + * File System plug-in, Central Repository table etc. not found + */ + IMPORT_C void EditMountEntryL(CRsfwMountEntry* aMountEntry); + + + /** + * Refresh a remote directory + * + * Ensures that contents of a remote directory are up to date. + * Synchronous variant deletes the currently cached version. + * Note that this function intentionally does not return directory + * contents. All data should be read through the File Server instead. + * + * @return KErrArgument Path refers to a file + * KErrNotFound path is not found from cache + */ + IMPORT_C TInt RefreshDirectory(const TDesC& aPath); + + /** + * Some applications have problems with handling remote files. + * Function checks whether app with given UID is one of them. + * + * @param aUid UID of the application + * @return ETrue if it is on the black list, otherwise EFalse + */ + IMPORT_C TBool IsAppOnBlackList(TUid aUid) const; + + + /** + * Cancels an active remote file upload or download + * + * @param aFile file name + * @return one of the system wide error codes. + */ + IMPORT_C TInt CancelRemoteTransfer(const TDesC& aFile); + + + /** + * Sets the connection state of a mount for an active remote drive + * sends a bling request, does not wait for reply + * + * @param aDriveLetter drive letter of the mount + * @param aConnectionState + * The following connection states have been defined: + * KMountStronglyConnected = strongly connected state + * KMountWeaklyConnected = weakly connected state + * KMountNotConnected = disconnected state + * + * @return error code + */ + IMPORT_C TInt SetMountConnectionStateBlind(TChar aDriveLetter, + TUint aConnectionState); + + +private: + /** + * C++ default constructor + */ + CRsfwMountMan(); + + /** + * Second phase constructor + */ + void ConstructL(TUint aDefaultFlags, + MRsfwMountManObserver* aMountManObserver); + +private: // Data + CRsfwMountManImpl* iMountManImpl; // implementation + }; + +#endif // CRSFWMOUNTMAN_H + +// End of File diff -r 88ee4cf65e19 -r 1aa8c82cb4cb rsfw_plat/rsfw_access_protocol_plugin_api/remote_storage_fw_mountman_api.metaxml --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/rsfw_plat/rsfw_access_protocol_plugin_api/remote_storage_fw_mountman_api.metaxml Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,18 @@ + + + Remote Storage FW MountMan API + Provides control functions that can be used to mount and unmount remote storages, make queries about active mounts, their connection properties (server name etc.) and connection state (connected/disconnected). It can also be used to set the connection state of some active mount. + c++ + remotestoragefw + + + + + + + + + no + no + + diff -r 88ee4cf65e19 -r 1aa8c82cb4cb sysdef_1_4_0.dtd --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/sysdef_1_4_0.dtd Wed Sep 01 12:15:08 2010 +0100 @@ -0,0 +1,86 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +