1*6777b538SAndroid Build Coastguard Worker // Copyright 2009 The Chromium Authors
2*6777b538SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be
3*6777b538SAndroid Build Coastguard Worker // found in the LICENSE file.
4*6777b538SAndroid Build Coastguard Worker
5*6777b538SAndroid Build Coastguard Worker #include <algorithm>
6*6777b538SAndroid Build Coastguard Worker
7*6777b538SAndroid Build Coastguard Worker #include "base/check.h"
8*6777b538SAndroid Build Coastguard Worker #include "base/format_macros.h"
9*6777b538SAndroid Build Coastguard Worker #include "base/strings/stringprintf.h"
10*6777b538SAndroid Build Coastguard Worker #include "net/http/http_byte_range.h"
11*6777b538SAndroid Build Coastguard Worker
12*6777b538SAndroid Build Coastguard Worker namespace {
13*6777b538SAndroid Build Coastguard Worker
14*6777b538SAndroid Build Coastguard Worker const int64_t kPositionNotSpecified = -1;
15*6777b538SAndroid Build Coastguard Worker
16*6777b538SAndroid Build Coastguard Worker } // namespace
17*6777b538SAndroid Build Coastguard Worker
18*6777b538SAndroid Build Coastguard Worker namespace net {
19*6777b538SAndroid Build Coastguard Worker
HttpByteRange()20*6777b538SAndroid Build Coastguard Worker HttpByteRange::HttpByteRange()
21*6777b538SAndroid Build Coastguard Worker : first_byte_position_(kPositionNotSpecified),
22*6777b538SAndroid Build Coastguard Worker last_byte_position_(kPositionNotSpecified),
23*6777b538SAndroid Build Coastguard Worker suffix_length_(kPositionNotSpecified) {}
24*6777b538SAndroid Build Coastguard Worker
25*6777b538SAndroid Build Coastguard Worker // static
Bounded(int64_t first_byte_position,int64_t last_byte_position)26*6777b538SAndroid Build Coastguard Worker HttpByteRange HttpByteRange::Bounded(int64_t first_byte_position,
27*6777b538SAndroid Build Coastguard Worker int64_t last_byte_position) {
28*6777b538SAndroid Build Coastguard Worker HttpByteRange range;
29*6777b538SAndroid Build Coastguard Worker range.set_first_byte_position(first_byte_position);
30*6777b538SAndroid Build Coastguard Worker range.set_last_byte_position(last_byte_position);
31*6777b538SAndroid Build Coastguard Worker return range;
32*6777b538SAndroid Build Coastguard Worker }
33*6777b538SAndroid Build Coastguard Worker
34*6777b538SAndroid Build Coastguard Worker // static
RightUnbounded(int64_t first_byte_position)35*6777b538SAndroid Build Coastguard Worker HttpByteRange HttpByteRange::RightUnbounded(int64_t first_byte_position) {
36*6777b538SAndroid Build Coastguard Worker HttpByteRange range;
37*6777b538SAndroid Build Coastguard Worker range.set_first_byte_position(first_byte_position);
38*6777b538SAndroid Build Coastguard Worker return range;
39*6777b538SAndroid Build Coastguard Worker }
40*6777b538SAndroid Build Coastguard Worker
41*6777b538SAndroid Build Coastguard Worker // static
Suffix(int64_t suffix_length)42*6777b538SAndroid Build Coastguard Worker HttpByteRange HttpByteRange::Suffix(int64_t suffix_length) {
43*6777b538SAndroid Build Coastguard Worker HttpByteRange range;
44*6777b538SAndroid Build Coastguard Worker range.set_suffix_length(suffix_length);
45*6777b538SAndroid Build Coastguard Worker return range;
46*6777b538SAndroid Build Coastguard Worker }
47*6777b538SAndroid Build Coastguard Worker
IsSuffixByteRange() const48*6777b538SAndroid Build Coastguard Worker bool HttpByteRange::IsSuffixByteRange() const {
49*6777b538SAndroid Build Coastguard Worker return suffix_length_ != kPositionNotSpecified;
50*6777b538SAndroid Build Coastguard Worker }
51*6777b538SAndroid Build Coastguard Worker
HasFirstBytePosition() const52*6777b538SAndroid Build Coastguard Worker bool HttpByteRange::HasFirstBytePosition() const {
53*6777b538SAndroid Build Coastguard Worker return first_byte_position_ != kPositionNotSpecified;
54*6777b538SAndroid Build Coastguard Worker }
55*6777b538SAndroid Build Coastguard Worker
HasLastBytePosition() const56*6777b538SAndroid Build Coastguard Worker bool HttpByteRange::HasLastBytePosition() const {
57*6777b538SAndroid Build Coastguard Worker return last_byte_position_ != kPositionNotSpecified;
58*6777b538SAndroid Build Coastguard Worker }
59*6777b538SAndroid Build Coastguard Worker
IsValid() const60*6777b538SAndroid Build Coastguard Worker bool HttpByteRange::IsValid() const {
61*6777b538SAndroid Build Coastguard Worker if (suffix_length_ > 0)
62*6777b538SAndroid Build Coastguard Worker return true;
63*6777b538SAndroid Build Coastguard Worker return (first_byte_position_ >= 0 &&
64*6777b538SAndroid Build Coastguard Worker (last_byte_position_ == kPositionNotSpecified ||
65*6777b538SAndroid Build Coastguard Worker last_byte_position_ >= first_byte_position_));
66*6777b538SAndroid Build Coastguard Worker }
67*6777b538SAndroid Build Coastguard Worker
GetHeaderValue() const68*6777b538SAndroid Build Coastguard Worker std::string HttpByteRange::GetHeaderValue() const {
69*6777b538SAndroid Build Coastguard Worker DCHECK(IsValid());
70*6777b538SAndroid Build Coastguard Worker
71*6777b538SAndroid Build Coastguard Worker if (IsSuffixByteRange())
72*6777b538SAndroid Build Coastguard Worker return base::StringPrintf("bytes=-%" PRId64, suffix_length());
73*6777b538SAndroid Build Coastguard Worker
74*6777b538SAndroid Build Coastguard Worker DCHECK(HasFirstBytePosition());
75*6777b538SAndroid Build Coastguard Worker
76*6777b538SAndroid Build Coastguard Worker if (!HasLastBytePosition())
77*6777b538SAndroid Build Coastguard Worker return base::StringPrintf("bytes=%" PRId64 "-", first_byte_position());
78*6777b538SAndroid Build Coastguard Worker
79*6777b538SAndroid Build Coastguard Worker return base::StringPrintf("bytes=%" PRId64 "-%" PRId64,
80*6777b538SAndroid Build Coastguard Worker first_byte_position(), last_byte_position());
81*6777b538SAndroid Build Coastguard Worker }
82*6777b538SAndroid Build Coastguard Worker
ComputeBounds(int64_t size)83*6777b538SAndroid Build Coastguard Worker bool HttpByteRange::ComputeBounds(int64_t size) {
84*6777b538SAndroid Build Coastguard Worker if (size < 0)
85*6777b538SAndroid Build Coastguard Worker return false;
86*6777b538SAndroid Build Coastguard Worker if (has_computed_bounds_)
87*6777b538SAndroid Build Coastguard Worker return false;
88*6777b538SAndroid Build Coastguard Worker has_computed_bounds_ = true;
89*6777b538SAndroid Build Coastguard Worker
90*6777b538SAndroid Build Coastguard Worker // Empty values.
91*6777b538SAndroid Build Coastguard Worker if (!HasFirstBytePosition() &&
92*6777b538SAndroid Build Coastguard Worker !HasLastBytePosition() &&
93*6777b538SAndroid Build Coastguard Worker !IsSuffixByteRange()) {
94*6777b538SAndroid Build Coastguard Worker first_byte_position_ = 0;
95*6777b538SAndroid Build Coastguard Worker last_byte_position_ = size - 1;
96*6777b538SAndroid Build Coastguard Worker return true;
97*6777b538SAndroid Build Coastguard Worker }
98*6777b538SAndroid Build Coastguard Worker if (!IsValid())
99*6777b538SAndroid Build Coastguard Worker return false;
100*6777b538SAndroid Build Coastguard Worker if (IsSuffixByteRange()) {
101*6777b538SAndroid Build Coastguard Worker first_byte_position_ = size - std::min(size, suffix_length_);
102*6777b538SAndroid Build Coastguard Worker last_byte_position_ = size - 1;
103*6777b538SAndroid Build Coastguard Worker return true;
104*6777b538SAndroid Build Coastguard Worker }
105*6777b538SAndroid Build Coastguard Worker if (first_byte_position_ < size) {
106*6777b538SAndroid Build Coastguard Worker if (HasLastBytePosition())
107*6777b538SAndroid Build Coastguard Worker last_byte_position_ = std::min(size - 1, last_byte_position_);
108*6777b538SAndroid Build Coastguard Worker else
109*6777b538SAndroid Build Coastguard Worker last_byte_position_ = size - 1;
110*6777b538SAndroid Build Coastguard Worker return true;
111*6777b538SAndroid Build Coastguard Worker }
112*6777b538SAndroid Build Coastguard Worker return false;
113*6777b538SAndroid Build Coastguard Worker }
114*6777b538SAndroid Build Coastguard Worker
115*6777b538SAndroid Build Coastguard Worker } // namespace net
116