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
/
inst_target_part.ycp
< prev
next >
Wrap
Text File
|
2006-11-29
|
12KB
|
425 lines
/**
* Module: inst_target_part.ycp
*
* Authors: Andreas Schwab (schwab@suse.de)
* Klaus KΣmpf (kkaempf@suse.de)
*
* Purpose: This module ask the user which partition to use:
* -Determing possible partitions.
* -Ask the user which partition to use.
* -Check the input and return error-messages.
*
* $Id: inst_target_part.ycp 33868 2006-10-30 15:35:53Z fehr $
*/
{
textdomain "storage";
import "Arch";
import "Mode";
import "Popup";
import "Storage";
import "Partitions";
import "Product";
import "FileSystems";
// flag for deleting a windows partition
integer win_partition_to_delete = -1;
// this is the device name !
string target_is = Storage::GetPartDisk();
// fall through to inst_custom_part if target_is not "USE_DISK"
if ( Storage::GetPartMode()!="USE_DISK" || Storage::GetCustomDisplay() )
return Storage::GetExitKey();
// Get test_mode flag from module Mode
boolean test_mode = Mode::test ();
//-------------------------------------------------------------------------
// The action
//-------------------------------------------------------------------------
integer max_partitions = 0;
// The partition number of the first logical partition
integer first_logical_nr = 5;
integer size_of_swap = 0;
integer size_of_boot = 0;
integer max_primary = 0;
// this will tell if automatic partitioning if feasible
boolean can_do_auto = false;
list<integer> unused_region = [ 0, 0 ];
include "partitioning/auto_part_functions.ycp";
include "partitioning/auto_part_prepare.ycp";
include "partitioning/auto_part_ui.ycp";
include "partitioning/partition_defines.ycp";
include "partitioning/auto_part_create.ycp";
import "Label";
import "Popup";
// Displays a popup with the message (can be dismissed with OK).
// After that only `abort or `back is allowed
// Every other user action ==> redisplay message
// Parameter: message to be displayed
// Return : `back or `abort
//
define symbol allow_back_abort_only( string message )
``{
symbol ret = `next;
// Enable back and next buttons independent of the settings
// in installation.ycp so the user has a chance to see the
// popup more than only once.
//
Wizard::EnableNextButton();
Wizard::EnableBackButton();
repeat
{
Popup::Message( message ); // Display the message
ret= (symbol)UI::UserInput(); // get user input
if( ret == `abort )
{
if( !Popup::ReallyAbort(true) )
{
// user didn't want to abort ==> stay in loop
ret = `dummy;
}
}
} until ( ret == `abort || ret == `back );
return( ret );
};
map win_partition = $[]; // may be needed later in the resize case (is also a flag)
// --------------------------------------------------------------
// find the selected target in the map of all possible targets
map<string,map> targetMap = Storage::GetTargetMap();
// description of the choosen target disk
map target = targetMap[target_is]:$[];
if (target == $[])
{
// popup text
Popup::Message(_("Your system can only be configured with the custom partitioning option."));
return `back;
}
// user visible name of target
string targetname = target["name"]:"";
// The current list of partitions
list< map > partitions = target["partitions"]:[];
//-------------------------------------------------------------------------
// The action
//-------------------------------------------------------------------------
// --------------------------------------------------------------
// general settings for automatically created partitions
max_partitions = compute_max_partitions(target);
// How much to allocate for swap
size_of_swap = 1024*1024*Partitions::SwapSizeMb(0);
// --------------------------------------------------------------
// set size of /boot partition
size_of_boot = Partitions::MinimalNeededBootsize();
// The number of possible primary partitions
max_primary = target["max_primary"]:4;
/*==================================================================
*
* prepare_partitions
*
*=================================================================*/
partitions = prepare_partitions (target, partitions);
SCR::Write( .target.ycp, Storage::SaveDumpPath("prepared_partitions"),
partitions);
term vbox = `Empty();
// show list of partitions if any found (else the disk is completely unpartitioned
if( num_primary(partitions)>0 || contains_extended(partitions) )
{
// If there is an unpartitioned area on the disk, ask user to use it
// (this will automatically partition this area)
if( !can_do_auto )
{
// There was not enough space to install Linux.
// Check if we could delete/shrink a windows partition.
//
win_partition = can_resize( partitions );
}
if( win_partition != $[] )
{
// this is the resize case
//
vbox = create_resize_dialog (partitions, target["cyl_size"]:1 );
vbox = add_common_widgets( vbox );
y2milestone ("can resize !");
}
else
{
// this is the normal case
//
map tmp = construct_partition_dialog( partitions,
target["label"]:"",
target["cyl_size"]:1 );
vbox = add_common_widgets( tmp["term"]:`Empty() );
}
}
// no partitions found
else
{
vbox = create_whole_disk_dialog();
vbox = add_common_widgets( vbox );
Storage::SetWholeDisk( true );
}
// Since resize case and normal case have different help texts we need
// to open different dialogs
//
if ( win_partition != $[] ) open_auto_dialog_resize (targetname, vbox);
else open_auto_dialog (targetname, vbox);
// Event handling
symbol ret = nil;
boolean ok = false;
while(!ok)
{
ret = (symbol)Wizard::UserInput();
y2milestone( "USERINPUT ret %1", ret );
if( ret == `lvm && UI::WidgetExists(`id(`evms)) )
UI::ChangeWidget( `id(`evms), `Value, false );
else if( ret == `evms && UI::WidgetExists(`id(`lvm)) )
UI::ChangeWidget( `id(`lvm), `Value, false );
else if( ret == `abort && Popup::ReallyAbort(true))
{
break;
}
else if (ret == `full)
{
// Set all checkboxes
foreach (map pentry, partitions,
``{
symbol ptype = pentry["type"]:`unknown;
integer ui_id = 0;
if( ptype != `extended &&
pentry["fsid"]:0 != Partitions::fsid_mac_hidden )
{
ui_id = pentry["ui_id"]:0;
if (ui_id != 0)
UI::ChangeWidget (`id (ui_id), `Value, true);
}
});
}
else if( ret == `back )
{
ok = true;
}
else if( ret == `next )
{
if( win_partition != $[] )
{
if( UI::QueryWidget( `id(`resize), `Value) == true)
{
// The user decided to shrink his windows.
// Check if this is Windows NT or Windows 2000 (curently not supported)
//
integer local_ret = check_win_nt_system( target );
if( test_mode )
{
// In test mode we _always_ assume there is no system that could cause problem
// so the windows resizer is always accessible (e.g. for screen shots).
local_ret = 0;
}
if( local_ret == 1 ) // Win NT / 2000
{
// The Windows version is Windows NT or Windows 2000. Tell the user that this is currently
// not supported and that he can go back in the installation or abort it.
string explanation = sformat( _("An error has occurred.
The Windows version on your system is
not compatible with the resizing tool.
Shrinking your Windows partition is not possible.
Choose a different disk or abort the installation and
shrink your Windows partition by other means.
"));
ret = allow_back_abort_only( explanation );
return( ret );
}
else if ( local_ret == 2 ) // local error
{
// The Windows version used could not be determined. Tell the user
// he can go back in the installation or abort it.
string explanation = sformat( _("The Windows version of your system could not be determined.
It is therefore not possible to shrink your Windows partition.
Choose a different disk or abort the installation and
shrink your Windows partition by other means.
"));
ret = allow_back_abort_only( explanation );
return( ret );
}
// OK --> No NT or 2000
// Tell the user about the risks of resizing his windows.
// Ask him if he really wants to do it
string explanation = sformat(_("You selected to shrink your Windows partition.
In the next dialog, specify the amount of
Windows space that should be freed for %1.
A data backup is strongly recommended
because data must be reorganized.
Under rare circumstances, this could fail.
Only continue if you have successfully run
the Windows system applications scandisk and defrag.
Really shrink your Windows partition?
"),Product::name);
if ( ! Popup::AnyQuestion( Popup::NoHeadline(), explanation,
// button text
_("&Shrink Windows"), Label::CancelButton(), `focus_yes ))
continue;
string fat_nr = ""+win_partition["nr"]:-1;
y2milestone ("Partition '%1' selected for resize", fat_nr);
Storage::SetDoResize( fat_nr );
break;
}
else
{
// Tell the user about the consequences of deleting his windows.
// Ask him if he really wants to do it
string explanation = _("You selected to delete your Windows partition completely.
All data on this partition will be lost in the process.
Really delete your Windows partition?
");
if ( !Popup::AnyQuestion( Popup::NoHeadline(), explanation,
// button text
_("&Delete Windows"),
Label::CancelButton(),
`focus_yes ))
continue;
y2milestone ("Don't resize, use entire partition");
Storage::SetDoResize( "NO" );
win_partition_to_delete = tointeger( win_partition["nr"]:-1 );
Storage::SetWholeDisk( true );
}
}
// this will be set when the first win partition is marked
// for deletion in the foreach() loop
boolean windows_part_marked_for_deletion = false;
// now loop through partitions and check
// if the partition is selected
partitions = maplist( map p, partitions,
``{
y2milestone( "p:%1", p );
symbol ptype = p["type"]:`unknown;
integer ui_id = 0;
if( ptype != `extended )
{
ui_id = p["ui_id"]:0;
boolean selection = p["fsid"]:0 != Partitions::fsid_mac_hidden &&
(!UI::WidgetExists( `id(ui_id) ) ||
(UI::QueryWidget( `id(ui_id), `Value)==true));
y2milestone( "sel:%1", selection );
if( win_partition_to_delete == p["nr"]:-2 )
{ // -2 !! (not -1 to be different from init)
selection = true;
windows_part_marked_for_deletion = true;
y2milestone( "Windows partition marked for deletion: <%1>",
win_partition_to_delete);
}
else if (windows_part_marked_for_deletion &&
(p["type"]:`dummy == `free))
{
// trailing free partition after (deleted) windows partition
selection = true;
y2milestone ("Trailing `free partition marked for deletion");
}
p["delete"] = selection;
}
return( p );
});
partitions = try_remove_sole_extended( partitions );
y2milestone ("partitions '%1'", partitions);
// Check selection for plausability
string reason = nil;
Storage::SetProposalHome( (boolean)UI::QueryWidget( `id(`home), `Value ));
if( (boolean)UI::QueryWidget( `id(`lvm), `Value )==true )
Storage::SetProposalLvm(true);
else if( (boolean)UI::QueryWidget( `id(`evms), `Value )==true )
Storage::SetProposalEvms(true);
else
{
Storage::SetProposalEvms(false);
Storage::SetProposalLvm(false);
}
ok = create_partitions( targetMap, target, partitions );
Storage::SetProposalDefault();
if( !ok )
{
reason = _("Too few partitions are marked for removal
or the disk is too small.
To install Linux, select more partitions to
remove or select a larger disk.");
display_error_box (reason);
}
}
} // while (true)
if( ret == `next )
{
y2milestone( "Set to inactive" );
Storage::SetPartProposalActive(false);
}
else if( ret == `back || ret == `abort )
{
Storage::RestoreTargetBackup("disk");
}
Storage::SaveExitKey( ret );
return ret;
}