@@ -7,6 +7,7 @@ package spdy
77import (
88 "encoding/binary"
99 "io"
10+ "math"
1011 "net/http"
1112 "strings"
1213)
@@ -47,13 +48,21 @@ func (frame *RstStreamFrame) write(f *Framer) (err error) {
4748func (frame * SettingsFrame ) write (f * Framer ) (err error ) {
4849 frame .CFHeader .version = Version
4950 frame .CFHeader .frameType = TypeSettings
50- frame .CFHeader .length = uint32 (len (frame .FlagIdValues )* 8 + 4 )
51+ payloadLen := len (frame .FlagIdValues )* 8 + 4
52+ if payloadLen > MaxDataLength {
53+ return & Error {InvalidControlFrame , 0 }
54+ }
55+ frame .CFHeader .length = uint32 (payloadLen )
5156
5257 // Serialize frame to Writer.
5358 if err = writeControlFrameHeader (f .w , frame .CFHeader ); err != nil {
5459 return
5560 }
56- if err = binary .Write (f .w , binary .BigEndian , uint32 (len (frame .FlagIdValues ))); err != nil {
61+ n := len (frame .FlagIdValues )
62+ if uint64 (n ) > math .MaxUint32 {
63+ return & Error {InvalidControlFrame , 0 }
64+ }
65+ if err = binary .Write (f .w , binary .BigEndian , uint32 (n )); err != nil {
5766 return
5867 }
5968 for _ , flagIdValue := range frame .FlagIdValues {
@@ -154,29 +163,41 @@ func writeControlFrameHeader(w io.Writer, h ControlFrameHeader) error {
154163
155164func writeHeaderValueBlock (w io.Writer , h http.Header ) (n int , err error ) {
156165 n = 0
157- if err = binary .Write (w , binary .BigEndian , uint32 (len (h ))); err != nil {
166+ numHeaders := len (h )
167+ if numHeaders > math .MaxUint32 {
168+ return n , & Error {InvalidControlFrame , 0 }
169+ }
170+ if err = binary .Write (w , binary .BigEndian , uint32 (numHeaders )); err != nil {
158171 return
159172 }
160173 n += 2
161174 for name , values := range h {
162- if err = binary .Write (w , binary .BigEndian , uint32 (len (name ))); err != nil {
175+ nameLen := len (name )
176+ if nameLen > math .MaxUint32 {
177+ return n , & Error {InvalidControlFrame , 0 }
178+ }
179+ if err = binary .Write (w , binary .BigEndian , uint32 (nameLen )); err != nil {
163180 return
164181 }
165182 n += 2
166183 name = strings .ToLower (name )
167184 if _ , err = io .WriteString (w , name ); err != nil {
168185 return
169186 }
170- n += len ( name )
187+ n += nameLen
171188 v := strings .Join (values , headerValueSeparator )
172- if err = binary .Write (w , binary .BigEndian , uint32 (len (v ))); err != nil {
189+ vLen := len (v )
190+ if vLen > math .MaxUint32 {
191+ return n , & Error {InvalidControlFrame , 0 }
192+ }
193+ if err = binary .Write (w , binary .BigEndian , uint32 (vLen )); err != nil {
173194 return
174195 }
175196 n += 2
176197 if _ , err = io .WriteString (w , v ); err != nil {
177198 return
178199 }
179- n += len ( v )
200+ n += vLen
180201 }
181202 return
182203}
@@ -200,7 +221,11 @@ func (f *Framer) writeSynStreamFrame(frame *SynStreamFrame) (err error) {
200221 // Set ControlFrameHeader.
201222 frame .CFHeader .version = Version
202223 frame .CFHeader .frameType = TypeSynStream
203- frame .CFHeader .length = uint32 (len (f .headerBuf .Bytes ()) + 10 )
224+ hLen := len (f .headerBuf .Bytes ()) + 10
225+ if hLen > MaxDataLength {
226+ return & Error {InvalidControlFrame , 0 }
227+ }
228+ frame .CFHeader .length = uint32 (hLen )
204229
205230 // Serialize frame to Writer.
206231 if err = writeControlFrameHeader (f .w , frame .CFHeader ); err != nil {
@@ -244,7 +269,11 @@ func (f *Framer) writeSynReplyFrame(frame *SynReplyFrame) (err error) {
244269 // Set ControlFrameHeader.
245270 frame .CFHeader .version = Version
246271 frame .CFHeader .frameType = TypeSynReply
247- frame .CFHeader .length = uint32 (len (f .headerBuf .Bytes ()) + 4 )
272+ hLen := len (f .headerBuf .Bytes ()) + 4
273+ if hLen > MaxDataLength {
274+ return & Error {InvalidControlFrame , 0 }
275+ }
276+ frame .CFHeader .length = uint32 (hLen )
248277
249278 // Serialize frame to Writer.
250279 if err = writeControlFrameHeader (f .w , frame .CFHeader ); err != nil {
@@ -279,7 +308,11 @@ func (f *Framer) writeHeadersFrame(frame *HeadersFrame) (err error) {
279308 // Set ControlFrameHeader.
280309 frame .CFHeader .version = Version
281310 frame .CFHeader .frameType = TypeHeaders
282- frame .CFHeader .length = uint32 (len (f .headerBuf .Bytes ()) + 4 )
311+ hLen := len (f .headerBuf .Bytes ()) + 4
312+ if hLen > MaxDataLength {
313+ return & Error {InvalidControlFrame , 0 }
314+ }
315+ frame .CFHeader .length = uint32 (hLen )
283316
284317 // Serialize frame to Writer.
285318 if err = writeControlFrameHeader (f .w , frame .CFHeader ); err != nil {
@@ -307,7 +340,11 @@ func (f *Framer) writeDataFrame(frame *DataFrame) (err error) {
307340 if err = binary .Write (f .w , binary .BigEndian , frame .StreamId ); err != nil {
308341 return
309342 }
310- flagsAndLength := uint32 (frame .Flags )<< 24 | uint32 (len (frame .Data ))
343+ dLen := len (frame .Data )
344+ if dLen > MaxDataLength {
345+ return & Error {InvalidDataFrame , frame .StreamId }
346+ }
347+ flagsAndLength := uint32 (frame .Flags )<< 24 | uint32 (dLen )
311348 if err = binary .Write (f .w , binary .BigEndian , flagsAndLength ); err != nil {
312349 return
313350 }
0 commit comments