Building and Running Freeipa 4.4.4 on Centos 7

One day, I was trying to replicate Freeipa from a Fedora 25/Freeipa 4.4.4 to NOT Fedora 25.  How hard could it be to rebuild Freeipa 4.4.4 on Centos?  It turns out it is fiddly to get the packages built.

The following is not for the faint of heart and leaves out a bunch of build environment stuff, so this is not a good package to learn rebuilding a package.  But, the instructions  should save you a ton of time.

Download Fedora 25’s Freeipa source.  It should be in this directory:

Download mod_wsgi source from Fedora 25.  It should be in this directory.

Download dinglibs source for Fedora 25.  I found it here:

Download cmocka source for Fedora 25.  I found it here:

And so on for the following: ldns, python-astroid, pylint.  I was unable to build the sssd version that ships with Fedora 25 and a couple of the Python packages.  That means the freeipa.spec file gets modified with lower version requirements and the python package requirements get commented out and installed with pip.

There are also modifications to the spec files needed to be sure the packages don’t conflict with themselves.

The modifications to the spec files to accept a lower version of some of the packages are easy.  The build script should complain the correct version isn’t available. Figure out what your distro packages and modify the spec file accordingly.

My recollection is the general order of build was:

  1. build mod-wsgi
  2. build dinglibs
  3. build cmocka
  4. build python-astroid
  5. build pylint
  6. build ldns
  7. build free-ipa

The freeipa build will probably fail a couple of times on simple dependencies in the spec file.  Just keep adjusting the spec file and you’ll get built packages in a few tries.

Here is my freeipa.spec file.  It is not perfect as a number of the packages built complain about conflicting with themselves. freeipa.spec

Do This Too!

For some reason, the replication setup script demands testing TCP port 7389 as another way to reach the LDAP server.  You need a port address translation for it.

firewall-cmd --permanent --zone=public --add-rich-rule="rule 
family="ipv4" \
source address="" \
port protocol="tcp" port="7389" accept"

firewall-cmd --permanent --zone=public --add-forward-port=port=7389:proto=tcp:toport=636:toaddr=

That’s the firewall-cmd way to forward anything showing up on TCP 7389 from the LAN and sending it to 636.  Adjust as needed.  It works for me.

Good luck!


Advanced Unbound DNS Server

Unbound is a multi-function DNS server from the BSD side of the Unix world.  It supports more features than dnsmasq, in particular, lots of security features related to DNSSEC.

Below is a configuration with no explicit DNSSEC that supports Kerberos, and LDAP.  It explicitly disables DNSSEC while acting as a local domain name server.

   access-control: allow
   cache-max-ttl: 14400
   cache-min-ttl: 900
   hide-identity: yes
   hide-version: yes
   minimal-responses: yes
   prefetch: yes
   qname-minimisation: yes
   rrset-roundrobin: yes
   use-caps-for-id: yes
   verbosity: 1

      name: "."
      forward-addr:        # Google
      forward-addr:        # Google
private-domain: "mydomain.zed"
domain-insecure: "mydomain.zed"
domain-insecure: ""
local-zone: "" nodefault
local-zone: "mydomain.zed." static
local-data: "mydomain.zed. 86400 IN NS ns1.mydomain.zed."
local-data: "mydomain.zed. 86400 IN NS ns2.mydomain.zed."
local-data: "mydomain.zed. 86400 IN SOA ns1.mydomain.zed. nobody.invalid. 1 3600 1200 604800 1080"
local-data: "mydomain.zed. 86400 IN SOA ns2.mydomain.zed. nobody.invalid. 1 3600 1200 604800 1080"
local-data: "ns1.mydomain.zed. 86400 IN A"
local-data: "ns2.mydomain.zed. 86400 IN A"
local-data: "server1.mydomain.zed. IN A"
local-data-ptr: " server1.mydomain.zed"
local-data: "server2.mydomain.zed IN A"
local-data-ptr: " server2.mydomain.zed"
local-data: "idserver.mydomain.zed IN A"
local-data-ptr: " idserver.mydomain.zed"
local-data: "_kerberos._tcp.mydomain.zed. 3600 IN SRV 0 100 88 idserver.mydomain.zed"
local-data: "_kerberos._udp.mydomain.zed. 3600 IN SRV 0 100 88 idserver.mydomain.zed"
local-data: "_kerberos-adm._tcp.mydomain.zed. 3600 IN SRV 0 100 749 idserver.mydomain.zed"
local-data: '_kerberos.mydomain.zed. TXT mydomain.zed"'
local-data: "idserver CNAME idserver.mydomain.zed"
local-data: "_kerberos-master._udp.mydomain.zed. 3600 IN SRV 0 100 749 idserver.mydomain.zed"
local-data: "_kpasswd._udp.mydomain.zed. 3600 IN SRV 0 100 749 idserver.mydomain.zed"
local-data: '_kerberos.mydomain.zed. TXT "mydomain.zed"'
local-data: "_ldap._tcp.mydomain.zed. 3600 IN SRV 0 100 389 idserver.mydomain.zed"

