home *** CD-ROM | disk | FTP | other *** search
/ Chip 2007 January, February, March & April / Chip-Cover-CD-2007-02.iso / boot / i386 / root / usr / share / YaST2 / include / bootloader / routines / autoinstall.ycp next >
Text File  |  2006-11-29  |  10KB  |  380 lines

  1. /**
  2.  * File:
  3.  *      autoinstall.ycp
  4.  *
  5.  * Module:
  6.  *      Bootloader installation and configuration
  7.  *
  8.  * Summary:
  9.  *      Bootloader autoinstallation preparation
  10.  *
  11.  * Authors:
  12.  *      Jiri Srain <jsrain@suse.cz>
  13.  *
  14.  * $Id: autoinstall.ycp 33911 2006-10-31 01:40:46Z odabrunz $
  15.  *
  16.  */
  17. {
  18.  
  19.     import "Bootloader";
  20.     import "BootCommon";
  21.     import "Initrd";
  22.     import "Kernel";
  23.     import "Mode";
  24.  
  25. /**
  26.  * Add missing data (eg. root filesystem) to sections imported from profile
  27.  * @param sect a list of all sections
  28.  * @return a lit of all updated sections
  29.  */
  30. list<map<string,any> > UpdateImportedSections (list<map<string,any> > sect) {
  31.     sect = maplist (map<string,any> s, sect, {
  32.     y2milestone ("Updating imported section %1", s);
  33.     string orig_name = s["original_name"]:s["name"]:"linux";
  34.     string type = s["type"]:"image";
  35.     if (type != "image")
  36.         return s;
  37.     s = (map<string,any>)union (
  38.         BootCommon::CreateLinuxSection (orig_name),
  39.         s);
  40.     return s;
  41.     });
  42.     return sect;
  43. }
  44.  
  45.     /**
  46.       * Translate the autoinstallation map to the Export map
  47.       * @param ai a map the autoinstallation map
  48.       * @return a map the export map
  49.       */
  50.     define map<string,any> AI2Export (map<string,any> ai) ``{
  51.     if (Mode::autoinst ())
  52.     {
  53.         BootCommon::DetectDisks ();
  54.     }
  55.     // prepare settings for default bootloader if not specified in the
  56.     // profile
  57.     if (Mode::autoinst () && (
  58.         ai["loader_type"]:"default" == "default"
  59.         || ai["loader_type"]:"default" == ""
  60.         )
  61.     ) {
  62.         ai["loader_type"] = Bootloader::getLoaderType ();
  63.     }
  64.     y2milestone ("Bootloader settings from profile: %1", ai);
  65.  
  66.     // bootloader type and location stuff
  67.     map<string,any> exp = $[
  68.         "loader_type" : ai["loader_type"]:"",
  69.         "specific" : $[],
  70.     ];
  71. /* FIXME
  72.     // global PPC stuff
  73.     if (ai["loader_type"]:"" == "ppc")
  74.     {
  75.         exp["specific", "activate"] = true;
  76.         foreach (string k, ["iseries_streamfile", "iseries_write_slot_a",
  77.         "iseries_write_slot_b", "iseries_write_streamfile",
  78.         "iseries_write_prepboot", "prep_boot_partition",
  79.         "of_defaultdevice", "board_type", "activate"],
  80.         {
  81.         if (haskey (ai, k))
  82.         {
  83.             exp["specific", k] = ai[k]:nil;
  84.         }
  85.         });
  86.     }
  87.     // global ELILO stuff
  88.     if (ai["loader_type"]:"" == "elilo")
  89.     {
  90.         string def_label = "";
  91.         if (! Mode::test ())
  92.         {
  93.         import "Product";
  94.         if (Mode::autoinst ())
  95.         {
  96.             def_label = Product::name;
  97.         }
  98.         }
  99.         // if EFI label not specified, use default label
  100.         exp["location"] = ai["efi_entry_label"]:ai["location"]:def_label;
  101.         exp["specific", "create_efi_entry"]
  102.         = ai["create_efi_entry"]:(exp["location"]:"" != "");
  103.     }
  104. */
  105.     // LILO and GRUB stuff
  106.     if (ai["loader_type"]:"" == "lilo" || ai["loader_type"]:"" == "grub")
  107.     {
  108.         foreach (string k, ["repl_mbr", "activate", ],
  109.             {
  110.         if (haskey (ai, k))
  111.         {
  112.             exp["specific", k] = ai[k]:nil;
  113.         }
  114.             });
  115.         // loader_location needs other default and key
  116.         exp["loader_location"] = ai["location"]:"custom";
  117.         foreach (string k, [/*"loader_location",*/ "loader_device"], {
  118.         if (haskey (ai, k))
  119.         {
  120.             exp[k] = ai[k]:nil;
  121.         }
  122.         });
  123.     }
  124.  
  125.     // device map stuff
  126.     if (size (ai["device_map"]:[]) > 0)
  127.     {
  128.         list<map<string,string> > dm = ai["device_map"]:[];
  129.         if (dm != nil && size (dm) > 0)
  130.         {
  131.         map<string,string> device_map = listmap (
  132.             map<string,string> entry, dm,
  133.         {
  134.             return $[ entry["linux"]:"" : entry["firmware"]:"" ];
  135.         });
  136.         exp["specific", "device_map"] = device_map;
  137.         }
  138.     }
  139.  
  140.     // initrd stuff
  141.     list<string> modlist = [];
  142.     map<string,any> modsett = $[];
  143.     foreach(map mod, ai["initrd_modules"]:[], ``{
  144.         modlist = add(modlist, mod["module"]:"");
  145.         modsett = add(modsett, mod["module"]:"", mod["module_args"]:$[]);
  146.     });
  147.         if (Mode::autoinst ())
  148.         {
  149.         map current = Initrd::Export();
  150.             y2milestone("Automatically detected initrd modules: %1", current);
  151.         list<string> modules = current["list"]:[];
  152.         map<string,any> modules_settings = current["settings"]:$[];
  153.         foreach (string m, modules, {
  154.         if (! contains (modlist, m))
  155.         {
  156.             // add only if it isn't present
  157.             modlist = add (modlist, m);
  158.         }
  159.         if (! haskey (modsett, m) && haskey (modules_settings, m))
  160.         {
  161.             // if the argument is in profile, prefer it
  162.             modsett[m] = modules_settings[m]:nil;
  163.         }
  164.         });
  165.             string parameters = ai["kernel_parameters"]:"";
  166.             if ( size(parameters) > 0)
  167.             {
  168.                 foreach ( string parameter, splitstring(parameters, " "), {
  169.             list param_value_list = splitstring (parameter, "=");
  170.             if (size (param_value_list) > 0)
  171.             {
  172.             Kernel::AddCmdLine (
  173.                 param_value_list[0]:"",
  174.                 param_value_list[1]:"");
  175.             }
  176.         });
  177.             }
  178.     }
  179.  
  180.     if (size(modlist) > 0 )
  181.         exp["initrd"] = $[ "list": modlist, "settings" : modsett ];
  182.  
  183.     boolean old_format = false;
  184.  
  185.     // section stuff
  186.     list<string> section_names = [];
  187.     if (size (ai["sections"]:[]) > 0)
  188.     {
  189.         foreach (any s, ai["sections"]:[], {
  190.         if (! is (s, map<string,any>))
  191.             old_format = true;
  192.         });
  193.         if (! old_format)
  194.         {
  195.         list<map<string,any> > sect = (list<map<string,any> >)
  196.             ai["sections"]:[];
  197.         sect = UpdateImportedSections (sect);
  198.         exp["specific", "sections"] = sect;
  199.         }
  200.     }
  201.  
  202.     // global stuff
  203.     if ((! haskey (ai, "global")) || is (ai["global"]:nil, map))
  204.     {
  205.         exp["specific", "global"] = mapmap (string k, any v,
  206.         ai["global"]:$[],
  207.         {
  208.         return $[ k : sformat ("%1", v) ];
  209.         });
  210.     }
  211.     else // old format
  212.     {
  213.         old_format = true;
  214.     }
  215.     y2milestone ("SLES9 format detected: %1", old_format);
  216.     if (old_format)
  217.     {
  218.         list<list<map> > sections = ai["sections"]:[];
  219.         list<map> globals = ai["global"]:[];
  220.         sections = prepend (sections, globals);
  221.         list<map> flat = flatten (sections);
  222.         string loader = ai["loader_type"]:"";
  223.         string separator = loader == "grub" ? " " : " = ";
  224.         list<string> lines = maplist (map f, flat, {
  225.         return sformat ("%1%2%3",
  226.             f["key"]:"", separator, f["value"]:"");
  227.         });
  228.         string file = mergestring (lines, "\n");
  229.         BootCommon::InitializeLibrary (true, loader);
  230.         BootCommon::SetDeviceMap (BootCommon::device_mapping);
  231.         BootCommon::SetSections ([]);
  232.         BootCommon::SetGlobal ($[]);
  233.         map<string,string> files = BootCommon::GetFilesContents ();
  234.         map<string,string> bl2file = $[
  235.         "grub" : "/boot/grub/menu.lst",
  236.         "lilo" : "/etc/lilo.conf",
  237.         // TODO the other bootloaders
  238.         ];
  239.         files[bl2file[loader]:""] = file;
  240.         BootCommon::SetFilesContents (files);
  241.         exp["specific", "global"] = BootCommon::GetGlobal ();
  242.         list<map<string,any> > sect = BootCommon::GetSections ();
  243.         sect = UpdateImportedSections (sect);
  244.         exp["specific", "sections"] = sect;
  245.         section_names = maplist (map<string,any> s, sect, {
  246.         return s["name"]:"";
  247.         });
  248.     }
  249.  
  250.     if (haskey (exp["specific", "global"]:$[], "default")
  251.         && ! contains (section_names,
  252.         exp["specific", "global", "default"]:""))
  253.     {
  254.         exp["specific", "global"]
  255.         = remove (exp["specific", "global"]:$[], "default");
  256.     }
  257.  
  258.     return exp;
  259.     }
  260.  
  261.     /**
  262.       * Translate the Export map to the autoinstallation map
  263.       * @param exp a map the export map
  264.       * @return a map the autoinstallation map
  265.       */
  266.     define map<string,any> Export2AI (map<string,any> exp) ``{
  267.     // bootloader type and location stuff
  268.     map<string,any> ai = $[
  269.         "loader_type" : exp["loader_type"]:"default",
  270.     ];
  271.     map<string,string> glob = filter (string k, string v,
  272.         exp["specific", "global"]:$[],
  273.     {
  274.         return substring (k, 0, 2) != "__";
  275.     });
  276.     // global options stuff
  277.     if (size (glob) > 0)
  278.     {
  279.         ai["global"] = mapmap (string k, string v, glob, {
  280.         if (k == "timeout")
  281.             return (map<string,any>)$[ k : tointeger (v) ];
  282.         else if (k == "embed_stage1.5")
  283.             return (map<string,any>)
  284.             $[ k : (v == "0" || v == "") ? false : true ];
  285.         return (map<string,any>)$[ k : v ];
  286.         });
  287.     }
  288.     // sections stuff
  289.     ai["sections"] = maplist (map<string,any> s,
  290.         exp["specific", "sections"]:[],
  291.     {
  292.         s = filter (string k, any v, s, {
  293.         return substring (k, 0, 2) != "__";
  294.         });
  295.         return s;
  296.     });
  297. /*
  298.     // global PPC stuff
  299.     if (ai["loader_type"]:"" == "ppc")
  300.     {
  301.         foreach (string k, ["iseries_streamfile", "iseries_write_slot_a",
  302.         "iseries_write_slot_b", "iseries_write_streamfile",
  303.         "iseries_write_prepboot", "prep_boot_partition",
  304.         "of_defaultdevice", "board_type", "activate", ],
  305.         {
  306.         if (haskey (exp["specific"]:$[], k))
  307.         {
  308.             ai[k] = exp["specific", k]:nil;
  309.         }
  310.         });
  311.     }
  312.  
  313.     // global ELILO stuff
  314.     if (ai["loader_type"]:"" == "elilo")
  315.     {
  316.         // discards location and loader device, it is correct.
  317.         ai = $[
  318.         "loader_type" : exp["loader_type"]:"",
  319.         "efi_entry_label" : exp["location"]:"",
  320.         "create_efi_entry" : exp["specific", "create_efi_entry"]:false,
  321.         ];
  322.     }
  323. */
  324.     // LILO and GRUB stuff
  325.     if (ai["loader_type"]:"" == "lilo" || ai["loader_type"]:"" == "grub")
  326.     {
  327.         foreach (string k, ["repl_mbr", "activate", ],
  328.             {
  329.                 if (haskey (exp["specific"]:$[], k))
  330.                 {
  331.                     ai[k] = exp["specific", k]:nil;
  332.                 }
  333.             });
  334.         if (haskey (exp, "loader_location"))
  335.         ai["location"] = exp["loader_location"]:"";
  336.         foreach (string k, ["loader_device"], {
  337.         if (haskey (exp, k))
  338.         {
  339.             ai[k] = exp[k]:nil;
  340.         }
  341.         });
  342.     }
  343.  
  344.     // device map stuff
  345.     if (size (exp["specific", "device_map"]:$[]) > 0)
  346.     {
  347.         map<string,string> device_map = exp["specific", "device_map"]:$[];
  348.         y2error ("DM: %1", device_map);
  349.         if (device_map != nil && size (device_map) > 0)
  350.         {
  351.         list<map<string,string> > dm = maplist (
  352.             string linux,
  353.             string firmware,
  354.             device_map,
  355.         {
  356.             return $[
  357.             "linux" : linux,
  358.             "firmware" : firmware,
  359.             ];
  360.         });
  361.         ai["device_map"] = dm;
  362.         }
  363.     }
  364.  
  365.     // initrd stuff
  366.     list<map> ayinitrd = maplist(string m, exp["initrd", "list"]:[], ``{
  367.         map tmp = $[];
  368.         tmp["module"] = m;
  369.         if (exp["initrd", "settings", m]:$[] != $[])
  370.         tmp["module_args"] = exp["initrd", "settings", m]:$[];
  371.         return (tmp);
  372.     });
  373.     if (size(ayinitrd) > 0 )
  374.         ai["initrd_modules"] = ayinitrd;
  375.  
  376.     return ai;
  377.     }
  378.  
  379. }
  380.