*copyc OSD$DEFAULT_PRAGMATS
MODULE iim$st_chnge_term_conn_defaults;

{ PURPOSE:  This module provides the ring 2 interface to change the
{           default connection attributes for a standalone task.
{           Consequently, subsequent file creations will employ the
{           new attribute values, but previously created files will
{           not be affected.
{
{  DESIGN:  The new attribute values are validated and are then used
{           to replace corresponding values in an IF attributes table
{           which resides in task shared memory.
{
{           For standalone connections, attribute validation consists
{           of verifying that the attribute key is known and that a
{           normal response is received after an attributes change
{           message is sent to the network for the input attribute
{           values.  After validation the new attribute values replace
{           their corresponding attributes in the connection table.
{
?? TITLE := 'MODULE iim$st_chnge_term_conn_defaults' ??

?? PUSH (LISTEXT := ON) ??
*copyc clp$get_ultimate_connection
*copyc ife$error_codes
*copyc iip$clear_lock
*copyc iip$connection_to_vt_attributes
*copyc iip$search_connection_desc
*copyc iip$set_lock
*copyc iip$st_update_actual_attributes
*copyc iip$st_update_default_atributes
*copyc iiv$connection_desc_ptr
*copyc jmp$system_job
*copyc osp$append_status_integer
*copyc osp$append_status_parameter
*copyc osp$set_status_abnormal
*copyc osv$job_pageable_heap
*copyc rmp$get_device_class
?? POP ??

*copyc iip$xlate_local_file_to_session
*copyc pmp$get_job_mode

?? NEWTITLE := 'PROCEDURE iip$st_chnge_term_conn_defaults', EJECT ??

  PROCEDURE [XDCL, #GATE] iip$st_chnge_term_conn_defaults (terminal_file_name: amt$local_file_name;
    connection_attributes: ift$connection_attributes;
    VAR status: ost$status);

    VAR
      connection_desc_ptr: ^iit$connection_description,
      device_assigned: boolean,
      device_class: rmt$device_class,
      file_id: amt$file_identifier,
      i: integer,
      index: integer,
      j: integer,
      job_mode: jmt$job_mode,
      k: integer,
      local_status: ost$status,
      new_connection_attributes: ^ift$connection_attributes,
      response_received: boolean,
      session_file: amt$local_file_name,
      set_of_term_conn_attribute_keys: iit$set_of_term_conn_attr_keys,
      ultimate_prompt_file: amt$local_file_name;

    status.normal := TRUE;

  { Validate the connection attribute keys and, if specified, the values for
  { the OS defined attributes--prompt_file, prompt_file_id, prompt_string,
  { input_timeout, input_timeout_length, input_timeout_purge, and end_of_information.

    set_of_term_conn_attribute_keys := - $iit$set_of_term_conn_attr_keys [];
    FOR i := LOWERBOUND (connection_attributes) TO UPPERBOUND
          (connection_attributes) DO
      IF NOT (connection_attributes [i].key IN set_of_term_conn_attribute_keys)
            THEN
        osp$set_status_abnormal (ifc$interactive_facility_id,
              ife$unknown_attribute_key, '', status);
        k := ORD (connection_attributes [i].key);
        osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
              FALSE, status);
        osp$append_status_parameter (osc$status_parameter_delimiter,
          'IFP$CHANGE_TERM_CONN_ATTRIBUTES', status);
        RETURN;
      IFEND;

      CASE connection_attributes [i].key OF
      = ifc$prompt_file =

        clp$get_ultimate_connection (connection_attributes [i].prompt_file, ultimate_prompt_file, status);
        IF NOT status.normal THEN
          RETURN;
        IFEND;

{ Verify that the file is assigned to a terminal device.

        rmp$get_device_class (ultimate_prompt_file, device_assigned, device_class, local_status);
        IF NOT local_status.normal THEN
          status := local_status;
          RETURN;
        ELSE
          IF NOT device_assigned THEN
            osp$set_status_abnormal (ifc$interactive_facility_id,
                  ife$prompt_file_name_not_found, ultimate_prompt_file, status);
            osp$append_status_parameter (osc$status_parameter_delimiter,
              'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
            RETURN;
          ELSEIF device_class <> rmc$terminal_device THEN
            osp$set_status_abnormal (ifc$interactive_facility_id,
                  ife$prompt_file_name_not_term, ultimate_prompt_file, status);
            osp$append_status_parameter (osc$status_parameter_delimiter,
              'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
            RETURN;
          IFEND;
        IFEND;

      = ifc$prompt_file_identifier =

{ Get the file_name for the file_id.

{ The following code is no-op'ed until BAM provides a way to obtain
{ the local_file_name given the file_id.

{       fetch_attributes [1].key := amc$local_file_name;
{       amp$fetch (connection_attributes [i].prompt_file_identifier, fetch_attributes,
{             local_status);
{       IF NOT local_status.normal THEN
{         status := local_status;
{         RETURN;
{       IFEND;
{
{       clp$get_ultimate_connection (connection_attributes [i].prompt_file, ultimate_prompt_file, status);
{       IF NOT status.normal THEN
{         RETURN;
{       IFEND;
{       IF ultimate_prompt_file <> ultimate_name THEN
{
{ Verify that the file is assigned to a terminal device.
{
{         rmp$get_device_class (fetch_attributes [1].file_name^.local_file_name,
{               device_assigned, device_class, local_status);
{         IF NOT local_status.normal THEN
{           status := local_status;
{           RETURN;
{         ELSE
{           IF NOT device_assigned THEN
{             osp$set_status_abnormal (ifc$interactive_facility_id,
{                   ife$prompt_file_id_not_found, fetch_attributes [1].
{                   file_name^.local_file_name, status);
{             osp$append_status_parameter (osc$status_parameter_delimiter,
{               'IFP$CHANGE_TERM_CONN_ATTRIBUTES', status);
{             RETURN;
{           ELSEIF device_class <> rmc$terminal_device THEN
{             osp$set_status_abnormal (ifc$interactive_facility_id,
{                   ife$prompt_file_id_not_term, fetch_attributes [1].file_name^.
{                   local_file_name, status);
{             osp$append_status_parameter (osc$status_parameter_delimiter,
{               'IFP$CHANGE_TERM_CONN_ATTRIBUTES', status);
{             RETURN;
{           IFEND;
{         IFEND;
{       IFEND;

      = ifc$prompt_string =

        k := connection_attributes [i].prompt_string.size;
        IF ((k < LOWERVALUE (ift$prompt_string_size)) OR (k > UPPERVALUE
              (ift$prompt_string_size))) THEN
          osp$set_status_abnormal (ifc$interactive_facility_id,
                ife$prompt_string_size, '', status);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          k := LOWERVALUE (ift$prompt_string_size);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          k := UPPERVALUE (ift$prompt_string_size);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          osp$append_status_parameter (osc$status_parameter_delimiter,
            'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
          RETURN;
        IFEND;

      = ifc$end_of_information =

        k := connection_attributes [i].end_of_information.size;
        IF ((k < LOWERVALUE (ift$end_of_information_size)) OR (k > UPPERVALUE
              (ift$end_of_information_size))) THEN
          osp$set_status_abnormal (ifc$interactive_facility_id,
                ife$end_of_information_size, '', status);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          k := LOWERVALUE (ift$end_of_information_size);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          k := UPPERVALUE (ift$end_of_information_size);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          osp$append_status_parameter (osc$status_parameter_delimiter,
            'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
          RETURN;
        IFEND;

      = ifc$input_timeout =

        IF ((connection_attributes [i].input_timeout < LOWERVALUE
              (boolean)) OR (connection_attributes [i].input_timeout >
              UPPERVALUE (boolean))) THEN
          osp$set_status_abnormal (ifc$interactive_facility_id,
                ife$input_timeout, 'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
          RETURN;
        IFEND;

      = ifc$input_timeout_length =

        k := connection_attributes [i].input_timeout_length;
        IF ((k < LOWERVALUE (ift$input_timeout_length)) OR (k > UPPERVALUE
              (ift$input_timeout_length))) THEN
          osp$set_status_abnormal (ifc$interactive_facility_id,
                ife$input_timeout_length, '', status);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          k := LOWERVALUE (ift$input_timeout_length);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          k := UPPERVALUE (ift$input_timeout_length);
          osp$append_status_integer (osc$status_parameter_delimiter, k, 10,
                FALSE, status);
          osp$append_status_parameter (osc$status_parameter_delimiter,
            'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
          RETURN;
        IFEND;

      = ifc$input_timeout_purge =

        IF ((connection_attributes [i].input_timeout_purge < LOWERVALUE
              (boolean)) OR (connection_attributes [i].input_timeout_purge >
              UPPERVALUE (boolean))) THEN
          osp$set_status_abnormal (ifc$interactive_facility_id,
                ife$input_timeout_purge, 'IFP$CHANGE_TERM_CONN_DEFAULTS', status);
          RETURN;
        IFEND;

      ELSE
      CASEND;
    FOREND;

    iip$xlate_local_file_to_session (terminal_file_name, session_file, status);
    IF NOT status.normal THEN
      RETURN;
    IFEND;
    iip$search_connection_desc (session_file, connection_desc_ptr);
    IF connection_desc_ptr = NIL THEN
      RETURN;
    IFEND;

    iip$set_lock (connection_desc_ptr^.connection_attributes_lock, osc$wait, status);
    IF NOT status.normal THEN
      RETURN;
    IFEND;

  { Validate the attribute values by changing them in the network and receiving a
  { normal status from the change.

    iip$connection_to_vt_attributes (connection_desc_ptr, connection_attributes,
           status);
    IF status.normal THEN

    { Update the default attributes in the connection table.

      iip$st_update_default_atributes (connection_desc_ptr, connection_attributes,
            ifc$change_term_conn_dflt_req);
      iip$st_update_actual_attributes (connection_desc_ptr, connection_attributes,
            ifc$change_term_conn_dflt_req);
    IFEND;
    iip$clear_lock (connection_desc_ptr^.connection_attributes_lock, local_status);

  PROCEND iip$st_chnge_term_conn_defaults;
MODEND iim$st_chnge_term_conn_defaults;
