You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@trafficserver.apache.org by am...@apache.org on 2015/06/08 16:29:18 UTC

trafficserver git commit: Fixed second full read problem.

Repository: trafficserver
Updated Branches:
  refs/heads/ts-974-5-3-x ebd737154 -> bf93bbb84


Fixed second full read problem.


Project: http://git-wip-us.apache.org/repos/asf/trafficserver/repo
Commit: http://git-wip-us.apache.org/repos/asf/trafficserver/commit/bf93bbb8
Tree: http://git-wip-us.apache.org/repos/asf/trafficserver/tree/bf93bbb8
Diff: http://git-wip-us.apache.org/repos/asf/trafficserver/diff/bf93bbb8

Branch: refs/heads/ts-974-5-3-x
Commit: bf93bbb84a2c462c9249fdff8cfdd93b8a4f75ea
Parents: ebd7371
Author: Alan M. Carroll <so...@yahoo-inc.com>
Authored: Mon Jun 8 09:28:34 2015 -0500
Committer: Alan M. Carroll <so...@yahoo-inc.com>
Committed: Mon Jun 8 09:28:34 2015 -0500

----------------------------------------------------------------------
 iocore/cache/Cache.cc             |  6 +++---
 iocore/cache/CacheHttp.cc         | 11 +++++++----
 iocore/cache/I_Cache.h            |  8 +++++++-
 iocore/cache/P_CacheHttp.h        |  2 +-
 iocore/cache/P_CacheInternal.h    |  2 +-
 proxy/hdrs/HTTP.cc                | 14 +++++++++-----
 proxy/hdrs/HTTP.h                 |  7 +++++--
 proxy/http/HttpTransact.cc        |  7 ++++++-
 proxy/http/HttpTransactHeaders.cc |  2 +-
 9 files changed, 40 insertions(+), 19 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/iocore/cache/Cache.cc
----------------------------------------------------------------------
diff --git a/iocore/cache/Cache.cc b/iocore/cache/Cache.cc
index 478e732..6095ddb 100644
--- a/iocore/cache/Cache.cc
+++ b/iocore/cache/Cache.cc
@@ -516,10 +516,10 @@ CacheVC::set_content_range(HTTPRangeSpec const& r)
 }
 
 bool
