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 / clients / lvm_config_ui.ycp < prev    next >
Text File  |  2006-11-29  |  12KB  |  442 lines

  1. /**
  2.  * File:
  3.  *   lvm_config_ui.ycp
  4.  *
  5.  * Module: 
  6.  *    configuration of lvm in installed system
  7.  * Summary:
  8.  *
  9.  * Authors:
  10.  *   mike <mike@suse.de>
  11.  *
  12.  * $Id: lvm_config_ui.ycp 33002 2006-09-20 10:28:09Z fehr $
  13.  *
  14.  *
  15.  *----------------------------------------------------
  16.  * IMPORTANT: when you read this code notice:
  17.  *
  18.  * vg  = volume group
  19.  * vgs = volume groups
  20.  *
  21.  * pv  = physical volume
  22.  * pvs = physical volumes
  23.  *
  24.  * lv  = logical volume
  25.  * lvs = logical volumes
  26.  *----------------------------------------------------
  27.  *
  28.  */
  29. {
  30.     import "Arch";
  31.     import "Storage";
  32.     import "FileSystems";
  33.     import "Partitions";
  34.     import "Mode";
  35.     
  36.     textdomain "storage"; 
  37.  
  38.     import "Popup";
  39.     include "partitioning/partition_defines.ycp";
  40.     include "partitioning/custom_part_dialogs.ycp";
  41.     include "partitioning/custom_part_lib.ycp";
  42.     include "partitioning/custom_part_helptexts.ycp";
  43.     include "partitioning/custom_part_dialogs.ycp";
  44.     include "partitioning/lvm_ui_dialogs.ycp";
  45.     include "partitioning/lvm_ui_lib.ycp";
  46.     include "partitioning/lvm_lib.ycp";
  47.     include "partitioning/lvm_lv_lib.ycp";
  48.     include "partitioning/lvm_pv_lib.ycp";
  49.   
  50.    
  51.     
  52. define boolean CheckItemIsNotMounted( string id )
  53.     ``{
  54.     y2milestone( "CheckItemIsNotMounted id:%1", id );
  55.     boolean ret = true;
  56.     if( size(id)>0 )
  57.     {
  58.     string device = id;
  59.     string cmd = "mount | grep \"^" + device + " \"";
  60.     y2milestone( "mounts cmd=%1", cmd );
  61.     map bo = (map)SCR::Execute(.target.bash_output, cmd);
  62.     string line = bo["stdout"]:"";
  63.     y2milestone( "mounts line=%1", line );
  64.     ret = size(line)<size(device);
  65.     if( !ret )
  66.         {
  67.         line = substring( line, search( line, "on " )+3 );
  68.         y2milestone( "mounts line=%1", line );
  69.         line = substring( line, 0, findfirstof( line, " " ) );
  70.         y2milestone( "mounts line=%1", line );
  71.         // popup text, %1 is device name.  %2 is mount point.
  72.         Popup::Message(sformat(_("Device %1 is already mounted at %2.  
  73. A mounted file system cannot be added to a volume group."),
  74.          device, line ));
  75.         }
  76.     }
  77.     y2milestone( "mounts ret=%1", ret );
  78.     return( ret );
  79.     }
  80.  
  81.     string  current_vg       = "none";    
  82.     string  vg_key = "";
  83.     integer pesize = 4*1024*1024;
  84.  
  85.    
  86.  
  87.     boolean test_mode        = Mode::test ();
  88.     boolean view_all_mnts    = Storage::GetLvmViewAllMnt();
  89.     map<string,map> targetMap = Storage::GetTargetMap();
  90.  
  91.     
  92.     ////////////////////////////////////////////////
  93.     // Testmode, should be commented in release
  94.     // test_mode   = true;
  95.     // test_mode   = false;
  96.     // architecture = "ppc";
  97.     // system_type = "prep";
  98.     // architecture = "axp";
  99.     ////////////////////////////////////////////////
  100.     
  101.     list    lvm_vgs      = get_vgs( targetMap );
  102.     list<map> parts_lv      = get_lvs_and_mounted_partitions( targetMap, view_all_mnts, current_vg );
  103.     list    table_lv      = get_lv_widget_table( parts_lv );
  104.     list<map> parts_pv      = get_possible_pvs( targetMap );
  105.     list    table_pv      = get_pv_widget_table( parts_pv );
  106.  
  107.     //////////////////////////////////////////////////////////////////////
  108.     // First we typically have to create a volumegroup
  109.     // check if there is already a lvm group
  110.     //////////////////////////////////////////////////////////////////////
  111.     
  112.     if( size( lvm_vgs ) == 0 )
  113.     {
  114.     map vg = DlgCreateVolumeGroup( lvm_vgs );
  115.     map addVG = addVolumeGroup( vg, targetMap, lvm_vgs );
  116.     
  117.     // has the user cancelled the dialog? 
  118.     if( !addVG["cancelled"]:false )
  119.         {
  120.         targetMap = Storage::GetTargetMap();
  121.         lvm_vgs = get_vgs( targetMap );
  122.         current_vg = addVG["vg"]:"";
  123.         }
  124.     else
  125.         {
  126.         return( `back );
  127.         }
  128.     }
  129.     else
  130.     {
  131.     // there are already vgs ... select the first one
  132.     current_vg = lvm_vgs[0]:""; 
  133.     }
  134.  
  135.     vg_key = "/dev/" + current_vg;
  136.     pesize = targetMap[vg_key,"cyl_size"]:(4*1024*1024);
  137.  
  138.     
  139.     // Display current vg:
  140.     new_vg_list( lvm_vgs );
  141.     UI::ChangeWidget( `id(`vg), `Value, current_vg);
  142.  
  143.  
  144.     //////////////////////////////////////////////////////////////////////
  145.     // mainloop
  146.     //////////////////////////////////////////////////////////////////////
  147.  
  148.     string  id          =  "";
  149.     symbol  ret         = `next;
  150.     integer max_size    = 0;
  151.     integer used_size   = 0;
  152.     list    size_list   = [];
  153.     string  vg_size_str = "";
  154.  
  155.     repeat
  156.     {
  157.         /////////////////////////////////////////////////////////////////
  158.     // Show the current state:
  159.     parts_pv      = get_possible_pvs( targetMap );
  160.     table_pv      = get_pv_widget_table( parts_pv );
  161.     string ti = (string)UI::QueryWidget(`id(`pv_table), `CurrentItem );
  162.     UI::ChangeWidget( `id(`pv_table), `Items, table_pv );
  163.     if( ti != nil )
  164.         UI::ChangeWidget( `id(`pv_table), `CurrentItem, ti );
  165.  
  166.         parts_lv = get_lvs_and_mounted_partitions( targetMap, view_all_mnts, 
  167.                            current_vg );
  168.     table_lv = get_lv_widget_table( parts_lv );
  169.     ti = (string)UI::QueryWidget(`id(`lv_table), `CurrentItem );
  170.     UI::ChangeWidget( `id(`lv_table), `Items, table_lv );
  171.     if( ti != nil )
  172.         UI::ChangeWidget( `id(`lv_table), `CurrentItem, ti );
  173.  
  174.     integer s = targetMap["/dev/"+current_vg,"size_k"]:0*1024;
  175.     string vg_size_str = ByteToHumanStringWithZero( s );
  176.     y2debug( "**** %1", vg_size_str );
  177.     UI::ChangeWidget( `id(`pv_size), `Value, vg_size_str);
  178.  
  179.         UI::SetFocus( `id(`pv_table));
  180.  
  181.  
  182.         
  183.     /////////////////////////////////////////////////////////////////
  184.     // Size for BarGraph
  185.  
  186.     size_list = get_lv_size_info( targetMap,  current_vg );
  187.     max_size  = size_list[1]:0;
  188.     used_size = size_list[0]:0;
  189.     y2debug( "list=%3, max_size=%1 used_size=%2", max_size, used_size, 
  190.              size_list );
  191.     vg_size_str = ByteToHumanStringWithZero( max_size );
  192.  
  193.     if( UI::HasSpecialWidget( `BarGraph ))
  194.         {
  195.         UI::ChangeWidget( `id(`vg_size), `Labels,
  196.                  [
  197.                   sformat( "used\n%1", 
  198.                            ByteToHumanStringWithZero(used_size)),
  199.                   sformat( "free\n%1", 
  200.                            ByteToHumanStringWithZero(max_size))
  201.                  ] );
  202.         UI::ChangeWidget( `id(`vg_size), `Values, 
  203.                           [ used_size / 1048576, max_size / 1048576 ] );
  204.         }
  205.     else
  206.         {
  207.         UI::ChangeWidget( `id(`vg_size), `Value, vg_size_str);
  208.         }
  209.  
  210.         /////////////////////////////////////////////////////////////////
  211.         // Wait for User input
  212.  
  213.     ret= (symbol)UI::UserInput();
  214.  
  215.     y2milestone( "USERINPUT %1", ret );
  216.  
  217.  
  218.         ////////////////////////////////////////
  219.     // user has changed "view all mountpoints" checkbox
  220.     ////////////////////////////////////////
  221.     
  222.     if( ret == `viewmnt )
  223.         {
  224.         view_all_mnts = (boolean)UI::QueryWidget(`id(`viewmnt), `Value );
  225.         }
  226.  
  227.  
  228.         ////////////////////////////////////////
  229.     // user has changed the current volume group
  230.     ////////////////////////////////////////
  231.     
  232.     if( ret == `vg )
  233.         {
  234.         current_vg = (string)UI::QueryWidget( `id(`vg), `Value);
  235.         vg_key = "/dev/" + current_vg;
  236.         pesize = targetMap[vg_key,"cyl_size"]:(4*1024*1024);
  237.         y2debug("TTT %1", current_vg );
  238.         }
  239.  
  240.     
  241.     ////////////////////////////////////////
  242.         // Add a new volume group:
  243.         ////////////////////////////////////////
  244.  
  245.         if( ret == `vg_add_vg )
  246.         {
  247.         map vg = DlgCreateVolumeGroup( lvm_vgs );
  248.             map addVG = addVolumeGroup( vg, targetMap, lvm_vgs );
  249.  
  250.             // has the user cancelled the dialog?
  251.             if( !addVG["cancelled"]:false )
  252.         {
  253.         targetMap = Storage::GetTargetMap();
  254.         lvm_vgs = get_vgs( targetMap );
  255.         current_vg = addVG["vg"]:"";
  256.         y2milestone( "new current_vg %1", current_vg );
  257.         }
  258.         }
  259.  
  260.     
  261.     ////////////////////////////////////////
  262.     // Remove volume group:
  263.     ////////////////////////////////////////
  264.     
  265.     if( ret == `vg_remove_vg && current_vg != nil )
  266.         {
  267.         if( HandleRemoveVg( targetMap, current_vg ))
  268.         {
  269.         targetMap = Storage::GetTargetMap();
  270.         lvm_vgs = get_vgs( targetMap );
  271.         current_vg = lvm_vgs[0]:"";
  272.         new_vg_list( lvm_vgs );
  273.         UI::ChangeWidget( `id(`vg), `Value, current_vg);
  274.         y2milestone( " current_vg %1" , current_vg );
  275.         }
  276.         }
  277.  
  278.     
  279.     ////////////////////////////////////////
  280.     // Add a new physical volume:
  281.     ////////////////////////////////////////
  282.     
  283.     
  284.     if( ret == `pv_add && current_vg != nil )
  285.         {
  286.         id = (string)UI::QueryWidget(`id(`pv_table), `CurrentItem );
  287.         y2debug( "WWW ID ADD GROUP %1", id);
  288.         
  289.         if( id!=nil && CheckItemIsNotPv(targetMap,id) && 
  290.             CheckItemIsNotMounted(id) )
  291.         {
  292.         addPhysicalVolume( targetMap, id, current_vg );
  293.         targetMap = Storage::GetTargetMap();
  294.         }
  295.         }
  296.  
  297.     ////////////////////////////////////////
  298.     // Delete a new physical volume:
  299.     ////////////////////////////////////////
  300.     
  301.     if( ret == `pv_delete && current_vg != nil )
  302.         {
  303.         id = (string)UI::QueryWidget(`id(`pv_table), `CurrentItem );
  304.         y2milestone( "id:%1", id );
  305.         
  306.         if( id!=nil && CheckItemIsPv(targetMap,id) )
  307.         {
  308.         string vg = "";
  309.         if( haskey( targetMap, id ))
  310.             vg = targetMap[id,"used_by"]:"";
  311.         else
  312.             vg = Storage::GetPartition( targetMap, id )["used_by"]:"";
  313.         vg = lvmVg(vg);
  314.         y2milestone( "vg=%1", vg );
  315.         if( !check_pv_delete( targetMap, id, vg ) )
  316.             {
  317.             ret = `again;
  318.             continue;
  319.             }
  320.  
  321.         removePhysicalVolume( targetMap, id, vg );
  322.         targetMap = Storage::GetTargetMap();
  323.         }
  324.         }
  325.  
  326.     
  327.     ////////////////////////////////////////
  328.     // Add a new logical volume:
  329.     ////////////////////////////////////////
  330.     
  331.     if( ret == `lv_add )
  332.         {
  333.         if( max_size<pesize )
  334.         {
  335.         //rwalter: add example VG for translators
  336.         // popup text, %1 is volume group, such as ???
  337.         Popup::Message(sformat(_("No space available in the current volume group %1."), current_vg ));
  338.         }
  339.         else
  340.         {
  341.         map<string,any> Lv = $[
  342.                "create"         :       true,
  343.                "used_fs"        :       Partitions::DefaultFs(),
  344.                "size_k"         :       max_size/4/pesize*pesize/1024,
  345.                "stripes"        :       1,
  346.                "format"         :       true,
  347.                "type"           :       `lvm,
  348.                "mount"          :       GetMountPointProposal(targetMap, [Partitions::BootMount()] )
  349.         ];
  350.  
  351.         if( Lv["size_k"]:0 == 0 )
  352.             {
  353.             Lv["size_k"] = max_size/pesize*pesize/1024;
  354.             }
  355.  
  356.         map createLv = DlgCreateEditLogicaVolume( `create, Lv,
  357.                               max_size, current_vg,
  358.                               get_lv_names(targetMap,current_vg),
  359.                               FileSystems::GetAllFileSystems(true,true),
  360.                               "", pesize );
  361.         
  362.         // has an error occured
  363.         if( size(createLv)>0 )
  364.             {
  365.             addLogicalVolume( createLv, current_vg );
  366.             targetMap = Storage::GetTargetMap();
  367.             }
  368.         }
  369.         }
  370.  
  371.     ////////////////////////////////////////
  372.     // Edit/Resize a new logical volume:
  373.     ////////////////////////////////////////
  374.     
  375.     
  376.     if( ret == `lv_edit )
  377.         {
  378.         id = (string)UI::QueryWidget(`id(`lv_table), `CurrentItem );
  379.         y2milestone("id %1", id);
  380.  
  381.         if ( id == nil )
  382.         {
  383.         // Popup text
  384.         Popup::Error(_("No device selected.
  385. Select the device to edit.
  386. "));
  387.         
  388.         }
  389.         else
  390.         {
  391.         HandleEditLv( targetMap, id );
  392.         targetMap = Storage::GetTargetMap();
  393.         }
  394.         }
  395.  
  396.     ////////////////////////////////////////
  397.     // Delete a new logical volume:
  398.     ////////////////////////////////////////
  399.  
  400.     if( ret == `lv_delete )
  401.         {
  402.         id = (string)UI::QueryWidget(`id(`lv_table), `CurrentItem );
  403.         if( id == nil )
  404.         {
  405.         // Popup text
  406.         Popup::Error(_("No device selected.
  407. Select the device to remove.
  408. "));
  409.         }
  410.         else
  411.         {
  412.         HandleRemoveLv( targetMap, id );
  413.         targetMap = Storage::GetTargetMap();
  414.         }
  415.         }
  416.  
  417.     if( ret == `help )
  418.         {
  419.         // LVM Helptext headline
  420.         Popup::LongText( _("LVM Configuration"), `RichText( getLvmHelptext()), 
  421.                            70, 20 );
  422.         }
  423.     
  424.         ////////////////////////////////////////
  425.     // Finish this step
  426.     ////////////////////////////////////////
  427.     
  428.     if( ret == `finish || ret == `apply )
  429.         {
  430.         y2milestone( "END___ %1", ret);
  431.         Storage::SetLvmViewAllMnt( view_all_mnts );
  432.         }
  433.  
  434.     } until (ret == `finish || ret == `apply || ret == `abort);
  435.  
  436.     y2milestone( "END_ %1", ret);
  437.     
  438.     return ret;
  439. }
  440.  
  441. // end
  442.