Virtual Server Administration

We will work through the setting up of a new domain. To do this, we first have to introduce the domain name as a known name in cyberspace. This is done with the Domain Name Systems, a.k.a. DNS. The result is that the website address, di.metri.us in this case, will be know as a certain IP address. When this is done, a name exists and nothing more. Use of this address at this time will result in a the browser looking for a server which might not exist, and if it exists, might be unprepared to resond to the browser's request.

The next step, then, is to clear the network path to the machine with the given IP address. The global routing structure of the Internet will take the request to my door, but we have a firewall which prevents the request to proceed further than the door. The firewall uses Network Address Translation, a.k.a. NAT, to regulate requests coming into my local network. Each machine on my local network uses local IP addresses which are not visible to the Internet. For the request to get to my server the firewall must rewrite the global IP address specified by the request packet to the local IP address of my machine, and the firewall must specifically permit passage of the packet according to certain security rules.

Now the browser requests is getting into the local network and has a the local address for a destination. SSL requires that each web site have its own IP address. Only in this way can the SSL handshake provide the correct certificate to the browser. A single machine can have multiple IP addresses, and we have to configure the web server to now recognize the new IP adress. The web server softare, Apache, must also be configured to handle the requests on that configured address. A single running instance of Apache can handle multiple IP addresses, and can correctly send off the connection to the correct set of web pages.

DNS

To create the di.metri.us domain we need to create an A record for that domain containing the IP address of the server for di.metri.us. The domain metri.us is owned by me and I use GoDaddy as the DNS server for this name. So I log onto my GoDaddy account and add the subdomain di and include the appropriate A record.

[burt@sherman Csc598.073]$ dig psi.metri.us

; <<>> DiG 8.3 <<>> psi.metri.us 
;; res options: init recurs defnam dnsrch
;; got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 2
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 2, ADDITIONAL: 2
;; QUERY SECTION:
;;      psi.metri.us, type = A, class = IN

;; ANSWER SECTION:
psi.metri.us.           1H IN A         192.31.89.7

;; AUTHORITY SECTION:
metri.us.               1h42m54s IN NS  PARK32.SECURESERVER.NET.
metri.us.               1h42m54s IN NS  PARK31.SECURESERVER.NET.

;; ADDITIONAL SECTION:
PARK32.SECURESERVER.NET.  15h48m16s IN A  208.109.80.74
PARK31.SECURESERVER.NET.  15h48m16s IN A  64.202.165.123

;; Total query time: 70 msec
;; FROM: sherman.cs.miami.edu to SERVER: default -- 127.0.0.1
;; WHEN: Wed Jun  6 12:48:55 2007
;; MSG SIZE  sent: 30  rcvd: 148

[burt@sherman Csc598.073]$ nslookup
Default Server:  localhost.cs.miami.edu
Address:  127.0.0.1

> server park32.secureserver.net
Default Server:  park32.secureserver.net
Address:  208.109.80.74

> psi.metri.us
Server:  park32.secureserver.net
Address:  208.109.80.74

Name:    psi.metri.us
Address:  192.31.89.7

> di.metri.us
Server:  park32.secureserver.net
Address:  208.109.80.74

Name:    di.metri.us
Address:  192.31.89.11

[burt@sherman Csc598.073]$ dig @park32.secureserver.net di.metri.us

; <<>> DiG 8.3 <<>> @park32.secureserver.net di.metri.us 
; (1 server found)
;; res options: init recurs defnam dnsrch
;; got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 4
;; flags: qr aa rd; QUERY: 1, ANSWER: 1, AUTHORITY: 2, ADDITIONAL: 0
;; QUERY SECTION:
;;      di.metri.us, type = A, class = IN

;; ANSWER SECTION:
di.metri.us.            30M IN A        192.31.89.11

;; AUTHORITY SECTION:
metri.us.               1H IN NS        park31.secureserver.net.
metri.us.               1H IN NS        park32.secureserver.net.

;; Total query time: 65 msec
;; FROM: sherman.cs.miami.edu to SERVER: park32.secureserver.net  208.109.80.74
;; WHEN: Wed Jun  6 13:05:40 2007
;; MSG SIZE  sent: 29  rcvd: 103

Since we are working from behind a firewall, locally di.metri.us will have a different, local address. We first install that A record in or local name server. Here is how:

sherman# nsupdate
> update add grant-B.cs.miami.edu 3600 A 172.21.0.11        
> 

