https://kotlinlang.org logo
#coroutines
Title
# coroutines
r

rrva

08/26/2020, 9:06 PM
can I combine kotlinx.coroutines.sync.Semaphore.acquire and kotlinx.coroutines.withTimeout ?
Copy code
import kotlinx.coroutines.sync.Semaphore
import kotlinx.coroutines.withTimeout

private val concurrentRequests = Semaphore(50)

suspend fun foo() {
    withTimeout(10) {
        concurrentRequests.acquire()
    }
    try {
        doStuff()
    } finally {
        concurrentRequests.release()
    }
}
o

octylFractal

08/26/2020, 9:06 PM
what do you mean by that? haven't you already done so here?
r

rrva

08/26/2020, 9:12 PM
I guess my question was: “kotlinx.coroutines.sync.Semaphore.acquire suspends until a permit is available. Is wrapping that inside withTimeout a valid way of waiting until a permit is available or the timeout is reached, whichever comes first, or is that code racy in some way in the sense that it is possible to acquire a permit AND receive a timeout in the same coroutine?”
o

octylFractal

08/26/2020, 9:15 PM
I do not believe so, either
acquire()
does not see cancellation and successfully returns (and in that case withTimeout will not throw); OR
acquire()
sees the cancellation from timeout and will not acquire the semaphore
of note is this internal comment:
Copy code
* If timeout is exceeded, but withTimeout() block was not suspended, we would like to return block value,
     * not a timeout exception.
l

louiscad

08/27/2020, 6:47 AM
You can combine them that way, yes.
r

rrva

08/27/2020, 9:38 AM
thanks