graal icon indicating copy to clipboard operation
graal copied to clipboard

[GR-54159] Fontconfig head is null, check your fonts or fonts configuration

Open zgmgt opened this issue 1 year ago • 5 comments

Describe GraalVM and your environment :

  • GraalVM version or commit id if built from source: [Oracle GraalVM 22.0.1+8.1 (build 22.0.1+8-jvmci-b01)]
  • CE or EE: [CE]
  • JDK version: [21]
  • OS and OS Version: [Debian12.5]
  • Architecture: [amd64]
  • The output of java -Xinternalversion:
 Java HotSpot(TM) 64-Bit Server VM (22.0.1+8-jvmci-b01) for linux-amd64 JRE (22.0.1+8-jvmci-b01), built on 2024-03-14T00:30:39Z by "buildslave" with gcc 13.2.0

Describe the issue I have a simple swing program that uses native-image to generate an executable file. I found that something went wrong when it was run. The error message was "Caused by: java.lang.RuntimeException: Fontconfig head is null, check your fonts or fonts configuration"

Code snippet or code repository that reproduces the issue

package org.example;
import java.awt.*;
import javax.swing.*;
public class SwingSample {
    public static void main(String[] args) throws Exception {
        if (System.getProperty("rrr","").equals("")) {
            System.setProperty("java.home",".");
        }
        SwingUtilities.invokeAndWait(() -> {
            JFrame frame = new JFrame("Hello World");
            JButton button = new JButton("Hello");
            button.addActionListener(e -> {
                System.out.printf("Hello, World!%n");
            });
            JPanel panel = new JPanel(new FlowLayout());
            panel.add(button);
            frame.add(panel);
            frame.setSize(400, 300);
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.setVisible(true);
        });
    }
}


<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>org.example</groupId>
    <artifactId>jdk21graalvm</artifactId>
    <version>1.0-SNAPSHOT</version>
    <properties>
        <maven.compiler.source>21</maven.compiler.source>
        <maven.compiler.target>21</maven.compiler.target>
    </properties>
    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-shade-plugin</artifactId>
                <executions>
                    <execution>
                        <phase>package</phase>
                        <goals>
                            <goal>shade</goal>
                        </goals>
                        <configuration>
                            <transformers>
                                <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                                    <mainClass>org.example.SwingSample</mainClass>
                                </transformer>
                            </transformers>
                        </configuration>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>

Steps to reproduce the issue

  1. mvn clean package
  2. java -Drrr=123 -agentlib:native-image-agent=config-output-dir=./cdir -jar jdk21graalvm-1.0-SNAPSHOT.jar
  3. native-image -jar jdk21graalvm-1.0-SNAPSHOT.jar -H:+ReportExceptionStackTraces --no-fallback --link-at-build-time -H:ConfigurationFileDirectories=./cdir -H:+AddAllCharsets --report-unsupported-elements-at-runtime --enable-url-protocols=https,http

After the build is completed, the following exception occurs when executing it

Exception in thread "main" java.lang.reflect.InvocationTargetException
        at [email protected]/java.awt.EventQueue.invokeAndWait(EventQueue.java:1371)
        at [email protected]/java.awt.EventQueue.invokeAndWait(EventQueue.java:1346)
        at [email protected]/javax.swing.SwingUtilities.invokeAndWait(SwingUtilities.java:1480)
        at org.example.SwingSample.main(SwingSample.java:9)
        at [email protected]/java.lang.invoke.LambdaForm$DMH/sa346b79c.invokeStaticInit(LambdaForm$DMH)
