1 # Functions for configuring DNS and DHCP servers together
6 &foreign_require("bind8", "bind8-lib.pl");
7 &foreign_require("dhcpd", "dhcpd-lib.pl");
10 # Returns a list of DHCP host structures for managed hosts
13 local $conf = &dhcpd::get_config();
14 local $parent = &dhcpd::get_parent_config();
18 foreach my $h (&dhcpd::find("host", $conf)) {
19 $h->{'parent'} = $parent;
24 foreach my $g (&dhcpd::find("group", $conf)) {
25 foreach my $h (&dhcpd::find("host", $g->{'members'})) {
31 # Hosts in subjects, and hosts in groups in subnets
32 foreach my $s (&dhcpd::find("subnet", $conf)) {
33 foreach my $h (&dhcpd::find("host", $s->{'members'})) {
37 foreach my $g (&dhcpd::find("group", $s->{'members'})) {
38 foreach my $h (&dhcpd::find("host", $g->{'members'})) {
45 # All of those, in shared networks
46 foreach my $n (&dhcpd::find("shared-network", $conf)) {
47 # Hosts in shared network
48 foreach my $h (&dhcpd::find("host", $n->{'members'})) {
54 foreach my $g (&dhcpd::find("group", $n->{'members'})) {
55 foreach my $h (&dhcpd::find("host", $g->{'members'})) {
61 # Hosts in subjects, and hosts in groups in subnets, in shared network
62 foreach my $s (&dhcpd::find("subnet", $n->{'members'})) {
63 foreach my $h (&dhcpd::find("host", $s->{'members'})) {
67 foreach my $g (&dhcpd::find("group", $s->{'members'})) {
68 foreach my $h (&dhcpd::find("host", $g->{'members'})) {
80 # Returns a list of all DHCP subnet objects
84 local $conf = &dhcpd::get_config();
85 local $parent = &dhcpd::get_parent_config();
86 foreach my $s (&dhcpd::find("subnet", $conf)) {
87 $s->{'parent'} = $parent;
90 foreach my $n (&dhcpd::find("shared-network", $conf)) {
91 foreach my $s (&dhcpd::find("subnet", $n->{'members'})) {
100 # Returns a form for editing or creating a host
106 $rv .= &ui_form_start("save.cgi", "post");
108 $rv .= &ui_hidden("new", 1);
111 $rv .= &ui_hidden("old", $h->{'values'}->[0]);
113 $rv .= &ui_table_start($text{'form_header'}, "width=100%", 2);
116 $rv .= &ui_table_row($text{'form_comment'},
117 &ui_textbox("comment", $host->{'comment'}, 50));
120 local $short = &short_hostname($h->{'values'}->[0]);
121 local $indom = $new || $short ne $h->{'values'}->[0];
122 $rv .= &ui_table_row($text{'form_host'},
123 &ui_textbox("host", $short, 20).
124 ($indom ? "<tt>.$config{'domain'}</tt>" : ""));
125 $rv .= &ui_hidden("indom", $indom);
128 local $fixed = &dhcpd::find("fixed-address", $h->{'members'});
129 $rv .= &ui_hidden("oldip", $fixed->{'values'}->[0]) if ($fixed);
130 local @subnets = &list_dhcp_subnets();
133 ($parsub) = grep { $_ eq $h->{'parent'} } @subnets;
136 $parsub = $subnets[0];
138 $rv .= &ui_table_row($text{'form_ip'},
139 &ui_textbox("ip", $fixed ? $fixed->{'values'}->[0] : undef, 20).
140 ($new ? " ".&ip_chooser_button("ip") : "").
141 " ".$text{'form_subnet'}." ".
142 &ui_select("subnet", $parsub ? $parsub->{'values'}->[0] : '',
143 [ $parsub ? ( ) : ( [ '', $text{'form_nosubnet'} ] ),
144 map { [ $_->{'values'}->[0] ] } @subnets ]));
145 $rv .= &ui_hidden("oldsubnet", $parsub ? $parsub->{'values'}->[0] : '');
148 local $hard = &dhcpd::find("hardware", $h->{'members'});
149 $rv .= &ui_hidden("oldmac", $hard->{'values'}->[1]) if ($hard);
150 $rv .= &ui_table_row($text{'form_mac'},
151 # &ui_select("media", $hard ? $hard->{'values'}->[0] : "ethernet",
152 # [ [ "ethernet", $text{'form_ethernet'} ],
153 # [ "token-ring", $text{'form_tr'} ],
154 # [ "fddi", $text{'form_fddi'} ] ], 1, 0, 1).
155 &ui_hidden("media", $hard ? $hard->{'values'}->[0] : "ethernet").
156 &ui_textbox("mac", $hard ? $hard->{'values'}->[1] : undef, 20));
158 $rv .= &ui_table_end();
160 $rv .= &ui_form_end([ [ undef, $text{'create'} ] ]);
163 $rv .= &ui_form_end([ [ undef, $text{'save'} ],
164 [ 'delete', $text{'delete'} ] ]);
172 if ($hn =~ /^(\S+)\.\Q$config{'domain'}\E$/) {
181 # Returns the records file and list of records for the domain
184 local $conf = &bind8::get_config();
185 local @zones = &bind8::find("zone", $conf);
186 foreach my $v (&bind8::find("view", $conf)) {
187 push(@zones, &bind8::find("zone", $v->{'members'}));
189 local ($z) = grep { lc($_->{'value'}) eq lc($config{'domain'}) } @zones;
191 local $file = &bind8::find("file", $z->{'members'});
192 local $fn = $file->{'values'}->[0];
193 local @recs = &bind8::read_zone_file($fn, $config{'domain'});
194 return ( $fn, \@recs );
197 # get_reverse_dns_zone(ip)
198 # Returns the records file and list of records for the domain for some IP
199 sub get_reverse_dns_zone
202 local $conf = &bind8::get_config();
203 local @zones = &bind8::find("zone", $conf);
204 foreach my $v (&bind8::find("view", $conf)) {
205 push(@zones, &bind8::find("zone", $v->{'members'}));
207 local $arpa = &bind8::ip_to_arpa($ip);
209 local ($z) = grep { $arpa =~ /\.$_->{'value'}$/i } @zones;
211 local $file = &bind8::find("file", $z->{'members'});
212 local $fn = $file->{'values'}->[0];
213 local @recs = &bind8::read_zone_file($fn, $config{'domain'});
214 return ( $fn, \@recs, $arpa, $z->{'value'} );
217 sub apply_configuration
219 &lock_file("$module_config_directory/apply");
221 $err = &dhcpd::restart_dhcpd();
223 $err = "DHCPD failed : $err";
226 $err = &bind8::restart_bind();
228 $err = "BIND failed : $err";
231 &unlock_file("$module_config_directory/apply");
235 # ip_chooser_button(field)
236 sub ip_chooser_button
238 return "<input type=button onClick='ifield = form.$_[0]; chooser = window.open(\"ip_chooser.cgi\", \"chooser\", \"toolbar=no,menubar=no,scrollbars=yes,resizable=yes,width=300,height=600\"); chooser.ifield = ifield; window.ifield = ifield' value=\"...\">\n";