konsoletyper / teavm

Compiles Java bytecode to JavaScript, WebAssembly and C
https://teavm.org
Apache License 2.0
2.55k stars 260 forks source link

Implement (minimal) SecureRandom #881

Closed tryone144 closed 5 months ago

tryone144 commented 5 months ago

Introduce a minimal working implementation of java.security.SecureRandom that uses getRandomValues() from the WebCrypto API when available. Otherwise and on non-supported platforms it falls back to the "normal insecure" random generator from java.util.Random.

The WASM backend would need a reference to the WebCrypto API in the JS runtime, the C backend could employ platform specific generators like /dev/urandom on UNIX-like systems or a random generator from the Win32 API. Both are not implemented yet.

Furthermore, this implementation does not support the SPI framework with different JCE providers. I am not sure, whether adding JCE support and putting the "native" implementation into an SPI is worth the effort in the current stage.

This PR also changes up java.util.Random to directly tap into the existing random() implementation of java.lang.Math. This reduces the duplicated code between both classes, as the resulting implementation is identical.

konsoletyper commented 5 months ago

I'm just curious, what's your use case? Are you using TeaVM on production, or just playing with it? Any plans for production use?

tryone144 commented 5 months ago

I am in the process of porting a custom language interpreter written in Java to our e-learning platform CrypTool-Online. So kind of production. I've already got a minimal proof-of-concept working and now back-porting my changes that might benefit others. :wink:

The language itself is pseudo-code inspired for building and playing with cryptographic algorithms in a style that is closely related to the notation used in papers. We want this interpreter for an interactive code-editor / playground.

This use-case doesn't strictly require cryptographically secure randomness, but we would like to use "the best" that is available for didactic purposes. The interpreter was originally developed to run on desktop platforms where this was/is less of a problem.

I had put some though into "properly" supporting the SPI design and potentially allowing the import of the bouncycastle library. But this is neither in the current scope of our project nor did that library appear to be easily integrated into TeaVM.

We also use some cryptographic primitives (e.g. AES) that are normally also dynamically provided via the JCE. For these I've just added a small wrapper around a JS library, a minimal CryptoProvider JSO interface, and written a similarly minimal implementation for javax.crypto.Cipher and related classes. Due to the dependency on an external library (crypto-browserify in this case), I don't think this is easily added to the TeaVM core.

konsoletyper commented 5 months ago

I see, very interesting. I'd track your progress with this project and perhaps assist where possible.

I had put some though into "properly" supporting the SPI design

I can help you with this. In AOT compiler it's a bit tricky. I'd suggest looking into how ServiceProvider is implemented, with the exception that for this part I think some sort of filtering necessary. Rationale: consider you have a JAR file in compile class path, which provides multiple algorithms, of which user wants one; in this case filtering should save some JS size.

easily integrated into TeaVM

What exactly are the problems with bouncycastle? Lots of synchronization primitives?

Anyway, I wish you luck with your project and don't hesitate to reach me directly with your questions.