 timeout
 encoding
 handler
-server-stopped ;
+server-stopped
+secure-context ;
 
 SYMBOL: running-servers
 running-servers [ HS{ } clone ] initialize

    [ (accept-connection) ]
    if* ;

: accept-loop ( server -- )
    [ accept-connection ] [ accept-loop ] bi ;

: start-accept-loop ( server -- ) accept-loop ;

\ start-accept-loop NOTICE add-error-logging

: init-server ( threaded-server -- threaded-server )
    <flag> >>server-stopped
    dup semaphore>> [
        dup max-connections>> [

    '[ [ _ <server> |dispose ] map ] with-destructors ;

: set-servers ( threaded-server -- threaded-server )
    dup [
        dup dup listen-on [ no-ports-configured ] [ (make-servers) ] if-empty
        >>servers
    ] with-existing-secure-context ;

: server-thread-name ( threaded-server addrspec -- string )
    [ name>> ] [ addr>> present ] bi* " server on " glue ;

PRIVATE>

: start-server ( threaded-server -- threaded-server )
    init-server
    [
        dup threaded-server [
            [ ] [ name>> ] bi
            [
                set-servers
                dup add-running-server
                dup servers>>
                [
                    [ '[ _ _ [ start-accept-loop ] with-disposal ] ]
                    [ server-thread-name ] 2bi spawn drop
                ] with each
            ] with-logging
        ] with-variable
    ] keep ;

: server-running? ( threaded-server -- ? )
    server-stopped>> [ value>> not ] [ f ] if* ;

: stop-server ( threaded-server -- )
    dup server-running? [
        [ remove-running-server ]
        [
            [
                [ secure-context>> [ &dispose drop ] when* ]
                [ [ f ] change-servers drop dispose-each ] bi
            ] with-destructors
        ]
        [ server-stopped>> raise-flag ] tri
    ] [
        drop
