Java网络编程实现的简单端口扫描器示例

本文实例讲述了Java网络编程实现的简单端口扫描器。分享给大家供大家参考,具体如下:

在计算机网络的学习中,不由得觉得这门课的零碎知识点异常之多,同时因为学习的课本是老外的教材——自顶向下方法,因此学习起来不免觉得吃力,但是从老外的教材里更能从一定高度理解计算机网络的知识体系,也是乐在其中,同时做英语的习题感觉也很有趣味,从各方面来说可以说是获益良多,认识了很多专业词汇。节课之后,便想做一个简单的端口扫描器,用的语言是java,因为实现界面很简单,同时也有封装好的Socket类可以使用,主要思路如下:

在主程序界面里输入指定主机名或ip地址,按下start按钮,就可以扫描主机的常用端口是否打开。内部设置了常用端口号:21, 22, 23, 25, 26, 69, 80, 110, 143,443, 465, 995, 1080, 1158,1433, 1521, 2100, 3128, 3306, 3389,7001, 8080, 8081, 9080, 9090, 43958。也可以自行修改。程序实现原理就是利用Java建立Socket去连接目标ip的指定端口,如果能连接上就证明该端口开放。反之,若在超时之前都没有连接上,则该端口是关闭的,同时会产生异常。同时考虑到单线程操作效率较低,也利用了Java可以多线程编程的特点,使用了多线程扫描目标主机的一个端口是否开放,因此最终显示结果中端口的排列顺序是随机的,且内部设定最多同时运行10个线程(可以根据实际情况更改)。

主要运用的网络知识就是套接字的使用。以及java内部的List容器,java的界面设计,界面布局,以及简单的泛型编程的用法。

