?? RIGHT := 110 ??
?? NEWTITLE := 'INSTALL_SOFTWARE Utility: CHANGE_INSTALLATION_DEFAULTS Subcommand.' ??
MODULE ram$change_installation_default;

{ PURPOSE:
{   This module contains the command interface and procedures to change the
{   installation defaults.
{
{ DESIGN:
{   The compiled module resides in RAF$LIBRARY.
{
{ NOTES:
{

?? NEWTITLE := 'Global Declarations Referenced by This Module', EJECT ??
?? PUSH (LISTEXT := ON) ??
*copyc rae$install_software_cc
*copyc rae$package_software_cc
*copyc rat$path
?? POP ??
*copyc clp$evaluate_parameters
*copyc clp$trimmed_string_size
*copyc osp$set_status_abnormal
*copyc rav$installation_defaults

?? TITLE := 'Global Declarations Declared by This Module', EJECT ??

?? TITLE := '[XDCL] rap$change_installation_default', EJECT ??

{ PURPOSE:
{   This command interface allows the user to change the installation
{   defaults used by the Install_Software Utility.
{
{ DESIGN:
{   Changing installation defaults revolves around changing the catalogs to
{   which various installation pieces are placed or expected to reside.
{   The default values for these catalogs are in the software
{   maintenance catalog under $system.
{
{   For each pdt parameter associated with this interface there is a path
{   field in the installation defaults variable that stores the current
{   path value.  When a parameter is specified the new value will replace
{   the current value of the associated path field.
{
{   In addition to changing the software matenance catalogs directly, there
{   are three hidden features for the benefit of INSS testing.
{
{   The first feature allows for testing to occur under any user catalog,
{   and still retain the basic catalog structures used by INSTALL_SOFTWARE.
{   By using the SYSTEM_CATALOG parameter, the family and user catalogs of
{   the software_maintenance catalogs are replaced with the catalog path
{   specified.  When an software_maintenance catalog parameter is specified
{   along with the SYSTEM_CATALOG parameter the family and user catalogs of
{   that software_maintenance catalog will not be replaced.  The complete
{   path specified by the software_maintenance catalog parameter will be
{   used instead.
{
{   The second hidden feature allows for storage class to be ignored.  This
{   is specified by IGNORE_STORAGE_CLASS parameter.  When set to TRUE all
{   products will be installed to the PRODUCT storage class which is avaiable
{   to all users.
{
{   The third hidden feature (provided for testing) is to relax ring
{   setting.  This allows the tester to install real products within their
{   own user environment regardless of minimum ring privileges.  Any ring
{   values (declared in the packing list for a file) that are below the
{   user's minimum ring will be set at the user's minimum ring value.  This
{   is specified with the RELAX_RING_SETTINGS parameter.
{
{   The only validation that occurs is checking for $LOCAL as the catalog
{   input.  It is assumed the path designates a catalog and not a file.
{
{   There is no verification that the caller has permission to create
{   catalogs and cycles in the specified catalogs.  It is left to be
{   discovered when the action to create catalogs or cycles occurs.
{
{ NOTES:
{

  PROCEDURE [XDCL] rap$change_installation_default
    (    parameter_list: clt$parameter_list;
     VAR status: ost$status);

{   PROCEDURE chaid_pdt (
{     installation_database, idb, id: file = $optional
{     installation_logs, il: file = $optional
{     correction_bases, cb: (BY_NAME, HIDDEN) file = $optional
{     correction_packages, cp: (BY_NAME, HIDDEN) file = $optional
{     ignore_storage_class,isc : (BY_NAME, HIDDEN) boolean = $optional
{     relax_ring_settings,rrs : (BY_NAME, HIDDEN) boolean = $optional
{     system_catalog,sc : (BY_NAME, HIDDEN) file = $optional
{     status)

?? PUSH (LISTEXT := ON) ??
?? FMT (FORMAT := OFF) ??

  VAR
    pdt: [STATIC, READ, cls$declaration_section] record
      header: clt$pdt_header,
      names: array [1 .. 16] of clt$pdt_parameter_name,
      parameters: array [1 .. 8] of clt$pdt_parameter,
      type1: record
        header: clt$type_specification_header,
      recend,
      type2: record
        header: clt$type_specification_header,
      recend,
      type3: record
        header: clt$type_specification_header,
      recend,
      type4: record
        header: clt$type_specification_header,
      recend,
      type5: record
        header: clt$type_specification_header,
      recend,
      type6: record
        header: clt$type_specification_header,
      recend,
      type7: record
        header: clt$type_specification_header,
      recend,
      type8: record
        header: clt$type_specification_header,
      recend,
    recend := [
    [1,
    [93, 8, 12, 11, 23, 14, 639],
    clc$command, 16, 8, 0, 0, 5, 0, 8, ''], [
    ['CB                             ',clc$abbreviation_entry, 3],
    ['CORRECTION_BASES               ',clc$nominal_entry, 3],
    ['CORRECTION_PACKAGES            ',clc$nominal_entry, 4],
    ['CP                             ',clc$abbreviation_entry, 4],
    ['ID                             ',clc$abbreviation_entry, 1],
    ['IDB                            ',clc$alias_entry, 1],
    ['IGNORE_STORAGE_CLASS           ',clc$nominal_entry, 5],
    ['IL                             ',clc$abbreviation_entry, 2],
    ['INSTALLATION_DATABASE          ',clc$nominal_entry, 1],
    ['INSTALLATION_LOGS              ',clc$nominal_entry, 2],
    ['ISC                            ',clc$abbreviation_entry, 5],
    ['RELAX_RING_SETTINGS            ',clc$nominal_entry, 6],
    ['RRS                            ',clc$abbreviation_entry, 6],
    ['SC                             ',clc$abbreviation_entry, 7],
    ['STATUS                         ',clc$nominal_entry, 8],
    ['SYSTEM_CATALOG                 ',clc$nominal_entry, 7]],
    [
{ PARAMETER 1
    [9, clc$normal_usage_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name, clc$specify_positionally],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 2
    [10, clc$normal_usage_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name, clc$specify_positionally],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 3
    [2, clc$hidden_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 4
    [3, clc$hidden_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 5
    [7, clc$hidden_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 6
    [12, clc$hidden_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 7
    [16, clc$hidden_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name],
    clc$pass_by_value, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0],
{ PARAMETER 8
    [15, clc$normal_usage_entry, clc$non_secure_parameter,
    $clt$parameter_spec_methods[clc$specify_by_name],
    clc$pass_by_reference, clc$immediate_evaluation,
  clc$standard_parameter_checking, 3, clc$optional_parameter, 0, 0]],
{ PARAMETER 1
    [[1, 0, clc$file_type]],
{ PARAMETER 2
    [[1, 0, clc$file_type]],
{ PARAMETER 3
    [[1, 0, clc$file_type]],
{ PARAMETER 4
    [[1, 0, clc$file_type]],
{ PARAMETER 5
    [[1, 0, clc$boolean_type]],
{ PARAMETER 6
    [[1, 0, clc$boolean_type]],
{ PARAMETER 7
    [[1, 0, clc$file_type]],
{ PARAMETER 8
    [[1, 0, clc$status_type]]];

?? FMT (FORMAT := ON) ??
?? POP ??

    CONST
      p$installation_database = 1,
      p$installation_logs = 2,
      p$correction_bases = 3,
      p$correction_packages = 4,
      p$ignore_storage_class = 5,
      p$relax_ring_settings = 6,
      p$system_catalog = 7,
      p$status = 8;

    VAR
      pvt: array [1 .. 8] of clt$parameter_value;

    status.normal := TRUE;

    clp$evaluate_parameters (parameter_list, #SEQ (pdt), NIL, ^pvt, status);
    IF NOT status.normal THEN
      RETURN;
    IFEND;

    validate_parameters (pvt [p$correction_bases], pvt [p$correction_packages], pvt [p$installation_database],
          pvt [p$installation_logs], pvt [p$ignore_storage_class], pvt [p$relax_ring_settings],
          pvt [p$system_catalog], status);
    IF NOT status.normal THEN
      RETURN;
    IFEND;

    IF pvt [p$correction_bases].specified THEN
      rav$installation_defaults.correction_bases.size := clp$trimmed_string_size
            (pvt [p$correction_bases].value^.file_value^);
      rav$installation_defaults.correction_bases.path := pvt [p$correction_bases].value^.file_value^;
    ELSEIF pvt [p$system_catalog].specified THEN
      replace_system_catalog (pvt [p$system_catalog].value^.file_value^,
            rav$installation_defaults.correction_bases);
    IFEND;

    IF pvt [p$correction_packages].specified THEN
      rav$installation_defaults.correction_packages.size :=
            clp$trimmed_string_size (pvt [p$correction_packages].value^.file_value^);
      rav$installation_defaults.correction_packages.path := pvt [p$correction_packages].value^.file_value^;
    ELSEIF pvt [p$system_catalog].specified THEN
      replace_system_catalog (pvt [p$system_catalog].value^.file_value^,
            rav$installation_defaults.correction_packages);
    IFEND;

    IF pvt [p$installation_database].specified THEN
      rav$installation_defaults.installation_database.size :=
            clp$trimmed_string_size (pvt [p$installation_database].value^.file_value^);
      rav$installation_defaults.installation_database.path := pvt [p$installation_database].value^.
            file_value^;
    ELSEIF pvt [p$system_catalog].specified THEN
      replace_system_catalog (pvt [p$system_catalog].value^.file_value^,
            rav$installation_defaults.installation_database);
    IFEND;

    IF pvt [p$installation_logs].specified THEN
      rav$installation_defaults.installation_logs.size := clp$trimmed_string_size
            (pvt [p$installation_logs].value^.file_value^);
      rav$installation_defaults.installation_logs.path := pvt [p$installation_logs].value^.file_value^;
    ELSEIF pvt [p$system_catalog].specified THEN
      replace_system_catalog (pvt [p$system_catalog].value^.file_value^,
            rav$installation_defaults.installation_logs);
    IFEND;

    IF pvt [p$ignore_storage_class].specified THEN
      rav$installation_defaults.ignore_storage_class := pvt [p$ignore_storage_class].value^.boolean_value.
            value;
    IFEND;

    IF pvt [p$relax_ring_settings].specified THEN
      rav$installation_defaults.relax_ring_settings := pvt [p$relax_ring_settings].value^.boolean_value.value;
    IFEND;

    IF pvt [p$system_catalog].specified THEN
      rav$installation_defaults.system_catalog.size := clp$trimmed_string_size
            (pvt [p$system_catalog].value^.file_value^);
      rav$installation_defaults.system_catalog.path := pvt [p$system_catalog].value^.file_value^;
    IFEND;

  PROCEND rap$change_installation_default;

?? TITLE := 'replace_system_catalog', EJECT ??

{ PURPOSE:
{   This procedure replaces the family and user catalogs of a path with the
{   supplied system catalog path.
{
{ DESIGN:
{   The assumptions being made are:  The path contains a family and user
{   catalog, and if only one delimiter ('.') is found the whole path is the
{   master catalog.
{
{ NOTES:
{   This will probably be developed into an interface used in applying the
{   system catalog to the subproduct installation paths.
{

  PROCEDURE replace_system_catalog
    (    system_catalog: fst$file_reference;
     VAR path {input, output} : rat$path);


    CONST
      catalog_delimiter = '.',
      family_user_catalogs = 2;


    VAR
      index: integer,
      number_of_catalogs_found: integer,
      temp_path: rat$path;


    index := 1;
    number_of_catalogs_found := 0;
    temp_path := path;

    WHILE (index <= temp_path.size) AND (number_of_catalogs_found <> family_user_catalogs) DO
      IF temp_path.path (index, 1) = catalog_delimiter THEN
        number_of_catalogs_found := number_of_catalogs_found + 1;
      IFEND;
      index := index + 1;
    WHILEND;

    path.path (1, * ) := '';

    IF index > temp_path.size THEN
      STRINGREP (path.path, path.size, system_catalog);
    ELSE
      STRINGREP (path.path, path.size, system_catalog, temp_path.
            path ((index - 1), (temp_path.size - index + 2)));
    IFEND;

  PROCEND replace_system_catalog;

?? TITLE := 'validate_parameters', EJECT ??

{ PURPOSE:
{   This procedure validates the command interfaces parameters within
{   the context of INSTALL_SOFTWARE.
{
{ DESIGN:
{   The input parameters are check so that at least one of the parameters
{   is specified and that any specified catalog paths cannot be to the
{   $LOCAL catalog.
{
{   Validation errors are returned in the status.  Returns on first
{   error encountered.
{
{ NOTES:
{

  PROCEDURE validate_parameters
    (    correction_bases: clt$parameter_value;
         correction_packages: clt$parameter_value;
         installation_database: clt$parameter_value;
         installation_logs: clt$parameter_value;
         ignore_storage_class: clt$parameter_value;
         relax_ring_settings: clt$parameter_value;
         system_catalog: clt$parameter_value;
     VAR status: ost$status);


    VAR
      local_catalog: [STATIC] rat$path := [7, ':$LOCAL'];

    IF (correction_bases.specified) AND (correction_bases.value^.file_value^ (1,
          local_catalog.size) = local_catalog.path) THEN
      osp$set_status_abnormal ('RA', rae$cannot_use_local_catalog, 'CORRECTION_BASES', status);
      RETURN;
    IFEND;

    IF (correction_packages.specified) AND (correction_packages.value^.file_value^ (1,
          local_catalog.size) = local_catalog.path) THEN
      osp$set_status_abnormal ('RA', rae$cannot_use_local_catalog, 'CORRECTION_PACKAGES', status);
      RETURN;
    IFEND;

    IF (installation_database.specified) AND (installation_database.value^.
          file_value^ (1, local_catalog.size) = local_catalog.path) THEN
      osp$set_status_abnormal ('RA', rae$cannot_use_local_catalog, 'INSTALLATION_DATABASE', status);
      RETURN;
    IFEND;

    IF (installation_logs.specified) AND (installation_logs.value^.file_value^ (1,
          local_catalog.size) = local_catalog.path) THEN
      osp$set_status_abnormal ('RA', rae$cannot_use_local_catalog, 'INSTALLATION_LOGS', status);
      RETURN;
    IFEND;

    IF (system_catalog.specified) AND (system_catalog.value^.file_value^ (1,
          local_catalog.size) = local_catalog.path) THEN
      osp$set_status_abnormal ('RA', rae$cannot_use_local_catalog, 'SYSTEM_CATALOG', status);
      RETURN;
    IFEND;

  PROCEND validate_parameters;

MODEND ram$change_installation_default;
