?? RIGHT := 110 ??                                                                                            
?? NEWTITLE := 'NOS/VE Dump Analyzer : Display Call Command' ??                                               
MODULE dum$display_call_command;                                                                              
                                                                                                              
{ PURPOSE:                                                                                                    
{   This module contains the code for the display_call command.                                               
                                                                                                              
?? NEWTITLE := 'Global Declarations Referenced by This Module', EJECT ??                                      
?? PUSH (LISTEXT := ON) ??                                                                                    
*copyc due$exception_condition_codes                                                                          
*copyc dut$condition_registers                                                                                
?? POP ??                                                                                                     
*copyc clp$close_display                                                                                      
*copyc clp$convert_integer_to_rjstring                                                                        
*copyc clp$get_command_origin                                                                                 
*copyc clp$horizontal_tab_display                                                                             
*copyc clp$new_display_line                                                                                   
*copyc clp$open_display_reference                                                                             
*copyc clp$put_display                                                                                        
*copyc dup$copy_virtual_memory_pva                                                                            
*copyc dup$determine_dump_information                                                                         
*copyc dup$display_exchange_package                                                                           
*copyc dup$display_message                                                                                    
*copyc dup$evaluate_parameters                                                                                
*copyc dup$new_page_procedure                                                                                 
*copyc dup$retrieve_exchange_package                                                                          
*copyc dup$put_item                                                                                           
*copyc ocp$find_debug_address                                                                                 
*copyc osp$append_status_integer                                                                              
*copyc osp$append_status_parameter                                                                            
*copyc osp$set_status_abnormal                                                                                
*copyc osp$disestablish_cond_handler                                                                          
*copyc osp$establish_block_exit_hndlr                                                                         
?? EJECT ??                                                                                                   
*copyc duv$dump_environment_p                                                                                 
*copyc duv$execution_environment                                                                              
*copyc duv$title_data                                                                                         
?? OLDTITLE ??                                                                                                
?? NEWTITLE := 'display_stack_frame', EJECT ??                                                                
                                                                                                              
{ PURPOSE:                                                                                                    
{   This procedure displays a stack frame.                                                                    
                                                                                                              
  PROCEDURE display_stack_frame                                                                               
    (    current_stack_frame: ost$pva;                                                                        
         exchange_package_p: ^dut$exchange_package;                                                           
         processor: 0 .. duc$de_maximum_processors;                                                           
         display_save_area: boolean;                                                                          
     VAR next_stack_frame_pva: ost$pva;                                                                       
     VAR display_control: clt$display_control;                                                                
     VAR status: ost$status);                                                                                 
                                                                                                              
    TYPE                                                                                                      
      t$a_register = RECORD                                                                                   
        CASE t$a_register_types OF                                                                            
        = c$a4_ucr =                                                                                          
          user_condition_register: ost$user_conditions,                                                       
        = c$a5_mcr =                                                                                          
          monitor_condition_register: ost$monitor_conditions,                                                 
        = c$a_n =                                                                                             
          two_bytes: 0 .. 0ffff(16),                                                                          
          a_register: ost$pva,                                                                                
        CASEND,                                                                                               
      RECEND,                                                                                                 
                                                                                                              
      t$a_register_types = (c$a4_ucr, c$a5_mcr, c$a_n),                                                       
                                                                                                              
      t$ascii_characters = SET OF 0 .. 255,                                                                   
                                                                                                              
      t$frame_descriptor = PACKED RECORD                                                                      
        critical_frame_flag: boolean,                                                                         
        on_condition_flag: boolean,                                                                           
        undefined: 0 .. 3(16),                                                                                
        x_starting: ost$register_number,                                                                      
        a_terminating: ost$register_number,                                                                   
        x_terminating: ost$register_number,                                                                   
      RECEND,                                                                                                 
                                                                                                              
      t$minimum_save_area = PACKED RECORD                                                                     
        CASE boolean OF                                                                                       
        = TRUE =                                                                                              
          p_register: ost$p_register,                                                                         
          vmid: ost$virtual_machine_identifier,                                                               
          undefined: 0 .. 0fff(16),                                                                           
          a0_dynamic_space_pointer: ost$pva,                                                                  
          frame_descriptor: t$frame_descriptor,                                                               
          a1_current_stack_frame: ost$pva,                                                                    
          user_mask: ost$user_conditions,                                                                     
          a2_previous_save_area: ost$pva,                                                                     
        = FALSE =                                                                                             
          p: t$a_register,                                                                                    
          a_registers: ARRAY [0 .. 2] OF t$a_register,                                                        
        CASEND,                                                                                               
      RECEND,                                                                                                 
                                                                                                              
      t$stack_frame_seq = SEQ (REP 1 OF t$minimum_save_area, REP 13 OF t$a_register,                          
            REP 16 OF ost$x_register),                                                                        
                                                                                                              
      t$x_register = RECORD                                                                                   
        CASE boolean OF                                                                                       
        = TRUE =                                                                                              
          int: ost$x_register,                                                                                
        = FALSE =                                                                                             
          part: ARRAY [0 .. 3] OF 0 .. 0ffff(16),                                                             
        CASEND,                                                                                               
      RECEND;                                                                                                 
                                                                                                              
    VAR                                                                                                       
      a_registers_p: ^ARRAY [ * ] OF t$a_register,                                                            
      a_terminating: ost$register_number,                                                                     
      access_data: dut$access_data,                                                                           
      blank: t$ascii_characters,                                                                              
      bytes_returned: ost$segment_length,                                                                     
      current_a_register: ost$register_number,                                                                
      current_x_register: ost$register_number,                                                                
      display_string: string (osc$max_string_size),                                                           
      found: boolean,                                                                                         
      found_blank: boolean,                                                                                   
      ignore_status: ost$status,                                                                              
      index: integer,                                                                                         
      interactive: boolean,                                                                                   
      local_status: ost$status,                                                                               
      mask_difference: ost$user_conditions,                                                                   
      maximum_frame_saved: boolean,                                                                           
      minimum_save_area_p: ^t$minimum_save_area,                                                              
      module_name: pmt$program_name,                                                                          
      monitor_condition: ost$monitor_condition,                                                               
      monitor_conditions: ost$monitor_conditions,                                                             
      offset_in_section: ost$segment_offset,                                                                  
      second_display_string: string (35),                                                                     
      section_name: pmt$program_name,                                                                         
      stack_frame_p: ^SEQ ( * ),                                                                              
      stack_frame_seq: t$stack_frame_seq,                                                                     
      stack_frame_seq_p: ^t$stack_frame_seq,                                                                  
      string_length: integer,                                                                                 
      trap_occurred: boolean,                                                                                 
      user_condition: ost$user_condition,                                                                     
      user_conditions: ost$user_conditions,                                                                   
      user_mask: ost$user_conditions,                                                                         
      x_part: 0 .. 3,                                                                                         
      x_registers_p: ^ARRAY [ * ] OF t$x_register,                                                            
      x_starting: ost$register_number,                                                                        
      x_terminating: ost$register_number;                                                                     
                                                                                                              
    status.normal := TRUE;                                                                                    
                                                                                                              
    stack_frame_seq_p := ^stack_frame_seq;                                                                    
    RESET stack_frame_seq_p;                                                                                  
    user_mask := exchange_package_p^.user_mask;                                                               
                                                                                                              
    { Retrieve the current stack frame from the restart file.                                                 
                                                                                                              
    NEXT stack_frame_p: [[REP #SIZE (t$stack_frame_seq) OF cell]] IN stack_frame_seq_p;                       
    IF stack_frame_p = NIL THEN                                                                               
      osp$set_status_abnormal (duc$dump_analyzer_id, due$nil_pointer, '', status);                            
      RETURN;  {---->                                                                                         
    IFEND;                                                                                                    
    RESET stack_frame_p;                                                                                      
    dup$copy_virtual_memory_pva (current_stack_frame, exchange_package_p^, processor,                         
          #SIZE (t$stack_frame_seq), TRUE, bytes_returned, stack_frame_p, access_data, status);               
    IF NOT status.normal THEN                                                                                 
      IF status.condition = due$address_translation_error THEN                                                
        dup$display_message (status, display_control);                                                        
        osp$set_status_abnormal (duc$dump_analyzer_id, due$invalid_sf_pointer, '', status);                   
        osp$append_status_parameter (osc$status_parameter_delimiter, ', segment = ',  status);                
        osp$append_status_integer (osc$status_parameter_delimiter, current_stack_frame.seg, 16, TRUE, status);
        osp$append_status_parameter (osc$status_parameter_delimiter, ', offset = ', status);                  
        osp$append_status_integer (osc$status_parameter_delimiter, current_stack_frame.offset, 16, TRUE,      
              status);                                                                                        
        clp$get_command_origin (interactive, local_status);                                                   
        IF local_status.normal AND NOT interactive THEN                                                       
          dup$display_message (status, display_control);                                                      
        IFEND;                                                                                                
      IFEND;                                                                                                  
      RETURN;  {---->                                                                                         
    IFEND;                                                                                                    
    IF bytes_returned = 0 THEN                                                                                
      osp$set_status_abnormal (duc$dump_analyzer_id, due$display_terminated, 'This frame is paged out.',      
            status);                                                                                          
      dup$display_message (status, display_control);                                                          
      RETURN;  {---->                                                                                         
    IFEND;                                                                                                    
                                                                                                              
    { Retrieve the minimum save area, the A registers and the X registers from the stack frame.               
                                                                                                              
    RESET stack_frame_p;                                                                                      
    minimum_save_area_p := NIL;                                                                               
    a_registers_p := NIL;                                                                                     
    x_registers_p := NIL;                                                                                     
    IF bytes_returned >= #SIZE (t$minimum_save_area) THEN                                                     
      NEXT minimum_save_area_p IN stack_frame_p;                                                              
      IF minimum_save_area_p = NIL THEN                                                                       
        osp$set_status_abnormal (duc$dump_analyzer_id, due$nil_pointer, '', status);                          
        RETURN;  {---->                                                                                       
      IFEND;                                                                                                  
      next_stack_frame_pva := minimum_save_area_p^.a2_previous_save_area;                                     
      a_terminating := minimum_save_area_p^.frame_descriptor.a_terminating;                                   
      x_starting := minimum_save_area_p^.frame_descriptor.x_starting;                                         
      x_terminating := minimum_save_area_p^.frame_descriptor.x_terminating;                                   
      maximum_frame_saved := (a_terminating = 0f(16)) AND (x_starting = 0) AND (x_terminating = 0f(16));      
      IF a_terminating > 2 THEN                                                                               
        NEXT a_registers_p: [3 .. a_terminating] IN stack_frame_p;                                            
        IF a_registers_p = NIL THEN                                                                           
          osp$set_status_abnormal (duc$dump_analyzer_id, due$nil_pointer, '', status);                        
          RETURN;  {---->                                                                                     
        IFEND;                                                                                                
      IFEND;                                                                                                  
      IF (a_terminating >= 2) AND (x_starting <= x_terminating) THEN                                          
        NEXT x_registers_p: [x_starting .. x_terminating] IN stack_frame_p;                                   
        IF x_registers_p = NIL THEN                                                                           
          osp$set_status_abnormal (duc$dump_analyzer_id, due$nil_pointer, '', status);                        
          RETURN;  {---->                                                                                     
        IFEND;                                                                                                
      IFEND                                                                                                   
    IFEND;                                                                                                    
                                                                                                              
    clp$horizontal_tab_display (display_control, 13, ignore_status);                                          
                                                                                                              
    ocp$find_debug_address (minimum_save_area_p^.p_register.pva.seg,                                          
          minimum_save_area_p^.p_register.pva.offset, found, module_name, section_name, offset_in_section,    
          status);                                                                                            
    IF NOT status.normal THEN                                                                                 
      IF (status.condition <> oce$e_debug_table_not_open) THEN                                                
        RETURN;  {---->                                                                                       
      IFEND;                                                                                                  
      status.normal := TRUE;                                                                                  
      found := FALSE;                                                                                         
    IFEND;                                                                                                    
                                                                                                              
    IF found THEN                                                                                             
      blank := $t$ascii_characters[$INTEGER(' ')];                                                            
      #SCAN (blank, section_name, index, found_blank);                                                        
      STRINGREP (display_string, string_length, section_name (1, index - 1), ' +', offset_in_section: #(16),  
            '(16)');                                                                                          
      dup$put_item (display_string (1, string_length), clc$no_trim, amc$continue, display_control);           
      STRINGREP (display_string, string_length, ' in ', module_name);                                         
      dup$put_item (display_string (1, string_length), clc$trim, amc$terminate, display_control);             
    ELSE                                                                                                      
      STRINGREP (display_string, string_length, ' P = ', minimum_save_area_p^.p_register.pva.ring: 2: #(16),  
            minimum_save_area_p^.p_register.pva.seg: 4: #(16),                                                
            minimum_save_area_p^.p_register.pva.offset: 10: #(16));                                           
      dup$put_item (display_string (1, string_length), clc$no_trim, amc$terminate, display_control);          
    IFEND;                                                                                                    
                                                                                                              
   /display_summary/                                                                                          
    BEGIN                                                                                                     
      IF (bytes_returned >= 10(16)) AND (minimum_save_area_p^.vmid <> osc$cyber_180_mode) AND                 
            (minimum_save_area_p^.vmid <> osc$cyber_170_mode) THEN                                            
        osp$set_status_abnormal (duc$dump_analyzer_id, due$invalid_stack_frame,                               
              ' The vmid field is not either 180 mode or 170 mode', local_status);                            
        dup$display_message (local_status, display_control);                                                  
        EXIT /display_summary/;  {---->                                                                       
      IFEND;                                                                                                  
                                                                                                              
      IF bytes_returned >= 18(16) THEN                                                                        
        IF a_terminating < 2 THEN                                                                             
          osp$set_status_abnormal (duc$dump_analyzer_id, due$invalid_stack_frame,                             
                ' In the sfsa descriptor, the terminating a register is less than 2.', local_status);         
          dup$display_message (local_status, display_control);                                                
          EXIT /display_summary/;  {---->                                                                     
        IFEND;                                                                                                
        IF minimum_save_area_p^.frame_descriptor.critical_frame_flag THEN                                     
          clp$put_display (display_control, ' --  The critical frame flag is set for this frame.',            
                clc$no_trim, ignore_status);                                                                  
        IFEND;                                                                                                
        IF minimum_save_area_p^.frame_descriptor.on_condition_flag THEN                                       
          clp$put_display (display_control, ' --  The on condition flag is set for this frame.', clc$no_trim, 
                ignore_status);                                                                               
        IFEND;                                                                                                
      IFEND;                                                                                                  
                                                                                                              
      IF bytes_returned >= #SIZE (t$minimum_save_area) THEN                                                   
        IF user_mask <> minimum_save_area_p^.user_mask THEN                                                   
          clp$put_display (display_control, ' --  The user mask has changed:', clc$no_trim, ignore_status);   
          mask_difference := user_mask - minimum_save_area_p^.user_mask;                                      
          FOR user_condition := osc$privileged_instruction TO osc$invalid_bdp_data DO                         
            IF user_condition IN mask_difference THEN                                                         
              dup$put_item (' --  ', clc$no_trim, amc$start, display_control);                                
              dup$put_item (duv$cr_user_condition_reg_def [(duc$cr_user_condition_lower_bit +                 
                    $INTEGER (user_condition))], clc$trim, amc$continue, display_control);                    
              dup$put_item (' is now de-selected.', clc$no_trim, amc$terminate, display_control);             
            IFEND;                                                                                            
          FOREND;                                                                                             
          mask_difference := minimum_save_area_p^.user_mask - user_mask;                                      
          FOR user_condition := osc$privileged_instruction TO osc$invalid_bdp_data DO                         
            IF user_condition IN mask_difference THEN                                                         
              dup$put_item (' --  ', clc$no_trim, amc$start, display_control);                                
              dup$put_item (duv$cr_user_condition_reg_def [(duc$cr_user_condition_lower_bit +                 
                    $INTEGER (user_condition))], clc$trim, amc$continue, display_control);                    
              dup$put_item (' is now selected.', clc$no_trim, amc$terminate, display_control);                
            IFEND;                                                                                            
          FOREND;                                                                                             
          user_mask := minimum_save_area_p^.user_mask;                                                        
        IFEND;                                                                                                
      IFEND;                                                                                                  
                                                                                                              
      trap_occurred := FALSE;                                                                                 
      IF bytes_returned >= 38(16) THEN                                                                        
        IF maximum_frame_saved THEN                                                                           
          user_conditions := a_registers_p^ [4].user_condition_register * user_mask;                          
          monitor_conditions := a_registers_p^ [5].monitor_condition_register *                               
                exchange_package_p^.monitor_mask;                                                             
          trap_occurred := (user_conditions <> $ost$user_conditions[ ]) OR                                    
                (monitor_conditions <> $ost$monitor_conditions[ ]);                                           
          IF trap_occurred THEN                                                                               
            clp$put_display (display_control, 'This is probably a trap frame.', clc$no_trim, ignore_status);  
          IFEND;                                                                                              
          IF user_conditions <> $ost$user_conditions [ ] THEN                                                 
            dup$put_item ('user conditions:', clc$no_trim, amc$start, display_control);                       
            FOR user_condition := osc$privileged_instruction TO osc$invalid_bdp_data DO                       
              IF user_condition IN user_conditions THEN                                                       
                clp$horizontal_tab_display (display_control, 21, ignore_status);                              
                dup$put_item (duv$cr_user_condition_reg_def [(duc$cr_user_condition_lower_bit +               
                      $INTEGER (user_condition))], clc$trim, amc$terminate, display_control);                 
              IFEND;                                                                                          
            FOREND;                                                                                           
          IFEND;                                                                                              
          IF monitor_conditions <> $ost$monitor_conditions [ ] THEN                                           
            dup$put_item ('monitor conditions:', clc$no_trim, amc$start, display_control);                    
            FOR monitor_condition := osc$detected_uncorrected_err TO osc$trap_exception DO                    
              IF monitor_condition IN monitor_conditions THEN                                                 
                clp$horizontal_tab_display (display_control, 21, ignore_status);                              
                dup$put_item (duv$cr_mtr_condition_reg_def [(duc$cr_mtr_condition_lower_bit +                 
                      $INTEGER (monitor_condition))], clc$trim, amc$terminate, display_control);              
              IFEND;                                                                                          
            FOREND;                                                                                           
          IFEND;                                                                                              
        IFEND;                                                                                                
      IFEND;                                                                                                  
    END /display_summary/;                                                                                    
                                                                                                              
   /display_frame/                                                                                            
    BEGIN                                                                                                     
      IF display_save_area THEN                                                                               
        clp$new_display_line (display_control, 1, ignore_status);                                             
        display_string := ' ';                                                                                
        clp$convert_integer_to_rjstring (minimum_save_area_p^.p.two_bytes, 16, FALSE, '0',                    
              display_string (1, 4), ignore_status);                                                          
        clp$horizontal_tab_display (display_control, 14, ignore_status);                                      
        dup$put_item (display_string (1, 4), clc$no_trim, amc$continue, display_control);                     
        STRINGREP (display_string, string_length, ' P  ',                                                     
              minimum_save_area_p^.p_register.pva.ring: 2: #(16),                                             
              minimum_save_area_p^.p_register.pva.seg: 4: #(16),                                              
              minimum_save_area_p^.p_register.pva.offset: 10: #(16));                                         
        clp$horizontal_tab_display (display_control, 24, ignore_status);                                      
        dup$put_item (display_string (1, string_length), clc$no_trim, amc$terminate, display_control);        
                                                                                                              
        IF bytes_returned < 10(16) THEN                                                                       
          EXIT /display_frame/;  {---->                                                                       
        IFEND;                                                                                                
                                                                                                              
        dup$put_item ('vmid', clc$no_trim, amc$start, display_control);                                       
        display_string := ' ';                                                                                
        clp$convert_integer_to_rjstring (minimum_save_area_p^.a_registers[0].two_bytes, 16, FALSE, '0',       
              display_string (1, 4), ignore_status);                                                          
        clp$horizontal_tab_display (display_control, 14, ignore_status);                                      
        dup$put_item (display_string (1, 4), clc$no_trim, amc$continue, display_control);                     
        STRINGREP (display_string, string_length, ' A0 ',                                                     
              minimum_save_area_p^.a0_dynamic_space_pointer.ring: 2: #(16),                                   
              minimum_save_area_p^.a0_dynamic_space_pointer.seg: 4: #(16),                                    
              minimum_save_area_p^.a0_dynamic_space_pointer.offset: 10: #(16), ' (dsp)');                     
        clp$horizontal_tab_display (display_control, 24, ignore_status);                                      
        dup$put_item (display_string (1, string_length), clc$no_trim, amc$terminate, display_control);        
                                                                                                              
        IF bytes_returned < 18(16) THEN                                                                       
          EXIT /display_frame/;  {---->                                                                       
        IFEND;                                                                                                
                                                                                                              
        dup$put_item ('sfsa desc', clc$no_trim, amc$start, display_control);                                  
        display_string := ' ';                                                                                
        clp$convert_integer_to_rjstring (minimum_save_area_p^.a_registers[1].two_bytes, 16, FALSE, '0',       
              display_string (1, 4), ignore_status);                                                          
        clp$horizontal_tab_display (display_control, 14, ignore_status);                                      
        dup$put_item (display_string (1, 4), clc$no_trim, amc$continue, display_control);                     
        STRINGREP (display_string, string_length, ' A1 ',                                                     
              minimum_save_area_p^.a1_current_stack_frame.ring: 2: #(16),                                     
              minimum_save_area_p^.a1_current_stack_frame.seg: 4: #(16),                                      
              minimum_save_area_p^.a1_current_stack_frame.offset: 10: #(16), ' (csf)');                       
        clp$horizontal_tab_display (display_control, 24, ignore_status);                                      
        dup$put_item (display_string (1, string_length), clc$no_trim, amc$terminate, display_control);        
                                                                                                              
        IF bytes_returned < 20(16) THEN                                                                       
          EXIT /display_frame/;  {---->                                                                       
        IFEND;                                                                                                
                                                                                                              
        dup$put_item ('user mask', clc$no_trim, amc$start, display_control);                                  
        display_string := ' ';                                                                                
        clp$convert_integer_to_rjstring (minimum_save_area_p^.a_registers [2].two_bytes, 16, FALSE, '0',      
              display_string (1, 4), ignore_status);                                                          
        clp$horizontal_tab_display (display_control, 14, ignore_status);                                      
        dup$put_item (display_string (1, 4), clc$no_trim, amc$continue, display_control);                     
        STRINGREP (display_string, string_length, ' A2 ',                                                     
              minimum_save_area_p^.a2_previous_save_area.ring: 2: #(16),                                      
              minimum_save_area_p^.a2_previous_save_area.seg: 4: #(16),                                       
              minimum_save_area_p^.a2_previous_save_area.offset: 10: #(16), ' (psa)');                        
        clp$horizontal_tab_display (display_control, 24, ignore_status);                                      
        dup$put_item (display_string (1, string_length), clc$no_trim, amc$terminate, display_control);        
                                                                                                              
        FOR current_a_register := 3 TO a_terminating DO                                                       
          IF bytes_returned < ((current_a_register + 2) * 8) THEN                                             
            EXIT /display_frame/;  {---->                                                                     
          IFEND;                                                                                              
          IF (current_a_register = 4) AND trap_occurred THEN                                                  
            dup$put_item ('ucr', clc$no_trim, amc$start, display_control);                                    
          ELSEIF (current_a_register = 5) AND trap_occurred THEN                                              
            dup$put_item ('mcr', clc$no_trim, amc$start, display_control);                                    
          IFEND;                                                                                              
          display_string := ' ';                                                                              
          clp$convert_integer_to_rjstring (a_registers_p^ [current_a_register].two_bytes, 16, FALSE, '0',     
                display_string (1, 4), ignore_status);                                                        
          clp$horizontal_tab_display (display_control, 14, ignore_status);                                    
          dup$put_item (display_string (1, 4), clc$no_trim, amc$continue, display_control);                   
          STRINGREP (second_display_string, string_length, current_a_register: 2: #(16));                     
          STRINGREP (display_string, string_length, ' A', second_display_string (2), ' ',                     
                a_registers_p^ [current_a_register].a_register.ring: 2: #(16),                                
                a_registers_p^ [current_a_register].a_register.seg: 4: #(16),                                 
                a_registers_p^ [current_a_register].a_register.offset: 10: #(16));                            
          clp$horizontal_tab_display (display_control, 24, ignore_status);                                    
          dup$put_item (display_string (1, string_length), clc$trim, amc$terminate, display_control);         
        FOREND;                                                                                               
                                                                                                              
        clp$new_display_line (display_control, 1, ignore_status);                                             
                                                                                                              
        FOR current_x_register := x_starting TO x_terminating DO                                              
          IF bytes_returned < ((a_terminating + 2) + (current_x_register - x_starting)) * 8 THEN              
            EXIT /display_frame/;  {---->                                                                     
          IFEND;                                                                                              
          display_string := '';                                                                               
          STRINGREP (display_string (1, 2), string_length, current_x_register: 2: #(16));                     
          display_string (1) := 'X';                                                                          
          FOR x_part := 0 TO 3 DO                                                                             
            clp$convert_integer_to_rjstring (x_registers_p^ [current_x_register].part[x_part], 16, FALSE, '0',
                  display_string (4 + x_part * 5, 4), ignore_status);                                         
          FOREND;                                                                                             
          clp$horizontal_tab_display (display_control, 11, ignore_status);                                    
          dup$put_item (display_string (1, 22), clc$no_trim, amc$terminate, display_control);                 
        FOREND;                                                                                               
                                                                                                              
      IFEND;                                                                                                  
    END /display_frame/;                                                                                      
                                                                                                              
    IF bytes_returned < #SIZE (t$minimum_save_area) THEN                                                      
      osp$set_status_abnormal (duc$dump_analyzer_id, due$display_terminated,                                  
            'The remainder of this frame is paged out.', status);                                             
      dup$display_message (status, display_control);                                                          
    IFEND;                                                                                                    
                                                                                                              
  PROCEND display_stack_frame;                                                                                
?? OLDTITLE ??                                                                                                
?? NEWTITLE := 'dup$display_call_command', EJECT ??                                                           
                                                                                                              
{ PURPOSE:                                                                                                    
{   This procedure displays the call chain.                                                                   
                                                                                                              
  PROCEDURE [XDCL] dup$display_call_command                                                                   
    (    parameter_list: clt$parameter_list;                                                                  
     VAR status: ost$status);                                                                                 
                                                                                                              
{ PROCEDURE display_call, disc (                                                                              
{   exchange, e: any of                                                                                       
{       key                                                                                                   
{         (active, a)                                                                                         
{         (monitor, m)                                                                                        
{         (job, j)                                                                                            
{       keyend                                                                                                
{       integer 0..0ffffffff(16)                                                                              
{     anyend = 0..0ffffffff(16)                                                                               
{   processor, p: integer 0..3 = 0                                                                            
{   count, c: any of                                                                                          
{       key                                                                                                   
{         all                                                                                                 
{       keyend                                                                                                
{       integer 1..0ffffffff(16)                                                                              
{     anyend = all                                                                                            
{   start, s: any of                                                                                          
{       key                                                                                                   
{         (exchange_package, ep)                                                                              
{       keyend                                                                                                
{       integer 0..0ffffffff(16)                                                                              
{     anyend = exchange_package                                                                               
{   display_option, do: list 1..2 of key                                                                      
{       (full, f)                                                                                             
{       (brief, b)                                                                                            
{       (save, s)                                                                                             
{     keyend = brief                                                                                          
{   title, t: string 1..31 = 'display_call'                                                                   
{   output, o: file = $optional                                                                               
{   status)                                                                                                   
                                                                                                              
?? PUSH (LISTEXT := ON) ??                                                                                    
?? FMT (FORMAT := OFF) ??                                                                                     
                                                                                                              
  VAR                                                                                                         
    pdt: [STATIC, READ, cls$declaration_section] record                                                       
      header: clt$pdt_header,                                                                                 
      names: array [1 .. 15] of clt$pdt_parameter_name,                                                       
      parameters: array [1 .. 8] of clt$pdt_parameter,                                                        
      type1: record                                                                                           
        header: clt$type_specification_header,                                                                
        qualifier: clt$union_type_qualifier,                                                                  
        type_size_1: clt$type_specification_size,                                                             
        element_type_spec_1: record                                                                           
          header: clt$type_specification_header,                                                              
          qualifier: clt$keyword_type_qualifier,                                                              
          keyword_specs: array [1 .. 6] of clt$keyword_specification,                                         
        recend,                                                                                               
        type_size_2: clt$type_specification_size,                                                             
        element_type_spec_2: record                                                                           
          header: clt$type_specification_header,                                                              
          qualifier: clt$integer_type_qualifier,                                                              
        recend,                                                                                               
        default_value: string (16),                                                                           
      recend,                                                                                                 
      type2: record                                                                                           
        header: clt$type_specification_header,                                                                
        qualifier: clt$integer_type_qualifier,                                                                
        default_value: string (1),                                                                            
      recend,                                                                                                 
      type3: record                                                                                           
        header: clt$type_specification_header,                                                                
        qualifier: clt$union_type_qualifier,                                                                  
        type_size_1: clt$type_specification_size,                                                             
        element_type_spec_1: record                                                                           
          header: clt$type_specification_header,                                                              
          qualifier: clt$keyword_type_qualifier,                                                              
          keyword_specs: array [1 .. 1] of clt$keyword_specification,                                         
        recend,                                                                                               
        type_size_2: clt$type_specification_size,                                                             
        element_type_spec_2: record                                                                           
          header: clt$type_specification_header,                                                              
          qualifier: clt$integer_type_qualifier,                                                              
        recend,                                                                                               
        default_value: string (3),                                                                            
      recend,                                                                                                 
      type4: record                                                                                           
        header: clt$type_specification_header,                                                                
        qualifier: clt$union_type_qualifier,                                                                  
        type_size_1: clt$type_specification_size,                                                             
        element_type_spec_1: record                                                                           
          header: clt$type_specification_header,                                                              
          qualifier: clt$keyword_type_qualifier,                                                              
          keyword_specs: array [1 .. 2] of clt$keyword_specification,                                         
        recend,                                                                                               
        type_size_2: clt$type_specification_size,                                                             
        element_type_spec_2: record                                                                           
          header: clt$type_specification_header,                                                              
          qualifier: clt$integer_type_qualifier,                                                              
        recend,                                                                                               
        default_value: string (16),                                                                           
      recend,                                                                                                 
      type5: record                                                                                           
        header: clt$type_specification_header,                                                                
        qualifier: clt$list_type_qualifier_v2,                                                                
        element_type_spec: record                                                                             
          header: clt$type_specification_header,                                                              
          qualifier: clt$keyword_type_qualifier,                                                              
          keyword_specs: array [1 .. 6] of clt$keyword_specification,                                         
        recend,                                                                                               
        default_value: string (5),                                                                            
      recend,                                                                                                 
      type6: record                                                                                           
        header: clt$type_specification_header,                                                                
        qualifier: clt$string_type_qualifier,                                                                 
        default_value: string (14),                                                                           
      recend,                                                                                                 
      type7: record                                                                                           
        header: clt$type_specification_header,                                                                
      recend,                                                                                                 
      type8: record                                                                                           
        header: clt$type_specification_header,                                                                
      recend,                                                                                                 
    recend := [                                                                                               
    [1,                                                                                                       
    [103, 1, 13, 10, 42, 29, 487],                                                                            
    clc$command, 15, 8, 0, 0, 0, 0, 8, ''], [                                                                 
    ['C                              ',clc$abbreviation_entry, 3],                                            
    ['COUNT                          ',clc$nominal_entry, 3],                                                 
    ['DISPLAY_OPTION                 ',clc$nominal_entry, 5],                                                 
    ['DO                             ',clc$abbreviation_entry, 5],                                            
    ['E                              ',clc$abbreviation_entry, 1],                                            
    ['EXCHANGE                       ',clc$nominal_entry, 1],                                                 
    ['O                              ',clc$abbreviation_entry, 7],                                            
    ['OUTPUT                         ',clc$nominal_entry, 7],                                                 
    ['P                              ',clc$abbreviation_entry, 2],                                            
    ['PROCESSOR                      ',clc$nominal_entry, 2],                                                 
    ['S                              ',clc$abbreviation_entry, 4],                                            
    ['START                          ',clc$nominal_entry, 4],                                                 
    ['STATUS                         ',clc$nominal_entry, 8],                                                 
    ['T                              ',clc$abbreviation_entry, 6],                                            
    ['TITLE                          ',clc$nominal_entry, 6]],                                                
    [                                                                                                         
{ PARAMETER 1                                                                                                 
    [6, 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, 269,                        
  clc$optional_default_parameter, 0, 16],                                                                     
{ 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, 20,                         
  clc$optional_default_parameter, 0, 1],                                                                      
{ PARAMETER 3                                                                                                 
    [2, 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, 84,                         
  clc$optional_default_parameter, 0, 3],                                                                      
{ PARAMETER 4                                                                                                 
    [12, 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, 121,                        
  clc$optional_default_parameter, 0, 16],                                                                     
{ PARAMETER 5                                                                                                 
    [3, 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, 245,                        
  clc$optional_default_parameter, 0, 5],                                                                      
{ PARAMETER 6                                                                                                 
    [15, 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, 8,                          
  clc$optional_default_parameter, 0, 14],                                                                     
{ PARAMETER 7                                                                                                 
    [8, 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 8                                                                                                 
    [13, 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$union_type], [[clc$integer_type, clc$keyword_type],                                           
    FALSE, 2],                                                                                                
    229, [[1, 0, clc$keyword_type], [6], [                                                                    
      ['A                              ', clc$abbreviation_entry, clc$normal_usage_entry, 1],                 
      ['ACTIVE                         ', clc$nominal_entry, clc$normal_usage_entry, 1],                      
      ['J                              ', clc$abbreviation_entry, clc$normal_usage_entry, 3],                 
      ['JOB                            ', clc$nominal_entry, clc$normal_usage_entry, 3],                      
      ['M                              ', clc$abbreviation_entry, clc$normal_usage_entry, 2],                 
      ['MONITOR                        ', clc$nominal_entry, clc$normal_usage_entry, 2]]                      
      ],                                                                                                      
    20, [[1, 0, clc$integer_type], [0, 0ffffffff(16), 10]]                                                    
    ,                                                                                                         
    '0..0ffffffff(16)'],                                                                                      
{ PARAMETER 2                                                                                                 
    [[1, 0, clc$integer_type], [0, 3, 10],                                                                    
    '0'],                                                                                                     
{ PARAMETER 3                                                                                                 
    [[1, 0, clc$union_type], [[clc$integer_type, clc$keyword_type],                                           
    FALSE, 2],                                                                                                
    44, [[1, 0, clc$keyword_type], [1], [                                                                     
      ['ALL                            ', clc$nominal_entry, clc$normal_usage_entry, 1]]                      
      ],                                                                                                      
    20, [[1, 0, clc$integer_type], [1, 0ffffffff(16), 10]]                                                    
    ,                                                                                                         
    'all'],                                                                                                   
{ PARAMETER 4                                                                                                 
    [[1, 0, clc$union_type], [[clc$integer_type, clc$keyword_type],                                           
    FALSE, 2],                                                                                                
    81, [[1, 0, clc$keyword_type], [2], [                                                                     
      ['EP                             ', clc$abbreviation_entry, clc$normal_usage_entry, 1],                 
      ['EXCHANGE_PACKAGE               ', clc$nominal_entry, clc$normal_usage_entry, 1]]                      
      ],                                                                                                      
    20, [[1, 0, clc$integer_type], [0, 0ffffffff(16), 10]]                                                    
    ,                                                                                                         
    'exchange_package'],                                                                                      
{ PARAMETER 5                                                                                                 
    [[1, 0, clc$list_type], [229, 1, 2, 0, FALSE, FALSE],                                                     
      [[1, 0, clc$keyword_type], [6], [                                                                       
      ['B                              ', clc$abbreviation_entry, clc$normal_usage_entry, 2],                 
      ['BRIEF                          ', clc$nominal_entry, clc$normal_usage_entry, 2],                      
      ['F                              ', clc$abbreviation_entry, clc$normal_usage_entry, 1],                 
      ['FULL                           ', clc$nominal_entry, clc$normal_usage_entry, 1],                      
      ['S                              ', clc$abbreviation_entry, clc$normal_usage_entry, 3],                 
      ['SAVE                           ', clc$nominal_entry, clc$normal_usage_entry, 3]]                      
      ]                                                                                                       
    ,                                                                                                         
    'brief'],                                                                                                 
{ PARAMETER 6                                                                                                 
    [[1, 0, clc$string_type], [1, 31, FALSE],                                                                 
    '''display_call'''],                                                                                      
{ PARAMETER 7                                                                                                 
    [[1, 0, clc$file_type]],                                                                                  
{ PARAMETER 8                                                                                                 
    [[1, 0, clc$status_type]]];                                                                               
                                                                                                              
?? FMT (FORMAT := ON) ??                                                                                      
?? POP ??                                                                                                     
                                                                                                              
    CONST                                                                                                     
      p$exchange = 1,                                                                                         
      p$processor = 2,                                                                                        
      p$count = 3,                                                                                            
      p$start = 4,                                                                                            
      p$display_option = 5,                                                                                   
      p$title = 6,                                                                                            
      p$output = 7,                                                                                           
      p$status = 8;                                                                                           
                                                                                                              
    VAR                                                                                                       
      pvt: array [1 .. 8] of clt$parameter_value;                                                             
                                                                                                              
    TYPE                                                                                                      
      t$next_stack_frame_seq = SEQ (REP 1 OF ost$pva);                                                        
                                                                                                              
    VAR                                                                                                       
      access_data: dut$access_data,                                                                           
      bytes_returned: ost$segment_length,                                                                     
      count: 1 .. 0ffffffff(16),                                                                              
      current: 0 .. 0ffffffff(16),                                                                            
      current_stack_frame: ost$pva,                                                                           
      default_list: ARRAY [1 .. 2] OF dut$default_change_list_entry,                                          
      display_control: clt$display_control,                                                                   
      display_save_area: boolean,                                                                             
      display_string: string (osc$max_string_size),                                                           
      dump_information: dut$dump_information,                                                                 
      exchange_package_p: ^dut$exchange_package,                                                              
      full_display: boolean,                                                                                  
      ignore_status: ost$status,                                                                              
      interactive: boolean,                                                                                   
      list_p: ^clt$data_value,                                                                                
      local_status: ost$status,                                                                               
      next_stack_frame_p: ^SEQ ( * ),                                                                         
      next_stack_frame_pva: ost$pva,                                                                          
      next_stack_frame_pva_p: ^ost$pva,                                                                       
      next_stack_frame_seq: t$next_stack_frame_seq,                                                           
      next_stack_frame_seq_p: ^t$next_stack_frame_seq,                                                        
      option_p: ^clt$data_value,                                                                              
      output_display_opened: boolean,                                                                         
      processor: 0 .. duc$de_maximum_processors,                                                              
      ring_attributes: amt$ring_attributes,                                                                   
      start: 0 .. 0ffffffff(16),                                                                              
      string_length: integer;                                                                                 
                                                                                                              
*copy dup$abort_handler                                                                                       
?? NEWTITLE := 'clean_up', EJECT ??                                                                           
                                                                                                              
{ PURPOSE:                                                                                                    
{   This procedure is called from the abort handler to close the file.                                        
                                                                                                              
    PROCEDURE [INLINE] clean_up;                                                                              
                                                                                                              
      VAR                                                                                                     
        ignore_status: ost$status;                                                                            
                                                                                                              
      IF output_display_opened THEN                                                                           
        clp$close_display (display_control, ignore_status);                                                   
      IFEND;                                                                                                  
                                                                                                              
    PROCEND clean_up;                                                                                         
?? OLDTITLE, EJECT ??                                                                                         
                                                                                                              
    status.normal := TRUE;                                                                                    
                                                                                                              
    { Change the default value for the EXCHANGE and PROCESSOR parameters.                                     
                                                                                                              
    default_list [1].default_name := duc$dp_exchange;                                                         
    default_list [1].number := p$exchange;                                                                    
    default_list [2].default_name := duc$dp_processor;                                                        
    default_list [2].number := p$processor;                                                                   
    dup$evaluate_parameters (parameter_list, default_list, #SEQ (pdt), ^pvt, status);                         
    IF NOT status.normal THEN                                                                                 
      RETURN;  {---->                                                                                         
    IFEND;                                                                                                    
                                                                                                              
    IF duv$dump_environment_p = NIL THEN                                                                      
      osp$set_status_abnormal (duc$dump_analyzer_id, due$no_restart_file, '', status);                        
      RETURN;  {---->                                                                                         
    IFEND;                                                                                                    
                                                                                                              
    IF pvt [p$count].value^.kind = clc$keyword THEN                                                           
      count := 0ffffffff(16);                                                                                 
    ELSE                                                                                                      
      count := pvt [p$count].value^.integer_value.value;                                                      
    IFEND;                                                                                                    
                                                                                                              
    IF pvt [p$start].value^.kind = clc$keyword THEN                                                           
      start := 0;                                                                                             
    ELSE                                                                                                      
      start := pvt [p$start].value^.integer_value.value;                                                      
    IFEND;                                                                                                    
                                                                                                              
    { Determine the display options.                                                                          
                                                                                                              
    full_display := FALSE;                                                                                    
    display_save_area := FALSE;                                                                               
    list_p := pvt [p$display_option].value;                                                                   
    WHILE list_p <> NIL DO                                                                                    
      option_p := list_p^.element_value;                                                                      
      list_p := list_p^.link;                                                                                 
      IF option_p^.keyword_value = 'FULL' THEN                                                                
        full_display := TRUE;                                                                                 
      ELSEIF option_p^.keyword_value = 'BRIEF' THEN                                                           
        full_display := FALSE;                                                                                
      ELSE  { option_p^.keyword_value = 'SAVE' }                                                              
        display_save_area := TRUE;                                                                            
      IFEND;                                                                                                  
    WHILEND;                                                                                                  
                                                                                                              
    processor := pvt [p$processor].value^.integer_value.value;                                                
                                                                                                              
    output_display_opened := FALSE;                                                                           
    osp$establish_block_exit_hndlr (^abort_handler);                                                          
                                                                                                              
   /display_opened/                                                                                           
    BEGIN                                                                                                     
                                                                                                              
      { Prepare the output display file.                                                                      
                                                                                                              
      IF pvt [p$output].specified THEN                                                                        
        ring_attributes.r1 := #RING (^ring_attributes);                                                       
        ring_attributes.r2 := #RING (^ring_attributes);                                                       
        ring_attributes.r3 := #RING (^ring_attributes);                                                       
        clp$open_display_reference (pvt [p$output].value^.file_value^, ^dup$new_page_procedure, fsc$list,     
              ring_attributes, display_control, status);                                                      
        IF NOT status.normal THEN                                                                             
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
        output_display_opened := TRUE;                                                                        
      ELSE                                                                                                    
        display_control := duv$execution_environment.output_file.display_control;                             
        display_control.line_number := display_control.page_length + 1;                                       
      IFEND;                                                                                                  
                                                                                                              
      duv$title_data.build_title := TRUE;                                                                     
      duv$title_data.command_name := pvt [p$title].value^.string_value^;                                      
                                                                                                              
      dup$retrieve_exchange_package (processor, pvt [p$exchange].value^, exchange_package_p, status);         
      IF NOT status.normal THEN                                                                               
        EXIT /display_opened/;  {---->                                                                        
      IFEND;                                                                                                  
                                                                                                              
      dup$determine_dump_information (dump_information);                                                      
                                                                                                              
      IF pvt [p$exchange].value^.kind = clc$keyword THEN                                                      
        IF pvt [p$exchange].value^.keyword_value = 'ACTIVE' THEN                                              
          IF ((dump_information.dump_type = duc$di_dt_cy2000) AND (duc$ee_cy_monitor_mode IN                  
                duv$execution_environment.processor_registers [processor].status_summary.cy2000)) OR          
                (duc$ee_gen_180_monitor_mode IN                                                               
                duv$execution_environment.processor_registers [processor].status_summary.general) THEN        
            clp$put_display (display_control, 'Active exchange package selected: CPU is in 180 monitor mode.',
                  clc$no_trim, ignore_status);                                                                
          ELSE                                                                                                
            clp$put_display (display_control, 'Active exchange package selected: CPU is in job mode.',        
                  clc$no_trim, ignore_status);                                                                
          IFEND;                                                                                              
        ELSEIF pvt [p$exchange].value^.keyword_value = 'MONITOR' THEN                                         
          STRINGREP (display_string, string_length, 'Exchange address = ',                                    
                duv$execution_environment.processor_registers [processor].monitor_process_state: #(16),       
                '(16)');                                                                                      
          clp$put_display (display_control, display_string (1, string_length), clc$trim, ignore_status);      
        ELSE  { pvt [p$exchange].value^.keyword_value = 'JOB' }                                               
          STRINGREP (display_string, string_length, 'Exchange address = ',                                    
                duv$execution_environment.processor_registers [processor].job_process_state: #(16), '(16)');  
          clp$put_display (display_control, display_string (1, string_length), clc$trim, ignore_status);      
        IFEND;                                                                                                
      IFEND;                                                                                                  
                                                                                                              
      IF start = 0 THEN                                                                                       
        dup$display_exchange_package (exchange_package_p^, full_display, display_control, status);            
        IF NOT status.normal THEN                                                                             
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
      ELSEIF exchange_package_p^.vmid = osc$cyber_170_mode THEN                                               
        osp$set_status_abnormal (duc$dump_analyzer_id, due$processor_in_170_mode, '', local_status);          
        dup$display_message (local_status, display_control);                                                  
      IFEND;                                                                                                  
                                                                                                              
      next_stack_frame_seq_p := ^next_stack_frame_seq;                                                        
      RESET next_stack_frame_seq_p;                                                                           
      next_stack_frame_pva := exchange_package_p^.a2_previous_save_area;                                      
                                                                                                              
      IF (next_stack_frame_pva.ring = osc$max_ring) AND (next_stack_frame_pva.seg = osc$maximum_segment) AND  
            (next_stack_frame_pva.offset < 0) THEN                                                            
        osp$set_status_abnormal (duc$dump_analyzer_id, due$display_terminated,                                
              'end of call chain encountered in the exchange package.', local_status);                        
        dup$display_message (local_status, display_control);                                                  
        EXIT /display_opened/;  {---->                                                                        
      IFEND;                                                                                                  
                                                                                                              
      IF start = 0 THEN                                                                                       
        IF count = 1 THEN                                                                                     
          EXIT /display_opened/;  {---->                                                                      
        ELSE                                                                                                  
          start := 1;                                                                                         
        IFEND;                                                                                                
      IFEND;                                                                                                  
                                                                                                              
      { Skip to the desired stack frame.                                                                      
                                                                                                              
      FOR current := 1 TO (start - 1) DO                                                                      
                                                                                                              
        current_stack_frame := next_stack_frame_pva;                                                          
        current_stack_frame.offset := current_stack_frame.offset + 1a(16);                                    
                                                                                                              
        RESET next_stack_frame_seq_p;                                                                         
        NEXT next_stack_frame_p: [[REP 1 OF ost$pva]] IN next_stack_frame_seq_p;                              
        IF next_stack_frame_p = NIL THEN                                                                      
          osp$set_status_abnormal (duc$dump_analyzer_id, due$nil_pointer, '', status);                        
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
        dup$copy_virtual_memory_pva (current_stack_frame, exchange_package_p^, processor, #SIZE (ost$pva),    
              TRUE, bytes_returned, next_stack_frame_p, access_data, status);                                 
        IF NOT status.normal THEN                                                                             
          IF status.condition = due$address_translation_error THEN                                            
            dup$display_message (status, display_control);                                                    
            osp$set_status_abnormal (duc$dump_analyzer_id, due$invalid_sf_pointer, '', status);               
            osp$append_status_parameter (osc$status_parameter_delimiter, ', segment = ',  status);            
            osp$append_status_integer (osc$status_parameter_delimiter, current_stack_frame.seg, 16, TRUE,     
                  status);                                                                                    
            osp$append_status_parameter (osc$status_parameter_delimiter, ', offset = ', status);              
            osp$append_status_integer (osc$status_parameter_delimiter, current_stack_frame.offset, 16, TRUE,  
                  status);                                                                                    
            clp$get_command_origin (interactive, local_status);                                               
            IF local_status.normal AND NOT interactive THEN                                                   
              dup$display_message (status, display_control);                                                  
            IFEND;                                                                                            
          IFEND;                                                                                              
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
        IF bytes_returned < #SIZE (ost$pva) THEN                                                              
          osp$set_status_abnormal (duc$dump_analyzer_id, due$display_terminated, 'frame', local_status);      
          osp$append_status_integer (osc$status_parameter_delimiter, current, 10, FALSE, local_status);       
          osp$append_status_parameter (osc$status_parameter_delimiter, 'is paged out.', local_status);        
          dup$display_message (local_status, display_control);                                                
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
        RESET next_stack_frame_p;                                                                             
        NEXT next_stack_frame_pva_p IN next_stack_frame_p;                                                    
        IF next_stack_frame_pva_p = NIL THEN                                                                  
          osp$set_status_abnormal (duc$dump_analyzer_id, due$nil_pointer, '', status);                        
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
        next_stack_frame_pva := next_stack_frame_pva_p^;                                                      
                                                                                                              
        IF (next_stack_frame_pva.ring = osc$max_ring) AND (next_stack_frame_pva.seg = osc$maximum_segment) AND
              (next_stack_frame_pva.offset < 0) THEN                                                          
          osp$set_status_abnormal (duc$dump_analyzer_id, due$display_terminated,                              
                'end of call chain encountered in frame', local_status);                                      
          osp$append_status_integer (osc$status_parameter_delimiter, current, 10, FALSE, local_status);       
          dup$display_message (local_status, display_control);                                                
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
      FOREND;                                                                                                 
                                                                                                              
      { Display the desired stack frames.                                                                     
                                                                                                              
      FOR current := start TO (start + count - 1) DO                                                          
        current_stack_frame := next_stack_frame_pva;                                                          
                                                                                                              
        clp$new_display_line (display_control, 1, ignore_status);                                             
                                                                                                              
        STRINGREP (display_string, string_length, 'Frame ', current, ': ');                                   
        dup$put_item (display_string (1, string_length), clc$no_trim, amc$start, display_control);            
                                                                                                              
        display_stack_frame (current_stack_frame, exchange_package_p, processor, display_save_area,           
              next_stack_frame_pva, display_control, status);                                                 
        IF NOT status.normal THEN                                                                             
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
                                                                                                              
        IF (next_stack_frame_pva.ring = osc$max_ring) AND (next_stack_frame_pva.seg = osc$maximum_segment) AND
              (next_stack_frame_pva.offset < 0) THEN                                                          
          osp$set_status_abnormal (duc$dump_analyzer_id, due$display_terminated,                              
                'end of call chain encountered in frame', local_status);                                      
          osp$append_status_integer (osc$status_parameter_delimiter, current, 10, FALSE, local_status);       
          dup$display_message (local_status, display_control);                                                
          EXIT /display_opened/;  {---->                                                                      
        IFEND;                                                                                                
      FOREND;                                                                                                 
                                                                                                              
    END /display_opened/;                                                                                     
                                                                                                              
    IF output_display_opened THEN                                                                             
      clp$close_display (display_control, ignore_status);                                                     
    IFEND;                                                                                                    
    osp$disestablish_cond_handler;                                                                            
                                                                                                              
  PROCEND dup$display_call_command;                                                                           
MODEND dum$display_call_command;                                                                              
