File:
1.15.3a/server/bin/discover.php (
View as Code)
1: 2: /* -------------------------------------------------------------
3: This file is part of FreeNATS
4:
5: FreeNATS is (C) Copyright 2008 PurplePixie Systems
6:
7: FreeNATS is free software: you can redistribute it and/or modify
8: it under the terms of the GNU General Public License as published by
9: the Free Software Foundation, either version 3 of the License, or
10: (at your option) any later version.
11:
12: FreeNATS is distributed in the hope that it will be useful,
13: but WITHOUT ANY WARRANTY; without even the implied warranty of
14: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15: GNU General Public License for more details.
16:
17: You should have received a copy of the GNU General Public License
18: along with FreeNATS. If not, see www.gnu.org/licenses
19:
20: For more information see www.purplepixie.org/freenats
21: -------------------------------------------------------------- */
22:
23: $ranges=array();
24: $actranges=array();
25: $rangecount=0;
26: $recorded=0;
27: $webprobe=false;
28: $live=false;
29: $debug=false;
30: $outfile="discover.xml";
31: $output="";
32:
33:
34:
35: function AddNode($nodeid,$hostname,$description="")
36: {
37: global $output;
38: $output.="\n";
39: $output.=" ".$nodeid."\n";
40: $output.=" ".$hostname."\n";
41: $output.=" ".$description."\n";
42: $output.="\n\n";
43: }
44:
45: function AddLocaltest($nodeid,$testtype,$param)
46: {
47: global $output,$recorded;
48: $output.="\n";
49: $output.=" ".$nodeid."\n";
50: $output.=" ".$testtype."\n";
51: $output.=" ".$param."\n";
52: $output.="\n\n";
53: }
54:
55: function DiscovericmpChecksum($data)
56: {
57: if (strlen($data)%2)
58: $data .= "\x00";
59:
60: $bit = unpack('n*', $data);
61: $sum = array_sum($bit);
62:
63: while ($sum >> 16)
64: $sum = ($sum >> 16) + ($sum & 0xffff);
65:
66: return pack('n*', ~$sum);
67: }
68:
69: function DiscoverPing($host)
70: {
71: // Make Package
72: $type= "\x08";
73: $code= "\x00";
74: $checksum= "\x00\x00";
75: $identifier = "\x00\x00";
76: $seqNumber = "\x00\x00";
77: $data= "FreeNATS";
78: $package = $type.$code.$checksum.$identifier.$seqNumber.$data;
79: $checksum = DiscovericmpChecksum($package); // Calculate the checksum
80: $package = $type.$code.$checksum.$identifier.$seqNumber.$data;
81:
82: // Return s or ms(s*1000)
83: $returnsecs=true;
84:
85:
86: // Timeout Values
87: $timeout=10;
88:
89: // Create Socket
90: $socket = @socket_create(AF_INET, SOCK_RAW, 1);
91: //or die(socket_strerror(socket_last_error()));
92: if (!$socket) return -1;
93:
94: // Set Non-Blocking
95: @socket_set_nonblock($socket);
96:
97: // Connect Socket
98: $sconn=@socket_connect($socket, $host, null);
99: if (!$sconn) return -1;
100:
101: // Send Data
102: @socket_send($socket, $package, strLen($package), 0);
103:
104: $startTime=microtime(true);
105:
106:
107: // Read Data
108: $keepon=true;
109:
110: while( (!(@socket_read($socket, 255))) && $keepon)
111: { // basically just kill time
112: // consider putting some sort of sleepy thing here to lower load but would f* with figures!
113:
114: if ( (microtime(true) - $startTime) > $timeout )
115: $keepon=false;
116: }
117:
118: if ($keepon) // didn't time out - read data
119: {
120:
121: @socket_close($socket);
122:
123: return 1;
124:
125: }
126:
127: // Socket timed out
128: @socket_close($socket);
129: return 0;
130: }
131:
132:
133: function ddt($txt) // discovery debug text
134: {
135: global $debug;
136: if ($debug) echo $txt."\n";
137: }
138:
139: if ($argc<2)
140: {
141: echo "FreeNATS Discovery Tool\n";
142: echo "Usage: php discover.php [ ...] [options]\n\n";
143: echo "Goes through IPs or ranges and discovers nodes, outputting an XML file for\n";
144: echo "import to FreeNATS with the bulk importer.\n\n";
145: echo "IPs or Ranges are Specified as:";
146: echo " 10.0.10.1 - single IP address\n";
147: echo " 10.0.10.1-10.0.10.254 - range of IP addresses\n";
148: echo " 10.0.10.0/24 - network with numeric netmask\n";
149: echo " 10.0.10.0/255.255.255.0 - network with IPv4 netmask\n\n";
150: echo "Options are:";
151: echo " --file - output XML file (defaults to discover.xml)\n";
152: echo " --webprobe - do a web probe and add the test if found\n";
153: echo " --recorded - set the record data flag for any discovered tests by default\n\n";
154: echo "See www.purplepixie.org/freenats for more information.\n\n";
155: exit();
156: }
157:
158: for ($ac=1; $ac<$argc; $ac++)
159: {
160: $arg=$argv[$ac];
161: if ($arg=="--live") $live=true;
162: else if ($arg=="--debug") $debug=true;
163: else if ($arg=="--file") $outfile=$argv[++$ac];
164: else if ($arg=="--webprobe") $webprobe=true;
165: else if ($arg=="--recorded") $recorded=1;
166: else
167: {
168: $ranges[$rangecount]=$arg;
169: $actranges[$rangecount]['start']=0;
170: $actranges[$rangecount]['finish']=0;
171:
172: if (strpos($arg,"-")!==false) // range
173: {
174: $pos=strpos($arg,"-");
175: $from=substr($arg,0,$pos);
176: $to=substr($arg,$pos+1);
177: $actranges[$rangecount]['start']=ip2long($from);
178: $actranges[$rangecount]['finish']=ip2long($to);
179: }
180: else if (strpos($arg,"/")!==false) // mask delimited
181: {
182: $pos=strpos($arg,"/");
183: $ip=substr($arg,0,$pos);
184: $mask=substr($arg,$pos+1);
185: if (is_numeric($mask)) // numeric mask
186: {
187: ddt("Numeric Netmask ".$mask);
188: $netmask=0;
189: for ($a=0; $a<$mask; $a++)
190: {
191: $val=pow(2,(32-$a-1));
192: ddt("Numeric Netmask: Pos ".$a." Adding ".$val);
193: $netmask+=$val;
194: }
195: ddt("Numeric Netmask ".long2ip($netmask)." ".$netmask);
196: $netmask=ip2long(long2ip($netmask)); // weirdness avoidance!!
197: //
198: }
199: else $netmask=ip2long($mask);
200: ddt("Netmask ".$netmask);
201: $ipaddr=ip2long($ip);
202: ddt("IP ".$ipaddr." (".$ip.")");
203: $network=($ipaddr & $netmask);
204: $firsthost=$network+1;
205:
206: $broadcast=($network | (~$netmask));
207: $lasthost=$broadcast-1;
208:
209: $actranges[$rangecount]['start']=$firsthost;
210:
211: $actranges[$rangecount]['finish']=$lasthost;
212:
213: }
214: else
215: { // single host
216: $actranges[$rangecount]['start']=ip2long($arg);
217: $actranges[$rangecount]['finish']=ip2long($arg);
218: }
219:
220: $rangecount++;
221: }
222: }
223:
224:
225: $output.="\n";
226: $output.="\n\n";
227:
228: $output.="\n";
229: $output.=" 1\n";
230: $output.=" 0\n";
231: $output.="\n\n";
232:
233: $output.="\n";
234: $output.=" 1\n";
235: $output.=" ".$recorded."\n";
236: $output.="\n\n";
237:
238:
239:
240: echo "FreeNATS Discover Started\n";
241: echo " Live: ";
242: if ($live) echo "Yes";
243: else echo "No";
244: echo " Debug: ";
245: if ($debug) echo "Yes";
246: else echo "No";
247: echo "\n File: ".$outfile;
248: echo "\n\n";
249: echo "Ranges: ".$rangecount."\n";
250: if ($rangecount<=0)
251: {
252: echo "\nNo ranges or IP addresses specified\n";
253: }
254:
255: for($a=0; $a<$rangecount; $a++)
256: {
257: echo " ".$ranges[$a]." ".$actranges[$a]['start']."-".$actranges[$a]['finish']." ".long2ip($actranges[$a]['start'])."-".long2ip($actranges[$a]['finish'])."\n";
258: }
259: echo "\n";
260:
261: for($a=0; $a<$rangecount; $a++)
262: {
263: $start=$actranges[$a]['start'];
264: $finish=$actranges[$a]['finish'];
265: echo "+ ".long2ip($start)." - ".long2ip($finish)."\n";
266: for ($ip=$start; $ip<=$finish; $ip++)
267: {
268: ddt("- ".long2ip($ip)." (".$ip.")");
269: $res=DiscoverPing(long2ip($ip));
270: if ($res<0)
271: {
272: echo "Fatal Error: Could Not Open ICMP Connection (Ping Send Failed)\n\n";
273: exit();
274: }
275: else if ($res==0)
276: {
277: ddt("- No Reply for Ping");
278: }
279: else
280: {
281: echo "- Ping Returned - Host Active\n";
282: $hostname=gethostbyaddr(long2ip($ip));
283: echo "- Name: ".$hostname."\n";
284: $ipaddr=long2ip($ip);
285: if ($hostname==$ipaddr)
286: {
287: $nodeid=$ipaddr;
288: }
289: else
290: {
291: $exp=explode(".",$hostname);
292: $nodeid=$exp[0];
293: }
294: echo "- NodeID: ".$nodeid."\n";
295: AddNode($nodeid,$ipaddr,$hostname);
296: if ($webprobe)
297: {
298: $url="http://".$ipaddr."/";
299: echo "- Web Probe: ".$url."... ";
300: $fp=@fopen($url,"r");
301: if ($fp<=0) echo "Failed\n";
302: else
303: {
304: echo "Succeeded\n";
305: fclose($fp);
306: AddLocaltest($nodeid,"webtime",$url);
307: echo "- Adding Web Test ".$url."\n";
308: }
309: }
310: }
311: echo "\n";
312: }
313: echo "\n";
314: }
315:
316: $output.="\n";
317:
318: echo "\nFinish... Writing File... ";
319: $fp=fopen($outfile,"w");
320: fputs($fp,$output,strlen($output));
321: fclose($fp);
322: echo "\n";
323:
324: ?>