Code

Updated opsi activation .
[gosa.git] / gosa-plugins / systems / admin / systems / class_termDNS.inc
index 526eefcccb6a6ea6747de25cc0dc99a07195775d..6fd06d3c602077beda626330b3699d2c0657c0e4 100644 (file)
@@ -1,18 +1,38 @@
 <?php
+/*
+ * This code is part of GOsa (http://www.gosa-project.org)
+ * Copyright (C) 2003-2008 GONICUS GmbH
+ *
+ * ID: $$Id$$
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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 for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
 
 class termDNS extends plugin
 {
   /* attribute list for save action */
   var $ignore_account = true;
-  var $autonet        = false;
 
   /* Basic informations 
    */
   var $attributes     = array("ipHostNumber","macAddress");
   var $objectclasses  = array("whatever");
 
-  var $ipHostNumber   = "";    // IP address 
-  var $macAddress     = "";    // Mac address 
+  var $ipHostNumber          = "";    // IP address 
+  var $additionalHostNumbers = array();
+  var $macAddress            = "";    // Mac address 
 
   var $orig_ipHostNumber   = "";    // IP address 
   var $orig_macAddress     = "";    // Mac address 
@@ -21,7 +41,7 @@ class termDNS extends plugin
   var $OrigCn         = "";    // Initial cn
   var $IPisMust       = false;
   var $MACisMust      = false;
-  var $dialog;
+  var $dialog         = false;
 
   /* DCHP Attributes 
    */
@@ -39,7 +59,7 @@ class termDNS extends plugin
 
   /* DNS attributes  
    */
-  var $DNSattributes            = array("dNSClass","zoneName","dNSTTL");
+  var $DNSattributes            = array("zoneName","dNSTTL");
   var $DNS_is_account           = false;
   var $initially_was_account = false;
   var $dnsEntry                 = array();
@@ -64,6 +84,14 @@ class termDNS extends plugin
       $this->cn = preg_replace("/\\\$\$/","",$this->attrs['cn'][0]);
     }
 
+    /* Create list of additional ipHostNumber.
+     */
+    $this->additionalHostNumbers = array();
+    if(isset($this->attrs['ipHostNumber']) && $this->attrs['ipHostNumber']['count'] > 1){
+      for($i = 1 ; $i < $this->attrs['ipHostNumber']['count']; $i ++){
+        $this->additionalHostNumbers[] = $this->attrs['ipHostNumber'][$i];
+      }
+    }
  
     /************
      * DHCP 
@@ -74,6 +102,11 @@ class termDNS extends plugin
     if($this->config->search("servdhcp","class",array("tabs"))){
       $this->dhcpEnabled = TRUE;
     }
+    
+    if(!class_available("dhcpHost")){
+      $this->dhcpEnabled = FALSE;
+    }
+
     if($this->dhcpEnabled){
       $this->dhcpParentNodes = $this->get_dhcp_parent_nodes();
       $this->dhcpParentNode  = $this->get_dhcp_parent_node();
@@ -87,16 +120,6 @@ class termDNS extends plugin
     }
 
 
-    /************
-     * Autonetwork hook 
-     ************/
-    /* Do we have autonet support? */
-    if (isset($this->config->data['MAIN']['AUTO_NETWORK_HOOK'])){
-      $this->autonet= true;
-    }
-
-
     /************
      * DNS
      ************/
@@ -109,6 +132,11 @@ class termDNS extends plugin
         $this->DNSenabled = true;
       }
     }
+
+    if(!class_available("DNS")){
+      $this->DNSenabled = FALSE;
+    }
+  
     if(!$this->DNSenabled){
       $this->DNS_is_account = false;
       return;
@@ -149,18 +177,42 @@ class termDNS extends plugin
       }
     }
 
-    /* Create a list of used mac and ip addresses */
+    /* Create a list of used mac and ip addresses.
+
+       ! We use this optically huge amount of code to fetch all 
+       Mac and IP addresses, because a simple search for mac and IP
+       over the whole ldap server was 10 to 20 times slower.
+     */
+    $deps  = array();
+    $ou = preg_replace("/,.*$/","",get_ou("systemRDN"));
+    $a_ous = array(get_ou("serverRDN"),
+                  get_ou("terminalRDN"),
+                  get_ou("workstationRDN"),
+                  get_ou("printerRDN"),
+                  get_ou("phoneRDN"),
+                  get_ou("componentRDN"));
+  
     $ldap = $this->config->get_ldap_link();
     $ldap->cd($this->config->current['BASE']);
