vibe-d / vibe.d

Official vibe.d development
MIT License
1.15k stars 284 forks source link

Websocket.close crushes&leaks when program terminated by 15 #2396

Open kerdemdemir opened 4 years ago

kerdemdemir commented 4 years ago

Using:

vibe-core 1.7.0: on Ubuntu 16.04 with DMD 2.089.0

Compile and run the program below: And terminate it with signal 15 .

import std.stdio;
import vibe.data.json;
import std.datetime;

public import std.conv : to;
public import std.string;

import vibe.core.sync;
import vibe.core.concurrency;
import vibe.stream.operations : readAllUTF8;
import vibe.http.websockets;
import vibe.core.log;
import vibe.core.core;
import vibe.core.concurrency;
import vibe.inet.url;
import std.getopt;
import std.process;
import core.sys.posix.signal;
import core.stdc.stdlib;

bool doQuit = false;

extern(C) void handler(int num) nothrow @nogc @system
{
    printf("Caught signal %d\n",num);
    doQuit = true;
}

extern(C) void handlerAbort(int num) nothrow @nogc @system
{
    printf("Caught signal %d\n",num);
    doQuit = true;
}

WebSocket startSocket( string temp )
{
    auto ws_url = URL(temp);
    auto ws = connectWebSocket(ws_url);
    if ( !ws.connected )
        return null;    
    return  ws;
}

void closeInternal( ref WebSocket ws )
{
    if (ws && ws.connected)
        ws.close(); 
}

