获取系统空闲端口

端口取值范围

以下搜自互联网

一般用到的是1到65535,其中0不使用,1-1023为系统端口,也叫BSD保留端口;1024-65535为用户端口,又分为: BSD临时端口(1024-5000)和BSD服务器(非特权)端口(5001-65535).

0-1023: BSD保留端口,也叫系统端口,这些端口只有系统特许的进程才能使用;

1024-5000: BSD临时端口,一般的应用程序使用1024到4999来进行通讯;

5001-65535: BSD服务器(非特权)端口,用来给用户自定义端口.

常规方法

首先想到的方法有两种

  1. 取[1024, 65536)之间的一个随机数
  2. 循环取[1024, 65536)进行bind,直到bind成功为止

第一种方法,无法保证随机获取的端口是未占用的

第二种方法,不停的尝试bind,效率很低

使用InetSocketAddress

InetSocketAddress有三种构造函数

  • InetSocketAddress(int port)
  • InetSocketAddress(InetAddress addr, int port)
  • InetSocketAddress(String hostname, int port)

查看java源码中对第一种构造函数的解释

/**
 * Creates a socket address where the IP address is the wildcard address
 * and the port number a specified value.
 * <p>
 * A valid port value is between 0 and 65535.
 * A port number of {@code zero} will let the system pick up an
 * ephemeral port in a {@code bind} operation.
 * <p>
 * @param   port    The port number
 * @throws IllegalArgumentException if the port parameter is outside the specified
 * range of valid port values.
 */
public InetSocketAddress(int port) {
    this(InetAddress.anyLocalAddress(), port);
}

当入参port为0时,由系统自动分配一个临时端口,据此,便可以写出一个工具类,如下

/**
 * <p>
 * <b>系统空闲端口</b>
 * <p>
 * <pre>
 * 系统空闲端口
 * <b>
 * use like:<i><code>
 * SysFreePort.custom().getPort();
 * SysFreePort.custom().getPortAndFree();</code></i></b>
 * </pre>
 *
 * @author ManerFan 2015年2月3日
 */
public class SysFreePort {

    private static Random random = new Random();

    private Socket socket;

    /**
     * <p>
     * <b>获取系统空闲端口</b>
     * <p>
     * <pre>
     * 获取系统空闲端口,并占用该端口资源
     * </pre>
     *
     * @throws    IOException
     */
    public static SysFreePort custom() throws IOException {
        return new SysFreePort();
    }

    private SysFreePort() throws IOException {
        socket = new Socket();
        InetSocketAddress inetAddress = new InetSocketAddress(0);
        socket.bind(inetAddress);
    }

    /**
     * <p>
     * <b>释放端口资源</b>
     * <p>
     * <pre>
     * 释放该端口资源
     * </pre>
     *
     * @throws    IOException
     */
    public void freePort() throws IOException {
        if (null == socket || socket.isClosed()) {
            return;
        }

        socket.close();
    }

    /**
     * <p>
     * <b>返回端口</b>
     * <p>
     * <pre>
     * 返回端口,不释放该端口资源
     * </pre>
     */
    public int getPort() {
        if (null == socket || socket.isClosed()) {
            return -1;
        }

        return socket.getLocalPort();
    }

    /**
     * <p>
     * <b>返回端口</b>
     * <p>
     * <pre>
     * 返回端口并释放该端口资源
     * </pre>
     *
     * @throws    IOException
     */
    public int getPortAndFree() throws IOException {
        if (null == socket || socket.isClosed()) {
            return -1;
        }

        int port = socket.getLocalPort();
        socket.close();
        return port;
    }

    /**
     * <p>
     * <b>生成随机port</b>
     * <p>
     * <pre>
     * 在[start, end)间随机生成一个数字作为port
     * </pre>
     *
     * @param   start
     * @param   end
     * @return  int
     */
    public static int random(int start, int end) {
        return random.nextInt(Math.abs(end - start)) + start;
    }
}

使用SysFreePort port = SysFreePort.custom();获取系统空闲端口并占用(防止其他程序再次占用此端口)

使用port.getPort();返回获取到的空闲端口(不释放端口资源)

使用port.getPortAndFree();返回获取到的空闲端口,并释放该端口资源

使用port.freePort();释放该端口资源

