| OLD | NEW |
| 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "net/http/http_cache.h" | 5 #include "net/http/http_cache.h" |
| 6 | 6 |
| 7 #include "base/hash_tables.h" | 7 #include "base/hash_tables.h" |
| 8 #include "base/message_loop.h" | 8 #include "base/message_loop.h" |
| 9 #include "base/string_util.h" | 9 #include "base/string_util.h" |
| 10 #include "net/base/net_errors.h" | 10 #include "net/base/net_errors.h" |
| (...skipping 515 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 526 EXPECT_EQ(0, cache.disk_cache()->open_count()); | 526 EXPECT_EQ(0, cache.disk_cache()->open_count()); |
| 527 EXPECT_EQ(1, cache.disk_cache()->create_count()); | 527 EXPECT_EQ(1, cache.disk_cache()->create_count()); |
| 528 | 528 |
| 529 for (int i = 0; i < kNumTransactions; ++i) { | 529 for (int i = 0; i < kNumTransactions; ++i) { |
| 530 Context* c = context_list[i]; | 530 Context* c = context_list[i]; |
| 531 c->trans->Destroy(); | 531 c->trans->Destroy(); |
| 532 delete c; | 532 delete c; |
| 533 } | 533 } |
| 534 } | 534 } |
| 535 | 535 |
| 536 // This is a test for http://code.google.com/p/chromium/issues/detail?id=4769. |
| 537 // If cancelling a request is racing with another request for the same resource |
| 538 // finishing, we have to make sure that we remove both transactions from the |
| 539 // entry. |
| 540 TEST(HttpCache, SimpleGET_RacingReaders) { |
| 541 MockHttpCache cache; |
| 542 |
| 543 MockHttpRequest request(kSimpleGET_Transaction); |
| 544 MockHttpRequest reader_request(kSimpleGET_Transaction); |
| 545 reader_request.load_flags = net::LOAD_ONLY_FROM_CACHE; |
| 546 |
| 547 std::vector<Context*> context_list; |
| 548 const int kNumTransactions = 5; |
| 549 |
| 550 for (int i = 0; i < kNumTransactions; ++i) { |
| 551 context_list.push_back( |
| 552 new Context(cache.http_cache()->CreateTransaction())); |
| 553 |
| 554 Context* c = context_list[i]; |
| 555 MockHttpRequest* this_request = &request; |
| 556 if (i == 1 || i == 2) |
| 557 this_request = &reader_request; |
| 558 |
| 559 int rv = c->trans->Start(this_request, &c->callback); |
| 560 if (rv != net::ERR_IO_PENDING) |
| 561 c->result = rv; |
| 562 } |
| 563 |
| 564 // The first request should be a writer at this point, and the subsequent |
| 565 // requests should be pending. |
| 566 |
| 567 EXPECT_EQ(1, cache.network_layer()->transaction_count()); |
| 568 EXPECT_EQ(0, cache.disk_cache()->open_count()); |
| 569 EXPECT_EQ(1, cache.disk_cache()->create_count()); |
| 570 |
| 571 Context* c = context_list[0]; |
| 572 ASSERT_EQ(net::ERR_IO_PENDING, c->result); |
| 573 c->result = c->callback.WaitForResult(); |
| 574 ReadAndVerifyTransaction(c->trans, kSimpleGET_Transaction); |
| 575 |
| 576 // Now we have 2 active readers and two queued transactions. |
| 577 |
| 578 c = context_list[1]; |
| 579 ASSERT_EQ(net::ERR_IO_PENDING, c->result); |
| 580 c->result = c->callback.WaitForResult(); |
| 581 ReadAndVerifyTransaction(c->trans, kSimpleGET_Transaction); |
| 582 |
| 583 // At this point we have one reader, two pending transactions and a task on |
| 584 // the queue to move to the next transaction. Now we cancel the request that |
| 585 // is the current reader, and expect the queued task to be able to start the |
| 586 // next request. |
| 587 |
| 588 c = context_list[2]; |
| 589 c->trans->Destroy(); |
| 590 |
| 591 for (int i = 3; i < kNumTransactions; ++i) { |
| 592 Context* c = context_list[i]; |
| 593 if (c->result == net::ERR_IO_PENDING) |
| 594 c->result = c->callback.WaitForResult(); |
| 595 ReadAndVerifyTransaction(c->trans, kSimpleGET_Transaction); |
| 596 } |
| 597 |
| 598 // We should not have had to re-open the disk entry. |
| 599 |
| 600 EXPECT_EQ(1, cache.network_layer()->transaction_count()); |
| 601 EXPECT_EQ(0, cache.disk_cache()->open_count()); |
| 602 EXPECT_EQ(1, cache.disk_cache()->create_count()); |
| 603 |
| 604 for (int i = 0; i < kNumTransactions; ++i) { |
| 605 Context* c = context_list[i]; |
| 606 delete c; |
| 607 } |
| 608 } |
| 609 |
| 536 TEST(HttpCache, SimpleGET_ManyWriters_CancelFirst) { | 610 TEST(HttpCache, SimpleGET_ManyWriters_CancelFirst) { |
| 537 MockHttpCache cache; | 611 MockHttpCache cache; |
| 538 | 612 |
| 539 MockHttpRequest request(kSimpleGET_Transaction); | 613 MockHttpRequest request(kSimpleGET_Transaction); |
| 540 | 614 |
| 541 std::vector<Context*> context_list; | 615 std::vector<Context*> context_list; |
| 542 const int kNumTransactions = 2; | 616 const int kNumTransactions = 2; |
| 543 | 617 |
| 544 for (int i = 0; i < kNumTransactions; ++i) { | 618 for (int i = 0; i < kNumTransactions; ++i) { |
| 545 context_list.push_back( | 619 context_list.push_back( |
| (...skipping 419 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 965 net::HttpTransaction* trans = cache.http_cache()->CreateTransaction(); | 1039 net::HttpTransaction* trans = cache.http_cache()->CreateTransaction(); |
| 966 ASSERT_TRUE(trans); | 1040 ASSERT_TRUE(trans); |
| 967 | 1041 |
| 968 int rv = trans->Start(&request, &callback); | 1042 int rv = trans->Start(&request, &callback); |
| 969 if (rv == net::ERR_IO_PENDING) | 1043 if (rv == net::ERR_IO_PENDING) |
| 970 rv = callback.WaitForResult(); | 1044 rv = callback.WaitForResult(); |
| 971 ASSERT_EQ(net::ERR_CACHE_MISS, rv); | 1045 ASSERT_EQ(net::ERR_CACHE_MISS, rv); |
| 972 | 1046 |
| 973 trans->Destroy(); | 1047 trans->Destroy(); |
| 974 } | 1048 } |
| OLD | NEW |