1/* 2 * Copyright (C) 2007, 2008, 2013 Apple Inc. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. Neither the name of Apple Inc. ("Apple") nor the names of 14 * its contributors may be used to endorse or promote products derived 15 * from this software without specific prior written permission. 16 * 17 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY 18 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 19 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 20 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY 21 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 22 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 23 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 24 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 */ 28 29#include "config.h" 30#include "SQLTransactionBackend.h" 31 32#if ENABLE(SQL_DATABASE) 33 34#include "AbstractSQLTransaction.h" 35#include "Database.h" // FIXME: Should only be used in the frontend. 36#include "DatabaseAuthorizer.h" 37#include "DatabaseBackend.h" 38#include "DatabaseBackendContext.h" 39#include "DatabaseThread.h" 40#include "DatabaseTracker.h" 41#include "ExceptionCode.h" 42#include "Logging.h" 43#include "OriginLock.h" 44#include "SQLError.h" 45#include "SQLStatementBackend.h" 46#include "SQLTransactionClient.h" 47#include "SQLTransactionCoordinator.h" 48#include "SQLValue.h" 49#include "SQLiteTransaction.h" 50#include <wtf/StdLibExtras.h> 51#include <wtf/text/WTFString.h> 52 53 54// How does a SQLTransaction work? 55// ============================== 56// The SQLTransaction is a state machine that executes a series of states / steps. 57// 58// The work of the transaction states are defined in section of 4.3.2 of the 59// webdatabase spec: http://dev.w3.org/html5/webdatabase/#processing-model 60// 61// the State Transition Graph at a glance: 62// ====================================== 63// 64// Backend . Frontend 65// (works with SQLiteDatabase) . (works with Script) 66// =========================== . =================== 67// . 68// 1. Idle . 69// v . 70// 2. AcquireLock . 71// v . 72// 3. OpenTransactionAndPreflight ------------------------------------------. 73// | . | 74// `-------------------------------> 8. DeliverTransactionCallback --. | 75// . | v v 76// ,-------------------------------------' 9. DeliverTransactionErrorCallback + 77// | . ^ ^ ^ | 78// v . | | | | 79// 4. RunStatements -----------------------------------------------------' | | | 80// | ^ ^ | ^ | . | | | 81// |--------' | | | `------------> 10. DeliverStatementCallback +-----' | | 82// | | | `---------------------------------------------' | | 83// | | `-----------------> 11. DeliverQuotaIncreaseCallback + | | 84// | `-----------------------------------------------------' | | 85// v . | | 86// 5. PostflightAndCommit --+--------------------------------------------------' | 87// |----------> 12. DeliverSuccessCallback + | 88// ,--------------------' . | | 89// v . | | 90// 6. CleanupAndTerminate <-----------------------------------------' | 91// v ^ . | 92// 0. End | . | 93// | . | 94// 7: CleanupAfterTransactionErrorCallback <----------------------------' 95// . 96// 97// the States and State Transitions: 98// ================================ 99// 0. SQLTransactionState::End 100// - the end state. 101// 102// 1. SQLTransactionState::Idle 103// - placeholder state while waiting on frontend/backend, etc. See comment on 104// "State transitions between SQLTransaction and SQLTransactionBackend" 105// below. 106// 107// 2. SQLTransactionState::AcquireLock (runs in backend) 108// - this is the start state. 109// - acquire the "lock". 110// - on "lock" acquisition, goto SQLTransactionState::OpenTransactionAndPreflight. 111// 112// 3. SQLTransactionState::openTransactionAndPreflight (runs in backend) 113// - Sets up an SQLiteTransaction. 114// - begin the SQLiteTransaction. 115// - call the SQLTransactionWrapper preflight if available. 116// - schedule script callback. 117// - on error, goto SQLTransactionState::DeliverTransactionErrorCallback. 118// - goto SQLTransactionState::DeliverTransactionCallback. 119// 120// 4. SQLTransactionState::DeliverTransactionCallback (runs in frontend) 121// - invoke the script function callback() if available. 122// - on error, goto SQLTransactionState::DeliverTransactionErrorCallback. 123// - goto SQLTransactionState::RunStatements. 124// 125// 5. SQLTransactionState::DeliverTransactionErrorCallback (runs in frontend) 126// - invoke the script function errorCallback if available. 127// - goto SQLTransactionState::CleanupAfterTransactionErrorCallback. 128// 129// 6. SQLTransactionState::RunStatements (runs in backend) 130// - while there are statements { 131// - run a statement. 132// - if statementCallback is available, goto SQLTransactionState::DeliverStatementCallback. 133// - on error, 134// goto SQLTransactionState::DeliverQuotaIncreaseCallback, or 135// goto SQLTransactionState::DeliverStatementCallback, or 136// goto SQLTransactionState::deliverTransactionErrorCallback. 137// } 138// - goto SQLTransactionState::PostflightAndCommit. 139// 140// 7. SQLTransactionState::DeliverStatementCallback (runs in frontend) 141// - invoke script statement callback (assume available). 142// - on error, goto SQLTransactionState::DeliverTransactionErrorCallback. 143// - goto SQLTransactionState::RunStatements. 144// 145// 8. SQLTransactionState::DeliverQuotaIncreaseCallback (runs in frontend) 146// - give client a chance to increase the quota. 147// - goto SQLTransactionState::RunStatements. 148// 149// 9. SQLTransactionState::PostflightAndCommit (runs in backend) 150// - call the SQLTransactionWrapper postflight if available. 151// - commit the SQLiteTansaction. 152// - on error, goto SQLTransactionState::DeliverTransactionErrorCallback. 153// - if successCallback is available, goto SQLTransactionState::DeliverSuccessCallback. 154// else goto SQLTransactionState::CleanupAndTerminate. 155// 156// 10. SQLTransactionState::DeliverSuccessCallback (runs in frontend) 157// - invoke the script function successCallback() if available. 158// - goto SQLTransactionState::CleanupAndTerminate. 159// 160// 11. SQLTransactionState::CleanupAndTerminate (runs in backend) 161// - stop and clear the SQLiteTransaction. 162// - release the "lock". 163// - goto SQLTransactionState::End. 164// 165// 12. SQLTransactionState::CleanupAfterTransactionErrorCallback (runs in backend) 166// - rollback the SQLiteTransaction. 167// - goto SQLTransactionState::CleanupAndTerminate. 168// 169// State transitions between SQLTransaction and SQLTransactionBackend 170// ================================================================== 171// As shown above, there are state transitions that crosses the boundary between 172// the frontend and backend. For example, 173// 174// OpenTransactionAndPreflight (state 3 in the backend) 175// transitions to DeliverTransactionCallback (state 8 in the frontend), 176// which in turn transitions to RunStatements (state 4 in the backend). 177// 178// This cross boundary transition is done by posting transition requests to the 179// other side and letting the other side's state machine execute the state 180// transition in the appropriate thread (i.e. the script thread for the frontend, 181// and the database thread for the backend). 182// 183// Logically, the state transitions work as shown in the graph above. But 184// physically, the transition mechanism uses the Idle state (both in the frontend 185// and backend) as a waiting state for further activity. For example, taking a 186// closer look at the 3 state transition example above, what actually happens 187// is as follows: 188// 189// Step 1: 190// ====== 191// In the frontend thread: 192// - waiting quietly is Idle. Not doing any work. 193// 194// In the backend: 195// - is in OpenTransactionAndPreflight, and doing its work. 196// - when done, it transits to the backend DeliverTransactionCallback. 197// - the backend DeliverTransactionCallback sends a request to the frontend 198// to transit to DeliverTransactionCallback, and then itself transits to 199// Idle. 200// 201// Step 2: 202// ====== 203// In the frontend thread: 204// - transits to DeliverTransactionCallback and does its work. 205// - when done, it transits to the frontend RunStatements. 206// - the frontend RunStatements sends a request to the backend to transit 207// to RunStatements, and then itself transits to Idle. 208// 209// In the backend: 210// - waiting quietly in Idle. 211// 212// Step 3: 213// ====== 214// In the frontend thread: 215// - waiting quietly is Idle. Not doing any work. 216// 217// In the backend: 218// - transits to RunStatements, and does its work. 219// ... 220// 221// So, when the frontend or backend are not active, they will park themselves in 222// their Idle states. This means their m_nextState is set to Idle, but they never 223// actually run the corresponding state function. Note: for both the frontend and 224// backend, the state function for Idle is unreachableState(). 225// 226// The states that send a request to their peer across the front/back boundary 227// are implemented with just 2 functions: SQLTransaction::sendToBackendState() 228// and SQLTransactionBackend::sendToFrontendState(). These state functions do 229// nothing but sends a request to the other side to transit to the current 230// state (indicated by m_nextState), and then transits itself to the Idle state 231// to wait for further action. 232 233 234// The Life-Cycle of a SQLTransaction i.e. Who's keeping the SQLTransaction alive? 235// ============================================================================== 236// The RefPtr chain goes something like this: 237// 238// At birth (in DatabaseBackend::runTransaction()): 239// ==================================================== 240// DatabaseBackend // Deque<RefPtr<SQLTransactionBackend>> m_transactionQueue points to ... 241// --> SQLTransactionBackend // RefPtr<SQLTransaction> m_frontend points to ... 242// --> SQLTransaction // RefPtr<SQLTransactionBackend> m_backend points to ... 243// --> SQLTransactionBackend // which is a circular reference. 244// 245// Note: there's a circular reference between the SQLTransaction front-end and 246// back-end. This circular reference is established in the constructor of the 247// SQLTransactionBackend. The circular reference will be broken by calling 248// doCleanup() to nullify m_frontend. This is done at the end of the transaction's 249// clean up state (i.e. when the transaction should no longer be in use thereafter), 250// or if the database was interrupted. See comments on "What happens if a transaction 251// is interrupted?" below for details. 252// 253// After scheduling the transaction with the DatabaseThread (DatabaseBackend::scheduleTransaction()): 254// ====================================================================================================== 255// DatabaseThread // MessageQueue<DatabaseTask> m_queue points to ... 256// --> DatabaseTransactionTask // RefPtr<SQLTransactionBackend> m_transaction points to ... 257// --> SQLTransactionBackend // RefPtr<SQLTransaction> m_frontend points to ... 258// --> SQLTransaction // RefPtr<SQLTransactionBackend> m_backend points to ... 259// --> SQLTransactionBackend // which is a circular reference. 260// 261// When executing the transaction (in DatabaseThread::databaseThread()): 262// ==================================================================== 263// std::unique_ptr<DatabaseTask> task; // points to ... 264// --> DatabaseTransactionTask // RefPtr<SQLTransactionBackend> m_transaction points to ... 265// --> SQLTransactionBackend // RefPtr<SQLTransaction> m_frontend; 266// --> SQLTransaction // RefPtr<SQLTransactionBackend> m_backend points to ... 267// --> SQLTransactionBackend // which is a circular reference. 268// 269// At the end of cleanupAndTerminate(): 270// =================================== 271// At the end of the cleanup state, the SQLTransactionBackend::m_frontend is nullified. 272// If by then, a JSObject wrapper is referring to the SQLTransaction, then the reference 273// chain looks like this: 274// 275// JSObjectWrapper 276// --> SQLTransaction // in RefPtr<SQLTransactionBackend> m_backend points to ... 277// --> SQLTransactionBackend // which no longer points back to its SQLTransaction. 278// 279// When the GC collects the corresponding JSObject, the above chain will be cleaned up 280// and deleted. 281// 282// If there is no JSObject wrapper referring to the SQLTransaction when the cleanup 283// states nullify SQLTransactionBackend::m_frontend, the SQLTransaction will deleted then. 284// However, there will still be a DatabaseTask pointing to the SQLTransactionBackend (see 285// the "When executing the transaction" chain above). This will keep the 286// SQLTransactionBackend alive until DatabaseThread::databaseThread() releases its 287// task std::unique_ptr. 288// 289// What happens if a transaction is interrupted? 290// ============================================ 291// If the transaction is interrupted half way, it won't get to run to state 292// CleanupAndTerminate, and hence, would not have called SQLTransactionBackend's 293// doCleanup(). doCleanup() is where we nullify SQLTransactionBackend::m_frontend 294// to break the reference cycle between the frontend and backend. Hence, we need 295// to cleanup the transaction by other means. 296// 297// Note: calling SQLTransactionBackend::notifyDatabaseThreadIsShuttingDown() 298// is effectively the same as calling SQLTransactionBackend::doClean(). 299// 300// In terms of who needs to call doCleanup(), there are 5 phases in the 301// SQLTransactionBackend life-cycle. These are the phases and how the clean 302// up is done: 303// 304// Phase 1. After Birth, before scheduling 305// 306// - To clean up, DatabaseThread::databaseThread() will call 307// DatabaseBackend::close() during its shutdown. 308// - DatabaseBackend::close() will iterate 309// DatabaseBackend::m_transactionQueue and call 310// notifyDatabaseThreadIsShuttingDown() on each transaction there. 311// 312// Phase 2. After scheduling, before state AcquireLock 313// 314// - If the interruption occures before the DatabaseTransactionTask is 315// scheduled in DatabaseThread::m_queue but hasn't gotten to execute 316// (i.e. DatabaseTransactionTask::performTask() has not been called), 317// then the DatabaseTransactionTask may get destructed before it ever 318// gets to execute. 319// - To clean up, the destructor will check if the task's m_wasExecuted is 320// set. If not, it will call notifyDatabaseThreadIsShuttingDown() on 321// the task's transaction. 322// 323// Phase 3. After state AcquireLock, before "lockAcquired" 324// 325// - In this phase, the transaction would have been added to the 326// SQLTransactionCoordinator's CoordinationInfo's pendingTransactions. 327// - To clean up, during shutdown, DatabaseThread::databaseThread() calls 328// SQLTransactionCoordinator::shutdown(), which calls 329// notifyDatabaseThreadIsShuttingDown(). 330// 331// Phase 4: After "lockAcquired", before state CleanupAndTerminate 332// 333// - In this phase, the transaction would have been added either to the 334// SQLTransactionCoordinator's CoordinationInfo's activeWriteTransaction 335// or activeReadTransactions. 336// - To clean up, during shutdown, DatabaseThread::databaseThread() calls 337// SQLTransactionCoordinator::shutdown(), which calls 338// notifyDatabaseThreadIsShuttingDown(). 339// 340// Phase 5: After state CleanupAndTerminate 341// 342// - This is how a transaction ends normally. 343// - state CleanupAndTerminate calls doCleanup(). 344 345namespace WebCore { 346 347PassRefPtr<SQLTransactionBackend> SQLTransactionBackend::create(DatabaseBackend* db, 348 PassRefPtr<AbstractSQLTransaction> frontend, PassRefPtr<SQLTransactionWrapper> wrapper, bool readOnly) 349{ 350 return adoptRef(new SQLTransactionBackend(db, frontend, wrapper, readOnly)); 351} 352 353SQLTransactionBackend::SQLTransactionBackend(DatabaseBackend* db, 354 PassRefPtr<AbstractSQLTransaction> frontend, PassRefPtr<SQLTransactionWrapper> wrapper, bool readOnly) 355 : m_frontend(frontend) 356 , m_database(db) 357 , m_wrapper(wrapper) 358 , m_hasCallback(m_frontend->hasCallback()) 359 , m_hasSuccessCallback(m_frontend->hasSuccessCallback()) 360 , m_hasErrorCallback(m_frontend->hasErrorCallback()) 361 , m_shouldRetryCurrentStatement(false) 362 , m_modifiedDatabase(false) 363 , m_lockAcquired(false) 364 , m_readOnly(readOnly) 365 , m_hasVersionMismatch(false) 366{ 367 ASSERT(m_database); 368 m_frontend->setBackend(this); 369 m_requestedState = SQLTransactionState::AcquireLock; 370} 371 372SQLTransactionBackend::~SQLTransactionBackend() 373{ 374 ASSERT(!m_sqliteTransaction); 375} 376 377void SQLTransactionBackend::doCleanup() 378{ 379 if (!m_frontend) 380 return; 381 m_frontend = 0; // Break the reference cycle. See comment about the life-cycle above. 382 383 ASSERT(currentThread() == database()->databaseContext()->databaseThread()->getThreadID()); 384 385 releaseOriginLockIfNeeded(); 386 387 MutexLocker locker(m_statementMutex); 388 m_statementQueue.clear(); 389 390 if (m_sqliteTransaction) { 391 // In the event we got here because of an interruption or error (i.e. if 392 // the transaction is in progress), we should roll it back here. Clearing 393 // m_sqliteTransaction invokes SQLiteTransaction's destructor which does 394 // just that. We might as well do this unconditionally and free up its 395 // resources because we're already terminating. 396 m_sqliteTransaction = nullptr; 397 } 398 399 // Release the lock on this database 400 if (m_lockAcquired) 401 m_database->transactionCoordinator()->releaseLock(this); 402 403 // Do some aggresive clean up here except for m_database. 404 // 405 // We can't clear m_database here because the frontend may asynchronously 406 // invoke SQLTransactionBackend::requestTransitToState(), and that function 407 // uses m_database to schedule a state transition. This may occur because 408 // the frontend (being in another thread) may already be on the way to 409 // requesting our next state before it detects an interruption. 410 // 411 // There is no harm in letting it finish making the request. It'll set 412 // m_requestedState, but we won't execute a transition to that state because 413 // we've already shut down the transaction. 414 // 415 // We also can't clear m_currentStatementBackend and m_transactionError. 416 // m_currentStatementBackend may be accessed asynchronously by the 417 // frontend's deliverStatementCallback() state. Similarly, 418 // m_transactionError may be accessed by deliverTransactionErrorCallback(). 419 // This occurs if requests for transition to those states have already been 420 // registered with the frontend just prior to a clean up request arriving. 421 // 422 // So instead, let our destructor handle their clean up since this 423 // SQLTransactionBackend is guaranteed to not destruct until the frontend 424 // is also destructing. 425 426 m_wrapper = 0; 427} 428 429AbstractSQLStatement* SQLTransactionBackend::currentStatement() 430{ 431 return m_currentStatementBackend->frontend(); 432} 433 434PassRefPtr<SQLError> SQLTransactionBackend::transactionError() 435{ 436 return m_transactionError; 437} 438 439void SQLTransactionBackend::setShouldRetryCurrentStatement(bool shouldRetry) 440{ 441 ASSERT(!m_shouldRetryCurrentStatement); 442 m_shouldRetryCurrentStatement = shouldRetry; 443} 444 445SQLTransactionBackend::StateFunction SQLTransactionBackend::stateFunctionFor(SQLTransactionState state) 446{ 447 static const StateFunction stateFunctions[] = { 448 &SQLTransactionBackend::unreachableState, // 0. end 449 &SQLTransactionBackend::unreachableState, // 1. idle 450 &SQLTransactionBackend::acquireLock, // 2. 451 &SQLTransactionBackend::openTransactionAndPreflight, // 3. 452 &SQLTransactionBackend::runStatements, // 4. 453 &SQLTransactionBackend::postflightAndCommit, // 5. 454 &SQLTransactionBackend::cleanupAndTerminate, // 6. 455 &SQLTransactionBackend::cleanupAfterTransactionErrorCallback, // 7. 456 &SQLTransactionBackend::sendToFrontendState, // 8. deliverTransactionCallback 457 &SQLTransactionBackend::sendToFrontendState, // 9. deliverTransactionErrorCallback 458 &SQLTransactionBackend::sendToFrontendState, // 10. deliverStatementCallback 459 &SQLTransactionBackend::sendToFrontendState, // 11. deliverQuotaIncreaseCallback 460 &SQLTransactionBackend::sendToFrontendState // 12. deliverSuccessCallback 461 }; 462 463 ASSERT(WTF_ARRAY_LENGTH(stateFunctions) == static_cast<int>(SQLTransactionState::NumberOfStates)); 464 ASSERT(state < SQLTransactionState::NumberOfStates); 465 466 return stateFunctions[static_cast<int>(state)]; 467} 468 469void SQLTransactionBackend::enqueueStatementBackend(PassRefPtr<SQLStatementBackend> statementBackend) 470{ 471 MutexLocker locker(m_statementMutex); 472 m_statementQueue.append(statementBackend); 473} 474 475void SQLTransactionBackend::computeNextStateAndCleanupIfNeeded() 476{ 477 // Only honor the requested state transition if we're not supposed to be 478 // cleaning up and shutting down: 479 if (m_database->opened() && !m_database->isInterrupted()) { 480 setStateToRequestedState(); 481 ASSERT(m_nextState == SQLTransactionState::AcquireLock 482 || m_nextState == SQLTransactionState::OpenTransactionAndPreflight 483 || m_nextState == SQLTransactionState::RunStatements 484 || m_nextState == SQLTransactionState::PostflightAndCommit 485 || m_nextState == SQLTransactionState::CleanupAndTerminate 486 || m_nextState == SQLTransactionState::CleanupAfterTransactionErrorCallback); 487 488 LOG(StorageAPI, "State %s\n", nameForSQLTransactionState(m_nextState)); 489 return; 490 } 491 492 // If we get here, then we should be shutting down. Do clean up if needed: 493 if (m_nextState == SQLTransactionState::End) 494 return; 495 m_nextState = SQLTransactionState::End; 496 497 // If the database was stopped, don't do anything and cancel queued work 498 LOG(StorageAPI, "Database was stopped or interrupted - cancelling work for this transaction"); 499 500 // The current SQLite transaction should be stopped, as well 501 if (m_sqliteTransaction) { 502 m_sqliteTransaction->stop(); 503 m_sqliteTransaction = nullptr; 504 } 505 506 // Terminate the frontend state machine. This also gets the frontend to 507 // call computeNextStateAndCleanupIfNeeded() and clear its wrappers 508 // if needed. 509 m_frontend->requestTransitToState(SQLTransactionState::End); 510 511 // Redirect to the end state to abort, clean up, and end the transaction. 512 doCleanup(); 513} 514 515void SQLTransactionBackend::performNextStep() 516{ 517 computeNextStateAndCleanupIfNeeded(); 518 runStateMachine(); 519} 520 521#if PLATFORM(IOS) 522bool SQLTransactionBackend::shouldPerformWhilePaused() const 523{ 524 // SQLTransactions should only run-while-paused if they have progressed passed the first transaction step. 525 return m_nextState != SQLTransactionState::AcquireLock; 526} 527#endif 528 529void SQLTransactionBackend::executeSQL(std::unique_ptr<AbstractSQLStatement> statement, 530 const String& sqlStatement, const Vector<SQLValue>& arguments, int permissions) 531{ 532 RefPtr<SQLStatementBackend> statementBackend; 533 statementBackend = SQLStatementBackend::create(WTF::move(statement), sqlStatement, arguments, permissions); 534 535 if (Database::from(m_database.get())->deleted()) 536 statementBackend->setDatabaseDeletedError(); 537 538 enqueueStatementBackend(statementBackend); 539} 540 541void SQLTransactionBackend::notifyDatabaseThreadIsShuttingDown() 542{ 543 ASSERT(currentThread() == database()->databaseContext()->databaseThread()->getThreadID()); 544 545 // If the transaction is in progress, we should roll it back here, since this 546 // is our last opportunity to do something related to this transaction on the 547 // DB thread. Amongst other work, doCleanup() will clear m_sqliteTransaction 548 // which invokes SQLiteTransaction's destructor, which will do the roll back 549 // if necessary. 550 doCleanup(); 551} 552 553SQLTransactionState SQLTransactionBackend::acquireLock() 554{ 555 m_database->transactionCoordinator()->acquireLock(this); 556 return SQLTransactionState::Idle; 557} 558 559void SQLTransactionBackend::lockAcquired() 560{ 561 m_lockAcquired = true; 562 requestTransitToState(SQLTransactionState::OpenTransactionAndPreflight); 563} 564 565SQLTransactionState SQLTransactionBackend::openTransactionAndPreflight() 566{ 567 ASSERT(!m_database->sqliteDatabase().transactionInProgress()); 568 ASSERT(m_lockAcquired); 569 570 LOG(StorageAPI, "Opening and preflighting transaction %p", this); 571 572 // If the database was deleted, jump to the error callback 573 if (Database::from(m_database.get())->deleted()) { 574 m_transactionError = SQLError::create(SQLError::UNKNOWN_ERR, "unable to open a transaction, because the user deleted the database"); 575 return nextStateForTransactionError(); 576 } 577 578 // Set the maximum usage for this transaction if this transactions is not read-only 579 if (!m_readOnly) { 580 acquireOriginLock(); 581 m_database->sqliteDatabase().setMaximumSize(m_database->maximumSize()); 582 } 583 584 ASSERT(!m_sqliteTransaction); 585 m_sqliteTransaction = std::make_unique<SQLiteTransaction>(m_database->sqliteDatabase(), m_readOnly); 586 587 m_database->resetDeletes(); 588 m_database->disableAuthorizer(); 589 m_sqliteTransaction->begin(); 590 m_database->enableAuthorizer(); 591 592 // Spec 4.3.2.1+2: Open a transaction to the database, jumping to the error callback if that fails 593 if (!m_sqliteTransaction->inProgress()) { 594 ASSERT(!m_database->sqliteDatabase().transactionInProgress()); 595 m_transactionError = SQLError::create(SQLError::DATABASE_ERR, "unable to begin transaction", 596 m_database->sqliteDatabase().lastError(), m_database->sqliteDatabase().lastErrorMsg()); 597 m_sqliteTransaction = nullptr; 598 return nextStateForTransactionError(); 599 } 600 601 // Note: We intentionally retrieve the actual version even with an empty expected version. 602 // In multi-process browsers, we take this opportinutiy to update the cached value for 603 // the actual version. In single-process browsers, this is just a map lookup. 604 String actualVersion; 605 if (!m_database->getActualVersionForTransaction(actualVersion)) { 606 m_transactionError = SQLError::create(SQLError::DATABASE_ERR, "unable to read version", 607 m_database->sqliteDatabase().lastError(), m_database->sqliteDatabase().lastErrorMsg()); 608 m_database->disableAuthorizer(); 609 m_sqliteTransaction = nullptr; 610 m_database->enableAuthorizer(); 611 return nextStateForTransactionError(); 612 } 613 m_hasVersionMismatch = !m_database->expectedVersion().isEmpty() && (m_database->expectedVersion() != actualVersion); 614 615 // Spec 4.3.2.3: Perform preflight steps, jumping to the error callback if they fail 616 if (m_wrapper && !m_wrapper->performPreflight(this)) { 617 m_database->disableAuthorizer(); 618 m_sqliteTransaction = nullptr; 619 m_database->enableAuthorizer(); 620 m_transactionError = m_wrapper->sqlError(); 621 if (!m_transactionError) 622 m_transactionError = SQLError::create(SQLError::UNKNOWN_ERR, "unknown error occurred during transaction preflight"); 623 return nextStateForTransactionError(); 624 } 625 626 // Spec 4.3.2.4: Invoke the transaction callback with the new SQLTransaction object 627 if (m_hasCallback) 628 return SQLTransactionState::DeliverTransactionCallback; 629 630 // If we have no callback to make, skip pass to the state after: 631 return SQLTransactionState::RunStatements; 632} 633 634SQLTransactionState SQLTransactionBackend::runStatements() 635{ 636 ASSERT(m_lockAcquired); 637 SQLTransactionState nextState; 638 639 // If there is a series of statements queued up that are all successful and have no associated 640 // SQLStatementCallback objects, then we can burn through the queue 641 do { 642 if (m_shouldRetryCurrentStatement && !m_sqliteTransaction->wasRolledBackBySqlite()) { 643 m_shouldRetryCurrentStatement = false; 644 // FIXME - Another place that needs fixing up after <rdar://problem/5628468> is addressed. 645 // See ::openTransactionAndPreflight() for discussion 646 647 // Reset the maximum size here, as it was increased to allow us to retry this statement. 648 // m_shouldRetryCurrentStatement is set to true only when a statement exceeds 649 // the quota, which can happen only in a read-write transaction. Therefore, there 650 // is no need to check here if the transaction is read-write. 651 m_database->sqliteDatabase().setMaximumSize(m_database->maximumSize()); 652 } else { 653 // If the current statement has already been run, failed due to quota constraints, and we're not retrying it, 654 // that means it ended in an error. Handle it now 655 if (m_currentStatementBackend && m_currentStatementBackend->lastExecutionFailedDueToQuota()) { 656 return nextStateForCurrentStatementError(); 657 } 658 659 // Otherwise, advance to the next statement 660 getNextStatement(); 661 } 662 nextState = runCurrentStatementAndGetNextState(); 663 } while (nextState == SQLTransactionState::RunStatements); 664 665 return nextState; 666} 667 668void SQLTransactionBackend::getNextStatement() 669{ 670 m_currentStatementBackend = 0; 671 672 MutexLocker locker(m_statementMutex); 673 if (!m_statementQueue.isEmpty()) 674 m_currentStatementBackend = m_statementQueue.takeFirst(); 675} 676 677SQLTransactionState SQLTransactionBackend::runCurrentStatementAndGetNextState() 678{ 679 if (!m_currentStatementBackend) { 680 // No more statements to run. So move on to the next state. 681 return SQLTransactionState::PostflightAndCommit; 682 } 683 684 m_database->resetAuthorizer(); 685 686 if (m_hasVersionMismatch) 687 m_currentStatementBackend->setVersionMismatchedError(); 688 689 if (m_currentStatementBackend->execute(m_database.get())) { 690 if (m_database->lastActionChangedDatabase()) { 691 // Flag this transaction as having changed the database for later delegate notification 692 m_modifiedDatabase = true; 693 } 694 695 if (m_currentStatementBackend->hasStatementCallback()) { 696 return SQLTransactionState::DeliverStatementCallback; 697 } 698 699 // If we get here, then the statement doesn't have a callback to invoke. 700 // We can move on to the next statement. Hence, stay in this state. 701 return SQLTransactionState::RunStatements; 702 } 703 704 if (m_currentStatementBackend->lastExecutionFailedDueToQuota()) { 705 return SQLTransactionState::DeliverQuotaIncreaseCallback; 706 } 707 708 return nextStateForCurrentStatementError(); 709} 710 711SQLTransactionState SQLTransactionBackend::nextStateForCurrentStatementError() 712{ 713 // Spec 4.3.2.6.6: error - Call the statement's error callback, but if there was no error callback, 714 // or the transaction was rolled back, jump to the transaction error callback 715 if (m_currentStatementBackend->hasStatementErrorCallback() && !m_sqliteTransaction->wasRolledBackBySqlite()) 716 return SQLTransactionState::DeliverStatementCallback; 717 718 m_transactionError = m_currentStatementBackend->sqlError(); 719 if (!m_transactionError) 720 m_transactionError = SQLError::create(SQLError::DATABASE_ERR, "the statement failed to execute"); 721 return nextStateForTransactionError(); 722} 723 724SQLTransactionState SQLTransactionBackend::postflightAndCommit() 725{ 726 ASSERT(m_lockAcquired); 727 728 // Spec 4.3.2.7: Perform postflight steps, jumping to the error callback if they fail. 729 if (m_wrapper && !m_wrapper->performPostflight(this)) { 730 m_transactionError = m_wrapper->sqlError(); 731 if (!m_transactionError) 732 m_transactionError = SQLError::create(SQLError::UNKNOWN_ERR, "unknown error occurred during transaction postflight"); 733 return nextStateForTransactionError(); 734 } 735 736 // Spec 4.3.2.7: Commit the transaction, jumping to the error callback if that fails. 737 ASSERT(m_sqliteTransaction); 738 739 m_database->disableAuthorizer(); 740 m_sqliteTransaction->commit(); 741 m_database->enableAuthorizer(); 742 743 releaseOriginLockIfNeeded(); 744 745 // If the commit failed, the transaction will still be marked as "in progress" 746 if (m_sqliteTransaction->inProgress()) { 747 if (m_wrapper) 748 m_wrapper->handleCommitFailedAfterPostflight(this); 749 m_transactionError = SQLError::create(SQLError::DATABASE_ERR, "unable to commit transaction", 750 m_database->sqliteDatabase().lastError(), m_database->sqliteDatabase().lastErrorMsg()); 751 return nextStateForTransactionError(); 752 } 753 754 // Vacuum the database if anything was deleted. 755 if (m_database->hadDeletes()) 756 m_database->incrementalVacuumIfNeeded(); 757 758 // The commit was successful. If the transaction modified this database, notify the delegates. 759 if (m_modifiedDatabase) 760 m_database->transactionClient()->didCommitWriteTransaction(database()); 761 762 // Spec 4.3.2.8: Deliver success callback, if there is one. 763 return SQLTransactionState::DeliverSuccessCallback; 764} 765 766SQLTransactionState SQLTransactionBackend::cleanupAndTerminate() 767{ 768 ASSERT(m_lockAcquired); 769 770 // Spec 4.3.2.9: End transaction steps. There is no next step. 771 LOG(StorageAPI, "Transaction %p is complete\n", this); 772 ASSERT(!m_database->sqliteDatabase().transactionInProgress()); 773 774 // Phase 5 cleanup. See comment on the SQLTransaction life-cycle above. 775 doCleanup(); 776 m_database->inProgressTransactionCompleted(); 777 return SQLTransactionState::End; 778} 779 780SQLTransactionState SQLTransactionBackend::nextStateForTransactionError() 781{ 782 ASSERT(m_transactionError); 783 if (m_hasErrorCallback) 784 return SQLTransactionState::DeliverTransactionErrorCallback; 785 786 // No error callback, so fast-forward to the next state and rollback the 787 // transaction. 788 return SQLTransactionState::CleanupAfterTransactionErrorCallback; 789} 790 791SQLTransactionState SQLTransactionBackend::cleanupAfterTransactionErrorCallback() 792{ 793 ASSERT(m_lockAcquired); 794 795 LOG(StorageAPI, "Transaction %p is complete with an error\n", this); 796 m_database->disableAuthorizer(); 797 if (m_sqliteTransaction) { 798 // Spec 4.3.2.10: Rollback the transaction. 799 m_sqliteTransaction->rollback(); 800 801 ASSERT(!m_database->sqliteDatabase().transactionInProgress()); 802 m_sqliteTransaction = nullptr; 803 } 804 m_database->enableAuthorizer(); 805 806 releaseOriginLockIfNeeded(); 807 808 ASSERT(!m_database->sqliteDatabase().transactionInProgress()); 809 810 return SQLTransactionState::CleanupAndTerminate; 811} 812 813// requestTransitToState() can be called from the frontend. Hence, it should 814// NOT be modifying SQLTransactionBackend in general. The only safe field to 815// modify is m_requestedState which is meant for this purpose. 816void SQLTransactionBackend::requestTransitToState(SQLTransactionState nextState) 817{ 818 LOG(StorageAPI, "Scheduling %s for transaction %p\n", nameForSQLTransactionState(nextState), this); 819 m_requestedState = nextState; 820 ASSERT(m_requestedState != SQLTransactionState::End); 821 m_database->scheduleTransactionStep(this); 822} 823 824// This state function is used as a stub function to plug unimplemented states 825// in the state dispatch table. They are unimplemented because they should 826// never be reached in the course of correct execution. 827SQLTransactionState SQLTransactionBackend::unreachableState() 828{ 829 ASSERT_NOT_REACHED(); 830 return SQLTransactionState::End; 831} 832 833SQLTransactionState SQLTransactionBackend::sendToFrontendState() 834{ 835 ASSERT(m_nextState != SQLTransactionState::Idle); 836 m_frontend->requestTransitToState(m_nextState); 837 return SQLTransactionState::Idle; 838} 839 840void SQLTransactionBackend::acquireOriginLock() 841{ 842 ASSERT(!m_originLock); 843 m_originLock = DatabaseTracker::tracker().originLockFor(m_database->securityOrigin()); 844 m_originLock->lock(); 845} 846 847void SQLTransactionBackend::releaseOriginLockIfNeeded() 848{ 849 if (m_originLock) { 850 m_originLock->unlock(); 851 m_originLock.clear(); 852 } 853} 854 855} // namespace WebCore 856 857#endif // ENABLE(SQL_DATABASE) 858