- add sources.
[platform/framework/web/crosswalk.git] / src / net / spdy / spdy_frame_reader.cc
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include <limits>
6
7 #include "base/sys_byteorder.h"
8 #include "net/spdy/spdy_frame_reader.h"
9 #include "net/spdy/spdy_protocol.h"
10
11 namespace net {
12
13 SpdyFrameReader::SpdyFrameReader(const char* data, const size_t len)
14     : data_(data),
15       len_(len),
16       ofs_(0) {
17 }
18
19 bool SpdyFrameReader::ReadUInt8(uint8* result) {
20   // Make sure that we have the whole uint8.
21   if (!CanRead(1)) {
22     OnFailure();
23     return false;
24   }
25
26   // Read into result.
27   *result = *reinterpret_cast<const uint8*>(data_ + ofs_);
28
29   // Iterate.
30   ofs_ += 1;
31
32   return true;
33 }
34
35 bool SpdyFrameReader::ReadUInt16(uint16* result) {
36   // Make sure that we have the whole uint16.
37   if (!CanRead(2)) {
38     OnFailure();
39     return false;
40   }
41
42   // Read into result.
43   *result = ntohs(*(reinterpret_cast<const uint16*>(data_ + ofs_)));
44
45   // Iterate.
46   ofs_ += 2;
47
48   return true;
49 }
50
51 bool SpdyFrameReader::ReadUInt32(uint32* result) {
52   // Make sure that we have the whole uint32.
53   if (!CanRead(4)) {
54     OnFailure();
55     return false;
56   }
57
58   // Read into result.
59   *result = ntohl(*(reinterpret_cast<const uint32*>(data_ + ofs_)));
60
61   // Iterate.
62   ofs_ += 4;
63
64   return true;
65 }
66
67 bool SpdyFrameReader::ReadUInt31(uint32* result) {
68   bool success = ReadUInt32(result);
69
70   // Zero out highest-order bit.
71   if (success) {
72     *result &= 0x7fffffff;
73   }
74
75   return success;
76 }
77
78 bool SpdyFrameReader::ReadUInt24(uint32* result) {
79   // Make sure that we have the whole uint24.
80   if (!CanRead(3)) {
81     OnFailure();
82     return false;
83   }
84
85   // Read into result.
86   *result = 0;
87   memcpy(reinterpret_cast<char*>(result) + 1, data_ + ofs_, 3);
88   *result = ntohl(*result);
89
90   // Iterate.
91   ofs_ += 3;
92
93   return true;
94 }
95
96 bool SpdyFrameReader::ReadStringPiece16(base::StringPiece* result) {
97   // Read resultant length.
98   uint16 result_len;
99   if (!ReadUInt16(&result_len)) {
100     // OnFailure() already called.
101     return false;
102   }
103
104   // Make sure that we have the whole string.
105   if (!CanRead(result_len)) {
106     OnFailure();
107     return false;
108   }
109
110   // Set result.
111   result->set(data_ + ofs_, result_len);
112
113   // Iterate.
114   ofs_ += result_len;
115
116   return true;
117 }
118
119 bool SpdyFrameReader::ReadStringPiece32(base::StringPiece* result) {
120   // Read resultant length.
121   uint32 result_len;
122   if (!ReadUInt32(&result_len)) {
123     // OnFailure() already called.
124     return false;
125   }
126
127   // Make sure that we have the whole string.
128   if (!CanRead(result_len)) {
129     OnFailure();
130     return false;
131   }
132
133   // Set result.
134   result->set(data_ + ofs_, result_len);
135
136   // Iterate.
137   ofs_ += result_len;
138
139   return true;
140 }
141
142 bool SpdyFrameReader::ReadBytes(void* result, size_t size) {
143   // Make sure that we have enough data to read.
144   if (!CanRead(size)) {
145     OnFailure();
146     return false;
147   }
148
149   // Read into result.
150   memcpy(result, data_ + ofs_, size);
151
152   // Iterate.
153   ofs_ += size;
154
155   return true;
156 }
157
158 bool SpdyFrameReader::Seek(size_t size) {
159   if (!CanRead(size)) {
160     OnFailure();
161     return false;
162   }
163
164   // Iterate.
165   ofs_ += size;
166
167   return true;
168 }
169
170 bool SpdyFrameReader::IsDoneReading() const {
171   return len_ == ofs_;
172 }
173
174 bool SpdyFrameReader::CanRead(size_t bytes) const {
175   return bytes <= (len_ - ofs_);
176 }
177
178 void SpdyFrameReader::OnFailure() {
179   // Set our iterator to the end of the buffer so that further reads fail
180   // immediately.
181   ofs_ = len_;
182 }
183
184 }  // namespace net