mirror of
https://github.com/nmap/nmap.git
synced 2025-12-06 04:31:29 +00:00
Merged nmap-dedup branch from nmap-exp/luis/nmap-dedup. This completes the Nmap/Nping code de-duplication phase.
This commit is contained in:
21
Makefile.in
21
Makefile.in
@@ -8,6 +8,7 @@ exec_prefix = @exec_prefix@
|
||||
bindir = @bindir@
|
||||
sbindir = @sbindir@
|
||||
mandir = @mandir@
|
||||
top_srcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
nmapdatadir = @datadir@/nmap
|
||||
deskdir = $(prefix)/share/applications
|
||||
@@ -46,7 +47,7 @@ export CFLAGS = $(CXXFLAGS)
|
||||
# CFLAGS = $(DEFS) $(INCLS)
|
||||
STATIC =
|
||||
LDFLAGS = @LDFLAGS@ $(DBGFLAGS) $(STATIC)
|
||||
LIBS = @LIBNBASE_LIBS@ @LIBNSOCK_LIBS@ @LIBPCRE_LIBS@ @LIBPCAP_LIBS@ @OPENSSL_LIBS@ @LIBDNET_LIBS@ @LIBLUA_LIBS@ @LIBS@
|
||||
LIBS = @LIBNBASE_LIBS@ @LIBNSOCK_LIBS@ @LIBPCRE_LIBS@ @LIBPCAP_LIBS@ @OPENSSL_LIBS@ libnetutil/libnetutil.a @LIBDNET_LIBS@ @LIBLUA_LIBS@ @LIBS@
|
||||
# LIBS = -lefence @LIBS@
|
||||
# LIBS = -lrmalloc @LIBS@
|
||||
INSTALL = @INSTALL@
|
||||
@@ -101,10 +102,10 @@ OBJS = main.o nmap.o targets.o tcpip.o nmap_error.o utils.o idle_scan.o osscan.o
|
||||
.cc.o:
|
||||
$(CXX) -c $(CPPFLAGS) $(CXXFLAGS) $< -o $@
|
||||
|
||||
all: @LUA_BUILD@ @PCAP_BUILD@ @PCRE_BUILD@ @DNET_BUILD@ @NBASE_BUILD@ @NSOCK_BUILD@ @NCAT_BUILD@
|
||||
all: @LUA_BUILD@ @PCAP_BUILD@ @PCRE_BUILD@ @DNET_BUILD@ @NBASE_BUILD@ @NSOCK_BUILD@ @NCAT_BUILD@ netutil_build
|
||||
$(MAKE) $(TARGET) $(BUILDZENMAP) $(BUILDNDIFF) $(BUILDNPING)
|
||||
|
||||
$(TARGET): @LUA_DEPENDS@ @PCAP_DEPENDS@ @PCRE_DEPENDS@ @DNET_DEPENDS@ $(NBASEDIR)/libnbase.a $(NSOCKDIR)/src/libnsock.a $(OBJS)
|
||||
$(TARGET): @LUA_DEPENDS@ @PCAP_DEPENDS@ @PCRE_DEPENDS@ @DNET_DEPENDS@ $(NBASEDIR)/libnbase.a $(NSOCKDIR)/src/libnsock.a libnetutil/libnetutil.a $(OBJS)
|
||||
@echo Compiling nmap
|
||||
rm -f $@
|
||||
$(CXX) $(LDFLAGS) -o $@ $(OBJS) $(LIBS)
|
||||
@@ -126,6 +127,10 @@ nsock_build: $(NSOCKDIR)/src/Makefile nbase_build
|
||||
@echo Compiling libnsock;
|
||||
cd $(NSOCKDIR)/src && $(MAKE)
|
||||
|
||||
netutil_build: libnetutil/Makefile
|
||||
@echo Compiling libnetutil;
|
||||
cd libnetutil && $(MAKE)
|
||||
|
||||
ncat_build: $(NCATDIR)/Makefile nbase_build nsock_build $(NCATDIR)/ncat.h
|
||||
cd $(NCATDIR) && $(MAKE)
|
||||
|
||||
@@ -160,7 +165,7 @@ release-rpms:
|
||||
web:
|
||||
cd $(NMAPDEVDIR) && $(MAKE) web
|
||||
|
||||
clean: @LUA_CLEAN@ @PCAP_CLEAN@ @PCRE_CLEAN@ @DNET_CLEAN@ nsock_clean nbase_clean my_clean @NPING_CLEAN@ @ZENMAP_CLEAN@ @NCAT_CLEAN@
|
||||
clean: @LUA_CLEAN@ @PCAP_CLEAN@ @PCRE_CLEAN@ @DNET_CLEAN@ nsock_clean nbase_clean netutil_clean my_clean @NPING_CLEAN@ @ZENMAP_CLEAN@ @NCAT_CLEAN@
|
||||
|
||||
my_clean:
|
||||
rm -f dependencies.mk makefile.dep
|
||||
@@ -175,6 +180,8 @@ nbase_clean:
|
||||
-cd $(NBASEDIR) && $(MAKE) clean
|
||||
nsock_clean:
|
||||
-cd $(NSOCKDIR)/src && $(MAKE) clean
|
||||
netutil_clean:
|
||||
-cd libnetutil && $(MAKE) clean
|
||||
ncat_clean:
|
||||
-cd $(NCATDIR) && $(MAKE) clean
|
||||
lua_clean:
|
||||
@@ -197,6 +204,8 @@ nbase_dist_clean:
|
||||
-cd $(NBASEDIR) && $(MAKE) distclean
|
||||
nsock_dist_clean:
|
||||
-cd $(NSOCKDIR)/src && $(MAKE) distclean
|
||||
netutil_dist_clean:
|
||||
-cd libnetutil && $(MAKE) distclean
|
||||
ncat_dist_clean:
|
||||
-cd $(NCATDIR) && $(MAKE) distclean
|
||||
zenmap_dist_clean: zenmap_clean
|
||||
@@ -208,7 +217,7 @@ nping_dist_clean:
|
||||
debugclean:
|
||||
rm -f *.gcov *.gcda *.gcno gmon.out
|
||||
|
||||
distclean: my_clean my_distclean @LUA_DIST_CLEAN@ @PCAP_DIST_CLEAN@ @PCRE_DIST_CLEAN@ @DNET_DIST_CLEAN@ @NPING_DIST_CLEAN@ @ZENMAP_DIST_CLEAN@ @NCAT_DIST_CLEAN@ nbase_dist_clean nsock_dist_clean
|
||||
distclean: my_clean my_distclean @LUA_DIST_CLEAN@ @PCAP_DIST_CLEAN@ @PCRE_DIST_CLEAN@ @DNET_DIST_CLEAN@ @NPING_DIST_CLEAN@ @ZENMAP_DIST_CLEAN@ @NCAT_DIST_CLEAN@ nbase_dist_clean nsock_dist_clean netutil_dist_clean
|
||||
|
||||
my_distclean:
|
||||
rm -f Makefile Makefile.bak makefile.dep nmap_config.h stamp-h stamp-h.in \
|
||||
@@ -281,7 +290,7 @@ install-zenmap: $(ZENMAPDIR)/setup.py
|
||||
build-ndiff:
|
||||
cd $(NDIFFDIR) && $(PYTHON) setup.py build $(if $(DESTDIR),--executable "$(DEFAULT_PYTHON_PATH)")
|
||||
|
||||
build-nping: $(NPINGDIR)/Makefile nbase_build nsock_build $(NPINGDIR)/nping.h
|
||||
build-nping: $(NPINGDIR)/Makefile nbase_build nsock_build netutil_build $(NPINGDIR)/nping.h
|
||||
@cd $(NPINGDIR) && $(MAKE)
|
||||
|
||||
install-ndiff:
|
||||
|
||||
1
Target.h
1
Target.h
@@ -96,6 +96,7 @@
|
||||
|
||||
#include "nmap.h"
|
||||
#include "FingerPrintResults.h"
|
||||
#include "libnetutil/netutil.h"
|
||||
|
||||
#ifndef NOLUA
|
||||
#include "nse_main.h"
|
||||
|
||||
46
configure.ac
46
configure.ac
@@ -47,6 +47,7 @@ AC_C_INLINE
|
||||
dnl Checks for programs.
|
||||
AC_PROG_CC
|
||||
AC_PROG_CXX
|
||||
AC_PROG_RANLIB
|
||||
AC_PROG_INSTALL
|
||||
|
||||
if test -n "$GXX"; then
|
||||
@@ -172,6 +173,23 @@ AC_SUBST(LUA_CFLAGS)
|
||||
|
||||
dnl Checks for header files.
|
||||
AC_CHECK_HEADERS(pwd.h termios.h sys/sockio.h)
|
||||
dnl A special check required for <net/if.h> on Darwin. See
|
||||
dnl http://www.gnu.org/software/autoconf/manual/html_node/Header-Portability.html.
|
||||
AC_CHECK_HEADERS([sys/socket.h])
|
||||
AC_CHECK_HEADERS([net/if.h], [], [],
|
||||
[#include <stdio.h>
|
||||
#ifdef STDC_HEADERS
|
||||
# include <stdlib.h>
|
||||
# include <stddef.h>
|
||||
#else
|
||||
# ifdef HAVE_STDLIB_H
|
||||
# include <stdlib.h>
|
||||
# endif
|
||||
#endif
|
||||
#ifdef HAVE_SYS_SOCKET_H
|
||||
# include <sys/socket.h>
|
||||
#endif
|
||||
])
|
||||
|
||||
dnl If any socket libraries needed
|
||||
AC_SEARCH_LIBS(setsockopt, socket)
|
||||
@@ -382,7 +400,7 @@ if test $have_libpcap != yes; then
|
||||
if test "${LIBPCAP_INC+set}" = "set"; then
|
||||
CPPFLAGS="$CPPFLAGS -I$LIBPCAP_INC"
|
||||
else
|
||||
CPPFLAGS="$CPPFLAGS -I$libpcapdir"
|
||||
CPPFLAGS="$CPPFLAGS -I\$(top_srcdir)/$libpcapdir"
|
||||
fi
|
||||
LIBPCAP_LIBS='$(LIBPCAPDIR)/libpcap.a'
|
||||
PCAP_DEPENDS='$(LIBPCAPDIR)/libpcap.a'
|
||||
@@ -439,7 +457,7 @@ fi
|
||||
# If we still don't have it, we use our own
|
||||
if test $have_pcre != yes ; then
|
||||
AC_CONFIG_SUBDIRS( libpcre )
|
||||
CPPFLAGS="-I$LIBPCREDIR $CPPFLAGS"
|
||||
CPPFLAGS="-I\$(top_srcdir)/$LIBPCREDIR $CPPFLAGS"
|
||||
LIBPCRE_LIBS="$LIBPCREDIR/libpcre.a"
|
||||
PCRE_DEPENDS="$LIBPCREDIR/libpcre.a"
|
||||
PCRE_BUILD="pcre_build"
|
||||
@@ -491,9 +509,9 @@ AC_HELP_STRING([--with-libdnet=included], [Use the libdnet version included with
|
||||
# If they didn't provide location, we use the included one
|
||||
if test $have_dnet != yes ; then
|
||||
AC_CONFIG_SUBDIRS( libdnet-stripped )
|
||||
CPPFLAGS="-I$LIBDNETDIR/include $CPPFLAGS"
|
||||
LIBDNET_LIBS="$LIBDNETDIR/src/.libs/libdnet.a"
|
||||
DNET_DEPENDS="$LIBDNETDIR/src/.libs/libdnet.a"
|
||||
CPPFLAGS="-I\$(top_srcdir)/$LIBDNETDIR/include $CPPFLAGS"
|
||||
LIBDNET_LIBS="\$(top_srcdir)/$LIBDNETDIR/src/.libs/libdnet.a"
|
||||
DNET_DEPENDS="\$(top_srcdir)/$LIBDNETDIR/src/.libs/libdnet.a"
|
||||
DNET_BUILD="dnet_build"
|
||||
DNET_CLEAN="dnet_clean"
|
||||
DNET_DIST_CLEAN="dnet_dist_clean"
|
||||
@@ -527,9 +545,9 @@ AC_HELP_STRING([--without-liblua], [Compile without lua (this will exclude all o
|
||||
yes)
|
||||
;;
|
||||
included)
|
||||
CPPFLAGS="-I$LIBLUADIR $CPPFLAGS"
|
||||
LIBLUA_LIBS="$LIBLUADIR/liblua.a"
|
||||
LUA_DEPENDS="$LIBLUADIR/liblua.a"
|
||||
CPPFLAGS="-I\$(top_srcdir)/$LIBLUADIR $CPPFLAGS"
|
||||
LIBLUA_LIBS="\$(top_srcdir)/$LIBLUADIR/liblua.a"
|
||||
LUA_DEPENDS="\$(top_srcdir)/$LIBLUADIR/liblua.a"
|
||||
LUA_BUILD="lua_build"
|
||||
LUA_CLEAN="lua_clean"
|
||||
LUA_DIST_CLEAN="lua_dist_clean"
|
||||
@@ -588,9 +606,9 @@ else
|
||||
# if we didn't find we use our own
|
||||
if test $have_lua != yes; then
|
||||
AC_MSG_RESULT(no)
|
||||
CPPFLAGS="-I$LIBLUADIR $CPPFLAGS"
|
||||
LIBLUA_LIBS="$LIBLUADIR/liblua.a"
|
||||
LUA_DEPENDS="$LIBLUADIR/liblua.a"
|
||||
CPPFLAGS="-I\$(top_srcdir)/$LIBLUADIR $CPPFLAGS"
|
||||
LIBLUA_LIBS="\$(top_srcdir)/$LIBLUADIR/liblua.a"
|
||||
LUA_DEPENDS="\$(top_srcdir)/$LIBLUADIR/liblua.a"
|
||||
LUA_BUILD="lua_build"
|
||||
LUA_CLEAN="lua_clean"
|
||||
LUA_DIST_CLEAN="lua_dist_clean"
|
||||
@@ -712,7 +730,7 @@ NBASEDIR="nbase"
|
||||
)
|
||||
|
||||
LDFLAGS="$LDFLAGS -L$NBASEDIR"
|
||||
CPPFLAGS="$CPPFLAGS -I$NBASEDIR"
|
||||
CPPFLAGS="$CPPFLAGS -I\$(top_srcdir)/$NBASEDIR"
|
||||
LIBNBASE_LIBS="-lnbase"
|
||||
|
||||
AC_SUBST(NBASEDIR)
|
||||
@@ -736,7 +754,7 @@ AC_HELP_STRING([--with-libnsock=DIR], [Compile and link to libnsock in DIR]),
|
||||
)
|
||||
|
||||
LDFLAGS="$LDFLAGS -L$NSOCKDIR/src/"
|
||||
CPPFLAGS="$CPPFLAGS -I$NSOCKDIR/include"
|
||||
CPPFLAGS="$CPPFLAGS -I\$(top_srcdir)/$NSOCKDIR/include"
|
||||
LIBNSOCK_LIBS="-lnsock"
|
||||
|
||||
AC_SUBST(NSOCKDIR)
|
||||
@@ -772,7 +790,7 @@ AC_SUBST(NCAT_UNINSTALL)
|
||||
AC_SUBST(NCAT_CLEAN)
|
||||
AC_SUBST(NCAT_DIST_CLEAN)
|
||||
|
||||
AC_OUTPUT(Makefile)
|
||||
AC_OUTPUT(Makefile libnetutil/Makefile)
|
||||
# Krad ASCII ART#!#@$!@#$
|
||||
if test -f docs/leet-nmap-ascii-art.txt; then
|
||||
cat docs/leet-nmap-ascii-art.txt
|
||||
|
||||
11
idle_scan.cc
11
idle_scan.cc
@@ -102,6 +102,7 @@
|
||||
#include "services.h"
|
||||
#include "Target.h"
|
||||
#include "utils.h"
|
||||
#include "output.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
@@ -329,7 +330,7 @@ static void initialize_idleproxy(struct idle_proxy_info *proxy, char *proxyName,
|
||||
}
|
||||
|
||||
proxy->host.setHostName(name);
|
||||
if (resolve(name, &ss, &sslen, o.pf()) == 0) {
|
||||
if (resolve(name, 0, 0, &ss, &sslen, o.pf()) == 0) {
|
||||
fatal("Could not resolve idle scan zombie host: %s", name);
|
||||
}
|
||||
proxy->host.setTargetSockAddr(&ss, sslen);
|
||||
@@ -337,7 +338,7 @@ static void initialize_idleproxy(struct idle_proxy_info *proxy, char *proxyName,
|
||||
/* Lets figure out the appropriate source address to use when sending
|
||||
the pr0bez */
|
||||
proxy->host.TargetSockAddr(&ss, &sslen);
|
||||
if (!route_dst(&ss, &rnfo))
|
||||
if (!nmap_route_dst(&ss, &rnfo))
|
||||
fatal("Unable to find appropriate source address and device interface to use when sending packets to %s", proxyName);
|
||||
|
||||
if (o.spoofsource) {
|
||||
@@ -390,7 +391,9 @@ static void initialize_idleproxy(struct idle_proxy_info *proxy, char *proxyName,
|
||||
/* Now for the pcap opening nonsense ... */
|
||||
/* Note that the snaplen is 152 = 64 byte max IPhdr + 24 byte max link_layer
|
||||
* header + 64 byte max TCP header. */
|
||||
proxy->pd = my_pcap_open_live(proxy->host.deviceName(), 152, (o.spoofsource)? 1 : 0, 50);
|
||||
if((proxy->pd=my_pcap_open_live(proxy->host.deviceName(), 152, (o.spoofsource)? 1 : 0, 50))==NULL)
|
||||
fatal("%s", PCAP_OPEN_ERRMSG);
|
||||
|
||||
|
||||
p = strdup(proxy->host.targetipstr());
|
||||
q = strdup(inet_ntoa(proxy->host.v4source()));
|
||||
@@ -398,6 +401,8 @@ static void initialize_idleproxy(struct idle_proxy_info *proxy, char *proxyName,
|
||||
free(p);
|
||||
free(q);
|
||||
set_pcap_filter(proxy->host.deviceFullName(), proxy->pd, filter);
|
||||
if (o.debugging)
|
||||
log_write(LOG_STDOUT, "Packet capture filter (device %s): %s\n", proxy->host.deviceFullName(), filter);
|
||||
/* Windows nonsense -- I am not sure why this is needed, but I should
|
||||
get rid of it at sometime */
|
||||
|
||||
|
||||
40
libnetutil/Makefile.in
Normal file
40
libnetutil/Makefile.in
Normal file
@@ -0,0 +1,40 @@
|
||||
top_srcdir = @top_srcdir@
|
||||
srcdir = @srcdir@
|
||||
|
||||
CXX = @CXX@
|
||||
AR = ar
|
||||
RANLIB = @RANLIB@
|
||||
DEFS = @DEFS@
|
||||
DEFS += -D_FORTIFY_SOURCE=2
|
||||
CPPFLAGS = @CPPFLAGS@
|
||||
|
||||
LIBDNETDIR = @LIBDNETDIR@
|
||||
LIBPCAPDIR = @libpcapdir@
|
||||
|
||||
TARGET = libnetutil.a
|
||||
|
||||
SRCS = $(srcdir)/netutil.cc
|
||||
OBJS = netutil.o
|
||||
|
||||
all: $(TARGET)
|
||||
|
||||
$(TARGET): $(OBJS)
|
||||
rm -f $@
|
||||
$(AR) cr $@ $(OBJS)
|
||||
$(RANLIB) $@
|
||||
|
||||
clean:
|
||||
rm -f $(OBJS) $(TARGET)
|
||||
|
||||
distclean: clean
|
||||
rm -rf Makefile
|
||||
|
||||
Makefile: Makefile.in $(top_srcdir)/config.status
|
||||
cd $(top_srcdir) && ./config.status
|
||||
|
||||
.cc.o:
|
||||
$(CXX) -c $(CPPFLAGS) $(DEFS) $*.cc
|
||||
|
||||
makefile.dep:
|
||||
$(CXX) -MM $(CPPFLAGS) $(SRCS) > $@
|
||||
include makefile.dep
|
||||
178
libnetutil/libnetutil.vcproj
Normal file
178
libnetutil/libnetutil.vcproj
Normal file
@@ -0,0 +1,178 @@
|
||||
<?xml version="1.0" encoding="Windows-1252"?>
|
||||
<VisualStudioProject
|
||||
ProjectType="Visual C++"
|
||||
Version="9,00"
|
||||
Name="libnetutil"
|
||||
ProjectGUID="{99157C3F-39F6-4663-99D7-1D9C1484494E}"
|
||||
RootNamespace="libnetutil"
|
||||
Keyword="Win32Proj"
|
||||
TargetFrameworkVersion="196613"
|
||||
>
|
||||
<Platforms>
|
||||
<Platform
|
||||
Name="Win32"
|
||||
/>
|
||||
</Platforms>
|
||||
<ToolFiles>
|
||||
</ToolFiles>
|
||||
<Configurations>
|
||||
<Configuration
|
||||
Name="Debug|Win32"
|
||||
OutputDirectory="."
|
||||
IntermediateDirectory="$(ConfigurationName)"
|
||||
ConfigurationType="4"
|
||||
CharacterSet="1"
|
||||
>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
AdditionalIncludeDirectories="..;../mswin32;../nbase;../mswin32/pcap-include;../libdnet-stripped/include"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_LIB"
|
||||
MinimalRebuild="true"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="1"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
DebugInformationFormat="4"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCManagedResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
OutputFile="$(OutDir)/libnetutil.lib"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCALinkTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXDCMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCBscMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCFxCopTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"
|
||||
/>
|
||||
</Configuration>
|
||||
<Configuration
|
||||
Name="Release|Win32"
|
||||
OutputDirectory="$(SolutionDir)$(ConfigurationName)"
|
||||
IntermediateDirectory="$(ConfigurationName)"
|
||||
ConfigurationType="4"
|
||||
CharacterSet="1"
|
||||
WholeProgramOptimization="1"
|
||||
>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="2"
|
||||
EnableIntrinsicFunctions="true"
|
||||
AdditionalIncludeDirectories="..;../mswin32;../nbase;../mswin32/pcap-include;../libdnet-stripped/include"
|
||||
PreprocessorDefinitions="WIN32;NDEBUG;_LIB"
|
||||
RuntimeLibrary="2"
|
||||
EnableFunctionLevelLinking="true"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
DebugInformationFormat="3"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCManagedResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCALinkTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXDCMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCBscMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCFxCopTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"
|
||||
/>
|
||||
</Configuration>
|
||||
</Configurations>
|
||||
<References>
|
||||
</References>
|
||||
<Files>
|
||||
<Filter
|
||||
Name="Source Files"
|
||||
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
|
||||
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
|
||||
>
|
||||
<File
|
||||
RelativePath=".\netutil.cc"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Header Files"
|
||||
Filter="h;hpp;hxx;hm;inl;inc;xsd"
|
||||
UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
|
||||
>
|
||||
<File
|
||||
RelativePath=".\netutil.h"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Resource Files"
|
||||
Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
|
||||
UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
|
||||
>
|
||||
</Filter>
|
||||
</Files>
|
||||
<Globals>
|
||||
</Globals>
|
||||
</VisualStudioProject>
|
||||
3686
libnetutil/netutil.cc
Normal file
3686
libnetutil/netutil.cc
Normal file
File diff suppressed because it is too large
Load Diff
476
libnetutil/netutil.h
Normal file
476
libnetutil/netutil.h
Normal file
@@ -0,0 +1,476 @@
|
||||
|
||||
/***************************************************************************
|
||||
* netutil.h -- The main include file exposing the external API for *
|
||||
* libnetutil, a library that provides network-related functions or *
|
||||
* classes that make it easier to handle things like network interfaces, *
|
||||
* routing tables, raw packet manipulation, etc. The lib was originally *
|
||||
* written for use in the Nmap Security Scanner ( http://nmap.org ). *
|
||||
* *
|
||||
***********************IMPORTANT NMAP LICENSE TERMS************************
|
||||
* *
|
||||
* The Nmap Security Scanner is (C) 1996-2010 Insecure.Com LLC. Nmap is *
|
||||
* also a registered trademark of Insecure.Com LLC. This program is free *
|
||||
* software; you may redistribute and/or modify it under the terms of the *
|
||||
* GNU General Public License as published by the Free Software *
|
||||
* Foundation; Version 2 with the clarifications and exceptions described *
|
||||
* below. This guarantees your right to use, modify, and redistribute *
|
||||
* this software under certain conditions. If you wish to embed Nmap *
|
||||
* technology into proprietary software, we sell alternative licenses *
|
||||
* (contact sales@insecure.com). Dozens of software vendors already *
|
||||
* license Nmap technology such as host discovery, port scanning, OS *
|
||||
* detection, and version detection. *
|
||||
* *
|
||||
* Note that the GPL places important restrictions on "derived works", yet *
|
||||
* it does not provide a detailed definition of that term. To avoid *
|
||||
* misunderstandings, we consider an application to constitute a *
|
||||
* "derivative work" for the purpose of this license if it does any of the *
|
||||
* following: *
|
||||
* o Integrates source code from Nmap *
|
||||
* o Reads or includes Nmap copyrighted data files, such as *
|
||||
* nmap-os-db or nmap-service-probes. *
|
||||
* o Executes Nmap and parses the results (as opposed to typical shell or *
|
||||
* execution-menu apps, which simply display raw Nmap output and so are *
|
||||
* not derivative works.) *
|
||||
* o Integrates/includes/aggregates Nmap into a proprietary executable *
|
||||
* installer, such as those produced by InstallShield. *
|
||||
* o Links to a library or executes a program that does any of the above *
|
||||
* *
|
||||
* The term "Nmap" should be taken to also include any portions or derived *
|
||||
* works of Nmap. This list is not exclusive, but is meant to clarify our *
|
||||
* interpretation of derived works with some common examples. Our *
|
||||
* interpretation applies only to Nmap--we don't speak for other people's *
|
||||
* GPL works. *
|
||||
* *
|
||||
* If you have any questions about the GPL licensing restrictions on using *
|
||||
* Nmap in non-GPL works, we would be happy to help. As mentioned above, *
|
||||
* we also offer alternative license to integrate Nmap into proprietary *
|
||||
* applications and appliances. These contracts have been sold to dozens *
|
||||
* of software vendors, and generally include a perpetual license as well *
|
||||
* as providing for priority support and updates as well as helping to *
|
||||
* fund the continued development of Nmap technology. Please email *
|
||||
* sales@insecure.com for further information. *
|
||||
* *
|
||||
* As a special exception to the GPL terms, Insecure.Com LLC grants *
|
||||
* permission to link the code of this program with any version of the *
|
||||
* OpenSSL library which is distributed under a license identical to that *
|
||||
* listed in the included COPYING.OpenSSL file, and distribute linked *
|
||||
* combinations including the two. You must obey the GNU GPL in all *
|
||||
* respects for all of the code used other than OpenSSL. If you modify *
|
||||
* this file, you may extend this exception to your version of the file, *
|
||||
* but you are not obligated to do so. *
|
||||
* *
|
||||
* If you received these files with a written license agreement or *
|
||||
* contract stating terms other than the terms above, then that *
|
||||
* alternative license agreement takes precedence over these comments. *
|
||||
* *
|
||||
* Source is provided to this software because we believe users have a *
|
||||
* right to know exactly what a program is going to do before they run it. *
|
||||
* This also allows you to audit the software for security holes (none *
|
||||
* have been found so far). *
|
||||
* *
|
||||
* Source code also allows you to port Nmap to new platforms, fix bugs, *
|
||||
* and add new features. You are highly encouraged to send your changes *
|
||||
* to nmap-dev@insecure.org for possible incorporation into the main *
|
||||
* distribution. By sending these changes to Fyodor or one of the *
|
||||
* Insecure.Org development mailing lists, it is assumed that you are *
|
||||
* offering the Nmap Project (Insecure.Com LLC) the unlimited, *
|
||||
* non-exclusive right to reuse, modify, and relicense the code. Nmap *
|
||||
* will always be available Open Source, but this is important because the *
|
||||
* inability to relicense code has caused devastating problems for other *
|
||||
* Free Software projects (such as KDE and NASM). We also occasionally *
|
||||
* relicense the code to third parties as discussed above. If you wish to *
|
||||
* specify special license conditions of your contributions, just say so *
|
||||
* when you send them. *
|
||||
* *
|
||||
* This program is distributed in the hope that it will be useful, but *
|
||||
* WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* General Public License v2.0 for more details at *
|
||||
* http://www.gnu.org/licenses/gpl-2.0.html , or in the COPYING file *
|
||||
* included with Nmap. *
|
||||
* *
|
||||
***************************************************************************/
|
||||
|
||||
/* $Id: netutil.h 18098 2010-06-14 11:50:12Z luis $ */
|
||||
|
||||
#ifndef _NETUTIL_H_
|
||||
#define _NETUTIL_H_ 1
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
#include <pcap.h>
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#include "dnet.h"
|
||||
|
||||
enum { OP_FAILURE = -1, OP_SUCCESS = 0 };
|
||||
|
||||
|
||||
/* For systems without SCTP in netinet/in.h, such as MacOS X or Win */
|
||||
#ifndef IPPROTO_SCTP
|
||||
#define IPPROTO_SCTP 132
|
||||
#endif
|
||||
|
||||
int netutil_fatal(const char *str, ...)
|
||||
__attribute__ ((format (printf, 1, 2)));
|
||||
|
||||
int netutil_error(const char *str, ...)
|
||||
__attribute__ ((format (printf, 1, 2)));
|
||||
|
||||
/* This function converts zero-terminated 'txt' string to binary 'data'.
|
||||
It is used to parse user input for ip options. Some examples of possible input
|
||||
strings and results:
|
||||
'\x01*2\xA2' -> [0x01,0x01,0xA2] // with 'x' number is parsed in hex
|
||||
'\01\01\255' -> [0x01,0x01,0xFF] // without 'x' its in decimal
|
||||
'\x01\x00*2' -> [0x01,0x00,0x00] // '*' is copying char
|
||||
'R' -> Record Route with 9 slots
|
||||
'S 192.168.0.1 172.16.0.1' -> Strict Route with 2 slots
|
||||
'L 192.168.0.1 172.16.0.1' -> Loose Route with 2 slots
|
||||
'T' -> Record Timestamp with 9 slots
|
||||
'U' -> Record Timestamp and Ip Address with 4 slots
|
||||
On success, the function returns the length of the final binary
|
||||
options stored in "data". In case of error, OP_FAILURE is returned
|
||||
and the "errstr" buffer is filled with an error message
|
||||
(unless it's NULL). Note that the returned error message does NOT
|
||||
contain a newline character at the end. */
|
||||
int parse_ip_options(const char *txt, u8 *data, int datalen, int* firsthopoff, int* lasthopoff, char *errstr, size_t errstrlen);
|
||||
|
||||
/* Tries to resolve the given name (or literal IP) into a sockaddr structure.
|
||||
- Parameter "hostname" is the name to be resolved.
|
||||
- Parameter "port" sets the port in each returned address structure
|
||||
(you can safely pass 0 for the port if you don't care)
|
||||
- Parameter "nodns": If set, it means that the supplied hostname is actually a
|
||||
numeric IP address. The flag prevents any type of name resolution service
|
||||
from being called. In 99% of the cases this should be 0.
|
||||
Returns 1 on success or 0 if hostname could not be resolved. */
|
||||
int resolve(const char *hostname, u16 port, int nodns, struct sockaddr_storage *ss, size_t *sslen, int af);
|
||||
|
||||
/*
|
||||
* Returns 1 if this is a reserved IP address, where "reserved" means
|
||||
* either a private address, non-routable address, or even a non-reserved
|
||||
* but unassigned address which has an extremely high probability of being
|
||||
* black-holed.
|
||||
*
|
||||
* We try to optimize speed when ordering the tests. This optimization
|
||||
* assumes that all byte values are equally likely in the input.
|
||||
*
|
||||
* Warning: This function needs frequent attention because IANA has been
|
||||
* allocating address blocks many times per year (although it's questionable
|
||||
* how much longer this trend can be kept up).
|
||||
*
|
||||
* Check
|
||||
* <http://www.iana.org/assignments/ipv4-address-space/ipv4-address-space.txt>
|
||||
* for the most recent assigments and
|
||||
* <http://www.cymru.com/Documents/bogon-bn-nonagg.txt> for bogon
|
||||
* netblocks.
|
||||
*/
|
||||
int ip_is_reserved(struct in_addr *ip);
|
||||
|
||||
|
||||
/* A couple of trivial functions that maintain a cache of IP to MAC
|
||||
* Address entries. Function arp_cache_get() looks for the IPv4 address
|
||||
* in ss and fills in the 'mac' parameter and returns true if it is
|
||||
* found. Otherwise (not found), the function returns false.
|
||||
* Function arp_cache_set() adds an entry with the given ip (ss) and
|
||||
* mac address. An existing entry for the IP ss will be overwritten
|
||||
* with the new MAC address. arp_cache_set() always returns true. */
|
||||
int arp_cache_get(struct sockaddr_storage *ss, u8 *mac);
|
||||
int arp_cache_set(struct sockaddr_storage *ss, u8 *mac);
|
||||
|
||||
/* Standard BSD internet checksum routine. */
|
||||
unsigned short in_cksum(u16 *ptr, int nbytes);
|
||||
|
||||
/* For computing TCP/UDP checksums, see RFC 1071 and TCP/IP Illustrated
|
||||
sections 3.2, 11.3, and 17.3.*/
|
||||
unsigned short tcpudp_cksum(const struct in_addr *src, const struct in_addr *dst,
|
||||
u8 proto, u16 len, const void *hstart);
|
||||
|
||||
void sethdrinclude(int sd);
|
||||
void set_ipoptions(int sd, void *opts, size_t optslen);
|
||||
void set_ttl(int sd, int ttl);
|
||||
|
||||
/* Returns whether the system supports pcap_get_selectable_fd() properly */
|
||||
int pcap_selectable_fd_valid();
|
||||
|
||||
/* Call this instead of pcap_get_selectable_fd directly (or your code
|
||||
won't compile on Windows). On systems which don't seem to support
|
||||
the pcap_get_selectable_fd() function properly, returns -1,
|
||||
otherwise simply calls pcap_selectable_fd and returns the
|
||||
results. If you just want to test whether the function is supported,
|
||||
use pcap_selectable_fd_valid() instead. */
|
||||
int my_pcap_get_selectable_fd(pcap_t *p);
|
||||
|
||||
|
||||
/* These two function return -1 if we can't use select() on the pcap
|
||||
* device, 0 for timeout, and >0 for success. If select() fails we bail
|
||||
* out because it couldn't work with the file descriptor we got from
|
||||
* my_pcap_get_selectable_fd() */
|
||||
int pcap_select(pcap_t *p, struct timeval *timeout);
|
||||
int pcap_select(pcap_t *p, long usecs);
|
||||
|
||||
typedef enum { devt_ethernet, devt_loopback, devt_p2p, devt_other } devtype;
|
||||
|
||||
#define MAX_LINK_HEADERSZ 24
|
||||
struct link_header {
|
||||
int datalinktype; /* pcap_datalink(), such as DLT_EN10MB */
|
||||
int headerlen; /* 0 if header was too big or unavailaable */
|
||||
u8 header[MAX_LINK_HEADERSZ];
|
||||
};
|
||||
|
||||
/* Relevant (to Nmap) information about an interface */
|
||||
struct interface_info {
|
||||
char devname[16];
|
||||
char devfullname[16]; /* can include alias info, such as eth0:2. */
|
||||
struct sockaddr_storage addr;
|
||||
u16 netmask_bits; /* CIDR-style. So 24 means class C (255.255.255.0)*/
|
||||
devtype device_type; /* devt_ethernet, devt_loopback, devt_p2p, devt_other */
|
||||
int device_up; /* True if the device is up (enabled) */
|
||||
u8 mac[6]; /* Interface MAC address if device_type is devt_ethernet */
|
||||
};
|
||||
|
||||
struct route_nfo {
|
||||
struct interface_info ii;
|
||||
|
||||
/* true if the target is directly connected on the network (no routing
|
||||
required). */
|
||||
int direct_connect;
|
||||
|
||||
/* This is the source address that should be used by the packets. It
|
||||
may be different than ii.addr if you are using localhost interface
|
||||
to scan the IP of another interface on the machine */
|
||||
struct sockaddr_storage srcaddr;
|
||||
|
||||
/* If direct_connect is 0, this is filled in with the next hop
|
||||
required to route to the target */
|
||||
struct sockaddr_storage nexthop;
|
||||
};
|
||||
|
||||
struct sys_route {
|
||||
struct interface_info *device;
|
||||
u32 dest;
|
||||
u32 netmask;
|
||||
struct in_addr gw; /* gateway - 0 if none */
|
||||
};
|
||||
|
||||
struct eth_nfo {
|
||||
char srcmac[6];
|
||||
char dstmac[6];
|
||||
eth_t *ethsd; // Optional, but improves performance. Set to NULL if unavail
|
||||
char devname[16]; // Only needed if ethsd is NULL.
|
||||
};
|
||||
|
||||
/* A simple function that caches the eth_t from dnet for one device,
|
||||
to avoid opening, closing, and re-opening it thousands of tims. If
|
||||
you give a different device, this function will close the first
|
||||
one. Thus this should never be used by programs that need to deal
|
||||
with multiple devices at once. In addition, you MUST NEVER
|
||||
eth_close() A DEVICE OBTAINED FROM THIS FUNCTION. Instead, you can
|
||||
call eth_close_cached() to close whichever device (if any) is
|
||||
cached. Returns NULL if it fails to open the device. */
|
||||
eth_t *eth_open_cached(const char *device);
|
||||
|
||||
/* See the description for eth_open_cached */
|
||||
void eth_close_cached();
|
||||
|
||||
/* Takes a protocol number like IPPROTO_TCP, IPPROTO_UDP, or
|
||||
* IPPROTO_IP and returns a ascii representation (or "unknown" if it
|
||||
* doesn't recognize the number). Returned string is in lowercase. */
|
||||
const char *proto2ascii_lowercase(u8 proto) ;
|
||||
|
||||
/* Same as proto2ascii() but returns a string in uppercase. */
|
||||
const char *proto2ascii_uppercase(u8 proto);
|
||||
|
||||
/* Get an ASCII information about a tcp option which is pointed by
|
||||
optp, with a length of len. The result is stored in the result
|
||||
buffer. The result may look like "<mss 1452,sackOK,timestamp
|
||||
45848914 0,nop,wscale 7>" */
|
||||
void tcppacketoptinfo(u8 *optp, int len, char *result, int bufsize);
|
||||
|
||||
/* Convert an IP address to the device (IE ppp0 eth0) using that
|
||||
* address. Supplied "dev" must be able to hold at least 32 bytes.
|
||||
* Returns 0 on success or -1 in case of error. */
|
||||
int ipaddr2devname( char *dev, const struct in_addr *addr );
|
||||
|
||||
/* Convert a network interface name (IE ppp0 eth0) to an IPv4 address.
|
||||
* Returns 0 on success or -1 in case of error. */
|
||||
int devname2ipaddr(char *dev, struct in_addr *addr);
|
||||
|
||||
/* Returns an allocated array of struct interface_info representing the
|
||||
available interfaces. The number of interfaces is returned in *howmany. This
|
||||
function just does caching of results; the real work is done in
|
||||
getinterfaces_dnet() or getinterfaces_siocgifconf().
|
||||
On error, NULL is returned, howmany is set to -1 and the supplied
|
||||
error buffer "errstr", if not NULL, will contain an error message. */
|
||||
struct interface_info *getinterfaces(int *howmany, char *errstr, size_t errstrlen);
|
||||
|
||||
/* This struct is abused to carry either routes or interfaces, depending on the
|
||||
function it's used in. */
|
||||
struct dnet_collector_route_nfo {
|
||||
struct sys_route *routes;
|
||||
int numroutes;
|
||||
int capacity; /* Capacity of routes or ifaces, depending on context */
|
||||
struct interface_info *ifaces;
|
||||
int numifaces;
|
||||
};
|
||||
|
||||
/* Looks for an interface with the given name (iname), and returns the
|
||||
corresponding interface_info if found. Will accept a match of
|
||||
devname or devfullname. Returns NULL if none found */
|
||||
struct interface_info *getInterfaceByName(char *iname);
|
||||
|
||||
/* Parse the system routing table, converting each route into a
|
||||
sys_route entry. Returns an array of sys_routes. numroutes is set
|
||||
to the number of routes in the array. The routing table is only
|
||||
read the first time this is called -- later results are cached.
|
||||
The returned route array is sorted by netmask with the most
|
||||
specific matches first.
|
||||
On error, NULL is returned, howmany is set to -1 and the supplied
|
||||
error buffer "errstr", if not NULL, will contain an error message. */
|
||||
struct sys_route *getsysroutes(int *howmany, char *errstr, size_t errstrlen);
|
||||
|
||||
/* Tries to determine whether the supplied address corresponds to
|
||||
* localhost. (eg: the address is something like 127.x.x.x, the address
|
||||
* matches one of the local network interfaces' address, etc).
|
||||
* Returns 1 if the address is thought to be localhost and 0 otherwise */
|
||||
int islocalhost(const struct in_addr *const addr);
|
||||
|
||||
/* Determines whether the supplied address corresponds to a private,
|
||||
* non-Internet-routable address. See RFC1918 for details.
|
||||
* Returns 1 if the address is private or 0 otherwise. */
|
||||
int isipprivate(const struct in_addr *const addr);
|
||||
|
||||
/* Takes binary data found in the IP Options field of an IPv4 packet
|
||||
* and returns a string containing an ASCII description of the options
|
||||
* found. The function returns a pointer to a static buffer that
|
||||
* subsequent calls will overwrite. On error, NULL is returned. */
|
||||
char *format_ip_options(u8* ipopt, int ipoptlen);
|
||||
|
||||
/* Returns a buffer of ASCII information about an IP packet that may
|
||||
* look like "TCP 127.0.0.1:50923 > 127.0.0.1:3 S ttl=61 id=39516
|
||||
* iplen=40 seq=625950769" or "ICMP PING (0/1) ttl=61 id=39516 iplen=40".
|
||||
* Returned buffer is static so it is NOT safe to call this in
|
||||
* multi-threaded environments without appropriate sync protection, or
|
||||
* call it twice in the same sentence (eg: as two printf parameters).
|
||||
* Obviously, the caller should never attempt to free() the buffer. The
|
||||
* returned buffer is guaranteed to be NULL-terminated but no
|
||||
* assumptions should be made concerning its length.
|
||||
*
|
||||
* The function provides full support for IPv4,TCP,UDP,SCTP and ICMPv4.
|
||||
* It also provides support for standard IPv6 but not for its extension
|
||||
* headers. If an IPv6 packet contains an ICMPv6 Header, the output will
|
||||
* reflect this but no parsing of ICMPv6 contents will be performed.
|
||||
*
|
||||
* The output has three different levels of detail. Parameter "detail"
|
||||
* determines how verbose the output should be. It should take one of
|
||||
* the following values:
|
||||
*
|
||||
* LOW_DETAIL (0x01): Traditional output.
|
||||
* MEDIUM_DETAIL (0x02): More verbose than traditional.
|
||||
* HIGH_DETAIL (0x03): Contents of virtually every field of the
|
||||
* protocol headers .
|
||||
*/
|
||||
#define LOW_DETAIL 1
|
||||
#define MEDIUM_DETAIL 2
|
||||
#define HIGH_DETAIL 3
|
||||
const char *ippackethdrinfo(const u8 *packet, u32 len, int detail);
|
||||
|
||||
|
||||
/* Takes an IPv4 destination address (dst) and tries to determine the
|
||||
* source address and interface necessary to route to this address.
|
||||
* If no route is found, 0 is returned and "rnfo" is undefined. If
|
||||
* a route is found, 1 is returned and "rnfo" is filled in with all
|
||||
* of the routing details. If the source address needs to be spoofed,
|
||||
* it should be passed through "spoofss" (otherwise NULL should be
|
||||
* specified), along with a suitable network device (parameter "device").
|
||||
* Even if spoofss is NULL, if user specified a network device with -e,
|
||||
* it should still be passed. Note that it's OK to pass either NULL or
|
||||
* an empty string as the "device", as long as spoofss==NULL. */
|
||||
int route_dst(const struct sockaddr_storage * const dst, struct route_nfo *rnfo,
|
||||
char *device, struct sockaddr_storage *spoofss);
|
||||
|
||||
/* Send an IP packet over a raw socket. */
|
||||
int send_ip_packet_sd(int sd, u8 *packet, unsigned int packetlen);
|
||||
|
||||
/* Send an IP packet over an ethernet handle. */
|
||||
int send_ip_packet_eth(struct eth_nfo *eth, u8 *packet, unsigned int packetlen);
|
||||
|
||||
/* Sends the supplied pre-built IPv4 packet. The packet is sent through
|
||||
* the raw socket "sd" if "eth" is NULL. Otherwise, it gets sent at raw
|
||||
* ethernet level. */
|
||||
int send_ip_packet_eth_or_sd(int sd, struct eth_nfo *eth, u8 *packet, unsigned int packetlen);
|
||||
|
||||
/* Create and send all fragments of a pre-built IPv4 packet.
|
||||
* Minimal MTU for IPv4 is 68 and maximal IPv4 header size is 60
|
||||
* which gives us a right to cut TCP header after 8th byte */
|
||||
int send_frag_ip_packet(int sd, struct eth_nfo *eth, u8 *packet,
|
||||
unsigned int packetlen, unsigned int mtu);
|
||||
|
||||
/* Wrapper for system function sendto(), which retries a few times when
|
||||
* the call fails. It also prints informational messages about the
|
||||
* errors encountered. It returns the number of bytes sent or -1 in
|
||||
* case of error. */
|
||||
int Sendto(const char *functionname, int sd, const unsigned char *packet,
|
||||
int len, unsigned int flags, struct sockaddr *to, int tolen);
|
||||
|
||||
/* This function is used to obtain a packet capture handle to look at
|
||||
* packets on the network. It is actually a wrapper for libpcap's
|
||||
* pcap_open_live() that takes care of compatibility issues and error
|
||||
* checking. Prints an error and fatal()s if the call fails, so a
|
||||
* valid pcap_t will always be returned. */
|
||||
pcap_t *my_pcap_open_live(const char *device, int snaplen, int promisc, int to_ms);
|
||||
|
||||
/* Set a pcap filter */
|
||||
void set_pcap_filter(const char *device, pcap_t *pd, const char *bpf, ...);
|
||||
|
||||
/* Issues an ARP request for the MAC of targetss (which will be placed
|
||||
in targetmac if obtained) from the source IP (srcip) and source mac
|
||||
(srcmac) given. "The request is ussued using device dev to the
|
||||
broadcast MAC address. The transmission is attempted up to 3
|
||||
times. If none of these elicit a response, false will be returned.
|
||||
If the mac is determined, true is returned. The last parameter is
|
||||
a pointer to a callback function that can be used for packet traceing.
|
||||
This is intended to be used by Nmap only. Any other calling this
|
||||
should pass NULL instead. */
|
||||
bool doArp(const char *dev, const u8 *srcmac,
|
||||
const struct sockaddr_storage *srcip,
|
||||
const struct sockaddr_storage *targetip,
|
||||
u8 *targetmac,
|
||||
void (*traceArp_callback)(int, const u8 *, u32 , struct timeval *));
|
||||
|
||||
/* Attempts to read one IPv4/Ethernet ARP reply packet from the pcap
|
||||
descriptor pd. If it receives one, fills in sendermac (must pass
|
||||
in 6 bytes), senderIP, and rcvdtime (can be NULL if you don't care)
|
||||
and returns 1. If it times out and reads no arp requests, returns
|
||||
0. to_usec is the timeout period in microseconds. Use 0 to avoid
|
||||
blocking to the extent possible. Returns -1 or exits if there is
|
||||
an error. The last parameter is a pointer to a callback function
|
||||
that can be used for packet tracing. This is intended to be used
|
||||
by Nmap only. Any other calling this should pass NULL instead. */
|
||||
int read_arp_reply_pcap(pcap_t *pd, u8 *sendermac,
|
||||
struct in_addr *senderIP, long to_usec,
|
||||
struct timeval *rcvdtime,
|
||||
void (*traceArp_callback)(int, const u8 *, u32 , struct timeval *));
|
||||
|
||||
/* Read a single host specification from a file, as for -iL and --excludefile.
|
||||
It returns the length of the string read; an overflow is indicated when the
|
||||
return value is >= n. Returns 0 if there was no specification to be read. The
|
||||
buffer is always null-terminated. */
|
||||
size_t read_host_from_file(FILE *fp, char *buf, size_t n);
|
||||
|
||||
/* Return next target host specification from the supplied stream.
|
||||
* if parameter "random" is set to true, then the function will
|
||||
* return a random, non-reserved, IP address in decimal-dot notation */
|
||||
char *grab_next_host_spec(FILE *inputfd, bool random, int argc, char **fakeargv);
|
||||
|
||||
#ifdef WIN32
|
||||
/* Convert a dnet interface name into the long pcap style. This also caches the
|
||||
data to speed things up. Fills out pcapdev (up to pcapdevlen) and returns
|
||||
true if it finds anything. Otherwise returns false. This is only necessary
|
||||
on Windows. */
|
||||
int DnetName2PcapName(const char *dnetdev, char *pcapdev, int pcapdevlen);
|
||||
#endif
|
||||
|
||||
#endif /* _NETUTIL_H_ */
|
||||
@@ -1,5 +1,5 @@
|
||||
Microsoft Visual Studio Solution File, Format Version 10.00
|
||||
# Visual C++ Express 2008
|
||||
# Visual Studio 2008
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "nmap", "nmap.vcproj", "{361719F0-AB42-4C93-9DE8-7D2144B96625}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
{31FB0767-A71F-4575-8379-002D72B8AF86} = {31FB0767-A71F-4575-8379-002D72B8AF86}
|
||||
@@ -30,6 +30,8 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ncat", "..\ncat\ncat.vcproj
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "nping", "..\nping\nping.vcproj", "{CDB10BBA-9085-4B9B-AC8F-BA31D3906B36}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libnetutil", "..\libnetutil\libnetutil.vcproj", "{99157C3F-39F6-4663-99D7-1D9C1484494E}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Win32 = Debug|Win32
|
||||
@@ -68,6 +70,10 @@ Global
|
||||
{CDB10BBA-9085-4B9B-AC8F-BA31D3906B36}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{CDB10BBA-9085-4B9B-AC8F-BA31D3906B36}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{CDB10BBA-9085-4B9B-AC8F-BA31D3906B36}.Release|Win32.Build.0 = Release|Win32
|
||||
{99157C3F-39F6-4663-99D7-1D9C1484494E}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{99157C3F-39F6-4663-99D7-1D9C1484494E}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{99157C3F-39F6-4663-99D7-1D9C1484494E}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{99157C3F-39F6-4663-99D7-1D9C1484494E}.Release|Win32.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
<?xml version="1.0" encoding="Windows-1252"?>
|
||||
<VisualStudioProject
|
||||
ProjectType="Visual C++"
|
||||
Version="9.00"
|
||||
Version="9,00"
|
||||
Name="nmap"
|
||||
ProjectGUID="{361719F0-AB42-4C93-9DE8-7D2144B96625}"
|
||||
RootNamespace="nmap"
|
||||
@@ -72,11 +72,11 @@
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLinkerTool"
|
||||
AdditionalDependencies="liblua.lib nsock.lib libpcre.lib nbase.lib libdnet-stripped.lib ws2_32.lib IPHlpAPI.Lib wpcap.lib packet.lib advapi32.lib libeay32.lib ssleay32.lib shell32.lib $(NOINHERIT)"
|
||||
AdditionalDependencies="liblua.lib nsock.lib libpcre.lib nbase.lib libdnet-stripped.lib ws2_32.lib IPHlpAPI.Lib wpcap.lib packet.lib advapi32.lib libeay32.lib ssleay32.lib shell32.lib libnetutil.lib $(NOINHERIT)"
|
||||
OutputFile=".\Debug\nmap.exe"
|
||||
LinkIncremental="2"
|
||||
SuppressStartupBanner="true"
|
||||
AdditionalLibraryDirectories="lib;..\liblua;..\libpcre;..\nsock;..\nbase;"..\libdnet-stripped";OpenSSL\lib;"
|
||||
AdditionalLibraryDirectories="lib;..\liblua;..\libpcre;..\nsock;..\nbase;"..\libdnet-stripped";../libnetutil;OpenSSL\lib"
|
||||
IgnoreDefaultLibraryNames=""
|
||||
DelayLoadDLLs="packet.dll,wpcap.dll,iphlpapi.dll"
|
||||
GenerateDebugInformation="true"
|
||||
@@ -165,11 +165,11 @@
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLinkerTool"
|
||||
AdditionalDependencies="liblua.lib nsock.lib libpcre.lib nbase.lib libdnet-stripped.lib ws2_32.lib IPHlpAPI.Lib wpcap.lib packet.lib advapi32.lib libeay32.lib ssleay32.lib shell32.lib $(NOINHERIT)"
|
||||
AdditionalDependencies="liblua.lib nsock.lib libpcre.lib nbase.lib libdnet-stripped.lib ws2_32.lib IPHlpAPI.Lib wpcap.lib packet.lib advapi32.lib libeay32.lib ssleay32.lib shell32.lib libnetutil.lib $(NOINHERIT)"
|
||||
OutputFile=".\Release/nmap.exe"
|
||||
LinkIncremental="2"
|
||||
SuppressStartupBanner="true"
|
||||
AdditionalLibraryDirectories="lib;..\liblua;..\libpcre;..\nsock;..\nbase;"..\libdnet-stripped";OpenSSL\lib;"
|
||||
AdditionalLibraryDirectories="lib;..\liblua;..\libpcre;..\nsock;..\nbase;"..\libdnet-stripped";../libnetutil;OpenSSL\lib"
|
||||
IgnoreDefaultLibraryNames=""
|
||||
DelayLoadDLLs="packet.dll,wpcap.dll,iphlpapi.dll"
|
||||
ProgramDatabaseFile=".\Release/nmap.pdb"
|
||||
|
||||
165
nmap.cc
165
nmap.cc
@@ -320,123 +320,6 @@ printf("%s %s ( %s )\n"
|
||||
exit(rc);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns 1 if this is a reserved IP address, where "reserved" means
|
||||
* either a private address, non-routable address, or even a non-reserved
|
||||
* but unassigned address which has an extremely high probability of being
|
||||
* black-holed.
|
||||
*
|
||||
* We try to optimize speed when ordering the tests. This optimization
|
||||
* assumes that all byte values are equally likely in the input.
|
||||
*
|
||||
* Warning: This function needs frequent attention because IANA has been
|
||||
* allocating address blocks many times per year (although it's questionable
|
||||
* how much longer this trend can be kept up).
|
||||
*
|
||||
* Check
|
||||
* <http://www.iana.org/assignments/ipv4-address-space/ipv4-address-space.txt>
|
||||
* for the most recent assigments and
|
||||
* <http://www.cymru.com/Documents/bogon-bn-nonagg.txt> for bogon
|
||||
* netblocks.
|
||||
*/
|
||||
static int ip_is_reserved(struct in_addr *ip)
|
||||
{
|
||||
char *ipc = (char *) &(ip->s_addr);
|
||||
unsigned char i1 = ipc[0], i2 = ipc[1], i3 = ipc[2]; /* i4 not currently used - , i4 = ipc[3]; */
|
||||
|
||||
/* do all the /7's and /8's with a big switch statement, hopefully the
|
||||
* compiler will be able to optimize this a little better using a jump table
|
||||
* or what have you
|
||||
*/
|
||||
switch (i1)
|
||||
{
|
||||
case 0: /* 000/8 is IANA reserved */
|
||||
case 5: /* 005/8 is IANA reserved */
|
||||
case 6: /* USA Army ISC */
|
||||
case 7: /* used for BGP protocol */
|
||||
case 10: /* the infamous 10.0.0.0/8 */
|
||||
case 23: /* 023/8 is IANA reserved */
|
||||
case 36: /* 036/8 is IANA reserved */
|
||||
case 37: /* 037/8 is IANA reserved */
|
||||
case 39: /* 039/8 is IANA reserved */
|
||||
case 42: /* 042/8 is IANA reserved */
|
||||
case 49: /* 049/8 is IANA reserved */
|
||||
case 55: /* misc. U.S.A. Armed forces */
|
||||
case 127: /* 127/8 is reserved for loopback */
|
||||
case 179: /* 179/8 is IANA reserved */
|
||||
case 185: /* 185/8 is IANA reserved */
|
||||
return 1;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
/* 100-106/8 is IANA reserved */
|
||||
if (i1 >= 100 && i1 <= 106)
|
||||
return 1;
|
||||
|
||||
/* 172.16.0.0/12 is reserved for private nets by RFC1819 */
|
||||
if (i1 == 172 && i2 >= 16 && i2 <= 31)
|
||||
return 1;
|
||||
|
||||
/* 192.0.2.0/24 is reserved for documentation and examples (RFC5737) */
|
||||
/* 192.88.99.0/24 is used as 6to4 Relay anycast prefix by RFC3068 */
|
||||
/* 192.168.0.0/16 is reserved for private nets by RFC1819 */
|
||||
if (i1 == 192) {
|
||||
if (i2 == 0 && i3 == 2)
|
||||
return 1;
|
||||
if (i2 == 88 && i3 == 99)
|
||||
return 1;
|
||||
if (i2 == 168)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* 198.18.0.0/15 is used for benchmark tests by RFC2544 */
|
||||
/* 198.51.100.0/24 is reserved for documentation (RFC5737) */
|
||||
if (i1 == 198) {
|
||||
if (i2 == 18 || i2 == 19)
|
||||
return 1;
|
||||
if (i2 == 51 && i3 == 100)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* 169.254.0.0/16 is reserved for DHCP clients seeking addresses */
|
||||
if (i1 == 169 && i2 == 254)
|
||||
return 1;
|
||||
|
||||
/* 203.0.113.0/24 is reserved for documentation (RFC5737) */
|
||||
if (i1 == 203 && i2 == 0 && i3 == 113)
|
||||
return 1;
|
||||
|
||||
/* 224-239/8 is all multicast stuff */
|
||||
/* 240-255/8 is IANA reserved */
|
||||
if (i1 >= 224)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static char *grab_next_host_spec(FILE *inputfd, int argc, char **fakeargv) {
|
||||
static char host_spec[1024];
|
||||
struct in_addr ip;
|
||||
size_t n;
|
||||
|
||||
if (o.generate_random_ips) {
|
||||
do {
|
||||
ip.s_addr = get_random_unique_u32();
|
||||
} while (ip_is_reserved(&ip));
|
||||
Strncpy(host_spec, inet_ntoa(ip), sizeof(host_spec));
|
||||
} else if (!inputfd) {
|
||||
return( (optind < argc)? fakeargv[optind++] : NULL);
|
||||
} else {
|
||||
n = read_host_from_file(inputfd, host_spec, sizeof(host_spec));
|
||||
if (n == 0)
|
||||
return NULL;
|
||||
else if (n >= sizeof(host_spec))
|
||||
fatal("One of the host specifications from your input file is too long (>= %u chars)", (unsigned int) sizeof(host_spec));
|
||||
}
|
||||
return host_spec;
|
||||
}
|
||||
|
||||
static void insert_port_into_merge_list(unsigned short *mlist,
|
||||
int *merged_port_count,
|
||||
unsigned short p) {
|
||||
@@ -581,6 +464,7 @@ int nmap_main(int argc, char *argv[]) {
|
||||
time_t timep;
|
||||
char mytime[128];
|
||||
char tbuf[128];
|
||||
char errstr[256];
|
||||
struct sockaddr_storage ss;
|
||||
size_t sslen;
|
||||
int option_index;
|
||||
@@ -980,7 +864,8 @@ int nmap_main(int argc, char *argv[]) {
|
||||
fatal("--top-ports should be an integer 1 or greater");
|
||||
} else if (optcmp(long_options[option_index].name, "ip-options") == 0){
|
||||
o.ipoptions = (u8*) safe_malloc(4*10+1);
|
||||
o.ipoptionslen = parse_ip_options(optarg, o.ipoptions, 4*10+1, &o.ipopt_firsthop, &o.ipopt_lasthop);
|
||||
if( (o.ipoptionslen=parse_ip_options(optarg, o.ipoptions, 4*10+1, &o.ipopt_firsthop, &o.ipopt_lasthop, errstr, sizeof(errstr)))==OP_FAILURE )
|
||||
fatal("%s", errstr);
|
||||
if(o.ipoptionslen > 4*10)
|
||||
fatal("Ip options can't be more than 40 bytes long");
|
||||
if(o.ipoptionslen %4 != 0)
|
||||
@@ -1060,7 +945,12 @@ int nmap_main(int argc, char *argv[]) {
|
||||
} else {
|
||||
if (o.numdecoys >= MAX_DECOYS -1)
|
||||
fatal("You are only allowed %d decoys (if you need more redefine MAX_DECOYS in nmap.h)", MAX_DECOYS);
|
||||
if (resolve(p, &o.decoys[o.numdecoys])) {
|
||||
|
||||
/* Try to resolve it */
|
||||
struct sockaddr_in decoytemp;
|
||||
size_t decoytemplen=sizeof(struct sockaddr_in);
|
||||
if( resolve(p, 0, 0, (sockaddr_storage*)&decoytemp, &decoytemplen, AF_INET) == 1 ){
|
||||
o.decoys[o.numdecoys]=decoytemp.sin_addr;
|
||||
o.numdecoys++;
|
||||
} else {
|
||||
fatal("Failed to resolve decoy host: %s (must be hostname or IP address)", p);
|
||||
@@ -1244,7 +1134,7 @@ int nmap_main(int argc, char *argv[]) {
|
||||
case 'S':
|
||||
if (o.spoofsource)
|
||||
fatal("You can only use the source option once! Use -D <decoy1> -D <decoy2> etc. for decoys\n");
|
||||
if (resolve(optarg, &ss, &sslen, o.af()) == 0) {
|
||||
if (resolve(optarg, 0, 0, &ss, &sslen, o.af()) == 0) {
|
||||
fatal("Failed to resolve/decode supposed %s source address %s. Note that if you are using IPv6, the -6 argument must come before -S", (o.af() == AF_INET)? "IPv4" : "IPv6", optarg);
|
||||
}
|
||||
o.setSourceSockAddr(&ss, sslen);
|
||||
@@ -1384,7 +1274,7 @@ int nmap_main(int argc, char *argv[]) {
|
||||
if (o.ipoptionslen >= 8) // at least one ip address
|
||||
log_write(LOG_STDOUT, "Binary ip options to be send:\n%s", buf);
|
||||
log_write(LOG_STDOUT, "Parsed ip options to be send:\n%s\n",
|
||||
print_ip_options(o.ipoptions, o.ipoptionslen));
|
||||
format_ip_options(o.ipoptions, o.ipoptionslen));
|
||||
}
|
||||
|
||||
/* Open the log files, now that we know whether the user wants them appended
|
||||
@@ -1740,7 +1630,7 @@ int nmap_main(int argc, char *argv[]) {
|
||||
/* Now grab any new expressions */
|
||||
while(num_host_exp_groups < o.ping_group_sz &&
|
||||
(!o.max_ips_to_scan || o.max_ips_to_scan > o.numhosts_scanned + (int) Targets.size() + num_host_exp_groups) &&
|
||||
(host_spec = grab_next_host_spec(inputfd, argc, fakeargv))) {
|
||||
(host_spec = grab_next_host_spec(inputfd, o.generate_random_ips, argc, fakeargv))) {
|
||||
// For purposes of random scan
|
||||
host_exp_group[num_host_exp_groups++] = strdup(host_spec);
|
||||
}
|
||||
@@ -1804,7 +1694,7 @@ int nmap_main(int argc, char *argv[]) {
|
||||
currenths->setSourceSockAddr(&ss, sslen);
|
||||
} else {
|
||||
if (gethostname(myname, MAXHOSTNAMELEN) ||
|
||||
resolve(myname, &ss, &sslen, o.af()) == 0)
|
||||
resolve(myname, 0, 0, &ss, &sslen, o.af()) == 0)
|
||||
fatal("Cannot get hostname! Try using -S <my_IP_address> or -e <interface to scan through>\n");
|
||||
|
||||
o.setSourceSockAddr(&ss, sslen);
|
||||
@@ -2782,36 +2672,7 @@ int ftp_anon_connect(struct ftpinfo *ftp) {
|
||||
return sd;
|
||||
}
|
||||
|
||||
/* Returns one if the file pathname given exists, is not a directory and
|
||||
* is readable by the executing process. Returns two if it is readable
|
||||
* and is a directory. Otherwise returns 0.
|
||||
*/
|
||||
|
||||
int fileexistsandisreadable(const char *pathname) {
|
||||
char *pathname_buf = strdup(pathname);
|
||||
int status = 0;
|
||||
|
||||
#ifdef WIN32
|
||||
// stat on windows only works for "dir_name" not for "dir_name/" or "dir_name\\"
|
||||
int pathname_len = strlen(pathname_buf);
|
||||
char last_char = pathname_buf[pathname_len - 1];
|
||||
|
||||
if( last_char == '/'
|
||||
|| last_char == '\\')
|
||||
pathname_buf[pathname_len - 1] = '\0';
|
||||
|
||||
#endif
|
||||
|
||||
struct stat st;
|
||||
|
||||
if (stat(pathname_buf, &st) == -1)
|
||||
status = 0;
|
||||
else if (access(pathname_buf, R_OK) != -1)
|
||||
status = S_ISDIR(st.st_mode) ? 2 : 1;
|
||||
|
||||
free(pathname_buf);
|
||||
return status;
|
||||
}
|
||||
|
||||
int nmap_fileexistsandisreadable(const char* pathname) {
|
||||
return fileexistsandisreadable(pathname);
|
||||
|
||||
@@ -132,6 +132,8 @@
|
||||
|
||||
#undef HAVE_SYS_STAT_H
|
||||
|
||||
#undef HAVE_NET_IF_H
|
||||
|
||||
#undef HAVE_FCNTL_H
|
||||
|
||||
#undef HAVE_TERMIOS_H
|
||||
|
||||
@@ -799,7 +799,7 @@ static void add_dns_server(char *ipaddrs) {
|
||||
|
||||
for (hostname = strtok(ipaddrs, " ,"); hostname != NULL; hostname = strtok(NULL, " ,")) {
|
||||
|
||||
if (!resolve(hostname, (struct sockaddr_storage *) &addr, &addr_len, PF_UNSPEC)) continue;
|
||||
if (!resolve(hostname, 0, 0, (struct sockaddr_storage *) &addr, &addr_len, PF_UNSPEC)) continue;
|
||||
|
||||
for(servI = servs.begin(); servI != servs.end(); servI++) {
|
||||
tpserv = *servI;
|
||||
|
||||
17
nmap_rpc.cc
17
nmap_rpc.cc
@@ -100,6 +100,7 @@
|
||||
#include "timing.h"
|
||||
#include "nmap_error.h"
|
||||
#include "utils.h"
|
||||
#include "nbase.h"
|
||||
|
||||
extern NmapOps o;
|
||||
static struct rpc_info ri;
|
||||
@@ -230,7 +231,7 @@ int send_rpc_query(Target *target_host, unsigned short portno,
|
||||
rpc_xid_base = (unsigned long) get_random_uint();
|
||||
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Sending RPC probe for program %li to %hu/%s -- scan_offset=%d trynum=%d xid=%lX\n", program, portno, proto2ascii(ipproto), scan_offset, trynum, rpc_xid_base + ((portno & 0x3FFF) << 16) + (trynum << 30) + scan_offset);
|
||||
log_write(LOG_PLAIN, "Sending RPC probe for program %li to %hu/%s -- scan_offset=%d trynum=%d xid=%lX\n", program, portno, proto2ascii_lowercase(ipproto), scan_offset, trynum, rpc_xid_base + ((portno & 0x3FFF) << 16) + (trynum << 30) + scan_offset);
|
||||
}
|
||||
|
||||
memset(&sock, 0, sizeof(sock));
|
||||
@@ -372,7 +373,7 @@ static int rpc_are_we_done(char *msg, int msg_len, Target *target,
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Port %hu/%s labelled NON_RPC because of invalid sized message (%d)\n",
|
||||
rsi->rpc_current_port->portno,
|
||||
proto2ascii(rsi->rpc_current_port->proto, true), msg_len);
|
||||
proto2ascii_uppercase(rsi->rpc_current_port->proto), msg_len);
|
||||
}
|
||||
rsi->rpc_status = RPC_STATUS_NOT_RPC;
|
||||
ss->numqueries_outstanding = 0;
|
||||
@@ -385,7 +386,7 @@ static int rpc_are_we_done(char *msg, int msg_len, Target *target,
|
||||
if (((scan_offset >> 16) & 0x3FFF) != (unsigned long) (rsi->rpc_current_port->portno & 0x3FFF)) {
|
||||
/* Doh -- this doesn't seem right */
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Port %hu/%s labelled NON_RPC because ((scan_offset >> 16) & 0x3FFF) is %li\n", rsi->rpc_current_port->portno, proto2ascii(rsi->rpc_current_port->proto, true), ((scan_offset >> 16) & 0x3FFF));
|
||||
log_write(LOG_PLAIN, "Port %hu/%s labelled NON_RPC because ((scan_offset >> 16) & 0x3FFF) is %li\n", rsi->rpc_current_port->portno, proto2ascii_uppercase(rsi->rpc_current_port->proto), ((scan_offset >> 16) & 0x3FFF));
|
||||
}
|
||||
rsi->rpc_status = RPC_STATUS_NOT_RPC;
|
||||
ss->numqueries_outstanding = 0;
|
||||
@@ -465,13 +466,13 @@ static int rpc_are_we_done(char *msg, int msg_len, Target *target,
|
||||
if (o.debugging > 1) {
|
||||
error("Port %hu/%s claims that it is not RPC service %li",
|
||||
rsi->rpc_current_port->portno,
|
||||
proto2ascii(rsi->rpc_current_port->proto, true), current->portno);
|
||||
proto2ascii_uppercase(rsi->rpc_current_port->proto), current->portno);
|
||||
}
|
||||
rsi->valid_responses_this_port++;
|
||||
return 0;
|
||||
} else if (ntohl(rpc_pack->accept_stat) == PROG_MISMATCH) {
|
||||
if (o.debugging > 1) {
|
||||
error("Port %hu/%s claims IT IS RPC service %li", rsi->rpc_current_port->portno, proto2ascii(rsi->rpc_current_port->proto, true), current->portno);
|
||||
error("Port %hu/%s claims IT IS RPC service %li", rsi->rpc_current_port->portno, proto2ascii_uppercase(rsi->rpc_current_port->proto), current->portno);
|
||||
}
|
||||
current->state = PORT_OPEN;
|
||||
rsi->rpc_status = RPC_STATUS_GOOD_PROG;
|
||||
@@ -589,7 +590,7 @@ void get_rpc_results(Target *target, struct portinfo *scan,
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Port %hu/%s labelled NON_RPC because tcp_readlen is %d (should be at least 28)\n",
|
||||
rsi->rpc_current_port->portno,
|
||||
proto2ascii(rsi->rpc_current_port->proto, true),
|
||||
proto2ascii_uppercase(rsi->rpc_current_port->proto),
|
||||
(int) tcp_readlen);
|
||||
}
|
||||
ss->numqueries_outstanding = 0;
|
||||
@@ -603,7 +604,7 @@ void get_rpc_results(Target *target, struct portinfo *scan,
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Port %hu/%s labelled NON_RPC because current_msg_len is %li while tcp_readlen is %d\n",
|
||||
rsi->rpc_current_port->portno,
|
||||
proto2ascii(rsi->rpc_current_port->proto, true),
|
||||
proto2ascii_uppercase(rsi->rpc_current_port->proto),
|
||||
current_msg_len, (int) tcp_readlen);
|
||||
}
|
||||
ss->numqueries_outstanding = 0;
|
||||
@@ -634,7 +635,7 @@ void get_rpc_results(Target *target, struct portinfo *scan,
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Port %hu/%s labelled NON_RPC because current_msg_len is %li\n",
|
||||
rsi->rpc_current_port->portno,
|
||||
proto2ascii(rsi->rpc_current_port->proto, true),
|
||||
proto2ascii_uppercase(rsi->rpc_current_port->proto),
|
||||
current_msg_len);
|
||||
}
|
||||
rsi->rpc_status = RPC_STATUS_NOT_RPC;
|
||||
|
||||
@@ -21,6 +21,7 @@ extern "C"
|
||||
#include "utils.h"
|
||||
#include "tcpip.h"
|
||||
#include "protocols.h"
|
||||
#include "libnetutil/netutil.h"
|
||||
|
||||
#if HAVE_OPENSSL
|
||||
# include <openssl/ssl.h>
|
||||
@@ -1324,10 +1325,6 @@ int l_nsock_sleep(lua_State * L)
|
||||
}
|
||||
|
||||
/****************** NCAP_SOCKET ***********************************************/
|
||||
#ifdef WIN32
|
||||
/* From tcpip.cc. Gets pcap device name from dnet name. */
|
||||
bool DnetName2PcapName(const char *dnetdev, char *pcapdev, int pcapdevlen);
|
||||
#endif
|
||||
|
||||
/* fuckin' C++ maps stuff */
|
||||
/* here we store ncap_sockets */
|
||||
@@ -2144,7 +2141,7 @@ static int l_dnet_send_ip(lua_State * L)
|
||||
dstsin->sin_family = AF_INET;
|
||||
dstsin->sin_addr.s_addr = ip->ip_dst.s_addr;
|
||||
|
||||
if (!route_dst(&dstss, &route))
|
||||
if (!nmap_route_dst(&dstss, &route))
|
||||
goto usesock;
|
||||
|
||||
strncpy(dev, route.ii.devname, sizeof(dev));
|
||||
|
||||
@@ -2992,7 +2992,7 @@ int HostOsScan::send_closedudp_probe(HostOsScanStats *hss,
|
||||
udp->uh_ulen = htons(8 + datalen);
|
||||
|
||||
/* OK, now we should be able to compute a valid checksum */
|
||||
realcheck = magic_tcpudp_cksum(source, hss->target->v4hostip(), IPPROTO_UDP,
|
||||
realcheck = tcpudp_cksum(source, hss->target->v4hostip(), IPPROTO_UDP,
|
||||
sizeof(struct udp_hdr) + datalen, (char *) udp);
|
||||
#if STUPID_SOLARIS_CHECKSUM_BUG
|
||||
udp->uh_sum = sizeof(struct udp_hdr) + datalen;
|
||||
@@ -3207,7 +3207,8 @@ static void begin_sniffer(HostOsScan *HOS, vector<Target *> &Targets) {
|
||||
}
|
||||
filterlen = 0;
|
||||
|
||||
HOS->pd = my_pcap_open_live(Targets[0]->deviceName(), 8192, (o.spoofsource)? 1 : 0, pcap_selectable_fd_valid()? 200 : 2);
|
||||
if((HOS->pd=my_pcap_open_live(Targets[0]->deviceName(), 8192, (o.spoofsource)? 1 : 0, pcap_selectable_fd_valid()? 200 : 2))==NULL)
|
||||
fatal("%s", PCAP_OPEN_ERRMSG);
|
||||
|
||||
if (doIndividual)
|
||||
len = Snprintf(pcap_filter, sizeof(pcap_filter), "dst host %s and (icmp or (tcp and (%s",
|
||||
@@ -3219,9 +3220,9 @@ static void begin_sniffer(HostOsScan *HOS, vector<Target *> &Targets) {
|
||||
fatal("ran out of space in pcap filter");
|
||||
filterlen = len;
|
||||
|
||||
if (o.debugging > 2) log_write(LOG_PLAIN, "Pcap filter: %s\n", pcap_filter);
|
||||
if (o.debugging) log_write(LOG_PLAIN, "Packet capture filter (device %s): %s\n", Targets[0]->deviceFullName(), pcap_filter);
|
||||
set_pcap_filter(Targets[0]->deviceFullName(), HOS->pd, pcap_filter);
|
||||
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
34
output.cc
34
output.cc
@@ -105,6 +105,8 @@
|
||||
#include "Target.h"
|
||||
#include "utils.h"
|
||||
#include "xml.h"
|
||||
#include "nbase.h"
|
||||
#include "libnetutil/netutil.h"
|
||||
|
||||
#include <math.h>
|
||||
|
||||
@@ -251,9 +253,6 @@ void win32_warn_raw_sockets(const char *devname) {
|
||||
}
|
||||
}
|
||||
|
||||
/* From tcpip.cc. */
|
||||
bool DnetName2PcapName(const char *dnetdev, char *pcapdev, int pcapdevlen);
|
||||
|
||||
/* Display the mapping from libdnet interface names (like "eth0") to WinPcap
|
||||
interface names (like "\Device\NPF_{...}"). This is the same mapping used by
|
||||
eth_open and so can help diagnose connection problems. Additionally display
|
||||
@@ -325,11 +324,17 @@ int print_iflist(void) {
|
||||
struct interface_info *iflist;
|
||||
struct sys_route *routes;
|
||||
NmapOutputTable *Tbl = NULL;
|
||||
iflist = getinterfaces(&numifs);
|
||||
char errstr[256];
|
||||
errstr[0]='\0';
|
||||
|
||||
iflist = getinterfaces(&numifs, errstr, sizeof(errstr));
|
||||
|
||||
int i;
|
||||
/* First let's handle interfaces ... */
|
||||
if (numifs == 0) {
|
||||
if (iflist==NULL || numifs<=0) {
|
||||
log_write(LOG_PLAIN, "INTERFACES: NONE FOUND(!)\n");
|
||||
if (o.debugging)
|
||||
log_write(LOG_STDOUT, "Reason: %s\n", errstr);
|
||||
} else {
|
||||
int devcol = 0, shortdevcol = 1, ipcol = 2, typecol = 3, upcol = 4, maccol = 5;
|
||||
Tbl = new NmapOutputTable(numifs + 1, 6);
|
||||
@@ -374,12 +379,15 @@ int print_iflist(void) {
|
||||
#endif
|
||||
|
||||
/* OK -- time to handle routes */
|
||||
routes = getsysroutes(&numroutes);
|
||||
errstr[0]='\0';
|
||||
routes = getsysroutes(&numroutes, errstr, sizeof(errstr));
|
||||
u32 mask_nbo;
|
||||
u16 nbits;
|
||||
struct in_addr ia;
|
||||
if (numroutes == 0) {
|
||||
if (routes==NULL || numroutes<= 0) {
|
||||
log_write(LOG_PLAIN, "ROUTES: NONE FOUND(!)\n");
|
||||
if (o.debugging)
|
||||
log_write(LOG_STDOUT, "Reason: %s\n", errstr);
|
||||
} else {
|
||||
int dstcol = 0, devcol = 1, gwcol = 2;
|
||||
Tbl = new NmapOutputTable(numroutes + 1, 3);
|
||||
@@ -1950,13 +1958,13 @@ static void printtraceroute_normal(Target * currenths) {
|
||||
probe = currenths->traceroute_probespec;
|
||||
if (probe.type == PS_TCP) {
|
||||
log_write(LOG_PLAIN, "TRACEROUTE (using port %d/%s)\n",
|
||||
probe.pd.tcp.dport, proto2ascii(probe.proto));
|
||||
probe.pd.tcp.dport, proto2ascii_lowercase(probe.proto));
|
||||
} else if (probe.type == PS_UDP) {
|
||||
log_write(LOG_PLAIN, "TRACEROUTE (using port %d/%s)\n",
|
||||
probe.pd.udp.dport, proto2ascii(probe.proto));
|
||||
probe.pd.udp.dport, proto2ascii_lowercase(probe.proto));
|
||||
} else if (probe.type == PS_SCTP) {
|
||||
log_write(LOG_PLAIN, "TRACEROUTE (using port %d/%s)\n",
|
||||
probe.pd.sctp.dport, proto2ascii(probe.proto));
|
||||
probe.pd.sctp.dport, proto2ascii_lowercase(probe.proto));
|
||||
} else if (probe.type == PS_ICMP || probe.type == PS_PROTO) {
|
||||
struct protoent *proto = nmap_getprotbynum(htons(probe.proto));
|
||||
log_write(LOG_PLAIN, "TRACEROUTE (using proto %d/%s)\n",
|
||||
@@ -2055,13 +2063,13 @@ static void printtraceroute_xml(Target * currenths) {
|
||||
probe = currenths->traceroute_probespec;
|
||||
if (probe.type == PS_TCP) {
|
||||
xml_attribute("port", "%d", probe.pd.tcp.dport);
|
||||
xml_attribute("proto", "%s", proto2ascii(probe.proto));
|
||||
xml_attribute("proto", "%s", proto2ascii_lowercase(probe.proto));
|
||||
} else if (probe.type == PS_UDP) {
|
||||
xml_attribute("port", "%d", probe.pd.udp.dport);
|
||||
xml_attribute("proto", "%s", proto2ascii(probe.proto));
|
||||
xml_attribute("proto", "%s", proto2ascii_lowercase(probe.proto));
|
||||
} else if (probe.type == PS_SCTP) {
|
||||
xml_attribute("port", "%d", probe.pd.sctp.dport);
|
||||
xml_attribute("proto", "%s", proto2ascii(probe.proto));
|
||||
xml_attribute("proto", "%s", proto2ascii_lowercase(probe.proto));
|
||||
} else if (probe.type == PS_ICMP || probe.type == PS_PROTO) {
|
||||
struct protoent *proto = nmap_getprotbynum(htons(probe.proto));
|
||||
if (proto == NULL)
|
||||
|
||||
17
output.h
17
output.h
@@ -112,6 +112,23 @@
|
||||
|
||||
#define LOG_NAMES {"normal", "machine", "$Cr!pT |<!dd!3", "XML"}
|
||||
|
||||
#define PCAP_OPEN_ERRMSG "Call to pcap_open_live() failed three times. "\
|
||||
"There are several possible reasons for this, depending on your operating "\
|
||||
"system:\nLINUX: If you are getting Socket type not supported, try "\
|
||||
"modprobe af_packet or recompile your kernel with SOCK_PACKET enabled.\n "\
|
||||
"*BSD: If you are getting device not configured, you need to recompile "\
|
||||
"your kernel with Berkeley Packet Filter support. If you are getting "\
|
||||
"No such file or directory, try creating the device (eg cd /dev; "\
|
||||
"MAKEDEV <device>; or use mknod).\n*WINDOWS: Nmap only supports "\
|
||||
"ethernet interfaces on Windows for most operations because Microsoft "\
|
||||
"disabled raw sockets as of Windows XP SP2. Depending on the reason for "\
|
||||
"this error, it is possible that the --unprivileged command-line argument "\
|
||||
"will help.\nSOLARIS: If you are trying to scan localhost or the "\
|
||||
"address of an interface and are getting '/dev/lo0: No such file or "\
|
||||
"directory' or 'lo0: No DLPI device found', complain to Sun. I don't "\
|
||||
"think Solaris can support advanced localhost scans. You can probably "\
|
||||
"use \"-Pn -sT localhost\" though.\n\n"
|
||||
|
||||
#include "portlist.h"
|
||||
#include "nmap.h"
|
||||
#include "global_structures.h"
|
||||
|
||||
@@ -98,6 +98,7 @@
|
||||
#include "protocols.h"
|
||||
#include "nmap_rpc.h"
|
||||
#include "tcpip.h"
|
||||
#include "libnetutil/netutil.h"
|
||||
|
||||
using namespace std;
|
||||
|
||||
@@ -503,7 +504,7 @@ void PortList::setPortState(u16 portno, u8 protocol, int state) {
|
||||
if ((state == PORT_OPEN && o.verbose) || (o.debugging > 1)) {
|
||||
log_write(LOG_STDOUT, "Discovered %s port %hu/%s%s\n",
|
||||
statenum2str(state), portno,
|
||||
proto2ascii(protocol), idstr? idstr : "");
|
||||
proto2ascii_lowercase(protocol), idstr? idstr : "");
|
||||
log_flush(LOG_STDOUT);
|
||||
}
|
||||
|
||||
@@ -521,7 +522,7 @@ void PortList::setPortState(u16 portno, u8 protocol, int state) {
|
||||
/* We must discount our statistics from the old values. Also warn
|
||||
if a complete duplicate */
|
||||
if (o.debugging && oldport->state == state) {
|
||||
error("Duplicate port (%hu/%s)", portno, proto2ascii(protocol));
|
||||
error("Duplicate port (%hu/%s)", portno, proto2ascii_lowercase(protocol));
|
||||
}
|
||||
state_counts_proto[proto][oldport->state]--;
|
||||
} else {
|
||||
@@ -716,7 +717,7 @@ int PortList::forgetPort(u16 portno, u8 protocol) {
|
||||
|
||||
if (o.verbose) {
|
||||
log_write(LOG_STDOUT, "Deleting port %hu/%s, which we thought was %s\n",
|
||||
portno, proto2ascii(answer->proto),
|
||||
portno, proto2ascii_lowercase(answer->proto),
|
||||
statenum2str(answer->state));
|
||||
log_flush(LOG_STDOUT);
|
||||
}
|
||||
|
||||
@@ -3933,7 +3933,7 @@ static bool get_arp_result(UltraScanInfo *USI, struct timeval *stime) {
|
||||
do {
|
||||
to_usec = TIMEVAL_SUBTRACT(*stime, USI->now);
|
||||
if (to_usec < 2000) to_usec = 2000;
|
||||
rc = read_arp_reply_pcap(USI->pd, rcvdmac, &rcvdIP, to_usec, &rcvdtime);
|
||||
rc = read_arp_reply_pcap(USI->pd, rcvdmac, &rcvdIP, to_usec, &rcvdtime, PacketTrace::traceArp);
|
||||
gettimeofday(&USI->now, NULL);
|
||||
if (rc == -1) fatal("Received -1 response from readarp_reply_pcap");
|
||||
if (rc == 0) {
|
||||
@@ -4884,7 +4884,9 @@ static void begin_sniffer(UltraScanInfo *USI, vector<Target *> &Targets) {
|
||||
}
|
||||
}
|
||||
|
||||
USI->pd = my_pcap_open_live(Targets[0]->deviceName(), 100, (o.spoofsource)? 1 : 0, pcap_selectable_fd_valid()? 200 : 2);
|
||||
if((USI->pd=my_pcap_open_live(Targets[0]->deviceName(), 100, (o.spoofsource)? 1 : 0, pcap_selectable_fd_valid()? 200 : 2))==NULL)
|
||||
fatal("%s", PCAP_OPEN_ERRMSG);
|
||||
|
||||
if (USI->ping_scan_arp){
|
||||
/* Some OSs including Windows 7 and Solaris 10 have been seen to send their
|
||||
ARP replies to the broadcast address, not to the (unicast) address that
|
||||
@@ -4931,7 +4933,7 @@ static void begin_sniffer(UltraScanInfo *USI, vector<Target *> &Targets) {
|
||||
pcap_filter+=" and (icmp or tcp or udp or sctp)";
|
||||
}
|
||||
}else assert(0);
|
||||
if (o.debugging > 2) log_write(LOG_PLAIN, "Pcap filter: %s\n", pcap_filter.c_str());
|
||||
if (o.debugging) log_write(LOG_PLAIN, "Packet capture filter (device %s): %s\n", Targets[0]->deviceFullName(), pcap_filter.c_str());
|
||||
set_pcap_filter(Targets[0]->deviceFullName(), USI->pd, pcap_filter.c_str());
|
||||
/* pcap_setnonblock(USI->pd, 1, NULL); */
|
||||
return;
|
||||
|
||||
@@ -1420,7 +1420,7 @@ void ServiceNFO::addToServiceFingerprint(const char *probeName, const u8 *resp,
|
||||
if (servicefplen == 0) {
|
||||
timep = time(NULL);
|
||||
ltime = localtime(&timep);
|
||||
servicefplen = Snprintf(servicefp, spaceleft, "SF-Port%hu-%s:V=%s%s%%I=%d%%D=%d/%d%%Time=%X%%P=%s", portno, proto2ascii(proto, true), NMAP_VERSION, (tunnel == SERVICE_TUNNEL_SSL)? "%T=SSL" : "", o.version_intensity, ltime->tm_mon + 1, ltime->tm_mday, (int) timep, NMAP_PLATFORM);
|
||||
servicefplen = Snprintf(servicefp, spaceleft, "SF-Port%hu-%s:V=%s%s%%I=%d%%D=%d/%d%%Time=%X%%P=%s", portno, proto2ascii_uppercase(proto), NMAP_VERSION, (tunnel == SERVICE_TUNNEL_SSL)? "%T=SSL" : "", o.version_intensity, ltime->tm_mon + 1, ltime->tm_mday, (int) timep, NMAP_PLATFORM);
|
||||
}
|
||||
|
||||
// Note that we give the total length of the response, even though we
|
||||
@@ -1711,7 +1711,7 @@ static void adjustPortStateIfNecessary(ServiceNFO *svc) {
|
||||
svc->target->NameIP(host, sizeof(host));
|
||||
|
||||
log_write(LOG_STDOUT, "Discovered %s port %hu/%s on %s is actually open\n",
|
||||
statenum2str(oldstate), svc->portno, proto2ascii(svc->proto), host);
|
||||
statenum2str(oldstate), svc->portno, proto2ascii_lowercase(svc->proto), host);
|
||||
log_flush(LOG_STDOUT);
|
||||
}
|
||||
}
|
||||
@@ -1728,7 +1728,7 @@ static void adjustPortStateIfNecessary(ServiceNFO *svc) {
|
||||
|
||||
// Report data as probes are sent if --version-trace has been requested
|
||||
if (o.debugging > 1 || o.versionTrace()) {
|
||||
log_write(LOG_PLAIN, "Service scan sending probe %s to %s:%hu (%s)\n", probe->getName(), svc->target->targetipstr(), svc->portno, proto2ascii(svc->proto));
|
||||
log_write(LOG_PLAIN, "Service scan sending probe %s to %s:%hu (%s)\n", probe->getName(), svc->target->targetipstr(), svc->portno, proto2ascii_lowercase(svc->proto));
|
||||
}
|
||||
|
||||
assert(probe);
|
||||
@@ -1984,7 +1984,7 @@ static int launchSomeServiceProbes(nsock_pool nsp, ServiceGroup *SG) {
|
||||
fatal("Failed to allocate Nsock I/O descriptor in %s()", __func__);
|
||||
}
|
||||
if (o.debugging > 1) {
|
||||
log_write(LOG_PLAIN, "Starting probes against new service: %s:%hu (%s)\n", svc->target->targetipstr(), svc->portno, proto2ascii(svc->proto));
|
||||
log_write(LOG_PLAIN, "Starting probes against new service: %s:%hu (%s)\n", svc->target->targetipstr(), svc->portno, proto2ascii_lowercase(svc->proto));
|
||||
}
|
||||
if (o.spoofsource) {
|
||||
o.SourceSockAddr(&ss, &ss_len);
|
||||
|
||||
42
targets.cc
42
targets.cc
@@ -285,46 +285,6 @@ TargetGroup* load_exclude_string(const char *s) {
|
||||
return specs_to_targetgroups(specs);
|
||||
}
|
||||
|
||||
static inline bool is_host_separator(int c) {
|
||||
return c == ' ' || c == '\r' || c == '\n' || c == '\t' || c == '\0';
|
||||
}
|
||||
|
||||
/* Read a single host specification from a file, as for -iL and --excludefile.
|
||||
It returns the length of the string read; an overflow is indicated when the
|
||||
return value is >= n. Returns 0 if there was no specification to be read. The
|
||||
buffer is always null-terminated. */
|
||||
size_t read_host_from_file(FILE *fp, char *buf, size_t n)
|
||||
{
|
||||
int ch;
|
||||
size_t i;
|
||||
|
||||
i = 0;
|
||||
ch = getc(fp);
|
||||
while (is_host_separator(ch) || ch == '#') {
|
||||
if (ch == '#') {
|
||||
/* Skip comments to the end of the line. */
|
||||
while ((ch = getc(fp)) != EOF && ch != '\n')
|
||||
;
|
||||
} else {
|
||||
ch = getc(fp);
|
||||
}
|
||||
}
|
||||
while (ch != EOF && !(is_host_separator(ch) || ch == '#')) {
|
||||
if (i < n)
|
||||
buf[i] = ch;
|
||||
i++;
|
||||
ch = getc(fp);
|
||||
}
|
||||
if (ch != EOF)
|
||||
ungetc(ch, fp);
|
||||
if (i < n)
|
||||
buf[i] = '\0';
|
||||
else if (n > 0)
|
||||
/* Null-terminate even though it was too long. */
|
||||
buf[n - 1] = '\0';
|
||||
|
||||
return i;
|
||||
}
|
||||
|
||||
/* A debug routine to dump some information to stdout. Invoked if debugging is
|
||||
set to 3 or higher. I had to make significant changes from wam's code.
|
||||
@@ -505,7 +465,7 @@ Target *nexthost(HostGroupState *hs, TargetGroup *exclude_group,
|
||||
#endif // WIN32
|
||||
)) {
|
||||
t->TargetSockAddr(&ss, &sslen);
|
||||
if (!route_dst(&ss, &rnfo)) {
|
||||
if (!nmap_route_dst(&ss, &rnfo)) {
|
||||
fatal("%s: failed to determine route to %s", __func__, t->NameIP());
|
||||
}
|
||||
if (rnfo.direct_connect) {
|
||||
|
||||
@@ -161,8 +161,6 @@ Target *nexthost(HostGroupState *hs, TargetGroup *exclude_group,
|
||||
struct scan_lists *ports, int pingtype);
|
||||
TargetGroup* load_exclude_file(FILE *fp);
|
||||
TargetGroup* load_exclude_string(const char *s);
|
||||
/* Read a single host specification from a file, as for -iL and --excludefile. */
|
||||
size_t read_host_from_file(FILE *fp, char *buf, size_t n);
|
||||
/* a debugging routine to dump an exclude list to stdout. */
|
||||
int dumpExclude(TargetGroup*exclude_group);
|
||||
/* Returns the last host obtained by nexthost. It will be given again the next
|
||||
|
||||
137
tcpip.h
137
tcpip.h
@@ -212,7 +212,7 @@ extern "C" {
|
||||
#include <netinet/ip_icmp.h>
|
||||
#endif
|
||||
|
||||
typedef enum { devt_ethernet, devt_loopback, devt_p2p, devt_other } devtype;
|
||||
|
||||
|
||||
#include "nmap.h"
|
||||
#include "global_structures.h"
|
||||
@@ -224,11 +224,12 @@ typedef enum { devt_ethernet, devt_loopback, devt_p2p, devt_other } devtype;
|
||||
|
||||
/* Used for tracing all packets sent or received (eg the
|
||||
--packet-trace option) */
|
||||
|
||||
class PacketTrace {
|
||||
public:
|
||||
/* static const int SEND=1;
|
||||
static const int RCV=2; */
|
||||
enum pdirection { SENT=1, RCVD=2 };
|
||||
static const int SENT=1; /* These two values must not be changed */
|
||||
static const int RCVD=2;
|
||||
typedef int pdirection;
|
||||
/* Takes an IP PACKET and prints it if packet tracing is enabled.
|
||||
'packet' must point to the IPv4 header. The direction must be
|
||||
PacketTrace::SENT or PacketTrace::RCVD . Optional 'now' argument
|
||||
@@ -265,54 +266,6 @@ class PacketCounter {
|
||||
sendPackets, sendBytes, recvPackets, recvBytes;
|
||||
};
|
||||
|
||||
#define MAX_LINK_HEADERSZ 24
|
||||
struct link_header {
|
||||
int datalinktype; /* pcap_datalink(), such as DLT_EN10MB */
|
||||
int headerlen; /* 0 if header was too big or unavailaable */
|
||||
u8 header[MAX_LINK_HEADERSZ];
|
||||
};
|
||||
|
||||
/* Relevant (to Nmap) information about an interface */
|
||||
struct interface_info {
|
||||
char devname[16];
|
||||
char devfullname[16]; /* can include alias info, such as eth0:2. */
|
||||
struct sockaddr_storage addr;
|
||||
u16 netmask_bits; /* CIDR-style. So 24 means class C (255.255.255.0)*/
|
||||
devtype device_type; /* devt_ethernet, devt_loopback, devt_p2p, devt_other */
|
||||
bool device_up; /* True if the device is up (enabled) */
|
||||
u8 mac[6]; /* Interface MAC address if device_type is devt_ethernet */
|
||||
};
|
||||
|
||||
struct route_nfo {
|
||||
struct interface_info ii;
|
||||
|
||||
/* true if the target is directly connected on the network (no routing
|
||||
required). */
|
||||
bool direct_connect;
|
||||
|
||||
/* This is the source address that should be used by the packets. It
|
||||
may be different than ii.addr if you are using localhost interface
|
||||
to scan the IP of another interface on the machine */
|
||||
struct sockaddr_storage srcaddr;
|
||||
|
||||
/* If direct_connect is 0, this is filled in with the next hop
|
||||
required to route to the target */
|
||||
struct sockaddr_storage nexthop;
|
||||
};
|
||||
|
||||
struct sys_route {
|
||||
struct interface_info *device;
|
||||
u32 dest;
|
||||
u32 netmask;
|
||||
struct in_addr gw; /* gateway - 0 if none */
|
||||
};
|
||||
|
||||
struct eth_nfo {
|
||||
char srcmac[6];
|
||||
char dstmac[6];
|
||||
eth_t *ethsd; // Optional, but improves performance. Set to NULL if unavail
|
||||
char devname[16]; // Only needed if ethsd is NULL.
|
||||
};
|
||||
|
||||
#ifndef HAVE_STRUCT_IP
|
||||
#define HAVE_STRUCT_IP
|
||||
@@ -435,23 +388,12 @@ struct icmp
|
||||
not thread-safe and can only be used once in calls like printf()
|
||||
*/
|
||||
const char *inet_socktop(struct sockaddr_storage *ss);
|
||||
|
||||
/* Tries to resolve the given name (or literal IP) into a sockaddr
|
||||
structure. This function calls getaddrinfo and returns the same
|
||||
addrinfo linked list that getaddrinfo produces. Returns NULL for any
|
||||
error or failure to resolve. */
|
||||
struct addrinfo *resolve_all(char *hostname, int pf);
|
||||
/* Tries to resolve the given name (or literal IP) into a sockaddr
|
||||
structure. The af should be PF_INET (for IPv4) or PF_INET6. Returns 0
|
||||
if hostname cannot be resolved. It is OK to pass in a sockaddr_in or
|
||||
sockaddr_in6 casted to a sockaddr_storage as long as you use the matching
|
||||
pf.*/
|
||||
int resolve(char *hostname, struct sockaddr_storage *ss, size_t *sslen,
|
||||
int pf);
|
||||
/* LEGACY resolve() function that only supports IPv4 -- see IPv6 version
|
||||
above. Tries to resolve given hostname and stores
|
||||
result in ip . returns 0 if hostname cannot
|
||||
be resolved */
|
||||
int resolve(char *hostname, struct in_addr *ip);
|
||||
|
||||
/* Takes a destination address (dst) and tries to determine the
|
||||
source address and interface necessary to route to this address.
|
||||
@@ -459,7 +401,7 @@ int resolve(char *hostname, struct in_addr *ip);
|
||||
a route is found, true is returned and rnfo is filled in with all
|
||||
of the routing details. This function takes into account -S and -e
|
||||
options set by user (o.spoofsource, o.device) */
|
||||
bool route_dst(const struct sockaddr_storage *const dst, struct route_nfo *rnfo);
|
||||
int nmap_route_dst(const struct sockaddr_storage * const dst, struct route_nfo *rnfo);
|
||||
|
||||
/* Determines what interface packets destined to 'dest' should be
|
||||
routed through. It can also discover the appropriate next hop (if
|
||||
@@ -475,9 +417,6 @@ bool routethrough(const struct sockaddr_storage * const dest,
|
||||
|
||||
unsigned short in_cksum(u16 *ptr,int nbytes);
|
||||
|
||||
unsigned short magic_tcpudp_cksum(const struct in_addr *src,
|
||||
const struct in_addr *dst,
|
||||
u8 proto, u16 len, const void *hstart);
|
||||
|
||||
/* Build and send a raw tcp packet. If TTL is -1, a partially random
|
||||
(but likely large enough) one is chosen */
|
||||
@@ -606,22 +545,6 @@ int send_udp_raw_decoys( int sd, struct eth_nfo *eth,
|
||||
char *data, u16 datalen);
|
||||
|
||||
|
||||
/* Calls pcap_open_live and spits out an error (and quits) if the call fails.
|
||||
So a valid pcap_t will always be returned. */
|
||||
pcap_t *my_pcap_open_live(const char *device, int snaplen, int promisc,
|
||||
int to_ms);
|
||||
|
||||
// Returns whether the system supports pcap_get_selectable_fd() properly
|
||||
bool pcap_selectable_fd_valid();
|
||||
|
||||
/* Call this instead of pcap_get_selectable_fd directly (or your code
|
||||
won't compile on Windows). On systems which don't seem to support
|
||||
the pcap_get_selectable_fd() function properly, returns -1,
|
||||
otherwise simply calls pcap_selectable_fd and returns the
|
||||
results. If you just want to test whether the function is supported,
|
||||
use pcap_selectable_fd_valid() instead. */
|
||||
int my_pcap_get_selectable_fd(pcap_t *p);
|
||||
|
||||
// Returns whether the packet receive time value obtaned from libpcap
|
||||
// (and thus by readip_pcap()) should be considered valid. When
|
||||
// invalid (Windows and Amiga), readip_pcap returns the time you called it.
|
||||
@@ -631,51 +554,20 @@ bool pcap_recv_timeval_valid();
|
||||
packets). */
|
||||
void pcap_print_stats(int logt, pcap_t *pd);
|
||||
|
||||
/* A simple function that caches the eth_t from dnet for one device,
|
||||
to avoid opening, closing, and re-opening it thousands of tims. If
|
||||
you give a different device, this function will close the first
|
||||
one. Thus this should never be used by programs that need to deal
|
||||
with multiple devices at once. In addition, you MUST NEVER
|
||||
eth_close() A DEVICE OBTAINED FROM THIS FUNCTION. Instead, you can
|
||||
call eth_close_cached() to close whichever device (if any) is
|
||||
cached. Returns NULL if it fails to open the device. */
|
||||
eth_t *eth_open_cached(const char *device);
|
||||
|
||||
/* See the description for eth_open_cached */
|
||||
void eth_close_cached();
|
||||
|
||||
/* A simple function I wrote to help in debugging, shows the important fields
|
||||
of a TCP packet*/
|
||||
int readtcppacket(const u8 *packet, int readdata);
|
||||
int readudppacket(const u8 *packet, int readdata);
|
||||
/* Convert an IP address to the device (IE ppp0 eth0) using that address. Dev passed in must be at least
|
||||
32 bytes long */
|
||||
int ipaddr2devname( char *dev, const struct in_addr *addr );
|
||||
/* And vice versa */
|
||||
int devname2ipaddr(char *dev, struct in_addr *addr);
|
||||
|
||||
/* Looks for an interface assigned to the given IP (ss), and returns
|
||||
the interface_info for the first one found. If non found, returns NULL */
|
||||
struct interface_info *getInterfaceByIP(struct sockaddr_storage *ss);
|
||||
/* Looks for an interface with the given name (iname), and returns the
|
||||
corresponding interface_info if found. Will accept a match of
|
||||
devname or devfullname. Returns NULL if none found */
|
||||
struct interface_info *getInterfaceByName(char *iname);
|
||||
/* Where the above 4 functions get their info */
|
||||
struct interface_info *getinterfaces(int *howmany);
|
||||
|
||||
|
||||
pcap_if_t *getpcapinterfaces();
|
||||
|
||||
/* Parse the system routing table, converting each route into a
|
||||
sys_route entry. Returns an array of sys_routes. numroutes is set
|
||||
to the number of routes in the array. The routing table is only
|
||||
read the first time this is called -- later results are cached.
|
||||
The returned route array is sorted by netmask with the most
|
||||
specific matches first. */
|
||||
struct sys_route *getsysroutes(int *howmany);
|
||||
void sethdrinclude(int sd);
|
||||
|
||||
void set_ipoptions(int sd, void *opts, size_t optslen);
|
||||
|
||||
void set_ttl(int sd, int ttl);
|
||||
|
||||
/* Fill buf (up to buflen -- truncate if necessary but always
|
||||
terminate) with a short representation of the packet stats.
|
||||
@@ -711,15 +603,8 @@ bool setTargetNextHopMAC(Target *target);
|
||||
bool getNextHopMAC(char *iface, u8 *srcmac, struct sockaddr_storage *srcss,
|
||||
struct sockaddr_storage *dstss, u8 *dstmac);
|
||||
|
||||
int islocalhost(const struct in_addr * const addr);
|
||||
int isipprivate(const struct in_addr * const addr);
|
||||
|
||||
// Takes a protocol number like IPPROTO_TCP, IPPROTO_UDP, or
|
||||
// IPPROTO_IP and returns a ascii representation (or "unknown" if it
|
||||
// doesn't recognize the number). If uppercase is true, the returned
|
||||
// value will be in all uppercase letters. You can skip this
|
||||
// parameter to use lowercase.
|
||||
const char *proto2ascii(u8 proto, bool uppercase=false);
|
||||
|
||||
/* Hex dump */
|
||||
int get_link_offset(char *device);
|
||||
/* If rcvdtime is non-null and a packet is returned, rcvd will be
|
||||
|
||||
@@ -781,14 +781,16 @@ TracerouteState::TracerouteState(std::vector<Target *> &targets) {
|
||||
}
|
||||
|
||||
/* Assume that all the targets share the same device. */
|
||||
pd = my_pcap_open_live(targets[0]->deviceName(), 128, o.spoofsource, 2);
|
||||
if((pd=my_pcap_open_live(targets[0]->deviceName(), 128, o.spoofsource, 2))==NULL)
|
||||
fatal("%s", PCAP_OPEN_ERRMSG);
|
||||
sslen = sizeof(srcaddr);
|
||||
targets[0]->SourceSockAddr(&srcaddr, &sslen);
|
||||
n = Snprintf(pcap_filter, sizeof(pcap_filter), "dst host %s",
|
||||
ss_to_string(&srcaddr));
|
||||
assert(n < (int) sizeof(pcap_filter));
|
||||
set_pcap_filter(targets[0]->deviceFullName(), pd, pcap_filter);
|
||||
|
||||
if (o.debugging)
|
||||
log_write(LOG_STDOUT, "Packet capture filter (device %s): %s\n", targets[0]->deviceFullName(), pcap_filter);
|
||||
for (it = targets.begin(); it != targets.end(); it++) {
|
||||
HostState *state = new HostState(*it);
|
||||
hosts.push_back(state);
|
||||
|
||||
352
utils.cc
352
utils.cc
@@ -171,24 +171,6 @@ char *chomp(char *string) {
|
||||
return string;
|
||||
}
|
||||
|
||||
/* Compare a canonical option name (e.g. "max-scan-delay") with a
|
||||
user-generated option such as "max_scan_delay" and returns 0 if the
|
||||
two values are considered equivalant (for example, - and _ are
|
||||
considered to be the same), nonzero otherwise. */
|
||||
int optcmp(const char *a, const char *b) {
|
||||
while(*a && *b) {
|
||||
if (*a == '_' || *a == '-') {
|
||||
if (*b != '_' && *b != '-')
|
||||
return 1;
|
||||
}
|
||||
else if (*a != *b)
|
||||
return 1;
|
||||
a++; b++;
|
||||
}
|
||||
if (*a || *b)
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Scramble the contents of an array*/
|
||||
void genfry(unsigned char *arr, int elem_sz, int num_elem) {
|
||||
@@ -447,143 +429,6 @@ char *cstring_unescape(char *str, unsigned int *newlen) {
|
||||
return str;
|
||||
}
|
||||
|
||||
/* This function converts zero-terminated 'txt' string to binary 'data'.
|
||||
It is used to parse user input for ip options. Some examples of possible input
|
||||
strings and results:
|
||||
'\x01*2\xA2' -> [0x01,0x01,0xA2] // with 'x' number is parsed in hex
|
||||
'\01\01\255' -> [0x01,0x01,0xFF] // without 'x' its in decimal
|
||||
'\x01\x00*2' -> [0x01,0x00,0x00] // '*' is copying char
|
||||
'R' -> Record Route with 9 slots
|
||||
'S 192.168.0.1 172.16.0.1' -> Strict Route with 2 slots
|
||||
'L 192.168.0.1 172.16.0.1' -> Loose Route with 2 slots
|
||||
'T' -> Record Timestamp with 9 slots
|
||||
'U' -> Record Timestamp and Ip Address with 4 slots
|
||||
*/
|
||||
int parse_ip_options(char *txt, u8 *data, int datalen, int* firsthopoff, int* lasthopoff){
|
||||
enum{
|
||||
NONE = 0,
|
||||
SLASH = 1,
|
||||
MUL = 2,
|
||||
RR = 3,
|
||||
TIME = 4,
|
||||
} s = NONE;
|
||||
char *n, lc;
|
||||
char *c = txt;
|
||||
u8 *d = data;
|
||||
int i,j;
|
||||
int base = 10;
|
||||
u8 *dataend = &data[datalen];
|
||||
u8 *len = NULL;
|
||||
char buf[32];
|
||||
memset(data, 0, datalen);
|
||||
bool sourcerouting = false;
|
||||
|
||||
|
||||
for(;*c;c++){
|
||||
switch(s){
|
||||
case SLASH:
|
||||
// parse \x00 string
|
||||
if(*c == 'x'){// just ignore this char
|
||||
base = 16;
|
||||
break;
|
||||
}
|
||||
if(isxdigit((int) (unsigned char) *c)){
|
||||
*d++ = strtol(c, &n, base);
|
||||
c=n-1;
|
||||
}else
|
||||
fatal("not a digit after '\\'");
|
||||
s = NONE;
|
||||
break;
|
||||
case MUL:
|
||||
if(d==data)
|
||||
fatal("nothing before '*' char");
|
||||
i = strtol(c, &n, 10);
|
||||
if(i<2)
|
||||
fatal("bad number after '*'");
|
||||
c = n-1; // move current txt pointer
|
||||
lc = *(d-1); // last char, we'll copy this
|
||||
for(j=1; j<i; j++){
|
||||
*d++ = lc;
|
||||
if(d == dataend) // check for overflow
|
||||
goto after;
|
||||
}
|
||||
s = NONE;
|
||||
break;
|
||||
case RR:
|
||||
if(*c==' ' || *c==',')
|
||||
break;
|
||||
n = buf;
|
||||
while((*c=='.' || (*c>='0' && *c<='9')) && n-buf <= ((int)sizeof(buf)-1))
|
||||
*n++ = *c++;
|
||||
*n = '\0'; c--;
|
||||
if(d+4>=dataend)
|
||||
fatal("Buffer too small. Or input data too big :)");
|
||||
i = inet_pton(AF_INET, buf, d);
|
||||
if(i<1)
|
||||
fatal("Not a valid ipv4 address '%s'",buf);
|
||||
// remember offset of first hop
|
||||
if(sourcerouting && !*firsthopoff)
|
||||
*firsthopoff = d - data;
|
||||
d+=4;
|
||||
if(*len<37)
|
||||
*len += 4;
|
||||
break;
|
||||
case TIME:
|
||||
fatal("No more arguments allowed!");
|
||||
default:
|
||||
switch(*c){
|
||||
case '\\':s = SLASH;base=10;break;
|
||||
case '*':s = MUL;break;
|
||||
case 'R':
|
||||
case 'S':
|
||||
case 'L':
|
||||
if(d != data)
|
||||
fatal("This option can't be used in that way");
|
||||
*d++ = '\x01';//NOP
|
||||
switch(*c){
|
||||
case 'R':*d++ = 7;break;
|
||||
case 'S':*d++ = 137; sourcerouting=true; break;
|
||||
case 'L':*d++ = 131; sourcerouting=true; break;
|
||||
}
|
||||
len = d;
|
||||
*d++ = (*c=='R')? 39 : 3; // length: 3+4*9 bytes
|
||||
*d++ = 4; //pointer
|
||||
s = RR;
|
||||
break;
|
||||
case 'T':
|
||||
case 'U':
|
||||
if(d != data)
|
||||
fatal("This option can't be used in that way");
|
||||
*d++ = 68; // option type
|
||||
len = d;
|
||||
*d++ = (*c=='U') ? 36 : 40; // length: 3+4*9 bytes or 4+4*9 bytes
|
||||
*d++ = 5; // pointer
|
||||
*d++ = (*c=='U') ? 1 : 0; // flag: address and Time fields
|
||||
s = TIME;
|
||||
break;
|
||||
default://*d++ = *c;
|
||||
fatal("Bad character in ip option '%c'",*c);
|
||||
}
|
||||
}
|
||||
if(d == dataend)
|
||||
break;
|
||||
assert(d<dataend);
|
||||
}
|
||||
if(sourcerouting){
|
||||
if(*len<37){
|
||||
*len+=4;
|
||||
*lasthopoff = d - data;
|
||||
*d++ = 0;*d++ = 0;*d++ = 0;*d++ = 0;
|
||||
}else
|
||||
fatal("When using source routing you must leave at least one slot for target's ip.");
|
||||
}
|
||||
if(s == RR)
|
||||
return(*len+1); // because we inject NOP before
|
||||
if(s == TIME)
|
||||
return(*len);
|
||||
after:
|
||||
return(d - data);
|
||||
}
|
||||
|
||||
void bintohexstr(char *buf, int buflen, char *src, int srclen){
|
||||
int bp=0;
|
||||
@@ -604,203 +449,6 @@ void bintohexstr(char *buf, int buflen, char *src, int srclen){
|
||||
bp += Snprintf(buf+bp, buflen-bp,"\n");
|
||||
}
|
||||
|
||||
static inline char* STRAPP(const char *fmt, ...) {
|
||||
static char buf[256];
|
||||
static int bp;
|
||||
int left = (int)sizeof(buf)-bp;
|
||||
if(!fmt){
|
||||
bp = 0;
|
||||
return(buf);
|
||||
}
|
||||
if (left <= 0)
|
||||
return buf;
|
||||
va_list ap;
|
||||
va_start(ap, fmt);
|
||||
bp += Vsnprintf (buf+bp, left, fmt, ap);
|
||||
va_end(ap);
|
||||
|
||||
return(buf);
|
||||
}
|
||||
|
||||
#define HEXDUMP -2
|
||||
#define UNKNOWN -1
|
||||
|
||||
#define BREAK() \
|
||||
{option_type = HEXDUMP; break;}
|
||||
#define CHECK(tt) \
|
||||
if(tt >= option_end) \
|
||||
{option_type = HEXDUMP; break;}
|
||||
/* It tries to decode ip options.
|
||||
Returns static buffer. watch out. */
|
||||
char* print_ip_options(u8* ipopt, int ipoptlen) {
|
||||
char ipstring[32];
|
||||
int option_type = UNKNOWN;// option type
|
||||
int option_len = 0; // option length
|
||||
int option_pt = 0; // option pointer
|
||||
int option_fl = 0; // option flag
|
||||
u8 *tptr; // temp pointer
|
||||
u32 *tint; // temp int
|
||||
|
||||
int option_sta = 0; // option start offset
|
||||
int option_end = 0; // option end offset
|
||||
int pt = 0; // current offset
|
||||
|
||||
// clear buffer
|
||||
STRAPP(NULL,NULL);
|
||||
|
||||
if(!ipoptlen)
|
||||
return(NULL);
|
||||
|
||||
while(pt<ipoptlen){ // for every char in ipopt
|
||||
// read ip option header
|
||||
if(option_type == UNKNOWN) {
|
||||
option_sta = pt;
|
||||
option_type = ipopt[pt++];
|
||||
if(option_type != 0 && option_type != 1) { // should we be interested in length field?
|
||||
if(pt >= ipoptlen) // no more chars
|
||||
{option_type = HEXDUMP;pt--; option_end = 255; continue;} // no length field, hex dump to the end
|
||||
option_len = ipopt[pt++];
|
||||
// end must not be greater than length
|
||||
option_end = MIN(option_sta + option_len, ipoptlen);
|
||||
// end must not be smaller than current position
|
||||
option_end = MAX(option_end, option_sta+2);
|
||||
}
|
||||
}
|
||||
switch(option_type) {
|
||||
case 0: // IPOPT_END
|
||||
STRAPP(" EOL", NULL);
|
||||
option_type = UNKNOWN;
|
||||
break;
|
||||
case 1: // IPOPT_NOP
|
||||
STRAPP(" NOP", NULL);
|
||||
option_type = UNKNOWN;
|
||||
break;
|
||||
/* case 130: // IPOPT_SECURITY
|
||||
option_type=-1;
|
||||
break;*/
|
||||
case 131: // IPOPT_LSRR -> Loose Source and Record Route
|
||||
case 137: // IPOPT_SSRR -> Strict Source and Record Route
|
||||
case 7: // IPOPT_RR -> Record Route
|
||||
if(pt - option_sta == 2) {
|
||||
STRAPP(" %s%s{", (option_type==131)?"LS":(option_type==137)?"SS":"", "RR");
|
||||
// option pointer
|
||||
CHECK(pt);
|
||||
option_pt = ipopt[pt++];
|
||||
if(option_pt%4 != 0 || (option_sta + option_pt-1)>option_end || option_pt<4) //bad or too big pointer
|
||||
STRAPP(" [bad ptr=%02i]", option_pt);
|
||||
}
|
||||
if(pt - option_sta > 2) { // ip's
|
||||
int i, s = (option_pt)%4;
|
||||
// if pointer is mangled, fix it. it's max 3 bytes wrong
|
||||
CHECK(pt+3);
|
||||
for(i=0; i<s; i++)
|
||||
STRAPP("\\x%02x", ipopt[pt++]);
|
||||
option_pt -= i;
|
||||
// okay, now we can start printing ip's
|
||||
CHECK(pt+3);
|
||||
tptr = &ipopt[pt]; pt+=4;
|
||||
if(inet_ntop(AF_INET, (char *) tptr, ipstring, sizeof(ipstring)) == NULL)
|
||||
fatal("Failed to convert target address to presentation format!?! Error: %s", strerror(socket_errno()));
|
||||
STRAPP("%c%s",(pt-3-option_sta)==option_pt?'#':' ', ipstring);
|
||||
if(pt == option_end)
|
||||
STRAPP("%s",(pt-option_sta)==(option_pt-1)?"#":""); // pointer in the end?
|
||||
}else BREAK();
|
||||
break;
|
||||
case 68: // IPOPT_TS -> Internet Timestamp
|
||||
if(pt - option_sta == 2){
|
||||
STRAPP(" TM{");
|
||||
// pointer
|
||||
CHECK(pt);
|
||||
option_pt = ipopt[pt++];
|
||||
// bad or too big pointer
|
||||
if(option_pt%4 != 1 || (option_sta + option_pt-1)>option_end || option_pt<5)
|
||||
STRAPP(" [bad ptr=%02i]", option_pt);
|
||||
// flags + overflow
|
||||
CHECK(pt);
|
||||
option_fl = ipopt[pt++];
|
||||
if((option_fl&0x0C) || (option_fl&0x03)==2)
|
||||
STRAPP(" [bad flags=\\x%01hhx]", option_fl&0x0F);
|
||||
STRAPP("[%i hosts not recorded]", option_fl>>4);
|
||||
option_fl &= 0x03;
|
||||
}
|
||||
if(pt - option_sta > 2) {// ip's
|
||||
int i, s = (option_pt+3)%(option_fl==0?4:8);
|
||||
// if pointer is mangled, fix it. it's max 3 bytes wrong
|
||||
CHECK(pt+(option_fl==0?3:7));
|
||||
for(i=0; i<s; i++)
|
||||
STRAPP("\\x%02x", ipopt[pt++]);
|
||||
option_pt-=i;
|
||||
|
||||
// print pt
|
||||
STRAPP("%c",(pt+1-option_sta)==option_pt?'#':' ');
|
||||
// okay, first grab ip.
|
||||
if(option_fl!=0){
|
||||
CHECK(pt+3);
|
||||
tptr = &ipopt[pt]; pt+=4;
|
||||
if(inet_ntop(AF_INET, (char *) tptr, ipstring, sizeof(ipstring)) == NULL)
|
||||
fatal("Failed to convert target address to presentation format!?! Error: %s", strerror(socket_errno()));
|
||||
STRAPP("%s@", ipstring);
|
||||
}
|
||||
CHECK(pt+3);
|
||||
tint = (u32*)&ipopt[pt]; pt+=4;
|
||||
STRAPP("%u", ntohl(*tint));
|
||||
|
||||
if(pt == option_end)
|
||||
STRAPP("%s",(pt-option_sta)==(option_pt-1)?"#":" ");
|
||||
}else BREAK();
|
||||
break;
|
||||
case 136: // IPOPT_SATID -> (SANET) Stream Identifier
|
||||
if(pt - option_sta == 2){
|
||||
u16 *sh;
|
||||
STRAPP(" SI{",NULL);
|
||||
// length
|
||||
if(option_sta+option_len > ipoptlen || option_len!=4)
|
||||
STRAPP("[bad len %02i]", option_len);
|
||||
|
||||
// stream id
|
||||
CHECK(pt+1);
|
||||
sh = (u16*) &ipopt[pt]; pt+=2;
|
||||
option_pt = ntohs(*sh);
|
||||
STRAPP("id=%i", option_pt);
|
||||
if(pt != option_end)
|
||||
BREAK();
|
||||
}else BREAK();
|
||||
break;
|
||||
case UNKNOWN:
|
||||
default:
|
||||
// we read option_type and option_len, print them.
|
||||
STRAPP(" ??{\\x%02hhx\\x%02hhx", option_type, option_len);
|
||||
// check option_end once more:
|
||||
if(option_len < ipoptlen)
|
||||
option_end = MIN(MAX(option_sta+option_len, option_sta+2),ipoptlen);
|
||||
else
|
||||
option_end = 255;
|
||||
option_type = HEXDUMP;
|
||||
break;
|
||||
case HEXDUMP:
|
||||
assert(pt<=option_end);
|
||||
if(pt == option_end){
|
||||
STRAPP("}",NULL);
|
||||
option_type=-1;
|
||||
break;
|
||||
}
|
||||
STRAPP("\\x%02hhx", ipopt[pt++]);
|
||||
break;
|
||||
}
|
||||
if(pt == option_end && option_type != UNKNOWN) {
|
||||
STRAPP("}",NULL);
|
||||
option_type = UNKNOWN;
|
||||
}
|
||||
} // while
|
||||
if(option_type != UNKNOWN)
|
||||
STRAPP("}");
|
||||
|
||||
return(STRAPP("",NULL));
|
||||
}
|
||||
#undef CHECK
|
||||
#undef BREAK
|
||||
#undef UNKNOWN
|
||||
#undef HEXDUMP
|
||||
|
||||
|
||||
/* mmap() an entire file into the address space. Returns a pointer
|
||||
|
||||
21
utils.h
21
utils.h
@@ -175,12 +175,6 @@ int wildtest(char *wild, char *test);
|
||||
|
||||
void nmap_hexdump(unsigned char *cp, unsigned int length);
|
||||
|
||||
/* Compare a canonical option name (e.g. "max-scan-delay") with a
|
||||
user-generated option such as "max_scan_delay" and returns 0 if the
|
||||
two values are considered equivalant (for example, - and _ are
|
||||
considered to be the same), nonzero otherwise. */
|
||||
int optcmp(const char *canonical, const char *instance);
|
||||
|
||||
/* Scramble the contents of an array*/
|
||||
void genfry(unsigned char *arr, int elem_sz, int num_elem);
|
||||
void shortfry(unsigned short *arr, int num_elem);
|
||||
@@ -204,23 +198,8 @@ void arg_parse_free(char **argv);
|
||||
str is returned. */
|
||||
char *cstring_unescape(char *str, unsigned int *len);
|
||||
|
||||
/* This function converts zero-terminated 'txt' string to binary 'data'.
|
||||
It is used to parse user input for ip options. Some examples of possible input
|
||||
strings and results:
|
||||
'\x01*2\xA2' -> [0x01,0x01,0xA2] // with 'x' number is parsed in hex
|
||||
'\01\01\255' -> [0x01,0x01,0xFF] // without 'x' its in decimal
|
||||
'\x01\x00*2' -> [0x01,0x00,0x00] // '*' is copying char
|
||||
'R' -> Record Route with 9 slots
|
||||
'S 192.168.0.1 172.16.0.1' -> Strict Route with 2 slots
|
||||
'L 192.168.0.1 172.16.0.1' -> Loose Route with 2 slots
|
||||
'T' -> Record Timestamp with 9 slots
|
||||
'U' -> Record Timestamp and Ip Address with 4 slots
|
||||
*/
|
||||
int parse_ip_options(char *txt, u8 *data, int datalen, int* firsthopoff, int* lasthopoff);
|
||||
|
||||
void bintohexstr(char *buf, int buflen, char *src, int srclen);
|
||||
|
||||
char* print_ip_options(u8* ipopt, int ipoptlen);
|
||||
|
||||
#ifndef HAVE_STRERROR
|
||||
char *strerror(int errnum);
|
||||
|
||||
Reference in New Issue
Block a user