JDK-8097121 : Replace sun.misc.BASE64* with java.util.Base64
  • Type: Bug
  • Component: javafx
  • Sub-Component: other
  • Affected Version: 8
  • Priority: P3
  • Status: Resolved
  • Resolution: Fixed
  • Submitted: 2015-01-16
  • Updated: 2025-11-03
  • Resolved: 2015-02-18
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 8
8u60Fixed
Related Reports
Cloners :  
Relates :  
Description
JavaFX is using the following internal base64 classes from sun.misc:

sun.misc.BASE64Decoder
sun.misc.BASE64Encoder

These can and should be replaced by using the public java.util.Base64 class. This will be required for JDK 9 when the module system is enabled, but is a good bit of cleanup for 8, so I will target this for 8u60.
Comments
Web changes: http://hg.openjdk.java.net/openjfx/8u-dev/rt/rev/e02e66310dec
18-02-2015

The fix and the test look fine to me, thanks!
18-02-2015

Looks clean to me. +1
17-02-2015

I'm finally getting back to this one. Here is the updated webrev. The only code change is in the readFully method where I implemented the suggestion to avoid the copy in the case of a full buffer (and I tested that code path as well). I also confirmed that converting an image to a dataURL still works correctly, and added a unit test. http://cr.openjdk.java.net/~kcr/RT-39826/webrev.01/
17-02-2015

Ok, thanks for the details. I just thought that the MIME version you used in your fix corresponds to sun.misc.BASE64Encoder().
11-02-2015

* The equivalent of sun.misc.BASE64Encoder() and sun.misc.BASE64Decoder() is Base64.getMimeEncoder() and Base64.getMimeDecoder() respectively. I verified this by looking at the code and by running tests. Danno confirmed that the packager changes are OK because they weren't relying on the line-splitting behavior of MIME encoder/decoder. It's possible that the web code doesn't rely on it either, but the safest thing to do is to use the MIME versions, since they produce identical results to what is there now. * Thanks for the hint on testing the PrismImage#toDataURL method. I will try it and also see if I can create a unit test from it. * Good suggestion on readFully. I will do that and send out a new webrev.
11-02-2015

I noticed that in http://cr.openjdk.java.net/~shemnon/RT-39826/webrev.00 the Utils.getBase64Encoded() public method replaces BASE64Encoder with Base64.getEncoder(). The former, according to its javadoc, implements the MIME specification, but the latter implements the basic specification. There's a difference in that MIME specifies a line length in the output char sequence. Thus, the changed method will produce another result. Does it matter for this particular method? PrismImage.toDataURL implements the corresponding canvas API method: https://developer.mozilla.org/en-US/docs/Web/API/HTMLCanvasElement.toDataURL It can be tested with WebLauncher on this page: http://www.w3schools.com/html/tryit.asp?filename=tryhtml5_canvas_first It's enough to add the following two lines to the script on the page: var dataURL = c.toDataURL(); document.body.innerHTML=dataURL; and it then will output the result into the right tab. We don't have a unit test, right... Your fix looks fine to me. However, I'm thinking of improving the following code chunk: + final byte[] buffer = new byte[4096]; + + while (true) { + int nBytes = in.read(buffer); + if (nBytes < 0) break; + byte[] chunk = new byte[nBytes]; + System.arraycopy(buffer, 0, chunk, 0, nBytes); + outList.add(chunk); + outSize += nBytes; + } Can we allocate the "chunk" array as new byte[4096], then read into it and then add it to the list, in case it's full. Only in case it's not full, another array of the appropriate size is allocated and arraycopy is called. Seems like in this way we will avoid redundant allocations and arraycopy. What do you think? (At the same time the encoded sequence will rather be less than 4096 bytes in this method, so the improvement might be irrelevant.)
11-02-2015

Anton: please review the web changes for Base64: http://cr.openjdk.java.net/~kcr/RT-39826/webrev.00/ I have tested two of the three paths (WebEngine#setUserStyleSheetLocation and DataURLConnection constructor), and verified that they produce the same results as before. There is no unit test for PrismImage.toDataURL and running a simple web viewer and browsing to various sites does not exercise that code path. It is the simplest change, so I am tempted to just push the change with your review, but I note that this is a hole in our testing.
10-02-2015

Packager changes: http://hg.openjdk.java.net/openjfx/8u-dev/rt/rev/613aeb121d49
23-01-2015

Go ahead and push the packager changes. We'll leave this bug open until the web changes are pushed.
23-01-2015

Here's a webrev for the packager stuff: http://cr.openjdk.java.net/~shemnon/RT-39826/webrev.00/ Should I just commit it or are you going to aggregate the fixes into one push?
23-01-2015

Here are the classes that use sun.misc.BASE64* classes: modules/fxpackager/src/main/java/com/javafx/main/Main.java modules/fxpackager/src/main/java/com/oracle/tools/packager/mac/MacDmgBundler.java modules/fxpackager/src/main/java/com/sun/javafx/tools/ant/Utils.java modules/web/src/android/java/javafx/scene/web/WebEngine.java modules/web/src/main/java/com/sun/javafx/webkit/prism/PrismImage.java modules/web/src/main/java/com/sun/webkit/network/data/DataURLConnection.java modules/web/src/main/java/javafx/scene/web/WebEngine.java
16-01-2015