transport: don't crash if peer sends an empty header field name

The grpc-http2 transport doesn't validate hpack-decoded field names to be
valid http2 field names before checking their first byte. Had it verified
first and found that the empty string is illegal, this crash wouldn't happen,
but currently a malicious request can crash a gRPC server by sending an empty
hpack string.
This commit is contained in:
Brad Fitzpatrick 2016-02-10 21:45:00 +00:00
parent 51d644aca6
commit 8aa7cbbc33
2 changed files with 24 additions and 1 deletions

View File

@ -120,7 +120,7 @@ type headerFrame interface {
// reserved by gRPC protocol. Any other headers are classified as the
// user-specified metadata.
func isReservedHeader(hdr string) bool {
if hdr[0] == ':' {
if hdr != "" && hdr[0] == ':' {
return true
}
switch hdr {

View File

@ -660,3 +660,26 @@ func TestStreamContext(t *testing.T) {
t.Fatalf("GetStreamFromContext(%v) = %v, %t, want: %v, true", ctx, *s, ok, expectedStream)
}
}
func TestIsReservedHeader(t *testing.T) {
tests := []struct {
h string
want bool
}{
{"", false}, // but should be rejected earlier
{"foo", false},
{"content-type", true},
{"grpc-message-type", true},
{"grpc-encoding", true},
{"grpc-message", true},
{"grpc-status", true},
{"grpc-timeout", true},
{"te", true},
}
for _, tt := range tests {
got := isReservedHeader(tt.h)
if got != tt.want {
t.Errorf("isReservedHeader(%q) = %v; want %v", tt.h, got, tt.want)
}
}
}