]> gitweb.factorcode.org Git - factor.git/blob - basis/compiler/tree/propagation/slots/slots.factor
Merge branch 'master' of git://factorcode.org/git/factor
[factor.git] / basis / compiler / tree / propagation / slots / slots.factor
1 ! Copyright (C) 2008, 2009 Slava Pestov.
2 ! See http://factorcode.org/license.txt for BSD license.
3 USING: fry assocs arrays byte-arrays strings accessors sequences
4 kernel slots classes.algebra classes.tuple classes.tuple.private
5 words math math.private combinators sequences.private namespaces
6 slots.private classes compiler.tree.propagation.info ;
7 IN: compiler.tree.propagation.slots
8
9 ! Propagation of immutable slots and array lengths
10
11 UNION: fixed-length-sequence array byte-array string ;
12
13 : sequence-constructor? ( word -- ? )
14     { <array> <byte-array> (byte-array) <string> } memq? ;
15
16 : constructor-output-class ( word -- class )
17     {
18         { <array> array }
19         { <byte-array> byte-array }
20         { (byte-array) byte-array }
21         { <string> string }
22     } at ;
23
24 : propagate-sequence-constructor ( #call word -- infos )
25     [ in-d>> first <sequence-info> ]
26     [ constructor-output-class <class-info> ]
27     bi* value-info-intersect 1array ;
28
29 : fold-<tuple-boa> ( values class -- info )
30     [ [ literal>> ] map ] dip prefix >tuple
31     <literal-info> ;
32
33 : (propagate-tuple-constructor) ( values class -- info )
34     [ [ value-info ] map ] dip [ read-only-slots ] keep
35     over rest-slice [ dup [ literal?>> ] when ] all? [
36         [ rest-slice ] dip fold-<tuple-boa>
37     ] [
38         <tuple-info>
39     ] if ;
40
41 : propagate-<tuple-boa> ( #call -- infos )
42     in-d>> unclip-last
43     value-info literal>> first (propagate-tuple-constructor) 1array ;
44
45 : read-only-slot? ( n class -- ? )
46     all-slots [ offset>> = ] with find nip
47     dup [ read-only>> ] when ;
48
49 : literal-info-slot ( slot object -- info/f )
50     2dup class read-only-slot?
51     [ swap slot <literal-info> ] [ 2drop f ] if ;
52
53 : length-accessor? ( slot info -- ? )
54     [ 1 = ] [ length>> ] bi* and ;
55
56 : value-info-slot ( slot info -- info' )
57     {
58         { [ over 0 = ] [ 2drop fixnum <class-info> ] }
59         { [ 2dup length-accessor? ] [ nip length>> ] }
60         { [ dup literal?>> ] [ literal>> literal-info-slot ] }
61         [ [ 1- ] [ slots>> ] bi* ?nth ]
62     } cond [ object-info ] unless* ;