From eed77282df91837ac5e32b5d1d57ea4a59b7d013 Mon Sep 17 00:00:00 2001 From: ketmar Date: Sun, 21 Nov 2010 00:59:42 +0200 Subject: [PATCH] compiler now raises an error when it encounters assigning in unexpected place --- imgsrc/defs/compiler/compiler.st | 132 +++++++++++++++++++++++++-------------- 1 file changed, 84 insertions(+), 48 deletions(-) diff --git a/imgsrc/defs/compiler/compiler.st b/imgsrc/defs/compiler/compiler.st index 301c166..6ea564f 100644 --- a/imgsrc/defs/compiler/compiler.st +++ b/imgsrc/defs/compiler/compiler.st @@ -173,19 +173,19 @@ nextChar [ ] skipComment [ - | cc lstart | + | c lstart | lstart := lineNum. - [ (cc := self nextChar) isEOF ifTrue: [ self error: 'unterminated comment' line: lstart ]. - cc == $" ] whileFalse: [ nil ]. + [ (c := self nextChar) isEOF ifTrue: [ self error: 'unterminated comment' line: lstart ]. + c == $" ] whileFalse: [ nil ]. self nextChar. ^self skipBlanks ] skipBlanks [ - | cc | - cc := self peekChar. - [ cc isBlank ] whileTrue: [ cc := self nextChar ]. - ( cc == $" ) ifTrue: [ ^self skipComment ] + | c | + c := self peekChar. + [ c isBlank ] whileTrue: [ c := self nextChar ]. + ( c == $" ) ifTrue: [ ^self skipComment ] ] nextLex [ @@ -221,10 +221,10 @@ lexNumber [ lexAlnum [ "keyword (with possible colons)" - | cc start | + | c start | start := index. "add any trailing colons too" - [ ((cc := self nextChar) isAlphanumeric) or: [ cc == $: ]] whileTrue: [ nil ]. + [ ((c := self nextChar) isAlphanumeric) or: [ c == $: ]] whileTrue: [ nil ]. token := text from: start to: index - 1 ] @@ -354,6 +354,42 @@ readStatement [ ^self readExpression ] +goBackComment: idx [ + "last double-quote already skipped" + | c | + [ idx > 0 ] whileTrue: [ + (c := text at: idx) == $" ifTrue: [ ^idx - 1 ]. + idx := idx - 1. + ]. + ^idx +] + +goBackBlanks: idx [ + | c | + [ idx > 0 ] whileTrue: [ + (c := text at: idx) isBlank ifFalse: [ + c == $" ifFalse: [ ^idx ]. + idx := self goBackComment: idx - 1. + ] ifTrue: [ idx := idx - 1 ]. + ]. + ^idx +] + +goBackName: idx [ + | c | + [ idx > 0 ] whileTrue: [ + (c := text at: idx) isAlphanumeric ifFalse: [ ^idx ]. + idx := idx - 1. + 'n: ' print. c printString printNl. + ]. + ^idx +] + +goBackFromName: idx [ + "skip name token and move backwards until we hit text start or non-blank" + ^self goBackBlanks: (self goBackName: (self goBackBlanks: idx)). +] + readExpression [ | node lnum name newVar nameLine | self tokenIsName ifFalse: [ ^self readCascade: self readTerm ]. @@ -368,13 +404,12 @@ readExpression [ ]. node := self nameNode: name. newVar ifTrue: [ usedTemps at: name put: false ]. "restore 'assigned, but never used' state" - self tokenIsAssign - ifTrue: [ - node assignable ifFalse: [ self error: 'illegal assignment' line: nameLine ]. - lnum := lineNum. - self nextLex. - ^(AstAssignNode at: lnum) target: node expression: self readExpression - ]. + self tokenIsAssign ifTrue: [ + node assignable ifFalse: [ self error: 'illegal assignment' line: nameLine ]. + lnum := lineNum. + self nextLex. + ^(AstAssignNode at: lnum) target: node expression: self readExpression + ]. ^self readCascade: node ] @@ -484,36 +519,36 @@ readCharCodeInBase: base maxLen: len line: lineNo doNC: aNCFlag [ ] readString [ - | cc str strline | + | c str strline | strline := lineNum. index := index - 1. str := StringBuffer new. - [ (cc := self nextChar) isEOF ifTrue: [ self error: 'unterminated string constant' line: strline ]. - cc ~= $' ] + [ (c := self nextChar) isEOF ifTrue: [ self error: 'unterminated string constant' line: strline ]. + c ~= $' ] whileTrue: [ - cc == $\ ifTrue: [ + c == $\ ifTrue: [ "escape sequence" - (cc := self nextChar) isEOF ifTrue: [ self error: 'unterminated string constant' line: strline ]. - Case test: cc lowerCase; - case: $a do: [ cc := Char new: 7 ]; - case: $b do: [ cc := Char new: 8 ]; - case: $d do: [ cc := Char new: 127 ]; "delete" - case: $e do: [ cc := Char new: 27 ]; "escape" - case: $f do: [ cc := Char new: 12 ]; "form feed" - case: $n do: [ cc := Char new: 10 ]; - case: $r do: [ cc := Char new: 13 ]; - case: $t do: [ cc := Char new: 9 ]; - case: $v do: [ cc := Char new: 11 ]; "vertical tab" - case: $z do: [ cc := Char new: 0 ]; - case: $\ do: [ cc := $\ ]; - case: $/ do: [ cc := $/ ]; - case: $" do: [ cc := $" ]; - case: $' do: [ cc := $' ]; - case: $x do: [ cc := Char new: (self readCharCodeInBase: 16 maxLen: 2 line: strline doNC: true) ]; - when: [:c | c value between: 48 and: 57] do: [ cc := Char new: (self readCharCodeInBase: 8 maxLen: 3 doNC: false) ]; - else: [ self error: 'invalid escape sequence: ' + cc asString line: strline ]. + (c := self nextChar) isEOF ifTrue: [ self error: 'unterminated string constant' line: strline ]. + Case test: c lowerCase; + case: $a do: [ c := Char new: 7 ]; + case: $b do: [ c := Char new: 8 ]; + case: $d do: [ c := Char new: 127 ]; "delete" + case: $e do: [ c := Char new: 27 ]; "escape" + case: $f do: [ c := Char new: 12 ]; "form feed" + case: $n do: [ c := Char new: 10 ]; + case: $r do: [ c := Char new: 13 ]; + case: $t do: [ c := Char new: 9 ]; + case: $v do: [ c := Char new: 11 ]; "vertical tab" + case: $z do: [ c := Char new: 0 ]; + case: $\ do: [ c := $\ ]; + case: $/ do: [ c := $/ ]; + case: $" do: [ c := $" ]; + case: $' do: [ c := $' ]; + case: $x do: [ c := Char new: (self readCharCodeInBase: 16 maxLen: 2 line: strline doNC: true) ]; + when: [:c | c value between: 48 and: 57] do: [ c := Char new: (self readCharCodeInBase: 8 maxLen: 3 doNC: false) ]; + else: [ self error: 'invalid escape sequence: ' + c asString line: strline ]. ]. - str << cc. + str << c. ]. self nextChar. str := str asString. @@ -523,15 +558,15 @@ readString [ ] readSymbol [ - | cc | - cc := self peekChar. - (cc isEOF or: [ cc isBlank ]) ifTrue: [ self error: 'invalid symbol' ]. - cc == $( ifTrue: [ ^self readArray ]. - cc == ${ ifTrue: [ ^self readSpecialArray ]. - (self charIsSyntax: cc) ifTrue: [ self error: 'invalid symbol' ]. + | c | + c := self peekChar. + (c isEOF or: [ c isBlank ]) ifTrue: [ self error: 'invalid symbol' ]. + c == $( ifTrue: [ ^self readArray ]. + c == ${ ifTrue: [ ^self readSpecialArray ]. + (self charIsSyntax: c) ifTrue: [ self error: 'invalid symbol' ]. self nextLex. - cc := Symbol new: token. self nextLex. - ^cc + c := Symbol new: token. self nextLex. + ^c ] readArray [ @@ -720,6 +755,7 @@ binaryContinuation: base [ receiver := self unaryContinuation: base. [ self tokenIsBinary ] whileTrue: [ + self tokenIsAssign ifTrue: [ ^self error: 'assign as binary -- previous statement not terminated' line: lexLineNum ]. lnum := lineNum. name := token asSymbol. self nextLex. -- 2.11.4.GIT