#!/bin/zsh # # ven mai 16 12:08:49 CEST 2008 # # Testcase: # Un PC avec Windows et linux: une partition NTFS, # optionnellement une seconde NTFS, une partition SWAP # et une seule partition Linux. L'ordre importe peu, puisque # les numéros des partitions sont cherchés (sauf peut # etre pour la NTFS1 qui doit etre la premiere car windows bootera pas # Un repertoire par profil de machine, avec un profil par defaut. # Attention: la partition NTFS doit avoir la meme taille que celle qui a été ghosté: ici 22000Mo # # TODO: savoir faire un timeout sur le select # TODO: savoir demarrer le serveur multicast sur le serveur # TODO: joindre le linux au domaine # ###################################### # Senario où tout est fait: # Montage du serveur NFS # partition disque # copie mbr # mkfs de l'ext3 # copie windows # copie linux # changement nom sysprep # modifs UUID partition linux ########################################################################## # serveur NFS ou sont les fichiers NFSSERVER=oie # partage sur le serveur nfs DATASERVER=/data/ghosts #l'endroit où on va monter nfs en local LOCALDATA=/mnt/serveur #le montage local de linux pour modifs LOCALLINUX=/mnt/linux #le montage local de windows pour modifs WINDOWS1=/mnt/windows1 #ports pour le multicast (port et port+1 sont utilisé) #cas du serveur attendant 16 clients PORTLINUX16=19741 PORTNTFS16=19751 MYTMPFILE=/tmp/toto$$ #Commande a lancer coté serveur: # cat master-sda1.img.gz_a* |udp-sender --portbase 19741 --ttl 1 --min-clients 16 --max-wait 240 # Renvoie les partition d'un type donné en parametre # Param $1: 83 (Linux) 82 (Swap) ou 7 (NTFS) getlistpartochfromtype() { LIST=$(/sbin/sfdisk -d /dev/sda | sed -e 's/ //g' |grep "Id=$1" |cut -f1 -d':') echo $LIST } #Renvoie le nb de parttion d'un type donné en parametre # Param $1: 83 (Linux) 82 (Swap) ou 7 (NTFS) getnbpartochfromtype() { NB=$(/sbin/sfdisk -d /dev/sda | sed -e 's/ //g' |grep -c "Id=$1") echo $NB } # Recherche une partition # Param $1: 83 (Linux) 82 (Swap) ou 7 (NTFS) # renvoie /dev/sdx (ne renvoie que la premiere sinon utiliser la liste et |head tail) lookforpartoch() { echo $(getlistpartochfromtype $1|cut -f1 -d' ') } # Restaure une partition sauvee # Utilise: $DEVDISK $LOCALDATA $PROFIL # Rem: le fichier $LOCALDATA/$PROFIL/master-sfdisk.dump et $LOCALDATA/$PROFIL/master.mbr doivent exister partition() { /sbin/sfdisk -q $DEVDISK < $LOCALDATA/$PROFIL/master-sfdisk.dump dd if=$LOCALDATA/$PROFIL/master.mbr of=$DEVDISK >/dev/null 2>/dev/null } # Prend un param qui est la partition a formater formateNTFS() { if [ $# -eq 1 ]; then mkfs.ntfs -f $1 fi } # Prend un param qui est la partition a formater formateExt3() { if [ $# -eq 1 ]; then mkfs.ext3 -q $1 tune2fs -i 0 -m 0 $1 >/dev/null 2>/dev/null fi } # Premier parametre: la partition a ecraser # Second parametre: le port copieNTFS() { if [ "$WHATTODO" -eq "1" ]; then udp-receiver --portbase $2 |gunzip | ntfsclone -r -O $1 - else cat $LOCALDATA/$PROFIL/master-sda1.img.gz_* | gunzip | ntfsclone -r -O $DEVNTFS1 - fi } # Premier parametre: la partition a ecraser # Second parametre: le port copieLinux() { if [ "$WHATTODO" -eq "1" ]; then udp-receiver --portbase $2 |gunzip |tar xf - -C $1 else cat $LOCALDATA/$PROFIL/master-sda7.img.gz_* | gunzip |tar xf - -C $LOCALLINUX fi } # Prepare le sysprep pour la partition windows # On ajoute dans le fichier sysprep.inf, le nom de l'ordinateur suffixé d'un W (pour differencier des nomsm sous linux) # XRESO/YRESO ne semblent plus preis en compte # Utilise: $DEVNTFS1 $WINDOWS1 $MONHOSTSHORT $XRESO $YRESO fixeSysprep() { mount.ntfs-3g $DEVNTFS1 $WINDOWS1 cat $WINDOWS1/SYSPREP/sysprep.inf | \ sed -e "s/OrgName=URS/OrgName=URS\n ComputerName=${MONHOSTSHORT}W/" | \ sed -e "s/Xresolution=1024/Xresolution=$XRESO/" | \ sed -e "s/Yresolution=768/Yresolution=$YRESO/" \ > $WINDOWS1/SYSPREP/sysprep.inf.new mv $WINDOWS1/SYSPREP/sysprep.inf.new $WINDOWS1/SYSPREP/sysprep.inf } # Prepare le boot loader # ajuste l'endroit où se trouve les stage 1.5 et 2 de grub # TODO: faire le subs en une fois ... # Utilise: $OLDUUID $UUIDMDV $LOCALLINUX $DEVSWAP $DISQUEBOOTGRUB fixegrub() { #cp -f $LOCALLINUX/boot/grub/menu.lst $LOCALLINUX/boot/grub/menu.old sed -e "s/$OLDUUID/$UUIDMDV/" $LOCALLINUX/boot/grub/menu.lst > $LOCALLINUX/boot/grub/menu.lst.new mv -f $LOCALLINUX/boot/grub/menu.lst.new $LOCALLINUX/boot/grub/menu.lst sed -e "s:resume=/dev/....:resume=$DEVSWAP:" $LOCALLINUX/boot/grub/menu.lst > $LOCALLINUX/boot/grub/menu.lst.new mv $LOCALLINUX/boot/grub/menu.lst.new $LOCALLINUX/boot/grub/menu.lst sed -e "s:kernel (hd.,.):kernel $DISQUEBOOTGRUB:" $LOCALLINUX/boot/grub/menu.lst > $LOCALLINUX/boot/grub/menu.lst.new mv $LOCALLINUX/boot/grub/menu.lst.new $LOCALLINUX/boot/grub/menu.lst sed -e "s:initrd (hd.,.):initrd $DISQUEBOOTGRUB:" $LOCALLINUX/boot/grub/menu.lst > $LOCALLINUX/boot/grub/menu.lst.new mv $LOCALLINUX/boot/grub/menu.lst.new $LOCALLINUX/boot/grub/menu.lst sed -e "s:gfxmenu (hd.,.):gfxmenu $DISQUEBOOTGRUB:" $LOCALLINUX/boot/grub/menu.lst > $LOCALLINUX/boot/grub/menu.lst.new mv $LOCALLINUX/boot/grub/menu.lst.new $LOCALLINUX/boot/grub/menu.lst mount -t proc none $LOCALLINUX/proc mount -o bind /dev $LOCALLINUX/dev echo " echo \"find /boot/grub/stage1 root $DISQUEBOOTGRUB setup (hd0) quit \" | grub --batch " >> $LOCALLINUX/root/fixegrub.sh chmod +x $LOCALLINUX/root/fixegrub.sh chroot $LOCALLINUX /root/fixegrub.sh rm $LOCALLINUX/root/fixegrub.sh umount $LOCALLINUX/proc umount $LOCALLINUX/dev } # Fixe la table de montade des disques (Linux) # # TODO: peut etre un peu trop perso ? # Utilise: $UUIDMDV $UUIDSWAP $LOCALLINUX fixefstab() { echo " UUID=$UUIDMDV / ext3 relatime 1 1 none /proc proc defaults 0 0 UUID=$UUIDSWAP swap swap defaults 0 0 oie:/data/home /home nfs defaults 0 0 " >$LOCALLINUX/etc/fstab } # Fixe le clonage (Linux) # le fichier qui est effacé ici contient la MAC de la carte reseau. Au reboot suivant, # la nouvelle interface serait nommé eth1 si on n'effacait pas ce fichier. # Utilise $LOCALLINUX fixelinux(){ rm -f $LOCALLINUX/etc/udev/rules.d/61-net_confi* echo "timeout 15;" > $LOCALLINUX/etc/dhclient-eth0.conf #pb carte reseau qui recoie pas les paquets tout de suite } # Renvoie une valeur qui decide de ce qu'on va faire comme type d'install # Le RENVOIE SE FAIT DANS WHATTODO causeavecmoi() { clear PS3="Prend ton marteau pour donner ton choix... " select word in "Toute la salle" "Un seul poste, Complet" "Juste Windows" "Juste Linux" do case $REPLY in 1|2|3|4) WHATTODO=$REPLY; break;; *) echo "Enleve tes mouffles....";; esac done } guesspartoches() { DEVDISK=/dev/sda # On est toujours dans ce cas, de nos jours ? echo $(getlistpartochfromtype 83) | grep -q " " if [ "$?" -eq "0" ]; then echo "Plusieurs partitions linux, cas non prévu, pressez pour rebooter"; read toto; reboot fi NBNTFS=$(getnbpartochfromtype 7) # On regarde combien on a de NTFS sur le disque primaire DEVNTFS1=$(lookforpartoch 7) # On prend le premier disque DEVNTFS2= DEVSWAP=$(lookforpartoch 82) DEVMDV=$(lookforpartoch 83) LENB=$(echo $DEVMDV|rev |cut -b1 |rev) LENB=$(($LENB - 1)) DISQUEBOOTGRUB="(hd0,$LENB)" #Ce qui sevra etre changé dans le boot loader echo $(getlistpartochfromtype 7) | grep -q " " if [ "$?" -eq "0" ]; then DEVNTFS2=$(getlistpartochfromtype 7 |cut -f2 -d' ') fi if [ "toto$DEVSWAP" == "toto" -a \( "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "4" \) ]; then echo "Pas de swap trouvé, cas non prévu, pressez pour rebooter"; read toto; reboot fi if [ "toto$DEVMDV" == "toto" -a \( "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "4" \) ]; then echo "Pas de partition linux trouvé, cas non prévu, pressez pour rebooter"; read toto; reboot fi if [ "toto$DEVNTFS1" == "toto" -a \( "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "3" \) ]; then echo "Pas de partition NTFS trouvé, cas non prévu, pressez pour rebooter"; read toto; reboot fi } printpartoches() { echo "Disque: $DEVDISK" echo "Nb de NTFS trouvées: $NBNTFS" echo "NTFS1 : $DEVNTFS1" echo "NTFS2 : $DEVNTFS2" echo "Swap : $DEVSWAP" echo "Linux : $DEVMDV" echo "Bootloader: $DISQUEBOOTGRUB" } ########################################################################## ########################################################################## echo "C'est parti mon coco...." #on met a l'heure sinon caca dans le tar ntpdate ntp.u-strasbg.fr mkdir $LOCALDATA mkdir $WINDOWS1 mkdir $LOCALLINUX /etc/init.d/portmap start mount $NFSSERVER:$DATASERVER $LOCALDATA # identification du PC MONIP=$(/sbin/ifconfig eth0 |grep "inet addr" |cut -f2 -d':' |tr -s " "|cut -f1 -d' ') MONHOSTFQDN=$(host $MONIP|cut -f5 -d' '|cut -f-3 -d'.') host $MONIP >/dev/null || (MONHOSTFQDN=none.u-strasbg.fr && echo "Attention pas de reverse pour cette ip..."; sleep 60; reboot) MONHOSTSHORT=$(echo $MONHOSTFQDN | cut -f1 -d'.') hostname $MONHOSTFQDN WHATTODO=999 PROFIL=7800-80 #Ce profil est adapté pour une reinstall linux ou windows causeavecmoi # va initialiser WHATTODO echo "le choix: $WHATTODO" if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" ]; then PROFIL=7800-80 fi #TODO: changer pour trouver le bon profil suivant le bon PC # on a l'IP donc ca devrait etre easy # PROFIL=7800-80 echo "...on cherche les partitions...." guesspartoches printpartoches # En niveau 1 ou 2 on repartitionne, sinon pas. if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" ]; then echo "...fdisk/mbr...."; partition fi; if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "3" ]; then echo "...ntfsclone...."; formateNTFS $DEVNTFS1; copieNTFS $DEVNTFS1 $PORTNTFS16 if [ $NBNTFS -eq 2 ]; then formateNTFS $DEVNTFS2 ; fi ; fi if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "4" ]; then echo "...mkskap, mkfs, tune...."; mkswap $DEVSWAP; formateExt3 $DEVMDV echo "...untar...." ; mount $DEVMDV $LOCALLINUX ; copieLinux $LOCALLINUX $PORTLINUX16 fi if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "4" ]; then echo "...calcul des uuid...." # on s'occupe des UUID: on cherche le nouveau et l'ancien dans le fichier de conf UUIDMDV=$(vol_id --uuid $DEVMDV) UUIDSWAP=$(vol_id --uuid $DEVSWAP) OLDUUID=$(grep root=UUID $LOCALLINUX/boot/grub/menu.lst|sed -e 's/.*UUID=//g' | cut -f1 -d' ') fi if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "4" ]; then # on se fait le fstab a la main ... echo "...creation fstab...."; fixefstab echo "...effacement du 61-net-dev de udev...." ; fixelinux # TODO: on joint la machine au domaine: fi if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "3" ]; then # mettre le nom dans le sysprep echo "...fixe sysprep...."; fixeSysprep fi # TODO vérifier que ca marche sans ce besoin pour juste windows if [ "$WHATTODO" -eq "1" -o "$WHATTODO" -eq "2" -o "$WHATTODO" -eq "4" ]; then echo "...remplacement UUID dans grub...."; fixegrub fi echo "...thanks you for playing...." umount $LOCALDATA umount $WINDOWS1 umount $LOCALLINUX sync sync umount -a reboot