主要代码如下:

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.io.IOException;
import java.net.InetAddress;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.net.SocketAddress;
import java.net.UnknownHostException;
import java.util.Arrays;
import java.util.LinkedList;
import java.util.List;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import javax.swing.BorderFactory;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextArea;
import javax.swing.JTextField;
public class ScanPort extends JFrame {
 /**
  * 端口扫描启动主程序
  */
 private static final long serialVersionUID = 1L;
 String str1 = " 常见端口有:";
 String str2 = "ftp:21,22,telnet:23,smtp:25,http:80";
 String str3 = "dns:53,tftp:69,snmp:161,162";
 String str4 = "1158,1433,1521,2100,3128,26,69";
 String str5 = "3306,3389,7001,8080,8081,110,143";
 String str6 = "9080,9090,43958,443,465,995,1080";
 JButton jb1 = new JButton("strat");
 JTextArea jta = new JTextArea();
 JScrollPane jsp = new JScrollPane(jta);
 JTextField jtf = new JTextField(17);
 String IP = "";//待扫描IP或域名
 List <Integer>portList = new LinkedList<Integer>();// 定义一个List容器表示扫描的团口的List集合
 Integer[] ports = new Integer[] { 21, 22, 23, 25, 26, 53,69, 80, 110, 143,
   443,465,69,161,162,135,995,1080,1158,1433,1521,2100, 3128, 3306, 3389,
   7001, 8080, 8081, 9080, 9090, 43958 ,135,445,1025,1026,1027,1028,1055,5357};
 // 常见端口集合
 public ScanPort() {
  this.add(getPanel(), BorderLayout.SOUTH);
  jsp.setBorder(BorderFactory.createEtchedBorder());
  jsp.setBackground(Color.cyan);
  this.add(jsp, BorderLayout.CENTER);
  this.add(getPanel2(), BorderLayout.NORTH);
  this.add(getPanel3(), BorderLayout.WEST);
  this.setBounds(300, 60, 600, 600);
  this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
  this.setTitle("ScanPort");
  jta.setTabSize(4);
  jta.setFont(new Font("标楷体", Font.BOLD, 16));
  jta.setLineWrap(true);// 激活自动换行功能
  jta.setWrapStyleWord(true);// 激活断行不断字功能
  portList.addAll(Arrays.asList(ports));
  //将ports中的值加入到set中,并去掉重复的
  jb1.addActionListener(new ActionListener() {
   @Override
   public void actionPerformed(ActionEvent e) {
    // TODO Auto-generated method stub
    IP = jta.getText();
    //ip为文本框内输入的字符串
    scanPorts(IP, portList, 10, 800);
    //超时时间设定为800,线程数设定为10
   }
  });
  this.setVisible(true);
 }
 /**
  * 多线程扫描目标主机指定List端口集合的开放情况
  *
  * @param ip
  *   待扫描IP或域名
  * @param portList
  *   待扫描的端口的List集合
  * @param threadNumber
  *   线程数
  * @param timeout
  *   连接超时时间
  * */
 public void scanPorts(String ip, List<Integer> portSet,int threadNumber, int timeout) {
  ExecutorService threadPool = Executors.newCachedThreadPool();
  //线程池
  for (int i = 0; i < threadNumber; i++) {
   //10个线程 加入到线程池里
   ScanMethod scanMethod2 = new ScanMethod(ip, portSet,threadNumber, i, timeout);
   threadPool.execute(scanMethod2);
  }
  threadPool.shutdown();
  while (true) {
   if (threadPool.isTerminated()) {
    System.out.println("扫描结束");
    break;
   }
   try {
    Thread.sleep(1000);
   } catch (InterruptedException e) {
    e.printStackTrace();
   }
  }// end of while
 }
 /*
  * 扫描方式:针对一个待扫描的端口的List集合进行扫描
  */
 private class ScanMethod implements Runnable {
  private String ip; // 目标IP
  private List<Integer> portList; // 待扫描的端口的List集合
  private int threadNumber, serial, timeout; // 线程数,这是第几个线程,超时时间
  public ScanMethod(String ip, List<Integer> portList, int threadNumber,int serial, int timeout) {
   this.ip = ip;
   this.portList = portList;
   this.threadNumber = threadNumber;
   this.serial = serial;
   this.timeout = timeout;
  }
  public void run() {
   int port = 0;
   Integer[] ports = portList.toArray(new Integer[portList.size()]); // List转数组
   try {
    InetAddress address = InetAddress.getByName(ip); //如果输入的是主机名,尝试获取ip地址
    Socket socket;//定义套接字
    SocketAddress socketAddress;//传递ip和端口
    if (ports.length < 1)
     //若数组没有元素,返回,不执行
     return;
    for (port = 0 + serial; port <= ports.length - 1; port += threadNumber) {
     //每次运行10个线程
     socket = new Socket();
     //为对象分配内存空间
     socketAddress = new InetSocketAddress(address, ports[port]);
     try {
      socket.connect(socketAddress, timeout);
      //对目标主机的指定端口进行连接,超时后连接失败
      socket.close();
      //关闭端口
      System.out.println("端口 " + ports[port] + " :开放");
      jta.append("端口 " + ports[port] + " :开放\n");
      //在文本区域里更新消息
     } catch (IOException e) {
      System.out.println("端口 " + ports[port] + " :关闭");
      jta.append("端口 " + ports[port] + " :关闭\n");
      //产生异常表示端口关闭
     }
    }
   } catch (UnknownHostException e) {
    e.printStackTrace();
   }
  }
  //end of run()
 }//end of ScanMethod
 public JPanel getPanel() {
  JPanel jp = new JPanel();
  jp.add(jb1, BorderLayout.CENTER);
  jp.setBorder(BorderFactory.createRaisedBevelBorder());
  jp.setBackground(Color.lightGray);
  return jp;
 }
 public JPanel getPanel2() {
  JPanel jp = new JPanel();
  JLabel jl = new JLabel();
  jl.setText("请输入主机名或ip地址,将扫描该主机的常见端口号:");
  jp.add(jl);
  jp.add(jtf);
  jp.setBorder(BorderFactory.createRaisedBevelBorder());
  jp.setBackground(Color.LIGHT_GRAY);
  return jp;
 }
 public JPanel getPanel3() {
  JLabel jl1 = new JLabel(str1);
  JLabel jl2 = new JLabel(str2);
  JLabel jl3 = new JLabel(str3);
  JLabel jl4 = new JLabel(str4);
  JLabel jl5 = new JLabel(str5);
  JLabel jl6 = new JLabel(str6);
  JPanel jp = new JPanel();
  jp.setLayout(new GridLayout(6, 1));
  jp.add(jl1);
  jp.add(jl2);
  jp.add(jl3);
  jp.add(jl4);
  jp.add(jl5);
  jp.add(jl6);
  jp.setBorder(BorderFactory.createEtchedBorder());
  //蚀刻边框
  return jp;
 }
 public static void main(String[] args) {
  new ScanPort();
 }
}

更多关于java相关内容感兴趣的读者可查看本站专题:《Java网络编程技巧总结》、《Java Socket编程技巧总结》、《Java文件与目录操作技巧汇总》、《Java数据结构与算法教程》、《Java操作DOM节点技巧总结》和《Java缓存操作技巧汇总》