PAY ATTENTION to the use of single-quotes for the TXT record!

There’s an unbound package for Debian Stable (Stretch at time of writing)

Things to Know about Samba 4.x in 2017

It’s April, 2017 and Samba 3.x has been used as a domain controller for many, many years.  Samba 4.x has introduced radical new capabilities while still including the 3.x kitchen sink.

I recently successfully migrated a Windows domain controller to Samba 4.x and discovered a few very important distinctions and supported capabilities of 4.x vs. 3.x CentOS vs. Debian that a new Samba admin should know.

  1. Samba 4.x is nothing like 3.x.  4.x doesn’t need much in the way of a configuration.  Samba-tool makes an smb.conf and kerberos config for you. Use them.
  2. CENTOS  Samba 4.0 domain controller functionality is entirely unsupported.  What CENTOS 7.x supports is running Samba 4.x in 3.x mode. Samba-tool does not work therefore it isn’t provided. That’s very important to know if you are trying to set up a modern Windows domain.  The reason for the required the encryption backend isn’t in CENTOS and apparently there are no plans for it.
  3. Use Debian Testing as a virtual machine.  You get everything you need with Debian Testing.  There is full Samba 4.x support, samba-tool works like the wiki states.  I run CENTOS 7.x as the host OS for a bunch of servers. Running libvirt/kvm-qemu works great.

Things to Know Before Setting Up FreeIPA

A few notes about the things I discovered  testing FreeIPA about February, 2017.

  1. It’s NOT A Windows domain controller. This should be obvious just checking the basic docs.
  2. It conflicts with samba.  The first impulse is to deny this claim because, hey, there’s ample documentation about adding samba and some kind of connector/backend from FreeIPA to Samba.  However FreeIPA forces /etc/hosts format to be opposite Samba’s demanded order.   For example freeipa and freeipa.  I’m not sure how one gets around this.
  3. The LDAP server must be dedicated to freeIPA.  Putting other databases in the same 389 server causes some confusion on the part of the FreeIPA environment.  The systemd scripts just don’t work with more than one 389 database.
  4.  Use a virtual machine like kvm.  FreeIPA can run as an lxc-container. BUT  auditing does not work.  This is a limitation of the lxc container.
  5. /etc/hosts file parsing is quite strict.  If things don’t work while the system configures itself, check the arrangement in /etc/hosts.

ISC DHCPD with LDAP Part 2

If you haven’t set up your LDAP server and added the DHCP schema, then visit Part 1 of the series before moving on.

Thanks to this guy:

Based on that blogspot post, I was able to get pretty far. You should too.

Step 1: Add OU

What worked for me was adding an organizationalUnit to the LDAP tree, ou=dhcp,dc=michaelpapet,dc=com.  All the configs sit under that branch.

Step 2: /etc/dhcp/dhcpd.conf

Since we are letting Debian install the server, the slapd package maintainer allows anonymous search “out of the box.” the /etc/dhcp/dhcpd.conf doesn’t need a username and password.  If you want, you can do that.

ldap-server                 "localhost";
ldap-port                   389;
# We do an anonymous bind
# ldap-username             "cn=directorymanagerloginname";
# ldap-password             "mypassword";
ldap-base-dn                "ou=dhcp,dc=michaelpapet,dc=com";
ldap-method                 static;
ldap-debug-file             "/var/log/dhcp-ldap-startup.log";
ldap-dhcp-server-cn         "cn=server,ou=dhcp,dc=michaelpapet,dc=com"


