Changes in / [c64e979:98d4df9]
- Files:
-
- 1 added
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
src/ResolvExpr/Cost.h
rc64e979 r98d4df9 10 10 // Created On : Sun May 17 09:39:50 2015 11 11 // Last Modified By : Peter A. Buhr 12 // Last Modified On : Sun Apr 28 18:26:36201913 // Update Count : 2912 // Last Modified On : Mon Apr 29 18:33:44 2019 13 // Update Count : 49 14 14 // 15 15 … … 18 18 #include <iostream> 19 19 #include <cassert> 20 #include <climits> 20 21 21 22 namespace ResolvExpr { … … 216 217 << cost.referenceCost << " )"; 217 218 } 218 #endif // 0 219 220 #else 219 221 220 222 //*************************** NEW *************************** 223 224 // To maximize performance and space, the 7 resolution costs are packed into a single 64-bit word. However, the 225 // specialization cost is a negative value so a correction is needed is a few places. 221 226 222 227 class Cost { … … 234 239 unsigned char unsafeCost; ///< Unsafe (narrowing) conversions 235 240 #else 236 #error BIG_ENDIAN unsupported241 #error Cost BIG_ENDIAN unsupported 237 242 #endif 238 243 } v; 239 244 uint64_t all; 240 245 }; 246 static const unsigned char correctb = 0xff; // byte correction for negative spec cost 247 static const uint64_t correctw = 0x00'00'00'00'00'ff'00'00; //' word correction for negative spec cost 241 248 public: 242 249 // Compiler adjusts constants for correct endian. 243 250 enum : uint64_t { 244 zero = 0x00'00'00'00'00'ff'00'00, 245 infinity = 0xff'ff'ff'ff'ff'00'ff'ff, 246 correction = 0x00'00'00'00'00'ff'00'00, // correct for negative spec cost 247 unsafe = 0x01'00'00'00'00'ff'00'00, 248 poly = 0x00'01'00'00'00'ff'00'00, 249 safe = 0x00'00'01'00'00'ff'00'00, 250 sign = 0x00'00'00'01'00'ff'00'00, 251 var = 0x00'00'00'00'01'ff'00'00, 252 spec = 0x00'00'00'00'00'fe'00'00, 253 reference = 0x00'00'00'00'00'ff'01'00, 254 }; // 251 zero = 0x00'00'00'00'00'ff'00'00, 252 infinity = 0xff'ff'ff'ff'ff'00'ff'ff, 253 unsafe = 0x01'00'00'00'00'ff'00'00, 254 poly = 0x00'01'00'00'00'ff'00'00, 255 safe = 0x00'00'01'00'00'ff'00'00, 256 sign = 0x00'00'00'01'00'ff'00'00, 257 var = 0x00'00'00'00'01'ff'00'00, 258 spec = 0x00'00'00'00'00'fe'00'00, 259 reference = 0x00'00'00'00'00'ff'01'00, 260 }; //' 255 261 256 262 Cost( uint64_t all ) { Cost::all = all; } … … 258 264 // Assume little-endian => first value is low priority and last is high priority. 259 265 v = { 266 #if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__ 260 267 (unsigned char)0, // padding 261 (unsigned char)referenceCost, 262 (unsigned char)(specCost + 0xff ),// correct for signedness268 (unsigned char)referenceCost, // low priority 269 (unsigned char)(specCost + correctb), // correct for signedness 263 270 (unsigned char)varCost, 264 271 (unsigned char)signCost, 265 272 (unsigned char)safeCost, 266 273 (unsigned char)polyCost, 267 (unsigned char)unsafeCost, 274 (unsigned char)unsafeCost, // high priority 275 #else 276 #error Cost BIG_ENDIAN unsupported 277 #endif 268 278 }; 269 279 } … … 274 284 int get_signCost() const { return v.signCost; } 275 285 int get_varCost() const { return v.varCost; } 276 int get_specCost() const { return -( 0xff- v.specCost); }286 int get_specCost() const { return -(correctb - v.specCost); } 277 287 int get_referenceCost() const { return v.referenceCost; } 278 288 … … 295 305 return *this; 296 306 } 297 all += rhs.all - correct ion;// correct for negative spec cost307 all += rhs.all - correctw; // correct for negative spec cost 298 308 return *this; 299 309 } 300 310 301 311 Cost incUnsafe( int inc = 1 ) { 302 if ( all != infinity ) { assert( v.unsafeCost + inc < 256); v.unsafeCost += inc; }312 if ( all != infinity ) { assert( v.unsafeCost + inc <= UCHAR_MAX ); v.unsafeCost += inc; } 303 313 return *this; 304 314 } 305 315 306 316 Cost incPoly( int inc = 1 ) { 307 if ( all != infinity ) { assert( v.polyCost + inc < 256); v.polyCost += inc; }317 if ( all != infinity ) { assert( v.polyCost + inc <= UCHAR_MAX ); v.polyCost += inc; } 308 318 return *this; 309 319 } 310 320 311 321 Cost incSafe( int inc = 1 ) { 312 if ( all != infinity ) { assert( v.safeCost + inc < 256); v.safeCost += inc; }322 if ( all != infinity ) { assert( v.safeCost + inc <= UCHAR_MAX ); v.safeCost += inc; } 313 323 return *this; 314 324 } 315 325 316 326 Cost incSign( int inc = 1 ) { 317 if ( all != infinity ) { assert( v.signCost + inc < 256); v.signCost += inc; }327 if ( all != infinity ) { assert( v.signCost + inc <= UCHAR_MAX ); v.signCost += inc; } 318 328 return *this; 319 329 } 320 330 321 331 Cost incVar( int inc = 1 ) { 322 if ( all != infinity ) { assert( v.varCost + inc < 256); v.varCost += inc; }332 if ( all != infinity ) { assert( v.varCost + inc <= UCHAR_MAX ); v.varCost += inc; } 323 333 return *this; 324 334 } 325 335 326 336 Cost decSpec( int dec = 1 ) { 327 if ( all != infinity ) { v.specCost -= dec; }337 if ( all != infinity ) { assert( v.specCost - dec >= 0 ); v.specCost -= dec; } 328 338 return *this; 329 339 } 330 340 331 341 Cost incReference( int inc = 1 ) { 332 if ( all != infinity ) { assert( v.referenceCost + inc < 256); v.referenceCost += inc; }342 if ( all != infinity ) { assert( v.referenceCost + inc <= UCHAR_MAX ); v.referenceCost += inc; } 333 343 return *this; 334 344 } … … 353 363 inline Cost operator+( const Cost lhs, const Cost rhs ) { 354 364 if ( lhs.all == Cost::infinity || rhs.all == Cost::infinity ) return Cost{ Cost::infinity }; 355 return Cost{ lhs.all + rhs.all - Cost::correct ion}; // correct for negative spec cost365 return Cost{ lhs.all + rhs.all - Cost::correctw }; // correct for negative spec cost 356 366 } 357 367 … … 361 371 << ", " << cost.get_referenceCost() << " )"; 362 372 } 373 #endif // 0 363 374 } // namespace ResolvExpr 364 375 -
src/ResolvExpr/ResolveAssertions.cc
rc64e979 r98d4df9 155 155 k += computeConversionCost( 156 156 assn.match.adjType, assn.decl->get_type(), indexer, x.env ); 157 158 // mark vars+specialization cost on function-type assertions 159 PointerType* ptr = dynamic_cast< PointerType* >( assn.decl->get_type() ); 160 if ( ! ptr ) continue; 161 FunctionType* func = dynamic_cast< FunctionType* >( ptr->base ); 162 if ( ! func ) continue; 163 164 for ( DeclarationWithType* formal : func->parameters ) { 165 k.decSpec( specCost( formal->get_type() ) ); 166 } 167 k.incVar( func->forall.size() ); 168 for ( TypeDecl* td : func->forall ) { 169 k.decSpec( td->assertions.size() ); 170 } 157 171 } 158 172 it = cache.emplace_hint( it, &x, k );
Note: See TracChangeset
for help on using the changeset viewer.