-CacheVC::get_uncached(HTTPRangeSpec const& req, HTTPRangeSpec& result)
+CacheVC::get_uncached(HTTPRangeSpec const& req, HTTPRangeSpec& result, int64_t initial)
 {
-  HTTPRangeSpec::Range r = od ? write_vector->get_uncached_hull(earliest_key, req)
-    : alternate.get_uncached_hull(req)
+  HTTPRangeSpec::Range r = od ? write_vector->get_uncached_hull(earliest_key, req, initial)
+    : alternate.get_uncached_hull(req, initial)
     ;
   if (r.isValid()) {
     result.add(r);

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/iocore/cache/CacheHttp.cc
----------------------------------------------------------------------
diff --git a/iocore/cache/CacheHttp.cc b/iocore/cache/CacheHttp.cc
index 623e5b8..dd4b4fc 100644
--- a/iocore/cache/CacheHttp.cc
+++ b/iocore/cache/CacheHttp.cc
@@ -355,7 +355,7 @@ CacheHTTPInfoVector::close_writer(CacheKey const& alt_key, CacheVC* vc)
   -------------------------------------------------------------------------*/
 
 HTTPRangeSpec::Range
-CacheHTTPInfoVector::get_uncached_hull(CacheKey const& alt_key, HTTPRangeSpec const& req)
+CacheHTTPInfoVector::get_uncached_hull(CacheKey const& alt_key, HTTPRangeSpec const& req, int64_t initial)
 {
   int alt_idx = this->index_of(alt_key);
   Item& item = data[alt_idx];
@@ -364,7 +364,7 @@ CacheHTTPInfoVector::get_uncached_hull(CacheKey const& alt_key, HTTPRangeSpec co
   CacheVC* cycle_vc = NULL;
   // Yeah, this need to be tunable.
   uint64_t DELTA = item._alternate.get_frag_fixed_size() * 16;
-  HTTPRangeSpec::Range r(item._alternate.get_uncached_hull(req));
+  HTTPRangeSpec::Range r(item._alternate.get_uncached_hull(req, initial));
 
   if (r.isValid()) {
     /* Now clip against the writers.
@@ -424,12 +424,15 @@ CacheRange::init(HTTPHdr* req)
 bool
 CacheRange::start()
 {
-  bool zret = false;
+  bool zret = true;
 
   if (_r.hasRanges()) {
     _offset = _r[_idx = 0]._min;
     _pending_range_shift_p = _r.isMulti();
-    zret = true;
+  } else if (_r.isEmpty()) {
+    _offset = 0;
+  } else {
+    zret = false;
   }
   return zret;
 }

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/iocore/cache/I_Cache.h
----------------------------------------------------------------------
diff --git a/iocore/cache/I_Cache.h b/iocore/cache/I_Cache.h
index 187343b..675ee82 100644
--- a/iocore/cache/I_Cache.h
+++ b/iocore/cache/I_Cache.h
@@ -254,7 +254,13 @@ struct CacheVConnection : public VConnection {
   /// @return @c true if the @a result is not empty.
   /// @internal Currently this just returns the single range that is convex hull of the uncached request.
   /// Someday we may want to do the exact range spec but we use the type for now because it's easier.
-  virtual bool get_uncached(HTTPRangeSpec const& req, HTTPRangeSpec& result) { (void)req; (void)result; return false; }
+  virtual bool get_uncached(HTTPRangeSpec const& req, HTTPRangeSpec& result, int64_t initial)
+  {
+    (void)req;
+    (void)result;
+    (void)initial;
+    return false;
+  }
 
   /** Set the range for the input (response content).
       The incoming bytes will be written to this section of the object.

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/iocore/cache/P_CacheHttp.h
----------------------------------------------------------------------
diff --git a/iocore/cache/P_CacheHttp.h b/iocore/cache/P_CacheHttp.h
index 458fb9e..ea0ac43 100644
--- a/iocore/cache/P_CacheHttp.h
+++ b/iocore/cache/P_CacheHttp.h
@@ -148,7 +148,7 @@ struct CacheHTTPInfoVector {
 
       @return @c true if there is uncached data that must be retrieved.
    */
-  HTTPRangeSpec::Range get_uncached_hull(CacheKey const &alt_key, HTTPRangeSpec const &request);
+  HTTPRangeSpec::Range get_uncached_hull(CacheKey const &alt_key, HTTPRangeSpec const &request, int64_t initial);
 
   /** Sigh, yet another custom array class.
       @c Vec doesn't work because it really only works well with pointers, not objects.

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/iocore/cache/P_CacheInternal.h
----------------------------------------------------------------------
diff --git a/iocore/cache/P_CacheInternal.h b/iocore/cache/P_CacheInternal.h
index 0aca4f2..5de9158 100644
--- a/iocore/cache/P_CacheInternal.h
+++ b/iocore/cache/P_CacheInternal.h
@@ -392,7 +392,7 @@ struct CacheVC: public CacheVConnection
   virtual char const* get_http_range_boundary_string(int* len) const;
   virtual int64_t get_effective_content_size();
   virtual void set_full_content_length(int64_t size);
-  virtual bool get_uncached(HTTPRangeSpec const& req, HTTPRangeSpec& result);
+  virtual bool get_uncached(HTTPRangeSpec const& req, HTTPRangeSpec& result, int64_t initial);
   /** This sets a range for data flowing in to the cache VC.
       The CacheVC will write the incoming data to this part of the overall object.
       @internal It's done this way to isolate the CacheVC from parsing range separators

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/proxy/hdrs/HTTP.cc
----------------------------------------------------------------------
diff --git a/proxy/hdrs/HTTP.cc b/proxy/hdrs/HTTP.cc
index 2108766..ace4185 100644
--- a/proxy/hdrs/HTTP.cc
+++ b/proxy/hdrs/HTTP.cc
@@ -1827,6 +1827,9 @@ HTTPCacheAlt::copy(HTTPCacheAlt *that)
   if (m_flag.table_allocated_p)
     ats_free(m_fragments);
 
+  // Safe to copy now, and we need to do that before we copy the fragment table.
+  m_flags = that->m_flags;
+
   if (that->m_fragments) {
     size_t size = FragmentDescriptorTable::calc_size(that->m_fragments->m_n);
     m_fragments = static_cast<FragmentDescriptorTable*>(ats_malloc(size));
@@ -1834,6 +1837,7 @@ HTTPCacheAlt::copy(HTTPCacheAlt *that)
     m_flag.table_allocated_p = true;
   } else {
     m_fragments = 0;
+    m_flag.table_allocated_p = false;
   }
 }
 
@@ -2189,7 +2193,7 @@ HTTPInfo::mark_frag_write(unsigned int idx) {
     while (j < m_alt->m_frag_count && (*m_alt->m_fragments)[j].m_flag.cached_p)
       ++j;
     m_alt->m_fragments->m_cached_idx = j - 1;
-    if (m_alt->m_flag.content_length_p &&
+    if (!m_alt->m_flag.content_length_p &&
         (this->get_frag_fixed_size() + this->get_frag_offset(j-1)) > static_cast<int64_t>(m_alt->m_earliest.m_offset))
       m_alt->m_flag.complete_p = true;
   }
@@ -2563,10 +2567,10 @@ HTTPRangeSpec::print(char* buff, size_t len) const
 }
 
 int
-HTTPRangeSpec::print_quantized(char* buff, size_t len, int64_t quantum, int64_t interstitial, int64_t initial) const
+HTTPRangeSpec::print_quantized(char* buff, size_t len, int64_t quantum, int64_t interstitial) const
 {
   static const int MAX_R = 20; // this needs to be promoted
-  // We will want a max # of ranges, probably a build time constant, in the not so distant
+  // We will want to have a max # of ranges limit, probably a build time constant, in the not so distant
   // future anyway, so might as well start here.
   int qrn = 0; // count of quantized ranges
   Range qr[MAX_R]; // quantized ranges
@@ -2585,7 +2589,6 @@ HTTPRangeSpec::print_quantized(char* buff, size_t len, int64_t quantum, int64_t
       r._min = (r._min / quantum) * quantum;
       r._max = ((r._max + quantum - 1)/quantum) * quantum - 1;
     }
-    if (1 < initial && r._min < static_cast<uint64_t>(initial)) r._min = 0;
     // blend in to the current ranges
     for ( i = 0 ; i < qrn ; ++i ) {
       Range& cr = qr[i];
@@ -2634,7 +2637,7 @@ HTTPInfo::get_range_for_frags(int low, int high)
 */
 
 HTTPRangeSpec::Range
-HTTPInfo::get_uncached_hull(HTTPRangeSpec const& req)
+HTTPInfo::get_uncached_hull(HTTPRangeSpec const& req, int64_t initial)
 {
   HTTPRangeSpec::Range r;
 
@@ -2673,6 +2676,7 @@ HTTPInfo::get_uncached_hull(HTTPRangeSpec const& req)
     }
     if (r.isValid() && m_alt->m_flag.content_length_p && static_cast<int64_t>(r._max) > this->object_size_get())
       r._max = this->object_size_get();
+    if (static_cast<int64_t>(r._min) < initial && !m_alt->m_earliest.m_flag.cached_p) r._min = 0;
   }
   return r;
 }

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/proxy/hdrs/HTTP.h
----------------------------------------------------------------------
diff --git a/proxy/hdrs/HTTP.h b/proxy/hdrs/HTTP.h
index a42d686..b7b3ab0 100644
--- a/proxy/hdrs/HTTP.h
+++ b/proxy/hdrs/HTTP.h
@@ -609,8 +609,6 @@ struct HTTPRangeSpec {
                       int64_t quantum ///< Align ranges to multiples of this value.
                       ,
                       int64_t interstitial ///< Require gaps to be at least this large.
-                      ,
-                      int64_t initial ///< Require the initial gap to be at least this large.
                       ) const;
 
   /// Print the @a ranges.
@@ -1846,9 +1844,14 @@ public:
 
   /** Compute the convex hull of uncached ranges.
 
+      If the resulting range has a minimum that is less than @a initial @b and the earliest fragment
+      is not cached then the minimum will be changed to zero. Alternatively, the initial uncached
+      segment must be at least @a initial bytes long.
+
       @return An invalid range if all of the request is available in cache.
   */
   HTTPRangeSpec::Range get_uncached_hull(HTTPRangeSpec const &req ///< [in] UA request with content length applied
+					 , int64_t initial ///< Minimize size for uncached initial data
                                          );
 
   /// Get the fragment table.

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/proxy/http/HttpTransact.cc
----------------------------------------------------------------------
diff --git a/proxy/http/HttpTransact.cc b/proxy/http/HttpTransact.cc
index 7c71b11..6fcba7b 100644
--- a/proxy/http/HttpTransact.cc
+++ b/proxy/http/HttpTransact.cc
@@ -49,6 +49,11 @@
 
 static char const HTTP_RANGE_MULTIPART_CONTENT_TYPE[] = "multipart/byteranges; boundary=";
 
+/// If the intial uncached segment is less than this, expand the request to include the earliest fragment.
+/// Hardwired for now, this needs to be promoted to a config var at some point. It should also be a multiple
+/// of the fragment size.
+static int64_t const MIN_INITIAL_UNCACHED = 4 * 1<<20;
+
 #define HTTP_INCREMENT_TRANS_STAT(X) update_stat(s, X, 1);
 #define HTTP_SUM_TRANS_STAT(X, S) update_stat(s, X, (ink_statval_t)S);
 
@@ -2692,7 +2697,7 @@ HttpTransact::HandleCacheOpenReadHit(State *s)
   }
 
   // Check if we need to get some data from the origin.
-  if (s->state_machine->get_cache_sm().cache_read_vc->get_uncached(s->hdr_info.request_range, range)) {
+  if (s->state_machine->get_cache_sm().cache_read_vc->get_uncached(s->hdr_info.request_range, range, MIN_INITIAL_UNCACHED)) {
     Debug("amc", "Request touches uncached fragments");
     find_server_and_update_current_info(s);
     if (!ats_is_ip(&s->current.server->addr)) {

http://git-wip-us.apache.org/repos/asf/trafficserver/blob/bf93bbb8/proxy/http/HttpTransactHeaders.cc
----------------------------------------------------------------------
diff --git a/proxy/http/HttpTransactHeaders.cc b/proxy/http/HttpTransactHeaders.cc
index a5277bb..7c41850 100644
--- a/proxy/http/HttpTransactHeaders.cc
+++ b/proxy/http/HttpTransactHeaders.cc
@@ -1045,7 +1045,7 @@ HttpTransactHeaders::insert_request_range_header(HTTPHdr* header, HTTPRangeSpec
  
   if (ranges->hasRanges()) {
     int64_t ffs = cacheProcessor.get_fixed_fragment_size();
-    n = ranges->print_quantized(buff, sizeof(buff), ffs, ffs, 4 * ffs);
+    n = ranges->print_quantized(buff, sizeof(buff), ffs, ffs);
     header->value_set(MIME_FIELD_RANGE, MIME_LEN_RANGE, buff, n);
   }
 }