Senders of #@- not showing up

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|

Senders of #@- not showing up

marcel.taeumel
Hi, there.

I cannot browse the senders of #@-.


Best,
Marcel


Reply | Threaded
Open this post in threaded view
|

Re: Senders of #@- not showing up

Tobias Pape

> On 31.05.2018, at 12:26, Marcel Taeumel <[hidden email]> wrote:
>
> Hi, there.
>
> I cannot browse the senders of #@-

There's no sender of @- in that method. It probably was compiled at a time where 1@-1 was parsed as "1" "@" "-1", hence, no @-.

When you recompile, it should first warn and second be browsable.

-t


> <image.png>
>
> Best,
> Marcel
>


Reply | Threaded
Open this post in threaded view
|

Re: Senders of #@- not showing up

Eliot Miranda-2
In reply to this post by marcel.taeumel
Hi Marcel, Hi All,

On Thu, May 31, 2018 at 3:26 AM, Marcel Taeumel <[hidden email]> wrote:
Hi, there.

I cannot browse the senders of #@-.

I thought I'd try and look for examples of binary selectors followed by plus or minus signs.  It turned out to be harder than I thought. It did find an issue with Shout.  Shout incorrectly flags a keyword followed by a negative constant with no intervening whitespace as a syntax error.  e.g. this from IntervalTest>>testExtent
self assert: (1 to: 10) extent = 9.
self assert: (1 to: 10 by: 2) extent = 9.
self assert: (1 to:-1) extent = -2

Shout flags a syntax error from ":-1) extent", but this is legal.

Anyway, for the browse code I'm able to see just four false positives using the following looking for negative integers:

