Time.kt uses Duration.toMillis in unsafe manner
See original GitHub issueUsing Duration.ofSeconds(Long.MAX_VALUE)
as the timeout argument for kotlinx.coroutines.withTimeout
will cause an ArithmaticOverflowException
This is because, in pure java Durations.ofSeconds(Long.MAX_VALUE).toMillis()
will cause an Arithmatic overflow.
I’ve got a fix that basically involves adding an extension function toMillisOrMax
that returns Long.MAX_VALUE
when toMillis
would otherwise overflow.
Use case:
I’m a big fan of null objects, and the way I’ve structured things is such that the “default” timeout is Duration.of(seconds = Long.MAX_VALUE, nanos = 999__999_999)
(which is effectively Duration.MAX_VALUE
), such that our down-stack code need not consider the case where no timeout is specified.
If you guys are interested in this fix I’ll submit a pull request to that involves simply:
private fun Duration.toMillisOrMax(): Long = when(this.seconds) {
in 0L .. (Long.MAX_VALUE / MILLIS_PER_SECOND) -> duration.toMillis()
else -> Long.MAX_VALUE
}
as a function in TimeKt
, invoked instead of Duration.toMillis()
Issue Analytics
- State:
- Created 5 years ago
- Comments:9 (6 by maintainers)
I simple workaround is to avoid time check at all if the duration exceed a large number.
So if the duration is greater than a century (example) then the code is executed without any timeout (this avoid some system calls and related work).
Obviously. But I tried to migrate some java only code to common from ktor websockets (it has only java part now). One of the blockers was java.time package. That’s why I think about migration from platform-specific to universal code in every project