1 /* ***********************************************************
 2    *                                                         *
 3    * Copyright, (C) Honeywell Information Systems Inc., 1982 *
 4    *                                                         *
 5    * Copyright (c) 1972 by Massachusetts Institute of        *
 6    * Technology and Honeywell Information Systems, Inc.      *
 7    *                                                         *
 8    *********************************************************** */
 9 
10 
11 /* Procedure to save value of a reference by converting it into an aligned temporary
12 
13    Initial Version:  9 February 1972 by BLW
14           Modified: 12 December 1972 by BLW
15           Modified: 15 February 1973 by RAB
16           Modified: 9 March 1977 by RAB to change mod_word handling
17           Modified: 25 March 1977 by RAB to fix 1599
18           Modified: 9 April 1977 by RAB to remove mod_word
19           Modified: 30 March 1980 by RAB for reference.(padded aligned)_for_store_ref.
20                     See prepare_operand for details.        */
21 
22 save_value: proc(pt);
23 
24 dcl       pt ptr;             /* points at a reference node */
25 
26 dcl       (p,q) ptr,
27           n fixed bin,
28           (null,substr) builtin,
29           adjust_ref_count entry(ptr,fixed bin),
30           stack_temp$free_temp entry(ptr),
31           state_man$flush_address entry(ptr);
32 
33 %include reference;
34 %include operator;
35 %include boundary;
36 %include nodes;
37 
38           p = pt;
39 
40           if p -> reference.temp_ref & (p -> reference.aggregate | p -> reference.dont_save)
41                then return;
42 
43           q = p -> reference.length;
44           if q ^= null
45           then do;
46                if q -> node.type = operator_node then q = q -> operand(1);
47                if ^ q -> reference.shared
48                     then call adjust_ref_count(q,-1);
49                end;
50 
51           q = p -> reference.qualifier;
52           if q ^= null
53           then do;
54                if q -> node.type = temporary_node
55                then call stack_temp$free_temp(p);
56                else do;
57                     if q -> node.type = operator_node
58                          then q = q -> operand(1);
59                     if ^ q -> reference.shared
60                          then call adjust_ref_count(q,-1);
61                     end;
62                end;
63 
64           q = p -> reference.offset;
65           if q ^= null
66           then do;
67                if q -> node.type = operator_node
68                     then q = q -> operand(1);
69 
70                if ^ q -> reference.shared
71                     then call adjust_ref_count(q,-1);
72                end;
73 
74           p -> reference.aligned_ref,
75           p -> reference.temp_ref,
76           p -> reference.padded_ref,
77           p -> reference.aligned_for_store_ref,
78           p -> reference.padded_for_store_ref = "1"b;
79 
80           p -> reference.units = word_;
81 
82           p -> reference.length,
83           p -> reference.offset,
84           p -> reference.qualifier = null;
85 
86           p -> reference.c_offset = 0;
87 
88           p -> reference.fo_in_qual,
89           p -> reference.hard_to_load,
90           p -> reference.store_ins,
91           p -> reference.defined_ref,
92           p -> reference.allocated,
93           p -> reference.value_in.storage = "0"b;
94 
95           if string(p -> reference.address_in)
96                then call state_man$flush_address(p);
97           end;