ACC SHELL

Path : /usr/share/YaST2/include/partitioning/
File Upload :
Current File : //usr/share/YaST2/include/partitioning/auto_part_prepare.ycp

/**
 * Module: 		auto_part_prepare.ycp
 *
 * Authors: 		Andreas Schwab (schwab@suse.de)
 *			Klaus Kämpf (kkaempf@suse.de)
 *
 * Purpose: 		This module preparse the raw targetMap to
 *			cover the whole disk, including unpartitioned
 *			areas as 'dummy' partitions.
 *
 * $Id: auto_part_prepare.ycp 59894 2009-12-02 14:26:01Z aschnell $
 *
 */
{
textdomain "storage";

import "Partitions";

define list<map> prepare_partitions( map target, list<map> partitions )
    ``{
    // --------------------------------------------------------------
    // The size of a unit (eg. one cylinder)
    integer  bytes_per_unit = target["cyl_size"]:1;
    // The size of the disk in units
    integer disk_size = target["cyl_count"]:1;
    y2milestone( "prepare_partitions bytes_per_unit: %1 disk_size:%2", 
                 bytes_per_unit, disk_size );

    integer size_of_boot = Partitions::MinimalNeededBootsize();
    integer size_of_swap = 1024 * 1024 * Partitions::SwapSizeMb(0);

    // The minimum size needed to install a default system
    integer required_size = 1500 * 1024 * 1024 + size_of_boot + size_of_swap;

    // filter out all "create" paritions, they will be re-created at exit
    //   (this ensures a 'clean' partition list if this dialogue is re-entered

    partitions = filter (map pentry, partitions, ``(!pentry["create"]:false));

    // reset all "delete" paritions, they will be re-created at exit
    //   (this ensures a 'clean' partition list if this dialogue is re-entered

    partitions = maplist (map pentry, partitions, ``(add (pentry, "delete", false)));

    // The region that describes the full disk
    list<integer> full_region = [ 0, disk_size ];

    //-------------------------------------------------------------------------
    // The action
    //-------------------------------------------------------------------------

    // First sort the partitions on the starting cylinder
    partitions = sort( map p1, map p2, partitions,
		       ``(start_of_region (p1["region"]:[])
			  < start_of_region(p2["region"]:[])));

    // now check if automatic partitioning if feasible

    // unpartitioned disk -> yes

    can_do_auto = false;

    if( size(partitions)==0 ) 
	{
	// No partitions -> use the entire disk
	can_do_auto = true;
	unused_region = full_region;
	}

    // extended region with enough free space -> yes

    if( (!can_do_auto) && contains_extended(partitions) ) 
	{
	// Extended partition already exists -> look for free space at
	// the end of it
	unused_region = unused_extended_region (partitions);

	// check if this is enough
	if( (size_of_region(unused_region,bytes_per_unit) > required_size) && 
	    can_create_logical (partitions,5,target["max_logical"]:15))
	    can_do_auto = true;
	}

    // no extended region, but primaries left
    //   if there is enough space after the last defined primary -> yes

    if( !can_do_auto && !contains_extended (partitions) && 
	num_primary(partitions) != max_primary ) 
	{
	map last_partition = partitions[size(partitions)-1]:$[];
	if( ignored_partition( target, last_partition ))
	    last_partition = partitions[size(partitions)-2]:$[];
	list<integer> last_region = last_partition["region"]:[];
	integer last_used = end_of_region(last_region);

	if (last_used < disk_size) 
	    {
	    unused_region = [ last_used, disk_size-last_used ];
	    if (size_of_region (unused_region,bytes_per_unit) > required_size)
		can_do_auto = true;
	    }
	}


    //-------------------------------------------------------------------------
    // Augment the partition list with a description for holes

    integer last_end = 0;
    integer free_nr = 0;

    if( target["label"]:"" == "sun" )
	last_end = 1;

    // first the mid-disk holes

    partitions = flatten( maplist( map pentry, partitions, 
	``{
	list<map> ret = [];
	list<integer> region = pentry["region"]:[];

	if( !ignored_partition( target, pentry ) &&
	    start_of_region (region) > last_end) 
	    {
	    free_nr = free_nr + 1;
	    ret = add (ret, $["type":`free,
			     "region": [ last_end,
				       start_of_region (region) - last_end ]]);
	    // if free space is directly located before extended partition
	    last_end = start_of_region (region);
	    }

	// if this partition is not the extended partition or a ignored
	//    use its end_of_region as last_end
	// on BSD-like partitions, partition # 3 is handled similary

	if( (pentry["type"]:`unknown != `extended) &&
	    !ignored_partition( target, pentry ) )
	    last_end = end_of_region (pentry["region"]:[]);
	return add (ret, pentry);
	}));

    // then the end-disk hole

    if (last_end < disk_size) 
	{
	free_nr = free_nr + 1;
	partitions = add (partitions,
			  $[ "type":`free,
			     "region": [ last_end, disk_size - last_end ]]);
	}

    // now the partitions list spans the whole disk

    //-------------------------------------------------------------------------
    // Create a checkbox for every real (primary or logical) partition
    // and any free space

    // give each partition a unique id

    integer ui_id = 0;
    partitions = maplist (map p, partitions, 
	``{
	ui_id = ui_id + 1;
	p["ui_id"] = ui_id;
	if( p["type"]:`unknown == `free )
	    p["size_k"] = size_of_region( p["region"]:[0,0], bytes_per_unit )/1024;
	if( haskey(p,"mount") && p["mount"]:""!="swap" && !p["inactive"]:false )
	    p = remove( p, "mount" );
	return( p );
	});

    // now the partitions list spans the whole disk
    y2milestone("prepare_partitions partitions: %1", partitions);

    return partitions;
    };
}

ACC SHELL 2018