Nmap NSE 库分析 >>> nmap

时间:2022-07-23
本文章向大家介绍Nmap NSE 库分析 >>> nmap,主要内容包括其使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。

https://nmap.org/nsedoc/lib/nmap.html

0x00 简介

nmap模块是具有Nmap内部功能和数据结构的接口, 该API提供目标主机详细信息,例如端口状态和版本检测结果。它还提供了Nsock库的接口,以实现有效的网络 I/O

0x01 方法

方法名

功能介绍

address_family()

返回Nmap使用的协议簇, inet 或者 inet6

bind (addr, port)

设置socket的本地端口

clock ()

以秒为单位返回当前日期和时间

clock_ms ()

返回当前日期和时间(以毫秒为单位)

close ()

关闭一个连接

condvar (object)

为对象创建环境变量

connect (host, port, protocol)

建立一个连接

debugging ()

以非负整数形式返回调试级别

ethernet_close ()

关闭以太网接口

ethernet_open(interface_name)

开启一个以太网口以发送原始数据包

ethernet_send(packet)

发送原始以太网帧

fetchfile(filename)

搜索相对于Nmap的搜索路径的指定文件,并返回一个包含其路径的字符串(如果已找到并且可读)(对进程而言)。绝对路径和相对于当前目录的路径将不会被搜索。

get_info ()

get_interface ()

返回Nmap使用的网络接口的信息

get_interface_info(interface_name)

获取指定接口信息

get_payload_length ()

返回--data-length指定的 payload 的长度

get_port_state(host, port)

获取给定主机上端口的端口表

get_ports (host, port, proto, state)

遍历端口表以匹配给定主机的协议和状态

get_ssl_certificate ()

检索对等方的SSL证书。可以像表一样访问返回的值,并具有以下成员:

get_ttl ()

返回 --ttl 参数指定的值

have_ssl ()

确定Nmap是否使用SSL支持进行编译

ip_close ()

关闭原始IPv4 socket

ip_open ()

打开一个 socket 以发送原始IPv4数据包。

ip_send (packet, dst)

发送原始IPv4或IPv6数据包

is_privileged ()

返回脚本是否应该能够执行特权操作

list_interfaces ()

列出网络接口

log_write (file, string)

写入到log文件

mutex (object)

创建一个线程锁

new_dnet ()

创建一个新的dnet对象,用于发送原始数据包

new_socket(protocol, af)

建立一个新的NSE socket

new_try(handler)

创建一个新的异常处理

pcap_close ()

关闭一个pcap设备

pcap_open(device, snaplen, promisc, bpf)

打开一个套接字以捕获原始数据包

pcap_receive ()

pcap接收数据

receive ()

从 socket 接收数据

receive_buf(delimiter, keeppattern)

使用缓冲区和分隔符进行接收数据

receive_bytes(n)

接收 bytes数据

receive_lines (n)

接收多行数据

reconnect_ssl ()

用SSL重新连接打开的(已连接)套接字

resolve (host, family)

使用可选的地址族解析指定的主机名,并返回包含所有匹配地址的表

send (data)

发送数据

sendto (host, port, data)

将未连接的套接字上的数据发送到给定的目的地

set_port_state(host, port, state)

设置给定主机上端口的状态

set_port_version (host, port, probestate)

在端口上设置版本信息

set_timeout (t)

给 socket 设置超时时间

timing_level ()

以非负整数形式返回计时级别

verbosity ()

以非负数的形式返回 verbosity 等级

version_intensity ()

返回 version intensity 的值

0x02 方法实战

如果你想做端口扫描等等之类的,可以尝试把这些都试一试,但是这里还是以渗透为主,所以只挑选其中较为有意义的进行演示

nmap库是没有源码的,只有描述,我们根据描述进行摸索演示

0x001 new_socket

new_socket 有两个参数 protocol, af

  • protocol 协议,默认 tcp
  • af 协议簇,默认 inet

使用方法 local socket = nmap.new_socket('tcp', 'inet')

0x002 connect

