AssignmentNode.st
author Claus Gittinger <cg@exept.de>
Thu, 25 Apr 1996 19:09:53 +0200
changeset 263 3b21d0991eff
parent 261 0372e948ca2d
child 375 00e24958b103
permissions -rw-r--r--
documentation

"
 COPYRIGHT (c) 1989 by Claus Gittinger
	      All Rights Reserved

 This software is furnished under a license and may be used
 only in accordance with the terms of that license and with the
 inclusion of the above copyright notice.   This software may not
 be provided or otherwise made available to, or used by, any
 other person.  No title to or ownership of the software is
 hereby transferred.
"

ParseNode subclass:#AssignmentNode
	instanceVariableNames:'variable expression'
	classVariableNames:''
	poolDictionaries:''
	category:'System-Compiler-Support'
!

!AssignmentNode class methodsFor:'documentation'!

copyright
"
 COPYRIGHT (c) 1989 by Claus Gittinger
	      All Rights Reserved

 This software is furnished under a license and may be used
 only in accordance with the terms of that license and with the
 inclusion of the above copyright notice.   This software may not
 be provided or otherwise made available to, or used by, any
 other person.  No title to or ownership of the software is
 hereby transferred.
"
!

documentation
"
    node for parse-trees, representing assignments.
    This is a helper class for the compiler.

    [author:]
        Claus Gittinger

"
! !

!AssignmentNode class methodsFor:'instance creation'!

variable:v expression:e
    ^ (self basicNew) variable:v expression:e
! !

!AssignmentNode methodsFor:'accessing'!

expression
    ^ expression
!

variable:v expression:e
    variable := v.
    expression := e
! !

!AssignmentNode methodsFor:'code generation'!

checkIncDecOn:aStream
    "check if we can use incMvar / decMvar instruction.
     If so, code it and return true.
     Otherwise, return false."

    |sel erec arg code|

    (variable type == #MethodVariable) ifTrue:[
        expression isBinaryMessage ifTrue:[
            sel := expression selector.
            erec := expression receiver.

            ((sel == #+) or:[sel == #-]) ifTrue:[
                (erec type == #MethodVariable) ifTrue:[
                    (erec index == variable index) ifTrue:[
                        arg := expression arg1.
                        arg isConstant ifTrue:[
                            (arg value == 1) ifTrue:[
                                (sel == #+) ifTrue:[
                                    code := #incMethodVar
                                ] ifFalse:[
                                    code := #decMethodVar
                                ].
                                aStream nextPut:code; nextPut:(expression lineNumber); nextPut:(variable index).
                                ^ true
                            ]
                        ]
                    ]
                ]
            ]
        ]
    ].
    ^ false

    "Modified: 1.3.1996 / 00:08:02 / cg"
!

codeForSideEffectOn:aStream inBlock:b for:aCompiler
    (self checkIncDecOn:aStream) ifTrue:[^ self].

    self codeNormalOn:aStream valueNeeded:false inBlock:b for:aCompiler

    "Modified: 4.9.1995 / 14:38:10 / claus"
    "Modified: 1.3.1996 / 00:42:10 / cg"
!

codeNormalOn:aStream valueNeeded:forValue inBlock:b for:aCompiler
    expression codeOn:aStream inBlock:b for:aCompiler.
    expression isBlock ifTrue:[
        variable isLocal ifTrue:[
            aStream nextPut:#blockRef
        ]
    ].

    variable codeStoreOn:aStream inBlock:b valueNeeded:forValue for:aCompiler

    "Modified: 4.9.1995 / 14:38:10 / claus"
    "Modified: 1.3.1996 / 00:10:13 / cg"
    "Created: 1.3.1996 / 00:41:43 / cg"
!

codeOn:aStream inBlock:b for:aCompiler
    (self checkIncDecOn:aStream) ifTrue:[
        expression receiver codeOn:aStream inBlock:b for:aCompiler.
        ^ self
    ].

    self codeNormalOn:aStream valueNeeded:true inBlock:b for:aCompiler

    "Modified: 1.3.1996 / 00:42:21 / cg"
! !

!AssignmentNode methodsFor:'evaluating'!

evaluate
    |value|
    value := expression evaluate.
    variable store:value.
    ^ value
! !

!AssignmentNode methodsFor:'printing'!

printOn:aStream indent:i
    variable printOn:aStream.
    aStream nextPutAll:' := '.
    expression printOn:aStream
! !

!AssignmentNode methodsFor:'queries'!

isAssignment
    "return true, if this is a node for an assignment"

    ^ true
! !

!AssignmentNode class methodsFor:'documentation'!

version
    ^ '$Header: /cvs/stx/stx/libcomp/AssignmentNode.st,v 1.19 1996-04-25 17:08:51 cg Exp $'
! !