162 /* dimension will be filled in during stage 3 (array_range_check_c) with the number of elements in this subrange */ |
162 /* dimension will be filled in during stage 3 (array_range_check_c) with the number of elements in this subrange */ |
163 // SYM_REF2(subrange_c, lower_limit, upper_limit, unsigned long long int dimension) |
163 // SYM_REF2(subrange_c, lower_limit, upper_limit, unsigned long long int dimension) |
164 void *array_range_check_c::visit(subrange_c *symbol) { |
164 void *array_range_check_c::visit(subrange_c *symbol) { |
165 unsigned long long int dimension = 0; // we use unsigned long long instead of uint64_t since it might just happen to be larger than uint64_t in the platform used for compiling this code!! |
165 unsigned long long int dimension = 0; // we use unsigned long long instead of uint64_t since it might just happen to be larger than uint64_t in the platform used for compiling this code!! |
166 |
166 |
167 /* Determine the size of the array... */ |
167 /* Determine the size of the array... */ |
168 if (VALID_CVALUE( int64, symbol->upper_limit) && VALID_CVALUE( int64, symbol->lower_limit)) { |
168 if (VALID_CVALUE( int64, symbol->upper_limit) && VALID_CVALUE( int64, symbol->lower_limit)) { |
169 // do the sums in such a way that no overflow is possible... even during intermediate steps used by compiler! |
169 // do the sums in such a way that no overflow is possible... even during intermediate steps used by compiler! |
170 // remember that the result (dimension) is unsigned, while the operands are signed!! |
170 // remember that the result (dimension) is unsigned, while the operands are signed!! |
171 // dimension = GET_CVALUE( int64, symbol->upper_limit) - VALID_CVALUE( int64, symbol->lower_limit); |
171 // dimension = GET_CVALUE( int64, symbol->upper_limit) - VALID_CVALUE( int64, symbol->lower_limit); |
172 if (VALID_CVALUE( int64, symbol->lower_limit) >= 0) { |
172 if (GET_CVALUE( int64, symbol->lower_limit) >= 0) { |
173 dimension = GET_CVALUE( int64, symbol->upper_limit) - GET_CVALUE( int64, symbol->lower_limit); |
173 dimension = GET_CVALUE( int64, symbol->upper_limit) - GET_CVALUE( int64, symbol->lower_limit); |
174 } else { |
174 } else { |
175 dimension = -GET_CVALUE( int64, symbol->lower_limit); |
175 dimension = -GET_CVALUE( int64, symbol->lower_limit); |
176 dimension += GET_CVALUE( int64, symbol->upper_limit); |
176 dimension += GET_CVALUE( int64, symbol->upper_limit); |
177 } |
177 } |
178 } else if (VALID_CVALUE(uint64, symbol->upper_limit) && VALID_CVALUE(uint64, symbol->lower_limit)) { |
178 } else if (VALID_CVALUE(uint64, symbol->upper_limit) && VALID_CVALUE(uint64, symbol->lower_limit)) { |
179 dimension = GET_CVALUE(uint64, symbol->upper_limit) - VALID_CVALUE(uint64, symbol->lower_limit); |
179 dimension = GET_CVALUE(uint64, symbol->upper_limit) - GET_CVALUE(uint64, symbol->lower_limit); |
180 } else if (VALID_CVALUE(uint64, symbol->upper_limit) && VALID_CVALUE( int64, symbol->lower_limit)) { |
180 } else if (VALID_CVALUE(uint64, symbol->upper_limit) && VALID_CVALUE( int64, symbol->lower_limit)) { |
181 if (VALID_CVALUE( int64, symbol->lower_limit) >= 0) { |
181 if (GET_CVALUE( int64, symbol->lower_limit) >= 0) { |
182 dimension = GET_CVALUE( int64, symbol->upper_limit) - GET_CVALUE( int64, symbol->lower_limit); |
182 dimension = GET_CVALUE(uint64, symbol->upper_limit) - GET_CVALUE( int64, symbol->lower_limit); |
183 } else { |
183 } else { |
184 unsigned long long int lower_ull; |
184 unsigned long long int lower_ull; |
185 lower_ull = -GET_CVALUE( int64, symbol->lower_limit); |
185 lower_ull = -GET_CVALUE( int64, symbol->lower_limit); |
186 dimension = GET_CVALUE( int64, symbol->upper_limit) + lower_ull; |
186 dimension = GET_CVALUE(uint64, symbol->upper_limit) + lower_ull; |
187 /* TODO: check this overflow test, it does not seem to be working. I don't have to go now... Will check later. */ |
187 if (dimension < lower_ull) |
188 if (dimension < lower_ull) |
188 STAGE3_ERROR(0, symbol, symbol, "Number of elements in array subrange exceeds maximum number of elements (%llu).", std::numeric_limits< unsigned long long int >::max()); |
189 STAGE3_ERROR(0, symbol, symbol, "Number of elements in array subrange exceeds maximum number of elements (%llu).", std::numeric_limits< unsigned long long int >::max()); |
|
190 } |
189 } |
191 } else ERROR; |
190 } else ERROR; |
192 |
191 |
193 /* correct value for dimension is actually ---> dimension = upper_limit - lower_limit + 1 |
192 /* correct value for dimension is actually ---> dimension = upper_limit - lower_limit + 1 |
194 * Up to now, we have only determined dimension = upper_limit - lower_limit |
193 * Up to now, we have only determined dimension = upper_limit - lower_limit |