PXE-INSTALLATION-SERVER FOR REDHAT LINUX

Malte Eismann

Abstract:

Server for the installation of RedHat-Linux ( 9 / Enterprise 3) 


Contents

1 Consideration

1.1 is-analysis

At the moment of writing this tutorial, all servers in the ISC get installed from an FTP-server. The needed medias for this are: a boot CD-Rom, a floppy with ks.cfg-configfile and the FTP-server with the (updated) RPM-packages for the installation. The server to be installed (in the following referred to as client) is booted from the CD-Rom. The kickstartfile, ks.cfg, gets read from the floppy, the client then installs itself from the updated RPM-resources from the FTP-server. To accomplish this task, a local admin must access the client several times to put in and remove installation-medias (take out the CD to prevent from loop-installing).

1.2 target-analysis

Afterwards a client should be installed by using its pre-execution-environment. The client should connect automatically on the initial boot to the installationserver and find the ks.cfg to install itself automagically. On the installationserver, there should be a web-interface to enter the correct client-relevant information (IP's, DNS etc.), write the ks.cfg to the correct place on the harddisk, and restart DHCPd after committing changes in dhcpd.conf (MAC).

2 Analysis

2.1 Question: What about...

2.1.1 the configfile ks.cfg

The ks.cfg contains all parameters beeing relevant to the installation, which normally get prompted to the user during installation. For example, there is a section about the partitioning of the harddisk, or the list of packages to be installed. Furthermore, it is possible to involve scripts that get accomplished before or after the installation finishes. If the ks.cfg is created with the webinterface, the client installs automagically; no further accessing of informations or interaction is needed. It is required to take care of the layout of ks.cfg:

A typical way to use the pre-installation script is a backup of partitions that get overwritten by the installation. In a postinstallationscript you can i.e. create users, remove packages like kudzu etc. in the newly installed system.

In the appendix you will find an example, further information can be found on the RedHat website: http://www.redhat.com/docs/manuals/linux/RHL-9-Manual/custom-guide/s1-kickstart2-file.html.

2.1.2 the pre-execution-environment

PXE is a special boot-image for network-interface-cards (NIC). The software on the ROM of the NIC follows a standard and is not projectrelated, i.e. the software Etherboot for thinclients. The linux-support for PXE comes from the syslinux-project (a bootloader) and PXElinux. Since the existence of a PXE-compatible NIC, it gets very easy to install/boot a client via the network. A good reference for further research can be found in the etherboot-developer-manual http://etherboot.sourceforge.net/doc/html/devman/extension.html.

2.2 overview of different kickstart-variants

2.2.1 kickstarting with CD/DVD and floppy

In this example, the client needs a distribution-install-CD/DVD and a floppy with the ks.cfg on it. It gets booted from the CD/DVD, reads the ks.cfg on the floppy and installs itself without prompting the admin.

After installing, the admin is required to:

2.2.2 kickstarting with floppy and FTP/NFS-server

With this method, the client boots from a floppy, finds the ks.cfg on the first floppy, and installs pre-updated packages from the central FTP- or NFS-server. The RedHat online FTP-server, ftp.redhat.com, can also be used for this procedure. Three floppys are required:

2.2.3 kickstarting with PXE-boot

Utilizing this technique, the client boots from its onboard boot-PROM, located on the NIC. There is a minimalistic system intended to open up a connection to a DHCPd-server. The DHCPd-server informs the client about its IP-address and the name of the kernelimage to boot next. Via NFS, the client receives the ramdisc and the kernel. The kernelimage contains the drivers for mass storage controllers (SCSI/RAID) and NIC's. Furthermore, in the NFS-share there is the ks.cfg for the client. It is named after the IP-address of the client, not to confuse other installations running at the same time.

2.2.4 conclusion

In many circumstances, the installations of a server do not require the complexity of a PXE-installation. Keeping in mind that here, in the ISC in Berlin, new Linux-servers are setup everyday, it is definitely worth adapting this technique. Taking less than ten minutes to install, it saves approximately one man-hour per installation. To assume we have one installation a day, means the reduction of up to 365 man-hours a year, or 45 workingdays for one admin. Therefore, time consumption is reduced by 1.5 months per ISC a year.

3 Execution

3.1 testing environment

There are two Rennix-servers (RAID1/1Ghz Intel-CPU/two onboard NIC's 100Mbit/PXE-bootable) in the 19'' rack in the testing laboratory of the ISC. The two machines are wired with a twisted-pair crossover cable. Accessibility is not limited to local console, but can be SSH'ed from the administrative LAN. Furthermore, I connected a screen and keyboard to the servers, to monitor live-running logfiles. Internet-access is directed through the second NIC of the installation-server which owns a private IP and can reach the proxyserver located in Frankfurt.
testumgebung.png

3.2 comissioning the installation-server

I installed the server with the help of three boot-floppys from the actual sources found on the online RedHat FTP-server, utilizing a preconfigured ks.cfg with minimum-packet-configuration. The partitions are setup in the following manner: /, /swap /boot and /data. After rebooting the server, I input values in '/etc/resolv.conf', and mirrored the installation-rpm's from the RedHat FTP-server with ''Ncftp'' onto '/data'.

3.3 implementing the DHCPd-server

'rpm -ivh /data/RedHat/dhcp-3.0' installed the DHCPd-server.

The config-file '/etc/dhcpd.conf' was configured to the known values, you will find the complete dhcpd.conf in the appendix.

3.4 implementing FTP-server

'rpm -ivh /data/pub/RedHat/vsftpd' installs the RedHat-trusted FTP-server ''VsFTPd''. By giving the option 'chroot_local_users=yes' in '/etc/vsftp/vsftpd.conf', I obtain the required security to use that FTP-server in the companies-environment. The chroot creates a restriction for the users so they cannot changedir to any other location but the one mentioned in '/etc/vsftpd.conf'. The anonymous access points to '/var/ftp/'. I created a new directory 'pub/' and mounted the '/data'-partition there (readonly!), to make the data accessible via ftp://. An entry in '/etc/fstab' saves this mount for further reboots. More information can be found in the appendix (fstab/vsftpd.conf) or on the website of the VsFTPd-project http://vsftpd.beasts.org/.

3.5 NFS-share for ks.cfg

The next step is to share the ks.cfg to the client. The server receives a mount-request from a client, checks the contents of '/etc/exports' and compares the IP-address/name. The values in '/etc/exports' must be locked securely, to prevent someone else except the installing client to read the ks.cfg. For installations we are using a special range of IP-addresses that get distributed by the DHCPd for (earlier configured) MAC-adresses. Refer to the exports-file in the appendix for further information.

3.6 implementing the TFTP-server

PXE utilizes the TFTP-protocol. Therefore, we need a TFTP-server running on the installation-server that is distributing the bootloader for the PXE-installation. Because users cannot be authenticated, the security of the trivial file transfer protocol is insufficient and for this reason, we offer only the initrd.img and the kernel during the client-installation. By typing the command 'rpm -ivh /data/RedHat/tftp-server-0.32-4', the TFTP-server gets installed. In '/etc/xinetd.d/tftp', we configured 'disable=no', so Xinetd is answering incoming requests and starts up the TFTP-server. The TFTP-share is also configured here: 'server args = -s /tftpboot'. See the appendix.

3.7 offering a bootloader for PXE

To load the kernel via PXE, we need to acquire a bootloader. PXE is capable of loading up to 64 KB (see RFC). A good base to work on is the Syslinux-project of H. Peter Advin.

Let's sum things up: the bootloader gets loaded to load the kernel, ok. The presence of a configfile for the bootloader decides what to boot next, that means if the client is installed, or the local system on the harddisc is booted.

In '/tftpboot/', I placed the bootloader 'pxelinux.0'. In '/tftpboot/pxelinux.cfg/' the 'pxelinux.0' searches for its configfile. In order to install multiple clients at the same time, the bootloader-configfile gets assigned to the IP-address of the client to be installed. Therefore PXELINUX searches for the configfile for a client in the following way:

  1. primary target is the clients' IP-address in 'upper case hexadecimal' , i.e. 192.168.1.1 => C0A80101
  2. if the filename is not found accordingly, the client removes a hex-digit and tries again. Here is an example of the procedure:
hex-digit.png

The default bootloader-config is configured to boot the client from its local harddisc. With H.P. Anvins' program ''gethostip'' its a pleasure to change IP-addresses in hex-digits. The script can be found in the appendix, further information can be obtained from the Syslinux-project site http://syslinux.zytor.com/.

3.8 keeping the installationmedia up-to-date

Every installation is dependable on the current versions of the installation-sources. To have the most actual sources, I mirrored the complete RedHat-server to /data/ (see also 3.1). To keep up with the updates offered by RedHat I incorporated a program called ''Mirror'', supported by a daily cronjob. It downloads new RPM's, sorts old ones out, puts new ones in the installation-tree on the FTP-server after RPM-GPG-key checking.

Placing new ones automatically in, and meanwhile keeping the old ones, makes a good archive for the ISC. Customers can find older pakages fitting their relatively old distribution, and therefore making their applications run properly.

For the installation, the RedHat installerprogram ''Anaconda'' needs an updated hdlist (keeping info about RPM-packets), because we updated packets, we need to update the hdlist as well. To accomplish this task, I need to install ''Anaconda-runtime''.

You will find the configfile for ''Mirror'' and the update.sh script in the appendix.

4 where to keep your eye on

4.1 the phenomenon of loop-installing

Because the client is configured to boot via network, it will

To bypass this problem, the bootloader configfile (we placed it in '/tftpboot/pxelinux.cfg/') must be taken away; only then the default bootloader configfile is used to boot the client from local hdd (see 3.7).

The sense of the installation-server is to automagically install clients, so we don't want to sit in front of the client and wait until it reboots after installation. For this, I employed a daemon called 'PXEconfigchanger.pl'. It is watching the messages-logfile in realtime and looks out for a string 'kickstart_end'.

The last action a client executes before rebooting, is to search the server via 'tftp://' for a packet called 'kickstart_end'. There is no so-called packet (and this is intended), the logfile-entry is done in conjunction with the clients IP-address, and the 'PXEconfigchanger.pl' is removing the bootloader-config from '/tftpboot/pxelinux.cfg/', carefully checking the hex-digit of the IP-address it receives from the logfile-entry.

4.2 the chaos of ks.cfg

The kickstart-configfile ks.cfg may give you a hard time. It is absolutely necessary to keep some things in mind when writing a ks.cfg for PXE-installations. Informations about partitioning must be entered in the appropriate section, otherwise the user is prompted for action and installation is no longer fully automated. The NIC for installing must also be mentioned here. Include the packet 'TFTP-client' in the packet-collection because at the end of the installation the client needs to ask for a packet 'kickstart_end' via 'tftp://' (see 4.1).

5 Logging

5.1 ...of the installations

The installations are getting logged by the FTP-server. In '/var/log/vsftpd.log' the admin can see which packets have been installed. Involved in logrotate, the logs are weekly rotated, compressed and stored for a number of weeks (See the 'logrotate.conf' in the appendix). On the clientside, you'll find the file '/root/install.log' documenting which packets were installed during installation. If requested, this can be transfered into a database on the installation-server (this feature is not yet implemented).

5.2 ...of packet-updates on the server

For this merthod, there is a logfile written by ''Mirror'', watch out for it at '/data/updates/9/i386/' (this is one location). The meaning of placing it there, is to give future users the possibility to see which packages have been updated in the past. An example can be found in the appendix.

5.3 ...of the FTP-server

As mentioned in 5.1, client-access to the FTP-server is logged. Lets assume, the  customers of the company use this FTP-server for updating their machines. Following murphy's law, there is always something going wrong. Here you have the possibility, of searching which stations have (post-)installed a package that is a troublemaker/security-issue in the actual configuration. Customers can be warned early before the breach of security takes place, when their configuration differs from realtime security-issues.

6 hardening the server

6.1 general questions

You need to decide how secure your server has to be, and how comfortable it's use should be.

In general: the more easy to use, the more easy to abuse.

The more secure I build the system, the more passwords I need to enter for getting relevant information. The implementations of security systems (like tripwire i.e.) would blast the amount of time reserved for this project. DoS-attacks can be driven on every system offering a service, internal attacks are always near.

I don't want to say this server is unsecure, but to use it we need to loosen the tightness of security.

I decided to place the server into the adminstration-LAN and moved it away from most of the known security-threats.

For further security, it is advisable to spread the services offered by one server at the moment to more servers in the future. If any of the services get compromised, the others will maintain functionality as result of beeing on separate machines. A redundant system is not designated in this project, but easy to implement when the hardware is available.

More about general security can be found here: http://www.tldp.org/LDP/solrhe/Securing-Optimizing-Linux-The-Ultimate-Solution-v2.0.pdf

6.2 multiple NIC's and networks

When using two NIC's in the server, it is possible to offer the installation-service to only one network (administration-LAN). The FTP-server for customers must be offered globaly, an internet access is also required for updating the installation-packages.

6.3 Firewall

I decided to implement 'shorewall' as a frontend to 'ip-tables'. By editing comfortable configfiles, the user gets an effective kernelbased packet-filter (a good tutorial can be found on www.shorewall.net).

The complete procedure of setting up the firewall would pollute this documentation, and is generally not the task here.

6.4 Users

For doing the maintenance and running the scripts I established a standard user account. This user account has no password, and no shell to logon. For example the 'update.sh'-script is running under this user. There are some users in RedHat that need to be removed after installation, these are: lp, news, sync, uucp, games, gopher, rpc, nscd and pcap.

6.5 removing unnecessary packages

Services and functions not required by the server must be deactivated or sometimes deinstalled immediately. RedHats minimal configuration installs packages that aren't needed in our setup, (i.e. sendmail).

A. Appendix

A..1 Configfiles

A..1.1 ks.cfg

A..1.2 dhcpd.conf


ddns-update-style none;

subnet 10.162.xxx.0

netmask 255.255.255.0

{

    option routers 10.162.xxx.xxx;

    option subnet-mask 255.255.255.0;

    option domain-name "workgroup";

    range 10.162.xxx.56 10.162.xxx.56;

    default-lease-time 21600;

    max-lease-time 43200;

    allow unknown-clients;

}

group

{

    default-lease-time 7200;

    max-lease-time 64800;

    host MALTE

        {

        hardware ethernet xx:30:6E:1C:BC:D9;

        fixed-address 10.162.xxx.56;

        next-server 10.162.xxx.55;

<>

<>        filename "0ACx640C";

        option root-path "initrd-taroon.img";

        }

}

A..1.3 vsftpd.conf


# This is vsftpd.conf

# maintained by Malte Eismann <malte@fuldastrasse.de>

anonymous_enable=YES

local_enable=YES

write_enable=YES

local_umask=022

#anon_upload_enable=YES

#anon_mkdir_write_enable=YES

dirmessage_enable=YES

xferlog_enable=YES

connect_from_port_20=YES

#chown_uploads=YES

#chown_username=whoever

#xferlog_file=/var/log/vsftpd.log

xferlog_std_format=YES

#idle_session_timeout=600

#data_connection_timeout=120

#nopriv_user=ftpsecure

#async_abor_enable=YES

#ascii_upload_enable=YES

#ascii_download_enable=YES

#ftpd_banner=Welcome to blah FTP service.

#deny_email_enable=YES

#banned_email_file=/etc/vsftpd.banned_emails

#chroot_list_enable=YES

#chroot_list_file=/etc/vsftpd.chroot_list

ls_recurse_enable=YES

pam_service_name=xxxxxx

userlist_enable=YES

#enable for standalone mode listen=YES

tcp_wrappers=NO chroot_local_user=YES

A..1.4 fstab


LABEL=/ / ext3 defaults 1 1

LABEL=/boot /boot ext3 defaults 1 2

LABEL=/data /data ext3 defaults 1 2

none /dev/pts devpts gid=5,mode=620 0 0

none /proc proc defaults 0 0

none /dev/shm tmpfs defaults 0 0

/dev/sda3 swap swap defaults 0 0

/dev/cdrom /mnt/cdrom udf,iso9660 noauto,owner,kudzu,ro 0 0

/dev/fd0 /mnt/floppy auto noauto,owner,kudzu 0 0

/data/ /var/ftp/pub/ ext3 ro,bind

A..1.5 /etc/exports


# /tftpboot/kickstart/ *(ro)

/tftpboot/kickstart/ks.cfg 10.162.xxx.56(ro)

#/tftpboot/kickstart/ks.cfg 10.162.xxx.55(ro,sync)

A..1.6 /etc/xinetd.d/tftp


service tftp

{

socket_type = dgram

protocol = udp

wait = yes

user = xxxxx

server = /usr/sbin/in.tftpd

server_args = -s /tftpboot -v

disable = no

per_source = 11

cps = 100 2

flags = IPv4

}

A..1.7 /etc/mirror.defaults


package=defaults

# The LOCAL hostname - if not the same as `hostname`

# (I advertise the name sunsite.org.uk but the machine is

# really swallow.sunsite.org.uk.)

hostname=praktikant-51.xxx.xxx.xxx.x.net

# Keep all local_dirs relative to here

local_dir=/data/

# The local_dir must exist FIRST

#local_dir_check=true

remote_password=superbaguss@gmx.de

mail_to=root

# Don't mirror file modes. Set all dirs/files to these

dir_mode=0755

file_mode=0444

# By defaults files are owned by root.zero

user=0

group=0

# Keep a log file in each updated directory

update_log=.mirror

# update_log=

# Don't overwrite my mirror log with the remote one.

# Don't pull back any of their mirror temporary files.

# nor any FSP or gopher files...

exclude_patt=(^|/)(\.mirror$|\.mirror\.log|core$|\.cap|\.in\..*\.$|MIRR OR\.LOG|#.*#|\.FSP|\.cache|\.zipped|\.notar|\.message|lost\+found/|Network Tras h Folder)|suky.mpe?g

# Do not to compress anything compress_patt= compress_prog=compress

# Don't compress information files, files that don't benifit from

# being compressed, files that tell ftpd, gopher, wais... to do things,

# the sources for compression programs...

# (Note this is the only regexp that is case insensitive.)

# z matches compress/pack/gzip, gz for gzip. (built into perl)

# taz/tgz is compressed or gzipped tar files

# arc, arj, lzh, zip and zoo are pc and/or amiga archives.

# sea are mac archives.

# vms used -z instead of .z. stupid vms.

# shk is multimedia? used on apple2s.

# rpm and deb are package formats used on RedHat and Debian Linux

#compress_excl+|-z(\d+)?$|\.tgz|_tgz|\.tar\.Z|\.tar\.gz|\.taz$|\.arc$|\. zip$|\.lzh$|\.zoo$|\.exe$|\.lha$|\.zom$|\.gif$|\.jpeg$|\.jpg$|\.mpeg$|\.au$|\.s hk$|rpm$|deb$|read.*me|index|info|faq|gzip|compress|(^|/)\.\.?$

# Don't delete own mirror log, .notar or .cache files (incl in subdirs)

# delete_excl=(^|/)\.(mirror|notar|cache)$

# Ignore any local readme and .mirror files local_ignore=README.doc.ic|(^|/)\.(mirror|notar)$

# Automatically delete local copies of files that the

# remote site has zapped

do_deletes=true

max_delete_files=50%

max_delete_dirs=50%

timeout=300 #failed_gets_excl=\:\ Permission denied\.$

package=RPMS

comment=RedHat9 RPMS

site=ftp.rrz.uni-koeln.de

remote_dir=redhat/linux/9/en/os/i386/RedHat/RPMS/

# Local_dir+ causes gnu to be appended to the default local_dir

# so making /public/gnu local_dir+updates/9/i386/

# exclude_patt+|^ListArchives/|^lost+found/|^scheme-7.0/|^\.history

# I tend to only keep the latest couple of versions of things

# this stops mirror from retrieving the older versions I've removed

# max_days=100

do_deletes=false

# algorithm=1

passive_ftp=true

A..1.8 /etc/logrotate.conf


# see "man logrotate" for details

# rotate log files weekly

weekly

# keep 4 weeks worth of backlogs

rotate 4

# create new (empty) log files after rotating old ones

create

# uncomment this if you want your log files compressed

compress

# RPM packages drop log rotation information into this directory

include /etc/logrotate.d

# no packages own wtmp - we'll rotate them here

/var/log/wtmp

{

monthly

create 0664 root utmp

rotate 1

}

A..2 Bootloaders and Scripts

A..2.1 Installation-PXE-Bootloader-config


label linux

kernel vmlinuz

append initrd=initrd.img ks=nfs:10.162.xxx.55:/tftpboot/kickstart/ks.cfg ksdevice=eth0

A..2.2 default PXE-Bootloader-config


default linux

label linux

localboot 0

A..2.3 PXEcfg_changer.pl


#!/usr/bin/perl -w

#

# Author: Alf Wachsmann, <alfw@slac.stanford.edu>, August 15, 2002

# configured for PEEEEP by malte eismann, <malte@fuldastrasse.de>, 12.11.2003

# Name of script: PXEcfg_changer.pl

# Version 2.0

# usage:

# $path/PXEcfg_changer.pl

use strict;

use vars qw($VERSION $PRG $PATH);

my $debug = 0;

my $verbose = 1;

my $file = '/var/log/messages';

$VERSION = '2.0';

$PRG = $0;

$PRG =~ s{(.*/)}{};

$PATH = $1;

my $PXEtftpPATH = "/tftpboot/pxelinux.cfg";

my $PXEdefault = $PXEtftpPATH."/install";

die("Directory '$PXEtftpPATH' does not exist!") unless (-d $PXEtftpPATH);

die("File '$PXEdefault' does not exist!") unless (-f $PXEdefault);

my $hexIP_prefix = uc(sprintf("%02x", 10).sprintf("%02x", 162));

my $pid = open(INPUT, "/usr/bin/tail -n 1 -f $file |");

$SIG{INT} = $SIG{TERM} = sub { system("kill $pid") };

while (<INPUT>) {

# this regexp matches output from tftpd that looks like this:

# tftpd[9960]:RRQ from 10.162.xxx.56 filename kickstart_end

next unless $_ =~ /tftpd\[\d+\]: RRQ from 10\.162\.(\d+)\.(\d+) filename kickstart_end/;

my $hexIP = uc(sprintf("%02x", $1).sprintf("%02x", $2));

print "unlink($PXEtftpPATH/$hexIP_prefix$hexIP)\n" if $debug|$verbose;

unlink($PXEtftpPATH."/".$hexIP_prefix.$hexIP) unless $debug;

}

A..2.4 gethostip.c


#ident "$Id: projekt.lyx,v 1.1.1.1 2004/01/14 11:28:42 malte Exp $"

/* ------------------------------------ *

*

* Copyright 2001 H. Peter Anvin - All Rights Reserved

*

* 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, Inc., 675 Mass Ave, Cambridge MA 02139,

* USA; either version 2 of the License, or (at your option) any later

* version; incorporated herein by reference.

*

* ------------------------------------ */

/*

* gethostip.c

*

* Small program to use gethostbyname() to print out a hostname in

* hex and/or dotted-quad notation

*/

#include <stdio.h>

#include <stdlib.h>

#include <netdb.h>

#include <sys/socket.h>

#include <unistd.h>

#include <sysexits.h>

#define _GNU_SOURCE /* For getopt_long */

#include <getopt.h>

const struct option options[] =

{

{ "hexadecimal", 0, NULL, 'x' },

{ "decimal", 0, NULL, 'd' },

{ "dotted-quad", 0, NULL, 'd' },

{ "full-output", 0, NULL, 'f' },

{ "name", 0, NULL, 'n' },

{ "help", 0, NULL, 'h' },

{ NULL, 0, NULL, 0 }

};

const char *program;

void usage(int exit_code)

{

fprintf(stderr, "Usage: %s [-dxnf] hostname/ip...\n", program);

exit(exit_code);

}

int main(int argc, char *argv[])

{

int opt;

int output = 0;

int i;

char *sep;

char dotquad[16];

int err = 0;

struct hostent *host;

program = argv[0];

while ( (opt = getopt_long(argc, argv, "dxfnh", options, NULL)) != -1 ) {

switch ( opt ) {

case 'd':

output |= 2; /* Decimal output */

break;

case 'x':

output |= 4; /* Hexadecimal output */

break;

case 'n':

output |= 1; /* Canonical name output */

break;

case 'f':

output = 7; /* Full output */

break;

case 'h':

usage(0);

break;

default:

usage(EX_USAGE);

break;

}

}

if ( optind == argc )

usage(EX_USAGE);

if ( output == 0 )

output = 7; /* Default output */

for ( i = optind ; i < argc ; i++ ) {

sep = "";

host = gethostbyname(argv[i]);

if ( !host ) {

herror(argv[i]);

err = 1;

continue;

}

if ( host->h_addrtype != AF_INET || host->h_length != 4 ) {

fprintf(stderr, "%s: No IPv4 address associated with name\n", argv[i]);

err = 1;

continue;

}

if ( output & 1 ) {

printf("%s%s", sep, host->h_name);

sep = " ";

}

if ( output & 2 ) {

sprintf(dotquad, "%u.%u.%u.%u",

((unsigned char *)host->h_addr)[0],

((unsigned char *)host->h_addr)[1],

((unsigned char *)host->h_addr)[2],

((unsigned char *)host->h_addr)[3]);

printf("%s%s", sep, dotquad);

sep = " ";

}

if ( output & 4 ) {

unsigned long addr =

(((unsigned char *)host->h_addr)[0] << 24UL) +

(((unsigned char *)host->h_addr)[1] << 16UL) +

(((unsigned char *)host->h_addr)[2] << 8UL) +

(((unsigned char *)host->h_addr)[3]);

printf("%s%08lX", sep, addr);

sep = " ";

}

putchar('\n');

}

return err;

}

A..2.5 update.sh


#!/bin/bash

umask 022

echo "mirrorin..."

/usr/bin/mirror

echo "merging..."

# merging

# the i386 part :-)

# The following will update rpms in a RedHat distribution found in $RPMDIR.

# The old rpms will be placed in $OLDDIR.

# The new rpms should be located in $UPDDIR.

# The new images are in $IMGDIR

# The images to be updated are in $OMGDIR

SYSTEMS="i386 i686"

REDHATS="9"

for RHVS in $REDHATS ; do

echo "working in $RHVS..."

for SYST in $SYSTEMS ; do

RHROOT=/data/RedHat${RHVS}

RPMDIR=${RHROOT}/RedHat/RPMS

UPDDIR=/data/updates/${RHVS}/${SYST}

OLDDIR=${RHROOT}/old_${SYST}

if [ ! -d $OLDDIR ] ; then

echo making directory $OLDDIR

mkdir $OLDDIR

fi

allow_null_glob_expansion=1

for rpm in `ls ${UPDDIR}/*.${SYST}.rpm` ; do

NAME=`rpm -queryformat "%{NAME}" -qp $rpm`

# echo "NAME: $NAME"

unset OLDNAME

for oldrpm in `ls ${RPMDIR}/${NAME}*.rpm` ; do

Q1=`rpm -queryformat "%{NAME}" -qp $oldrpm`

# echo "Q1: $Q1 = $NAME ?"

if [ `rpm -queryformat "%{NAME}" -qp $oldrpm` == "$NAME" ]; then

OLDNAME=$oldrpm;

# echo "send BREAK!!!!!"

break

fi

done

if [ -z "$OLDNAME" ]; then

echo $NAME is new

cp -pv $rpm $RPMDIR

else

if [ `basename $rpm` != `basename $OLDNAME` ]; then

mv $OLDNAME $OLDDIR

cp -pv $rpm $RPMDIR

fi

fi

done

done

echo generating hdlist...

echo "genhdlist for RedHat${RHVS}"

/usr/lib/anaconda-runtime/genhdlist -withnumbers -hdlist /data/RedHat${RHVS}/RedHat/base/hdlist /data/RedHat${RHVS}/ || echo "*** GENHDLIST FAILED ***"

done

A..3 Logfiles

A..3.1 extraction of /root/install.log


Installing 352 packages

-snip-

Installing glibc-common-2.3.2-11.9.

Installing hwdata-0.75-1.

Installing redhat-logos-1.1.12-1.

Installing setup-2.5.25-1.

Installing filesystem-2.2.1-3.

Installing basesystem-8.0-2.

Installing glibc-2.3.2-11.9.

Installing bzip2-libs-1.0.2-8.

Installing chkconfig-1.3.8-1.

Installing cracklib-2.7-21.

Installing db4-4.0.14-20.

Installing e2fsprogs-1.32-6.

Installing elfutils-libelf-0.76-3.

Installing expat-1.95.5-2.

Installing gdbm-1.8.0-20.

Installing glib-1.2.10-10.

Installing glib2-2.2.1-1.

Installing gmp-4.1.2-2.

Installing hdparm-5.2-4.

Installing iputils-20020927-2.

Installing libattr-2.2.0-1.

Installing libacl-2.2.3-1.

Installing libgcc-3.2.2-5.

Installing losetup-2.11y-9.

Installing mingetty-1.01-1.

Installing mktemp-1.5-18.

Installing mount-2.11y-9.

Installing net-tools-1.60-12.

Installing pcre-3.9-10.

Installing popt-1.8-0.69.

Installing setserial-2.17-12.

Installing shadow-utils-4.0.3-6.

Installing slang-1.4.5-16.

Installing newt-0.51.4-1.

Installing termcap-11.0.1-16.

Installing libtermcap-2.0.8-35.

Installing bash-2.05b-20.

Installing iproute-2.4.7-7.

Installing lvm-1.0.3-12.

Installing MAKEDEV-3.3.2-5.

Installing ncurses-5.3-4.

Installing lsof-4.63-4.

Installing mailcap-2.1.13-1.

Installing mailx-8.1.1-28.

Installing make-3.79.1-17.

Installing man-1.5k-6.

Installing man-pages-1.53-3.

Installing minicom-2.00.0-12.

Installing rdist-6.1.5-26.

Installing telnet-0.17-25.

Installing time-1.7-21.

Installing tmpwatch-2.8.4-5.

Installing traceroute-1.4a12-9.

Installing unix2dos-2.2-19.

Installing unzip-5.50-7.

Installing up2date-3.1.23-1.

Installing utempter-0.5.2-16.

Installing vconfig-1.6-2.

Installing vixie-cron-3.0.1-74.

Installing anacron-2.3-25.

Installing wget-1.8.2-9.

Installing wvdial-1.53-9.

Installing ypbind-1.11-4.

Installing yp-tools-2.7-5.

Installing zip-2.3-16.

Installing gdk-pixbuf-0.18.0-7.

Installing libungif-4.1.0-15.

Installing ImageMagick-5.4.7-10.

Installing w3m-0.3.2.2-5.

Installing libgnomeui-2.2.0.1-5.

Installing pygtk2-1.99.14-4.

Installing gnome-python2-canvas-1.99.14-5.

Installing pygtk2-libglade-1.99.14-4.

Installing redhat-config-keyboard-1.0.3-4.

Installing redhat-config-kickstart-2.3.6-4.

Installing redhat-config-language-1.0.4-1.

Installing redhat-config-packages-1.1.8-1.

Installing redhat-config-proc-0.21-1.

-snap-

A..3.2 extraction of ''mirror''-logfile


-snip-

mirroring RPMS (kickstartserver:/pub/RedHat/RPMS) completed successfully @ 10 Dec 103 13:15

Got mutt-1.5.5.1-1.i386.rpm 1323803 0

mirroring RPMS (kickstartserver:/pub/RedHat/RPMS) completed successfully @ 10 Dec 103 13:58

mirroring RPMS (ftp.rrz.uni-koeln.de:redhat/linux/9/en/os/i386/RedHat/RPMS/)

completed successfully @ 10 Dec 103 14:34

Got tree-1.2-22.i386.rpm 14732 0

-snap-

 




Malte Eismann 2004-03-02 http://www.malte-eismann.de