Mercurial > hg > octave-avbm
comparison src/pt-id.cc @ 7336:745a8299c2b5
[project @ 2007-12-28 20:56:55 by jwe]
author | jwe |
---|---|
date | Fri, 28 Dec 2007 20:56:58 +0000 |
parents | a1dbe9d80eee |
children | 40c428ea3408 |
comparison
equal
deleted
inserted
replaced
7335:58f5fab3ebe5 | 7336:745a8299c2b5 |
---|---|
37 #include "utils.h" | 37 #include "utils.h" |
38 #include "variables.h" | 38 #include "variables.h" |
39 | 39 |
40 // Symbols from the symbol table. | 40 // Symbols from the symbol table. |
41 | 41 |
42 std::string | |
43 tree_identifier::name (void) const | |
44 { | |
45 std::string retval; | |
46 if (sym) | |
47 retval = sym->name (); | |
48 return retval; | |
49 } | |
50 | |
51 tree_identifier * | |
52 tree_identifier::define (octave_function *f, unsigned int sym_type) | |
53 { | |
54 int status = sym->define (f, sym_type); | |
55 return status ? this : 0; | |
56 } | |
57 | |
58 void | |
59 tree_identifier::document (const std::string& s) | |
60 { | |
61 if (sym) | |
62 sym->document (s); | |
63 } | |
64 | |
65 bool | |
66 tree_identifier::is_defined (void) | |
67 { | |
68 return (sym && sym->is_defined ()); | |
69 } | |
70 | |
71 bool | |
72 tree_identifier::is_function (void) | |
73 { | |
74 return (sym && sym->is_function ()); | |
75 } | |
76 | |
77 void | 42 void |
78 tree_identifier::eval_undefined_error (void) | 43 tree_identifier::eval_undefined_error (void) |
79 { | 44 { |
80 int l = line (); | 45 int l = line (); |
81 int c = column (); | 46 int c = column (); |
85 else | 50 else |
86 ::error ("`%s' undefined near line %d column %d", | 51 ::error ("`%s' undefined near line %d column %d", |
87 name ().c_str (), l, c); | 52 name ().c_str (), l, c); |
88 } | 53 } |
89 | 54 |
90 // Try to find a definition for an identifier. Here's how: | |
91 // | |
92 // * If the identifier is already defined and is a function defined | |
93 // in an function file that has been modified since the last time | |
94 // we parsed it, parse it again. | |
95 // | |
96 // * If the identifier is not defined, try to find a builtin | |
97 // variable or an already compiled function with the same name. | |
98 // | |
99 // * If the identifier is still undefined, try looking for an | |
100 // function file to parse. | |
101 // | |
102 // * On systems that support dynamic linking, we prefer .oct files, | |
103 // then .mex files, then .m files. | |
104 | |
105 octave_value | |
106 tree_identifier::do_lookup (bool& script_file_executed, bool exec_script) | |
107 { | |
108 static octave_value foo; | |
109 | |
110 script_file_executed = lookup (sym, exec_script); | |
111 | |
112 return script_file_executed ? foo : sym->def (); | |
113 } | |
114 | |
115 void | |
116 tree_identifier::link_to_global (void) | |
117 { | |
118 if (sym) | |
119 { | |
120 if (! sym->is_linked_to_global ()) | |
121 { | |
122 if (sym->is_defined () && sym->is_variable ()) | |
123 { | |
124 std::string nm = sym->name (); | |
125 | |
126 warning ("value of local variable `%s' may have changed to match global", | |
127 nm.c_str ()); | |
128 } | |
129 | |
130 link_to_global_variable (sym); | |
131 } | |
132 } | |
133 } | |
134 | |
135 void | |
136 tree_identifier::mark_as_static (void) | |
137 { | |
138 if (sym) | |
139 sym->mark_as_static (); | |
140 } | |
141 | |
142 void | |
143 tree_identifier::mark_as_formal_parameter (void) | |
144 { | |
145 if (sym) | |
146 sym->mark_as_formal_parameter (); | |
147 } | |
148 | |
149 octave_value_list | 55 octave_value_list |
150 tree_identifier::rvalue (int nargout) | 56 tree_identifier::rvalue (int nargout) |
151 { | 57 { |
152 octave_value_list retval; | 58 octave_value_list retval; |
153 | 59 |
154 MAYBE_DO_BREAKPOINT; | 60 MAYBE_DO_BREAKPOINT; |
155 | 61 |
156 if (error_state) | 62 if (error_state) |
157 return retval; | 63 return retval; |
158 | 64 |
159 bool script_file_executed = false; | 65 octave_value_list evaluated_args; |
66 bool args_evaluated; | |
160 | 67 |
161 octave_value val = do_lookup (script_file_executed); | 68 octave_value val = sym.find (0, string_vector (), evaluated_args, |
69 args_evaluated); | |
162 | 70 |
163 if (! script_file_executed) | 71 if (val.is_defined ()) |
164 { | 72 { |
165 if (val.is_defined ()) | 73 // GAGME -- this would be cleaner if we required |
74 // parens to indicate function calls. | |
75 // | |
76 // If this identifier refers to a function, we need to know | |
77 // whether it is indexed so that we can do the same thing | |
78 // for `f' and `f()'. If the index is present, return the | |
79 // function object and let tree_index_expression::rvalue | |
80 // handle indexing. Otherwise, arrange to call the function | |
81 // here, so that we don't return the function definition as | |
82 // a value. | |
83 | |
84 if (val.is_function () && ! is_postfix_indexed ()) | |
166 { | 85 { |
167 // GAGME -- this would be cleaner if we required | 86 octave_value_list tmp_args; |
168 // parens to indicate function calls. | |
169 // | |
170 // If this identifier refers to a function, we need to know | |
171 // whether it is indexed so that we can do the same thing | |
172 // for `f' and `f()'. If the index is present, return the | |
173 // function object and let tree_index_expression::rvalue | |
174 // handle indexing. Otherwise, arrange to call the function | |
175 // here, so that we don't return the function definition as | |
176 // a value. | |
177 | 87 |
178 if (val.is_function () && ! is_postfix_indexed ()) | 88 retval = val.do_multi_index_op (nargout, tmp_args); |
179 { | |
180 octave_value_list tmp_args; | |
181 | |
182 retval = val.do_multi_index_op (nargout, tmp_args); | |
183 } | |
184 else | |
185 { | |
186 if (print_result () && nargout == 0) | |
187 val.print_with_name (octave_stdout, name ()); | |
188 | |
189 retval = val; | |
190 } | |
191 } | 89 } |
192 else | 90 else |
193 eval_undefined_error (); | 91 { |
92 if (print_result () && nargout == 0) | |
93 val.print_with_name (octave_stdout, name ()); | |
94 | |
95 retval = val; | |
96 } | |
194 } | 97 } |
98 else | |
99 eval_undefined_error (); | |
195 | 100 |
196 return retval; | 101 return retval; |
197 } | 102 } |
198 | 103 |
199 octave_value | 104 octave_value |
212 octave_lvalue | 117 octave_lvalue |
213 tree_identifier::lvalue (void) | 118 tree_identifier::lvalue (void) |
214 { | 119 { |
215 MAYBE_DO_BREAKPOINT; | 120 MAYBE_DO_BREAKPOINT; |
216 | 121 |
217 return sym->variable_reference (); | 122 return octave_lvalue (&(sym.varref ())); |
218 } | 123 } |
219 | 124 |
220 tree_identifier * | 125 tree_identifier * |
221 tree_identifier::dup (symbol_table *sym_tab) | 126 tree_identifier::dup (symbol_table::scope_id scope) |
222 { | 127 { |
223 symbol_record *sr = (sym_tab && sym) ? sym_tab->lookup (sym->name ()) : 0; | 128 // The new tree_identifier object contains a symbol_record |
129 // entry from the duplicated scope. | |
224 | 130 |
225 tree_identifier *new_id = new tree_identifier (sr, line (), column ()); | 131 // FIXME -- is this the best way? |
132 symbol_table::symbol_record new_sym | |
133 = symbol_table::find_symbol (sym.name (), scope); | |
134 | |
135 tree_identifier *new_id | |
136 = new tree_identifier (new_sym, line (), column ()); | |
226 | 137 |
227 new_id->copy_base (*this); | 138 new_id->copy_base (*this); |
228 | 139 |
229 return new_id; | 140 return new_id; |
230 } | 141 } |