00:06
vendethiel joined
|
|||
samcv | nice | 00:25 | |
any improvement is an improvement | |||
02:03
agentzh joined
06:15
domidumont joined
06:36
brrt joined
|
|||
brrt | samcv; it's a good question | 06:46 | |
samcv | brrt, which is a good question? | ||
brrt | why JITting helps, even if the advantage per function is pretty small | 06:47 | |
(well, per op) | |||
samcv | ah yeah | ||
why can't we just JIT everything auto-magically | |||
brrt | hehe | ||
samcv | WHY | ||
brrt | well, there's a good answer to that | ||
we have a couple hundred ops | 06:48 | ||
and many of them are de facto C calls | 06:51 | ||
to JIT them correctly, we need to know what those calls look like | |||
however, if we have only one op doesn't work, we can't JIT the entire function | |||
we can't just fall back into interpreting | |||
perl5 could, as could python, because they can have 'nested interpreters' | 06:53 | ||
in general, JITting makes running code cheaper mostly by removing the interpretation overhead, which is argubably not the primary source of overhead for a 'dynamic' language | 06:54 | ||
so the trick, i think, is to be able to represent the code to be interpreted in a way to reduce the effective complexity of code | 06:56 | ||
06:57
domidumont joined
|
|||
samcv | ok so you tell it special hints and info about the function and how it is | 07:02 | |
and that allows it to be effectively JIT'd. that makes sense | |||
otherwise everything would break if you put the wrong things in huh | |||
is whether it is static or can be affected by other variables part of the info you define? | 07:03 | ||
brrt | well, usually specific ops are just altogether added | 07:16 | |
as in, it's entirely possible to 'bail out' JITting in specific conditions | |||
but it is rare that we do | 07:17 | ||
(i broke spilling again :-() | 07:20 | ||
07:21
vendethiel- joined
|
|||
samcv | what do we do with spilling. that's about register alocation and moving it from cache to memory right? | 07:22 | |
brrt | yeah, the 'cache' is the register | 07:23 | |
07:28
vendethiel joined
|
|||
samcv | how can I try and ensure things don't spill into the cache? Or is that only a problem for VM allocation and stuff | 07:45 | |
07:46
brrt joined
|
|||
brrt | i found the issue, i guess | 07:46 | |
Geth | MoarVM/even-moar-jit: 8f0d36dcf8 | (Bart Wiegmans)++ | 4 files MVM_jit_tile_make should take values MVM_jit_tile is supposed to make it easy to make 'complete' tiles inline, so that includes values. Could've chosen to use refs (to the tree), but these are used by the register allocator (and only for live range determination), whereas values are used by the tile itself. |
08:30 | |
09:12
domidumont joined
09:33
zakharyas joined
10:03
lizmat joined
10:53
geekosaur joined
12:35
domidumont joined
|
|||
dogbert17_ wonders if MasterDuke++ created a MoarVM issue describing the problems with t/spec/S17-promise/nonblocking-await.t that he discovered yesterday | 12:40 | ||
MasterDuke | MasterDuke-- did not | ||
12:41
domidumont joined
|
|||
MasterDuke | dogbert17_: have you started to? if not i can do that now | 12:42 | |
dogbert17_, jnthn: written up as github.com/MoarVM/MoarVM/issues/554 | 13:00 | ||
dogbert17_ | MasterDuke+++ :) | 13:18 | |
13:19
geekosaur joined
14:27
ggoebel joined
|
|||
timotimo | samcv: you don't really have to worry about spilling in your own work; it's just something the register allocator will do for you, just like it would in a C or C++ compiler | 15:48 | |
samcv: also, our current JIT basically spills all registers that were used to memory after every single op | 15:49 | ||
(and it can still give you a very strong improvement in performance) | 15:59 | ||
16:12
brrt joined
|
|||
timotimo | brrt: how do you feel about allowing providers of extops to also provide a function that constructs a simple jit graph? like, C function calls only, for example | 16:33 | |
see conversation in #perl6-dev on the trade-off between p6bool making a frame un-jittable and the overhead of ?? !! being potentially bigger than p6bool could do | 16:35 | ||
brrt | let me read that for a bit | ||
jnthn wonders why p6bool is unjittable | |||
brrt | that would be awesome | ||
jnthn | We can JIT ext-ops? | 16:36 | |
brrt wonders too | |||
we can | |||
we ought to be able at least | |||
jnthn | I mean, we JIT them into C calls to the op bodies, don't we? | ||
timotimo | wait, we can? | ||
we already have the functionality for that? | |||
big oops %) | |||
lizmat | jnthn: no idea, but it appears that nqp::p6bool is quite a lot slower than ?? True !! False :-( | ||
brrt | we can and we do | 16:37 | |
i'm not sure what the restrictions on p6bool are | |||
but extops were the first use case for the new data segment | |||
timotimo | yup, it does jit it | 16:38 | |
i spoke way too soon | |||
brrt | hmmm | ||
timotimo | but now, how do we explain the performance discrepancy liz is measuring? | ||
brrt | good question | ||
(the JIT sucks, haha) | 16:39 | ||
timotimo | is the jit code for that loop really so tight in comparison to a C function call? | ||
jnthn | lizmat: I don't see that | ||
$ time perl6-m -e 'use nqp; for ^1000000 { $ = 1 ?? True !! False }' | |||
real0m0.838s | |||
$ time perl6-m -e 'use nqp; for ^1000000 { $ = nqp::p6bool(1) }' | |||
real0m0.830s | |||
Pretty much identical | |||
And with | 16:40 | ||
$ time perl6-m -e 'use nqp; my $x = 1; for ^1000000 { $ = $x ?? True !! False }' | |||
real0m0.837s | |||
$ time perl6-m -e 'use nqp; my $x = 1; for ^1000000 { $ = nqp::p6bool($x) }' | |||
real0m0.786s | |||
timotimo | oh, i have an idea | ||
jnthn | It comes in faster | ||
lizmat | huh? | ||
it comes in slower for me | |||
timotimo | hm, no, p6bool is defined on native ints, not on objects | ||
jnthn | OK, doing several runs they basically come out the same within noise | ||
timotimo | not on my machine | 16:41 | |
jnthn | timotimo: yeah, but the code-gen first does istrue iirc | ||
timotimo | hm, OK | ||
for 10_000_000 i get 5.7s vs 6.4s | |||
the measurements are not very noisy | 16:42 | ||
lizmat | jnthn: I've used a native int for $x, does that make a difference to you ? | ||
jnthn | 6.766 vs 6.783 for me | ||
lizmat: Lemme try | |||
lizmat | the reason I used a native int, is that p6bool is usually used in conjunction with native int values | 16:43 | |
jnthn | Aha, now I see the difference | ||
timotimo | right, with a non-native variable they are only half a second apart | 16:44 | |
jnthn | github.com/rakudo/rakudo/blob/nom/...s.nqp#L277 | ||
The code-gen there isn't aware of intlexref | 16:45 | ||
Well, lexical refs in general | |||
timotimo | that's a good point | ||
jnthn | So that's probably where the discrepancy comes from | ||
lizmat | ah, so the use case for p6bool doesn't use it :-( | ||
timotimo | i didn't know we had a piece of compiler for p6bool | ||
it does use it, because it's forced to | |||
it just doesn't understand it could just decont_i or decont_n | 16:46 | ||
jnthn | Not even that | ||
timotimo | so it goes through the general istrue_o | ||
jnthn | I can just do a lexical access | ||
*It | |||
lizmat | so it's first boxing the value | ||
? | |||
timotimo | right, it probably creates an *LexRef and will istrue_o that | ||
whereas the ?? !! version probably doesn't allocate anything at all | 16:47 | ||
jnthn | Yes, the decont will box | ||
lizmat has to be afk again | |||
jnthn | Anyway, good news is we can fix it in one place :) | ||
timotimo | that's something we'd have to implement in the Optimizer, no? | ||
hm, no, actually | |||
jnthn | timotimo: No, we can just handle it in p6bool's compilation | ||
timotimo | we do get the qast that has the lexicalref into that function | ||
jnthn | Just case-analyze what we get | ||
Yes | |||
It'll be a QAST::Var with scope lexicalref | 16:48 | ||
In that case we can actually just :want($MVM_reg_int64) when we compile_mast | |||
timotimo | right, so w'll do that before $exprres gets created and twiddle the Var node first | ||
oh, ok, no need to twiddle, then | |||
jnthn | And then it'll compile it into a lexical lookup | ||
Yeah, I'd rather not twiddle the AST | |||
We've been burnt from doing that before | |||
timotimo | i would have twiddled it the same way the nfg tree gets twiddled | 16:49 | |
i.e. create a copy, modify that | |||
let me try to whip something up | |||
jnthn | Yeah, but we can do even easier and just pass a :want in :) | 16:50 | |
And then leave the rest of the code the same :) | |||
timotimo | right | ||
but we should only do it if we detect an IntLexRef, right? | |||
i'm actually not sure how to get at the target lexical from here | 16:51 | ||
jnthn | I'm saying you don't need to | ||
timotimo | like, to figure out if we'll want an int or num or what | ||
oh, not at all? | |||
jnthn | Hm, actually maybe you do to know what to :$want | 16:52 | |
I'd do somethin glike | |||
my $want; | |||
if it's a QAST::Var with .scope eq 'lexicalref' | |||
get the objprimspec of the type, aand use that to assign $MVM_reg_int64, $MVM_reg_num64, or $MVM_reg_str to $want | 16:53 | ||
Then pass that to compile_mat | |||
*compile_mast | |||
timotimo | i'm imagining someone calling nqp::p6bool on, say, 1e100 and we'd asplode with "this num is too big to be boxed into an int" | ||
ah, objprimspec is the one i'd want | |||
would i grab it from the .returns of QAST::Var? | 16:54 | ||
jnthn | Yeah | ||
timotimo | i feel like i haven't touched qast compiler stuff in ages :| | 16:55 | |
jnthn | Heh, same for me :) | 16:56 | |
It's not an area where bugs crop up all that often | |||
timotimo | i can make bugs there! | 16:57 | |
;) | |||
jnthn | :P | ||
timotimo | i got distracted waiting for the build to finish | 17:05 | |
now i'll spectest with my change | |||
17:09
brrt joined
|
|||
timotimo | okay, all spec tests clean except the one that always goes out of order and the subst one | 17:15 | |
i broke it \o/ | 17:16 | ||
objprimspec isn't compatible with the enum we use for :want ? | 17:17 | ||
that's it | 17:20 | ||
okay, that closed the performance gap | 17:21 | ||
good catch in any case, jnthn :) | 17:24 | ||
jnthn | Well, lizmat++ spotted the perf diff, I just figured out what was going on :) | 17:25 | |
timotimo | right | ||
jnthn | timotimo++ for fixing it | ||
timotimo | lizmat++ jnthn++ :) | ||
depending on the branch you take in p6bool, we'll look up $*REGALLOC between 4 and 6 times; is caching that in a lexical a useless micro-optimization? | 17:26 | ||
5 lookups in p6sink, i expect we call that a bajillion times all in all? | 17:28 | ||
17:28
domidumont joined
|
|||
jnthn | Probably worth it | 17:29 | |
timotimo | i'll make a pass over Ops.nqp and do a full measurement of the core setting build 10x with and 10x without during my next AFK | 17:31 | |
"regal" in german means "cupboard" or "shelf" | 17:33 | ||
jnthn | Ain't languages fun :) | 17:34 | |
jnthn has tomorrow set aside for doing Perl 6 and Moar stuffs | 17:35 | ||
[Coke] | nine. | ||
jnthn | ten! | ||
jnthn goes to rest a bit :) | 17:36 | ||
timotimo | timings will now commence (and i'm AFK) | 17:39 | |
17:43
brrt joined
17:54
brrt joined
|
|||
timotimo | barely noticable, but statistically significant | 18:19 | |
0.02s or something | 18:24 | ||
interesting. on the nqp side of things, there's already a whole lot of "my $regalloc := $*REGALLOC" in QASTOperationsMAST | 18:35 | ||
in moarvm's irclog search i only found a timtoady gist from 2 years ago about dynamic var lookup stats | 18:37 | ||
ah, perl6-dev has one from a month ago | 18:38 | ||
there regalloc only accounts for like 0.25% of time | |||
i could put up the changes for $REGALLOC in a branch in case the dynamic var cache gets made 100x slower or something :P | 18:40 | ||
18:44
domidumont joined
|
|||
samcv | good * | 19:39 | |
19:51
ggoebel joined
19:52
lizmat joined
20:45
domidumont joined
|
|||
jnthn | o/ samcv | 21:15 | |
Geth | MoarVM/master: 6 commits pushed by (Samantha McVey)++, (Jonathan Worthington)++
|
21:20 | |
21:21
colomon_ joined
|
|||
timotimo | yo samcv | 22:03 | |
samcv | yo | 22:47 | |
should be fine building with local repos for everything but libtommath right? | 22:50 | ||
using --has-libffi --has-libatomic_ops --has-libuv --has-dyncall atm | 22:51 | ||
timotimo | it should be erroneous to have both libffi and dyncall in the configure line | 22:52 | |
it doesn't make sense to have more than one of those two | |||
samcv | well those flags only tell it to use locally installed versions instead of the moarvm provided ones right | 22:53 | |
or maybe i'm wrong | |||
timotimo | hm, maybe | ||
i didn't do much inside Configure.pl | |||
samcv | which one is the default? or best, do we have backends for both libs or something? | 22:54 | |
timotimo | yeah, we have a little wrapper for each of those | 22:55 | |
these wrappers both have the same API that the rest of moarvm then uses | |||
samcv | github.com/MoarVM/MoarVM/issues/183 | 22:56 | |
so i guess dyncall is the preferred one | |||
jnthn | So far as I remember, they don't support completely overlapping sets of platforms | 22:57 | |
samcv | libs: -lffi -L/usr/lib/../lib -lffi -latomic_ops -L/usr/lib/../lib -lffi -luv -L/usr/lib/../lib -lffi -lm -lpthread -lrt -ldl | ||
well | |||
so i guess i've been using libffi | 22:58 | ||
timotimo | right, platform support is the reason why we even pulled libffi in | ||
we used to have only dyncall, which is also what parrot had | |||
grrr | 23:01 | ||
i'm getting python errors but no apparent way to figure out where they originated | 23:02 | ||
print("sizeclass " + sizeclass + " being analyzed") | 23:06 | ||
TypeError: Can't convert 'int' object to str implicitly | |||
has this always been like that? | |||
geekosaur | apparently yes | 23:07 | |
python isn't perl | 23:08 | ||
(arguably you can depend on python doing what perl doesn't...) | |||
23:12
agentzh joined
|
|||
timotimo | okay, getting the errors from trying to stringify a string that contains ropes | 23:17 | |
someone needs to rewrite this code | 23:18 | ||
23:29
vendethiel- joined
|
|||
samcv | is this with python only or inline::python? | 23:29 | |
timotimo | python only | ||
we'd need inline.perl6 to make this bearable ;) | |||
samcv | so python is broken? lol | 23:30 | |
timotimo | huh? | ||
samcv | <timotimo> okay, getting the errors from trying to stringify a string that contains ropes | ||
that was refering to python or perl6? | |||
timotimo | let me show you | ||
github.com/MoarVM/MoarVM/blob/mast...#L180-L205 | 23:31 | ||
this is what's broken | |||
samcv | ah | 23:53 | |
makes sense now | 23:54 | ||
timotimo | i don't think it was ever correct, either | ||
i think it gave off-by-ones all the time :P | 23:55 | ||
for the time being i turned it off and put the address of the string into the histogram | 23:57 | ||
23:58
brrt joined
|