Pin Chrome's shortcut to the Win10 Start menu on install and OS upgrade.
[chromium-blink-merge.git] / net / spdy / spdy_frame_builder.h
blob2cecd65b50e6a8392cc064d09c414f1489f5b42f
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.
5 #ifndef NET_SPDY_SPDY_FRAME_BUILDER_H_
6 #define NET_SPDY_SPDY_FRAME_BUILDER_H_
8 #include <string>
10 #include "base/basictypes.h"
11 #include "base/memory/scoped_ptr.h"
12 #include "base/strings/string_piece.h"
13 #include "base/sys_byteorder.h"
14 #include "net/base/net_export.h"
15 #include "net/spdy/spdy_protocol.h"
17 namespace net {
19 class SpdyFramer;
21 // This class provides facilities for basic binary value packing
22 // into Spdy frames.
24 // The SpdyFrameBuilder supports appending primitive values (int, string, etc)
25 // to a frame instance. The SpdyFrameBuilder grows its internal memory buffer
26 // dynamically to hold the sequence of primitive values. The internal memory
27 // buffer is exposed as the "data" of the SpdyFrameBuilder.
28 class NET_EXPORT_PRIVATE SpdyFrameBuilder {
29 public:
30 // Initializes a SpdyFrameBuilder with a buffer of given size
31 SpdyFrameBuilder(size_t size, SpdyMajorVersion version);
33 ~SpdyFrameBuilder();
35 // Returns the total size of the SpdyFrameBuilder's data, which may include
36 // multiple frames.
37 size_t length() const { return offset_ + length_; }
39 // Returns a writeable buffer of given size in bytes, to be appended to the
40 // currently written frame. Does bounds checking on length but does not
41 // increment the underlying iterator. To do so, consumers should subsequently
42 // call Seek().
43 // In general, consumers should use Write*() calls instead of this.
44 // Returns NULL on failure.
45 char* GetWritableBuffer(size_t length);
47 // Seeks forward by the given number of bytes. Useful in conjunction with
48 // GetWriteableBuffer() above.
49 bool Seek(size_t length);
51 // Populates this frame with a SPDY control frame header using
52 // version-specific information from the |framer| and length information from
53 // capacity_. The given type must be a control frame type.
54 // Used only for SPDY versions <4.
55 bool WriteControlFrameHeader(const SpdyFramer& framer,
56 SpdyFrameType type,
57 uint8 flags);
59 // Populates this frame with a SPDY data frame header using version-specific
60 // information from the |framer| and length information from capacity_.
61 bool WriteDataFrameHeader(const SpdyFramer& framer,
62 SpdyStreamId stream_id,
63 uint8 flags);
65 // Populates this frame with a SPDY4/HTTP2 frame prefix using
66 // version-specific information from the |framer| and length information from
67 // capacity_. The given type must be a control frame type.
68 // Used only for SPDY versions >=4.
69 bool BeginNewFrame(const SpdyFramer& framer,
70 SpdyFrameType type,
71 uint8 flags,
72 SpdyStreamId stream_id);
74 // Takes the buffer from the SpdyFrameBuilder.
75 SpdyFrame* take() {
76 if (version_ > SPDY3) {
77 DLOG_IF(DFATAL, SpdyConstants::GetFrameMaximumSize(version_) < length_)
78 << "Frame length " << length_
79 << " is longer than the maximum allowed length.";
81 SpdyFrame* rv = new SpdyFrame(buffer_.release(), length(), true);
82 capacity_ = 0;
83 length_ = 0;
84 offset_ = 0;
85 return rv;
88 // Methods for adding to the payload. These values are appended to the end
89 // of the SpdyFrameBuilder payload. Note - binary integers are converted from
90 // host to network form.
91 bool WriteUInt8(uint8 value) {
92 return WriteBytes(&value, sizeof(value));
94 bool WriteUInt16(uint16 value) {
95 value = htons(value);
96 return WriteBytes(&value, sizeof(value));
98 bool WriteUInt24(uint32 value) {
99 value = htonl(value);
100 return WriteBytes(reinterpret_cast<char*>(&value) + 1,
101 sizeof(value) - 1);
103 bool WriteUInt32(uint32 value) {
104 value = htonl(value);
105 return WriteBytes(&value, sizeof(value));
107 bool WriteUInt64(uint64 value) {
108 uint32 upper = htonl(value >> 32);
109 uint32 lower = htonl(static_cast<uint32>(value));
110 return (WriteBytes(&upper, sizeof(upper)) &&
111 WriteBytes(&lower, sizeof(lower)));
113 bool WriteStringPiece16(const base::StringPiece& value);
114 bool WriteStringPiece32(const base::StringPiece& value);
115 bool WriteBytes(const void* data, uint32 data_len);
117 // Update (in-place) the length field in the frame being built to reflect the
118 // current actual length of bytes written to said frame through this builder.
119 // The framer parameter is used to determine version-specific location and
120 // size information of the length field to be written, and must be initialized
121 // with the correct version for the frame being written.
122 bool RewriteLength(const SpdyFramer& framer);
124 // Update (in-place) the length field in the frame being built to reflect the
125 // given length.
126 // The framer parameter is used to determine version-specific location and
127 // size information of the length field to be written, and must be initialized
128 // with the correct version for the frame being written.
129 bool OverwriteLength(const SpdyFramer& framer, size_t length);
131 // Update (in-place) the flags field in the frame being built to reflect the
132 // given flags value.
133 // Used only for SPDY versions >=4.
134 bool OverwriteFlags(const SpdyFramer& framer, uint8 flags);
136 private:
137 // Checks to make sure that there is an appropriate amount of space for a
138 // write of given size, in bytes.
139 bool CanWrite(size_t length) const;
141 scoped_ptr<char[]> buffer_;
142 size_t capacity_; // Allocation size of payload, set by constructor.
143 size_t length_; // Length of the latest frame in the buffer.
144 size_t offset_; // Position at which the latest frame begins.
146 const SpdyMajorVersion version_;
149 } // namespace net
151 #endif // NET_SPDY_SPDY_FRAME_BUILDER_H_