480 * The goal of this function is to find all "system" fonts which
481 * are needed by the JRE to display text in supported locales etc, and
482 * to support APIs which allow users to enumerate all system fonts and use
483 * them from their Java applications.
484 * The preferred mechanism is now using the new "fontconfig" library
485 * This exists on newer versions of Linux and Solaris (S10 and above)
486 * The library is dynamically located. The results are merged with
487 * a set of "known" locations and with the X11 font path, if running in
488 * a local X11 environment.
489 * The hardwired paths are built into the JDK binary so as new font locations
490 * are created on a host plaform for them to be located by the JRE they will
491 * need to be added ito the host's font configuration database, typically
492 * /etc/fonts/local.conf, and to ensure that directory contains a fonts.dir
493 * NB: Fontconfig also depends heavily for performance on the host O/S
494 * maintaining up to date caches.
495 * This is consistent with the requirements of the desktop environments
496 * on these OSes.
497 * This also frees us from X11 APIs as JRE is required to function in
498 * a "headless" mode where there is no Xserver.
499 */
500 static char *getPlatformFontPathChars(JNIEnv *env, jboolean noType1) {
501
502 char **fcdirs = NULL, **x11dirs = NULL, **knowndirs = NULL, *path = NULL;
503
504 /* As of 1.5 we try to use fontconfig on both Solaris and Linux.
505 * If its not available NULL is returned.
506 */
507 fcdirs = getFontConfigLocations();
508
509 #if defined(__linux__)
510 knowndirs = fullLinuxFontPath;
511 #elif defined(__solaris__)
512 knowndirs = fullSolarisFontPath;
513 #elif defined(_AIX)
514 knowndirs = fullAixFontPath;
515 #endif
516 /* REMIND: this code requires to be executed when the GraphicsEnvironment
517 * is already initialised. That is always true, but if it were not so,
518 * this code could throw an exception and the fontpath would fail to
519 * be initialised.
520 */
521 #ifndef HEADLESS
522 #if defined(__linux__)
523 /* There's no headless build on linux ... */
524 if (!AWTIsHeadless()) { /* .. so need to call a function to check */
525 #endif
526 /* Using the X11 font path to locate font files is now a fallback
527 * useful only if fontconfig failed, or is incomplete. So we could
528 * remove this code completely and the consequences should be rare
529 * and non-fatal. If this happens, then the calling Java code can
530 * be modified to no longer require that the AWT lock (the X11GE)
531 * be initialised prior to calling this code.
532 */
533 AWT_LOCK();
534 if (isDisplayLocal(env)) {
535 x11dirs = getX11FontPath();
536 }
537 AWT_UNLOCK();
538 #if defined(__linux__)
539 }
540 #endif
541 #endif /* !HEADLESS */
542 path = mergePaths(fcdirs, x11dirs, knowndirs, noType1);
543 if (fcdirs != NULL) {
544 char **p = fcdirs;
545 while (*p != NULL) free(*p++);
546 free(fcdirs);
547 }
548
549 if (x11dirs != NULL) {
550 char **p = x11dirs;
551 while (*p != NULL) free(*p++);
552 free(x11dirs);
553 }
554
555 return path;
556 }
557
558 JNIEXPORT jstring JNICALL Java_sun_awt_X11FontManager_getFontPathNative
559 (JNIEnv *env, jobject thiz, jboolean noType1) {
560 jstring ret;
561 static char *ptr = NULL; /* retain result across calls */
562
563 if (ptr == NULL) {
564 ptr = getPlatformFontPathChars(env, noType1);
565 }
566 ret = (*env)->NewStringUTF(env, ptr);
567 return ret;
568 }
569
570 #include <dlfcn.h>
571
572 #include "fontconfig.h"
573
574
575 static void* openFontConfig() {
576
577 char *homeEnv;
578 static char *homeEnvStr = "HOME="; /* must be static */
579 void* libfontconfig = NULL;
580 #ifdef __solaris__
581 #define SYSINFOBUFSZ 8
582 char sysinfobuf[SYSINFOBUFSZ];
583 #endif
584
|
480 * The goal of this function is to find all "system" fonts which
481 * are needed by the JRE to display text in supported locales etc, and
482 * to support APIs which allow users to enumerate all system fonts and use
483 * them from their Java applications.
484 * The preferred mechanism is now using the new "fontconfig" library
485 * This exists on newer versions of Linux and Solaris (S10 and above)
486 * The library is dynamically located. The results are merged with
487 * a set of "known" locations and with the X11 font path, if running in
488 * a local X11 environment.
489 * The hardwired paths are built into the JDK binary so as new font locations
490 * are created on a host plaform for them to be located by the JRE they will
491 * need to be added ito the host's font configuration database, typically
492 * /etc/fonts/local.conf, and to ensure that directory contains a fonts.dir
493 * NB: Fontconfig also depends heavily for performance on the host O/S
494 * maintaining up to date caches.
495 * This is consistent with the requirements of the desktop environments
496 * on these OSes.
497 * This also frees us from X11 APIs as JRE is required to function in
498 * a "headless" mode where there is no Xserver.
499 */
500 static char *getPlatformFontPathChars(JNIEnv *env, jboolean noType1, jboolean isX11) {
501
502 char **fcdirs = NULL, **x11dirs = NULL, **knowndirs = NULL, *path = NULL;
503
504 /* As of 1.5 we try to use fontconfig on both Solaris and Linux.
505 * If its not available NULL is returned.
506 */
507 fcdirs = getFontConfigLocations();
508
509 #if defined(__linux__)
510 knowndirs = fullLinuxFontPath;
511 #elif defined(__solaris__)
512 knowndirs = fullSolarisFontPath;
513 #elif defined(_AIX)
514 knowndirs = fullAixFontPath;
515 #endif
516 /* REMIND: this code requires to be executed when the GraphicsEnvironment
517 * is already initialised. That is always true, but if it were not so,
518 * this code could throw an exception and the fontpath would fail to
519 * be initialised.
520 */
521 #ifndef HEADLESS
522 if (isX11) { // The following only works in an x11 environment.
523 #if defined(__linux__)
524 /* There's no headless build on linux ... */
525 if (!AWTIsHeadless()) { /* .. so need to call a function to check */
526 #endif
527 /* Using the X11 font path to locate font files is now a fallback
528 * useful only if fontconfig failed, or is incomplete. So we could
529 * remove this code completely and the consequences should be rare
530 * and non-fatal. If this happens, then the calling Java code can
531 * be modified to no longer require that the AWT lock (the X11GE)
532 * be initialised prior to calling this code.
533 */
534 AWT_LOCK();
535 if (isDisplayLocal(env)) {
536 x11dirs = getX11FontPath();
537 }
538 AWT_UNLOCK();
539 #if defined(__linux__)
540 }
541 #endif
542 }
543 #endif /* !HEADLESS */
544 path = mergePaths(fcdirs, x11dirs, knowndirs, noType1);
545 if (fcdirs != NULL) {
546 char **p = fcdirs;
547 while (*p != NULL) free(*p++);
548 free(fcdirs);
549 }
550
551 if (x11dirs != NULL) {
552 char **p = x11dirs;
553 while (*p != NULL) free(*p++);
554 free(x11dirs);
555 }
556
557 return path;
558 }
559
560 JNIEXPORT jstring JNICALL Java_sun_awt_FcFontManager_getFontPathNative
561 (JNIEnv *env, jobject thiz, jboolean noType1, jboolean isX11) {
562 jstring ret;
563 static char *ptr = NULL; /* retain result across calls */
564
565 if (ptr == NULL) {
566 ptr = getPlatformFontPathChars(env, noType1, isX11);
567 }
568 ret = (*env)->NewStringUTF(env, ptr);
569 return ret;
570 }
571
572 #include <dlfcn.h>
573
574 #include "fontconfig.h"
575
576
577 static void* openFontConfig() {
578
579 char *homeEnv;
580 static char *homeEnvStr = "HOME="; /* must be static */
581 void* libfontconfig = NULL;
582 #ifdef __solaris__
583 #define SYSINFOBUFSZ 8
584 char sysinfobuf[SYSINFOBUFSZ];
585 #endif
586
|