void main( ) {

    signal(SIGTERM, &handler);
    signal(SIGABRT, &handlerAbort);

    string socketName =  "wss://stream.binance.com:9443/ws/bnbbtc@aggTrade";
    auto curSocket = startSocket(socketName);
    int counter = 0;
    while (true) {
        if (  curSocket.waitForData(100.msecs) )
        {
            auto text = curSocket.receiveText();
            writeln(text);
        }
        if ( doQuit )
            break;
        sleep(50.msecs);    

    }
    sleep(1.seconds);
    curSocket.closeInternal();
}
Caught signal 15
Caught signal 15
Caught signal 15
core.exception.AssertError@../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/net.d(605): Assertion failure
----------------
??:? _d_assertp [0x915e3d]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/net.d:605 pure nothrow @nogc @safe void vibe.core.net.TCPConnection.waitForDataEx(core.time.Duration).__lambda4!(eventcore.driver.StreamSocketFD, eventcore.driver.IOStatus, ulong).__lambda4(eventcore.driver.StreamSocketFD, eventcore.driver.IOStatus, ulong) [0x8a7540]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/internal/async.d-mixin-161:170 nothrow @safe void vibe.internal.async.asyncAwaitAny!(true, vibe.internal.async.Waitable!(void delegate(eventcore.driver.StreamSocketFD, eventcore.driver.IOStatus, ulong) nothrow @safe, vibe.core.net.TCPConnection.waitForDataEx(core.time.Duration).__lambda2, vibe.core.net.TCPConnection.waitForDataEx(core.time.Duration).__lambda3, vibe.core.net.TCPConnection.waitForDataEx(core.time.Duration).__lambda4)).asyncAwaitAny(immutable(char)[]).__lambda3(eventcore.driver.StreamSocketFD, eventcore.driver.IOStatus, ulong) [0x876620]
../../../.dub/packages/eventcore-0.8.48/eventcore/source/eventcore/drivers/posix/sockets.d:439 nothrow @safe void eventcore.drivers.posix.sockets.PosixEventDriverSockets!(eventcore.drivers.posix.epoll.EpollEventLoop).PosixEventDriverSockets.onSocketRead(eventcore.driver.FD).finalize!().finalize(eventcore.driver.IOStatus) [0x8b861c]
../../../.dub/packages/eventcore-0.8.48/eventcore/source/eventcore/drivers/posix/sockets.d:455 nothrow @safe void eventcore.drivers.posix.sockets.PosixEventDriverSockets!(eventcore.drivers.posix.epoll.EpollEventLoop).PosixEventDriverSockets.onSocketRead(eventcore.driver.FD) [0x8b5d25]
../../../.dub/packages/eventcore-0.8.48/eventcore/source/eventcore/drivers/posix/driver.d:342 nothrow @safe void eventcore.drivers.posix.driver.PosixEventLoop.notify!(0).notify(eventcore.driver.FD) [0x8d6f6d]
../../../.dub/packages/eventcore-0.8.48/eventcore/source/eventcore/drivers/posix/epoll.d:56 nothrow @trusted bool eventcore.drivers.posix.epoll.EpollEventLoop.doProcessEvents(core.time.Duration) [0x8b132d]
../../../.dub/packages/eventcore-0.8.48/eventcore/source/eventcore/drivers/posix/driver.d:223 nothrow @safe eventcore.driver.ExitReason eventcore.drivers.posix.driver.PosixEventDriverCore!(eventcore.drivers.posix.epoll.EpollEventLoop, eventcore.drivers.timer.LoopTimeoutTimerDriver, eventcore.drivers.posix.events.PosixEventDriverEvents!(eventcore.drivers.posix.epoll.EpollEventLoop, eventcore.drivers.posix.sockets.PosixEventDriverSockets!(eventcore.drivers.posix.epoll.EpollEventLoop).PosixEventDriverSockets).PosixEventDriverEvents, eventcore.drivers.posix.processes.PosixEventDriverProcesses!(eventcore.drivers.posix.epoll.EpollEventLoop).PosixEventDriverProcesses).PosixEventDriverCore.processEvents(core.time.Duration) [0x8b0cb0]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/task.d:775 nothrow @safe eventcore.driver.ExitReason vibe.core.task.TaskScheduler.process() [0x8890ca]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/task.d:813 nothrow @safe eventcore.driver.ExitReason vibe.core.task.TaskScheduler.waitAndProcess() [0x889194]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/core.d:285 nothrow @safe eventcore.driver.ExitReason vibe.core.core.runEventLoopOnce() [0x8a3dd3]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/core.d:702 nothrow @safe void vibe.core.core.hibernate(scope void delegate() nothrow @safe) [0x8a3f5d]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/internal/async.d:172 @safe void vibe.internal.async.asyncAwaitAny!(true, vibe.internal.async.Waitable!(void delegate() nothrow @safe, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, bool delegate() nothrow @safe).__lambda5, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda6, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda7()), vibe.internal.async.Waitable!(void delegate(eventcore.driver.EventID) nothrow @safe, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda8, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda9, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda10)).asyncAwaitAny(immutable(char)[]) [0x884e87]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/internal/async.d:85 @safe void vibe.internal.async.asyncAwaitAny!(true, vibe.internal.async.Waitable!(void delegate() nothrow @safe, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, bool delegate() nothrow @safe).__lambda5, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda6, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda7()), vibe.internal.async.Waitable!(void delegate(eventcore.driver.EventID) nothrow @safe, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda8, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda9, vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, scope bool delegate() nothrow @safe).__lambda10)).asyncAwaitAny(core.time.Duration, immutable(char)[]) [0x884c69]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/sync.d:1456 @safe bool vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter.wait!(true).wait(core.time.Duration, eventcore.driver.EventID, bool delegate() nothrow @safe) [0x884ab5]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/sync.d:1144 @safe void vibe.core.sync.ManualEvent.doWaitShared!(true).doWaitShared(core.time.Duration, int).__lambda4(scope vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter) [0x88490d]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/sync.d:1204 shared @safe void vibe.core.sync.ManualEvent.acquireThreadWaiter!(void delegate(scope vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter) @safe).acquireThreadWaiter(scope void delegate(scope vibe.core.sync.ThreadLocalWaiter!(true).ThreadLocalWaiter) @safe) [0x88581f]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/sync.d:1142 shared @safe int vibe.core.sync.ManualEvent.doWaitShared!(true).doWaitShared(core.time.Duration, int) [0x884811]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/sync.d:1107 shared @safe int vibe.core.sync.ManualEvent.wait(int) [0x87ad86]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/task.d:505 shared @trusted void vibe.core.task.TaskFiber.join!(true).join(ulong) [0x88ab12]
../../../.dub/packages/vibe-core-1.7.0/vibe-core/source/vibe/core/task.d:96 @trusted void vibe.core.task.Task.join() [0x887d1c]
../../../.dub/packages/vibe-d-0.8.6/vibe-d/http/vibe/http/websockets.d:724 @safe void vibe.http.websockets.WebSocket.close(short, scope const(char)[]) [0x75f504]
WebSocketDenemesi/src/app.d:50 void app.closeInternal(ref vibe.http.websockets.WebSocket) [0x73a598]

When I spawn this program from a parent program I also observe memory leaks

Warning (thread: main): leaking eventcore driver because there are still active handles
   FD 6 (streamSocket)
Warning (thread: main): leaking eventcore driver because there are still active handles
   FD 6 (streamSocket)
Printing memory:Diff: 65536 ---> Leaked amount 

The crash does not appear if I dont close the websocket but leak is still there. I saw another similar ticket on windows but I wanted to create still since mine is on ubuntu . The way I trigger is a bit different.

Geod24 commented 4 years ago

Regarding the leak, there is #2245 . Regarding the crash, can you reproduce with the latest vibe / vibe-core / eventcore ?