On Mon, May 20, 2024 at 05:01:15PM +0500, Andrey M. Borodin wrote:
> Both features look useful to me.
> I've tried to rebase my test of CV sleep during multixact generation[0]. I 
> used it like this:
> 
>     INJECTION_POINT_PRELOAD("GetNewMultiXactId-done");
>     multi = GetNewMultiXactId(nmembers, &offset); // starts critsection
>     INJECTION_POINT("GetNewMultiXactId-done");

Thanks for the feedback.

> And it fails like this:
> 
> 2024-05-20 16:50:40.430 +05 [21830] 001_multixact.pl LOG:  statement: select 
> test_create_multixact();
> TRAP: failed Assert("CritSectionCount == 0 || 
> (context)->allowInCritSection"), File: "mcxt.c", Line: 1185, PID: 21830
> 0   postgres                            0x0000000101452ed0 
> ExceptionalCondition + 220
> 1   postgres                            0x00000001014a6050 MemoryContextAlloc 
> + 208
> 2   postgres                            0x00000001011c3bf0 
> dsm_create_descriptor + 72
> 3   postgres                            0x00000001011c3ef4 dsm_attach + 400
> 4   postgres                            0x00000001014990d8 dsa_attach + 24
> 5   postgres                            0x00000001011c716c init_dsm_registry 
> + 240
> 6   postgres                            0x00000001011c6e60 GetNamedDSMSegment 
> + 456
> 7   injection_points.dylib              0x0000000101c871f8 
> injection_init_shmem + 60
> 8   injection_points.dylib              0x0000000101c86f1c injection_wait + 64
> 9   postgres                            0x000000010148e228 
> InjectionPointRunInternal + 376
> 10  postgres                            0x000000010148e0a4 InjectionPointRun 
> + 32
> 11  postgres                            0x0000000100cab798 
> MultiXactIdCreateFromMembers + 344
> 12  postgres                            0x0000000100cab604 MultiXactIdCreate 
> + 312
> 
> Am I doing something wrong? Seems like extension have to know too that it is 
> preloaded.

Your stack is pointing at the shared memory section initialized in the
module injection_points, which is a bit of a chicken-and-egg problem
because you'd want an extra preload to happen before even that, like a
pre-preload.  From what I can see, you have a good point about the
shmem initialized in the module: injection_points_preload() should
call injection_init_shmem() so as this area would not trigger the
assertion.

However, there is a second thing here inherent to your test: shouldn't
the script call injection_points_preload() to make sure that the local
cache behind GetNewMultiXactId-done is fully allocated and prepared
for the moment where injection point will be run?

So I agree that 0002 ought to call injection_init_shmem() when calling
injection_points_preload(), but it also seems to me that the test is
missing the fact that it should heat the backend cache to avoid the
allocations in the critical sections.

Note that I disagree with taking a shortcut in the backend-side
injection point code where we would bypass CritSectionCount or
allowInCritSection.  These states should stay consistent for the sake
of the callbacks registered so as these can rely on the same stack and
conditions as the code where they are called.
--
Michael

Attachment: signature.asc
Description: PGP signature

Reply via email to