-    $ldap->search("(|(macAddress=*)(ipHostNumber=*))",array("macAddress","ipHostNumber"));
+    $ldap->search("(&(objectClass=organizationalUnit)(".$ou."))",array("dn"));
     while($attrs = $ldap->fetch()){
-      if(isset($attrs['ipHostNumber'][0])){
-        $this->used_ip_mac["ip:".$attrs['ipHostNumber'][0]] = "ip:".$attrs['ipHostNumber'][0];
-      }
-      if(isset($attrs['macAddress'][0])){
-        $this->used_ip_mac["mac:".$attrs['macAddress'][0]] = "mac:".$attrs['macAddress'][0];
+      foreach($a_ous as $allowed){
+        $deps[] = $allowed.$attrs['dn'];
       }
-    } 
+    }
+
+    foreach($deps as $dep){
+      $ldap->cd($dep);
+      $ldap->search("(|(macAddress=*)(ipHostNumber=*))",array("macAddress","ipHostNumber"));
+      while($attrs = $ldap->fetch()){
+        if(isset($attrs['ipHostNumber'][0])){
+          $this->used_ip_mac["ip:".$attrs['ipHostNumber'][0]] = "ip:".$attrs['ipHostNumber'][0];
+        }
+        if(isset($attrs['macAddress'][0])){
+          $this->used_ip_mac["mac:".$attrs['macAddress'][0]] = "mac:".$attrs['macAddress'][0];
+        }
+      } 
+    }
 
     /* Save initial ip and mac values, to be able 
         check if the used values are already in use */ 
