|
马上注册,结交更多好友,享用更多功能^_^
您需要 登录 才可以下载或查看,没有账号?立即注册
x
如何改成可以搜索多IP地址,例如扫描192.168.0.0到192.168.10.10之间的端口,怎么加循环
PortScan.rar
(84.55 KB, 下载次数: 0)
program Portscan;
(*
1.10d - Okay, upon request the whole file moves out of the EXE again to be
able to customize the port descriptions ;)
1.10c - now the programmer can optionally include the short names for the
ports as string table resource using the PORTNAMES compiler switch.
(A Perl script in the \SOURCE directory can be used to extract the
names. Just put a file called "port-numbers.txt" into the directory
and then execute the .CMD file to extract the names - get the file
from: http://www.iana.org/assignments/port-numbers)
1.10b - can be minimized to tray now by double clicking the caption
1.10a - small enhancements
1.10 - sports new scheduling scheme. Thanks to Hagen for pointing it out to me.
1.00 - initial release
The program can definitely be compiled with Delphi 3 through 5!
The program will start and maybe run on Windows 9x. But when reaching a limit
of 32K items in the listbox it will hang or whatever. I don't know. I just
want you to notice it. It's a limitation of Windows 9x I am not willing to
work around, since Windows 9x hopefully will disappear from PCs soon.
*)
uses
Windows,
Messages,
ShellApi,
CommCtrl,
CommDlg,
WinSock;
{R MAIN.RES}
{$INCLUDE .\Include\FormatString.pas}
{$INCLUDE .\Include\GetFont.pas}
const
IDD_DIALOG1 = 101;
IDI_ICON1 = 102;
IDI_ICON2 = 103;
IDC_EDITIP = 1001;
IDC_EDITPORT_FROM = 1005;
IDC_EDITPORT_TO = 1008;
IDC_LIST1 = 1009;
IDC_BUTTON_OPENPORTS = 1010;
IDC_BUTTON_SAVE = 1011;
IDC_CHECK1 = 1012;
IDC_EDIT_NUMTHREADS = 1014;
IDC_SPIN_NUMTHREADS = 1015;
IDC_STATIC_NUMTHREADS = 1016;
IDC_STATIC_NUMITEMS = 1017;
// Some application defined window messages
WM_ADDIP_TCPCONNPORT = WM_APP + 123; // open TCP port
WM_ADDIP_TCPPORT = WM_APP + 124; // closed TCP port
WM_ADDIP_UDPCONNPORT = WM_APP + 125; // open UDP port
WM_ADDIP_UDPPORT = WM_APP + 126; // closed UDP port
WM_SETCOUNTER = WM_APP + 200; // sets the thread counter STATIC
WM_SHELLNOTIFY = WM_APP + 201;
SC_TRAY = WM_APP + 202;
maxports =FFFF;
cancelports = 1 + maxports * 2;
allfiles_filterstring = 'Text files'#0'*.txt'#0'All files'#0'*.*'#0#0;
portfile = 'ports.conf';
type
PIP = ^TIP;
TIP = record
IP,
StartPort,
EndPort: DWORD;
ThreadCounter: Integer;
end;
PPortArray = ^TPortArray;
TPortArray = array[0..FFFF]ofstring;varportdesc:PPortArray;note:TNotifyIconData;numthreads:DWORD=100; // FIXED!!!
wsa: TWSAData;
cs: TRTLCriticalSection;
hDlg: HWND = 0;
ct: Boolean = False; // Icon "counter"
icons: array[0..1] of HICON; // Two alternating icons
IP: TIP;
gPortCounter: DWORD;
MsgTaskbarcreated: DWORD = 0;
function EnumChildSetFonts(hwnd: HWND; lParam: LPARAM): BOOL; stdcall;
(*
Iterates through all dialog child controls and sets fonts and text length limit.
*)
begin
result := True;
// For any of the controls here, let's set the font :)
case GetDlgCtrlID(hwnd) of
IDC_LIST1,
IDC_EDITIP,
IDC_EDITPORT_FROM,
IDC_EDITPORT_TO:
SendMessage(hwnd, WM_SETFONT, lParam, ord(TRUE));
end;
case GetDlgCtrlID(hwnd) of
IDC_LIST1,
IDC_EDITIP:
SendMessage(hwnd, EM_SETLIMITTEXT, 20, 0);
IDC_EDITPORT_FROM,
IDC_EDITPORT_TO:
SendMessage(hwnd, EM_SETLIMITTEXT, 5, 0);
end;
end;
function GetIP(hwnd: HWND): DWORD;
// Get's an IP address in host byte order from the text of the IDC_EDITIP control
var
IP: DWORD;
pc: PChar;
begin
result := 0;
IP := GetWindowTextLength(GetDlgItem(hwnd, IDC_EDITIP)) + 2;
GetMem(pc, IP);
if Assigned(pc) then
try
ZeroMemory(pc, IP);
GetWindowText(GetDlgItem(hwnd, IDC_EDITIP), pc, IP);
result := ntohl(inet_addr(pc));
finally
FreeMem(pc);
end;
end;
function ScanTCPPort(IP, Port: DWORD): Boolean;
// Scans a specific TCP port and on a specific IP
var
OPTON: DWORD;
TCPsock: TSocket;
A: TSockAddrIn;
begin
result := False;
// Create/open a socket (stream, not datagram)
TCPsock := socket(AF_INET, SOCK_STREAM, 0);
if TCPsock <> INVALID_SOCKET then
try
// Set socket options
OPTON := 0;
setsockopt(TCPsock, SOL_SOCKET, SO_KEEPALIVE, @OPTON, sizeof(OPTON));
OPTON := 1;
setsockopt(TCPsock, SOL_SOCKET, SO_DONTLINGER, @OPTON, sizeof(OPTON));
// Only for compatibility with WinSock 1.1! It's default on newer versions.
setsockopt(TCPsock, IPPROTO_TCP, TCP_NODELAY, @OPTON, sizeof(OPTON));
// Reset and init address structure
ZeroMemory(@A, sizeof(A));
A.sin_family := AF_INET;
A.sin_addr.S_addr := ntohl(IP);
A.sin_port := htons(Port);
// Try to connect and return result
result := connect(TCPsock, A, sizeof(A)) = 0;
finally
// Close the socket
closesocket(TCPsock);
end;
end;
function BeepThread(unused: DWORD): DWORD; stdcall;
// Does a long beep
begin
result := 0;
Windows.Beep(200, 100);
Windows.Beep(400, 100);
Windows.Beep(600, 100);
Windows.Beep(800, 100);
Windows.Beep(1000, 100);
Windows.Beep(1200, 100);
Windows.Beep(1400, 100);
Windows.Beep(1600, 100);
Windows.Beep(1800, 100);
Windows.Beep(2000, 100);
end;
function ScanThread(unused: DWORD): DWORD; stdcall;
// Does the job for ONE port each time. It loops in a loop that increases a global
// port counter. The next unscanned port is scanned by the next free thread
var
lPort: DWORD;
begin
result := 0;
// Thread counter
InterLockedIncrement(IP.ThreadCounter);
// Post updated number of threads
PostMessage(hDlg, WM_SETCOUNTER, IP.ThreadCounter, 0);
// Set lower thread priority
SetThreadPriority(GetCurrentThread, THREAD_PRIORITY_IDLE);
// Loop while the current port number is smaller or equal the end port number
while True do
begin
asm
// Atomic operation
MOV EAX, 1
XADD gPortCounter, EAX
MOV lPort, EAX
end;
// Exit condition
if lPort > IP.EndPort then
Break;
// Scan ports ...
if ScanTCPPort(IP.IP, lPort) then
PostMessage(hDlg, WM_ADDIP_TCPCONNPORT, IP.IP, lPort)
else
PostMessage(hDlg, WM_ADDIP_TCPPORT, IP.IP, lPort);
end;
// Atomic operation ... decreases thread counter
InterLockedDecrement(IP.ThreadCounter);
// Post updated number of threads
PostMessage(hDlg, WM_SETCOUNTER, IP.ThreadCounter, 0);
end;
procedure TryPortscan(hwnd: HWND);
// Retrieves all necessary values from the dialog and starts scanning.
var
i, TID: DWORD;
trans: BOOL;
begin
IP.IP := GetIP(hwnd);
if (IP.IP <> INADDR_NONE) then
begin
SetDlgItemInt(hwnd, IDC_STATIC_NUMITEMS, 0, False);
i := SendDlgItemMessage(hwnd, IDC_SPIN_NUMTHREADS, UDM_GETPOS, 0, 0);
IP.StartPort := GetDlgItemInt(hwnd, IDC_EDITPORT_FROM, trans, False);
IP.EndPort := GetDlgItemInt(hwnd, IDC_EDITPORT_TO, trans, False);
// If the ports have wrong order (max < min) then change them
if IP.StartPort > IP.EndPort then
begin
TID := IP.StartPort;
IP.StartPort := IP.EndPort;
IP.EndPort := TID;
if IP.EndPort > maxports then
SetDlgItemInt(hwnd, IDC_EDITPORT_FROM, IP.StartPort, False);
SetDlgItemInt(hwnd, IDC_EDITPORT_TO, IP.EndPort, False);
end;
// Prevent thread switching
if i > (IP.EndPort - IP.StartPort) then
i := (IP.EndPort - IP.StartPort) + 1;
SendDlgItemMessage(hwnd, IDC_LIST1, LB_RESETCONTENT, 0, 0);
gPortCounter := IP.StartPort;
IP.ThreadCounter := 0;
// Set lower thread priority
SetThreadPriority(GetCurrentThread, THREAD_PRIORITY_BELOW_NORMAL);
// Start a whole lott of threads ...
for i := 0 to i - 1 do
// Parameter is the current counter value
CreateThread(nil, FFFF,@ScanThread,nil,0,TID);endelseMessageBox(hwnd,′PleasegiveavalidIPaddressandnumberofthreads!′,nil,0);end;procedureEnableWindows(hwnd:HWND;b:BOOL);//EnablesordisablescontrolsthatmightdisturbwhilescanningbeginEnableWindow(GetDlgItem(hwnd,IDOK),b);EnableWindow(GetDlgItem(hwnd,IDCEDITNUMTHREADS),b);EnableWindow(GetDlgItem(hwnd,IDCEDITIP),b);EnableWindow(GetDlgItem(hwnd,IDCEDITPORTFROM),b);EnableWindow(GetDlgItem(hwnd,IDCEDITPORTTO),b);EnableWindow(GetDlgItem(hwnd,IDCSPINNUMTHREADS),b);//EnableWindow(GetDlgItem(hwnd,IDCBUTTONSAVE),b);end;procedureSetIcon(hwnd:HWND;handle:HICON);//Setsthemainwindow′siconbeginSendMessage(hwnd,WMSETICON,ICONBIG,handle);SendMessage(hwnd,WMSETICON,ICONSMALL,handle);end;functionGetFileName(hwnd:HWND;default:string;varreturnname:string):Boolean;//Getsthenameforthefiletosavethereportvarofn:TOpenFilename;ofnbuffer:array[0..MAXPATH]ofChar;beginZeroMemory(@ofnbuffer,sizeof(ofnbuffer));ZeroMemory(@ofn,sizeof(ofn));lstrcpyn(@ofnbuffer[0],@default[1],sizeof(ofnbuffer));ofn.lStructSize:=sizeof(ofn);ofn.lpstrFile:=@ofnbuffer;ofn.hWndOwner:=hwnd;ofn.hInstance:=hInstance;ofn.lpstrFilter:=@allfilesfilterstring[1];ofn.nMaxFile:=sizeof(ofnbuffer);ofn.Flags:=OFNPATHMUSTEXISTorOFNLONGNAMESorOFNEXPLORERorOFNHIDEREADONLY;result:=GetSaveFileName(ofn);ifresultthenSetString(returnname,PChar(@ofnbuffer),lstrlen(@ofnbuffer[0]));end;functionGetLBItem(hwnd:HWND;idx:Integer):string;//Getsonelistboxiteminastring(byindex)vari:Integer;pc:PChar;beginresult:=″;i:=SendMessage(hwnd,LBGETTEXTLEN,idx,0)+2;GetMem(pc,i);ifAssigned(pc)thentryZeroMemory(pc,i);SendMessage(hwnd,LBGETTEXT,idx,LPARAM(pc));SetString(result,pc,lstrlen(pc));finallyFreeMem(pc);end;end;procedureCreateTrayIcon(hwnd:HWND);//Createsthetrayiconbeginnote.cbSize:=SizeOf(TNotifyIconData);note.wnd:=hwnd;note.uID:=SCTRAY;note.uFlags:=NIFICONorNIFMESSAGEorNIFTIP;note.uCallbackMessage:=WMSHELLNOTIFY;note.hIcon:=icons[0];lstrcpy(note.szTip,′FastScan(doubleclickrestores)′);ShowWindow(hWnd,SWHIDE);ShellNotifyIcon(NIMADD,@note);end;procedureDestroyTrayIcon;//DestroysthetrayiconbeginShellNotifyIcon(NIMDELETE,@note);end;procedureModifyTrayIconText;//ModifiesthetrayiconbeginShellNotifyIcon(NIMMODIFY,@note);end;procedureBlinkTrayIcon;//Actuallyblinksthetrayiconbeginnote.hIcon:=icons[ord(ct)];ModifyTrayIconText;end;procedureTimerFunc(hwnd:HWND;uMsg:UINT;idEvent:UINT;dwTime:DWORD);stdcall;//Makesthetrayiconblinkwhenfinishedbeginct:=notct;BlinkTrayIcon;end;functionGetTCPPortDescription(IP:DWORD;Port:Word;ports:PPortArray):string;beginresult:=Format(′Byte(IPshr24),Byte(IPshr16),Byte(IPshr8),Byte(IP),Port]);ifAssigned(ports)thenifports[Port]<>″thenresult:=Format(′end;functionDlgFunc(hwnd:HWND;umsg:UINT;wparam:WPARAM;lparam:LPARAM):BOOL;stdcall;vars:string;hFile:THandle;written:DWORD;i:Integer;se:servent;pse:PServEntabsolutese;x,y:integer;beginResult:=True;caseumsgofWMINITDIALOG:beginhDlg:=hwnd;SetIcon(hwnd,icons[0]);//SetfixedfontforalleditfieldsEnumChildWindows(hwnd,@EnumChildSetFonts,GetFont(hwnd,8,FWNORMAL,True));//SetinitialIPaddressbeginforx:=52to54dofory:=77to79doSetDlgItemText(hwnd,IDCEDITIP,′172.26.x.y′);end;SendDlgItemMessage(hwnd,IDCSPINNUMTHREADS,UDMSETRANGE,0,MAKELONG(numthreads,1));SendDlgItemMessage(hwnd,IDCSPINNUMTHREADS,UDMSETPOS,0,MAKELONG(numthreads,0));//SetinitialportrangeSetDlgItemInt(hwnd,IDCEDITPORTFROM,0,False);SetDlgItemInt(hwnd,IDCEDITPORTTO,maxports,False);SetDlgItemInt(hwnd,IDCSTATICNUMTHREADS,0,False);SetDlgItemInt(hwnd,IDCSTATICNUMITEMS,0,False);//RegisterthemessageMsgTaskbarcreated:=RegisterWindowMessage(′TaskbarCreated′);end;WMTIMER:casewParamofIDDDIALOG1:beginct:=notct;SetIcon(hwnd,icons[ord(ct)]);end;end;WMSETCOUNTER:beginSetDlgItemInt(hwnd,IDCSTATICNUMTHREADS,wParam,False);ifwParam>0thenEnableWindows(hwnd,False)elsebeginEnableWindows(hwnd,True);//RemovetimerKillTimer(hwnd,IDDDIALOG1);//ReseticonSetIcon(hwnd,icons[0]);//SetlowerthreadprioritySetThreadPriority(GetCurrentThread,THREADPRIORITYNORMAL);ifnotIsWindowVisible(hwnd)thenbegin//MakethetrayiconblinkSetTimer(hwnd,SCTRAY,350,@TimerFunc);//Makealongbeeeeep;)CreateThread(nil,FFFF, @BeepThread, nil, 0, PDWORD(nil)^);
end;
end;
end;
WM_ADDIP_TCPCONNPORT:
begin
// s := Format('%3.3d.%3.3d.%3.3d.%3.3d:%5.5d - ', [
s := GetTCPPortDescription(wParam, lParam, portdesc);
SendDlgItemMessage(hwnd, IDC_LIST1, LB_ADDSTRING, 0, Integer(@s[1]));
if IsDlgButtonChecked(hwnd, IDC_CHECK1) = BST_CHECKED then
SendDlgItemMessage(hwnd, IDC_LIST1, LB_SETTOPINDEX,
SendDlgItemMessage(hwnd, IDC_LIST1, LB_GETCOUNT, 0, 0) - 1, 0);
SetDlgItemInt(hwnd, IDC_STATIC_NUMITEMS, gPortCounter, False);
end;
WM_ADDIP_TCPPORT:
SetDlgItemInt(hwnd, IDC_STATIC_NUMITEMS, gPortCounter, False);
WM_CTLCOLOREDIT:
case GetDlgCtrlID(lParam) of
IDC_EDITIP:
begin
SetTextColor(wParam, RGB(00,80, 00));SetBkColor(wParam,GetSysColor(COLORINFOBK));result:=BOOL(GetSysColorBrush(COLORINFOBK));end;IDCEDITPORTFROM,IDCEDITPORTTO:beginSetTextColor(wParam,RGB(00, 00,80));
SetBkColor(wParam, GetSysColor(COLOR_INFOBK));
result := BOOL(GetSysColorBrush(COLOR_INFOBK));
end;
IDC_EDIT_NUMTHREADS:
begin
SetTextColor(wParam, RGB(80,00, 00));SetBkColor(wParam,GetSysColor(COLORINFOBK));result:=BOOL(GetSysColorBrush(COLORINFOBK));end;elseresult:=False;end;WMCTLCOLORLISTBOX:caseGetDlgCtrlID(lParam)ofIDCLIST1:beginSetTextColor(wParam,RGB(00, 00,80));
SetBkColor(wParam, GetSysColor(COLOR_BTNFACE));
result := BOOL(GetSysColorBrush(COLOR_BTNFACE));
end;
else
result := False;
end;
WM_CLOSE:
EndDialog(hwnd, 0);
WM_COMMAND:
if HiWord(WParam) = BN_CLICKED then
case LOWORD(wParam) of
IDOK:
begin
SetTimer(hwnd, IDD_DIALOG1, 400, nil);
TryPortScan(hwnd);
end;
IDCANCEL:
SendMessage(hwnd, WM_CLOSE, 0, 0);
IDC_BUTTON_OPENPORTS:
// Open the IANA website with port number assignments
ShellExecute(hwnd,
'open',
'http://www.iana.org/assignments/port-numbers',
nil,
nil,
SW_SHOW);
IDC_BUTTON_SAVE:
begin
i := SendDlgItemMessage(hwnd, IDC_LIST1, LB_GETCOUNT, 0, 0);
if i > 0 then
if GetFileName(hwnd, 'ScanReport.txt', s) then
begin
hFile := CreateFile(@s[1], GENERIC_WRITE, 0, nil, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0);
if ((hFile <> INVALID_HANDLE_VALUE) and (i <> LB_ERR)) then
try
for i := 0 to i do
begin
s := GetLBItem(GetDlgItem(hwnd, IDC_LIST1), i) + #13#10;
WriteFile(hFile, PChar(@s[1])^, length(s), written, nil);
end;
finally
CloseHandle(hFile);
end
else
MessageBox(hwnd, 'Could not create file.', nil, 0);
end;
end;
end;
(******************************************************************************
Handle: minimize to tray
******************************************************************************)
WM_SIZE:
if wParam = SIZE_MINIMIZED then
CreateTrayIcon(hwnd);
WM_SHELLNOTIFY:
case wParam of
SC_TRAY:
case lParam of
WM_LBUTTONDBLCLK:
begin
DestroyTrayIcon;
ShowWindow(hWnd, SW_RESTORE);
SetForeGroundWindow(hwnd);
end;
end;
end;
WM_NCLBUTTONDBLCLK:
case wParam = HTCAPTION of
TRUE: Showwindow(hwnd, SW_MINIMIZE);
end;
else
if ((MsgTaskbarcreated <> 0) and (uMsg = MsgTaskbarcreated)) then
begin
DestroyTrayIcon;
CreateTrayIcon(hwnd);
end
else
Result := False;
end;
end;
function InitPortArray(fname: string): PPortArray;
var
f: Textfile;
s: string;
Port: Word;
Code: Integer;
begin
result := nil;
AssignFile(f, fname);
{I-} Reset(f); {$I+} if IOResult = 0 then try GetMem(result, sizeof(result^)); if Assigned(result) then begin ZeroMemory(result, sizeof(result^)); while not EOF(f) do begin Readln(f, s); if s[1] = '#' then continue; val(copy(s, 1, 5), Port, Code); if Code = 0 then result^[Port] := copy(s, 7, length(s)); end; end; finally CloseFile(f); end; end; begin // Warning on Win9x if GetVersion and80000000 <> 0 then
begin
MessageBox(0, 'Note: There are certain limitations on Windows 9x/Me which might' +
' cause the program to hang or not work at all! Be warned! You use it at your own risk.', 'Information', MB_ICONWARNING);
numthreads := $F;
end;
// Create critical section
InitializeCriticalSection(cs);
// Init comctl library
InitCommonControls;
try
// Init WinSock (v 1.1)
if WSAStartup(MAKEWORD(1, 1), wsa) = 0 then
try
icons[0] := LoadIcon(hInstance, MAKEINTRESOURCE(IDI_ICON1));
icons[1] := LoadIcon(hInstance, MAKEINTRESOURCE(IDI_ICON2));
// Init port list
portdesc := InitPortArray(portfile);
// Start main window
DialogBoxParam(hInstance, MAKEINTRESOURCE(IDD_DIALOG1), 0, @dlgfunc, 0);
finally
// Finit WinSock
WSACleanup;
end
else
MessageBox(0, 'Found no appropriate WinSock support. Version 1.1 needed.', nil, 0);
finally
// Remove critical section
DeleteCriticalSection(cs);
// Free the port list
if Assigned(portdesc) then
FreeMem(portdesc);
end;
end.
|
|