root/morphix/trunk/morph-scripts/isomorph.pl

Revision 2, 15.8 kB (checked in by nextime, 2 years ago)

Initial import, branching from morphix svn

  • Property svn:executable set to
Line 
1 #!/usr/bin/perl
2
3 #
4 # isomorph
5 #
6
7 # Description:
8 #
9 # lets you morph a currently downloaded iso
10 # by adding a new mini- or mainmodule, debian package, shell script, copy-on-boot file,
11 # removing these, getting, or listing them
12 #
13
14 ###
15 #
16 # See isomorph -h for usage
17 #
18 ###
19
20 use File::Temp qw/ tempdir /;
21 use File::Copy;
22
23 $mode = "";
24 $type = "";
25 $file = "";
26 $path = "";
27
28 $xml = 0;
29
30 $oldmountpoint = "";
31 $newmountpoint = "";
32
33 $oldiso = "";
34 $newiso = "";
35
36 sub type_valid {
37     $t = @_[0];
38     if ($t eq "main" ||
39         $t eq "mini" ||
40         $t eq "deb" ||
41         $t eq "exec" ||
42         $t eq "base" ||
43         $t eq "copy" ||
44         $t eq "boot") {
45         return 1;
46     }
47     return 0;
48 }
49
50 ###
51 #
52 # Option handling stuff
53 #
54 ###
55
56 $option = $ARGV[0];
57 $type = $ARGV[1];
58
59 if ($option eq "--add") {
60     if ($ARGV[4] ne "" && type_valid($type) == 1) {
61         $mode = "add";
62         $file = $ARGV[2];
63         if ($type eq "copy") {
64             $path = $ARGV[3];
65             $oldiso = $ARGV[4];
66             $newiso = $ARGV[5];
67         }
68         else {
69             $oldiso = $ARGV[3];
70             $newiso = $ARGV[4];
71         }
72     }
73     else {
74         $mode = "";
75     }
76 }
77
78 if ($option eq "--get") {
79     if ($ARGV[4] ne "" && type_valid($type) == 1) {
80         $mode = "get";
81         $oldiso = $ARGV[3];
82         $path = $ARGV[4];
83     }
84     else {
85         if ($ARGV[3] ne "") {
86             $mode = "get";
87             $type = "all";
88             $oldiso = $ARGV[2];
89             $path = $ARGV[3];
90         }
91         else {
92             $mode = "";
93         }
94     }
95 }
96
97 if ($option eq "--del" || $option eq "--del-all") {
98     $mode = "del";
99
100     if ($ARGV[2] eq "" && type_valid($type) == 0) {
101         $mode = "";
102     }
103     elsif ($ARGV[4] ne "" && type_valid($type) == 1) {
104         $file = $ARGV[2];
105         $oldiso = $ARGV[3];
106         $newiso = $ARGV[4];
107     }
108     elsif ($ARGV[3] ne "" && type_valid($type) == 1) {
109         $mode = "del-all";
110         $oldiso = $ARGV[2];
111         $newiso = $ARGV[3];
112     }
113     else {
114         $mode = "del-all";
115         $oldiso = $ARGV[1];
116         $newiso = $ARGV[2];
117         $type = "all";
118     }
119 }
120
121 if ($option eq "--list" || $option eq "--list-xml") {
122     if ($option eq "--list-xml") {
123         $xml = 1;
124     }
125     if ($ARGV[2] ne "" && type_valid($type) == 1) {
126         $mode = "list";
127         $oldiso = $ARGV[2];
128     }
129     else { # if only one argument, type is the iso
130         if ($ARGV[1] ne "") {
131             $mode = "list";
132             $type = "all";
133             $oldiso = $ARGV[1];
134         }
135         else {
136             $mode = "";
137         }
138     }
139 }
140
141 ###
142 #
143 # Mode handling stuff
144 #
145 ###
146
147 if ($mode eq "") {
148         print("Usage: isomorph [OPTION]
149 All isomorph options are of 4 types: list, add, get and delete
150 'list' and 'get' are actions on a single iso,
151 'add' and 'delete' output a modified iso and leave the old iso intact.
152 With these 4 options, many types of actions are possible:
153
154 list options:
155 [--list ISO]\t\t\t\tlist all morphix files on iso
156 [--list-xml ISO]\t\t\tlist all morphix files in XML format
157 [--list main ISO]\t\t\tlist mainmodules
158 [--list mini ISO]\t\t\tlist minimodules
159 [--list deb ISO]\t\t\tlist debian packages
160 [--list exec ISO]\t\t\tlist scripts
161 [--list copy ISO]\t\t\tlist copy-on-boot files
162
163 add options:
164 [--add base BASEMODULE OLDISO NEWISO]\t\treplace basemodule
165 [--add main MAINMODULE OLDISO NEWISO]\t\tadd mainmodule to oldiso
166 [--add mini MINIMODULE OLDISO NEWISO]\t\tadd minimodule to oldiso
167 [--add deb  DEBPACKAGE OLDISO NEWISO]\t\tadd package to oldiso
168 [--add exec SHELLSCRIPT OLDISO NEWISO]\t\tadd script to oldiso
169 [--add copy FILE PATH OLDISO NEWISO]\t\tadd file to oldiso in path
170 [--add boot \"Boot Option\" OLDISO NEWISO]\tadd boot option to oldiso
171
172 get options:
173 [--get ISO DIRECTORY]\t\t\tcopy all morphix files from iso to dir
174 [--get main ISO DIRECTORY]\t\tcopy mainmodules from iso to directory
175 [--get mini ISO DIRECTORY]\t\tcopy minimodules
176 [--get deb ISO DIRECTORY]\t\tcopy debian packages
177 [--get exec ISO DIRECTORY]\t\tcopy scripts
178 [--get copy ISO DIRECTORY]\t\tcopy copy-on-boot files
179
180 delete options:
181 [--del-all OLDISO NEWISO]\t\t\tdelete all morphix files from ISO
182 [--del-all main OLDISO NEWISO]\t\t\tdelete all mainmodules
183 [--del-all mini OLDISO NEWISO]\t\t\tdelete all minimodules
184 [--del-all deb OLDISO NEWISO]
185 [--del-all exec OLDISO NEWISO]
186 [--del-all copy OLDISO NEWISO]
187 [--del main MAINMODULE OLDISO NEWISO]\t\tdelete mainmodule from oldiso
188 [--del mini MINIMODULE OLDISO NEWISO]\t\tdelete minimodule from oldiso
189 [--del deb DEBPACKAGE OLDISO NEWISO]\t\tdelete package from oldiso
190 [--del exec SHELLSCRIPT OLDISO NEWISO]
191 [--del copy FILE OLDISO NEWISO]
192 [--del boot \"Boot Option\" OLDISO NEWISO]\tdelete boot option from oldiso
193 \n");
194         exit(1);
195 }
196
197 sub makenewiso {
198     $mode = @_[0];
199     if ($mode eq "add" || $mode eq "del" || $mode eq "del-all") {
200         return 1;
201     }
202     return 0;
203 }
204
205 sub dostuff {
206     if ($mode eq "list") {
207         if ($xml == 1) {
208             listxmlheader();
209         }
210         if ($type eq "main" || $type eq "all") {
211             domain();
212         }
213         if ($type eq "mini" || $type eq "all") {
214             domini();
215         }
216         if ($type eq "deb" || $type eq "all") {
217             dodeb();
218         }
219         if ($type eq "exec" || $type eq "all") {
220             doexec();
221         }
222         if ($type eq "copy" || $type eq "all") {
223             docopy();
224         }
225         if ($mode eq "list" && $xml == 1) {
226             listxmlfooter();
227         }
228     }
229     if ($mode eq "get") {
230         if ($type eq "main" || $type eq "all") {
231             domain();
232         }
233         if ($type eq "mini" || $type eq "all") {
234             domini();
235         }
236         if ($type eq "deb" || $type eq "all") {
237             dodeb();
238         }
239         if ($type eq "exec" || $type eq "all") {
240             doexec();
241         }
242         if ($type eq "copy" || $type eq "all") {
243             docopy();
244         }
245     }
246            
247
248     if (makenewiso($mode)) {
249         print $newmountpoint;
250         print $oldmountpoint;
251         print ("Copying old iso...\n");
252         system("cp -a $oldmountpoint/* $newmountpoint");
253         print ("Busy making new iso...\n");
254     }
255     if ($mode eq "add") {
256         if ($type eq "base") {
257             if ( -e $file) {
258                 system("cp $file $newmountpoint/base/morphix");
259             } else {
260                 isodie("Basemodule $file not found!");
261             }
262         }
263         if ($type eq "mini") {
264             if ( -e $file) {
265                 system("cp $file $newmountpoint/minimod/");
266             } else {
267                 isodie("Minimodule $file not found!");
268             }
269         }
270         if ($type eq "main") {
271             if ( -e $file) {
272                 system("cp $file $newmountpoint/mainmod/");
273             } else {
274                 isodie("Mainmodule $fie not found!");
275             }
276         }
277         if ($type eq "deb") {
278             if ( -e $file) {
279                 system("cp $file $newmountpoint/deb/");
280             } else {
281                 isodie("Debian package $file not found!");
282             }
283         }
284         if ($type eq "exec") {
285             if ( -e $file) {
286                 system("cp $file $newmountpoint/exec/");
287             } else {
288                 isodie("Shell script $file not found!");
289             }
290         }
291         if ($type eq "copy") {
292             if ( -e $file) {
293                 system("mkdir -p $newmountpoint/copy/$path");
294                 if (-e "$newmountpoint/copy/$path") {
295                     system("cp $file $newmountpoint/copy/$path");
296                 }
297                 else {
298                     isodie("Can't make directory $newmountpoint/copy/$path");
299                 }
300             } else {
301                 isodie("File $file to be placed in /copy not found!");
302             }
303         }
304         if ($type eq "boot") {
305             if (-e "$newmountpoint/base/boot.img") {
306                 isodie("Old boot.img not yet supported for adding removing boot options");
307             }
308             elsif (-e "$newmountpoint/boot/grub/iso9660_stage1_5" || -e "$newmountpoint/boot/grub/stage2_eltorito") {
309                 $dir = "$oldmountpoint/boot/grub";
310                 opendir(DIR, $dir);
311                 @file2 = grep !/^\.\.?$/, readdir DIR;
312                 foreach $item (@file2) {
313                     if ($item =~ m".lst") {
314                             system ("sed '/kernel/s/\$/ $file/' $oldmountpoint/boot/grub/$item >$newmountpoint/boot/grub/$item");
315                         }
316                     }
317                 closedir(DIR); 
318                 }
319             else {
320                 isodie("Can't add boot option unable to find boot option");
321                 }
322             }
323     }
324     if ($mode eq "del") {
325         if ($type eq "mini") {
326             if (! -e "$newmountpoint/minimod/$file") {
327                 isodie("Minimodule $file not found!");
328             }
329             system("rm $newmountpoint/minimod/$file");
330             if (-e "$newmountpoint/minimod/$file") {
331                 isodie("Minimodule $file not deleteable: $!");
332             }
333         }
334         if ($type eq "main") {
335             if (! -e "$newmountpoint/mainmod/$file") {
336                 isodie("Mainmodule $file not found!");
337             }
338             system("rm $newmountpoint/mainmod/$file");
339             if (-e "$newmountpoint/mainmod/$file") {
340                 isodie("Mainmodule $file not deleteable: $!");
341             }
342         }
343         if ($type eq "deb") {
344             if (! -e "$newmountpoint/deb/$file") {
345                 isodie("Debian package $file not found!");
346             }
347             system("rm $newmountpoint/deb/$file");
348             if (-e "$newmountpoint/deb/$file") {
349                 isodie("Debian package $file not deleteable: $!");
350             }
351         }
352         if ($type eq "exec") {
353             if (! -e "$newmountpoint/exec/$file") {
354                 isodie("Script $file not found!");
355             }
356             system("rm $newmountpoint/exec/$file");
357             if (-e "$newmountpoint/exec/$file") {
358                 isodie("Script $file not deleteable: $!");
359             }
360         }
361         if ($type eq "copy") {
362             if (! -e "$newmountpoint/copy/$file") {
363                 isodie("File $file not found!");
364             }
365             system("rm $newmountpoint/copy/$file");
366             if (-e "$newmountpoint/copy/$file") {
367                 isodie("File $file not deleteable: $!");
368             }
369         }
370         if ($type eq "boot") {
371             if (-e "$newmountpoint/base/boot.img") {
372                 isodie("Old boot.img not yet supported for adding removing boot options");
373             }
374             elsif (-e "$newmountpoint/boot/grub/iso9660_stage1_5" || -e "$newmountpoint/boot/grub/stage2_eltorito") {
375                 $dir = "$oldmountpoint/boot/grub";
376                 opendir(DIR, $dir);
377                 @file2 = grep !/^\.\.?$/, readdir DIR;
378                 foreach $item (@file2) {
379                     if ($item =~ m".lst") {
380                             system ("sed '/kernel/s/$file//g' $oldmountpoint/boot/grub/$item >$newmountpoint/boot/grub/$item");
381                             system ("cat $newmountpoint/boot/grub/$item");
382                         }
383                     }
384                 closedir(DIR); 
385                 }
386             else {
387                 isodie("Can't remove boot option unable to find boot option");
388                 }
389             }   
390     }
391     if ($mode eq "del-all") {
392         if ($type eq "mini" || $type eq "all") {
393             system("rm -r $newmountpoint/minimod");
394             if (-e "$newmountpoint/minimod") {
395                 isodie("Minimodule dir not deleteable: $!");
396             }
397             mkdir("$newmountpoint/minimod");
398         }
399         if ($type eq "main" || $type eq "all") {
400             system("rm -r $newmountpoint/mainmod");
401             if (-e "$newmountpoint/mainmod") {
402                 isodie("Mainmodule dir not deleteable: $!");
403             }
404             mkdir("$newmountpoint/mainmod");
405         }
406         if ($type eq "deb" || $type eq "all") {
407             system("rm -r $newmountpoint/deb");
408             if (-e "$newmountpoint/deb") {
409                 isodie("Debian package dir not deleteable: $!");
410             }
411             mkdir("$newmountpoint/deb");
412         }
413         if ($type eq "exec" || $type eq "all") {
414             system("rm -r $newmountpoint/exec");
415             if (-e "$newmountpoint/exec") {
416                 isodie("Exec dir not deleteable: $!");
417             }
418             mkdir("$newmountpoint/exec");
419         }
420         if ($type eq "copy" || $type eq "all") {
421             system("rm -r $newmountpoint/copy");
422             if (-e "$newmountpoint/copy") {
423                 isodie("Copy dir not deleteable: $!");
424             }
425             mkdir("$newmountpoint/copy");
426         }
427        
428     }
429     if (makenewiso($mode)) {   
430         # do those md5sums
431         system("find $newmountpoint/ -type f -print0 | xargs -0 md5sum > $newmountpoint/md5sums.txt");
432        
433         # finally make the damn thing
434         # We currently have used 2 types of CD bootloaders:
435         # syslinux or grub with floppy emulation, of which we only have
436         # to boot using the /base/boot.img file
437         # and grub no-floppy-emulation booting, of which there are two
438         # methods for booting: using the iso9660 stage 1.5 grub image or
439         # the stage2 eltorito image.
440         # Floppy emulation is deprecated in favour of the use of the
441         # iso9660 stage 1.5 grub image, but is as of now the most common
442
443         if (-e "$newmountpoint/base/boot.img") {
444             system("mkisofs -pad -l -r -J -v -V \"Morphix Live CD\" -b base/boot.img -c base/boot.cat -hide-rr-moved -o $newiso $newmountpoint");
445         }
446         elsif (-e "$newmountpoint/boot/grub/iso9660_stage1_5") {
447             system("mkisofs -pad -l -r -J -v -V \"Morphix LiveCD\" -b boot/grub/iso9660_stage1_5 -c base/boot.cat -no-emul-boot -boot-load-size 4 -boot-info-table -hide -rr -moved -o $newiso $newmountpoint");
448         }
449         elsif (-e "$newmountpoint/boot/grub/stage2_eltorito") {
450             system("mkisofs -pad -l -r -J -v -V \"Morphix LiveCD\" -b boot/grub/stage2_eltorito -c base/boot.cat -no-emul-boot -boot-load-size 4 -boot-info-table -hide -rr -moved -o $newiso $newmountpoint");
451         }
452     }
453 }
454
455 sub checkiso {
456     if (-e "@_[0]/mainmod" && -e "@_[0]/mainmod" && -e "@_[0]/base") {
457         return 1;
458     }
459     return 0;
460 }
461
462 sub isodie {
463     umountoldiso();
464     removetempdirs();
465     die "Error: @_[0]";
466 }
467
468 sub listxmlheader {
469     print("<iso>\n");
470 }
471
472 sub listxmlfooter {
473     print("</iso>\n");
474 }
475
476 sub domain {
477     $dir = "$oldmountpoint/mainmod";
478     opendir(DIR, $dir);
479     if (DIR && $xml == 1) {
480         @file2 = grep !/^\.\.?$/, readdir DIR;
481         foreach $item (@file2) {
482             print "\t<main>$item</main>\n";
483         }
484         closedir(DIR);
485     }
486     elsif (DIR) {
487         if ($mode eq "list") {
488            
489             print("Mainmodules in $oldiso:\n");
490             @file2 = grep !/^\.\.?$/, readdir DIR;
491             print "@file2\n";
492             closedir(DIR);
493         }
494         else {
495             @file2 = grep !/^\.\.?$/, readdir DIR;
496             foreach $file3 (@file2) {
497                 system("cp $dir/$file3 $path/");
498             }
499             closedir(DIR);
500         }
501     }
502 }
503
504 sub domini {
505     $dir = "$oldmountpoint/minimod";
506     opendir(DIR, $dir);
507     if (DIR && $xml == 1) {
508         @file2 = grep !/^\.\.?$/, readdir DIR;
509         foreach $item (@file2) {
510             print "\t<mini>$item</mini>\n";
511         }
512         closedir(DIR);
513     }
514     elsif (DIR) {
515         if ($mode eq "list") {
516             print("Minimodules in $oldiso:\n");
517             @file2 = grep !/^\.\.?$/, readdir DIR;
518             print "@file2\n";
519             closedir(DIR);
520         }
521         else {
522             @file2 = grep !/^\.\.?$/, readdir DIR;
523             foreach $file3 (@file2) {
524                 system("cp $dir/$file3 $path/");
525             }
526             closedir(DIR);
527         }
528     }
529 }
530
531 sub dodeb {
532     $dir = "$oldmountpoint/deb";
533     opendir(DIR, $dir);
534     if (DIR && $xml == 1) {
535         @file2 = grep !/^\.\.?$/, readdir DIR;
536         foreach $item (@file2) {
537             print "\t<deb>$item</deb>\n";
538         }
539         closedir(DIR);
540     }
541     elsif (DIR) {
542         if ($mode eq "list") {
543             print("Debian packages in $oldiso:\n");
544             @file2 = grep !/^\.\.?$/, readdir DIR;
545             print "@file2\n";
546             closedir(DIR);
547         }
548         else {
549             @file2 = grep !/^\.\.?$/, readdir DIR;
550             foreach $file3 (@file2) {
551                 system("cp $dir/$file3 $path/");
552             }
553             closedir(DIR);
554         }
555     }
556 }
557
558 sub doexec {
559     $dir = "$oldmountpoint/exec";
560     opendir(DIR, $dir);
561     if (DIR && $xml == 1) {
562         @file2 = grep !/^\.\.?$/, readdir DIR;
563         foreach $item (@file2) {
564             print "\t<exec>$item</exec>\n";
565         }
566         closedir(DIR);
567     }
568     elsif (DIR) {
569         if ($mode eq "list") {
570             print("Shell scripts in $oldiso:\n");
571             @file2 = grep !/^\.\.?$/, readdir DIR;
572             print "@file2\n";</