1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "content/browser/renderer_host/pepper/quota_reservation.h"
8 #include "base/callback.h"
9 #include "content/public/browser/browser_thread.h"
10 #include "storage/browser/fileapi/file_system_operation_runner.h"
11 #include "storage/browser/fileapi/quota/open_file_handle.h"
12 #include "storage/browser/fileapi/quota/quota_reservation.h"
13 #include "storage/common/fileapi/file_system_util.h"
18 scoped_refptr
<QuotaReservation
> QuotaReservation::Create(
19 scoped_refptr
<storage::FileSystemContext
> file_system_context
,
20 const GURL
& origin_url
,
21 storage::FileSystemType type
) {
22 return scoped_refptr
<QuotaReservation
>(
23 new QuotaReservation(file_system_context
, origin_url
, type
));
26 QuotaReservation::QuotaReservation(
27 scoped_refptr
<storage::FileSystemContext
> file_system_context
,
28 const GURL
& origin_url
,
29 storage::FileSystemType file_system_type
)
30 : file_system_context_(file_system_context
) {
32 file_system_context
->CreateQuotaReservationOnFileTaskRunner(
33 origin_url
, file_system_type
);
36 // For unit testing only.
37 QuotaReservation::QuotaReservation(
38 scoped_refptr
<storage::QuotaReservation
> quota_reservation
,
39 const GURL
& /* origin_url */,
40 storage::FileSystemType
/* file_system_type */)
41 : quota_reservation_(quota_reservation
) {
44 QuotaReservation::~QuotaReservation() {
45 // We should have no open files at this point.
46 DCHECK(files_
.size() == 0);
47 for (FileMap::iterator it
= files_
.begin(); it
!= files_
.end(); ++it
)
51 int64_t QuotaReservation::OpenFile(int32_t id
,
52 const storage::FileSystemURL
& url
) {
53 base::FilePath platform_file_path
;
54 if (file_system_context_
.get()) {
55 base::File::Error error
=
56 file_system_context_
->operation_runner()->SyncGetPlatformPath(
57 url
, &platform_file_path
);
58 if (error
!= base::File::FILE_OK
) {
64 platform_file_path
= url
.path();
67 scoped_ptr
<storage::OpenFileHandle
> file_handle
=
68 quota_reservation_
->GetOpenFileHandle(platform_file_path
);
69 std::pair
<FileMap::iterator
, bool> insert_result
=
70 files_
.insert(std::make_pair(id
, file_handle
.get()));
71 if (insert_result
.second
) {
72 int64_t max_written_offset
= file_handle
->GetMaxWrittenOffset();
73 ignore_result(file_handle
.release());
74 return max_written_offset
;
80 void QuotaReservation::CloseFile(int32_t id
,
81 const ppapi::FileGrowth
& file_growth
) {
82 FileMap::iterator it
= files_
.find(id
);
83 if (it
!= files_
.end()) {
84 it
->second
->UpdateMaxWrittenOffset(file_growth
.max_written_offset
);
85 it
->second
->AddAppendModeWriteAmount(file_growth
.append_mode_write_amount
);
93 void QuotaReservation::ReserveQuota(int64_t amount
,
94 const ppapi::FileGrowthMap
& file_growths
,
95 const ReserveQuotaCallback
& callback
) {
96 for (FileMap::iterator it
= files_
.begin(); it
!= files_
.end(); ++it
) {
97 ppapi::FileGrowthMap::const_iterator growth_it
=
98 file_growths
.find(it
->first
);
99 if (growth_it
!= file_growths
.end()) {
100 it
->second
->UpdateMaxWrittenOffset(growth_it
->second
.max_written_offset
);
101 it
->second
->AddAppendModeWriteAmount(
102 growth_it
->second
.append_mode_write_amount
);
108 quota_reservation_
->RefreshReservation(
109 amount
, base::Bind(&QuotaReservation::GotReservedQuota
, this, callback
));
112 void QuotaReservation::OnClientCrash() { quota_reservation_
->OnClientCrash(); }
114 void QuotaReservation::GotReservedQuota(const ReserveQuotaCallback
& callback
,
115 base::File::Error error
) {
116 ppapi::FileSizeMap file_sizes
;
117 for (FileMap::iterator it
= files_
.begin(); it
!= files_
.end(); ++it
)
118 file_sizes
[it
->first
] = it
->second
->GetMaxWrittenOffset();
120 if (file_system_context_
.get()) {
121 BrowserThread::PostTask(
125 callback
, quota_reservation_
->remaining_quota(), file_sizes
));
127 // Unit testing code path.
128 callback
.Run(quota_reservation_
->remaining_quota(), file_sizes
);
132 void QuotaReservation::DeleteOnCorrectThread() const {
133 if (file_system_context_
.get() &&
134 !file_system_context_
->default_file_task_runner()
135 ->RunsTasksOnCurrentThread()) {
136 file_system_context_
->default_file_task_runner()->DeleteSoon(FROM_HERE
,
139 // We're on the right thread to delete, or unit test.
144 } // namespace content