CurrentReadOnlySourceFiles cacheDuring:
[self systemNavigation browseAllSelect:
[:m|
(m scanForInstructionSequence:
[:a :b|
a selector = #pushConstant:
and: [a argument isInteger
and: [a argument negative
and: [b selector = #send:super:numArgs:
and: [b arguments first isBinary]]]]])
and: [| sansComments |
sansComments := String streamContents:
[:o| | inComment s |
inComment := false.
s := m getSource asString readStream.
[s atEnd] whileFalse:
[inComment
ifTrue: [s next = $" ifTrue: [inComment := false]]
ifFalse:
[s peek = $"
ifTrue: [inComment := true. s next]
ifFalse: [o nextPut: s next]]].
o contents].
(sansComments piecesCutWhere: [:a :b| b = $-]) allButLast
anySatisfy:
[:s| s last isSeparator not and: [s last isDigit not and: [('''${[()' includes: s last) not and: [s last asSymbol isBinary]]]]]]].

The scanForInstructionSequence: code looks for binary selectors with negative arguments (e.g. 1@-1).
sansComments strips the method source of its comments so we're not confused by characters in comments.
To look for binary selectors followed by '-' I use piecesCutWhere: to cut at the '-', and look at the last character of the preceding piece.
Alas a separator or a digit as symbol (e.g. #' ' and #'9') answer true to isBinary, so they need filtering out.
And there are plenty of occurrences of '-1' {-1. (-1 etc that are not examples of binary selectors.

The above found four false positives and no examples.  The following looks for positive numbers too. It's much slower, but also detects far more false positives.  Can anyone suggest better code?

CurrentReadOnlySourceFiles cacheDuring:
[self systemNavigation browseAllSelect:
[:m|
(m scanForInstructionSequence:
[:a :b|
a selector = #pushConstant:
and: [a argument isInteger
and: [b selector = #send:super:numArgs:
and: [b arguments first isBinary]]]])
and: [| sansComments |
sansComments := String streamContents:
[:o| | inComment s |
inComment := false.
s := m getSource asString readStream.
[s atEnd] whileFalse:
[inComment
ifTrue: [s next = $" ifTrue: [inComment := false]]
ifFalse:
[s peek = $"
ifTrue: [inComment := true. s next]
ifFalse: [o nextPut: s next]]].
o contents].
(sansComments piecesCutWhere: [:a :b| '+-' includes: b]) allButLast
anySatisfy:
[:s| s last isSeparator not and: [s last isDigit not and: [('''${[()' includes: s last) not and: [s last asSymbol isBinary]]]]]]].



Best,
Marcel

_,,,^..^,,,_
best, Eliot


Reply | Threaded
Open this post in threaded view
|

Re: Senders of #@- not showing up

Eliot Miranda-2


On Thu, May 31, 2018 at 1:22 PM, Eliot Miranda <[hidden email]> wrote:
Hi Marcel, Hi All,

On Thu, May 31, 2018 at 3:26 AM, Marcel Taeumel <[hidden email]> wrote:
Hi, there.

I cannot browse the senders of #@-.

I thought I'd try and look for examples of binary selectors followed by plus or minus signs.  It turned out to be harder than I thought. It did find an issue with Shout.  Shout incorrectly flags a keyword followed by a negative constant with no intervening whitespace as a syntax error.  e.g. this from IntervalTest>>testExtent
self assert: (1 to: 10) extent = 9.
self assert: (1 to: 10 by: 2) extent = 9.
self assert: (1 to:-1) extent = -2

Shout flags a syntax error from ":-1) extent", but this is legal.

Anyway, for the browse code I'm able to see just four false positives using the following looking for negative integers:

CurrentReadOnlySourceFiles cacheDuring:
[self systemNavigation browseAllSelect:
[:m|
(m scanForInstructionSequence:
[:a :b|
a selector = #pushConstant:
and: [a argument isInteger
and: [a argument negative
and: [b selector = #send:super:numArgs:
and: [b arguments first isBinary]]]]])
and: [| sansComments |
sansComments := String streamContents:
[:o| | inComment s |
inComment := false.
s := m getSource asString readStream.
[s atEnd] whileFalse:
[inComment
ifTrue: [s next = $" ifTrue: [inComment := false]]
ifFalse:
[s peek = $"
ifTrue: [inComment := true. s next]
ifFalse: [o nextPut: s next]]].
o contents].
(sansComments piecesCutWhere: [:a :b| b = $-]) allButLast
anySatisfy:
[:s| s last isSeparator not and: [s last isDigit not and: [('''${[()' includes: s last) not and: [s last asSymbol isBinary]]]]]]].

The scanForInstructionSequence: code looks for binary selectors with negative arguments (e.g. 1@-1).
sansComments strips the method source of its comments so we're not confused by characters in comments.
To look for binary selectors followed by '-' I use piecesCutWhere: to cut at the '-', and look at the last character of the preceding piece.
Alas a separator or a digit as symbol (e.g. #' ' and #'9') answer true to isBinary, so they need filtering out.
And there are plenty of occurrences of '-1' {-1. (-1 etc that are not examples of binary selectors.

The above found four false positives and no examples.  The following looks for positive numbers too. It's much slower, but also detects far more false positives.  Can anyone suggest better code?

Doh!  Here's a much better way.  We can use the scanner to tokenize the method and find offending binary tokens in the stream:

CurrentReadOnlySourceFiles cacheDuring:
[self systemNavigation browseAllSelect:
[:m|
(m scanForInstructionSequence:
[:a :b|
a selector = #pushConstant:
and: [a argument isInteger
and: [b selector = #send:super:numArgs:
and: [b arguments first isBinary]]]])
and: [(Scanner new typedScanTokens: m getSource) anySatisfy:
[:t| t isSymbol and: [t isBinary and: [t size > 1 and: ['+-' includes: t last]]]]]]]
 
With this I find only one method, a false positive, Utilities class>>#fixUpProblemsWithAllCategory, which contains the symbol #'-- all --'


CurrentReadOnlySourceFiles cacheDuring:
[self systemNavigation browseAllSelect:
[:m|
(m scanForInstructionSequence:
[:a :b|
a selector = #pushConstant:
and: [a argument isInteger
and: [b selector = #send:super:numArgs:
and: [b arguments first isBinary]]]])
and: [| sansComments |
sansComments := String streamContents:
[:o| | inComment s |
inComment := false.
s := m getSource asString readStream.
[s atEnd] whileFalse:
[inComment
ifTrue: [s next = $" ifTrue: [inComment := false]]
ifFalse:
[s peek = $"
ifTrue: [inComment := true. s next]
ifFalse: [o nextPut: s next]]].
o contents].
(sansComments piecesCutWhere: [:a :b| '+-' includes: b]) allButLast
anySatisfy:
[:s| s last isSeparator not and: [s last isDigit not and: [('''${[()' includes: s last) not and: [s last asSymbol isBinary]]]]]]].



Best,
Marcel

_,,,^..^,,,_
best, Eliot



--
_,,,^..^,,,_
best, Eliot