Sunny
Sunny

Reputation: 2332

Why does this goroutine block?

This goroutine blocks...

go log.Fatal(http.ListenAndServe(":8000", nil))
log.Print("This doesn't print")

This goroutine doesn't block...

go func() {
    log.Fatal(http.ListenAndServe(":8000", nil))
}()
log.Print("This prints")

This goroutine also doesn't block...

go http.ListenAndServe(":8000", nil)
log.Print("This prints")

Upvotes: 2

Views: 1546

Answers (3)

jfly
jfly

Reputation: 8010

go log.Fatal(http.ListenAndServe(":8000", nil)) is equivalent to

e := http.ListenAndServe(":8000", nil)
go log.Fatal(e)

of course it blocks. As to
go func() { log.Fatal(http.ListenAndServe(":8000", nil)) }()

it starts the execution of function as an independent goroutine. Then you call log.Print("This prints"), as a logger can be used simultaneously from multiple goroutines, so it prints.

Upvotes: 2

Danilo
Danilo

Reputation: 3327

This is according to the spec:

The function value and parameters are evaluated as usual in the calling goroutine

https://golang.org/ref/spec#Go_statements

In

go log.Fatal(http.ListenAndServe(":8000", nil))

The first parameter is

http.ListenAndServe(":8000", nil)

which will be evaluated before executing the function log.Fatal as a goroutine, thus blocking.

Upvotes: 6

mylk
mylk

Reputation: 21

Hmm, I ran program:

package main

import (
    "net/http"
    "log"
)

func main() {
    go log.Fatal(http.ListenAndServe(":8000", nil))
    log.Print("This doesn't print")
}

And it seems to work well:

curl 127.0.0.1:8000 -v
* Rebuilt URL to: 127.0.0.1:8000/
*   Trying 127.0.0.1...
* TCP_NODELAY set
* Connected to 127.0.0.1 (127.0.0.1) port 8000 (#0)
> GET / HTTP/1.1
> Host: 127.0.0.1:8000
> User-Agent: curl/7.51.0
> Accept: */*
> 
< HTTP/1.1 404 Not Found
< Content-Type: text/plain; charset=utf-8
< X-Content-Type-Options: nosniff
< Date: Fri, 24 Feb 2017 08:22:19 GMT
< Content-Length: 19
< 
404 page not found
* Curl_http_done: called premature == 0
* Connection #0 to host 127.0.0.1 left intact

My go version:

go1.7.3 darwin/amd64

Please specify more information about your runtime, like go version, architecture etc.

Upvotes: -2

Related Questions