希望本文所述对大家java程序设计有所帮助。

(0)

相关推荐

  • java中获取当前服务器的Ip地址的方法

    1.tomcat是一款免费的开源Web服务器,如果部署在本地,那么对应的那么为localhost,对应地址为127.0.0.1. 例子:可以通过http://localhost:8080/项目root值访问,也可以通过http://127.0.0.1/项目root值访问. 如果部署在服务器(linux)系统类,则需要通过服务器的Ip地址进行访问. 2.下面说说怎么获取Ip地址: 获取本地的Ip地址: public static void main(String[] args) { try { I

  • 微信端口及协议分析(java、C版)

    有朋友公司需求如下,手机通过WIFI连接上网,而老板要求,员工使用手机只能上微信,而不能上其他网页和看在线视频.上网搜索了微信使用协议和端口. 微信通过TCP方式来进行通讯. TCP通讯方式分析 通讯端口分析 远程通讯端口范围: 80,443,80,443,8080. HTTP方式分析 在特征分析中,发现微信会采用HTTP协议进行通讯. 连接的主机(Host)(正则表达式)为:^short\.weixin\.qq\.com,^(mmsns|mmbiz)\.qpic\.cn. TLS方式分析 在特

  • java编程实现获取服务器IP地址及MAC地址的方法

    本文实例讲述了java编程实现获取服务器IP地址及MAC地址的方法.分享给大家供大家参考,具体如下: 已测系统: windows linux unix 排除127.0.0.1 和 0.0.0.0.1等非正常IP import java.net.InetAddress; import java.net.NetworkInterface; import java.net.SocketException; import java.util.ArrayList; import java.util.Enu

  • java 获取服务器真实IP的实例

     java 获取服务器真实IP的实例 前言: 根据操作系统的不同,获取的结果不同,故需要区分系统,分别获取 实现代码: import java.io.BufferedReader; import java.io.IOException; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.PrintWriter; import java.io.UnsupportedEncodingExcept

  • java替换url的域名和端口方法

    实例如下: public static String replaceDomainAndPort(String domain,String port,String url){ String url_bak = ""; if(url.indexOf("//") != -1 ){ String[] splitTemp = url.split("//"); url_bak = splitTemp[0]+"//"; if(port !=

  • Java查看本机端口是否被占用源码

    记得以前在写程序的时候,有一次需要查看端口的被占用情况,虽然我不会,但是有人会.所以通过网上查找相关的文章,具体如下. 127.0.0.1代表本机 主要原理是: Socket socket = new Socket(Address,port);#address代表主机的IP地址,port代表端口号 如果对该主机的特定端口号能建立一个socket,则说明该主机的该端口在使用. /** * @author MrBread * @date 2017年6月18日 * @time 下午3:14:05 *

  • Java获取服务器IP及端口的方法实例分析

    本文实例讲述了Java获取服务器IP及端口的方法.分享给大家供大家参考,具体如下: 前几天写过一个获取远程服务器的IP和端口的程序,从网上查了一些资料顺便加一些自己的理解,希望对大家有所帮助: struts2 获取request HttpServletRequest requet=ServletActionContext.getRequest(); requet.getScheme()+"://"+requet.getServerName()+":"+requet.

  • java实现服务器文件打包zip并下载的示例(边打包边下载)

    使用该方法,可以即时打包文件,一边打包一边传输,不使用任何的缓存,让用户零等待! 复制代码 代码如下: /** *  * mySocket 客户端 Socket * @param file 待打包的文件夹或文件 * @param fileName 打包下载的文件名 * @throws IOException */ private void down(File file, String fileName) throws IOException { OutputStream outputStream

  • Java网络编程实现的简单端口扫描器示例

    本文实例讲述了Java网络编程实现的简单端口扫描器.分享给大家供大家参考,具体如下: 在计算机网络的学习中,不由得觉得这门课的零碎知识点异常之多,同时因为学习的课本是老外的教材--自顶向下方法,因此学习起来不免觉得吃力,但是从老外的教材里更能从一定高度理解计算机网络的知识体系,也是乐在其中,同时做英语的习题感觉也很有趣味,从各方面来说可以说是获益良多,认识了很多专业词汇.节课之后,便想做一个简单的端口扫描器,用的语言是java,因为实现界面很简单,同时也有封装好的Socket类可以使用,主要思路

  • Java网络编程之简单的服务端客户端应用实例

    本文实例讲述了Java网络编程之简单的服务端客户端应用.分享给大家供大家参考.具体如下: 在Java中,我们使用java.net.Socket及其相关类来完成有关网络的相关功能.Socket类非常简单易用,因为Java技术隐藏了建立网络连接和通过连接发送数据的复杂过程.下面所说的内容只适用于TCP协议. 一.连接到服务器 我们可以使用Socket类的构造函数来打开一个套接字,如 Socket sk = new Socket("210.0.235.14",13); 其中,210.0.23

  • Java网络编程实例——简单模拟在线聊天

    1.前提知识 需要知道简单的IO流操作,以及简单的UDP发送数据包的原理. 需要用到的类:DatagramSocket.DatagramPacket UDP数据包基于DatagramSocket发送和接收,DatagramPacket用于封装数据包 看下案例: 客户端发送消息: 正常情况下从控制台读信息,封装到DatagramPacket之中,再由DatagramSocket的send方法发出 读取到bye的时候退出聊天 public class UdpOnlineClient { public

  • 详解Java网络编程

    一.网络编程 1.1.概述 1.计算机网络是通过传输介质.通信设施和网络通信协议,把分散在不同地点的计算机设备互连起来,实现资源共享和数据传输的系统.网络编程就就是编写程序使联网的两个(或多个)设备(例如计算机)之间进行数据传输.Java语言对网络编程提供了良好的支持,通过其提供的接口我们可以很方便地进行网络编程. 2.Java是 Internet 上的语言,它从语言级上提供了对网络应用程 序的支持,程序员能够很容易开发常见的网络应用程序. 3.Java提供的网络类库,可以实现无痛的网络连接,联

  • 老生常谈Java网络编程TCP通信(必看篇)

    Socket简介: Socket称为"套接字",描述IP地址和端口.在Internet上的主机一般运行多个服务软件,同时提供几种服务,每种服务都打开一个Socket,并绑定在一个端口上,不同的端口对应于不同的服务.Socket和ServerSocket类位于java.net包中.ServerSocket用于服务端,Socket是建立网络连接时使用的.连接成功时,应用程序两端都会产生一个Socket实例,通过操作这个实例完成所需会话. Socket常用方法: -int getLocalP

  • java网络编程基础知识介绍

    网络基础知识 1.OSI分层模型和TCP/IP分层模型的对应关系 这里对于7层模型不展开来讲,只选择跟这次系列主题相关的知识点介绍. 2.七层模型与协议的对应关系 网络层 ------------ IP(网络之间的互联协议) 传输层 ------------ TCP(传输控制协议).UDP(用户数据报协议) 应用层 ------------ Telnet(Internet远程登录服务的标准协议和主要方式).FTP(文本传输协议).HTTP(超文本传送协议) 3.IP地址和端口号 1.ip地址用于

  • 基于Java网络编程和多线程的多对多聊天系统

    1.前言 程序实现基于星型结构(服务器接收来自各个客户端发送的信息,然后将信息传递给其他客户端界面并在其他客户端界面显示发送的信息) 2.类图 3.代码 客户端代码: package netProgram; import java.io.IOException; import java.net.Socket; import java.net.SocketAddress; public class Client implements ScreenInputInterface{ private So

  • Java网络编程TCP实现文件上传功能

    本文实例为大家分享了Java网络编程TCP实现文件上传的具体代码,供大家参考,具体内容如下 上一篇博客,用网络编程TCP 实现聊天,这次实现文件上传. 客户端: package com.kuang.lesson02; import java.io.*; import java.net.InetAddress; import java.net.Socket; //客户端 public class TcpClientDemo2 { public static void main(String[] a

  • Java网络编程实现多线程聊天

    本文实例为大家分享了Java网络编程实现多线程聊天的具体代码,供大家参考,具体内容如下 聊天程序如果是单线程,会导致没人只能说一句,并且说了以后,必须等到另一个人的回复,才能说第二句.收发都在主线程中,不能同时进行. 解决方法: 将收发放到两个不同的线程 1. SendThread 发送消息线程 2. RecieveThread 接受消息线程 3. Server一旦接受到连接,就启动收发两个线程 4. Client 一旦建立了连接,就启动收发两个线程 多线程聊天 1 SendThread pac

  • Java网络编程之入门篇

    目录 一.网络基础 二.网络协议 URL类 一.网络基础 二.网络协议 实现TCP的网络编程 例子1:客户端发送信息给服务端,服务端将数据显示在控制台上 public class TCPTest1 { //客户端 @Test public void client() { Socket socket = null; OutputStream os = null; try { //1.创建Socket对象,指明服务器端的ip和端口号 InetAddress inet = InetAddress.ge

随机推荐