15ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen/* 25ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * Copyright (C) 2010 Google Inc. All rights reserved. 35ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * 45ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * Redistribution and use in source and binary forms, with or without 55ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * modification, are permitted provided that the following conditions are 65ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * met: 75ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * 85ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * * Redistributions of source code must retain the above copyright 95ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * notice, this list of conditions and the following disclaimer. 105ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * * Redistributions in binary form must reproduce the above 115ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * copyright notice, this list of conditions and the following disclaimer 125ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * in the documentation and/or other materials provided with the 135ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * distribution. 145ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * * Neither the name of Google Inc. nor the names of its 155ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * contributors may be used to endorse or promote products derived from 165ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * this software without specific prior written permission. 175ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * 185ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 195ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 205ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 215ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 225ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 235ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 245ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 255ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 265ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 275ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 285ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 295ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen */ 305ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 315ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "config.h" 325ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 3368513a70bcd92384395513322f1b801e7bf9c729Steve Block#if ENABLE(FILE_SYSTEM) 345ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 355ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "FileWriter.h" 365ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 375ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "AsyncFileWriter.h" 385ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "Blob.h" 395ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "ExceptionCode.h" 405ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "FileError.h" 41e14391e94c850b8bd03680c23b38978db68687a8John Reck#include "FileException.h" 425ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen#include "ProgressEvent.h" 435ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 445ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsennamespace WebCore { 455ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 465ddde30071f639962dd557c453f2ad01f8f0fd00Kristian MonsenFileWriter::FileWriter(ScriptExecutionContext* context) 475ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen : ActiveDOMObject(context, this) 485ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen , m_readyState(INIT) 49a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch , m_startedWriting(false) 505ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen , m_bytesWritten(0) 515ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen , m_bytesToWrite(0) 52bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen , m_truncateLength(-1) 535ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 545ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 555ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 565ddde30071f639962dd557c453f2ad01f8f0fd00Kristian MonsenFileWriter::~FileWriter() 575ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 585ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (m_readyState == WRITING) 595ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen stop(); 605ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 615ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 625ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenbool FileWriter::hasPendingActivity() const 635ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 645ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return m_readyState == WRITING || ActiveDOMObject::hasPendingActivity(); 655ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 665ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 675ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenbool FileWriter::canSuspend() const 685ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 695ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen // FIXME: It is not currently possible to suspend a FileWriter, so pages with FileWriter can not go into page cache. 705ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return false; 715ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 725ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 735ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::stop() 745ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 754576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (writer() && m_readyState == WRITING) 764576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang writer()->abort(); 77a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_blobBeingWritten.clear(); 785ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_readyState = DONE; 795ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 805ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 815ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::write(Blob* data, ExceptionCode& ec) 825ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 834576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang ASSERT(writer()); 845ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (m_readyState == WRITING) { 85e14391e94c850b8bd03680c23b38978db68687a8John Reck setError(FileError::INVALID_STATE_ERR, ec); 865ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return; 875ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen } 88a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (!data) { 89e14391e94c850b8bd03680c23b38978db68687a8John Reck setError(FileError::TYPE_MISMATCH_ERR, ec); 90a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch return; 91a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } 925ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 93a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_blobBeingWritten = data; 945ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_readyState = WRITING; 95a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_startedWriting = false; 965ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesWritten = 0; 975ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesToWrite = data->size(); 984576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang writer()->write(position(), data); 995ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1005ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1015ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::seek(long long position, ExceptionCode& ec) 1025ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 1034576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang ASSERT(writer()); 1045ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (m_readyState == WRITING) { 105e14391e94c850b8bd03680c23b38978db68687a8John Reck setError(FileError::INVALID_STATE_ERR, ec); 1065ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return; 1075ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen } 1085ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1095ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesWritten = 0; 1105ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesToWrite = 0; 1114576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang seekInternal(position); 1125ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1135ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1145ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::truncate(long long position, ExceptionCode& ec) 1155ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 1164576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang ASSERT(writer()); 117bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen if (m_readyState == WRITING || position < 0) { 118e14391e94c850b8bd03680c23b38978db68687a8John Reck setError(FileError::INVALID_STATE_ERR, ec); 1195ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return; 1205ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen } 1215ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_readyState = WRITING; 1225ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesWritten = 0; 1235ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesToWrite = 0; 124bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_truncateLength = position; 1254576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang writer()->truncate(position); 1265ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1275ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1285ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::abort(ExceptionCode& ec) 1295ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 1304576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang ASSERT(writer()); 1315ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen if (m_readyState != WRITING) { 132e14391e94c850b8bd03680c23b38978db68687a8John Reck setError(FileError::INVALID_STATE_ERR, ec); 1335ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen return; 1345ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen } 135e14391e94c850b8bd03680c23b38978db68687a8John Reck 136e14391e94c850b8bd03680c23b38978db68687a8John Reck m_error = FileError::create(FileError::ABORT_ERR); 1374576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang writer()->abort(); 1385ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1395ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1405ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::didWrite(long long bytes, bool complete) 1415ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 1425ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen ASSERT(bytes + m_bytesWritten > 0); 1435ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen ASSERT(bytes + m_bytesWritten <= m_bytesToWrite); 144a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch if (!m_startedWriting) { 145bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen fireEvent(eventNames().writestartEvent); 146a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_startedWriting = true; 147a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch } 1485ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen m_bytesWritten += bytes; 149a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch ASSERT((m_bytesWritten == m_bytesToWrite) || !complete); 1504576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang setPosition(position() + bytes); 1514576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (position() > length()) 1524576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang setLength(position()); 153a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch fireEvent(eventNames().progressEvent); 154bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen if (complete) { 155a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_blobBeingWritten.clear(); 156a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch fireEvent(eventNames().writeEvent); 157bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_readyState = DONE; 1585ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen fireEvent(eventNames().writeendEvent); 159bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen } 1605ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1615ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 162bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsenvoid FileWriter::didTruncate() 1635ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 164bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen ASSERT(m_truncateLength >= 0); 165bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen fireEvent(eventNames().writestartEvent); 1664576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang setLength(m_truncateLength); 1674576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang if (position() > length()) 1684576aa36e9a9671459299c7963ac95aa94beaea9Shimeng (Simon) Wang setPosition(length()); 169bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_truncateLength = -1; 1705ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen fireEvent(eventNames().writeEvent); 171bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_readyState = DONE; 1725ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen fireEvent(eventNames().writeendEvent); 1735ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1745ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 175e14391e94c850b8bd03680c23b38978db68687a8John Reckvoid FileWriter::didFail(FileError::ErrorCode code) 1765ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 177e14391e94c850b8bd03680c23b38978db68687a8John Reck m_error = FileError::create(code); 1785ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen fireEvent(eventNames().errorEvent); 179e14391e94c850b8bd03680c23b38978db68687a8John Reck if (FileError::ABORT_ERR == code) 180bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen fireEvent(eventNames().abortEvent); 181bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen fireEvent(eventNames().errorEvent); 182a94275402997c11dd2e778633dacf4b7e630a35dBen Murdoch m_blobBeingWritten.clear(); 183bec39347bb3bb5bf1187ccaf471d26247f28b585Kristian Monsen m_readyState = DONE; 1845ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen fireEvent(eventNames().writeendEvent); 1855ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1865ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 1875ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsenvoid FileWriter::fireEvent(const AtomicString& type) 1885ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen{ 189f05b935882198ccf7d81675736e3aeb089c5113aBen Murdoch dispatchEvent(ProgressEvent::create(type, true, m_bytesWritten, m_bytesToWrite)); 1905ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} 1915ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen 192e14391e94c850b8bd03680c23b38978db68687a8John Reckvoid FileWriter::setError(FileError::ErrorCode errorCode, ExceptionCode& ec) 193e14391e94c850b8bd03680c23b38978db68687a8John Reck{ 194e14391e94c850b8bd03680c23b38978db68687a8John Reck ec = FileException::ErrorCodeToExceptionCode(errorCode); 195e14391e94c850b8bd03680c23b38978db68687a8John Reck m_error = FileError::create(errorCode); 196e14391e94c850b8bd03680c23b38978db68687a8John Reck} 197e14391e94c850b8bd03680c23b38978db68687a8John Reck 1985ddde30071f639962dd557c453f2ad01f8f0fd00Kristian Monsen} // namespace WebCore 199e14391e94c850b8bd03680c23b38978db68687a8John Reck 20068513a70bcd92384395513322f1b801e7bf9c729Steve Block#endif // ENABLE(FILE_SYSTEM) 201