Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

FreeListRef.checkInvariant's assert fails since v2.096 (dtorfields on by default) #283

Open
Geod24 opened this issue Jun 2, 2021 · 2 comments
Labels

Comments

@Geod24
Copy link
Contributor

Geod24 commented Jun 2, 2021

Situation: A client connects to a node. The node crashes (e.g. SEGV) or just abruptly drops the connection.

The following error is triggeredm client side:

object.Exception@../../submodules/vibe.d/stream/vibe/stream/operations.d(378): Reached EOF while searching for end marker.
----------------
??:? pure @safe void std.exception.bailOut!(Exception).bailOut(immutable(char)[], ulong, scope const(char)[]) [0x10040e51a]
??:? pure @safe bool std.exception.enforce!().enforce!(bool).enforce(bool, lazy const(char)[], immutable(char)[], ulong) [0x10040e48b]
source/main.d:125 @safe void vibe.stream.operations.readUntilSmall!(vibe.utils.array.AllocAppender!(ubyte[], ubyte).AllocAppender, vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy).readUntilSmall(vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy, ref vibe.utils.array.AllocAppender!(ubyte[], ubyte).AllocAppender, in ubyte[], ulong) [0x1002b01a3]
source/main.d:125 @safe void vibe.stream.operations.readUntil!(vibe.utils.array.AllocAppender!(ubyte[], ubyte).AllocAppender, vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy).readUntil(vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy, ref vibe.utils.array.AllocAppender!(ubyte[], ubyte).AllocAppender, in ubyte[], ulong) [0x1002b0073]
source/main.d:125 @safe void vibe.stream.operations.readLine!(vibe.utils.array.AllocAppender!(ubyte[], ubyte).AllocAppender, vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy).readLine(vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy, ref vibe.utils.array.AllocAppender!(ubyte[], ubyte).AllocAppender, ulong, immutable(char)[]) [0x1002aff94]
source/main.d:125 @safe ubyte[] vibe.stream.operations.readLine!(vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy).readLine(vibe.internal.interfaceproxy.InterfaceProxy!(vibe.core.stream.Stream).InterfaceProxy, ulong, immutable(char)[], stdx.allocator.IAllocator) [0x1002afeb4]
source/main.d:125 @trusted immutable(char)[] vibe.http.client.HTTPClientResponse.__ctor(vibe.http.client.HTTPClient, bool, bool, stdx.allocator.IAllocator, std.datetime.systime.SysTime).__lambda6() [0x1003207c1]
source/main.d:125 @safe vibe.http.client.HTTPClientResponse vibe.http.client.HTTPClientResponse.__ctor(vibe.http.client.HTTPClient, bool, bool, stdx.allocator.IAllocator, std.datetime.systime.SysTime) [0x10031fe36]
source/main.d:125 @safe vibe.http.client.HTTPClientResponse vibe.http.client.HTTPClient.request(scope void delegate(vibe.http.client.HTTPClientRequest)) [0x10031d6d2]
source/main.d:125 @safe vibe.http.client.HTTPClientResponse vibe.http.client.requestHTTP(vibe.inet.url.URL, void delegate(scope vibe.http.client.HTTPClientRequest), const(vibe.http.client.HTTPClientSettings)) [0x10031b823]
source/main.d:125 @safe vibe.http.client.HTTPClientResponse vibe.web.rest.request(vibe.inet.url.URL, void delegate(vibe.http.client.HTTPClientRequest) @safe, scope void delegate(vibe.http.client.HTTPClientRequest, scope vibe.core.stream.InputStream) @safe, vibe.http.common.HTTPMethod, immutable(char)[], scope ref const(vibe.utils.dictionarylist.DictionaryList!(immutable(char)[], false, 12uL, false).DictionaryList), immutable(char)[], immutable(char)[], ref vibe.utils.dictionarylist.DictionaryList!(immutable(char)[], false, 12uL, false).DictionaryList, ref vibe.utils.dictionarylist.DictionaryList!(immutable(char)[], false, 12uL, false).DictionaryList, in vibe.http.client.HTTPClientSettings) [0x1002c5953]
source/main.d:125 @safe ulong vibe.web.rest.executeClientMethod!(agora.api.FullNode.API, 3).executeClientMethod(scope ref const(vibe.web.internal.rest.common.RestInterface!(agora.api.FullNode.API).RestInterface), void delegate(vibe.http.client.HTTPClientRequest) @safe, scope void delegate(vibe.http.client.HTTPClientRequest, scope vibe.core.stream.InputStream) @safe) [0x1002cd322]
source/main.d:125 @safe ulong vibe.web.rest.RestInterfaceClient!(agora.api.FullNode.API).RestInterfaceClient.__mixin23.getBlockHeight() [0x1002c68c2]
source/main.d:87 void main.main(immutable(char)[][]).assertBlockHeightAtleast(ulong) [0x100006436]
source/main.d:125 void main.main(immutable(char)[][]).__lambda14!(int).__lambda14(int) [0x10000be9b]
source/main.d:125 std.typecons.Flag!("each").Flag std.algorithm.iteration.each!(main.main(immutable(char)[][]).__lambda14).each!(std.range.iota!(int, int).iota(int, int).Result).each(std.range.iota!(int, int).iota(int, int).Result) [0x10000bed0]
source/main.d:125 _Dmain [0x1000027d9]
Process 60969 exited with status = 1 (0x00000001)