There are two options for ldap-method.  Static reads the ldap directory and writes a config based on the directory contents.  Dynamic reads the ldap directory as needed. This has bad consequences if you are trying to debug your config with a cat /var/log/dhcp-ldap-startup.log.  Some of the config wil be “missing” on startup.  But, if a client somehow triggers a search for all settings, then the setting would be returned.

Order matters in the LDAP tree for the dhcpd server.  AFAICT, the easiest way to set it up is to adhere to the parent/child relationships mentioned below.

Step 3: Add the service.

Then, per the instructions, you add the service.  Note that the service has to correctly reference the server.  And, the server has to  correctly reference the service path.  The URL above shows that pretty clearly.

Also worth noting, your global DHCP server options go under the service.  For example, authoritative, classes, subclass and more are added using the dhcpStatements attribute.

Step 4: Add the subnet setting beneath the service

The subnet, and related settings goes in the subnet objectClass.  For example, default-lease-time would go into the dhcpOption attribute.  You will probably add a few.

Optional Step 5: Add pools as children to subnet and classes

If you want pools, then set them up under the subnet.  If you want allow/deny rules, then add something to the dhcpPermitList attribute like

allow members of "my-hosts"

Which leads us to the dhcpClass attribute.  I got it to work by using the attribute below the dhcpServer objectClass. In LDAP-ese cn=my-hosts,cn=MainServer,ou=dhcp,dc=michaelpapet,dc=com.

Then the attribute dhcpSubClassesdn points to a group of mac addresses.  For example, ou=my-macs,cn=MainServer,ou=dhcp,dc=michaelpapet,dc=com.

Under ou=my-macs, add objectClass dhcpSubClass.  As an example, attribute dhcpClassData = my-macs, cn=1:0a:1b:2c:3d:4e:5f NOTE THE 1: prefix to the mac address.  My limited understanding this means it identifies the MAC address.

Step 6: Test
dhcpd -f -d

If there were no problems, then the server is running, not forked.  You can then see it working to be sure it does what you want.

To see what config the server is running,

cat /var/log/dhcp-ldap-startup.log

Again, be sure the dhcpd server is running in static mode in /etc/dhcp/dhcpd.conf to see the config that is/isn’t running.

ISC DHCPD with LDAP Config Part 1

The average environment with one or two admins can probably do just fine with the /etc/dhcp/dhcpd.conf flat file.  Syntax isn’t the challenge.  As soon as you get into access control and many devices/subnets, the flat file gets long and that’s when mistakes happen. LDAP backend makes everything easier.

It’s important to note at the outset I’m running Debian Testing,  February 2016, Debian’s repositories.  Maybe by the time you read this, things have changed.  If you are new to LDAP, it’s a learning curve.  This first part might take a while.  I’m rushing through setup.

Get Ready

I like using an LDAP browser.  I like jxplorer because it supports the modern cn=config editing.  On Windows, the popular (and useful) ldapadmin is good, but does not support cn=config editing.

Get Packages
apt-get install slapd isc-dhcp-server-ldap isc-dhcp-server

Debian’s packages set up slapd (that’s the openldap server) for you, prompting you for an admin password.  It seems like they want you to use the command line tools ldapsearch and ldapmodify to edit cn=config. Check out what’s configured with this.

ldapsearch -Y EXTERNAL -H ldapi:/// -b "cn=config"


This is probably bad advice: I set a cn=config password.  A little later on, I can use jxplorer to change the config.

To start: use ldapsearch to find the config database.

ldapsearch -Y EXTERNAL -H ldapi:/// -b "cn=config"

Then you write the file that adds the password.

dn: olcDatabase={0}config,cn=config #be sure config is database 0.  
#You looked carefully at the output of ldapsearch, right?
changetype: modify
add: olcRootPW
olcRootPW: {SSHA}some_hashed_password #this was made with slappasswd

Then ldapmodify to add a password field. ldapmodify -c -Y EXTERNAL -H ldapi:/// -f /home/thatsme/pwd.ldif

If you aren’t familiar with ldif syntax, that should take a while to learn.


Debian’s package includes the schema file.  Openldap’s cn=config doesn’t support old-school schema files and that’s what the Debian package maintainer ships.  So, you have to find someone who has converted it for you if you don’t want to do a bunch of search/replace.

ldapadd -Y EXTERNAL -H ldapi:/// -f /etc/ldap/schema/dhcp.ldif

This is a good stopping place.  Next article, the ISC DHCP server setup.