Caused by: java.lang.RuntimeException: Fontconfig head is null, check your fonts or fonts configuration
        at [email protected]/sun.awt.FontConfiguration.getVersion(FontConfiguration.java:1263)
        at [email protected]/sun.awt.FontConfiguration.readFontConfigFile(FontConfiguration.java:221)
        at [email protected]/sun.awt.FontConfiguration.init(FontConfiguration.java:105)
        at [email protected]/sun.awt.X11FontManager.createFontConfiguration(X11FontManager.java:696)
        at [email protected]/sun.font.SunFontManager$2.run(SunFontManager.java:352)
        at [email protected]/sun.font.SunFontManager$2.run(SunFontManager.java:309)
        at [email protected]/java.security.AccessController.executePrivileged(AccessController.java:128)
        at [email protected]/java.security.AccessController.doPrivileged(AccessController.java:319)
        at [email protected]/sun.font.SunFontManager.<init>(SunFontManager.java:309)
        at [email protected]/sun.awt.FcFontManager.<init>(FcFontManager.java:35)
        at [email protected]/sun.awt.X11FontManager.<init>(X11FontManager.java:55)
        at [email protected]/sun.font.PlatformFontInfo.createFontManager(PlatformFontInfo.java:37)
        at [email protected]/sun.font.FontManagerFactory.getInstance(FontManagerFactory.java:51)
        at [email protected]/sun.font.SunFontManager.getInstance(SunFontManager.java:242)
        at [email protected]/sun.font.FontDesignMetrics.getMetrics(FontDesignMetrics.java:260)
        at [email protected]/sun.swing.SwingUtilities2.getFontMetrics(SwingUtilities2.java:1242)
        at [email protected]/javax.swing.JComponent.getFontMetrics(JComponent.java:1700)
        at [email protected]/javax.swing.plaf.basic.BasicGraphicsUtils.getPreferredButtonSize(BasicGraphicsUtils.java:360)
        at [email protected]/javax.swing.plaf.basic.BasicButtonUI.getPreferredSize(BasicButtonUI.java:542)
        at [email protected]/javax.swing.JComponent.getPreferredSize(JComponent.java:1734)
        at [email protected]/java.awt.FlowLayout.layoutContainer(FlowLayout.java:612)
        at [email protected]/java.awt.Container.layout(Container.java:1541)
        at [email protected]/java.awt.Container.doLayout(Container.java:1530)
        at [email protected]/java.awt.Container.validateTree(Container.java:1725)
        at [email protected]/java.awt.Container.validateTree(Container.java:1734)
        at [email protected]/java.awt.Container.validateTree(Container.java:1734)
        at [email protected]/java.awt.Container.validateTree(Container.java:1734)
        at [email protected]/java.awt.Container.validateTree(Container.java:1734)
        at [email protected]/java.awt.Container.validate(Container.java:1660)
        at [email protected]/java.awt.Container.validateUnconditionally(Container.java:1697)
        at [email protected]/java.awt.Window.show(Window.java:1055)
        at [email protected]/java.awt.Component.show(Component.java:1728)
        at [email protected]/java.awt.Component.setVisible(Component.java:1675)
        at [email protected]/java.awt.Window.setVisible(Window.java:1036)
        at com.zgm.SwingSample.lambda$main$1(SwingSample.java:34)
        at [email protected]/java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:308)
        at [email protected]/java.awt.EventQueue.dispatchEventImpl(EventQueue.java:773)
        at [email protected]/java.awt.EventQueue$4.run(EventQueue.java:720)
        at [email protected]/java.awt.EventQueue$4.run(EventQueue.java:714)
        at [email protected]/java.security.AccessController.executePrivileged(AccessController.java:128)
        at [email protected]/java.security.AccessController.doPrivileged(AccessController.java:400)
        at [email protected]/java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:87)
        at [email protected]/java.awt.EventQueue.dispatchEvent(EventQueue.java:742)
        at [email protected]/java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:203)
        at [email protected]/java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:124)
        at [email protected]/java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:113)
        at [email protected]/java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:109)
        at [email protected]/java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
        at [email protected]/java.awt.EventDispatchThread.run(EventDispatchThread.java:90)
        at org.graalvm.nativeimage.builder/com.oracle.svm.core.thread.PlatformThreads.threadStartRoutine(PlatformThreads.java:853)
        at org.graalvm.nativeimage.builder/com.oracle.svm.core.thread.PlatformThreads.threadStartRoutine(PlatformThreads.java:829)

