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 }