DependentsArray size and subscript is out of bounds

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

DependentsArray size and subscript is out of bounds

Mathieu SUEN
Hi,

It is normal that:

(DependentsArray new: 100) size

return 0?

If yes so why?

And if I do:

| o |
o := WriteStream on: (DependentsArray new: 100).
1 to: 24 do: [:each | o nextPut: Object new]. "do it sevral time"

it raise an error 'subscript is out of bounds: 22' from time to time
why?

Thx
Math

Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Nicolas Cellier-3
Le Jeudi 20 Juillet 2006 00:38, mathieu a écrit :
> Hi,
>
> It is normal that:
>
> (DependentsArray new: 100) size
>
> return 0?

Yes

> If yes so why?

DependentsArray count only non nil elements

> And if I do:
> | o |
>
> o := WriteStream on: (DependentsArray new: 100).
> 1 to: 24 do: [:each | o nextPut: Object new]. "do it sevral time"
>
> it raise an error 'subscript is out of bounds: 22' from time to time
> why?

You cannot do that with DependentsArray.

DependentsArray are weak array: that mean that storing an object into a
DependentsArray does not prevent it from being garbageCollected.

When an element is garbage collected, corresponding index in DependentsArray
is replaced by nil.

All is occuring in pastEndPut:
Since initial size (non nil elements) is zero, then the array is grown to
size: oldSize + ((oldSize max: 20) min: 1000000)

When no garbageCollection occurs, that works fine (except a new
DependentsArray is created each time you add an Object).

When a garbage collect occurs, all unreferenced (Object new) are removed from
the DependentsArray, except one (I do not know who is referencing it, maybe
the BlockContext...).

Thus you allocate a DependentsArray of size 21 and fail when storing element
number 22...

> Thx
> Math

What do you need DependentsArray for?

Nicolas


Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Mathieu SUEN
nicolas cellier a écrit :

> Le Jeudi 20 Juillet 2006 00:38, mathieu a écrit :
>> Hi,
>>
>> It is normal that:
>>
>> (DependentsArray new: 100) size
>>
>> return 0?
>
> Yes
>
>> If yes so why?
>
> DependentsArray count only non nil elements
>
>> And if I do:
>> | o |
>>
>> o := WriteStream on: (DependentsArray new: 100).
>> 1 to: 24 do: [:each | o nextPut: Object new]. "do it sevral time"
>>
>> it raise an error 'subscript is out of bounds: 22' from time to time
>> why?
>
> You cannot do that with DependentsArray.
>
> DependentsArray are weak array: that mean that storing an object into a
> DependentsArray does not prevent it from being garbageCollected.
>
> When an element is garbage collected, corresponding index in DependentsArray
> is replaced by nil.
>
> All is occuring in pastEndPut:
> Since initial size (non nil elements) is zero, then the array is grown to
> size: oldSize + ((oldSize max: 20) min: 1000000)
>
> When no garbageCollection occurs, that works fine (except a new
> DependentsArray is created each time you add an Object).
>
> When a garbage collect occurs, all unreferenced (Object new) are removed from
> the DependentsArray, except one (I do not know who is referencing it, maybe
> the BlockContext...).
>
> Thus you allocate a DependentsArray of size 21 and fail when storing element
> number 22...
>
>> Thx
>> Math
>
> What do you need DependentsArray for?
>
> Nicolas

ok thx :)

In fact this is "used" in SmaCC and raise this error:

======================================================
DependentsArray(Object)>>error:
        Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
<period> ">" <name> E O F)
        Arguments and temporary variables:
                aString: *'subscript is out of bounds: 23'*
        Receiver's instance variables:
a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
<name> E O F)

DependentsArray(Object)>>errorSubscriptBounds:
        Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
<period> ">" <name> E O F)
        Arguments and temporary variables:
                index: 23
        Receiver's instance variables:
a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
<name> E O F)

DependentsArray(Object)>>at:put:
        Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
<period> ">" <name> E O F)
        Arguments and temporary variables:
                index: 23
                value:
        Receiver's instance variables:
a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
<name> E O F)

WriteStream>>pastEndPut:
        Receiver: <<error during printing>>
        Arguments and temporary variables:
                anObject:
                oldSize: 2
                grownCollection: a DependentsArray(<keyword> ")" "]" <binarySymbol>
"}" ";" <pe...etc...
        Receiver's instance variables:
                collection: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}"
";" <period>...etc...
                position: 23
                readLimit: 23
                writeLimit: 1


--- The full stack ---
DependentsArray(Object)>>error:
DependentsArray(Object)>>errorSubscriptBounds:
DependentsArray(Object)>>at:put:
WriteStream>>pastEndPut:
 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
WriteStream>>nextPut:
[] in DependentsArray>>copyWith: {[:s |  self   do: [:item | s nextPut:
item].  s nextPut: newElement]}
DependentsArray class(SequenceableCollection class)>>streamContents:
DependentsArray>>copyWith:
DependentsArray(Array)>>copyWithDependent:
SmaCCSymbolSet(Object)>>addDependent:
SmaCCSymbolSet>>addComponent:
SmaCCSymbolSet>>baseOn:
SmaCCSymbolSet class>>basedOn:
SmaCCLR1Item>>moveNext
[] in SmaCCItemSet>>moveOn: {[:each | each nextSymbol == aGrammarSymbol
  ifTrue: [anItemSet add: each mo...]}
SmaCCItemSet(Set)>>do:
SmaCCItemSet>>moveOn:
[] in SmaCCGrammarCompiler>>createItemSets {[:each |  newState :=
itemSet moveOn: each.  newState notEmpty   ifTrue: [sh...]}
SortedCollection(OrderedCollection)>>do:
SmaCCGrammarCompiler>>createItemSets
SmaCCGrammarCompiler>>transitionTable
SmaCCGrammarCompiler>>compileTransitionTable
SmaCCGrammarCompiler>>compileParser
SmaCCGrammarCompiler>>createChanges
======================================================



Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Andrew Tween
Hi,
I think that the problem occurs iff a garbage collect/finalization occurs during
the DependentsArray>>copyWith: .

This code exhibits the problem that you describe...

     d := (DependentsArray new: 1).
     1 to: 50 do:[:i |
        d := d copyWith: Object new ].

whereas this code runs without error....

    d := (DependentsArray new: 1).
    1 to: 50 do:[:i |
          Smalltalk garbageCollect.
          d := d copyWith: Object new ].

I have also seen this problem when using Smacc, but didn't solve the root cause
of the problem. I just did a garbage collect before generating the
parser/scanner and the problem went away.

Hope this helps.
Cheers,
Andy



----- Original Message -----
From: "mathieu" <[hidden email]>
To: <[hidden email]>; "The general-purpose Squeak developers list"
<[hidden email]>
Sent: Thursday, July 20, 2006 6:49 AM
Subject: Re: DependentsArray size and subscript is out of bounds


> nicolas cellier a écrit :
> > Le Jeudi 20 Juillet 2006 00:38, mathieu a écrit :
> >> Hi,
> >>
> >> It is normal that:
> >>
> >> (DependentsArray new: 100) size
> >>
> >> return 0?
> >
> > Yes
> >
> >> If yes so why?
> >
> > DependentsArray count only non nil elements
> >
> >> And if I do:
> >> | o |
> >>
> >> o := WriteStream on: (DependentsArray new: 100).
> >> 1 to: 24 do: [:each | o nextPut: Object new]. "do it sevral time"
> >>
> >> it raise an error 'subscript is out of bounds: 22' from time to time
> >> why?
> >
> > You cannot do that with DependentsArray.
> >
> > DependentsArray are weak array: that mean that storing an object into a
> > DependentsArray does not prevent it from being garbageCollected.
> >
> > When an element is garbage collected, corresponding index in DependentsArray
> > is replaced by nil.
> >
> > All is occuring in pastEndPut:
> > Since initial size (non nil elements) is zero, then the array is grown to
> > size: oldSize + ((oldSize max: 20) min: 1000000)
> >
> > When no garbageCollection occurs, that works fine (except a new
> > DependentsArray is created each time you add an Object).
> >
> > When a garbage collect occurs, all unreferenced (Object new) are removed
from

> > the DependentsArray, except one (I do not know who is referencing it, maybe
> > the BlockContext...).
> >
> > Thus you allocate a DependentsArray of size 21 and fail when storing element
> > number 22...
> >
> >> Thx
> >> Math
> >
> > What do you need DependentsArray for?
> >
> > Nicolas
>
> ok thx :)
>
> In fact this is "used" in SmaCC and raise this error:
>
> ======================================================
> DependentsArray(Object)>>error:
> Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
> <period> ">" <name> E O F)
> Arguments and temporary variables:
> aString: *'subscript is out of bounds: 23'*
> Receiver's instance variables:
> a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
> <name> E O F)
>
> DependentsArray(Object)>>errorSubscriptBounds:
> Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
> <period> ">" <name> E O F)
> Arguments and temporary variables:
> index: 23
> Receiver's instance variables:
> a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
> <name> E O F)
>
> DependentsArray(Object)>>at:put:
> Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
> <period> ">" <name> E O F)
> Arguments and temporary variables:
> index: 23
> value:
> Receiver's instance variables:
> a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
> <name> E O F)
>
> WriteStream>>pastEndPut:
> Receiver: <<error during printing>>
> Arguments and temporary variables:
> anObject:
> oldSize: 2
> grownCollection: a DependentsArray(<keyword> ")" "]" <binarySymbol>
> "}" ";" <pe...etc...
> Receiver's instance variables:
> collection: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}"
> ";" <period>...etc...
> position: 23
> readLimit: 23
> writeLimit: 1
>
>
> --- The full stack ---
> DependentsArray(Object)>>error:
> DependentsArray(Object)>>errorSubscriptBounds:
> DependentsArray(Object)>>at:put:
> WriteStream>>pastEndPut:
>  - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
> WriteStream>>nextPut:
> [] in DependentsArray>>copyWith: {[:s |  self   do: [:item | s nextPut:
> item].  s nextPut: newElement]}
> DependentsArray class(SequenceableCollection class)>>streamContents:
> DependentsArray>>copyWith:
> DependentsArray(Array)>>copyWithDependent:
> SmaCCSymbolSet(Object)>>addDependent:
> SmaCCSymbolSet>>addComponent:
> SmaCCSymbolSet>>baseOn:
> SmaCCSymbolSet class>>basedOn:
> SmaCCLR1Item>>moveNext
> [] in SmaCCItemSet>>moveOn: {[:each | each nextSymbol == aGrammarSymbol
>   ifTrue: [anItemSet add: each mo...]}
> SmaCCItemSet(Set)>>do:
> SmaCCItemSet>>moveOn:
> [] in SmaCCGrammarCompiler>>createItemSets {[:each |  newState :=
> itemSet moveOn: each.  newState notEmpty   ifTrue: [sh...]}
> SortedCollection(OrderedCollection)>>do:
> SmaCCGrammarCompiler>>createItemSets
> SmaCCGrammarCompiler>>transitionTable
> SmaCCGrammarCompiler>>compileTransitionTable
> SmaCCGrammarCompiler>>compileParser
> SmaCCGrammarCompiler>>createChanges
> ======================================================
>
>
>
>

Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Nicolas Cellier-3
OK, so this is not a bug of SmaCC, this is one of the many bugs in
DependentsArray...

(see http://bugs.impara.de/view.php?id=2701)

As long as #at: and #size messages are not defined consistently
(possibility to use an index greater than size) DependentsArray cannot
inherit safely from SequenceableCollection.

It would be better to place it in a different hierarchy, maybe under
Collection...

Nicolas

Andrew Tween a écrit :

> Hi,
> I think that the problem occurs iff a garbage collect/finalization occurs during
> the DependentsArray>>copyWith: .
>
> This code exhibits the problem that you describe...
>
>      d := (DependentsArray new: 1).
>      1 to: 50 do:[:i |
>         d := d copyWith: Object new ].
>
> whereas this code runs without error....
>
>     d := (DependentsArray new: 1).
>     1 to: 50 do:[:i |
>           Smalltalk garbageCollect.
>           d := d copyWith: Object new ].
>
> I have also seen this problem when using Smacc, but didn't solve the root cause
> of the problem. I just did a garbage collect before generating the
> parser/scanner and the problem went away.
>
> Hope this helps.
> Cheers,
> Andy
>
>
>
> ----- Original Message -----
> From: "mathieu" <[hidden email]>
> To: <[hidden email]>; "The general-purpose Squeak developers list"
> <[hidden email]>
> Sent: Thursday, July 20, 2006 6:49 AM
> Subject: Re: DependentsArray size and subscript is out of bounds
>
>
>  
>> nicolas cellier a écrit :
>>    
>>> Le Jeudi 20 Juillet 2006 00:38, mathieu a écrit :
>>>      
>>>> Hi,
>>>>
>>>> It is normal that:
>>>>
>>>> (DependentsArray new: 100) size
>>>>
>>>> return 0?
>>>>        
>>> Yes
>>>
>>>      
>>>> If yes so why?
>>>>        
>>> DependentsArray count only non nil elements
>>>
>>>      
>>>> And if I do:
>>>> | o |
>>>>
>>>> o := WriteStream on: (DependentsArray new: 100).
>>>> 1 to: 24 do: [:each | o nextPut: Object new]. "do it sevral time"
>>>>
>>>> it raise an error 'subscript is out of bounds: 22' from time to time
>>>> why?
>>>>        
>>> You cannot do that with DependentsArray.
>>>
>>> DependentsArray are weak array: that mean that storing an object into a
>>> DependentsArray does not prevent it from being garbageCollected.
>>>
>>> When an element is garbage collected, corresponding index in DependentsArray
>>> is replaced by nil.
>>>
>>> All is occuring in pastEndPut:
>>> Since initial size (non nil elements) is zero, then the array is grown to
>>> size: oldSize + ((oldSize max: 20) min: 1000000)
>>>
>>> When no garbageCollection occurs, that works fine (except a new
>>> DependentsArray is created each time you add an Object).
>>>
>>> When a garbage collect occurs, all unreferenced (Object new) are removed
>>>      
> from
>  
>>> the DependentsArray, except one (I do not know who is referencing it, maybe
>>> the BlockContext...).
>>>
>>> Thus you allocate a DependentsArray of size 21 and fail when storing element
>>> number 22...
>>>
>>>      
>>>> Thx
>>>> Math
>>>>        
>>> What do you need DependentsArray for?
>>>
>>> Nicolas
>>>      
>> ok thx :)
>>
>> In fact this is "used" in SmaCC and raise this error:
>>
>> ======================================================
>> DependentsArray(Object)>>error:
>> Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
>> <period> ">" <name> E O F)
>> Arguments and temporary variables:
>> aString: *'subscript is out of bounds: 23'*
>> Receiver's instance variables:
>> a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
>> <name> E O F)
>>
>> DependentsArray(Object)>>errorSubscriptBounds:
>> Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
>> <period> ">" <name> E O F)
>> Arguments and temporary variables:
>> index: 23
>> Receiver's instance variables:
>> a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
>> <name> E O F)
>>
>> DependentsArray(Object)>>at:put:
>> Receiver: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";"
>> <period> ">" <name> E O F)
>> Arguments and temporary variables:
>> index: 23
>> value:
>> Receiver's instance variables:
>> a DependentsArray(<keyword> ")" "]" <binarySymbol> "}" ";" <period> ">"
>> <name> E O F)
>>
>> WriteStream>>pastEndPut:
>> Receiver: <<error during printing>>
>> Arguments and temporary variables:
>> anObject:
>> oldSize: 2
>> grownCollection: a DependentsArray(<keyword> ")" "]" <binarySymbol>
>> "}" ";" <pe...etc...
>> Receiver's instance variables:
>> collection: a DependentsArray(<keyword> ")" "]" <binarySymbol> "}"
>> ";" <period>...etc...
>> position: 23
>> readLimit: 23
>> writeLimit: 1
>>
>>
>> --- The full stack ---
>> DependentsArray(Object)>>error:
>> DependentsArray(Object)>>errorSubscriptBounds:
>> DependentsArray(Object)>>at:put:
>> WriteStream>>pastEndPut:
>>  - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
>> WriteStream>>nextPut:
>> [] in DependentsArray>>copyWith: {[:s |  self   do: [:item | s nextPut:
>> item].  s nextPut: newElement]}
>> DependentsArray class(SequenceableCollection class)>>streamContents:
>> DependentsArray>>copyWith:
>> DependentsArray(Array)>>copyWithDependent:
>> SmaCCSymbolSet(Object)>>addDependent:
>> SmaCCSymbolSet>>addComponent:
>> SmaCCSymbolSet>>baseOn:
>> SmaCCSymbolSet class>>basedOn:
>> SmaCCLR1Item>>moveNext
>> [] in SmaCCItemSet>>moveOn: {[:each | each nextSymbol == aGrammarSymbol
>>   ifTrue: [anItemSet add: each mo...]}
>> SmaCCItemSet(Set)>>do:
>> SmaCCItemSet>>moveOn:
>> [] in SmaCCGrammarCompiler>>createItemSets {[:each |  newState :=
>> itemSet moveOn: each.  newState notEmpty   ifTrue: [sh...]}
>> SortedCollection(OrderedCollection)>>do:
>> SmaCCGrammarCompiler>>createItemSets
>> SmaCCGrammarCompiler>>transitionTable
>> SmaCCGrammarCompiler>>compileTransitionTable
>> SmaCCGrammarCompiler>>compileParser
>> SmaCCGrammarCompiler>>createChanges
>> ======================================================
>>
>>
>>
>>
>>    
>
>
>  


Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Marcus Denker
In reply to this post by Andrew Tween

On 20.07.2006, at 10:37, Andrew Tween wrote:

>
>
> I have also seen this problem when using Smacc, but didn't solve  
> the root cause
> of the problem. I just did a garbage collect before generating the
> parser/scanner and the problem went away.
>

So I changed the parser generator to do a "Smalltalk garbageCollect"  
befor compiling
a grammar. It's in SmaCCDev-md.4.mcz

http://www.squeaksource.com/SmaccDevelopment

I did not yet test if it really helps, though.

        Marcus


smime.p7s (5K) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Mathieu SUEN
2006/7/21, Marcus Denker <[hidden email]>:

>
> On 20.07.2006, at 10:37, Andrew Tween wrote:
>
> >
> >
> > I have also seen this problem when using Smacc, but didn't solve
> > the root cause
> > of the problem. I just did a garbage collect before generating the
> > parser/scanner and the problem went away.
> >
>
> So I changed the parser generator to do a "Smalltalk garbageCollect"
> befor compiling
> a grammar. It's in SmaCCDev-md.4.mcz
>
> http://www.squeaksource.com/SmaccDevelopment
>
> I did not yet test if it really helps, though.
>
>         Marcus
>
>
Yep thanks Marcus I will try
>
>
>
>

Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Andrew Tween
If you still have problems, even with the garbage collect, then you could try
modifying DependentsArray>>copyWith: to something like this...

---------
copyWith: newElement
 "Re-implemented to not copy any niled out dependents.
 The receiver's elements are copied into a temporary collection
 to prevent them from being being garbage collected while the
 copy is being made"
 | answer tmp element |

 tmp := IdentitySet new: self basicSize.
 1 to: self basicSize do:[:i2 |
  (element := self at: i2)
   ifNotNil:[tmp add: element]].
 answer := self class streamContents:[:s|
  self do:[:item| s nextPut: item].
  s nextPut: newElement].
 ^answer
-----------

This solves the previous "test case", and doesn't appear to have any adverse
effects.
Cheers,
Andy

----- Original Message -----
From: "Mathieu SUEN" <[hidden email]>
To: "The general-purpose Squeak developers list"
<[hidden email]>
Sent: Friday, July 21, 2006 10:23 AM
Subject: Re: DependentsArray size and subscript is out of bounds


> 2006/7/21, Marcus Denker <[hidden email]>:
> >
> > On 20.07.2006, at 10:37, Andrew Tween wrote:
> >
> > >
> > >
> > > I have also seen this problem when using Smacc, but didn't solve
> > > the root cause
> > > of the problem. I just did a garbage collect before generating the
> > > parser/scanner and the problem went away.
> > >
> >
> > So I changed the parser generator to do a "Smalltalk garbageCollect"
> > befor compiling
> > a grammar. It's in SmaCCDev-md.4.mcz
> >
> > http://www.squeaksource.com/SmaccDevelopment
> >
> > I did not yet test if it really helps, though.
> >
> >         Marcus
> >
> >
> Yep thanks Marcus I will try
> >
> >
> >
> >
>
>



DependentsArrayFix.1.cs (743 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

[FIX] Re: DependentsArray size and subscript is out of bounds

Bert Freudenberg-3
Andrew,

if you try this:

| a |
a := DependentsArray new.
[1 to: 1000 do: [:i | a := a copyWith: Object new]] timeToRun

The old code will complete that in less than a second. Your version  
takes 3 minutes (I think because of hidden size calls on the  
DependentsArray which are very expensive). This is not a realistic  
use case, but still ;-)

I suggest the following:

copyWith: newElement
        "Re-implemented to not copy any niled out dependents."
        | copy i |
        copy := self class new: self size + 1.
        i := 0.
        self do: [:item | copy at: (i:=i+1) put: item].
        copy at: (i:=i+1) put: newElement.
        ^copy

This appears to be even more efficient than the original. I'll attach  
the CS.

The actual problem was that #streamContents: does not work correctly  
with dynamically sized collections (capacity ~= size). Try this for  
the same problem:

        OrderedCollection streamContents: [:s | s nextPut: 42]

Creating strong refs temporarily would only fix a symptom of that  
issue. Not sure if it's a bug.

- Bert -

Am 21.07.2006 um 11:45 schrieb Andrew Tween:

> If you still have problems, even with the garbage collect, then you  
> could try
> modifying DependentsArray>>copyWith: to something like this...
>
> ---------
> copyWith: newElement
>  "Re-implemented to not copy any niled out dependents.
>  The receiver's elements are copied into a temporary collection
>  to prevent them from being being garbage collected while the
>  copy is being made"
>  | answer tmp element |
>
>  tmp := IdentitySet new: self basicSize.
>  1 to: self basicSize do:[:i2 |
>   (element := self at: i2)
>    ifNotNil:[tmp add: element]].
>  answer := self class streamContents:[:s|
>   self do:[:item| s nextPut: item].
>   s nextPut: newElement].
>  ^answer
> -----------
>
> This solves the previous "test case", and doesn't appear to have  
> any adverse
> effects.
> Cheers,
> Andy
>
> ----- Original Message -----
> From: "Mathieu SUEN" <[hidden email]>
> To: "The general-purpose Squeak developers list"
> <[hidden email]>
> Sent: Friday, July 21, 2006 10:23 AM
> Subject: Re: DependentsArray size and subscript is out of bounds
>
>
>> 2006/7/21, Marcus Denker <[hidden email]>:
>>>
>>> On 20.07.2006, at 10:37, Andrew Tween wrote:
>>>
>>>>
>>>>
>>>> I have also seen this problem when using Smacc, but didn't solve
>>>> the root cause
>>>> of the problem. I just did a garbage collect before generating the
>>>> parser/scanner and the problem went away.
>>>>
>>>
>>> So I changed the parser generator to do a "Smalltalk garbageCollect"
>>> befor compiling
>>> a grammar. It's in SmaCCDev-md.4.mcz
>>>
>>> http://www.squeaksource.com/SmaccDevelopment
>>>
>>> I did not yet test if it really helps, though.
>>>
>>>         Marcus
>>>
>>>
>> Yep thanks Marcus I will try
>>>
>>>
>>>
>>>
>>
>>
>> <DependentsArrayFix.1.cs>
>





depArrayFix-bf.1.cs.gz (552 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: [FIX] Re: DependentsArray size and subscript is out of bounds

Andrew Tween
..

> if you try this:
>
> | a |
> a := DependentsArray new.
> [1 to: 1000 do: [:i | a := a copyWith: Object new]] timeToRun
>
> The old code will complete that in less than a second. Your version
> takes 3 minutes (I think because of hidden size calls on the
> DependentsArray which are very expensive). This is not a realistic
> use case, but still ;-)

Well...the old code fails within a second , at least on my machine ;)
With a slightly different test...
    | a |
    a := DependentsArray new.
    [1 to: 1000 do: [:i | a := a copyWith: i]] timeToRun.
I get these timings...
old code: 5.5 minutes
my fix: 5.6 minutes

>
> I suggest the following:
>
> copyWith: newElement
> "Re-implemented to not copy any niled out dependents."
> | copy i |
> copy := self class new: self size + 1.
> i := 0.
> self do: [:item | copy at: (i:=i+1) put: item].
> copy at: (i:=i+1) put: newElement.
> ^copy
>
> This appears to be even more efficient than the original. I'll attach
> the CS.

Using the same timing test as above, we have....

old code: 5.5 minutes
my fix: 5.6 minutes
your fix: 0.6 seconds

Congrats. I think that qualifies for 'speed-up' of the day (or month, or year,
or decade ?)
Cheers,
Andy

..

Reply | Threaded
Open this post in threaded view
|

Re: [FIX] Re: DependentsArray size and subscript is out of bounds

Mathieu SUEN
Andrew Tween a écrit :

> ..
>> if you try this:
>>
>> | a |
>> a := DependentsArray new.
>> [1 to: 1000 do: [:i | a := a copyWith: Object new]] timeToRun
>>
>> The old code will complete that in less than a second. Your version
>> takes 3 minutes (I think because of hidden size calls on the
>> DependentsArray which are very expensive). This is not a realistic
>> use case, but still ;-)
>
> Well...the old code fails within a second , at least on my machine ;)
> With a slightly different test...
>     | a |
>     a := DependentsArray new.
>     [1 to: 1000 do: [:i | a := a copyWith: i]] timeToRun.
> I get these timings...
> old code: 5.5 minutes
> my fix: 5.6 minutes
>
>> I suggest the following:
>>
>> copyWith: newElement
>> "Re-implemented to not copy any niled out dependents."
>> | copy i |
>> copy := self class new: self size + 1.
>> i := 0.
>> self do: [:item | copy at: (i:=i+1) put: item].
>> copy at: (i:=i+1) put: newElement.
>> ^copy

Yes! Well done. SmaCC works fine now thanks

>>
>> This appears to be even more efficient than the original. I'll attach
>> the CS.
>
> Using the same timing test as above, we have....
>
> old code: 5.5 minutes
> my fix: 5.6 minutes
> your fix: 0.6 seconds
>
> Congrats. I think that qualifies for 'speed-up' of the day (or month, or year,
> or decade ?)
> Cheers,
> Andy
>
> ..
>
>


Reply | Threaded
Open this post in threaded view
|

Re: DependentsArray size and subscript is out of bounds

Mathieu SUEN
In reply to this post by Marcus Denker
Marcus Denker a écrit :

>
> On 20.07.2006, at 10:37, Andrew Tween wrote:
>
>>
>>
>> I have also seen this problem when using Smacc, but didn't solve the
>> root cause
>> of the problem. I just did a garbage collect before generating the
>> parser/scanner and the problem went away.
>>
>
> So I changed the parser generator to do a "Smalltalk garbageCollect"
> befor compiling
> a grammar. It's in SmaCCDev-md.4.mcz
>
> http://www.squeaksource.com/SmaccDevelopment
>
> I did not yet test if it really helps, though.
>
>        Marcus
>
>
> ------------------------------------------------------------------------
>
>
Oops! It seem that nothing change for me but the fix of Bert works.

Even so thanks! :)