zgmgt avatar May 09 '24 07:05 zgmgt

Hi @zgmgt, thank you for reaching out to us!

I am trying to reproduce the issue but I am getting a different error. Could you please share with me the full pom file you're using? Thank you!

selhagani avatar May 09 '24 14:05 selhagani

Hi @zgmgt, thank you for reaching out to us!

I am trying to reproduce the issue but I am getting a different error. Could you please share with me the full pom file you're using? Thank you!

Hi @selhagani ,thank you for your reply. The attachment is my project file jdk21graalvm.zip

zgmgt avatar May 09 '24 14:05 zgmgt

Hey @zgmgt, Unfortunately, I can't download the project directly due to our internal policy. Would you mind uploading it to a public GitHub repository and sharing the link with me? Thank you!

selhagani avatar May 09 '24 14:05 selhagani

Hey @zgmgt, Unfortunately, I can't download the project directly due to our internal policy. Would you mind uploading it to a public GitHub repository and sharing the link with me? Thank you!

Hey @selhagani . Okay, I'll just paste them out, just two files.

SwingSample.java

package org.example;
import java.awt.*;
import javax.swing.*;
public class SwingSample {
    public static void main(String[] args) throws Exception {
        if (System.getProperty("rrr","").equals("")) {
            System.setProperty("java.home",".");
        }
        System.getProperties().list(System.out);
        SwingUtilities.invokeAndWait(() -> {
            JFrame frame = new JFrame("Hello World");
            JButton button = new JButton("Hello");
            button.addActionListener(e -> {
                System.out.printf("Hello, World!%n");
            });
            JPanel panel = new JPanel(new FlowLayout());
            panel.add(button);
            frame.add(panel);
            frame.setSize(400, 300);
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.setVisible(true);
        });
    }
}
pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>org.example</groupId>
    <artifactId>jdk21graalvm</artifactId>
    <version>1.0-SNAPSHOT</version>
    <properties>
        <maven.compiler.source>21</maven.compiler.source>
        <maven.compiler.target>21</maven.compiler.target>
    </properties>
    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-shade-plugin</artifactId>
                <executions>
                    <execution>
                        <phase>package</phase>
                        <goals>
                            <goal>shade</goal>
                        </goals>
                        <configuration>
                            <transformers>
                                <transformer implementation="org.apache.maven.plugins.shade.resource.ManifestResourceTransformer">
                                    <mainClass>org.example.SwingSample</mainClass>
                                </transformer>
                            </transformers>
                        </configuration>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>
</project>

zgmgt avatar May 09 '24 14:05 zgmgt

Hi @zgmgt, I wanted to share a helpful update regarding the issue you're facing. When I used the latest version of GraalVM CE which can be found here and I removed this part from the code: if (System.getProperty("rrr","").equals("")) { System.setProperty("java.home","."); } Then I ran the command mvn clean package Followed up by java -agentlib:native-image-agent=config-output-dir=./cdir -jar jdk21graalvm-1.0-SNAPSHOT.jar then I used this command to generate the native image: native-image -jar jdk21graalvm-1.0-SNAPSHOT.jar -H:+ReportExceptionStackTraces --no-fallback --link-at-build-time -H:ConfigurationFileDirectories=./cdir -H:+AddAllCharsets --report-unsupported-elements-at-runtime --enable-url-protocols=https,http -Djava.awt.headless=false and then I ran the native image using the following command ./jdk21graalvm-1.0-SNAPSHOT -Djava.home=/home/soufiane/Downloads/graalvm-community-openjdk-22.0.1+8.1

Then it worked correctly.

The issue is attributed to how some AWT/Swing classes are loading required properties from the JVM at runtime by invoking the system.getProperty("java.home") which is not available to native images at runtime.

selhagani avatar May 20 '24 09:05 selhagani