[burt@sherman Csc598.073]$ dig grant-B.cs.miami.edu

; <<>> DiG 8.3 <<>> grant-B.cs.miami.edu 
;; res options: init recurs defnam dnsrch
;; got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 2
;; flags: qr aa rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 1, ADDITIONAL: 1
;; QUERY SECTION:
;;      grant-B.cs.miami.edu, type = A, class = IN

;; ANSWER SECTION:
grant-B.cs.miami.edu.   1H IN A         172.21.0.11

;; AUTHORITY SECTION:
cs.miami.edu.           1D IN NS        sherman.cs.miami.edu.

;; ADDITIONAL SECTION:
sherman.cs.miami.edu.   1D IN A         172.20.0.2

;; Total query time: 0 msec
;; FROM: sherman.cs.miami.edu to SERVER: default -- 127.0.0.1
;; WHEN: Wed Jun  6 12:42:29 2007
;; MSG SIZE  sent: 38  rcvd: 92

Firewall

The firewall is a Cisco PIX. We have to map the outside IP adress to the inside address by making a static entry between the two security levels: outside and sandbox (our target webserver is in the sandbox security level). The second step is to allow http and https data to flow through this static, by modifying the outward facing access list.

cs-gate(config)# static (sandbox,outside) 192.31.89.11 172.21.0.11 netmask 255.255.255.255 0 0
cs-gate(config)# show static
static (public,outside) 192.31.89.3 172.18.0.2 netmask 255.255.255.255 0 0 
static (sandbox,outside) 192.31.89.7 172.21.0.7 netmask 255.255.255.255 0 0 
static (sandbox,outside) 192.31.89.11 172.21.0.11 netmask 255$
cs-gate(config)# access-list acl_out permit tcp any host 192.31.89.11 eq www
cs-gate(config)# access-list acl_out permit tcp any host 192.31.89.11 eq https
cs-gate(config)# show access-list
access-list acl_out; 15 elements
access-list acl_out permit icmp any any (hitcnt=1235348) 
access-list acl_out permit tcp any host 192.31.89.2 eq ssh (hitcnt=281501) 
access-list acl_out permit tcp any host 192.31.89.3 eq www (hitcnt=4889353) 
access-list acl_out permit tcp any host 192.31.89.3 eq domain (hitcnt=230909) 
access-list acl_out permit udp any host 192.31.89.3 eq domain (hitcnt=6136272) 
access-list acl_out permit tcp any host 192.31.89.5 eq ssh (hitcnt=166444) 
access-list acl_out permit tcp any host 192.31.89.5 eq smtp (hitcnt=181126) 
access-list acl_out permit tcp any host 192.31.89.2 eq smtp (hitcnt=82548) 
access-list acl_out permit tcp any host 192.31.89.7 eq www (hitcnt=228970) 
access-list acl_out permit tcp any host 192.31.89.6 eq ssh (hitcnt=198243) 
access-list acl_out permit tcp any host 192.31.89.6 eq smtp (hitcnt=144) 
access-list acl_out permit tcp any host 192.31.89.9 eq smtp (hitcnt=49264) 
access-list acl_out permit tcp any host 192.31.89.7 eq https (hitcnt=39) 
access-list acl_out permit tcp any host 192.31.89.11 eq www (hitcnt=0) 
access-list acl_out permit tcp any host 192.31.89.11 eq https (hitcnt=0) 
access-list acl_pub; 22 elements
cs-gate(config)# exit
cs-gate# write mem
Building configuration...
Cryptochecksum: 462369d9 0717b743 19bf28ba 75c3462d 
[OK]

Now to test the firewall configuration by trying to contact the server using a raw telnet and checking that the hit count for the access-list rule increments.

[burt@sherman Csc598.073]$ telnet 192.31.89.11 80
Trying 192.31.89.11...

