diff options
Diffstat (limited to 'chrome/browser/renderer_host/database_dispatcher_host.cc')
-rw-r--r-- | chrome/browser/renderer_host/database_dispatcher_host.cc | 200 |
1 files changed, 72 insertions, 128 deletions
diff --git a/chrome/browser/renderer_host/database_dispatcher_host.cc b/chrome/browser/renderer_host/database_dispatcher_host.cc index e7734ac..4c56f3b 100644 --- a/chrome/browser/renderer_host/database_dispatcher_host.cc +++ b/chrome/browser/renderer_host/database_dispatcher_host.cc @@ -97,6 +97,7 @@ bool DatabaseDispatcherHost::OnMessageReceived( IPC_MESSAGE_HANDLER(ViewHostMsg_DatabaseOpened, OnDatabaseOpened) IPC_MESSAGE_HANDLER(ViewHostMsg_DatabaseModified, OnDatabaseModified) IPC_MESSAGE_HANDLER(ViewHostMsg_DatabaseClosed, OnDatabaseClosed) + IPC_MESSAGE_HANDLER_DELAY_REPLY(ViewHostMsg_AllowDatabase, OnAllowDatabase) IPC_MESSAGE_UNHANDLED(handled = false) IPC_END_MESSAGE_MAP_EX() return handled; @@ -107,11 +108,18 @@ void DatabaseDispatcherHost::ReceivedBadMessage(uint32 msg_type) { msg_type, process_handle_); } -// Scheduled by the file thread on the IO thread. -// Sends back to the renderer process the given message. -void DatabaseDispatcherHost::SendMessage(IPC::Message* message) { - DCHECK(ChromeThread::CurrentlyOn(ChromeThread::IO)); - if (!shutdown_) +void DatabaseDispatcherHost::Send(IPC::Message* message) { + if (!ChromeThread::CurrentlyOn(ChromeThread::IO)) { + if (!ChromeThread::PostTask( + ChromeThread::IO, FROM_HERE, + NewRunnableMethod(this, + &DatabaseDispatcherHost::Send, + message))) + delete message; + return; + } + + if (!shutdown_ && resource_message_filter_) resource_message_filter_->Send(message); else delete message; @@ -127,55 +135,13 @@ void DatabaseDispatcherHost::OnDatabaseOpenFile(const string16& vfs_file_name, NewRunnableMethod(this, &DatabaseDispatcherHost::AddObserver)); } - // Only ask permission on the main database file in read/write mode. - if (!VfsBackend::FileTypeIsMainDB(desired_flags) || - !VfsBackend::OpenTypeIsReadWrite(desired_flags)) { - OnDatabaseOpenFileAllowed(vfs_file_name, desired_flags, message_id); - return; - } - - string16 origin_identifier; - string16 database_name; - bool ok = DatabaseUtil::CrackVfsFileName(vfs_file_name, - &origin_identifier, - &database_name, - NULL); - DCHECK(ok); // Should we assume this is an attack and kill the renderer? - if (!ok) { - OnDatabaseOpenFileBlocked(message_id); - return; - } - - // TODO(jorlow): createFromDatabaseIdentifier should not return a pointer. - scoped_ptr<WebSecurityOrigin> security_origin( - WebSecurityOrigin::createFromDatabaseIdentifier(origin_identifier)); - string16 origin(security_origin->toString()); - GURL url = GURL(origin); - - HostContentSettingsMap* host_content_settings_map = resource_message_filter_-> - GetRequestContextForURL(url)->host_content_settings_map(); - ContentSetting content_setting = host_content_settings_map->GetContentSetting( - url.host(), CONTENT_SETTINGS_TYPE_COOKIES); - - if (content_setting == CONTENT_SETTING_ASK) { - // Create a task for each possible outcome. - scoped_ptr<Task> on_allow(NewRunnableMethod( - this, &DatabaseDispatcherHost::OnDatabaseOpenFileAllowed, - vfs_file_name, desired_flags, message_id)); - scoped_ptr<Task> on_block(NewRunnableMethod( - this, &DatabaseDispatcherHost::OnDatabaseOpenFileBlocked, message_id)); - // And then let the permission request object do the rest. - scoped_refptr<DatabasePermissionRequest> request( - new DatabasePermissionRequest(url, database_name, on_allow.release(), - on_block.release(), - host_content_settings_map)); - request->RequestPermission(); - } else if (content_setting == CONTENT_SETTING_ALLOW) { - OnDatabaseOpenFileAllowed(vfs_file_name, desired_flags, message_id); - } else { - DCHECK(content_setting == CONTENT_SETTING_BLOCK); - OnDatabaseOpenFileBlocked(message_id); - } + ChromeThread::PostTask( + ChromeThread::FILE, FROM_HERE, + NewRunnableMethod(this, + &DatabaseDispatcherHost::DatabaseOpenFile, + vfs_file_name, + desired_flags, + message_id)); } static void SetOpenFileResponseParams( @@ -220,12 +186,7 @@ void DatabaseDispatcherHost::DatabaseOpenFile(const string16& vfs_file_name, ViewMsg_DatabaseOpenFileResponse_Params response_params; SetOpenFileResponseParams(&response_params, target_handle, target_dir_handle); - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseOpenFileResponse( - message_id, response_params))); + Send(new ViewMsg_DatabaseOpenFileResponse(message_id, response_params)); } void DatabaseDispatcherHost::OnDatabaseDeleteFile(const string16& vfs_file_name, @@ -273,12 +234,7 @@ void DatabaseDispatcherHost::DatabaseDeleteFile(const string16& vfs_file_name, } } - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseDeleteFileResponse( - message_id, error_code))); + Send(new ViewMsg_DatabaseDeleteFileResponse(message_id, error_code)); } void DatabaseDispatcherHost::OnDatabaseGetFileAttributes( @@ -305,12 +261,7 @@ void DatabaseDispatcherHost::DatabaseGetFileAttributes( DatabaseUtil::GetFullFilePathForVfsFile(db_tracker_, vfs_file_name); if (!db_file.empty()) attributes = VfsBackend::GetFileAttributes(db_file); - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseGetFileAttributesResponse( - message_id, attributes))); + Send(new ViewMsg_DatabaseGetFileAttributesResponse(message_id, attributes)); } void DatabaseDispatcherHost::OnDatabaseGetFileSize( @@ -335,12 +286,7 @@ void DatabaseDispatcherHost::DatabaseGetFileSize(const string16& vfs_file_name, DatabaseUtil::GetFullFilePathForVfsFile(db_tracker_, vfs_file_name); if (!db_file.empty()) size = VfsBackend::GetFileSize(db_file); - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseGetFileSizeResponse( - message_id, size))); + Send(new ViewMsg_DatabaseGetFileSizeResponse(message_id, size)); } void DatabaseDispatcherHost::OnDatabaseOpened(const string16& origin_identifier, @@ -367,13 +313,8 @@ void DatabaseDispatcherHost::DatabaseOpened(const string16& origin_identifier, database_connections_.AddConnection(origin_identifier, database_name); db_tracker_->DatabaseOpened(origin_identifier, database_name, description, estimated_size, &database_size, &space_available); - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseUpdateSize( - origin_identifier, database_name, - database_size, space_available))); + Send(new ViewMsg_DatabaseUpdateSize(origin_identifier, database_name, + database_size, space_available)); } void DatabaseDispatcherHost::OnDatabaseModified( @@ -409,6 +350,49 @@ void DatabaseDispatcherHost::OnDatabaseClosed(const string16& origin_identifier, database_name)); } +void DatabaseDispatcherHost::OnAllowDatabase(const std::string& origin_url, + const string16& name, + const string16& display_name, + unsigned long estimated_size, + IPC::Message* reply_msg) { + GURL url = GURL(origin_url); + HostContentSettingsMap* host_content_settings_map = resource_message_filter_-> + GetRequestContextForURL(url)->host_content_settings_map(); + ContentSetting content_setting = host_content_settings_map->GetContentSetting( + url.host(), CONTENT_SETTINGS_TYPE_COOKIES); + + if (content_setting == CONTENT_SETTING_ASK) { + // Create a task for each possible outcome. + scoped_ptr<Task> on_allow(NewRunnableMethod( + this, &DatabaseDispatcherHost::AllowDatabaseResponse, + reply_msg, CONTENT_SETTING_ALLOW)); + scoped_ptr<Task> on_block(NewRunnableMethod( + this, &DatabaseDispatcherHost::AllowDatabaseResponse, + reply_msg, CONTENT_SETTING_BLOCK)); + // And then let the permission request object do the rest. + scoped_refptr<DatabasePermissionRequest> request( + new DatabasePermissionRequest(url, name, display_name, estimated_size, + on_allow.release(), on_block.release(), + host_content_settings_map)); + request->RequestPermission(); + + // Tell the renderer that it needs to run a nested message loop. + Send(new ViewMsg_SignalCookiePromptEvent()); + return; + } + + AllowDatabaseResponse(reply_msg, content_setting); +} + +void DatabaseDispatcherHost::AllowDatabaseResponse( + IPC::Message* reply_msg, ContentSetting content_setting) { + DCHECK((content_setting == CONTENT_SETTING_ALLOW) || + (content_setting == CONTENT_SETTING_BLOCK)); + ViewHostMsg_AllowDatabase::WriteReplyParams( + reply_msg, content_setting == CONTENT_SETTING_ALLOW); + Send(reply_msg); +} + void DatabaseDispatcherHost::DatabaseClosed(const string16& origin_identifier, const string16& database_name) { DCHECK(ChromeThread::CurrentlyOn(ChromeThread::FILE)); @@ -429,13 +413,8 @@ void DatabaseDispatcherHost::OnDatabaseSizeChanged( int64 space_available) { DCHECK(ChromeThread::CurrentlyOn(ChromeThread::FILE)); if (database_connections_.IsOriginUsed(origin_identifier)) { - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseUpdateSize( - origin_identifier, database_name, - database_size, space_available))); + Send(new ViewMsg_DatabaseUpdateSize(origin_identifier, database_name, + database_size, space_available)); } } @@ -443,40 +422,5 @@ void DatabaseDispatcherHost::OnDatabaseScheduledForDeletion( const string16& origin_identifier, const string16& database_name) { DCHECK(ChromeThread::CurrentlyOn(ChromeThread::FILE)); - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::SendMessage, - new ViewMsg_DatabaseCloseImmediately( - origin_identifier, database_name))); -} - -void DatabaseDispatcherHost::OnDatabaseOpenFileAllowed( - const string16& vfs_file_name, int desired_flags, int32 message_id) { - DCHECK(ChromeThread::CurrentlyOn(ChromeThread::IO)); - if (shutdown_) - return; - - ChromeThread::PostTask( - ChromeThread::FILE, FROM_HERE, - NewRunnableMethod(this, - &DatabaseDispatcherHost::DatabaseOpenFile, - vfs_file_name, - desired_flags, - message_id)); -} - -void DatabaseDispatcherHost::OnDatabaseOpenFileBlocked(int32 message_id) { - DCHECK(ChromeThread::CurrentlyOn(ChromeThread::IO)); - if (shutdown_) - return; - - // This will result in failed transactions NOT a failed window.openDatabase - // call. - ViewMsg_DatabaseOpenFileResponse_Params response_params; - SetOpenFileResponseParams(&response_params, - base::kInvalidPlatformFileValue, - base::kInvalidPlatformFileValue); - SendMessage(new ViewMsg_DatabaseOpenFileResponse(message_id, - response_params)); + Send(new ViewMsg_DatabaseCloseImmediately(origin_identifier, database_name)); } |