AQu*_*rky 4 windows port http windows-10
我发现我的 Windows 10 机器上有许多端口,它们 (1) 没有被任何进程使用,并且 (2) 我无法监听。
我在尝试运行使用端口 3000 的节点服务器时发现了这个问题。我发现了许多关于这个主题的问题。这是典型的: Node.js 端口 3000 已在使用中,但实际上并未使用?
这个问题和类似问题的所有受访者都建议使用“netstat -ano”来查找正在使用该端口并杀死它的进程。
我发现有大量与进程无关的端口被阻塞。这与 AV 或防火墙无关。我关闭了防火墙,我只有 Windows Defender AV。
我写了一个程序来监听 127.0.0.1 上 3000 到 5000 之间的端口。
int port = 3000;
while(port <= 5001)
{
try
{
ListenOnPort(port);
++port;
}
catch (Exception ex)
{
Console.WriteLine($"Listen on {port} failed: {ex.Message}");
++port;
}
}
Run Code Online (Sandbox Code Playgroud)
ListenOnPort 在哪里...
private static void ListenOnPort(int v)
{
var uri = new UriBuilder("http", "127.0.0.1", v);
HttpListener listener = new HttpListener();
listener.Prefixes.Add(uri.Uri.ToString());
Console.WriteLine($"Listening on {v}");
listener.TimeoutManager.IdleConnection = new TimeSpan(0, 0, 1);
listener.Start();
var task = listener.GetContextAsync();
if(task.Wait(new TimeSpan(0,0,1)))
{
HttpListenerResponse response = task.Result.Response;
// Construct a response.
string responseString = "<HTML><BODY> Hello world!</BODY></HTML>";
byte[] buffer = System.Text.Encoding.UTF8.GetBytes(responseString);
// Get a response stream and write the response to it.
response.ContentLength64 = buffer.Length;
System.IO.Stream output = response.OutputStream;
output.Write(buffer, 0, buffer.Length);
// You must close the output stream.
output.Close();
}
listener.Stop();
}
Run Code Online (Sandbox Code Playgroud)
该程序产生类似于此的输出......
Listening on 3000
Listen on 3000 failed: The process cannot access the file because it is being used by another process
Listening on 3001
Listen on 3001 failed: The process cannot access the file because it is being used by another process
Listening on 3002
Listen on 3002 failed: The process cannot access the file because it is being used by another process
Listening on 3003
Listen on 3003 failed: The process cannot access the file because it is being used by another process
Listening on 3004
Listen on 3004 failed: The process cannot access the file because it is being used by another process
Listening on 3005
Listen on 3005 failed: The process cannot access the file because it is being used by another process
Listening on 3006
Listening on 3007
Listening on 3008
Listening on 3009
Listening on 3010
Run Code Online (Sandbox Code Playgroud)
我发现在 3000 和 5000 之间,有 624 个端口被阻塞。同时,“netstat -ano”显示该范围内正好有 5 个端口在使用。那么是什么阻塞了 619 个其他端口?
AQu*_*rky 11
对...
在寻找其他东西时,我找到了答案(至少是问题的根源)。我无法连接到这些端口的原因是因为它们都是 Windows 上排除端口范围的一部分。要查看排除的端口,请使用...
$ netsh int ipv4 show excludedportrange tcp
Run Code Online (Sandbox Code Playgroud)
神奇的是,这里列出了我无法连接的所有端口。这些排除的端口范围显然来自于我已经安装的 HyperV 和 Docker。显然有一种方法可以恢复端口......这并不容易,因为它涉及卸载 Docker 和 HyperV,然后为自己保留端口范围,然后重新安装 HyperV 和 Docker。不值得。既然我只知道如何找到我无法使用的端口,我就不会使用它们!
我们设法在您无法更改端口号(如不可配置的应用程序)的情况下解决此问题。
当您发出命令时:
netsh int ip show excludedportrange protocol=tcp
Run Code Online (Sandbox Code Playgroud)
您将得到一个包含保留端口范围列表的输出:
Protocol tcp Port Exclusion Ranges
Start Port End Port
---------- --------
33474 33573
50000 50059 *
58159 58258
58259 58358
58359 58458
58459 58558
58559 58658
58659 58758
58759 58858
* - Administered port exclusions.
Run Code Online (Sandbox Code Playgroud)
最可能的原因是 Windows Hyper-V(微软的硬件虚拟化产品)保留了随机端口范围(通常为 100 个端口块)。这变得很痛苦,因为如果您正在开发使用多个端口的应用程序或更大的解决方案,有时您会遇到冲突,有时在重新启动系统后不会发生冲突。
要查找“动态端口范围”,您可以发出以下命令:
netsh int ipv4 show dynamicport tcp
Run Code Online (Sandbox Code Playgroud)
答案:
Protocol tcp Dynamic Port Range
---------------------------------
Start Port : 1024
Number of Ports : 64511
Run Code Online (Sandbox Code Playgroud)
您可以指示 Windows 将此范围修改为冲突区域之外。假设您的开发在端口 60000 以下,您可以发出以下命令来限制动态端口范围(您必须具有管理员权限):
netsh int ipv4 set dynamic tcp start=60001 num=5534
Run Code Online (Sandbox Code Playgroud)
要使 Hyper-V(以及一般的 Windows)使用这个新的动态范围,您必须重新启动系统。
现在,如果我们请求排除的端口范围:
netsh int ip show excludedportrange protocol=tcp
Run Code Online (Sandbox Code Playgroud)
响应已更改:
Protocol tcp Port Exclusion Ranges
Start Port End Port
---------- --------
50000 50059 *
63904 64003
64004 64103
64105 64204
64205 64304
64305 64404
64405 64504
64505 64604
64605 64704
* - Administered port exclusions.
Run Code Online (Sandbox Code Playgroud)
仅“受管理的端口排除”保留在端口 60001 以下