时间: 2024-08-05 03:59:16

获取系统空闲端口的相关文章

获取系统空闲时间

//定义结构体 internal struct LASTINPUTINFO { public uint cbSize; public uint dwTime; } //引入系统API [DllImport("User32.dll")] private static extern bool GetLastInputInfo(ref LASTINPUTINFO plii); /// <summary> /// get the system idle time /// </

系统空闲时间判断&amp;命名验证

一.系统空闲时间判断 需要一个自动登录注销的功能,当鼠标移动和或者键盘输入的时候认为当前用户在线,否则过了设置时间就自动退出.好在前辈们留下了这样的一个类: MouseKeyBoardOperate: using System; using System.Runtime.InteropServices; namespace SCADA.RTDB.Framework.Helpers { /// <summary> /// Class MouseKeyBoardOperate /// </s

Java如何获取系统cpu、内存、硬盘信息

1 概述 前段时间摸索在Java中怎么获取系统信息包括cpu.内存.硬盘信息等,刚开始使用Java自带的包进行获取,但这样获取的内存信息不够准确并且容易出现找不到相应包等错误,所以后面使用sigar插件进行获取.下面列举出了这两种方式获取系统信息的方式及代码. 2 使用Java自带包获取系统信息 2.1 使用Java自带包获取系统信息代码如下: 2.1.1 Bytes.java public class Bytes { public static String substring(String

python获取系统状态psutil模块

python关于获取当前系统的状态系统性能信息模块 psutil  #可跨平台psutil是一个跨平台库,轻松获取系统运行的进程和系统利用率能实现ps.top.lso.nice.netstat.ifconfig.who.df.kill.freeionice.iostat.iotop.uptime.pidof.tty.taskset.pmap 这些命令的功能首先确定下当前系统有没有psutil模块import psutil如果有的话,就直接导入模块成功,如果没有,就会提示错误然后到官网上下载psu

C# 判断系统空闲(键盘、鼠标不操作一段时间)

利用windows API函数 GetLastInputInfo()来判断系统空闲 //添加引用 using System.Runtime.InteropServices; 1 // 创建结构体用于返回捕获时间 2 [StructLayout(LayoutKind.Sequential)] 3 struct LASTINPUTINFO 4 { 5 // 设置结构体块容量 6 [MarshalAs(UnmanagedType.U4)] 7 public int cbSize; 8 // 捕获的时间

获取系统cpu使用率(linux C)

typedef struct cpu_occupy_ //定义一个cpu occupy的结构体 { char name[20]; //定义一个char类型的数组名name有20个元素 unsigned int user; //定义一个无符号的int类型的user unsigned int nice; //定义一个无符号的int类型的nice unsigned int system; //定义一个无符号的int类型的system unsigned int idle; //定义一个无符号的int类型

C#判断一个端口是不是被占用以及返回一个空闲端口

一.引言 在最近的工作当中,用到了 Socket 通信,然后要给 Socket 服务器端的监听获取一个空闲的本地监听端口. 对于这个获取方法要满足如下几点的要求: 这个端口不能是别的程序所使用的端口: 这个获取要支持异步,即多个线程同时获取不会出现返回多个相同的空闲端口(即线程安全): 这端口要有效的遍历一个区域内的端口,直到返回一个可用的空闲端口: 二.实现方法 网上的实现方法主要有两种: 1. 使用 .NET 提供的 IPGlobaProperties.GetIPGlobaPropertie

2016-06-02 获取系统当前日期和时间并显示在某个元素上

1. <script> window.onload=function(){ getDateAndTime(); setInterval(getDateAndTime,1000); } //获取系统的日期和时间并显示在某个元素上 function getDateAndTime(){ var myDate = new Date(); var year = myDate.getFullYear(); var month = myDate.getMonth()+1; var day = myDate.

Android如何获取系统高度、标题栏和状态栏高度

在android应用中,有时需要计算个View的位置,导致需要计算状态栏高度,标题栏高度等信息.为以后方便,在此做个简单记录. 晒代码前先了解一下android屏幕区域的划分,如下图(该图引用自此文http://www.iteye.com/topic/828830 ) 1. 屏幕区域的获取 [java] view plaincopy activity.getWindowManager().getDefaultDisplay(); 2.应用区域的获取 [java] view plaincopy R