&lt;snip&gt;<br><div class="gmail_quote"><blockquote class="gmail_quote" style="border-left: 1px solid rgb(204, 204, 204); margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><br>
It seems that only a small number of RGCTXs is ever used, and the ones<br>
that are used could make do with 2 to 5 slots on average. &nbsp;For FSharp,<br>
for instance, if we used an optimal allocation strategy (i.e. only<br>
allocate RGCTXs if needed, only allocate as many slots as needed and<br>
don&#39;t use any meta-data) we could get the 600k down to about 6k, which<br>
would be more than acceptable.<br>
There is a problem with allocating a RGCTX lazily, though. &nbsp;Allocating<br>
a RGCTX requires some information. &nbsp;Specifically, it requires the<br>
MonoVTable* for the class for which to allocate the RGCTX. &nbsp;This is<br>
not an issue for non-static methods because the vtable is accessible<br>
through the &quot;this&quot; argument. &nbsp;Static methods don&#39;t have that argument,<br>
though. &nbsp;In fact, the RGCTX must contain a pointer to the vtable<br>
because we need it in static methods for some purposes, like exception<br>
handling. &nbsp;So I think we&#39;ll need to switch to passing not the RGCTX,<br>
but the vtable to static methods, since the latter contains a pointer<br>
to the RGCTX anyway, which, for lazy allocation, could be NULL. &nbsp;This<br>
would give us the additional advantage of not having to store the<br>
vtable in the RGCTX, saving us 4/8 bytes per RGCTX.<br>
As for how to arrange the RGCTX itself I have the following proposal:<br>
Let&#39;s get rid of all the superclass and type argument type information<br>
and just concentrate on the extensible part. &nbsp;I&#39;d like to implement<br>
two different kinds of RGCTX - small ones and large ones. &nbsp;Small<br>
RGCTXs would have space for up to some constant number of slots,<br>
preferably 3 or 7. &nbsp;The layout would look like this on a 32-bit<br>
struct small_rgctx {<br>
 &nbsp;guint8 size;<br>
 &nbsp;guint8 slot_numbers[3];<br>
 &nbsp;gpointer slots[0];<br>
size would be the number of slots in the RGCTX. &nbsp;slot_numbers would<br>
identify the type information stored in the slots array.<br>
To fetch an item out of the RGCTX we&#39;d have to search through the<br>
slot_numbers array to find the required type information and then<br>
fetch the corresponding pointer from the slots array. &nbsp;If the type<br>
information is not found we&#39;d jump into unmanaged code and extend the<br>
RGCTX by allocating a new one with space for one more slot or, if the<br>
maximum number of slots is reached, upgrading to a large RGCTX.<br>
Another reason for using a large RGCTX would be if the values of the<br>
slot numbers exceeded 255, which should be very unlikely, though.<br>
We could keep free lists per domain of the RGCTXs we&#39;ve thrown away.<br>
It might be necessary to use hazard pointers for access to the RGCTX<br>
so as to avoid reusing memory of a thrown-away RGCTX if another thread<br>
is still accessing it.<br>
</blockquote><div><br>Isn&#39;t possible or better to do RGCTX free&#39;ing at GC time? It would be simpler, the hardest<br>part would be guarding against parking threads inside RGCTX related code, which can be done with<br>
some link time trickery and a lit of changes on stack scanning code.<br><br>&nbsp;</div><blockquote class="gmail_quote" style="border-left: 1px solid rgb(204, 204, 204); margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><br>
A large RGCTX could be some kind of small hash table.<br>
With such data structures we could also do another optimization.<br>
Right now every class that is either a generic class or is a direct or<br>
indirect subclass of a generic class has its own RGCTX. &nbsp;Non-generic<br>
classes can never give rise to the need for another piece of type<br>
information in a RGCTX, so they could share the RGCTXs of their<br>
generic superclasses.<br>
Does this sound like a sensible plan? &nbsp;Am I missing something crucial?<br>
&nbsp;Does anybody have any suggestions or better ideas?<br>
Mark</blockquote><div>&nbsp;</div></div><br>These are great news Mark.<br><br>In Madrid we discussed about using segfaults to trigger lazy filling of rgctx, have you thought about using that?<br><br>I remember that a major issue with the rgctx layout was that you need to coordinate slot filling between a type and all it&#39;s parents to avoid collisions. How would that work on your proposed schema? How about using a pointer to the parent context? This would eliminate the whole issue, could save some bytes for parents with fat rgctx and make even less likely to have a large rgctx.<br>
<br>One more thing, your stats miss something I guess it&#39;s important, how many generic sharing failures each test suite has? This is important to see how much further this could be improved if constrained and mixed reference/valuetype sharing gets done. <br>
<br>It might too early to think about this, but do you have some speed results for these tests? <br><br><br>Cheers,<br>Rodrigo<br><br><br>