[net] http2: support SETTINGS_NO_RFC7540_PRIORITIES in SETTINGS frame

2 views
Skip to first unread message

Nicholas Husin (Gerrit)

unread,
Dec 10, 2025, 3:43:11 PM (11 days ago) Dec 10
to Damien Neil, goph...@pubsubhelper.golang.org, golang-co...@googlegroups.com
Attention needed from Damien Neil

Nicholas Husin has uploaded the change for review

Nicholas Husin would like Damien Neil to review this change.

Commit message

http2: support SETTINGS_NO_RFC7540_PRIORITIES in SETTINGS frame

To make sure that clients do not unnecessarily send RFC 7540 priority
signals when it would be treated as a no-op, this change makes it so
that our server always sends SETTINGS_NO_RFC7540_PRIORITIES in our
SETTINGS frame when our write scheduler is set to anything other than
the RFC 7540 write scheduler.

For golang/go#75500
Change-Id: I7a54251022087319999deda7efb663f8b251aa95

Change diff

diff --git a/http2/http2.go b/http2/http2.go
index 105fe12..6320f4e 100644
--- a/http2/http2.go
+++ b/http2/http2.go
@@ -169,6 +169,7 @@
SettingMaxFrameSize SettingID = 0x5
SettingMaxHeaderListSize SettingID = 0x6
SettingEnableConnectProtocol SettingID = 0x8
+ SettingNoRFC7540Priorities SettingID = 0x9
)

var settingName = map[SettingID]string{
@@ -179,6 +180,7 @@
SettingMaxFrameSize: "MAX_FRAME_SIZE",
SettingMaxHeaderListSize: "MAX_HEADER_LIST_SIZE",
SettingEnableConnectProtocol: "ENABLE_CONNECT_PROTOCOL",
+ SettingNoRFC7540Priorities: "NO_RFC7540_PRIORITIES",
}

func (s SettingID) String() string {
diff --git a/http2/server.go b/http2/server.go
index d1fa038..25331bf 100644
--- a/http2/server.go
+++ b/http2/server.go
@@ -942,6 +942,9 @@
if !disableExtendedConnectProtocol {
settings = append(settings, Setting{SettingEnableConnectProtocol, 1})
}
+ if _, ok := sc.writeSched.(*priorityWriteSchedulerRFC7540); !ok {
+ settings = append(settings, Setting{SettingNoRFC7540Priorities, 1})
+ }
sc.writeFrame(FrameWriteRequest{
write: settings,
})
@@ -1809,6 +1812,10 @@
case SettingEnableConnectProtocol:
// Receipt of this parameter by a server does not
// have any impact
+ case SettingNoRFC7540Priorities:
+ if s.Val > 1 {
+ return ConnectionError(ErrCodeProtocol)
+ }
default:
// Unknown setting: "An endpoint that receives a SETTINGS
// frame with any unknown or unsupported identifier MUST
diff --git a/http2/server_test.go b/http2/server_test.go
index 5e1848f..e21f721 100644
--- a/http2/server_test.go
+++ b/http2/server_test.go
@@ -5152,6 +5152,68 @@
st.wantIdle()
}

