mirror of
https://github.com/mickael-kerjean/filestash
synced 2025-12-07 17:02:29 +01:00
maintain (dep): Bump golang.org/x/crypto from 0.0.0-20220131195533-30dcbda58838 to 0.1.0 (#572)
Bumps [golang.org/x/crypto](https://github.com/golang/crypto) from 0.0.0-20220131195533-30dcbda58838 to 0.1.0. - [Release notes](https://github.com/golang/crypto/releases) - [Commits](https://github.com/golang/crypto/commits/v0.1.0) --- updated-dependencies: - dependency-name: golang.org/x/crypto dependency-type: direct:production ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
This commit is contained in:
parent
b3d1e8681b
commit
88412fb13f
278 changed files with 21070 additions and 7727 deletions
6
go.mod
6
go.mod
|
|
@ -33,11 +33,11 @@ require (
|
||||||
github.com/tredoe/osutil v1.0.6
|
github.com/tredoe/osutil v1.0.6
|
||||||
github.com/vmware/go-nfs-client v0.0.0-20190605212624-d43b92724c1b
|
github.com/vmware/go-nfs-client v0.0.0-20190605212624-d43b92724c1b
|
||||||
github.com/wayneashleyberry/terminal-dimensions v1.1.0 // indirect
|
github.com/wayneashleyberry/terminal-dimensions v1.1.0 // indirect
|
||||||
golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838
|
golang.org/x/crypto v0.1.0
|
||||||
golang.org/x/image v0.0.0-20211028202545-6944b10bf410
|
golang.org/x/image v0.0.0-20211028202545-6944b10bf410
|
||||||
golang.org/x/net v0.0.0-20211118161319-6a13c67c3ce4
|
golang.org/x/net v0.1.0
|
||||||
golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d
|
golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d
|
||||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c
|
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4
|
||||||
golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9
|
golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9
|
||||||
google.golang.org/api v0.15.0
|
google.golang.org/api v0.15.0
|
||||||
gopkg.in/alexcesaro/quotedprintable.v3 v3.0.0-20150716171945-2caba252f4dc // indirect
|
gopkg.in/alexcesaro/quotedprintable.v3 v3.0.0-20150716171945-2caba252f4dc // indirect
|
||||||
|
|
|
||||||
36
go.sum
36
go.sum
|
|
@ -287,6 +287,7 @@ github.com/xanzy/ssh-agent v0.2.1/go.mod h1:mLlQY/MoOhWBj+gOGMQkOeiEvkx+8pJSI+0B
|
||||||
github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
||||||
github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74=
|
||||||
github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k=
|
||||||
|
github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY=
|
||||||
github.com/zeebo/admission/v3 v3.0.3/go.mod h1:2OWyAS5yo0Xvj2AEUosOjTUHxaY0oIIiCrXGKCYzWpo=
|
github.com/zeebo/admission/v3 v3.0.3/go.mod h1:2OWyAS5yo0Xvj2AEUosOjTUHxaY0oIIiCrXGKCYzWpo=
|
||||||
github.com/zeebo/assert v1.3.0 h1:g7C04CbJuIDKNPFHmsk4hwZDO5O+kntRxzaUoNXj+IQ=
|
github.com/zeebo/assert v1.3.0 h1:g7C04CbJuIDKNPFHmsk4hwZDO5O+kntRxzaUoNXj+IQ=
|
||||||
github.com/zeebo/assert v1.3.0/go.mod h1:Pq9JiuJQpG8JLJdtkwrJESF0Foym2/D9XMU5ciN/wJ0=
|
github.com/zeebo/assert v1.3.0/go.mod h1:Pq9JiuJQpG8JLJdtkwrJESF0Foym2/D9XMU5ciN/wJ0=
|
||||||
|
|
@ -310,11 +311,11 @@ golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8U
|
||||||
golang.org/x/crypto v0.0.0-20200221231518-2aa609cf4a9d/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
golang.org/x/crypto v0.0.0-20200221231518-2aa609cf4a9d/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||||
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||||
golang.org/x/crypto v0.0.0-20200728195943-123391ffb6de/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
golang.org/x/crypto v0.0.0-20200728195943-123391ffb6de/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto=
|
||||||
golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838 h1:71vQrMauZZhcTVK6KdYM+rklehEEwb3E+ZhaE5jrPrE=
|
golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc=
|
||||||
golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
|
golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
|
||||||
|
golang.org/x/crypto v0.1.0 h1:MDRAIl0xIo9Io2xV565hzXHw3zVseKrJKodhohM5CjU=
|
||||||
|
golang.org/x/crypto v0.1.0/go.mod h1:RecgLatLF4+eUMCP1PoPZQb+cVrJcOPbHkTkbkB9sbw=
|
||||||
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
||||||
golang.org/x/image v0.0.0-20210622092929-e6eecd499c2c h1:FRR4fGZm/CMwZka5baQ4z8c8StbxJOMjS/45e0BAxK0=
|
|
||||||
golang.org/x/image v0.0.0-20210622092929-e6eecd499c2c/go.mod h1:023OzeP/+EPmXeapQh35lcL3II3LrY8Ic+EFFKVhULM=
|
|
||||||
golang.org/x/image v0.0.0-20211028202545-6944b10bf410 h1:hTftEOvwiOq2+O8k2D5/Q7COC7k5Qcrgc2TFURJYnvQ=
|
golang.org/x/image v0.0.0-20211028202545-6944b10bf410 h1:hTftEOvwiOq2+O8k2D5/Q7COC7k5Qcrgc2TFURJYnvQ=
|
||||||
golang.org/x/image v0.0.0-20211028202545-6944b10bf410/go.mod h1:023OzeP/+EPmXeapQh35lcL3II3LrY8Ic+EFFKVhULM=
|
golang.org/x/image v0.0.0-20211028202545-6944b10bf410/go.mod h1:023OzeP/+EPmXeapQh35lcL3II3LrY8Ic+EFFKVhULM=
|
||||||
golang.org/x/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
|
golang.org/x/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
|
||||||
|
|
@ -325,8 +326,9 @@ golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHl
|
||||||
golang.org/x/lint v0.0.0-20190409202823-959b441ac422/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
|
golang.org/x/lint v0.0.0-20190409202823-959b441ac422/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc=
|
||||||
golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||||
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||||
golang.org/x/mod v0.4.2 h1:Gz96sIWK3OalVv/I/qNygP42zyoKp3xptRVCWRFEBvo=
|
|
||||||
golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
|
||||||
|
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4 h1:6zppjxzCulZykYSLyVDYbneBfbaBIQPYMevg0bEwv2s=
|
||||||
|
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
|
||||||
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||||
golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||||
golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||||
|
|
@ -345,13 +347,15 @@ golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLL
|
||||||
golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
|
golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
|
||||||
golang.org/x/net v0.0.0-20200707034311-ab3426394381/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA=
|
golang.org/x/net v0.0.0-20200707034311-ab3426394381/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA=
|
||||||
golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||||
|
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||||
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
|
golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM=
|
||||||
golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk=
|
golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk=
|
||||||
golang.org/x/net v0.0.0-20210614182718-04defd469f4e/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
golang.org/x/net v0.0.0-20210614182718-04defd469f4e/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||||
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2 h1:CIJ76btIcR3eFI5EgSo6k1qKw9KJexJuRLI9G7Hp5wE=
|
|
||||||
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||||
golang.org/x/net v0.0.0-20211118161319-6a13c67c3ce4 h1:DZshvxDdVoeKIbudAdFEKi+f70l51luSy/7b76ibTY0=
|
|
||||||
golang.org/x/net v0.0.0-20211118161319-6a13c67c3ce4/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
golang.org/x/net v0.0.0-20211118161319-6a13c67c3ce4/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y=
|
||||||
|
golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
|
||||||
|
golang.org/x/net v0.1.0 h1:hZ/3BUoy5aId7sCpA/Tc5lt8DkFgdVS2onTpJsZ/fl0=
|
||||||
|
golang.org/x/net v0.1.0/go.mod h1:Cx3nUiGt4eDBEyega/BKRp+/AlGL8hYe7U9odMt2Cco=
|
||||||
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||||
golang.org/x/oauth2 v0.0.0-20181017192945-9dcd33a902f4/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
golang.org/x/oauth2 v0.0.0-20181017192945-9dcd33a902f4/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||||
golang.org/x/oauth2 v0.0.0-20181203162652-d668ce993890/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
golang.org/x/oauth2 v0.0.0-20181203162652-d668ce993890/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||||
|
|
@ -367,8 +371,9 @@ golang.org/x/sync v0.0.0-20190227155943-e225da77a7e6/go.mod h1:RxMgew5VJxzue5/jJ
|
||||||
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c h1:5KslGYwFpkhGh+Q16bwMP3cOontH8FOep7tGV86Y7SQ=
|
|
||||||
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
|
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4 h1:uVc8UZUe6tr40fFVnUP5Oj+veunVezqYl9z7DYw9xzw=
|
||||||
|
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||||
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
golang.org/x/sys v0.0.0-20181029174526-d69651ed3497/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
golang.org/x/sys v0.0.0-20181029174526-d69651ed3497/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||||
|
|
@ -395,16 +400,23 @@ golang.org/x/sys v0.0.0-20210514084401-e8d321eab015/go.mod h1:oPkhp1MJrh7nUepCBc
|
||||||
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20211007075335-d3039528d8ac/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20211007075335-d3039528d8ac/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20220128215802-99c3d69c2c27/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20220128215802-99c3d69c2c27/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab h1:2QkjZIsXupsJbJIdSjjUOgWK3aEtzyuh2mPt3l/CkeU=
|
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
|
golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1 h1:v+OssWQX+hTHEmOBgwxdZxK4zHq3yOs8F9J7mk0PY8E=
|
golang.org/x/sys v0.1.0 h1:kunALQeHf1/185U1i0GOB/fy1IPRDDpuoOOqRReG57U=
|
||||||
|
golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
||||||
|
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
||||||
|
golang.org/x/term v0.1.0 h1:g6Z6vPFA9dYBAF7DWcH6sCcOntplXsDKcliusYijMlw=
|
||||||
|
golang.org/x/term v0.1.0/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
|
||||||
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||||
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||||
golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
||||||
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M=
|
|
||||||
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
|
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
|
||||||
|
golang.org/x/text v0.4.0 h1:BrVqGRd7+k1DiOgtnFvAkoQEWQvBc25ouMJM6429SFg=
|
||||||
|
golang.org/x/text v0.4.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
|
||||||
golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||||
golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9 h1:ftMN5LMiBFjbzleLqtoBZk7KdJwhuybIU+FckUHgoyQ=
|
golang.org/x/time v0.0.0-20220722155302-e5dcc9cfc0b9 h1:ftMN5LMiBFjbzleLqtoBZk7KdJwhuybIU+FckUHgoyQ=
|
||||||
|
|
@ -424,12 +436,12 @@ golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roY
|
||||||
golang.org/x/tools v0.0.0-20201124115921-2c860bdd6e78/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
golang.org/x/tools v0.0.0-20201124115921-2c860bdd6e78/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||||
golang.org/x/tools v0.0.0-20201224043029-2b0845dc783e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
golang.org/x/tools v0.0.0-20201224043029-2b0845dc783e/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||||
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA=
|
||||||
golang.org/x/tools v0.1.1 h1:wGiQel/hW0NnEkJUk8lbzkX2gFJU6PFxf1v5OlCfuOs=
|
|
||||||
golang.org/x/tools v0.1.1/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
|
golang.org/x/tools v0.1.1/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
|
||||||
|
golang.org/x/tools v0.1.12 h1:VveCTK38A2rkS8ZqFY25HIDFscX5X9OoEhJd3quQmXU=
|
||||||
|
golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
|
||||||
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1 h1:go1bK/D/BFZV2I8cIQd1NKEZ+0owSTG1fDTci4IqFcE=
|
|
||||||
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
|
||||||
google.golang.org/api v0.0.0-20180910000450-7ca32eb868bf/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
google.golang.org/api v0.0.0-20180910000450-7ca32eb868bf/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
||||||
google.golang.org/api v0.0.0-20181030000543-1d582fd0359e/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
google.golang.org/api v0.0.0-20181030000543-1d582fd0359e/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/AUTHORS
generated
vendored
3
vendor/golang.org/x/crypto/AUTHORS
generated
vendored
|
|
@ -1,3 +0,0 @@
|
||||||
# This source code refers to The Go Authors for copyright purposes.
|
|
||||||
# The master list of authors is in the main Go distribution,
|
|
||||||
# visible at https://tip.golang.org/AUTHORS.
|
|
||||||
3
vendor/golang.org/x/crypto/CONTRIBUTORS
generated
vendored
3
vendor/golang.org/x/crypto/CONTRIBUTORS
generated
vendored
|
|
@ -1,3 +0,0 @@
|
||||||
# This source code was written by the Go contributors.
|
|
||||||
# The master list of contributors is in the main Go distribution,
|
|
||||||
# visible at https://tip.golang.org/CONTRIBUTORS.
|
|
||||||
418
vendor/golang.org/x/crypto/acme/acme.go
generated
vendored
418
vendor/golang.org/x/crypto/acme/acme.go
generated
vendored
|
|
@ -3,17 +3,20 @@
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
// Package acme provides an implementation of the
|
// Package acme provides an implementation of the
|
||||||
// Automatic Certificate Management Environment (ACME) spec.
|
// Automatic Certificate Management Environment (ACME) spec,
|
||||||
// The initial implementation was based on ACME draft-02 and
|
// most famously used by Let's Encrypt.
|
||||||
// is now being extended to comply with RFC 8555.
|
//
|
||||||
// See https://tools.ietf.org/html/draft-ietf-acme-acme-02
|
// The initial implementation of this package was based on an early version
|
||||||
// and https://tools.ietf.org/html/rfc8555 for details.
|
// of the spec. The current implementation supports only the modern
|
||||||
|
// RFC 8555 but some of the old API surface remains for compatibility.
|
||||||
|
// While code using the old API will still compile, it will return an error.
|
||||||
|
// Note the deprecation comments to update your code.
|
||||||
|
//
|
||||||
|
// See https://tools.ietf.org/html/rfc8555 for the spec.
|
||||||
//
|
//
|
||||||
// Most common scenarios will want to use autocert subdirectory instead,
|
// Most common scenarios will want to use autocert subdirectory instead,
|
||||||
// which provides automatic access to certificates from Let's Encrypt
|
// which provides automatic access to certificates from Let's Encrypt
|
||||||
// and any other ACME-based CA.
|
// and any other ACME-based CA.
|
||||||
//
|
|
||||||
// This package is a work in progress and makes no API stability promises.
|
|
||||||
package acme
|
package acme
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
@ -33,8 +36,6 @@ import (
|
||||||
"encoding/pem"
|
"encoding/pem"
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
|
||||||
"io/ioutil"
|
|
||||||
"math/big"
|
"math/big"
|
||||||
"net/http"
|
"net/http"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
@ -72,6 +73,7 @@ const (
|
||||||
)
|
)
|
||||||
|
|
||||||
// Client is an ACME client.
|
// Client is an ACME client.
|
||||||
|
//
|
||||||
// The only required field is Key. An example of creating a client with a new key
|
// The only required field is Key. An example of creating a client with a new key
|
||||||
// is as follows:
|
// is as follows:
|
||||||
//
|
//
|
||||||
|
|
@ -80,7 +82,6 @@ const (
|
||||||
// log.Fatal(err)
|
// log.Fatal(err)
|
||||||
// }
|
// }
|
||||||
// client := &Client{Key: key}
|
// client := &Client{Key: key}
|
||||||
//
|
|
||||||
type Client struct {
|
type Client struct {
|
||||||
// Key is the account key used to register with a CA and sign requests.
|
// Key is the account key used to register with a CA and sign requests.
|
||||||
// Key.Public() must return a *rsa.PublicKey or *ecdsa.PublicKey.
|
// Key.Public() must return a *rsa.PublicKey or *ecdsa.PublicKey.
|
||||||
|
|
@ -145,9 +146,6 @@ type Client struct {
|
||||||
func (c *Client) accountKID(ctx context.Context) KeyID {
|
func (c *Client) accountKID(ctx context.Context) KeyID {
|
||||||
c.cacheMu.Lock()
|
c.cacheMu.Lock()
|
||||||
defer c.cacheMu.Unlock()
|
defer c.cacheMu.Unlock()
|
||||||
if !c.dir.rfcCompliant() {
|
|
||||||
return noKeyID
|
|
||||||
}
|
|
||||||
if c.KID != noKeyID {
|
if c.KID != noKeyID {
|
||||||
return c.KID
|
return c.KID
|
||||||
}
|
}
|
||||||
|
|
@ -159,6 +157,8 @@ func (c *Client) accountKID(ctx context.Context) KeyID {
|
||||||
return c.KID
|
return c.KID
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var errPreRFC = errors.New("acme: server does not support the RFC 8555 version of ACME")
|
||||||
|
|
||||||
// Discover performs ACME server discovery using c.DirectoryURL.
|
// Discover performs ACME server discovery using c.DirectoryURL.
|
||||||
//
|
//
|
||||||
// It caches successful result. So, subsequent calls will not result in
|
// It caches successful result. So, subsequent calls will not result in
|
||||||
|
|
@ -179,53 +179,36 @@ func (c *Client) Discover(ctx context.Context) (Directory, error) {
|
||||||
c.addNonce(res.Header)
|
c.addNonce(res.Header)
|
||||||
|
|
||||||
var v struct {
|
var v struct {
|
||||||
Reg string `json:"new-reg"`
|
Reg string `json:"newAccount"`
|
||||||
RegRFC string `json:"newAccount"`
|
Authz string `json:"newAuthz"`
|
||||||
Authz string `json:"new-authz"`
|
Order string `json:"newOrder"`
|
||||||
AuthzRFC string `json:"newAuthz"`
|
Revoke string `json:"revokeCert"`
|
||||||
OrderRFC string `json:"newOrder"`
|
Nonce string `json:"newNonce"`
|
||||||
Cert string `json:"new-cert"`
|
KeyChange string `json:"keyChange"`
|
||||||
Revoke string `json:"revoke-cert"`
|
|
||||||
RevokeRFC string `json:"revokeCert"`
|
|
||||||
NonceRFC string `json:"newNonce"`
|
|
||||||
KeyChangeRFC string `json:"keyChange"`
|
|
||||||
Meta struct {
|
Meta struct {
|
||||||
Terms string `json:"terms-of-service"`
|
Terms string `json:"termsOfService"`
|
||||||
TermsRFC string `json:"termsOfService"`
|
Website string `json:"website"`
|
||||||
WebsiteRFC string `json:"website"`
|
CAA []string `json:"caaIdentities"`
|
||||||
CAA []string `json:"caa-identities"`
|
ExternalAcct bool `json:"externalAccountRequired"`
|
||||||
CAARFC []string `json:"caaIdentities"`
|
|
||||||
ExternalAcctRFC bool `json:"externalAccountRequired"`
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if err := json.NewDecoder(res.Body).Decode(&v); err != nil {
|
if err := json.NewDecoder(res.Body).Decode(&v); err != nil {
|
||||||
return Directory{}, err
|
return Directory{}, err
|
||||||
}
|
}
|
||||||
if v.OrderRFC == "" {
|
if v.Order == "" {
|
||||||
// Non-RFC compliant ACME CA.
|
return Directory{}, errPreRFC
|
||||||
|
}
|
||||||
c.dir = &Directory{
|
c.dir = &Directory{
|
||||||
RegURL: v.Reg,
|
RegURL: v.Reg,
|
||||||
AuthzURL: v.Authz,
|
AuthzURL: v.Authz,
|
||||||
CertURL: v.Cert,
|
OrderURL: v.Order,
|
||||||
RevokeURL: v.Revoke,
|
RevokeURL: v.Revoke,
|
||||||
|
NonceURL: v.Nonce,
|
||||||
|
KeyChangeURL: v.KeyChange,
|
||||||
Terms: v.Meta.Terms,
|
Terms: v.Meta.Terms,
|
||||||
Website: v.Meta.WebsiteRFC,
|
Website: v.Meta.Website,
|
||||||
CAA: v.Meta.CAA,
|
CAA: v.Meta.CAA,
|
||||||
}
|
ExternalAccountRequired: v.Meta.ExternalAcct,
|
||||||
return *c.dir, nil
|
|
||||||
}
|
|
||||||
// RFC compliant ACME CA.
|
|
||||||
c.dir = &Directory{
|
|
||||||
RegURL: v.RegRFC,
|
|
||||||
AuthzURL: v.AuthzRFC,
|
|
||||||
OrderURL: v.OrderRFC,
|
|
||||||
RevokeURL: v.RevokeRFC,
|
|
||||||
NonceURL: v.NonceRFC,
|
|
||||||
KeyChangeURL: v.KeyChangeRFC,
|
|
||||||
Terms: v.Meta.TermsRFC,
|
|
||||||
Website: v.Meta.WebsiteRFC,
|
|
||||||
CAA: v.Meta.CAARFC,
|
|
||||||
ExternalAccountRequired: v.Meta.ExternalAcctRFC,
|
|
||||||
}
|
}
|
||||||
return *c.dir, nil
|
return *c.dir, nil
|
||||||
}
|
}
|
||||||
|
|
@ -237,55 +220,11 @@ func (c *Client) directoryURL() string {
|
||||||
return LetsEncryptURL
|
return LetsEncryptURL
|
||||||
}
|
}
|
||||||
|
|
||||||
// CreateCert requests a new certificate using the Certificate Signing Request csr encoded in DER format.
|
// CreateCert was part of the old version of ACME. It is incompatible with RFC 8555.
|
||||||
// It is incompatible with RFC 8555. Callers should use CreateOrderCert when interfacing
|
|
||||||
// with an RFC-compliant CA.
|
|
||||||
//
|
//
|
||||||
// The exp argument indicates the desired certificate validity duration. CA may issue a certificate
|
// Deprecated: this was for the pre-RFC 8555 version of ACME. Callers should use CreateOrderCert.
|
||||||
// with a different duration.
|
|
||||||
// If the bundle argument is true, the returned value will also contain the CA (issuer) certificate chain.
|
|
||||||
//
|
|
||||||
// In the case where CA server does not provide the issued certificate in the response,
|
|
||||||
// CreateCert will poll certURL using c.FetchCert, which will result in additional round-trips.
|
|
||||||
// In such a scenario, the caller can cancel the polling with ctx.
|
|
||||||
//
|
|
||||||
// CreateCert returns an error if the CA's response or chain was unreasonably large.
|
|
||||||
// Callers are encouraged to parse the returned value to ensure the certificate is valid and has the expected features.
|
|
||||||
func (c *Client) CreateCert(ctx context.Context, csr []byte, exp time.Duration, bundle bool) (der [][]byte, certURL string, err error) {
|
func (c *Client) CreateCert(ctx context.Context, csr []byte, exp time.Duration, bundle bool) (der [][]byte, certURL string, err error) {
|
||||||
if _, err := c.Discover(ctx); err != nil {
|
return nil, "", errPreRFC
|
||||||
return nil, "", err
|
|
||||||
}
|
|
||||||
|
|
||||||
req := struct {
|
|
||||||
Resource string `json:"resource"`
|
|
||||||
CSR string `json:"csr"`
|
|
||||||
NotBefore string `json:"notBefore,omitempty"`
|
|
||||||
NotAfter string `json:"notAfter,omitempty"`
|
|
||||||
}{
|
|
||||||
Resource: "new-cert",
|
|
||||||
CSR: base64.RawURLEncoding.EncodeToString(csr),
|
|
||||||
}
|
|
||||||
now := timeNow()
|
|
||||||
req.NotBefore = now.Format(time.RFC3339)
|
|
||||||
if exp > 0 {
|
|
||||||
req.NotAfter = now.Add(exp).Format(time.RFC3339)
|
|
||||||
}
|
|
||||||
|
|
||||||
res, err := c.post(ctx, nil, c.dir.CertURL, req, wantStatus(http.StatusCreated))
|
|
||||||
if err != nil {
|
|
||||||
return nil, "", err
|
|
||||||
}
|
|
||||||
defer res.Body.Close()
|
|
||||||
|
|
||||||
curl := res.Header.Get("Location") // cert permanent URL
|
|
||||||
if res.ContentLength == 0 {
|
|
||||||
// no cert in the body; poll until we get it
|
|
||||||
cert, err := c.FetchCert(ctx, curl, bundle)
|
|
||||||
return cert, curl, err
|
|
||||||
}
|
|
||||||
// slurp issued cert and CA chain, if requested
|
|
||||||
cert, err := c.responseCert(ctx, res, bundle)
|
|
||||||
return cert, curl, err
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// FetchCert retrieves already issued certificate from the given url, in DER format.
|
// FetchCert retrieves already issued certificate from the given url, in DER format.
|
||||||
|
|
@ -299,22 +238,12 @@ func (c *Client) CreateCert(ctx context.Context, csr []byte, exp time.Duration,
|
||||||
// Callers are encouraged to parse the returned value to ensure the certificate is valid
|
// Callers are encouraged to parse the returned value to ensure the certificate is valid
|
||||||
// and has expected features.
|
// and has expected features.
|
||||||
func (c *Client) FetchCert(ctx context.Context, url string, bundle bool) ([][]byte, error) {
|
func (c *Client) FetchCert(ctx context.Context, url string, bundle bool) ([][]byte, error) {
|
||||||
dir, err := c.Discover(ctx)
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if dir.rfcCompliant() {
|
|
||||||
return c.fetchCertRFC(ctx, url, bundle)
|
return c.fetchCertRFC(ctx, url, bundle)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Legacy non-authenticated GET request.
|
|
||||||
res, err := c.get(ctx, url, wantStatus(http.StatusOK))
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
return c.responseCert(ctx, res, bundle)
|
|
||||||
}
|
|
||||||
|
|
||||||
// RevokeCert revokes a previously issued certificate cert, provided in DER format.
|
// RevokeCert revokes a previously issued certificate cert, provided in DER format.
|
||||||
//
|
//
|
||||||
// The key argument, used to sign the request, must be authorized
|
// The key argument, used to sign the request, must be authorized
|
||||||
|
|
@ -322,32 +251,12 @@ func (c *Client) FetchCert(ctx context.Context, url string, bundle bool) ([][]by
|
||||||
// For instance, the key pair of the certificate may be authorized.
|
// For instance, the key pair of the certificate may be authorized.
|
||||||
// If the key is nil, c.Key is used instead.
|
// If the key is nil, c.Key is used instead.
|
||||||
func (c *Client) RevokeCert(ctx context.Context, key crypto.Signer, cert []byte, reason CRLReasonCode) error {
|
func (c *Client) RevokeCert(ctx context.Context, key crypto.Signer, cert []byte, reason CRLReasonCode) error {
|
||||||
dir, err := c.Discover(ctx)
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
if err != nil {
|
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if dir.rfcCompliant() {
|
|
||||||
return c.revokeCertRFC(ctx, key, cert, reason)
|
return c.revokeCertRFC(ctx, key, cert, reason)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Legacy CA.
|
|
||||||
body := &struct {
|
|
||||||
Resource string `json:"resource"`
|
|
||||||
Cert string `json:"certificate"`
|
|
||||||
Reason int `json:"reason"`
|
|
||||||
}{
|
|
||||||
Resource: "revoke-cert",
|
|
||||||
Cert: base64.RawURLEncoding.EncodeToString(cert),
|
|
||||||
Reason: int(reason),
|
|
||||||
}
|
|
||||||
res, err := c.post(ctx, key, dir.RevokeURL, body, wantStatus(http.StatusOK))
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
defer res.Body.Close()
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// AcceptTOS always returns true to indicate the acceptance of a CA's Terms of Service
|
// AcceptTOS always returns true to indicate the acceptance of a CA's Terms of Service
|
||||||
// during account registration. See Register method of Client for more details.
|
// during account registration. See Register method of Client for more details.
|
||||||
func AcceptTOS(tosURL string) bool { return true }
|
func AcceptTOS(tosURL string) bool { return true }
|
||||||
|
|
@ -368,75 +277,47 @@ func (c *Client) Register(ctx context.Context, acct *Account, prompt func(tosURL
|
||||||
if c.Key == nil {
|
if c.Key == nil {
|
||||||
return nil, errors.New("acme: client.Key must be set to Register")
|
return nil, errors.New("acme: client.Key must be set to Register")
|
||||||
}
|
}
|
||||||
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
dir, err := c.Discover(ctx)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if dir.rfcCompliant() {
|
|
||||||
return c.registerRFC(ctx, acct, prompt)
|
return c.registerRFC(ctx, acct, prompt)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Legacy ACME draft registration flow.
|
|
||||||
a, err := c.doReg(ctx, dir.RegURL, "new-reg", acct)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
var accept bool
|
|
||||||
if a.CurrentTerms != "" && a.CurrentTerms != a.AgreedTerms {
|
|
||||||
accept = prompt(a.CurrentTerms)
|
|
||||||
}
|
|
||||||
if accept {
|
|
||||||
a.AgreedTerms = a.CurrentTerms
|
|
||||||
a, err = c.UpdateReg(ctx, a)
|
|
||||||
}
|
|
||||||
return a, err
|
|
||||||
}
|
|
||||||
|
|
||||||
// GetReg retrieves an existing account associated with c.Key.
|
// GetReg retrieves an existing account associated with c.Key.
|
||||||
//
|
//
|
||||||
// The url argument is an Account URI used with pre-RFC 8555 CAs.
|
// The url argument is a legacy artifact of the pre-RFC 8555 API
|
||||||
// It is ignored when interfacing with an RFC-compliant CA.
|
// and is ignored.
|
||||||
func (c *Client) GetReg(ctx context.Context, url string) (*Account, error) {
|
func (c *Client) GetReg(ctx context.Context, url string) (*Account, error) {
|
||||||
dir, err := c.Discover(ctx)
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if dir.rfcCompliant() {
|
|
||||||
return c.getRegRFC(ctx)
|
return c.getRegRFC(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Legacy CA.
|
|
||||||
a, err := c.doReg(ctx, url, "reg", nil)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
a.URI = url
|
|
||||||
return a, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// UpdateReg updates an existing registration.
|
// UpdateReg updates an existing registration.
|
||||||
// It returns an updated account copy. The provided account is not modified.
|
// It returns an updated account copy. The provided account is not modified.
|
||||||
//
|
//
|
||||||
// When interfacing with RFC-compliant CAs, a.URI is ignored and the account URL
|
// The account's URI is ignored and the account URL associated with
|
||||||
// associated with c.Key is used instead.
|
// c.Key is used instead.
|
||||||
func (c *Client) UpdateReg(ctx context.Context, acct *Account) (*Account, error) {
|
func (c *Client) UpdateReg(ctx context.Context, acct *Account) (*Account, error) {
|
||||||
dir, err := c.Discover(ctx)
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
if dir.rfcCompliant() {
|
|
||||||
return c.updateRegRFC(ctx, acct)
|
return c.updateRegRFC(ctx, acct)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Legacy CA.
|
// AccountKeyRollover attempts to transition a client's account key to a new key.
|
||||||
uri := acct.URI
|
// On success client's Key is updated which is not concurrency safe.
|
||||||
a, err := c.doReg(ctx, uri, "reg", acct)
|
// On failure an error will be returned.
|
||||||
if err != nil {
|
// The new key is already registered with the ACME provider if the following is true:
|
||||||
return nil, err
|
// - error is of type acme.Error
|
||||||
}
|
// - StatusCode should be 409 (Conflict)
|
||||||
a.URI = uri
|
// - Location header will have the KID of the associated account
|
||||||
return a, nil
|
//
|
||||||
|
// More about account key rollover can be found at
|
||||||
|
// https://tools.ietf.org/html/rfc8555#section-7.3.5.
|
||||||
|
func (c *Client) AccountKeyRollover(ctx context.Context, newKey crypto.Signer) error {
|
||||||
|
return c.accountKeyRollover(ctx, newKey)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Authorize performs the initial step in the pre-authorization flow,
|
// Authorize performs the initial step in the pre-authorization flow,
|
||||||
|
|
@ -505,17 +386,11 @@ func (c *Client) authorize(ctx context.Context, typ, val string) (*Authorization
|
||||||
// If a caller needs to poll an authorization until its status is final,
|
// If a caller needs to poll an authorization until its status is final,
|
||||||
// see the WaitAuthorization method.
|
// see the WaitAuthorization method.
|
||||||
func (c *Client) GetAuthorization(ctx context.Context, url string) (*Authorization, error) {
|
func (c *Client) GetAuthorization(ctx context.Context, url string) (*Authorization, error) {
|
||||||
dir, err := c.Discover(ctx)
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
var res *http.Response
|
res, err := c.postAsGet(ctx, url, wantStatus(http.StatusOK))
|
||||||
if dir.rfcCompliant() {
|
|
||||||
res, err = c.postAsGet(ctx, url, wantStatus(http.StatusOK))
|
|
||||||
} else {
|
|
||||||
res, err = c.get(ctx, url, wantStatus(http.StatusOK, http.StatusAccepted))
|
|
||||||
}
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -537,7 +412,6 @@ func (c *Client) GetAuthorization(ctx context.Context, url string) (*Authorizati
|
||||||
//
|
//
|
||||||
// It does not revoke existing certificates.
|
// It does not revoke existing certificates.
|
||||||
func (c *Client) RevokeAuthorization(ctx context.Context, url string) error {
|
func (c *Client) RevokeAuthorization(ctx context.Context, url string) error {
|
||||||
// Required for c.accountKID() when in RFC mode.
|
|
||||||
if _, err := c.Discover(ctx); err != nil {
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
@ -567,18 +441,11 @@ func (c *Client) RevokeAuthorization(ctx context.Context, url string) error {
|
||||||
// In all other cases WaitAuthorization returns an error.
|
// In all other cases WaitAuthorization returns an error.
|
||||||
// If the Status is StatusInvalid, the returned error is of type *AuthorizationError.
|
// If the Status is StatusInvalid, the returned error is of type *AuthorizationError.
|
||||||
func (c *Client) WaitAuthorization(ctx context.Context, url string) (*Authorization, error) {
|
func (c *Client) WaitAuthorization(ctx context.Context, url string) (*Authorization, error) {
|
||||||
// Required for c.accountKID() when in RFC mode.
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
dir, err := c.Discover(ctx)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
getfn := c.postAsGet
|
|
||||||
if !dir.rfcCompliant() {
|
|
||||||
getfn = c.get
|
|
||||||
}
|
|
||||||
|
|
||||||
for {
|
for {
|
||||||
res, err := getfn(ctx, url, wantStatus(http.StatusOK, http.StatusAccepted))
|
res, err := c.postAsGet(ctx, url, wantStatus(http.StatusOK, http.StatusAccepted))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -621,17 +488,11 @@ func (c *Client) WaitAuthorization(ctx context.Context, url string) (*Authorizat
|
||||||
//
|
//
|
||||||
// A client typically polls a challenge status using this method.
|
// A client typically polls a challenge status using this method.
|
||||||
func (c *Client) GetChallenge(ctx context.Context, url string) (*Challenge, error) {
|
func (c *Client) GetChallenge(ctx context.Context, url string) (*Challenge, error) {
|
||||||
// Required for c.accountKID() when in RFC mode.
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
dir, err := c.Discover(ctx)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
getfn := c.postAsGet
|
res, err := c.postAsGet(ctx, url, wantStatus(http.StatusOK, http.StatusAccepted))
|
||||||
if !dir.rfcCompliant() {
|
|
||||||
getfn = c.get
|
|
||||||
}
|
|
||||||
res, err := getfn(ctx, url, wantStatus(http.StatusOK, http.StatusAccepted))
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -649,29 +510,11 @@ func (c *Client) GetChallenge(ctx context.Context, url string) (*Challenge, erro
|
||||||
//
|
//
|
||||||
// The server will then perform the validation asynchronously.
|
// The server will then perform the validation asynchronously.
|
||||||
func (c *Client) Accept(ctx context.Context, chal *Challenge) (*Challenge, error) {
|
func (c *Client) Accept(ctx context.Context, chal *Challenge) (*Challenge, error) {
|
||||||
// Required for c.accountKID() when in RFC mode.
|
if _, err := c.Discover(ctx); err != nil {
|
||||||
dir, err := c.Discover(ctx)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
var req interface{} = json.RawMessage("{}") // RFC-compliant CA
|
res, err := c.post(ctx, nil, chal.URI, json.RawMessage("{}"), wantStatus(
|
||||||
if !dir.rfcCompliant() {
|
|
||||||
auth, err := keyAuth(c.Key.Public(), chal.Token)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
req = struct {
|
|
||||||
Resource string `json:"resource"`
|
|
||||||
Type string `json:"type"`
|
|
||||||
Auth string `json:"keyAuthorization"`
|
|
||||||
}{
|
|
||||||
Resource: "challenge",
|
|
||||||
Type: chal.Type,
|
|
||||||
Auth: auth,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
res, err := c.post(ctx, nil, chal.URI, req, wantStatus(
|
|
||||||
http.StatusOK, // according to the spec
|
http.StatusOK, // according to the spec
|
||||||
http.StatusAccepted, // Let's Encrypt: see https://goo.gl/WsJ7VT (acme-divergences.md)
|
http.StatusAccepted, // Let's Encrypt: see https://goo.gl/WsJ7VT (acme-divergences.md)
|
||||||
))
|
))
|
||||||
|
|
@ -722,7 +565,7 @@ func (c *Client) HTTP01ChallengePath(token string) string {
|
||||||
|
|
||||||
// TLSSNI01ChallengeCert creates a certificate for TLS-SNI-01 challenge response.
|
// TLSSNI01ChallengeCert creates a certificate for TLS-SNI-01 challenge response.
|
||||||
//
|
//
|
||||||
// Deprecated: This challenge type is unused in both draft-02 and RFC versions of ACME spec.
|
// Deprecated: This challenge type is unused in both draft-02 and RFC versions of the ACME spec.
|
||||||
func (c *Client) TLSSNI01ChallengeCert(token string, opt ...CertOption) (cert tls.Certificate, name string, err error) {
|
func (c *Client) TLSSNI01ChallengeCert(token string, opt ...CertOption) (cert tls.Certificate, name string, err error) {
|
||||||
ka, err := keyAuth(c.Key.Public(), token)
|
ka, err := keyAuth(c.Key.Public(), token)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -740,7 +583,7 @@ func (c *Client) TLSSNI01ChallengeCert(token string, opt ...CertOption) (cert tl
|
||||||
|
|
||||||
// TLSSNI02ChallengeCert creates a certificate for TLS-SNI-02 challenge response.
|
// TLSSNI02ChallengeCert creates a certificate for TLS-SNI-02 challenge response.
|
||||||
//
|
//
|
||||||
// Deprecated: This challenge type is unused in both draft-02 and RFC versions of ACME spec.
|
// Deprecated: This challenge type is unused in both draft-02 and RFC versions of the ACME spec.
|
||||||
func (c *Client) TLSSNI02ChallengeCert(token string, opt ...CertOption) (cert tls.Certificate, name string, err error) {
|
func (c *Client) TLSSNI02ChallengeCert(token string, opt ...CertOption) (cert tls.Certificate, name string, err error) {
|
||||||
b := sha256.Sum256([]byte(token))
|
b := sha256.Sum256([]byte(token))
|
||||||
h := hex.EncodeToString(b[:])
|
h := hex.EncodeToString(b[:])
|
||||||
|
|
@ -807,63 +650,6 @@ func (c *Client) TLSALPN01ChallengeCert(token, domain string, opt ...CertOption)
|
||||||
return tlsChallengeCert([]string{domain}, newOpt)
|
return tlsChallengeCert([]string{domain}, newOpt)
|
||||||
}
|
}
|
||||||
|
|
||||||
// doReg sends all types of registration requests the old way (pre-RFC world).
|
|
||||||
// The type of request is identified by typ argument, which is a "resource"
|
|
||||||
// in the ACME spec terms.
|
|
||||||
//
|
|
||||||
// A non-nil acct argument indicates whether the intention is to mutate data
|
|
||||||
// of the Account. Only Contact and Agreement of its fields are used
|
|
||||||
// in such cases.
|
|
||||||
func (c *Client) doReg(ctx context.Context, url string, typ string, acct *Account) (*Account, error) {
|
|
||||||
req := struct {
|
|
||||||
Resource string `json:"resource"`
|
|
||||||
Contact []string `json:"contact,omitempty"`
|
|
||||||
Agreement string `json:"agreement,omitempty"`
|
|
||||||
}{
|
|
||||||
Resource: typ,
|
|
||||||
}
|
|
||||||
if acct != nil {
|
|
||||||
req.Contact = acct.Contact
|
|
||||||
req.Agreement = acct.AgreedTerms
|
|
||||||
}
|
|
||||||
res, err := c.post(ctx, nil, url, req, wantStatus(
|
|
||||||
http.StatusOK, // updates and deletes
|
|
||||||
http.StatusCreated, // new account creation
|
|
||||||
http.StatusAccepted, // Let's Encrypt divergent implementation
|
|
||||||
))
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
defer res.Body.Close()
|
|
||||||
|
|
||||||
var v struct {
|
|
||||||
Contact []string
|
|
||||||
Agreement string
|
|
||||||
Authorizations string
|
|
||||||
Certificates string
|
|
||||||
}
|
|
||||||
if err := json.NewDecoder(res.Body).Decode(&v); err != nil {
|
|
||||||
return nil, fmt.Errorf("acme: invalid response: %v", err)
|
|
||||||
}
|
|
||||||
var tos string
|
|
||||||
if v := linkHeader(res.Header, "terms-of-service"); len(v) > 0 {
|
|
||||||
tos = v[0]
|
|
||||||
}
|
|
||||||
var authz string
|
|
||||||
if v := linkHeader(res.Header, "next"); len(v) > 0 {
|
|
||||||
authz = v[0]
|
|
||||||
}
|
|
||||||
return &Account{
|
|
||||||
URI: res.Header.Get("Location"),
|
|
||||||
Contact: v.Contact,
|
|
||||||
AgreedTerms: v.Agreement,
|
|
||||||
CurrentTerms: tos,
|
|
||||||
Authz: authz,
|
|
||||||
Authorizations: v.Authorizations,
|
|
||||||
Certificates: v.Certificates,
|
|
||||||
}, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// popNonce returns a nonce value previously stored with c.addNonce
|
// popNonce returns a nonce value previously stored with c.addNonce
|
||||||
// or fetches a fresh one from c.dir.NonceURL.
|
// or fetches a fresh one from c.dir.NonceURL.
|
||||||
// If NonceURL is empty, it first tries c.directoryURL() and, failing that,
|
// If NonceURL is empty, it first tries c.directoryURL() and, failing that,
|
||||||
|
|
@ -938,78 +724,6 @@ func nonceFromHeader(h http.Header) string {
|
||||||
return h.Get("Replay-Nonce")
|
return h.Get("Replay-Nonce")
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Client) responseCert(ctx context.Context, res *http.Response, bundle bool) ([][]byte, error) {
|
|
||||||
b, err := ioutil.ReadAll(io.LimitReader(res.Body, maxCertSize+1))
|
|
||||||
if err != nil {
|
|
||||||
return nil, fmt.Errorf("acme: response stream: %v", err)
|
|
||||||
}
|
|
||||||
if len(b) > maxCertSize {
|
|
||||||
return nil, errors.New("acme: certificate is too big")
|
|
||||||
}
|
|
||||||
cert := [][]byte{b}
|
|
||||||
if !bundle {
|
|
||||||
return cert, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// Append CA chain cert(s).
|
|
||||||
// At least one is required according to the spec:
|
|
||||||
// https://tools.ietf.org/html/draft-ietf-acme-acme-03#section-6.3.1
|
|
||||||
up := linkHeader(res.Header, "up")
|
|
||||||
if len(up) == 0 {
|
|
||||||
return nil, errors.New("acme: rel=up link not found")
|
|
||||||
}
|
|
||||||
if len(up) > maxChainLen {
|
|
||||||
return nil, errors.New("acme: rel=up link is too large")
|
|
||||||
}
|
|
||||||
for _, url := range up {
|
|
||||||
cc, err := c.chainCert(ctx, url, 0)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
cert = append(cert, cc...)
|
|
||||||
}
|
|
||||||
return cert, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// chainCert fetches CA certificate chain recursively by following "up" links.
|
|
||||||
// Each recursive call increments the depth by 1, resulting in an error
|
|
||||||
// if the recursion level reaches maxChainLen.
|
|
||||||
//
|
|
||||||
// First chainCert call starts with depth of 0.
|
|
||||||
func (c *Client) chainCert(ctx context.Context, url string, depth int) ([][]byte, error) {
|
|
||||||
if depth >= maxChainLen {
|
|
||||||
return nil, errors.New("acme: certificate chain is too deep")
|
|
||||||
}
|
|
||||||
|
|
||||||
res, err := c.get(ctx, url, wantStatus(http.StatusOK))
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
defer res.Body.Close()
|
|
||||||
b, err := ioutil.ReadAll(io.LimitReader(res.Body, maxCertSize+1))
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
if len(b) > maxCertSize {
|
|
||||||
return nil, errors.New("acme: certificate is too big")
|
|
||||||
}
|
|
||||||
chain := [][]byte{b}
|
|
||||||
|
|
||||||
uplink := linkHeader(res.Header, "up")
|
|
||||||
if len(uplink) > maxChainLen {
|
|
||||||
return nil, errors.New("acme: certificate chain is too large")
|
|
||||||
}
|
|
||||||
for _, up := range uplink {
|
|
||||||
cc, err := c.chainCert(ctx, up, depth+1)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
chain = append(chain, cc...)
|
|
||||||
}
|
|
||||||
|
|
||||||
return chain, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// linkHeader returns URI-Reference values of all Link headers
|
// linkHeader returns URI-Reference values of all Link headers
|
||||||
// with relation-type rel.
|
// with relation-type rel.
|
||||||
// See https://tools.ietf.org/html/rfc5988#section-5 for details.
|
// See https://tools.ietf.org/html/rfc5988#section-5 for details.
|
||||||
|
|
@ -1100,5 +814,5 @@ func encodePEM(typ string, b []byte) []byte {
|
||||||
return pem.EncodeToMemory(pb)
|
return pem.EncodeToMemory(pb)
|
||||||
}
|
}
|
||||||
|
|
||||||
// timeNow is useful for testing for fixed current time.
|
// timeNow is time.Now, except in tests which can mess with it.
|
||||||
var timeNow = time.Now
|
var timeNow = time.Now
|
||||||
|
|
|
||||||
105
vendor/golang.org/x/crypto/acme/autocert/autocert.go
generated
vendored
105
vendor/golang.org/x/crypto/acme/autocert/autocert.go
generated
vendored
|
|
@ -47,6 +47,8 @@ var createCertRetryAfter = time.Minute
|
||||||
// pseudoRand is safe for concurrent use.
|
// pseudoRand is safe for concurrent use.
|
||||||
var pseudoRand *lockedMathRand
|
var pseudoRand *lockedMathRand
|
||||||
|
|
||||||
|
var errPreRFC = errors.New("autocert: ACME server doesn't support RFC 8555")
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
src := mathrand.NewSource(time.Now().UnixNano())
|
src := mathrand.NewSource(time.Now().UnixNano())
|
||||||
pseudoRand = &lockedMathRand{rnd: mathrand.New(src)}
|
pseudoRand = &lockedMathRand{rnd: mathrand.New(src)}
|
||||||
|
|
@ -168,6 +170,11 @@ type Manager struct {
|
||||||
// in the template's ExtraExtensions field as is.
|
// in the template's ExtraExtensions field as is.
|
||||||
ExtraExtensions []pkix.Extension
|
ExtraExtensions []pkix.Extension
|
||||||
|
|
||||||
|
// ExternalAccountBinding optionally represents an arbitrary binding to an
|
||||||
|
// account of the CA to which the ACME server is tied.
|
||||||
|
// See RFC 8555, Section 7.3.4 for more details.
|
||||||
|
ExternalAccountBinding *acme.ExternalAccountBinding
|
||||||
|
|
||||||
clientMu sync.Mutex
|
clientMu sync.Mutex
|
||||||
client *acme.Client // initialized by acmeClient method
|
client *acme.Client // initialized by acmeClient method
|
||||||
|
|
||||||
|
|
@ -456,7 +463,7 @@ func (m *Manager) cert(ctx context.Context, ck certKey) (*tls.Certificate, error
|
||||||
leaf: cert.Leaf,
|
leaf: cert.Leaf,
|
||||||
}
|
}
|
||||||
m.state[ck] = s
|
m.state[ck] = s
|
||||||
go m.renew(ck, s.key, s.leaf.NotAfter)
|
m.startRenew(ck, s.key, s.leaf.NotAfter)
|
||||||
return cert, nil
|
return cert, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -582,8 +589,9 @@ func (m *Manager) createCert(ctx context.Context, ck certKey) (*tls.Certificate,
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// Remove the failed state after some time,
|
// Remove the failed state after some time,
|
||||||
// making the manager call createCert again on the following TLS hello.
|
// making the manager call createCert again on the following TLS hello.
|
||||||
|
didRemove := testDidRemoveState // The lifetime of this timer is untracked, so copy mutable local state to avoid races.
|
||||||
time.AfterFunc(createCertRetryAfter, func() {
|
time.AfterFunc(createCertRetryAfter, func() {
|
||||||
defer testDidRemoveState(ck)
|
defer didRemove(ck)
|
||||||
m.stateMu.Lock()
|
m.stateMu.Lock()
|
||||||
defer m.stateMu.Unlock()
|
defer m.stateMu.Unlock()
|
||||||
// Verify the state hasn't changed and it's still invalid
|
// Verify the state hasn't changed and it's still invalid
|
||||||
|
|
@ -601,7 +609,7 @@ func (m *Manager) createCert(ctx context.Context, ck certKey) (*tls.Certificate,
|
||||||
}
|
}
|
||||||
state.cert = der
|
state.cert = der
|
||||||
state.leaf = leaf
|
state.leaf = leaf
|
||||||
go m.renew(ck, state.key, state.leaf.NotAfter)
|
m.startRenew(ck, state.key, state.leaf.NotAfter)
|
||||||
return state.tlscert()
|
return state.tlscert()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -658,31 +666,19 @@ func (m *Manager) authorizedCert(ctx context.Context, key crypto.Signer, ck cert
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
if dir.OrderURL == "" {
|
||||||
|
return nil, nil, errPreRFC
|
||||||
|
}
|
||||||
|
|
||||||
var chain [][]byte
|
|
||||||
switch {
|
|
||||||
// Pre-RFC legacy CA.
|
|
||||||
case dir.OrderURL == "":
|
|
||||||
if err := m.verify(ctx, client, ck.domain); err != nil {
|
|
||||||
return nil, nil, err
|
|
||||||
}
|
|
||||||
der, _, err := client.CreateCert(ctx, csr, 0, true)
|
|
||||||
if err != nil {
|
|
||||||
return nil, nil, err
|
|
||||||
}
|
|
||||||
chain = der
|
|
||||||
// RFC 8555 compliant CA.
|
|
||||||
default:
|
|
||||||
o, err := m.verifyRFC(ctx, client, ck.domain)
|
o, err := m.verifyRFC(ctx, client, ck.domain)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
der, _, err := client.CreateOrderCert(ctx, o.FinalizeURL, csr, true)
|
chain, _, err := client.CreateOrderCert(ctx, o.FinalizeURL, csr, true)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
chain = der
|
|
||||||
}
|
|
||||||
leaf, err = validCert(ck, chain, key, m.now())
|
leaf, err = validCert(ck, chain, key, m.now())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
|
|
@ -690,69 +686,6 @@ func (m *Manager) authorizedCert(ctx context.Context, key crypto.Signer, ck cert
|
||||||
return chain, leaf, nil
|
return chain, leaf, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// verify runs the identifier (domain) pre-authorization flow for legacy CAs
|
|
||||||
// using each applicable ACME challenge type.
|
|
||||||
func (m *Manager) verify(ctx context.Context, client *acme.Client, domain string) error {
|
|
||||||
// Remove all hanging authorizations to reduce rate limit quotas
|
|
||||||
// after we're done.
|
|
||||||
var authzURLs []string
|
|
||||||
defer func() {
|
|
||||||
go m.deactivatePendingAuthz(authzURLs)
|
|
||||||
}()
|
|
||||||
|
|
||||||
// errs accumulates challenge failure errors, printed if all fail
|
|
||||||
errs := make(map[*acme.Challenge]error)
|
|
||||||
challengeTypes := m.supportedChallengeTypes()
|
|
||||||
var nextTyp int // challengeType index of the next challenge type to try
|
|
||||||
for {
|
|
||||||
// Start domain authorization and get the challenge.
|
|
||||||
authz, err := client.Authorize(ctx, domain)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
authzURLs = append(authzURLs, authz.URI)
|
|
||||||
// No point in accepting challenges if the authorization status
|
|
||||||
// is in a final state.
|
|
||||||
switch authz.Status {
|
|
||||||
case acme.StatusValid:
|
|
||||||
return nil // already authorized
|
|
||||||
case acme.StatusInvalid:
|
|
||||||
return fmt.Errorf("acme/autocert: invalid authorization %q", authz.URI)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Pick the next preferred challenge.
|
|
||||||
var chal *acme.Challenge
|
|
||||||
for chal == nil && nextTyp < len(challengeTypes) {
|
|
||||||
chal = pickChallenge(challengeTypes[nextTyp], authz.Challenges)
|
|
||||||
nextTyp++
|
|
||||||
}
|
|
||||||
if chal == nil {
|
|
||||||
errorMsg := fmt.Sprintf("acme/autocert: unable to authorize %q", domain)
|
|
||||||
for chal, err := range errs {
|
|
||||||
errorMsg += fmt.Sprintf("; challenge %q failed with error: %v", chal.Type, err)
|
|
||||||
}
|
|
||||||
return errors.New(errorMsg)
|
|
||||||
}
|
|
||||||
cleanup, err := m.fulfill(ctx, client, chal, domain)
|
|
||||||
if err != nil {
|
|
||||||
errs[chal] = err
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
defer cleanup()
|
|
||||||
if _, err := client.Accept(ctx, chal); err != nil {
|
|
||||||
errs[chal] = err
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
// A challenge is fulfilled and accepted: wait for the CA to validate.
|
|
||||||
if _, err := client.WaitAuthorization(ctx, authz.URI); err != nil {
|
|
||||||
errs[chal] = err
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// verifyRFC runs the identifier (domain) order-based authorization flow for RFC compliant CAs
|
// verifyRFC runs the identifier (domain) order-based authorization flow for RFC compliant CAs
|
||||||
// using each applicable ACME challenge type.
|
// using each applicable ACME challenge type.
|
||||||
func (m *Manager) verifyRFC(ctx context.Context, client *acme.Client, domain string) (*acme.Order, error) {
|
func (m *Manager) verifyRFC(ctx context.Context, client *acme.Client, domain string) (*acme.Order, error) {
|
||||||
|
|
@ -966,7 +899,7 @@ func httpTokenCacheKey(tokenPath string) string {
|
||||||
return path.Base(tokenPath) + "+http-01"
|
return path.Base(tokenPath) + "+http-01"
|
||||||
}
|
}
|
||||||
|
|
||||||
// renew starts a cert renewal timer loop, one per domain.
|
// startRenew starts a cert renewal timer loop, one per domain.
|
||||||
//
|
//
|
||||||
// The loop is scheduled in two cases:
|
// The loop is scheduled in two cases:
|
||||||
// - a cert was fetched from cache for the first time (wasn't in m.state)
|
// - a cert was fetched from cache for the first time (wasn't in m.state)
|
||||||
|
|
@ -974,7 +907,7 @@ func httpTokenCacheKey(tokenPath string) string {
|
||||||
//
|
//
|
||||||
// The key argument is a certificate private key.
|
// The key argument is a certificate private key.
|
||||||
// The exp argument is the cert expiration time (NotAfter).
|
// The exp argument is the cert expiration time (NotAfter).
|
||||||
func (m *Manager) renew(ck certKey, key crypto.Signer, exp time.Time) {
|
func (m *Manager) startRenew(ck certKey, key crypto.Signer, exp time.Time) {
|
||||||
m.renewalMu.Lock()
|
m.renewalMu.Lock()
|
||||||
defer m.renewalMu.Unlock()
|
defer m.renewalMu.Unlock()
|
||||||
if m.renewal[ck] != nil {
|
if m.renewal[ck] != nil {
|
||||||
|
|
@ -1068,7 +1001,7 @@ func (m *Manager) acmeClient(ctx context.Context) (*acme.Client, error) {
|
||||||
if m.Email != "" {
|
if m.Email != "" {
|
||||||
contact = []string{"mailto:" + m.Email}
|
contact = []string{"mailto:" + m.Email}
|
||||||
}
|
}
|
||||||
a := &acme.Account{Contact: contact}
|
a := &acme.Account{Contact: contact, ExternalAccountBinding: m.ExternalAccountBinding}
|
||||||
_, err := client.Register(ctx, a, m.Prompt)
|
_, err := client.Register(ctx, a, m.Prompt)
|
||||||
if err == nil || isAccountAlreadyExist(err) {
|
if err == nil || isAccountAlreadyExist(err) {
|
||||||
m.client = client
|
m.client = client
|
||||||
|
|
|
||||||
11
vendor/golang.org/x/crypto/acme/autocert/cache.go
generated
vendored
11
vendor/golang.org/x/crypto/acme/autocert/cache.go
generated
vendored
|
|
@ -7,7 +7,6 @@ package autocert
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"errors"
|
"errors"
|
||||||
"io/ioutil"
|
|
||||||
"os"
|
"os"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
)
|
)
|
||||||
|
|
@ -41,14 +40,14 @@ type DirCache string
|
||||||
|
|
||||||
// Get reads a certificate data from the specified file name.
|
// Get reads a certificate data from the specified file name.
|
||||||
func (d DirCache) Get(ctx context.Context, name string) ([]byte, error) {
|
func (d DirCache) Get(ctx context.Context, name string) ([]byte, error) {
|
||||||
name = filepath.Join(string(d), name)
|
name = filepath.Join(string(d), filepath.Clean("/"+name))
|
||||||
var (
|
var (
|
||||||
data []byte
|
data []byte
|
||||||
err error
|
err error
|
||||||
done = make(chan struct{})
|
done = make(chan struct{})
|
||||||
)
|
)
|
||||||
go func() {
|
go func() {
|
||||||
data, err = ioutil.ReadFile(name)
|
data, err = os.ReadFile(name)
|
||||||
close(done)
|
close(done)
|
||||||
}()
|
}()
|
||||||
select {
|
select {
|
||||||
|
|
@ -82,7 +81,7 @@ func (d DirCache) Put(ctx context.Context, name string, data []byte) error {
|
||||||
case <-ctx.Done():
|
case <-ctx.Done():
|
||||||
// Don't overwrite the file if the context was canceled.
|
// Don't overwrite the file if the context was canceled.
|
||||||
default:
|
default:
|
||||||
newName := filepath.Join(string(d), name)
|
newName := filepath.Join(string(d), filepath.Clean("/"+name))
|
||||||
err = os.Rename(tmp, newName)
|
err = os.Rename(tmp, newName)
|
||||||
}
|
}
|
||||||
}()
|
}()
|
||||||
|
|
@ -96,7 +95,7 @@ func (d DirCache) Put(ctx context.Context, name string, data []byte) error {
|
||||||
|
|
||||||
// Delete removes the specified file name.
|
// Delete removes the specified file name.
|
||||||
func (d DirCache) Delete(ctx context.Context, name string) error {
|
func (d DirCache) Delete(ctx context.Context, name string) error {
|
||||||
name = filepath.Join(string(d), name)
|
name = filepath.Join(string(d), filepath.Clean("/"+name))
|
||||||
var (
|
var (
|
||||||
err error
|
err error
|
||||||
done = make(chan struct{})
|
done = make(chan struct{})
|
||||||
|
|
@ -119,7 +118,7 @@ func (d DirCache) Delete(ctx context.Context, name string) error {
|
||||||
// writeTempFile writes b to a temporary file, closes the file and returns its path.
|
// writeTempFile writes b to a temporary file, closes the file and returns its path.
|
||||||
func (d DirCache) writeTempFile(prefix string, b []byte) (name string, reterr error) {
|
func (d DirCache) writeTempFile(prefix string, b []byte) (name string, reterr error) {
|
||||||
// TempFile uses 0600 permissions
|
// TempFile uses 0600 permissions
|
||||||
f, err := ioutil.TempFile(string(d), prefix)
|
f, err := os.CreateTemp(string(d), prefix)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
25
vendor/golang.org/x/crypto/acme/autocert/renewal.go
generated
vendored
25
vendor/golang.org/x/crypto/acme/autocert/renewal.go
generated
vendored
|
|
@ -23,6 +23,7 @@ type domainRenewal struct {
|
||||||
|
|
||||||
timerMu sync.Mutex
|
timerMu sync.Mutex
|
||||||
timer *time.Timer
|
timer *time.Timer
|
||||||
|
timerClose chan struct{} // if non-nil, renew closes this channel (and nils out the timer fields) instead of running
|
||||||
}
|
}
|
||||||
|
|
||||||
// start starts a cert renewal timer at the time
|
// start starts a cert renewal timer at the time
|
||||||
|
|
@ -38,16 +39,28 @@ func (dr *domainRenewal) start(exp time.Time) {
|
||||||
dr.timer = time.AfterFunc(dr.next(exp), dr.renew)
|
dr.timer = time.AfterFunc(dr.next(exp), dr.renew)
|
||||||
}
|
}
|
||||||
|
|
||||||
// stop stops the cert renewal timer.
|
// stop stops the cert renewal timer and waits for any in-flight calls to renew
|
||||||
// If the timer is already stopped, calling stop is a noop.
|
// to complete. If the timer is already stopped, calling stop is a noop.
|
||||||
func (dr *domainRenewal) stop() {
|
func (dr *domainRenewal) stop() {
|
||||||
dr.timerMu.Lock()
|
dr.timerMu.Lock()
|
||||||
defer dr.timerMu.Unlock()
|
defer dr.timerMu.Unlock()
|
||||||
|
for {
|
||||||
if dr.timer == nil {
|
if dr.timer == nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
dr.timer.Stop()
|
if dr.timer.Stop() {
|
||||||
dr.timer = nil
|
dr.timer = nil
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
// dr.timer fired, and we acquired dr.timerMu before the renew callback did.
|
||||||
|
// (We know this because otherwise the renew callback would have reset dr.timer!)
|
||||||
|
timerClose := make(chan struct{})
|
||||||
|
dr.timerClose = timerClose
|
||||||
|
dr.timerMu.Unlock()
|
||||||
|
<-timerClose
|
||||||
|
dr.timerMu.Lock()
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// renew is called periodically by a timer.
|
// renew is called periodically by a timer.
|
||||||
|
|
@ -55,7 +68,9 @@ func (dr *domainRenewal) stop() {
|
||||||
func (dr *domainRenewal) renew() {
|
func (dr *domainRenewal) renew() {
|
||||||
dr.timerMu.Lock()
|
dr.timerMu.Lock()
|
||||||
defer dr.timerMu.Unlock()
|
defer dr.timerMu.Unlock()
|
||||||
if dr.timer == nil {
|
if dr.timerClose != nil {
|
||||||
|
close(dr.timerClose)
|
||||||
|
dr.timer, dr.timerClose = nil, nil
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -67,8 +82,8 @@ func (dr *domainRenewal) renew() {
|
||||||
next = renewJitter / 2
|
next = renewJitter / 2
|
||||||
next += time.Duration(pseudoRand.int63n(int64(next)))
|
next += time.Duration(pseudoRand.int63n(int64(next)))
|
||||||
}
|
}
|
||||||
dr.timer = time.AfterFunc(next, dr.renew)
|
|
||||||
testDidRenewLoop(next, err)
|
testDidRenewLoop(next, err)
|
||||||
|
dr.timer = time.AfterFunc(next, dr.renew)
|
||||||
}
|
}
|
||||||
|
|
||||||
// updateState locks and replaces the relevant Manager.state item with the given
|
// updateState locks and replaces the relevant Manager.state item with the given
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/crypto/acme/http.go
generated
vendored
4
vendor/golang.org/x/crypto/acme/http.go
generated
vendored
|
|
@ -12,7 +12,7 @@ import (
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io/ioutil"
|
"io"
|
||||||
"math/big"
|
"math/big"
|
||||||
"net/http"
|
"net/http"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
@ -310,7 +310,7 @@ func isRetriable(code int) bool {
|
||||||
func responseError(resp *http.Response) error {
|
func responseError(resp *http.Response) error {
|
||||||
// don't care if ReadAll returns an error:
|
// don't care if ReadAll returns an error:
|
||||||
// json.Unmarshal will fail in that case anyway
|
// json.Unmarshal will fail in that case anyway
|
||||||
b, _ := ioutil.ReadAll(resp.Body)
|
b, _ := io.ReadAll(resp.Body)
|
||||||
e := &wireError{Status: resp.StatusCode}
|
e := &wireError{Status: resp.StatusCode}
|
||||||
if err := json.Unmarshal(b, e); err != nil {
|
if err := json.Unmarshal(b, e); err != nil {
|
||||||
// this is not a regular error response:
|
// this is not a regular error response:
|
||||||
|
|
|
||||||
40
vendor/golang.org/x/crypto/acme/jws.go
generated
vendored
40
vendor/golang.org/x/crypto/acme/jws.go
generated
vendored
|
|
@ -33,6 +33,10 @@ const noKeyID = KeyID("")
|
||||||
// See https://tools.ietf.org/html/rfc8555#section-6.3 for more details.
|
// See https://tools.ietf.org/html/rfc8555#section-6.3 for more details.
|
||||||
const noPayload = ""
|
const noPayload = ""
|
||||||
|
|
||||||
|
// noNonce indicates that the nonce should be omitted from the protected header.
|
||||||
|
// See jwsEncodeJSON for details.
|
||||||
|
const noNonce = ""
|
||||||
|
|
||||||
// jsonWebSignature can be easily serialized into a JWS following
|
// jsonWebSignature can be easily serialized into a JWS following
|
||||||
// https://tools.ietf.org/html/rfc7515#section-3.2.
|
// https://tools.ietf.org/html/rfc7515#section-3.2.
|
||||||
type jsonWebSignature struct {
|
type jsonWebSignature struct {
|
||||||
|
|
@ -45,30 +49,54 @@ type jsonWebSignature struct {
|
||||||
// The result is serialized in JSON format containing either kid or jwk
|
// The result is serialized in JSON format containing either kid or jwk
|
||||||
// fields based on the provided KeyID value.
|
// fields based on the provided KeyID value.
|
||||||
//
|
//
|
||||||
// If kid is non-empty, its quoted value is inserted in the protected head
|
// The claimset is marshalled using json.Marshal unless it is a string.
|
||||||
|
// In which case it is inserted directly into the message.
|
||||||
|
//
|
||||||
|
// If kid is non-empty, its quoted value is inserted in the protected header
|
||||||
// as "kid" field value. Otherwise, JWK is computed using jwkEncode and inserted
|
// as "kid" field value. Otherwise, JWK is computed using jwkEncode and inserted
|
||||||
// as "jwk" field value. The "jwk" and "kid" fields are mutually exclusive.
|
// as "jwk" field value. The "jwk" and "kid" fields are mutually exclusive.
|
||||||
//
|
//
|
||||||
|
// If nonce is non-empty, its quoted value is inserted in the protected header.
|
||||||
|
//
|
||||||
// See https://tools.ietf.org/html/rfc7515#section-7.
|
// See https://tools.ietf.org/html/rfc7515#section-7.
|
||||||
func jwsEncodeJSON(claimset interface{}, key crypto.Signer, kid KeyID, nonce, url string) ([]byte, error) {
|
func jwsEncodeJSON(claimset interface{}, key crypto.Signer, kid KeyID, nonce, url string) ([]byte, error) {
|
||||||
|
if key == nil {
|
||||||
|
return nil, errors.New("nil key")
|
||||||
|
}
|
||||||
alg, sha := jwsHasher(key.Public())
|
alg, sha := jwsHasher(key.Public())
|
||||||
if alg == "" || !sha.Available() {
|
if alg == "" || !sha.Available() {
|
||||||
return nil, ErrUnsupportedKey
|
return nil, ErrUnsupportedKey
|
||||||
}
|
}
|
||||||
var phead string
|
headers := struct {
|
||||||
|
Alg string `json:"alg"`
|
||||||
|
KID string `json:"kid,omitempty"`
|
||||||
|
JWK json.RawMessage `json:"jwk,omitempty"`
|
||||||
|
Nonce string `json:"nonce,omitempty"`
|
||||||
|
URL string `json:"url"`
|
||||||
|
}{
|
||||||
|
Alg: alg,
|
||||||
|
Nonce: nonce,
|
||||||
|
URL: url,
|
||||||
|
}
|
||||||
switch kid {
|
switch kid {
|
||||||
case noKeyID:
|
case noKeyID:
|
||||||
jwk, err := jwkEncode(key.Public())
|
jwk, err := jwkEncode(key.Public())
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
phead = fmt.Sprintf(`{"alg":%q,"jwk":%s,"nonce":%q,"url":%q}`, alg, jwk, nonce, url)
|
headers.JWK = json.RawMessage(jwk)
|
||||||
default:
|
default:
|
||||||
phead = fmt.Sprintf(`{"alg":%q,"kid":%q,"nonce":%q,"url":%q}`, alg, kid, nonce, url)
|
headers.KID = string(kid)
|
||||||
}
|
}
|
||||||
phead = base64.RawURLEncoding.EncodeToString([]byte(phead))
|
phJSON, err := json.Marshal(headers)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
phead := base64.RawURLEncoding.EncodeToString([]byte(phJSON))
|
||||||
var payload string
|
var payload string
|
||||||
if claimset != noPayload {
|
if val, ok := claimset.(string); ok {
|
||||||
|
payload = val
|
||||||
|
} else {
|
||||||
cs, err := json.Marshal(claimset)
|
cs, err := json.Marshal(claimset)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
|
||||||
44
vendor/golang.org/x/crypto/acme/rfc8555.go
generated
vendored
44
vendor/golang.org/x/crypto/acme/rfc8555.go
generated
vendored
|
|
@ -13,7 +13,6 @@ import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
"net/http"
|
"net/http"
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
@ -24,6 +23,9 @@ import (
|
||||||
//
|
//
|
||||||
// It only works with CAs implementing RFC 8555.
|
// It only works with CAs implementing RFC 8555.
|
||||||
func (c *Client) DeactivateReg(ctx context.Context) error {
|
func (c *Client) DeactivateReg(ctx context.Context) error {
|
||||||
|
if _, err := c.Discover(ctx); err != nil { // required by c.accountKID
|
||||||
|
return err
|
||||||
|
}
|
||||||
url := string(c.accountKID(ctx))
|
url := string(c.accountKID(ctx))
|
||||||
if url == "" {
|
if url == "" {
|
||||||
return ErrNoAccount
|
return ErrNoAccount
|
||||||
|
|
@ -148,6 +150,42 @@ func responseAccount(res *http.Response) (*Account, error) {
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// accountKeyRollover attempts to perform account key rollover.
|
||||||
|
// On success it will change client.Key to the new key.
|
||||||
|
func (c *Client) accountKeyRollover(ctx context.Context, newKey crypto.Signer) error {
|
||||||
|
dir, err := c.Discover(ctx) // Also required by c.accountKID
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
kid := c.accountKID(ctx)
|
||||||
|
if kid == noKeyID {
|
||||||
|
return ErrNoAccount
|
||||||
|
}
|
||||||
|
oldKey, err := jwkEncode(c.Key.Public())
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
payload := struct {
|
||||||
|
Account string `json:"account"`
|
||||||
|
OldKey json.RawMessage `json:"oldKey"`
|
||||||
|
}{
|
||||||
|
Account: string(kid),
|
||||||
|
OldKey: json.RawMessage(oldKey),
|
||||||
|
}
|
||||||
|
inner, err := jwsEncodeJSON(payload, newKey, noKeyID, noNonce, dir.KeyChangeURL)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
res, err := c.post(ctx, nil, dir.KeyChangeURL, base64.RawURLEncoding.EncodeToString(inner), wantStatus(http.StatusOK))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
defer res.Body.Close()
|
||||||
|
c.Key = newKey
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
// AuthorizeOrder initiates the order-based application for certificate issuance,
|
// AuthorizeOrder initiates the order-based application for certificate issuance,
|
||||||
// as opposed to pre-authorization in Authorize.
|
// as opposed to pre-authorization in Authorize.
|
||||||
// It is only supported by CAs implementing RFC 8555.
|
// It is only supported by CAs implementing RFC 8555.
|
||||||
|
|
@ -351,7 +389,7 @@ func (c *Client) fetchCertRFC(ctx context.Context, url string, bundle bool) ([][
|
||||||
// Get all the bytes up to a sane maximum.
|
// Get all the bytes up to a sane maximum.
|
||||||
// Account very roughly for base64 overhead.
|
// Account very roughly for base64 overhead.
|
||||||
const max = maxCertChainSize + maxCertChainSize/33
|
const max = maxCertChainSize + maxCertChainSize/33
|
||||||
b, err := ioutil.ReadAll(io.LimitReader(res.Body, max+1))
|
b, err := io.ReadAll(io.LimitReader(res.Body, max+1))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, fmt.Errorf("acme: fetch cert response stream: %v", err)
|
return nil, fmt.Errorf("acme: fetch cert response stream: %v", err)
|
||||||
}
|
}
|
||||||
|
|
@ -430,7 +468,7 @@ func (c *Client) ListCertAlternates(ctx context.Context, url string) ([]string,
|
||||||
|
|
||||||
// We don't need the body but we need to discard it so we don't end up
|
// We don't need the body but we need to discard it so we don't end up
|
||||||
// preventing keep-alive
|
// preventing keep-alive
|
||||||
if _, err := io.Copy(ioutil.Discard, res.Body); err != nil {
|
if _, err := io.Copy(io.Discard, res.Body); err != nil {
|
||||||
return nil, fmt.Errorf("acme: cert alternates response stream: %v", err)
|
return nil, fmt.Errorf("acme: cert alternates response stream: %v", err)
|
||||||
}
|
}
|
||||||
alts := linkHeader(res.Header, "alternate")
|
alts := linkHeader(res.Header, "alternate")
|
||||||
|
|
|
||||||
8
vendor/golang.org/x/crypto/acme/types.go
generated
vendored
8
vendor/golang.org/x/crypto/acme/types.go
generated
vendored
|
|
@ -305,14 +305,6 @@ type Directory struct {
|
||||||
ExternalAccountRequired bool
|
ExternalAccountRequired bool
|
||||||
}
|
}
|
||||||
|
|
||||||
// rfcCompliant reports whether the ACME server implements RFC 8555.
|
|
||||||
// Note that some servers may have incomplete RFC implementation
|
|
||||||
// even if the returned value is true.
|
|
||||||
// If rfcCompliant reports false, the server most likely implements draft-02.
|
|
||||||
func (d *Directory) rfcCompliant() bool {
|
|
||||||
return d.OrderURL != ""
|
|
||||||
}
|
|
||||||
|
|
||||||
// Order represents a client's request for a certificate.
|
// Order represents a client's request for a certificate.
|
||||||
// It tracks the request flow progress through to issuance.
|
// It tracks the request flow progress through to issuance.
|
||||||
type Order struct {
|
type Order struct {
|
||||||
|
|
|
||||||
6
vendor/golang.org/x/crypto/argon2/argon2.go
generated
vendored
6
vendor/golang.org/x/crypto/argon2/argon2.go
generated
vendored
|
|
@ -11,8 +11,7 @@
|
||||||
// If you aren't sure which function you need, use Argon2id (IDKey) and
|
// If you aren't sure which function you need, use Argon2id (IDKey) and
|
||||||
// the parameter recommendations for your scenario.
|
// the parameter recommendations for your scenario.
|
||||||
//
|
//
|
||||||
//
|
// # Argon2i
|
||||||
// Argon2i
|
|
||||||
//
|
//
|
||||||
// Argon2i (implemented by Key) is the side-channel resistant version of Argon2.
|
// Argon2i (implemented by Key) is the side-channel resistant version of Argon2.
|
||||||
// It uses data-independent memory access, which is preferred for password
|
// It uses data-independent memory access, which is preferred for password
|
||||||
|
|
@ -21,8 +20,7 @@
|
||||||
// parameters (taken from [2]) for non-interactive operations are time=3 and to
|
// parameters (taken from [2]) for non-interactive operations are time=3 and to
|
||||||
// use the maximum available memory.
|
// use the maximum available memory.
|
||||||
//
|
//
|
||||||
//
|
// # Argon2id
|
||||||
// Argon2id
|
|
||||||
//
|
//
|
||||||
// Argon2id (implemented by IDKey) is a hybrid version of Argon2 combining
|
// Argon2id (implemented by IDKey) is a hybrid version of Argon2 combining
|
||||||
// Argon2i and Argon2d. It uses data-independent memory access for the first
|
// Argon2i and Argon2d. It uses data-independent memory access for the first
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/crypto/chacha20/chacha_generic.go
generated
vendored
4
vendor/golang.org/x/crypto/chacha20/chacha_generic.go
generated
vendored
|
|
@ -12,7 +12,7 @@ import (
|
||||||
"errors"
|
"errors"
|
||||||
"math/bits"
|
"math/bits"
|
||||||
|
|
||||||
"golang.org/x/crypto/internal/subtle"
|
"golang.org/x/crypto/internal/alias"
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
|
@ -189,7 +189,7 @@ func (s *Cipher) XORKeyStream(dst, src []byte) {
|
||||||
panic("chacha20: output smaller than input")
|
panic("chacha20: output smaller than input")
|
||||||
}
|
}
|
||||||
dst = dst[:len(src)]
|
dst = dst[:len(src)]
|
||||||
if subtle.InexactOverlap(dst, src) {
|
if alias.InexactOverlap(dst, src) {
|
||||||
panic("chacha20: invalid buffer overlap")
|
panic("chacha20: invalid buffer overlap")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
1
vendor/golang.org/x/crypto/chacha20/chacha_s390x.go
generated
vendored
1
vendor/golang.org/x/crypto/chacha20/chacha_s390x.go
generated
vendored
|
|
@ -15,6 +15,7 @@ const bufSize = 256
|
||||||
|
|
||||||
// xorKeyStreamVX is an assembly implementation of XORKeyStream. It must only
|
// xorKeyStreamVX is an assembly implementation of XORKeyStream. It must only
|
||||||
// be called when the vector facility is available. Implementation in asm_s390x.s.
|
// be called when the vector facility is available. Implementation in asm_s390x.s.
|
||||||
|
//
|
||||||
//go:noescape
|
//go:noescape
|
||||||
func xorKeyStreamVX(dst, src []byte, key *[8]uint32, nonce *[3]uint32, counter *uint32)
|
func xorKeyStreamVX(dst, src []byte, key *[8]uint32, nonce *[3]uint32, counter *uint32)
|
||||||
|
|
||||||
|
|
|
||||||
9
vendor/golang.org/x/crypto/curve25519/curve25519.go
generated
vendored
9
vendor/golang.org/x/crypto/curve25519/curve25519.go
generated
vendored
|
|
@ -9,7 +9,8 @@ package curve25519 // import "golang.org/x/crypto/curve25519"
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"crypto/subtle"
|
"crypto/subtle"
|
||||||
"fmt"
|
"errors"
|
||||||
|
"strconv"
|
||||||
|
|
||||||
"golang.org/x/crypto/curve25519/internal/field"
|
"golang.org/x/crypto/curve25519/internal/field"
|
||||||
)
|
)
|
||||||
|
|
@ -124,10 +125,10 @@ func X25519(scalar, point []byte) ([]byte, error) {
|
||||||
func x25519(dst *[32]byte, scalar, point []byte) ([]byte, error) {
|
func x25519(dst *[32]byte, scalar, point []byte) ([]byte, error) {
|
||||||
var in [32]byte
|
var in [32]byte
|
||||||
if l := len(scalar); l != 32 {
|
if l := len(scalar); l != 32 {
|
||||||
return nil, fmt.Errorf("bad scalar length: %d, expected %d", l, 32)
|
return nil, errors.New("bad scalar length: " + strconv.Itoa(l) + ", expected 32")
|
||||||
}
|
}
|
||||||
if l := len(point); l != 32 {
|
if l := len(point); l != 32 {
|
||||||
return nil, fmt.Errorf("bad point length: %d, expected %d", l, 32)
|
return nil, errors.New("bad point length: " + strconv.Itoa(l) + ", expected 32")
|
||||||
}
|
}
|
||||||
copy(in[:], scalar)
|
copy(in[:], scalar)
|
||||||
if &point[0] == &Basepoint[0] {
|
if &point[0] == &Basepoint[0] {
|
||||||
|
|
@ -138,7 +139,7 @@ func x25519(dst *[32]byte, scalar, point []byte) ([]byte, error) {
|
||||||
copy(base[:], point)
|
copy(base[:], point)
|
||||||
ScalarMult(dst, &in, &base)
|
ScalarMult(dst, &in, &base)
|
||||||
if subtle.ConstantTimeCompare(dst[:], zero[:]) == 1 {
|
if subtle.ConstantTimeCompare(dst[:], zero[:]) == 1 {
|
||||||
return nil, fmt.Errorf("bad input point: low order point")
|
return nil, errors.New("bad input point: low order point")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return dst[:], nil
|
return dst[:], nil
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/curve25519/internal/field/fe_amd64.go
generated
vendored
3
vendor/golang.org/x/crypto/curve25519/internal/field/fe_amd64.go
generated
vendored
|
|
@ -1,13 +1,16 @@
|
||||||
// Code generated by command: go run fe_amd64_asm.go -out ../fe_amd64.s -stubs ../fe_amd64.go -pkg field. DO NOT EDIT.
|
// Code generated by command: go run fe_amd64_asm.go -out ../fe_amd64.s -stubs ../fe_amd64.go -pkg field. DO NOT EDIT.
|
||||||
|
|
||||||
|
//go:build amd64 && gc && !purego
|
||||||
// +build amd64,gc,!purego
|
// +build amd64,gc,!purego
|
||||||
|
|
||||||
package field
|
package field
|
||||||
|
|
||||||
// feMul sets out = a * b. It works like feMulGeneric.
|
// feMul sets out = a * b. It works like feMulGeneric.
|
||||||
|
//
|
||||||
//go:noescape
|
//go:noescape
|
||||||
func feMul(out *Element, a *Element, b *Element)
|
func feMul(out *Element, a *Element, b *Element)
|
||||||
|
|
||||||
// feSquare sets out = a * a. It works like feSquareGeneric.
|
// feSquare sets out = a * a. It works like feSquareGeneric.
|
||||||
|
//
|
||||||
//go:noescape
|
//go:noescape
|
||||||
func feSquare(out *Element, a *Element)
|
func feSquare(out *Element, a *Element)
|
||||||
|
|
|
||||||
188
vendor/golang.org/x/crypto/ed25519/ed25519.go
generated
vendored
188
vendor/golang.org/x/crypto/ed25519/ed25519.go
generated
vendored
|
|
@ -1,13 +1,7 @@
|
||||||
// Copyright 2016 The Go Authors. All rights reserved.
|
// Copyright 2019 The Go Authors. All rights reserved.
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
// In Go 1.13, the ed25519 package was promoted to the standard library as
|
|
||||||
// crypto/ed25519, and this package became a wrapper for the standard library one.
|
|
||||||
//
|
|
||||||
//go:build !go1.13
|
|
||||||
// +build !go1.13
|
|
||||||
|
|
||||||
// Package ed25519 implements the Ed25519 signature algorithm. See
|
// Package ed25519 implements the Ed25519 signature algorithm. See
|
||||||
// https://ed25519.cr.yp.to/.
|
// https://ed25519.cr.yp.to/.
|
||||||
//
|
//
|
||||||
|
|
@ -16,21 +10,15 @@
|
||||||
// representation includes a public key suffix to make multiple signing
|
// representation includes a public key suffix to make multiple signing
|
||||||
// operations with the same key more efficient. This package refers to the RFC
|
// operations with the same key more efficient. This package refers to the RFC
|
||||||
// 8032 private key as the “seed”.
|
// 8032 private key as the “seed”.
|
||||||
|
//
|
||||||
|
// Beginning with Go 1.13, the functionality of this package was moved to the
|
||||||
|
// standard library as crypto/ed25519. This package only acts as a compatibility
|
||||||
|
// wrapper.
|
||||||
package ed25519
|
package ed25519
|
||||||
|
|
||||||
// This code is a port of the public domain, “ref10” implementation of ed25519
|
|
||||||
// from SUPERCOP.
|
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"crypto/ed25519"
|
||||||
"crypto"
|
|
||||||
cryptorand "crypto/rand"
|
|
||||||
"crypto/sha512"
|
|
||||||
"errors"
|
|
||||||
"io"
|
"io"
|
||||||
"strconv"
|
|
||||||
|
|
||||||
"golang.org/x/crypto/ed25519/internal/edwards25519"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
|
@ -45,57 +33,21 @@ const (
|
||||||
)
|
)
|
||||||
|
|
||||||
// PublicKey is the type of Ed25519 public keys.
|
// PublicKey is the type of Ed25519 public keys.
|
||||||
type PublicKey []byte
|
//
|
||||||
|
// This type is an alias for crypto/ed25519's PublicKey type.
|
||||||
|
// See the crypto/ed25519 package for the methods on this type.
|
||||||
|
type PublicKey = ed25519.PublicKey
|
||||||
|
|
||||||
// PrivateKey is the type of Ed25519 private keys. It implements crypto.Signer.
|
// PrivateKey is the type of Ed25519 private keys. It implements crypto.Signer.
|
||||||
type PrivateKey []byte
|
//
|
||||||
|
// This type is an alias for crypto/ed25519's PrivateKey type.
|
||||||
// Public returns the PublicKey corresponding to priv.
|
// See the crypto/ed25519 package for the methods on this type.
|
||||||
func (priv PrivateKey) Public() crypto.PublicKey {
|
type PrivateKey = ed25519.PrivateKey
|
||||||
publicKey := make([]byte, PublicKeySize)
|
|
||||||
copy(publicKey, priv[32:])
|
|
||||||
return PublicKey(publicKey)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Seed returns the private key seed corresponding to priv. It is provided for
|
|
||||||
// interoperability with RFC 8032. RFC 8032's private keys correspond to seeds
|
|
||||||
// in this package.
|
|
||||||
func (priv PrivateKey) Seed() []byte {
|
|
||||||
seed := make([]byte, SeedSize)
|
|
||||||
copy(seed, priv[:32])
|
|
||||||
return seed
|
|
||||||
}
|
|
||||||
|
|
||||||
// Sign signs the given message with priv.
|
|
||||||
// Ed25519 performs two passes over messages to be signed and therefore cannot
|
|
||||||
// handle pre-hashed messages. Thus opts.HashFunc() must return zero to
|
|
||||||
// indicate the message hasn't been hashed. This can be achieved by passing
|
|
||||||
// crypto.Hash(0) as the value for opts.
|
|
||||||
func (priv PrivateKey) Sign(rand io.Reader, message []byte, opts crypto.SignerOpts) (signature []byte, err error) {
|
|
||||||
if opts.HashFunc() != crypto.Hash(0) {
|
|
||||||
return nil, errors.New("ed25519: cannot sign hashed message")
|
|
||||||
}
|
|
||||||
|
|
||||||
return Sign(priv, message), nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// GenerateKey generates a public/private key pair using entropy from rand.
|
// GenerateKey generates a public/private key pair using entropy from rand.
|
||||||
// If rand is nil, crypto/rand.Reader will be used.
|
// If rand is nil, crypto/rand.Reader will be used.
|
||||||
func GenerateKey(rand io.Reader) (PublicKey, PrivateKey, error) {
|
func GenerateKey(rand io.Reader) (PublicKey, PrivateKey, error) {
|
||||||
if rand == nil {
|
return ed25519.GenerateKey(rand)
|
||||||
rand = cryptorand.Reader
|
|
||||||
}
|
|
||||||
|
|
||||||
seed := make([]byte, SeedSize)
|
|
||||||
if _, err := io.ReadFull(rand, seed); err != nil {
|
|
||||||
return nil, nil, err
|
|
||||||
}
|
|
||||||
|
|
||||||
privateKey := NewKeyFromSeed(seed)
|
|
||||||
publicKey := make([]byte, PublicKeySize)
|
|
||||||
copy(publicKey, privateKey[32:])
|
|
||||||
|
|
||||||
return publicKey, privateKey, nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// NewKeyFromSeed calculates a private key from a seed. It will panic if
|
// NewKeyFromSeed calculates a private key from a seed. It will panic if
|
||||||
|
|
@ -103,121 +55,17 @@ func GenerateKey(rand io.Reader) (PublicKey, PrivateKey, error) {
|
||||||
// with RFC 8032. RFC 8032's private keys correspond to seeds in this
|
// with RFC 8032. RFC 8032's private keys correspond to seeds in this
|
||||||
// package.
|
// package.
|
||||||
func NewKeyFromSeed(seed []byte) PrivateKey {
|
func NewKeyFromSeed(seed []byte) PrivateKey {
|
||||||
if l := len(seed); l != SeedSize {
|
return ed25519.NewKeyFromSeed(seed)
|
||||||
panic("ed25519: bad seed length: " + strconv.Itoa(l))
|
|
||||||
}
|
|
||||||
|
|
||||||
digest := sha512.Sum512(seed)
|
|
||||||
digest[0] &= 248
|
|
||||||
digest[31] &= 127
|
|
||||||
digest[31] |= 64
|
|
||||||
|
|
||||||
var A edwards25519.ExtendedGroupElement
|
|
||||||
var hBytes [32]byte
|
|
||||||
copy(hBytes[:], digest[:])
|
|
||||||
edwards25519.GeScalarMultBase(&A, &hBytes)
|
|
||||||
var publicKeyBytes [32]byte
|
|
||||||
A.ToBytes(&publicKeyBytes)
|
|
||||||
|
|
||||||
privateKey := make([]byte, PrivateKeySize)
|
|
||||||
copy(privateKey, seed)
|
|
||||||
copy(privateKey[32:], publicKeyBytes[:])
|
|
||||||
|
|
||||||
return privateKey
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Sign signs the message with privateKey and returns a signature. It will
|
// Sign signs the message with privateKey and returns a signature. It will
|
||||||
// panic if len(privateKey) is not PrivateKeySize.
|
// panic if len(privateKey) is not PrivateKeySize.
|
||||||
func Sign(privateKey PrivateKey, message []byte) []byte {
|
func Sign(privateKey PrivateKey, message []byte) []byte {
|
||||||
if l := len(privateKey); l != PrivateKeySize {
|
return ed25519.Sign(privateKey, message)
|
||||||
panic("ed25519: bad private key length: " + strconv.Itoa(l))
|
|
||||||
}
|
|
||||||
|
|
||||||
h := sha512.New()
|
|
||||||
h.Write(privateKey[:32])
|
|
||||||
|
|
||||||
var digest1, messageDigest, hramDigest [64]byte
|
|
||||||
var expandedSecretKey [32]byte
|
|
||||||
h.Sum(digest1[:0])
|
|
||||||
copy(expandedSecretKey[:], digest1[:])
|
|
||||||
expandedSecretKey[0] &= 248
|
|
||||||
expandedSecretKey[31] &= 63
|
|
||||||
expandedSecretKey[31] |= 64
|
|
||||||
|
|
||||||
h.Reset()
|
|
||||||
h.Write(digest1[32:])
|
|
||||||
h.Write(message)
|
|
||||||
h.Sum(messageDigest[:0])
|
|
||||||
|
|
||||||
var messageDigestReduced [32]byte
|
|
||||||
edwards25519.ScReduce(&messageDigestReduced, &messageDigest)
|
|
||||||
var R edwards25519.ExtendedGroupElement
|
|
||||||
edwards25519.GeScalarMultBase(&R, &messageDigestReduced)
|
|
||||||
|
|
||||||
var encodedR [32]byte
|
|
||||||
R.ToBytes(&encodedR)
|
|
||||||
|
|
||||||
h.Reset()
|
|
||||||
h.Write(encodedR[:])
|
|
||||||
h.Write(privateKey[32:])
|
|
||||||
h.Write(message)
|
|
||||||
h.Sum(hramDigest[:0])
|
|
||||||
var hramDigestReduced [32]byte
|
|
||||||
edwards25519.ScReduce(&hramDigestReduced, &hramDigest)
|
|
||||||
|
|
||||||
var s [32]byte
|
|
||||||
edwards25519.ScMulAdd(&s, &hramDigestReduced, &expandedSecretKey, &messageDigestReduced)
|
|
||||||
|
|
||||||
signature := make([]byte, SignatureSize)
|
|
||||||
copy(signature[:], encodedR[:])
|
|
||||||
copy(signature[32:], s[:])
|
|
||||||
|
|
||||||
return signature
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Verify reports whether sig is a valid signature of message by publicKey. It
|
// Verify reports whether sig is a valid signature of message by publicKey. It
|
||||||
// will panic if len(publicKey) is not PublicKeySize.
|
// will panic if len(publicKey) is not PublicKeySize.
|
||||||
func Verify(publicKey PublicKey, message, sig []byte) bool {
|
func Verify(publicKey PublicKey, message, sig []byte) bool {
|
||||||
if l := len(publicKey); l != PublicKeySize {
|
return ed25519.Verify(publicKey, message, sig)
|
||||||
panic("ed25519: bad public key length: " + strconv.Itoa(l))
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(sig) != SignatureSize || sig[63]&224 != 0 {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
var A edwards25519.ExtendedGroupElement
|
|
||||||
var publicKeyBytes [32]byte
|
|
||||||
copy(publicKeyBytes[:], publicKey)
|
|
||||||
if !A.FromBytes(&publicKeyBytes) {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
edwards25519.FeNeg(&A.X, &A.X)
|
|
||||||
edwards25519.FeNeg(&A.T, &A.T)
|
|
||||||
|
|
||||||
h := sha512.New()
|
|
||||||
h.Write(sig[:32])
|
|
||||||
h.Write(publicKey[:])
|
|
||||||
h.Write(message)
|
|
||||||
var digest [64]byte
|
|
||||||
h.Sum(digest[:0])
|
|
||||||
|
|
||||||
var hReduced [32]byte
|
|
||||||
edwards25519.ScReduce(&hReduced, &digest)
|
|
||||||
|
|
||||||
var R edwards25519.ProjectiveGroupElement
|
|
||||||
var s [32]byte
|
|
||||||
copy(s[:], sig[32:])
|
|
||||||
|
|
||||||
// https://tools.ietf.org/html/rfc8032#section-5.1.7 requires that s be in
|
|
||||||
// the range [0, order) in order to prevent signature malleability.
|
|
||||||
if !edwards25519.ScMinimal(&s) {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
edwards25519.GeDoubleScalarMultVartime(&R, &hReduced, &A, &s)
|
|
||||||
|
|
||||||
var checkR [32]byte
|
|
||||||
R.ToBytes(&checkR)
|
|
||||||
return bytes.Equal(sig[:32], checkR[:])
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
74
vendor/golang.org/x/crypto/ed25519/ed25519_go113.go
generated
vendored
74
vendor/golang.org/x/crypto/ed25519/ed25519_go113.go
generated
vendored
|
|
@ -1,74 +0,0 @@
|
||||||
// Copyright 2019 The Go Authors. All rights reserved.
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file.
|
|
||||||
|
|
||||||
//go:build go1.13
|
|
||||||
// +build go1.13
|
|
||||||
|
|
||||||
// Package ed25519 implements the Ed25519 signature algorithm. See
|
|
||||||
// https://ed25519.cr.yp.to/.
|
|
||||||
//
|
|
||||||
// These functions are also compatible with the “Ed25519” function defined in
|
|
||||||
// RFC 8032. However, unlike RFC 8032's formulation, this package's private key
|
|
||||||
// representation includes a public key suffix to make multiple signing
|
|
||||||
// operations with the same key more efficient. This package refers to the RFC
|
|
||||||
// 8032 private key as the “seed”.
|
|
||||||
//
|
|
||||||
// Beginning with Go 1.13, the functionality of this package was moved to the
|
|
||||||
// standard library as crypto/ed25519. This package only acts as a compatibility
|
|
||||||
// wrapper.
|
|
||||||
package ed25519
|
|
||||||
|
|
||||||
import (
|
|
||||||
"crypto/ed25519"
|
|
||||||
"io"
|
|
||||||
)
|
|
||||||
|
|
||||||
const (
|
|
||||||
// PublicKeySize is the size, in bytes, of public keys as used in this package.
|
|
||||||
PublicKeySize = 32
|
|
||||||
// PrivateKeySize is the size, in bytes, of private keys as used in this package.
|
|
||||||
PrivateKeySize = 64
|
|
||||||
// SignatureSize is the size, in bytes, of signatures generated and verified by this package.
|
|
||||||
SignatureSize = 64
|
|
||||||
// SeedSize is the size, in bytes, of private key seeds. These are the private key representations used by RFC 8032.
|
|
||||||
SeedSize = 32
|
|
||||||
)
|
|
||||||
|
|
||||||
// PublicKey is the type of Ed25519 public keys.
|
|
||||||
//
|
|
||||||
// This type is an alias for crypto/ed25519's PublicKey type.
|
|
||||||
// See the crypto/ed25519 package for the methods on this type.
|
|
||||||
type PublicKey = ed25519.PublicKey
|
|
||||||
|
|
||||||
// PrivateKey is the type of Ed25519 private keys. It implements crypto.Signer.
|
|
||||||
//
|
|
||||||
// This type is an alias for crypto/ed25519's PrivateKey type.
|
|
||||||
// See the crypto/ed25519 package for the methods on this type.
|
|
||||||
type PrivateKey = ed25519.PrivateKey
|
|
||||||
|
|
||||||
// GenerateKey generates a public/private key pair using entropy from rand.
|
|
||||||
// If rand is nil, crypto/rand.Reader will be used.
|
|
||||||
func GenerateKey(rand io.Reader) (PublicKey, PrivateKey, error) {
|
|
||||||
return ed25519.GenerateKey(rand)
|
|
||||||
}
|
|
||||||
|
|
||||||
// NewKeyFromSeed calculates a private key from a seed. It will panic if
|
|
||||||
// len(seed) is not SeedSize. This function is provided for interoperability
|
|
||||||
// with RFC 8032. RFC 8032's private keys correspond to seeds in this
|
|
||||||
// package.
|
|
||||||
func NewKeyFromSeed(seed []byte) PrivateKey {
|
|
||||||
return ed25519.NewKeyFromSeed(seed)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Sign signs the message with privateKey and returns a signature. It will
|
|
||||||
// panic if len(privateKey) is not PrivateKeySize.
|
|
||||||
func Sign(privateKey PrivateKey, message []byte) []byte {
|
|
||||||
return ed25519.Sign(privateKey, message)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Verify reports whether sig is a valid signature of message by publicKey. It
|
|
||||||
// will panic if len(publicKey) is not PublicKeySize.
|
|
||||||
func Verify(publicKey PublicKey, message, sig []byte) bool {
|
|
||||||
return ed25519.Verify(publicKey, message, sig)
|
|
||||||
}
|
|
||||||
1422
vendor/golang.org/x/crypto/ed25519/internal/edwards25519/const.go
generated
vendored
1422
vendor/golang.org/x/crypto/ed25519/internal/edwards25519/const.go
generated
vendored
File diff suppressed because it is too large
Load diff
1793
vendor/golang.org/x/crypto/ed25519/internal/edwards25519/edwards25519.go
generated
vendored
1793
vendor/golang.org/x/crypto/ed25519/internal/edwards25519/edwards25519.go
generated
vendored
File diff suppressed because it is too large
Load diff
|
|
@ -5,9 +5,8 @@
|
||||||
//go:build !purego
|
//go:build !purego
|
||||||
// +build !purego
|
// +build !purego
|
||||||
|
|
||||||
// Package subtle implements functions that are often useful in cryptographic
|
// Package alias implements memory aliasing tests.
|
||||||
// code but require careful thought to use correctly.
|
package alias
|
||||||
package subtle // import "golang.org/x/crypto/internal/subtle"
|
|
||||||
|
|
||||||
import "unsafe"
|
import "unsafe"
|
||||||
|
|
||||||
|
|
@ -5,9 +5,8 @@
|
||||||
//go:build purego
|
//go:build purego
|
||||||
// +build purego
|
// +build purego
|
||||||
|
|
||||||
// Package subtle implements functions that are often useful in cryptographic
|
// Package alias implements memory aliasing tests.
|
||||||
// code but require careful thought to use correctly.
|
package alias
|
||||||
package subtle // import "golang.org/x/crypto/internal/subtle"
|
|
||||||
|
|
||||||
// This is the Google App Engine standard variant based on reflect
|
// This is the Google App Engine standard variant based on reflect
|
||||||
// because the unsafe package and cgo are disallowed.
|
// because the unsafe package and cgo are disallowed.
|
||||||
1
vendor/golang.org/x/crypto/internal/poly1305/sum_generic.go
generated
vendored
1
vendor/golang.org/x/crypto/internal/poly1305/sum_generic.go
generated
vendored
|
|
@ -279,7 +279,6 @@ const (
|
||||||
// finalize completes the modular reduction of h and computes
|
// finalize completes the modular reduction of h and computes
|
||||||
//
|
//
|
||||||
// out = h + s mod 2¹²⁸
|
// out = h + s mod 2¹²⁸
|
||||||
//
|
|
||||||
func finalize(out *[TagSize]byte, h *[3]uint64, s *[2]uint64) {
|
func finalize(out *[TagSize]byte, h *[3]uint64, s *[2]uint64) {
|
||||||
h0, h1, h2 := h[0], h[1], h[2]
|
h0, h1, h2 := h[0], h[1], h[2]
|
||||||
|
|
||||||
|
|
|
||||||
1
vendor/golang.org/x/crypto/internal/poly1305/sum_s390x.go
generated
vendored
1
vendor/golang.org/x/crypto/internal/poly1305/sum_s390x.go
generated
vendored
|
|
@ -14,6 +14,7 @@ import (
|
||||||
// updateVX is an assembly implementation of Poly1305 that uses vector
|
// updateVX is an assembly implementation of Poly1305 that uses vector
|
||||||
// instructions. It must only be called if the vector facility (vx) is
|
// instructions. It must only be called if the vector facility (vx) is
|
||||||
// available.
|
// available.
|
||||||
|
//
|
||||||
//go:noescape
|
//go:noescape
|
||||||
func updateVX(state *macState, msg []byte)
|
func updateVX(state *macState, msg []byte)
|
||||||
|
|
||||||
|
|
|
||||||
6
vendor/golang.org/x/crypto/nacl/secretbox/secretbox.go
generated
vendored
6
vendor/golang.org/x/crypto/nacl/secretbox/secretbox.go
generated
vendored
|
|
@ -35,8 +35,8 @@ This package is interoperable with NaCl: https://nacl.cr.yp.to/secretbox.html.
|
||||||
package secretbox // import "golang.org/x/crypto/nacl/secretbox"
|
package secretbox // import "golang.org/x/crypto/nacl/secretbox"
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"golang.org/x/crypto/internal/alias"
|
||||||
"golang.org/x/crypto/internal/poly1305"
|
"golang.org/x/crypto/internal/poly1305"
|
||||||
"golang.org/x/crypto/internal/subtle"
|
|
||||||
"golang.org/x/crypto/salsa20/salsa"
|
"golang.org/x/crypto/salsa20/salsa"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -88,7 +88,7 @@ func Seal(out, message []byte, nonce *[24]byte, key *[32]byte) []byte {
|
||||||
copy(poly1305Key[:], firstBlock[:])
|
copy(poly1305Key[:], firstBlock[:])
|
||||||
|
|
||||||
ret, out := sliceForAppend(out, len(message)+poly1305.TagSize)
|
ret, out := sliceForAppend(out, len(message)+poly1305.TagSize)
|
||||||
if subtle.AnyOverlap(out, message) {
|
if alias.AnyOverlap(out, message) {
|
||||||
panic("nacl: invalid buffer overlap")
|
panic("nacl: invalid buffer overlap")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -147,7 +147,7 @@ func Open(out, box []byte, nonce *[24]byte, key *[32]byte) ([]byte, bool) {
|
||||||
}
|
}
|
||||||
|
|
||||||
ret, out := sliceForAppend(out, len(box)-Overhead)
|
ret, out := sliceForAppend(out, len(box)-Overhead)
|
||||||
if subtle.AnyOverlap(out, box) {
|
if alias.AnyOverlap(out, box) {
|
||||||
panic("nacl: invalid buffer overlap")
|
panic("nacl: invalid buffer overlap")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/crypto/openpgp/armor/armor.go
generated
vendored
2
vendor/golang.org/x/crypto/openpgp/armor/armor.go
generated
vendored
|
|
@ -23,12 +23,14 @@ import (
|
||||||
// A Block represents an OpenPGP armored structure.
|
// A Block represents an OpenPGP armored structure.
|
||||||
//
|
//
|
||||||
// The encoded form is:
|
// The encoded form is:
|
||||||
|
//
|
||||||
// -----BEGIN Type-----
|
// -----BEGIN Type-----
|
||||||
// Headers
|
// Headers
|
||||||
//
|
//
|
||||||
// base64-encoded Bytes
|
// base64-encoded Bytes
|
||||||
// '=' base64 encoded checksum
|
// '=' base64 encoded checksum
|
||||||
// -----END Type-----
|
// -----END Type-----
|
||||||
|
//
|
||||||
// where Headers is a possibly empty sequence of Key: Value lines.
|
// where Headers is a possibly empty sequence of Key: Value lines.
|
||||||
//
|
//
|
||||||
// Since the armored data can be very large, this package presents a streaming
|
// Since the armored data can be very large, this package presents a streaming
|
||||||
|
|
|
||||||
1
vendor/golang.org/x/crypto/openpgp/armor/encode.go
generated
vendored
1
vendor/golang.org/x/crypto/openpgp/armor/encode.go
generated
vendored
|
|
@ -96,6 +96,7 @@ func (l *lineBreaker) Close() (err error) {
|
||||||
// trailer.
|
// trailer.
|
||||||
//
|
//
|
||||||
// It's built into a stack of io.Writers:
|
// It's built into a stack of io.Writers:
|
||||||
|
//
|
||||||
// encoding -> base64 encoder -> lineBreaker -> out
|
// encoding -> base64 encoder -> lineBreaker -> out
|
||||||
type encoding struct {
|
type encoding struct {
|
||||||
out io.Writer
|
out io.Writer
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/crypto/openpgp/elgamal/elgamal.go
generated
vendored
4
vendor/golang.org/x/crypto/openpgp/elgamal/elgamal.go
generated
vendored
|
|
@ -77,8 +77,8 @@ func Encrypt(random io.Reader, pub *PublicKey, msg []byte) (c1, c2 *big.Int, err
|
||||||
// returns the plaintext of the message. An error can result only if the
|
// returns the plaintext of the message. An error can result only if the
|
||||||
// ciphertext is invalid. Users should keep in mind that this is a padding
|
// ciphertext is invalid. Users should keep in mind that this is a padding
|
||||||
// oracle and thus, if exposed to an adaptive chosen ciphertext attack, can
|
// oracle and thus, if exposed to an adaptive chosen ciphertext attack, can
|
||||||
// be used to break the cryptosystem. See ``Chosen Ciphertext Attacks
|
// be used to break the cryptosystem. See “Chosen Ciphertext Attacks
|
||||||
// Against Protocols Based on the RSA Encryption Standard PKCS #1'', Daniel
|
// Against Protocols Based on the RSA Encryption Standard PKCS #1”, Daniel
|
||||||
// Bleichenbacher, Advances in Cryptology (Crypto '98),
|
// Bleichenbacher, Advances in Cryptology (Crypto '98),
|
||||||
func Decrypt(priv *PrivateKey, c1, c2 *big.Int) (msg []byte, err error) {
|
func Decrypt(priv *PrivateKey, c1, c2 *big.Int) (msg []byte, err error) {
|
||||||
s := new(big.Int).Exp(c1, priv.X, priv.P)
|
s := new(big.Int).Exp(c1, priv.X, priv.P)
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/openpgp/packet/opaque.go
generated
vendored
3
vendor/golang.org/x/crypto/openpgp/packet/opaque.go
generated
vendored
|
|
@ -7,7 +7,6 @@ package packet
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
|
|
||||||
"golang.org/x/crypto/openpgp/errors"
|
"golang.org/x/crypto/openpgp/errors"
|
||||||
)
|
)
|
||||||
|
|
@ -26,7 +25,7 @@ type OpaquePacket struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (op *OpaquePacket) parse(r io.Reader) (err error) {
|
func (op *OpaquePacket) parse(r io.Reader) (err error) {
|
||||||
op.Contents, err = ioutil.ReadAll(r)
|
op.Contents, err = io.ReadAll(r)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/openpgp/packet/private_key.go
generated
vendored
3
vendor/golang.org/x/crypto/openpgp/packet/private_key.go
generated
vendored
|
|
@ -13,7 +13,6 @@ import (
|
||||||
"crypto/rsa"
|
"crypto/rsa"
|
||||||
"crypto/sha1"
|
"crypto/sha1"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
"math/big"
|
"math/big"
|
||||||
"strconv"
|
"strconv"
|
||||||
"time"
|
"time"
|
||||||
|
|
@ -133,7 +132,7 @@ func (pk *PrivateKey) parse(r io.Reader) (err error) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pk.encryptedData, err = ioutil.ReadAll(r)
|
pk.encryptedData, err = io.ReadAll(r)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/crypto/openpgp/packet/symmetrically_encrypted.go
generated
vendored
2
vendor/golang.org/x/crypto/openpgp/packet/symmetrically_encrypted.go
generated
vendored
|
|
@ -236,7 +236,7 @@ func (w *seMDCWriter) Close() (err error) {
|
||||||
return w.w.Close()
|
return w.w.Close()
|
||||||
}
|
}
|
||||||
|
|
||||||
// noOpCloser is like an ioutil.NopCloser, but for an io.Writer.
|
// noOpCloser is like an io.NopCloser, but for an io.Writer.
|
||||||
type noOpCloser struct {
|
type noOpCloser struct {
|
||||||
w io.Writer
|
w io.Writer
|
||||||
}
|
}
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/openpgp/packet/userattribute.go
generated
vendored
3
vendor/golang.org/x/crypto/openpgp/packet/userattribute.go
generated
vendored
|
|
@ -9,7 +9,6 @@ import (
|
||||||
"image"
|
"image"
|
||||||
"image/jpeg"
|
"image/jpeg"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const UserAttrImageSubpacket = 1
|
const UserAttrImageSubpacket = 1
|
||||||
|
|
@ -56,7 +55,7 @@ func NewUserAttribute(contents ...*OpaqueSubpacket) *UserAttribute {
|
||||||
|
|
||||||
func (uat *UserAttribute) parse(r io.Reader) (err error) {
|
func (uat *UserAttribute) parse(r io.Reader) (err error) {
|
||||||
// RFC 4880, section 5.13
|
// RFC 4880, section 5.13
|
||||||
b, err := ioutil.ReadAll(r)
|
b, err := io.ReadAll(r)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/openpgp/packet/userid.go
generated
vendored
3
vendor/golang.org/x/crypto/openpgp/packet/userid.go
generated
vendored
|
|
@ -6,7 +6,6 @@ package packet
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
"strings"
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -66,7 +65,7 @@ func NewUserId(name, comment, email string) *UserId {
|
||||||
|
|
||||||
func (uid *UserId) parse(r io.Reader) (err error) {
|
func (uid *UserId) parse(r io.Reader) (err error) {
|
||||||
// RFC 4880, section 5.11
|
// RFC 4880, section 5.11
|
||||||
b, err := ioutil.ReadAll(r)
|
b, err := io.ReadAll(r)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/crypto/openpgp/s2k/s2k.go
generated
vendored
2
vendor/golang.org/x/crypto/openpgp/s2k/s2k.go
generated
vendored
|
|
@ -268,7 +268,7 @@ func HashIdToString(id byte) (name string, ok bool) {
|
||||||
return "", false
|
return "", false
|
||||||
}
|
}
|
||||||
|
|
||||||
// HashIdToHash returns an OpenPGP hash id which corresponds the given Hash.
|
// HashToHashId returns an OpenPGP hash id which corresponds the given Hash.
|
||||||
func HashToHashId(h crypto.Hash) (id byte, ok bool) {
|
func HashToHashId(h crypto.Hash) (id byte, ok bool) {
|
||||||
for _, m := range hashToHashIdMapping {
|
for _, m := range hashToHashIdMapping {
|
||||||
if m.hash == h {
|
if m.hash == h {
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/crypto/openpgp/write.go
generated
vendored
2
vendor/golang.org/x/crypto/openpgp/write.go
generated
vendored
|
|
@ -402,7 +402,7 @@ func (s signatureWriter) Close() error {
|
||||||
return s.encryptedData.Close()
|
return s.encryptedData.Close()
|
||||||
}
|
}
|
||||||
|
|
||||||
// noOpCloser is like an ioutil.NopCloser, but for an io.Writer.
|
// noOpCloser is like an io.NopCloser, but for an io.Writer.
|
||||||
// TODO: we have two of these in OpenPGP packages alone. This probably needs
|
// TODO: we have two of these in OpenPGP packages alone. This probably needs
|
||||||
// to be promoted somewhere more common.
|
// to be promoted somewhere more common.
|
||||||
type noOpCloser struct {
|
type noOpCloser struct {
|
||||||
|
|
|
||||||
12
vendor/golang.org/x/crypto/sha3/doc.go
generated
vendored
12
vendor/golang.org/x/crypto/sha3/doc.go
generated
vendored
|
|
@ -8,8 +8,7 @@
|
||||||
// Both types of hash function use the "sponge" construction and the Keccak
|
// Both types of hash function use the "sponge" construction and the Keccak
|
||||||
// permutation. For a detailed specification see http://keccak.noekeon.org/
|
// permutation. For a detailed specification see http://keccak.noekeon.org/
|
||||||
//
|
//
|
||||||
//
|
// # Guidance
|
||||||
// Guidance
|
|
||||||
//
|
//
|
||||||
// If you aren't sure what function you need, use SHAKE256 with at least 64
|
// If you aren't sure what function you need, use SHAKE256 with at least 64
|
||||||
// bytes of output. The SHAKE instances are faster than the SHA3 instances;
|
// bytes of output. The SHAKE instances are faster than the SHA3 instances;
|
||||||
|
|
@ -19,8 +18,7 @@
|
||||||
// secret key to the input, hash with SHAKE256 and read at least 32 bytes of
|
// secret key to the input, hash with SHAKE256 and read at least 32 bytes of
|
||||||
// output.
|
// output.
|
||||||
//
|
//
|
||||||
//
|
// # Security strengths
|
||||||
// Security strengths
|
|
||||||
//
|
//
|
||||||
// The SHA3-x (x equals 224, 256, 384, or 512) functions have a security
|
// The SHA3-x (x equals 224, 256, 384, or 512) functions have a security
|
||||||
// strength against preimage attacks of x bits. Since they only produce "x"
|
// strength against preimage attacks of x bits. Since they only produce "x"
|
||||||
|
|
@ -31,8 +29,7 @@
|
||||||
// is used. Requesting more than 64 or 32 bytes of output, respectively, does
|
// is used. Requesting more than 64 or 32 bytes of output, respectively, does
|
||||||
// not increase the collision-resistance of the SHAKE functions.
|
// not increase the collision-resistance of the SHAKE functions.
|
||||||
//
|
//
|
||||||
//
|
// # The sponge construction
|
||||||
// The sponge construction
|
|
||||||
//
|
//
|
||||||
// A sponge builds a pseudo-random function from a public pseudo-random
|
// A sponge builds a pseudo-random function from a public pseudo-random
|
||||||
// permutation, by applying the permutation to a state of "rate + capacity"
|
// permutation, by applying the permutation to a state of "rate + capacity"
|
||||||
|
|
@ -50,8 +47,7 @@
|
||||||
// Since the KeccakF-1600 permutation is 1600 bits (200 bytes) wide, this means
|
// Since the KeccakF-1600 permutation is 1600 bits (200 bytes) wide, this means
|
||||||
// that the security strength of a sponge instance is equal to (1600 - bitrate) / 2.
|
// that the security strength of a sponge instance is equal to (1600 - bitrate) / 2.
|
||||||
//
|
//
|
||||||
//
|
// # Recommendations
|
||||||
// Recommendations
|
|
||||||
//
|
//
|
||||||
// The SHAKE functions are recommended for most new uses. They can produce
|
// The SHAKE functions are recommended for most new uses. They can produce
|
||||||
// output of arbitrary length. SHAKE256, with an output length of at least
|
// output of arbitrary length. SHAKE256, with an output length of at least
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/crypto/sha3/sha3.go
generated
vendored
2
vendor/golang.org/x/crypto/sha3/sha3.go
generated
vendored
|
|
@ -86,7 +86,7 @@ func (d *state) permute() {
|
||||||
d.buf = d.storage.asBytes()[:0]
|
d.buf = d.storage.asBytes()[:0]
|
||||||
keccakF1600(&d.a)
|
keccakF1600(&d.a)
|
||||||
case spongeSqueezing:
|
case spongeSqueezing:
|
||||||
// If we're squeezing, we need to apply the permutatin before
|
// If we're squeezing, we need to apply the permutation before
|
||||||
// copying more output.
|
// copying more output.
|
||||||
keccakF1600(&d.a)
|
keccakF1600(&d.a)
|
||||||
d.buf = d.storage.asBytes()[:d.rate]
|
d.buf = d.storage.asBytes()[:d.rate]
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/crypto/sha3/sha3_s390x.go
generated
vendored
2
vendor/golang.org/x/crypto/sha3/sha3_s390x.go
generated
vendored
|
|
@ -34,11 +34,13 @@ const (
|
||||||
|
|
||||||
// kimd is a wrapper for the 'compute intermediate message digest' instruction.
|
// kimd is a wrapper for the 'compute intermediate message digest' instruction.
|
||||||
// src must be a multiple of the rate for the given function code.
|
// src must be a multiple of the rate for the given function code.
|
||||||
|
//
|
||||||
//go:noescape
|
//go:noescape
|
||||||
func kimd(function code, chain *[200]byte, src []byte)
|
func kimd(function code, chain *[200]byte, src []byte)
|
||||||
|
|
||||||
// klmd is a wrapper for the 'compute last message digest' instruction.
|
// klmd is a wrapper for the 'compute last message digest' instruction.
|
||||||
// src padding is handled by the instruction.
|
// src padding is handled by the instruction.
|
||||||
|
//
|
||||||
//go:noescape
|
//go:noescape
|
||||||
func klmd(function code, chain *[200]byte, dst, src []byte)
|
func klmd(function code, chain *[200]byte, dst, src []byte)
|
||||||
|
|
||||||
|
|
|
||||||
56
vendor/golang.org/x/crypto/ssh/agent/client.go
generated
vendored
56
vendor/golang.org/x/crypto/ssh/agent/client.go
generated
vendored
|
|
@ -8,6 +8,7 @@
|
||||||
// ssh-agent process using the sample server.
|
// ssh-agent process using the sample server.
|
||||||
//
|
//
|
||||||
// References:
|
// References:
|
||||||
|
//
|
||||||
// [PROTOCOL.agent]: https://tools.ietf.org/html/draft-miller-ssh-agent-00
|
// [PROTOCOL.agent]: https://tools.ietf.org/html/draft-miller-ssh-agent-00
|
||||||
package agent // import "golang.org/x/crypto/ssh/agent"
|
package agent // import "golang.org/x/crypto/ssh/agent"
|
||||||
|
|
||||||
|
|
@ -25,7 +26,6 @@ import (
|
||||||
"math/big"
|
"math/big"
|
||||||
"sync"
|
"sync"
|
||||||
|
|
||||||
"crypto"
|
|
||||||
"golang.org/x/crypto/ed25519"
|
"golang.org/x/crypto/ed25519"
|
||||||
"golang.org/x/crypto/ssh"
|
"golang.org/x/crypto/ssh"
|
||||||
)
|
)
|
||||||
|
|
@ -93,7 +93,7 @@ type ExtendedAgent interface {
|
||||||
type ConstraintExtension struct {
|
type ConstraintExtension struct {
|
||||||
// ExtensionName consist of a UTF-8 string suffixed by the
|
// ExtensionName consist of a UTF-8 string suffixed by the
|
||||||
// implementation domain following the naming scheme defined
|
// implementation domain following the naming scheme defined
|
||||||
// in Section 4.2 of [RFC4251], e.g. "foo@example.com".
|
// in Section 4.2 of RFC 4251, e.g. "foo@example.com".
|
||||||
ExtensionName string
|
ExtensionName string
|
||||||
// ExtensionDetails contains the actual content of the extended
|
// ExtensionDetails contains the actual content of the extended
|
||||||
// constraint.
|
// constraint.
|
||||||
|
|
@ -226,7 +226,9 @@ var ErrExtensionUnsupported = errors.New("agent: extension unsupported")
|
||||||
|
|
||||||
type extensionAgentMsg struct {
|
type extensionAgentMsg struct {
|
||||||
ExtensionType string `sshtype:"27"`
|
ExtensionType string `sshtype:"27"`
|
||||||
Contents []byte
|
// NOTE: this matches OpenSSH's PROTOCOL.agent, not the IETF draft [PROTOCOL.agent],
|
||||||
|
// so that it matches what OpenSSH actually implements in the wild.
|
||||||
|
Contents []byte `ssh:"rest"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Key represents a protocol 2 public key as defined in
|
// Key represents a protocol 2 public key as defined in
|
||||||
|
|
@ -729,7 +731,7 @@ func (c *client) insertCert(s interface{}, cert *ssh.Certificate, comment string
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if bytes.Compare(cert.Key.Marshal(), signer.PublicKey().Marshal()) != 0 {
|
if !bytes.Equal(cert.Key.Marshal(), signer.PublicKey().Marshal()) {
|
||||||
return errors.New("agent: signer and cert have different public key")
|
return errors.New("agent: signer and cert have different public key")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -771,19 +773,53 @@ func (s *agentKeyringSigner) Sign(rand io.Reader, data []byte) (*ssh.Signature,
|
||||||
return s.agent.Sign(s.pub, data)
|
return s.agent.Sign(s.pub, data)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *agentKeyringSigner) SignWithOpts(rand io.Reader, data []byte, opts crypto.SignerOpts) (*ssh.Signature, error) {
|
func (s *agentKeyringSigner) SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*ssh.Signature, error) {
|
||||||
|
if algorithm == "" || algorithm == underlyingAlgo(s.pub.Type()) {
|
||||||
|
return s.Sign(rand, data)
|
||||||
|
}
|
||||||
|
|
||||||
var flags SignatureFlags
|
var flags SignatureFlags
|
||||||
if opts != nil {
|
switch algorithm {
|
||||||
switch opts.HashFunc() {
|
case ssh.KeyAlgoRSASHA256:
|
||||||
case crypto.SHA256:
|
|
||||||
flags = SignatureFlagRsaSha256
|
flags = SignatureFlagRsaSha256
|
||||||
case crypto.SHA512:
|
case ssh.KeyAlgoRSASHA512:
|
||||||
flags = SignatureFlagRsaSha512
|
flags = SignatureFlagRsaSha512
|
||||||
|
default:
|
||||||
|
return nil, fmt.Errorf("agent: unsupported algorithm %q", algorithm)
|
||||||
}
|
}
|
||||||
}
|
|
||||||
return s.agent.SignWithFlags(s.pub, data, flags)
|
return s.agent.SignWithFlags(s.pub, data, flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var _ ssh.AlgorithmSigner = &agentKeyringSigner{}
|
||||||
|
|
||||||
|
// certKeyAlgoNames is a mapping from known certificate algorithm names to the
|
||||||
|
// corresponding public key signature algorithm.
|
||||||
|
//
|
||||||
|
// This map must be kept in sync with the one in certs.go.
|
||||||
|
var certKeyAlgoNames = map[string]string{
|
||||||
|
ssh.CertAlgoRSAv01: ssh.KeyAlgoRSA,
|
||||||
|
ssh.CertAlgoRSASHA256v01: ssh.KeyAlgoRSASHA256,
|
||||||
|
ssh.CertAlgoRSASHA512v01: ssh.KeyAlgoRSASHA512,
|
||||||
|
ssh.CertAlgoDSAv01: ssh.KeyAlgoDSA,
|
||||||
|
ssh.CertAlgoECDSA256v01: ssh.KeyAlgoECDSA256,
|
||||||
|
ssh.CertAlgoECDSA384v01: ssh.KeyAlgoECDSA384,
|
||||||
|
ssh.CertAlgoECDSA521v01: ssh.KeyAlgoECDSA521,
|
||||||
|
ssh.CertAlgoSKECDSA256v01: ssh.KeyAlgoSKECDSA256,
|
||||||
|
ssh.CertAlgoED25519v01: ssh.KeyAlgoED25519,
|
||||||
|
ssh.CertAlgoSKED25519v01: ssh.KeyAlgoSKED25519,
|
||||||
|
}
|
||||||
|
|
||||||
|
// underlyingAlgo returns the signature algorithm associated with algo (which is
|
||||||
|
// an advertised or negotiated public key or host key algorithm). These are
|
||||||
|
// usually the same, except for certificate algorithms.
|
||||||
|
func underlyingAlgo(algo string) string {
|
||||||
|
if a, ok := certKeyAlgoNames[algo]; ok {
|
||||||
|
return a
|
||||||
|
}
|
||||||
|
return algo
|
||||||
|
}
|
||||||
|
|
||||||
// Calls an extension method. It is up to the agent implementation as to whether or not
|
// Calls an extension method. It is up to the agent implementation as to whether or not
|
||||||
// any particular extension is supported and may always return an error. Because the
|
// any particular extension is supported and may always return an error. Because the
|
||||||
// type of the response is up to the implementation, this returns the bytes of the
|
// type of the response is up to the implementation, this returns the bytes of the
|
||||||
|
|
|
||||||
6
vendor/golang.org/x/crypto/ssh/agent/keyring.go
generated
vendored
6
vendor/golang.org/x/crypto/ssh/agent/keyring.go
generated
vendored
|
|
@ -113,7 +113,7 @@ func (r *keyring) Unlock(passphrase []byte) error {
|
||||||
|
|
||||||
// expireKeysLocked removes expired keys from the keyring. If a key was added
|
// expireKeysLocked removes expired keys from the keyring. If a key was added
|
||||||
// with a lifetimesecs contraint and seconds >= lifetimesecs seconds have
|
// with a lifetimesecs contraint and seconds >= lifetimesecs seconds have
|
||||||
// ellapsed, it is removed. The caller *must* be holding the keyring mutex.
|
// elapsed, it is removed. The caller *must* be holding the keyring mutex.
|
||||||
func (r *keyring) expireKeysLocked() {
|
func (r *keyring) expireKeysLocked() {
|
||||||
for _, k := range r.keys {
|
for _, k := range r.keys {
|
||||||
if k.expire != nil && time.Now().After(*k.expire) {
|
if k.expire != nil && time.Now().After(*k.expire) {
|
||||||
|
|
@ -205,9 +205,9 @@ func (r *keyring) SignWithFlags(key ssh.PublicKey, data []byte, flags SignatureF
|
||||||
var algorithm string
|
var algorithm string
|
||||||
switch flags {
|
switch flags {
|
||||||
case SignatureFlagRsaSha256:
|
case SignatureFlagRsaSha256:
|
||||||
algorithm = ssh.SigAlgoRSASHA2256
|
algorithm = ssh.KeyAlgoRSASHA256
|
||||||
case SignatureFlagRsaSha512:
|
case SignatureFlagRsaSha512:
|
||||||
algorithm = ssh.SigAlgoRSASHA2512
|
algorithm = ssh.KeyAlgoRSASHA512
|
||||||
default:
|
default:
|
||||||
return nil, fmt.Errorf("agent: unsupported signature flags: %d", flags)
|
return nil, fmt.Errorf("agent: unsupported signature flags: %d", flags)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
97
vendor/golang.org/x/crypto/ssh/certs.go
generated
vendored
97
vendor/golang.org/x/crypto/ssh/certs.go
generated
vendored
|
|
@ -14,8 +14,10 @@ import (
|
||||||
"time"
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
// These constants from [PROTOCOL.certkeys] represent the key algorithm names
|
// Certificate algorithm names from [PROTOCOL.certkeys]. These values can appear
|
||||||
// for certificate types supported by this package.
|
// in Certificate.Type, PublicKey.Type, and ClientConfig.HostKeyAlgorithms.
|
||||||
|
// Unlike key algorithm names, these are not passed to AlgorithmSigner and don't
|
||||||
|
// appear in the Signature.Format field.
|
||||||
const (
|
const (
|
||||||
CertAlgoRSAv01 = "ssh-rsa-cert-v01@openssh.com"
|
CertAlgoRSAv01 = "ssh-rsa-cert-v01@openssh.com"
|
||||||
CertAlgoDSAv01 = "ssh-dss-cert-v01@openssh.com"
|
CertAlgoDSAv01 = "ssh-dss-cert-v01@openssh.com"
|
||||||
|
|
@ -25,14 +27,21 @@ const (
|
||||||
CertAlgoSKECDSA256v01 = "sk-ecdsa-sha2-nistp256-cert-v01@openssh.com"
|
CertAlgoSKECDSA256v01 = "sk-ecdsa-sha2-nistp256-cert-v01@openssh.com"
|
||||||
CertAlgoED25519v01 = "ssh-ed25519-cert-v01@openssh.com"
|
CertAlgoED25519v01 = "ssh-ed25519-cert-v01@openssh.com"
|
||||||
CertAlgoSKED25519v01 = "sk-ssh-ed25519-cert-v01@openssh.com"
|
CertAlgoSKED25519v01 = "sk-ssh-ed25519-cert-v01@openssh.com"
|
||||||
|
|
||||||
|
// CertAlgoRSASHA256v01 and CertAlgoRSASHA512v01 can't appear as a
|
||||||
|
// Certificate.Type (or PublicKey.Type), but only in
|
||||||
|
// ClientConfig.HostKeyAlgorithms.
|
||||||
|
CertAlgoRSASHA256v01 = "rsa-sha2-256-cert-v01@openssh.com"
|
||||||
|
CertAlgoRSASHA512v01 = "rsa-sha2-512-cert-v01@openssh.com"
|
||||||
)
|
)
|
||||||
|
|
||||||
// These constants from [PROTOCOL.certkeys] represent additional signature
|
|
||||||
// algorithm names for certificate types supported by this package.
|
|
||||||
const (
|
const (
|
||||||
CertSigAlgoRSAv01 = "ssh-rsa-cert-v01@openssh.com"
|
// Deprecated: use CertAlgoRSAv01.
|
||||||
CertSigAlgoRSASHA2256v01 = "rsa-sha2-256-cert-v01@openssh.com"
|
CertSigAlgoRSAv01 = CertAlgoRSAv01
|
||||||
CertSigAlgoRSASHA2512v01 = "rsa-sha2-512-cert-v01@openssh.com"
|
// Deprecated: use CertAlgoRSASHA256v01.
|
||||||
|
CertSigAlgoRSASHA2256v01 = CertAlgoRSASHA256v01
|
||||||
|
// Deprecated: use CertAlgoRSASHA512v01.
|
||||||
|
CertSigAlgoRSASHA2512v01 = CertAlgoRSASHA512v01
|
||||||
)
|
)
|
||||||
|
|
||||||
// Certificate types distinguish between host and user
|
// Certificate types distinguish between host and user
|
||||||
|
|
@ -242,7 +251,7 @@ type algorithmOpenSSHCertSigner struct {
|
||||||
// private key is held by signer. It returns an error if the public key in cert
|
// private key is held by signer. It returns an error if the public key in cert
|
||||||
// doesn't match the key used by signer.
|
// doesn't match the key used by signer.
|
||||||
func NewCertSigner(cert *Certificate, signer Signer) (Signer, error) {
|
func NewCertSigner(cert *Certificate, signer Signer) (Signer, error) {
|
||||||
if bytes.Compare(cert.Key.Marshal(), signer.PublicKey().Marshal()) != 0 {
|
if !bytes.Equal(cert.Key.Marshal(), signer.PublicKey().Marshal()) {
|
||||||
return nil, errors.New("ssh: signer and cert have different public key")
|
return nil, errors.New("ssh: signer and cert have different public key")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -431,10 +440,14 @@ func (c *Certificate) SignCert(rand io.Reader, authority Signer) error {
|
||||||
}
|
}
|
||||||
c.SignatureKey = authority.PublicKey()
|
c.SignatureKey = authority.PublicKey()
|
||||||
|
|
||||||
if v, ok := authority.(AlgorithmSigner); ok {
|
// Default to KeyAlgoRSASHA512 for ssh-rsa signers.
|
||||||
if v.PublicKey().Type() == KeyAlgoRSA {
|
if v, ok := authority.(AlgorithmSigner); ok && v.PublicKey().Type() == KeyAlgoRSA {
|
||||||
authority = &rsaSigner{v, SigAlgoRSASHA2512}
|
sig, err := v.SignWithAlgorithm(rand, c.bytesForSigning(), KeyAlgoRSASHA512)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
}
|
}
|
||||||
|
c.Signature = sig
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
sig, err := authority.Sign(rand, c.bytesForSigning())
|
sig, err := authority.Sign(rand, c.bytesForSigning())
|
||||||
|
|
@ -445,32 +458,42 @@ func (c *Certificate) SignCert(rand io.Reader, authority Signer) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// certAlgoNames includes a mapping from signature algorithms to the
|
// certKeyAlgoNames is a mapping from known certificate algorithm names to the
|
||||||
// corresponding certificate signature algorithm. When a key type (such
|
// corresponding public key signature algorithm.
|
||||||
// as ED25516) is associated with only one algorithm, the KeyAlgo
|
//
|
||||||
// constant is used instead of the SigAlgo.
|
// This map must be kept in sync with the one in agent/client.go.
|
||||||
var certAlgoNames = map[string]string{
|
var certKeyAlgoNames = map[string]string{
|
||||||
SigAlgoRSA: CertSigAlgoRSAv01,
|
CertAlgoRSAv01: KeyAlgoRSA,
|
||||||
SigAlgoRSASHA2256: CertSigAlgoRSASHA2256v01,
|
CertAlgoRSASHA256v01: KeyAlgoRSASHA256,
|
||||||
SigAlgoRSASHA2512: CertSigAlgoRSASHA2512v01,
|
CertAlgoRSASHA512v01: KeyAlgoRSASHA512,
|
||||||
KeyAlgoDSA: CertAlgoDSAv01,
|
CertAlgoDSAv01: KeyAlgoDSA,
|
||||||
KeyAlgoECDSA256: CertAlgoECDSA256v01,
|
CertAlgoECDSA256v01: KeyAlgoECDSA256,
|
||||||
KeyAlgoECDSA384: CertAlgoECDSA384v01,
|
CertAlgoECDSA384v01: KeyAlgoECDSA384,
|
||||||
KeyAlgoECDSA521: CertAlgoECDSA521v01,
|
CertAlgoECDSA521v01: KeyAlgoECDSA521,
|
||||||
KeyAlgoSKECDSA256: CertAlgoSKECDSA256v01,
|
CertAlgoSKECDSA256v01: KeyAlgoSKECDSA256,
|
||||||
KeyAlgoED25519: CertAlgoED25519v01,
|
CertAlgoED25519v01: KeyAlgoED25519,
|
||||||
KeyAlgoSKED25519: CertAlgoSKED25519v01,
|
CertAlgoSKED25519v01: KeyAlgoSKED25519,
|
||||||
}
|
}
|
||||||
|
|
||||||
// certToPrivAlgo returns the underlying algorithm for a certificate algorithm.
|
// underlyingAlgo returns the signature algorithm associated with algo (which is
|
||||||
// Panics if a non-certificate algorithm is passed.
|
// an advertised or negotiated public key or host key algorithm). These are
|
||||||
func certToPrivAlgo(algo string) string {
|
// usually the same, except for certificate algorithms.
|
||||||
for privAlgo, pubAlgo := range certAlgoNames {
|
func underlyingAlgo(algo string) string {
|
||||||
if pubAlgo == algo {
|
if a, ok := certKeyAlgoNames[algo]; ok {
|
||||||
return privAlgo
|
return a
|
||||||
|
}
|
||||||
|
return algo
|
||||||
|
}
|
||||||
|
|
||||||
|
// certificateAlgo returns the certificate algorithms that uses the provided
|
||||||
|
// underlying signature algorithm.
|
||||||
|
func certificateAlgo(algo string) (certAlgo string, ok bool) {
|
||||||
|
for certName, algoName := range certKeyAlgoNames {
|
||||||
|
if algoName == algo {
|
||||||
|
return certName, true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
panic("unknown cert algorithm")
|
return "", false
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cert *Certificate) bytesForSigning() []byte {
|
func (cert *Certificate) bytesForSigning() []byte {
|
||||||
|
|
@ -514,13 +537,13 @@ func (c *Certificate) Marshal() []byte {
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
// Type returns the key name. It is part of the PublicKey interface.
|
// Type returns the certificate algorithm name. It is part of the PublicKey interface.
|
||||||
func (c *Certificate) Type() string {
|
func (c *Certificate) Type() string {
|
||||||
algo, ok := certAlgoNames[c.Key.Type()]
|
certName, ok := certificateAlgo(c.Key.Type())
|
||||||
if !ok {
|
if !ok {
|
||||||
panic("unknown cert key type " + c.Key.Type())
|
panic("unknown certificate type for key type " + c.Key.Type())
|
||||||
}
|
}
|
||||||
return algo
|
return certName
|
||||||
}
|
}
|
||||||
|
|
||||||
// Verify verifies a signature against the certificate's public
|
// Verify verifies a signature against the certificate's public
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/crypto/ssh/cipher.go
generated
vendored
3
vendor/golang.org/x/crypto/ssh/cipher.go
generated
vendored
|
|
@ -15,7 +15,6 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"hash"
|
"hash"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
|
|
||||||
"golang.org/x/crypto/chacha20"
|
"golang.org/x/crypto/chacha20"
|
||||||
"golang.org/x/crypto/internal/poly1305"
|
"golang.org/x/crypto/internal/poly1305"
|
||||||
|
|
@ -497,7 +496,7 @@ func (c *cbcCipher) readCipherPacket(seqNum uint32, r io.Reader) ([]byte, error)
|
||||||
// data, to make distinguishing between
|
// data, to make distinguishing between
|
||||||
// failing MAC and failing length check more
|
// failing MAC and failing length check more
|
||||||
// difficult.
|
// difficult.
|
||||||
io.CopyN(ioutil.Discard, r, int64(c.oracleCamouflage))
|
io.CopyN(io.Discard, r, int64(c.oracleCamouflage))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return p, err
|
return p, err
|
||||||
|
|
|
||||||
25
vendor/golang.org/x/crypto/ssh/client.go
generated
vendored
25
vendor/golang.org/x/crypto/ssh/client.go
generated
vendored
|
|
@ -113,25 +113,16 @@ func (c *connection) clientHandshake(dialAddress string, config *ClientConfig) e
|
||||||
return c.clientAuthenticate(config)
|
return c.clientAuthenticate(config)
|
||||||
}
|
}
|
||||||
|
|
||||||
// verifyHostKeySignature verifies the host key obtained in the key
|
// verifyHostKeySignature verifies the host key obtained in the key exchange.
|
||||||
// exchange.
|
// algo is the negotiated algorithm, and may be a certificate type.
|
||||||
func verifyHostKeySignature(hostKey PublicKey, algo string, result *kexResult) error {
|
func verifyHostKeySignature(hostKey PublicKey, algo string, result *kexResult) error {
|
||||||
sig, rest, ok := parseSignatureBody(result.Signature)
|
sig, rest, ok := parseSignatureBody(result.Signature)
|
||||||
if len(rest) > 0 || !ok {
|
if len(rest) > 0 || !ok {
|
||||||
return errors.New("ssh: signature parse error")
|
return errors.New("ssh: signature parse error")
|
||||||
}
|
}
|
||||||
|
|
||||||
// For keys, underlyingAlgo is exactly algo. For certificates,
|
if a := underlyingAlgo(algo); sig.Format != a {
|
||||||
// we have to look up the underlying key algorithm that SSH
|
return fmt.Errorf("ssh: invalid signature algorithm %q, expected %q", sig.Format, a)
|
||||||
// uses to evaluate signatures.
|
|
||||||
underlyingAlgo := algo
|
|
||||||
for sigAlgo, certAlgo := range certAlgoNames {
|
|
||||||
if certAlgo == algo {
|
|
||||||
underlyingAlgo = sigAlgo
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if sig.Format != underlyingAlgo {
|
|
||||||
return fmt.Errorf("ssh: invalid signature algorithm %q, expected %q", sig.Format, underlyingAlgo)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return hostKey.Verify(result.H, sig)
|
return hostKey.Verify(result.H, sig)
|
||||||
|
|
@ -237,11 +228,11 @@ type ClientConfig struct {
|
||||||
// be used for the connection. If empty, a reasonable default is used.
|
// be used for the connection. If empty, a reasonable default is used.
|
||||||
ClientVersion string
|
ClientVersion string
|
||||||
|
|
||||||
// HostKeyAlgorithms lists the key types that the client will
|
// HostKeyAlgorithms lists the public key algorithms that the client will
|
||||||
// accept from the server as host key, in order of
|
// accept from the server for host key authentication, in order of
|
||||||
// preference. If empty, a reasonable default is used. Any
|
// preference. If empty, a reasonable default is used. Any
|
||||||
// string returned from PublicKey.Type method may be used, or
|
// string returned from a PublicKey.Type method may be used, or
|
||||||
// any of the CertAlgoXxxx and KeyAlgoXxxx constants.
|
// any of the CertAlgo and KeyAlgo constants.
|
||||||
HostKeyAlgorithms []string
|
HostKeyAlgorithms []string
|
||||||
|
|
||||||
// Timeout is the maximum amount of time for the TCP connection to establish.
|
// Timeout is the maximum amount of time for the TCP connection to establish.
|
||||||
|
|
|
||||||
132
vendor/golang.org/x/crypto/ssh/client_auth.go
generated
vendored
132
vendor/golang.org/x/crypto/ssh/client_auth.go
generated
vendored
|
|
@ -9,6 +9,7 @@ import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
|
"strings"
|
||||||
)
|
)
|
||||||
|
|
||||||
type authResult int
|
type authResult int
|
||||||
|
|
@ -29,6 +30,33 @@ func (c *connection) clientAuthenticate(config *ClientConfig) error {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
// The server may choose to send a SSH_MSG_EXT_INFO at this point (if we
|
||||||
|
// advertised willingness to receive one, which we always do) or not. See
|
||||||
|
// RFC 8308, Section 2.4.
|
||||||
|
extensions := make(map[string][]byte)
|
||||||
|
if len(packet) > 0 && packet[0] == msgExtInfo {
|
||||||
|
var extInfo extInfoMsg
|
||||||
|
if err := Unmarshal(packet, &extInfo); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
payload := extInfo.Payload
|
||||||
|
for i := uint32(0); i < extInfo.NumExtensions; i++ {
|
||||||
|
name, rest, ok := parseString(payload)
|
||||||
|
if !ok {
|
||||||
|
return parseError(msgExtInfo)
|
||||||
|
}
|
||||||
|
value, rest, ok := parseString(rest)
|
||||||
|
if !ok {
|
||||||
|
return parseError(msgExtInfo)
|
||||||
|
}
|
||||||
|
extensions[string(name)] = value
|
||||||
|
payload = rest
|
||||||
|
}
|
||||||
|
packet, err = c.transport.readPacket()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
var serviceAccept serviceAcceptMsg
|
var serviceAccept serviceAcceptMsg
|
||||||
if err := Unmarshal(packet, &serviceAccept); err != nil {
|
if err := Unmarshal(packet, &serviceAccept); err != nil {
|
||||||
return err
|
return err
|
||||||
|
|
@ -41,7 +69,7 @@ func (c *connection) clientAuthenticate(config *ClientConfig) error {
|
||||||
|
|
||||||
sessionID := c.transport.getSessionID()
|
sessionID := c.transport.getSessionID()
|
||||||
for auth := AuthMethod(new(noneAuth)); auth != nil; {
|
for auth := AuthMethod(new(noneAuth)); auth != nil; {
|
||||||
ok, methods, err := auth.auth(sessionID, config.User, c.transport, config.Rand)
|
ok, methods, err := auth.auth(sessionID, config.User, c.transport, config.Rand, extensions)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
@ -93,7 +121,7 @@ type AuthMethod interface {
|
||||||
// If authentication is not successful, a []string of alternative
|
// If authentication is not successful, a []string of alternative
|
||||||
// method names is returned. If the slice is nil, it will be ignored
|
// method names is returned. If the slice is nil, it will be ignored
|
||||||
// and the previous set of possible methods will be reused.
|
// and the previous set of possible methods will be reused.
|
||||||
auth(session []byte, user string, p packetConn, rand io.Reader) (authResult, []string, error)
|
auth(session []byte, user string, p packetConn, rand io.Reader, extensions map[string][]byte) (authResult, []string, error)
|
||||||
|
|
||||||
// method returns the RFC 4252 method name.
|
// method returns the RFC 4252 method name.
|
||||||
method() string
|
method() string
|
||||||
|
|
@ -102,7 +130,7 @@ type AuthMethod interface {
|
||||||
// "none" authentication, RFC 4252 section 5.2.
|
// "none" authentication, RFC 4252 section 5.2.
|
||||||
type noneAuth int
|
type noneAuth int
|
||||||
|
|
||||||
func (n *noneAuth) auth(session []byte, user string, c packetConn, rand io.Reader) (authResult, []string, error) {
|
func (n *noneAuth) auth(session []byte, user string, c packetConn, rand io.Reader, _ map[string][]byte) (authResult, []string, error) {
|
||||||
if err := c.writePacket(Marshal(&userAuthRequestMsg{
|
if err := c.writePacket(Marshal(&userAuthRequestMsg{
|
||||||
User: user,
|
User: user,
|
||||||
Service: serviceSSH,
|
Service: serviceSSH,
|
||||||
|
|
@ -122,7 +150,7 @@ func (n *noneAuth) method() string {
|
||||||
// a function call, e.g. by prompting the user.
|
// a function call, e.g. by prompting the user.
|
||||||
type passwordCallback func() (password string, err error)
|
type passwordCallback func() (password string, err error)
|
||||||
|
|
||||||
func (cb passwordCallback) auth(session []byte, user string, c packetConn, rand io.Reader) (authResult, []string, error) {
|
func (cb passwordCallback) auth(session []byte, user string, c packetConn, rand io.Reader, _ map[string][]byte) (authResult, []string, error) {
|
||||||
type passwordAuthMsg struct {
|
type passwordAuthMsg struct {
|
||||||
User string `sshtype:"50"`
|
User string `sshtype:"50"`
|
||||||
Service string
|
Service string
|
||||||
|
|
@ -189,7 +217,46 @@ func (cb publicKeyCallback) method() string {
|
||||||
return "publickey"
|
return "publickey"
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cb publicKeyCallback) auth(session []byte, user string, c packetConn, rand io.Reader) (authResult, []string, error) {
|
func pickSignatureAlgorithm(signer Signer, extensions map[string][]byte) (as AlgorithmSigner, algo string) {
|
||||||
|
keyFormat := signer.PublicKey().Type()
|
||||||
|
|
||||||
|
// Like in sendKexInit, if the public key implements AlgorithmSigner we
|
||||||
|
// assume it supports all algorithms, otherwise only the key format one.
|
||||||
|
as, ok := signer.(AlgorithmSigner)
|
||||||
|
if !ok {
|
||||||
|
return algorithmSignerWrapper{signer}, keyFormat
|
||||||
|
}
|
||||||
|
|
||||||
|
extPayload, ok := extensions["server-sig-algs"]
|
||||||
|
if !ok {
|
||||||
|
// If there is no "server-sig-algs" extension, fall back to the key
|
||||||
|
// format algorithm.
|
||||||
|
return as, keyFormat
|
||||||
|
}
|
||||||
|
|
||||||
|
// The server-sig-algs extension only carries underlying signature
|
||||||
|
// algorithm, but we are trying to select a protocol-level public key
|
||||||
|
// algorithm, which might be a certificate type. Extend the list of server
|
||||||
|
// supported algorithms to include the corresponding certificate algorithms.
|
||||||
|
serverAlgos := strings.Split(string(extPayload), ",")
|
||||||
|
for _, algo := range serverAlgos {
|
||||||
|
if certAlgo, ok := certificateAlgo(algo); ok {
|
||||||
|
serverAlgos = append(serverAlgos, certAlgo)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
keyAlgos := algorithmsForKeyFormat(keyFormat)
|
||||||
|
algo, err := findCommon("public key signature algorithm", keyAlgos, serverAlgos)
|
||||||
|
if err != nil {
|
||||||
|
// If there is no overlap, try the key anyway with the key format
|
||||||
|
// algorithm, to support servers that fail to list all supported
|
||||||
|
// algorithms.
|
||||||
|
return as, keyFormat
|
||||||
|
}
|
||||||
|
return as, algo
|
||||||
|
}
|
||||||
|
|
||||||
|
func (cb publicKeyCallback) auth(session []byte, user string, c packetConn, rand io.Reader, extensions map[string][]byte) (authResult, []string, error) {
|
||||||
// Authentication is performed by sending an enquiry to test if a key is
|
// Authentication is performed by sending an enquiry to test if a key is
|
||||||
// acceptable to the remote. If the key is acceptable, the client will
|
// acceptable to the remote. If the key is acceptable, the client will
|
||||||
// attempt to authenticate with the valid key. If not the client will repeat
|
// attempt to authenticate with the valid key. If not the client will repeat
|
||||||
|
|
@ -201,7 +268,10 @@ func (cb publicKeyCallback) auth(session []byte, user string, c packetConn, rand
|
||||||
}
|
}
|
||||||
var methods []string
|
var methods []string
|
||||||
for _, signer := range signers {
|
for _, signer := range signers {
|
||||||
ok, err := validateKey(signer.PublicKey(), user, c)
|
pub := signer.PublicKey()
|
||||||
|
as, algo := pickSignatureAlgorithm(signer, extensions)
|
||||||
|
|
||||||
|
ok, err := validateKey(pub, algo, user, c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return authFailure, nil, err
|
return authFailure, nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -209,13 +279,13 @@ func (cb publicKeyCallback) auth(session []byte, user string, c packetConn, rand
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
pub := signer.PublicKey()
|
|
||||||
pubKey := pub.Marshal()
|
pubKey := pub.Marshal()
|
||||||
sign, err := signer.Sign(rand, buildDataSignedForAuth(session, userAuthRequestMsg{
|
data := buildDataSignedForAuth(session, userAuthRequestMsg{
|
||||||
User: user,
|
User: user,
|
||||||
Service: serviceSSH,
|
Service: serviceSSH,
|
||||||
Method: cb.method(),
|
Method: cb.method(),
|
||||||
}, []byte(pub.Type()), pubKey))
|
}, algo, pubKey)
|
||||||
|
sign, err := as.SignWithAlgorithm(rand, data, underlyingAlgo(algo))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return authFailure, nil, err
|
return authFailure, nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -229,7 +299,7 @@ func (cb publicKeyCallback) auth(session []byte, user string, c packetConn, rand
|
||||||
Service: serviceSSH,
|
Service: serviceSSH,
|
||||||
Method: cb.method(),
|
Method: cb.method(),
|
||||||
HasSig: true,
|
HasSig: true,
|
||||||
Algoname: pub.Type(),
|
Algoname: algo,
|
||||||
PubKey: pubKey,
|
PubKey: pubKey,
|
||||||
Sig: sig,
|
Sig: sig,
|
||||||
}
|
}
|
||||||
|
|
@ -266,26 +336,25 @@ func containsMethod(methods []string, method string) bool {
|
||||||
}
|
}
|
||||||
|
|
||||||
// validateKey validates the key provided is acceptable to the server.
|
// validateKey validates the key provided is acceptable to the server.
|
||||||
func validateKey(key PublicKey, user string, c packetConn) (bool, error) {
|
func validateKey(key PublicKey, algo string, user string, c packetConn) (bool, error) {
|
||||||
pubKey := key.Marshal()
|
pubKey := key.Marshal()
|
||||||
msg := publickeyAuthMsg{
|
msg := publickeyAuthMsg{
|
||||||
User: user,
|
User: user,
|
||||||
Service: serviceSSH,
|
Service: serviceSSH,
|
||||||
Method: "publickey",
|
Method: "publickey",
|
||||||
HasSig: false,
|
HasSig: false,
|
||||||
Algoname: key.Type(),
|
Algoname: algo,
|
||||||
PubKey: pubKey,
|
PubKey: pubKey,
|
||||||
}
|
}
|
||||||
if err := c.writePacket(Marshal(&msg)); err != nil {
|
if err := c.writePacket(Marshal(&msg)); err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
return confirmKeyAck(key, c)
|
return confirmKeyAck(key, algo, c)
|
||||||
}
|
}
|
||||||
|
|
||||||
func confirmKeyAck(key PublicKey, c packetConn) (bool, error) {
|
func confirmKeyAck(key PublicKey, algo string, c packetConn) (bool, error) {
|
||||||
pubKey := key.Marshal()
|
pubKey := key.Marshal()
|
||||||
algoname := key.Type()
|
|
||||||
|
|
||||||
for {
|
for {
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
|
|
@ -302,14 +371,14 @@ func confirmKeyAck(key PublicKey, c packetConn) (bool, error) {
|
||||||
if err := Unmarshal(packet, &msg); err != nil {
|
if err := Unmarshal(packet, &msg); err != nil {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
if msg.Algo != algoname || !bytes.Equal(msg.PubKey, pubKey) {
|
if msg.Algo != algo || !bytes.Equal(msg.PubKey, pubKey) {
|
||||||
return false, nil
|
return false, nil
|
||||||
}
|
}
|
||||||
return true, nil
|
return true, nil
|
||||||
case msgUserAuthFailure:
|
case msgUserAuthFailure:
|
||||||
return false, nil
|
return false, nil
|
||||||
default:
|
default:
|
||||||
return false, unexpectedMessageError(msgUserAuthSuccess, packet[0])
|
return false, unexpectedMessageError(msgUserAuthPubKeyOk, packet[0])
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -330,6 +399,7 @@ func PublicKeysCallback(getSigners func() (signers []Signer, err error)) AuthMet
|
||||||
// along with a list of remaining authentication methods to try next and
|
// along with a list of remaining authentication methods to try next and
|
||||||
// an error if an unexpected response was received.
|
// an error if an unexpected response was received.
|
||||||
func handleAuthResponse(c packetConn) (authResult, []string, error) {
|
func handleAuthResponse(c packetConn) (authResult, []string, error) {
|
||||||
|
gotMsgExtInfo := false
|
||||||
for {
|
for {
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -341,6 +411,12 @@ func handleAuthResponse(c packetConn) (authResult, []string, error) {
|
||||||
if err := handleBannerResponse(c, packet); err != nil {
|
if err := handleBannerResponse(c, packet); err != nil {
|
||||||
return authFailure, nil, err
|
return authFailure, nil, err
|
||||||
}
|
}
|
||||||
|
case msgExtInfo:
|
||||||
|
// Ignore post-authentication RFC 8308 extensions, once.
|
||||||
|
if gotMsgExtInfo {
|
||||||
|
return authFailure, nil, unexpectedMessageError(msgUserAuthSuccess, packet[0])
|
||||||
|
}
|
||||||
|
gotMsgExtInfo = true
|
||||||
case msgUserAuthFailure:
|
case msgUserAuthFailure:
|
||||||
var msg userAuthFailureMsg
|
var msg userAuthFailureMsg
|
||||||
if err := Unmarshal(packet, &msg); err != nil {
|
if err := Unmarshal(packet, &msg); err != nil {
|
||||||
|
|
@ -380,10 +456,10 @@ func handleBannerResponse(c packetConn, packet []byte) error {
|
||||||
// disabling echoing (e.g. for passwords), and return all the answers.
|
// disabling echoing (e.g. for passwords), and return all the answers.
|
||||||
// Challenge may be called multiple times in a single session. After
|
// Challenge may be called multiple times in a single session. After
|
||||||
// successful authentication, the server may send a challenge with no
|
// successful authentication, the server may send a challenge with no
|
||||||
// questions, for which the user and instruction messages should be
|
// questions, for which the name and instruction messages should be
|
||||||
// printed. RFC 4256 section 3.3 details how the UI should behave for
|
// printed. RFC 4256 section 3.3 details how the UI should behave for
|
||||||
// both CLI and GUI environments.
|
// both CLI and GUI environments.
|
||||||
type KeyboardInteractiveChallenge func(user, instruction string, questions []string, echos []bool) (answers []string, err error)
|
type KeyboardInteractiveChallenge func(name, instruction string, questions []string, echos []bool) (answers []string, err error)
|
||||||
|
|
||||||
// KeyboardInteractive returns an AuthMethod using a prompt/response
|
// KeyboardInteractive returns an AuthMethod using a prompt/response
|
||||||
// sequence controlled by the server.
|
// sequence controlled by the server.
|
||||||
|
|
@ -395,7 +471,7 @@ func (cb KeyboardInteractiveChallenge) method() string {
|
||||||
return "keyboard-interactive"
|
return "keyboard-interactive"
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cb KeyboardInteractiveChallenge) auth(session []byte, user string, c packetConn, rand io.Reader) (authResult, []string, error) {
|
func (cb KeyboardInteractiveChallenge) auth(session []byte, user string, c packetConn, rand io.Reader, _ map[string][]byte) (authResult, []string, error) {
|
||||||
type initiateMsg struct {
|
type initiateMsg struct {
|
||||||
User string `sshtype:"50"`
|
User string `sshtype:"50"`
|
||||||
Service string
|
Service string
|
||||||
|
|
@ -412,6 +488,7 @@ func (cb KeyboardInteractiveChallenge) auth(session []byte, user string, c packe
|
||||||
return authFailure, nil, err
|
return authFailure, nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
gotMsgExtInfo := false
|
||||||
for {
|
for {
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -425,6 +502,13 @@ func (cb KeyboardInteractiveChallenge) auth(session []byte, user string, c packe
|
||||||
return authFailure, nil, err
|
return authFailure, nil, err
|
||||||
}
|
}
|
||||||
continue
|
continue
|
||||||
|
case msgExtInfo:
|
||||||
|
// Ignore post-authentication RFC 8308 extensions, once.
|
||||||
|
if gotMsgExtInfo {
|
||||||
|
return authFailure, nil, unexpectedMessageError(msgUserAuthInfoRequest, packet[0])
|
||||||
|
}
|
||||||
|
gotMsgExtInfo = true
|
||||||
|
continue
|
||||||
case msgUserAuthInfoRequest:
|
case msgUserAuthInfoRequest:
|
||||||
// OK
|
// OK
|
||||||
case msgUserAuthFailure:
|
case msgUserAuthFailure:
|
||||||
|
|
@ -465,7 +549,7 @@ func (cb KeyboardInteractiveChallenge) auth(session []byte, user string, c packe
|
||||||
return authFailure, nil, errors.New("ssh: extra data following keyboard-interactive pairs")
|
return authFailure, nil, errors.New("ssh: extra data following keyboard-interactive pairs")
|
||||||
}
|
}
|
||||||
|
|
||||||
answers, err := cb(msg.User, msg.Instruction, prompts, echos)
|
answers, err := cb(msg.Name, msg.Instruction, prompts, echos)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return authFailure, nil, err
|
return authFailure, nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -497,9 +581,9 @@ type retryableAuthMethod struct {
|
||||||
maxTries int
|
maxTries int
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *retryableAuthMethod) auth(session []byte, user string, c packetConn, rand io.Reader) (ok authResult, methods []string, err error) {
|
func (r *retryableAuthMethod) auth(session []byte, user string, c packetConn, rand io.Reader, extensions map[string][]byte) (ok authResult, methods []string, err error) {
|
||||||
for i := 0; r.maxTries <= 0 || i < r.maxTries; i++ {
|
for i := 0; r.maxTries <= 0 || i < r.maxTries; i++ {
|
||||||
ok, methods, err = r.authMethod.auth(session, user, c, rand)
|
ok, methods, err = r.authMethod.auth(session, user, c, rand, extensions)
|
||||||
if ok != authFailure || err != nil { // either success, partial success or error terminate
|
if ok != authFailure || err != nil { // either success, partial success or error terminate
|
||||||
return ok, methods, err
|
return ok, methods, err
|
||||||
}
|
}
|
||||||
|
|
@ -542,7 +626,7 @@ type gssAPIWithMICCallback struct {
|
||||||
target string
|
target string
|
||||||
}
|
}
|
||||||
|
|
||||||
func (g *gssAPIWithMICCallback) auth(session []byte, user string, c packetConn, rand io.Reader) (authResult, []string, error) {
|
func (g *gssAPIWithMICCallback) auth(session []byte, user string, c packetConn, rand io.Reader, _ map[string][]byte) (authResult, []string, error) {
|
||||||
m := &userAuthRequestMsg{
|
m := &userAuthRequestMsg{
|
||||||
User: user,
|
User: user,
|
||||||
Service: serviceSSH,
|
Service: serviceSSH,
|
||||||
|
|
|
||||||
66
vendor/golang.org/x/crypto/ssh/common.go
generated
vendored
66
vendor/golang.org/x/crypto/ssh/common.go
generated
vendored
|
|
@ -44,11 +44,11 @@ var preferredCiphers = []string{
|
||||||
// supportedKexAlgos specifies the supported key-exchange algorithms in
|
// supportedKexAlgos specifies the supported key-exchange algorithms in
|
||||||
// preference order.
|
// preference order.
|
||||||
var supportedKexAlgos = []string{
|
var supportedKexAlgos = []string{
|
||||||
kexAlgoCurve25519SHA256,
|
kexAlgoCurve25519SHA256, kexAlgoCurve25519SHA256LibSSH,
|
||||||
// P384 and P521 are not constant-time yet, but since we don't
|
// P384 and P521 are not constant-time yet, but since we don't
|
||||||
// reuse ephemeral keys, using them for ECDH should be OK.
|
// reuse ephemeral keys, using them for ECDH should be OK.
|
||||||
kexAlgoECDH256, kexAlgoECDH384, kexAlgoECDH521,
|
kexAlgoECDH256, kexAlgoECDH384, kexAlgoECDH521,
|
||||||
kexAlgoDH14SHA1, kexAlgoDH1SHA1,
|
kexAlgoDH14SHA256, kexAlgoDH14SHA1, kexAlgoDH1SHA1,
|
||||||
}
|
}
|
||||||
|
|
||||||
// serverForbiddenKexAlgos contains key exchange algorithms, that are forbidden
|
// serverForbiddenKexAlgos contains key exchange algorithms, that are forbidden
|
||||||
|
|
@ -61,21 +61,21 @@ var serverForbiddenKexAlgos = map[string]struct{}{
|
||||||
// preferredKexAlgos specifies the default preference for key-exchange algorithms
|
// preferredKexAlgos specifies the default preference for key-exchange algorithms
|
||||||
// in preference order.
|
// in preference order.
|
||||||
var preferredKexAlgos = []string{
|
var preferredKexAlgos = []string{
|
||||||
kexAlgoCurve25519SHA256,
|
kexAlgoCurve25519SHA256, kexAlgoCurve25519SHA256LibSSH,
|
||||||
kexAlgoECDH256, kexAlgoECDH384, kexAlgoECDH521,
|
kexAlgoECDH256, kexAlgoECDH384, kexAlgoECDH521,
|
||||||
kexAlgoDH14SHA1,
|
kexAlgoDH14SHA256, kexAlgoDH14SHA1,
|
||||||
}
|
}
|
||||||
|
|
||||||
// supportedHostKeyAlgos specifies the supported host-key algorithms (i.e. methods
|
// supportedHostKeyAlgos specifies the supported host-key algorithms (i.e. methods
|
||||||
// of authenticating servers) in preference order.
|
// of authenticating servers) in preference order.
|
||||||
var supportedHostKeyAlgos = []string{
|
var supportedHostKeyAlgos = []string{
|
||||||
CertSigAlgoRSASHA2512v01, CertSigAlgoRSASHA2256v01,
|
CertAlgoRSASHA512v01, CertAlgoRSASHA256v01,
|
||||||
CertSigAlgoRSAv01, CertAlgoDSAv01, CertAlgoECDSA256v01,
|
CertAlgoRSAv01, CertAlgoDSAv01, CertAlgoECDSA256v01,
|
||||||
CertAlgoECDSA384v01, CertAlgoECDSA521v01, CertAlgoED25519v01,
|
CertAlgoECDSA384v01, CertAlgoECDSA521v01, CertAlgoED25519v01,
|
||||||
|
|
||||||
KeyAlgoECDSA256, KeyAlgoECDSA384, KeyAlgoECDSA521,
|
KeyAlgoECDSA256, KeyAlgoECDSA384, KeyAlgoECDSA521,
|
||||||
SigAlgoRSASHA2512, SigAlgoRSASHA2256,
|
KeyAlgoRSASHA512, KeyAlgoRSASHA256,
|
||||||
SigAlgoRSA, KeyAlgoDSA,
|
KeyAlgoRSA, KeyAlgoDSA,
|
||||||
|
|
||||||
KeyAlgoED25519,
|
KeyAlgoED25519,
|
||||||
}
|
}
|
||||||
|
|
@ -89,23 +89,33 @@ var supportedMACs = []string{
|
||||||
|
|
||||||
var supportedCompressions = []string{compressionNone}
|
var supportedCompressions = []string{compressionNone}
|
||||||
|
|
||||||
// hashFuncs keeps the mapping of supported algorithms to their respective
|
// hashFuncs keeps the mapping of supported signature algorithms to their
|
||||||
// hashes needed for signature verification.
|
// respective hashes needed for signing and verification.
|
||||||
var hashFuncs = map[string]crypto.Hash{
|
var hashFuncs = map[string]crypto.Hash{
|
||||||
SigAlgoRSA: crypto.SHA1,
|
KeyAlgoRSA: crypto.SHA1,
|
||||||
SigAlgoRSASHA2256: crypto.SHA256,
|
KeyAlgoRSASHA256: crypto.SHA256,
|
||||||
SigAlgoRSASHA2512: crypto.SHA512,
|
KeyAlgoRSASHA512: crypto.SHA512,
|
||||||
KeyAlgoDSA: crypto.SHA1,
|
KeyAlgoDSA: crypto.SHA1,
|
||||||
KeyAlgoECDSA256: crypto.SHA256,
|
KeyAlgoECDSA256: crypto.SHA256,
|
||||||
KeyAlgoECDSA384: crypto.SHA384,
|
KeyAlgoECDSA384: crypto.SHA384,
|
||||||
KeyAlgoECDSA521: crypto.SHA512,
|
KeyAlgoECDSA521: crypto.SHA512,
|
||||||
CertSigAlgoRSAv01: crypto.SHA1,
|
// KeyAlgoED25519 doesn't pre-hash.
|
||||||
CertSigAlgoRSASHA2256v01: crypto.SHA256,
|
KeyAlgoSKECDSA256: crypto.SHA256,
|
||||||
CertSigAlgoRSASHA2512v01: crypto.SHA512,
|
KeyAlgoSKED25519: crypto.SHA256,
|
||||||
CertAlgoDSAv01: crypto.SHA1,
|
}
|
||||||
CertAlgoECDSA256v01: crypto.SHA256,
|
|
||||||
CertAlgoECDSA384v01: crypto.SHA384,
|
// algorithmsForKeyFormat returns the supported signature algorithms for a given
|
||||||
CertAlgoECDSA521v01: crypto.SHA512,
|
// public key format (PublicKey.Type), in order of preference. See RFC 8332,
|
||||||
|
// Section 2. See also the note in sendKexInit on backwards compatibility.
|
||||||
|
func algorithmsForKeyFormat(keyFormat string) []string {
|
||||||
|
switch keyFormat {
|
||||||
|
case KeyAlgoRSA:
|
||||||
|
return []string{KeyAlgoRSASHA256, KeyAlgoRSASHA512, KeyAlgoRSA}
|
||||||
|
case CertAlgoRSAv01:
|
||||||
|
return []string{CertAlgoRSASHA256v01, CertAlgoRSASHA512v01, CertAlgoRSAv01}
|
||||||
|
default:
|
||||||
|
return []string{keyFormat}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// unexpectedMessageError results when the SSH message that we received didn't
|
// unexpectedMessageError results when the SSH message that we received didn't
|
||||||
|
|
@ -152,6 +162,11 @@ func (a *directionAlgorithms) rekeyBytes() int64 {
|
||||||
return 1 << 30
|
return 1 << 30
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var aeadCiphers = map[string]bool{
|
||||||
|
gcmCipherID: true,
|
||||||
|
chacha20Poly1305ID: true,
|
||||||
|
}
|
||||||
|
|
||||||
type algorithms struct {
|
type algorithms struct {
|
||||||
kex string
|
kex string
|
||||||
hostKey string
|
hostKey string
|
||||||
|
|
@ -187,15 +202,19 @@ func findAgreedAlgorithms(isClient bool, clientKexInit, serverKexInit *kexInitMs
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if !aeadCiphers[ctos.Cipher] {
|
||||||
ctos.MAC, err = findCommon("client to server MAC", clientKexInit.MACsClientServer, serverKexInit.MACsClientServer)
|
ctos.MAC, err = findCommon("client to server MAC", clientKexInit.MACsClientServer, serverKexInit.MACsClientServer)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if !aeadCiphers[stoc.Cipher] {
|
||||||
stoc.MAC, err = findCommon("server to client MAC", clientKexInit.MACsServerClient, serverKexInit.MACsServerClient)
|
stoc.MAC, err = findCommon("server to client MAC", clientKexInit.MACsServerClient, serverKexInit.MACsServerClient)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ctos.Compression, err = findCommon("client to server compression", clientKexInit.CompressionClientServer, serverKexInit.CompressionClientServer)
|
ctos.Compression, err = findCommon("client to server compression", clientKexInit.CompressionClientServer, serverKexInit.CompressionClientServer)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -278,8 +297,9 @@ func (c *Config) SetDefaults() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// buildDataSignedForAuth returns the data that is signed in order to prove
|
// buildDataSignedForAuth returns the data that is signed in order to prove
|
||||||
// possession of a private key. See RFC 4252, section 7.
|
// possession of a private key. See RFC 4252, section 7. algo is the advertised
|
||||||
func buildDataSignedForAuth(sessionID []byte, req userAuthRequestMsg, algo, pubKey []byte) []byte {
|
// algorithm, and may be a certificate type.
|
||||||
|
func buildDataSignedForAuth(sessionID []byte, req userAuthRequestMsg, algo string, pubKey []byte) []byte {
|
||||||
data := struct {
|
data := struct {
|
||||||
Session []byte
|
Session []byte
|
||||||
Type byte
|
Type byte
|
||||||
|
|
@ -287,7 +307,7 @@ func buildDataSignedForAuth(sessionID []byte, req userAuthRequestMsg, algo, pubK
|
||||||
Service string
|
Service string
|
||||||
Method string
|
Method string
|
||||||
Sign bool
|
Sign bool
|
||||||
Algo []byte
|
Algo string
|
||||||
PubKey []byte
|
PubKey []byte
|
||||||
}{
|
}{
|
||||||
sessionID,
|
sessionID,
|
||||||
|
|
|
||||||
1
vendor/golang.org/x/crypto/ssh/doc.go
generated
vendored
1
vendor/golang.org/x/crypto/ssh/doc.go
generated
vendored
|
|
@ -12,6 +12,7 @@ the multiplexed nature of SSH is exposed to users that wish to support
|
||||||
others.
|
others.
|
||||||
|
|
||||||
References:
|
References:
|
||||||
|
|
||||||
[PROTOCOL.certkeys]: http://cvsweb.openbsd.org/cgi-bin/cvsweb/src/usr.bin/ssh/PROTOCOL.certkeys?rev=HEAD
|
[PROTOCOL.certkeys]: http://cvsweb.openbsd.org/cgi-bin/cvsweb/src/usr.bin/ssh/PROTOCOL.certkeys?rev=HEAD
|
||||||
[SSH-PARAMETERS]: http://www.iana.org/assignments/ssh-parameters/ssh-parameters.xml#ssh-parameters-1
|
[SSH-PARAMETERS]: http://www.iana.org/assignments/ssh-parameters/ssh-parameters.xml#ssh-parameters-1
|
||||||
|
|
||||||
|
|
|
||||||
104
vendor/golang.org/x/crypto/ssh/handshake.go
generated
vendored
104
vendor/golang.org/x/crypto/ssh/handshake.go
generated
vendored
|
|
@ -455,21 +455,38 @@ func (t *handshakeTransport) sendKexInit() error {
|
||||||
}
|
}
|
||||||
io.ReadFull(rand.Reader, msg.Cookie[:])
|
io.ReadFull(rand.Reader, msg.Cookie[:])
|
||||||
|
|
||||||
if len(t.hostKeys) > 0 {
|
isServer := len(t.hostKeys) > 0
|
||||||
|
if isServer {
|
||||||
for _, k := range t.hostKeys {
|
for _, k := range t.hostKeys {
|
||||||
algo := k.PublicKey().Type()
|
// If k is an AlgorithmSigner, presume it supports all signature algorithms
|
||||||
switch algo {
|
// associated with the key format. (Ideally AlgorithmSigner would have a
|
||||||
case KeyAlgoRSA:
|
// method to advertise supported algorithms, but it doesn't. This means that
|
||||||
msg.ServerHostKeyAlgos = append(msg.ServerHostKeyAlgos, []string{SigAlgoRSASHA2512, SigAlgoRSASHA2256, SigAlgoRSA}...)
|
// adding support for a new algorithm is a breaking change, as we will
|
||||||
case CertAlgoRSAv01:
|
// immediately negotiate it even if existing implementations don't support
|
||||||
msg.ServerHostKeyAlgos = append(msg.ServerHostKeyAlgos, []string{CertSigAlgoRSASHA2512v01, CertSigAlgoRSASHA2256v01, CertSigAlgoRSAv01}...)
|
// it. If that ever happens, we'll have to figure something out.)
|
||||||
default:
|
// If k is not an AlgorithmSigner, we can only assume it only supports the
|
||||||
msg.ServerHostKeyAlgos = append(msg.ServerHostKeyAlgos, algo)
|
// algorithms that matches the key format. (This means that Sign can't pick
|
||||||
|
// a different default.)
|
||||||
|
keyFormat := k.PublicKey().Type()
|
||||||
|
if _, ok := k.(AlgorithmSigner); ok {
|
||||||
|
msg.ServerHostKeyAlgos = append(msg.ServerHostKeyAlgos, algorithmsForKeyFormat(keyFormat)...)
|
||||||
|
} else {
|
||||||
|
msg.ServerHostKeyAlgos = append(msg.ServerHostKeyAlgos, keyFormat)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
msg.ServerHostKeyAlgos = t.hostKeyAlgorithms
|
msg.ServerHostKeyAlgos = t.hostKeyAlgorithms
|
||||||
|
|
||||||
|
// As a client we opt in to receiving SSH_MSG_EXT_INFO so we know what
|
||||||
|
// algorithms the server supports for public key authentication. See RFC
|
||||||
|
// 8308, Section 2.1.
|
||||||
|
if firstKeyExchange := t.sessionID == nil; firstKeyExchange {
|
||||||
|
msg.KexAlgos = make([]string, 0, len(t.config.KeyExchanges)+1)
|
||||||
|
msg.KexAlgos = append(msg.KexAlgos, t.config.KeyExchanges...)
|
||||||
|
msg.KexAlgos = append(msg.KexAlgos, "ext-info-c")
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
packet := Marshal(msg)
|
packet := Marshal(msg)
|
||||||
|
|
||||||
// writePacket destroys the contents, so save a copy.
|
// writePacket destroys the contents, so save a copy.
|
||||||
|
|
@ -589,9 +606,9 @@ func (t *handshakeTransport) enterKeyExchange(otherInitPacket []byte) error {
|
||||||
|
|
||||||
var result *kexResult
|
var result *kexResult
|
||||||
if len(t.hostKeys) > 0 {
|
if len(t.hostKeys) > 0 {
|
||||||
result, err = t.server(kex, t.algorithms, &magics)
|
result, err = t.server(kex, &magics)
|
||||||
} else {
|
} else {
|
||||||
result, err = t.client(kex, t.algorithms, &magics)
|
result, err = t.client(kex, &magics)
|
||||||
}
|
}
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -618,33 +635,52 @@ func (t *handshakeTransport) enterKeyExchange(otherInitPacket []byte) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *handshakeTransport) server(kex kexAlgorithm, algs *algorithms, magics *handshakeMagics) (*kexResult, error) {
|
// algorithmSignerWrapper is an AlgorithmSigner that only supports the default
|
||||||
var hostKey Signer
|
// key format algorithm.
|
||||||
for _, k := range t.hostKeys {
|
//
|
||||||
kt := k.PublicKey().Type()
|
// This is technically a violation of the AlgorithmSigner interface, but it
|
||||||
if kt == algs.hostKey {
|
// should be unreachable given where we use this. Anyway, at least it returns an
|
||||||
hostKey = k
|
// error instead of panicing or producing an incorrect signature.
|
||||||
} else if signer, ok := k.(AlgorithmSigner); ok {
|
type algorithmSignerWrapper struct {
|
||||||
// Some signature algorithms don't show up as key types
|
Signer
|
||||||
// so we have to manually check for a compatible host key.
|
|
||||||
switch kt {
|
|
||||||
case KeyAlgoRSA:
|
|
||||||
if algs.hostKey == SigAlgoRSASHA2256 || algs.hostKey == SigAlgoRSASHA2512 {
|
|
||||||
hostKey = &rsaSigner{signer, algs.hostKey}
|
|
||||||
}
|
|
||||||
case CertAlgoRSAv01:
|
|
||||||
if algs.hostKey == CertSigAlgoRSASHA2256v01 || algs.hostKey == CertSigAlgoRSASHA2512v01 {
|
|
||||||
hostKey = &rsaSigner{signer, certToPrivAlgo(algs.hostKey)}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
r, err := kex.Server(t.conn, t.config.Rand, magics, hostKey)
|
func (a algorithmSignerWrapper) SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error) {
|
||||||
|
if algorithm != underlyingAlgo(a.PublicKey().Type()) {
|
||||||
|
return nil, errors.New("ssh: internal error: algorithmSignerWrapper invoked with non-default algorithm")
|
||||||
|
}
|
||||||
|
return a.Sign(rand, data)
|
||||||
|
}
|
||||||
|
|
||||||
|
func pickHostKey(hostKeys []Signer, algo string) AlgorithmSigner {
|
||||||
|
for _, k := range hostKeys {
|
||||||
|
if algo == k.PublicKey().Type() {
|
||||||
|
return algorithmSignerWrapper{k}
|
||||||
|
}
|
||||||
|
k, ok := k.(AlgorithmSigner)
|
||||||
|
if !ok {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
for _, a := range algorithmsForKeyFormat(k.PublicKey().Type()) {
|
||||||
|
if algo == a {
|
||||||
|
return k
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (t *handshakeTransport) server(kex kexAlgorithm, magics *handshakeMagics) (*kexResult, error) {
|
||||||
|
hostKey := pickHostKey(t.hostKeys, t.algorithms.hostKey)
|
||||||
|
if hostKey == nil {
|
||||||
|
return nil, errors.New("ssh: internal error: negotiated unsupported signature type")
|
||||||
|
}
|
||||||
|
|
||||||
|
r, err := kex.Server(t.conn, t.config.Rand, magics, hostKey, t.algorithms.hostKey)
|
||||||
return r, err
|
return r, err
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *handshakeTransport) client(kex kexAlgorithm, algs *algorithms, magics *handshakeMagics) (*kexResult, error) {
|
func (t *handshakeTransport) client(kex kexAlgorithm, magics *handshakeMagics) (*kexResult, error) {
|
||||||
result, err := kex.Client(t.conn, t.config.Rand, magics)
|
result, err := kex.Client(t.conn, t.config.Rand, magics)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
@ -655,7 +691,7 @@ func (t *handshakeTransport) client(kex kexAlgorithm, algs *algorithms, magics *
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := verifyHostKeySignature(hostKey, algs.hostKey, result); err != nil {
|
if err := verifyHostKeySignature(hostKey, t.algorithms.hostKey, result); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
170
vendor/golang.org/x/crypto/ssh/kex.go
generated
vendored
170
vendor/golang.org/x/crypto/ssh/kex.go
generated
vendored
|
|
@ -22,10 +22,12 @@ import (
|
||||||
const (
|
const (
|
||||||
kexAlgoDH1SHA1 = "diffie-hellman-group1-sha1"
|
kexAlgoDH1SHA1 = "diffie-hellman-group1-sha1"
|
||||||
kexAlgoDH14SHA1 = "diffie-hellman-group14-sha1"
|
kexAlgoDH14SHA1 = "diffie-hellman-group14-sha1"
|
||||||
|
kexAlgoDH14SHA256 = "diffie-hellman-group14-sha256"
|
||||||
kexAlgoECDH256 = "ecdh-sha2-nistp256"
|
kexAlgoECDH256 = "ecdh-sha2-nistp256"
|
||||||
kexAlgoECDH384 = "ecdh-sha2-nistp384"
|
kexAlgoECDH384 = "ecdh-sha2-nistp384"
|
||||||
kexAlgoECDH521 = "ecdh-sha2-nistp521"
|
kexAlgoECDH521 = "ecdh-sha2-nistp521"
|
||||||
kexAlgoCurve25519SHA256 = "curve25519-sha256@libssh.org"
|
kexAlgoCurve25519SHA256LibSSH = "curve25519-sha256@libssh.org"
|
||||||
|
kexAlgoCurve25519SHA256 = "curve25519-sha256"
|
||||||
|
|
||||||
// For the following kex only the client half contains a production
|
// For the following kex only the client half contains a production
|
||||||
// ready implementation. The server half only consists of a minimal
|
// ready implementation. The server half only consists of a minimal
|
||||||
|
|
@ -75,8 +77,9 @@ func (m *handshakeMagics) write(w io.Writer) {
|
||||||
// kexAlgorithm abstracts different key exchange algorithms.
|
// kexAlgorithm abstracts different key exchange algorithms.
|
||||||
type kexAlgorithm interface {
|
type kexAlgorithm interface {
|
||||||
// Server runs server-side key agreement, signing the result
|
// Server runs server-side key agreement, signing the result
|
||||||
// with a hostkey.
|
// with a hostkey. algo is the negotiated algorithm, and may
|
||||||
Server(p packetConn, rand io.Reader, magics *handshakeMagics, s Signer) (*kexResult, error)
|
// be a certificate type.
|
||||||
|
Server(p packetConn, rand io.Reader, magics *handshakeMagics, s AlgorithmSigner, algo string) (*kexResult, error)
|
||||||
|
|
||||||
// Client runs the client-side key agreement. Caller is
|
// Client runs the client-side key agreement. Caller is
|
||||||
// responsible for verifying the host key signature.
|
// responsible for verifying the host key signature.
|
||||||
|
|
@ -86,6 +89,7 @@ type kexAlgorithm interface {
|
||||||
// dhGroup is a multiplicative group suitable for implementing Diffie-Hellman key agreement.
|
// dhGroup is a multiplicative group suitable for implementing Diffie-Hellman key agreement.
|
||||||
type dhGroup struct {
|
type dhGroup struct {
|
||||||
g, p, pMinus1 *big.Int
|
g, p, pMinus1 *big.Int
|
||||||
|
hashFunc crypto.Hash
|
||||||
}
|
}
|
||||||
|
|
||||||
func (group *dhGroup) diffieHellman(theirPublic, myPrivate *big.Int) (*big.Int, error) {
|
func (group *dhGroup) diffieHellman(theirPublic, myPrivate *big.Int) (*big.Int, error) {
|
||||||
|
|
@ -96,8 +100,6 @@ func (group *dhGroup) diffieHellman(theirPublic, myPrivate *big.Int) (*big.Int,
|
||||||
}
|
}
|
||||||
|
|
||||||
func (group *dhGroup) Client(c packetConn, randSource io.Reader, magics *handshakeMagics) (*kexResult, error) {
|
func (group *dhGroup) Client(c packetConn, randSource io.Reader, magics *handshakeMagics) (*kexResult, error) {
|
||||||
hashFunc := crypto.SHA1
|
|
||||||
|
|
||||||
var x *big.Int
|
var x *big.Int
|
||||||
for {
|
for {
|
||||||
var err error
|
var err error
|
||||||
|
|
@ -132,7 +134,7 @@ func (group *dhGroup) Client(c packetConn, randSource io.Reader, magics *handsha
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
h := hashFunc.New()
|
h := group.hashFunc.New()
|
||||||
magics.write(h)
|
magics.write(h)
|
||||||
writeString(h, kexDHReply.HostKey)
|
writeString(h, kexDHReply.HostKey)
|
||||||
writeInt(h, X)
|
writeInt(h, X)
|
||||||
|
|
@ -146,12 +148,11 @@ func (group *dhGroup) Client(c packetConn, randSource io.Reader, magics *handsha
|
||||||
K: K,
|
K: K,
|
||||||
HostKey: kexDHReply.HostKey,
|
HostKey: kexDHReply.HostKey,
|
||||||
Signature: kexDHReply.Signature,
|
Signature: kexDHReply.Signature,
|
||||||
Hash: crypto.SHA1,
|
Hash: group.hashFunc,
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (group *dhGroup) Server(c packetConn, randSource io.Reader, magics *handshakeMagics, priv Signer) (result *kexResult, err error) {
|
func (group *dhGroup) Server(c packetConn, randSource io.Reader, magics *handshakeMagics, priv AlgorithmSigner, algo string) (result *kexResult, err error) {
|
||||||
hashFunc := crypto.SHA1
|
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
|
|
@ -179,7 +180,7 @@ func (group *dhGroup) Server(c packetConn, randSource io.Reader, magics *handsha
|
||||||
|
|
||||||
hostKeyBytes := priv.PublicKey().Marshal()
|
hostKeyBytes := priv.PublicKey().Marshal()
|
||||||
|
|
||||||
h := hashFunc.New()
|
h := group.hashFunc.New()
|
||||||
magics.write(h)
|
magics.write(h)
|
||||||
writeString(h, hostKeyBytes)
|
writeString(h, hostKeyBytes)
|
||||||
writeInt(h, kexDHInit.X)
|
writeInt(h, kexDHInit.X)
|
||||||
|
|
@ -193,7 +194,7 @@ func (group *dhGroup) Server(c packetConn, randSource io.Reader, magics *handsha
|
||||||
|
|
||||||
// H is already a hash, but the hostkey signing will apply its
|
// H is already a hash, but the hostkey signing will apply its
|
||||||
// own key-specific hash algorithm.
|
// own key-specific hash algorithm.
|
||||||
sig, err := signAndMarshal(priv, randSource, H)
|
sig, err := signAndMarshal(priv, randSource, H, algo)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -211,7 +212,7 @@ func (group *dhGroup) Server(c packetConn, randSource io.Reader, magics *handsha
|
||||||
K: K,
|
K: K,
|
||||||
HostKey: hostKeyBytes,
|
HostKey: hostKeyBytes,
|
||||||
Signature: sig,
|
Signature: sig,
|
||||||
Hash: crypto.SHA1,
|
Hash: group.hashFunc,
|
||||||
}, err
|
}, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -314,7 +315,7 @@ func validateECPublicKey(curve elliptic.Curve, x, y *big.Int) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
func (kex *ecdh) Server(c packetConn, rand io.Reader, magics *handshakeMagics, priv Signer) (result *kexResult, err error) {
|
func (kex *ecdh) Server(c packetConn, rand io.Reader, magics *handshakeMagics, priv AlgorithmSigner, algo string) (result *kexResult, err error) {
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
@ -359,7 +360,7 @@ func (kex *ecdh) Server(c packetConn, rand io.Reader, magics *handshakeMagics, p
|
||||||
|
|
||||||
// H is already a hash, but the hostkey signing will apply its
|
// H is already a hash, but the hostkey signing will apply its
|
||||||
// own key-specific hash algorithm.
|
// own key-specific hash algorithm.
|
||||||
sig, err := signAndMarshal(priv, rand, H)
|
sig, err := signAndMarshal(priv, rand, H, algo)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -384,39 +385,62 @@ func (kex *ecdh) Server(c packetConn, rand io.Reader, magics *handshakeMagics, p
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ecHash returns the hash to match the given elliptic curve, see RFC
|
||||||
|
// 5656, section 6.2.1
|
||||||
|
func ecHash(curve elliptic.Curve) crypto.Hash {
|
||||||
|
bitSize := curve.Params().BitSize
|
||||||
|
switch {
|
||||||
|
case bitSize <= 256:
|
||||||
|
return crypto.SHA256
|
||||||
|
case bitSize <= 384:
|
||||||
|
return crypto.SHA384
|
||||||
|
}
|
||||||
|
return crypto.SHA512
|
||||||
|
}
|
||||||
|
|
||||||
var kexAlgoMap = map[string]kexAlgorithm{}
|
var kexAlgoMap = map[string]kexAlgorithm{}
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
// This is the group called diffie-hellman-group1-sha1 in RFC
|
// This is the group called diffie-hellman-group1-sha1 in
|
||||||
// 4253 and Oakley Group 2 in RFC 2409.
|
// RFC 4253 and Oakley Group 2 in RFC 2409.
|
||||||
p, _ := new(big.Int).SetString("FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE65381FFFFFFFFFFFFFFFF", 16)
|
p, _ := new(big.Int).SetString("FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE65381FFFFFFFFFFFFFFFF", 16)
|
||||||
kexAlgoMap[kexAlgoDH1SHA1] = &dhGroup{
|
kexAlgoMap[kexAlgoDH1SHA1] = &dhGroup{
|
||||||
g: new(big.Int).SetInt64(2),
|
g: new(big.Int).SetInt64(2),
|
||||||
p: p,
|
p: p,
|
||||||
pMinus1: new(big.Int).Sub(p, bigOne),
|
pMinus1: new(big.Int).Sub(p, bigOne),
|
||||||
|
hashFunc: crypto.SHA1,
|
||||||
}
|
}
|
||||||
|
|
||||||
// This is the group called diffie-hellman-group14-sha1 in RFC
|
// This are the groups called diffie-hellman-group14-sha1 and
|
||||||
// 4253 and Oakley Group 14 in RFC 3526.
|
// diffie-hellman-group14-sha256 in RFC 4253 and RFC 8268,
|
||||||
|
// and Oakley Group 14 in RFC 3526.
|
||||||
p, _ = new(big.Int).SetString("FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3BE39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF6955817183995497CEA956AE515D2261898FA051015728E5A8AACAA68FFFFFFFFFFFFFFFF", 16)
|
p, _ = new(big.Int).SetString("FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3BE39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF6955817183995497CEA956AE515D2261898FA051015728E5A8AACAA68FFFFFFFFFFFFFFFF", 16)
|
||||||
|
group14 := &dhGroup{
|
||||||
kexAlgoMap[kexAlgoDH14SHA1] = &dhGroup{
|
|
||||||
g: new(big.Int).SetInt64(2),
|
g: new(big.Int).SetInt64(2),
|
||||||
p: p,
|
p: p,
|
||||||
pMinus1: new(big.Int).Sub(p, bigOne),
|
pMinus1: new(big.Int).Sub(p, bigOne),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
kexAlgoMap[kexAlgoDH14SHA1] = &dhGroup{
|
||||||
|
g: group14.g, p: group14.p, pMinus1: group14.pMinus1,
|
||||||
|
hashFunc: crypto.SHA1,
|
||||||
|
}
|
||||||
|
kexAlgoMap[kexAlgoDH14SHA256] = &dhGroup{
|
||||||
|
g: group14.g, p: group14.p, pMinus1: group14.pMinus1,
|
||||||
|
hashFunc: crypto.SHA256,
|
||||||
|
}
|
||||||
|
|
||||||
kexAlgoMap[kexAlgoECDH521] = &ecdh{elliptic.P521()}
|
kexAlgoMap[kexAlgoECDH521] = &ecdh{elliptic.P521()}
|
||||||
kexAlgoMap[kexAlgoECDH384] = &ecdh{elliptic.P384()}
|
kexAlgoMap[kexAlgoECDH384] = &ecdh{elliptic.P384()}
|
||||||
kexAlgoMap[kexAlgoECDH256] = &ecdh{elliptic.P256()}
|
kexAlgoMap[kexAlgoECDH256] = &ecdh{elliptic.P256()}
|
||||||
kexAlgoMap[kexAlgoCurve25519SHA256] = &curve25519sha256{}
|
kexAlgoMap[kexAlgoCurve25519SHA256] = &curve25519sha256{}
|
||||||
|
kexAlgoMap[kexAlgoCurve25519SHA256LibSSH] = &curve25519sha256{}
|
||||||
kexAlgoMap[kexAlgoDHGEXSHA1] = &dhGEXSHA{hashFunc: crypto.SHA1}
|
kexAlgoMap[kexAlgoDHGEXSHA1] = &dhGEXSHA{hashFunc: crypto.SHA1}
|
||||||
kexAlgoMap[kexAlgoDHGEXSHA256] = &dhGEXSHA{hashFunc: crypto.SHA256}
|
kexAlgoMap[kexAlgoDHGEXSHA256] = &dhGEXSHA{hashFunc: crypto.SHA256}
|
||||||
}
|
}
|
||||||
|
|
||||||
// curve25519sha256 implements the curve25519-sha256@libssh.org key
|
// curve25519sha256 implements the curve25519-sha256 (formerly known as
|
||||||
// agreement protocol, as described in
|
// curve25519-sha256@libssh.org) key exchange method, as described in RFC 8731.
|
||||||
// https://git.libssh.org/projects/libssh.git/tree/doc/curve25519-sha256@libssh.org.txt
|
|
||||||
type curve25519sha256 struct{}
|
type curve25519sha256 struct{}
|
||||||
|
|
||||||
type curve25519KeyPair struct {
|
type curve25519KeyPair struct {
|
||||||
|
|
@ -486,7 +510,7 @@ func (kex *curve25519sha256) Client(c packetConn, rand io.Reader, magics *handsh
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (kex *curve25519sha256) Server(c packetConn, rand io.Reader, magics *handshakeMagics, priv Signer) (result *kexResult, err error) {
|
func (kex *curve25519sha256) Server(c packetConn, rand io.Reader, magics *handshakeMagics, priv AlgorithmSigner, algo string) (result *kexResult, err error) {
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
|
|
@ -527,7 +551,7 @@ func (kex *curve25519sha256) Server(c packetConn, rand io.Reader, magics *handsh
|
||||||
|
|
||||||
H := h.Sum(nil)
|
H := h.Sum(nil)
|
||||||
|
|
||||||
sig, err := signAndMarshal(priv, rand, H)
|
sig, err := signAndMarshal(priv, rand, H, algo)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -553,7 +577,6 @@ func (kex *curve25519sha256) Server(c packetConn, rand io.Reader, magics *handsh
|
||||||
// diffie-hellman-group-exchange-sha256 key agreement protocols,
|
// diffie-hellman-group-exchange-sha256 key agreement protocols,
|
||||||
// as described in RFC 4419
|
// as described in RFC 4419
|
||||||
type dhGEXSHA struct {
|
type dhGEXSHA struct {
|
||||||
g, p *big.Int
|
|
||||||
hashFunc crypto.Hash
|
hashFunc crypto.Hash
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -563,14 +586,7 @@ const (
|
||||||
dhGroupExchangeMaximumBits = 8192
|
dhGroupExchangeMaximumBits = 8192
|
||||||
)
|
)
|
||||||
|
|
||||||
func (gex *dhGEXSHA) diffieHellman(theirPublic, myPrivate *big.Int) (*big.Int, error) {
|
func (gex *dhGEXSHA) Client(c packetConn, randSource io.Reader, magics *handshakeMagics) (*kexResult, error) {
|
||||||
if theirPublic.Sign() <= 0 || theirPublic.Cmp(gex.p) >= 0 {
|
|
||||||
return nil, fmt.Errorf("ssh: DH parameter out of bounds")
|
|
||||||
}
|
|
||||||
return new(big.Int).Exp(theirPublic, myPrivate, gex.p), nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (gex dhGEXSHA) Client(c packetConn, randSource io.Reader, magics *handshakeMagics) (*kexResult, error) {
|
|
||||||
// Send GexRequest
|
// Send GexRequest
|
||||||
kexDHGexRequest := kexDHGexRequestMsg{
|
kexDHGexRequest := kexDHGexRequestMsg{
|
||||||
MinBits: dhGroupExchangeMinimumBits,
|
MinBits: dhGroupExchangeMinimumBits,
|
||||||
|
|
@ -587,35 +603,29 @@ func (gex dhGEXSHA) Client(c packetConn, randSource io.Reader, magics *handshake
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
var kexDHGexGroup kexDHGexGroupMsg
|
var msg kexDHGexGroupMsg
|
||||||
if err = Unmarshal(packet, &kexDHGexGroup); err != nil {
|
if err = Unmarshal(packet, &msg); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
// reject if p's bit length < dhGroupExchangeMinimumBits or > dhGroupExchangeMaximumBits
|
// reject if p's bit length < dhGroupExchangeMinimumBits or > dhGroupExchangeMaximumBits
|
||||||
if kexDHGexGroup.P.BitLen() < dhGroupExchangeMinimumBits || kexDHGexGroup.P.BitLen() > dhGroupExchangeMaximumBits {
|
if msg.P.BitLen() < dhGroupExchangeMinimumBits || msg.P.BitLen() > dhGroupExchangeMaximumBits {
|
||||||
return nil, fmt.Errorf("ssh: server-generated gex p is out of range (%d bits)", kexDHGexGroup.P.BitLen())
|
return nil, fmt.Errorf("ssh: server-generated gex p is out of range (%d bits)", msg.P.BitLen())
|
||||||
}
|
}
|
||||||
|
|
||||||
gex.p = kexDHGexGroup.P
|
// Check if g is safe by verifying that 1 < g < p-1
|
||||||
gex.g = kexDHGexGroup.G
|
pMinusOne := new(big.Int).Sub(msg.P, bigOne)
|
||||||
|
if msg.G.Cmp(bigOne) <= 0 || msg.G.Cmp(pMinusOne) >= 0 {
|
||||||
// Check if g is safe by verifing that g > 1 and g < p - 1
|
|
||||||
one := big.NewInt(1)
|
|
||||||
var pMinusOne = &big.Int{}
|
|
||||||
pMinusOne.Sub(gex.p, one)
|
|
||||||
if gex.g.Cmp(one) != 1 && gex.g.Cmp(pMinusOne) != -1 {
|
|
||||||
return nil, fmt.Errorf("ssh: server provided gex g is not safe")
|
return nil, fmt.Errorf("ssh: server provided gex g is not safe")
|
||||||
}
|
}
|
||||||
|
|
||||||
// Send GexInit
|
// Send GexInit
|
||||||
var pHalf = &big.Int{}
|
pHalf := new(big.Int).Rsh(msg.P, 1)
|
||||||
pHalf.Rsh(gex.p, 1)
|
|
||||||
x, err := rand.Int(randSource, pHalf)
|
x, err := rand.Int(randSource, pHalf)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
X := new(big.Int).Exp(gex.g, x, gex.p)
|
X := new(big.Int).Exp(msg.G, x, msg.P)
|
||||||
kexDHGexInit := kexDHGexInitMsg{
|
kexDHGexInit := kexDHGexInitMsg{
|
||||||
X: X,
|
X: X,
|
||||||
}
|
}
|
||||||
|
|
@ -634,13 +644,13 @@ func (gex dhGEXSHA) Client(c packetConn, randSource io.Reader, magics *handshake
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
kInt, err := gex.diffieHellman(kexDHGexReply.Y, x)
|
if kexDHGexReply.Y.Cmp(bigOne) <= 0 || kexDHGexReply.Y.Cmp(pMinusOne) >= 0 {
|
||||||
if err != nil {
|
return nil, errors.New("ssh: DH parameter out of bounds")
|
||||||
return nil, err
|
|
||||||
}
|
}
|
||||||
|
kInt := new(big.Int).Exp(kexDHGexReply.Y, x, msg.P)
|
||||||
|
|
||||||
// Check if k is safe by verifing that k > 1 and k < p - 1
|
// Check if k is safe by verifying that k > 1 and k < p - 1
|
||||||
if kInt.Cmp(one) != 1 && kInt.Cmp(pMinusOne) != -1 {
|
if kInt.Cmp(bigOne) <= 0 || kInt.Cmp(pMinusOne) >= 0 {
|
||||||
return nil, fmt.Errorf("ssh: derived k is not safe")
|
return nil, fmt.Errorf("ssh: derived k is not safe")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -650,8 +660,8 @@ func (gex dhGEXSHA) Client(c packetConn, randSource io.Reader, magics *handshake
|
||||||
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMinimumBits))
|
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMinimumBits))
|
||||||
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangePreferredBits))
|
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangePreferredBits))
|
||||||
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMaximumBits))
|
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMaximumBits))
|
||||||
writeInt(h, gex.p)
|
writeInt(h, msg.P)
|
||||||
writeInt(h, gex.g)
|
writeInt(h, msg.G)
|
||||||
writeInt(h, X)
|
writeInt(h, X)
|
||||||
writeInt(h, kexDHGexReply.Y)
|
writeInt(h, kexDHGexReply.Y)
|
||||||
K := make([]byte, intLength(kInt))
|
K := make([]byte, intLength(kInt))
|
||||||
|
|
@ -670,7 +680,7 @@ func (gex dhGEXSHA) Client(c packetConn, randSource io.Reader, magics *handshake
|
||||||
// Server half implementation of the Diffie Hellman Key Exchange with SHA1 and SHA256.
|
// Server half implementation of the Diffie Hellman Key Exchange with SHA1 and SHA256.
|
||||||
//
|
//
|
||||||
// This is a minimal implementation to satisfy the automated tests.
|
// This is a minimal implementation to satisfy the automated tests.
|
||||||
func (gex dhGEXSHA) Server(c packetConn, randSource io.Reader, magics *handshakeMagics, priv Signer) (result *kexResult, err error) {
|
func (gex dhGEXSHA) Server(c packetConn, randSource io.Reader, magics *handshakeMagics, priv AlgorithmSigner, algo string) (result *kexResult, err error) {
|
||||||
// Receive GexRequest
|
// Receive GexRequest
|
||||||
packet, err := c.readPacket()
|
packet, err := c.readPacket()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
@ -681,35 +691,17 @@ func (gex dhGEXSHA) Server(c packetConn, randSource io.Reader, magics *handshake
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
// smoosh the user's preferred size into our own limits
|
|
||||||
if kexDHGexRequest.PreferedBits > dhGroupExchangeMaximumBits {
|
|
||||||
kexDHGexRequest.PreferedBits = dhGroupExchangeMaximumBits
|
|
||||||
}
|
|
||||||
if kexDHGexRequest.PreferedBits < dhGroupExchangeMinimumBits {
|
|
||||||
kexDHGexRequest.PreferedBits = dhGroupExchangeMinimumBits
|
|
||||||
}
|
|
||||||
// fix min/max if they're inconsistent. technically, we could just pout
|
|
||||||
// and hang up, but there's no harm in giving them the benefit of the
|
|
||||||
// doubt and just picking a bitsize for them.
|
|
||||||
if kexDHGexRequest.MinBits > kexDHGexRequest.PreferedBits {
|
|
||||||
kexDHGexRequest.MinBits = kexDHGexRequest.PreferedBits
|
|
||||||
}
|
|
||||||
if kexDHGexRequest.MaxBits < kexDHGexRequest.PreferedBits {
|
|
||||||
kexDHGexRequest.MaxBits = kexDHGexRequest.PreferedBits
|
|
||||||
}
|
|
||||||
|
|
||||||
// Send GexGroup
|
// Send GexGroup
|
||||||
// This is the group called diffie-hellman-group14-sha1 in RFC
|
// This is the group called diffie-hellman-group14-sha1 in RFC
|
||||||
// 4253 and Oakley Group 14 in RFC 3526.
|
// 4253 and Oakley Group 14 in RFC 3526.
|
||||||
p, _ := new(big.Int).SetString("FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3BE39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF6955817183995497CEA956AE515D2261898FA051015728E5A8AACAA68FFFFFFFFFFFFFFFF", 16)
|
p, _ := new(big.Int).SetString("FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3BE39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF6955817183995497CEA956AE515D2261898FA051015728E5A8AACAA68FFFFFFFFFFFFFFFF", 16)
|
||||||
gex.p = p
|
g := big.NewInt(2)
|
||||||
gex.g = big.NewInt(2)
|
|
||||||
|
|
||||||
kexDHGexGroup := kexDHGexGroupMsg{
|
msg := &kexDHGexGroupMsg{
|
||||||
P: gex.p,
|
P: p,
|
||||||
G: gex.g,
|
G: g,
|
||||||
}
|
}
|
||||||
if err := c.writePacket(Marshal(&kexDHGexGroup)); err != nil {
|
if err := c.writePacket(Marshal(msg)); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -723,19 +715,19 @@ func (gex dhGEXSHA) Server(c packetConn, randSource io.Reader, magics *handshake
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
var pHalf = &big.Int{}
|
pHalf := new(big.Int).Rsh(p, 1)
|
||||||
pHalf.Rsh(gex.p, 1)
|
|
||||||
|
|
||||||
y, err := rand.Int(randSource, pHalf)
|
y, err := rand.Int(randSource, pHalf)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
Y := new(big.Int).Exp(g, y, p)
|
||||||
|
|
||||||
Y := new(big.Int).Exp(gex.g, y, gex.p)
|
pMinusOne := new(big.Int).Sub(p, bigOne)
|
||||||
kInt, err := gex.diffieHellman(kexDHGexInit.X, y)
|
if kexDHGexInit.X.Cmp(bigOne) <= 0 || kexDHGexInit.X.Cmp(pMinusOne) >= 0 {
|
||||||
if err != nil {
|
return nil, errors.New("ssh: DH parameter out of bounds")
|
||||||
return nil, err
|
|
||||||
}
|
}
|
||||||
|
kInt := new(big.Int).Exp(kexDHGexInit.X, y, p)
|
||||||
|
|
||||||
hostKeyBytes := priv.PublicKey().Marshal()
|
hostKeyBytes := priv.PublicKey().Marshal()
|
||||||
|
|
||||||
|
|
@ -745,8 +737,8 @@ func (gex dhGEXSHA) Server(c packetConn, randSource io.Reader, magics *handshake
|
||||||
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMinimumBits))
|
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMinimumBits))
|
||||||
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangePreferredBits))
|
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangePreferredBits))
|
||||||
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMaximumBits))
|
binary.Write(h, binary.BigEndian, uint32(dhGroupExchangeMaximumBits))
|
||||||
writeInt(h, gex.p)
|
writeInt(h, p)
|
||||||
writeInt(h, gex.g)
|
writeInt(h, g)
|
||||||
writeInt(h, kexDHGexInit.X)
|
writeInt(h, kexDHGexInit.X)
|
||||||
writeInt(h, Y)
|
writeInt(h, Y)
|
||||||
|
|
||||||
|
|
@ -758,7 +750,7 @@ func (gex dhGEXSHA) Server(c packetConn, randSource io.Reader, magics *handshake
|
||||||
|
|
||||||
// H is already a hash, but the hostkey signing will apply its
|
// H is already a hash, but the hostkey signing will apply its
|
||||||
// own key-specific hash algorithm.
|
// own key-specific hash algorithm.
|
||||||
sig, err := signAndMarshal(priv, randSource, H)
|
sig, err := signAndMarshal(priv, randSource, H, algo)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
152
vendor/golang.org/x/crypto/ssh/keys.go
generated
vendored
152
vendor/golang.org/x/crypto/ssh/keys.go
generated
vendored
|
|
@ -30,8 +30,9 @@ import (
|
||||||
"golang.org/x/crypto/ssh/internal/bcrypt_pbkdf"
|
"golang.org/x/crypto/ssh/internal/bcrypt_pbkdf"
|
||||||
)
|
)
|
||||||
|
|
||||||
// These constants represent the algorithm names for key types supported by this
|
// Public key algorithms names. These values can appear in PublicKey.Type,
|
||||||
// package.
|
// ClientConfig.HostKeyAlgorithms, Signature.Format, or as AlgorithmSigner
|
||||||
|
// arguments.
|
||||||
const (
|
const (
|
||||||
KeyAlgoRSA = "ssh-rsa"
|
KeyAlgoRSA = "ssh-rsa"
|
||||||
KeyAlgoDSA = "ssh-dss"
|
KeyAlgoDSA = "ssh-dss"
|
||||||
|
|
@ -41,16 +42,21 @@ const (
|
||||||
KeyAlgoECDSA521 = "ecdsa-sha2-nistp521"
|
KeyAlgoECDSA521 = "ecdsa-sha2-nistp521"
|
||||||
KeyAlgoED25519 = "ssh-ed25519"
|
KeyAlgoED25519 = "ssh-ed25519"
|
||||||
KeyAlgoSKED25519 = "sk-ssh-ed25519@openssh.com"
|
KeyAlgoSKED25519 = "sk-ssh-ed25519@openssh.com"
|
||||||
|
|
||||||
|
// KeyAlgoRSASHA256 and KeyAlgoRSASHA512 are only public key algorithms, not
|
||||||
|
// public key formats, so they can't appear as a PublicKey.Type. The
|
||||||
|
// corresponding PublicKey.Type is KeyAlgoRSA. See RFC 8332, Section 2.
|
||||||
|
KeyAlgoRSASHA256 = "rsa-sha2-256"
|
||||||
|
KeyAlgoRSASHA512 = "rsa-sha2-512"
|
||||||
)
|
)
|
||||||
|
|
||||||
// These constants represent non-default signature algorithms that are supported
|
|
||||||
// as algorithm parameters to AlgorithmSigner.SignWithAlgorithm methods. See
|
|
||||||
// [PROTOCOL.agent] section 4.5.1 and
|
|
||||||
// https://tools.ietf.org/html/draft-ietf-curdle-rsa-sha2-10
|
|
||||||
const (
|
const (
|
||||||
SigAlgoRSA = "ssh-rsa"
|
// Deprecated: use KeyAlgoRSA.
|
||||||
SigAlgoRSASHA2256 = "rsa-sha2-256"
|
SigAlgoRSA = KeyAlgoRSA
|
||||||
SigAlgoRSASHA2512 = "rsa-sha2-512"
|
// Deprecated: use KeyAlgoRSASHA256.
|
||||||
|
SigAlgoRSASHA2256 = KeyAlgoRSASHA256
|
||||||
|
// Deprecated: use KeyAlgoRSASHA512.
|
||||||
|
SigAlgoRSASHA2512 = KeyAlgoRSASHA512
|
||||||
)
|
)
|
||||||
|
|
||||||
// parsePubKey parses a public key of the given algorithm.
|
// parsePubKey parses a public key of the given algorithm.
|
||||||
|
|
@ -70,7 +76,7 @@ func parsePubKey(in []byte, algo string) (pubKey PublicKey, rest []byte, err err
|
||||||
case KeyAlgoSKED25519:
|
case KeyAlgoSKED25519:
|
||||||
return parseSKEd25519(in)
|
return parseSKEd25519(in)
|
||||||
case CertAlgoRSAv01, CertAlgoDSAv01, CertAlgoECDSA256v01, CertAlgoECDSA384v01, CertAlgoECDSA521v01, CertAlgoSKECDSA256v01, CertAlgoED25519v01, CertAlgoSKED25519v01:
|
case CertAlgoRSAv01, CertAlgoDSAv01, CertAlgoECDSA256v01, CertAlgoECDSA384v01, CertAlgoECDSA521v01, CertAlgoSKECDSA256v01, CertAlgoED25519v01, CertAlgoSKED25519v01:
|
||||||
cert, err := parseCert(in, certToPrivAlgo(algo))
|
cert, err := parseCert(in, certKeyAlgoNames[algo])
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -178,7 +184,7 @@ func ParseKnownHosts(in []byte) (marker string, hosts []string, pubKey PublicKey
|
||||||
return "", nil, nil, "", nil, io.EOF
|
return "", nil, nil, "", nil, io.EOF
|
||||||
}
|
}
|
||||||
|
|
||||||
// ParseAuthorizedKeys parses a public key from an authorized_keys
|
// ParseAuthorizedKey parses a public key from an authorized_keys
|
||||||
// file used in OpenSSH according to the sshd(8) manual page.
|
// file used in OpenSSH according to the sshd(8) manual page.
|
||||||
func ParseAuthorizedKey(in []byte) (out PublicKey, comment string, options []string, rest []byte, err error) {
|
func ParseAuthorizedKey(in []byte) (out PublicKey, comment string, options []string, rest []byte, err error) {
|
||||||
for len(in) > 0 {
|
for len(in) > 0 {
|
||||||
|
|
@ -289,18 +295,21 @@ func MarshalAuthorizedKey(key PublicKey) []byte {
|
||||||
return b.Bytes()
|
return b.Bytes()
|
||||||
}
|
}
|
||||||
|
|
||||||
// PublicKey is an abstraction of different types of public keys.
|
// PublicKey represents a public key using an unspecified algorithm.
|
||||||
|
//
|
||||||
|
// Some PublicKeys provided by this package also implement CryptoPublicKey.
|
||||||
type PublicKey interface {
|
type PublicKey interface {
|
||||||
// Type returns the key's type, e.g. "ssh-rsa".
|
// Type returns the key format name, e.g. "ssh-rsa".
|
||||||
Type() string
|
Type() string
|
||||||
|
|
||||||
// Marshal returns the serialized key data in SSH wire format,
|
// Marshal returns the serialized key data in SSH wire format, with the name
|
||||||
// with the name prefix. To unmarshal the returned data, use
|
// prefix. To unmarshal the returned data, use the ParsePublicKey function.
|
||||||
// the ParsePublicKey function.
|
|
||||||
Marshal() []byte
|
Marshal() []byte
|
||||||
|
|
||||||
// Verify that sig is a signature on the given data using this
|
// Verify that sig is a signature on the given data using this key. This
|
||||||
// key. This function will hash the data appropriately first.
|
// method will hash the data appropriately first. sig.Format is allowed to
|
||||||
|
// be any signature algorithm compatible with the key type, the caller
|
||||||
|
// should check if it has more stringent requirements.
|
||||||
Verify(data []byte, sig *Signature) error
|
Verify(data []byte, sig *Signature) error
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -311,25 +320,32 @@ type CryptoPublicKey interface {
|
||||||
}
|
}
|
||||||
|
|
||||||
// A Signer can create signatures that verify against a public key.
|
// A Signer can create signatures that verify against a public key.
|
||||||
|
//
|
||||||
|
// Some Signers provided by this package also implement AlgorithmSigner.
|
||||||
type Signer interface {
|
type Signer interface {
|
||||||
// PublicKey returns an associated PublicKey instance.
|
// PublicKey returns the associated PublicKey.
|
||||||
PublicKey() PublicKey
|
PublicKey() PublicKey
|
||||||
|
|
||||||
// Sign returns raw signature for the given data. This method
|
// Sign returns a signature for the given data. This method will hash the
|
||||||
// will apply the hash specified for the keytype to the data.
|
// data appropriately first. The signature algorithm is expected to match
|
||||||
|
// the key format returned by the PublicKey.Type method (and not to be any
|
||||||
|
// alternative algorithm supported by the key format).
|
||||||
Sign(rand io.Reader, data []byte) (*Signature, error)
|
Sign(rand io.Reader, data []byte) (*Signature, error)
|
||||||
}
|
}
|
||||||
|
|
||||||
// A AlgorithmSigner is a Signer that also supports specifying a specific
|
// An AlgorithmSigner is a Signer that also supports specifying an algorithm to
|
||||||
// algorithm to use for signing.
|
// use for signing.
|
||||||
|
//
|
||||||
|
// An AlgorithmSigner can't advertise the algorithms it supports, so it should
|
||||||
|
// be prepared to be invoked with every algorithm supported by the public key
|
||||||
|
// format.
|
||||||
type AlgorithmSigner interface {
|
type AlgorithmSigner interface {
|
||||||
Signer
|
Signer
|
||||||
|
|
||||||
// SignWithAlgorithm is like Signer.Sign, but allows specification of a
|
// SignWithAlgorithm is like Signer.Sign, but allows specifying a desired
|
||||||
// non-default signing algorithm. See the SigAlgo* constants in this
|
// signing algorithm. Callers may pass an empty string for the algorithm in
|
||||||
// package for signature algorithms supported by this package. Callers may
|
// which case the AlgorithmSigner will use a default algorithm. This default
|
||||||
// pass an empty string for the algorithm in which case the AlgorithmSigner
|
// doesn't currently control any behavior in this package.
|
||||||
// will use its default algorithm.
|
|
||||||
SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error)
|
SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -381,17 +397,11 @@ func (r *rsaPublicKey) Marshal() []byte {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (r *rsaPublicKey) Verify(data []byte, sig *Signature) error {
|
func (r *rsaPublicKey) Verify(data []byte, sig *Signature) error {
|
||||||
var hash crypto.Hash
|
supportedAlgos := algorithmsForKeyFormat(r.Type())
|
||||||
switch sig.Format {
|
if !contains(supportedAlgos, sig.Format) {
|
||||||
case SigAlgoRSA:
|
|
||||||
hash = crypto.SHA1
|
|
||||||
case SigAlgoRSASHA2256:
|
|
||||||
hash = crypto.SHA256
|
|
||||||
case SigAlgoRSASHA2512:
|
|
||||||
hash = crypto.SHA512
|
|
||||||
default:
|
|
||||||
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, r.Type())
|
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, r.Type())
|
||||||
}
|
}
|
||||||
|
hash := hashFuncs[sig.Format]
|
||||||
h := hash.New()
|
h := hash.New()
|
||||||
h.Write(data)
|
h.Write(data)
|
||||||
digest := h.Sum(nil)
|
digest := h.Sum(nil)
|
||||||
|
|
@ -466,7 +476,7 @@ func (k *dsaPublicKey) Verify(data []byte, sig *Signature) error {
|
||||||
if sig.Format != k.Type() {
|
if sig.Format != k.Type() {
|
||||||
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, k.Type())
|
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, k.Type())
|
||||||
}
|
}
|
||||||
h := crypto.SHA1.New()
|
h := hashFuncs[sig.Format].New()
|
||||||
h.Write(data)
|
h.Write(data)
|
||||||
digest := h.Sum(nil)
|
digest := h.Sum(nil)
|
||||||
|
|
||||||
|
|
@ -499,7 +509,7 @@ func (k *dsaPrivateKey) PublicKey() PublicKey {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (k *dsaPrivateKey) Sign(rand io.Reader, data []byte) (*Signature, error) {
|
func (k *dsaPrivateKey) Sign(rand io.Reader, data []byte) (*Signature, error) {
|
||||||
return k.SignWithAlgorithm(rand, data, "")
|
return k.SignWithAlgorithm(rand, data, k.PublicKey().Type())
|
||||||
}
|
}
|
||||||
|
|
||||||
func (k *dsaPrivateKey) SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error) {
|
func (k *dsaPrivateKey) SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error) {
|
||||||
|
|
@ -507,7 +517,7 @@ func (k *dsaPrivateKey) SignWithAlgorithm(rand io.Reader, data []byte, algorithm
|
||||||
return nil, fmt.Errorf("ssh: unsupported signature algorithm %s", algorithm)
|
return nil, fmt.Errorf("ssh: unsupported signature algorithm %s", algorithm)
|
||||||
}
|
}
|
||||||
|
|
||||||
h := crypto.SHA1.New()
|
h := hashFuncs[k.PublicKey().Type()].New()
|
||||||
h.Write(data)
|
h.Write(data)
|
||||||
digest := h.Sum(nil)
|
digest := h.Sum(nil)
|
||||||
r, s, err := dsa.Sign(rand, k.PrivateKey, digest)
|
r, s, err := dsa.Sign(rand, k.PrivateKey, digest)
|
||||||
|
|
@ -603,19 +613,6 @@ func supportedEllipticCurve(curve elliptic.Curve) bool {
|
||||||
return curve == elliptic.P256() || curve == elliptic.P384() || curve == elliptic.P521()
|
return curve == elliptic.P256() || curve == elliptic.P384() || curve == elliptic.P521()
|
||||||
}
|
}
|
||||||
|
|
||||||
// ecHash returns the hash to match the given elliptic curve, see RFC
|
|
||||||
// 5656, section 6.2.1
|
|
||||||
func ecHash(curve elliptic.Curve) crypto.Hash {
|
|
||||||
bitSize := curve.Params().BitSize
|
|
||||||
switch {
|
|
||||||
case bitSize <= 256:
|
|
||||||
return crypto.SHA256
|
|
||||||
case bitSize <= 384:
|
|
||||||
return crypto.SHA384
|
|
||||||
}
|
|
||||||
return crypto.SHA512
|
|
||||||
}
|
|
||||||
|
|
||||||
// parseECDSA parses an ECDSA key according to RFC 5656, section 3.1.
|
// parseECDSA parses an ECDSA key according to RFC 5656, section 3.1.
|
||||||
func parseECDSA(in []byte) (out PublicKey, rest []byte, err error) {
|
func parseECDSA(in []byte) (out PublicKey, rest []byte, err error) {
|
||||||
var w struct {
|
var w struct {
|
||||||
|
|
@ -671,7 +668,7 @@ func (k *ecdsaPublicKey) Verify(data []byte, sig *Signature) error {
|
||||||
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, k.Type())
|
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, k.Type())
|
||||||
}
|
}
|
||||||
|
|
||||||
h := ecHash(k.Curve).New()
|
h := hashFuncs[sig.Format].New()
|
||||||
h.Write(data)
|
h.Write(data)
|
||||||
digest := h.Sum(nil)
|
digest := h.Sum(nil)
|
||||||
|
|
||||||
|
|
@ -775,7 +772,7 @@ func (k *skECDSAPublicKey) Verify(data []byte, sig *Signature) error {
|
||||||
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, k.Type())
|
return fmt.Errorf("ssh: signature type %s for key type %s", sig.Format, k.Type())
|
||||||
}
|
}
|
||||||
|
|
||||||
h := ecHash(k.Curve).New()
|
h := hashFuncs[sig.Format].New()
|
||||||
h.Write([]byte(k.application))
|
h.Write([]byte(k.application))
|
||||||
appDigest := h.Sum(nil)
|
appDigest := h.Sum(nil)
|
||||||
|
|
||||||
|
|
@ -874,7 +871,7 @@ func (k *skEd25519PublicKey) Verify(data []byte, sig *Signature) error {
|
||||||
return fmt.Errorf("invalid size %d for Ed25519 public key", l)
|
return fmt.Errorf("invalid size %d for Ed25519 public key", l)
|
||||||
}
|
}
|
||||||
|
|
||||||
h := sha256.New()
|
h := hashFuncs[sig.Format].New()
|
||||||
h.Write([]byte(k.application))
|
h.Write([]byte(k.application))
|
||||||
appDigest := h.Sum(nil)
|
appDigest := h.Sum(nil)
|
||||||
|
|
||||||
|
|
@ -939,15 +936,6 @@ func newDSAPrivateKey(key *dsa.PrivateKey) (Signer, error) {
|
||||||
return &dsaPrivateKey{key}, nil
|
return &dsaPrivateKey{key}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
type rsaSigner struct {
|
|
||||||
AlgorithmSigner
|
|
||||||
defaultAlgorithm string
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *rsaSigner) Sign(rand io.Reader, data []byte) (*Signature, error) {
|
|
||||||
return s.AlgorithmSigner.SignWithAlgorithm(rand, data, s.defaultAlgorithm)
|
|
||||||
}
|
|
||||||
|
|
||||||
type wrappedSigner struct {
|
type wrappedSigner struct {
|
||||||
signer crypto.Signer
|
signer crypto.Signer
|
||||||
pubKey PublicKey
|
pubKey PublicKey
|
||||||
|
|
@ -970,44 +958,20 @@ func (s *wrappedSigner) PublicKey() PublicKey {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *wrappedSigner) Sign(rand io.Reader, data []byte) (*Signature, error) {
|
func (s *wrappedSigner) Sign(rand io.Reader, data []byte) (*Signature, error) {
|
||||||
return s.SignWithAlgorithm(rand, data, "")
|
return s.SignWithAlgorithm(rand, data, s.pubKey.Type())
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *wrappedSigner) SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error) {
|
func (s *wrappedSigner) SignWithAlgorithm(rand io.Reader, data []byte, algorithm string) (*Signature, error) {
|
||||||
var hashFunc crypto.Hash
|
|
||||||
|
|
||||||
if _, ok := s.pubKey.(*rsaPublicKey); ok {
|
|
||||||
// RSA keys support a few hash functions determined by the requested signature algorithm
|
|
||||||
switch algorithm {
|
|
||||||
case "", SigAlgoRSA:
|
|
||||||
algorithm = SigAlgoRSA
|
|
||||||
hashFunc = crypto.SHA1
|
|
||||||
case SigAlgoRSASHA2256:
|
|
||||||
hashFunc = crypto.SHA256
|
|
||||||
case SigAlgoRSASHA2512:
|
|
||||||
hashFunc = crypto.SHA512
|
|
||||||
default:
|
|
||||||
return nil, fmt.Errorf("ssh: unsupported signature algorithm %s", algorithm)
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// The only supported algorithm for all other key types is the same as the type of the key
|
|
||||||
if algorithm == "" {
|
if algorithm == "" {
|
||||||
algorithm = s.pubKey.Type()
|
algorithm = s.pubKey.Type()
|
||||||
} else if algorithm != s.pubKey.Type() {
|
|
||||||
return nil, fmt.Errorf("ssh: unsupported signature algorithm %s", algorithm)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
switch key := s.pubKey.(type) {
|
supportedAlgos := algorithmsForKeyFormat(s.pubKey.Type())
|
||||||
case *dsaPublicKey:
|
if !contains(supportedAlgos, algorithm) {
|
||||||
hashFunc = crypto.SHA1
|
return nil, fmt.Errorf("ssh: unsupported signature algorithm %q for key format %q", algorithm, s.pubKey.Type())
|
||||||
case *ecdsaPublicKey:
|
|
||||||
hashFunc = ecHash(key.Curve)
|
|
||||||
case ed25519PublicKey:
|
|
||||||
default:
|
|
||||||
return nil, fmt.Errorf("ssh: unsupported key type %T", key)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
hashFunc := hashFuncs[algorithm]
|
||||||
var digest []byte
|
var digest []byte
|
||||||
if hashFunc != 0 {
|
if hashFunc != 0 {
|
||||||
h := hashFunc.New()
|
h := hashFunc.New()
|
||||||
|
|
|
||||||
15
vendor/golang.org/x/crypto/ssh/messages.go
generated
vendored
15
vendor/golang.org/x/crypto/ssh/messages.go
generated
vendored
|
|
@ -141,6 +141,14 @@ type serviceAcceptMsg struct {
|
||||||
Service string `sshtype:"6"`
|
Service string `sshtype:"6"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// See RFC 8308, section 2.3
|
||||||
|
const msgExtInfo = 7
|
||||||
|
|
||||||
|
type extInfoMsg struct {
|
||||||
|
NumExtensions uint32 `sshtype:"7"`
|
||||||
|
Payload []byte `ssh:"rest"`
|
||||||
|
}
|
||||||
|
|
||||||
// See RFC 4252, section 5.
|
// See RFC 4252, section 5.
|
||||||
const msgUserAuthRequest = 50
|
const msgUserAuthRequest = 50
|
||||||
|
|
||||||
|
|
@ -180,9 +188,9 @@ const msgUserAuthInfoRequest = 60
|
||||||
const msgUserAuthInfoResponse = 61
|
const msgUserAuthInfoResponse = 61
|
||||||
|
|
||||||
type userAuthInfoRequestMsg struct {
|
type userAuthInfoRequestMsg struct {
|
||||||
User string `sshtype:"60"`
|
Name string `sshtype:"60"`
|
||||||
Instruction string
|
Instruction string
|
||||||
DeprecatedLanguage string
|
Language string
|
||||||
NumPrompts uint32
|
NumPrompts uint32
|
||||||
Prompts []byte `ssh:"rest"`
|
Prompts []byte `ssh:"rest"`
|
||||||
}
|
}
|
||||||
|
|
@ -782,6 +790,8 @@ func decode(packet []byte) (interface{}, error) {
|
||||||
msg = new(serviceRequestMsg)
|
msg = new(serviceRequestMsg)
|
||||||
case msgServiceAccept:
|
case msgServiceAccept:
|
||||||
msg = new(serviceAcceptMsg)
|
msg = new(serviceAcceptMsg)
|
||||||
|
case msgExtInfo:
|
||||||
|
msg = new(extInfoMsg)
|
||||||
case msgKexInit:
|
case msgKexInit:
|
||||||
msg = new(kexInitMsg)
|
msg = new(kexInitMsg)
|
||||||
case msgKexDHInit:
|
case msgKexDHInit:
|
||||||
|
|
@ -843,6 +853,7 @@ var packetTypeNames = map[byte]string{
|
||||||
msgDisconnect: "disconnectMsg",
|
msgDisconnect: "disconnectMsg",
|
||||||
msgServiceRequest: "serviceRequestMsg",
|
msgServiceRequest: "serviceRequestMsg",
|
||||||
msgServiceAccept: "serviceAcceptMsg",
|
msgServiceAccept: "serviceAcceptMsg",
|
||||||
|
msgExtInfo: "extInfoMsg",
|
||||||
msgKexInit: "kexInitMsg",
|
msgKexInit: "kexInitMsg",
|
||||||
msgKexDHInit: "kexDHInitMsg",
|
msgKexDHInit: "kexDHInitMsg",
|
||||||
msgKexDHReply: "kexDHReplyMsg",
|
msgKexDHReply: "kexDHReplyMsg",
|
||||||
|
|
|
||||||
58
vendor/golang.org/x/crypto/ssh/server.go
generated
vendored
58
vendor/golang.org/x/crypto/ssh/server.go
generated
vendored
|
|
@ -68,8 +68,16 @@ type ServerConfig struct {
|
||||||
|
|
||||||
// NoClientAuth is true if clients are allowed to connect without
|
// NoClientAuth is true if clients are allowed to connect without
|
||||||
// authenticating.
|
// authenticating.
|
||||||
|
// To determine NoClientAuth at runtime, set NoClientAuth to true
|
||||||
|
// and the optional NoClientAuthCallback to a non-nil value.
|
||||||
NoClientAuth bool
|
NoClientAuth bool
|
||||||
|
|
||||||
|
// NoClientAuthCallback, if non-nil, is called when a user
|
||||||
|
// attempts to authenticate with auth method "none".
|
||||||
|
// NoClientAuth must also be set to true for this be used, or
|
||||||
|
// this func is unused.
|
||||||
|
NoClientAuthCallback func(ConnMetadata) (*Permissions, error)
|
||||||
|
|
||||||
// MaxAuthTries specifies the maximum number of authentication attempts
|
// MaxAuthTries specifies the maximum number of authentication attempts
|
||||||
// permitted per connection. If set to a negative number, the number of
|
// permitted per connection. If set to a negative number, the number of
|
||||||
// attempts are unlimited. If set to zero, the number of attempts are limited
|
// attempts are unlimited. If set to zero, the number of attempts are limited
|
||||||
|
|
@ -120,7 +128,7 @@ type ServerConfig struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
// AddHostKey adds a private key as a host key. If an existing host
|
// AddHostKey adds a private key as a host key. If an existing host
|
||||||
// key exists with the same algorithm, it is overwritten. Each server
|
// key exists with the same public key format, it is replaced. Each server
|
||||||
// config must have at least one host key.
|
// config must have at least one host key.
|
||||||
func (s *ServerConfig) AddHostKey(key Signer) {
|
func (s *ServerConfig) AddHostKey(key Signer) {
|
||||||
for i, k := range s.hostKeys {
|
for i, k := range s.hostKeys {
|
||||||
|
|
@ -212,9 +220,10 @@ func NewServerConn(c net.Conn, config *ServerConfig) (*ServerConn, <-chan NewCha
|
||||||
}
|
}
|
||||||
|
|
||||||
// signAndMarshal signs the data with the appropriate algorithm,
|
// signAndMarshal signs the data with the appropriate algorithm,
|
||||||
// and serializes the result in SSH wire format.
|
// and serializes the result in SSH wire format. algo is the negotiate
|
||||||
func signAndMarshal(k Signer, rand io.Reader, data []byte) ([]byte, error) {
|
// algorithm and may be a certificate type.
|
||||||
sig, err := k.Sign(rand, data)
|
func signAndMarshal(k AlgorithmSigner, rand io.Reader, data []byte, algo string) ([]byte, error) {
|
||||||
|
sig, err := k.SignWithAlgorithm(rand, data, underlyingAlgo(algo))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -284,7 +293,7 @@ func (s *connection) serverHandshake(config *ServerConfig) (*Permissions, error)
|
||||||
|
|
||||||
func isAcceptableAlgo(algo string) bool {
|
func isAcceptableAlgo(algo string) bool {
|
||||||
switch algo {
|
switch algo {
|
||||||
case SigAlgoRSA, SigAlgoRSASHA2256, SigAlgoRSASHA2512, KeyAlgoDSA, KeyAlgoECDSA256, KeyAlgoECDSA384, KeyAlgoECDSA521, KeyAlgoSKECDSA256, KeyAlgoED25519, KeyAlgoSKED25519,
|
case KeyAlgoRSA, KeyAlgoRSASHA256, KeyAlgoRSASHA512, KeyAlgoDSA, KeyAlgoECDSA256, KeyAlgoECDSA384, KeyAlgoECDSA521, KeyAlgoSKECDSA256, KeyAlgoED25519, KeyAlgoSKED25519,
|
||||||
CertAlgoRSAv01, CertAlgoDSAv01, CertAlgoECDSA256v01, CertAlgoECDSA384v01, CertAlgoECDSA521v01, CertAlgoSKECDSA256v01, CertAlgoED25519v01, CertAlgoSKED25519v01:
|
CertAlgoRSAv01, CertAlgoDSAv01, CertAlgoECDSA256v01, CertAlgoECDSA384v01, CertAlgoECDSA521v01, CertAlgoSKECDSA256v01, CertAlgoED25519v01, CertAlgoSKED25519v01:
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
@ -454,8 +463,12 @@ userAuthLoop:
|
||||||
switch userAuthReq.Method {
|
switch userAuthReq.Method {
|
||||||
case "none":
|
case "none":
|
||||||
if config.NoClientAuth {
|
if config.NoClientAuth {
|
||||||
|
if config.NoClientAuthCallback != nil {
|
||||||
|
perms, authErr = config.NoClientAuthCallback(s)
|
||||||
|
} else {
|
||||||
authErr = nil
|
authErr = nil
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// allow initial attempt of 'none' without penalty
|
// allow initial attempt of 'none' without penalty
|
||||||
if authFailures == 0 {
|
if authFailures == 0 {
|
||||||
|
|
@ -553,6 +566,7 @@ userAuthLoop:
|
||||||
if !ok || len(payload) > 0 {
|
if !ok || len(payload) > 0 {
|
||||||
return nil, parseError(msgUserAuthRequest)
|
return nil, parseError(msgUserAuthRequest)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Ensure the public key algo and signature algo
|
// Ensure the public key algo and signature algo
|
||||||
// are supported. Compare the private key
|
// are supported. Compare the private key
|
||||||
// algorithm name that corresponds to algo with
|
// algorithm name that corresponds to algo with
|
||||||
|
|
@ -562,7 +576,12 @@ userAuthLoop:
|
||||||
authErr = fmt.Errorf("ssh: algorithm %q not accepted", sig.Format)
|
authErr = fmt.Errorf("ssh: algorithm %q not accepted", sig.Format)
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
signedData := buildDataSignedForAuth(sessionID, userAuthReq, algoBytes, pubKeyData)
|
if underlyingAlgo(algo) != sig.Format {
|
||||||
|
authErr = fmt.Errorf("ssh: signature %q not compatible with selected algorithm %q", sig.Format, algo)
|
||||||
|
break
|
||||||
|
}
|
||||||
|
|
||||||
|
signedData := buildDataSignedForAuth(sessionID, userAuthReq, algo, pubKeyData)
|
||||||
|
|
||||||
if err := pubKey.Verify(signedData, sig); err != nil {
|
if err := pubKey.Verify(signedData, sig); err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
@ -633,6 +652,30 @@ userAuthLoop:
|
||||||
}
|
}
|
||||||
|
|
||||||
authFailures++
|
authFailures++
|
||||||
|
if config.MaxAuthTries > 0 && authFailures >= config.MaxAuthTries {
|
||||||
|
// If we have hit the max attempts, don't bother sending the
|
||||||
|
// final SSH_MSG_USERAUTH_FAILURE message, since there are
|
||||||
|
// no more authentication methods which can be attempted,
|
||||||
|
// and this message may cause the client to re-attempt
|
||||||
|
// authentication while we send the disconnect message.
|
||||||
|
// Continue, and trigger the disconnect at the start of
|
||||||
|
// the loop.
|
||||||
|
//
|
||||||
|
// The SSH specification is somewhat confusing about this,
|
||||||
|
// RFC 4252 Section 5.1 requires each authentication failure
|
||||||
|
// be responded to with a respective SSH_MSG_USERAUTH_FAILURE
|
||||||
|
// message, but Section 4 says the server should disconnect
|
||||||
|
// after some number of attempts, but it isn't explicit which
|
||||||
|
// message should take precedence (i.e. should there be a failure
|
||||||
|
// message than a disconnect message, or if we are going to
|
||||||
|
// disconnect, should we only send that message.)
|
||||||
|
//
|
||||||
|
// Either way, OpenSSH disconnects immediately after the last
|
||||||
|
// failed authnetication attempt, and given they are typically
|
||||||
|
// considered the golden implementation it seems reasonable
|
||||||
|
// to match that behavior.
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
var failureMsg userAuthFailureMsg
|
var failureMsg userAuthFailureMsg
|
||||||
if config.PasswordCallback != nil {
|
if config.PasswordCallback != nil {
|
||||||
|
|
@ -670,7 +713,7 @@ type sshClientKeyboardInteractive struct {
|
||||||
*connection
|
*connection
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *sshClientKeyboardInteractive) Challenge(user, instruction string, questions []string, echos []bool) (answers []string, err error) {
|
func (c *sshClientKeyboardInteractive) Challenge(name, instruction string, questions []string, echos []bool) (answers []string, err error) {
|
||||||
if len(questions) != len(echos) {
|
if len(questions) != len(echos) {
|
||||||
return nil, errors.New("ssh: echos and questions must have equal length")
|
return nil, errors.New("ssh: echos and questions must have equal length")
|
||||||
}
|
}
|
||||||
|
|
@ -682,6 +725,7 @@ func (c *sshClientKeyboardInteractive) Challenge(user, instruction string, quest
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := c.transport.writePacket(Marshal(&userAuthInfoRequestMsg{
|
if err := c.transport.writePacket(Marshal(&userAuthInfoRequestMsg{
|
||||||
|
Name: name,
|
||||||
Instruction: instruction,
|
Instruction: instruction,
|
||||||
NumPrompts: uint32(len(questions)),
|
NumPrompts: uint32(len(questions)),
|
||||||
Prompts: prompts,
|
Prompts: prompts,
|
||||||
|
|
|
||||||
8
vendor/golang.org/x/crypto/ssh/session.go
generated
vendored
8
vendor/golang.org/x/crypto/ssh/session.go
generated
vendored
|
|
@ -13,7 +13,6 @@ import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
"sync"
|
"sync"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -85,6 +84,7 @@ const (
|
||||||
IXANY = 39
|
IXANY = 39
|
||||||
IXOFF = 40
|
IXOFF = 40
|
||||||
IMAXBEL = 41
|
IMAXBEL = 41
|
||||||
|
IUTF8 = 42 // RFC 8160
|
||||||
ISIG = 50
|
ISIG = 50
|
||||||
ICANON = 51
|
ICANON = 51
|
||||||
XCASE = 52
|
XCASE = 52
|
||||||
|
|
@ -123,7 +123,7 @@ type Session struct {
|
||||||
// output and error.
|
// output and error.
|
||||||
//
|
//
|
||||||
// If either is nil, Run connects the corresponding file
|
// If either is nil, Run connects the corresponding file
|
||||||
// descriptor to an instance of ioutil.Discard. There is a
|
// descriptor to an instance of io.Discard. There is a
|
||||||
// fixed amount of buffering that is shared for the two streams.
|
// fixed amount of buffering that is shared for the two streams.
|
||||||
// If either blocks it may eventually cause the remote
|
// If either blocks it may eventually cause the remote
|
||||||
// command to block.
|
// command to block.
|
||||||
|
|
@ -505,7 +505,7 @@ func (s *Session) stdout() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if s.Stdout == nil {
|
if s.Stdout == nil {
|
||||||
s.Stdout = ioutil.Discard
|
s.Stdout = io.Discard
|
||||||
}
|
}
|
||||||
s.copyFuncs = append(s.copyFuncs, func() error {
|
s.copyFuncs = append(s.copyFuncs, func() error {
|
||||||
_, err := io.Copy(s.Stdout, s.ch)
|
_, err := io.Copy(s.Stdout, s.ch)
|
||||||
|
|
@ -518,7 +518,7 @@ func (s *Session) stderr() {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if s.Stderr == nil {
|
if s.Stderr == nil {
|
||||||
s.Stderr = ioutil.Discard
|
s.Stderr = io.Discard
|
||||||
}
|
}
|
||||||
s.copyFuncs = append(s.copyFuncs, func() error {
|
s.copyFuncs = append(s.copyFuncs, func() error {
|
||||||
_, err := io.Copy(s.Stderr, s.ch.Stderr())
|
_, err := io.Copy(s.Stderr, s.ch.Stderr())
|
||||||
|
|
|
||||||
8
vendor/golang.org/x/crypto/ssh/transport.go
generated
vendored
8
vendor/golang.org/x/crypto/ssh/transport.go
generated
vendored
|
|
@ -238,15 +238,19 @@ var (
|
||||||
// (to setup server->client keys) or clientKeys (for client->server keys).
|
// (to setup server->client keys) or clientKeys (for client->server keys).
|
||||||
func newPacketCipher(d direction, algs directionAlgorithms, kex *kexResult) (packetCipher, error) {
|
func newPacketCipher(d direction, algs directionAlgorithms, kex *kexResult) (packetCipher, error) {
|
||||||
cipherMode := cipherModes[algs.Cipher]
|
cipherMode := cipherModes[algs.Cipher]
|
||||||
macMode := macModes[algs.MAC]
|
|
||||||
|
|
||||||
iv := make([]byte, cipherMode.ivSize)
|
iv := make([]byte, cipherMode.ivSize)
|
||||||
key := make([]byte, cipherMode.keySize)
|
key := make([]byte, cipherMode.keySize)
|
||||||
macKey := make([]byte, macMode.keySize)
|
|
||||||
|
|
||||||
generateKeyMaterial(iv, d.ivTag, kex)
|
generateKeyMaterial(iv, d.ivTag, kex)
|
||||||
generateKeyMaterial(key, d.keyTag, kex)
|
generateKeyMaterial(key, d.keyTag, kex)
|
||||||
|
|
||||||
|
var macKey []byte
|
||||||
|
if !aeadCiphers[algs.Cipher] {
|
||||||
|
macMode := macModes[algs.MAC]
|
||||||
|
macKey = make([]byte, macMode.keySize)
|
||||||
generateKeyMaterial(macKey, d.macKeyTag, kex)
|
generateKeyMaterial(macKey, d.macKeyTag, kex)
|
||||||
|
}
|
||||||
|
|
||||||
return cipherModes[algs.Cipher].create(key, iv, macKey, algs)
|
return cipherModes[algs.Cipher].create(key, iv, macKey, algs)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
30
vendor/golang.org/x/mod/semver/semver.go
generated
vendored
30
vendor/golang.org/x/mod/semver/semver.go
generated
vendored
|
|
@ -22,6 +22,8 @@
|
||||||
// as shorthands for vMAJOR.0.0 and vMAJOR.MINOR.0.
|
// as shorthands for vMAJOR.0.0 and vMAJOR.MINOR.0.
|
||||||
package semver
|
package semver
|
||||||
|
|
||||||
|
import "sort"
|
||||||
|
|
||||||
// parsed returns the parsed form of a semantic version string.
|
// parsed returns the parsed form of a semantic version string.
|
||||||
type parsed struct {
|
type parsed struct {
|
||||||
major string
|
major string
|
||||||
|
|
@ -30,7 +32,6 @@ type parsed struct {
|
||||||
short string
|
short string
|
||||||
prerelease string
|
prerelease string
|
||||||
build string
|
build string
|
||||||
err string
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsValid reports whether v is a valid semantic version string.
|
// IsValid reports whether v is a valid semantic version string.
|
||||||
|
|
@ -150,14 +151,30 @@ func Max(v, w string) string {
|
||||||
return w
|
return w
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ByVersion implements sort.Interface for sorting semantic version strings.
|
||||||
|
type ByVersion []string
|
||||||
|
|
||||||
|
func (vs ByVersion) Len() int { return len(vs) }
|
||||||
|
func (vs ByVersion) Swap(i, j int) { vs[i], vs[j] = vs[j], vs[i] }
|
||||||
|
func (vs ByVersion) Less(i, j int) bool {
|
||||||
|
cmp := Compare(vs[i], vs[j])
|
||||||
|
if cmp != 0 {
|
||||||
|
return cmp < 0
|
||||||
|
}
|
||||||
|
return vs[i] < vs[j]
|
||||||
|
}
|
||||||
|
|
||||||
|
// Sort sorts a list of semantic version strings using ByVersion.
|
||||||
|
func Sort(list []string) {
|
||||||
|
sort.Sort(ByVersion(list))
|
||||||
|
}
|
||||||
|
|
||||||
func parse(v string) (p parsed, ok bool) {
|
func parse(v string) (p parsed, ok bool) {
|
||||||
if v == "" || v[0] != 'v' {
|
if v == "" || v[0] != 'v' {
|
||||||
p.err = "missing v prefix"
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
p.major, v, ok = parseInt(v[1:])
|
p.major, v, ok = parseInt(v[1:])
|
||||||
if !ok {
|
if !ok {
|
||||||
p.err = "bad major version"
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if v == "" {
|
if v == "" {
|
||||||
|
|
@ -167,13 +184,11 @@ func parse(v string) (p parsed, ok bool) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if v[0] != '.' {
|
if v[0] != '.' {
|
||||||
p.err = "bad minor prefix"
|
|
||||||
ok = false
|
ok = false
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
p.minor, v, ok = parseInt(v[1:])
|
p.minor, v, ok = parseInt(v[1:])
|
||||||
if !ok {
|
if !ok {
|
||||||
p.err = "bad minor version"
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if v == "" {
|
if v == "" {
|
||||||
|
|
@ -182,31 +197,26 @@ func parse(v string) (p parsed, ok bool) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if v[0] != '.' {
|
if v[0] != '.' {
|
||||||
p.err = "bad patch prefix"
|
|
||||||
ok = false
|
ok = false
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
p.patch, v, ok = parseInt(v[1:])
|
p.patch, v, ok = parseInt(v[1:])
|
||||||
if !ok {
|
if !ok {
|
||||||
p.err = "bad patch version"
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
if len(v) > 0 && v[0] == '-' {
|
if len(v) > 0 && v[0] == '-' {
|
||||||
p.prerelease, v, ok = parsePrerelease(v)
|
p.prerelease, v, ok = parsePrerelease(v)
|
||||||
if !ok {
|
if !ok {
|
||||||
p.err = "bad prerelease"
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if len(v) > 0 && v[0] == '+' {
|
if len(v) > 0 && v[0] == '+' {
|
||||||
p.build, v, ok = parseBuild(v)
|
p.build, v, ok = parseBuild(v)
|
||||||
if !ok {
|
if !ok {
|
||||||
p.err = "bad build"
|
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if v != "" {
|
if v != "" {
|
||||||
p.err = "junk on end"
|
|
||||||
ok = false
|
ok = false
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/net/AUTHORS
generated
vendored
3
vendor/golang.org/x/net/AUTHORS
generated
vendored
|
|
@ -1,3 +0,0 @@
|
||||||
# This source code refers to The Go Authors for copyright purposes.
|
|
||||||
# The master list of authors is in the main Go distribution,
|
|
||||||
# visible at http://tip.golang.org/AUTHORS.
|
|
||||||
3
vendor/golang.org/x/net/CONTRIBUTORS
generated
vendored
3
vendor/golang.org/x/net/CONTRIBUTORS
generated
vendored
|
|
@ -1,3 +0,0 @@
|
||||||
# This source code was written by the Go contributors.
|
|
||||||
# The master list of contributors is in the main Go distribution,
|
|
||||||
# visible at http://tip.golang.org/CONTRIBUTORS.
|
|
||||||
4
vendor/golang.org/x/net/context/go17.go
generated
vendored
4
vendor/golang.org/x/net/context/go17.go
generated
vendored
|
|
@ -32,7 +32,7 @@ var DeadlineExceeded = context.DeadlineExceeded
|
||||||
// call cancel as soon as the operations running in this Context complete.
|
// call cancel as soon as the operations running in this Context complete.
|
||||||
func WithCancel(parent Context) (ctx Context, cancel CancelFunc) {
|
func WithCancel(parent Context) (ctx Context, cancel CancelFunc) {
|
||||||
ctx, f := context.WithCancel(parent)
|
ctx, f := context.WithCancel(parent)
|
||||||
return ctx, CancelFunc(f)
|
return ctx, f
|
||||||
}
|
}
|
||||||
|
|
||||||
// WithDeadline returns a copy of the parent context with the deadline adjusted
|
// WithDeadline returns a copy of the parent context with the deadline adjusted
|
||||||
|
|
@ -46,7 +46,7 @@ func WithCancel(parent Context) (ctx Context, cancel CancelFunc) {
|
||||||
// call cancel as soon as the operations running in this Context complete.
|
// call cancel as soon as the operations running in this Context complete.
|
||||||
func WithDeadline(parent Context, deadline time.Time) (Context, CancelFunc) {
|
func WithDeadline(parent Context, deadline time.Time) (Context, CancelFunc) {
|
||||||
ctx, f := context.WithDeadline(parent, deadline)
|
ctx, f := context.WithDeadline(parent, deadline)
|
||||||
return ctx, CancelFunc(f)
|
return ctx, f
|
||||||
}
|
}
|
||||||
|
|
||||||
// WithTimeout returns WithDeadline(parent, time.Now().Add(timeout)).
|
// WithTimeout returns WithDeadline(parent, time.Now().Add(timeout)).
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/net/html/parse.go
generated
vendored
2
vendor/golang.org/x/net/html/parse.go
generated
vendored
|
|
@ -734,7 +734,7 @@ func inHeadIM(p *parser) bool {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
// 12.2.6.4.5.
|
// Section 12.2.6.4.5.
|
||||||
func inHeadNoscriptIM(p *parser) bool {
|
func inHeadNoscriptIM(p *parser) bool {
|
||||||
switch p.tok.Type {
|
switch p.tok.Type {
|
||||||
case DoctypeToken:
|
case DoctypeToken:
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/net/html/render.go
generated
vendored
4
vendor/golang.org/x/net/html/render.go
generated
vendored
|
|
@ -85,7 +85,7 @@ func render1(w writer, n *Node) error {
|
||||||
if _, err := w.WriteString("<!--"); err != nil {
|
if _, err := w.WriteString("<!--"); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if _, err := w.WriteString(n.Data); err != nil {
|
if err := escape(w, n.Data); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if _, err := w.WriteString("-->"); err != nil {
|
if _, err := w.WriteString("-->"); err != nil {
|
||||||
|
|
@ -96,7 +96,7 @@ func render1(w writer, n *Node) error {
|
||||||
if _, err := w.WriteString("<!DOCTYPE "); err != nil {
|
if _, err := w.WriteString("<!DOCTYPE "); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if _, err := w.WriteString(n.Data); err != nil {
|
if err := escape(w, n.Data); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if n.Attr != nil {
|
if n.Attr != nil {
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/net/html/token.go
generated
vendored
4
vendor/golang.org/x/net/html/token.go
generated
vendored
|
|
@ -110,9 +110,9 @@ func (t Token) String() string {
|
||||||
case SelfClosingTagToken:
|
case SelfClosingTagToken:
|
||||||
return "<" + t.tagString() + "/>"
|
return "<" + t.tagString() + "/>"
|
||||||
case CommentToken:
|
case CommentToken:
|
||||||
return "<!--" + t.Data + "-->"
|
return "<!--" + EscapeString(t.Data) + "-->"
|
||||||
case DoctypeToken:
|
case DoctypeToken:
|
||||||
return "<!DOCTYPE " + t.Data + ">"
|
return "<!DOCTYPE " + EscapeString(t.Data) + ">"
|
||||||
}
|
}
|
||||||
return "Invalid(" + strconv.Itoa(int(t.Type)) + ")"
|
return "Invalid(" + strconv.Itoa(int(t.Type)) + ")"
|
||||||
}
|
}
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/net/http/httpguts/httplex.go
generated
vendored
4
vendor/golang.org/x/net/http/httpguts/httplex.go
generated
vendored
|
|
@ -173,11 +173,13 @@ func tokenEqual(t1, t2 string) bool {
|
||||||
|
|
||||||
// isLWS reports whether b is linear white space, according
|
// isLWS reports whether b is linear white space, according
|
||||||
// to http://www.w3.org/Protocols/rfc2616/rfc2616-sec2.html#sec2.2
|
// to http://www.w3.org/Protocols/rfc2616/rfc2616-sec2.html#sec2.2
|
||||||
|
//
|
||||||
// LWS = [CRLF] 1*( SP | HT )
|
// LWS = [CRLF] 1*( SP | HT )
|
||||||
func isLWS(b byte) bool { return b == ' ' || b == '\t' }
|
func isLWS(b byte) bool { return b == ' ' || b == '\t' }
|
||||||
|
|
||||||
// isCTL reports whether b is a control byte, according
|
// isCTL reports whether b is a control byte, according
|
||||||
// to http://www.w3.org/Protocols/rfc2616/rfc2616-sec2.html#sec2.2
|
// to http://www.w3.org/Protocols/rfc2616/rfc2616-sec2.html#sec2.2
|
||||||
|
//
|
||||||
// CTL = <any US-ASCII control character
|
// CTL = <any US-ASCII control character
|
||||||
// (octets 0 - 31) and DEL (127)>
|
// (octets 0 - 31) and DEL (127)>
|
||||||
func isCTL(b byte) bool {
|
func isCTL(b byte) bool {
|
||||||
|
|
@ -190,6 +192,7 @@ func isCTL(b byte) bool {
|
||||||
// letters are not allowed.
|
// letters are not allowed.
|
||||||
//
|
//
|
||||||
// RFC 7230 says:
|
// RFC 7230 says:
|
||||||
|
//
|
||||||
// header-field = field-name ":" OWS field-value OWS
|
// header-field = field-name ":" OWS field-value OWS
|
||||||
// field-name = token
|
// field-name = token
|
||||||
// token = 1*tchar
|
// token = 1*tchar
|
||||||
|
|
@ -282,6 +285,7 @@ var validHostByte = [256]bool{
|
||||||
// (octets 0 - 31) and DEL (127)>
|
// (octets 0 - 31) and DEL (127)>
|
||||||
//
|
//
|
||||||
// RFC 7230 says:
|
// RFC 7230 says:
|
||||||
|
//
|
||||||
// field-value = *( field-content / obs-fold )
|
// field-value = *( field-content / obs-fold )
|
||||||
// obj-fold = N/A to http2, and deprecated
|
// obj-fold = N/A to http2, and deprecated
|
||||||
// field-content = field-vchar [ 1*( SP / HTAB ) field-vchar ]
|
// field-content = field-vchar [ 1*( SP / HTAB ) field-vchar ]
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/net/http2/client_conn_pool.go
generated
vendored
3
vendor/golang.org/x/net/http2/client_conn_pool.go
generated
vendored
|
|
@ -139,7 +139,6 @@ func (p *clientConnPool) getStartDialLocked(ctx context.Context, addr string) *d
|
||||||
func (c *dialCall) dial(ctx context.Context, addr string) {
|
func (c *dialCall) dial(ctx context.Context, addr string) {
|
||||||
const singleUse = false // shared conn
|
const singleUse = false // shared conn
|
||||||
c.res, c.err = c.p.t.dialClientConn(ctx, addr, singleUse)
|
c.res, c.err = c.p.t.dialClientConn(ctx, addr, singleUse)
|
||||||
close(c.done)
|
|
||||||
|
|
||||||
c.p.mu.Lock()
|
c.p.mu.Lock()
|
||||||
delete(c.p.dialing, addr)
|
delete(c.p.dialing, addr)
|
||||||
|
|
@ -147,6 +146,8 @@ func (c *dialCall) dial(ctx context.Context, addr string) {
|
||||||
c.p.addConnLocked(addr, c.res)
|
c.p.addConnLocked(addr, c.res)
|
||||||
}
|
}
|
||||||
c.p.mu.Unlock()
|
c.p.mu.Unlock()
|
||||||
|
|
||||||
|
close(c.done)
|
||||||
}
|
}
|
||||||
|
|
||||||
// addConnIfNeeded makes a NewClientConn out of c if a connection for key doesn't
|
// addConnIfNeeded makes a NewClientConn out of c if a connection for key doesn't
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/net/http2/errors.go
generated
vendored
2
vendor/golang.org/x/net/http2/errors.go
generated
vendored
|
|
@ -136,7 +136,7 @@ func (e headerFieldNameError) Error() string {
|
||||||
type headerFieldValueError string
|
type headerFieldValueError string
|
||||||
|
|
||||||
func (e headerFieldValueError) Error() string {
|
func (e headerFieldValueError) Error() string {
|
||||||
return fmt.Sprintf("invalid header field value %q", string(e))
|
return fmt.Sprintf("invalid header field value for %q", string(e))
|
||||||
}
|
}
|
||||||
|
|
||||||
var (
|
var (
|
||||||
|
|
|
||||||
25
vendor/golang.org/x/net/http2/frame.go
generated
vendored
25
vendor/golang.org/x/net/http2/frame.go
generated
vendored
|
|
@ -23,7 +23,7 @@ const frameHeaderLen = 9
|
||||||
var padZeros = make([]byte, 255) // zeros for padding
|
var padZeros = make([]byte, 255) // zeros for padding
|
||||||
|
|
||||||
// A FrameType is a registered frame type as defined in
|
// A FrameType is a registered frame type as defined in
|
||||||
// http://http2.github.io/http2-spec/#rfc.section.11.2
|
// https://httpwg.org/specs/rfc7540.html#rfc.section.11.2
|
||||||
type FrameType uint8
|
type FrameType uint8
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
|
@ -146,7 +146,7 @@ func typeFrameParser(t FrameType) frameParser {
|
||||||
|
|
||||||
// A FrameHeader is the 9 byte header of all HTTP/2 frames.
|
// A FrameHeader is the 9 byte header of all HTTP/2 frames.
|
||||||
//
|
//
|
||||||
// See http://http2.github.io/http2-spec/#FrameHeader
|
// See https://httpwg.org/specs/rfc7540.html#FrameHeader
|
||||||
type FrameHeader struct {
|
type FrameHeader struct {
|
||||||
valid bool // caller can access []byte fields in the Frame
|
valid bool // caller can access []byte fields in the Frame
|
||||||
|
|
||||||
|
|
@ -575,7 +575,7 @@ func (fr *Framer) checkFrameOrder(f Frame) error {
|
||||||
|
|
||||||
// A DataFrame conveys arbitrary, variable-length sequences of octets
|
// A DataFrame conveys arbitrary, variable-length sequences of octets
|
||||||
// associated with a stream.
|
// associated with a stream.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.1
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.1
|
||||||
type DataFrame struct {
|
type DataFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
data []byte
|
data []byte
|
||||||
|
|
@ -698,7 +698,7 @@ func (f *Framer) WriteDataPadded(streamID uint32, endStream bool, data, pad []by
|
||||||
// endpoints communicate, such as preferences and constraints on peer
|
// endpoints communicate, such as preferences and constraints on peer
|
||||||
// behavior.
|
// behavior.
|
||||||
//
|
//
|
||||||
// See http://http2.github.io/http2-spec/#SETTINGS
|
// See https://httpwg.org/specs/rfc7540.html#SETTINGS
|
||||||
type SettingsFrame struct {
|
type SettingsFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
p []byte
|
p []byte
|
||||||
|
|
@ -837,7 +837,7 @@ func (f *Framer) WriteSettingsAck() error {
|
||||||
// A PingFrame is a mechanism for measuring a minimal round trip time
|
// A PingFrame is a mechanism for measuring a minimal round trip time
|
||||||
// from the sender, as well as determining whether an idle connection
|
// from the sender, as well as determining whether an idle connection
|
||||||
// is still functional.
|
// is still functional.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.7
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.7
|
||||||
type PingFrame struct {
|
type PingFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
Data [8]byte
|
Data [8]byte
|
||||||
|
|
@ -870,7 +870,7 @@ func (f *Framer) WritePing(ack bool, data [8]byte) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// A GoAwayFrame informs the remote peer to stop creating streams on this connection.
|
// A GoAwayFrame informs the remote peer to stop creating streams on this connection.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.8
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.8
|
||||||
type GoAwayFrame struct {
|
type GoAwayFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
LastStreamID uint32
|
LastStreamID uint32
|
||||||
|
|
@ -934,7 +934,7 @@ func parseUnknownFrame(_ *frameCache, fh FrameHeader, countError func(string), p
|
||||||
}
|
}
|
||||||
|
|
||||||
// A WindowUpdateFrame is used to implement flow control.
|
// A WindowUpdateFrame is used to implement flow control.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.9
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.9
|
||||||
type WindowUpdateFrame struct {
|
type WindowUpdateFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
Increment uint32 // never read with high bit set
|
Increment uint32 // never read with high bit set
|
||||||
|
|
@ -1123,7 +1123,7 @@ func (f *Framer) WriteHeaders(p HeadersFrameParam) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// A PriorityFrame specifies the sender-advised priority of a stream.
|
// A PriorityFrame specifies the sender-advised priority of a stream.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.3
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.3
|
||||||
type PriorityFrame struct {
|
type PriorityFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
PriorityParam
|
PriorityParam
|
||||||
|
|
@ -1193,7 +1193,7 @@ func (f *Framer) WritePriority(streamID uint32, p PriorityParam) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// A RSTStreamFrame allows for abnormal termination of a stream.
|
// A RSTStreamFrame allows for abnormal termination of a stream.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.4
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.4
|
||||||
type RSTStreamFrame struct {
|
type RSTStreamFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
ErrCode ErrCode
|
ErrCode ErrCode
|
||||||
|
|
@ -1225,7 +1225,7 @@ func (f *Framer) WriteRSTStream(streamID uint32, code ErrCode) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// A ContinuationFrame is used to continue a sequence of header block fragments.
|
// A ContinuationFrame is used to continue a sequence of header block fragments.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.10
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.10
|
||||||
type ContinuationFrame struct {
|
type ContinuationFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
headerFragBuf []byte
|
headerFragBuf []byte
|
||||||
|
|
@ -1266,7 +1266,7 @@ func (f *Framer) WriteContinuation(streamID uint32, endHeaders bool, headerBlock
|
||||||
}
|
}
|
||||||
|
|
||||||
// A PushPromiseFrame is used to initiate a server stream.
|
// A PushPromiseFrame is used to initiate a server stream.
|
||||||
// See http://http2.github.io/http2-spec/#rfc.section.6.6
|
// See https://httpwg.org/specs/rfc7540.html#rfc.section.6.6
|
||||||
type PushPromiseFrame struct {
|
type PushPromiseFrame struct {
|
||||||
FrameHeader
|
FrameHeader
|
||||||
PromiseID uint32
|
PromiseID uint32
|
||||||
|
|
@ -1532,7 +1532,8 @@ func (fr *Framer) readMetaFrame(hf *HeadersFrame) (*MetaHeadersFrame, error) {
|
||||||
fr.debugReadLoggerf("http2: decoded hpack field %+v", hf)
|
fr.debugReadLoggerf("http2: decoded hpack field %+v", hf)
|
||||||
}
|
}
|
||||||
if !httpguts.ValidHeaderFieldValue(hf.Value) {
|
if !httpguts.ValidHeaderFieldValue(hf.Value) {
|
||||||
invalid = headerFieldValueError(hf.Value)
|
// Don't include the value in the error, because it may be sensitive.
|
||||||
|
invalid = headerFieldValueError(hf.Name)
|
||||||
}
|
}
|
||||||
isPseudo := strings.HasPrefix(hf.Name, ":")
|
isPseudo := strings.HasPrefix(hf.Name, ":")
|
||||||
if isPseudo {
|
if isPseudo {
|
||||||
|
|
|
||||||
17
vendor/golang.org/x/net/http2/go118.go
generated
vendored
Normal file
17
vendor/golang.org/x/net/http2/go118.go
generated
vendored
Normal file
|
|
@ -0,0 +1,17 @@
|
||||||
|
// Copyright 2021 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
//go:build go1.18
|
||||||
|
// +build go1.18
|
||||||
|
|
||||||
|
package http2
|
||||||
|
|
||||||
|
import (
|
||||||
|
"crypto/tls"
|
||||||
|
"net"
|
||||||
|
)
|
||||||
|
|
||||||
|
func tlsUnderlyingConn(tc *tls.Conn) net.Conn {
|
||||||
|
return tc.NetConn()
|
||||||
|
}
|
||||||
2
vendor/golang.org/x/net/http2/hpack/encode.go
generated
vendored
2
vendor/golang.org/x/net/http2/hpack/encode.go
generated
vendored
|
|
@ -191,7 +191,7 @@ func appendTableSize(dst []byte, v uint32) []byte {
|
||||||
// bit prefix, to dst and returns the extended buffer.
|
// bit prefix, to dst and returns the extended buffer.
|
||||||
//
|
//
|
||||||
// See
|
// See
|
||||||
// http://http2.github.io/http2-spec/compression.html#integer.representation
|
// https://httpwg.org/specs/rfc7541.html#integer.representation
|
||||||
func appendVarInt(dst []byte, n byte, i uint64) []byte {
|
func appendVarInt(dst []byte, n byte, i uint64) []byte {
|
||||||
k := uint64((1 << n) - 1)
|
k := uint64((1 << n) - 1)
|
||||||
if i < k {
|
if i < k {
|
||||||
|
|
|
||||||
16
vendor/golang.org/x/net/http2/hpack/hpack.go
generated
vendored
16
vendor/golang.org/x/net/http2/hpack/hpack.go
generated
vendored
|
|
@ -59,7 +59,7 @@ func (hf HeaderField) String() string {
|
||||||
|
|
||||||
// Size returns the size of an entry per RFC 7541 section 4.1.
|
// Size returns the size of an entry per RFC 7541 section 4.1.
|
||||||
func (hf HeaderField) Size() uint32 {
|
func (hf HeaderField) Size() uint32 {
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.4.1
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.4.1
|
||||||
// "The size of the dynamic table is the sum of the size of
|
// "The size of the dynamic table is the sum of the size of
|
||||||
// its entries. The size of an entry is the sum of its name's
|
// its entries. The size of an entry is the sum of its name's
|
||||||
// length in octets (as defined in Section 5.2), its value's
|
// length in octets (as defined in Section 5.2), its value's
|
||||||
|
|
@ -158,7 +158,7 @@ func (d *Decoder) SetAllowedMaxDynamicTableSize(v uint32) {
|
||||||
}
|
}
|
||||||
|
|
||||||
type dynamicTable struct {
|
type dynamicTable struct {
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.2.3.2
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.2.3.2
|
||||||
table headerFieldTable
|
table headerFieldTable
|
||||||
size uint32 // in bytes
|
size uint32 // in bytes
|
||||||
maxSize uint32 // current maxSize
|
maxSize uint32 // current maxSize
|
||||||
|
|
@ -307,27 +307,27 @@ func (d *Decoder) parseHeaderFieldRepr() error {
|
||||||
case b&128 != 0:
|
case b&128 != 0:
|
||||||
// Indexed representation.
|
// Indexed representation.
|
||||||
// High bit set?
|
// High bit set?
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.6.1
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.6.1
|
||||||
return d.parseFieldIndexed()
|
return d.parseFieldIndexed()
|
||||||
case b&192 == 64:
|
case b&192 == 64:
|
||||||
// 6.2.1 Literal Header Field with Incremental Indexing
|
// 6.2.1 Literal Header Field with Incremental Indexing
|
||||||
// 0b10xxxxxx: top two bits are 10
|
// 0b10xxxxxx: top two bits are 10
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.6.2.1
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.6.2.1
|
||||||
return d.parseFieldLiteral(6, indexedTrue)
|
return d.parseFieldLiteral(6, indexedTrue)
|
||||||
case b&240 == 0:
|
case b&240 == 0:
|
||||||
// 6.2.2 Literal Header Field without Indexing
|
// 6.2.2 Literal Header Field without Indexing
|
||||||
// 0b0000xxxx: top four bits are 0000
|
// 0b0000xxxx: top four bits are 0000
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.6.2.2
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.6.2.2
|
||||||
return d.parseFieldLiteral(4, indexedFalse)
|
return d.parseFieldLiteral(4, indexedFalse)
|
||||||
case b&240 == 16:
|
case b&240 == 16:
|
||||||
// 6.2.3 Literal Header Field never Indexed
|
// 6.2.3 Literal Header Field never Indexed
|
||||||
// 0b0001xxxx: top four bits are 0001
|
// 0b0001xxxx: top four bits are 0001
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.6.2.3
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.6.2.3
|
||||||
return d.parseFieldLiteral(4, indexedNever)
|
return d.parseFieldLiteral(4, indexedNever)
|
||||||
case b&224 == 32:
|
case b&224 == 32:
|
||||||
// 6.3 Dynamic Table Size Update
|
// 6.3 Dynamic Table Size Update
|
||||||
// Top three bits are '001'.
|
// Top three bits are '001'.
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.6.3
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.6.3
|
||||||
return d.parseDynamicTableSizeUpdate()
|
return d.parseDynamicTableSizeUpdate()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -420,7 +420,7 @@ var errVarintOverflow = DecodingError{errors.New("varint integer overflow")}
|
||||||
|
|
||||||
// readVarInt reads an unsigned variable length integer off the
|
// readVarInt reads an unsigned variable length integer off the
|
||||||
// beginning of p. n is the parameter as described in
|
// beginning of p. n is the parameter as described in
|
||||||
// http://http2.github.io/http2-spec/compression.html#rfc.section.5.1.
|
// https://httpwg.org/specs/rfc7541.html#rfc.section.5.1.
|
||||||
//
|
//
|
||||||
// n must always be between 1 and 8.
|
// n must always be between 1 and 8.
|
||||||
//
|
//
|
||||||
|
|
|
||||||
85
vendor/golang.org/x/net/http2/hpack/huffman.go
generated
vendored
85
vendor/golang.org/x/net/http2/hpack/huffman.go
generated
vendored
|
|
@ -169,25 +169,50 @@ func buildRootHuffmanNode() {
|
||||||
// AppendHuffmanString appends s, as encoded in Huffman codes, to dst
|
// AppendHuffmanString appends s, as encoded in Huffman codes, to dst
|
||||||
// and returns the extended buffer.
|
// and returns the extended buffer.
|
||||||
func AppendHuffmanString(dst []byte, s string) []byte {
|
func AppendHuffmanString(dst []byte, s string) []byte {
|
||||||
rembits := uint8(8)
|
// This relies on the maximum huffman code length being 30 (See tables.go huffmanCodeLen array)
|
||||||
|
// So if a uint64 buffer has less than 32 valid bits can always accommodate another huffmanCode.
|
||||||
|
var (
|
||||||
|
x uint64 // buffer
|
||||||
|
n uint // number valid of bits present in x
|
||||||
|
)
|
||||||
for i := 0; i < len(s); i++ {
|
for i := 0; i < len(s); i++ {
|
||||||
if rembits == 8 {
|
c := s[i]
|
||||||
dst = append(dst, 0)
|
n += uint(huffmanCodeLen[c])
|
||||||
|
x <<= huffmanCodeLen[c] % 64
|
||||||
|
x |= uint64(huffmanCodes[c])
|
||||||
|
if n >= 32 {
|
||||||
|
n %= 32 // Normally would be -= 32 but %= 32 informs compiler 0 <= n <= 31 for upcoming shift
|
||||||
|
y := uint32(x >> n) // Compiler doesn't combine memory writes if y isn't uint32
|
||||||
|
dst = append(dst, byte(y>>24), byte(y>>16), byte(y>>8), byte(y))
|
||||||
}
|
}
|
||||||
dst, rembits = appendByteToHuffmanCode(dst, rembits, s[i])
|
|
||||||
}
|
}
|
||||||
|
// Add padding bits if necessary
|
||||||
if rembits < 8 {
|
if over := n % 8; over > 0 {
|
||||||
// special EOS symbol
|
const (
|
||||||
code := uint32(0x3fffffff)
|
eosCode = 0x3fffffff
|
||||||
nbits := uint8(30)
|
eosNBits = 30
|
||||||
|
eosPadByte = eosCode >> (eosNBits - 8)
|
||||||
t := uint8(code >> (nbits - rembits))
|
)
|
||||||
dst[len(dst)-1] |= t
|
pad := 8 - over
|
||||||
|
x = (x << pad) | (eosPadByte >> over)
|
||||||
|
n += pad // 8 now divides into n exactly
|
||||||
}
|
}
|
||||||
|
// n in (0, 8, 16, 24, 32)
|
||||||
|
switch n / 8 {
|
||||||
|
case 0:
|
||||||
return dst
|
return dst
|
||||||
|
case 1:
|
||||||
|
return append(dst, byte(x))
|
||||||
|
case 2:
|
||||||
|
y := uint16(x)
|
||||||
|
return append(dst, byte(y>>8), byte(y))
|
||||||
|
case 3:
|
||||||
|
y := uint16(x >> 8)
|
||||||
|
return append(dst, byte(y>>8), byte(y), byte(x))
|
||||||
|
}
|
||||||
|
// case 4:
|
||||||
|
y := uint32(x)
|
||||||
|
return append(dst, byte(y>>24), byte(y>>16), byte(y>>8), byte(y))
|
||||||
}
|
}
|
||||||
|
|
||||||
// HuffmanEncodeLength returns the number of bytes required to encode
|
// HuffmanEncodeLength returns the number of bytes required to encode
|
||||||
|
|
@ -199,35 +224,3 @@ func HuffmanEncodeLength(s string) uint64 {
|
||||||
}
|
}
|
||||||
return (n + 7) / 8
|
return (n + 7) / 8
|
||||||
}
|
}
|
||||||
|
|
||||||
// appendByteToHuffmanCode appends Huffman code for c to dst and
|
|
||||||
// returns the extended buffer and the remaining bits in the last
|
|
||||||
// element. The appending is not byte aligned and the remaining bits
|
|
||||||
// in the last element of dst is given in rembits.
|
|
||||||
func appendByteToHuffmanCode(dst []byte, rembits uint8, c byte) ([]byte, uint8) {
|
|
||||||
code := huffmanCodes[c]
|
|
||||||
nbits := huffmanCodeLen[c]
|
|
||||||
|
|
||||||
for {
|
|
||||||
if rembits > nbits {
|
|
||||||
t := uint8(code << (rembits - nbits))
|
|
||||||
dst[len(dst)-1] |= t
|
|
||||||
rembits -= nbits
|
|
||||||
break
|
|
||||||
}
|
|
||||||
|
|
||||||
t := uint8(code >> (nbits - rembits))
|
|
||||||
dst[len(dst)-1] |= t
|
|
||||||
|
|
||||||
nbits -= rembits
|
|
||||||
rembits = 8
|
|
||||||
|
|
||||||
if nbits == 0 {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
|
|
||||||
dst = append(dst, 0)
|
|
||||||
}
|
|
||||||
|
|
||||||
return dst, rembits
|
|
||||||
}
|
|
||||||
|
|
|
||||||
14
vendor/golang.org/x/net/http2/http2.go
generated
vendored
14
vendor/golang.org/x/net/http2/http2.go
generated
vendored
|
|
@ -13,7 +13,6 @@
|
||||||
// See https://http2.github.io/ for more information on HTTP/2.
|
// See https://http2.github.io/ for more information on HTTP/2.
|
||||||
//
|
//
|
||||||
// See https://http2.golang.org/ for a test server running this code.
|
// See https://http2.golang.org/ for a test server running this code.
|
||||||
//
|
|
||||||
package http2 // import "golang.org/x/net/http2"
|
package http2 // import "golang.org/x/net/http2"
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
|
@ -56,14 +55,14 @@ const (
|
||||||
ClientPreface = "PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n"
|
ClientPreface = "PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n"
|
||||||
|
|
||||||
// SETTINGS_MAX_FRAME_SIZE default
|
// SETTINGS_MAX_FRAME_SIZE default
|
||||||
// http://http2.github.io/http2-spec/#rfc.section.6.5.2
|
// https://httpwg.org/specs/rfc7540.html#rfc.section.6.5.2
|
||||||
initialMaxFrameSize = 16384
|
initialMaxFrameSize = 16384
|
||||||
|
|
||||||
// NextProtoTLS is the NPN/ALPN protocol negotiated during
|
// NextProtoTLS is the NPN/ALPN protocol negotiated during
|
||||||
// HTTP/2's TLS setup.
|
// HTTP/2's TLS setup.
|
||||||
NextProtoTLS = "h2"
|
NextProtoTLS = "h2"
|
||||||
|
|
||||||
// http://http2.github.io/http2-spec/#SettingValues
|
// https://httpwg.org/specs/rfc7540.html#SettingValues
|
||||||
initialHeaderTableSize = 4096
|
initialHeaderTableSize = 4096
|
||||||
|
|
||||||
initialWindowSize = 65535 // 6.9.2 Initial Flow Control Window Size
|
initialWindowSize = 65535 // 6.9.2 Initial Flow Control Window Size
|
||||||
|
|
@ -112,7 +111,7 @@ func (st streamState) String() string {
|
||||||
// Setting is a setting parameter: which setting it is, and its value.
|
// Setting is a setting parameter: which setting it is, and its value.
|
||||||
type Setting struct {
|
type Setting struct {
|
||||||
// ID is which setting is being set.
|
// ID is which setting is being set.
|
||||||
// See http://http2.github.io/http2-spec/#SettingValues
|
// See https://httpwg.org/specs/rfc7540.html#SettingFormat
|
||||||
ID SettingID
|
ID SettingID
|
||||||
|
|
||||||
// Val is the value.
|
// Val is the value.
|
||||||
|
|
@ -144,7 +143,7 @@ func (s Setting) Valid() error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// A SettingID is an HTTP/2 setting as defined in
|
// A SettingID is an HTTP/2 setting as defined in
|
||||||
// http://http2.github.io/http2-spec/#iana-settings
|
// https://httpwg.org/specs/rfc7540.html#iana-settings
|
||||||
type SettingID uint16
|
type SettingID uint16
|
||||||
|
|
||||||
const (
|
const (
|
||||||
|
|
@ -176,6 +175,7 @@ func (s SettingID) String() string {
|
||||||
// name (key). See httpguts.ValidHeaderName for the base rules.
|
// name (key). See httpguts.ValidHeaderName for the base rules.
|
||||||
//
|
//
|
||||||
// Further, http2 says:
|
// Further, http2 says:
|
||||||
|
//
|
||||||
// "Just as in HTTP/1.x, header field names are strings of ASCII
|
// "Just as in HTTP/1.x, header field names are strings of ASCII
|
||||||
// characters that are compared in a case-insensitive
|
// characters that are compared in a case-insensitive
|
||||||
// fashion. However, header field names MUST be converted to
|
// fashion. However, header field names MUST be converted to
|
||||||
|
|
@ -365,8 +365,8 @@ func (s *sorter) SortStrings(ss []string) {
|
||||||
// validPseudoPath reports whether v is a valid :path pseudo-header
|
// validPseudoPath reports whether v is a valid :path pseudo-header
|
||||||
// value. It must be either:
|
// value. It must be either:
|
||||||
//
|
//
|
||||||
// *) a non-empty string starting with '/'
|
// - a non-empty string starting with '/'
|
||||||
// *) the string '*', for OPTIONS requests.
|
// - the string '*', for OPTIONS requests.
|
||||||
//
|
//
|
||||||
// For now this is only used a quick check for deciding when to clean
|
// For now this is only used a quick check for deciding when to clean
|
||||||
// up Opaque URLs before sending requests from the Transport.
|
// up Opaque URLs before sending requests from the Transport.
|
||||||
|
|
|
||||||
17
vendor/golang.org/x/net/http2/not_go118.go
generated
vendored
Normal file
17
vendor/golang.org/x/net/http2/not_go118.go
generated
vendored
Normal file
|
|
@ -0,0 +1,17 @@
|
||||||
|
// Copyright 2021 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
//go:build !go1.18
|
||||||
|
// +build !go1.18
|
||||||
|
|
||||||
|
package http2
|
||||||
|
|
||||||
|
import (
|
||||||
|
"crypto/tls"
|
||||||
|
"net"
|
||||||
|
)
|
||||||
|
|
||||||
|
func tlsUnderlyingConn(tc *tls.Conn) net.Conn {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
181
vendor/golang.org/x/net/http2/server.go
generated
vendored
181
vendor/golang.org/x/net/http2/server.go
generated
vendored
|
|
@ -143,7 +143,7 @@ type Server struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Server) initialConnRecvWindowSize() int32 {
|
func (s *Server) initialConnRecvWindowSize() int32 {
|
||||||
if s.MaxUploadBufferPerConnection > initialWindowSize {
|
if s.MaxUploadBufferPerConnection >= initialWindowSize {
|
||||||
return s.MaxUploadBufferPerConnection
|
return s.MaxUploadBufferPerConnection
|
||||||
}
|
}
|
||||||
return 1 << 20
|
return 1 << 20
|
||||||
|
|
@ -315,6 +315,20 @@ type ServeConnOpts struct {
|
||||||
// requests. If nil, BaseConfig.Handler is used. If BaseConfig
|
// requests. If nil, BaseConfig.Handler is used. If BaseConfig
|
||||||
// or BaseConfig.Handler is nil, http.DefaultServeMux is used.
|
// or BaseConfig.Handler is nil, http.DefaultServeMux is used.
|
||||||
Handler http.Handler
|
Handler http.Handler
|
||||||
|
|
||||||
|
// UpgradeRequest is an initial request received on a connection
|
||||||
|
// undergoing an h2c upgrade. The request body must have been
|
||||||
|
// completely read from the connection before calling ServeConn,
|
||||||
|
// and the 101 Switching Protocols response written.
|
||||||
|
UpgradeRequest *http.Request
|
||||||
|
|
||||||
|
// Settings is the decoded contents of the HTTP2-Settings header
|
||||||
|
// in an h2c upgrade request.
|
||||||
|
Settings []byte
|
||||||
|
|
||||||
|
// SawClientPreface is set if the HTTP/2 connection preface
|
||||||
|
// has already been read from the connection.
|
||||||
|
SawClientPreface bool
|
||||||
}
|
}
|
||||||
|
|
||||||
func (o *ServeConnOpts) context() context.Context {
|
func (o *ServeConnOpts) context() context.Context {
|
||||||
|
|
@ -383,6 +397,7 @@ func (s *Server) ServeConn(c net.Conn, opts *ServeConnOpts) {
|
||||||
headerTableSize: initialHeaderTableSize,
|
headerTableSize: initialHeaderTableSize,
|
||||||
serveG: newGoroutineLock(),
|
serveG: newGoroutineLock(),
|
||||||
pushEnabled: true,
|
pushEnabled: true,
|
||||||
|
sawClientPreface: opts.SawClientPreface,
|
||||||
}
|
}
|
||||||
|
|
||||||
s.state.registerConn(sc)
|
s.state.registerConn(sc)
|
||||||
|
|
@ -400,7 +415,7 @@ func (s *Server) ServeConn(c net.Conn, opts *ServeConnOpts) {
|
||||||
if s.NewWriteScheduler != nil {
|
if s.NewWriteScheduler != nil {
|
||||||
sc.writeSched = s.NewWriteScheduler()
|
sc.writeSched = s.NewWriteScheduler()
|
||||||
} else {
|
} else {
|
||||||
sc.writeSched = NewRandomWriteScheduler()
|
sc.writeSched = NewPriorityWriteScheduler(nil)
|
||||||
}
|
}
|
||||||
|
|
||||||
// These start at the RFC-specified defaults. If there is a higher
|
// These start at the RFC-specified defaults. If there is a higher
|
||||||
|
|
@ -465,9 +480,27 @@ func (s *Server) ServeConn(c net.Conn, opts *ServeConnOpts) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if opts.Settings != nil {
|
||||||
|
fr := &SettingsFrame{
|
||||||
|
FrameHeader: FrameHeader{valid: true},
|
||||||
|
p: opts.Settings,
|
||||||
|
}
|
||||||
|
if err := fr.ForeachSetting(sc.processSetting); err != nil {
|
||||||
|
sc.rejectConn(ErrCodeProtocol, "invalid settings")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
opts.Settings = nil
|
||||||
|
}
|
||||||
|
|
||||||
if hook := testHookGetServerConn; hook != nil {
|
if hook := testHookGetServerConn; hook != nil {
|
||||||
hook(sc)
|
hook(sc)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if opts.UpgradeRequest != nil {
|
||||||
|
sc.upgradeRequest(opts.UpgradeRequest)
|
||||||
|
opts.UpgradeRequest = nil
|
||||||
|
}
|
||||||
|
|
||||||
sc.serve()
|
sc.serve()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -512,6 +545,7 @@ type serverConn struct {
|
||||||
// Everything following is owned by the serve loop; use serveG.check():
|
// Everything following is owned by the serve loop; use serveG.check():
|
||||||
serveG goroutineLock // used to verify funcs are on serve()
|
serveG goroutineLock // used to verify funcs are on serve()
|
||||||
pushEnabled bool
|
pushEnabled bool
|
||||||
|
sawClientPreface bool // preface has already been read, used in h2c upgrade
|
||||||
sawFirstSettings bool // got the initial SETTINGS frame after the preface
|
sawFirstSettings bool // got the initial SETTINGS frame after the preface
|
||||||
needToSendSettingsAck bool
|
needToSendSettingsAck bool
|
||||||
unackedSettings int // how many SETTINGS have we sent without ACKs?
|
unackedSettings int // how many SETTINGS have we sent without ACKs?
|
||||||
|
|
@ -719,7 +753,15 @@ func (sc *serverConn) canonicalHeader(v string) string {
|
||||||
sc.canonHeader = make(map[string]string)
|
sc.canonHeader = make(map[string]string)
|
||||||
}
|
}
|
||||||
cv = http.CanonicalHeaderKey(v)
|
cv = http.CanonicalHeaderKey(v)
|
||||||
|
// maxCachedCanonicalHeaders is an arbitrarily-chosen limit on the number of
|
||||||
|
// entries in the canonHeader cache. This should be larger than the number
|
||||||
|
// of unique, uncommon header keys likely to be sent by the peer, while not
|
||||||
|
// so high as to permit unreasonable memory usage if the peer sends an unbounded
|
||||||
|
// number of unique header keys.
|
||||||
|
const maxCachedCanonicalHeaders = 32
|
||||||
|
if len(sc.canonHeader) < maxCachedCanonicalHeaders {
|
||||||
sc.canonHeader[v] = cv
|
sc.canonHeader[v] = cv
|
||||||
|
}
|
||||||
return cv
|
return cv
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -827,9 +869,7 @@ func (sc *serverConn) serve() {
|
||||||
|
|
||||||
// Each connection starts with initialWindowSize inflow tokens.
|
// Each connection starts with initialWindowSize inflow tokens.
|
||||||
// If a higher value is configured, we add more tokens.
|
// If a higher value is configured, we add more tokens.
|
||||||
if diff := sc.srv.initialConnRecvWindowSize() - initialWindowSize; diff > 0 {
|
sc.sendWindowUpdate(nil)
|
||||||
sc.sendWindowUpdate(nil, int(diff))
|
|
||||||
}
|
|
||||||
|
|
||||||
if err := sc.readPreface(); err != nil {
|
if err := sc.readPreface(); err != nil {
|
||||||
sc.condlogf(err, "http2: server: error reading preface from client %v: %v", sc.conn.RemoteAddr(), err)
|
sc.condlogf(err, "http2: server: error reading preface from client %v: %v", sc.conn.RemoteAddr(), err)
|
||||||
|
|
@ -966,6 +1006,9 @@ var errPrefaceTimeout = errors.New("timeout waiting for client preface")
|
||||||
// returns errPrefaceTimeout on timeout, or an error if the greeting
|
// returns errPrefaceTimeout on timeout, or an error if the greeting
|
||||||
// is invalid.
|
// is invalid.
|
||||||
func (sc *serverConn) readPreface() error {
|
func (sc *serverConn) readPreface() error {
|
||||||
|
if sc.sawClientPreface {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
errc := make(chan error, 1)
|
errc := make(chan error, 1)
|
||||||
go func() {
|
go func() {
|
||||||
// Read the client preface
|
// Read the client preface
|
||||||
|
|
@ -1326,6 +1369,9 @@ func (sc *serverConn) startGracefulShutdownInternal() {
|
||||||
func (sc *serverConn) goAway(code ErrCode) {
|
func (sc *serverConn) goAway(code ErrCode) {
|
||||||
sc.serveG.check()
|
sc.serveG.check()
|
||||||
if sc.inGoAway {
|
if sc.inGoAway {
|
||||||
|
if sc.goAwayCode == ErrCodeNo {
|
||||||
|
sc.goAwayCode = code
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
sc.inGoAway = true
|
sc.inGoAway = true
|
||||||
|
|
@ -1540,7 +1586,7 @@ func (sc *serverConn) closeStream(st *stream, err error) {
|
||||||
if p := st.body; p != nil {
|
if p := st.body; p != nil {
|
||||||
// Return any buffered unread bytes worth of conn-level flow control.
|
// Return any buffered unread bytes worth of conn-level flow control.
|
||||||
// See golang.org/issue/16481
|
// See golang.org/issue/16481
|
||||||
sc.sendWindowUpdate(nil, p.Len())
|
sc.sendWindowUpdate(nil)
|
||||||
|
|
||||||
p.CloseWithError(err)
|
p.CloseWithError(err)
|
||||||
}
|
}
|
||||||
|
|
@ -1688,7 +1734,7 @@ func (sc *serverConn) processData(f *DataFrame) error {
|
||||||
// sendWindowUpdate, which also schedules sending the
|
// sendWindowUpdate, which also schedules sending the
|
||||||
// frames.
|
// frames.
|
||||||
sc.inflow.take(int32(f.Length))
|
sc.inflow.take(int32(f.Length))
|
||||||
sc.sendWindowUpdate(nil, int(f.Length)) // conn-level
|
sc.sendWindowUpdate(nil) // conn-level
|
||||||
|
|
||||||
if st != nil && st.resetQueued {
|
if st != nil && st.resetQueued {
|
||||||
// Already have a stream error in flight. Don't send another.
|
// Already have a stream error in flight. Don't send another.
|
||||||
|
|
@ -1702,6 +1748,12 @@ func (sc *serverConn) processData(f *DataFrame) error {
|
||||||
|
|
||||||
// Sender sending more than they'd declared?
|
// Sender sending more than they'd declared?
|
||||||
if st.declBodyBytes != -1 && st.bodyBytes+int64(len(data)) > st.declBodyBytes {
|
if st.declBodyBytes != -1 && st.bodyBytes+int64(len(data)) > st.declBodyBytes {
|
||||||
|
if sc.inflow.available() < int32(f.Length) {
|
||||||
|
return sc.countError("data_flow", streamError(id, ErrCodeFlowControl))
|
||||||
|
}
|
||||||
|
sc.inflow.take(int32(f.Length))
|
||||||
|
sc.sendWindowUpdate(nil) // conn-level
|
||||||
|
|
||||||
st.body.CloseWithError(fmt.Errorf("sender tried to send more than declared Content-Length of %d bytes", st.declBodyBytes))
|
st.body.CloseWithError(fmt.Errorf("sender tried to send more than declared Content-Length of %d bytes", st.declBodyBytes))
|
||||||
// RFC 7540, sec 8.1.2.6: A request or response is also malformed if the
|
// RFC 7540, sec 8.1.2.6: A request or response is also malformed if the
|
||||||
// value of a content-length header field does not equal the sum of the
|
// value of a content-length header field does not equal the sum of the
|
||||||
|
|
@ -1718,7 +1770,7 @@ func (sc *serverConn) processData(f *DataFrame) error {
|
||||||
if len(data) > 0 {
|
if len(data) > 0 {
|
||||||
wrote, err := st.body.Write(data)
|
wrote, err := st.body.Write(data)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
sc.sendWindowUpdate(nil, int(f.Length)-wrote)
|
sc.sendWindowUpdate32(nil, int32(f.Length)-int32(wrote))
|
||||||
return sc.countError("body_write_err", streamError(id, ErrCodeStreamClosed))
|
return sc.countError("body_write_err", streamError(id, ErrCodeStreamClosed))
|
||||||
}
|
}
|
||||||
if wrote != len(data) {
|
if wrote != len(data) {
|
||||||
|
|
@ -1907,6 +1959,26 @@ func (sc *serverConn) processHeaders(f *MetaHeadersFrame) error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (sc *serverConn) upgradeRequest(req *http.Request) {
|
||||||
|
sc.serveG.check()
|
||||||
|
id := uint32(1)
|
||||||
|
sc.maxClientStreamID = id
|
||||||
|
st := sc.newStream(id, 0, stateHalfClosedRemote)
|
||||||
|
st.reqTrailer = req.Trailer
|
||||||
|
if st.reqTrailer != nil {
|
||||||
|
st.trailer = make(http.Header)
|
||||||
|
}
|
||||||
|
rw := sc.newResponseWriter(st, req)
|
||||||
|
|
||||||
|
// Disable any read deadline set by the net/http package
|
||||||
|
// prior to the upgrade.
|
||||||
|
if sc.hs.ReadTimeout != 0 {
|
||||||
|
sc.conn.SetReadDeadline(time.Time{})
|
||||||
|
}
|
||||||
|
|
||||||
|
go sc.runHandler(rw, req, sc.handler.ServeHTTP)
|
||||||
|
}
|
||||||
|
|
||||||
func (st *stream) processTrailerHeaders(f *MetaHeadersFrame) error {
|
func (st *stream) processTrailerHeaders(f *MetaHeadersFrame) error {
|
||||||
sc := st.sc
|
sc := st.sc
|
||||||
sc.serveG.check()
|
sc.serveG.check()
|
||||||
|
|
@ -2025,12 +2097,6 @@ func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*res
|
||||||
return nil, nil, sc.countError("bad_path_method", streamError(f.StreamID, ErrCodeProtocol))
|
return nil, nil, sc.countError("bad_path_method", streamError(f.StreamID, ErrCodeProtocol))
|
||||||
}
|
}
|
||||||
|
|
||||||
bodyOpen := !f.StreamEnded()
|
|
||||||
if rp.method == "HEAD" && bodyOpen {
|
|
||||||
// HEAD requests can't have bodies
|
|
||||||
return nil, nil, sc.countError("head_body", streamError(f.StreamID, ErrCodeProtocol))
|
|
||||||
}
|
|
||||||
|
|
||||||
rp.header = make(http.Header)
|
rp.header = make(http.Header)
|
||||||
for _, hf := range f.RegularFields() {
|
for _, hf := range f.RegularFields() {
|
||||||
rp.header.Add(sc.canonicalHeader(hf.Name), hf.Value)
|
rp.header.Add(sc.canonicalHeader(hf.Name), hf.Value)
|
||||||
|
|
@ -2043,6 +2109,7 @@ func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*res
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
bodyOpen := !f.StreamEnded()
|
||||||
if bodyOpen {
|
if bodyOpen {
|
||||||
if vv, ok := rp.header["Content-Length"]; ok {
|
if vv, ok := rp.header["Content-Length"]; ok {
|
||||||
if cl, err := strconv.ParseUint(vv[0], 10, 63); err == nil {
|
if cl, err := strconv.ParseUint(vv[0], 10, 63); err == nil {
|
||||||
|
|
@ -2137,6 +2204,11 @@ func (sc *serverConn) newWriterAndRequestNoBody(st *stream, rp requestParam) (*r
|
||||||
}
|
}
|
||||||
req = req.WithContext(st.ctx)
|
req = req.WithContext(st.ctx)
|
||||||
|
|
||||||
|
rw := sc.newResponseWriter(st, req)
|
||||||
|
return rw, req, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (sc *serverConn) newResponseWriter(st *stream, req *http.Request) *responseWriter {
|
||||||
rws := responseWriterStatePool.Get().(*responseWriterState)
|
rws := responseWriterStatePool.Get().(*responseWriterState)
|
||||||
bwSave := rws.bw
|
bwSave := rws.bw
|
||||||
*rws = responseWriterState{} // zero all the fields
|
*rws = responseWriterState{} // zero all the fields
|
||||||
|
|
@ -2145,10 +2217,7 @@ func (sc *serverConn) newWriterAndRequestNoBody(st *stream, rp requestParam) (*r
|
||||||
rws.bw.Reset(chunkWriter{rws})
|
rws.bw.Reset(chunkWriter{rws})
|
||||||
rws.stream = st
|
rws.stream = st
|
||||||
rws.req = req
|
rws.req = req
|
||||||
rws.body = body
|
return &responseWriter{rws: rws}
|
||||||
|
|
||||||
rw := &responseWriter{rws: rws}
|
|
||||||
return rw, req, nil
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Run on its own goroutine.
|
// Run on its own goroutine.
|
||||||
|
|
@ -2156,6 +2225,9 @@ func (sc *serverConn) runHandler(rw *responseWriter, req *http.Request, handler
|
||||||
didPanic := true
|
didPanic := true
|
||||||
defer func() {
|
defer func() {
|
||||||
rw.rws.stream.cancelCtx()
|
rw.rws.stream.cancelCtx()
|
||||||
|
if req.MultipartForm != nil {
|
||||||
|
req.MultipartForm.RemoveAll()
|
||||||
|
}
|
||||||
if didPanic {
|
if didPanic {
|
||||||
e := recover()
|
e := recover()
|
||||||
sc.writeFrameFromHandler(FrameWriteRequest{
|
sc.writeFrameFromHandler(FrameWriteRequest{
|
||||||
|
|
@ -2250,17 +2322,32 @@ func (sc *serverConn) noteBodyReadFromHandler(st *stream, n int, err error) {
|
||||||
|
|
||||||
func (sc *serverConn) noteBodyRead(st *stream, n int) {
|
func (sc *serverConn) noteBodyRead(st *stream, n int) {
|
||||||
sc.serveG.check()
|
sc.serveG.check()
|
||||||
sc.sendWindowUpdate(nil, n) // conn-level
|
sc.sendWindowUpdate(nil) // conn-level
|
||||||
if st.state != stateHalfClosedRemote && st.state != stateClosed {
|
if st.state != stateHalfClosedRemote && st.state != stateClosed {
|
||||||
// Don't send this WINDOW_UPDATE if the stream is closed
|
// Don't send this WINDOW_UPDATE if the stream is closed
|
||||||
// remotely.
|
// remotely.
|
||||||
sc.sendWindowUpdate(st, n)
|
sc.sendWindowUpdate(st)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// st may be nil for conn-level
|
// st may be nil for conn-level
|
||||||
func (sc *serverConn) sendWindowUpdate(st *stream, n int) {
|
func (sc *serverConn) sendWindowUpdate(st *stream) {
|
||||||
sc.serveG.check()
|
sc.serveG.check()
|
||||||
|
|
||||||
|
var n int32
|
||||||
|
if st == nil {
|
||||||
|
if avail, windowSize := sc.inflow.available(), sc.srv.initialConnRecvWindowSize(); avail > windowSize/2 {
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
n = windowSize - avail
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if avail, windowSize := st.inflow.available(), sc.srv.initialStreamRecvWindowSize(); avail > windowSize/2 {
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
n = windowSize - avail
|
||||||
|
}
|
||||||
|
}
|
||||||
// "The legal range for the increment to the flow control
|
// "The legal range for the increment to the flow control
|
||||||
// window is 1 to 2^31-1 (2,147,483,647) octets."
|
// window is 1 to 2^31-1 (2,147,483,647) octets."
|
||||||
// A Go Read call on 64-bit machines could in theory read
|
// A Go Read call on 64-bit machines could in theory read
|
||||||
|
|
@ -2308,17 +2395,18 @@ type requestBody struct {
|
||||||
_ incomparable
|
_ incomparable
|
||||||
stream *stream
|
stream *stream
|
||||||
conn *serverConn
|
conn *serverConn
|
||||||
closed bool // for use by Close only
|
closeOnce sync.Once // for use by Close only
|
||||||
sawEOF bool // for use by Read only
|
sawEOF bool // for use by Read only
|
||||||
pipe *pipe // non-nil if we have a HTTP entity message body
|
pipe *pipe // non-nil if we have a HTTP entity message body
|
||||||
needsContinue bool // need to send a 100-continue
|
needsContinue bool // need to send a 100-continue
|
||||||
}
|
}
|
||||||
|
|
||||||
func (b *requestBody) Close() error {
|
func (b *requestBody) Close() error {
|
||||||
if b.pipe != nil && !b.closed {
|
b.closeOnce.Do(func() {
|
||||||
|
if b.pipe != nil {
|
||||||
b.pipe.BreakWithError(errClosedBody)
|
b.pipe.BreakWithError(errClosedBody)
|
||||||
}
|
}
|
||||||
b.closed = true
|
})
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2362,7 +2450,6 @@ type responseWriterState struct {
|
||||||
// immutable within a request:
|
// immutable within a request:
|
||||||
stream *stream
|
stream *stream
|
||||||
req *http.Request
|
req *http.Request
|
||||||
body *requestBody // to close at end of request, if DATA frames didn't
|
|
||||||
conn *serverConn
|
conn *serverConn
|
||||||
|
|
||||||
// TODO: adjust buffer writing sizes based on server config, frame size updates from peer, etc
|
// TODO: adjust buffer writing sizes based on server config, frame size updates from peer, etc
|
||||||
|
|
@ -2426,6 +2513,10 @@ func (rws *responseWriterState) writeChunk(p []byte) (n int, err error) {
|
||||||
rws.writeHeader(200)
|
rws.writeHeader(200)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if rws.handlerDone {
|
||||||
|
rws.promoteUndeclaredTrailers()
|
||||||
|
}
|
||||||
|
|
||||||
isHeadResp := rws.req.Method == "HEAD"
|
isHeadResp := rws.req.Method == "HEAD"
|
||||||
if !rws.sentHeader {
|
if !rws.sentHeader {
|
||||||
rws.sentHeader = true
|
rws.sentHeader = true
|
||||||
|
|
@ -2497,10 +2588,6 @@ func (rws *responseWriterState) writeChunk(p []byte) (n int, err error) {
|
||||||
return 0, nil
|
return 0, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
if rws.handlerDone {
|
|
||||||
rws.promoteUndeclaredTrailers()
|
|
||||||
}
|
|
||||||
|
|
||||||
// only send trailers if they have actually been defined by the
|
// only send trailers if they have actually been defined by the
|
||||||
// server handler.
|
// server handler.
|
||||||
hasNonemptyTrailers := rws.hasNonemptyTrailers()
|
hasNonemptyTrailers := rws.hasNonemptyTrailers()
|
||||||
|
|
@ -2538,6 +2625,7 @@ func (rws *responseWriterState) writeChunk(p []byte) (n int, err error) {
|
||||||
// prior to the headers being written. If the set of trailers is fixed
|
// prior to the headers being written. If the set of trailers is fixed
|
||||||
// or known before the header is written, the normal Go trailers mechanism
|
// or known before the header is written, the normal Go trailers mechanism
|
||||||
// is preferred:
|
// is preferred:
|
||||||
|
//
|
||||||
// https://golang.org/pkg/net/http/#ResponseWriter
|
// https://golang.org/pkg/net/http/#ResponseWriter
|
||||||
// https://golang.org/pkg/net/http/#example_ResponseWriter_trailers
|
// https://golang.org/pkg/net/http/#example_ResponseWriter_trailers
|
||||||
const TrailerPrefix = "Trailer:"
|
const TrailerPrefix = "Trailer:"
|
||||||
|
|
@ -2635,8 +2723,7 @@ func checkWriteHeaderCode(code int) {
|
||||||
// Issue 22880: require valid WriteHeader status codes.
|
// Issue 22880: require valid WriteHeader status codes.
|
||||||
// For now we only enforce that it's three digits.
|
// For now we only enforce that it's three digits.
|
||||||
// In the future we might block things over 599 (600 and above aren't defined
|
// In the future we might block things over 599 (600 and above aren't defined
|
||||||
// at http://httpwg.org/specs/rfc7231.html#status.codes)
|
// at http://httpwg.org/specs/rfc7231.html#status.codes).
|
||||||
// and we might block under 200 (once we have more mature 1xx support).
|
|
||||||
// But for now any three digits.
|
// But for now any three digits.
|
||||||
//
|
//
|
||||||
// We used to send "HTTP/1.1 000 0" on the wire in responses but there's
|
// We used to send "HTTP/1.1 000 0" on the wire in responses but there's
|
||||||
|
|
@ -2657,15 +2744,43 @@ func (w *responseWriter) WriteHeader(code int) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (rws *responseWriterState) writeHeader(code int) {
|
func (rws *responseWriterState) writeHeader(code int) {
|
||||||
if !rws.wroteHeader {
|
if rws.wroteHeader {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
checkWriteHeaderCode(code)
|
checkWriteHeaderCode(code)
|
||||||
|
|
||||||
|
// Handle informational headers
|
||||||
|
if code >= 100 && code <= 199 {
|
||||||
|
// Per RFC 8297 we must not clear the current header map
|
||||||
|
h := rws.handlerHeader
|
||||||
|
|
||||||
|
_, cl := h["Content-Length"]
|
||||||
|
_, te := h["Transfer-Encoding"]
|
||||||
|
if cl || te {
|
||||||
|
h = h.Clone()
|
||||||
|
h.Del("Content-Length")
|
||||||
|
h.Del("Transfer-Encoding")
|
||||||
|
}
|
||||||
|
|
||||||
|
if rws.conn.writeHeaders(rws.stream, &writeResHeaders{
|
||||||
|
streamID: rws.stream.id,
|
||||||
|
httpResCode: code,
|
||||||
|
h: h,
|
||||||
|
endStream: rws.handlerDone && !rws.hasTrailers(),
|
||||||
|
}) != nil {
|
||||||
|
rws.dirty = true
|
||||||
|
}
|
||||||
|
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
rws.wroteHeader = true
|
rws.wroteHeader = true
|
||||||
rws.status = code
|
rws.status = code
|
||||||
if len(rws.handlerHeader) > 0 {
|
if len(rws.handlerHeader) > 0 {
|
||||||
rws.snapHeader = cloneHeader(rws.handlerHeader)
|
rws.snapHeader = cloneHeader(rws.handlerHeader)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
func cloneHeader(h http.Header) http.Header {
|
func cloneHeader(h http.Header) http.Header {
|
||||||
h2 := make(http.Header, len(h))
|
h2 := make(http.Header, len(h))
|
||||||
|
|
|
||||||
155
vendor/golang.org/x/net/http2/transport.go
generated
vendored
155
vendor/golang.org/x/net/http2/transport.go
generated
vendored
|
|
@ -16,7 +16,6 @@ import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
|
||||||
"log"
|
"log"
|
||||||
"math"
|
"math"
|
||||||
mathrand "math/rand"
|
mathrand "math/rand"
|
||||||
|
|
@ -68,13 +67,23 @@ const (
|
||||||
// A Transport internally caches connections to servers. It is safe
|
// A Transport internally caches connections to servers. It is safe
|
||||||
// for concurrent use by multiple goroutines.
|
// for concurrent use by multiple goroutines.
|
||||||
type Transport struct {
|
type Transport struct {
|
||||||
// DialTLS specifies an optional dial function for creating
|
// DialTLSContext specifies an optional dial function with context for
|
||||||
// TLS connections for requests.
|
// creating TLS connections for requests.
|
||||||
//
|
//
|
||||||
// If DialTLS is nil, tls.Dial is used.
|
// If DialTLSContext and DialTLS is nil, tls.Dial is used.
|
||||||
//
|
//
|
||||||
// If the returned net.Conn has a ConnectionState method like tls.Conn,
|
// If the returned net.Conn has a ConnectionState method like tls.Conn,
|
||||||
// it will be used to set http.Response.TLS.
|
// it will be used to set http.Response.TLS.
|
||||||
|
DialTLSContext func(ctx context.Context, network, addr string, cfg *tls.Config) (net.Conn, error)
|
||||||
|
|
||||||
|
// DialTLS specifies an optional dial function for creating
|
||||||
|
// TLS connections for requests.
|
||||||
|
//
|
||||||
|
// If DialTLSContext and DialTLS is nil, tls.Dial is used.
|
||||||
|
//
|
||||||
|
// Deprecated: Use DialTLSContext instead, which allows the transport
|
||||||
|
// to cancel dials as soon as they are no longer needed.
|
||||||
|
// If both are set, DialTLSContext takes priority.
|
||||||
DialTLS func(network, addr string, cfg *tls.Config) (net.Conn, error)
|
DialTLS func(network, addr string, cfg *tls.Config) (net.Conn, error)
|
||||||
|
|
||||||
// TLSClientConfig specifies the TLS configuration to use with
|
// TLSClientConfig specifies the TLS configuration to use with
|
||||||
|
|
@ -250,6 +259,7 @@ func (t *Transport) initConnPool() {
|
||||||
type ClientConn struct {
|
type ClientConn struct {
|
||||||
t *Transport
|
t *Transport
|
||||||
tconn net.Conn // usually *tls.Conn, except specialized impls
|
tconn net.Conn // usually *tls.Conn, except specialized impls
|
||||||
|
tconnClosed bool
|
||||||
tlsState *tls.ConnectionState // nil only for specialized impls
|
tlsState *tls.ConnectionState // nil only for specialized impls
|
||||||
reused uint32 // whether conn is being reused; atomic
|
reused uint32 // whether conn is being reused; atomic
|
||||||
singleUse bool // whether being used for a single http.Request
|
singleUse bool // whether being used for a single http.Request
|
||||||
|
|
@ -336,7 +346,7 @@ type clientStream struct {
|
||||||
|
|
||||||
reqBody io.ReadCloser
|
reqBody io.ReadCloser
|
||||||
reqBodyContentLength int64 // -1 means unknown
|
reqBodyContentLength int64 // -1 means unknown
|
||||||
reqBodyClosed bool // body has been closed; guarded by cc.mu
|
reqBodyClosed chan struct{} // guarded by cc.mu; non-nil on Close, closed when done
|
||||||
|
|
||||||
// owned by writeRequest:
|
// owned by writeRequest:
|
||||||
sentEndStream bool // sent an END_STREAM flag to the peer
|
sentEndStream bool // sent an END_STREAM flag to the peer
|
||||||
|
|
@ -376,9 +386,8 @@ func (cs *clientStream) abortStreamLocked(err error) {
|
||||||
cs.abortErr = err
|
cs.abortErr = err
|
||||||
close(cs.abort)
|
close(cs.abort)
|
||||||
})
|
})
|
||||||
if cs.reqBody != nil && !cs.reqBodyClosed {
|
if cs.reqBody != nil {
|
||||||
cs.reqBody.Close()
|
cs.closeReqBodyLocked()
|
||||||
cs.reqBodyClosed = true
|
|
||||||
}
|
}
|
||||||
// TODO(dneil): Clean up tests where cs.cc.cond is nil.
|
// TODO(dneil): Clean up tests where cs.cc.cond is nil.
|
||||||
if cs.cc.cond != nil {
|
if cs.cc.cond != nil {
|
||||||
|
|
@ -391,13 +400,24 @@ func (cs *clientStream) abortRequestBodyWrite() {
|
||||||
cc := cs.cc
|
cc := cs.cc
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
defer cc.mu.Unlock()
|
defer cc.mu.Unlock()
|
||||||
if cs.reqBody != nil && !cs.reqBodyClosed {
|
if cs.reqBody != nil && cs.reqBodyClosed == nil {
|
||||||
cs.reqBody.Close()
|
cs.closeReqBodyLocked()
|
||||||
cs.reqBodyClosed = true
|
|
||||||
cc.cond.Broadcast()
|
cc.cond.Broadcast()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cs *clientStream) closeReqBodyLocked() {
|
||||||
|
if cs.reqBodyClosed != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
cs.reqBodyClosed = make(chan struct{})
|
||||||
|
reqBodyClosed := cs.reqBodyClosed
|
||||||
|
go func() {
|
||||||
|
cs.reqBody.Close()
|
||||||
|
close(reqBodyClosed)
|
||||||
|
}()
|
||||||
|
}
|
||||||
|
|
||||||
type stickyErrWriter struct {
|
type stickyErrWriter struct {
|
||||||
conn net.Conn
|
conn net.Conn
|
||||||
timeout time.Duration
|
timeout time.Duration
|
||||||
|
|
@ -501,12 +521,14 @@ func (t *Transport) RoundTripOpt(req *http.Request, opt RoundTripOpt) (*http.Res
|
||||||
if req, err = shouldRetryRequest(req, err); err == nil {
|
if req, err = shouldRetryRequest(req, err); err == nil {
|
||||||
// After the first retry, do exponential backoff with 10% jitter.
|
// After the first retry, do exponential backoff with 10% jitter.
|
||||||
if retry == 0 {
|
if retry == 0 {
|
||||||
|
t.vlogf("RoundTrip retrying after failure: %v", err)
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
backoff := float64(uint(1) << (uint(retry) - 1))
|
backoff := float64(uint(1) << (uint(retry) - 1))
|
||||||
backoff += backoff * (0.1 * mathrand.Float64())
|
backoff += backoff * (0.1 * mathrand.Float64())
|
||||||
select {
|
select {
|
||||||
case <-time.After(time.Second * time.Duration(backoff)):
|
case <-time.After(time.Second * time.Duration(backoff)):
|
||||||
|
t.vlogf("RoundTrip retrying after failure: %v", err)
|
||||||
continue
|
continue
|
||||||
case <-req.Context().Done():
|
case <-req.Context().Done():
|
||||||
err = req.Context().Err()
|
err = req.Context().Err()
|
||||||
|
|
@ -591,7 +613,7 @@ func (t *Transport) dialClientConn(ctx context.Context, addr string, singleUse b
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
tconn, err := t.dialTLS(ctx)("tcp", addr, t.newTLSConfig(host))
|
tconn, err := t.dialTLS(ctx, "tcp", addr, t.newTLSConfig(host))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -612,12 +634,14 @@ func (t *Transport) newTLSConfig(host string) *tls.Config {
|
||||||
return cfg
|
return cfg
|
||||||
}
|
}
|
||||||
|
|
||||||
func (t *Transport) dialTLS(ctx context.Context) func(string, string, *tls.Config) (net.Conn, error) {
|
func (t *Transport) dialTLS(ctx context.Context, network, addr string, tlsCfg *tls.Config) (net.Conn, error) {
|
||||||
if t.DialTLS != nil {
|
if t.DialTLSContext != nil {
|
||||||
return t.DialTLS
|
return t.DialTLSContext(ctx, network, addr, tlsCfg)
|
||||||
|
} else if t.DialTLS != nil {
|
||||||
|
return t.DialTLS(network, addr, tlsCfg)
|
||||||
}
|
}
|
||||||
return func(network, addr string, cfg *tls.Config) (net.Conn, error) {
|
|
||||||
tlsCn, err := t.dialTLSWithContext(ctx, network, addr, cfg)
|
tlsCn, err := t.dialTLSWithContext(ctx, network, addr, tlsCfg)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
@ -630,7 +654,6 @@ func (t *Transport) dialTLS(ctx context.Context) func(string, string, *tls.Confi
|
||||||
}
|
}
|
||||||
return tlsCn, nil
|
return tlsCn, nil
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// disableKeepAlives reports whether connections should be closed as
|
// disableKeepAlives reports whether connections should be closed as
|
||||||
// soon as possible after handling the first request.
|
// soon as possible after handling the first request.
|
||||||
|
|
@ -732,11 +755,13 @@ func (cc *ClientConn) healthCheck() {
|
||||||
// trigger the healthCheck again if there is no frame received.
|
// trigger the healthCheck again if there is no frame received.
|
||||||
ctx, cancel := context.WithTimeout(context.Background(), pingTimeout)
|
ctx, cancel := context.WithTimeout(context.Background(), pingTimeout)
|
||||||
defer cancel()
|
defer cancel()
|
||||||
|
cc.vlogf("http2: Transport sending health check")
|
||||||
err := cc.Ping(ctx)
|
err := cc.Ping(ctx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
cc.vlogf("http2: Transport health check failure: %v", err)
|
||||||
cc.closeForLostPing()
|
cc.closeForLostPing()
|
||||||
cc.t.connPool().MarkDead(cc)
|
} else {
|
||||||
return
|
cc.vlogf("http2: Transport health check success")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -907,6 +932,24 @@ func (cc *ClientConn) onIdleTimeout() {
|
||||||
cc.closeIfIdle()
|
cc.closeIfIdle()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cc *ClientConn) closeConn() {
|
||||||
|
t := time.AfterFunc(250*time.Millisecond, cc.forceCloseConn)
|
||||||
|
defer t.Stop()
|
||||||
|
cc.tconn.Close()
|
||||||
|
}
|
||||||
|
|
||||||
|
// A tls.Conn.Close can hang for a long time if the peer is unresponsive.
|
||||||
|
// Try to shut it down more aggressively.
|
||||||
|
func (cc *ClientConn) forceCloseConn() {
|
||||||
|
tc, ok := cc.tconn.(*tls.Conn)
|
||||||
|
if !ok {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if nc := tlsUnderlyingConn(tc); nc != nil {
|
||||||
|
nc.Close()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func (cc *ClientConn) closeIfIdle() {
|
func (cc *ClientConn) closeIfIdle() {
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
if len(cc.streams) > 0 || cc.streamsReserved > 0 {
|
if len(cc.streams) > 0 || cc.streamsReserved > 0 {
|
||||||
|
|
@ -921,7 +964,7 @@ func (cc *ClientConn) closeIfIdle() {
|
||||||
if VerboseLogs {
|
if VerboseLogs {
|
||||||
cc.vlogf("http2: Transport closing idle conn %p (forSingleUse=%v, maxStream=%v)", cc, cc.singleUse, nextID-2)
|
cc.vlogf("http2: Transport closing idle conn %p (forSingleUse=%v, maxStream=%v)", cc, cc.singleUse, nextID-2)
|
||||||
}
|
}
|
||||||
cc.tconn.Close()
|
cc.closeConn()
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cc *ClientConn) isDoNotReuseAndIdle() bool {
|
func (cc *ClientConn) isDoNotReuseAndIdle() bool {
|
||||||
|
|
@ -938,7 +981,7 @@ func (cc *ClientConn) Shutdown(ctx context.Context) error {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
// Wait for all in-flight streams to complete or connection to close
|
// Wait for all in-flight streams to complete or connection to close
|
||||||
done := make(chan error, 1)
|
done := make(chan struct{})
|
||||||
cancelled := false // guarded by cc.mu
|
cancelled := false // guarded by cc.mu
|
||||||
go func() {
|
go func() {
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
|
|
@ -946,7 +989,7 @@ func (cc *ClientConn) Shutdown(ctx context.Context) error {
|
||||||
for {
|
for {
|
||||||
if len(cc.streams) == 0 || cc.closed {
|
if len(cc.streams) == 0 || cc.closed {
|
||||||
cc.closed = true
|
cc.closed = true
|
||||||
done <- cc.tconn.Close()
|
close(done)
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if cancelled {
|
if cancelled {
|
||||||
|
|
@ -957,8 +1000,9 @@ func (cc *ClientConn) Shutdown(ctx context.Context) error {
|
||||||
}()
|
}()
|
||||||
shutdownEnterWaitStateHook()
|
shutdownEnterWaitStateHook()
|
||||||
select {
|
select {
|
||||||
case err := <-done:
|
case <-done:
|
||||||
return err
|
cc.closeConn()
|
||||||
|
return nil
|
||||||
case <-ctx.Done():
|
case <-ctx.Done():
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
// Free the goroutine above
|
// Free the goroutine above
|
||||||
|
|
@ -995,15 +1039,15 @@ func (cc *ClientConn) sendGoAway() error {
|
||||||
|
|
||||||
// closes the client connection immediately. In-flight requests are interrupted.
|
// closes the client connection immediately. In-flight requests are interrupted.
|
||||||
// err is sent to streams.
|
// err is sent to streams.
|
||||||
func (cc *ClientConn) closeForError(err error) error {
|
func (cc *ClientConn) closeForError(err error) {
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
cc.closed = true
|
cc.closed = true
|
||||||
for _, cs := range cc.streams {
|
for _, cs := range cc.streams {
|
||||||
cs.abortStreamLocked(err)
|
cs.abortStreamLocked(err)
|
||||||
}
|
}
|
||||||
defer cc.cond.Broadcast()
|
cc.cond.Broadcast()
|
||||||
defer cc.mu.Unlock()
|
cc.mu.Unlock()
|
||||||
return cc.tconn.Close()
|
cc.closeConn()
|
||||||
}
|
}
|
||||||
|
|
||||||
// Close closes the client connection immediately.
|
// Close closes the client connection immediately.
|
||||||
|
|
@ -1011,16 +1055,17 @@ func (cc *ClientConn) closeForError(err error) error {
|
||||||
// In-flight requests are interrupted. For a graceful shutdown, use Shutdown instead.
|
// In-flight requests are interrupted. For a graceful shutdown, use Shutdown instead.
|
||||||
func (cc *ClientConn) Close() error {
|
func (cc *ClientConn) Close() error {
|
||||||
err := errors.New("http2: client connection force closed via ClientConn.Close")
|
err := errors.New("http2: client connection force closed via ClientConn.Close")
|
||||||
return cc.closeForError(err)
|
cc.closeForError(err)
|
||||||
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// closes the client connection immediately. In-flight requests are interrupted.
|
// closes the client connection immediately. In-flight requests are interrupted.
|
||||||
func (cc *ClientConn) closeForLostPing() error {
|
func (cc *ClientConn) closeForLostPing() {
|
||||||
err := errors.New("http2: client connection lost")
|
err := errors.New("http2: client connection lost")
|
||||||
if f := cc.t.CountError; f != nil {
|
if f := cc.t.CountError; f != nil {
|
||||||
f("conn_close_lost_ping")
|
f("conn_close_lost_ping")
|
||||||
}
|
}
|
||||||
return cc.closeForError(err)
|
cc.closeForError(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
// errRequestCanceled is a copy of net/http's errRequestCanceled because it's not
|
// errRequestCanceled is a copy of net/http's errRequestCanceled because it's not
|
||||||
|
|
@ -1252,13 +1297,13 @@ func (cs *clientStream) writeRequest(req *http.Request) (err error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
continueTimeout := cc.t.expectContinueTimeout()
|
continueTimeout := cc.t.expectContinueTimeout()
|
||||||
if continueTimeout != 0 &&
|
if continueTimeout != 0 {
|
||||||
!httpguts.HeaderValuesContainsToken(
|
if !httpguts.HeaderValuesContainsToken(req.Header["Expect"], "100-continue") {
|
||||||
req.Header["Expect"],
|
|
||||||
"100-continue") {
|
|
||||||
continueTimeout = 0
|
continueTimeout = 0
|
||||||
|
} else {
|
||||||
cs.on100 = make(chan struct{}, 1)
|
cs.on100 = make(chan struct{}, 1)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Past this point (where we send request headers), it is possible for
|
// Past this point (where we send request headers), it is possible for
|
||||||
// RoundTrip to return successfully. Since the RoundTrip contract permits
|
// RoundTrip to return successfully. Since the RoundTrip contract permits
|
||||||
|
|
@ -1398,11 +1443,19 @@ func (cs *clientStream) cleanupWriteRequest(err error) {
|
||||||
// and in multiple cases: server replies <=299 and >299
|
// and in multiple cases: server replies <=299 and >299
|
||||||
// while still writing request body
|
// while still writing request body
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
|
mustCloseBody := false
|
||||||
|
if cs.reqBody != nil && cs.reqBodyClosed == nil {
|
||||||
|
mustCloseBody = true
|
||||||
|
cs.reqBodyClosed = make(chan struct{})
|
||||||
|
}
|
||||||
bodyClosed := cs.reqBodyClosed
|
bodyClosed := cs.reqBodyClosed
|
||||||
cs.reqBodyClosed = true
|
|
||||||
cc.mu.Unlock()
|
cc.mu.Unlock()
|
||||||
if !bodyClosed && cs.reqBody != nil {
|
if mustCloseBody {
|
||||||
cs.reqBody.Close()
|
cs.reqBody.Close()
|
||||||
|
close(bodyClosed)
|
||||||
|
}
|
||||||
|
if bodyClosed != nil {
|
||||||
|
<-bodyClosed
|
||||||
}
|
}
|
||||||
|
|
||||||
if err != nil && cs.sentEndStream {
|
if err != nil && cs.sentEndStream {
|
||||||
|
|
@ -1582,7 +1635,7 @@ func (cs *clientStream) writeRequestBody(req *http.Request) (err error) {
|
||||||
}
|
}
|
||||||
if err != nil {
|
if err != nil {
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
bodyClosed := cs.reqBodyClosed
|
bodyClosed := cs.reqBodyClosed != nil
|
||||||
cc.mu.Unlock()
|
cc.mu.Unlock()
|
||||||
switch {
|
switch {
|
||||||
case bodyClosed:
|
case bodyClosed:
|
||||||
|
|
@ -1677,7 +1730,7 @@ func (cs *clientStream) awaitFlowControl(maxBytes int) (taken int32, err error)
|
||||||
if cc.closed {
|
if cc.closed {
|
||||||
return 0, errClientConnClosed
|
return 0, errClientConnClosed
|
||||||
}
|
}
|
||||||
if cs.reqBodyClosed {
|
if cs.reqBodyClosed != nil {
|
||||||
return 0, errStopReqBodyWrite
|
return 0, errStopReqBodyWrite
|
||||||
}
|
}
|
||||||
select {
|
select {
|
||||||
|
|
@ -1748,7 +1801,8 @@ func (cc *ClientConn) encodeHeaders(req *http.Request, addGzipHeader bool, trail
|
||||||
}
|
}
|
||||||
for _, v := range vv {
|
for _, v := range vv {
|
||||||
if !httpguts.ValidHeaderFieldValue(v) {
|
if !httpguts.ValidHeaderFieldValue(v) {
|
||||||
return nil, fmt.Errorf("invalid HTTP header value %q for header %q", v, k)
|
// Don't include the value in the error, because it may be sensitive.
|
||||||
|
return nil, fmt.Errorf("invalid HTTP header value for header %q", k)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -1972,13 +2026,13 @@ func (cc *ClientConn) forgetStreamID(id uint32) {
|
||||||
// wake up RoundTrip if there is a pending request.
|
// wake up RoundTrip if there is a pending request.
|
||||||
cc.cond.Broadcast()
|
cc.cond.Broadcast()
|
||||||
|
|
||||||
closeOnIdle := cc.singleUse || cc.doNotReuse || cc.t.disableKeepAlives()
|
closeOnIdle := cc.singleUse || cc.doNotReuse || cc.t.disableKeepAlives() || cc.goAway != nil
|
||||||
if closeOnIdle && cc.streamsReserved == 0 && len(cc.streams) == 0 {
|
if closeOnIdle && cc.streamsReserved == 0 && len(cc.streams) == 0 {
|
||||||
if VerboseLogs {
|
if VerboseLogs {
|
||||||
cc.vlogf("http2: Transport closing idle conn %p (forSingleUse=%v, maxStream=%v)", cc, cc.singleUse, cc.nextStreamID-2)
|
cc.vlogf("http2: Transport closing idle conn %p (forSingleUse=%v, maxStream=%v)", cc, cc.singleUse, cc.nextStreamID-2)
|
||||||
}
|
}
|
||||||
cc.closed = true
|
cc.closed = true
|
||||||
defer cc.tconn.Close()
|
defer cc.closeConn()
|
||||||
}
|
}
|
||||||
|
|
||||||
cc.mu.Unlock()
|
cc.mu.Unlock()
|
||||||
|
|
@ -2025,8 +2079,8 @@ func isEOFOrNetReadError(err error) bool {
|
||||||
|
|
||||||
func (rl *clientConnReadLoop) cleanup() {
|
func (rl *clientConnReadLoop) cleanup() {
|
||||||
cc := rl.cc
|
cc := rl.cc
|
||||||
defer cc.tconn.Close()
|
cc.t.connPool().MarkDead(cc)
|
||||||
defer cc.t.connPool().MarkDead(cc)
|
defer cc.closeConn()
|
||||||
defer close(cc.readerDone)
|
defer close(cc.readerDone)
|
||||||
|
|
||||||
if cc.idleTimer != nil {
|
if cc.idleTimer != nil {
|
||||||
|
|
@ -2048,6 +2102,7 @@ func (rl *clientConnReadLoop) cleanup() {
|
||||||
err = io.ErrUnexpectedEOF
|
err = io.ErrUnexpectedEOF
|
||||||
}
|
}
|
||||||
cc.closed = true
|
cc.closed = true
|
||||||
|
|
||||||
for _, cs := range cc.streams {
|
for _, cs := range cc.streams {
|
||||||
select {
|
select {
|
||||||
case <-cs.peerClosed:
|
case <-cs.peerClosed:
|
||||||
|
|
@ -2641,7 +2696,6 @@ func (rl *clientConnReadLoop) processGoAway(f *GoAwayFrame) error {
|
||||||
if fn := cc.t.CountError; fn != nil {
|
if fn := cc.t.CountError; fn != nil {
|
||||||
fn("recv_goaway_" + f.ErrCode.stringToken())
|
fn("recv_goaway_" + f.ErrCode.stringToken())
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
cc.setGoAway(f)
|
cc.setGoAway(f)
|
||||||
return nil
|
return nil
|
||||||
|
|
@ -2881,7 +2935,12 @@ func (t *Transport) logf(format string, args ...interface{}) {
|
||||||
log.Printf(format, args...)
|
log.Printf(format, args...)
|
||||||
}
|
}
|
||||||
|
|
||||||
var noBody io.ReadCloser = ioutil.NopCloser(bytes.NewReader(nil))
|
var noBody io.ReadCloser = noBodyReader{}
|
||||||
|
|
||||||
|
type noBodyReader struct{}
|
||||||
|
|
||||||
|
func (noBodyReader) Close() error { return nil }
|
||||||
|
func (noBodyReader) Read([]byte) (int, error) { return 0, io.EOF }
|
||||||
|
|
||||||
type missingBody struct{}
|
type missingBody struct{}
|
||||||
|
|
||||||
|
|
@ -2990,7 +3049,7 @@ func traceGotConn(req *http.Request, cc *ClientConn, reused bool) {
|
||||||
cc.mu.Lock()
|
cc.mu.Lock()
|
||||||
ci.WasIdle = len(cc.streams) == 0 && reused
|
ci.WasIdle = len(cc.streams) == 0 && reused
|
||||||
if ci.WasIdle && !cc.lastActive.IsZero() {
|
if ci.WasIdle && !cc.lastActive.IsZero() {
|
||||||
ci.IdleTime = time.Now().Sub(cc.lastActive)
|
ci.IdleTime = time.Since(cc.lastActive)
|
||||||
}
|
}
|
||||||
cc.mu.Unlock()
|
cc.mu.Unlock()
|
||||||
|
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/net/http2/writesched.go
generated
vendored
4
vendor/golang.org/x/net/http2/writesched.go
generated
vendored
|
|
@ -32,7 +32,8 @@ type WriteScheduler interface {
|
||||||
|
|
||||||
// Pop dequeues the next frame to write. Returns false if no frames can
|
// Pop dequeues the next frame to write. Returns false if no frames can
|
||||||
// be written. Frames with a given wr.StreamID() are Pop'd in the same
|
// be written. Frames with a given wr.StreamID() are Pop'd in the same
|
||||||
// order they are Push'd. No frames should be discarded except by CloseStream.
|
// order they are Push'd, except RST_STREAM frames. No frames should be
|
||||||
|
// discarded except by CloseStream.
|
||||||
Pop() (wr FrameWriteRequest, ok bool)
|
Pop() (wr FrameWriteRequest, ok bool)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -52,6 +53,7 @@ type FrameWriteRequest struct {
|
||||||
|
|
||||||
// stream is the stream on which this frame will be written.
|
// stream is the stream on which this frame will be written.
|
||||||
// nil for non-stream frames like PING and SETTINGS.
|
// nil for non-stream frames like PING and SETTINGS.
|
||||||
|
// nil for RST_STREAM streams, which use the StreamError.StreamID field instead.
|
||||||
stream *stream
|
stream *stream
|
||||||
|
|
||||||
// done, if non-nil, must be a buffered channel with space for
|
// done, if non-nil, must be a buffered channel with space for
|
||||||
|
|
|
||||||
9
vendor/golang.org/x/net/http2/writesched_priority.go
generated
vendored
9
vendor/golang.org/x/net/http2/writesched_priority.go
generated
vendored
|
|
@ -383,16 +383,15 @@ func (ws *priorityWriteScheduler) AdjustStream(streamID uint32, priority Priorit
|
||||||
|
|
||||||
func (ws *priorityWriteScheduler) Push(wr FrameWriteRequest) {
|
func (ws *priorityWriteScheduler) Push(wr FrameWriteRequest) {
|
||||||
var n *priorityNode
|
var n *priorityNode
|
||||||
if id := wr.StreamID(); id == 0 {
|
if wr.isControl() {
|
||||||
n = &ws.root
|
n = &ws.root
|
||||||
} else {
|
} else {
|
||||||
|
id := wr.StreamID()
|
||||||
n = ws.nodes[id]
|
n = ws.nodes[id]
|
||||||
if n == nil {
|
if n == nil {
|
||||||
// id is an idle or closed stream. wr should not be a HEADERS or
|
// id is an idle or closed stream. wr should not be a HEADERS or
|
||||||
// DATA frame. However, wr can be a RST_STREAM. In this case, we
|
// DATA frame. In other case, we push wr onto the root, rather
|
||||||
// push wr onto the root, rather than creating a new priorityNode,
|
// than creating a new priorityNode.
|
||||||
// since RST_STREAM is tiny and the stream's priority is unknown
|
|
||||||
// anyway. See issue #17919.
|
|
||||||
if wr.DataSize() > 0 {
|
if wr.DataSize() > 0 {
|
||||||
panic("add DATA on non-open stream")
|
panic("add DATA on non-open stream")
|
||||||
}
|
}
|
||||||
|
|
|
||||||
6
vendor/golang.org/x/net/http2/writesched_random.go
generated
vendored
6
vendor/golang.org/x/net/http2/writesched_random.go
generated
vendored
|
|
@ -45,11 +45,11 @@ func (ws *randomWriteScheduler) AdjustStream(streamID uint32, priority PriorityP
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ws *randomWriteScheduler) Push(wr FrameWriteRequest) {
|
func (ws *randomWriteScheduler) Push(wr FrameWriteRequest) {
|
||||||
id := wr.StreamID()
|
if wr.isControl() {
|
||||||
if id == 0 {
|
|
||||||
ws.zero.push(wr)
|
ws.zero.push(wr)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
id := wr.StreamID()
|
||||||
q, ok := ws.sq[id]
|
q, ok := ws.sq[id]
|
||||||
if !ok {
|
if !ok {
|
||||||
q = ws.queuePool.get()
|
q = ws.queuePool.get()
|
||||||
|
|
@ -59,7 +59,7 @@ func (ws *randomWriteScheduler) Push(wr FrameWriteRequest) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ws *randomWriteScheduler) Pop() (FrameWriteRequest, bool) {
|
func (ws *randomWriteScheduler) Pop() (FrameWriteRequest, bool) {
|
||||||
// Control frames first.
|
// Control and RST_STREAM frames first.
|
||||||
if !ws.zero.empty() {
|
if !ws.zero.empty() {
|
||||||
return ws.zero.shift(), true
|
return ws.zero.shift(), true
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/net/trace/trace.go
generated
vendored
2
vendor/golang.org/x/net/trace/trace.go
generated
vendored
|
|
@ -395,7 +395,7 @@ func New(family, title string) Trace {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (tr *trace) Finish() {
|
func (tr *trace) Finish() {
|
||||||
elapsed := time.Now().Sub(tr.Start)
|
elapsed := time.Since(tr.Start)
|
||||||
tr.mu.Lock()
|
tr.mu.Lock()
|
||||||
tr.Elapsed = elapsed
|
tr.Elapsed = elapsed
|
||||||
tr.mu.Unlock()
|
tr.mu.Unlock()
|
||||||
|
|
|
||||||
3
vendor/golang.org/x/sync/AUTHORS
generated
vendored
3
vendor/golang.org/x/sync/AUTHORS
generated
vendored
|
|
@ -1,3 +0,0 @@
|
||||||
# This source code refers to The Go Authors for copyright purposes.
|
|
||||||
# The master list of authors is in the main Go distribution,
|
|
||||||
# visible at http://tip.golang.org/AUTHORS.
|
|
||||||
3
vendor/golang.org/x/sync/CONTRIBUTORS
generated
vendored
3
vendor/golang.org/x/sync/CONTRIBUTORS
generated
vendored
|
|
@ -1,3 +0,0 @@
|
||||||
# This source code was written by the Go contributors.
|
|
||||||
# The master list of contributors is in the main Go distribution,
|
|
||||||
# visible at http://tip.golang.org/CONTRIBUTORS.
|
|
||||||
72
vendor/golang.org/x/sync/errgroup/errgroup.go
generated
vendored
72
vendor/golang.org/x/sync/errgroup/errgroup.go
generated
vendored
|
|
@ -8,22 +8,35 @@ package errgroup
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
|
"fmt"
|
||||||
"sync"
|
"sync"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
type token struct{}
|
||||||
|
|
||||||
// A Group is a collection of goroutines working on subtasks that are part of
|
// A Group is a collection of goroutines working on subtasks that are part of
|
||||||
// the same overall task.
|
// the same overall task.
|
||||||
//
|
//
|
||||||
// A zero Group is valid and does not cancel on error.
|
// A zero Group is valid, has no limit on the number of active goroutines,
|
||||||
|
// and does not cancel on error.
|
||||||
type Group struct {
|
type Group struct {
|
||||||
cancel func()
|
cancel func()
|
||||||
|
|
||||||
wg sync.WaitGroup
|
wg sync.WaitGroup
|
||||||
|
|
||||||
|
sem chan token
|
||||||
|
|
||||||
errOnce sync.Once
|
errOnce sync.Once
|
||||||
err error
|
err error
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (g *Group) done() {
|
||||||
|
if g.sem != nil {
|
||||||
|
<-g.sem
|
||||||
|
}
|
||||||
|
g.wg.Done()
|
||||||
|
}
|
||||||
|
|
||||||
// WithContext returns a new Group and an associated Context derived from ctx.
|
// WithContext returns a new Group and an associated Context derived from ctx.
|
||||||
//
|
//
|
||||||
// The derived Context is canceled the first time a function passed to Go
|
// The derived Context is canceled the first time a function passed to Go
|
||||||
|
|
@ -45,14 +58,19 @@ func (g *Group) Wait() error {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Go calls the given function in a new goroutine.
|
// Go calls the given function in a new goroutine.
|
||||||
|
// It blocks until the new goroutine can be added without the number of
|
||||||
|
// active goroutines in the group exceeding the configured limit.
|
||||||
//
|
//
|
||||||
// The first call to return a non-nil error cancels the group; its error will be
|
// The first call to return a non-nil error cancels the group; its error will be
|
||||||
// returned by Wait.
|
// returned by Wait.
|
||||||
func (g *Group) Go(f func() error) {
|
func (g *Group) Go(f func() error) {
|
||||||
g.wg.Add(1)
|
if g.sem != nil {
|
||||||
|
g.sem <- token{}
|
||||||
|
}
|
||||||
|
|
||||||
|
g.wg.Add(1)
|
||||||
go func() {
|
go func() {
|
||||||
defer g.wg.Done()
|
defer g.done()
|
||||||
|
|
||||||
if err := f(); err != nil {
|
if err := f(); err != nil {
|
||||||
g.errOnce.Do(func() {
|
g.errOnce.Do(func() {
|
||||||
|
|
@ -64,3 +82,51 @@ func (g *Group) Go(f func() error) {
|
||||||
}
|
}
|
||||||
}()
|
}()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TryGo calls the given function in a new goroutine only if the number of
|
||||||
|
// active goroutines in the group is currently below the configured limit.
|
||||||
|
//
|
||||||
|
// The return value reports whether the goroutine was started.
|
||||||
|
func (g *Group) TryGo(f func() error) bool {
|
||||||
|
if g.sem != nil {
|
||||||
|
select {
|
||||||
|
case g.sem <- token{}:
|
||||||
|
// Note: this allows barging iff channels in general allow barging.
|
||||||
|
default:
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
g.wg.Add(1)
|
||||||
|
go func() {
|
||||||
|
defer g.done()
|
||||||
|
|
||||||
|
if err := f(); err != nil {
|
||||||
|
g.errOnce.Do(func() {
|
||||||
|
g.err = err
|
||||||
|
if g.cancel != nil {
|
||||||
|
g.cancel()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// SetLimit limits the number of active goroutines in this group to at most n.
|
||||||
|
// A negative value indicates no limit.
|
||||||
|
//
|
||||||
|
// Any subsequent call to the Go method will block until it can add an active
|
||||||
|
// goroutine without exceeding the configured limit.
|
||||||
|
//
|
||||||
|
// The limit must not be modified while any goroutines in the group are active.
|
||||||
|
func (g *Group) SetLimit(n int) {
|
||||||
|
if n < 0 {
|
||||||
|
g.sem = nil
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if len(g.sem) != 0 {
|
||||||
|
panic(fmt.Errorf("errgroup: modify limit while %v goroutines in the group are still active", len(g.sem)))
|
||||||
|
}
|
||||||
|
g.sem = make(chan token, n)
|
||||||
|
}
|
||||||
|
|
|
||||||
5
vendor/golang.org/x/sys/cpu/cpu_arm64.go
generated
vendored
5
vendor/golang.org/x/sys/cpu/cpu_arm64.go
generated
vendored
|
|
@ -6,7 +6,10 @@ package cpu
|
||||||
|
|
||||||
import "runtime"
|
import "runtime"
|
||||||
|
|
||||||
const cacheLineSize = 64
|
// cacheLineSize is used to prevent false sharing of cache lines.
|
||||||
|
// We choose 128 because Apple Silicon, a.k.a. M1, has 128-byte cache line size.
|
||||||
|
// It doesn't cost much and is much more future-proof.
|
||||||
|
const cacheLineSize = 128
|
||||||
|
|
||||||
func initOptions() {
|
func initOptions() {
|
||||||
options = []option{
|
options = []option{
|
||||||
|
|
|
||||||
15
vendor/golang.org/x/sys/cpu/cpu_other_ppc64x.go
generated
vendored
Normal file
15
vendor/golang.org/x/sys/cpu/cpu_other_ppc64x.go
generated
vendored
Normal file
|
|
@ -0,0 +1,15 @@
|
||||||
|
// Copyright 2022 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
//go:build !aix && !linux && (ppc64 || ppc64le)
|
||||||
|
// +build !aix
|
||||||
|
// +build !linux
|
||||||
|
// +build ppc64 ppc64le
|
||||||
|
|
||||||
|
package cpu
|
||||||
|
|
||||||
|
func archInit() {
|
||||||
|
PPC64.IsPOWER8 = true
|
||||||
|
Initialized = true
|
||||||
|
}
|
||||||
31
vendor/golang.org/x/sys/unix/asm_bsd_ppc64.s
generated
vendored
Normal file
31
vendor/golang.org/x/sys/unix/asm_bsd_ppc64.s
generated
vendored
Normal file
|
|
@ -0,0 +1,31 @@
|
||||||
|
// Copyright 2022 The Go Authors. All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
//go:build (darwin || freebsd || netbsd || openbsd) && gc
|
||||||
|
// +build darwin freebsd netbsd openbsd
|
||||||
|
// +build gc
|
||||||
|
|
||||||
|
#include "textflag.h"
|
||||||
|
|
||||||
|
//
|
||||||
|
// System call support for ppc64, BSD
|
||||||
|
//
|
||||||
|
|
||||||
|
// Just jump to package syscall's implementation for all these functions.
|
||||||
|
// The runtime may know about them.
|
||||||
|
|
||||||
|
TEXT ·Syscall(SB),NOSPLIT,$0-56
|
||||||
|
JMP syscall·Syscall(SB)
|
||||||
|
|
||||||
|
TEXT ·Syscall6(SB),NOSPLIT,$0-80
|
||||||
|
JMP syscall·Syscall6(SB)
|
||||||
|
|
||||||
|
TEXT ·Syscall9(SB),NOSPLIT,$0-104
|
||||||
|
JMP syscall·Syscall9(SB)
|
||||||
|
|
||||||
|
TEXT ·RawSyscall(SB),NOSPLIT,$0-56
|
||||||
|
JMP syscall·RawSyscall(SB)
|
||||||
|
|
||||||
|
TEXT ·RawSyscall6(SB),NOSPLIT,$0-80
|
||||||
|
JMP syscall·RawSyscall6(SB)
|
||||||
4
vendor/golang.org/x/sys/unix/dirent.go
generated
vendored
4
vendor/golang.org/x/sys/unix/dirent.go
generated
vendored
|
|
@ -2,8 +2,8 @@
|
||||||
// Use of this source code is governed by a BSD-style
|
// Use of this source code is governed by a BSD-style
|
||||||
// license that can be found in the LICENSE file.
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
//go:build aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd || solaris
|
//go:build aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd || solaris || zos
|
||||||
// +build aix darwin dragonfly freebsd linux netbsd openbsd solaris
|
// +build aix darwin dragonfly freebsd linux netbsd openbsd solaris zos
|
||||||
|
|
||||||
package unix
|
package unix
|
||||||
|
|
||||||
|
|
|
||||||
20
vendor/golang.org/x/sys/unix/ioctl_linux.go
generated
vendored
20
vendor/golang.org/x/sys/unix/ioctl_linux.go
generated
vendored
|
|
@ -4,9 +4,7 @@
|
||||||
|
|
||||||
package unix
|
package unix
|
||||||
|
|
||||||
import (
|
import "unsafe"
|
||||||
"unsafe"
|
|
||||||
)
|
|
||||||
|
|
||||||
// IoctlRetInt performs an ioctl operation specified by req on a device
|
// IoctlRetInt performs an ioctl operation specified by req on a device
|
||||||
// associated with opened file descriptor fd, and returns a non-negative
|
// associated with opened file descriptor fd, and returns a non-negative
|
||||||
|
|
@ -217,3 +215,19 @@ func IoctlKCMAttach(fd int, info KCMAttach) error {
|
||||||
func IoctlKCMUnattach(fd int, info KCMUnattach) error {
|
func IoctlKCMUnattach(fd int, info KCMUnattach) error {
|
||||||
return ioctlPtr(fd, SIOCKCMUNATTACH, unsafe.Pointer(&info))
|
return ioctlPtr(fd, SIOCKCMUNATTACH, unsafe.Pointer(&info))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// IoctlLoopGetStatus64 gets the status of the loop device associated with the
|
||||||
|
// file descriptor fd using the LOOP_GET_STATUS64 operation.
|
||||||
|
func IoctlLoopGetStatus64(fd int) (*LoopInfo64, error) {
|
||||||
|
var value LoopInfo64
|
||||||
|
if err := ioctlPtr(fd, LOOP_GET_STATUS64, unsafe.Pointer(&value)); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return &value, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// IoctlLoopSetStatus64 sets the status of the loop device associated with the
|
||||||
|
// file descriptor fd using the LOOP_SET_STATUS64 operation.
|
||||||
|
func IoctlLoopSetStatus64(fd int, value *LoopInfo64) error {
|
||||||
|
return ioctlPtr(fd, LOOP_SET_STATUS64, unsafe.Pointer(value))
|
||||||
|
}
|
||||||
|
|
|
||||||
27
vendor/golang.org/x/sys/unix/mkall.sh
generated
vendored
27
vendor/golang.org/x/sys/unix/mkall.sh
generated
vendored
|
|
@ -156,10 +156,10 @@ openbsd_amd64)
|
||||||
mktypes="GOARCH=$GOARCH go tool cgo -godefs"
|
mktypes="GOARCH=$GOARCH go tool cgo -godefs"
|
||||||
;;
|
;;
|
||||||
openbsd_arm)
|
openbsd_arm)
|
||||||
|
mkasm="go run mkasm.go"
|
||||||
mkerrors="$mkerrors"
|
mkerrors="$mkerrors"
|
||||||
mksyscall="go run mksyscall.go -l32 -openbsd -arm"
|
mksyscall="go run mksyscall.go -l32 -openbsd -arm -libc"
|
||||||
mksysctl="go run mksysctl_openbsd.go"
|
mksysctl="go run mksysctl_openbsd.go"
|
||||||
mksysnum="go run mksysnum.go 'https://cvsweb.openbsd.org/cgi-bin/cvsweb/~checkout~/src/sys/kern/syscalls.master'"
|
|
||||||
# Let the type of C char be signed for making the bare syscall
|
# Let the type of C char be signed for making the bare syscall
|
||||||
# API consistent across platforms.
|
# API consistent across platforms.
|
||||||
mktypes="GOARCH=$GOARCH go tool cgo -godefs -- -fsigned-char"
|
mktypes="GOARCH=$GOARCH go tool cgo -godefs -- -fsigned-char"
|
||||||
|
|
@ -182,6 +182,24 @@ openbsd_mips64)
|
||||||
# API consistent across platforms.
|
# API consistent across platforms.
|
||||||
mktypes="GOARCH=$GOARCH go tool cgo -godefs -- -fsigned-char"
|
mktypes="GOARCH=$GOARCH go tool cgo -godefs -- -fsigned-char"
|
||||||
;;
|
;;
|
||||||
|
openbsd_ppc64)
|
||||||
|
mkasm="go run mkasm.go"
|
||||||
|
mkerrors="$mkerrors -m64"
|
||||||
|
mksyscall="go run mksyscall.go -openbsd -libc"
|
||||||
|
mksysctl="go run mksysctl_openbsd.go"
|
||||||
|
# Let the type of C char be signed for making the bare syscall
|
||||||
|
# API consistent across platforms.
|
||||||
|
mktypes="GOARCH=$GOARCH go tool cgo -godefs -- -fsigned-char"
|
||||||
|
;;
|
||||||
|
openbsd_riscv64)
|
||||||
|
mkasm="go run mkasm.go"
|
||||||
|
mkerrors="$mkerrors -m64"
|
||||||
|
mksyscall="go run mksyscall.go -openbsd -libc"
|
||||||
|
mksysctl="go run mksysctl_openbsd.go"
|
||||||
|
# Let the type of C char be signed for making the bare syscall
|
||||||
|
# API consistent across platforms.
|
||||||
|
mktypes="GOARCH=$GOARCH go tool cgo -godefs -- -fsigned-char"
|
||||||
|
;;
|
||||||
solaris_amd64)
|
solaris_amd64)
|
||||||
mksyscall="go run mksyscall_solaris.go"
|
mksyscall="go run mksyscall_solaris.go"
|
||||||
mkerrors="$mkerrors -m64"
|
mkerrors="$mkerrors -m64"
|
||||||
|
|
@ -214,11 +232,6 @@ esac
|
||||||
if [ "$GOOSARCH" == "aix_ppc64" ]; then
|
if [ "$GOOSARCH" == "aix_ppc64" ]; then
|
||||||
# aix/ppc64 script generates files instead of writing to stdin.
|
# aix/ppc64 script generates files instead of writing to stdin.
|
||||||
echo "$mksyscall -tags $GOOS,$GOARCH $syscall_goos $GOOSARCH_in && gofmt -w zsyscall_$GOOSARCH.go && gofmt -w zsyscall_"$GOOSARCH"_gccgo.go && gofmt -w zsyscall_"$GOOSARCH"_gc.go " ;
|
echo "$mksyscall -tags $GOOS,$GOARCH $syscall_goos $GOOSARCH_in && gofmt -w zsyscall_$GOOSARCH.go && gofmt -w zsyscall_"$GOOSARCH"_gccgo.go && gofmt -w zsyscall_"$GOOSARCH"_gc.go " ;
|
||||||
elif [ "$GOOS" == "darwin" ]; then
|
|
||||||
# 1.12 and later, syscalls via libSystem
|
|
||||||
echo "$mksyscall -tags $GOOS,$GOARCH,go1.12 $syscall_goos $GOOSARCH_in |gofmt >zsyscall_$GOOSARCH.go";
|
|
||||||
# 1.13 and later, syscalls via libSystem (including syscallPtr)
|
|
||||||
echo "$mksyscall -tags $GOOS,$GOARCH,go1.13 syscall_darwin.1_13.go |gofmt >zsyscall_$GOOSARCH.1_13.go";
|
|
||||||
elif [ "$GOOS" == "illumos" ]; then
|
elif [ "$GOOS" == "illumos" ]; then
|
||||||
# illumos code generation requires a --illumos switch
|
# illumos code generation requires a --illumos switch
|
||||||
echo "$mksyscall -illumos -tags illumos,$GOARCH syscall_illumos.go |gofmt > zsyscall_illumos_$GOARCH.go";
|
echo "$mksyscall -illumos -tags illumos,$GOARCH syscall_illumos.go |gofmt > zsyscall_illumos_$GOARCH.go";
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/sys/unix/mkerrors.sh
generated
vendored
4
vendor/golang.org/x/sys/unix/mkerrors.sh
generated
vendored
|
|
@ -642,7 +642,7 @@ errors=$(
|
||||||
signals=$(
|
signals=$(
|
||||||
echo '#include <signal.h>' | $CC -x c - -E -dM $ccflags |
|
echo '#include <signal.h>' | $CC -x c - -E -dM $ccflags |
|
||||||
awk '$1=="#define" && $2 ~ /^SIG[A-Z0-9]+$/ { print $2 }' |
|
awk '$1=="#define" && $2 ~ /^SIG[A-Z0-9]+$/ { print $2 }' |
|
||||||
egrep -v '(SIGSTKSIZE|SIGSTKSZ|SIGRT|SIGMAX64)' |
|
grep -v 'SIGSTKSIZE\|SIGSTKSZ\|SIGRT\|SIGMAX64' |
|
||||||
sort
|
sort
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -652,7 +652,7 @@ echo '#include <errno.h>' | $CC -x c - -E -dM $ccflags |
|
||||||
sort >_error.grep
|
sort >_error.grep
|
||||||
echo '#include <signal.h>' | $CC -x c - -E -dM $ccflags |
|
echo '#include <signal.h>' | $CC -x c - -E -dM $ccflags |
|
||||||
awk '$1=="#define" && $2 ~ /^SIG[A-Z0-9]+$/ { print "^\t" $2 "[ \t]*=" }' |
|
awk '$1=="#define" && $2 ~ /^SIG[A-Z0-9]+$/ { print "^\t" $2 "[ \t]*=" }' |
|
||||||
egrep -v '(SIGSTKSIZE|SIGSTKSZ|SIGRT|SIGMAX64)' |
|
grep -v 'SIGSTKSIZE\|SIGSTKSZ\|SIGRT\|SIGMAX64' |
|
||||||
sort >_signal.grep
|
sort >_signal.grep
|
||||||
|
|
||||||
echo '// mkerrors.sh' "$@"
|
echo '// mkerrors.sh' "$@"
|
||||||
|
|
|
||||||
27
vendor/golang.org/x/sys/unix/str.go
generated
vendored
27
vendor/golang.org/x/sys/unix/str.go
generated
vendored
|
|
@ -1,27 +0,0 @@
|
||||||
// Copyright 2009 The Go Authors. All rights reserved.
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file.
|
|
||||||
|
|
||||||
//go:build aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd || solaris
|
|
||||||
// +build aix darwin dragonfly freebsd linux netbsd openbsd solaris
|
|
||||||
|
|
||||||
package unix
|
|
||||||
|
|
||||||
func itoa(val int) string { // do it here rather than with fmt to avoid dependency
|
|
||||||
if val < 0 {
|
|
||||||
return "-" + uitoa(uint(-val))
|
|
||||||
}
|
|
||||||
return uitoa(uint(val))
|
|
||||||
}
|
|
||||||
|
|
||||||
func uitoa(val uint) string {
|
|
||||||
var buf [32]byte // big enough for int64
|
|
||||||
i := len(buf) - 1
|
|
||||||
for val >= 10 {
|
|
||||||
buf[i] = byte(val%10 + '0')
|
|
||||||
i--
|
|
||||||
val /= 10
|
|
||||||
}
|
|
||||||
buf[i] = byte(val + '0')
|
|
||||||
return string(buf[i:])
|
|
||||||
}
|
|
||||||
10
vendor/golang.org/x/sys/unix/syscall.go
generated
vendored
10
vendor/golang.org/x/sys/unix/syscall.go
generated
vendored
|
|
@ -29,8 +29,6 @@ import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"strings"
|
"strings"
|
||||||
"unsafe"
|
"unsafe"
|
||||||
|
|
||||||
"golang.org/x/sys/internal/unsafeheader"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// ByteSliceFromString returns a NUL-terminated slice of bytes
|
// ByteSliceFromString returns a NUL-terminated slice of bytes
|
||||||
|
|
@ -82,13 +80,7 @@ func BytePtrToString(p *byte) string {
|
||||||
ptr = unsafe.Pointer(uintptr(ptr) + 1)
|
ptr = unsafe.Pointer(uintptr(ptr) + 1)
|
||||||
}
|
}
|
||||||
|
|
||||||
var s []byte
|
return string(unsafe.Slice(p, n))
|
||||||
h := (*unsafeheader.Slice)(unsafe.Pointer(&s))
|
|
||||||
h.Data = unsafe.Pointer(p)
|
|
||||||
h.Len = n
|
|
||||||
h.Cap = n
|
|
||||||
|
|
||||||
return string(s)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Single-word zero for use when we need a valid pointer to 0 bytes.
|
// Single-word zero for use when we need a valid pointer to 0 bytes.
|
||||||
|
|
|
||||||
32
vendor/golang.org/x/sys/unix/syscall_darwin.1_12.go
generated
vendored
32
vendor/golang.org/x/sys/unix/syscall_darwin.1_12.go
generated
vendored
|
|
@ -1,32 +0,0 @@
|
||||||
// Copyright 2019 The Go Authors. All rights reserved.
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file.
|
|
||||||
|
|
||||||
//go:build darwin && go1.12 && !go1.13
|
|
||||||
// +build darwin,go1.12,!go1.13
|
|
||||||
|
|
||||||
package unix
|
|
||||||
|
|
||||||
import (
|
|
||||||
"unsafe"
|
|
||||||
)
|
|
||||||
|
|
||||||
const _SYS_GETDIRENTRIES64 = 344
|
|
||||||
|
|
||||||
func Getdirentries(fd int, buf []byte, basep *uintptr) (n int, err error) {
|
|
||||||
// To implement this using libSystem we'd need syscall_syscallPtr for
|
|
||||||
// fdopendir. However, syscallPtr was only added in Go 1.13, so we fall
|
|
||||||
// back to raw syscalls for this func on Go 1.12.
|
|
||||||
var p unsafe.Pointer
|
|
||||||
if len(buf) > 0 {
|
|
||||||
p = unsafe.Pointer(&buf[0])
|
|
||||||
} else {
|
|
||||||
p = unsafe.Pointer(&_zero)
|
|
||||||
}
|
|
||||||
r0, _, e1 := Syscall6(_SYS_GETDIRENTRIES64, uintptr(fd), uintptr(p), uintptr(len(buf)), uintptr(unsafe.Pointer(basep)), 0, 0)
|
|
||||||
n = int(r0)
|
|
||||||
if e1 != 0 {
|
|
||||||
return n, errnoErr(e1)
|
|
||||||
}
|
|
||||||
return n, nil
|
|
||||||
}
|
|
||||||
108
vendor/golang.org/x/sys/unix/syscall_darwin.1_13.go
generated
vendored
108
vendor/golang.org/x/sys/unix/syscall_darwin.1_13.go
generated
vendored
|
|
@ -1,108 +0,0 @@
|
||||||
// Copyright 2019 The Go Authors. All rights reserved.
|
|
||||||
// Use of this source code is governed by a BSD-style
|
|
||||||
// license that can be found in the LICENSE file.
|
|
||||||
|
|
||||||
//go:build darwin && go1.13
|
|
||||||
// +build darwin,go1.13
|
|
||||||
|
|
||||||
package unix
|
|
||||||
|
|
||||||
import (
|
|
||||||
"unsafe"
|
|
||||||
|
|
||||||
"golang.org/x/sys/internal/unsafeheader"
|
|
||||||
)
|
|
||||||
|
|
||||||
//sys closedir(dir uintptr) (err error)
|
|
||||||
//sys readdir_r(dir uintptr, entry *Dirent, result **Dirent) (res Errno)
|
|
||||||
|
|
||||||
func fdopendir(fd int) (dir uintptr, err error) {
|
|
||||||
r0, _, e1 := syscall_syscallPtr(libc_fdopendir_trampoline_addr, uintptr(fd), 0, 0)
|
|
||||||
dir = uintptr(r0)
|
|
||||||
if e1 != 0 {
|
|
||||||
err = errnoErr(e1)
|
|
||||||
}
|
|
||||||
return
|
|
||||||
}
|
|
||||||
|
|
||||||
var libc_fdopendir_trampoline_addr uintptr
|
|
||||||
|
|
||||||
//go:cgo_import_dynamic libc_fdopendir fdopendir "/usr/lib/libSystem.B.dylib"
|
|
||||||
|
|
||||||
func Getdirentries(fd int, buf []byte, basep *uintptr) (n int, err error) {
|
|
||||||
// Simulate Getdirentries using fdopendir/readdir_r/closedir.
|
|
||||||
// We store the number of entries to skip in the seek
|
|
||||||
// offset of fd. See issue #31368.
|
|
||||||
// It's not the full required semantics, but should handle the case
|
|
||||||
// of calling Getdirentries or ReadDirent repeatedly.
|
|
||||||
// It won't handle assigning the results of lseek to *basep, or handle
|
|
||||||
// the directory being edited underfoot.
|
|
||||||
skip, err := Seek(fd, 0, 1 /* SEEK_CUR */)
|
|
||||||
if err != nil {
|
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
|
|
||||||
// We need to duplicate the incoming file descriptor
|
|
||||||
// because the caller expects to retain control of it, but
|
|
||||||
// fdopendir expects to take control of its argument.
|
|
||||||
// Just Dup'ing the file descriptor is not enough, as the
|
|
||||||
// result shares underlying state. Use Openat to make a really
|
|
||||||
// new file descriptor referring to the same directory.
|
|
||||||
fd2, err := Openat(fd, ".", O_RDONLY, 0)
|
|
||||||
if err != nil {
|
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
d, err := fdopendir(fd2)
|
|
||||||
if err != nil {
|
|
||||||
Close(fd2)
|
|
||||||
return 0, err
|
|
||||||
}
|
|
||||||
defer closedir(d)
|
|
||||||
|
|
||||||
var cnt int64
|
|
||||||
for {
|
|
||||||
var entry Dirent
|
|
||||||
var entryp *Dirent
|
|
||||||
e := readdir_r(d, &entry, &entryp)
|
|
||||||
if e != 0 {
|
|
||||||
return n, errnoErr(e)
|
|
||||||
}
|
|
||||||
if entryp == nil {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
if skip > 0 {
|
|
||||||
skip--
|
|
||||||
cnt++
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
reclen := int(entry.Reclen)
|
|
||||||
if reclen > len(buf) {
|
|
||||||
// Not enough room. Return for now.
|
|
||||||
// The counter will let us know where we should start up again.
|
|
||||||
// Note: this strategy for suspending in the middle and
|
|
||||||
// restarting is O(n^2) in the length of the directory. Oh well.
|
|
||||||
break
|
|
||||||
}
|
|
||||||
|
|
||||||
// Copy entry into return buffer.
|
|
||||||
var s []byte
|
|
||||||
hdr := (*unsafeheader.Slice)(unsafe.Pointer(&s))
|
|
||||||
hdr.Data = unsafe.Pointer(&entry)
|
|
||||||
hdr.Cap = reclen
|
|
||||||
hdr.Len = reclen
|
|
||||||
copy(buf, s)
|
|
||||||
|
|
||||||
buf = buf[reclen:]
|
|
||||||
n += reclen
|
|
||||||
cnt++
|
|
||||||
}
|
|
||||||
// Set the seek offset of the input fd to record
|
|
||||||
// how many files we've already returned.
|
|
||||||
_, err = Seek(fd, cnt, 0 /* SEEK_SET */)
|
|
||||||
if err != nil {
|
|
||||||
return n, err
|
|
||||||
}
|
|
||||||
|
|
||||||
return n, nil
|
|
||||||
}
|
|
||||||
90
vendor/golang.org/x/sys/unix/syscall_darwin.go
generated
vendored
90
vendor/golang.org/x/sys/unix/syscall_darwin.go
generated
vendored
|
|
@ -19,6 +19,96 @@ import (
|
||||||
"unsafe"
|
"unsafe"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
//sys closedir(dir uintptr) (err error)
|
||||||
|
//sys readdir_r(dir uintptr, entry *Dirent, result **Dirent) (res Errno)
|
||||||
|
|
||||||
|
func fdopendir(fd int) (dir uintptr, err error) {
|
||||||
|
r0, _, e1 := syscall_syscallPtr(libc_fdopendir_trampoline_addr, uintptr(fd), 0, 0)
|
||||||
|
dir = uintptr(r0)
|
||||||
|
if e1 != 0 {
|
||||||
|
err = errnoErr(e1)
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
var libc_fdopendir_trampoline_addr uintptr
|
||||||
|
|
||||||
|
//go:cgo_import_dynamic libc_fdopendir fdopendir "/usr/lib/libSystem.B.dylib"
|
||||||
|
|
||||||
|
func Getdirentries(fd int, buf []byte, basep *uintptr) (n int, err error) {
|
||||||
|
// Simulate Getdirentries using fdopendir/readdir_r/closedir.
|
||||||
|
// We store the number of entries to skip in the seek
|
||||||
|
// offset of fd. See issue #31368.
|
||||||
|
// It's not the full required semantics, but should handle the case
|
||||||
|
// of calling Getdirentries or ReadDirent repeatedly.
|
||||||
|
// It won't handle assigning the results of lseek to *basep, or handle
|
||||||
|
// the directory being edited underfoot.
|
||||||
|
skip, err := Seek(fd, 0, 1 /* SEEK_CUR */)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
|
||||||
|
// We need to duplicate the incoming file descriptor
|
||||||
|
// because the caller expects to retain control of it, but
|
||||||
|
// fdopendir expects to take control of its argument.
|
||||||
|
// Just Dup'ing the file descriptor is not enough, as the
|
||||||
|
// result shares underlying state. Use Openat to make a really
|
||||||
|
// new file descriptor referring to the same directory.
|
||||||
|
fd2, err := Openat(fd, ".", O_RDONLY, 0)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
d, err := fdopendir(fd2)
|
||||||
|
if err != nil {
|
||||||
|
Close(fd2)
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
defer closedir(d)
|
||||||
|
|
||||||
|
var cnt int64
|
||||||
|
for {
|
||||||
|
var entry Dirent
|
||||||
|
var entryp *Dirent
|
||||||
|
e := readdir_r(d, &entry, &entryp)
|
||||||
|
if e != 0 {
|
||||||
|
return n, errnoErr(e)
|
||||||
|
}
|
||||||
|
if entryp == nil {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if skip > 0 {
|
||||||
|
skip--
|
||||||
|
cnt++
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
reclen := int(entry.Reclen)
|
||||||
|
if reclen > len(buf) {
|
||||||
|
// Not enough room. Return for now.
|
||||||
|
// The counter will let us know where we should start up again.
|
||||||
|
// Note: this strategy for suspending in the middle and
|
||||||
|
// restarting is O(n^2) in the length of the directory. Oh well.
|
||||||
|
break
|
||||||
|
}
|
||||||
|
|
||||||
|
// Copy entry into return buffer.
|
||||||
|
s := unsafe.Slice((*byte)(unsafe.Pointer(&entry)), reclen)
|
||||||
|
copy(buf, s)
|
||||||
|
|
||||||
|
buf = buf[reclen:]
|
||||||
|
n += reclen
|
||||||
|
cnt++
|
||||||
|
}
|
||||||
|
// Set the seek offset of the input fd to record
|
||||||
|
// how many files we've already returned.
|
||||||
|
_, err = Seek(fd, cnt, 0 /* SEEK_SET */)
|
||||||
|
if err != nil {
|
||||||
|
return n, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return n, nil
|
||||||
|
}
|
||||||
|
|
||||||
// SockaddrDatalink implements the Sockaddr interface for AF_LINK type sockets.
|
// SockaddrDatalink implements the Sockaddr interface for AF_LINK type sockets.
|
||||||
type SockaddrDatalink struct {
|
type SockaddrDatalink struct {
|
||||||
Len uint8
|
Len uint8
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/sys/unix/syscall_freebsd_386.go
generated
vendored
2
vendor/golang.org/x/sys/unix/syscall_freebsd_386.go
generated
vendored
|
|
@ -61,7 +61,7 @@ func PtraceGetFsBase(pid int, fsbase *int64) (err error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
||||||
ioDesc := PtraceIoDesc{Op: int32(req), Offs: (*byte)(unsafe.Pointer(addr)), Addr: (*byte)(unsafe.Pointer(&out[0])), Len: uint32(countin)}
|
ioDesc := PtraceIoDesc{Op: int32(req), Offs: uintptr(unsafe.Pointer(addr)), Addr: uintptr(unsafe.Pointer(&out[0])), Len: uint32(countin)}
|
||||||
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
||||||
return int(ioDesc.Len), err
|
return int(ioDesc.Len), err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/sys/unix/syscall_freebsd_amd64.go
generated
vendored
2
vendor/golang.org/x/sys/unix/syscall_freebsd_amd64.go
generated
vendored
|
|
@ -61,7 +61,7 @@ func PtraceGetFsBase(pid int, fsbase *int64) (err error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
||||||
ioDesc := PtraceIoDesc{Op: int32(req), Offs: (*byte)(unsafe.Pointer(addr)), Addr: (*byte)(unsafe.Pointer(&out[0])), Len: uint64(countin)}
|
ioDesc := PtraceIoDesc{Op: int32(req), Offs: uintptr(unsafe.Pointer(addr)), Addr: uintptr(unsafe.Pointer(&out[0])), Len: uint64(countin)}
|
||||||
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
||||||
return int(ioDesc.Len), err
|
return int(ioDesc.Len), err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/sys/unix/syscall_freebsd_arm.go
generated
vendored
2
vendor/golang.org/x/sys/unix/syscall_freebsd_arm.go
generated
vendored
|
|
@ -57,7 +57,7 @@ func sendfile(outfd int, infd int, offset *int64, count int) (written int, err e
|
||||||
func Syscall9(num, a1, a2, a3, a4, a5, a6, a7, a8, a9 uintptr) (r1, r2 uintptr, err syscall.Errno)
|
func Syscall9(num, a1, a2, a3, a4, a5, a6, a7, a8, a9 uintptr) (r1, r2 uintptr, err syscall.Errno)
|
||||||
|
|
||||||
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
||||||
ioDesc := PtraceIoDesc{Op: int32(req), Offs: (*byte)(unsafe.Pointer(addr)), Addr: (*byte)(unsafe.Pointer(&out[0])), Len: uint32(countin)}
|
ioDesc := PtraceIoDesc{Op: int32(req), Offs: uintptr(unsafe.Pointer(addr)), Addr: uintptr(unsafe.Pointer(&out[0])), Len: uint32(countin)}
|
||||||
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
||||||
return int(ioDesc.Len), err
|
return int(ioDesc.Len), err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/sys/unix/syscall_freebsd_arm64.go
generated
vendored
2
vendor/golang.org/x/sys/unix/syscall_freebsd_arm64.go
generated
vendored
|
|
@ -57,7 +57,7 @@ func sendfile(outfd int, infd int, offset *int64, count int) (written int, err e
|
||||||
func Syscall9(num, a1, a2, a3, a4, a5, a6, a7, a8, a9 uintptr) (r1, r2 uintptr, err syscall.Errno)
|
func Syscall9(num, a1, a2, a3, a4, a5, a6, a7, a8, a9 uintptr) (r1, r2 uintptr, err syscall.Errno)
|
||||||
|
|
||||||
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
||||||
ioDesc := PtraceIoDesc{Op: int32(req), Offs: (*byte)(unsafe.Pointer(addr)), Addr: (*byte)(unsafe.Pointer(&out[0])), Len: uint64(countin)}
|
ioDesc := PtraceIoDesc{Op: int32(req), Offs: uintptr(unsafe.Pointer(addr)), Addr: uintptr(unsafe.Pointer(&out[0])), Len: uint64(countin)}
|
||||||
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
||||||
return int(ioDesc.Len), err
|
return int(ioDesc.Len), err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2
vendor/golang.org/x/sys/unix/syscall_freebsd_riscv64.go
generated
vendored
2
vendor/golang.org/x/sys/unix/syscall_freebsd_riscv64.go
generated
vendored
|
|
@ -57,7 +57,7 @@ func sendfile(outfd int, infd int, offset *int64, count int) (written int, err e
|
||||||
func Syscall9(num, a1, a2, a3, a4, a5, a6, a7, a8, a9 uintptr) (r1, r2 uintptr, err syscall.Errno)
|
func Syscall9(num, a1, a2, a3, a4, a5, a6, a7, a8, a9 uintptr) (r1, r2 uintptr, err syscall.Errno)
|
||||||
|
|
||||||
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
func PtraceIO(req int, pid int, addr uintptr, out []byte, countin int) (count int, err error) {
|
||||||
ioDesc := PtraceIoDesc{Op: int32(req), Offs: (*byte)(unsafe.Pointer(addr)), Addr: (*byte)(unsafe.Pointer(&out[0])), Len: uint64(countin)}
|
ioDesc := PtraceIoDesc{Op: int32(req), Offs: uintptr(unsafe.Pointer(addr)), Addr: uintptr(unsafe.Pointer(&out[0])), Len: uint64(countin)}
|
||||||
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
err = ptrace(PT_IO, pid, uintptr(unsafe.Pointer(&ioDesc)), 0)
|
||||||
return int(ioDesc.Len), err
|
return int(ioDesc.Len), err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
106
vendor/golang.org/x/sys/unix/syscall_illumos.go
generated
vendored
106
vendor/golang.org/x/sys/unix/syscall_illumos.go
generated
vendored
|
|
@ -10,8 +10,6 @@
|
||||||
package unix
|
package unix
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
|
||||||
"runtime"
|
|
||||||
"unsafe"
|
"unsafe"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
@ -79,107 +77,3 @@ func Accept4(fd int, flags int) (nfd int, sa Sockaddr, err error) {
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
//sys putmsg(fd int, clptr *strbuf, dataptr *strbuf, flags int) (err error)
|
|
||||||
|
|
||||||
func Putmsg(fd int, cl []byte, data []byte, flags int) (err error) {
|
|
||||||
var clp, datap *strbuf
|
|
||||||
if len(cl) > 0 {
|
|
||||||
clp = &strbuf{
|
|
||||||
Len: int32(len(cl)),
|
|
||||||
Buf: (*int8)(unsafe.Pointer(&cl[0])),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if len(data) > 0 {
|
|
||||||
datap = &strbuf{
|
|
||||||
Len: int32(len(data)),
|
|
||||||
Buf: (*int8)(unsafe.Pointer(&data[0])),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return putmsg(fd, clp, datap, flags)
|
|
||||||
}
|
|
||||||
|
|
||||||
//sys getmsg(fd int, clptr *strbuf, dataptr *strbuf, flags *int) (err error)
|
|
||||||
|
|
||||||
func Getmsg(fd int, cl []byte, data []byte) (retCl []byte, retData []byte, flags int, err error) {
|
|
||||||
var clp, datap *strbuf
|
|
||||||
if len(cl) > 0 {
|
|
||||||
clp = &strbuf{
|
|
||||||
Maxlen: int32(len(cl)),
|
|
||||||
Buf: (*int8)(unsafe.Pointer(&cl[0])),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if len(data) > 0 {
|
|
||||||
datap = &strbuf{
|
|
||||||
Maxlen: int32(len(data)),
|
|
||||||
Buf: (*int8)(unsafe.Pointer(&data[0])),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if err = getmsg(fd, clp, datap, &flags); err != nil {
|
|
||||||
return nil, nil, 0, err
|
|
||||||
}
|
|
||||||
|
|
||||||
if len(cl) > 0 {
|
|
||||||
retCl = cl[:clp.Len]
|
|
||||||
}
|
|
||||||
if len(data) > 0 {
|
|
||||||
retData = data[:datap.Len]
|
|
||||||
}
|
|
||||||
return retCl, retData, flags, nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func IoctlSetIntRetInt(fd int, req uint, arg int) (int, error) {
|
|
||||||
return ioctlRet(fd, req, uintptr(arg))
|
|
||||||
}
|
|
||||||
|
|
||||||
func IoctlSetString(fd int, req uint, val string) error {
|
|
||||||
bs := make([]byte, len(val)+1)
|
|
||||||
copy(bs[:len(bs)-1], val)
|
|
||||||
err := ioctl(fd, req, uintptr(unsafe.Pointer(&bs[0])))
|
|
||||||
runtime.KeepAlive(&bs[0])
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
// Lifreq Helpers
|
|
||||||
|
|
||||||
func (l *Lifreq) SetName(name string) error {
|
|
||||||
if len(name) >= len(l.Name) {
|
|
||||||
return fmt.Errorf("name cannot be more than %d characters", len(l.Name)-1)
|
|
||||||
}
|
|
||||||
for i := range name {
|
|
||||||
l.Name[i] = int8(name[i])
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func (l *Lifreq) SetLifruInt(d int) {
|
|
||||||
*(*int)(unsafe.Pointer(&l.Lifru[0])) = d
|
|
||||||
}
|
|
||||||
|
|
||||||
func (l *Lifreq) GetLifruInt() int {
|
|
||||||
return *(*int)(unsafe.Pointer(&l.Lifru[0]))
|
|
||||||
}
|
|
||||||
|
|
||||||
func (l *Lifreq) SetLifruUint(d uint) {
|
|
||||||
*(*uint)(unsafe.Pointer(&l.Lifru[0])) = d
|
|
||||||
}
|
|
||||||
|
|
||||||
func (l *Lifreq) GetLifruUint() uint {
|
|
||||||
return *(*uint)(unsafe.Pointer(&l.Lifru[0]))
|
|
||||||
}
|
|
||||||
|
|
||||||
func IoctlLifreq(fd int, req uint, l *Lifreq) error {
|
|
||||||
return ioctl(fd, req, uintptr(unsafe.Pointer(l)))
|
|
||||||
}
|
|
||||||
|
|
||||||
// Strioctl Helpers
|
|
||||||
|
|
||||||
func (s *Strioctl) SetInt(i int) {
|
|
||||||
s.Len = int32(unsafe.Sizeof(i))
|
|
||||||
s.Dp = (*int8)(unsafe.Pointer(&i))
|
|
||||||
}
|
|
||||||
|
|
||||||
func IoctlSetStrioctlRetInt(fd int, req uint, s *Strioctl) (int, error) {
|
|
||||||
return ioctlRet(fd, req, uintptr(unsafe.Pointer(s)))
|
|
||||||
}
|
|
||||||
|
|
|
||||||
43
vendor/golang.org/x/sys/unix/syscall_linux.go
generated
vendored
43
vendor/golang.org/x/sys/unix/syscall_linux.go
generated
vendored
|
|
@ -13,6 +13,7 @@ package unix
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"encoding/binary"
|
"encoding/binary"
|
||||||
|
"strconv"
|
||||||
"syscall"
|
"syscall"
|
||||||
"time"
|
"time"
|
||||||
"unsafe"
|
"unsafe"
|
||||||
|
|
@ -233,7 +234,7 @@ func Futimesat(dirfd int, path string, tv []Timeval) error {
|
||||||
func Futimes(fd int, tv []Timeval) (err error) {
|
func Futimes(fd int, tv []Timeval) (err error) {
|
||||||
// Believe it or not, this is the best we can do on Linux
|
// Believe it or not, this is the best we can do on Linux
|
||||||
// (and is what glibc does).
|
// (and is what glibc does).
|
||||||
return Utimes("/proc/self/fd/"+itoa(fd), tv)
|
return Utimes("/proc/self/fd/"+strconv.Itoa(fd), tv)
|
||||||
}
|
}
|
||||||
|
|
||||||
const ImplementsGetwd = true
|
const ImplementsGetwd = true
|
||||||
|
|
@ -1891,17 +1892,28 @@ func PrctlRetInt(option int, arg2 uintptr, arg3 uintptr, arg4 uintptr, arg5 uint
|
||||||
return int(ret), nil
|
return int(ret), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// issue 1435.
|
|
||||||
// On linux Setuid and Setgid only affects the current thread, not the process.
|
|
||||||
// This does not match what most callers expect so we must return an error
|
|
||||||
// here rather than letting the caller think that the call succeeded.
|
|
||||||
|
|
||||||
func Setuid(uid int) (err error) {
|
func Setuid(uid int) (err error) {
|
||||||
return EOPNOTSUPP
|
return syscall.Setuid(uid)
|
||||||
}
|
}
|
||||||
|
|
||||||
func Setgid(uid int) (err error) {
|
func Setgid(gid int) (err error) {
|
||||||
return EOPNOTSUPP
|
return syscall.Setgid(gid)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Setreuid(ruid, euid int) (err error) {
|
||||||
|
return syscall.Setreuid(ruid, euid)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Setregid(rgid, egid int) (err error) {
|
||||||
|
return syscall.Setregid(rgid, egid)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Setresuid(ruid, euid, suid int) (err error) {
|
||||||
|
return syscall.Setresuid(ruid, euid, suid)
|
||||||
|
}
|
||||||
|
|
||||||
|
func Setresgid(rgid, egid, sgid int) (err error) {
|
||||||
|
return syscall.Setresgid(rgid, egid, sgid)
|
||||||
}
|
}
|
||||||
|
|
||||||
// SetfsgidRetGid sets fsgid for current thread and returns previous fsgid set.
|
// SetfsgidRetGid sets fsgid for current thread and returns previous fsgid set.
|
||||||
|
|
@ -2240,7 +2252,7 @@ func (fh *FileHandle) Bytes() []byte {
|
||||||
if n == 0 {
|
if n == 0 {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
return (*[1 << 30]byte)(unsafe.Pointer(uintptr(unsafe.Pointer(&fh.fileHandle.Type)) + 4))[:n:n]
|
return unsafe.Slice((*byte)(unsafe.Pointer(uintptr(unsafe.Pointer(&fh.fileHandle.Type))+4)), n)
|
||||||
}
|
}
|
||||||
|
|
||||||
// NameToHandleAt wraps the name_to_handle_at system call; it obtains
|
// NameToHandleAt wraps the name_to_handle_at system call; it obtains
|
||||||
|
|
@ -2356,6 +2368,16 @@ func Setitimer(which ItimerWhich, it Itimerval) (Itimerval, error) {
|
||||||
return prev, nil
|
return prev, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//sysnb rtSigprocmask(how int, set *Sigset_t, oldset *Sigset_t, sigsetsize uintptr) (err error) = SYS_RT_SIGPROCMASK
|
||||||
|
|
||||||
|
func PthreadSigmask(how int, set, oldset *Sigset_t) error {
|
||||||
|
if oldset != nil {
|
||||||
|
// Explicitly clear in case Sigset_t is larger than _C__NSIG.
|
||||||
|
*oldset = Sigset_t{}
|
||||||
|
}
|
||||||
|
return rtSigprocmask(how, set, oldset, _C__NSIG/8)
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Unimplemented
|
* Unimplemented
|
||||||
*/
|
*/
|
||||||
|
|
@ -2414,7 +2436,6 @@ func Setitimer(which ItimerWhich, it Itimerval) (Itimerval, error) {
|
||||||
// RestartSyscall
|
// RestartSyscall
|
||||||
// RtSigaction
|
// RtSigaction
|
||||||
// RtSigpending
|
// RtSigpending
|
||||||
// RtSigprocmask
|
|
||||||
// RtSigqueueinfo
|
// RtSigqueueinfo
|
||||||
// RtSigreturn
|
// RtSigreturn
|
||||||
// RtSigsuspend
|
// RtSigsuspend
|
||||||
|
|
|
||||||
4
vendor/golang.org/x/sys/unix/syscall_linux_386.go
generated
vendored
4
vendor/golang.org/x/sys/unix/syscall_linux_386.go
generated
vendored
|
|
@ -41,10 +41,6 @@ func setTimeval(sec, usec int64) Timeval {
|
||||||
//sys sendfile(outfd int, infd int, offset *int64, count int) (written int, err error) = SYS_SENDFILE64
|
//sys sendfile(outfd int, infd int, offset *int64, count int) (written int, err error) = SYS_SENDFILE64
|
||||||
//sys setfsgid(gid int) (prev int, err error) = SYS_SETFSGID32
|
//sys setfsgid(gid int) (prev int, err error) = SYS_SETFSGID32
|
||||||
//sys setfsuid(uid int) (prev int, err error) = SYS_SETFSUID32
|
//sys setfsuid(uid int) (prev int, err error) = SYS_SETFSUID32
|
||||||
//sysnb Setregid(rgid int, egid int) (err error) = SYS_SETREGID32
|
|
||||||
//sysnb Setresgid(rgid int, egid int, sgid int) (err error) = SYS_SETRESGID32
|
|
||||||
//sysnb Setresuid(ruid int, euid int, suid int) (err error) = SYS_SETRESUID32
|
|
||||||
//sysnb Setreuid(ruid int, euid int) (err error) = SYS_SETREUID32
|
|
||||||
//sys Splice(rfd int, roff *int64, wfd int, woff *int64, len int, flags int) (n int, err error)
|
//sys Splice(rfd int, roff *int64, wfd int, woff *int64, len int, flags int) (n int, err error)
|
||||||
//sys Stat(path string, stat *Stat_t) (err error) = SYS_STAT64
|
//sys Stat(path string, stat *Stat_t) (err error) = SYS_STAT64
|
||||||
//sys SyncFileRange(fd int, off int64, n int64, flags int) (err error)
|
//sys SyncFileRange(fd int, off int64, n int64, flags int) (err error)
|
||||||
|
|
|
||||||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue