Just print this two scripts:
|s| s := WideString with: (Character value: 16r55E4). [100000 timesRepeat: [s hash]] timeToRun. |s| s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4). [100000 timesRepeat: [s hash]] timeToRun. I've seen that "ByteString>>stringHash:initialHash" use a primitive. Could we have such optimisation for WideString ? Christophe. |
On Fri, 14 May 2010, [hidden email] wrote:
> Just print this two scripts: > > |s| > s := WideString with: (Character value: 16r55E4). > [100000 timesRepeat: [s hash]] timeToRun. > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000 timesRepeat: [s hash]] timeToRun. > > I've seen that "ByteString>>stringHash:initialHash" use a primitive. Could we > have such optimisation for WideString ? Sure. There are (at least) four ways to do it: 1) Update the implementation of the primitive to support wordarrays. Then build a vm with it and finally change the image side code. This would be the best IMHO. Is there a reason why the primitive is not implemented this way? 2) Use NativeBoost to write a primitive for this method. This is much easier than building a vm/plugin, though you have to write the code in X86 assembly. This would be a cool demo for NativeBoost's primitive writing capabilities. (Much better than the Fibonacci-number calculator. :)) 3) Use Exupery, I think it can optimize methods like this. 4) Use the Cog VM. ;) (I wonder how fast this method is with Cog.) Levente > > Christophe. > > |
On 5/14/10, Levente Uzonyi <[hidden email]> wrote:
> On Fri, 14 May 2010, [hidden email] wrote: > >> Just print this two scripts: >> >> |s| >> s := WideString with: (Character value: 16r55E4). >> [100000 timesRepeat: [s hash]] timeToRun. >> >> |s| >> s := ByteString with: (Character value: 16rE4) with: (Character value: >> 16rE4) >> with: (Character value: 16rE4) with: (Character value: 16rE4). >> [100000 timesRepeat: [s hash]] timeToRun. >> >> I've seen that "ByteString>>stringHash:initialHash" use a primitive. Could >> we >> have such optimisation for WideString ? > Sure. There are (at least) four ways to do it: > 1) Update the implementation of the primitive to support wordarrays. Then > build a vm with it and finally change the image side code. This would be > the best IMHO. Is there a reason why the primitive is not implemented this > way? If this is not a work you feel comfortable with then post this on the VM developer list and/or create a Mantis entry. > 2) Use NativeBoost to write a primitive for this method. This is much > easier than building a vm/plugin, though you have to write the code in X86 > assembly. This would be a cool demo for NativeBoost's primitive writing > capabilities. (Much better than the Fibonacci-number calculator. :)) Yes, this would be a very good demonstration. > 3) Use Exupery, I think it can optimize methods like this. > 4) Use the Cog VM. ;) (I wonder how fast this method is with Cog.) What kind of VM are we using in 4.1? It supports closures, but seeminly is not the Cog VM(yet)? Hannes |
In reply to this post by Levente Uzonyi-2
On Fri, May 14, 2010 at 10:28 AM, Levente Uzonyi <[hidden email]> wrote:
2.66GHz Intel Core i7 MacBook Pro (my new tool!!!!). Current Cog, my 3.8 derived work image:
|s| s := WideString with: (Character value: 16r55E4). [100000 timesRepeat: [s hash]] timeToRun. 16 |s| s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4)
with: (Character value: 16rE4) with: (Character value: 16rE4). [100000 timesRepeat: [s hash]] timeToRun. 10 |s| s := WideString with: (Character value: 16r55E4).
[100000000 timesRepeat: [s hash]] timeToRun. 15725 |s| s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4).
[100000000 timesRepeat: [s hash]] timeToRun. 11078 Current 4.1/Squeak 4.1.1beta2U.app: |s| s := WideString with: (Character value: 16r55E4).
[100000 timesRepeat: [s hash]] timeToRun. 98 |s| s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4).
[100000 timesRepeat: [s hash]] timeToRun. 31 |s| s := WideString with: (Character value: 16r55E4). [100000000 timesRepeat: [s hash]] timeToRun. 100660 |s| s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4). [100000000 timesRepeat: [s hash]] timeToRun. 29476
Current 4.1/current Cog |s| s := WideString with: (Character value: 16r55E4). [100000 timesRepeat: [s hash]] timeToRun. 14 |s|
s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4) with: (Character value: 16rE4). [100000 timesRepeat: [s hash]] timeToRun. 10 |s| s := WideString with: (Character value: 16r55E4). [100000000 timesRepeat: [s hash]] timeToRun. 14946 |s| s := ByteString with: (Character value: 16rE4) with: (Character value: 16rE4)
with: (Character value: 16rE4) with: (Character value: 16rE4). [100000000 timesRepeat: [s hash]] timeToRun. 10171 So quite a bit faster :) best Eliot
|
On Fri, 14 May 2010, Eliot Miranda wrote:
> On Fri, May 14, 2010 at 10:28 AM, Levente Uzonyi <[hidden email]> wrote: > >> On Fri, 14 May 2010, [hidden email] wrote: >> >> Just print this two scripts: >>> >>> |s| >>> s := WideString with: (Character value: 16r55E4). >>> [100000 timesRepeat: [s hash]] timeToRun. >>> >>> |s| >>> s := ByteString with: (Character value: 16rE4) with: (Character value: >>> 16rE4) >>> with: (Character value: 16rE4) with: (Character value: 16rE4). >>> [100000 timesRepeat: [s hash]] timeToRun. >>> >>> I've seen that "ByteString>>stringHash:initialHash" use a primitive. Could >>> we >>> have such optimisation for WideString ? >>> >> >> Sure. There are (at least) four ways to do it: >> 1) Update the implementation of the primitive to support wordarrays. Then >> build a vm with it and finally change the image side code. This would be the >> best IMHO. Is there a reason why the primitive is not implemented this way? >> 2) Use NativeBoost to write a primitive for this method. This is much >> easier than building a vm/plugin, though you have to write the code in X86 >> assembly. This would be a cool demo for NativeBoost's primitive writing >> capabilities. (Much better than the Fibonacci-number calculator. :)) >> 3) Use Exupery, I think it can optimize methods like this. >> 4) Use the Cog VM. ;) (I wonder how fast this method is with Cog.) >> > > 2.66GHz Intel Core i7 MacBook Pro (my new tool!!!!). Current Cog, my 3.8 > derived work image: > > |s| > s := WideString with: (Character value: 16r55E4). > [100000 timesRepeat: [s hash]] timeToRun. 16 > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: > 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000 timesRepeat: [s hash]] timeToRun. 10 > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s hash]] timeToRun. 15725 > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: > 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000000 timesRepeat: [s hash]] timeToRun. 11078 > > > Current 4.1/Squeak 4.1.1beta2U.app: > |s| > s := WideString with: (Character value: 16r55E4). > [100000 timesRepeat: [s hash]] timeToRun. 98 > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: > 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000 timesRepeat: [s hash]] timeToRun. 31 > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s hash]] timeToRun. 100660 > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: > 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000000 timesRepeat: [s hash]] timeToRun. 29476 > > Current 4.1/current Cog > |s| > s := WideString with: (Character value: 16r55E4). > [100000 timesRepeat: [s hash]] timeToRun. 14 > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: > 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000 timesRepeat: [s hash]] timeToRun. 10 > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s hash]] timeToRun. 14946 > > |s| > s := ByteString with: (Character value: 16rE4) with: (Character value: > 16rE4) > with: (Character value: 16rE4) with: (Character value: 16rE4). > [100000000 timesRepeat: [s hash]] timeToRun. 10171 > > So quite a bit faster :) Thanks, it looks really nice. I wonder why are the results with 4.1 better than with your 3.8 derived image. Levente > > best > Eliot > > >> >> Levente >> >> >>> Christophe. >>> >>> >>> >> > |
On Fri, May 14, 2010 at 1:03 PM, Levente Uzonyi <[hidden email]> wrote:
The code looks the same and so I expect the times are close enough to be in the noise. I didn't shut my machine down to a consistent state so other tasks could have affected things, etc.
|
In reply to this post by Eliot Miranda-2
I implemented WideString hash in NB.
|s| s := WideString with: (Character value: 16r55E4). [100000000 timesRepeat: [s hash]] timeToRun. 155718 |s| s := WideString with: (Character value: 16r55E4). [100000000 timesRepeat: [s nbHash]] timeToRun. 81231 Which makes me think, that we're benching the outer loop, rather then hash function itself :) So, here is more appropriate , i think: |s t1 t2 | s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. 10 timesRepeat: [ s := s , s ]. self assert: (s hash = s nbHash). t1 := [1000 timesRepeat: [s hash]] timeToRun. t2 := [1000 timesRepeat: [s nbHash]] timeToRun. { t1. t2 } #(11479 134) ~ 85x faster :) -- Best regards, Igor Stasenko AKA sig. |
added implementation into examples package:
http://www.squeaksource.com/NativeBoost/NativeBoost-Examples-Igor.Stasenko.1.mcz On 15 May 2010 01:14, Igor Stasenko <[hidden email]> wrote: > I implemented WideString hash in NB. > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s hash]] timeToRun. 155718 > > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s nbHash]] timeToRun. 81231 > > Which makes me think, that we're benching the outer loop, rather then > hash function itself :) > > So, here is more appropriate , i think: > > |s t1 t2 | > s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. > 10 timesRepeat: [ s := s , s ]. > self assert: (s hash = s nbHash). > t1 := [1000 timesRepeat: [s hash]] timeToRun. > t2 := [1000 timesRepeat: [s nbHash]] timeToRun. > > { t1. t2 } > #(11479 134) > > ~ 85x faster :) > > > -- > Best regards, > Igor Stasenko AKA sig. > -- Best regards, Igor Stasenko AKA sig. |
Oh, yeah..
i forgot to hash the strings.. for comparison: |ss s t1 t2 t3 | s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. ss := (String with: $z) , 'abcdefghijklmno'. 10 timesRepeat: [ s := s , s. ss := ss , ss ]. self assert: (s hash = s nbHash). t1 := [1000 timesRepeat: [s hash]] timeToRun. t2 := [1000 timesRepeat: [s nbHash]] timeToRun. t3 := [1000 timesRepeat: [ss hash]] timeToRun. { t1. t2. t3 } #(11477 134 190) so, WideString>>nbHash outperforms ByteString>>hash a little, for same string sizes. ;) -- Best regards, Igor Stasenko AKA sig. |
Hi Igor,
is the NB implementation mapping the character codes in the wide strings into Character objects and taking the character hashes? If so, very cool. The NB code is very fast. If on the other hand you're just short-circuiting the character code lookup then you're cheating :)
On Fri, May 14, 2010 at 3:31 PM, Igor Stasenko <[hidden email]> wrote: Oh, yeah.. |
In reply to this post by Igor Stasenko
Should the hash function be the same between ByteString and WideString ?
I mean: if a WideString contains the same characters than a ByteString, I guess that they should have both the same hashcode no ? Christophe ----- Mail Original ----- De: "Igor Stasenko" <[hidden email]> À: "The general-purpose Squeak developers list" <[hidden email]> Envoyé: Samedi 15 Mai 2010 00h26:18 GMT +01:00 Amsterdam / Berlin / Berne / Rome / Stockholm / Vienne Objet: Re: [squeak-dev] WideString hash is way slower than ByteString hash. added implementation into examples package: http://www.squeaksource.com/NativeBoost/NativeBoost-Examples-Igor.Stasenko.1.mcz On 15 May 2010 01:14, Igor Stasenko <[hidden email]> wrote: > I implemented WideString hash in NB. > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s hash]] timeToRun. 155718 > > > |s| > s := WideString with: (Character value: 16r55E4). > [100000000 timesRepeat: [s nbHash]] timeToRun. 81231 > > Which makes me think, that we're benching the outer loop, rather then > hash function itself :) > > So, here is more appropriate , i think: > > |s t1 t2 | > s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. > 10 timesRepeat: [ s := s , s ]. > self assert: (s hash = s nbHash). > t1 := [1000 timesRepeat: [s hash]] timeToRun. > t2 := [1000 timesRepeat: [s nbHash]] timeToRun. > > { t1. t2 } > #(11479 134) > > ~ 85x faster :) > > > -- > Best regards, > Igor Stasenko AKA sig. > -- Best regards, Igor Stasenko AKA sig. |
In reply to this post by Eliot Miranda-2
On 15 May 2010 01:38, Eliot Miranda <[hidden email]> wrote:
> Hi Igor, > is the NB implementation mapping the character codes in the wide strings > into Character objects and taking the character hashes? If so, very cool. > The NB code is very fast. If on the other hand you're just > short-circuiting the character code lookup then you're cheating :) > What mapping you have in mind? WideString>>at: index "Answer the Character stored in the field of the receiver indexed by the argument." ^ Character value: (self wordAt: index). Character class>>value: anInteger "Answer the Character whose value is anInteger." anInteger > 255 ifTrue: [^self basicNew setValue: anInteger]. ^ CharacterTable at: anInteger + 1. (Character classPool at: #CharacterTable) withIndexDo: [:ch :i | self assert: (ch asInteger = (i-1))] So, it is 1:1 correspondence between word, stored in wide string (self wordAt: index), and Character value, used for hashing. So, no mapping required. -- Best regards, Igor Stasenko AKA sig. |
In reply to this post by christophe.jalady
On Sat, 15 May 2010, [hidden email] wrote:
> Should the hash function be the same between ByteString and WideString ? > I mean: if a WideString contains the same characters than a ByteString, I guess that they should have both the same hashcode no ? Yes, they should be the same. And they are the same, aren't they? Levente > > Christophe > > > ----- Mail Original ----- > De: "Igor Stasenko" <[hidden email]> > ˙˙: "The general-purpose Squeak developers list" <[hidden email]> > Envoyé: Samedi 15 Mai 2010 00h26:18 GMT +01:00 Amsterdam / Berlin / Berne / Rome / Stockholm / Vienne > Objet: Re: [squeak-dev] WideString hash is way slower than ByteString hash. > > added implementation into examples package: > http://www.squeaksource.com/NativeBoost/NativeBoost-Examples-Igor.Stasenko.1.mcz > > On 15 May 2010 01:14, Igor Stasenko <[hidden email]> wrote: >> I implemented WideString hash in NB. >> >> |s| >> s := WideString with: (Character value: 16r55E4). >> [100000000 timesRepeat: [s hash]] timeToRun. 155718 >> >> >> |s| >> s := WideString with: (Character value: 16r55E4). >> [100000000 timesRepeat: [s nbHash]] timeToRun. 81231 >> >> Which makes me think, that we're benching the outer loop, rather then >> hash function itself :) >> >> So, here is more appropriate , i think: >> >> |s t1 t2 | >> s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. >> 10 timesRepeat: [ s := s , s ]. >> self assert: (s hash = s nbHash). >> t1 := [1000 timesRepeat: [s hash]] timeToRun. >> t2 := [1000 timesRepeat: [s nbHash]] timeToRun. >> >> { t1. t2 } >> #(11479 134) >> >> ~ 85x faster :) >> >> >> -- >> Best regards, >> Igor Stasenko AKA sig. >> > > > > -- > Best regards, > Igor Stasenko AKA sig. > > > |
In reply to this post by christophe.jalady
On 15 May 2010 01:53, <[hidden email]> wrote:
> Should the hash function be the same between ByteString and WideString ? > I mean: if a WideString contains the same characters than a ByteString, I guess that they should have both the same hashcode no ? > Seems so. |s | s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. s at: 1 put: $a. s class. WideString s nbHash. 196130722 s nbHash 196130722 'aabcdefghijklmno' hash 196130722 -- Best regards, Igor Stasenko AKA sig. |
In reply to this post by Igor Stasenko
And besides, if someone would bother implementing a primitive
for hasing the WideString, i doubt that he will go and create an instances of Character for each indice, and then read its value and only then use it for hashing. So, i don't think this is cheating. Its just an optimization :) Of course, Cog , even if it optimize things cleverly, still has to follow a code, and should create a real instances of Character, simply because it is written so, and it should honor the language semantics. On 15 May 2010 01:53, Igor Stasenko <[hidden email]> wrote: > On 15 May 2010 01:38, Eliot Miranda <[hidden email]> wrote: >> Hi Igor, >> is the NB implementation mapping the character codes in the wide strings >> into Character objects and taking the character hashes? If so, very cool. >> The NB code is very fast. If on the other hand you're just >> short-circuiting the character code lookup then you're cheating :) >> > What mapping you have in mind? > > WideString>>at: index > "Answer the Character stored in the field of the receiver indexed by > the argument." > ^ Character value: (self wordAt: index). > > Character class>>value: anInteger > "Answer the Character whose value is anInteger." > > anInteger > 255 ifTrue: [^self basicNew setValue: anInteger]. > ^ CharacterTable at: anInteger + 1. > > (Character classPool at: #CharacterTable) withIndexDo: [:ch :i | self > assert: (ch asInteger = (i-1))] > > So, it is 1:1 correspondence between word, stored in wide string (self > wordAt: index), > and Character value, used for hashing. So, no mapping required. > > > -- > Best regards, > Igor Stasenko AKA sig. > -- Best regards, Igor Stasenko AKA sig. |
The cardinal rule of running benchmarks is to compare apples to apples. You've compared apples to oranges, i.e. an optimized reimplementation of WideString>>hash that eliminates the mapping of codes to characters, against the vanilla Squeak implementation. You need to at least compare the NB implementation against
WideString methods for comparison fastHash | stringSize hash low | stringSize := self size.
hash := ByteString identityHash bitAnd: 16rFFFFFFF. 1 to: stringSize do: [:pos |
hash := hash + (self wordAt: pos). "Begin hashMultiply" low := hash bitAnd: 16383.
hash := (16r260D * low + ((16r260D * (hash bitShift: -14) + (16r0065 * low) bitAnd: 16383) * 16384)) bitAnd: 16r0FFFFFFF. ].
^ hash | s n |
s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. n := 100000.
{ [1 to: n do: [:i| s fastHash. s fastHash. s fastHash. s fastHash. s fastHash. s fastHash. s fastHash. s fastHash. s fastHash. s fastHash]] timeToRun.
[1 to: n do: [:i| s hash. s hash. s hash. s hash. s hash. s hash. s hash. s hash. s hash. s hash]] timeToRun. } #(829 1254)
ASo your measurements tell us nothing about a general comparison of NB against the Squeak VM or Cog. They only demonstrate (unsurprisingly) that a loop summing integers in an array goes PDQ. On the other hand my numbers showed Cog 10x faster than the Squeak interpreter when executing exactly the same bytecode.
best Eliot On Fri, May 14, 2010 at 4:13 PM, Igor Stasenko <[hidden email]> wrote: And besides, if someone would bother implementing a primitive |
On 15 May 2010 02:35, Eliot Miranda <[hidden email]> wrote:
> The cardinal rule of running benchmarks is to compare apples to apples. > You've compared apples to oranges, i.e. an optimized reimplementation of > WideString>>hash that eliminates the mapping of codes to characters, against > the vanilla Squeak implementation. You need to at least compare the NB > implementation against > WideString methods for comparison > fastHash > | stringSize hash low | > stringSize := self size. > hash := ByteString identityHash bitAnd: 16rFFFFFFF. > 1 to: stringSize do: [:pos | > hash := hash + (self wordAt: pos). > "Begin hashMultiply" > low := hash bitAnd: 16383. > hash := (16r260D * low + ((16r260D * (hash bitShift: -14) + (16r0065 * low) > bitAnd: 16383) * 16384)) bitAnd: 16r0FFFFFFF. > ]. > ^ hash > | s n | > s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. > n := 100000. > { [1 to: n do: [:i| s fastHash. s fastHash. s fastHash. s fastHash. s > fastHash. s fastHash. s fastHash. s fastHash. s fastHash. s fastHash]] > timeToRun. > [1 to: n do: [:i| s hash. s hash. s hash. s hash. s hash. s hash. s hash. s > hash. s hash. s hash]] timeToRun. } > #(829 1254) > ASo your measurements tell us nothing about a general comparison of NB > against the Squeak VM or Cog. They only demonstrate (unsurprisingly) that a > loop summing integers in an array goes PDQ. On the other hand my numbers > showed Cog 10x faster than the Squeak interpreter when executing exactly the > same bytecode. Yes, of course you're right. But i didn't compared it with Cog, because i can't. And NB is not for translating bytecodes into native code, it is for authoring a primitives using native code. So, my comparison is how faster it could be , if implemented primitively. I can only imagine, how faster the whole thing would be if we cross-hatch NB and Cog, where Cog will serve as a smalltalk optimizer , and NB will serve for manual optimizations for heavy numerical crunching :) > best > Eliot > -- Best regards, Igor Stasenko AKA sig. |
In reply to this post by Igor Stasenko
Hi again,
On Sat, 15 May 2010, Igor Stasenko wrote: > added implementation into examples package: > http://www.squeaksource.com/NativeBoost/NativeBoost-Examples-Igor.Stasenko.1.mcz just tried to run the following code: 'foo' asWideString nbHash but I get an assertion failure at this line: imul: ESI with: 16r260D; " 16r260D * low " The code generator is unhappy about ESI. In AJInstructionDescription >> #emitimul:operand1:operand2:operand3: There's an assertion: self assert: op1 isRegTypeGPW. If I just press proceed, it will be unhappy with the other two registers passed to #imul:with:, but the code compiles and works, so probably the assertion is wrong. Levente > > On 15 May 2010 01:14, Igor Stasenko <[hidden email]> wrote: >> I implemented WideString hash in NB. >> >> |s| >> s := WideString with: (Character value: 16r55E4). >> [100000000 timesRepeat: [s hash]] timeToRun. 155718 >> >> >> |s| >> s := WideString with: (Character value: 16r55E4). >> [100000000 timesRepeat: [s nbHash]] timeToRun. 81231 >> >> Which makes me think, that we're benching the outer loop, rather then >> hash function itself :) >> >> So, here is more appropriate , i think: >> >> |s t1 t2 | >> s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. >> 10 timesRepeat: [ s := s , s ]. >> self assert: (s hash = s nbHash). >> t1 := [1000 timesRepeat: [s hash]] timeToRun. >> t2 := [1000 timesRepeat: [s nbHash]] timeToRun. >> >> { t1. t2 } >> #(11479 134) >> >> ~ 85x faster :) >> >> >> -- >> Best regards, >> Igor Stasenko AKA sig. >> > > > > -- > Best regards, > Igor Stasenko AKA sig. > > |
2010/5/15 Levente Uzonyi <[hidden email]>:
> Hi again, > > On Sat, 15 May 2010, Igor Stasenko wrote: > >> added implementation into examples package: >> >> http://www.squeaksource.com/NativeBoost/NativeBoost-Examples-Igor.Stasenko.1.mcz > > just tried to run the following code: > > 'foo' asWideString nbHash > > but I get an assertion failure at this line: > imul: ESI with: 16r260D; " 16r260D * low " > The code generator is unhappy about ESI. In > AJInstructionDescription >> #emitimul:operand1:operand2:operand3: > There's an assertion: > self assert: op1 isRegTypeGPW. > If I just press proceed, it will be unhappy with the other two registers > passed to #imul:with:, but the code compiles and works, so probably the > assertion is wrong. > I don't sure, but it seems either placed in a wrong place or wrong. > > Levente > >> >> On 15 May 2010 01:14, Igor Stasenko <[hidden email]> wrote: >>> >>> I implemented WideString hash in NB. >>> >>> |s| >>> s := WideString with: (Character value: 16r55E4). >>> [100000000 timesRepeat: [s hash]] timeToRun. 155718 >>> >>> >>> |s| >>> s := WideString with: (Character value: 16r55E4). >>> [100000000 timesRepeat: [s nbHash]] timeToRun. 81231 >>> >>> Which makes me think, that we're benching the outer loop, rather then >>> hash function itself :) >>> >>> So, here is more appropriate , i think: >>> >>> |s t1 t2 | >>> s := (WideString with: (Character value: 16r55E4)) , 'abcdefghijklmno'. >>> 10 timesRepeat: [ s := s , s ]. >>> self assert: (s hash = s nbHash). >>> t1 := [1000 timesRepeat: [s hash]] timeToRun. >>> t2 := [1000 timesRepeat: [s nbHash]] timeToRun. >>> >>> { t1. t2 } >>> #(11479 134) >>> >>> ~ 85x faster :) >>> >>> >>> -- >>> Best regards, >>> Igor Stasenko AKA sig. >>> >> >> >> >> -- >> Best regards, >> Igor Stasenko AKA sig. >> > > > > -- Best regards, Igor Stasenko AKA sig. |
In reply to this post by Igor Stasenko
On Fri, May 14, 2010 at 4:43 PM, Igor Stasenko <[hidden email]> wrote:
Yes, this is a very cool direction. One effort should be AOStA/SIStA with Marcus, which will do adaptive optimization/speculative inlining a la Self & Hotspot. Being able to directly generate machine code with NB and not have to rely on the VM's naive code generator would allow machine-specific optimization ad excellent register usage. This could beat C. The difficulty here is in portability. Another more researchy direction would be a Klein approach where the Cog code generator is eliminated and replaced by NB, perfectly possible since Cog retains the interpreter which can be fallen back upon at any time. Again portability is an issue.
best, Eliot
|
Free forum by Nabble | Edit this page |