(I'm on OSX, so line numbers are botched)
However, what was also triggered was an InvalidMemoryOperationError. Using LLDB, I could see that the InvalidMemoryOperationError was triggered by an assert triggering in a destructor, and assert allocating on failure. This is an upstream bug (reported in #248 ) and will be fixed in the next release (v2.097.0).

The assertion in question, obviously, shouldn't fail:

assert(m_magic == 0x1EE75817);

    frame #5: 0x00000001003c1626 systemtest-simple`_d_assertp + 94
    frame #6: 0x00000001001eaf53 systemtest-simple`_D4vibe8internal11freelistref__T11FreeListRefTCQBt6stream8counting22EndCallbackInputStreamVbi1ZQCl15checkInvariantsMxFNaNbNiNfZv at freelistref.d:175
    frame #7: 0x00000001001eae6c systemtest-simple`_D4vibe8internal11freelistref__T11FreeListRefTCQBt6stream8counting22EndCallbackInputStreamVbi1ZQCl5clearMFNbNfZv at freelistref.d:149
    frame #8: 0x00000001001eadbd systemtest-simple`_D4vibe8internal11freelistref__T11FreeListRefTCQBt6stream8counting22EndCallbackInputStreamVbi1ZQCl6__dtorMFNbNfZv at freelistref.d:121
    frame #9: 0x000000010032149c systemtest-simple`_D4vibe4http6client18HTTPClientResponse11__fieldDtorMFNeZv + 44
    frame #10: 0x00000001003214fe systemtest-simple`_D4vibe4http6client18HTTPClientResponse10__aggrDtorMFNeZv + 30
    frame #11: 0x00000001003ea370 systemtest-simple`rt_finalize2 + 112
    frame #12: 0x00000001003ea4ab systemtest-simple`rt_finalizeFromGC + 39

So after going down that rabbit hole, I was left wondering why on earth the assert fails. Luckily I have most major DMD change memorized so I added a -revert=dtorfields to my config and the assert stopped failing.
-preview=dtorfields have been enabled by default since v2.096.0 and that matches the timeline of when things started to spuriously fail for us.

@Geod24 Geod24 added the bug label Jun 2, 2021
@s-ludwig
Copy link
Member

s-ludwig commented Jun 2, 2021

There seems to be a double-destruction bug that has been introduced by dtorFields: https://run.dlang.io/is/l0nsn4

@Geod24
Copy link
Contributor Author

Geod24 commented Jun 2, 2021

Thanks for the fast reduction! Reported as https://issues.dlang.org/show_bug.cgi?id=21989 . That's pretty bad :/

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants