1 /*
2 * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
813 strlen(getenv("_AWT_IGNORE_XKB")) > 0) {
814 if (XkbIgnoreExtension(True)) {
815 printf("Ignoring XKB.\n");
816 }
817 }
818
819 dpy = awt_display = XOpenDisplay(NULL);
820 #ifdef NETSCAPE
821 sigprocmask(SIG_SETMASK, &oldset, NULL);
822 #endif
823 if (!dpy) {
824 jio_snprintf(errmsg,
825 sizeof(errmsg),
826 "Can't connect to X11 window server using '%s' as the value of the DISPLAY variable.",
827 (getenv("DISPLAY") == NULL) ? ":0.0" : getenv("DISPLAY"));
828 JNU_ThrowInternalError(env, errmsg);
829 return NULL;
830 }
831
832 XSetIOErrorHandler(xioerror_handler);
833
834 /* set awt_numScreens, and whether or not we're using Xinerama */
835 xineramaInit();
836
837 if (!usingXinerama) {
838 awt_numScreens = XScreenCount(awt_display);
839 }
840
841 DTRACE_PRINTLN1("allocating %i screens\n", awt_numScreens);
842 /* Allocate screen data structure array */
843 x11Screens = calloc(awt_numScreens, sizeof(AwtScreenData));
844 if (x11Screens == NULL) {
845 JNU_ThrowOutOfMemoryError((JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2),
846 NULL);
847 return NULL;
848 }
849
850 for (i = 0; i < awt_numScreens; i++) {
851 if (usingXinerama) {
852 /* All Xinerama screens use the same X11 root for now */
959
960 /*
961 * Class: sun_awt_X11GraphicsDevice
962 * Method: getDisplay
963 * Signature: ()J
964 */
965 JNIEXPORT jlong JNICALL
966 Java_sun_awt_X11GraphicsDevice_getDisplay(JNIEnv *env, jobject this)
967 {
968 #ifdef HEADLESS
969 return NULL;
970 #else
971 return ptr_to_jlong(awt_display);
972 #endif /* !HEADLESS */
973 }
974
975 #ifdef MITSHM
976
977 static jint canUseShmExt = UNSET_MITSHM;
978 static jint canUseShmExtPixmaps = UNSET_MITSHM;
979 static jboolean xshmAttachFailed = JNI_FALSE;
980
981 extern int mitShmPermissionMask;
982
983 int J2DXErrHandler(Display *display, XErrorEvent *xerr) {
984 int ret = 0;
985 if (xerr->minor_code == X_ShmAttach) {
986 xshmAttachFailed = JNI_TRUE;
987 } else {
988 ret = (*xerror_saved_handler)(display, xerr);
989 }
990 return ret;
991 }
992 jboolean isXShmAttachFailed() {
993 return xshmAttachFailed;
994 }
995 void resetXShmAttachFailed() {
996 xshmAttachFailed = JNI_FALSE;
997 }
998
999 void TryInitMITShm(JNIEnv *env, jint *shmExt, jint *shmPixmaps) {
1000 XShmSegmentInfo shminfo;
1001 int XShmMajor, XShmMinor;
1002 int a, b, c;
1003
1004 AWT_LOCK();
1005 if (canUseShmExt != UNSET_MITSHM) {
1006 *shmExt = canUseShmExt;
1007 *shmPixmaps = canUseShmExtPixmaps;
1008 AWT_UNLOCK();
1009 return;
1010 }
1011
1012 *shmExt = canUseShmExt = CANT_USE_MITSHM;
1013 *shmPixmaps = canUseShmExtPixmaps = CANT_USE_MITSHM;
1014
1015 /**
1016 * XShmQueryExtension returns False in remote server case.
1017 * Unfortunately it also returns True in ssh case, so
1018 * we need to test that we can actually do XShmAttach.
1019 */
1020 if (XShmQueryExtension(awt_display)) {
1021 shminfo.shmid = shmget(IPC_PRIVATE, 0x10000,
1022 IPC_CREAT|mitShmPermissionMask);
1023 if (shminfo.shmid < 0) {
1024 AWT_UNLOCK();
1025 J2dRlsTraceLn1(J2D_TRACE_ERROR,
1026 "TryInitMITShm: shmget has failed: %s",
1027 strerror(errno));
1028 return;
1029 }
1030 shminfo.shmaddr = (char *) shmat(shminfo.shmid, 0, 0);
1031 if (shminfo.shmaddr == ((char *) -1)) {
1032 shmctl(shminfo.shmid, IPC_RMID, 0);
1033 AWT_UNLOCK();
1034 J2dRlsTraceLn1(J2D_TRACE_ERROR,
1035 "TryInitMITShm: shmat has failed: %s",
1036 strerror(errno));
1037 return;
1038 }
1039 shminfo.readOnly = True;
1040
1041 resetXShmAttachFailed();
1042 /**
1043 * The J2DXErrHandler handler will set xshmAttachFailed
1044 * to JNI_TRUE if any Shm error has occured.
1045 */
1046 EXEC_WITH_XERROR_HANDLER(J2DXErrHandler,
1047 XShmAttach(awt_display, &shminfo));
1048
1049 /**
1050 * Get rid of the id now to reduce chances of leaking
1051 * system resources.
1052 */
1053 shmctl(shminfo.shmid, IPC_RMID, 0);
1054
1055 if (isXShmAttachFailed() == JNI_FALSE) {
1056 canUseShmExt = CAN_USE_MITSHM;
1057 /* check if we can use shared pixmaps */
1058 XShmQueryVersion(awt_display, &XShmMajor, &XShmMinor,
1059 (Bool*)&canUseShmExtPixmaps);
1060 canUseShmExtPixmaps = canUseShmExtPixmaps &&
1061 (XShmPixmapFormat(awt_display) == ZPixmap);
1062 XShmDetach(awt_display, &shminfo);
1063 }
1064 shmdt(shminfo.shmaddr);
1065 *shmExt = canUseShmExt;
1066 *shmPixmaps = canUseShmExtPixmaps;
1067 }
1068 AWT_UNLOCK();
1069 }
1070 #endif /* MITSHM */
1071
1072 /*
1073 * Class: sun_awt_X11GraphicsEnvironment
1074 * Method: checkShmExt
1075 * Signature: ()I
1076 */
1077 JNIEXPORT jint JNICALL
1078 Java_sun_awt_X11GraphicsEnvironment_checkShmExt(JNIEnv *env, jobject this)
1079 {
1080
1081 int shmExt = NOEXT_MITSHM, shmPixmaps;
1082 #ifdef MITSHM
1083 TryInitMITShm(env, &shmExt, &shmPixmaps);
1084 #endif
1085 return shmExt;
1086 }
1087
1088 /*
|
1 /*
2 * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation. Oracle designates this
8 * particular file as subject to the "Classpath" exception as provided
9 * by Oracle in the LICENSE file that accompanied this code.
10 *
11 * This code is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 * version 2 for more details (a copy is included in the LICENSE file that
15 * accompanied this code).
16 *
17 * You should have received a copy of the GNU General Public License version
18 * 2 along with this work; if not, write to the Free Software Foundation,
19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20 *
21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22 * or visit www.oracle.com if you need additional information or have any
813 strlen(getenv("_AWT_IGNORE_XKB")) > 0) {
814 if (XkbIgnoreExtension(True)) {
815 printf("Ignoring XKB.\n");
816 }
817 }
818
819 dpy = awt_display = XOpenDisplay(NULL);
820 #ifdef NETSCAPE
821 sigprocmask(SIG_SETMASK, &oldset, NULL);
822 #endif
823 if (!dpy) {
824 jio_snprintf(errmsg,
825 sizeof(errmsg),
826 "Can't connect to X11 window server using '%s' as the value of the DISPLAY variable.",
827 (getenv("DISPLAY") == NULL) ? ":0.0" : getenv("DISPLAY"));
828 JNU_ThrowInternalError(env, errmsg);
829 return NULL;
830 }
831
832 XSetIOErrorHandler(xioerror_handler);
833 JNU_CallStaticMethodByName(env, NULL, "sun/awt/X11/XErrorHandlerUtil", "init", "(J)V",
834 ptr_to_jlong(awt_display));
835
836 /* set awt_numScreens, and whether or not we're using Xinerama */
837 xineramaInit();
838
839 if (!usingXinerama) {
840 awt_numScreens = XScreenCount(awt_display);
841 }
842
843 DTRACE_PRINTLN1("allocating %i screens\n", awt_numScreens);
844 /* Allocate screen data structure array */
845 x11Screens = calloc(awt_numScreens, sizeof(AwtScreenData));
846 if (x11Screens == NULL) {
847 JNU_ThrowOutOfMemoryError((JNIEnv *)JNU_GetEnv(jvm, JNI_VERSION_1_2),
848 NULL);
849 return NULL;
850 }
851
852 for (i = 0; i < awt_numScreens; i++) {
853 if (usingXinerama) {
854 /* All Xinerama screens use the same X11 root for now */
961
962 /*
963 * Class: sun_awt_X11GraphicsDevice
964 * Method: getDisplay
965 * Signature: ()J
966 */
967 JNIEXPORT jlong JNICALL
968 Java_sun_awt_X11GraphicsDevice_getDisplay(JNIEnv *env, jobject this)
969 {
970 #ifdef HEADLESS
971 return NULL;
972 #else
973 return ptr_to_jlong(awt_display);
974 #endif /* !HEADLESS */
975 }
976
977 #ifdef MITSHM
978
979 static jint canUseShmExt = UNSET_MITSHM;
980 static jint canUseShmExtPixmaps = UNSET_MITSHM;
981
982 extern int mitShmPermissionMask;
983
984 void TryInitMITShm(JNIEnv *env, jint *shmExt, jint *shmPixmaps) {
985 XShmSegmentInfo shminfo;
986 int XShmMajor, XShmMinor;
987 int a, b, c;
988 jboolean xShmAttachResult;
989
990 AWT_LOCK();
991 if (canUseShmExt != UNSET_MITSHM) {
992 *shmExt = canUseShmExt;
993 *shmPixmaps = canUseShmExtPixmaps;
994 AWT_UNLOCK();
995 return;
996 }
997
998 *shmExt = canUseShmExt = CANT_USE_MITSHM;
999 *shmPixmaps = canUseShmExtPixmaps = CANT_USE_MITSHM;
1000
1001 /**
1002 * XShmQueryExtension returns False in remote server case.
1003 * Unfortunately it also returns True in ssh case, so
1004 * we need to test that we can actually do XShmAttach.
1005 */
1006 if (XShmQueryExtension(awt_display)) {
1007 shminfo.shmid = shmget(IPC_PRIVATE, 0x10000,
1008 IPC_CREAT|mitShmPermissionMask);
1009 if (shminfo.shmid < 0) {
1010 AWT_UNLOCK();
1011 J2dRlsTraceLn1(J2D_TRACE_ERROR,
1012 "TryInitMITShm: shmget has failed: %s",
1013 strerror(errno));
1014 return;
1015 }
1016 shminfo.shmaddr = (char *) shmat(shminfo.shmid, 0, 0);
1017 if (shminfo.shmaddr == ((char *) -1)) {
1018 shmctl(shminfo.shmid, IPC_RMID, 0);
1019 AWT_UNLOCK();
1020 J2dRlsTraceLn1(J2D_TRACE_ERROR,
1021 "TryInitMITShm: shmat has failed: %s",
1022 strerror(errno));
1023 return;
1024 }
1025 shminfo.readOnly = True;
1026
1027 xShmAttachResult = TryXShmAttach(env, awt_display, &shminfo);
1028 /**
1029 * Get rid of the id now to reduce chances of leaking
1030 * system resources.
1031 */
1032 shmctl(shminfo.shmid, IPC_RMID, 0);
1033
1034 if (xShmAttachResult == JNI_TRUE) {
1035 canUseShmExt = CAN_USE_MITSHM;
1036 /* check if we can use shared pixmaps */
1037 XShmQueryVersion(awt_display, &XShmMajor, &XShmMinor,
1038 (Bool*)&canUseShmExtPixmaps);
1039 canUseShmExtPixmaps = canUseShmExtPixmaps &&
1040 (XShmPixmapFormat(awt_display) == ZPixmap);
1041 XShmDetach(awt_display, &shminfo);
1042 }
1043 shmdt(shminfo.shmaddr);
1044 *shmExt = canUseShmExt;
1045 *shmPixmaps = canUseShmExtPixmaps;
1046 }
1047 AWT_UNLOCK();
1048 }
1049
1050 /*
1051 * Must be called with the acquired AWT lock.
1052 */
1053 jboolean TryXShmAttach(JNIEnv *env, Display *display, XShmSegmentInfo *shminfo) {
1054 jboolean errorOccurredFlag = JNI_FALSE;
1055 jobject errorHandlerRef;
1056
1057 /*
1058 * XShmAttachHandler will set its internal flag to JNI_TRUE, if any Shm error occurs.
1059 */
1060 EXEC_WITH_XERROR_HANDLER(env, "sun/awt/X11/XErrorHandler$XShmAttachHandler",
1061 "()Lsun/awt/X11/XErrorHandler$XShmAttachHandler;", JNI_TRUE,
1062 errorHandlerRef, errorOccurredFlag,
1063 XShmAttach(display, shminfo));
1064 return errorOccurredFlag == JNI_FALSE ? JNI_TRUE : JNI_FALSE;
1065 }
1066 #endif /* MITSHM */
1067
1068 /*
1069 * Class: sun_awt_X11GraphicsEnvironment
1070 * Method: checkShmExt
1071 * Signature: ()I
1072 */
1073 JNIEXPORT jint JNICALL
1074 Java_sun_awt_X11GraphicsEnvironment_checkShmExt(JNIEnv *env, jobject this)
1075 {
1076
1077 int shmExt = NOEXT_MITSHM, shmPixmaps;
1078 #ifdef MITSHM
1079 TryInitMITShm(env, &shmExt, &shmPixmaps);
1080 #endif
1081 return shmExt;
1082 }
1083
1084 /*
|