shithub: scripts

ref: 3519f1d58ff78407227adb5a3a202d7a4e626a93
dir: /lib/lua/nseport/nmap.lua/

View raw version
---
-- nmap.lua is a drop-in replacement for the nmap lua api
--

local p9 = require "p9"

---
-- nmap functions
--

-- clock
local function clock()
  return os.clock()
end

-- log function
local function log_write (where, ...)
  if where == "stdout" then
    io.stdout:write(...)
  else
    io.stderr:write(...)
  end  
end

-- debugging
local function debugging ()
  local nse_debug_level
  nse_debug_level = tonumber(os.getenv("NSE_DEBUG"))
  if nse_debug_level == nil then
    return 0
  end
  return nse_debug_level
end

-- verbosity
local function verbosity ()
  local nse_verbose_level
  nse_verbose_level = tonumber(os.getenv("NSE_VERBOSE"))
  if nse_verbose_level == nil then
    return 0
  end
  return nse_verbose_level
end

---
-- plan9 "socket" api
--

SOCKET_MAXSZ = 4096

local function sleep (seconds)
  p9.sleep(seconds * 1000)
end

Socket = {
  new = function(self, proto)
    local o = {}
    setmetatable(o, self)
    self.__index = self
    if proto ~= nil then
      self.proto = proto
    end
    return o
  end,

  -- connect to host and port
  connect = function(self, host, port)
    local cs_fd, clone_fd, data_fd, ctl_fd, proto
    local data_fid, conn_param, clone_path, addr

    if self.proto == nil then
      proto = "tcp"
    else
      proto = self.proto
    end

    cs_fd = io.open("/net/cs", "r+")
    cs_fd:write(proto.."!"..host.."!"..port)
	cs_fd:seek("set")
	conn_param = cs_fd:read("a")
	cs_fd:close()

    clone_path = string.sub(conn_param, 0, string.find(conn_param, " ") - 1)
    addr = string.sub(conn_param, string.find(conn_param, " ") + 1)

    clone_fd = io.open(clone_path, "r+")
    data_fid = clone_fd:read()
    clone_fd:seek("set")
    local n = clone_fd:write("connect "..addr.."\n")
    clone_fd:flush()

    data_fd = io.open("/net/"..proto.."/"..data_fid.."/data", "r+")

    self.data_fd = data_fd
    self.clone_fd = clone_fd

    return true
  end,

  -- close connection and file descriptors
  close = function(self)
    self.data_fd:close()
    self.clone_fd:write("close\n")
	self.clone_fd:close()
  end,

  -- dummy compat function
  set_timeout = function(self, t)
    self.timeout = t
  end,

  -- send data
  send = function(self, d)
    local fd = self.data_fd:write(d)
    self.data_fd:flush()
    if fd == nil then
      return false, nil
    end
    return true, d
  end,

  -- send wrapper (why does this exist?!)
  sendto = function(self, host, port, d)
    if self.data_fd == nil then
      self:connect(host, port)
    end
    return self:send(d)
  end,

  -- receive data
  receive = function(self, sz)
    if sz == nil then
      sz = SOCKET_MAXSZ
    end
    local data = self.data_fd:read(sz)
    return true, data
  end,

  -- receive blocking
  receive_buf = function(self, delim, incdelim)
    local data = ""
    local fdelim = false
    while not(fdelim) do
      local status, msg = self:receive()
      if not(status) then
        return status, data
      end
      print("one iteration yielded ", msg)
      fdelim = string.find(msg, "["..delim.."]")
      if fdelim then
        local where = fdelim - 1
        if incdelim then
          where = where + 1
        end
        data = data..string.sub(msg, 0, where)
        self.data_fd:seek(self.data_fd:seek() - fdelim)
        return true, data
      end
      
      data = data..msg
      p9.sleep(100)
    end
    return true, data
  end,
}

local function new_socket ()
  return Socket:new()
end

local socket = {
  sleep = sleep,
  new_socket = new_socket,
}

---
-- exports
--

local registry

local nmapcompat = {
  registry = registry,
  clock = clock,
  log_write = log_write,
  debugging = debugging,
  verbosity = verbosity,
  socket = socket,
}

return nmapcompat;