connect 有三个参数 host, port, protocol,这个就不用多说了,返回值有两个

  • status true or false
  • Err code 如果status为false则返回错误代码

0x003 set_timeout

set_timeout 只有一个参数 t ,单位为 ms

0x004 send

send 函数只有一个参数 data ,要发送的数据,返回值有两个

  • status true or false
  • Err code 如果status为false则返回错误代码

0x005 receive

receive 函数没有参数,接收发送过来的数据,返回值有两个

  • status true or false
  • data 如果status为true 则返回数据

0x006 close

close 函数没有参数,用来关闭一个连接


下面来统一演示一下这些函数

---
--- Generated by EmmyLua(https://github.com/EmmyLua)
--- Created by root.
--- DateTime: 2020/1/2 上午9:39
---

local stdnse = require "stdnse"
local shortport = require "shortport"
local nmap = require "nmap"

description = [[
This is a test for http.lua's functions
]]

author = "test94"
license = "Same as Nmap--See https://nmap.org/book/man-legal.html"
categories = {"default"}

prerule = function()
    print("functest running")
end
portrule = shortport.http

action = function()
    local output = stdnse.output_table()
    -- 建立一个socket
    local socket = nmap.new_socket('tcp','inet')
    
    -- 设置超时时间
    socket:set_timeout(1000)
    
    -- 连接本地 80 端口
    socket:connect('127.0.0.1', 80, 'tcp')
    
    -- 发送数据
    socket:send('hello world')
    
    -- 接收数据
    local result, data = socket:receive()
    
    -- 关闭连接
    socket:close()
    output.result = result
    output.data = data
    return output
end

使用nc 监听本地端口,并且将字符 hi 通过 nc 传输

我们测试一下能否连接

可以看到成功接收到数据,数据为 hi

0x007 new_try

new_try 只有一个参数,这个参数是一个函数,一个方法 我们就在刚才的代码上加上异常处理

---
--- Generated by EmmyLua(https://github.com/EmmyLua)
--- Created by root.
--- DateTime: 2020/1/2 上午9:39
---

local stdnse = require "stdnse"
local shortport = require "shortport"
local nmap = require "nmap"

description = [[
This is a test for http.lua's functions
]]

author = "test94"
license = "Same as Nmap--See https://nmap.org/book/man-legal.html"
categories = {"default"}

prerule = function()
    print("functest running")
end
portrule = shortport.http

action = function()
    local output = stdnse.output_table()

    -- 建立一个socket
    local socket = nmap.new_socket('tcp','inet')

    --
    local catch = function()
        print("aaaaaaaaaa")
        socket:close()
    end

    local try = nmap.new_try(catch)

    -- 设置超时时间
    try(socket:set_timeout(1000))

    -- 连接本地 80 端口
    try(socket:connect('127.0.0.1', 80, 'tcp'))

    -- 发送数据
    try(socket:send('hello world'))

    -- 接收数据
    local result, data = try(socket:receive())

    -- 关闭连接
    socket:close()
    output.result = result
    output.data = data
    return output
end

我们首先定义了 catch ,我特意在catch中print了一下,表示运行到这里了,只有发生异常时候才会调用 catch 的内容 之前我们都是用nc传递数据,所以这边能够接收到数据,这回nc不再传递数据,此时就会产生异常了 测试一下,nc 仅监听

这边测试一下

可以看到成功打印的 aaaaaa,说明进入了异常处理代码块

0x008 mutex

mutex 是多线程的锁,了解过其他语言的多线程这个知识点的肯定都知道了,这个线程锁可以接受一下四个指令

  • lock 锁住
  • trylock 锁住,如果互斥锁繁忙,则返回false
  • done 放开
  • running 返回互斥锁状态,没有锁定返回nil,一般debug时候使用
local mutex = nmap.mutex("My Script's Unique ID");
function action(host, port)
  mutex "lock";
  -- Do critical section work - only one thread at a time executes this.
  mutex "done";
  return script_output;
end

主要在多线程中会涉及到


关于 Nmap 的相关知识就到此,剩下的更多知识就让我们在实战脚本编程中学习吧