slidge-whatsapp 0.2.5__cp311-cp311-manylinux_2_36_aarch64.whl → 0.3.0__cp311-cp311-manylinux_2_36_aarch64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of slidge-whatsapp might be problematic. Click here for more details.

Files changed (484) hide show
  1. slidge_whatsapp/config.py +3 -0
  2. slidge_whatsapp/contact.py +15 -3
  3. slidge_whatsapp/event.go +171 -70
  4. slidge_whatsapp/gateway.go +16 -68
  5. slidge_whatsapp/gateway.py +4 -5
  6. slidge_whatsapp/generated/_whatsapp.cpython-311-aarch64-linux-gnu.h +168 -151
  7. slidge_whatsapp/generated/_whatsapp.cpython-311-aarch64-linux-gnu.so +0 -0
  8. slidge_whatsapp/generated/build.py +142 -128
  9. slidge_whatsapp/generated/whatsapp.c +1689 -1417
  10. slidge_whatsapp/generated/whatsapp.go +1011 -900
  11. slidge_whatsapp/generated/whatsapp.py +1175 -1050
  12. slidge_whatsapp/generated/whatsapp_go.h +168 -151
  13. slidge_whatsapp/go.mod +21 -15
  14. slidge_whatsapp/go.sum +49 -31
  15. slidge_whatsapp/group.py +34 -30
  16. slidge_whatsapp/media/media.go +22 -12
  17. slidge_whatsapp/session.go +106 -82
  18. slidge_whatsapp/session.py +46 -14
  19. slidge_whatsapp/vendor/github.com/beeper/argo-go/LICENSE +9 -0
  20. slidge_whatsapp/vendor/github.com/beeper/argo-go/block/blockreader.go +329 -0
  21. slidge_whatsapp/vendor/github.com/beeper/argo-go/block/blockwriter.go +417 -0
  22. slidge_whatsapp/vendor/github.com/beeper/argo-go/codec/decoder.go +652 -0
  23. slidge_whatsapp/vendor/github.com/beeper/argo-go/codec/encoder.go +985 -0
  24. slidge_whatsapp/vendor/github.com/beeper/argo-go/header/header.go +135 -0
  25. slidge_whatsapp/vendor/github.com/beeper/argo-go/internal/util/util.go +133 -0
  26. slidge_whatsapp/vendor/github.com/beeper/argo-go/label/label.go +384 -0
  27. slidge_whatsapp/vendor/github.com/beeper/argo-go/label/wiremarkers.go +37 -0
  28. slidge_whatsapp/vendor/github.com/beeper/argo-go/pkg/bitset/bitset.go +197 -0
  29. slidge_whatsapp/vendor/github.com/beeper/argo-go/pkg/buf/buf.go +420 -0
  30. slidge_whatsapp/vendor/github.com/beeper/argo-go/pkg/varint/varint.go +246 -0
  31. slidge_whatsapp/vendor/github.com/beeper/argo-go/wire/wire.go +614 -0
  32. slidge_whatsapp/vendor/github.com/beeper/argo-go/wirecodec/decode.go +341 -0
  33. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlfcn.go +4 -4
  34. slidge_whatsapp/vendor/github.com/ebitengine/purego/dlfcn_darwin.go +0 -5
  35. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/go_libinit.go +3 -0
  36. slidge_whatsapp/vendor/github.com/ebitengine/purego/internal/fakecgo/symbols.go +40 -20
  37. slidge_whatsapp/vendor/github.com/elliotchance/orderedmap/v3/LICENSE +21 -0
  38. slidge_whatsapp/vendor/github.com/elliotchance/orderedmap/v3/list.go +95 -0
  39. slidge_whatsapp/vendor/github.com/elliotchance/orderedmap/v3/orderedmap.go +187 -0
  40. slidge_whatsapp/vendor/github.com/gen2brain/go-fitz/fitz.go +1 -0
  41. slidge_whatsapp/vendor/github.com/gen2brain/go-fitz/fitz_cgo.go +3 -0
  42. slidge_whatsapp/vendor/github.com/gen2brain/go-fitz/fitz_nocgo.go +4 -5
  43. slidge_whatsapp/vendor/github.com/gen2brain/go-fitz/purego_darwin.go +11 -1
  44. slidge_whatsapp/vendor/github.com/gen2brain/go-fitz/purego_linux.go +10 -0
  45. slidge_whatsapp/vendor/github.com/gen2brain/go-fitz/purego_windows.go +12 -0
  46. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/.gitignore +0 -2
  47. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/CHANGELOG.md +44 -1
  48. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/COPYRIGHT.txt +6 -1
  49. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/README.md +14 -17
  50. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/abi.go +1 -1
  51. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/abi2.go +7 -0
  52. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/assets/libffi/LICENSE +21 -0
  53. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/assets/libffi/darwin_amd64/libffi.8.dylib +0 -0
  54. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/assets/libffi/darwin_arm64/libffi.8.dylib +0 -0
  55. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/assets/libffi/windows_amd64/libffi-8.dll +0 -0
  56. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/cif.go +15 -0
  57. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/cif_arm64.go +16 -0
  58. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/embed.go +49 -0
  59. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/embed_darwin_amd64.go +10 -0
  60. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/embed_darwin_arm64.go +10 -0
  61. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/embed_windows_amd64.go +10 -0
  62. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/ffi.go +53 -15
  63. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/fun.go +10 -2
  64. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/init.go +22 -9
  65. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/lib.go +1 -1
  66. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/lib_unix.go +1 -1
  67. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/lib_windows.go +1 -1
  68. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/README.md +4 -7
  69. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/callback.go +2 -1
  70. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3-binding.c +11545 -6680
  71. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3-binding.h +527 -273
  72. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3.go +57 -23
  73. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3_opt_unlock_notify.c +4 -0
  74. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3_opt_unlock_notify.go +4 -0
  75. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3_opt_userauth.go +13 -140
  76. slidge_whatsapp/vendor/github.com/mattn/go-sqlite3/sqlite3ext.h +4 -0
  77. slidge_whatsapp/vendor/github.com/petermattis/goid/.gitignore +4 -0
  78. slidge_whatsapp/vendor/github.com/petermattis/goid/LICENSE +202 -0
  79. slidge_whatsapp/vendor/github.com/petermattis/goid/README.md +4 -0
  80. slidge_whatsapp/vendor/github.com/petermattis/goid/goid.go +35 -0
  81. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_gccgo.go +26 -0
  82. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_go1.3.c +23 -0
  83. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_go1.3.go +22 -0
  84. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_go1.4.go +35 -0
  85. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_go1.4.s +18 -0
  86. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_go1.5.go +28 -0
  87. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_go1.5.s +44 -0
  88. slidge_whatsapp/vendor/github.com/petermattis/goid/goid_slow.go +24 -0
  89. slidge_whatsapp/vendor/github.com/petermattis/goid/runtime_gccgo_go1.8.go +17 -0
  90. slidge_whatsapp/vendor/github.com/petermattis/goid/runtime_go1.23.go +38 -0
  91. slidge_whatsapp/vendor/github.com/petermattis/goid/runtime_go1.25.go +37 -0
  92. slidge_whatsapp/vendor/github.com/petermattis/goid/runtime_go1.5.go +57 -0
  93. slidge_whatsapp/vendor/github.com/petermattis/goid/runtime_go1.6.go +43 -0
  94. slidge_whatsapp/vendor/github.com/petermattis/goid/runtime_go1.9.go +37 -0
  95. slidge_whatsapp/vendor/github.com/rs/zerolog/CONTRIBUTING.md +43 -0
  96. slidge_whatsapp/vendor/github.com/rs/zerolog/README.md +31 -0
  97. slidge_whatsapp/vendor/github.com/rs/zerolog/console.go +20 -5
  98. slidge_whatsapp/vendor/github.com/rs/zerolog/log/log.go +131 -0
  99. slidge_whatsapp/vendor/github.com/rs/zerolog/log.go +1 -1
  100. slidge_whatsapp/vendor/github.com/rs/zerolog/sampler.go +4 -1
  101. slidge_whatsapp/vendor/github.com/rs/zerolog/writer.go +9 -0
  102. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/LICENSE +19 -0
  103. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/argmap.go +37 -0
  104. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/collections.go +148 -0
  105. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/comment.go +31 -0
  106. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/decode.go +216 -0
  107. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/definition.go +110 -0
  108. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/directive.go +43 -0
  109. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/document.go +89 -0
  110. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/dumper.go +159 -0
  111. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/fragment.go +41 -0
  112. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/operation.go +32 -0
  113. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/path.go +72 -0
  114. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/selection.go +41 -0
  115. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/source.go +19 -0
  116. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/type.go +68 -0
  117. slidge_whatsapp/vendor/github.com/vektah/gqlparser/v2/ast/value.go +122 -0
  118. slidge_whatsapp/vendor/go.mau.fi/libsignal/groups/GroupCipher.go +17 -6
  119. slidge_whatsapp/vendor/go.mau.fi/libsignal/groups/GroupSessionBuilder.go +17 -7
  120. slidge_whatsapp/vendor/go.mau.fi/libsignal/groups/state/store/SenderKeyStore.go +4 -2
  121. slidge_whatsapp/vendor/go.mau.fi/libsignal/keys/chain/ChainKey.go +1 -0
  122. slidge_whatsapp/vendor/go.mau.fi/libsignal/keys/identity/IdentityKey.go +1 -0
  123. slidge_whatsapp/vendor/go.mau.fi/libsignal/logger/DefaultLogger.go +2 -2
  124. slidge_whatsapp/vendor/go.mau.fi/libsignal/serialize/FingerprintProtocol.pb.go +3 -2
  125. slidge_whatsapp/vendor/go.mau.fi/libsignal/serialize/LocalStorageProtocol.pb.go +3 -2
  126. slidge_whatsapp/vendor/go.mau.fi/libsignal/serialize/WhisperTextProtocol.pb.go +3 -2
  127. slidge_whatsapp/vendor/go.mau.fi/libsignal/session/Session.go +41 -17
  128. slidge_whatsapp/vendor/go.mau.fi/libsignal/session/SessionCipher.go +64 -30
  129. slidge_whatsapp/vendor/go.mau.fi/libsignal/state/store/IdentityKeyStore.go +5 -3
  130. slidge_whatsapp/vendor/go.mau.fi/libsignal/state/store/MessageKeyStore.go +6 -4
  131. slidge_whatsapp/vendor/go.mau.fi/libsignal/state/store/PreKeyStore.go +6 -4
  132. slidge_whatsapp/vendor/go.mau.fi/libsignal/state/store/SessionStore.go +8 -6
  133. slidge_whatsapp/vendor/go.mau.fi/libsignal/state/store/SignedPreKeyStore.go +7 -5
  134. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/connlog.go +257 -0
  135. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/database.go +309 -0
  136. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/iter.go +233 -0
  137. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/json.go +47 -0
  138. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/log.go +129 -0
  139. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/massinsert.go +164 -0
  140. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/queryhelper.go +137 -0
  141. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/reflectscan.go +30 -0
  142. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/transaction.go +180 -0
  143. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/upgrades.go +250 -0
  144. slidge_whatsapp/vendor/go.mau.fi/util/dbutil/upgradetable.go +331 -0
  145. slidge_whatsapp/vendor/go.mau.fi/util/exerrors/dualerror.go +33 -0
  146. slidge_whatsapp/vendor/go.mau.fi/util/exerrors/must.go +23 -0
  147. slidge_whatsapp/vendor/go.mau.fi/util/exhttp/cors.go +32 -0
  148. slidge_whatsapp/vendor/go.mau.fi/util/exhttp/handleerrors.go +98 -0
  149. slidge_whatsapp/vendor/go.mau.fi/util/exhttp/json.go +36 -0
  150. slidge_whatsapp/vendor/go.mau.fi/util/exhttp/middleware.go +30 -0
  151. slidge_whatsapp/vendor/go.mau.fi/util/exhttp/networkerror.go +38 -0
  152. slidge_whatsapp/vendor/go.mau.fi/util/exstrings/stringutil.go +104 -0
  153. slidge_whatsapp/vendor/go.mau.fi/util/exsync/event.go +104 -0
  154. slidge_whatsapp/vendor/go.mau.fi/util/exsync/returnonce.go +25 -0
  155. slidge_whatsapp/vendor/go.mau.fi/util/exsync/ringbuffer.go +139 -0
  156. slidge_whatsapp/vendor/go.mau.fi/util/exsync/syncmap.go +94 -0
  157. slidge_whatsapp/vendor/go.mau.fi/util/exsync/syncset.go +136 -0
  158. slidge_whatsapp/vendor/go.mau.fi/util/exzerolog/callermarshal.go +28 -0
  159. slidge_whatsapp/vendor/go.mau.fi/util/exzerolog/defaults.go +32 -0
  160. slidge_whatsapp/vendor/go.mau.fi/util/exzerolog/generics.go +45 -0
  161. slidge_whatsapp/vendor/go.mau.fi/util/exzerolog/writer.go +81 -0
  162. slidge_whatsapp/vendor/go.mau.fi/util/ptr/ptr.go +43 -0
  163. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/.pre-commit-config.yaml +3 -3
  164. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/decode.go +27 -26
  165. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/encode.go +4 -3
  166. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/hash.go +1 -1
  167. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate/keys.go +5 -4
  168. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/appstate.go +32 -26
  169. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/argo/argo-wire-type-store.argo +63 -0
  170. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/argo/argo.go +62 -0
  171. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/argo/name-to-queryids.json +306 -0
  172. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/armadillomessage.go +42 -8
  173. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/binary/encoder.go +1 -1
  174. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/broadcast.go +5 -4
  175. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/call.go +2 -1
  176. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/client.go +134 -55
  177. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/connectionevents.go +34 -11
  178. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/download-to-file.go +63 -30
  179. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/download.go +78 -34
  180. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/errors.go +4 -0
  181. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/group.go +157 -55
  182. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/internals.go +202 -154
  183. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/keepalive.go +3 -2
  184. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/mediaconn.go +5 -3
  185. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/mediaretry.go +2 -1
  186. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/message.go +448 -138
  187. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/msgsecret.go +106 -31
  188. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/newsletter.go +83 -7
  189. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/notification.go +83 -43
  190. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/pair-code.go +9 -6
  191. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/pair.go +42 -18
  192. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/prekeys.go +9 -5
  193. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/presence.go +17 -7
  194. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/privacysettings.go +10 -11
  195. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/extra.go +7 -0
  196. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloAddMessage/InstamadilloAddMessage.pb.go +983 -0
  197. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloAddMessage/InstamadilloAddMessage.proto +85 -0
  198. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloAddMessage/extra.go +3 -0
  199. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeActionLog/InstamadilloCoreTypeActionLog.pb.go +197 -0
  200. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeActionLog/InstamadilloCoreTypeActionLog.proto +13 -0
  201. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeAdminMessage/InstamadilloCoreTypeAdminMessage.pb.go +279 -0
  202. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeAdminMessage/InstamadilloCoreTypeAdminMessage.proto +21 -0
  203. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeCollection/InstamadilloCoreTypeCollection.pb.go +137 -0
  204. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeCollection/InstamadilloCoreTypeCollection.proto +10 -0
  205. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeLink/InstamadilloCoreTypeLink.pb.go +313 -0
  206. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeLink/InstamadilloCoreTypeLink.proto +27 -0
  207. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeMedia/InstamadilloCoreTypeMedia.pb.go +1299 -0
  208. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeMedia/InstamadilloCoreTypeMedia.proto +112 -0
  209. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeText/InstamadilloCoreTypeText.pb.go +514 -0
  210. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloCoreTypeText/InstamadilloCoreTypeText.proto +47 -0
  211. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloDeleteMessage/InstamadilloDeleteMessage.pb.go +123 -0
  212. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloDeleteMessage/InstamadilloDeleteMessage.proto +7 -0
  213. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloDeleteMessage/extra.go +3 -0
  214. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloSupplementMessage/InstamadilloSupplementMessage.pb.go +720 -0
  215. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloSupplementMessage/InstamadilloSupplementMessage.proto +59 -0
  216. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloSupplementMessage/extra.go +3 -0
  217. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloTransportPayload/InstamadilloTransportPayload.pb.go +365 -0
  218. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloTransportPayload/InstamadilloTransportPayload.proto +33 -0
  219. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloXmaContentRef/InstamadilloXmaContentRef.pb.go +1238 -0
  220. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/instamadilloXmaContentRef/InstamadilloXmaContentRef.proto +105 -0
  221. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waAdv/WAAdv.pb.go +39 -9
  222. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waArmadilloApplication/WAArmadilloApplication.pb.go +354 -175
  223. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waArmadilloApplication/WAArmadilloApplication.proto +5 -5
  224. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waArmadilloXMA/WAArmadilloXMA.pb.go +170 -15
  225. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waArmadilloXMA/WAArmadilloXMA.proto +4 -0
  226. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waBotMetadata/WABotMetadata.pb.go +5156 -0
  227. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waBotMetadata/WABotMetadata.proto +516 -0
  228. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCert/WACert.pb.go +29 -9
  229. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waChatLockSettings/WAProtobufsChatLockSettings.pb.go +13 -9
  230. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCommon/WACommon.pb.go +344 -31
  231. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCommon/WACommon.proto +26 -0
  232. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCompanionReg/{WAWebProtobufsCompanionReg.pb.go → WACompanionReg.pb.go} +211 -89
  233. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCompanionReg/{WAWebProtobufsCompanionReg.proto → WACompanionReg.proto} +5 -1
  234. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waConsumerApplication/WAConsumerApplication.pb.go +173 -9
  235. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waDeviceCapabilities/WAProtobufsDeviceCapabilities.pb.go +78 -16
  236. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waDeviceCapabilities/WAProtobufsDeviceCapabilities.proto +5 -0
  237. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waE2E/WAWebProtobufsE2E.pb.go +7463 -5180
  238. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waE2E/WAWebProtobufsE2E.proto +366 -343
  239. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waHistorySync/WAWebProtobufsHistorySync.pb.go +485 -135
  240. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waHistorySync/WAWebProtobufsHistorySync.proto +17 -0
  241. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waLidMigrationSyncPayload/WAWebProtobufLidMigrationSyncPayload.pb.go +198 -0
  242. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waLidMigrationSyncPayload/WAWebProtobufLidMigrationSyncPayload.proto +14 -0
  243. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMediaTransport/WAMediaTransport.pb.go +162 -9
  244. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMediaTransport/WAMediaTransport.proto +1 -0
  245. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMmsRetry/WAMmsRetry.pb.go +32 -9
  246. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMmsRetry/WAMmsRetry.proto +1 -0
  247. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMsgApplication/WAMsgApplication.pb.go +192 -52
  248. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMsgApplication/WAMsgApplication.proto +8 -0
  249. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMsgTransport/WAMsgTransport.pb.go +60 -9
  250. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMsgTransport/extra.go +7 -6
  251. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMultiDevice/WAMultiDevice.pb.go +39 -9
  252. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waServerSync/WAServerSync.pb.go +61 -9
  253. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waStatusAttributions/WAStatusAttributions.pb.go +952 -0
  254. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waStatusAttributions/WAStatusAttributions.proto +88 -0
  255. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waSyncAction/WASyncAction.pb.go +1802 -453
  256. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waSyncAction/WASyncAction.proto +92 -0
  257. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waUserPassword/WAProtobufsUserPassword.pb.go +27 -9
  258. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waVnameCert/WAWebProtobufsVnameCert.pb.go +59 -9
  259. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWa6/WAWebProtobufsWa6.pb.go +435 -109
  260. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWa6/WAWebProtobufsWa6.proto +11 -0
  261. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWeb/WAWebProtobufsWeb.pb.go +563 -9
  262. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWeb/WAWebProtobufsWeb.proto +4 -0
  263. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/receipt.go +32 -9
  264. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/reportingfields.json +1 -0
  265. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/reportingtoken.go +176 -0
  266. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/retry.go +39 -21
  267. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/send.go +267 -79
  268. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/sendfb.go +28 -16
  269. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/clientpayload.go +3 -1
  270. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/noop.go +87 -44
  271. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/signal.go +75 -88
  272. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/container.go +86 -65
  273. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/lidmap.go +186 -0
  274. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/store.go +314 -170
  275. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/00-latest-schema.sql +155 -0
  276. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/03-message-secrets.sql +11 -0
  277. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/04-privacy-tokens.sql +8 -0
  278. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/05-account-jid-format.sql +2 -0
  279. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/06-facebook-uuid.sql +2 -0
  280. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/07-account-lid.sql +2 -0
  281. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/08-lid-mapping.sql +5 -0
  282. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/09-decryption-buffer.sql +10 -0
  283. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/10-chat-db-lid-migration-ts.sql +2 -0
  284. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrades/upgrades.go +22 -0
  285. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/store.go +109 -56
  286. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/botmap.go +210 -0
  287. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/call.go +1 -0
  288. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/events/events.go +21 -2
  289. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/group.go +15 -6
  290. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/jid.go +9 -9
  291. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/message.go +18 -0
  292. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/types/user.go +2 -0
  293. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/update.go +3 -2
  294. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/upload.go +1 -1
  295. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/user.go +59 -37
  296. slidge_whatsapp/vendor/golang.org/x/crypto/curve25519/curve25519.go +1 -1
  297. slidge_whatsapp/vendor/golang.org/x/exp/LICENSE +27 -0
  298. slidge_whatsapp/vendor/golang.org/x/exp/PATENTS +22 -0
  299. slidge_whatsapp/vendor/golang.org/x/exp/constraints/constraints.go +54 -0
  300. slidge_whatsapp/vendor/golang.org/x/net/http/httpguts/guts.go +50 -0
  301. slidge_whatsapp/vendor/golang.org/x/net/http/httpguts/httplex.go +347 -0
  302. slidge_whatsapp/vendor/golang.org/x/net/http2/.gitignore +2 -0
  303. slidge_whatsapp/vendor/golang.org/x/net/http2/ascii.go +53 -0
  304. slidge_whatsapp/vendor/golang.org/x/net/http2/ciphers.go +641 -0
  305. slidge_whatsapp/vendor/golang.org/x/net/http2/client_conn_pool.go +311 -0
  306. slidge_whatsapp/vendor/golang.org/x/net/http2/config.go +164 -0
  307. slidge_whatsapp/vendor/golang.org/x/net/http2/databuffer.go +149 -0
  308. slidge_whatsapp/vendor/golang.org/x/net/http2/errors.go +145 -0
  309. slidge_whatsapp/vendor/golang.org/x/net/http2/flow.go +120 -0
  310. slidge_whatsapp/vendor/golang.org/x/net/http2/frame.go +1702 -0
  311. slidge_whatsapp/vendor/golang.org/x/net/http2/gotrack.go +181 -0
  312. slidge_whatsapp/vendor/golang.org/x/net/http2/hpack/encode.go +245 -0
  313. slidge_whatsapp/vendor/golang.org/x/net/http2/hpack/hpack.go +523 -0
  314. slidge_whatsapp/vendor/golang.org/x/net/http2/hpack/huffman.go +226 -0
  315. slidge_whatsapp/vendor/golang.org/x/net/http2/hpack/static_table.go +188 -0
  316. slidge_whatsapp/vendor/golang.org/x/net/http2/hpack/tables.go +403 -0
  317. slidge_whatsapp/vendor/golang.org/x/net/http2/http2.go +410 -0
  318. slidge_whatsapp/vendor/golang.org/x/net/http2/pipe.go +184 -0
  319. slidge_whatsapp/vendor/golang.org/x/net/http2/server.go +3332 -0
  320. slidge_whatsapp/vendor/golang.org/x/net/http2/transport.go +3233 -0
  321. slidge_whatsapp/vendor/golang.org/x/net/http2/unencrypted.go +32 -0
  322. slidge_whatsapp/vendor/golang.org/x/net/http2/write.go +381 -0
  323. slidge_whatsapp/vendor/golang.org/x/net/http2/writesched.go +251 -0
  324. slidge_whatsapp/vendor/golang.org/x/net/http2/writesched_priority.go +451 -0
  325. slidge_whatsapp/vendor/golang.org/x/net/http2/writesched_random.go +77 -0
  326. slidge_whatsapp/vendor/golang.org/x/net/http2/writesched_roundrobin.go +119 -0
  327. slidge_whatsapp/vendor/golang.org/x/net/idna/go118.go +13 -0
  328. slidge_whatsapp/vendor/golang.org/x/net/idna/idna10.0.0.go +769 -0
  329. slidge_whatsapp/vendor/golang.org/x/net/idna/idna9.0.0.go +717 -0
  330. slidge_whatsapp/vendor/golang.org/x/net/idna/pre_go118.go +11 -0
  331. slidge_whatsapp/vendor/golang.org/x/net/idna/punycode.go +217 -0
  332. slidge_whatsapp/vendor/golang.org/x/net/idna/tables10.0.0.go +4559 -0
  333. slidge_whatsapp/vendor/golang.org/x/net/idna/tables11.0.0.go +4653 -0
  334. slidge_whatsapp/vendor/golang.org/x/net/idna/tables12.0.0.go +4733 -0
  335. slidge_whatsapp/vendor/golang.org/x/net/idna/tables13.0.0.go +4959 -0
  336. slidge_whatsapp/vendor/golang.org/x/net/idna/tables15.0.0.go +5144 -0
  337. slidge_whatsapp/vendor/golang.org/x/net/idna/tables9.0.0.go +4486 -0
  338. slidge_whatsapp/vendor/golang.org/x/net/idna/trie.go +51 -0
  339. slidge_whatsapp/vendor/golang.org/x/net/idna/trie12.0.0.go +30 -0
  340. slidge_whatsapp/vendor/golang.org/x/net/idna/trie13.0.0.go +30 -0
  341. slidge_whatsapp/vendor/golang.org/x/net/idna/trieval.go +119 -0
  342. slidge_whatsapp/vendor/golang.org/x/net/internal/httpcommon/ascii.go +53 -0
  343. slidge_whatsapp/vendor/golang.org/x/net/internal/httpcommon/headermap.go +115 -0
  344. slidge_whatsapp/vendor/golang.org/x/net/internal/httpcommon/request.go +467 -0
  345. slidge_whatsapp/vendor/golang.org/x/sys/unix/affinity_linux.go +1 -3
  346. slidge_whatsapp/vendor/golang.org/x/sys/unix/mkerrors.sh +3 -0
  347. slidge_whatsapp/vendor/golang.org/x/sys/unix/syscall_darwin.go +93 -0
  348. slidge_whatsapp/vendor/golang.org/x/sys/unix/syscall_linux.go +16 -26
  349. slidge_whatsapp/vendor/golang.org/x/sys/unix/syscall_solaris.go +1 -1
  350. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux.go +47 -16
  351. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_386.go +3 -0
  352. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_amd64.go +3 -0
  353. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_arm.go +3 -0
  354. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_arm64.go +3 -0
  355. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_loong64.go +3 -0
  356. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_mips.go +3 -0
  357. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_mips64.go +3 -0
  358. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_mips64le.go +3 -0
  359. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_mipsle.go +3 -0
  360. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_ppc.go +3 -0
  361. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64.go +3 -0
  362. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64le.go +3 -0
  363. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_riscv64.go +3 -0
  364. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_s390x.go +3 -0
  365. slidge_whatsapp/vendor/golang.org/x/sys/unix/zerrors_linux_sparc64.go +3 -0
  366. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.go +84 -0
  367. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.s +20 -0
  368. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.go +84 -0
  369. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.s +20 -0
  370. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsyscall_solaris_amd64.go +4 -4
  371. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_386.go +1 -0
  372. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_amd64.go +1 -0
  373. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_arm.go +1 -0
  374. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_arm64.go +1 -0
  375. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_loong64.go +1 -0
  376. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_mips.go +1 -0
  377. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64.go +1 -0
  378. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64le.go +1 -0
  379. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_mipsle.go +1 -0
  380. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc.go +1 -0
  381. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64.go +1 -0
  382. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64le.go +1 -0
  383. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_riscv64.go +1 -0
  384. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_s390x.go +1 -0
  385. slidge_whatsapp/vendor/golang.org/x/sys/unix/zsysnum_linux_sparc64.go +1 -0
  386. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux.go +168 -12
  387. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_386.go +17 -1
  388. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_amd64.go +16 -0
  389. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_arm.go +18 -2
  390. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_arm64.go +16 -0
  391. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_loong64.go +16 -0
  392. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_mips.go +17 -1
  393. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_mips64.go +16 -0
  394. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_mips64le.go +16 -0
  395. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_mipsle.go +17 -1
  396. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_ppc.go +18 -2
  397. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_ppc64.go +16 -0
  398. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_ppc64le.go +16 -0
  399. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_riscv64.go +16 -0
  400. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_s390x.go +16 -0
  401. slidge_whatsapp/vendor/golang.org/x/sys/unix/ztypes_linux_sparc64.go +16 -0
  402. slidge_whatsapp/vendor/golang.org/x/sys/windows/security_windows.go +44 -5
  403. slidge_whatsapp/vendor/golang.org/x/sys/windows/syscall_windows.go +4 -2
  404. slidge_whatsapp/vendor/golang.org/x/sys/windows/types_windows.go +245 -0
  405. slidge_whatsapp/vendor/golang.org/x/sys/windows/zsyscall_windows.go +491 -482
  406. slidge_whatsapp/vendor/golang.org/x/text/LICENSE +27 -0
  407. slidge_whatsapp/vendor/golang.org/x/text/PATENTS +22 -0
  408. slidge_whatsapp/vendor/golang.org/x/text/secure/bidirule/bidirule.go +336 -0
  409. slidge_whatsapp/vendor/golang.org/x/text/secure/bidirule/bidirule10.0.0.go +11 -0
  410. slidge_whatsapp/vendor/golang.org/x/text/secure/bidirule/bidirule9.0.0.go +14 -0
  411. slidge_whatsapp/vendor/golang.org/x/text/transform/transform.go +709 -0
  412. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/bidi.go +359 -0
  413. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/bracket.go +335 -0
  414. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/core.go +1071 -0
  415. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/prop.go +206 -0
  416. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/tables10.0.0.go +1815 -0
  417. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/tables11.0.0.go +1887 -0
  418. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/tables12.0.0.go +1923 -0
  419. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/tables13.0.0.go +1955 -0
  420. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/tables15.0.0.go +2042 -0
  421. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/tables9.0.0.go +1781 -0
  422. slidge_whatsapp/vendor/golang.org/x/text/unicode/bidi/trieval.go +48 -0
  423. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/composition.go +512 -0
  424. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/forminfo.go +279 -0
  425. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/input.go +109 -0
  426. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/iter.go +458 -0
  427. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/normalize.go +610 -0
  428. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/readwriter.go +125 -0
  429. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/tables10.0.0.go +7657 -0
  430. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/tables11.0.0.go +7693 -0
  431. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/tables12.0.0.go +7710 -0
  432. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/tables13.0.0.go +7760 -0
  433. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/tables15.0.0.go +7907 -0
  434. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/tables9.0.0.go +7637 -0
  435. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/transform.go +88 -0
  436. slidge_whatsapp/vendor/golang.org/x/text/unicode/norm/trie.go +54 -0
  437. slidge_whatsapp/vendor/google.golang.org/protobuf/encoding/protowire/wire.go +25 -1
  438. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/editiondefaults/editions_defaults.binpb +0 -0
  439. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/filedesc/editions.go +13 -5
  440. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/filedesc/presence.go +33 -0
  441. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/genid/api_gen.go +6 -0
  442. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/genid/descriptor_gen.go +81 -19
  443. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/impl/codec_message_opaque.go +2 -1
  444. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/impl/message_opaque.go +8 -37
  445. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/impl/presence.go +0 -3
  446. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/strs/{strings_unsafe_go121.go → strings_unsafe.go} +0 -2
  447. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/version/version.go +1 -1
  448. slidge_whatsapp/vendor/google.golang.org/protobuf/proto/merge.go +6 -0
  449. slidge_whatsapp/vendor/google.golang.org/protobuf/reflect/protoreflect/source_gen.go +10 -0
  450. slidge_whatsapp/vendor/google.golang.org/protobuf/reflect/protoreflect/{value_unsafe_go121.go → value_unsafe.go} +0 -2
  451. slidge_whatsapp/vendor/modules.txt +80 -21
  452. {slidge_whatsapp-0.2.5.dist-info → slidge_whatsapp-0.3.0.dist-info}/METADATA +5 -4
  453. {slidge_whatsapp-0.2.5.dist-info → slidge_whatsapp-0.3.0.dist-info}/RECORD +456 -263
  454. {slidge_whatsapp-0.2.5.dist-info → slidge_whatsapp-0.3.0.dist-info}/WHEEL +1 -1
  455. slidge_whatsapp/vendor/github.com/jupiterrider/ffi/abi_amd64.go +0 -7
  456. slidge_whatsapp/vendor/github.com/rs/zerolog/CNAME +0 -1
  457. slidge_whatsapp/vendor/github.com/rs/zerolog/_config.yml +0 -1
  458. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waAdv/WAAdv.pb.raw +0 -0
  459. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waArmadilloApplication/WAArmadilloApplication.pb.raw +0 -0
  460. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waArmadilloXMA/WAArmadilloXMA.pb.raw +0 -0
  461. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCert/WACert.pb.raw +0 -23
  462. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waChatLockSettings/WAProtobufsChatLockSettings.pb.raw +0 -7
  463. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCommon/WACommon.pb.raw +0 -0
  464. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waCompanionReg/WAWebProtobufsCompanionReg.pb.raw +0 -0
  465. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waConsumerApplication/WAConsumerApplication.pb.raw +0 -0
  466. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waDeviceCapabilities/WAProtobufsDeviceCapabilities.pb.raw +0 -0
  467. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waE2E/WAWebProtobufsE2E.pb.raw +0 -0
  468. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waHistorySync/WAWebProtobufsHistorySync.pb.raw +0 -0
  469. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMediaTransport/WAMediaTransport.pb.raw +0 -0
  470. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMmsRetry/WAMmsRetry.pb.raw +0 -0
  471. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMsgApplication/WAMsgApplication.pb.raw +0 -0
  472. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMsgTransport/WAMsgTransport.pb.raw +0 -0
  473. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waMultiDevice/WAMultiDevice.pb.raw +0 -0
  474. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waServerSync/WAServerSync.pb.raw +0 -0
  475. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waSyncAction/WASyncAction.pb.raw +0 -0
  476. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waUserPassword/WAProtobufsUserPassword.pb.raw +0 -0
  477. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waVnameCert/WAWebProtobufsVnameCert.pb.raw +0 -0
  478. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWa6/WAWebProtobufsWa6.pb.raw +0 -0
  479. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/proto/waWeb/WAWebProtobufsWeb.pb.raw +0 -0
  480. slidge_whatsapp/vendor/go.mau.fi/whatsmeow/store/sqlstore/upgrade.go +0 -296
  481. slidge_whatsapp/vendor/google.golang.org/protobuf/internal/strs/strings_unsafe_go120.go +0 -94
  482. slidge_whatsapp/vendor/google.golang.org/protobuf/reflect/protoreflect/value_unsafe_go120.go +0 -98
  483. {slidge_whatsapp-0.2.5.dist-info → slidge_whatsapp-0.3.0.dist-info}/entry_points.txt +0 -0
  484. {slidge_whatsapp-0.2.5.dist-info → slidge_whatsapp-0.3.0.dist-info/licenses}/LICENSE +0 -0
