factor/library/inference/class-infer.factor

155 lines
3.9 KiB
Factor
Raw Normal View History

! Copyright (C) 2004, 2005 Slava Pestov.
! See http://factor.sf.net/license.txt for BSD license.
IN: inference
2005-08-02 01:28:38 -04:00
USING: generic hashtables kernel kernel-internals namespaces
sequences vectors words ;
! Infer possible classes of values in a dataflow IR.
! Variables used by the class inferencer
! Current value --> class mapping
SYMBOL: value-classes
2005-07-28 18:20:31 -04:00
! Current value --> literal mapping
SYMBOL: value-literals
2005-07-30 02:08:59 -04:00
! Maps ties to ties
SYMBOL: ties
2005-07-28 18:20:31 -04:00
GENERIC: apply-tie ( tie -- )
M: f apply-tie ( f -- ) drop ;
TUPLE: class-tie value class ;
: set-value-class ( class value -- )
2dup swap <class-tie> ties get hash [ apply-tie ] when*
value-classes get set-hash ;
M: class-tie apply-tie ( tie -- )
dup class-tie-class swap class-tie-value
set-value-class ;
TUPLE: literal-tie value literal ;
: set-value-literal ( literal value -- )
over class over set-value-class
2dup swap <literal-tie> ties get hash [ apply-tie ] when*
value-literals get set-hash ;
M: literal-tie apply-tie ( tie -- )
dup literal-tie-literal swap literal-tie-value
set-value-literal ;
GENERIC: infer-classes* ( node -- )
2005-07-28 18:20:31 -04:00
M: node infer-classes* ( node -- ) drop ;
! For conditionals, a map of child node # --> possibility
GENERIC: child-ties ( node -- seq )
M: node child-ties ( node -- seq )
node-children length f <repeated> ;
: value-class ( value -- class )
value-classes get hash [ object ] unless* ;
2005-07-28 18:20:31 -04:00
: value-literal ( value -- class )
value-literals get hash ;
: annotate-node ( node -- )
#! Annotate the node with the currently-inferred set of
#! value classes.
2005-07-28 18:20:31 -04:00
dup node-values ( 2dup )
[ value-class ] map>hash swap set-node-classes
( [ value-literal ] map>hash swap set-node-literals ) ;
: assume-classes ( classes values -- )
2005-07-28 18:20:31 -04:00
[ set-value-class ] 2each ;
: assume-literals ( literals values -- )
[ set-value-literal ] 2each ;
: intersect-classes ( classes values -- )
[ [ value-class class-and ] 2map ] keep assume-classes ;
\ type [
2005-08-14 18:13:16 -04:00
dup node-in-d first num-types [ type>class <class-tie> ] map-with
swap node-out-d first num-types [ <literal-tie> ] map-with
[ ties get set-hash ] 2each
] "create-ties" set-word-prop
2005-07-28 18:20:31 -04:00
: create-ties ( #call -- )
#! If the node is calling a class test predicate, create a
#! tie.
dup node-param "create-ties" word-prop dup [
call
2005-07-28 18:20:31 -04:00
] [
drop dup node-param "predicating" word-prop dup [
>r dup node-in-d first r> <class-tie>
swap node-out-d first general-t <class-tie>
ties get set-hash
] [
2drop
] ifte
2005-07-28 18:20:31 -04:00
] ifte ;
2005-08-02 01:28:38 -04:00
\ make-tuple [
dup node-in-d first literal-value 1vector
] "output-classes" set-word-prop
: output-classes ( node -- seq )
dup node-param "output-classes" word-prop [
call
] [
node-param "infer-effect" word-prop second
] ?ifte ;
M: #call infer-classes* ( node -- )
2005-08-01 16:22:53 -04:00
dup node-param [
dup create-ties
2005-08-02 01:28:38 -04:00
dup output-classes swap node-out-d intersect-classes
2005-08-01 16:22:53 -04:00
] [
drop
] ifte ;
M: #push infer-classes* ( node -- )
2005-08-07 00:00:57 -04:00
node-out-d dup [ literal-value ] map swap assume-literals ;
2005-07-28 18:20:31 -04:00
M: #ifte child-ties ( node -- seq )
node-in-d first dup general-t <class-tie>
swap f <literal-tie> 2vector ;
M: #dispatch child-ties ( node -- seq )
dup node-in-d first
swap node-children length [ <literal-tie> ] map-with ;
DEFER: (infer-classes)
: infer-children ( node -- )
dup node-children swap child-ties [
[
value-classes [ clone ] change
ties [ clone ] change
apply-tie
(infer-classes)
] with-scope
] 2each ;
: (infer-classes) ( node -- )
2005-08-01 16:22:53 -04:00
[
dup infer-classes*
dup annotate-node
dup infer-children
node-successor (infer-classes)
] when* ;
: infer-classes ( node -- )
[
<namespace> value-classes set
2005-07-28 18:20:31 -04:00
<namespace> value-literals set
<namespace> ties set
(infer-classes)
] with-scope ;