@@ -202,6 +254,7 @@ class termDNS extends plugin
   {
          /* Call parent execute */
     $smarty= get_smarty();
+    $smarty->assign("autonetACL",$this->acl_is_writeable("macAddress").$this->acl_is_writeable("ipHostNumber"));
 
     $tmp = $this->plInfo();
     foreach($tmp['plProvidedAcls'] as $name => $translation){
@@ -210,41 +263,63 @@ class termDNS extends plugin
 
     $display= "";
 
+    /**********
+     * Additional ipHostNumber handling 
+     **********/
+      
+    /* Add a new one */
+    if($this->acl_is_writeable("ipHostNumber")){
+      foreach($_POST as $name => $value){
+        if(preg_match("/^additionalHostNumbers_add/",$name)){
+          $this->additionalHostNumbers[] = "";
+          break;
+        }
+
+        /* Delete given entry */
+        if(preg_match("/^additionalHostNumbers_del_/",$name)){
+          $id = preg_replace("/^^additionalHostNumbers_del_([0-9]*)_.*/","\\1",$name);
+          if(isset($this->additionalHostNumbers[$id])){
+            unset($this->additionalHostNumbers[$id]);
+            $this->additionalHostNumbers = array_values($this->additionalHostNumbers);
+          }
+          break;
+        } 
+      }
+    }
+    $smarty->assign("additionalHostNumbers",$this->additionalHostNumbers);
     $smarty->assign("staticAddress", ""); 
-    $smarty->assign("autonet", $this->autonet);
+    /**********
+     * Autonet completion
+     **********/
  
     /* Check for autonet button */
-    if ($this->autonet && isset($_POST['autonet'])){
-      $cmd= $this->config->data['MAIN']['AUTO_NETWORK_HOOK'];
-      if(!empty($cmd) && $this->cn != ""){
-        $res = shell_exec($cmd." ".$this->cn);
-        if(!$res){
-          print_red(sprintf(_("Can't execute specified AUTO_NETWORK_HOOK '%s'. Please check your gosa.conf."),$cmd));
-        } else {
-          $res= split(';', trim($res));
-          if (isset($res[0]) && $res[0] != ""){
-            $this->ipHostNumber= $res[0];
-          }
-          if (isset($res[1]) && $res[1] != ""){
-            $this->macAddress= $res[1];
-          }
-        }
+    if (isset($_POST['autonet']) && ($this->acl_is_writeable("ipHostNumber") || $this->acl_is_writeable("macAddress"))){
+      $d= new gosaSupportDaemon(TRUE, 0.5);
+      $res= $d->_send("<xml><header>gosa_network_completition</header>".
+          "<source>GOSA</source><target>GOSA</target><hostname>".$this->cn."</hostname></xml>", TRUE);
+      if (isset($res['XML']['IP']) && $this->acl_is_writeable("ipHostNumber")){
+        $this->ipHostNumber= $res['XML']['IP'];
+      }
+      if (isset($res['XML']['MAC']) && $this->acl_is_writeable("macAddress")){
+        $this->macAddress= $res['XML']['MAC'];
       }
     }
-    
+
   
     /**********
      * DHCP Handling
      **********/
  
-    if(isset($_POST['dhcpEditOptions'])){
-
+    if(isset($_POST['dhcpEditOptions']) && $this->acl_is_readable("dhcpSetup")){
       if(count($this->dhcpHostEntry) == 0){
-        $this->dialog = new dhcpHost($this->dhcpParentNode,TRUE);
+        $this->dialog = new dhcpHost($this->parent,$this->dhcpParentNode,TRUE);
       }else{
-        $this->dialog = new dhcpHost($this->dhcpHostEntry,TRUE);
+        $this->dialog = new dhcpHost($this->parent,$this->dhcpHostEntry,TRUE);
       }
-      $this->dialog->cn = $this->cn; 
+      $this->dialog->cn   = $this->cn;
+      $this->dialog->read_only     = !$this->acl_is_writeable("dhcpSetup");
       $this->dialog->dhcpHWAddress = "ethernet ".$this->macAddress; 
       if(!empty($this->ipHostNumber)){
         $this->dialog->statements['fixed-address'] = $this->ipHostNumber; 
@@ -255,13 +330,12 @@ class termDNS extends plugin
       $this->dialog = FALSE; 
     }
 
-    if(isset($_POST['save_dhcp'])){
+    if(isset($_POST['save_dhcp']) && $this->acl_is_writeable("dhcpSetup")){
       $this->dialog->save_object();
-      
       $msgs = $this->dialog->check(array());
       if(count($msgs)){
         foreach($msgs as $msg){
-          print_red($msg);
+          msg_dialog::display(_("Error"), $msg, ERROR_DIALOG);
         }
       }else{
         $this->dhcpHostEntry = $this->dialog->save();
@@ -274,23 +348,25 @@ class termDNS extends plugin
       return($this->dialog->execute());
     }
  
-    $smarty->assign("dhcpEnabled",    $this->dhcpEnabled);
+    $smarty->assign("dhcpEnabled",    $this->dhcpEnabled && $this->acl_is_readable("dhcpSetup"));
     $smarty->assign("dhcp_is_Account",$this->dhcp_is_Account);
     $smarty->assign("dhcpParentNode", $this->dhcpParentNode);
     $smarty->assign("dhcpParentNodes",$this->dhcpParentNodes);
     $smarty->assign("dhcpParentNodeCnt",count($this->dhcpParentNodes));
 
-
     /**********
      * DNS Handling
      **********/
 
     /* There is no dns available
      */
+    $smarty->assign("DNS_is_account",$this->DNS_is_account);
+    $smarty->assign("DNSenabled",$this->DNSenabled && $this->acl_is_readable("dnsSetup"));
+
     if($this->DNSenabled == false){
 
       /* Is IP address must ? */
-      $smarty->assign("DNS_is_account",false);
+#      $smarty->assign("DNS_is_account",false);
       $smarty->assign("IPisMust",(($this->IPisMust)||($this->DNS_is_account)));
 
       /* Assign smarty all non DNs attributes */
@@ -301,15 +377,15 @@ class termDNS extends plugin
 
       $display.= $smarty->fetch(get_template_path('network.tpl', TRUE));
     }else{
-      $smarty->assign("DNS_is_account",true);
#     $smarty->assign("DNS_is_account",true);
 
       /* Add new empty array to our record list */
-      if(isset($_POST['AddNewRecord'])){
+      if(isset($_POST['AddNewRecord']) && $this->acl_is_writeable("dnsSetup")){
         $this->dnsEntry['RECORDS'][]  =array("type"=>"aRecord","value"=>"");
       }
 
       /* propose_ip */
-      if(isset($_POST['propose_ip'])){
+      if(isset($_POST['propose_ip']) && $this->acl_is_writeable("ipHostNumber")){
         foreach($this->Zones as $key => $name){
           if($name == $this->dnsEntry['zoneName']){
             $net = DNS::FlipIp(str_replace(".in-addr.arpa","",DNS::getNameFromMix($key)));
@@ -320,21 +396,23 @@ class termDNS extends plugin
 
       /* Handle all posts */
       $only_once =true;
-      foreach($_POST as $name => $value){
+      if($this->acl_is_writeable("dnsSetup")){
+        foreach($_POST as $name => $value){
 
-        /* Check if we have to delete a record entry */
-        if((preg_match("/RemoveRecord_/",$name))&&($only_once)) {
+          /* Check if we have to delete a record entry */
+          if((preg_match("/RemoveRecord_/",$name))&&($only_once)) {
 
-          /* Avoid performing this once again */
-          $only_once = false;
+            /* Avoid performing this once again */
+            $only_once = false;
 
-          /* Extract id for specified entry */
-          $id = preg_replace("/RemoveRecord_/","",$name);
-          $id = preg_replace("/_.*$/","",$id);
+            /* Extract id for specified entry */
+            $id = preg_replace("/RemoveRecord_/","",$name);
+            $id = preg_replace("/_.*$/","",$id);
 
-          /* Delete this record, mark edited entries to be able to delete them */
-          if(isset($this->dnsEntry['RECORDS'][$id])){
-            unset($this->dnsEntry['RECORDS'][$id]);
+            /* Delete this record, mark edited entries to be able to delete them */
+            if(isset($this->dnsEntry['RECORDS'][$id])){
+              unset($this->dnsEntry['RECORDS'][$id]);
+            }
           }
         }
       }
@@ -349,7 +427,7 @@ class termDNS extends plugin
       }
 
       /* Assign all needed vars */
-      $smarty->assign("DNSAccount",$this->DNS_is_account);
#     $smarty->assign("DNSAccount",$this->DNS_is_account);
       $smarty->assign("hide_dns_check_box",$this->hide_dns_check_box);
   
       $smarty->assign("Zones",$this->Zones);
@@ -377,27 +455,33 @@ class termDNS extends plugin
       $smarty->assign("changeStateForRecords",$changeStateForRecords);
       $smarty->assign("staticAddress","<font class=\"must\">*</font>");
 
+      $smarty->assign("autonetACL",$this->acl_is_writeable("macAddress").$this->acl_is_writeable("ipHostNumber"));
+
       $display.= $smarty->fetch(get_template_path('network.tpl', TRUE));
     }
+
     return($display);
   }
 
 
   function remove_from_parent()
   {
-    if($this->initially_was_account){
+    if($this->DNS_is_account){
 
       $ldap = $this->config->get_ldap_link();
 
       $tmp = array();
       $this->dnsEntry['exists'] = false;
       $tmp = DNS::getDNSHostEntriesDiff($this->config,$this->OrigCn,$this->dnsEntry,$this->cn);
-
+  
       /* Delete dns */
       foreach($tmp['del'] as $dn => $del){
         $ldap->cd($dn);
         $ldap->rmdir_recursive($dn);
         new log("remove","unknown/".get_class($this),$dn);
+        if (!$ldap->success()){
+          msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $dn, LDAP_DEL, get_class()));
+        }
       }
     }
   }
@@ -412,8 +496,25 @@ class termDNS extends plugin
       /* Save all posted vars */
       plugin::save_object();
 
-      /* Handle DHCP Posts*/
-      if($this->dhcpEnabled && isset($_POST['network_tpl_posted'])){
+      /******
+        Additional IP Host Numbers 
+       ******/
+
+      /* Get posts for all additionally added ipHostNumbers */
+      if($this->acl_is_writeable("ipHostNumber")){
+        foreach($this->additionalHostNumbers as $id => $value){
+          if(isset($_POST['additionalHostNumbers_'.$id])){
+            $this->additionalHostNumbers[$id] = get_post('additionalHostNumbers_'.$id);
+          }
+        } 
+      } 
+
+
+      /******
+        DHCP posts
+       ******/
+
+      if($this->acl_is_writeable("dhcpSetup") && $this->dhcpEnabled && isset($_POST['network_tpl_posted'])){
         foreach($this->dhcpAttributes as $attr){
           if(isset($_POST[$attr])){
             $this->$attr = $_POST[$attr];
@@ -433,18 +534,23 @@ class termDNS extends plugin
         }
       }
 
+
+      /******
+        DNS posts
+       ******/
+
       /* Check if DNS should be enabled / disabled */
-      if($this->DNS_is_account && $this->acl_is_removeable() && !isset($_POST['DNS_is_account'])){
+      if($this->DNS_is_account && $this->acl_is_writeable("dnsSetup") && !isset($_POST['DNS_is_account'])){
         $this->DNS_is_account = false;
-      }elseif(!$this->DNS_is_account && $this->acl_is_createable() && isset($_POST['DNS_is_account'])){
+      }elseif(!$this->DNS_is_account && $this->acl_is_writeable("dnsSetup") && isset($_POST['DNS_is_account'])){
         $this->DNS_is_account = true;
       }
 
       /* Get dns attributes */
-      if(($this->DNSenabled) && (isset($_POST['network_tpl_posted']))){
+      if(($this->DNSenabled) && (isset($_POST['network_tpl_posted'])) && $this->acl_is_writeable("dnsSetup")){
 
         /* Check for posted record changes */
-        if(is_array($this->dnsEntry['RECORDS']) && $this->acl_is_writeable("Records")){
+        if(is_array($this->dnsEntry['RECORDS'])){
           foreach($this->dnsEntry['RECORDS'] as $key => $value){
 
             /* Check if type has changed */
@@ -457,14 +563,13 @@ class termDNS extends plugin
             }
           }
         }
+
         /* Get all basic DNS attributes (TTL, Clas ..)*/
         foreach($this->DNSattributes as $attr){
-          if(isset($_POST[$attr]) && $this->acl_is_writeable($attr)){
+          if(isset($_POST[$attr])){
             $this->dnsEntry[$attr] = $_POST[$attr];
           }
         }
-
-
       }
       if($this->hide_dns_check_box){
         $this->DNS_is_account = true;
@@ -479,41 +584,47 @@ class termDNS extends plugin
     /* Call common method to give check the hook */
     $message= plugin::check();
 
-    if($this->dhcpEnabled && $this->dhcp_is_Account && $this->dhcpParentNode != "" && count($this->dhcpHostEntry) == 0){
-#      $message[] =_("You have not configured your dhcp settings yet.");
+    /******
+      check additional IP Host Numbers 
+     ******/
+
+    foreach($this->additionalHostNumbers as $id => $value){
+      if(!tests::is_ip($value)){
+        $message[]= msgPool::invalid(sprintf(_("IP address %s"),($id +2)), "", "", "192.168.1.10");
+      }
     }
-    
+
+
     /* Check if mac and ip are already used */
     if(!empty($this->ipHostNumber) && $this->DNS_is_account && 
         $this->ipHostNumber != $this->orig_ipHostNumber && 
         in_array("ip:".$this->ipHostNumber,$this->used_ip_mac)){
-      $message[] =_("The specified IP address is already in use.");
+      $message[]= msgPool::duplicated(_("IP address"));
     }
     if(!empty($this->macAddress) && $this->dhcp_is_Account && 
         $this->macAddress != $this->orig_macAddress && 
         in_array("mac:".$this->macAddress,$this->used_ip_mac)){
-      print_red(sprintf(_("The specified MAC address '%s' for this system '%s' is already in use."),$this->macAddress,$this->cn));
+      $message[]= msgPool::duplicated(_("MAC address"));
     }
 
     /* Check if ip must be given
      */  
     if(($this->IPisMust)||($this->DNS_is_account)){
       if (empty($this->ipHostNumber)){
-        $message[]= _("The required field 'IP-address' is not set.");
-      }
-
-      if (!tests::is_ip($this->ipHostNumber)){
-        $message[]= _("Wrong IP format in field IP-address.");
+        $message[]= msgPool::required(_("IP address"));
+      }elseif (!tests::is_ip($this->ipHostNumber)){
+        $message[]= msgPool::invalid(_("IP address"), "", "", "192.168.1.10");
       }
     }
 
     /* Check if mac is empty 
      */
-    if ($this->macAddress == "" ){
-      $message[]= _("The required field 'MAC-address' is not set.");
-    }
-    if(!tests::is_mac($this->macAddress)){
-      $message[]=(_("The given macaddress is invalid. There must be 6 2byte segments seperated by ':'."));
+    if($this->MACisMust || $this->dhcp_is_Account){
+      if ($this->macAddress == "" ){
+        $message[]= msgPool::required(_("MAC address"));
+      }elseif(!tests::is_mac($this->macAddress)){
+        $message[]= msgPool::invalid(_("MAC address"), "", "", "00:0C:7F:31:33:F1");
+      }
     }
 
     /* only perfrom this checks if this is a valid DNS account */
@@ -527,7 +638,7 @@ class termDNS extends plugin
        $tmp2 = $tmp[$this->dnsEntry['zoneName']];
        if(!$this->netmaskIsCoherent($tmp2)){ //this->dnsEntry['zoneName'])){
          $tmp2 = preg_replace("/^.*\//","",$tmp2);
-         $message[] =sprintf(_("The specified IP address '%s' is not matching the selected reverse zone entry '%s'."),$this->ipHostNumber,$tmp2);
+         $message[] =sprintf(_("The IP address '%s' is not part of the selected reverse zone '%s'!"),$this->ipHostNumber,$tmp2);
        }
 
       /* Walk through all entries and detect duplicates or mismatches
@@ -539,7 +650,7 @@ class termDNS extends plugin
         if(!isset($checkArray[$values['type']][$values['value']])){
           $checkArray[$values['type']][$values['value']] = 0;
         }else{
-          $message[] = sprintf(_("Found duplicate value for record type '%s'."),$values['type']);
+          $message[] = sprintf(_("Record type '%s' is duplicated!"),$values['type']);
         }
 
         /* Check if given entries in $onlyOnce are used more than once
@@ -547,7 +658,7 @@ class termDNS extends plugin
         if(isset($onlyOnce[$values['type']])){
           $onlyOnce[$values['type']] ++;
           if($onlyOnce[$values['type']] > 1){
-            $message[] = sprintf(_("Found more than one entry for the uniqe record type '%s'."),$values['type']);
+            $message[] = sprintf(_("Uniq record type '%s' is duplicated!"),$values['type']);
           }
         }
 
@@ -558,14 +669,16 @@ class termDNS extends plugin
         /* Check if there is an aRecord defined which uses the same IP as used in IPhostAddress 
          */
         if(($values['type'] == "aRecord")&&($values['value'] == $this->ipHostNumber)){
-          $message[]=sprintf(_("The device IP '%s' is added as 'A Record', this will be done automatically, please remove the record."), 
+          #TODO: Where's the problem here?
+          $message[]=sprintf(_("The IP address '%s' will be added as 'A Record', this will be done automatically, please remove the record."), 
                $this->ipHostNumber);
         }
 
         /* only lower-case is allowed in record entries ... 
          */
         if($values['value'] != strtolower($values['value'])){
-          $message[] = sprintf(_("Only lowercase is allowed, please check your '%ss'."),$values['type']);
+          #TODO: What's in values['value']? Something for a propper message?
+          $message[] = sprintf(_("Only lowercase records are allowed, please check your '%ss'."),$values['type']);
         }
       }
     }
@@ -590,6 +703,15 @@ class termDNS extends plugin
     /* Save DNS setting & ip/Mac*/
     plugin::save();
 
+    /* Add all additional ipHostNumbers now 
+     */
+    if(!empty($this->ipHostNumber)){
+      $this->attrs['ipHostNumber'] = array($this->ipHostNumber);
+    }
+    foreach($this->additionalHostNumbers as $value){
+      $this->attrs['ipHostNumber'][] = $value;
+    }
+
     /* Write back to ldap */
     $ldap->cd($this->dn);
     $this->cleanup();
@@ -600,25 +722,10 @@ class termDNS extends plugin
     /****************/ 
   
     /* New entry */
-    if($this->dhcpEnabled){
-
-      if(count($this->dhcpHostEntry) == 0){
-        $this->dialog = new dhcpHost($this->dhcpParentNode,TRUE);
-        $this->dialog->cn = $this->cn;
-        $this->dialog->dhcpHWAddress = "ethernet ".$this->macAddress;
-        if(!empty($this->ipHostNumber)){
-          $this->dialog->statements['fixed-address'] = $this->ipHostNumber;
-        }
-        $this->dialog->execute();
-        $this->dialog->save_object(); 
-        $this->dhcpHostEntry = $this->dialog->save();
-        if(count($this->dhcpHostEntry['dhcpOption']) == 0){
-          $this->dhcpHostEntry['dhcpOption']= array("host-name ".$this->cn);
-        }
-      }
+    if($this->dhcpEnabled && $this->acl_is_writeable("dhcpSetup")) {
 
       if(count($this->dhcpHostEntry) == 0){
-        $this->dialog = new dhcpHost($this->dhcpParentNode,TRUE);
+        $this->dialog = new dhcpHost($this->parent,$this->dhcpParentNode,TRUE);
         $this->dialog->cn = $this->cn;
         $this->dialog->dhcpHWAddress = "ethernet ".$this->macAddress;
         if(!empty($this->ipHostNumber)){
@@ -640,7 +747,16 @@ class termDNS extends plugin
           $this->dhcpHostEntry['MODIFIED'] = TRUE;
         }
       }
-  
+
+      /* Updated IP host number */
+      if($this->dhcp_is_Account){
+        foreach($this->dhcpHostEntry['dhcpStatements'] as $id => $value){
+          if(preg_match("/^fixed-address/",$value)){
+            $this->dhcpHostEntry['dhcpStatements'][$id] = "fixed-address ".$this->ipHostNumber; 
+            $this->dhcpHostEntry['MODIFIED'] = TRUE;
+          }
+        }
+      }
 
       /* Unset dhcpStatements if this attribute is empty  */
       if(isset($this->dhcpHostEntry['dhcpStatements']) && 
@@ -651,7 +767,9 @@ class termDNS extends plugin
       /* DHCP removed */
       if($this->initial_dhcp_is_Account && !$this->dhcp_is_Account){
         $ldap->rmdir_recursive($this->dhcpHostEntry['dn']);
-        show_ldap_error($ldap->get_error(),_("Removing dhcp entry for this object failed."));
+        if (!$ldap->success()){
+          msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dhcpHostEntry['dn'], LDAP_DEL, get_class()));
+        }
 
         $tmp = new servdhcp($this->config,$this->dhcpParentNode);
         $tmp->handle_post_events("remove");
@@ -668,7 +786,9 @@ class termDNS extends plugin
         $tmp = new servdhcp($this->config,$this->dhcpParentNode);
         $tmp->handle_post_events("add");
 
-        show_ldap_error($ldap->get_error(),_("Tried to add new dhcp entry failed."));
+        if (!$ldap->success()){
+          msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), "cn=".$this->cn.",".$this->dhcpParentNode, LDAP_ADD, get_class()));
+        }
       }
 
       /* DHCP still activated */
@@ -687,10 +807,14 @@ class termDNS extends plugin
           $tmp = new servdhcp($this->config,$this->dhcpParentNode);
           $tmp->handle_post_events("modify");
 
-          show_ldap_error($ldap->get_error(),_("Tried to add new dhcp entry failed."));
+          if (!$ldap->success()){
+            msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), "cn=".$this->cn.",".$this->dhcpParentNode, LDAP_ADD, get_class()));
+          }
           if($res){
             $ldap->rmdir_recursive($this->dhcpHostEntry['dn']);
-            show_ldap_error($ldap->get_error(),_("Removing old dhcp entry failed."));
+            if (!$ldap->success()){
+              msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dhcpHostEntry['dn'], LDAP_DEL, get_class()));
+            }
           }
         }
          
@@ -706,11 +830,13 @@ class termDNS extends plugin
           $tmp = new servdhcp($this->config,$this->dhcpParentNode);
           $tmp->handle_post_events("modify");
 
-          show_ldap_error($ldap->get_error(),_("Modifying dhcp entry failed."));
+          if (!$ldap->success()){
+            msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dhcpHostEntry['dn'], LDAP_MOD, get_class()));
+          }
         }    
       }
     }
-      
+    $this->dialog = FALSE; 
 
     /****************/ 
     /* DNS HANDLING */
@@ -721,7 +847,7 @@ class termDNS extends plugin
      */ 
     if((!$this->DNSenabled) || ((!$this->DNS_is_account)&&(!$this->initially_was_account))){
       return;
-    }else{
+    }elseif($this->acl_is_writeable("dnsSetup")){
 
       /* Add ipHostNumber to aRecords
        */
@@ -776,8 +902,8 @@ class termDNS extends plugin
 
       /* Display errors 
        */
-      if($ldap->get_error() != "Success"){
-        show_ldap_error($ldap->get_error(), sprintf(_("Saving of terminal/dns account with dn '%s' failed."),$this->dn));
+      if (!$ldap->success()){
+        msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $dn, 0, get_class()));
       }
 
       $tmp2 = new servdns($this->config,$this->dn);
@@ -857,16 +983,13 @@ class termDNS extends plugin
           "macAddress"    => _("MAC address"))
         );
 
-    /* Hide all dns specific code, if dns is not available
+    /* Hide all dns/dhcp configurations if not available
      */
-    $config = session::get('config');
-    foreach($config->data['TABS']['SERVERSERVICE'] as $tab){
-      if(preg_match("/^servdns$/",$tab['CLASS'])){
-        $tmp['plProvidedAcls']["Records"]        = _("DNS records");
-        $tmp['plProvidedAcls']["zoneName"]       = _("Zone name");
-        $tmp['plProvidedAcls']["dNSTTL"]         = _("TTL");
-        break;
-      }
+    if(class_available("servdns")){
+      $tmp['plProvidedAcls']["dnsSetup"]    = _("DNS configuration");
+    }
+    if(class_available("servdhcp")){
+      $tmp['plProvidedAcls']["dhcpSetup"]   = _("DHCP configuration");
     }
     return($tmp);
   }
@@ -913,7 +1036,7 @@ class termDNS extends plugin
 
   function get_dhcp_parent_node()
   {
-    return(preg_replace("/^cn=".normalizePreg($this->cn).",/","",$this->get_dhcp_host_entry_dn()));
+    return(preg_replace("/^cn=".preg_quote($this->cn, '/').",/","",$this->get_dhcp_host_entry_dn()));
   }
 
 
@@ -962,7 +1085,7 @@ class termDNS extends plugin
       $tmp = array_flip($this->Zones);
       $tmp = preg_replace("/^[^\/]*+\//","",$tmp[$this->dnsEntry['zoneName']]);
       $tmp = trim(preg_replace("/\.in-addr.arpa$/","",$tmp));
-      $ptr = preg_replace("/^".normalizePreg(DNS::FlipIp($tmp))."\./","",$this->ipHostNumber);
+      $ptr = preg_replace("/^".preg_quote(DNS::FlipIp($tmp), '/')."\./","",$this->ipHostNumber);
       return($ptr);
     }else{
       return(FALSE);
@@ -989,7 +1112,7 @@ class termDNS extends plugin
     $ret = array();
     foreach($arr as $r => $name){
       $base_part = str_replace($base,"",$r);
-      if(preg_match("/^[a-z]*=".normalizePreg($name)."(|,)$/i",$base_part)){
+      if(preg_match("/^[a-z]*=".preg_quote($name, '/')."(|,)$/i",$base_part)){
         $ret[$r] = $current.$name;
         $tmp = $this->create_tree($arr,$r,$current.".&nbsp;");
         foreach($tmp as $sub_key => $sub_name){
@@ -1003,8 +1126,12 @@ class termDNS extends plugin
   function force_dns()
   {
     if($this->DNSenabled){
-      $this->DNS_is_account  = TRUE;
-      $this->hide_dns_check_box = TRUE;
+
+      /* Only force DNS account, if we have at least on dns Zone */
+      if(count($this->Zones)){
+        $this->DNS_is_account  = TRUE;
+        $this->hide_dns_check_box = TRUE;
+      }
     }
   }
 }