+func TestServerSettingNoRFC7540Priorities(t *testing.T) {
+ synctestTest(t, testServerSettingNoRFC7540Priorities)
+}
+func testServerSettingNoRFC7540Priorities(t testing.TB) {
+ tests := []struct {
+ ws func() WriteScheduler
+ wantNoRFC7540Setting bool
+ }{
+ {
+ ws: func() WriteScheduler {
+ return newPriorityWriteSchedulerRFC7540(nil)
+ },
+ wantNoRFC7540Setting: false,
+ },
+ {
+ ws: newPriorityWriteSchedulerRFC9218,
+ wantNoRFC7540Setting: true,
+ },
+ {
+ ws: NewRandomWriteScheduler,
+ wantNoRFC7540Setting: true,
+ },
+ {
+ ws: newRoundRobinWriteScheduler,
+ wantNoRFC7540Setting: true,
+ },
+ }
+ for _, tt := range tests {
+ st := newServerTester(t, nil, func(s *Server) {
+ s.NewWriteScheduler = tt.ws
+ })
+ defer st.Close()
+
+ var gotNoRFC7540Setting bool
+ st.greetAndCheckSettings(func(s Setting) error {
+ if s.ID != SettingNoRFC7540Priorities {
+ return nil
+ }
+ gotNoRFC7540Setting = s.Val == 1
+ return nil
+ })
+ if tt.wantNoRFC7540Setting != gotNoRFC7540Setting {
+ t.Errorf("want SETTINGS_NO_RFC7540_PRIORITIES to be %v, got %v", tt.wantNoRFC7540Setting, gotNoRFC7540Setting)
+ }
+ }
+}
+
+func TestServerSettingNoRFC7540PrioritiesInvalid(t *testing.T) {
+ synctestTest(t, testServerSettingNoRFC7540PrioritiesInvalid)
+}
+func testServerSettingNoRFC7540PrioritiesInvalid(t testing.TB) {
+ st := newServerTester(t, nil)
+ defer st.Close()
+
+ st.writePreface()
+ st.writeSettings(Setting{ID: SettingNoRFC7540Priorities, Val: 2})
+ synctest.Wait()
+ st.readFrame() // SETTINGS frame
+ st.readFrame() // WINDOW_UPDATE frame
+ st.wantGoAway(0, ErrCodeProtocol)
+}
+
// This test documents current behavior, rather than ideal behavior that we
// would necessarily like to see. Refer to go.dev/issues/75936 for details.
func TestServerRFC7540PrioritySmallPayload(t *testing.T) {

Change information

Files:
  • M http2/http2.go
  • M http2/server.go
  • M http2/server_test.go
Change size: M
Delta: 3 files changed, 71 insertions(+), 0 deletions(-)
Open in Gerrit

Related details

Attention is currently required from:
  • Damien Neil
Submit Requirements:
  • requirement is not satisfiedCode-Review
  • requirement satisfiedNo-Unresolved-Comments
  • requirement is not satisfiedReview-Enforcement
  • requirement is not satisfiedTryBots-Pass
Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. DiffyGerrit
Gerrit-MessageType: newchange
Gerrit-Project: net
Gerrit-Branch: master
Gerrit-Change-Id: I7a54251022087319999deda7efb663f8b251aa95
Gerrit-Change-Number: 729141
Gerrit-PatchSet: 1
Gerrit-Owner: Nicholas Husin <n...@golang.org>
Gerrit-Reviewer: Damien Neil <dn...@google.com>
Gerrit-Reviewer: Nicholas Husin <n...@golang.org>
Gerrit-Attention: Damien Neil <dn...@google.com>
unsatisfied_requirement
satisfied_requirement
open
diffy

Damien Neil (Gerrit)

unread,
Dec 19, 2025, 6:09:38 PM (2 days ago) Dec 19
to Nicholas Husin, goph...@pubsubhelper.golang.org, Go LUCI, golang-co...@googlegroups.com
Attention needed from Nicholas Husin

Damien Neil added 1 comment

File http2/server.go
Line 946, Patchset 1 (Latest): settings = append(settings, Setting{SettingNoRFC7540Priorities, 1})
Damien Neil . unresolved

User-provided write schedulers might handle RFC 7540 priorities.

I think this should be flipped: Send SettingNoRFC7540Priorities only if the write scheduler is one we know doesn't use that priority scheme.

Open in Gerrit

Related details

Attention is currently required from:
  • Nicholas Husin
Submit Requirements:
    • requirement is not satisfiedCode-Review
    • requirement is not satisfiedNo-Unresolved-Comments
    • requirement is not satisfiedReview-Enforcement
    • requirement satisfiedTryBots-Pass
    Inspect html for hidden footers to help with email filtering. To unsubscribe visit settings. DiffyGerrit
    Gerrit-MessageType: comment
    Gerrit-Project: net
    Gerrit-Branch: master
    Gerrit-Change-Id: I7a54251022087319999deda7efb663f8b251aa95
    Gerrit-Change-Number: 729141
    Gerrit-PatchSet: 1
    Gerrit-Owner: Nicholas Husin <n...@golang.org>
    Gerrit-Reviewer: Damien Neil <dn...@google.com>
    Gerrit-Reviewer: Nicholas Husin <n...@golang.org>
    Gerrit-Attention: Nicholas Husin <n...@golang.org>
    Gerrit-Comment-Date: Fri, 19 Dec 2025 23:09:34 +0000
    Gerrit-HasComments: Yes
    Gerrit-Has-Labels: No
    unsatisfied_requirement
    satisfied_requirement
    open
    diffy
    Reply all
    Reply to author
    Forward
    0 new messages