cs-gate# show access-list
access-list acl_out; 15 elements
access-list acl_out permit icmp any any (hitcnt=1235350) 
access-list acl_out permit tcp any host 192.31.89.2 eq ssh (hitcnt=281501) 
access-list acl_out permit tcp any host 192.31.89.3 eq www (hitcnt=4889385) 
access-list acl_out permit tcp any host 192.31.89.3 eq domain (hitcnt=230909) 
access-list acl_out permit udp any host 192.31.89.3 eq domain (hitcnt=6136294) 
access-list acl_out permit tcp any host 192.31.89.5 eq ssh (hitcnt=166444) 
access-list acl_out permit tcp any host 192.31.89.5 eq smtp (hitcnt=181126) 
access-list acl_out permit tcp any host 192.31.89.2 eq smtp (hitcnt=82549) 
access-list acl_out permit tcp any host 192.31.89.7 eq www (hitcnt=228971) 
access-list acl_out permit tcp any host 192.31.89.6 eq ssh (hitcnt=198243) 
access-list acl_out permit tcp any host 192.31.89.6 eq smtp (hitcnt=144) 
access-list acl_out permit tcp any host 192.31.89.9 eq smtp (hitcnt=49264) 
access-list acl_out permit tcp any host 192.31.89.7 eq https (hitcnt=39) 
access-list acl_out permit tcp any host 192.31.89.11 eq www (hitcnt=1) 
access-list acl_out permit tcp any host 192.31.89.11 eq https (hitcnt=0) 
access-list acl_pub; 22 elements

IP configuration on web server

We add the new IP address to the network interface of the webserver. This is going to be specific to the version of Unix you are using. We are using FreeBSD. The following is added to /etc/rc.conf:

defaultrouter="172.21.0.1"
hostname="grant.cs.miami.edu"
ifconfig_fxp0="inet 172.21.0.7  netmask 255.255.0.0"
ifconfig_fxp0_alias0="inet 172.21.0.11  netmask 255.255.0.0"

And we restart networking using /etc/rc.d/netif restart. We check the configuration:

burt@grant$ ifconfig
fxp0: flags=8843 mtu 1500
        options=8
        inet6 fe80::2d0:b7ff:fee8:c3b5%fxp0 prefixlen 64 scopeid 0x1 
        inet 172.21.0.7 netmask 0xffff0000 broadcast 172.21.255.255
        inet 172.21.0.11 netmask 0xffff0000 broadcast 172.21.255.255
        ether 00:d0:b7:e8:c3:b5
        media: Ethernet autoselect (100baseTX )
        status: active

burt@grant$ telnet 172.21.0.11 80
Trying 172.21.0.11...
Connected to 172.21.0.11.
Escape character is '^]'.
GET / HTTP/1.1
Host: web.cs.miami.edu

HTTP/1.1 200 OK
Date: Wed, 06 Jun 2007 17:13:25 GMT
Server: Apache/2.2.0 (FreeBSD) mod_ssl/2.2.0 OpenSSL/0.9.7e DAV/2 PHP/5.1.4
Last-Modified: Tue, 01 Aug 2006 05:14:59 GMT
ETag: "10b084b-313-dc313ac0"
Accept-Ranges: bytes
Content-Length: 787
Content-Type: text/html

... [ page content here ] ...

Virtual Host: Apache configuration.

At this point we have a webserver at the IP address of di.metri.us, and the firewall will allow connections. Now we configure Apache. We have to tell Apache which data directory to use for connections at the di.metri.us address. Before this configuration step, Apache will return the main pages. There are two types of virtual hosting that can be configured: Name and IP address. We are using both on our server. Name-based means that the same IP address is used for multiple sites. The browser will always specify to the server, as part of the request, which site it is interested in. This method cannot be used for SSL, since certificate delivery does not depend on http or the browser, it depends on the IP address. So multiple certificates require multiple IP addresses. Here is the configuration:

NameVirtualHost 172.21.0.7:80

<VirtualHost 172.21.0.11:80>
   ServerName di.metri.us
   ServerAdmin burt@cs.miami.edu
   DocumentRoot "/home/burt/public_html/dimetrius"
</VirtualHost>

<VirtualHost 172.21.0.7:80>
    ServerName web.cs.miami.edu
    ServerAdmin burt@cs.miami.edu
    DocumentRoot "/usr/local/www/apache22/data"
</VirtualHost>

<VirtualHost 172.21.0.7:80>
    ServerName wiki.cs.miami.edu
    ServerAdmin burt@cs.miami.edu
    DocumentRoot "/usr/local/www/apache22/data"
#  ServerAlias x y z
    ErrorLog /var/log/httpd-wiki-error.log
    CustomLog /var/log/httpd-wiki-common.log common
    RedirectMatch ^/$ /pages/
    Alias /pages/ "/usr/local/www/data/dokuwiki/"
</VirtualHost>

<VirtualHost 172.21.0.7:80>
   ServerName psy.metri.us
   ServerAdmin burt@cs.miami.edu
   DocumentRoot "/home/burt/public_html/pmk/htdocs"
</VirtualHost>

We check it, and it works.