8
8
from collections import OrderedDict , deque
9
9
from collections .abc import Iterable , Iterator
10
10
from itertools import chain
11
- from typing import TYPE_CHECKING , Generic , NoReturn , TypeVar
11
+ from typing import TYPE_CHECKING , NoReturn , TypeVar
12
12
13
13
import claripy .clarirs as clarirs
14
14
from claripy import operations , simplifications
15
15
from claripy .backend_manager import backends
16
+ from claripy .clarirs import ASTCacheKey
16
17
from claripy .errors import BackendError , ClaripyOperationError , ClaripyReplacementError
17
18
18
19
if TYPE_CHECKING :
30
31
T = TypeVar ("T" , bound = "Base" )
31
32
32
33
33
- class ASTCacheKey (Generic [T ]):
34
- def __init__ (self , a : T ):
35
- self .ast : T = a
36
-
37
- def __hash__ (self ):
38
- return hash (self .ast )
39
-
40
- def __eq__ (self , other ):
41
- return type (self ) is type (other ) and self .ast ._hash == other .ast ._hash
42
-
43
- def __repr__ (self ):
44
- return f"<Key { self .ast ._type_name ()} { self .ast .__repr__ (inner = True )} >"
45
-
46
-
47
34
#
48
35
# AST variable naming
49
36
#
@@ -251,20 +238,16 @@ def __new__(cls, op, args, add_variables=None, hash=None, **kwargs): # pylint:d
251
238
h = Base ._calc_hash (op , a_args , kwargs ) if hash is None else hash
252
239
self = cache .get (h & 0x7FFF_FFFF_FFFF_FFFF , None )
253
240
if self is None :
241
+ # depth = arg_max_depth + 1
254
242
self = super ().__new__ (
255
243
cls ,
256
244
op ,
257
245
tuple (args ),
258
- kwargs .get ("length" , None ),
259
- frozenset (kwargs ["variables" ]),
260
- kwargs ["symbolic" ],
261
- annotations ,
262
- )
263
- depth = arg_max_depth + 1
264
- self .__a_init__ (
265
- op ,
266
- a_args ,
267
- depth = depth ,
246
+ kwargs .pop ("length" , None ),
247
+ frozenset (kwargs .pop ("variables" )),
248
+ kwargs .pop ("symbolic" ),
249
+ # annotations,
250
+ depth = arg_max_depth + 1 ,
268
251
uneliminatable_annotations = uneliminatable_annotations ,
269
252
relocatable_annotations = relocatable_annotations ,
270
253
** kwargs ,
@@ -287,18 +270,15 @@ def __init_with_annotations__(
287
270
if self is not None :
288
271
return self
289
272
273
+ print ("aaa" )
290
274
self = super ().__new__ (
291
275
cls ,
292
276
op ,
293
277
tuple (a_args ),
294
- kwargs .get ("length" , None ),
295
- frozenset (kwargs ["variables" ]),
296
- kwargs ["symbolic" ],
297
- tuple (kwargs .get ("annotations" , ())),
298
- )
299
- self .__a_init__ (
300
- op ,
301
- a_args ,
278
+ kwargs .pop ("length" , None ),
279
+ frozenset (kwargs .pop ("variables" )),
280
+ kwargs .pop ("symbolic" ),
281
+ tuple (kwargs .pop ("annotations" , ())),
302
282
depth = depth ,
303
283
uneliminatable_annotations = uneliminatable_annotations ,
304
284
relocatable_annotations = relocatable_annotations ,
@@ -322,75 +302,19 @@ def __reduce__(self):
322
302
def __init__ (self , * args , ** kwargs ):
323
303
pass
324
304
325
- # pylint:disable=attribute-defined-outside-init
326
- def __a_init__ (
327
- self ,
328
- op ,
329
- args ,
330
- variables = None ,
331
- symbolic = None ,
332
- length = None ,
333
- simplified = 0 ,
334
- errored = None ,
335
- eager_backends = None ,
336
- uninitialized = None ,
337
- uc_alloc_depth = None ,
338
- annotations = None ,
339
- encoded_name = None ,
340
- depth = None ,
341
- uneliminatable_annotations = None ,
342
- relocatable_annotations = None ,
343
- ): # pylint:disable=unused-argument
344
- """
345
- Initializes an AST. Takes the same arguments as ``Base.__new__()``
346
-
347
- We use this instead of ``__init__`` due to python's undesirable behavior w.r.t. automatically calling it on
348
- return from ``__new__``.
349
- """
350
-
351
- # HASHCONS: these attributes key the cache
352
- # BEFORE CHANGING THIS, SEE ALL OTHER INSTANCES OF "HASHCONS" IN THIS FILE
353
- # super().__new__(op, args, length, frozenset(variables), symbolic, annotations)
354
- # self.op = op
355
- # self.args = args if type(args) is tuple else tuple(args)
356
- # self.length = length
357
- # self.variables = frozenset(variables) if type(variables) is not frozenset else variables
358
- # self.symbolic = symbolic
359
- # self.annotations: tuple[Annotation] = annotations
360
- self ._uneliminatable_annotations = uneliminatable_annotations
361
- self ._relocatable_annotations = relocatable_annotations
362
-
363
- self .depth = depth if depth is not None else 1
364
-
365
- self ._eager_backends = eager_backends
366
- self ._cached_encoded_name = encoded_name
367
-
368
- self ._errored = errored if errored is not None else set ()
369
-
370
- self ._simplified = simplified
371
- self ._cache_key = ASTCacheKey (self )
372
- self ._excavated = None
373
- self ._burrowed = None
374
-
375
- self ._uninitialized = uninitialized
376
- self ._uc_alloc_depth = uc_alloc_depth
377
-
378
- if len (self .args ) == 0 :
379
- raise ClaripyOperationError ("AST with no arguments!" )
380
-
381
- # pylint:enable=attribute-defined-outside-init
382
-
383
305
def __hash__ (self ):
384
306
res = self ._hash
385
307
if not isinstance (self ._hash , int ):
386
308
res = hash (self ._hash )
387
309
return res
388
310
389
311
@property
390
- def cache_key (self : T ) -> ASTCacheKey [ T ] :
312
+ def cache_key (self : T ) -> ASTCacheKey :
391
313
"""
392
314
A key that refers to this AST - this value is appropriate for usage as a key in dictionaries.
393
315
"""
316
+ if self ._cache_key is None :
317
+ self ._cache_key = ASTCacheKey (self )
394
318
return self ._cache_key
395
319
396
320
@property
@@ -408,6 +332,7 @@ def make_like(self: T, op: str, args: Iterable, **kwargs) -> T:
408
332
simplified = simplifications .simpleton .simplify (op , args ) if kwargs .pop ("simplify" , False ) is True else None
409
333
if simplified is not None :
410
334
op = simplified .op
335
+
411
336
if (
412
337
simplified is None
413
338
and len (kwargs ) == 3
0 commit comments