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

Dispatcher allocation can hang forever #2926

Closed
scf37 opened this issue Mar 29, 2022 · 10 comments
Closed

Dispatcher allocation can hang forever #2926

scf37 opened this issue Mar 29, 2022 · 10 comments

Comments

@scf37
Copy link

scf37 commented Mar 29, 2022

cats-effect 3.3.9
In my project, second unsafeRunSync always hangs. When reproducing on Scastie, it either passes or hangs on first unsafeRunSync.

import cats.effect.std.Dispatcher
import cats.effect.{Async, IO, Resource}
import cats.effect.unsafe.implicits.global

println(1)
Dispatcher[IO].map { _ =>
  println(2)
}.allocated.unsafeRunSync() // can hang here

println(3)
Dispatcher[IO].map { _ =>
println(4)  
}.allocated.unsafeRunSync() // or here

https://scastie.scala-lang.org/65NZvvNKQcGfd8okMNNQMA

@vasilmkd
Copy link
Member

Can you please test if this is happening in 3.3.8 or maybe some other version too? It would be nice to find out if this is a bug for some time (possibly since the beginning) or a regression in the latest release. Thanks!

@scf37
Copy link
Author

scf37 commented Mar 29, 2022

On Scastie I tested 3.0, 3.1, 3.2, 3.3.0, 3.3.9

@vasilmkd
Copy link
Member

Reminds me of scala/bug#9076.

@armanbilge
Copy link
Member

Yup, pretty sure it's this problem:
https://fs2.io/#/faq?id=why-does-stream-evaluation-sometimes-hang-in-the-repl

In versions of Scala between 2.12.0 and 2.13.1, stream programs that call unsafeRunSync or other blocking operations sometimes hang in the REPL. This is a result of Scala's lambda encoding and was tracked in SI-9076. The issue was fixed in Scala 2.13.2 (see scala/scala#8748).

@scf37
Copy link
Author

scf37 commented Mar 29, 2022

It fails on 2.13.8. Also, originally it hung up in large project combined with other Resource-s. All those unsafeRunSync-s are just to reproduce the bug.

(Un)fortunately, minimal example within sbt project works as expected.

@wjoel
Copy link
Contributor

wjoel commented Apr 4, 2022

It's not Dispatcher which is the problem, it's cats.effect.unsafe.implicits.global and .unsafeRunSync(). This can hang after printing 1:

import cats.effect.std.Dispatcher
import cats.effect.{Async, IO, Resource}
import cats.effect.unsafe.implicits.global

println(1)
IO.println("hello").unsafeRunSync()
Dispatcher[IO].map { _ =>
  println(2)
}.allocated.unsafeRunSync()

println(3)
Dispatcher[IO].map { _ =>
println(4)  
}.allocated.unsafeRunSync()

https://scastie.scala-lang.org/AdxtHcz9RN68WO43bmYJtQ

@djspiewak
Copy link
Member

Is there any way we can reproduce this using a def main? Scastie and all REPLs have weirdness associated with initialization which could be at play here.

@scf37
Copy link
Author

scf37 commented Apr 4, 2022

Probably can be 'fixed' by using the same implementation for IOApp and unsafeRunXYZ. Current situation of completely different implementations for seems to be identical tasks is weird.

@djspiewak
Copy link
Member

Current situation of completely different implementations for seems to be identical tasks is weird.

How so?

@djspiewak
Copy link
Member

Closing this for now. We really need a def main reproduction. Btw just in case anyone lands here from Google, replying to a subtle point quickly:

Probably can be 'fixed' by using the same implementation for IOApp and unsafeRunXYZ

We do, sort of. All the unsafeRun variants use unsafeRunFiber under the surface, which is the same thing IOApp uses. However, because IOApp has the (soft) guarantee that it controls the very beginning and very end of the program, it is able to provide a lot more functionality, including things like fiber dumps, the MainThread executor, more deterministic fatal error reporting, Ctrl-C handling, and more. For this reason, IOApp#main will never be able to directly delegate to unsafeRunSync, and they already share as much of their implementations as is possible.

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

No branches or pull requests

5 participants