@@ -0,0 +1,3332 @@
1
+ // Copyright 2014 The Go Authors. All rights reserved.
2
+ // Use of this source code is governed by a BSD-style
3
+ // license that can be found in the LICENSE file.
4
+
5
+ // TODO: turn off the serve goroutine when idle, so
6
+ // an idle conn only has the readFrames goroutine active. (which could
7
+ // also be optimized probably to pin less memory in crypto/tls). This
8
+ // would involve tracking when the serve goroutine is active (atomic
9
+ // int32 read/CAS probably?) and starting it up when frames arrive,
10
+ // and shutting it down when all handlers exit. the occasional PING
11
+ // packets could use time.AfterFunc to call sc.wakeStartServeLoop()
12
+ // (which is a no-op if already running) and then queue the PING write
13
+ // as normal. The serve loop would then exit in most cases (if no
14
+ // Handlers running) and not be woken up again until the PING packet
15
+ // returns.
16
+
17
+ // TODO (maybe): add a mechanism for Handlers to going into
18
+ // half-closed-local mode (rw.(io.Closer) test?) but not exit their
19
+ // handler, and continue to be able to read from the
20
+ // Request.Body. This would be a somewhat semantic change from HTTP/1
21
+ // (or at least what we expose in net/http), so I'd probably want to
22
+ // add it there too. For now, this package says that returning from
23
+ // the Handler ServeHTTP function means you're both done reading and
24
+ // done writing, without a way to stop just one or the other.
25
+
26
+ package http2
27
+
28
+ import (
29
+ "bufio"
30
+ "bytes"
31
+ "context"
32
+ "crypto/rand"
33
+ "crypto/tls"
34
+ "errors"
35
+ "fmt"
36
+ "io"
37
+ "log"
38
+ "math"
39
+ "net"
40
+ "net/http"
41
+ "net/textproto"
42
+ "net/url"
43
+ "os"
44
+ "reflect"
45
+ "runtime"
46
+ "strconv"
47
+ "strings"
48
+ "sync"
49
+ "time"
50
+
51
+ "golang.org/x/net/http/httpguts"
52
+ "golang.org/x/net/http2/hpack"
53
+ "golang.org/x/net/internal/httpcommon"
54
+ )
55
+
56
+ const (
57
+ prefaceTimeout = 10 * time.Second
58
+ firstSettingsTimeout = 2 * time.Second // should be in-flight with preface anyway
59
+ handlerChunkWriteSize = 4 << 10
60
+ defaultMaxStreams = 250 // TODO: make this 100 as the GFE seems to?
61
+
62
+ // maxQueuedControlFrames is the maximum number of control frames like
63
+ // SETTINGS, PING and RST_STREAM that will be queued for writing before
64
+ // the connection is closed to prevent memory exhaustion attacks.
65
+ maxQueuedControlFrames = 10000
66
+ )
67
+
68
+ var (
69
+ errClientDisconnected = errors.New("client disconnected")
70
+ errClosedBody = errors.New("body closed by handler")
71
+ errHandlerComplete = errors.New("http2: request body closed due to handler exiting")
72
+ errStreamClosed = errors.New("http2: stream closed")
73
+ )
74
+
75
+ var responseWriterStatePool = sync.Pool{
76
+ New: func() interface{} {
77
+ rws := &responseWriterState{}
78
+ rws.bw = bufio.NewWriterSize(chunkWriter{rws}, handlerChunkWriteSize)
79
+ return rws
80
+ },
81
+ }
82
+
83
+ // Test hooks.
84
+ var (
85
+ testHookOnConn func()
86
+ testHookGetServerConn func(*serverConn)
87
+ testHookOnPanicMu *sync.Mutex // nil except in tests
88
+ testHookOnPanic func(sc *serverConn, panicVal interface{}) (rePanic bool)
89
+ )
90
+
91
+ // Server is an HTTP/2 server.
92
+ type Server struct {
93
+ // MaxHandlers limits the number of http.Handler ServeHTTP goroutines
94
+ // which may run at a time over all connections.
95
+ // Negative or zero no limit.
96
+ // TODO: implement
97
+ MaxHandlers int
98
+
99
+ // MaxConcurrentStreams optionally specifies the number of
100
+ // concurrent streams that each client may have open at a
101
+ // time. This is unrelated to the number of http.Handler goroutines
102
+ // which may be active globally, which is MaxHandlers.
103
+ // If zero, MaxConcurrentStreams defaults to at least 100, per
104
+ // the HTTP/2 spec's recommendations.
105
+ MaxConcurrentStreams uint32
106
+
107
+ // MaxDecoderHeaderTableSize optionally specifies the http2
108
+ // SETTINGS_HEADER_TABLE_SIZE to send in the initial settings frame. It
109
+ // informs the remote endpoint of the maximum size of the header compression
110
+ // table used to decode header blocks, in octets. If zero, the default value
111
+ // of 4096 is used.
112
+ MaxDecoderHeaderTableSize uint32
113
+
114
+ // MaxEncoderHeaderTableSize optionally specifies an upper limit for the
115
+ // header compression table used for encoding request headers. Received
116
+ // SETTINGS_HEADER_TABLE_SIZE settings are capped at this limit. If zero,
117
+ // the default value of 4096 is used.
118
+ MaxEncoderHeaderTableSize uint32
119
+
120
+ // MaxReadFrameSize optionally specifies the largest frame
121
+ // this server is willing to read. A valid value is between
122
+ // 16k and 16M, inclusive. If zero or otherwise invalid, a
123
+ // default value is used.
124
+ MaxReadFrameSize uint32
125
+
126
+ // PermitProhibitedCipherSuites, if true, permits the use of
127
+ // cipher suites prohibited by the HTTP/2 spec.
128
+ PermitProhibitedCipherSuites bool
129
+
130
+ // IdleTimeout specifies how long until idle clients should be
131
+ // closed with a GOAWAY frame. PING frames are not considered
132
+ // activity for the purposes of IdleTimeout.
133
+ // If zero or negative, there is no timeout.
134
+ IdleTimeout time.Duration
135
+
136
+ // ReadIdleTimeout is the timeout after which a health check using a ping
137
+ // frame will be carried out if no frame is received on the connection.
138
+ // If zero, no health check is performed.
139
+ ReadIdleTimeout time.Duration
140
+
141
+ // PingTimeout is the timeout after which the connection will be closed
142
+ // if a response to a ping is not received.
143
+ // If zero, a default of 15 seconds is used.
144
+ PingTimeout time.Duration
145
+
146
+ // WriteByteTimeout is the timeout after which a connection will be
147
+ // closed if no data can be written to it. The timeout begins when data is
148
+ // available to write, and is extended whenever any bytes are written.
149
+ // If zero or negative, there is no timeout.
150
+ WriteByteTimeout time.Duration
151
+
152
+ // MaxUploadBufferPerConnection is the size of the initial flow
153
+ // control window for each connections. The HTTP/2 spec does not
154
+ // allow this to be smaller than 65535 or larger than 2^32-1.
155
+ // If the value is outside this range, a default value will be
156
+ // used instead.
157
+ MaxUploadBufferPerConnection int32
158
+
159
+ // MaxUploadBufferPerStream is the size of the initial flow control
160
+ // window for each stream. The HTTP/2 spec does not allow this to
161
+ // be larger than 2^32-1. If the value is zero or larger than the
162
+ // maximum, a default value will be used instead.
163
+ MaxUploadBufferPerStream int32
164
+
165
+ // NewWriteScheduler constructs a write scheduler for a connection.
166
+ // If nil, a default scheduler is chosen.
167
+ NewWriteScheduler func() WriteScheduler
168
+
169
+ // CountError, if non-nil, is called on HTTP/2 server errors.
170
+ // It's intended to increment a metric for monitoring, such
171
+ // as an expvar or Prometheus metric.
172
+ // The errType consists of only ASCII word characters.
173
+ CountError func(errType string)
174
+
175
+ // Internal state. This is a pointer (rather than embedded directly)
176
+ // so that we don't embed a Mutex in this struct, which will make the
177
+ // struct non-copyable, which might break some callers.
178
+ state *serverInternalState
179
+ }
180
+
181
+ type serverInternalState struct {
182
+ mu sync.Mutex
183
+ activeConns map[*serverConn]struct{}
184
+ }
185
+
186
+ func (s *serverInternalState) registerConn(sc *serverConn) {
187
+ if s == nil {
188
+ return // if the Server was used without calling ConfigureServer
189
+ }
190
+ s.mu.Lock()
191
+ s.activeConns[sc] = struct{}{}
192
+ s.mu.Unlock()
193
+ }
194
+
195
+ func (s *serverInternalState) unregisterConn(sc *serverConn) {
196
+ if s == nil {
197
+ return // if the Server was used without calling ConfigureServer
198
+ }
199
+ s.mu.Lock()
200
+ delete(s.activeConns, sc)
201
+ s.mu.Unlock()
202
+ }
203
+
204
+ func (s *serverInternalState) startGracefulShutdown() {
205
+ if s == nil {
206
+ return // if the Server was used without calling ConfigureServer
207
+ }
208
+ s.mu.Lock()
209
+ for sc := range s.activeConns {
210
+ sc.startGracefulShutdown()
211
+ }
212
+ s.mu.Unlock()
213
+ }
214
+
215
+ // ConfigureServer adds HTTP/2 support to a net/http Server.
216
+ //
217
+ // The configuration conf may be nil.
218
+ //
219
+ // ConfigureServer must be called before s begins serving.
220
+ func ConfigureServer(s *http.Server, conf *Server) error {
221
+ if s == nil {
222
+ panic("nil *http.Server")
223
+ }
224
+ if conf == nil {
225
+ conf = new(Server)
226
+ }
227
+ conf.state = &serverInternalState{activeConns: make(map[*serverConn]struct{})}
228
+ if h1, h2 := s, conf; h2.IdleTimeout == 0 {
229
+ if h1.IdleTimeout != 0 {
230
+ h2.IdleTimeout = h1.IdleTimeout
231
+ } else {
232
+ h2.IdleTimeout = h1.ReadTimeout
233
+ }
234
+ }
235
+ s.RegisterOnShutdown(conf.state.startGracefulShutdown)
236
+
237
+ if s.TLSConfig == nil {
238
+ s.TLSConfig = new(tls.Config)
239
+ } else if s.TLSConfig.CipherSuites != nil && s.TLSConfig.MinVersion < tls.VersionTLS13 {
240
+ // If they already provided a TLS 1.0–1.2 CipherSuite list, return an
241
+ // error if it is missing ECDHE_RSA_WITH_AES_128_GCM_SHA256 or
242
+ // ECDHE_ECDSA_WITH_AES_128_GCM_SHA256.
243
+ haveRequired := false
244
+ for _, cs := range s.TLSConfig.CipherSuites {
245
+ switch cs {
246
+ case tls.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,
247
+ // Alternative MTI cipher to not discourage ECDSA-only servers.
248
+ // See http://golang.org/cl/30721 for further information.
249
+ tls.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256:
250
+ haveRequired = true
251
+ }
252
+ }
253
+ if !haveRequired {
254
+ return fmt.Errorf("http2: TLSConfig.CipherSuites is missing an HTTP/2-required AES_128_GCM_SHA256 cipher (need at least one of TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 or TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256)")
255
+ }
256
+ }
257
+
258
+ // Note: not setting MinVersion to tls.VersionTLS12,
259
+ // as we don't want to interfere with HTTP/1.1 traffic
260
+ // on the user's server. We enforce TLS 1.2 later once
261
+ // we accept a connection. Ideally this should be done
262
+ // during next-proto selection, but using TLS <1.2 with
263
+ // HTTP/2 is still the client's bug.
264
+
265
+ s.TLSConfig.PreferServerCipherSuites = true
266
+
267
+ if !strSliceContains(s.TLSConfig.NextProtos, NextProtoTLS) {
268
+ s.TLSConfig.NextProtos = append(s.TLSConfig.NextProtos, NextProtoTLS)
269
+ }
270
+ if !strSliceContains(s.TLSConfig.NextProtos, "http/1.1") {
271
+ s.TLSConfig.NextProtos = append(s.TLSConfig.NextProtos, "http/1.1")
272
+ }
273
+
274
+ if s.TLSNextProto == nil {
275
+ s.TLSNextProto = map[string]func(*http.Server, *tls.Conn, http.Handler){}
276
+ }
277
+ protoHandler := func(hs *http.Server, c net.Conn, h http.Handler, sawClientPreface bool) {
278
+ if testHookOnConn != nil {
279
+ testHookOnConn()
280
+ }
281
+ // The TLSNextProto interface predates contexts, so
282
+ // the net/http package passes down its per-connection
283
+ // base context via an exported but unadvertised
284
+ // method on the Handler. This is for internal
285
+ // net/http<=>http2 use only.
286
+ var ctx context.Context
287
+ type baseContexter interface {
288
+ BaseContext() context.Context
289
+ }
290
+ if bc, ok := h.(baseContexter); ok {
291
+ ctx = bc.BaseContext()
292
+ }
293
+ conf.ServeConn(c, &ServeConnOpts{
294
+ Context: ctx,
295
+ Handler: h,
296
+ BaseConfig: hs,
297
+ SawClientPreface: sawClientPreface,
298
+ })
299
+ }
300
+ s.TLSNextProto[NextProtoTLS] = func(hs *http.Server, c *tls.Conn, h http.Handler) {
301
+ protoHandler(hs, c, h, false)
302
+ }
303
+ // The "unencrypted_http2" TLSNextProto key is used to pass off non-TLS HTTP/2 conns.
304
+ //
305
+ // A connection passed in this method has already had the HTTP/2 preface read from it.
306
+ s.TLSNextProto[nextProtoUnencryptedHTTP2] = func(hs *http.Server, c *tls.Conn, h http.Handler) {
307
+ nc, err := unencryptedNetConnFromTLSConn(c)
308
+ if err != nil {
309
+ if lg := hs.ErrorLog; lg != nil {
310
+ lg.Print(err)
311
+ } else {
312
+ log.Print(err)
313
+ }
314
+ go c.Close()
315
+ return
316
+ }
317
+ protoHandler(hs, nc, h, true)
318
+ }
319
+ return nil
320
+ }
321
+
322
+ // ServeConnOpts are options for the Server.ServeConn method.
323
+ type ServeConnOpts struct {
324
+ // Context is the base context to use.
325
+ // If nil, context.Background is used.
326
+ Context context.Context
327
+
328
+ // BaseConfig optionally sets the base configuration
329
+ // for values. If nil, defaults are used.
330
+ BaseConfig *http.Server
331
+
332
+ // Handler specifies which handler to use for processing
333
+ // requests. If nil, BaseConfig.Handler is used. If BaseConfig
334
+ // or BaseConfig.Handler is nil, http.DefaultServeMux is used.
335
+ Handler http.Handler
336
+
337
+ // UpgradeRequest is an initial request received on a connection
338
+ // undergoing an h2c upgrade. The request body must have been
339
+ // completely read from the connection before calling ServeConn,
340
+ // and the 101 Switching Protocols response written.
341
+ UpgradeRequest *http.Request
342
+
343
+ // Settings is the decoded contents of the HTTP2-Settings header
344
+ // in an h2c upgrade request.
345
+ Settings []byte
346
+
347
+ // SawClientPreface is set if the HTTP/2 connection preface
348
+ // has already been read from the connection.
349
+ SawClientPreface bool
350
+ }
351
+
352
+ func (o *ServeConnOpts) context() context.Context {
353
+ if o != nil && o.Context != nil {
354
+ return o.Context
355
+ }
356
+ return context.Background()
357
+ }
358
+
359
+ func (o *ServeConnOpts) baseConfig() *http.Server {
360
+ if o != nil && o.BaseConfig != nil {
361
+ return o.BaseConfig
362
+ }
363
+ return new(http.Server)
364
+ }
365
+
366
+ func (o *ServeConnOpts) handler() http.Handler {
367
+ if o != nil {
368
+ if o.Handler != nil {
369
+ return o.Handler
370
+ }
371
+ if o.BaseConfig != nil && o.BaseConfig.Handler != nil {
372
+ return o.BaseConfig.Handler
373
+ }
374
+ }
375
+ return http.DefaultServeMux
376
+ }
377
+
378
+ // ServeConn serves HTTP/2 requests on the provided connection and
379
+ // blocks until the connection is no longer readable.
380
+ //
381
+ // ServeConn starts speaking HTTP/2 assuming that c has not had any
382
+ // reads or writes. It writes its initial settings frame and expects
383
+ // to be able to read the preface and settings frame from the
384
+ // client. If c has a ConnectionState method like a *tls.Conn, the
385
+ // ConnectionState is used to verify the TLS ciphersuite and to set
386
+ // the Request.TLS field in Handlers.
387
+ //
388
+ // ServeConn does not support h2c by itself. Any h2c support must be
389
+ // implemented in terms of providing a suitably-behaving net.Conn.
390
+ //
391
+ // The opts parameter is optional. If nil, default values are used.
392
+ func (s *Server) ServeConn(c net.Conn, opts *ServeConnOpts) {
393
+ if opts == nil {
394
+ opts = &ServeConnOpts{}
395
+ }
396
+ s.serveConn(c, opts, nil)
397
+ }
398
+
399
+ func (s *Server) serveConn(c net.Conn, opts *ServeConnOpts, newf func(*serverConn)) {
400
+ baseCtx, cancel := serverConnBaseContext(c, opts)
401
+ defer cancel()
402
+
403
+ http1srv := opts.baseConfig()
404
+ conf := configFromServer(http1srv, s)
405
+ sc := &serverConn{
406
+ srv: s,
407
+ hs: http1srv,
408
+ conn: c,
409
+ baseCtx: baseCtx,
410
+ remoteAddrStr: c.RemoteAddr().String(),
411
+ bw: newBufferedWriter(c, conf.WriteByteTimeout),
412
+ handler: opts.handler(),
413
+ streams: make(map[uint32]*stream),
414
+ readFrameCh: make(chan readFrameResult),
415
+ wantWriteFrameCh: make(chan FrameWriteRequest, 8),
416
+ serveMsgCh: make(chan interface{}, 8),
417
+ wroteFrameCh: make(chan frameWriteResult, 1), // buffered; one send in writeFrameAsync
418
+ bodyReadCh: make(chan bodyReadMsg), // buffering doesn't matter either way
419
+ doneServing: make(chan struct{}),
420
+ clientMaxStreams: math.MaxUint32, // Section 6.5.2: "Initially, there is no limit to this value"
421
+ advMaxStreams: conf.MaxConcurrentStreams,
422
+ initialStreamSendWindowSize: initialWindowSize,
423
+ initialStreamRecvWindowSize: conf.MaxUploadBufferPerStream,
424
+ maxFrameSize: initialMaxFrameSize,
425
+ pingTimeout: conf.PingTimeout,
426
+ countErrorFunc: conf.CountError,
427
+ serveG: newGoroutineLock(),
428
+ pushEnabled: true,
429
+ sawClientPreface: opts.SawClientPreface,
430
+ }
431
+ if newf != nil {
432
+ newf(sc)
433
+ }
434
+
435
+ s.state.registerConn(sc)
436
+ defer s.state.unregisterConn(sc)
437
+
438
+ // The net/http package sets the write deadline from the
439
+ // http.Server.WriteTimeout during the TLS handshake, but then
440
+ // passes the connection off to us with the deadline already set.
441
+ // Write deadlines are set per stream in serverConn.newStream.
442
+ // Disarm the net.Conn write deadline here.
443
+ if sc.hs.WriteTimeout > 0 {
444
+ sc.conn.SetWriteDeadline(time.Time{})
445
+ }
446
+
447
+ if s.NewWriteScheduler != nil {
448
+ sc.writeSched = s.NewWriteScheduler()
449
+ } else {
450
+ sc.writeSched = newRoundRobinWriteScheduler()
451
+ }
452
+
453
+ // These start at the RFC-specified defaults. If there is a higher
454
+ // configured value for inflow, that will be updated when we send a
455
+ // WINDOW_UPDATE shortly after sending SETTINGS.
456
+ sc.flow.add(initialWindowSize)
457
+ sc.inflow.init(initialWindowSize)
458
+ sc.hpackEncoder = hpack.NewEncoder(&sc.headerWriteBuf)
459
+ sc.hpackEncoder.SetMaxDynamicTableSizeLimit(conf.MaxEncoderHeaderTableSize)
460
+
461
+ fr := NewFramer(sc.bw, c)
462
+ if conf.CountError != nil {
463
+ fr.countError = conf.CountError
464
+ }
465
+ fr.ReadMetaHeaders = hpack.NewDecoder(conf.MaxDecoderHeaderTableSize, nil)
466
+ fr.MaxHeaderListSize = sc.maxHeaderListSize()
467
+ fr.SetMaxReadFrameSize(conf.MaxReadFrameSize)
468
+ sc.framer = fr
469
+
470
+ if tc, ok := c.(connectionStater); ok {
471
+ sc.tlsState = new(tls.ConnectionState)
472
+ *sc.tlsState = tc.ConnectionState()
473
+ // 9.2 Use of TLS Features
474
+ // An implementation of HTTP/2 over TLS MUST use TLS
475
+ // 1.2 or higher with the restrictions on feature set
476
+ // and cipher suite described in this section. Due to
477
+ // implementation limitations, it might not be
478
+ // possible to fail TLS negotiation. An endpoint MUST
479
+ // immediately terminate an HTTP/2 connection that
480
+ // does not meet the TLS requirements described in
481
+ // this section with a connection error (Section
482
+ // 5.4.1) of type INADEQUATE_SECURITY.
483
+ if sc.tlsState.Version < tls.VersionTLS12 {
484
+ sc.rejectConn(ErrCodeInadequateSecurity, "TLS version too low")
485
+ return
486
+ }
487
+
488
+ if sc.tlsState.ServerName == "" {
489
+ // Client must use SNI, but we don't enforce that anymore,
490
+ // since it was causing problems when connecting to bare IP
491
+ // addresses during development.
492
+ //
493
+ // TODO: optionally enforce? Or enforce at the time we receive
494
+ // a new request, and verify the ServerName matches the :authority?
495
+ // But that precludes proxy situations, perhaps.
496
+ //
497
+ // So for now, do nothing here again.
498
+ }
499
+
500
+ if !conf.PermitProhibitedCipherSuites && isBadCipher(sc.tlsState.CipherSuite) {
501
+ // "Endpoints MAY choose to generate a connection error
502
+ // (Section 5.4.1) of type INADEQUATE_SECURITY if one of
503
+ // the prohibited cipher suites are negotiated."
504
+ //
505
+ // We choose that. In my opinion, the spec is weak
506
+ // here. It also says both parties must support at least
507
+ // TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 so there's no
508
+ // excuses here. If we really must, we could allow an
509
+ // "AllowInsecureWeakCiphers" option on the server later.
510
+ // Let's see how it plays out first.
511
+ sc.rejectConn(ErrCodeInadequateSecurity, fmt.Sprintf("Prohibited TLS 1.2 Cipher Suite: %x", sc.tlsState.CipherSuite))
512
+ return
513
+ }
514
+ }
515
+
516
+ if opts.Settings != nil {
517
+ fr := &SettingsFrame{
518
+ FrameHeader: FrameHeader{valid: true},
519
+ p: opts.Settings,
520
+ }
521
+ if err := fr.ForeachSetting(sc.processSetting); err != nil {
522
+ sc.rejectConn(ErrCodeProtocol, "invalid settings")
523
+ return
524
+ }
525
+ opts.Settings = nil
526
+ }
527
+
528
+ if hook := testHookGetServerConn; hook != nil {
529
+ hook(sc)
530
+ }
531
+
532
+ if opts.UpgradeRequest != nil {
533
+ sc.upgradeRequest(opts.UpgradeRequest)
534
+ opts.UpgradeRequest = nil
535
+ }
536
+
537
+ sc.serve(conf)
538
+ }
539
+
540
+ func serverConnBaseContext(c net.Conn, opts *ServeConnOpts) (ctx context.Context, cancel func()) {
541
+ ctx, cancel = context.WithCancel(opts.context())
542
+ ctx = context.WithValue(ctx, http.LocalAddrContextKey, c.LocalAddr())
543
+ if hs := opts.baseConfig(); hs != nil {
544
+ ctx = context.WithValue(ctx, http.ServerContextKey, hs)
545
+ }
546
+ return
547
+ }
548
+
549
+ func (sc *serverConn) rejectConn(err ErrCode, debug string) {
550
+ sc.vlogf("http2: server rejecting conn: %v, %s", err, debug)
551
+ // ignoring errors. hanging up anyway.
552
+ sc.framer.WriteGoAway(0, err, []byte(debug))
553
+ sc.bw.Flush()
554
+ sc.conn.Close()
555
+ }
556
+
557
+ type serverConn struct {
558
+ // Immutable:
559
+ srv *Server
560
+ hs *http.Server
561
+ conn net.Conn
562
+ bw *bufferedWriter // writing to conn
563
+ handler http.Handler
564
+ baseCtx context.Context
565
+ framer *Framer
566
+ doneServing chan struct{} // closed when serverConn.serve ends
567
+ readFrameCh chan readFrameResult // written by serverConn.readFrames
568
+ wantWriteFrameCh chan FrameWriteRequest // from handlers -> serve
569
+ wroteFrameCh chan frameWriteResult // from writeFrameAsync -> serve, tickles more frame writes
570
+ bodyReadCh chan bodyReadMsg // from handlers -> serve
571
+ serveMsgCh chan interface{} // misc messages & code to send to / run on the serve loop
572
+ flow outflow // conn-wide (not stream-specific) outbound flow control
573
+ inflow inflow // conn-wide inbound flow control
574
+ tlsState *tls.ConnectionState // shared by all handlers, like net/http
575
+ remoteAddrStr string
576
+ writeSched WriteScheduler
577
+ countErrorFunc func(errType string)
578
+
579
+ // Everything following is owned by the serve loop; use serveG.check():
580
+ serveG goroutineLock // used to verify funcs are on serve()
581
+ pushEnabled bool
582
+ sawClientPreface bool // preface has already been read, used in h2c upgrade
583
+ sawFirstSettings bool // got the initial SETTINGS frame after the preface
584
+ needToSendSettingsAck bool
585
+ unackedSettings int // how many SETTINGS have we sent without ACKs?
586
+ queuedControlFrames int // control frames in the writeSched queue
587
+ clientMaxStreams uint32 // SETTINGS_MAX_CONCURRENT_STREAMS from client (our PUSH_PROMISE limit)
588
+ advMaxStreams uint32 // our SETTINGS_MAX_CONCURRENT_STREAMS advertised the client
589
+ curClientStreams uint32 // number of open streams initiated by the client
590
+ curPushedStreams uint32 // number of open streams initiated by server push
591
+ curHandlers uint32 // number of running handler goroutines
592
+ maxClientStreamID uint32 // max ever seen from client (odd), or 0 if there have been no client requests
593
+ maxPushPromiseID uint32 // ID of the last push promise (even), or 0 if there have been no pushes
594
+ streams map[uint32]*stream
595
+ unstartedHandlers []unstartedHandler
596
+ initialStreamSendWindowSize int32
597
+ initialStreamRecvWindowSize int32
598
+ maxFrameSize int32
599
+ peerMaxHeaderListSize uint32 // zero means unknown (default)
600
+ canonHeader map[string]string // http2-lower-case -> Go-Canonical-Case
601
+ canonHeaderKeysSize int // canonHeader keys size in bytes
602
+ writingFrame bool // started writing a frame (on serve goroutine or separate)
603
+ writingFrameAsync bool // started a frame on its own goroutine but haven't heard back on wroteFrameCh
604
+ needsFrameFlush bool // last frame write wasn't a flush
605
+ inGoAway bool // we've started to or sent GOAWAY
606
+ inFrameScheduleLoop bool // whether we're in the scheduleFrameWrite loop
607
+ needToSendGoAway bool // we need to schedule a GOAWAY frame write
608
+ pingSent bool
609
+ sentPingData [8]byte
610
+ goAwayCode ErrCode
611
+ shutdownTimer *time.Timer // nil until used
612
+ idleTimer *time.Timer // nil if unused
613
+ readIdleTimeout time.Duration
614
+ pingTimeout time.Duration
615
+ readIdleTimer *time.Timer // nil if unused
616
+
617
+ // Owned by the writeFrameAsync goroutine:
618
+ headerWriteBuf bytes.Buffer
619
+ hpackEncoder *hpack.Encoder
620
+
621
+ // Used by startGracefulShutdown.
622
+ shutdownOnce sync.Once
623
+ }
624
+
625
+ func (sc *serverConn) maxHeaderListSize() uint32 {
626
+ n := sc.hs.MaxHeaderBytes
627
+ if n <= 0 {
628
+ n = http.DefaultMaxHeaderBytes
629
+ }
630
+ return uint32(adjustHTTP1MaxHeaderSize(int64(n)))
631
+ }
632
+
633
+ func (sc *serverConn) curOpenStreams() uint32 {
634
+ sc.serveG.check()
635
+ return sc.curClientStreams + sc.curPushedStreams
636
+ }
637
+
638
+ // stream represents a stream. This is the minimal metadata needed by
639
+ // the serve goroutine. Most of the actual stream state is owned by
640
+ // the http.Handler's goroutine in the responseWriter. Because the
641
+ // responseWriter's responseWriterState is recycled at the end of a
642
+ // handler, this struct intentionally has no pointer to the
643
+ // *responseWriter{,State} itself, as the Handler ending nils out the
644
+ // responseWriter's state field.
645
+ type stream struct {
646
+ // immutable:
647
+ sc *serverConn
648
+ id uint32
649
+ body *pipe // non-nil if expecting DATA frames
650
+ cw closeWaiter // closed wait stream transitions to closed state
651
+ ctx context.Context
652
+ cancelCtx func()
653
+
654
+ // owned by serverConn's serve loop:
655
+ bodyBytes int64 // body bytes seen so far
656
+ declBodyBytes int64 // or -1 if undeclared
657
+ flow outflow // limits writing from Handler to client
658
+ inflow inflow // what the client is allowed to POST/etc to us
659
+ state streamState
660
+ resetQueued bool // RST_STREAM queued for write; set by sc.resetStream
661
+ gotTrailerHeader bool // HEADER frame for trailers was seen
662
+ wroteHeaders bool // whether we wrote headers (not status 100)
663
+ readDeadline *time.Timer // nil if unused
664
+ writeDeadline *time.Timer // nil if unused
665
+ closeErr error // set before cw is closed
666
+
667
+ trailer http.Header // accumulated trailers
668
+ reqTrailer http.Header // handler's Request.Trailer
669
+ }
670
+
671
+ func (sc *serverConn) Framer() *Framer { return sc.framer }
672
+ func (sc *serverConn) CloseConn() error { return sc.conn.Close() }
673
+ func (sc *serverConn) Flush() error { return sc.bw.Flush() }
674
+ func (sc *serverConn) HeaderEncoder() (*hpack.Encoder, *bytes.Buffer) {
675
+ return sc.hpackEncoder, &sc.headerWriteBuf
676
+ }
677
+
678
+ func (sc *serverConn) state(streamID uint32) (streamState, *stream) {
679
+ sc.serveG.check()
680
+ // http://tools.ietf.org/html/rfc7540#section-5.1
681
+ if st, ok := sc.streams[streamID]; ok {
682
+ return st.state, st
683
+ }
684
+ // "The first use of a new stream identifier implicitly closes all
685
+ // streams in the "idle" state that might have been initiated by
686
+ // that peer with a lower-valued stream identifier. For example, if
687
+ // a client sends a HEADERS frame on stream 7 without ever sending a
688
+ // frame on stream 5, then stream 5 transitions to the "closed"
689
+ // state when the first frame for stream 7 is sent or received."
690
+ if streamID%2 == 1 {
691
+ if streamID <= sc.maxClientStreamID {
692
+ return stateClosed, nil
693
+ }
694
+ } else {
695
+ if streamID <= sc.maxPushPromiseID {
696
+ return stateClosed, nil
697
+ }
698
+ }
699
+ return stateIdle, nil
700
+ }
701
+
702
+ // setConnState calls the net/http ConnState hook for this connection, if configured.
703
+ // Note that the net/http package does StateNew and StateClosed for us.
704
+ // There is currently no plan for StateHijacked or hijacking HTTP/2 connections.
705
+ func (sc *serverConn) setConnState(state http.ConnState) {
706
+ if sc.hs.ConnState != nil {
707
+ sc.hs.ConnState(sc.conn, state)
708
+ }
709
+ }
710
+
711
+ func (sc *serverConn) vlogf(format string, args ...interface{}) {
712
+ if VerboseLogs {
713
+ sc.logf(format, args...)
714
+ }
715
+ }
716
+
717
+ func (sc *serverConn) logf(format string, args ...interface{}) {
718
+ if lg := sc.hs.ErrorLog; lg != nil {
719
+ lg.Printf(format, args...)
720
+ } else {
721
+ log.Printf(format, args...)
722
+ }
723
+ }
724
+
725
+ // errno returns v's underlying uintptr, else 0.
726
+ //
727
+ // TODO: remove this helper function once http2 can use build
728
+ // tags. See comment in isClosedConnError.
729
+ func errno(v error) uintptr {
730
+ if rv := reflect.ValueOf(v); rv.Kind() == reflect.Uintptr {
731
+ return uintptr(rv.Uint())
732
+ }
733
+ return 0
734
+ }
735
+
736
+ // isClosedConnError reports whether err is an error from use of a closed
737
+ // network connection.
738
+ func isClosedConnError(err error) bool {
739
+ if err == nil {
740
+ return false
741
+ }
742
+
743
+ if errors.Is(err, net.ErrClosed) {
744
+ return true
745
+ }
746
+
747
+ // TODO(bradfitz): x/tools/cmd/bundle doesn't really support
748
+ // build tags, so I can't make an http2_windows.go file with
749
+ // Windows-specific stuff. Fix that and move this, once we
750
+ // have a way to bundle this into std's net/http somehow.
751
+ if runtime.GOOS == "windows" {
752
+ if oe, ok := err.(*net.OpError); ok && oe.Op == "read" {
753
+ if se, ok := oe.Err.(*os.SyscallError); ok && se.Syscall == "wsarecv" {
754
+ const WSAECONNABORTED = 10053
755
+ const WSAECONNRESET = 10054
756
+ if n := errno(se.Err); n == WSAECONNRESET || n == WSAECONNABORTED {
757
+ return true
758
+ }
759
+ }
760
+ }
761
+ }
762
+ return false
763
+ }
764
+
765
+ func (sc *serverConn) condlogf(err error, format string, args ...interface{}) {
766
+ if err == nil {
767
+ return
768
+ }
769
+ if err == io.EOF || err == io.ErrUnexpectedEOF || isClosedConnError(err) || err == errPrefaceTimeout {
770
+ // Boring, expected errors.
771
+ sc.vlogf(format, args...)
772
+ } else {
773
+ sc.logf(format, args...)
774
+ }
775
+ }
776
+
777
+ // maxCachedCanonicalHeadersKeysSize is an arbitrarily-chosen limit on the size
778
+ // of the entries in the canonHeader cache.
779
+ // This should be larger than the size of unique, uncommon header keys likely to
780
+ // be sent by the peer, while not so high as to permit unreasonable memory usage
781
+ // if the peer sends an unbounded number of unique header keys.
782
+ const maxCachedCanonicalHeadersKeysSize = 2048
783
+
784
+ func (sc *serverConn) canonicalHeader(v string) string {
785
+ sc.serveG.check()
786
+ cv, ok := httpcommon.CachedCanonicalHeader(v)
787
+ if ok {
788
+ return cv
789
+ }
790
+ cv, ok = sc.canonHeader[v]
791
+ if ok {
792
+ return cv
793
+ }
794
+ if sc.canonHeader == nil {
795
+ sc.canonHeader = make(map[string]string)
796
+ }
797
+ cv = http.CanonicalHeaderKey(v)
798
+ size := 100 + len(v)*2 // 100 bytes of map overhead + key + value
799
+ if sc.canonHeaderKeysSize+size <= maxCachedCanonicalHeadersKeysSize {
800
+ sc.canonHeader[v] = cv
801
+ sc.canonHeaderKeysSize += size
802
+ }
803
+ return cv
804
+ }
805
+
806
+ type readFrameResult struct {
807
+ f Frame // valid until readMore is called
808
+ err error
809
+
810
+ // readMore should be called once the consumer no longer needs or
811
+ // retains f. After readMore, f is invalid and more frames can be
812
+ // read.
813
+ readMore func()
814
+ }
815
+
816
+ // readFrames is the loop that reads incoming frames.
817
+ // It takes care to only read one frame at a time, blocking until the
818
+ // consumer is done with the frame.
819
+ // It's run on its own goroutine.
820
+ func (sc *serverConn) readFrames() {
821
+ gate := make(chan struct{})
822
+ gateDone := func() { gate <- struct{}{} }
823
+ for {
824
+ f, err := sc.framer.ReadFrame()
825
+ select {
826
+ case sc.readFrameCh <- readFrameResult{f, err, gateDone}:
827
+ case <-sc.doneServing:
828
+ return
829
+ }
830
+ select {
831
+ case <-gate:
832
+ case <-sc.doneServing:
833
+ return
834
+ }
835
+ if terminalReadFrameError(err) {
836
+ return
837
+ }
838
+ }
839
+ }
840
+
841
+ // frameWriteResult is the message passed from writeFrameAsync to the serve goroutine.
842
+ type frameWriteResult struct {
843
+ _ incomparable
844
+ wr FrameWriteRequest // what was written (or attempted)
845
+ err error // result of the writeFrame call
846
+ }
847
+
848
+ // writeFrameAsync runs in its own goroutine and writes a single frame
849
+ // and then reports when it's done.
850
+ // At most one goroutine can be running writeFrameAsync at a time per
851
+ // serverConn.
852
+ func (sc *serverConn) writeFrameAsync(wr FrameWriteRequest, wd *writeData) {
853
+ var err error
854
+ if wd == nil {
855
+ err = wr.write.writeFrame(sc)
856
+ } else {
857
+ err = sc.framer.endWrite()
858
+ }
859
+ sc.wroteFrameCh <- frameWriteResult{wr: wr, err: err}
860
+ }
861
+
862
+ func (sc *serverConn) closeAllStreamsOnConnClose() {
863
+ sc.serveG.check()
864
+ for _, st := range sc.streams {
865
+ sc.closeStream(st, errClientDisconnected)
866
+ }
867
+ }
868
+
869
+ func (sc *serverConn) stopShutdownTimer() {
870
+ sc.serveG.check()
871
+ if t := sc.shutdownTimer; t != nil {
872
+ t.Stop()
873
+ }
874
+ }
875
+
876
+ func (sc *serverConn) notePanic() {
877
+ // Note: this is for serverConn.serve panicking, not http.Handler code.
878
+ if testHookOnPanicMu != nil {
879
+ testHookOnPanicMu.Lock()
880
+ defer testHookOnPanicMu.Unlock()
881
+ }
882
+ if testHookOnPanic != nil {
883
+ if e := recover(); e != nil {
884
+ if testHookOnPanic(sc, e) {
885
+ panic(e)
886
+ }
887
+ }
888
+ }
889
+ }
890
+
891
+ func (sc *serverConn) serve(conf http2Config) {
892
+ sc.serveG.check()
893
+ defer sc.notePanic()
894
+ defer sc.conn.Close()
895
+ defer sc.closeAllStreamsOnConnClose()
896
+ defer sc.stopShutdownTimer()
897
+ defer close(sc.doneServing) // unblocks handlers trying to send
898
+
899
+ if VerboseLogs {
900
+ sc.vlogf("http2: server connection from %v on %p", sc.conn.RemoteAddr(), sc.hs)
901
+ }
902
+
903
+ settings := writeSettings{
904
+ {SettingMaxFrameSize, conf.MaxReadFrameSize},
905
+ {SettingMaxConcurrentStreams, sc.advMaxStreams},
906
+ {SettingMaxHeaderListSize, sc.maxHeaderListSize()},
907
+ {SettingHeaderTableSize, conf.MaxDecoderHeaderTableSize},
908
+ {SettingInitialWindowSize, uint32(sc.initialStreamRecvWindowSize)},
909
+ }
910
+ if !disableExtendedConnectProtocol {
911
+ settings = append(settings, Setting{SettingEnableConnectProtocol, 1})
912
+ }
913
+ sc.writeFrame(FrameWriteRequest{
914
+ write: settings,
915
+ })
916
+ sc.unackedSettings++
917
+
918
+ // Each connection starts with initialWindowSize inflow tokens.
919
+ // If a higher value is configured, we add more tokens.
920
+ if diff := conf.MaxUploadBufferPerConnection - initialWindowSize; diff > 0 {
921
+ sc.sendWindowUpdate(nil, int(diff))
922
+ }
923
+
924
+ if err := sc.readPreface(); err != nil {
925
+ sc.condlogf(err, "http2: server: error reading preface from client %v: %v", sc.conn.RemoteAddr(), err)
926
+ return
927
+ }
928
+ // Now that we've got the preface, get us out of the
929
+ // "StateNew" state. We can't go directly to idle, though.
930
+ // Active means we read some data and anticipate a request. We'll
931
+ // do another Active when we get a HEADERS frame.
932
+ sc.setConnState(http.StateActive)
933
+ sc.setConnState(http.StateIdle)
934
+
935
+ if sc.srv.IdleTimeout > 0 {
936
+ sc.idleTimer = time.AfterFunc(sc.srv.IdleTimeout, sc.onIdleTimer)
937
+ defer sc.idleTimer.Stop()
938
+ }
939
+
940
+ if conf.SendPingTimeout > 0 {
941
+ sc.readIdleTimeout = conf.SendPingTimeout
942
+ sc.readIdleTimer = time.AfterFunc(conf.SendPingTimeout, sc.onReadIdleTimer)
943
+ defer sc.readIdleTimer.Stop()
944
+ }
945
+
946
+ go sc.readFrames() // closed by defer sc.conn.Close above
947
+
948
+ settingsTimer := time.AfterFunc(firstSettingsTimeout, sc.onSettingsTimer)
949
+ defer settingsTimer.Stop()
950
+
951
+ lastFrameTime := time.Now()
952
+ loopNum := 0
953
+ for {
954
+ loopNum++
955
+ select {
956
+ case wr := <-sc.wantWriteFrameCh:
957
+ if se, ok := wr.write.(StreamError); ok {
958
+ sc.resetStream(se)
959
+ break
960
+ }
961
+ sc.writeFrame(wr)
962
+ case res := <-sc.wroteFrameCh:
963
+ sc.wroteFrame(res)
964
+ case res := <-sc.readFrameCh:
965
+ lastFrameTime = time.Now()
966
+ // Process any written frames before reading new frames from the client since a
967
+ // written frame could have triggered a new stream to be started.
968
+ if sc.writingFrameAsync {
969
+ select {
970
+ case wroteRes := <-sc.wroteFrameCh:
971
+ sc.wroteFrame(wroteRes)
972
+ default:
973
+ }
974
+ }
975
+ if !sc.processFrameFromReader(res) {
976
+ return
977
+ }
978
+ res.readMore()
979
+ if settingsTimer != nil {
980
+ settingsTimer.Stop()
981
+ settingsTimer = nil
982
+ }
983
+ case m := <-sc.bodyReadCh:
984
+ sc.noteBodyRead(m.st, m.n)
985
+ case msg := <-sc.serveMsgCh:
986
+ switch v := msg.(type) {
987
+ case func(int):
988
+ v(loopNum) // for testing
989
+ case *serverMessage:
990
+ switch v {
991
+ case settingsTimerMsg:
992
+ sc.logf("timeout waiting for SETTINGS frames from %v", sc.conn.RemoteAddr())
993
+ return
994
+ case idleTimerMsg:
995
+ sc.vlogf("connection is idle")
996
+ sc.goAway(ErrCodeNo)
997
+ case readIdleTimerMsg:
998
+ sc.handlePingTimer(lastFrameTime)
999
+ case shutdownTimerMsg:
1000
+ sc.vlogf("GOAWAY close timer fired; closing conn from %v", sc.conn.RemoteAddr())
1001
+ return
1002
+ case gracefulShutdownMsg:
1003
+ sc.startGracefulShutdownInternal()
1004
+ case handlerDoneMsg:
1005
+ sc.handlerDone()
1006
+ default:
1007
+ panic("unknown timer")
1008
+ }
1009
+ case *startPushRequest:
1010
+ sc.startPush(v)
1011
+ case func(*serverConn):
1012
+ v(sc)
1013
+ default:
1014
+ panic(fmt.Sprintf("unexpected type %T", v))
1015
+ }
1016
+ }
1017
+
1018
+ // If the peer is causing us to generate a lot of control frames,
1019
+ // but not reading them from us, assume they are trying to make us
1020
+ // run out of memory.
1021
+ if sc.queuedControlFrames > maxQueuedControlFrames {
1022
+ sc.vlogf("http2: too many control frames in send queue, closing connection")
1023
+ return
1024
+ }
1025
+
1026
+ // Start the shutdown timer after sending a GOAWAY. When sending GOAWAY
1027
+ // with no error code (graceful shutdown), don't start the timer until
1028
+ // all open streams have been completed.
1029
+ sentGoAway := sc.inGoAway && !sc.needToSendGoAway && !sc.writingFrame
1030
+ gracefulShutdownComplete := sc.goAwayCode == ErrCodeNo && sc.curOpenStreams() == 0
1031
+ if sentGoAway && sc.shutdownTimer == nil && (sc.goAwayCode != ErrCodeNo || gracefulShutdownComplete) {
1032
+ sc.shutDownIn(goAwayTimeout)
1033
+ }
1034
+ }
1035
+ }
1036
+
1037
+ func (sc *serverConn) handlePingTimer(lastFrameReadTime time.Time) {
1038
+ if sc.pingSent {
1039
+ sc.logf("timeout waiting for PING response")
1040
+ if f := sc.countErrorFunc; f != nil {
1041
+ f("conn_close_lost_ping")
1042
+ }
1043
+ sc.conn.Close()
1044
+ return
1045
+ }
1046
+
1047
+ pingAt := lastFrameReadTime.Add(sc.readIdleTimeout)
1048
+ now := time.Now()
1049
+ if pingAt.After(now) {
1050
+ // We received frames since arming the ping timer.
1051
+ // Reset it for the next possible timeout.
1052
+ sc.readIdleTimer.Reset(pingAt.Sub(now))
1053
+ return
1054
+ }
1055
+
1056
+ sc.pingSent = true
1057
+ // Ignore crypto/rand.Read errors: It generally can't fail, and worse case if it does
1058
+ // is we send a PING frame containing 0s.
1059
+ _, _ = rand.Read(sc.sentPingData[:])
1060
+ sc.writeFrame(FrameWriteRequest{
1061
+ write: &writePing{data: sc.sentPingData},
1062
+ })
1063
+ sc.readIdleTimer.Reset(sc.pingTimeout)
1064
+ }
1065
+
1066
+ type serverMessage int
1067
+
1068
+ // Message values sent to serveMsgCh.
1069
+ var (
1070
+ settingsTimerMsg = new(serverMessage)
1071
+ idleTimerMsg = new(serverMessage)
1072
+ readIdleTimerMsg = new(serverMessage)
1073
+ shutdownTimerMsg = new(serverMessage)
1074
+ gracefulShutdownMsg = new(serverMessage)
1075
+ handlerDoneMsg = new(serverMessage)
1076
+ )
1077
+
1078
+ func (sc *serverConn) onSettingsTimer() { sc.sendServeMsg(settingsTimerMsg) }
1079
+ func (sc *serverConn) onIdleTimer() { sc.sendServeMsg(idleTimerMsg) }
1080
+ func (sc *serverConn) onReadIdleTimer() { sc.sendServeMsg(readIdleTimerMsg) }
1081
+ func (sc *serverConn) onShutdownTimer() { sc.sendServeMsg(shutdownTimerMsg) }
1082
+
1083
+ func (sc *serverConn) sendServeMsg(msg interface{}) {
1084
+ sc.serveG.checkNotOn() // NOT
1085
+ select {
1086
+ case sc.serveMsgCh <- msg:
1087
+ case <-sc.doneServing:
1088
+ }
1089
+ }
1090
+
1091
+ var errPrefaceTimeout = errors.New("timeout waiting for client preface")
1092
+
1093
+ // readPreface reads the ClientPreface greeting from the peer or
1094
+ // returns errPrefaceTimeout on timeout, or an error if the greeting
1095
+ // is invalid.
1096
+ func (sc *serverConn) readPreface() error {
1097
+ if sc.sawClientPreface {
1098
+ return nil
1099
+ }
1100
+ errc := make(chan error, 1)
1101
+ go func() {
1102
+ // Read the client preface
1103
+ buf := make([]byte, len(ClientPreface))
1104
+ if _, err := io.ReadFull(sc.conn, buf); err != nil {
1105
+ errc <- err
1106
+ } else if !bytes.Equal(buf, clientPreface) {
1107
+ errc <- fmt.Errorf("bogus greeting %q", buf)
1108
+ } else {
1109
+ errc <- nil
1110
+ }
1111
+ }()
1112
+ timer := time.NewTimer(prefaceTimeout) // TODO: configurable on *Server?
1113
+ defer timer.Stop()
1114
+ select {
1115
+ case <-timer.C:
1116
+ return errPrefaceTimeout
1117
+ case err := <-errc:
1118
+ if err == nil {
1119
+ if VerboseLogs {
1120
+ sc.vlogf("http2: server: client %v said hello", sc.conn.RemoteAddr())
1121
+ }
1122
+ }
1123
+ return err
1124
+ }
1125
+ }
1126
+
1127
+ var errChanPool = sync.Pool{
1128
+ New: func() interface{} { return make(chan error, 1) },
1129
+ }
1130
+
1131
+ func getErrChan() chan error {
1132
+ if inTests {
1133
+ // Channels cannot be reused across synctest tests.
1134
+ return make(chan error, 1)
1135
+ } else {
1136
+ return errChanPool.Get().(chan error)
1137
+ }
1138
+ }
1139
+
1140
+ func putErrChan(ch chan error) {
1141
+ if !inTests {
1142
+ errChanPool.Put(ch)
1143
+ }
1144
+ }
1145
+
1146
+ var writeDataPool = sync.Pool{
1147
+ New: func() interface{} { return new(writeData) },
1148
+ }
1149
+
1150
+ // writeDataFromHandler writes DATA response frames from a handler on
1151
+ // the given stream.
1152
+ func (sc *serverConn) writeDataFromHandler(stream *stream, data []byte, endStream bool) error {
1153
+ ch := getErrChan()
1154
+ writeArg := writeDataPool.Get().(*writeData)
1155
+ *writeArg = writeData{stream.id, data, endStream}
1156
+ err := sc.writeFrameFromHandler(FrameWriteRequest{
1157
+ write: writeArg,
1158
+ stream: stream,
1159
+ done: ch,
1160
+ })
1161
+ if err != nil {
1162
+ return err
1163
+ }
1164
+ var frameWriteDone bool // the frame write is done (successfully or not)
1165
+ select {
1166
+ case err = <-ch:
1167
+ frameWriteDone = true
1168
+ case <-sc.doneServing:
1169
+ return errClientDisconnected
1170
+ case <-stream.cw:
1171
+ // If both ch and stream.cw were ready (as might
1172
+ // happen on the final Write after an http.Handler
1173
+ // ends), prefer the write result. Otherwise this
1174
+ // might just be us successfully closing the stream.
1175
+ // The writeFrameAsync and serve goroutines guarantee
1176
+ // that the ch send will happen before the stream.cw
1177
+ // close.
1178
+ select {
1179
+ case err = <-ch:
1180
+ frameWriteDone = true
1181
+ default:
1182
+ return errStreamClosed
1183
+ }
1184
+ }
1185
+ putErrChan(ch)
1186
+ if frameWriteDone {
1187
+ writeDataPool.Put(writeArg)
1188
+ }
1189
+ return err
1190
+ }
1191
+
1192
+ // writeFrameFromHandler sends wr to sc.wantWriteFrameCh, but aborts
1193
+ // if the connection has gone away.
1194
+ //
1195
+ // This must not be run from the serve goroutine itself, else it might
1196
+ // deadlock writing to sc.wantWriteFrameCh (which is only mildly
1197
+ // buffered and is read by serve itself). If you're on the serve
1198
+ // goroutine, call writeFrame instead.
1199
+ func (sc *serverConn) writeFrameFromHandler(wr FrameWriteRequest) error {
1200
+ sc.serveG.checkNotOn() // NOT
1201
+ select {
1202
+ case sc.wantWriteFrameCh <- wr:
1203
+ return nil
1204
+ case <-sc.doneServing:
1205
+ // Serve loop is gone.
1206
+ // Client has closed their connection to the server.
1207
+ return errClientDisconnected
1208
+ }
1209
+ }
1210
+
1211
+ // writeFrame schedules a frame to write and sends it if there's nothing
1212
+ // already being written.
1213
+ //
1214
+ // There is no pushback here (the serve goroutine never blocks). It's
1215
+ // the http.Handlers that block, waiting for their previous frames to
1216
+ // make it onto the wire
1217
+ //
1218
+ // If you're not on the serve goroutine, use writeFrameFromHandler instead.
1219
+ func (sc *serverConn) writeFrame(wr FrameWriteRequest) {
1220
+ sc.serveG.check()
1221
+
1222
+ // If true, wr will not be written and wr.done will not be signaled.
1223
+ var ignoreWrite bool
1224
+
1225
+ // We are not allowed to write frames on closed streams. RFC 7540 Section
1226
+ // 5.1.1 says: "An endpoint MUST NOT send frames other than PRIORITY on
1227
+ // a closed stream." Our server never sends PRIORITY, so that exception
1228
+ // does not apply.
1229
+ //
1230
+ // The serverConn might close an open stream while the stream's handler
1231
+ // is still running. For example, the server might close a stream when it
1232
+ // receives bad data from the client. If this happens, the handler might
1233
+ // attempt to write a frame after the stream has been closed (since the
1234
+ // handler hasn't yet been notified of the close). In this case, we simply
1235
+ // ignore the frame. The handler will notice that the stream is closed when
1236
+ // it waits for the frame to be written.
1237
+ //
1238
+ // As an exception to this rule, we allow sending RST_STREAM after close.
1239
+ // This allows us to immediately reject new streams without tracking any
1240
+ // state for those streams (except for the queued RST_STREAM frame). This
1241
+ // may result in duplicate RST_STREAMs in some cases, but the client should
1242
+ // ignore those.
1243
+ if wr.StreamID() != 0 {
1244
+ _, isReset := wr.write.(StreamError)
1245
+ if state, _ := sc.state(wr.StreamID()); state == stateClosed && !isReset {
1246
+ ignoreWrite = true
1247
+ }
1248
+ }
1249
+
1250
+ // Don't send a 100-continue response if we've already sent headers.
1251
+ // See golang.org/issue/14030.
1252
+ switch wr.write.(type) {
1253
+ case *writeResHeaders:
1254
+ wr.stream.wroteHeaders = true
1255
+ case write100ContinueHeadersFrame:
1256
+ if wr.stream.wroteHeaders {
1257
+ // We do not need to notify wr.done because this frame is
1258
+ // never written with wr.done != nil.
1259
+ if wr.done != nil {
1260
+ panic("wr.done != nil for write100ContinueHeadersFrame")
1261
+ }
1262
+ ignoreWrite = true
1263
+ }
1264
+ }
1265
+
1266
+ if !ignoreWrite {
1267
+ if wr.isControl() {
1268
+ sc.queuedControlFrames++
1269
+ // For extra safety, detect wraparounds, which should not happen,
1270
+ // and pull the plug.
1271
+ if sc.queuedControlFrames < 0 {
1272
+ sc.conn.Close()
1273
+ }
1274
+ }
1275
+ sc.writeSched.Push(wr)
1276
+ }
1277
+ sc.scheduleFrameWrite()
1278
+ }
1279
+
1280
+ // startFrameWrite starts a goroutine to write wr (in a separate
1281
+ // goroutine since that might block on the network), and updates the
1282
+ // serve goroutine's state about the world, updated from info in wr.
1283
+ func (sc *serverConn) startFrameWrite(wr FrameWriteRequest) {
1284
+ sc.serveG.check()
1285
+ if sc.writingFrame {
1286
+ panic("internal error: can only be writing one frame at a time")
1287
+ }
1288
+
1289
+ st := wr.stream
1290
+ if st != nil {
1291
+ switch st.state {
1292
+ case stateHalfClosedLocal:
1293
+ switch wr.write.(type) {
1294
+ case StreamError, handlerPanicRST, writeWindowUpdate:
1295
+ // RFC 7540 Section 5.1 allows sending RST_STREAM, PRIORITY, and WINDOW_UPDATE
1296
+ // in this state. (We never send PRIORITY from the server, so that is not checked.)
1297
+ default:
1298
+ panic(fmt.Sprintf("internal error: attempt to send frame on a half-closed-local stream: %v", wr))
1299
+ }
1300
+ case stateClosed:
1301
+ panic(fmt.Sprintf("internal error: attempt to send frame on a closed stream: %v", wr))
1302
+ }
1303
+ }
1304
+ if wpp, ok := wr.write.(*writePushPromise); ok {
1305
+ var err error
1306
+ wpp.promisedID, err = wpp.allocatePromisedID()
1307
+ if err != nil {
1308
+ sc.writingFrameAsync = false
1309
+ wr.replyToWriter(err)
1310
+ return
1311
+ }
1312
+ }
1313
+
1314
+ sc.writingFrame = true
1315
+ sc.needsFrameFlush = true
1316
+ if wr.write.staysWithinBuffer(sc.bw.Available()) {
1317
+ sc.writingFrameAsync = false
1318
+ err := wr.write.writeFrame(sc)
1319
+ sc.wroteFrame(frameWriteResult{wr: wr, err: err})
1320
+ } else if wd, ok := wr.write.(*writeData); ok {
1321
+ // Encode the frame in the serve goroutine, to ensure we don't have
1322
+ // any lingering asynchronous references to data passed to Write.
1323
+ // See https://go.dev/issue/58446.
1324
+ sc.framer.startWriteDataPadded(wd.streamID, wd.endStream, wd.p, nil)
1325
+ sc.writingFrameAsync = true
1326
+ go sc.writeFrameAsync(wr, wd)
1327
+ } else {
1328
+ sc.writingFrameAsync = true
1329
+ go sc.writeFrameAsync(wr, nil)
1330
+ }
1331
+ }
1332
+
1333
+ // errHandlerPanicked is the error given to any callers blocked in a read from
1334
+ // Request.Body when the main goroutine panics. Since most handlers read in the
1335
+ // main ServeHTTP goroutine, this will show up rarely.
1336
+ var errHandlerPanicked = errors.New("http2: handler panicked")
1337
+
1338
+ // wroteFrame is called on the serve goroutine with the result of
1339
+ // whatever happened on writeFrameAsync.
1340
+ func (sc *serverConn) wroteFrame(res frameWriteResult) {
1341
+ sc.serveG.check()
1342
+ if !sc.writingFrame {
1343
+ panic("internal error: expected to be already writing a frame")
1344
+ }
1345
+ sc.writingFrame = false
1346
+ sc.writingFrameAsync = false
1347
+
1348
+ if res.err != nil {
1349
+ sc.conn.Close()
1350
+ }
1351
+
1352
+ wr := res.wr
1353
+
1354
+ if writeEndsStream(wr.write) {
1355
+ st := wr.stream
1356
+ if st == nil {
1357
+ panic("internal error: expecting non-nil stream")
1358
+ }
1359
+ switch st.state {
1360
+ case stateOpen:
1361
+ // Here we would go to stateHalfClosedLocal in
1362
+ // theory, but since our handler is done and
1363
+ // the net/http package provides no mechanism
1364
+ // for closing a ResponseWriter while still
1365
+ // reading data (see possible TODO at top of
1366
+ // this file), we go into closed state here
1367
+ // anyway, after telling the peer we're
1368
+ // hanging up on them. We'll transition to
1369
+ // stateClosed after the RST_STREAM frame is
1370
+ // written.
1371
+ st.state = stateHalfClosedLocal
1372
+ // Section 8.1: a server MAY request that the client abort
1373
+ // transmission of a request without error by sending a
1374
+ // RST_STREAM with an error code of NO_ERROR after sending
1375
+ // a complete response.
1376
+ sc.resetStream(streamError(st.id, ErrCodeNo))
1377
+ case stateHalfClosedRemote:
1378
+ sc.closeStream(st, errHandlerComplete)
1379
+ }
1380
+ } else {
1381
+ switch v := wr.write.(type) {
1382
+ case StreamError:
1383
+ // st may be unknown if the RST_STREAM was generated to reject bad input.
1384
+ if st, ok := sc.streams[v.StreamID]; ok {
1385
+ sc.closeStream(st, v)
1386
+ }
1387
+ case handlerPanicRST:
1388
+ sc.closeStream(wr.stream, errHandlerPanicked)
1389
+ }
1390
+ }
1391
+
1392
+ // Reply (if requested) to unblock the ServeHTTP goroutine.
1393
+ wr.replyToWriter(res.err)
1394
+
1395
+ sc.scheduleFrameWrite()
1396
+ }
1397
+
1398
+ // scheduleFrameWrite tickles the frame writing scheduler.
1399
+ //
1400
+ // If a frame is already being written, nothing happens. This will be called again
1401
+ // when the frame is done being written.
1402
+ //
1403
+ // If a frame isn't being written and we need to send one, the best frame
1404
+ // to send is selected by writeSched.
1405
+ //
1406
+ // If a frame isn't being written and there's nothing else to send, we
1407
+ // flush the write buffer.
1408
+ func (sc *serverConn) scheduleFrameWrite() {
1409
+ sc.serveG.check()
1410
+ if sc.writingFrame || sc.inFrameScheduleLoop {
1411
+ return
1412
+ }
1413
+ sc.inFrameScheduleLoop = true
1414
+ for !sc.writingFrameAsync {
1415
+ if sc.needToSendGoAway {
1416
+ sc.needToSendGoAway = false
1417
+ sc.startFrameWrite(FrameWriteRequest{
1418
+ write: &writeGoAway{
1419
+ maxStreamID: sc.maxClientStreamID,
1420
+ code: sc.goAwayCode,
1421
+ },
1422
+ })
1423
+ continue
1424
+ }
1425
+ if sc.needToSendSettingsAck {
1426
+ sc.needToSendSettingsAck = false
1427
+ sc.startFrameWrite(FrameWriteRequest{write: writeSettingsAck{}})
1428
+ continue
1429
+ }
1430
+ if !sc.inGoAway || sc.goAwayCode == ErrCodeNo {
1431
+ if wr, ok := sc.writeSched.Pop(); ok {
1432
+ if wr.isControl() {
1433
+ sc.queuedControlFrames--
1434
+ }
1435
+ sc.startFrameWrite(wr)
1436
+ continue
1437
+ }
1438
+ }
1439
+ if sc.needsFrameFlush {
1440
+ sc.startFrameWrite(FrameWriteRequest{write: flushFrameWriter{}})
1441
+ sc.needsFrameFlush = false // after startFrameWrite, since it sets this true
1442
+ continue
1443
+ }
1444
+ break
1445
+ }
1446
+ sc.inFrameScheduleLoop = false
1447
+ }
1448
+
1449
+ // startGracefulShutdown gracefully shuts down a connection. This
1450
+ // sends GOAWAY with ErrCodeNo to tell the client we're gracefully
1451
+ // shutting down. The connection isn't closed until all current
1452
+ // streams are done.
1453
+ //
1454
+ // startGracefulShutdown returns immediately; it does not wait until
1455
+ // the connection has shut down.
1456
+ func (sc *serverConn) startGracefulShutdown() {
1457
+ sc.serveG.checkNotOn() // NOT
1458
+ sc.shutdownOnce.Do(func() { sc.sendServeMsg(gracefulShutdownMsg) })
1459
+ }
1460
+
1461
+ // After sending GOAWAY with an error code (non-graceful shutdown), the
1462
+ // connection will close after goAwayTimeout.
1463
+ //
1464
+ // If we close the connection immediately after sending GOAWAY, there may
1465
+ // be unsent data in our kernel receive buffer, which will cause the kernel
1466
+ // to send a TCP RST on close() instead of a FIN. This RST will abort the
1467
+ // connection immediately, whether or not the client had received the GOAWAY.
1468
+ //
1469
+ // Ideally we should delay for at least 1 RTT + epsilon so the client has
1470
+ // a chance to read the GOAWAY and stop sending messages. Measuring RTT
1471
+ // is hard, so we approximate with 1 second. See golang.org/issue/18701.
1472
+ //
1473
+ // This is a var so it can be shorter in tests, where all requests uses the
1474
+ // loopback interface making the expected RTT very small.
1475
+ //
1476
+ // TODO: configurable?
1477
+ var goAwayTimeout = 1 * time.Second
1478
+
1479
+ func (sc *serverConn) startGracefulShutdownInternal() {
1480
+ sc.goAway(ErrCodeNo)
1481
+ }
1482
+
1483
+ func (sc *serverConn) goAway(code ErrCode) {
1484
+ sc.serveG.check()
1485
+ if sc.inGoAway {
1486
+ if sc.goAwayCode == ErrCodeNo {
1487
+ sc.goAwayCode = code
1488
+ }
1489
+ return
1490
+ }
1491
+ sc.inGoAway = true
1492
+ sc.needToSendGoAway = true
1493
+ sc.goAwayCode = code
1494
+ sc.scheduleFrameWrite()
1495
+ }
1496
+
1497
+ func (sc *serverConn) shutDownIn(d time.Duration) {
1498
+ sc.serveG.check()
1499
+ sc.shutdownTimer = time.AfterFunc(d, sc.onShutdownTimer)
1500
+ }
1501
+
1502
+ func (sc *serverConn) resetStream(se StreamError) {
1503
+ sc.serveG.check()
1504
+ sc.writeFrame(FrameWriteRequest{write: se})
1505
+ if st, ok := sc.streams[se.StreamID]; ok {
1506
+ st.resetQueued = true
1507
+ }
1508
+ }
1509
+
1510
+ // processFrameFromReader processes the serve loop's read from readFrameCh from the
1511
+ // frame-reading goroutine.
1512
+ // processFrameFromReader returns whether the connection should be kept open.
1513
+ func (sc *serverConn) processFrameFromReader(res readFrameResult) bool {
1514
+ sc.serveG.check()
1515
+ err := res.err
1516
+ if err != nil {
1517
+ if err == ErrFrameTooLarge {
1518
+ sc.goAway(ErrCodeFrameSize)
1519
+ return true // goAway will close the loop
1520
+ }
1521
+ clientGone := err == io.EOF || err == io.ErrUnexpectedEOF || isClosedConnError(err)
1522
+ if clientGone {
1523
+ // TODO: could we also get into this state if
1524
+ // the peer does a half close
1525
+ // (e.g. CloseWrite) because they're done
1526
+ // sending frames but they're still wanting
1527
+ // our open replies? Investigate.
1528
+ // TODO: add CloseWrite to crypto/tls.Conn first
1529
+ // so we have a way to test this? I suppose
1530
+ // just for testing we could have a non-TLS mode.
1531
+ return false
1532
+ }
1533
+ } else {
1534
+ f := res.f
1535
+ if VerboseLogs {
1536
+ sc.vlogf("http2: server read frame %v", summarizeFrame(f))
1537
+ }
1538
+ err = sc.processFrame(f)
1539
+ if err == nil {
1540
+ return true
1541
+ }
1542
+ }
1543
+
1544
+ switch ev := err.(type) {
1545
+ case StreamError:
1546
+ sc.resetStream(ev)
1547
+ return true
1548
+ case goAwayFlowError:
1549
+ sc.goAway(ErrCodeFlowControl)
1550
+ return true
1551
+ case ConnectionError:
1552
+ if res.f != nil {
1553
+ if id := res.f.Header().StreamID; id > sc.maxClientStreamID {
1554
+ sc.maxClientStreamID = id
1555
+ }
1556
+ }
1557
+ sc.logf("http2: server connection error from %v: %v", sc.conn.RemoteAddr(), ev)
1558
+ sc.goAway(ErrCode(ev))
1559
+ return true // goAway will handle shutdown
1560
+ default:
1561
+ if res.err != nil {
1562
+ sc.vlogf("http2: server closing client connection; error reading frame from client %s: %v", sc.conn.RemoteAddr(), err)
1563
+ } else {
1564
+ sc.logf("http2: server closing client connection: %v", err)
1565
+ }
1566
+ return false
1567
+ }
1568
+ }
1569
+
1570
+ func (sc *serverConn) processFrame(f Frame) error {
1571
+ sc.serveG.check()
1572
+
1573
+ // First frame received must be SETTINGS.
1574
+ if !sc.sawFirstSettings {
1575
+ if _, ok := f.(*SettingsFrame); !ok {
1576
+ return sc.countError("first_settings", ConnectionError(ErrCodeProtocol))
1577
+ }
1578
+ sc.sawFirstSettings = true
1579
+ }
1580
+
1581
+ // Discard frames for streams initiated after the identified last
1582
+ // stream sent in a GOAWAY, or all frames after sending an error.
1583
+ // We still need to return connection-level flow control for DATA frames.
1584
+ // RFC 9113 Section 6.8.
1585
+ if sc.inGoAway && (sc.goAwayCode != ErrCodeNo || f.Header().StreamID > sc.maxClientStreamID) {
1586
+
1587
+ if f, ok := f.(*DataFrame); ok {
1588
+ if !sc.inflow.take(f.Length) {
1589
+ return sc.countError("data_flow", streamError(f.Header().StreamID, ErrCodeFlowControl))
1590
+ }
1591
+ sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
1592
+ }
1593
+ return nil
1594
+ }
1595
+
1596
+ switch f := f.(type) {
1597
+ case *SettingsFrame:
1598
+ return sc.processSettings(f)
1599
+ case *MetaHeadersFrame:
1600
+ return sc.processHeaders(f)
1601
+ case *WindowUpdateFrame:
1602
+ return sc.processWindowUpdate(f)
1603
+ case *PingFrame:
1604
+ return sc.processPing(f)
1605
+ case *DataFrame:
1606
+ return sc.processData(f)
1607
+ case *RSTStreamFrame:
1608
+ return sc.processResetStream(f)
1609
+ case *PriorityFrame:
1610
+ return sc.processPriority(f)
1611
+ case *GoAwayFrame:
1612
+ return sc.processGoAway(f)
1613
+ case *PushPromiseFrame:
1614
+ // A client cannot push. Thus, servers MUST treat the receipt of a PUSH_PROMISE
1615
+ // frame as a connection error (Section 5.4.1) of type PROTOCOL_ERROR.
1616
+ return sc.countError("push_promise", ConnectionError(ErrCodeProtocol))
1617
+ default:
1618
+ sc.vlogf("http2: server ignoring frame: %v", f.Header())
1619
+ return nil
1620
+ }
1621
+ }
1622
+
1623
+ func (sc *serverConn) processPing(f *PingFrame) error {
1624
+ sc.serveG.check()
1625
+ if f.IsAck() {
1626
+ if sc.pingSent && sc.sentPingData == f.Data {
1627
+ // This is a response to a PING we sent.
1628
+ sc.pingSent = false
1629
+ sc.readIdleTimer.Reset(sc.readIdleTimeout)
1630
+ }
1631
+ // 6.7 PING: " An endpoint MUST NOT respond to PING frames
1632
+ // containing this flag."
1633
+ return nil
1634
+ }
1635
+ if f.StreamID != 0 {
1636
+ // "PING frames are not associated with any individual
1637
+ // stream. If a PING frame is received with a stream
1638
+ // identifier field value other than 0x0, the recipient MUST
1639
+ // respond with a connection error (Section 5.4.1) of type
1640
+ // PROTOCOL_ERROR."
1641
+ return sc.countError("ping_on_stream", ConnectionError(ErrCodeProtocol))
1642
+ }
1643
+ sc.writeFrame(FrameWriteRequest{write: writePingAck{f}})
1644
+ return nil
1645
+ }
1646
+
1647
+ func (sc *serverConn) processWindowUpdate(f *WindowUpdateFrame) error {
1648
+ sc.serveG.check()
1649
+ switch {
1650
+ case f.StreamID != 0: // stream-level flow control
1651
+ state, st := sc.state(f.StreamID)
1652
+ if state == stateIdle {
1653
+ // Section 5.1: "Receiving any frame other than HEADERS
1654
+ // or PRIORITY on a stream in this state MUST be
1655
+ // treated as a connection error (Section 5.4.1) of
1656
+ // type PROTOCOL_ERROR."
1657
+ return sc.countError("stream_idle", ConnectionError(ErrCodeProtocol))
1658
+ }
1659
+ if st == nil {
1660
+ // "WINDOW_UPDATE can be sent by a peer that has sent a
1661
+ // frame bearing the END_STREAM flag. This means that a
1662
+ // receiver could receive a WINDOW_UPDATE frame on a "half
1663
+ // closed (remote)" or "closed" stream. A receiver MUST
1664
+ // NOT treat this as an error, see Section 5.1."
1665
+ return nil
1666
+ }
1667
+ if !st.flow.add(int32(f.Increment)) {
1668
+ return sc.countError("bad_flow", streamError(f.StreamID, ErrCodeFlowControl))
1669
+ }
1670
+ default: // connection-level flow control
1671
+ if !sc.flow.add(int32(f.Increment)) {
1672
+ return goAwayFlowError{}
1673
+ }
1674
+ }
1675
+ sc.scheduleFrameWrite()
1676
+ return nil
1677
+ }
1678
+
1679
+ func (sc *serverConn) processResetStream(f *RSTStreamFrame) error {
1680
+ sc.serveG.check()
1681
+
1682
+ state, st := sc.state(f.StreamID)
1683
+ if state == stateIdle {
1684
+ // 6.4 "RST_STREAM frames MUST NOT be sent for a
1685
+ // stream in the "idle" state. If a RST_STREAM frame
1686
+ // identifying an idle stream is received, the
1687
+ // recipient MUST treat this as a connection error
1688
+ // (Section 5.4.1) of type PROTOCOL_ERROR.
1689
+ return sc.countError("reset_idle_stream", ConnectionError(ErrCodeProtocol))
1690
+ }
1691
+ if st != nil {
1692
+ st.cancelCtx()
1693
+ sc.closeStream(st, streamError(f.StreamID, f.ErrCode))
1694
+ }
1695
+ return nil
1696
+ }
1697
+
1698
+ func (sc *serverConn) closeStream(st *stream, err error) {
1699
+ sc.serveG.check()
1700
+ if st.state == stateIdle || st.state == stateClosed {
1701
+ panic(fmt.Sprintf("invariant; can't close stream in state %v", st.state))
1702
+ }
1703
+ st.state = stateClosed
1704
+ if st.readDeadline != nil {
1705
+ st.readDeadline.Stop()
1706
+ }
1707
+ if st.writeDeadline != nil {
1708
+ st.writeDeadline.Stop()
1709
+ }
1710
+ if st.isPushed() {
1711
+ sc.curPushedStreams--
1712
+ } else {
1713
+ sc.curClientStreams--
1714
+ }
1715
+ delete(sc.streams, st.id)
1716
+ if len(sc.streams) == 0 {
1717
+ sc.setConnState(http.StateIdle)
1718
+ if sc.srv.IdleTimeout > 0 && sc.idleTimer != nil {
1719
+ sc.idleTimer.Reset(sc.srv.IdleTimeout)
1720
+ }
1721
+ if h1ServerKeepAlivesDisabled(sc.hs) {
1722
+ sc.startGracefulShutdownInternal()
1723
+ }
1724
+ }
1725
+ if p := st.body; p != nil {
1726
+ // Return any buffered unread bytes worth of conn-level flow control.
1727
+ // See golang.org/issue/16481
1728
+ sc.sendWindowUpdate(nil, p.Len())
1729
+
1730
+ p.CloseWithError(err)
1731
+ }
1732
+ if e, ok := err.(StreamError); ok {
1733
+ if e.Cause != nil {
1734
+ err = e.Cause
1735
+ } else {
1736
+ err = errStreamClosed
1737
+ }
1738
+ }
1739
+ st.closeErr = err
1740
+ st.cancelCtx()
1741
+ st.cw.Close() // signals Handler's CloseNotifier, unblocks writes, etc
1742
+ sc.writeSched.CloseStream(st.id)
1743
+ }
1744
+
1745
+ func (sc *serverConn) processSettings(f *SettingsFrame) error {
1746
+ sc.serveG.check()
1747
+ if f.IsAck() {
1748
+ sc.unackedSettings--
1749
+ if sc.unackedSettings < 0 {
1750
+ // Why is the peer ACKing settings we never sent?
1751
+ // The spec doesn't mention this case, but
1752
+ // hang up on them anyway.
1753
+ return sc.countError("ack_mystery", ConnectionError(ErrCodeProtocol))
1754
+ }
1755
+ return nil
1756
+ }
1757
+ if f.NumSettings() > 100 || f.HasDuplicates() {
1758
+ // This isn't actually in the spec, but hang up on
1759
+ // suspiciously large settings frames or those with
1760
+ // duplicate entries.
1761
+ return sc.countError("settings_big_or_dups", ConnectionError(ErrCodeProtocol))
1762
+ }
1763
+ if err := f.ForeachSetting(sc.processSetting); err != nil {
1764
+ return err
1765
+ }
1766
+ // TODO: judging by RFC 7540, Section 6.5.3 each SETTINGS frame should be
1767
+ // acknowledged individually, even if multiple are received before the ACK.
1768
+ sc.needToSendSettingsAck = true
1769
+ sc.scheduleFrameWrite()
1770
+ return nil
1771
+ }
1772
+
1773
+ func (sc *serverConn) processSetting(s Setting) error {
1774
+ sc.serveG.check()
1775
+ if err := s.Valid(); err != nil {
1776
+ return err
1777
+ }
1778
+ if VerboseLogs {
1779
+ sc.vlogf("http2: server processing setting %v", s)
1780
+ }
1781
+ switch s.ID {
1782
+ case SettingHeaderTableSize:
1783
+ sc.hpackEncoder.SetMaxDynamicTableSize(s.Val)
1784
+ case SettingEnablePush:
1785
+ sc.pushEnabled = s.Val != 0
1786
+ case SettingMaxConcurrentStreams:
1787
+ sc.clientMaxStreams = s.Val
1788
+ case SettingInitialWindowSize:
1789
+ return sc.processSettingInitialWindowSize(s.Val)
1790
+ case SettingMaxFrameSize:
1791
+ sc.maxFrameSize = int32(s.Val) // the maximum valid s.Val is < 2^31
1792
+ case SettingMaxHeaderListSize:
1793
+ sc.peerMaxHeaderListSize = s.Val
1794
+ case SettingEnableConnectProtocol:
1795
+ // Receipt of this parameter by a server does not
1796
+ // have any impact
1797
+ default:
1798
+ // Unknown setting: "An endpoint that receives a SETTINGS
1799
+ // frame with any unknown or unsupported identifier MUST
1800
+ // ignore that setting."
1801
+ if VerboseLogs {
1802
+ sc.vlogf("http2: server ignoring unknown setting %v", s)
1803
+ }
1804
+ }
1805
+ return nil
1806
+ }
1807
+
1808
+ func (sc *serverConn) processSettingInitialWindowSize(val uint32) error {
1809
+ sc.serveG.check()
1810
+ // Note: val already validated to be within range by
1811
+ // processSetting's Valid call.
1812
+
1813
+ // "A SETTINGS frame can alter the initial flow control window
1814
+ // size for all current streams. When the value of
1815
+ // SETTINGS_INITIAL_WINDOW_SIZE changes, a receiver MUST
1816
+ // adjust the size of all stream flow control windows that it
1817
+ // maintains by the difference between the new value and the
1818
+ // old value."
1819
+ old := sc.initialStreamSendWindowSize
1820
+ sc.initialStreamSendWindowSize = int32(val)
1821
+ growth := int32(val) - old // may be negative
1822
+ for _, st := range sc.streams {
1823
+ if !st.flow.add(growth) {
1824
+ // 6.9.2 Initial Flow Control Window Size
1825
+ // "An endpoint MUST treat a change to
1826
+ // SETTINGS_INITIAL_WINDOW_SIZE that causes any flow
1827
+ // control window to exceed the maximum size as a
1828
+ // connection error (Section 5.4.1) of type
1829
+ // FLOW_CONTROL_ERROR."
1830
+ return sc.countError("setting_win_size", ConnectionError(ErrCodeFlowControl))
1831
+ }
1832
+ }
1833
+ return nil
1834
+ }
1835
+
1836
+ func (sc *serverConn) processData(f *DataFrame) error {
1837
+ sc.serveG.check()
1838
+ id := f.Header().StreamID
1839
+
1840
+ data := f.Data()
1841
+ state, st := sc.state(id)
1842
+ if id == 0 || state == stateIdle {
1843
+ // Section 6.1: "DATA frames MUST be associated with a
1844
+ // stream. If a DATA frame is received whose stream
1845
+ // identifier field is 0x0, the recipient MUST respond
1846
+ // with a connection error (Section 5.4.1) of type
1847
+ // PROTOCOL_ERROR."
1848
+ //
1849
+ // Section 5.1: "Receiving any frame other than HEADERS
1850
+ // or PRIORITY on a stream in this state MUST be
1851
+ // treated as a connection error (Section 5.4.1) of
1852
+ // type PROTOCOL_ERROR."
1853
+ return sc.countError("data_on_idle", ConnectionError(ErrCodeProtocol))
1854
+ }
1855
+
1856
+ // "If a DATA frame is received whose stream is not in "open"
1857
+ // or "half closed (local)" state, the recipient MUST respond
1858
+ // with a stream error (Section 5.4.2) of type STREAM_CLOSED."
1859
+ if st == nil || state != stateOpen || st.gotTrailerHeader || st.resetQueued {
1860
+ // This includes sending a RST_STREAM if the stream is
1861
+ // in stateHalfClosedLocal (which currently means that
1862
+ // the http.Handler returned, so it's done reading &
1863
+ // done writing). Try to stop the client from sending
1864
+ // more DATA.
1865
+
1866
+ // But still enforce their connection-level flow control,
1867
+ // and return any flow control bytes since we're not going
1868
+ // to consume them.
1869
+ if !sc.inflow.take(f.Length) {
1870
+ return sc.countError("data_flow", streamError(id, ErrCodeFlowControl))
1871
+ }
1872
+ sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
1873
+
1874
+ if st != nil && st.resetQueued {
1875
+ // Already have a stream error in flight. Don't send another.
1876
+ return nil
1877
+ }
1878
+ return sc.countError("closed", streamError(id, ErrCodeStreamClosed))
1879
+ }
1880
+ if st.body == nil {
1881
+ panic("internal error: should have a body in this state")
1882
+ }
1883
+
1884
+ // Sender sending more than they'd declared?
1885
+ if st.declBodyBytes != -1 && st.bodyBytes+int64(len(data)) > st.declBodyBytes {
1886
+ if !sc.inflow.take(f.Length) {
1887
+ return sc.countError("data_flow", streamError(id, ErrCodeFlowControl))
1888
+ }
1889
+ sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
1890
+
1891
+ st.body.CloseWithError(fmt.Errorf("sender tried to send more than declared Content-Length of %d bytes", st.declBodyBytes))
1892
+ // RFC 7540, sec 8.1.2.6: A request or response is also malformed if the
1893
+ // value of a content-length header field does not equal the sum of the
1894
+ // DATA frame payload lengths that form the body.
1895
+ return sc.countError("send_too_much", streamError(id, ErrCodeProtocol))
1896
+ }
1897
+ if f.Length > 0 {
1898
+ // Check whether the client has flow control quota.
1899
+ if !takeInflows(&sc.inflow, &st.inflow, f.Length) {
1900
+ return sc.countError("flow_on_data_length", streamError(id, ErrCodeFlowControl))
1901
+ }
1902
+
1903
+ if len(data) > 0 {
1904
+ st.bodyBytes += int64(len(data))
1905
+ wrote, err := st.body.Write(data)
1906
+ if err != nil {
1907
+ // The handler has closed the request body.
1908
+ // Return the connection-level flow control for the discarded data,
1909
+ // but not the stream-level flow control.
1910
+ sc.sendWindowUpdate(nil, int(f.Length)-wrote)
1911
+ return nil
1912
+ }
1913
+ if wrote != len(data) {
1914
+ panic("internal error: bad Writer")
1915
+ }
1916
+ }
1917
+
1918
+ // Return any padded flow control now, since we won't
1919
+ // refund it later on body reads.
1920
+ // Call sendWindowUpdate even if there is no padding,
1921
+ // to return buffered flow control credit if the sent
1922
+ // window has shrunk.
1923
+ pad := int32(f.Length) - int32(len(data))
1924
+ sc.sendWindowUpdate32(nil, pad)
1925
+ sc.sendWindowUpdate32(st, pad)
1926
+ }
1927
+ if f.StreamEnded() {
1928
+ st.endStream()
1929
+ }
1930
+ return nil
1931
+ }
1932
+
1933
+ func (sc *serverConn) processGoAway(f *GoAwayFrame) error {
1934
+ sc.serveG.check()
1935
+ if f.ErrCode != ErrCodeNo {
1936
+ sc.logf("http2: received GOAWAY %+v, starting graceful shutdown", f)
1937
+ } else {
1938
+ sc.vlogf("http2: received GOAWAY %+v, starting graceful shutdown", f)
1939
+ }
1940
+ sc.startGracefulShutdownInternal()
1941
+ // http://tools.ietf.org/html/rfc7540#section-6.8
1942
+ // We should not create any new streams, which means we should disable push.
1943
+ sc.pushEnabled = false
1944
+ return nil
1945
+ }
1946
+
1947
+ // isPushed reports whether the stream is server-initiated.
1948
+ func (st *stream) isPushed() bool {
1949
+ return st.id%2 == 0
1950
+ }
1951
+
1952
+ // endStream closes a Request.Body's pipe. It is called when a DATA
1953
+ // frame says a request body is over (or after trailers).
1954
+ func (st *stream) endStream() {
1955
+ sc := st.sc
1956
+ sc.serveG.check()
1957
+
1958
+ if st.declBodyBytes != -1 && st.declBodyBytes != st.bodyBytes {
1959
+ st.body.CloseWithError(fmt.Errorf("request declared a Content-Length of %d but only wrote %d bytes",
1960
+ st.declBodyBytes, st.bodyBytes))
1961
+ } else {
1962
+ st.body.closeWithErrorAndCode(io.EOF, st.copyTrailersToHandlerRequest)
1963
+ st.body.CloseWithError(io.EOF)
1964
+ }
1965
+ st.state = stateHalfClosedRemote
1966
+ }
1967
+
1968
+ // copyTrailersToHandlerRequest is run in the Handler's goroutine in
1969
+ // its Request.Body.Read just before it gets io.EOF.
1970
+ func (st *stream) copyTrailersToHandlerRequest() {
1971
+ for k, vv := range st.trailer {
1972
+ if _, ok := st.reqTrailer[k]; ok {
1973
+ // Only copy it over it was pre-declared.
1974
+ st.reqTrailer[k] = vv
1975
+ }
1976
+ }
1977
+ }
1978
+
1979
+ // onReadTimeout is run on its own goroutine (from time.AfterFunc)
1980
+ // when the stream's ReadTimeout has fired.
1981
+ func (st *stream) onReadTimeout() {
1982
+ if st.body != nil {
1983
+ // Wrap the ErrDeadlineExceeded to avoid callers depending on us
1984
+ // returning the bare error.
1985
+ st.body.CloseWithError(fmt.Errorf("%w", os.ErrDeadlineExceeded))
1986
+ }
1987
+ }
1988
+
1989
+ // onWriteTimeout is run on its own goroutine (from time.AfterFunc)
1990
+ // when the stream's WriteTimeout has fired.
1991
+ func (st *stream) onWriteTimeout() {
1992
+ st.sc.writeFrameFromHandler(FrameWriteRequest{write: StreamError{
1993
+ StreamID: st.id,
1994
+ Code: ErrCodeInternal,
1995
+ Cause: os.ErrDeadlineExceeded,
1996
+ }})
1997
+ }
1998
+
1999
+ func (sc *serverConn) processHeaders(f *MetaHeadersFrame) error {
2000
+ sc.serveG.check()
2001
+ id := f.StreamID
2002
+ // http://tools.ietf.org/html/rfc7540#section-5.1.1
2003
+ // Streams initiated by a client MUST use odd-numbered stream
2004
+ // identifiers. [...] An endpoint that receives an unexpected
2005
+ // stream identifier MUST respond with a connection error
2006
+ // (Section 5.4.1) of type PROTOCOL_ERROR.
2007
+ if id%2 != 1 {
2008
+ return sc.countError("headers_even", ConnectionError(ErrCodeProtocol))
2009
+ }
2010
+ // A HEADERS frame can be used to create a new stream or
2011
+ // send a trailer for an open one. If we already have a stream
2012
+ // open, let it process its own HEADERS frame (trailers at this
2013
+ // point, if it's valid).
2014
+ if st := sc.streams[f.StreamID]; st != nil {
2015
+ if st.resetQueued {
2016
+ // We're sending RST_STREAM to close the stream, so don't bother
2017
+ // processing this frame.
2018
+ return nil
2019
+ }
2020
+ // RFC 7540, sec 5.1: If an endpoint receives additional frames, other than
2021
+ // WINDOW_UPDATE, PRIORITY, or RST_STREAM, for a stream that is in
2022
+ // this state, it MUST respond with a stream error (Section 5.4.2) of
2023
+ // type STREAM_CLOSED.
2024
+ if st.state == stateHalfClosedRemote {
2025
+ return sc.countError("headers_half_closed", streamError(id, ErrCodeStreamClosed))
2026
+ }
2027
+ return st.processTrailerHeaders(f)
2028
+ }
2029
+
2030
+ // [...] The identifier of a newly established stream MUST be
2031
+ // numerically greater than all streams that the initiating
2032
+ // endpoint has opened or reserved. [...] An endpoint that
2033
+ // receives an unexpected stream identifier MUST respond with
2034
+ // a connection error (Section 5.4.1) of type PROTOCOL_ERROR.
2035
+ if id <= sc.maxClientStreamID {
2036
+ return sc.countError("stream_went_down", ConnectionError(ErrCodeProtocol))
2037
+ }
2038
+ sc.maxClientStreamID = id
2039
+
2040
+ if sc.idleTimer != nil {
2041
+ sc.idleTimer.Stop()
2042
+ }
2043
+
2044
+ // http://tools.ietf.org/html/rfc7540#section-5.1.2
2045
+ // [...] Endpoints MUST NOT exceed the limit set by their peer. An
2046
+ // endpoint that receives a HEADERS frame that causes their
2047
+ // advertised concurrent stream limit to be exceeded MUST treat
2048
+ // this as a stream error (Section 5.4.2) of type PROTOCOL_ERROR
2049
+ // or REFUSED_STREAM.
2050
+ if sc.curClientStreams+1 > sc.advMaxStreams {
2051
+ if sc.unackedSettings == 0 {
2052
+ // They should know better.
2053
+ return sc.countError("over_max_streams", streamError(id, ErrCodeProtocol))
2054
+ }
2055
+ // Assume it's a network race, where they just haven't
2056
+ // received our last SETTINGS update. But actually
2057
+ // this can't happen yet, because we don't yet provide
2058
+ // a way for users to adjust server parameters at
2059
+ // runtime.
2060
+ return sc.countError("over_max_streams_race", streamError(id, ErrCodeRefusedStream))
2061
+ }
2062
+
2063
+ initialState := stateOpen
2064
+ if f.StreamEnded() {
2065
+ initialState = stateHalfClosedRemote
2066
+ }
2067
+ st := sc.newStream(id, 0, initialState)
2068
+
2069
+ if f.HasPriority() {
2070
+ if err := sc.checkPriority(f.StreamID, f.Priority); err != nil {
2071
+ return err
2072
+ }
2073
+ sc.writeSched.AdjustStream(st.id, f.Priority)
2074
+ }
2075
+
2076
+ rw, req, err := sc.newWriterAndRequest(st, f)
2077
+ if err != nil {
2078
+ return err
2079
+ }
2080
+ st.reqTrailer = req.Trailer
2081
+ if st.reqTrailer != nil {
2082
+ st.trailer = make(http.Header)
2083
+ }
2084
+ st.body = req.Body.(*requestBody).pipe // may be nil
2085
+ st.declBodyBytes = req.ContentLength
2086
+
2087
+ handler := sc.handler.ServeHTTP
2088
+ if f.Truncated {
2089
+ // Their header list was too long. Send a 431 error.
2090
+ handler = handleHeaderListTooLong
2091
+ } else if err := checkValidHTTP2RequestHeaders(req.Header); err != nil {
2092
+ handler = new400Handler(err)
2093
+ }
2094
+
2095
+ // The net/http package sets the read deadline from the
2096
+ // http.Server.ReadTimeout during the TLS handshake, but then
2097
+ // passes the connection off to us with the deadline already
2098
+ // set. Disarm it here after the request headers are read,
2099
+ // similar to how the http1 server works. Here it's
2100
+ // technically more like the http1 Server's ReadHeaderTimeout
2101
+ // (in Go 1.8), though. That's a more sane option anyway.
2102
+ if sc.hs.ReadTimeout > 0 {
2103
+ sc.conn.SetReadDeadline(time.Time{})
2104
+ st.readDeadline = time.AfterFunc(sc.hs.ReadTimeout, st.onReadTimeout)
2105
+ }
2106
+
2107
+ return sc.scheduleHandler(id, rw, req, handler)
2108
+ }
2109
+
2110
+ func (sc *serverConn) upgradeRequest(req *http.Request) {
2111
+ sc.serveG.check()
2112
+ id := uint32(1)
2113
+ sc.maxClientStreamID = id
2114
+ st := sc.newStream(id, 0, stateHalfClosedRemote)
2115
+ st.reqTrailer = req.Trailer
2116
+ if st.reqTrailer != nil {
2117
+ st.trailer = make(http.Header)
2118
+ }
2119
+ rw := sc.newResponseWriter(st, req)
2120
+
2121
+ // Disable any read deadline set by the net/http package
2122
+ // prior to the upgrade.
2123
+ if sc.hs.ReadTimeout > 0 {
2124
+ sc.conn.SetReadDeadline(time.Time{})
2125
+ }
2126
+
2127
+ // This is the first request on the connection,
2128
+ // so start the handler directly rather than going
2129
+ // through scheduleHandler.
2130
+ sc.curHandlers++
2131
+ go sc.runHandler(rw, req, sc.handler.ServeHTTP)
2132
+ }
2133
+
2134
+ func (st *stream) processTrailerHeaders(f *MetaHeadersFrame) error {
2135
+ sc := st.sc
2136
+ sc.serveG.check()
2137
+ if st.gotTrailerHeader {
2138
+ return sc.countError("dup_trailers", ConnectionError(ErrCodeProtocol))
2139
+ }
2140
+ st.gotTrailerHeader = true
2141
+ if !f.StreamEnded() {
2142
+ return sc.countError("trailers_not_ended", streamError(st.id, ErrCodeProtocol))
2143
+ }
2144
+
2145
+ if len(f.PseudoFields()) > 0 {
2146
+ return sc.countError("trailers_pseudo", streamError(st.id, ErrCodeProtocol))
2147
+ }
2148
+ if st.trailer != nil {
2149
+ for _, hf := range f.RegularFields() {
2150
+ key := sc.canonicalHeader(hf.Name)
2151
+ if !httpguts.ValidTrailerHeader(key) {
2152
+ // TODO: send more details to the peer somehow. But http2 has
2153
+ // no way to send debug data at a stream level. Discuss with
2154
+ // HTTP folk.
2155
+ return sc.countError("trailers_bogus", streamError(st.id, ErrCodeProtocol))
2156
+ }
2157
+ st.trailer[key] = append(st.trailer[key], hf.Value)
2158
+ }
2159
+ }
2160
+ st.endStream()
2161
+ return nil
2162
+ }
2163
+
2164
+ func (sc *serverConn) checkPriority(streamID uint32, p PriorityParam) error {
2165
+ if streamID == p.StreamDep {
2166
+ // Section 5.3.1: "A stream cannot depend on itself. An endpoint MUST treat
2167
+ // this as a stream error (Section 5.4.2) of type PROTOCOL_ERROR."
2168
+ // Section 5.3.3 says that a stream can depend on one of its dependencies,
2169
+ // so it's only self-dependencies that are forbidden.
2170
+ return sc.countError("priority", streamError(streamID, ErrCodeProtocol))
2171
+ }
2172
+ return nil
2173
+ }
2174
+
2175
+ func (sc *serverConn) processPriority(f *PriorityFrame) error {
2176
+ if err := sc.checkPriority(f.StreamID, f.PriorityParam); err != nil {
2177
+ return err
2178
+ }
2179
+ sc.writeSched.AdjustStream(f.StreamID, f.PriorityParam)
2180
+ return nil
2181
+ }
2182
+
2183
+ func (sc *serverConn) newStream(id, pusherID uint32, state streamState) *stream {
2184
+ sc.serveG.check()
2185
+ if id == 0 {
2186
+ panic("internal error: cannot create stream with id 0")
2187
+ }
2188
+
2189
+ ctx, cancelCtx := context.WithCancel(sc.baseCtx)
2190
+ st := &stream{
2191
+ sc: sc,
2192
+ id: id,
2193
+ state: state,
2194
+ ctx: ctx,
2195
+ cancelCtx: cancelCtx,
2196
+ }
2197
+ st.cw.Init()
2198
+ st.flow.conn = &sc.flow // link to conn-level counter
2199
+ st.flow.add(sc.initialStreamSendWindowSize)
2200
+ st.inflow.init(sc.initialStreamRecvWindowSize)
2201
+ if sc.hs.WriteTimeout > 0 {
2202
+ st.writeDeadline = time.AfterFunc(sc.hs.WriteTimeout, st.onWriteTimeout)
2203
+ }
2204
+
2205
+ sc.streams[id] = st
2206
+ sc.writeSched.OpenStream(st.id, OpenStreamOptions{PusherID: pusherID})
2207
+ if st.isPushed() {
2208
+ sc.curPushedStreams++
2209
+ } else {
2210
+ sc.curClientStreams++
2211
+ }
2212
+ if sc.curOpenStreams() == 1 {
2213
+ sc.setConnState(http.StateActive)
2214
+ }
2215
+
2216
+ return st
2217
+ }
2218
+
2219
+ func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*responseWriter, *http.Request, error) {
2220
+ sc.serveG.check()
2221
+
2222
+ rp := httpcommon.ServerRequestParam{
2223
+ Method: f.PseudoValue("method"),
2224
+ Scheme: f.PseudoValue("scheme"),
2225
+ Authority: f.PseudoValue("authority"),
2226
+ Path: f.PseudoValue("path"),
2227
+ Protocol: f.PseudoValue("protocol"),
2228
+ }
2229
+
2230
+ // extended connect is disabled, so we should not see :protocol
2231
+ if disableExtendedConnectProtocol && rp.Protocol != "" {
2232
+ return nil, nil, sc.countError("bad_connect", streamError(f.StreamID, ErrCodeProtocol))
2233
+ }
2234
+
2235
+ isConnect := rp.Method == "CONNECT"
2236
+ if isConnect {
2237
+ if rp.Protocol == "" && (rp.Path != "" || rp.Scheme != "" || rp.Authority == "") {
2238
+ return nil, nil, sc.countError("bad_connect", streamError(f.StreamID, ErrCodeProtocol))
2239
+ }
2240
+ } else if rp.Method == "" || rp.Path == "" || (rp.Scheme != "https" && rp.Scheme != "http") {
2241
+ // See 8.1.2.6 Malformed Requests and Responses:
2242
+ //
2243
+ // Malformed requests or responses that are detected
2244
+ // MUST be treated as a stream error (Section 5.4.2)
2245
+ // of type PROTOCOL_ERROR."
2246
+ //
2247
+ // 8.1.2.3 Request Pseudo-Header Fields
2248
+ // "All HTTP/2 requests MUST include exactly one valid
2249
+ // value for the :method, :scheme, and :path
2250
+ // pseudo-header fields"
2251
+ return nil, nil, sc.countError("bad_path_method", streamError(f.StreamID, ErrCodeProtocol))
2252
+ }
2253
+
2254
+ header := make(http.Header)
2255
+ rp.Header = header
2256
+ for _, hf := range f.RegularFields() {
2257
+ header.Add(sc.canonicalHeader(hf.Name), hf.Value)
2258
+ }
2259
+ if rp.Authority == "" {
2260
+ rp.Authority = header.Get("Host")
2261
+ }
2262
+ if rp.Protocol != "" {
2263
+ header.Set(":protocol", rp.Protocol)
2264
+ }
2265
+
2266
+ rw, req, err := sc.newWriterAndRequestNoBody(st, rp)
2267
+ if err != nil {
2268
+ return nil, nil, err
2269
+ }
2270
+ bodyOpen := !f.StreamEnded()
2271
+ if bodyOpen {
2272
+ if vv, ok := rp.Header["Content-Length"]; ok {
2273
+ if cl, err := strconv.ParseUint(vv[0], 10, 63); err == nil {
2274
+ req.ContentLength = int64(cl)
2275
+ } else {
2276
+ req.ContentLength = 0
2277
+ }
2278
+ } else {
2279
+ req.ContentLength = -1
2280
+ }
2281
+ req.Body.(*requestBody).pipe = &pipe{
2282
+ b: &dataBuffer{expected: req.ContentLength},
2283
+ }
2284
+ }
2285
+ return rw, req, nil
2286
+ }
2287
+
2288
+ func (sc *serverConn) newWriterAndRequestNoBody(st *stream, rp httpcommon.ServerRequestParam) (*responseWriter, *http.Request, error) {
2289
+ sc.serveG.check()
2290
+
2291
+ var tlsState *tls.ConnectionState // nil if not scheme https
2292
+ if rp.Scheme == "https" {
2293
+ tlsState = sc.tlsState
2294
+ }
2295
+
2296
+ res := httpcommon.NewServerRequest(rp)
2297
+ if res.InvalidReason != "" {
2298
+ return nil, nil, sc.countError(res.InvalidReason, streamError(st.id, ErrCodeProtocol))
2299
+ }
2300
+
2301
+ body := &requestBody{
2302
+ conn: sc,
2303
+ stream: st,
2304
+ needsContinue: res.NeedsContinue,
2305
+ }
2306
+ req := (&http.Request{
2307
+ Method: rp.Method,
2308
+ URL: res.URL,
2309
+ RemoteAddr: sc.remoteAddrStr,
2310
+ Header: rp.Header,
2311
+ RequestURI: res.RequestURI,
2312
+ Proto: "HTTP/2.0",
2313
+ ProtoMajor: 2,
2314
+ ProtoMinor: 0,
2315
+ TLS: tlsState,
2316
+ Host: rp.Authority,
2317
+ Body: body,
2318
+ Trailer: res.Trailer,
2319
+ }).WithContext(st.ctx)
2320
+ rw := sc.newResponseWriter(st, req)
2321
+ return rw, req, nil
2322
+ }
2323
+
2324
+ func (sc *serverConn) newResponseWriter(st *stream, req *http.Request) *responseWriter {
2325
+ rws := responseWriterStatePool.Get().(*responseWriterState)
2326
+ bwSave := rws.bw
2327
+ *rws = responseWriterState{} // zero all the fields
2328
+ rws.conn = sc
2329
+ rws.bw = bwSave
2330
+ rws.bw.Reset(chunkWriter{rws})
2331
+ rws.stream = st
2332
+ rws.req = req
2333
+ return &responseWriter{rws: rws}
2334
+ }
2335
+
2336
+ type unstartedHandler struct {
2337
+ streamID uint32
2338
+ rw *responseWriter
2339
+ req *http.Request
2340
+ handler func(http.ResponseWriter, *http.Request)
2341
+ }
2342
+
2343
+ // scheduleHandler starts a handler goroutine,
2344
+ // or schedules one to start as soon as an existing handler finishes.
2345
+ func (sc *serverConn) scheduleHandler(streamID uint32, rw *responseWriter, req *http.Request, handler func(http.ResponseWriter, *http.Request)) error {
2346
+ sc.serveG.check()
2347
+ maxHandlers := sc.advMaxStreams
2348
+ if sc.curHandlers < maxHandlers {
2349
+ sc.curHandlers++
2350
+ go sc.runHandler(rw, req, handler)
2351
+ return nil
2352
+ }
2353
+ if len(sc.unstartedHandlers) > int(4*sc.advMaxStreams) {
2354
+ return sc.countError("too_many_early_resets", ConnectionError(ErrCodeEnhanceYourCalm))
2355
+ }
2356
+ sc.unstartedHandlers = append(sc.unstartedHandlers, unstartedHandler{
2357
+ streamID: streamID,
2358
+ rw: rw,
2359
+ req: req,
2360
+ handler: handler,
2361
+ })
2362
+ return nil
2363
+ }
2364
+
2365
+ func (sc *serverConn) handlerDone() {
2366
+ sc.serveG.check()
2367
+ sc.curHandlers--
2368
+ i := 0
2369
+ maxHandlers := sc.advMaxStreams
2370
+ for ; i < len(sc.unstartedHandlers); i++ {
2371
+ u := sc.unstartedHandlers[i]
2372
+ if sc.streams[u.streamID] == nil {
2373
+ // This stream was reset before its goroutine had a chance to start.
2374
+ continue
2375
+ }
2376
+ if sc.curHandlers >= maxHandlers {
2377
+ break
2378
+ }
2379
+ sc.curHandlers++
2380
+ go sc.runHandler(u.rw, u.req, u.handler)
2381
+ sc.unstartedHandlers[i] = unstartedHandler{} // don't retain references
2382
+ }
2383
+ sc.unstartedHandlers = sc.unstartedHandlers[i:]
2384
+ if len(sc.unstartedHandlers) == 0 {
2385
+ sc.unstartedHandlers = nil
2386
+ }
2387
+ }
2388
+
2389
+ // Run on its own goroutine.
2390
+ func (sc *serverConn) runHandler(rw *responseWriter, req *http.Request, handler func(http.ResponseWriter, *http.Request)) {
2391
+ defer sc.sendServeMsg(handlerDoneMsg)
2392
+ didPanic := true
2393
+ defer func() {
2394
+ rw.rws.stream.cancelCtx()
2395
+ if req.MultipartForm != nil {
2396
+ req.MultipartForm.RemoveAll()
2397
+ }
2398
+ if didPanic {
2399
+ e := recover()
2400
+ sc.writeFrameFromHandler(FrameWriteRequest{
2401
+ write: handlerPanicRST{rw.rws.stream.id},
2402
+ stream: rw.rws.stream,
2403
+ })
2404
+ // Same as net/http:
2405
+ if e != nil && e != http.ErrAbortHandler {
2406
+ const size = 64 << 10
2407
+ buf := make([]byte, size)
2408
+ buf = buf[:runtime.Stack(buf, false)]
2409
+ sc.logf("http2: panic serving %v: %v\n%s", sc.conn.RemoteAddr(), e, buf)
2410
+ }
2411
+ return
2412
+ }
2413
+ rw.handlerDone()
2414
+ }()
2415
+ handler(rw, req)
2416
+ didPanic = false
2417
+ }
2418
+
2419
+ func handleHeaderListTooLong(w http.ResponseWriter, r *http.Request) {
2420
+ // 10.5.1 Limits on Header Block Size:
2421
+ // .. "A server that receives a larger header block than it is
2422
+ // willing to handle can send an HTTP 431 (Request Header Fields Too
2423
+ // Large) status code"
2424
+ const statusRequestHeaderFieldsTooLarge = 431 // only in Go 1.6+
2425
+ w.WriteHeader(statusRequestHeaderFieldsTooLarge)
2426
+ io.WriteString(w, "<h1>HTTP Error 431</h1><p>Request Header Field(s) Too Large</p>")
2427
+ }
2428
+
2429
+ // called from handler goroutines.
2430
+ // h may be nil.
2431
+ func (sc *serverConn) writeHeaders(st *stream, headerData *writeResHeaders) error {
2432
+ sc.serveG.checkNotOn() // NOT on
2433
+ var errc chan error
2434
+ if headerData.h != nil {
2435
+ // If there's a header map (which we don't own), so we have to block on
2436
+ // waiting for this frame to be written, so an http.Flush mid-handler
2437
+ // writes out the correct value of keys, before a handler later potentially
2438
+ // mutates it.
2439
+ errc = getErrChan()
2440
+ }
2441
+ if err := sc.writeFrameFromHandler(FrameWriteRequest{
2442
+ write: headerData,
2443
+ stream: st,
2444
+ done: errc,
2445
+ }); err != nil {
2446
+ return err
2447
+ }
2448
+ if errc != nil {
2449
+ select {
2450
+ case err := <-errc:
2451
+ putErrChan(errc)
2452
+ return err
2453
+ case <-sc.doneServing:
2454
+ return errClientDisconnected
2455
+ case <-st.cw:
2456
+ return errStreamClosed
2457
+ }
2458
+ }
2459
+ return nil
2460
+ }
2461
+
2462
+ // called from handler goroutines.
2463
+ func (sc *serverConn) write100ContinueHeaders(st *stream) {
2464
+ sc.writeFrameFromHandler(FrameWriteRequest{
2465
+ write: write100ContinueHeadersFrame{st.id},
2466
+ stream: st,
2467
+ })
2468
+ }
2469
+
2470
+ // A bodyReadMsg tells the server loop that the http.Handler read n
2471
+ // bytes of the DATA from the client on the given stream.
2472
+ type bodyReadMsg struct {
2473
+ st *stream
2474
+ n int
2475
+ }
2476
+
2477
+ // called from handler goroutines.
2478
+ // Notes that the handler for the given stream ID read n bytes of its body
2479
+ // and schedules flow control tokens to be sent.
2480
+ func (sc *serverConn) noteBodyReadFromHandler(st *stream, n int, err error) {
2481
+ sc.serveG.checkNotOn() // NOT on
2482
+ if n > 0 {
2483
+ select {
2484
+ case sc.bodyReadCh <- bodyReadMsg{st, n}:
2485
+ case <-sc.doneServing:
2486
+ }
2487
+ }
2488
+ }
2489
+
2490
+ func (sc *serverConn) noteBodyRead(st *stream, n int) {
2491
+ sc.serveG.check()
2492
+ sc.sendWindowUpdate(nil, n) // conn-level
2493
+ if st.state != stateHalfClosedRemote && st.state != stateClosed {
2494
+ // Don't send this WINDOW_UPDATE if the stream is closed
2495
+ // remotely.
2496
+ sc.sendWindowUpdate(st, n)
2497
+ }
2498
+ }
2499
+
2500
+ // st may be nil for conn-level
2501
+ func (sc *serverConn) sendWindowUpdate32(st *stream, n int32) {
2502
+ sc.sendWindowUpdate(st, int(n))
2503
+ }
2504
+
2505
+ // st may be nil for conn-level
2506
+ func (sc *serverConn) sendWindowUpdate(st *stream, n int) {
2507
+ sc.serveG.check()
2508
+ var streamID uint32
2509
+ var send int32
2510
+ if st == nil {
2511
+ send = sc.inflow.add(n)
2512
+ } else {
2513
+ streamID = st.id
2514
+ send = st.inflow.add(n)
2515
+ }
2516
+ if send == 0 {
2517
+ return
2518
+ }
2519
+ sc.writeFrame(FrameWriteRequest{
2520
+ write: writeWindowUpdate{streamID: streamID, n: uint32(send)},
2521
+ stream: st,
2522
+ })
2523
+ }
2524
+
2525
+ // requestBody is the Handler's Request.Body type.
2526
+ // Read and Close may be called concurrently.
2527
+ type requestBody struct {
2528
+ _ incomparable
2529
+ stream *stream
2530
+ conn *serverConn
2531
+ closeOnce sync.Once // for use by Close only
2532
+ sawEOF bool // for use by Read only
2533
+ pipe *pipe // non-nil if we have an HTTP entity message body
2534
+ needsContinue bool // need to send a 100-continue
2535
+ }
2536
+
2537
+ func (b *requestBody) Close() error {
2538
+ b.closeOnce.Do(func() {
2539
+ if b.pipe != nil {
2540
+ b.pipe.BreakWithError(errClosedBody)
2541
+ }
2542
+ })
2543
+ return nil
2544
+ }
2545
+
2546
+ func (b *requestBody) Read(p []byte) (n int, err error) {
2547
+ if b.needsContinue {
2548
+ b.needsContinue = false
2549
+ b.conn.write100ContinueHeaders(b.stream)
2550
+ }
2551
+ if b.pipe == nil || b.sawEOF {
2552
+ return 0, io.EOF
2553
+ }
2554
+ n, err = b.pipe.Read(p)
2555
+ if err == io.EOF {
2556
+ b.sawEOF = true
2557
+ }
2558
+ if b.conn == nil {
2559
+ return
2560
+ }
2561
+ b.conn.noteBodyReadFromHandler(b.stream, n, err)
2562
+ return
2563
+ }
2564
+
2565
+ // responseWriter is the http.ResponseWriter implementation. It's
2566
+ // intentionally small (1 pointer wide) to minimize garbage. The
2567
+ // responseWriterState pointer inside is zeroed at the end of a
2568
+ // request (in handlerDone) and calls on the responseWriter thereafter
2569
+ // simply crash (caller's mistake), but the much larger responseWriterState
2570
+ // and buffers are reused between multiple requests.
2571
+ type responseWriter struct {
2572
+ rws *responseWriterState
2573
+ }
2574
+
2575
+ // Optional http.ResponseWriter interfaces implemented.
2576
+ var (
2577
+ _ http.CloseNotifier = (*responseWriter)(nil)
2578
+ _ http.Flusher = (*responseWriter)(nil)
2579
+ _ stringWriter = (*responseWriter)(nil)
2580
+ )
2581
+
2582
+ type responseWriterState struct {
2583
+ // immutable within a request:
2584
+ stream *stream
2585
+ req *http.Request
2586
+ conn *serverConn
2587
+
2588
+ // TODO: adjust buffer writing sizes based on server config, frame size updates from peer, etc
2589
+ bw *bufio.Writer // writing to a chunkWriter{this *responseWriterState}
2590
+
2591
+ // mutated by http.Handler goroutine:
2592
+ handlerHeader http.Header // nil until called
2593
+ snapHeader http.Header // snapshot of handlerHeader at WriteHeader time
2594
+ trailers []string // set in writeChunk
2595
+ status int // status code passed to WriteHeader
2596
+ wroteHeader bool // WriteHeader called (explicitly or implicitly). Not necessarily sent to user yet.
2597
+ sentHeader bool // have we sent the header frame?
2598
+ handlerDone bool // handler has finished
2599
+
2600
+ sentContentLen int64 // non-zero if handler set a Content-Length header
2601
+ wroteBytes int64
2602
+
2603
+ closeNotifierMu sync.Mutex // guards closeNotifierCh
2604
+ closeNotifierCh chan bool // nil until first used
2605
+ }
2606
+
2607
+ type chunkWriter struct{ rws *responseWriterState }
2608
+
2609
+ func (cw chunkWriter) Write(p []byte) (n int, err error) {
2610
+ n, err = cw.rws.writeChunk(p)
2611
+ if err == errStreamClosed {
2612
+ // If writing failed because the stream has been closed,
2613
+ // return the reason it was closed.
2614
+ err = cw.rws.stream.closeErr
2615
+ }
2616
+ return n, err
2617
+ }
2618
+
2619
+ func (rws *responseWriterState) hasTrailers() bool { return len(rws.trailers) > 0 }
2620
+
2621
+ func (rws *responseWriterState) hasNonemptyTrailers() bool {
2622
+ for _, trailer := range rws.trailers {
2623
+ if _, ok := rws.handlerHeader[trailer]; ok {
2624
+ return true
2625
+ }
2626
+ }
2627
+ return false
2628
+ }
2629
+
2630
+ // declareTrailer is called for each Trailer header when the
2631
+ // response header is written. It notes that a header will need to be
2632
+ // written in the trailers at the end of the response.
2633
+ func (rws *responseWriterState) declareTrailer(k string) {
2634
+ k = http.CanonicalHeaderKey(k)
2635
+ if !httpguts.ValidTrailerHeader(k) {
2636
+ // Forbidden by RFC 7230, section 4.1.2.
2637
+ rws.conn.logf("ignoring invalid trailer %q", k)
2638
+ return
2639
+ }
2640
+ if !strSliceContains(rws.trailers, k) {
2641
+ rws.trailers = append(rws.trailers, k)
2642
+ }
2643
+ }
2644
+
2645
+ // writeChunk writes chunks from the bufio.Writer. But because
2646
+ // bufio.Writer may bypass its chunking, sometimes p may be
2647
+ // arbitrarily large.
2648
+ //
2649
+ // writeChunk is also responsible (on the first chunk) for sending the
2650
+ // HEADER response.
2651
+ func (rws *responseWriterState) writeChunk(p []byte) (n int, err error) {
2652
+ if !rws.wroteHeader {
2653
+ rws.writeHeader(200)
2654
+ }
2655
+
2656
+ if rws.handlerDone {
2657
+ rws.promoteUndeclaredTrailers()
2658
+ }
2659
+
2660
+ isHeadResp := rws.req.Method == "HEAD"
2661
+ if !rws.sentHeader {
2662
+ rws.sentHeader = true
2663
+ var ctype, clen string
2664
+ if clen = rws.snapHeader.Get("Content-Length"); clen != "" {
2665
+ rws.snapHeader.Del("Content-Length")
2666
+ if cl, err := strconv.ParseUint(clen, 10, 63); err == nil {
2667
+ rws.sentContentLen = int64(cl)
2668
+ } else {
2669
+ clen = ""
2670
+ }
2671
+ }
2672
+ _, hasContentLength := rws.snapHeader["Content-Length"]
2673
+ if !hasContentLength && clen == "" && rws.handlerDone && bodyAllowedForStatus(rws.status) && (len(p) > 0 || !isHeadResp) {
2674
+ clen = strconv.Itoa(len(p))
2675
+ }
2676
+ _, hasContentType := rws.snapHeader["Content-Type"]
2677
+ // If the Content-Encoding is non-blank, we shouldn't
2678
+ // sniff the body. See Issue golang.org/issue/31753.
2679
+ ce := rws.snapHeader.Get("Content-Encoding")
2680
+ hasCE := len(ce) > 0
2681
+ if !hasCE && !hasContentType && bodyAllowedForStatus(rws.status) && len(p) > 0 {
2682
+ ctype = http.DetectContentType(p)
2683
+ }
2684
+ var date string
2685
+ if _, ok := rws.snapHeader["Date"]; !ok {
2686
+ // TODO(bradfitz): be faster here, like net/http? measure.
2687
+ date = time.Now().UTC().Format(http.TimeFormat)
2688
+ }
2689
+
2690
+ for _, v := range rws.snapHeader["Trailer"] {
2691
+ foreachHeaderElement(v, rws.declareTrailer)
2692
+ }
2693
+
2694
+ // "Connection" headers aren't allowed in HTTP/2 (RFC 7540, 8.1.2.2),
2695
+ // but respect "Connection" == "close" to mean sending a GOAWAY and tearing
2696
+ // down the TCP connection when idle, like we do for HTTP/1.
2697
+ // TODO: remove more Connection-specific header fields here, in addition
2698
+ // to "Connection".
2699
+ if _, ok := rws.snapHeader["Connection"]; ok {
2700
+ v := rws.snapHeader.Get("Connection")
2701
+ delete(rws.snapHeader, "Connection")
2702
+ if v == "close" {
2703
+ rws.conn.startGracefulShutdown()
2704
+ }
2705
+ }
2706
+
2707
+ endStream := (rws.handlerDone && !rws.hasTrailers() && len(p) == 0) || isHeadResp
2708
+ err = rws.conn.writeHeaders(rws.stream, &writeResHeaders{
2709
+ streamID: rws.stream.id,
2710
+ httpResCode: rws.status,
2711
+ h: rws.snapHeader,
2712
+ endStream: endStream,
2713
+ contentType: ctype,
2714
+ contentLength: clen,
2715
+ date: date,
2716
+ })
2717
+ if err != nil {
2718
+ return 0, err
2719
+ }
2720
+ if endStream {
2721
+ return 0, nil
2722
+ }
2723
+ }
2724
+ if isHeadResp {
2725
+ return len(p), nil
2726
+ }
2727
+ if len(p) == 0 && !rws.handlerDone {
2728
+ return 0, nil
2729
+ }
2730
+
2731
+ // only send trailers if they have actually been defined by the
2732
+ // server handler.
2733
+ hasNonemptyTrailers := rws.hasNonemptyTrailers()
2734
+ endStream := rws.handlerDone && !hasNonemptyTrailers
2735
+ if len(p) > 0 || endStream {
2736
+ // only send a 0 byte DATA frame if we're ending the stream.
2737
+ if err := rws.conn.writeDataFromHandler(rws.stream, p, endStream); err != nil {
2738
+ return 0, err
2739
+ }
2740
+ }
2741
+
2742
+ if rws.handlerDone && hasNonemptyTrailers {
2743
+ err = rws.conn.writeHeaders(rws.stream, &writeResHeaders{
2744
+ streamID: rws.stream.id,
2745
+ h: rws.handlerHeader,
2746
+ trailers: rws.trailers,
2747
+ endStream: true,
2748
+ })
2749
+ return len(p), err
2750
+ }
2751
+ return len(p), nil
2752
+ }
2753
+
2754
+ // TrailerPrefix is a magic prefix for ResponseWriter.Header map keys
2755
+ // that, if present, signals that the map entry is actually for
2756
+ // the response trailers, and not the response headers. The prefix
2757
+ // is stripped after the ServeHTTP call finishes and the values are
2758
+ // sent in the trailers.
2759
+ //
2760
+ // This mechanism is intended only for trailers that are not known
2761
+ // prior to the headers being written. If the set of trailers is fixed
2762
+ // or known before the header is written, the normal Go trailers mechanism
2763
+ // is preferred:
2764
+ //
2765
+ // https://golang.org/pkg/net/http/#ResponseWriter
2766
+ // https://golang.org/pkg/net/http/#example_ResponseWriter_trailers
2767
+ const TrailerPrefix = "Trailer:"
2768
+
2769
+ // promoteUndeclaredTrailers permits http.Handlers to set trailers
2770
+ // after the header has already been flushed. Because the Go
2771
+ // ResponseWriter interface has no way to set Trailers (only the
2772
+ // Header), and because we didn't want to expand the ResponseWriter
2773
+ // interface, and because nobody used trailers, and because RFC 7230
2774
+ // says you SHOULD (but not must) predeclare any trailers in the
2775
+ // header, the official ResponseWriter rules said trailers in Go must
2776
+ // be predeclared, and then we reuse the same ResponseWriter.Header()
2777
+ // map to mean both Headers and Trailers. When it's time to write the
2778
+ // Trailers, we pick out the fields of Headers that were declared as
2779
+ // trailers. That worked for a while, until we found the first major
2780
+ // user of Trailers in the wild: gRPC (using them only over http2),
2781
+ // and gRPC libraries permit setting trailers mid-stream without
2782
+ // predeclaring them. So: change of plans. We still permit the old
2783
+ // way, but we also permit this hack: if a Header() key begins with
2784
+ // "Trailer:", the suffix of that key is a Trailer. Because ':' is an
2785
+ // invalid token byte anyway, there is no ambiguity. (And it's already
2786
+ // filtered out) It's mildly hacky, but not terrible.
2787
+ //
2788
+ // This method runs after the Handler is done and promotes any Header
2789
+ // fields to be trailers.
2790
+ func (rws *responseWriterState) promoteUndeclaredTrailers() {
2791
+ for k, vv := range rws.handlerHeader {
2792
+ if !strings.HasPrefix(k, TrailerPrefix) {
2793
+ continue
2794
+ }
2795
+ trailerKey := strings.TrimPrefix(k, TrailerPrefix)
2796
+ rws.declareTrailer(trailerKey)
2797
+ rws.handlerHeader[http.CanonicalHeaderKey(trailerKey)] = vv
2798
+ }
2799
+
2800
+ if len(rws.trailers) > 1 {
2801
+ sorter := sorterPool.Get().(*sorter)
2802
+ sorter.SortStrings(rws.trailers)
2803
+ sorterPool.Put(sorter)
2804
+ }
2805
+ }
2806
+
2807
+ func (w *responseWriter) SetReadDeadline(deadline time.Time) error {
2808
+ st := w.rws.stream
2809
+ if !deadline.IsZero() && deadline.Before(time.Now()) {
2810
+ // If we're setting a deadline in the past, reset the stream immediately
2811
+ // so writes after SetWriteDeadline returns will fail.
2812
+ st.onReadTimeout()
2813
+ return nil
2814
+ }
2815
+ w.rws.conn.sendServeMsg(func(sc *serverConn) {
2816
+ if st.readDeadline != nil {
2817
+ if !st.readDeadline.Stop() {
2818
+ // Deadline already exceeded, or stream has been closed.
2819
+ return
2820
+ }
2821
+ }
2822
+ if deadline.IsZero() {
2823
+ st.readDeadline = nil
2824
+ } else if st.readDeadline == nil {
2825
+ st.readDeadline = time.AfterFunc(deadline.Sub(time.Now()), st.onReadTimeout)
2826
+ } else {
2827
+ st.readDeadline.Reset(deadline.Sub(time.Now()))
2828
+ }
2829
+ })
2830
+ return nil
2831
+ }
2832
+
2833
+ func (w *responseWriter) SetWriteDeadline(deadline time.Time) error {
2834
+ st := w.rws.stream
2835
+ if !deadline.IsZero() && deadline.Before(time.Now()) {
2836
+ // If we're setting a deadline in the past, reset the stream immediately
2837
+ // so writes after SetWriteDeadline returns will fail.
2838
+ st.onWriteTimeout()
2839
+ return nil
2840
+ }
2841
+ w.rws.conn.sendServeMsg(func(sc *serverConn) {
2842
+ if st.writeDeadline != nil {
2843
+ if !st.writeDeadline.Stop() {
2844
+ // Deadline already exceeded, or stream has been closed.
2845
+ return
2846
+ }
2847
+ }
2848
+ if deadline.IsZero() {
2849
+ st.writeDeadline = nil
2850
+ } else if st.writeDeadline == nil {
2851
+ st.writeDeadline = time.AfterFunc(deadline.Sub(time.Now()), st.onWriteTimeout)
2852
+ } else {
2853
+ st.writeDeadline.Reset(deadline.Sub(time.Now()))
2854
+ }
2855
+ })
2856
+ return nil
2857
+ }
2858
+
2859
+ func (w *responseWriter) EnableFullDuplex() error {
2860
+ // We always support full duplex responses, so this is a no-op.
2861
+ return nil
2862
+ }
2863
+
2864
+ func (w *responseWriter) Flush() {
2865
+ w.FlushError()
2866
+ }
2867
+
2868
+ func (w *responseWriter) FlushError() error {
2869
+ rws := w.rws
2870
+ if rws == nil {
2871
+ panic("Header called after Handler finished")
2872
+ }
2873
+ var err error
2874
+ if rws.bw.Buffered() > 0 {
2875
+ err = rws.bw.Flush()
2876
+ } else {
2877
+ // The bufio.Writer won't call chunkWriter.Write
2878
+ // (writeChunk with zero bytes), so we have to do it
2879
+ // ourselves to force the HTTP response header and/or
2880
+ // final DATA frame (with END_STREAM) to be sent.
2881
+ _, err = chunkWriter{rws}.Write(nil)
2882
+ if err == nil {
2883
+ select {
2884
+ case <-rws.stream.cw:
2885
+ err = rws.stream.closeErr
2886
+ default:
2887
+ }
2888
+ }
2889
+ }
2890
+ return err
2891
+ }
2892
+
2893
+ func (w *responseWriter) CloseNotify() <-chan bool {
2894
+ rws := w.rws
2895
+ if rws == nil {
2896
+ panic("CloseNotify called after Handler finished")
2897
+ }
2898
+ rws.closeNotifierMu.Lock()
2899
+ ch := rws.closeNotifierCh
2900
+ if ch == nil {
2901
+ ch = make(chan bool, 1)
2902
+ rws.closeNotifierCh = ch
2903
+ cw := rws.stream.cw
2904
+ go func() {
2905
+ cw.Wait() // wait for close
2906
+ ch <- true
2907
+ }()
2908
+ }
2909
+ rws.closeNotifierMu.Unlock()
2910
+ return ch
2911
+ }
2912
+
2913
+ func (w *responseWriter) Header() http.Header {
2914
+ rws := w.rws
2915
+ if rws == nil {
2916
+ panic("Header called after Handler finished")
2917
+ }
2918
+ if rws.handlerHeader == nil {
2919
+ rws.handlerHeader = make(http.Header)
2920
+ }
2921
+ return rws.handlerHeader
2922
+ }
2923
+
2924
+ // checkWriteHeaderCode is a copy of net/http's checkWriteHeaderCode.
2925
+ func checkWriteHeaderCode(code int) {
2926
+ // Issue 22880: require valid WriteHeader status codes.
2927
+ // For now we only enforce that it's three digits.
2928
+ // In the future we might block things over 599 (600 and above aren't defined
2929
+ // at http://httpwg.org/specs/rfc7231.html#status.codes).
2930
+ // But for now any three digits.
2931
+ //
2932
+ // We used to send "HTTP/1.1 000 0" on the wire in responses but there's
2933
+ // no equivalent bogus thing we can realistically send in HTTP/2,
2934
+ // so we'll consistently panic instead and help people find their bugs
2935
+ // early. (We can't return an error from WriteHeader even if we wanted to.)
2936
+ if code < 100 || code > 999 {
2937
+ panic(fmt.Sprintf("invalid WriteHeader code %v", code))
2938
+ }
2939
+ }
2940
+
2941
+ func (w *responseWriter) WriteHeader(code int) {
2942
+ rws := w.rws
2943
+ if rws == nil {
2944
+ panic("WriteHeader called after Handler finished")
2945
+ }
2946
+ rws.writeHeader(code)
2947
+ }
2948
+
2949
+ func (rws *responseWriterState) writeHeader(code int) {
2950
+ if rws.wroteHeader {
2951
+ return
2952
+ }
2953
+
2954
+ checkWriteHeaderCode(code)
2955
+
2956
+ // Handle informational headers
2957
+ if code >= 100 && code <= 199 {
2958
+ // Per RFC 8297 we must not clear the current header map
2959
+ h := rws.handlerHeader
2960
+
2961
+ _, cl := h["Content-Length"]
2962
+ _, te := h["Transfer-Encoding"]
2963
+ if cl || te {
2964
+ h = h.Clone()
2965
+ h.Del("Content-Length")
2966
+ h.Del("Transfer-Encoding")
2967
+ }
2968
+
2969
+ rws.conn.writeHeaders(rws.stream, &writeResHeaders{
2970
+ streamID: rws.stream.id,
2971
+ httpResCode: code,
2972
+ h: h,
2973
+ endStream: rws.handlerDone && !rws.hasTrailers(),
2974
+ })
2975
+
2976
+ return
2977
+ }
2978
+
2979
+ rws.wroteHeader = true
2980
+ rws.status = code
2981
+ if len(rws.handlerHeader) > 0 {
2982
+ rws.snapHeader = cloneHeader(rws.handlerHeader)
2983
+ }
2984
+ }
2985
+
2986
+ func cloneHeader(h http.Header) http.Header {
2987
+ h2 := make(http.Header, len(h))
2988
+ for k, vv := range h {
2989
+ vv2 := make([]string, len(vv))
2990
+ copy(vv2, vv)
2991
+ h2[k] = vv2
2992
+ }
2993
+ return h2
2994
+ }
2995
+
2996
+ // The Life Of A Write is like this:
2997
+ //
2998
+ // * Handler calls w.Write or w.WriteString ->
2999
+ // * -> rws.bw (*bufio.Writer) ->
3000
+ // * (Handler might call Flush)
3001
+ // * -> chunkWriter{rws}
3002
+ // * -> responseWriterState.writeChunk(p []byte)
3003
+ // * -> responseWriterState.writeChunk (most of the magic; see comment there)
3004
+ func (w *responseWriter) Write(p []byte) (n int, err error) {
3005
+ return w.write(len(p), p, "")
3006
+ }
3007
+
3008
+ func (w *responseWriter) WriteString(s string) (n int, err error) {
3009
+ return w.write(len(s), nil, s)
3010
+ }
3011
+
3012
+ // either dataB or dataS is non-zero.
3013
+ func (w *responseWriter) write(lenData int, dataB []byte, dataS string) (n int, err error) {
3014
+ rws := w.rws
3015
+ if rws == nil {
3016
+ panic("Write called after Handler finished")
3017
+ }
3018
+ if !rws.wroteHeader {
3019
+ w.WriteHeader(200)
3020
+ }
3021
+ if !bodyAllowedForStatus(rws.status) {
3022
+ return 0, http.ErrBodyNotAllowed
3023
+ }
3024
+ rws.wroteBytes += int64(len(dataB)) + int64(len(dataS)) // only one can be set
3025
+ if rws.sentContentLen != 0 && rws.wroteBytes > rws.sentContentLen {
3026
+ // TODO: send a RST_STREAM
3027
+ return 0, errors.New("http2: handler wrote more than declared Content-Length")
3028
+ }
3029
+
3030
+ if dataB != nil {
3031
+ return rws.bw.Write(dataB)
3032
+ } else {
3033
+ return rws.bw.WriteString(dataS)
3034
+ }
3035
+ }
3036
+
3037
+ func (w *responseWriter) handlerDone() {
3038
+ rws := w.rws
3039
+ rws.handlerDone = true
3040
+ w.Flush()
3041
+ w.rws = nil
3042
+ responseWriterStatePool.Put(rws)
3043
+ }
3044
+
3045
+ // Push errors.
3046
+ var (
3047
+ ErrRecursivePush = errors.New("http2: recursive push not allowed")
3048
+ ErrPushLimitReached = errors.New("http2: push would exceed peer's SETTINGS_MAX_CONCURRENT_STREAMS")
3049
+ )
3050
+
3051
+ var _ http.Pusher = (*responseWriter)(nil)
3052
+
3053
+ func (w *responseWriter) Push(target string, opts *http.PushOptions) error {
3054
+ st := w.rws.stream
3055
+ sc := st.sc
3056
+ sc.serveG.checkNotOn()
3057
+
3058
+ // No recursive pushes: "PUSH_PROMISE frames MUST only be sent on a peer-initiated stream."
3059
+ // http://tools.ietf.org/html/rfc7540#section-6.6
3060
+ if st.isPushed() {
3061
+ return ErrRecursivePush
3062
+ }
3063
+
3064
+ if opts == nil {
3065
+ opts = new(http.PushOptions)
3066
+ }
3067
+
3068
+ // Default options.
3069
+ if opts.Method == "" {
3070
+ opts.Method = "GET"
3071
+ }
3072
+ if opts.Header == nil {
3073
+ opts.Header = http.Header{}
3074
+ }
3075
+ wantScheme := "http"
3076
+ if w.rws.req.TLS != nil {
3077
+ wantScheme = "https"
3078
+ }
3079
+
3080
+ // Validate the request.
3081
+ u, err := url.Parse(target)
3082
+ if err != nil {
3083
+ return err
3084
+ }
3085
+ if u.Scheme == "" {
3086
+ if !strings.HasPrefix(target, "/") {
3087
+ return fmt.Errorf("target must be an absolute URL or an absolute path: %q", target)
3088
+ }
3089
+ u.Scheme = wantScheme
3090
+ u.Host = w.rws.req.Host
3091
+ } else {
3092
+ if u.Scheme != wantScheme {
3093
+ return fmt.Errorf("cannot push URL with scheme %q from request with scheme %q", u.Scheme, wantScheme)
3094
+ }
3095
+ if u.Host == "" {
3096
+ return errors.New("URL must have a host")
3097
+ }
3098
+ }
3099
+ for k := range opts.Header {
3100
+ if strings.HasPrefix(k, ":") {
3101
+ return fmt.Errorf("promised request headers cannot include pseudo header %q", k)
3102
+ }
3103
+ // These headers are meaningful only if the request has a body,
3104
+ // but PUSH_PROMISE requests cannot have a body.
3105
+ // http://tools.ietf.org/html/rfc7540#section-8.2
3106
+ // Also disallow Host, since the promised URL must be absolute.
3107
+ if asciiEqualFold(k, "content-length") ||
3108
+ asciiEqualFold(k, "content-encoding") ||
3109
+ asciiEqualFold(k, "trailer") ||
3110
+ asciiEqualFold(k, "te") ||
3111
+ asciiEqualFold(k, "expect") ||
3112
+ asciiEqualFold(k, "host") {
3113
+ return fmt.Errorf("promised request headers cannot include %q", k)
3114
+ }
3115
+ }
3116
+ if err := checkValidHTTP2RequestHeaders(opts.Header); err != nil {
3117
+ return err
3118
+ }
3119
+
3120
+ // The RFC effectively limits promised requests to GET and HEAD:
3121
+ // "Promised requests MUST be cacheable [GET, HEAD, or POST], and MUST be safe [GET or HEAD]"
3122
+ // http://tools.ietf.org/html/rfc7540#section-8.2
3123
+ if opts.Method != "GET" && opts.Method != "HEAD" {
3124
+ return fmt.Errorf("method %q must be GET or HEAD", opts.Method)
3125
+ }
3126
+
3127
+ msg := &startPushRequest{
3128
+ parent: st,
3129
+ method: opts.Method,
3130
+ url: u,
3131
+ header: cloneHeader(opts.Header),
3132
+ done: getErrChan(),
3133
+ }
3134
+
3135
+ select {
3136
+ case <-sc.doneServing:
3137
+ return errClientDisconnected
3138
+ case <-st.cw:
3139
+ return errStreamClosed
3140
+ case sc.serveMsgCh <- msg:
3141
+ }
3142
+
3143
+ select {
3144
+ case <-sc.doneServing:
3145
+ return errClientDisconnected
3146
+ case <-st.cw:
3147
+ return errStreamClosed
3148
+ case err := <-msg.done:
3149
+ putErrChan(msg.done)
3150
+ return err
3151
+ }
3152
+ }
3153
+
3154
+ type startPushRequest struct {
3155
+ parent *stream
3156
+ method string
3157
+ url *url.URL
3158
+ header http.Header
3159
+ done chan error
3160
+ }
3161
+
3162
+ func (sc *serverConn) startPush(msg *startPushRequest) {
3163
+ sc.serveG.check()
3164
+
3165
+ // http://tools.ietf.org/html/rfc7540#section-6.6.
3166
+ // PUSH_PROMISE frames MUST only be sent on a peer-initiated stream that
3167
+ // is in either the "open" or "half-closed (remote)" state.
3168
+ if msg.parent.state != stateOpen && msg.parent.state != stateHalfClosedRemote {
3169
+ // responseWriter.Push checks that the stream is peer-initiated.
3170
+ msg.done <- errStreamClosed
3171
+ return
3172
+ }
3173
+
3174
+ // http://tools.ietf.org/html/rfc7540#section-6.6.
3175
+ if !sc.pushEnabled {
3176
+ msg.done <- http.ErrNotSupported
3177
+ return
3178
+ }
3179
+
3180
+ // PUSH_PROMISE frames must be sent in increasing order by stream ID, so
3181
+ // we allocate an ID for the promised stream lazily, when the PUSH_PROMISE
3182
+ // is written. Once the ID is allocated, we start the request handler.
3183
+ allocatePromisedID := func() (uint32, error) {
3184
+ sc.serveG.check()
3185
+
3186
+ // Check this again, just in case. Technically, we might have received
3187
+ // an updated SETTINGS by the time we got around to writing this frame.
3188
+ if !sc.pushEnabled {
3189
+ return 0, http.ErrNotSupported
3190
+ }
3191
+ // http://tools.ietf.org/html/rfc7540#section-6.5.2.
3192
+ if sc.curPushedStreams+1 > sc.clientMaxStreams {
3193
+ return 0, ErrPushLimitReached
3194
+ }
3195
+
3196
+ // http://tools.ietf.org/html/rfc7540#section-5.1.1.
3197
+ // Streams initiated by the server MUST use even-numbered identifiers.
3198
+ // A server that is unable to establish a new stream identifier can send a GOAWAY
3199
+ // frame so that the client is forced to open a new connection for new streams.
3200
+ if sc.maxPushPromiseID+2 >= 1<<31 {
3201
+ sc.startGracefulShutdownInternal()
3202
+ return 0, ErrPushLimitReached
3203
+ }
3204
+ sc.maxPushPromiseID += 2
3205
+ promisedID := sc.maxPushPromiseID
3206
+
3207
+ // http://tools.ietf.org/html/rfc7540#section-8.2.
3208
+ // Strictly speaking, the new stream should start in "reserved (local)", then
3209
+ // transition to "half closed (remote)" after sending the initial HEADERS, but
3210
+ // we start in "half closed (remote)" for simplicity.
3211
+ // See further comments at the definition of stateHalfClosedRemote.
3212
+ promised := sc.newStream(promisedID, msg.parent.id, stateHalfClosedRemote)
3213
+ rw, req, err := sc.newWriterAndRequestNoBody(promised, httpcommon.ServerRequestParam{
3214
+ Method: msg.method,
3215
+ Scheme: msg.url.Scheme,
3216
+ Authority: msg.url.Host,
3217
+ Path: msg.url.RequestURI(),
3218
+ Header: cloneHeader(msg.header), // clone since handler runs concurrently with writing the PUSH_PROMISE
3219
+ })
3220
+ if err != nil {
3221
+ // Should not happen, since we've already validated msg.url.
3222
+ panic(fmt.Sprintf("newWriterAndRequestNoBody(%+v): %v", msg.url, err))
3223
+ }
3224
+
3225
+ sc.curHandlers++
3226
+ go sc.runHandler(rw, req, sc.handler.ServeHTTP)
3227
+ return promisedID, nil
3228
+ }
3229
+
3230
+ sc.writeFrame(FrameWriteRequest{
3231
+ write: &writePushPromise{
3232
+ streamID: msg.parent.id,
3233
+ method: msg.method,
3234
+ url: msg.url,
3235
+ h: msg.header,
3236
+ allocatePromisedID: allocatePromisedID,
3237
+ },
3238
+ stream: msg.parent,
3239
+ done: msg.done,
3240
+ })
3241
+ }
3242
+
3243
+ // foreachHeaderElement splits v according to the "#rule" construction
3244
+ // in RFC 7230 section 7 and calls fn for each non-empty element.
3245
+ func foreachHeaderElement(v string, fn func(string)) {
3246
+ v = textproto.TrimString(v)
3247
+ if v == "" {
3248
+ return
3249
+ }
3250
+ if !strings.Contains(v, ",") {
3251
+ fn(v)
3252
+ return
3253
+ }
3254
+ for _, f := range strings.Split(v, ",") {
3255
+ if f = textproto.TrimString(f); f != "" {
3256
+ fn(f)
3257
+ }
3258
+ }
3259
+ }
3260
+
3261
+ // From http://httpwg.org/specs/rfc7540.html#rfc.section.8.1.2.2
3262
+ var connHeaders = []string{
3263
+ "Connection",
3264
+ "Keep-Alive",
3265
+ "Proxy-Connection",
3266
+ "Transfer-Encoding",
3267
+ "Upgrade",
3268
+ }
3269
+
3270
+ // checkValidHTTP2RequestHeaders checks whether h is a valid HTTP/2 request,
3271
+ // per RFC 7540 Section 8.1.2.2.
3272
+ // The returned error is reported to users.
3273
+ func checkValidHTTP2RequestHeaders(h http.Header) error {
3274
+ for _, k := range connHeaders {
3275
+ if _, ok := h[k]; ok {
3276
+ return fmt.Errorf("request header %q is not valid in HTTP/2", k)
3277
+ }
3278
+ }
3279
+ te := h["Te"]
3280
+ if len(te) > 0 && (len(te) > 1 || (te[0] != "trailers" && te[0] != "")) {
3281
+ return errors.New(`request header "TE" may only be "trailers" in HTTP/2`)
3282
+ }
3283
+ return nil
3284
+ }
3285
+
3286
+ func new400Handler(err error) http.HandlerFunc {
3287
+ return func(w http.ResponseWriter, r *http.Request) {
3288
+ http.Error(w, err.Error(), http.StatusBadRequest)
3289
+ }
3290
+ }
3291
+
3292
+ // h1ServerKeepAlivesDisabled reports whether hs has its keep-alives
3293
+ // disabled. See comments on h1ServerShutdownChan above for why
3294
+ // the code is written this way.
3295
+ func h1ServerKeepAlivesDisabled(hs *http.Server) bool {
3296
+ var x interface{} = hs
3297
+ type I interface {
3298
+ doKeepAlives() bool
3299
+ }
3300
+ if hs, ok := x.(I); ok {
3301
+ return !hs.doKeepAlives()
3302
+ }
3303
+ return false
3304
+ }
3305
+
3306
+ func (sc *serverConn) countError(name string, err error) error {
3307
+ if sc == nil || sc.srv == nil {
3308
+ return err
3309
+ }
3310
+ f := sc.countErrorFunc
3311
+ if f == nil {
3312
+ return err
3313
+ }
3314
+ var typ string
3315
+ var code ErrCode
3316
+ switch e := err.(type) {
3317
+ case ConnectionError:
3318
+ typ = "conn"
3319
+ code = ErrCode(e)
3320
+ case StreamError:
3321
+ typ = "stream"
3322
+ code = ErrCode(e.Code)
3323
+ default:
3324
+ return err
3325
+ }
3326
+ codeStr := errCodeName[code]
3327
+ if codeStr == "" {
3328
+ codeStr = strconv.Itoa(int(code))
3329
+ }
3330
+ f(fmt.Sprintf("%s_%s_%s", typ, codeStr, name))
3331
+ return err
3332
+ }