tools/adflib: build only host variant which is used by Sam440 target
[AROS.git] / workbench / network / stacks / AROSTCP / dhcp / contrib / ms2isc / ms2isc.pl
blobda3e10f79b2ecfb1a773d6695148e348420f9692
1 #set ts=3
3 # ms2isc.pl
4 # MS NT4 DHCP to ISC DHCP Configuration Migration Tool
6 # Author: Shu-Min Chang
8 # Copyright(c) 2003 Intel Corporation. All rights reserved
10 # Redistribution and use in source and binary forms, with or without
11 # modification, are permitted provided that the following conditions are met:
13 # 1. Redistributions of source code must retain the above copyright notice,
14 # this list of conditions and the following disclaimer.
15 # 2. Redistributions in binary form must reproduce the above copyright notice
16 # this list of conditions and the following disclaimer in the documentation
17 # and/or other materials provided with the distribution
18 # 3. Neither the name of Intel Corporation nor the names of its contributors
19 # may be used to endorse or promote products derived from this software
20 # without specific prior written permission.
22 # THIS SOFTWARE IS PROVIDED BY THE INTEL CORPORATION AND CONTRIBUTORS "AS IS"
23 # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 # ARE DISCLAIMED. IN NO EVENT SHALL THE INTEL CORPORATION OR CONTRIBUTORS BE
26 # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL EXEMPLARY, OR
27 # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO PROCUREMENT OF SUBSTITUE
28 # GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
29 # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
30 # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31 # OF THE USE OF THIS SOFTWARE, EVEN IF ADVICED OF THE POSSIBILITY OF SUCH
32 # DAMAGE.
34 use strict;
35 use Socket;
36 use Getopt::Std;
37 use Filehandle;
38 use Registry; # Custom Perl Module to make Registry access easier.
40 my $usage = << 'ENDOFHELP';
42 Purpose: A Perl Script converting MS NT4 DHCP configuration to ISC DHCP3
43 configuration file by reading NT4's registry.
45 Requires: Registry.pm and ActiveState 5.6.0
47 Usage: $ARGV -s <Srv> -o <Out> [-p <Pri> [-k <key>]] [-f <Fo>]
49 <Srv> Server IP or name for NT4 DHCP server to fetch the configuration from.
50 <Out> Output filename for the configuration file.
51 <Pri> Primary DNS server name for sending the dynamic DNS update to.
52 <Key> Key name for use in updating the dynamic DNS zone.
53 <Fo> Failover peer name shared with the DHCP partner.
55 Essentially the <Srv> needs to be an NT4 (3.x should work but not tested) which
56 you should have registry read access to. You must run this script from a
57 Windows machine because of the requirement to access the registry.
59 The <Pri> is optional parameter for desginating the dynamic DNS update if
60 missing then the "zone" section of the declaration will be skipped. The <Key>
61 is needed if you've configured your DNS zone with a key, in addition, you'll
62 need to define that key in this DHCP configuration file elsewhere manually,
63 read the DHCP Handbook to figure out what you need to define.
65 The <Fo> specifies the fail-over peer name in the pool section, you'll need to
66 define additional detail elsewhere manually, again read the DHCP handbook.
68 NOTE: the program only knows of the following global and subnet options:
69 3, 6, 15, 28, 44, and 46
71 If it runs into options other than the known ones, it will quit. You
72 may fix this by modifying the following procedures:
73 GetGlobalOptions
74 GetScopes
75 PrintSubnetConfig
77 In addition, the resulting subnets configuration will have the "deny
78 dynamic bootp clients" you should take them out if that's not what you
79 want :).
81 Finally, as the parameter structures implied, it is assumed that you
82 want the same zone primary and update key for all zones and that the
83 same failover is to be applied to all the pools. Furthermore the
84 subnet zones are all assumed to be class C delineated, but if you
85 happend to be delegated at the class B level, this will work fine too.
87 Author: Shu-Min Chang <smchang@yahoo.com>
89 Copyright: Please read the top of the source code
91 Acknowledgement:
92 Brian L. King for coding help, Douglas A. Darrah for testing, and James E.
93 Pressley for being the DHCP reference book :).
95 Usage: $ARGV -s <Srv> -o <Out> [-p <Pri> [-k <key>]] [-f <Fo>]
97 Version: 1.0.1
99 ENDOFHELP
101 ###################### Begin Main Program ####################################
103 my (%opts, %GlobalOptions, %SuperScopes, %Scopes);
105 ### Get parameters and make sure that they meet the require/optoinal criteria
106 getopts('s:o:p:k:f:', \%opts) or die $usage;
107 ($opts{s} and $opts{o}) or die $usage;
108 if ($opts{k}) { $opts{p} or die $usage; }
110 ### Read all the registry stuff into the memory
111 %GlobalOptions = GetGlobalOptions($opts{s});
112 %SuperScopes = GetSuperScope($opts{s});
113 %Scopes = GetScopes ($opts{s});
115 ### Process and print out to the output file
116 my ($outfile, $i, $j, @Domains);
118 $outfile = new FileHandle "> $opts{o}";
119 if (!defined $outfile) {
120 die "Can't open file: $opts{o}: $!";
123 for $i (keys %SuperScopes) {
124 print $outfile "\n##############################################################\n";
125 my ($Scopename) = $i;
126 $Scopename =~ s/ //g;
127 print $outfile "shared-network $Scopename {\n";
128 foreach $j (@{$SuperScopes{$i}}) {
129 PrintSubnetConfig($outfile, \%GlobalOptions, \%{$Scopes{$j}}, $j, "\t", $opts{f});
130 InsertIfUnique (\@Domains, $Scopes{$j}{domain}) if exists $Scopes{$j}{domain};
131 delete $Scopes{$j};
133 print $outfile "}\n";
134 if ($opts{p} or $opts{k}) {
135 foreach $j (@{$SuperScopes{$i}}) {
136 PrintSubnetUpdate($outfile, $j, $opts{p}, $opts{k});
141 for $i (keys %Scopes) {
142 print $outfile "\n##############################################################\n";
143 PrintSubnetConfig($outfile, \%GlobalOptions, \%{$Scopes{$i}}, $i, "", $opts{f});
144 if ($opts{p} or $opts{k}) { PrintSubnetUpdate($outfile, $i, $opts{p}, $opts{k}); }
145 InsertIfUnique (\@Domains, $Scopes{$i}{domain}) if exists $Scopes{$i}{domain};
148 if ($opts{p} or $opts{k}) {
149 InsertIfUnique (\@Domains, $GlobalOptions{domain}) if exists $GlobalOptions{domain};
150 for $i (@Domains) {
151 PrintDomainUpdate($outfile, $i, $opts{p}, $opts{k});
155 undef ($outfile);
156 print "Done.\n";
157 exit();
159 ################################## End Main Program ###########################
165 ######################################################################
166 sub InsertIfUnique ($$) {
167 my ($Array, $data) = @_;
168 # purpose: insert $data into array @{$Array} iff the data is not in there yet
169 # input:
170 # $data: scalar data to be added to the @{$Array} if unique
171 # $Array: reference of the Array to compare the uniqueness of the $data
172 # output:
173 # $Array: reference of the array with the resulting array.
174 # return: none
176 my ($i);
178 for ($i=0; $i<=$#{$Array} && ${$Array}[$i] ne $data; $i++) { }
180 if ($i > $#{$Array}) {
181 ${$Array}[$i] = $data;
184 ######################################################################
185 sub PrintDomainUpdate ($$$$) {
186 my ($outfile, $Domain, $DDNSServer, $key) = @_;
187 # purpose: print out the foward domain zone update declaration
188 # input:
189 # $outfile: filehandle of the file to write the output to
190 # $Domain: a string representing the forward domain
191 # $DDNSServer: a string of the DNS server accepting the DDNS update
192 # $key: a string representing the key used to update the zone
193 # output: none
194 # return: none
197 print $outfile "zone $Domain {\n";
198 print $outfile "\tprimary $DDNSServer;\n";
199 !$key or print $outfile "\tkey $key;\n";
200 print $outfile "}\n";
203 ######################################################################
204 sub PrintSubnetUpdate ($$$$) {
205 my ($outfile, $Subnet, $DDNSServer, $key) = @_;
206 # purpose: print out the reverse domain zone update declaration
207 # input:
208 # $outfile: filehandle of the file to write the output to
209 # $Subnet: a string representing the subnet in the form 1.2.3.4
210 # $DDNSServer: a string of the DNS server accepting the DDNS update
211 # $key: a string representing the key used to update the zone
212 # output: none
213 # return: none
216 my ($Reverse);
218 $_ = join (".", reverse(split(/\./, $Subnet)));
219 m/\d*\.(.*)/;
220 $Reverse = $1;
221 print $outfile "zone $Reverse.in-addr.arpa. {\n";
222 print $outfile "\tprimary $DDNSServer;\n";
223 !$key or print $outfile "\tkey $key;\n";
224 print $outfile "}\n";
227 ######################################################################
228 sub PrintSubnetConfig ($$$$$$) {
229 my ($outfile, $GlobalOptions, $Scope, $Subnet, $prefix, $failover) = @_;
230 # purpose: print out the effective scope configuration for one subnet as
231 # derived from the global and scope options.
232 # input:
233 # $outfile: filehandle of the file to write the output to
234 # $GlobalOptions: refernce to the hashed variable from GetGlobalOptions
235 # $Scopes: reference to the hashed variable of the subnet in interest
236 # $Subnet: string variable of the subnet being processed
237 # $prefix: string to be printed before each line (designed for tab)
238 # $failover: string to be used for the "failover peer" line
239 # output: none
240 # return: none
242 my ($pound) = ( ${$Scope}{disable}? "#".$prefix : $prefix);
243 print $outfile $pound, "subnet $Subnet netmask ${$Scope}{mask} {\n";
244 print $outfile "$prefix# Name: ${$Scope}{name}\n";
245 print $outfile "$prefix# Comment: ${$Scope}{comment}\n";
246 if (exists ${$Scope}{routers}) {
247 print $outfile $pound, "\toption routers @{${$Scope}{routers}};\n";
248 } elsif (exists ${$GlobalOptions}{routers}) {
249 print $outfile $pound, "\toption routers @{${$GlobalOptions}{routers}};\t# NOTE: obtained from global option, bad practice detected\n";
250 } else {
251 print $outfile "### WARNING: No router was found for this subnet!!! ##########\n";
254 if (exists ${$Scope}{dnses}) {
255 print $outfile $pound, "\toption domain-name-servers ", join(",", @{${$Scope}{dnses}}), ";\n";
256 } elsif (exists ${$GlobalOptions}{dnses}) {
257 print $outfile $pound, "\toption domain-name-servers ", join(",", @{${$GlobalOptions}{dnses}}), ";\n";
260 if (exists ${$Scope}{domain}) {
261 print $outfile $pound, "\toption domain-name \"${$Scope}{domain}\";\n";
262 } elsif (exists ${$GlobalOptions}{domain}) {
263 print $outfile $pound, "\toption domain-name \"${$GlobalOptions}{domain}\";\n";
266 if (exists ${$Scope}{broadcast}) {
267 print $outfile $pound, "\toption broadcast-address ${$Scope}{broadcast};\n";
268 } elsif (exists ${$GlobalOptions}{broadcast}) {
269 print $outfile $pound, "\toption broadcast-address ${$GlobalOptions}{broadcast};\n";
272 if (exists ${$Scope}{winses}) {
273 print $outfile $pound, "\toption netbios-name-servers ", join(",", @{${$Scope}{winses}}), ";\n";
274 } elsif (exists ${$GlobalOptions}{winses}) {
275 print $outfile $pound, "\toption netbios-name-servers ", join(",", @{${$GlobalOptions}{winses}}), ";\n";
278 if (exists ${$Scope}{winstype}) {
279 print $outfile $pound, "\toption netbios-node-type ${$Scope}{winstype};\n";
280 } elsif (exists ${$GlobalOptions}{winstype}) {
281 print $outfile $pound, "\toption netbios-node-type ${$GlobalOptions}{winstype};\n"
284 print $outfile $pound, "\tdefault-lease-time ${$Scope}{leaseduration};\n";
285 print $outfile $pound, "\tpool {\n";
286 for (my $r=0; $r<=$#{${$Scope}{ranges}}; $r+=2) {
287 print $outfile $pound, "\t\trange ${$Scope}{ranges}[$r] ${$Scope}{ranges}[$r+1];\n";
289 !$failover or print $outfile $pound, "\t\tfailover peer \"$failover\";\n";
290 print $outfile $pound, "\t\tdeny dynamic bootp clients;\n";
291 print $outfile $pound, "\t}\n";
292 print $outfile $pound, "}\n";
295 ######################################################################
296 sub GetScopes ($) {
297 my ($Server) = @_;
298 my (%Scopes);
299 # purpose: to return NT4 server's scope configuration
300 # input:
301 # $Server: string of the valid IP or name of the NT4 server
302 # output: none
303 # return:
304 # %Scope: hash of hash of hash of various data types to be returned of the
305 # following data structure
306 # $Scope{<subnet>}{disable} => boolean
307 # $Scope{<subnet>}{mask} => string (e.g. "1.2.3.255")
308 # $Scope{<subnet>}{name} => string (e.g "Office Subnet #1")
309 # $Scope{<subnet>}{comment} => string (e.g. "This is a funny subnet")
310 # $Scope{<subnet>}{ranges} => array of paired inclusion IP addresses
311 # (e.g. "1.2.3.1 1.2.3.10 1.2.3.100 10.2.3.200
312 # says that we have 2 inclusion ranges of
313 # 1-10 and 100-200)
314 # $Scopes{<subnet>}{routers} => array of IP address strings
315 # $Scopes{<subnet>}{dnses} => array of IP address/name string
316 # $Scopes{<subnet>}{domain} > string
317 # $Scopes{<subnet>}{broadcast} => string
318 # $Scopes{<subnet>}{winses} => array of IP addresses/name string
319 # $Scopes{<subnet>}{winstype} => integer
320 # $Scopes{<subnet>}{leaseduration} => integer
322 my ($RegVal, @Subnets, @Router, $SubnetName, $SubnetComment, @SubnetOptions, @SRouter, @SDNSServers, @SDomainname, @SWINSservers, @SNetBIOS, @SLeaseDuration, @SSubnetState, @SExclusionRanges, @SSubnetAddress, @SSubnetMask, @SFirstAddress, $SStartAddress, $SEndAddress, @InclusionRanges, @SBroadcastAddress);
324 print "Getting list of subnets\n";
325 if (Registry::GetRegSubkeyList ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets", \@Subnets)) {
326 die "Unable to obtain a list of subnets from the server!\n";
329 for (my $i=0; $i<=$#Subnets; $i++) {
330 print "\t Fetching Subnet $Subnets[$i] (",$i+1, "/", $#Subnets+1, "): ";
332 print ".";
333 if (!Registry::GetRegSubkeyList ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\IpRanges", \@SFirstAddress)) {
334 # Don't know why MS has a tree for this, but as far
335 # as I can tell, only one subtree will ever come out of
336 # this, so I'm skipping the 'for' loop
338 print ".";
339 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\IpRanges\\$SFirstAddress[0]\\StartAddress", \$RegVal)) {
340 $SStartAddress = $RegVal;
342 print ".";
343 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\IpRanges\\$SFirstAddress[0]\\EndAddress", \$RegVal)) {
344 $SEndAddress = $RegVal;
346 # print "\n\tInclusion Range: ", Registry::ExtractIp($SStartAddress), " - ", Registry::ExtractIp($SEndAddress),"\n";
348 } else {
349 die "\n\n# Error Getting Inclusion Range FirstAddress!!!\n\n";
352 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\ExcludedIpRanges", \$RegVal)) {
353 @SExclusionRanges = Registry::ExtractExclusionRanges($RegVal);
355 # for (my $j=2; $j<=$#SExclusionRanges; $j+=2) {
356 # if (unpack("L",$SExclusionRanges[$j]) < unpack("L",$SExclusionRanges[$j-2])) {
357 # print ("\n******** Subnet exclusion ranges out of order ********\n");
361 @SExclusionRanges = sort(@SExclusionRanges);
363 # print "\n\tExclusion Ranges: ";
364 # for (my $j=0; $j<=$#SExclusionRanges; $j+=2) {
365 # print "\n\t\t",Registry::ExtractIp($SExclusionRanges[$j])," - ",Registry::ExtractIp($SExclusionRanges[$j+1]);
369 @InclusionRanges = FindInclusionRanges ($SStartAddress, $SEndAddress, @SExclusionRanges);
371 print ".";
372 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetName", \$RegVal)) {
373 $SubnetName = $RegVal;
374 # print "\n\tSubnetName: $SubnetName";
377 print ".";
378 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetComment", \$RegVal)) {
379 $SubnetComment = $RegVal;
380 # print "\n\tSubnetComment: $SubnetComment";
382 print ".";
383 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetAddress", \$RegVal)) {
384 @SSubnetAddress = Registry::ExtractIp($RegVal);
385 # print "\n\tSubnetAddress: $SSubnetAddress[0]";
387 print ".";
388 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetMask", \$RegVal)) {
389 @SSubnetMask = Registry::ExtractIp($RegVal);
390 # print "\n\tSubnetMask: $SSubnetMask[0]";
393 print ".";
394 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetState", \$RegVal)) {
395 @SSubnetState = Registry::ExtractHex ($RegVal);
396 # print "\n\tSubnetState = $SSubnetState[0]";
399 $Scopes{$Subnets[$i]}{disable} = hex($SSubnetState[0]) ? 1 : 0;
400 $Scopes{$Subnets[$i]}{mask} = $SSubnetMask[0];
401 $Scopes{$Subnets[$i]}{name} = $SubnetName;
402 $Scopes{$Subnets[$i]}{comment} = $SubnetComment;
403 for (my $r=0; $r<=$#InclusionRanges; $r++) {
404 $Scopes{$Subnets[$i]}{ranges}[$r] = Registry::ExtractIp($InclusionRanges[$r]);
407 ################## Get scope options
409 my (@SubnetOptionsList);
411 print "\n\t\tOptions:";
412 if (Registry::GetRegSubkeyList ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetOptions", \@SubnetOptionsList)) {
413 die "Unable to get subnet options list for $Subnets[$i]!\n";
416 for (my $j=0; $j<=$#SubnetOptionsList; $j++) {
417 print ".";
418 if (!Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\Subnets\\$Subnets[$i]\\SubnetOptions\\$SubnetOptionsList[$j]\\OptionValue", \$RegVal)) {
419 for ($SubnetOptionsList[$j]) {
420 /003/ and do {
421 # @SRouter = Registry::ExtractOptionIps($RegVal);
422 $Scopes{$Subnets[$i]}{routers} = [Registry::ExtractOptionIps($RegVal)];
423 last;
425 /006/ and do {
426 @SDNSServers = Registry::ExtractOptionIps($RegVal);
427 for (my $d=0; $d<=$#SDNSServers; $d++) {
428 my ($ipname, $rest) = gethostbyaddr(pack("C4", split(/\./, $SDNSServers[$d])), &AF_INET);
429 $Scopes{$Subnets[$i]}{dnses}[$d] = $ipname ? $ipname : $SDNSServers[$d];
431 last;
433 /015/ and do {
434 @SDomainname = Registry::ExtractOptionStrings($RegVal);
435 $Scopes{$Subnets[$i]}{domain} = $SDomainname[0];
436 last;
438 /028/ and do {
439 @SBroadcastAddress = Registry::ExtractOptionIps($RegVal);
440 $Scopes{$Subnets[$i]}{broadcast} = $SBroadcastAddress[0];
441 last;
443 /044/ and do {
444 @SWINSservers = Registry::ExtractOptionIps($RegVal);
445 for (my $w=0; $w<=$#SWINSservers; $w++) {
446 my ($ipname, $rest) = gethostbyaddr(pack("C4", split(/\./, $SWINSservers[$w])), &AF_INET);
447 $Scopes{$Subnets[$i]}{winses}[$w] = $ipname ? $ipname : $SWINSservers[$w];
449 last;
451 /046/ and do {
452 @SNetBIOS = Registry::ExtractOptionHex($RegVal);
453 $Scopes{$Subnets[$i]}{winstype} = hex($SNetBIOS[0]);
454 last;
456 /051/ and do {
457 @SLeaseDuration = Registry::ExtractOptionHex($RegVal);
458 $Scopes{$Subnets[$i]}{leaseduration} = hex($SLeaseDuration[0]);
459 last;
461 die "This program does not recognize subnet option \#$SubnetOptionsList[$j] yet!\n"
463 } else {
464 die "Unable to obtain option SubnetOptionsList[$j] from $Subnets[$i], most likely a registry problem!\n"
467 print "\n";
470 return %Scopes;
473 ######################################################################
474 sub FindInclusionRanges ($$@) {
475 my ($StartAddress, $EndAddress, @ExclusionRanges) = @_;
476 # Purpose: to calculate and return the DHCP inclusion ranges out of
477 # data provided by the NT4 DHCP server
478 # input: $StartAddress:
479 # $EndAddress:
480 # @ExclusionRanges
481 # output: none
482 # return: An arry of IP address pair representing the inclusion ranges
483 # in the native registry format.
486 my ($SA, $EA, @ER);
487 $SA = unpack("L", $StartAddress);
488 $EA = unpack("L", $EndAddress);
489 @ER = @ExclusionRanges;
490 for (my $i=0; $i<=$#ER; $i++) {
491 $ER[$i] = unpack ("L", $ER[$i]);
494 my @InclusionRanges;
497 $InclusionRanges[0] = $SA;
498 $InclusionRanges[1] = $EA;
500 for (my $i=0; $i<=$#ER; $i+=2) {
501 if ($ER[$i] == $InclusionRanges[$#InclusionRanges-1]) {
502 $InclusionRanges[$#InclusionRanges-1] = $ER[$i+1] + 1;
504 if ($ER[$i] > $InclusionRanges[$#InclusionRanges-1]) {
505 $InclusionRanges[$#InclusionRanges] = $ER[$i]-1;
507 if (($ER[$i+1] > $InclusionRanges[$#InclusionRanges]) &&
508 ($ER[$i+1] != $EA)) {
509 $InclusionRanges[$#InclusionRanges+1] = $ER[$i+1] + 1;
510 $InclusionRanges[$#InclusionRanges+1] = $EA;
512 if ($InclusionRanges[$#InclusionRanges] < $InclusionRanges[$#InclusionRanges-1]) {
513 $#InclusionRanges -= 2;
517 for (my $i=0; $i<=$#InclusionRanges; $i++) {
518 $InclusionRanges[$i] = pack("L", $InclusionRanges[$i]);
519 # print "Inclusion: ", Registry::ExtractIp($InclusionRanges[$i]), "\n";
521 return @InclusionRanges;
524 ####################################################################
525 sub GetSuperScope ($) {
526 my ($Server) = @_;
527 my (%SuperScopes);
529 # purpose: gets the Superscope list from the given server
530 # input:
531 # $Server: string of the valid IP address or name of the NT4 server
532 # ouput: none
533 # return:
534 # %SuperScopes: hash of array subnets with the following data structure
535 # $SuperScopes{<SuperscopeName>} => array of sunbets
537 my (@SuperScopeNames, @SCSubnetList);
539 print "Getting Superscope list: ";
540 if (!Registry::GetRegSubkeyList ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\SuperScope", \@SuperScopeNames)) {
541 for (my $i=0; $i<=$#SuperScopeNames; $i++) {
542 print ".";
543 if (!Registry::GetRegSubkeyList ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\SuperScope\\$SuperScopeNames[$i]", \@SCSubnetList)) {
544 $SuperScopes{$SuperScopeNames[$i]} = [@SCSubnetList];
547 print "\n";
550 return %SuperScopes;
553 ####################################################################
554 sub GetGlobalOptions($) {
555 my ($Server) = @_;
556 my (%GlobalOptions);
557 # purpose: to return NT4 server's global scope configuration
558 # input:
559 # $Server: string of the valid IP or name of the NT4 server
560 # output: none
561 # return:
562 # %GlobalOptions: hash of hash of various data types to be returned of the
563 # following data structure
564 # $GlobalOptions{routers} => array of IP address strings
565 # $GlobalOptions{dnses} => array of IP address/name string
566 # $GlobalOptions{domain} > string
567 # $GlobalOptions{broadcast} => string
568 # $GlobalOptions{winses} => array of IP addresses/name string
569 # $GlobalOptions{winstype} => integer
571 my ($RegVal, @temp, @GlobalOptionValues);
573 print "Getting Global Options: ";
574 if (Registry::GetRegSubkeyList ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\Configuration\\GlobalOptionValues", \@GlobalOptionValues)) {
575 die "Unable to obtain GlobalOptionValues";
578 for (my $i=0; $i<=$#GlobalOptionValues; $i++) {
579 print ".";
580 if (Registry::GetRegKeyVal ("\\\\$Server\\HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\DHCPServer\\configuration\\globaloptionvalues\\$GlobalOptionValues[$i]\\optionvalue", \$RegVal)) {
581 die "Unable to retrive global option $GlobalOptionValues[$i]\n";
585 for ($GlobalOptionValues[$i]) {
586 /003/ and do {
587 @temp=Registry::ExtractOptionIps($RegVal);
588 $GlobalOptions{routers} = [@temp];
589 last;
591 /006/ and do {
592 # DNS Servers
593 @temp = Registry::ExtractOptionIps($RegVal);
594 for (my $d=0; $d<=$#temp; $d++) {
595 my ($ipname, $rest) = gethostbyaddr(pack("C4", split(/\./, $temp[$d])), &AF_INET);
596 $GlobalOptions{dnses}[$d] = $ipname ? $ipname : $temp[$d];
598 last;
600 /015/ and do {
601 # Domain Name
602 @temp = Registry::ExtractOptionStrings($RegVal);
603 $GlobalOptions{domain} = $temp[0];
604 last;
606 /028/ and do {
607 # broadcast address
608 @temp = Registry::ExtractOptionIps($RegVal);
609 $GlobalOptions{broadcast} = $temp[0];
610 last;
612 /044/ and do {
613 # WINS Servers
614 @temp = Registry::ExtractOptionIps ($RegVal);
615 $GlobalOptions{winses} = [@temp];
616 for (my $w=0; $w<=$#temp; $w++) {
617 my ($ipname, $rest) = gethostbyaddr(pack("C4", split(/\./, $temp[$w])), &AF_INET);
618 $GlobalOptions{winses}[$w] = $ipname ? $ipname : $temp[$w];
620 last;
622 /046/ and do {
623 # NETBIOS node type
624 @temp = Registry::ExtractOptionHex($RegVal);
625 $GlobalOptions{winstype} = hex($temp[0]);
626 last;
628 die "This program does not recgonize global option \#$GlobalOptionValues[$i] yet!\n"
631 print "\n";
633 return %GlobalOptions;