Reply | Threaded
Open this post in threaded view
|

Re: [FIX] Re: DependentsArray size and subscript is out of bounds

Bert Freudenberg-3
In reply to this post by Andrew Tween
Am 21.07.2006 um 18:39 schrieb Andrew Tween:

> ..
>> if you try this:
>>
>> | a |
>> a := DependentsArray new.
>> [1 to: 1000 do: [:i | a := a copyWith: Object new]] timeToRun
>>
>> The old code will complete that in less than a second. Your version
>> takes 3 minutes (I think because of hidden size calls on the
>> DependentsArray which are very expensive). This is not a realistic
>> use case, but still ;-)
>
> Well...the old code fails within a second , at least on my machine ;)
> With a slightly different test...
>     | a |
>     a := DependentsArray new.
>     [1 to: 1000 do: [:i | a := a copyWith: i]] timeToRun.
> I get these timings...
> old code: 5.5 minutes
> my fix: 5.6 minutes
>
>>
>> I suggest the following:
>>
>> copyWith: newElement
>> "Re-implemented to not copy any niled out dependents."
>> | copy i |
>> copy := self class new: self size + 1.
>> i := 0.
>> self do: [:item | copy at: (i:=i+1) put: item].
>> copy at: (i:=i+1) put: newElement.
>> ^copy
>>
>> This appears to be even more efficient than the original. I'll attach
>> the CS.
>
> Using the same timing test as above, we have....
>
> old code: 5.5 minutes
> my fix: 5.6 minutes
> your fix: 0.6 seconds
>
> Congrats. I think that qualifies for 'speed-up' of the day (or  
> month, or year,
> or decade ?)
> Cheers,
> Andy

Thanks. This stuff is hard to measure consistently because  
finalization differs from VM to VM and is rather unpredictable. But  
my open-coded version at least should be easily understandable.

Could anybody please take care to get this into 3.9?

- Bert -


Reply | Threaded
Open this post in threaded view
|

Re: [FIX] Re: DependentsArray size and subscript is out of bounds

Marcus Denker

On 23.07.2006, at 15:52, Bert Freudenberg wrote:

>
> Thanks. This stuff is hard to measure consistently because  
> finalization differs from VM to VM and is rather unpredictable. But  
> my open-coded version at least should be easily understandable.
>
> Could anybody please take care to get this into 3.9?

It is in 7048

     Marcus


smime.p7s (5K) Download Attachment